Show button rows in rich messages

Task: 2026/07/27/show-block-button-rows-in-rich-messages
This commit is contained in:
John Preston
2026-07-30 07:25:50 +04:00
parent ec688d566d
commit 45493fdfb1
35 changed files with 1704 additions and 219 deletions

View File

@@ -54,8 +54,7 @@ namespace {
void SendBotCallbackData(
not_null<Window::SessionController*> controller,
not_null<HistoryItem*> item,
int row,
int column,
BotButtonLookup lookup,
std::optional<Core::CloudPasswordResult> password,
Fn<void()> done = nullptr,
Fn<void(const QString &)> handleError = nullptr) {
@@ -68,10 +67,7 @@ void SendBotCallbackData(
const auto api = &session->api();
const auto bot = item->getMessageBot();
const auto fullId = item->fullId();
const auto getButton = [=] {
return HistoryMessageMarkupButton::Get(owner, fullId, row, column);
};
const auto button = getButton();
const auto button = lookup();
if (!button || button->requestId) {
return;
}
@@ -117,7 +113,7 @@ void SendBotCallbackData(
if (!item) {
return;
}
if (const auto button = getButton()) {
if (const auto button = lookup()) {
button->requestId = 0;
owner->requestItemRepaint(item);
}
@@ -169,7 +165,7 @@ void SendBotCallbackData(
return;
}
// Show error?
if (const auto button = getButton()) {
if (const auto button = lookup()) {
button->requestId = 0;
owner->requestItemRepaint(item);
}
@@ -208,16 +204,14 @@ void HideSingleUseKeyboard(
void SendBotCallbackData(
not_null<Window::SessionController*> controller,
not_null<HistoryItem*> item,
int row,
int column) {
SendBotCallbackData(controller, item, row, column, std::nullopt);
BotButtonLookup lookup) {
SendBotCallbackData(controller, item, std::move(lookup), std::nullopt);
}
void SendBotCallbackDataWithPassword(
not_null<Window::SessionController*> controller,
not_null<HistoryItem*> item,
int row,
int column) {
BotButtonLookup lookup) {
if (!item->isRegular()) {
return;
}
@@ -226,21 +220,13 @@ void SendBotCallbackDataWithPassword(
const auto owner = &history->owner();
const auto api = &session->api();
const auto fullId = item->fullId();
const auto getButton = [=] {
return HistoryMessageMarkupButton::Get(
owner,
fullId,
row,
column);
};
const auto button = getButton();
if (!button || button->requestId) {
if (const auto button = lookup(); !button || button->requestId) {
return;
}
api->cloudPassword().reload();
const auto weak = base::make_weak(controller);
const auto show = controller->uiShow();
SendBotCallbackData(controller, item, row, column, {}, {}, [=](
SendBotCallbackData(controller, item, lookup, {}, {}, [=](
const QString &error) {
auto box = PrePasswordErrorBox(
error,
@@ -252,7 +238,9 @@ void SendBotCallbackDataWithPassword(
show->showBox(std::move(box), Ui::LayerOption::CloseOther);
} else {
auto lifetime = std::make_shared<rpl::lifetime>();
button->requestId = -1;
if (const auto button = lookup()) {
button->requestId = -1;
}
api->cloudPassword().state(
) | rpl::take(
1
@@ -260,7 +248,7 @@ void SendBotCallbackDataWithPassword(
if (lifetime) {
base::take(lifetime)->destroy();
}
if (const auto button = getButton()) {
if (const auto button = lookup()) {
if (button->requestId == -1) {
button->requestId = 0;
}
@@ -275,7 +263,7 @@ void SendBotCallbackDataWithPassword(
fields.customCheckCallback = [=](
const Core::CloudPasswordResult &result,
base::weak_qptr<PasscodeBox> box) {
if (const auto button = getButton()) {
if (const auto button = lookup()) {
if (button->requestId) {
return;
}
@@ -287,15 +275,21 @@ void SendBotCallbackDataWithPassword(
if (!strongController) {
return;
}
SendBotCallbackData(strongController, item, row, column, result, [=] {
if (box) {
box->closeBox();
}
}, [=](const QString &error) {
if (box) {
box->handleCustomCheckError(error);
}
});
SendBotCallbackData(
strongController,
item,
lookup,
result,
[=] {
if (box) {
box->closeBox();
}
},
[=](const QString &error) {
if (box) {
box->handleCustomCheckError(error);
}
});
}
};
auto object = Box<PasscodeBox>(session, fields);
@@ -316,7 +310,7 @@ bool SwitchInlineBotButtonReceived(
samePeerReplyTo);
}
void ActivateBotCommand(ClickHandlerContext context, int row, int column) {
void ActivateBotButton(ClickHandlerContext context, BotButtonLookup lookup) {
const auto strong = context.sessionWindow.get();
if (!strong) {
return;
@@ -326,11 +320,7 @@ void ActivateBotCommand(ClickHandlerContext context, int row, int column) {
if (!item) {
return;
}
const auto button = HistoryMessageMarkupButton::Get(
&item->history()->owner(),
item->fullId(),
row,
column);
const auto button = lookup();
if (!button) {
return;
}
@@ -353,11 +343,11 @@ void ActivateBotCommand(ClickHandlerContext context, int row, int column) {
case ButtonType::Callback:
case ButtonType::Game: {
SendBotCallbackData(controller, item, row, column);
SendBotCallbackData(controller, item, lookup);
} break;
case ButtonType::CallbackWithPassword: {
SendBotCallbackDataWithPassword(controller, item, row, column);
SendBotCallbackDataWithPassword(controller, item, lookup);
} break;
case ButtonType::Buy: {
@@ -514,7 +504,7 @@ void ActivateBotCommand(ClickHandlerContext context, int row, int column) {
} break;
case ButtonType::Auth:
UrlAuthBox::ActivateButton(controller->uiShow(), item, row, column);
UrlAuthBox::ActivateButton(controller->uiShow(), item, lookup);
break;
case ButtonType::UserProfile: {
@@ -636,4 +626,16 @@ void ActivateBotCommand(ClickHandlerContext context, int row, int column) {
}
}
void ActivateBotCommand(ClickHandlerContext context, int row, int column) {
const auto strong = context.sessionWindow.get();
if (!strong) {
return;
}
const auto owner = &strong->session().data();
const auto itemId = context.itemId;
ActivateBotButton(context, [=] {
return HistoryMessageMarkupButton::Get(owner, itemId, row, column);
});
}
} // namespace Api