MainButton и BackButton: нативные элементы Telegram Подключишь нативную MainButton внизу экрана и BackButton в шапке Mini App.
Нативные кнопки Telegram
MainButton — кнопка в нижней панели клиента Telegram (над системной областью). BackButton — кнопка «назад» в шапке WebView. Обе рисует Telegram, не твой DOM: они выглядят нативно и не перекрываются твоим CSS случайно.
С Bot API 7.10+ у нижней панели также есть Secondary Button; в большинстве туториалов достаточно MainButton + BackButton.
MainButton для подтверждения, BackButton для навигации
typescript
Копировать// Telegram WebApp API (MainButton / BackButton), script: telegram-web-app.js
type WebApp = {
MainButton : {
text : string ;
isVisible : boolean ;
isActive : boolean ;
setText : ( text : string ) => WebApp [ "MainButton" ];
show : () => WebApp [ "MainButton" ];
hide : () => WebApp [ "MainButton" ];
enable : () => WebApp [ "MainButton" ];
disable : () => WebApp [ "MainButton" ];
showProgress : ( leaveActive ?: boolean ) => WebApp [ "MainButton" ];
hideProgress : () => WebApp [ "MainButton" ];
onClick : ( cb : () => void ) => WebApp [ "MainButton" ];
offClick : ( cb : () => void ) => WebApp [ "MainButton" ];
setParams : ( params : {
text ?: string ;
color ?: string ;
text_color ?: string ;
is_active ?: boolean ;
is_visible ?: boolean ;
}) => WebApp [ "MainButton" ];
};
BackButton : {
isVisible : boolean ;
show : () => WebApp [ "BackButton" ];
hide : () => WebApp [ "BackButton" ];
onClick : ( cb : () => void ) => WebApp [ "BackButton" ];
offClick : ( cb : () => void ) => WebApp [ "BackButton" ];
};
ready : () => void ;
HapticFeedback : {
impactOccurred : ( style : "light" | "medium" | "heavy" | "rigid" | "soft" ) => void ;
};
};
const tg = window.Telegram.WebApp as unknown as WebApp ;
tg. ready ();
function goToScreen ( screen : "list" | "details" ) {
if (screen === "details" ) {
tg.BackButton. show ();
tg.MainButton. setParams ({
text: "Подтвердить" ,
is_visible: true ,
is_active: true ,
});
} else {
tg.BackButton. hide ();
tg.MainButton. hide ();
}
}
const onMain = () => {
tg.MainButton. showProgress ();
// отправка формы / вызов API
void submitOrder ()
. then (() => {
tg.HapticFeedback. impactOccurred ( "medium" );
goToScreen ( "list" );
})
. finally (() => {
tg.MainButton. hideProgress ();
});
};
const onBack = () => {
goToScreen ( "list" );
};
tg.MainButton. onClick (onMain);
tg.BackButton. onClick (onBack);
goToScreen ( "details" );
async function submitOrder () : Promise < void > {
await fetch ( "/api/order" , { method: "POST" });
}
Как это работает
MainButton.setParams / setText + show — текст и видимость нижней кнопки.
onClick — обработчик нажатия (альтернатива: WebApp.onEvent('mainButtonClicked', ...)).
showProgress / hideProgress — спиннер на кнопке на время async-операции.
BackButton.show() — появляется стрелка назад в хедере Telegram; по умолчанию скрыта.
Свой HTML-footer дублировать не нужно — нативная кнопка уже занимает нижнюю зону.
Частые ошибки
Рисуешь свою sticky-кнопку поверх MainButton → двойной UI и конфликты с safe-area. Для главного CTA используй MainButton.
Не снимаешь onClick при размонтировании (SPA) → утечки обработчиков. В React — offClick в cleanup useEffect.
Ждёшь BackButton на корневом экране → она для «внутренних» экранов. На корне обычно hide().
Что дальше
НазадinitData: проверка подлинности пользователя на бэкенде Далее Тема оформления mini-app под клиент Telegram Материалы gramdocs.tech носят образовательный характер и не являются финансовой, юридической или инвестиционной рекомендацией. Работа с блокчейном TON и токеном Gram связана с рисками потери средств. Правовая информация
На этой странице