diff --git a/MiniApp/Cafe.cs b/MiniApp/Cafe.cs new file mode 100644 index 0000000..a1cd433 --- /dev/null +++ b/MiniApp/Cafe.cs @@ -0,0 +1,44 @@ +using System.Text.Json; +using Telegram.Bot; +using Telegram.Bot.Types.Payments; + +#pragma warning disable CA1305, IDE0059, IDE1006 + +internal static class Cafe +{ + internal record OrderItem(int id, int count); + internal record FoodItem(string name, string descr, double price, string img, string png, string tgs); + + internal static FoodItem[] FoodItems = JsonSerializer.Deserialize(File.ReadAllText("wwwroot/cafe.json"))!; + + internal static async Task OnCafeApi(TelegramBotClient bot, IConfiguration config, IFormCollection form) + { + var query = AuthHelpers.ParseValidateData(form["_auth"], config["BotToken"]!); + var orderData = JsonSerializer.Deserialize(form["order_data"]!)!; + if (form["method"] != "makeOrder" || form["invoice"] != "1") + return new { ok = false, error = "only Invoice mode is implemented" }; + string payload = ""; + var prices = new List(); + foreach (var orderItem in orderData) + { + payload += $"{orderItem.id}:{orderItem.count} "; + var foodItem = FoodItems[orderItem.id]; + prices.Add(new($"{foodItem.name} x{orderItem.count}", (int)(foodItem.price * orderItem.count * 100))); + } + return new + { + ok = true, + invoice_url = await bot.CreateInvoiceLinkAsync("Order #12345678", "Perfect lunch from Durger King", + payload.ToString(), config["PaymentProviderToken"], "USD", prices, needName: true, needPhoneNumber: true, needShippingAddress: true) + }; + } + + internal static string? OnPreCheckoutQuery(PreCheckoutQuery pcq) + { + int total_amount = 0; // recompute total price to be sure + foreach (var orderItem in pcq.InvoicePayload.Split()) + if (orderItem.Split(':') is [var id, var count]) + total_amount += (int)(FoodItems[int.Parse(id)].price * int.Parse(count) * 100); + return total_amount == pcq.TotalAmount ? null : "incorrect payment"; + } +} diff --git a/MiniApp/Pages/Index.cshtml b/MiniApp/Pages/Index.cshtml index 5d09a15..878657f 100644 --- a/MiniApp/Pages/Index.cshtml +++ b/MiniApp/Pages/Index.cshtml @@ -8,3 +8,6 @@

Welcome

This is your typical ASP.NET Core Razor example website.

+

We also included a

+

• the demo Webapp

+

• a clone of DurgerKingBot

diff --git a/MiniApp/Pages/cafe.cshtml b/MiniApp/Pages/cafe.cshtml new file mode 100644 index 0000000..6d46f51 --- /dev/null +++ b/MiniApp/Pages/cafe.cshtml @@ -0,0 +1,97 @@ +@page +@using System.Globalization +@{Layout = null;} + + + + + DurgerKingBot + + + + + + + + + + + +
+@{int id = 0;} +@foreach (var item in Cafe.FoodItems) +{ +
+
1
+
+ + + + + +
+
+ @item.name + $@item.price.ToString("0.00", CultureInfo.InvariantCulture) +
+
+ + +
+
+} +
+
+
+
+
+

Your Order

+ Edit +
+
+@{id = 0;} +@foreach (var item in Cafe.FoodItems) +{ +
+
+ + + + +
+
+
@item.name 1x
+
@item.descr
+
+
$@item.price.ToString("0.00", CultureInfo.InvariantCulture)
+
+} +
+
+
+ +
+ Any special requests, details, final wishes etc. +
+
+
+
+
+
+ + + + + + diff --git a/MiniApp/Pages/demo.cshtml b/MiniApp/Pages/demo.cshtml new file mode 100644 index 0000000..7a2684a --- /dev/null +++ b/MiniApp/Pages/demo.cshtml @@ -0,0 +1,297 @@ +@page +@{Layout = null;} + + + + + + + + + + + + + + + + + +
+ + + + + + + + + +
+ +
Header:
+
Background:
+
+
+ +

Test links:

+ + + +

Test permissions:

+ +

Test alerts:

+ +

Haptics:

+ +

Cloud storage:

+
+ + + + + + + + + + + + + + + + +
KeyValue
+ + +
+
+

Biometrics:

+
+ +
+
+
+ Data passed to webview. + Checking hash... +
+
+
+ Theme params +
+
+ Version: , + platform: +
+
+
+
+ + + + + + + diff --git a/MiniApp/Program.cs b/MiniApp/Program.cs index 5aca1d4..b86f40c 100644 --- a/MiniApp/Program.cs +++ b/MiniApp/Program.cs @@ -1,3 +1,6 @@ +using Microsoft.AspNetCore.Mvc; +using Microsoft.AspNetCore.StaticFiles; +using System.Text.Json; using Telegram.Bot; using Telegram.Bot.Types; using Telegram.Bot.Types.ReplyMarkups; @@ -22,7 +25,9 @@ } app.UseHttpsRedirection(); -app.UseStaticFiles(); + +var provider = new FileExtensionContentTypeProvider() { Mappings = { [".tgs"] = "application/x-tgsticker" } }; +app.UseStaticFiles(new StaticFileOptions { ContentTypeProvider = provider }); app.UseRouting(); @@ -33,6 +38,9 @@ // Bot entrypoints: app.MapGet("/bot/setWebhook", async (TelegramBotClient bot) => { await bot.SetWebhookAsync(webappUrl + "/bot"); return $"Webhook set to {webappUrl}/bot"; }); app.MapPost("/bot", OnUpdate); +// WebAppDemo & DurgerKing backend: (their AJAX don't use XSRF antiforgery but we validate Telegram Data anyway) +app.MapPost("/cafe/api", Cafe.OnCafeApi).DisableAntiforgery(); +app.MapPost("/demo/api", OnDemoApi).DisableAntiforgery(); app.Run(); @@ -42,10 +50,38 @@ async void OnUpdate(TelegramBotClient bot, Update update, ILogger logge switch (update) { case { Message.Text: "/start" }: - await bot.SendTextMessageAsync(update.Message.Chat, "Let's get started", + await bot.SendTextMessageAsync(update.Message.Chat, "Let's get started\n\nTry our Razor Webapp or order your perfect lunch! 🍟", parseMode: Telegram.Bot.Types.Enums.ParseMode.Html, replyMarkup: (InlineKeyboardMarkup)InlineKeyboardButton.WithWebApp("Launch Mini-App", webappUrl)); break; + case { PreCheckoutQuery: { } pcq }: + await bot.AnswerPreCheckoutQueryAsync(pcq.Id, Cafe.OnPreCheckoutQuery(pcq)); + break; + case { Message.SuccessfulPayment: { } sp }: + await bot.SendTextMessageAsync(update.Message.Chat, "Thank you for your 'payment'! Don't worry, your imaginary credit card was not charged. Your order is not on the way."); + break; + case { Message.WebAppData: { } wad }: + logger.LogInformation("Received WebAppData: {Data} | button {ButtonText}", wad.Data, wad.ButtonText); + break; default: break; } } + +async Task OnDemoApi(TelegramBotClient bot, IConfiguration config, [FromForm] string method, IFormCollection form) +{ + var query = AuthHelpers.ParseValidateData(form["_auth"], config["BotToken"]!); + switch (method) + { + case "checkInitData": + return new { ok = true }; + case "sendMessage": + string? msg_id = form["msg_id"], with_webview = form["with_webview"]; + var user = JsonSerializer.Deserialize(query["user"], JsonBotAPI.Options)!; + await bot.SendTextMessageAsync(user.Id, "Hello, World!", + replyMarkup: with_webview == "0" ? new ReplyKeyboardRemove() : + new ReplyKeyboardMarkup(true).AddButton(KeyboardButton.WithWebApp("Open WebApp", webappUrl + "/demo"))); + return new { response = new { ok = true } }; + default: + return new { ok = false, error = "Unsupported method: " + method }; + } +} diff --git a/MiniApp/README.md b/MiniApp/README.md index f0382fb..b0e80fc 100644 --- a/MiniApp/README.md +++ b/MiniApp/README.md @@ -6,3 +6,25 @@ Minimal changes were made: - Program.cs: for the bot webhook and starting the example website as a Telegram Mini-App - _Layout.cshtml: importing required telegram-web-app.js +----- + +Now we also included the WebAppDemo and DurgerKingBot example bot +(in demo.cshtml, cafe.cshtml, Cafe.cs and some wwwroot static files) + +## WebAppDemo & DurgerKingBot examples + +Static data imported from official WebApps: +- https://webappcontent.telegram.org/cafe +- https://webappcontent.telegram.org/demo + +Server-side code reconstructed from above, and adapted from: +- https://github.com/arynyklas/DurgerKingBot +- https://github.com/telegram-bot-php/durger-king + +## Notes + +For DurgerKing to serve invoices, you will need to set a "PaymentProviderToken" in appsettings.json +_(typically from [Stripe in TEST mode](https://telegrambots.github.io/book/4/payments.html))_ + +Sending WebAppData to bot (button "Send time to bot") works only when opening the webapp via a ReplyKeyboardButton +_(try using the second "Hello World!" button)_ diff --git a/MiniApp/wwwroot/cafe.json b/MiniApp/wwwroot/cafe.json new file mode 100644 index 0000000..89103ca --- /dev/null +++ b/MiniApp/wwwroot/cafe.json @@ -0,0 +1,98 @@ +[ + { + "name": "Burger", + "descr": "Meat™", + "price": 4.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjY4LDQ5OWMtNTEtMi0xMDYtMS0xNTMtMjItMjgtMTItMzktNDAtNDItNjgsMC00LDMtNywxLTEwLTUtNi0xNiwzLTEzLTE0LDItMTEsMTItMTQsMTEtMjcsMC0yLTUtMTItNS0xNiwwLTYsNS0xNyw0LTIyLTItNy05LTUtNi0xNSwzLTEwLDE0LTcsMTktMTMsNy0xMi0xNC0yNC0xNy0zMy0zLTEyLTEtMjgsMi0zOSwyOC0xMDEsMTQ4LTEzMywyMzktMTE1LDY0LDEzLDEzMCw1OSwxNDIsMTI3LDMsMTgsMCwzMi0xNSw0Mi0xLDEtMTEsMTMtNywxNiw0LDIsMjAsNCwyMiw5LDYsMTAtNywxNS05LDIyLTEsMywzLDExLDMsMTYsMCwyLTMsMTctMiwxOSwyLDIsOCwxLDEwLDQsMyw1LDQsMTYsNiwyMiw0LDEzLTE1LDIwLTE5LDI3LTksMjAsNSw0MC0yMyw2MC00MCwyOC0xMDEsMjktMTQ4LDMweiIvPjwvc3ZnPg==", + "png": "/img/cafe/Burger_148.png", + "tgs": "/img/cafe/Burger.tgs" + }, + { + "name": "Fries", + "descr": "Po-ta-toes", + "price": 1.49, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjUwLDQ3OGMtNTcsMS04OC00LTEzNS0zNi01LTQtNS0yOS01LTM1LTEwLTY5LTE5LTEzOS0yNi0yMDktMy0yOSwxNC0xMSwzMi0zMiw3Mi04NCwxOTQtODcsMjcxLTgsNCw1LDEwLDE1LDE2LDE4LDEsMSwyNCw0LDI0LDUsNywyMS0xNiwxNjctMjEsMTk4LTEsMTEtMSw1Ni05LDYyLTUzLDM4LTg2LDM4LTE0NywzN3oiLz48L3N2Zz4=", + "png": "/img/cafe/Fries_148.png", + "tgs": "/img/cafe/Fries.tgs" + }, + { + "name": "Hotdog", + "descr": "0% dog, 100% hot", + "price": 3.49, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMzIwLDQ4N2MtNTgtMi0xMTAtNDAtMTUyLTc4LTU1LTQ4LTIyMC0yMzQtMTA1LTI5NCwxMS02LTEtNzcsNjUtNjcsNiwxLDI1LDgsMzEsMTIsMSwxLDIsOCwzLDksMTAsMywyMCwxLDMwLDYsNTIsMjUsODYsMTAyLDEzMCwxNDMsMzYsMzYsMTAwLDY0LDEyNywxMDQsMTIsMTgsNSwzNSwxMCw1Myw1LDE5LDE0LDMwLDQsNTEtMjQsNDktNjgsMTUtNzYsMTktNSwzLTQsMTAtNywxNC0xNCwyMC0zNywyOC02MCwyOHoiLz48L3N2Zz4=", + "png": "/img/cafe/Hotdog_148.png", + "tgs": "/img/cafe/Hotdog.tgs" + }, + { + "name": "Taco", + "descr": "Mucho más", + "price": 3.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMTE1LDQ3MmMtNjYsMi04Ny03NS05MC0xMjctNi0xMjEsNzMtMjYxLDE5Ni0yODksNDItMTAsODktNSwxMjgsMTYsOSw1LDE3LDE2LDI3LDIwLDE4LDgsMzksNCw1OCwxNSw0MiwyNiw2Nyw5Miw1MiwxNDAtMTIsMzktMTM4LDEwMC0xNzQsMTIwLTQyLDI1LTE1NSwxMDMtMTk4LDEwNXoiLz48L3N2Zz4=", + "png": "/img/cafe/Tako_148.png", + "tgs": "/img/cafe/Tako.tgs" + }, + { + "name": "Pizza", + "descr": "That’s amore", + "price": 7.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMzc2LDQ4NGMtMzUtOC04NC0zOC0xMTAtNjMtMS0xLDEtNCwwLTUtNy0xMS0yMC0yMi0zMC0yOS01My00My0xMDAtOTItMTUyLTEzNy0xOS0xNi00OS04LTU5LTQxLTctMjIsMjQtNDcsMzctNjAsNzEtNzEsMTcwLTExNiwyNzAtMTI0LDE2LTEsNTEtNiw2NCw2LDIxLDIxLDEsNTMsMSw3NCwzLDY4LDMsMTM1LDEsMjAzLDEsMzAsMiwxNjMtMjIsMTc2eiIvPjwvc3ZnPg==", + "png": "/img/cafe/Pizza_148.png", + "tgs": "/img/cafe/Pizza.tgs" + }, + { + "name": "Donut", + "descr": "Hole included", + "price": 1.49, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjYxLDQ3OWMtNjYsMi0xMzItMTktMTc4LTY2LTc0LTc1LTgzLTIyNi05LTMwNCw2OS03MSwxODktOTAsMjgwLTU2LDg4LDM0LDEzOCwxMDUsMTMzLDIwMC04LDEzOS04MCwyMjQtMjI2LDIyNnoiLz48L3N2Zz4=", + "png": "/img/cafe/Donut_148.png", + "tgs": "/img/cafe/Donut.tgs" + }, + { + "name": "Popcorn", + "descr": "Lights, camera, corn", + "price": 1.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjg4LDQ5N2MtMTUsMi0xNDYtNC0xNDktMTAtNy0xNi05LTM2LTEzLTUzLTEyLTUxLTIyLTEwMy0zMS0xNTQtNC0xNy0xNC00Ni05LTYyLDMtMTEsMTYtMTUsMTctMjQsMS04LTItMTQsNC0yMCw1LTUsMTctMTQsMjEtMjAsMS00LDAtOCwwLTEyLDAtMywzNy00MywzOS00Myw3LTMsMTMsMiwxOSwyLDQsMCw0LTgsOC05LDMtMiw4LTEsMTEtMywxNC01LDMwLTMwLDQ0LTI3LDcsMSwxMywyMCwxNSwxOSwxMS0yLDE3LTksMjktMywzLDEsNSw1LDgsNiwyMiwyLDExLTYsMjksMTUsNiw3LDE3LDMsMjMsMTAsNyw2LDEsMTQsNCwxOSwxLDEsMTEsNCwxNCw2LDksMTAsMTQsMzAsMTcsNDIsMSwxLDcsMiw4LDIsNiw0LDYsMTAsOSwxNCwyLDIsNywxLDEwLDYsOSwxOS0yMCwxMjMtMjYsMTQ5LTMsMTgtMTYsMTEwLTI2LDExOS0xMCw5LTMwLDI3LTQzLDMxLTksMi0yMiwwLTMyLDB6Ii8+PC9zdmc+", + "png": "/img/cafe/Popcorn_148.png", + "tgs": "/img/cafe/Popcorn.tgs" + }, + { + "name": "Coke", + "descr": "The liquid kind", + "price": 1.49, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjQ4LDUwNWMtODYsMC03OC00Ny04NS0xMTMtMi0yMC05LTE1Ny0xNS0xNjMtMTEtMTItMTItNy0xMC0yNiwwLTQsMS05LDMtMTIsMTYtMTYsOTMtMTgsOTUtMjEsNi05LTMtMjksMi00MCw4LTE2LDEwMi00MCwxMTAtMjcsMjAsMjktNzMsMjktODUsNDAtMiwyLTMsMjUtMSwyNywxNSwxMSw4OC02LDk2LDIyLDEwLDMxLTcsMjEtOSwzNy0yLDIxLTMsNDItNSw2NC0zLDI5LTgsMTczLTIyLDE4OC0xOSwxOS00OSwyNC03NCwyNHoiLz48L3N2Zz4=", + "png": "/img/cafe/Coke_148.png", + "tgs": "/img/cafe/Coke.tgs" + }, + { + "name": "Cake", + "descr": "Bread substitute", + "price": 10.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNOTIsNDcyYy0zLDAtMTAsMS0xMy0yLTEwLTEyLTctOTQtOS0xMTQtMi0yMC0xOC0xMzgtOC0xNDgsMjktMjksNzgtNDYsMTE1LTY0LDIyLTExLDE2LTMwLDI5LTUwLDE2LTI0LDI4LTEyLDQ1LTIwLDEsMCwxLTEwLDQtMTIsNS00LDE3LDEzLDIxLDE1LDIsMSwyLTQsMy02LDEtMSw5LTksMTItNiw3LDgsMywxOCw3LDI1LDMsNSwyNyw3LDIxLDIwLTIsMywyNSwxMiwzMiwxNSwyNSwxMSw1MSwyMyw3NSwzNiwxNiw5LDM1LDE3LDQ3LDMyLDMxLDQwLDE1LDEyMSw5LDE2OC0yLDExLTIsNDctMTQsNTMtMzYsMTctMTI1LDIzLTE2NywzMC02OCwxMC0xNDAsMjgtMjA5LDI4eiIvPjwvc3ZnPg==", + "png": "/img/cafe/Cake_148.png", + "tgs": "/img/cafe/Cake.tgs" + }, + { + "name": "Icecream", + "descr": "Cone of shame", + "price": 5.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjU2LDQ4NGMtMTctMi00NSwzLTU5LTktMTAtOS0xNy05NS0xNi0xMDgsMS0yNi0xMC0xMi0xNC0yMy0yLTYsNy0xMSw2LTE1LTItNy0xOC0xOC0yMi0yNi00LTctNC0yMC04LTI3LTgtMTEtMjMtMTItMjctMjktOS0zNiwyNS0zMywzMi00MywxMC0xNS0yLTMxLDEtNDgsNS0zMiw0Ny0zOCw3MC01MiwxNS05LDI5LTMxLDEwLTQ0LTgtNS0xNS0yLTIzLTUtMjMtOCw0NC0xMiw0NC0xMiwzOCwwLDkxLDE5LDk2LDYzLDIsMjEtMTMsMzgtMyw1OCwxLDQsNywzLDEwLDUsMTgsMTMsMjEsMzIsMTIsNTAsMCwxLDEyLDcsMTMsNyw3LDUsMTYsMTYsMTUsMjYtMiwxNy0yMiwxNC0yNywyNi00LDEwLTUsMjEtMTIsMzItMyw1LTE3LDE0LTE5LDE5LDEsMyw4LDksNywxNC0xLDYtMTAsMy0xMiw2LTQsOCwxLDE5LTEsMjctMiwxMi0xMyw5NS0yMSwxMDAtMTQsOC0zNyw3LTUyLDh6Ii8+PC9zdmc+", + "png": "/img/cafe/Icecream_148.png", + "tgs": "/img/cafe/Icecream.tgs" + }, + { + "name": "Cookie", + "descr": "Milk’s favorite", + "price": 3.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjY5LDQ0MmMtNTIsMC0xMTMtMTUtMTUzLTQ5LTE2OS0xNDMsMzItMzkyLDIyMC0zMTcsMTk2LDc5LDEzOCwzNjEtNjcsMzY2eiIvPjwvc3ZnPg==", + "png": "/img/cafe/Cookie_148.png", + "tgs": "/img/cafe/Cookie.tgs" + }, + { + "name": "Flan", + "descr": "Flan-tastic", + "price": 7.99, + "img": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB2aWV3Qm94PSIwIDAgNTEyIDUxMiI+PGRlZnM+PGxpbmVhckdyYWRpZW50IGlkPSJnIiB4MT0iLTMwMCUiIHgyPSItMjAwJSIgeTE9IjAiIHkyPSIwIj48c3RvcCBvZmZzZXQ9Ii0xMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48c3RvcCBvZmZzZXQ9IjMwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjcwJSIgc3RvcC1vcGFjaXR5PSIuMDciLz48c3RvcCBvZmZzZXQ9IjExMCUiIHN0b3Atb3BhY2l0eT0iLjEiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MSIgZnJvbT0iLTMwMCUiIHRvPSIxMjAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48YW5pbWF0ZSBhdHRyaWJ1dGVOYW1lPSJ4MiIgZnJvbT0iLTIwMCUiIHRvPSIxMzAwJSIgZHVyPSIzcyIgcmVwZWF0Q291bnQ9ImluZGVmaW5pdGUiLz48L2xpbmVhckdyYWRpZW50PjwvZGVmcz48cGF0aCBmaWxsPSJ1cmwoI2cpIiBkPSJNMjU0LDQzMWMtNjgtMS0xNDQtMTUtMTk1LTYzLTUyLTQ4LTUxLTExNSwyLTE2MywxOC0xNyw2NS0zNCw3NC00Miw4LTgsOS0yMSwxOS0yOSw0MC0zNiwxMjAtMzcsMTY5LTE5LDE2LDYsMzQsMTQsNDQsMjksNCw1LDQsMTMsOSwxOCw4LDksMzIsMTQsNDMsMjAsNDMsMjYsODMsNzEsNzEsMTI1LTIyLDk2LTE1MywxMjQtMjM3LDEyNHoiLz48L3N2Zz4=", + "png": "/img/cafe/Flan_148.png", + "tgs": "/img/cafe/Flan.tgs" + } +] diff --git a/MiniApp/wwwroot/css/cafe.css b/MiniApp/wwwroot/css/cafe.css new file mode 100644 index 0000000..8fdfaf1 --- /dev/null +++ b/MiniApp/wwwroot/css/cafe.css @@ -0,0 +1,610 @@ +body { + font-family: var(--default-font); + font-size: 13px; + line-height: 16px; + font-weight: 400; + background-color: var(--block-bg-color); + color: var(--text-color); + color-scheme: var(--tg-color-scheme); + margin: 0; + padding: 0; + width: 1px; + min-width: 100%; + + --default-font: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; + --block-bg-color: var(--tg-theme-bg-color); + --bg-color: var(--tg-theme-secondary-bg-color, #ebedf0); + --animation: .15s ease; + --page-animation-duration: .3s; + --page-animation: var(--page-animation-duration) ease; + --status-height: 48px; + --accent-color: #31b545; + --main-color: #f8a917; + --text-color: #222; + --page-hint-color: #83878a; + --hint-color: #74787a; + --placeholder-color: #999da1; + --ripple-duration: .45s; + --ripple-end-duration: .3s; + -webkit-user-select: none; + user-select: none; + cursor: default; +} +html.dark body { + --block-bg-color: var(--tg-theme-bg-color); + --bg-color: var(--tg-theme-secondary-bg-color, #0f0f0f); + --text-color: #fff; + --page-hint-color: #9b9ba1; + --hint-color: #64666d; + --placeholder-color: #5d6163; +} +body.order-mode { + background-color: var(--bg-color); +} + +* { + -webkit-tap-highlight-color: transparent; +} + +.cafe-page { + transition: filter var(--animation); +} +body.closed .cafe-page { + filter: grayscale(1) opacity(0.7); +} + +.cafe-block { + background-color: var(--block-bg-color); + -webkit-box-shadow: 0 0.5px rgba(0, 0, 0, .07); + box-shadow: 0 0.5px rgba(0, 0, 0, .07); +} + +.cafe-items { + display: flex; + flex-wrap: wrap; + margin: 0 auto; + max-width: 480px; + justify-content: space-around; + align-content: flex-end; + transition: max-height var(--page-animation), opacity var(--page-animation); + background-color: var(--block-bg-color); +} +body.order-mode .cafe-items { + max-height: 0 !important; + opacity: 0 !important; +} +.cafe-items:after { + content: ''; + flex-grow: 2; +} +.cafe-item, +.cafe-item-shadow { + position: relative; + width: 120px; + height: 159px; + padding: 4px 5px 21px; + box-sizing: border-box; + text-align: center; +} +.cafe-item-shadow { + height: 0; + padding: 0; + margin: 0; +} +.stars-only, +.stars-supported .no-stars-only { + display: none; +} +.stars-supported .stars-only { + display: block; +} + +.cafe-item-photo { + position: relative; + height: 78px; +} +.cafe-item-photo .cafe-item-emoji { + font-size: 70px; + line-height: 78px; +} +.cafe-item-lottie { + display: inline-block; + vertical-align: top; + position: relative; + margin: 0 auto; +} +.cafe-item-photo .cafe-item-lottie { + width: 74px; +} +.cafe-item-lottie:before { + content: ''; + display: block; + padding-top: 100%; +} +.cafe-item-lottie img, +.cafe-item-lottie canvas { + position: absolute; + top: 0; bottom: 0; + left: 0; right: 0; + width: 100%; + height: 100%; +} +.cafe-item-new { + position: absolute; + right: 50%; + bottom: 10px; + margin-right: -40px; + display: inline-block; + font-family: var(--default-font); + font-weight: 500; + font-size: 11px; + line-height: 14px; + padding: 2px 5px; + border-radius: 4px; + box-sizing: border-box; + background-color: var(--accent-color); + text-transform: uppercase; + color: #fff; + outline: none; + border: none; +} +.cafe-item-label { + display: flex; + justify-content: center; +} +.cafe-item-title { + font-weight: 500; +} +.cafe-item-price { + font-weight: 700; + white-space: nowrap; +} +.cafe-item-price:before { + display: inline-block; + vertical-align: top; + content: ''; + width: 2px; + height: 2px; + border-radius: 2px; + background-color: currentColor; + margin: 7px 4px; +} +.cafe-item-buttons { + display: flex; + width: 80px; + justify-content: space-between; + margin: 10px auto 0; + position: relative; + transition: all var(--animation); +} +button { + cursor: pointer; +} +button, +.cafe-item-counter { + display: inline-block; + font-family: var(--default-font); + font-weight: 700; + font-size: 14px; + line-height: 18px; + padding: 6px 16px; + height: 30px; + border-radius: 7px; + box-sizing: border-box; + background-color: var(--main-color); + text-transform: uppercase; + color: #fff; + outline: none; + border: none; +} +.cafe-item-counter { + position: absolute; + right: 0; + top: 0; + min-width: 22px; + height: 22px; + padding: 2px 6px; + margin: 4px 6px; + border-radius: 11px; + transform: scale3d(0, 0, 1); + animation: var(--animation) both; + pointer-events: none; + z-index: 3; +} +.cafe-item-buy-button { + position: absolute !important; + background-color: var(--accent-color); + top: 0; + right: 0; + transition: width var(--animation); + width: 80px; +} +.cafe-item-incr-button { + position: absolute !important; + top: 0; + right: 0; + transition: width var(--animation); + width: 80px; +} +.selected .cafe-item-incr-button { + width: 38px; +} +.cafe-item-decr-button { + position: relative; + width: 38px; +} +.cafe-item-decr-button { + background-color: #e64d44; + pointer-events: none; + transform: scale3d(0.9, 0.9, 1); + transition: transform var(--animation), visibility var(--animation); + visibility: hidden; +} +.selected .cafe-item-decr-button { + pointer-events: auto; + transform: scale3d(1, 1, 1); + visibility: visible; +} +.cafe-item-incr-button:before, +.cafe-item-incr-button:after, +.cafe-item-decr-button:before { + display: inline-block; + position: absolute; + content: ''; + left: 0; + right: 0; + top: 0; + bottom: 0; + margin: auto; + width: 14px; + height: 3px; + background-color: #fff; + border-radius: 1px; + z-index: 1; +} +.cafe-item-incr-button:before, +.cafe-item-incr-button:after { + background-color: rgba(255, 255, 255, 0); + transition: background-color var(--animation); +} +.selected .cafe-item-incr-button:before, +.selected .cafe-item-incr-button:after { + background-color: #fff; +} +.cafe-item-incr-button .button-item-label { + transition: transform var(--animation); +} +.selected .cafe-item-incr-button .button-item-label { + transform: scale3d(0.4, 0, 1); +} +.cafe-item-incr-button:after { + width: 3px; + height: 14px; +} + +.cafe-status-wrap { + position: fixed; + left: 0; + right: 0; + top: 0; + transform: translateY(var(--tg-viewport-height, 100vh)); + z-index: 1; +} +.cafe-status { + position: fixed; + bottom: 0; + left: 0; + right: 0; + display: block; + width: 100%; + padding: 8px 20px; + display: flex; + justify-content: center; + align-items: center; + border-radius: 0; + background-color: #e64d44; + box-shadow: 0 var(--status-height) #e64d44; + color: #fff; + height: var(--status-height); + transition: transform var(--animation), visibility var(--animation); + transform: translateY(var(--status-height)); + box-sizing: border-box; + pointer-events: none; + visibility: hidden; + z-index: 11; +} +.cafe-status.shown { + pointer-events: auto; + visibility: visible; + transform: translateY(0); +} + +.cafe-order-overview { + display: none; + font-family: var(--default-font); + background-color: var(--bg-color); + transition: opacity var(--page-animation); + opacity: 0; +} +body.order-mode .cafe-order-overview { + opacity: 1; +} +.cafe-order-header-wrap { + padding: 21px 20px 14px; + display: flex; + align-items: center; +} +.cafe-order-header { + font-size: 17px; + line-height: 21px; + text-transform: uppercase; + flex-grow: 1; + padding: 0; + margin: 0; +} +.cafe-order-edit { + font-size: 15px; + line-height: 18px; + font-weight: 500; + color: var(--accent-color); +} +.cafe-order-item { + display: none; + padding: 5px 20px 5px 14px; +} +.cafe-order-item.selected { + display: flex; +} +.cafe-order-item-label { + flex-grow: 1; +} +.cafe-order-item-photo { + text-align: center; + width: 50px; + height: 50px; + margin-right: 11px; +} +.cafe-order-item-photo .cafe-item-emoji { + font-size: 38px; + line-height: 50px; +} +.cafe-order-item-photo .cafe-item-lottie { + width: 40px; + margin: 4px 0; +} +.cafe-order-item-title { + font-size: 15px; + line-height: 18px; + font-weight: 700; + padding: 3px 0; +} +.cafe-order-item-counter { + color: var(--main-color); +} +.cafe-order-item-description { + font-size: 14px; + line-height: 17px; + -webkit-font-smoothing: antialiased; + color: var(--page-hint-color); + padding: 2px 0; +} +.cafe-order-item-price { + font-size: 14px; + line-height: 17px; + font-weight: 500; + padding: 4px 0; +} + +.cafe-text-field-wrap { + margin-top: 14px; +} +.cafe-text-field { + font-family: var(--default-font); + font-size: 17px; + line-height: 21px; + -webkit-font-smoothing: antialiased; + padding: 12px 20px 13px; + box-sizing: border-box; + display: block; + outline: none; + border: none; + border-radius: 0; + resize: none; + color: var(--text-color); + -webkit-user-select: auto; + user-select: auto; + cursor: auto; + width: 100%; +} +.cafe-text-field::-webkit-input-placeholder { + transition: color var(--animation); + color: var(--placeholder-color); + text-overflow: ellipsis; +} +.cafe-text-field::-moz-placeholder { + transition: color var(--animation); + color: var(--placeholder-color); + text-overflow: ellipsis; +} +.cafe-text-field:-ms-input-placeholder { + transition: color var(--animation); + color: var(--placeholder-color); + text-overflow: ellipsis; +} +.cafe-text-field::placeholder { + text-overflow: ellipsis; +} +.cafe-text-field-hint { + font-family: var(--default-font); + font-size: 14px; + line-height: 18px; + -webkit-font-smoothing: antialiased; + padding: 10px 20px 24px; + color: var(--hint-color); +} + + +.button-item.ripple-handler { + position: relative; +} +.ripple-mask { + position: absolute; + left: 0; right: 0; + top: 0; bottom: 0; + transform: translateZ(0); + overflow: hidden; + pointer-events: none; +} +.button-item .ripple-mask { + border-radius: inherit; +} +.button-item .ripple { + position: absolute; + width: 200%; + left: 50%; top: 50%; + margin: -100% 0 0 -100%; + padding-top: 200%; + border-radius: 50%; + background-color: rgba(0, 0, 0, 0.07); + transition: + transform var(--ripple-duration) ease-out, + opacity var(--ripple-duration) ease-out, + background-color var(--ripple-duration) ease-out; + opacity: 0; +} +.button-item-label { + display: inline-block; + max-width: 100%; + overflow: hidden; + text-overflow: ellipsis; + vertical-align: top; + position: relative; + z-index: 1; +} + +.cafe-item-add-button .ripple, +.cafe-item-incr-button .ripple { + background-color: #ed960b; +} +.cafe-item-decr-button .ripple { + background-color: #d3362d; +} + +i.star-icon { + display: inline-block; + vertical-align: top; + white-space: nowrap; + font-style: normal; + overflow: hidden; + position: relative; + background: url('data:image/svg+xml,%3Csvg%20height%3D%2245%22%20viewBox%3D%220%200%2046%2045%22%20width%3D%2246%22%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20xmlns%3Axlink%3D%22http%3A%2F%2Fwww.w3.org%2F1999%2Fxlink%22%3E%3Cdefs%3E%3ClinearGradient%20id%3D%22a%22%20x1%3D%2225%25%22%20x2%3D%2274.92%25%22%20y1%3D%22.825%25%22%20y2%3D%22107.86%25%22%3E%3Cstop%20offset%3D%220%22%20stop-color%3D%22%23ffd951%22%2F%3E%3Cstop%20offset%3D%221%22%20stop-color%3D%22%23ffb222%22%2F%3E%3C%2FlinearGradient%3E%3ClinearGradient%20id%3D%22b%22%20x1%3D%2250%25%22%20x2%3D%2250%25%22%20y1%3D%220%25%22%20y2%3D%2299.795%25%22%3E%3Cstop%20offset%3D%220%22%20stop-color%3D%22%23e58f0d%22%2F%3E%3Cstop%20offset%3D%22.99963%22%20stop-color%3D%22%23eb7915%22%2F%3E%3C%2FlinearGradient%3E%3Cpath%20id%3D%22c%22%20d%3D%22m15.45%2013.17%205.29-10.61c.61-1.22%202.09-1.71%203.3-1.09.47.24.86.63%201.09%201.11l5%2010.23c.41.83%201.21%201.4%202.12%201.51l10.47%201.27c1.42.17%202.43%201.47%202.26%202.91-.07.59-.34%201.14-.76%201.56l-8.27%208.2c-.33.33-.49.8-.44%201.27l1.38%2011.08c.2%201.59-.92%203.04-2.49%203.23-.59.08-1.19-.04-1.72-.32l-8.74-4.81c-.63-.35-1.39-.36-2.03-.03l-9.06%204.68c-1.27.66-2.83.14-3.48-1.14-.25-.49-.34-1.03-.26-1.57l.72-5.08c.36-2.49%201.89-4.64%204.1-5.78l10.06-5.17c.27-.14.37-.47.24-.74-.11-.21-.34-.33-.57-.29l-12.3%201.77c-1.88.27-3.78-.27-5.26-1.48l-4.09-3.36c-1.17-.96-1.35-2.7-.4-3.88.44-.55%201.08-.9%201.77-.99l10.5-1.36c.68-.09%201.26-.51%201.57-1.12z%22%2F%3E%3Cfilter%20id%3D%22d%22%20height%3D%22111.7%25%22%20width%3D%22111.4%25%22%20x%3D%22-5.7%25%22%20y%3D%22-5.9%25%22%3E%3CfeOffset%20dx%3D%222%22%20dy%3D%223%22%20in%3D%22SourceAlpha%22%20result%3D%22shadowOffsetInner1%22%2F%3E%3CfeComposite%20in%3D%22shadowOffsetInner1%22%20in2%3D%22SourceAlpha%22%20k2%3D%22-1%22%20k3%3D%221%22%20operator%3D%22arithmetic%22%20result%3D%22shadowInnerInner1%22%2F%3E%3CfeColorMatrix%20in%3D%22shadowInnerInner1%22%20type%3D%22matrix%22%20values%3D%220%200%200%200%201%20%20%200%200%200%200%201%20%20%200%200%200%200%201%20%200%200%200%200.65667938%200%22%2F%3E%3C%2Ffilter%3E%3C%2Fdefs%3E%3Cg%20fill%3D%22none%22%20fill-rule%3D%22evenodd%22%3E%3Cuse%20fill%3D%22url%28%23a%29%22%20fill-rule%3D%22evenodd%22%20xlink%3Ahref%3D%22%23c%22%2F%3E%3Cuse%20fill%3D%22%23000%22%20filter%3D%22url%28%23d%29%22%20xlink%3Ahref%3D%22%23c%22%2F%3E%3Cuse%20stroke%3D%22url%28%23b%29%22%20stroke-width%3D%222%22%20xlink%3Ahref%3D%22%23c%22%2F%3E%3C%2Fg%3E%3C%2Fsvg%3E') no-repeat center; + background-size: contain; + letter-spacing: 10em; + text-indent: -10em; + width: 1.3em; +} + + +.loading-icon { + position: absolute; + top: 0; + right: 0; + pointer-events: none; + transform: scale(0); + visibility: hidden; + opacity: 0.2; + transform-origin: 50%; + transition: all var(--animation); +} +body.loading .loading-icon { + transition-delay: .4s; + transform: scale(1); + visibility: visible; + opacity: 1; +} +.loading-icon-circle { + stroke: #fff; + stroke-width: 2.25px; + stroke-linecap: round; + fill: transparent; + transform: rotateZ(-90deg); + transform-origin: 50%; + animation: rotate-circle linear 1.5s infinite, resize-circle linear 360s infinite; + stroke-dasharray: calc(var(--radius) * 6.28); + r: var(--radius); + --radius: 9px; +} + +@-webkit-keyframes rotate-circle { + from { transform: rotateZ(-90deg); } + to { transform: rotateZ(630deg); } +} +@keyframes rotate-circle { + from { transform: rotateZ(-90deg); } + to { transform: rotateZ(630deg); } +} + +@-webkit-keyframes resize-circle { + from { stroke-dashoffset: 0; } + to { stroke-dashoffset: 12500px; } +} +@keyframes resize-circle { + from { stroke-dashoffset: 0; } + to { stroke-dashoffset: 12500px; } +} + +@-webkit-keyframes badge-incr { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(1.2, 1.2, 1); } +} +@keyframes badge-incr { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(1.2, 1.2, 1); } +} + +@-webkit-keyframes badge-incr2 { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(1.2, 1.2, 1); } +} +@keyframes badge-incr2 { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(1.2, 1.2, 1); } +} + +@-webkit-keyframes badge-decr { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(0.8, 0.8, 1); } +} +@keyframes badge-decr { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(0.8, 0.8, 1); } +} + +@-webkit-keyframes badge-decr2 { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(0.8, 0.8, 1); } +} +@keyframes badge-decr2 { + from, to { transform: scale3d(1, 1, 1); } + 40% { transform: scale3d(0.8, 0.8, 1); } +} + +@-webkit-keyframes badge-show { + from { transform: scale3d(0.5, 0.5, 1); opacity: 0; visibility: hidden; } + 30% { transform: scale3d(1.2, 1.2, 1); } + to { transform: scale3d(1, 1, 1); opacity: 1; visibility: visible; } +} +@keyframes badge-show { + from { transform: scale3d(0.5, 0.5, 1); opacity: 0; visibility: hidden; } + 30% { transform: scale3d(1.2, 1.2, 1); } + to { transform: scale3d(1, 1, 1); opacity: 1; visibility: visible; } +} + +@-webkit-keyframes badge-hide { + from { transform: scale3d(1, 1, 1); opacity: 1; visibility: visible; } + to { transform: scale3d(0.5, 0.5, 1); opacity: 0; visibility: hidden; } +} +@keyframes badge-hide { + from { transform: scale3d(1, 1, 1); opacity: 1; visibility: visible; } + to { transform: scale3d(0.5, 0.5, 1); opacity: 0; visibility: hidden; } +} diff --git a/MiniApp/wwwroot/css/webappdemo.css b/MiniApp/wwwroot/css/webappdemo.css new file mode 100644 index 0000000..00da395 --- /dev/null +++ b/MiniApp/wwwroot/css/webappdemo.css @@ -0,0 +1,287 @@ +html { + overscroll-behavior-x: none; +} +body { + --bg-color: var(--tg-theme-bg-color, #fff); + font-family: sans-serif; +/* background-color: var(--bg-color);*/ + background: transparent linear-gradient(180deg, var(--bg-color) 0%, var(--bg-color) 100%) no-repeat; + color: var(--tg-theme-text-color, #222); + font-size: 14px; + margin: 0; + padding: 0; + color-scheme: var(--tg-color-scheme); +} +body.gray { +/* background-color: var(--tg-theme-secondary-bg-color, #efefef);*/ + background: transparent linear-gradient(180deg, var(--tg-theme-secondary-bg-color, #efefef) 0%, var(--tg-theme-secondary-bg-color, #efefef) 100%) no-repeat; +} +a { + color: var(--tg-theme-link-color, #2678b6); +} +.btn { + font-size: 14px; + padding: 10px 17px; +} +.btn-primary { + background-color: var(--tg-theme-button-color, #50a8eb); + color: var(--tg-theme-button-text-color, #fff); + border: none; +} +.main-container { + padding: 15px; +} +.list-header { + text-transform: uppercase; + font-size: .92em; + color: var(--tg-theme-hint-color, #ccc); + margin: 0 0 10px; +} +a.list-group-item, +button.list-group-item { + color: var(--tg-theme-text-color, #222); +} +.main-container p { + margin: 0 0 10px; +} +.main-container pre, +.main-container > .btn { + margin: 0 0 7px; +} +.main-container pre + .hint, +.main-container > .btn + .hint { + text-align: center; + margin: 0 0 15px; +} + +button { + display: block; + width: 100%; + font-size: 14px; + margin: 15px 0; + padding: 12px 20px; + border: none; + border-radius: 4px; + background-color: var(--tg-theme-button-color, #50a8eb); + color: var(--tg-theme-button-text-color, #fff); + cursor: pointer; +} +button[disabled] { + opacity: 0.6; + cursor: auto; + pointer-events: none; +} +button.close_btn { + /*position: fixed;*/ + position: absolute; + left: 0; + right: 0; + bottom: 0; + border-radius: 0; + margin: 0; + padding: 16px 20px; + text-transform: uppercase; +} +table.table-condensed button { + display: inline-block; + width: auto; + font-size: 12px; + margin: 0 2px 2px 0; + padding: 2px 7px; +} +.table-bordered>tfoot>tr>th, +.table-bordered>tfoot>tr>td { + border-top-width: 2px; +} +input[type="text"], +.input[contenteditable] { + display: block; + box-sizing: border-box; + font-size: 14px; + width: 100%; + padding: 12px 20px; + margin: 15px 0; + border: 1px solid var(--tg-theme-link-color, #000); + background-color: var(--tg-theme-bg-color, #ffffff); + border-radius: 4px; + color: var(--tg-theme-text-color, #222222); + text-align: start; +} +input[type="text"]::-webkit-input-placeholder { + color: var(--tg-theme-hint-color, #ccc); +} +input[type="text"]::-moz-placeholder { + color: var(--tg-theme-hint-color, #ccc); +} +input[type="text"]:-ms-input-placeholder { + color: var(--tg-theme-hint-color, #ccc); +} +.input[data-placeholder] { + position: relative; +} +.input[data-placeholder]:empty:before { + position: absolute; + left: 0; + right: 0; + content: attr(data-placeholder); + color: var(--tg-theme-hint-color, #ccc); + padding: 0 20px; + font-weight: normal; + white-space: nowrap; + text-overflow: ellipsis; + overflow: hidden; + pointer-events: none; + z-index: -1; +} +table.table-condensed input[type="text"] { + font-size: 12px; + padding: 5px; + margin: 0; + border-color: #eee; +} +section { + padding: 15px; + text-align: center; + background-color: var(--bg-color, #ffffff); +} +section#top_sect { + background-color: var(--header-color, var(--tg-theme-bg-color, #ffffff)); +} +section#top_sect.second { + background-color: var(--header-color, var(--tg-theme-secondary-bg-color, #efefef)); +} +section .sect_row { + margin: 10px 0; +} +section + section { + padding: 0 15px 65px; +} +p { + margin: 40px 0 15px; +} +ul { + text-align: left; +} +li { + color: var(--tg-theme-hint-color, #a8a8a8); +} +textarea { + width: 100%; + box-sizing: border-box; + padding: 7px; +} +pre { + background: rgba(0, 0, 0, .07); + color: var(--tg-theme-text-color, #222); + font-size: 12px; + border: none; + border-radius: 4px; + padding: 8px; + margin: 7px 0; + word-break: break-all; + word-break: break-word; + white-space: pre-wrap; + text-align: left; +} +.dark pre { + background: rgba(255, 255, 255, .15); +} +.chat_img { + width: 30px; + border-radius: 15px; + margin-right: 10px; +} +.columns { + display: flex; +} +.columns>* { + flex-grow: 1; + flex-basis: 20%; +} +.hint { + font-size: .8em; + color: var(--tg-theme-hint-color, #a8a8a8); +} +.ok { + color: green; +} +.err { + color: red; +} +.txt { + color: var(--tg-theme-text-color, #222); +} +.status_need { + display: none; +} +#fixed_wrap { + position: fixed; + left: 0; + right: 0; + top: 0; + transform: translateY(100vh); +} +.viewport-container { + position: fixed; + left: 0; + right: 0; + top: 0; + height: var(--tg-viewport-stable-height, 100vh); + transition: height .2s ease; +} +.viewport-container .main-container { + position: absolute; + left: 0; + right: 0; + top: 0; + bottom: 0; + display: flex; + justify-content: center; + align-items: center; +} +.viewport-container .main-container button { + width: auto; +} +.viewport-border, +.viewport-stable_border { + position: fixed; + left: 0; + right: 0; + top: 0; + height: var(--tg-viewport-height, 100vh); + pointer-events: none; +} +.viewport-stable_border { + height: var(--tg-viewport-stable-height, 100vh); +} +.viewport-border:before, +.viewport-stable_border:before { + content: attr(text); + display: inline-block; + position: absolute; + background: gray; + right: 0; + top: 0; + font-size: 7px; + padding: 2px 4px; + vertical-align: top; +} +.viewport-stable_border:before { + background: green; + left: 0; + right: auto; +} +.viewport-border:after, +.viewport-stable_border:after { + content: ''; + display: block; + position: absolute; + left: 0; + right: 0; + top: 0; + bottom: 0; + border: 2px dashed gray; +} +.viewport-stable_border:after { + border-color: green; +} \ No newline at end of file diff --git a/MiniApp/wwwroot/img/cafe/Burger.tgs b/MiniApp/wwwroot/img/cafe/Burger.tgs new file mode 100644 index 0000000..95aea0a Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Burger.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Burger_148.png b/MiniApp/wwwroot/img/cafe/Burger_148.png new file mode 100644 index 0000000..012ad15 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Burger_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Cake.tgs b/MiniApp/wwwroot/img/cafe/Cake.tgs new file mode 100644 index 0000000..60d9566 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Cake.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Cake_148.png b/MiniApp/wwwroot/img/cafe/Cake_148.png new file mode 100644 index 0000000..f4cae7a Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Cake_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Coke.tgs b/MiniApp/wwwroot/img/cafe/Coke.tgs new file mode 100644 index 0000000..009a4c6 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Coke.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Coke_148.png b/MiniApp/wwwroot/img/cafe/Coke_148.png new file mode 100644 index 0000000..c1787b0 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Coke_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Cookie.tgs b/MiniApp/wwwroot/img/cafe/Cookie.tgs new file mode 100644 index 0000000..5a99efc Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Cookie.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Cookie_148.png b/MiniApp/wwwroot/img/cafe/Cookie_148.png new file mode 100644 index 0000000..a98013f Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Cookie_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Donut.tgs b/MiniApp/wwwroot/img/cafe/Donut.tgs new file mode 100644 index 0000000..3cb8ff5 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Donut.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Donut_148.png b/MiniApp/wwwroot/img/cafe/Donut_148.png new file mode 100644 index 0000000..e28d88c Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Donut_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Flan.tgs b/MiniApp/wwwroot/img/cafe/Flan.tgs new file mode 100644 index 0000000..7d600c6 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Flan.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Flan_148.png b/MiniApp/wwwroot/img/cafe/Flan_148.png new file mode 100644 index 0000000..4f80a02 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Flan_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Fries.tgs b/MiniApp/wwwroot/img/cafe/Fries.tgs new file mode 100644 index 0000000..13a4d76 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Fries.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Fries_148.png b/MiniApp/wwwroot/img/cafe/Fries_148.png new file mode 100644 index 0000000..bdfe598 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Fries_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Hotdog.tgs b/MiniApp/wwwroot/img/cafe/Hotdog.tgs new file mode 100644 index 0000000..81d46d6 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Hotdog.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Hotdog_148.png b/MiniApp/wwwroot/img/cafe/Hotdog_148.png new file mode 100644 index 0000000..fea0cd6 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Hotdog_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Icecream.tgs b/MiniApp/wwwroot/img/cafe/Icecream.tgs new file mode 100644 index 0000000..47d3d83 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Icecream.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Icecream_148.png b/MiniApp/wwwroot/img/cafe/Icecream_148.png new file mode 100644 index 0000000..1e46001 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Icecream_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Pizza.tgs b/MiniApp/wwwroot/img/cafe/Pizza.tgs new file mode 100644 index 0000000..df76271 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Pizza.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Pizza_148.png b/MiniApp/wwwroot/img/cafe/Pizza_148.png new file mode 100644 index 0000000..c939926 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Pizza_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Popcorn.tgs b/MiniApp/wwwroot/img/cafe/Popcorn.tgs new file mode 100644 index 0000000..4c6bbbc Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Popcorn.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Popcorn_148.png b/MiniApp/wwwroot/img/cafe/Popcorn_148.png new file mode 100644 index 0000000..062afd2 Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Popcorn_148.png differ diff --git a/MiniApp/wwwroot/img/cafe/Tako.tgs b/MiniApp/wwwroot/img/cafe/Tako.tgs new file mode 100644 index 0000000..2a619be Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Tako.tgs differ diff --git a/MiniApp/wwwroot/img/cafe/Tako_148.png b/MiniApp/wwwroot/img/cafe/Tako_148.png new file mode 100644 index 0000000..1ea008f Binary files /dev/null and b/MiniApp/wwwroot/img/cafe/Tako_148.png differ diff --git a/MiniApp/wwwroot/js/cafe.js b/MiniApp/wwwroot/js/cafe.js new file mode 100644 index 0000000..8362e4f --- /dev/null +++ b/MiniApp/wwwroot/js/cafe.js @@ -0,0 +1,485 @@ +(function($) { + $.fn.redraw = function() { + return this.map(function(){ this.offsetTop; return this; }); + }; +})(jQuery); + +var Cafe = { + canPay: false, + modeOrder: false, + totalPrice: 0, + + init: function(options) { + Telegram.WebApp.ready(); + Cafe.apiUrl = options.apiUrl; + Cafe.mode = options.mode; + Cafe.userId = options.userId; + Cafe.userHash = options.userHash; + Cafe.initLotties(); + var starsSupported = Telegram.WebApp.isVersionAtLeast('7.4'); + $('body').toggleClass('stars-supported', starsSupported).show(); + if ((!Telegram.WebApp.initDataUnsafe || + !Telegram.WebApp.initDataUnsafe.query_id) && + Cafe.mode != 'inline' && + Cafe.mode != 'link') { + Cafe.isClosed = true; + $('body').addClass('closed'); + Cafe.showStatus('Cafe is temporarily closed'); + return; + } + $('.js-item-lottie').on('click', Cafe.eLottieClicked); + $('.js-item-incr-btn').on('click', Cafe.eIncrClicked); + $('.js-item-decr-btn').on('click', Cafe.eDecrClicked); + $('.js-item-buy-btn').on('click', Cafe.eBuyClicked); + $('.js-order-edit').on('click', Cafe.eEditClicked); + $('.js-status').on('click', Cafe.eStatusClicked); + $('.js-order-comment-field').each(function() { + autosize(this); + }); + Telegram.WebApp.MainButton.setParams({ + text_color: '#fff' + }).onClick(Cafe.mainBtnClicked); + Telegram.WebApp.BackButton.onClick(Cafe.backBtnClicked); + Telegram.WebApp.setHeaderColor('bg_color'); + initRipple(); + }, + initLotties: function() { + $('.js-item-lottie').each(function() { + RLottie.init(this, { + maxDeviceRatio: 2, + cachingModulo: 3, + noAutoPlay: true + }); + }); + }, + eLottieClicked: function(e) { + if (Cafe.isClosed) { + return false; + } + RLottie.playOnce(this); + }, + eIncrClicked: function(e) { + e.preventDefault(); + Telegram.WebApp.HapticFeedback.impactOccurred('light'); + var itemEl = $(this).parents('.js-item'); + Cafe.incrClicked(itemEl, 1); + }, + eDecrClicked: function(e) { + e.preventDefault(); + Telegram.WebApp.HapticFeedback.impactOccurred('light'); + var itemEl = $(this).parents('.js-item'); + Cafe.incrClicked(itemEl, -1); + }, + eBuyClicked: function(e) { + e.preventDefault(); + Telegram.WebApp.HapticFeedback.impactOccurred('light'); + var itemEl = $(this).parents('.js-item'); + Cafe.buyClicked(itemEl); + }, + eEditClicked: function(e) { + e.preventDefault(); + Cafe.toggleMode(false); + }, + backBtnClicked: function() { + Cafe.toggleMode(false); + document.activeElement && document.activeElement.blur(); + }, + getOrderItem: function(itemEl) { + var id = itemEl.data('item-id'); + return $('.js-order-item').filter(function() { + return ($(this).data('item-id') == id); + }); + }, + updateItem: function(itemEl, delta) { + var price = +itemEl.data('item-price'); + var count = +itemEl.data('item-count') || 0; + var counterEl = $('.js-item-counter', itemEl); + counterEl.text(count ? count : 1); + var isSelected = itemEl.hasClass('selected'); + if (!isSelected && count > 0) { + $('.js-item-lottie', itemEl).each(function() { + RLottie.playOnce(this); + }); + } + var anim_name = isSelected ? (delta > 0 ? 'badge-incr' : (count > 0 ? 'badge-decr' : 'badge-hide')) : 'badge-show'; + var cur_anim_name = counterEl.css('animation-name'); + if ((anim_name == 'badge-incr' || anim_name == 'badge-decr') && anim_name == cur_anim_name) { + anim_name += '2'; + } + counterEl.css('animation-name', anim_name); + itemEl.toggleClass('selected', count > 0); + + var orderItemEl = Cafe.getOrderItem(itemEl); + var orderCounterEl = $('.js-order-item-counter', orderItemEl); + orderCounterEl.text(count ? count : 1); + orderItemEl.toggleClass('selected', count > 0); + var orderPriceEl = $('.js-order-item-price', orderItemEl); + var item_price = count * price; + orderPriceEl.text(Cafe.formatPrice(item_price)); + + Cafe.updateTotalPrice(); + }, + incrClicked: function(itemEl, delta) { + if (Cafe.isLoading || Cafe.isClosed) { + return false; + } + var count = +itemEl.data('item-count') || 0; + count += delta; + if (count < 0) { + count = 0; + } + itemEl.data('item-count', count); + Cafe.updateItem(itemEl, delta); + }, + formatPrice: function(price) { + return '$' + Cafe.formatNumber(price / 100, 2, '.', ','); + }, + formatNumber: function(number, decimals, decPoint, thousandsSep) { + number = (number + '').replace(/[^0-9+\-Ee.]/g, '') + var n = !isFinite(+number) ? 0 : +number + var prec = !isFinite(+decimals) ? 0 : Math.abs(decimals) + var sep = (typeof thousandsSep === 'undefined') ? ',' : thousandsSep + var dec = (typeof decPoint === 'undefined') ? '.' : decPoint + var s = '' + var toFixedFix = function (n, prec) { + if (('' + n).indexOf('e') === -1) { + return +(Math.round(n + 'e+' + prec) + 'e-' + prec) + } else { + var arr = ('' + n).split('e') + var sig = '' + if (+arr[1] + prec > 0) { + sig = '+' + } + return (+(Math.round(+arr[0] + 'e' + sig + (+arr[1] + prec)) + 'e-' + prec)).toFixed(prec) + } + } + s = (prec ? toFixedFix(n, prec).toString() : '' + Math.round(n)).split('.') + if (s[0].length > 3) { + s[0] = s[0].replace(/\B(?=(?:\d{3})+(?!\d))/g, sep) + } + if ((s[1] || '').length < prec) { + s[1] = s[1] || '' + s[1] += new Array(prec - s[1].length + 1).join('0') + } + return s.join(dec) + }, + updateBackgroundColor: function() { + var style = window.getComputedStyle(document.body); + var bg_color = parseColorToHex(style.backgroundColor || '#fff'); + Telegram.WebApp.setBackgroundColor(bg_color); + }, + updateMainButton: function() { + var mainButton = Telegram.WebApp.MainButton; + if (Cafe.modeOrder) { + if (Cafe.isLoading) { + mainButton.setParams({ + is_visible: true, + color: '#65c36d' + }).showProgress(); + } else { + mainButton.setParams({ + is_visible: !!Cafe.canPay, + text: Cafe.mode == 'inline' ? 'CREATE ORDER' : (Cafe.mode == 'link' ? 'CHOOSE A CHAT…' : 'PAY ' + Cafe.formatPrice(Cafe.totalPrice)), + color: '#31b545' + }).hideProgress(); + } + } else { + mainButton.setParams({ + is_visible: !!Cafe.canPay, + text: 'VIEW ORDER', + color: '#31b545' + }).hideProgress(); + } + Telegram.WebApp.isClosingConfirmationEnabled = !!Cafe.canPay; + }, + updateTotalPrice: function() { + var total_price = 0; + $('.js-item').each(function() { + var itemEl = $(this) + var price = +itemEl.data('item-price'); + var count = +itemEl.data('item-count') || 0; + total_price += price * count; + }); + Cafe.canPay = total_price > 0; + Cafe.totalPrice = total_price; + Cafe.updateMainButton(); + }, + getOrderData: function() { + var order_data = []; + $('.js-item').each(function() { + var itemEl = $(this); + var id = itemEl.data('item-id'); + var count = +itemEl.data('item-count') || 0; + if (count > 0) { + order_data.push({id: id, count: count}); + } + }); + return JSON.stringify(order_data); + }, + toggleMode: function(mode_order) { + Cafe.modeOrder = mode_order; + var anim_duration, match; + try { + anim_duration = window.getComputedStyle(document.body).getPropertyValue('--page-animation-duration'); + if (match = /([\d\.]+)(ms|s)/.exec(anim_duration)) { + anim_duration = +match[1]; + if (match[2] == 's') { + anim_duration *= 1000; + } + } else { + anim_duration = 400; + } + } catch (e) { + anim_duration = 400; + } + if (mode_order) { + var height = $('.cafe-items').height(); + $('.js-item-lottie').each(function() { + RLottie.pause(this); + }); + $('.cafe-order-overview').show(); + $('.cafe-items').css('maxHeight', height).redraw(); + $('body').addClass('order-mode'); + $('.js-order-comment-field').each(function() { + autosize.update(this); + }); + Telegram.WebApp.expand(); + Telegram.WebApp.BackButton.show(); + } else { + $('.js-item-lottie').each(function() { + RLottie.reset(this); + }); + $('body').removeClass('order-mode'); + setTimeout(function() { + $('.cafe-items').css('maxHeight', ''); + $('.cafe-order-overview').hide(); + $('.js-item-lottie').each(function() { + }); + }, anim_duration); + Telegram.WebApp.BackButton.hide(); + } + Cafe.updateBackgroundColor(); + Cafe.updateMainButton(); + }, + toggleLoading: function(loading) { + Cafe.isLoading = loading; + Cafe.updateMainButton(); + $('body').toggleClass('loading', !!Cafe.isLoading); + Cafe.updateTotalPrice(); + }, + mainBtnClicked: function() { + if (!Cafe.canPay || Cafe.isLoading || Cafe.isClosed) { + return false; + } + if (Cafe.modeOrder) { + var comment = $('.js-order-comment-field').val(); + var params = { + order_data: Cafe.getOrderData(), + comment: comment + }; + if (Cafe.mode) { + params.mode = Cafe.mode; + } + if (Cafe.userId && Cafe.userHash) { + params.user_id = Cafe.userId; + params.user_hash = Cafe.userHash; + } + var invoiceSupported = Telegram.WebApp.isVersionAtLeast('6.1'); + if (invoiceSupported) { + params.invoice = 1; + } + Cafe.toggleLoading(true); + Cafe.apiRequest('makeOrder', params, function(result) { + Cafe.toggleLoading(false); + if (result.ok) { + if (Cafe.mode == 'inline') { + Telegram.WebApp.switchInlineQuery('#' + result.order_id); + } else if (Cafe.mode == 'link') { + Telegram.WebApp.switchInlineQuery('#' + result.order_id, ['users', 'groups']); + } else if (invoiceSupported) { + Telegram.WebApp.openInvoice(result.invoice_url, function(status) { + if (status == 'paid') { + Telegram.WebApp.close(); + } else if (status == 'failed') { + Telegram.WebApp.HapticFeedback.notificationOccurred('error'); + Cafe.showStatus('Payment has been failed.'); + } else { + Telegram.WebApp.HapticFeedback.notificationOccurred('warning'); + Cafe.showStatus('You have cancelled this order.'); + } + }); + } else { + Telegram.WebApp.close(); + } + } + if (result.error) { + Telegram.WebApp.HapticFeedback.notificationOccurred('error'); + Cafe.showStatus(result.error); + } + }); + } else { + Cafe.toggleMode(true); + } + }, + buyClicked: function(itemEl) { + if (Cafe.isLoading || Cafe.isClosed) { + return false; + } + var id = itemEl.data('item-id'); + var params = { + item_id: id + }; + if (Cafe.mode) { + params.mode = Cafe.mode; + } + if (Cafe.userId && Cafe.userHash) { + params.user_id = Cafe.userId; + params.user_hash = Cafe.userHash; + } + var invoiceSupported = Telegram.WebApp.isVersionAtLeast('6.1'); + if (invoiceSupported) { + params.invoice = 1; + } + Cafe.toggleLoading(true); + Cafe.apiRequest('buyItem', params, function(result) { + Cafe.toggleLoading(false); + if (result.ok) { + if (invoiceSupported) { + Telegram.WebApp.openInvoice(result.invoice_url, function(status) { + if (status == 'paid') { + Telegram.WebApp.close(); + } else if (status == 'failed') { + Telegram.WebApp.HapticFeedback.notificationOccurred('error'); + Cafe.showStatus('Payment has been failed.'); + } else { + Telegram.WebApp.HapticFeedback.notificationOccurred('warning'); + Cafe.showStatus('You have cancelled this order.'); + } + }); + } else { + Telegram.WebApp.close(); + } + } + if (result.error) { + Telegram.WebApp.HapticFeedback.notificationOccurred('error'); + Cafe.showStatus(result.error); + } + }); + }, + eStatusClicked: function() { + Cafe.hideStatus(); + }, + showStatus: function(text) { + clearTimeout(Cafe.statusTo); + $('.js-status').text(text).addClass('shown'); + if (!Cafe.isClosed) { + Cafe.statusTo = setTimeout(function(){ Cafe.hideStatus(); }, 2500); + } + }, + hideStatus: function() { + clearTimeout(Cafe.statusTo); + $('.js-status').removeClass('shown'); + }, + apiRequest: function(method, data, onCallback) { + var authData = Telegram.WebApp.initData || ''; + $.ajax(Cafe.apiUrl, { + type: 'POST', + data: $.extend(data, {_auth: authData, method: method}), + dataType: 'json', + xhrFields: { + withCredentials: true + }, + success: function(result) { + onCallback && onCallback(result); + }, + error: function(xhr) { + onCallback && onCallback({error: 'Server error'}); + } + }); + } +}; + +function parseColorToHex(color) { + color += ''; + var match; + if (match = /^\s*#([0-9a-f]{6})\s*$/i.exec(color)) { + return '#' + match[1].toLowerCase(); + } + else if (match = /^\s*#([0-9a-f])([0-9a-f])([0-9a-f])\s*$/i.exec(color)) { + return ('#' + match[1] + match[1] + match[2] + match[2] + match[3] + match[3]).toLowerCase(); + } + else if (match = /^\s*rgba?\((\d+),\s*(\d+),\s*(\d+)(?:,\s*(\d+\.{0,1}\d*))?\)\s*$/.exec(color)) { + var r = parseInt(match[1]), g = parseInt(match[2]), b = parseInt(match[3]); + r = (r < 16 ? '0' : '') + r.toString(16); + g = (g < 16 ? '0' : '') + g.toString(16); + b = (b < 16 ? '0' : '') + b.toString(16); + return '#' + r + g + b; + } + return false; +} + +/*! + Autosize 3.0.20 + license: MIT + http://www.jacklmoore.com/autosize +*/ +!function(e,t){if("function"==typeof define&&define.amd)define(["exports","module"],t);else if("undefined"!=typeof exports&&"undefined"!=typeof module)t(exports,module);else{var n={exports:{}};t(n.exports,n),e.autosize=n.exports}}(this,function(e,t){"use strict";function n(e){function t(){var t=window.getComputedStyle(e,null);"vertical"===t.resize?e.style.resize="none":"both"===t.resize&&(e.style.resize="horizontal"),s="content-box"===t.boxSizing?-(parseFloat(t.paddingTop)+parseFloat(t.paddingBottom)):parseFloat(t.borderTopWidth)+parseFloat(t.borderBottomWidth),isNaN(s)&&(s=0),l()}function n(t){var n=e.style.width;e.style.width="0px",e.offsetWidth,e.style.width=n,e.style.overflowY=t}function o(e){for(var t=[];e&&e.parentNode&&e.parentNode instanceof Element;)e.parentNode.scrollTop&&t.push({node:e.parentNode,scrollTop:e.parentNode.scrollTop}),e=e.parentNode;return t}function r(){var t=e.style.height,n=o(e),r=document.documentElement&&document.documentElement.scrollTop;e.style.height="auto";var i=e.scrollHeight+s;return 0===e.scrollHeight?void(e.style.height=t):(e.style.height=i+"px",u=e.clientWidth,n.forEach(function(e){e.node.scrollTop=e.scrollTop}),void(r&&(document.documentElement.scrollTop=r)))}function l(){r();var t=Math.round(parseFloat(e.style.height)),o=window.getComputedStyle(e,null),i=Math.round(parseFloat(o.height));if(i!==t?"visible"!==o.overflowY&&(n("visible"),r(),i=Math.round(parseFloat(window.getComputedStyle(e,null).height))):"hidden"!==o.overflowY&&(n("hidden"),r(),i=Math.round(parseFloat(window.getComputedStyle(e,null).height))),a!==i){a=i;var l=d("autosize:resized");try{e.dispatchEvent(l)}catch(e){}}}if(e&&e.nodeName&&"TEXTAREA"===e.nodeName&&!i.has(e)){var s=null,u=e.clientWidth,a=null,p=function(){e.clientWidth!==u&&l()},c=function(t){window.removeEventListener("resize",p,!1),e.removeEventListener("input",l,!1),e.removeEventListener("keyup",l,!1),e.removeEventListener("autosize:destroy",c,!1),e.removeEventListener("autosize:update",l,!1),Object.keys(t).forEach(function(n){e.style[n]=t[n]}),i.delete(e)}.bind(e,{height:e.style.height,resize:e.style.resize,overflowY:e.style.overflowY,overflowX:e.style.overflowX,wordWrap:e.style.wordWrap});e.addEventListener("autosize:destroy",c,!1),"onpropertychange"in e&&"oninput"in e&&e.addEventListener("keyup",l,!1),window.addEventListener("resize",p,!1),e.addEventListener("input",l,!1),e.addEventListener("autosize:update",l,!1),e.style.overflowX="hidden",e.style.wordWrap="break-word",i.set(e,{destroy:c,update:l}),t()}}function o(e){var t=i.get(e);t&&t.destroy()}function r(e){var t=i.get(e);t&&t.update()}var i="function"==typeof Map?new Map:function(){var e=[],t=[];return{has:function(t){return e.indexOf(t)>-1},get:function(n){return t[e.indexOf(n)]},set:function(n,o){e.indexOf(n)===-1&&(e.push(n),t.push(o))},delete:function(n){var o=e.indexOf(n);o>-1&&(e.splice(o,1),t.splice(o,1))}}}(),d=function(e){return new Event(e,{bubbles:!0})};try{new Event("test")}catch(e){d=function(e){var t=document.createEvent("Event");return t.initEvent(e,!0,!1),t}}var l=null;"undefined"==typeof window||"function"!=typeof window.getComputedStyle?(l=function(e){return e},l.destroy=function(e){return e},l.update=function(e){return e}):(l=function(e,t){return e&&Array.prototype.forEach.call(e.length?e:[e],function(e){return n(e,t)}),e},l.destroy=function(e){return e&&Array.prototype.forEach.call(e.length?e:[e],o),e},l.update=function(e){return e&&Array.prototype.forEach.call(e.length?e:[e],r),e}),t.exports=l}); + +/* Ripple */ + +function initRipple() { + if (!document.querySelectorAll) return; + var rippleHandlers = document.querySelectorAll('.ripple-handler'); + var redraw = function(el) { el.offsetTop + 1; } + var isTouch = ('ontouchstart' in window); + for (var i = 0; i < rippleHandlers.length; i++) { + (function(rippleHandler) { + function onRippleStart(e) { + var rippleMask = rippleHandler.querySelector('.ripple-mask'); + if (!rippleMask) return; + var rect = rippleMask.getBoundingClientRect(); + if (e.type == 'touchstart') { + var clientX = e.targetTouches[0].clientX; + var clientY = e.targetTouches[0].clientY; + } else { + var clientX = e.clientX; + var clientY = e.clientY; + } + var rippleX = (clientX - rect.left) - rippleMask.offsetWidth / 2; + var rippleY = (clientY - rect.top) - rippleMask.offsetHeight / 2; + var ripple = rippleHandler.querySelector('.ripple'); + ripple.style.transition = 'none'; + redraw(ripple); + ripple.style.transform = 'translate3d(' + rippleX + 'px, ' + rippleY + 'px, 0) scale3d(0.2, 0.2, 1)'; + ripple.style.opacity = 1; + redraw(ripple); + ripple.style.transform = 'translate3d(' + rippleX + 'px, ' + rippleY + 'px, 0) scale3d(1, 1, 1)'; + ripple.style.transition = ''; + + function onRippleEnd(e) { + ripple.style.transitionDuration = 'var(--ripple-end-duration, .2s)'; + ripple.style.opacity = 0; + if (isTouch) { + document.removeEventListener('touchend', onRippleEnd); + document.removeEventListener('touchcancel', onRippleEnd); + } else { + document.removeEventListener('mouseup', onRippleEnd); + } + } + if (isTouch) { + document.addEventListener('touchend', onRippleEnd); + document.addEventListener('touchcancel', onRippleEnd); + } else { + document.addEventListener('mouseup', onRippleEnd); + } + } + if (isTouch) { + rippleHandler.removeEventListener('touchstart', onRippleStart); + rippleHandler.addEventListener('touchstart', onRippleStart); + } else { + rippleHandler.removeEventListener('mousedown', onRippleStart); + rippleHandler.addEventListener('mousedown', onRippleStart); + } + })(rippleHandlers[i]); + } +} diff --git a/MiniApp/wwwroot/js/pako-inflate.min.js b/MiniApp/wwwroot/js/pako-inflate.min.js new file mode 100644 index 0000000..a191a78 --- /dev/null +++ b/MiniApp/wwwroot/js/pako-inflate.min.js @@ -0,0 +1 @@ +!function(e){if("object"==typeof exports&&"undefined"!=typeof module)module.exports=e();else if("function"==typeof define&&define.amd)define([],e);else{("undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self?self:this).pako=e()}}(function(){return function r(o,s,f){function l(t,e){if(!s[t]){if(!o[t]){var i="function"==typeof require&&require;if(!e&&i)return i(t,!0);if(d)return d(t,!0);var n=new Error("Cannot find module '"+t+"'");throw n.code="MODULE_NOT_FOUND",n}var a=s[t]={exports:{}};o[t][0].call(a.exports,function(e){return l(o[t][1][e]||e)},a,a.exports,r,o,s,f)}return s[t].exports}for(var d="function"==typeof require&&require,e=0;e>>6:(i<65536?t[r++]=224|i>>>12:(t[r++]=240|i>>>18,t[r++]=128|i>>>12&63),t[r++]=128|i>>>6&63),t[r++]=128|63&i);return t},i.buf2binstring=function(e){return d(e,e.length)},i.binstring2buf=function(e){for(var t=new f.Buf8(e.length),i=0,n=t.length;i>10&1023,s[n++]=56320|1023&a)}return d(s,n)},i.utf8border=function(e,t){var i;for((t=t||e.length)>e.length&&(t=e.length),i=t-1;0<=i&&128==(192&e[i]);)i--;return i<0?t:0===i?t:i+l[e[i]]>t?i:t}},{"./common":1}],3:[function(e,t,i){"use strict";t.exports=function(e,t,i,n){for(var a=65535&e|0,r=e>>>16&65535|0,o=0;0!==i;){for(i-=o=2e3>>1:e>>>1;t[i]=e}return t}();t.exports=function(e,t,i,n){var a=s,r=n+i;e^=-1;for(var o=n;o>>8^a[255&(e^t[o])];return-1^e}},{}],6:[function(e,t,i){"use strict";t.exports=function(){this.text=0,this.time=0,this.xflags=0,this.os=0,this.extra=null,this.extra_len=0,this.name="",this.comment="",this.hcrc=0,this.done=!1}},{}],7:[function(e,t,i){"use strict";t.exports=function(e,t){var i,n,a,r,o,s,f,l,d,c,u,h,b,m,w,k,_,g,v,p,x,y,S,E,Z;i=e.state,n=e.next_in,E=e.input,a=n+(e.avail_in-5),r=e.next_out,Z=e.output,o=r-(t-e.avail_out),s=r+(e.avail_out-257),f=i.dmax,l=i.wsize,d=i.whave,c=i.wnext,u=i.window,h=i.hold,b=i.bits,m=i.lencode,w=i.distcode,k=(1<>>=v=g>>>24,b-=v,0===(v=g>>>16&255))Z[r++]=65535&g;else{if(!(16&v)){if(0==(64&v)){g=m[(65535&g)+(h&(1<>>=v,b-=v),b<15&&(h+=E[n++]<>>=v=g>>>24,b-=v,!(16&(v=g>>>16&255))){if(0==(64&v)){g=w[(65535&g)+(h&(1<>>=v,b-=v,(v=r-o)>3,h&=(1<<(b-=p<<3))-1,e.next_in=n,e.next_out=r,e.avail_in=n>>24&255)+(e>>>8&65280)+((65280&e)<<8)+((255&e)<<24)}function r(){this.mode=0,this.last=!1,this.wrap=0,this.havedict=!1,this.flags=0,this.dmax=0,this.check=0,this.total=0,this.head=null,this.wbits=0,this.wsize=0,this.whave=0,this.wnext=0,this.window=null,this.hold=0,this.bits=0,this.length=0,this.offset=0,this.extra=0,this.lencode=null,this.distcode=null,this.lenbits=0,this.distbits=0,this.ncode=0,this.nlen=0,this.ndist=0,this.have=0,this.next=null,this.lens=new z.Buf16(320),this.work=new z.Buf16(288),this.lendyn=null,this.distdyn=null,this.sane=0,this.back=0,this.was=0}function o(e){var t;return e&&e.state?(t=e.state,e.total_in=e.total_out=t.total=0,e.msg="",t.wrap&&(e.adler=1&t.wrap),t.mode=F,t.last=0,t.havedict=0,t.dmax=32768,t.head=null,t.hold=0,t.bits=0,t.lencode=t.lendyn=new z.Buf32(n),t.distcode=t.distdyn=new z.Buf32(a),t.sane=1,t.back=-1,T):U}function s(e){var t;return e&&e.state?((t=e.state).wsize=0,t.whave=0,t.wnext=0,o(e)):U}function f(e,t){var i,n;return e&&e.state?(n=e.state,t<0?(i=0,t=-t):(i=1+(t>>4),t<48&&(t&=15)),t&&(t<8||15=r.wsize?(z.arraySet(r.window,t,i-r.wsize,r.wsize,0),r.wnext=0,r.whave=r.wsize):(n<(a=r.wsize-r.wnext)&&(a=n),z.arraySet(r.window,t,i-n,a,r.wnext),(n-=a)?(z.arraySet(r.window,t,i-n,n,0),r.wnext=n,r.whave=r.wsize):(r.wnext+=a,r.wnext===r.wsize&&(r.wnext=0),r.whave>>8&255,i.check=N(i.check,B,2,0),d=l=0,i.mode=2;break}if(i.flags=0,i.head&&(i.head.done=!1),!(1&i.wrap)||(((255&l)<<8)+(l>>8))%31){e.msg="incorrect header check",i.mode=30;break}if(8!=(15&l)){e.msg="unknown compression method",i.mode=30;break}if(d-=4,x=8+(15&(l>>>=4)),0===i.wbits)i.wbits=x;else if(x>i.wbits){e.msg="invalid window size",i.mode=30;break}i.dmax=1<>8&1),512&i.flags&&(B[0]=255&l,B[1]=l>>>8&255,i.check=N(i.check,B,2,0)),d=l=0,i.mode=3;case 3:for(;d<32;){if(0===s)break e;s--,l+=n[r++]<>>8&255,B[2]=l>>>16&255,B[3]=l>>>24&255,i.check=N(i.check,B,4,0)),d=l=0,i.mode=4;case 4:for(;d<16;){if(0===s)break e;s--,l+=n[r++]<>8),512&i.flags&&(B[0]=255&l,B[1]=l>>>8&255,i.check=N(i.check,B,2,0)),d=l=0,i.mode=5;case 5:if(1024&i.flags){for(;d<16;){if(0===s)break e;s--,l+=n[r++]<>>8&255,i.check=N(i.check,B,2,0)),d=l=0}else i.head&&(i.head.extra=null);i.mode=6;case 6:if(1024&i.flags&&(s<(h=i.length)&&(h=s),h&&(i.head&&(x=i.head.extra_len-i.length,i.head.extra||(i.head.extra=new Array(i.head.extra_len)),z.arraySet(i.head.extra,n,r,h,x)),512&i.flags&&(i.check=N(i.check,n,h,r)),s-=h,r+=h,i.length-=h),i.length))break e;i.length=0,i.mode=7;case 7:if(2048&i.flags){if(0===s)break e;for(h=0;x=n[r+h++],i.head&&x&&i.length<65536&&(i.head.name+=String.fromCharCode(x)),x&&h>9&1,i.head.done=!0),e.adler=i.check=0,i.mode=12;break;case 10:for(;d<32;){if(0===s)break e;s--,l+=n[r++]<>>=7&d,d-=7&d,i.mode=27;break}for(;d<3;){if(0===s)break e;s--,l+=n[r++]<>>=1)){case 0:i.mode=14;break;case 1:if(H(i),i.mode=20,6!==t)break;l>>>=2,d-=2;break e;case 2:i.mode=17;break;case 3:e.msg="invalid block type",i.mode=30}l>>>=2,d-=2;break;case 14:for(l>>>=7&d,d-=7&d;d<32;){if(0===s)break e;s--,l+=n[r++]<>>16^65535)){e.msg="invalid stored block lengths",i.mode=30;break}if(i.length=65535&l,d=l=0,i.mode=15,6===t)break e;case 15:i.mode=16;case 16:if(h=i.length){if(s>>=5,d-=5,i.ndist=1+(31&l),l>>>=5,d-=5,i.ncode=4+(15&l),l>>>=4,d-=4,286>>=3,d-=3}for(;i.have<19;)i.lens[A[i.have++]]=0;if(i.lencode=i.lendyn,i.lenbits=7,S={bits:i.lenbits},y=C(0,i.lens,0,19,i.lencode,0,i.work,S),i.lenbits=S.bits,y){e.msg="invalid code lengths set",i.mode=30;break}i.have=0,i.mode=19;case 19:for(;i.have>>16&255,_=65535&Z,!((w=Z>>>24)<=d);){if(0===s)break e;s--,l+=n[r++]<>>=w,d-=w,i.lens[i.have++]=_;else{if(16===_){for(E=w+2;d>>=w,d-=w,0===i.have){e.msg="invalid bit length repeat",i.mode=30;break}x=i.lens[i.have-1],h=3+(3&l),l>>>=2,d-=2}else if(17===_){for(E=w+3;d>>=w)),l>>>=3,d-=3}else{for(E=w+7;d>>=w)),l>>>=7,d-=7}if(i.have+h>i.nlen+i.ndist){e.msg="invalid bit length repeat",i.mode=30;break}for(;h--;)i.lens[i.have++]=x}}if(30===i.mode)break;if(0===i.lens[256]){e.msg="invalid code -- missing end-of-block",i.mode=30;break}if(i.lenbits=9,S={bits:i.lenbits},y=C(I,i.lens,0,i.nlen,i.lencode,0,i.work,S),i.lenbits=S.bits,y){e.msg="invalid literal/lengths set",i.mode=30;break}if(i.distbits=6,i.distcode=i.distdyn,S={bits:i.distbits},y=C(D,i.lens,i.nlen,i.ndist,i.distcode,0,i.work,S),i.distbits=S.bits,y){e.msg="invalid distances set",i.mode=30;break}if(i.mode=20,6===t)break e;case 20:i.mode=21;case 21:if(6<=s&&258<=f){e.next_out=o,e.avail_out=f,e.next_in=r,e.avail_in=s,i.hold=l,i.bits=d,O(e,u),o=e.next_out,a=e.output,f=e.avail_out,r=e.next_in,n=e.input,s=e.avail_in,l=i.hold,d=i.bits,12===i.mode&&(i.back=-1);break}for(i.back=0;k=(Z=i.lencode[l&(1<>>16&255,_=65535&Z,!((w=Z>>>24)<=d);){if(0===s)break e;s--,l+=n[r++]<>g)])>>>16&255,_=65535&Z,!(g+(w=Z>>>24)<=d);){if(0===s)break e;s--,l+=n[r++]<>>=g,d-=g,i.back+=g}if(l>>>=w,d-=w,i.back+=w,i.length=_,0===k){i.mode=26;break}if(32&k){i.back=-1,i.mode=12;break}if(64&k){e.msg="invalid literal/length code",i.mode=30;break}i.extra=15&k,i.mode=22;case 22:if(i.extra){for(E=i.extra;d>>=i.extra,d-=i.extra,i.back+=i.extra}i.was=i.length,i.mode=23;case 23:for(;k=(Z=i.distcode[l&(1<>>16&255,_=65535&Z,!((w=Z>>>24)<=d);){if(0===s)break e;s--,l+=n[r++]<>g)])>>>16&255,_=65535&Z,!(g+(w=Z>>>24)<=d);){if(0===s)break e;s--,l+=n[r++]<>>=g,d-=g,i.back+=g}if(l>>>=w,d-=w,i.back+=w,64&k){e.msg="invalid distance code",i.mode=30;break}i.offset=_,i.extra=15&k,i.mode=24;case 24:if(i.extra){for(E=i.extra;d>>=i.extra,d-=i.extra,i.back+=i.extra}if(i.offset>i.dmax){e.msg="invalid distance too far back",i.mode=30;break}i.mode=25;case 25:if(0===f)break e;if(h=u-f,i.offset>h){if((h=i.offset-h)>i.whave&&i.sane){e.msg="invalid distance too far back",i.mode=30;break}h>i.wnext?(h-=i.wnext,b=i.wsize-h):b=i.wnext-h,h>i.length&&(h=i.length),m=i.window}else m=a,b=o-i.offset,h=i.length;for(fh?(m=O[C+o[g]],w=A[z+o[g]]):(m=96,w=0),f=1<<_-S,v=l=1<>S)+(l-=f)]=b<<24|m<<16|w|0,0!==l;);for(f=1<<_-1;B&f;)f>>=1;if(0!==f?(B&=f-1,B+=f):B=0,g++,0==--R[_]){if(_===p)break;_=t[i+o[g]]}if(x<_&&(B&c)!==d){for(0===S&&(S=x),u+=v,E=1<<(y=_-S);y+S1){thisProgram=process["argv"][1].replace(/\\/g,"/")}arguments_=process["argv"].slice(2);if(typeof module!=="undefined"){module["exports"]=Module}process["on"]("uncaughtException",function(ex){if(!(ex instanceof ExitStatus)){throw ex}});process["on"]("unhandledRejection",abort);quit_=function(status){process["exit"](status)};Module["inspect"]=function(){return"[Emscripten Module object]"}}else if(ENVIRONMENT_IS_SHELL){if(typeof read!="undefined"){read_=function shell_read(f){return read(f)}}readBinary=function readBinary(f){var data;if(typeof readbuffer==="function"){return new Uint8Array(readbuffer(f))}data=read(f,"binary");assert(typeof data==="object");return data};if(typeof scriptArgs!="undefined"){arguments_=scriptArgs}else if(typeof arguments!="undefined"){arguments_=arguments}if(typeof quit==="function"){quit_=function(status){quit(status)}}if(typeof print!=="undefined"){if(typeof console==="undefined")console={};console.log=print;console.warn=console.error=typeof printErr!=="undefined"?printErr:print}}else if(ENVIRONMENT_IS_WEB||ENVIRONMENT_IS_WORKER){if(ENVIRONMENT_IS_WORKER){scriptDirectory=self.location.href}else if(document.currentScript){scriptDirectory=document.currentScript.src}if(scriptDirectory.indexOf("blob:")!==0){scriptDirectory=scriptDirectory.substr(0,scriptDirectory.lastIndexOf("/")+1)}else{scriptDirectory=""}read_=function shell_read(url){var xhr=new XMLHttpRequest;xhr.open("GET",url,false);xhr.send(null);return xhr.responseText};if(ENVIRONMENT_IS_WORKER){readBinary=function readBinary(url){var xhr=new XMLHttpRequest;xhr.open("GET",url,false);xhr.responseType="arraybuffer";xhr.send(null);return new Uint8Array(xhr.response)}}readAsync=function readAsync(url,onload,onerror){var xhr=new XMLHttpRequest;xhr.open("GET",url,true);xhr.responseType="arraybuffer";xhr.onload=function xhr_onload(){if(xhr.status==200||xhr.status==0&&xhr.response){onload(xhr.response);return}onerror()};xhr.onerror=onerror;xhr.send(null)};setWindowTitle=function(title){document.title=title}}else{}var out=Module["print"]||console.log.bind(console);var err=Module["printErr"]||console.warn.bind(console);for(key in moduleOverrides){if(moduleOverrides.hasOwnProperty(key)){Module[key]=moduleOverrides[key]}}moduleOverrides=null;if(Module["arguments"])arguments_=Module["arguments"];if(Module["thisProgram"])thisProgram=Module["thisProgram"];if(Module["quit"])quit_=Module["quit"];function dynamicAlloc(size){var ret=HEAP32[DYNAMICTOP_PTR>>2];var end=ret+size+15&-16;if(end>_emscripten_get_heap_size()){abort()}HEAP32[DYNAMICTOP_PTR>>2]=end;return ret}function getNativeTypeSize(type){switch(type){case"i1":case"i8":return 1;case"i16":return 2;case"i32":return 4;case"i64":return 8;case"float":return 4;case"double":return 8;default:{if(type[type.length-1]==="*"){return 4}else if(type[0]==="i"){var bits=parseInt(type.substr(1));assert(bits%8===0,"getNativeTypeSize invalid bits "+bits+", type "+type);return bits/8}else{return 0}}}}var asm2wasmImports={"f64-rem":function(x,y){return x%y},"debugger":function(){}};var functionPointers=new Array(0);var tempRet0=0;var setTempRet0=function(value){tempRet0=value};var getTempRet0=function(){return tempRet0};var wasmBinary;if(Module["wasmBinary"])wasmBinary=Module["wasmBinary"];var noExitRuntime;if(Module["noExitRuntime"])noExitRuntime=Module["noExitRuntime"];if(typeof WebAssembly!=="object"){err("no native wasm support detected")}function setValue(ptr,value,type,noSafe){type=type||"i8";if(type.charAt(type.length-1)==="*")type="i32";switch(type){case"i1":HEAP8[ptr>>0]=value;break;case"i8":HEAP8[ptr>>0]=value;break;case"i16":HEAP16[ptr>>1]=value;break;case"i32":HEAP32[ptr>>2]=value;break;case"i64":tempI64=[value>>>0,(tempDouble=value,+Math_abs(tempDouble)>=1?tempDouble>0?(Math_min(+Math_floor(tempDouble/4294967296),4294967295)|0)>>>0:~~+Math_ceil((tempDouble-+(~~tempDouble>>>0))/4294967296)>>>0:0)],HEAP32[ptr>>2]=tempI64[0],HEAP32[ptr+4>>2]=tempI64[1];break;case"float":HEAPF32[ptr>>2]=value;break;case"double":HEAPF64[ptr>>3]=value;break;default:abort("invalid type for setValue: "+type)}}var wasmMemory;var wasmTable=new WebAssembly.Table({"initial":684,"maximum":684,"element":"anyfunc"});var ABORT=false;var EXITSTATUS=0;function assert(condition,text){if(!condition){abort("Assertion failed: "+text)}}function getCFunc(ident){var func=Module["_"+ident];assert(func,"Cannot call unknown function "+ident+", make sure it is exported");return func}function ccall(ident,returnType,argTypes,args,opts){var toC={"string":function(str){var ret=0;if(str!==null&&str!==undefined&&str!==0){var len=(str.length<<2)+1;ret=stackAlloc(len);stringToUTF8(str,ret,len)}return ret},"array":function(arr){var ret=stackAlloc(arr.length);writeArrayToMemory(arr,ret);return ret}};function convertReturnValue(ret){if(returnType==="string")return UTF8ToString(ret);if(returnType==="boolean")return Boolean(ret);return ret}var func=getCFunc(ident);var cArgs=[];var stack=0;if(args){for(var i=0;i>2]=0}stop=ret+size;while(ptr>0]=0}return ret}if(singleType==="i8"){if(slab.subarray||slab.slice){HEAPU8.set(slab,ret)}else{HEAPU8.set(new Uint8Array(slab),ret)}return ret}var i=0,type,typeSize,previousType;while(i=endIdx))++endPtr;if(endPtr-idx>16&&u8Array.subarray&&UTF8Decoder){return UTF8Decoder.decode(u8Array.subarray(idx,endPtr))}else{var str="";while(idx>10,56320|ch&1023)}}}return str}function UTF8ToString(ptr,maxBytesToRead){return ptr?UTF8ArrayToString(HEAPU8,ptr,maxBytesToRead):""}function stringToUTF8Array(str,outU8Array,outIdx,maxBytesToWrite){if(!(maxBytesToWrite>0))return 0;var startIdx=outIdx;var endIdx=outIdx+maxBytesToWrite-1;for(var i=0;i=55296&&u<=57343){var u1=str.charCodeAt(++i);u=65536+((u&1023)<<10)|u1&1023}if(u<=127){if(outIdx>=endIdx)break;outU8Array[outIdx++]=u}else if(u<=2047){if(outIdx+1>=endIdx)break;outU8Array[outIdx++]=192|u>>6;outU8Array[outIdx++]=128|u&63}else if(u<=65535){if(outIdx+2>=endIdx)break;outU8Array[outIdx++]=224|u>>12;outU8Array[outIdx++]=128|u>>6&63;outU8Array[outIdx++]=128|u&63}else{if(outIdx+3>=endIdx)break;outU8Array[outIdx++]=240|u>>18;outU8Array[outIdx++]=128|u>>12&63;outU8Array[outIdx++]=128|u>>6&63;outU8Array[outIdx++]=128|u&63}}outU8Array[outIdx]=0;return outIdx-startIdx}function stringToUTF8(str,outPtr,maxBytesToWrite){return stringToUTF8Array(str,HEAPU8,outPtr,maxBytesToWrite)}function lengthBytesUTF8(str){var len=0;for(var i=0;i=55296&&u<=57343)u=65536+((u&1023)<<10)|str.charCodeAt(++i)&1023;if(u<=127)++len;else if(u<=2047)len+=2;else if(u<=65535)len+=3;else len+=4}return len}var UTF16Decoder=typeof TextDecoder!=="undefined"?new TextDecoder("utf-16le"):undefined;function allocateUTF8(str){var size=lengthBytesUTF8(str)+1;var ret=_malloc(size);if(ret)stringToUTF8Array(str,HEAP8,ret,size);return ret}function writeArrayToMemory(array,buffer){HEAP8.set(array,buffer)}var WASM_PAGE_SIZE=65536;function alignUp(x,multiple){if(x%multiple>0){x+=multiple-x%multiple}return x}var buffer,HEAP8,HEAPU8,HEAP16,HEAPU16,HEAP32,HEAPU32,HEAPF32,HEAPF64;function updateGlobalBufferAndViews(buf){buffer=buf;Module["HEAP8"]=HEAP8=new Int8Array(buf);Module["HEAP16"]=HEAP16=new Int16Array(buf);Module["HEAP32"]=HEAP32=new Int32Array(buf);Module["HEAPU8"]=HEAPU8=new Uint8Array(buf);Module["HEAPU16"]=HEAPU16=new Uint16Array(buf);Module["HEAPU32"]=HEAPU32=new Uint32Array(buf);Module["HEAPF32"]=HEAPF32=new Float32Array(buf);Module["HEAPF64"]=HEAPF64=new Float64Array(buf)}var DYNAMIC_BASE=5316768,DYNAMICTOP_PTR=73680;var INITIAL_TOTAL_MEMORY=Module["TOTAL_MEMORY"]||16777216;if(Module["wasmMemory"]){wasmMemory=Module["wasmMemory"]}else{wasmMemory=new WebAssembly.Memory({"initial":INITIAL_TOTAL_MEMORY/WASM_PAGE_SIZE})}if(wasmMemory){buffer=wasmMemory.buffer}INITIAL_TOTAL_MEMORY=buffer.byteLength;updateGlobalBufferAndViews(buffer);HEAP32[DYNAMICTOP_PTR>>2]=DYNAMIC_BASE;function callRuntimeCallbacks(callbacks){while(callbacks.length>0){var callback=callbacks.shift();if(typeof callback=="function"){callback();continue}var func=callback.func;if(typeof func==="number"){if(callback.arg===undefined){Module["dynCall_v"](func)}else{Module["dynCall_vi"](func,callback.arg)}}else{func(callback.arg===undefined?null:callback.arg)}}}var __ATPRERUN__=[];var __ATINIT__=[];var __ATMAIN__=[];var __ATEXIT__=[];var __ATPOSTRUN__=[];var runtimeInitialized=false;function preRun(){if(Module["preRun"]){if(typeof Module["preRun"]=="function")Module["preRun"]=[Module["preRun"]];while(Module["preRun"].length){addOnPreRun(Module["preRun"].shift())}}callRuntimeCallbacks(__ATPRERUN__)}function initRuntime(){runtimeInitialized=true;if(!Module["noFSInit"]&&!FS.init.initialized)FS.init();TTY.init();callRuntimeCallbacks(__ATINIT__)}function preMain(){FS.ignorePermissions=false;callRuntimeCallbacks(__ATMAIN__)}function postRun(){if(Module["postRun"]){if(typeof Module["postRun"]=="function")Module["postRun"]=[Module["postRun"]];while(Module["postRun"].length){addOnPostRun(Module["postRun"].shift())}}callRuntimeCallbacks(__ATPOSTRUN__)}function addOnPreRun(cb){__ATPRERUN__.unshift(cb)}function addOnPostRun(cb){__ATPOSTRUN__.unshift(cb)}var Math_abs=Math.abs;var Math_ceil=Math.ceil;var Math_floor=Math.floor;var Math_min=Math.min;var runDependencies=0;var runDependencyWatcher=null;var dependenciesFulfilled=null;function getUniqueRunDependency(id){return id}function addRunDependency(id){runDependencies++;if(Module["monitorRunDependencies"]){Module["monitorRunDependencies"](runDependencies)}}function removeRunDependency(id){runDependencies--;if(Module["monitorRunDependencies"]){Module["monitorRunDependencies"](runDependencies)}if(runDependencies==0){if(runDependencyWatcher!==null){clearInterval(runDependencyWatcher);runDependencyWatcher=null}if(dependenciesFulfilled){var callback=dependenciesFulfilled;dependenciesFulfilled=null;callback()}}}Module["preloadedImages"]={};Module["preloadedAudios"]={};function abort(what){if(Module["onAbort"]){Module["onAbort"](what)}what+="";out(what);err(what);ABORT=true;EXITSTATUS=1;throw"abort("+what+"). Build with -s ASSERTIONS=1 for more info."}var dataURIPrefix="data:application/octet-stream;base64,";function isDataURI(filename){return String.prototype.startsWith?filename.startsWith(dataURIPrefix):filename.indexOf(dataURIPrefix)===0}var wasmBinaryFile="rlottie-wasm.wasm";if(!isDataURI(wasmBinaryFile)){wasmBinaryFile=locateFile(wasmBinaryFile)}function getBinary(){try{if(wasmBinary){return new Uint8Array(wasmBinary)}if(readBinary){return readBinary(wasmBinaryFile)}else{throw"both async and sync fetching of the wasm failed"}}catch(err){abort(err)}}function getBinaryPromise(){if(!wasmBinary&&(ENVIRONMENT_IS_WEB||ENVIRONMENT_IS_WORKER)&&typeof fetch==="function"){return fetch(wasmBinaryFile,{credentials:"same-origin"}).then(function(response){if(!response["ok"]){throw"failed to load wasm binary file at '"+wasmBinaryFile+"'"}return response["arrayBuffer"]()}).catch(function(){return getBinary()})}return new Promise(function(resolve,reject){resolve(getBinary())})}function createWasm(){var info={"env":asmLibraryArg,"wasi_unstable":asmLibraryArg,"global":{"NaN":NaN,Infinity:Infinity},"global.Math":Math,"asm2wasm":asm2wasmImports};function receiveInstance(instance,module){var exports=instance.exports;Module["asm"]=exports;removeRunDependency("wasm-instantiate")}addRunDependency("wasm-instantiate");function receiveInstantiatedSource(output){receiveInstance(output["instance"])}function instantiateArrayBuffer(receiver){return getBinaryPromise().then(function(binary){return WebAssembly.instantiate(binary,info)}).then(receiver,function(reason){err("failed to asynchronously prepare wasm: "+reason);abort(reason)})}function instantiateAsync(){if(!wasmBinary&&typeof WebAssembly.instantiateStreaming==="function"&&!isDataURI(wasmBinaryFile)&&typeof fetch==="function"){fetch(wasmBinaryFile,{credentials:"same-origin"}).then(function(response){var result=WebAssembly.instantiateStreaming(response,info);return result.then(receiveInstantiatedSource,function(reason){err("wasm streaming compile failed: "+reason);err("falling back to ArrayBuffer instantiation");instantiateArrayBuffer(receiveInstantiatedSource)})})}else{return instantiateArrayBuffer(receiveInstantiatedSource)}}if(Module["instantiateWasm"]){try{var exports=Module["instantiateWasm"](info,receiveInstance);return exports}catch(e){err("Module.instantiateWasm callback failed with error: "+e);return false}}instantiateAsync();return{}}Module["asm"]=createWasm;var tempDouble;var tempI64;__ATINIT__.push({func:function(){__GLOBAL__sub_I_rlottie_wrapper_cpp()}});function demangle(func){return func}function demangleAll(text){var regex=/\b__Z[\w\d_]+/g;return text.replace(regex,function(x){var y=demangle(x);return x===y?x:y+" ["+x+"]"})}function jsStackTrace(){var err=new Error;if(!err.stack){try{throw new Error(0)}catch(e){err=e}if(!err.stack){return"(no stack trace available)"}}return err.stack.toString()}function stackTrace(){var js=jsStackTrace();if(Module["extraStackTrace"])js+="\n"+Module["extraStackTrace"]();return demangleAll(js)}function ___assert_fail(condition,filename,line,func){abort("Assertion failed: "+UTF8ToString(condition)+", at: "+[filename?UTF8ToString(filename):"unknown filename",line,func?UTF8ToString(func):"unknown function"])}function ___cxa_pure_virtual(){ABORT=true;throw"Pure virtual function called!"}function _atexit(func,arg){__ATEXIT__.unshift({func:func,arg:arg})}function ___cxa_thread_atexit(){return _atexit.apply(null,arguments)}function ___cxa_uncaught_exceptions(){err("missing function: __cxa_uncaught_exceptions");abort(-1)}function ___lock(){}function ___setErrNo(value){if(Module["___errno_location"])HEAP32[Module["___errno_location"]()>>2]=value;return value}function ___map_file(pathname,size){___setErrNo(1);return-1}var PATH={splitPath:function(filename){var splitPathRe=/^(\/?|)([\s\S]*?)((?:\.{1,2}|[^\/]+?|)(\.[^.\/]*|))(?:[\/]*)$/;return splitPathRe.exec(filename).slice(1)},normalizeArray:function(parts,allowAboveRoot){var up=0;for(var i=parts.length-1;i>=0;i--){var last=parts[i];if(last==="."){parts.splice(i,1)}else if(last===".."){parts.splice(i,1);up++}else if(up){parts.splice(i,1);up--}}if(allowAboveRoot){for(;up;up--){parts.unshift("..")}}return parts},normalize:function(path){var isAbsolute=path.charAt(0)==="/",trailingSlash=path.substr(-1)==="/";path=PATH.normalizeArray(path.split("/").filter(function(p){return!!p}),!isAbsolute).join("/");if(!path&&!isAbsolute){path="."}if(path&&trailingSlash){path+="/"}return(isAbsolute?"/":"")+path},dirname:function(path){var result=PATH.splitPath(path),root=result[0],dir=result[1];if(!root&&!dir){return"."}if(dir){dir=dir.substr(0,dir.length-1)}return root+dir},basename:function(path){if(path==="/")return"/";var lastSlash=path.lastIndexOf("/");if(lastSlash===-1)return path;return path.substr(lastSlash+1)},extname:function(path){return PATH.splitPath(path)[3]},join:function(){var paths=Array.prototype.slice.call(arguments,0);return PATH.normalize(paths.join("/"))},join2:function(l,r){return PATH.normalize(l+"/"+r)}};var PATH_FS={resolve:function(){var resolvedPath="",resolvedAbsolute=false;for(var i=arguments.length-1;i>=-1&&!resolvedAbsolute;i--){var path=i>=0?arguments[i]:FS.cwd();if(typeof path!=="string"){throw new TypeError("Arguments to path.resolve must be strings")}else if(!path){return""}resolvedPath=path+"/"+resolvedPath;resolvedAbsolute=path.charAt(0)==="/"}resolvedPath=PATH.normalizeArray(resolvedPath.split("/").filter(function(p){return!!p}),!resolvedAbsolute).join("/");return(resolvedAbsolute?"/":"")+resolvedPath||"."},relative:function(from,to){from=PATH_FS.resolve(from).substr(1);to=PATH_FS.resolve(to).substr(1);function trim(arr){var start=0;for(;start=0;end--){if(arr[end]!=="")break}if(start>end)return[];return arr.slice(start,end-start+1)}var fromParts=trim(from.split("/"));var toParts=trim(to.split("/"));var length=Math.min(fromParts.length,toParts.length);var samePartsLength=length;for(var i=0;i0){result=buf.slice(0,bytesRead).toString("utf-8")}else{result=null}}else if(typeof window!="undefined"&&typeof window.prompt=="function"){result=window.prompt("Input: ");if(result!==null){result+="\n"}}else if(typeof readline=="function"){result=readline();if(result!==null){result+="\n"}}if(!result){return null}tty.input=intArrayFromString(result,true)}return tty.input.shift()},put_char:function(tty,val){if(val===null||val===10){out(UTF8ArrayToString(tty.output,0));tty.output=[]}else{if(val!=0)tty.output.push(val)}},flush:function(tty){if(tty.output&&tty.output.length>0){out(UTF8ArrayToString(tty.output,0));tty.output=[]}}},default_tty1_ops:{put_char:function(tty,val){if(val===null||val===10){err(UTF8ArrayToString(tty.output,0));tty.output=[]}else{if(val!=0)tty.output.push(val)}},flush:function(tty){if(tty.output&&tty.output.length>0){err(UTF8ArrayToString(tty.output,0));tty.output=[]}}}};var MEMFS={ops_table:null,mount:function(mount){return MEMFS.createNode(null,"/",16384|511,0)},createNode:function(parent,name,mode,dev){if(FS.isBlkdev(mode)||FS.isFIFO(mode)){throw new FS.ErrnoError(1)}if(!MEMFS.ops_table){MEMFS.ops_table={dir:{node:{getattr:MEMFS.node_ops.getattr,setattr:MEMFS.node_ops.setattr,lookup:MEMFS.node_ops.lookup,mknod:MEMFS.node_ops.mknod,rename:MEMFS.node_ops.rename,unlink:MEMFS.node_ops.unlink,rmdir:MEMFS.node_ops.rmdir,readdir:MEMFS.node_ops.readdir,symlink:MEMFS.node_ops.symlink},stream:{llseek:MEMFS.stream_ops.llseek}},file:{node:{getattr:MEMFS.node_ops.getattr,setattr:MEMFS.node_ops.setattr},stream:{llseek:MEMFS.stream_ops.llseek,read:MEMFS.stream_ops.read,write:MEMFS.stream_ops.write,allocate:MEMFS.stream_ops.allocate,mmap:MEMFS.stream_ops.mmap,msync:MEMFS.stream_ops.msync}},link:{node:{getattr:MEMFS.node_ops.getattr,setattr:MEMFS.node_ops.setattr,readlink:MEMFS.node_ops.readlink},stream:{}},chrdev:{node:{getattr:MEMFS.node_ops.getattr,setattr:MEMFS.node_ops.setattr},stream:FS.chrdev_stream_ops}}}var node=FS.createNode(parent,name,mode,dev);if(FS.isDir(node.mode)){node.node_ops=MEMFS.ops_table.dir.node;node.stream_ops=MEMFS.ops_table.dir.stream;node.contents={}}else if(FS.isFile(node.mode)){node.node_ops=MEMFS.ops_table.file.node;node.stream_ops=MEMFS.ops_table.file.stream;node.usedBytes=0;node.contents=null}else if(FS.isLink(node.mode)){node.node_ops=MEMFS.ops_table.link.node;node.stream_ops=MEMFS.ops_table.link.stream}else if(FS.isChrdev(node.mode)){node.node_ops=MEMFS.ops_table.chrdev.node;node.stream_ops=MEMFS.ops_table.chrdev.stream}node.timestamp=Date.now();if(parent){parent.contents[name]=node}return node},getFileDataAsRegularArray:function(node){if(node.contents&&node.contents.subarray){var arr=[];for(var i=0;i=newCapacity)return;var CAPACITY_DOUBLING_MAX=1024*1024;newCapacity=Math.max(newCapacity,prevCapacity*(prevCapacity0)node.contents.set(oldContents.subarray(0,node.usedBytes),0);return},resizeFileStorage:function(node,newSize){if(node.usedBytes==newSize)return;if(newSize==0){node.contents=null;node.usedBytes=0;return}if(!node.contents||node.contents.subarray){var oldContents=node.contents;node.contents=new Uint8Array(new ArrayBuffer(newSize));if(oldContents){node.contents.set(oldContents.subarray(0,Math.min(newSize,node.usedBytes)))}node.usedBytes=newSize;return}if(!node.contents)node.contents=[];if(node.contents.length>newSize)node.contents.length=newSize;else while(node.contents.length=stream.node.usedBytes)return 0;var size=Math.min(stream.node.usedBytes-position,length);if(size>8&&contents.subarray){buffer.set(contents.subarray(position,position+size),offset)}else{for(var i=0;i0||position+lengthe2.timestamp){create.push(key);total++}});var remove=[];Object.keys(dst.entries).forEach(function(key){var e=dst.entries[key];var e2=src.entries[key];if(!e2){remove.push(key);total++}});if(!total){return callback(null)}var errored=false;var db=src.type==="remote"?src.db:dst.db;var transaction=db.transaction([IDBFS.DB_STORE_NAME],"readwrite");var store=transaction.objectStore(IDBFS.DB_STORE_NAME);function done(err){if(err&&!errored){errored=true;return callback(err)}}transaction.onerror=function(e){done(this.error);e.preventDefault()};transaction.oncomplete=function(e){if(!errored){callback(null)}};create.sort().forEach(function(path){if(dst.type==="local"){IDBFS.loadRemoteEntry(store,path,function(err,entry){if(err)return done(err);IDBFS.storeLocalEntry(path,entry,done)})}else{IDBFS.loadLocalEntry(path,function(err,entry){if(err)return done(err);IDBFS.storeRemoteEntry(store,path,entry,done)})}});remove.sort().reverse().forEach(function(path){if(dst.type==="local"){IDBFS.removeLocalEntry(path,done)}else{IDBFS.removeRemoteEntry(store,path,done)}})}};var NODEFS={isWindows:false,staticInit:function(){NODEFS.isWindows=!!process.platform.match(/^win/);var flags=process["binding"]("constants");if(flags["fs"]){flags=flags["fs"]}NODEFS.flagsForNodeMap={1024:flags["O_APPEND"],64:flags["O_CREAT"],128:flags["O_EXCL"],0:flags["O_RDONLY"],2:flags["O_RDWR"],4096:flags["O_SYNC"],512:flags["O_TRUNC"],1:flags["O_WRONLY"]}},bufferFrom:function(arrayBuffer){return Buffer["alloc"]?Buffer.from(arrayBuffer):new Buffer(arrayBuffer)},mount:function(mount){assert(ENVIRONMENT_HAS_NODE);return NODEFS.createNode(null,"/",NODEFS.getMode(mount.opts.root),0)},createNode:function(parent,name,mode,dev){if(!FS.isDir(mode)&&!FS.isFile(mode)&&!FS.isLink(mode)){throw new FS.ErrnoError(22)}var node=FS.createNode(parent,name,mode);node.node_ops=NODEFS.node_ops;node.stream_ops=NODEFS.stream_ops;return node},getMode:function(path){var stat;try{stat=fs.lstatSync(path);if(NODEFS.isWindows){stat.mode=stat.mode|(stat.mode&292)>>2}}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}return stat.mode},realPath:function(node){var parts=[];while(node.parent!==node){parts.push(node.name);node=node.parent}parts.push(node.mount.opts.root);parts.reverse();return PATH.join.apply(null,parts)},flagsForNode:function(flags){flags&=~2097152;flags&=~2048;flags&=~32768;flags&=~524288;var newFlags=0;for(var k in NODEFS.flagsForNodeMap){if(flags&k){newFlags|=NODEFS.flagsForNodeMap[k];flags^=k}}if(!flags){return newFlags}else{throw new FS.ErrnoError(22)}},node_ops:{getattr:function(node){var path=NODEFS.realPath(node);var stat;try{stat=fs.lstatSync(path)}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}if(NODEFS.isWindows&&!stat.blksize){stat.blksize=4096}if(NODEFS.isWindows&&!stat.blocks){stat.blocks=(stat.size+stat.blksize-1)/stat.blksize|0}return{dev:stat.dev,ino:stat.ino,mode:stat.mode,nlink:stat.nlink,uid:stat.uid,gid:stat.gid,rdev:stat.rdev,size:stat.size,atime:stat.atime,mtime:stat.mtime,ctime:stat.ctime,blksize:stat.blksize,blocks:stat.blocks}},setattr:function(node,attr){var path=NODEFS.realPath(node);try{if(attr.mode!==undefined){fs.chmodSync(path,attr.mode);node.mode=attr.mode}if(attr.timestamp!==undefined){var date=new Date(attr.timestamp);fs.utimesSync(path,date,date)}if(attr.size!==undefined){fs.truncateSync(path,attr.size)}}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},lookup:function(parent,name){var path=PATH.join2(NODEFS.realPath(parent),name);var mode=NODEFS.getMode(path);return NODEFS.createNode(parent,name,mode)},mknod:function(parent,name,mode,dev){var node=NODEFS.createNode(parent,name,mode,dev);var path=NODEFS.realPath(node);try{if(FS.isDir(node.mode)){fs.mkdirSync(path,node.mode)}else{fs.writeFileSync(path,"",{mode:node.mode})}}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}return node},rename:function(oldNode,newDir,newName){var oldPath=NODEFS.realPath(oldNode);var newPath=PATH.join2(NODEFS.realPath(newDir),newName);try{fs.renameSync(oldPath,newPath)}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},unlink:function(parent,name){var path=PATH.join2(NODEFS.realPath(parent),name);try{fs.unlinkSync(path)}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},rmdir:function(parent,name){var path=PATH.join2(NODEFS.realPath(parent),name);try{fs.rmdirSync(path)}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},readdir:function(node){var path=NODEFS.realPath(node);try{return fs.readdirSync(path)}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},symlink:function(parent,newName,oldPath){var newPath=PATH.join2(NODEFS.realPath(parent),newName);try{fs.symlinkSync(oldPath,newPath)}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},readlink:function(node){var path=NODEFS.realPath(node);try{path=fs.readlinkSync(path);path=NODEJS_PATH.relative(NODEJS_PATH.resolve(node.mount.opts.root),path);return path}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}}},stream_ops:{open:function(stream){var path=NODEFS.realPath(stream.node);try{if(FS.isFile(stream.node.mode)){stream.nfd=fs.openSync(path,NODEFS.flagsForNode(stream.flags))}}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},close:function(stream){try{if(FS.isFile(stream.node.mode)&&stream.nfd){fs.closeSync(stream.nfd)}}catch(e){if(!e.code)throw e;throw new FS.ErrnoError(-e.errno)}},read:function(stream,buffer,offset,length,position){if(length===0)return 0;try{return fs.readSync(stream.nfd,NODEFS.bufferFrom(buffer.buffer),offset,length,position)}catch(e){throw new FS.ErrnoError(-e.errno)}},write:function(stream,buffer,offset,length,position){try{return fs.writeSync(stream.nfd,NODEFS.bufferFrom(buffer.buffer),offset,length,position)}catch(e){throw new FS.ErrnoError(-e.errno)}},llseek:function(stream,offset,whence){var position=offset;if(whence===1){position+=stream.position}else if(whence===2){if(FS.isFile(stream.node.mode)){try{var stat=fs.fstatSync(stream.nfd);position+=stat.size}catch(e){throw new FS.ErrnoError(-e.errno)}}}if(position<0){throw new FS.ErrnoError(22)}return position}}};var WORKERFS={DIR_MODE:16895,FILE_MODE:33279,reader:null,mount:function(mount){assert(ENVIRONMENT_IS_WORKER);if(!WORKERFS.reader)WORKERFS.reader=new FileReaderSync;var root=WORKERFS.createNode(null,"/",WORKERFS.DIR_MODE,0);var createdParents={};function ensureParent(path){var parts=path.split("/");var parent=root;for(var i=0;i=stream.node.size)return 0;var chunk=stream.node.contents.slice(position,position+length);var ab=WORKERFS.reader.readAsArrayBuffer(chunk);buffer.set(new Uint8Array(ab),offset);return chunk.size},write:function(stream,buffer,offset,length,position){throw new FS.ErrnoError(5)},llseek:function(stream,offset,whence){var position=offset;if(whence===1){position+=stream.position}else if(whence===2){if(FS.isFile(stream.node.mode)){position+=stream.node.size}}if(position<0){throw new FS.ErrnoError(22)}return position}}};var FS={root:null,mounts:[],devices:{},streams:[],nextInode:1,nameTable:null,currentPath:"/",initialized:false,ignorePermissions:true,trackingDelegate:{},tracking:{openFlags:{READ:1,WRITE:2}},ErrnoError:null,genericErrors:{},filesystems:null,syncFSRequests:0,handleFSError:function(e){if(!(e instanceof FS.ErrnoError))throw e+" : "+stackTrace();return ___setErrNo(e.errno)},lookupPath:function(path,opts){path=PATH_FS.resolve(FS.cwd(),path);opts=opts||{};if(!path)return{path:"",node:null};var defaults={follow_mount:true,recurse_count:0};for(var key in defaults){if(opts[key]===undefined){opts[key]=defaults[key]}}if(opts.recurse_count>8){throw new FS.ErrnoError(40)}var parts=PATH.normalizeArray(path.split("/").filter(function(p){return!!p}),false);var current=FS.root;var current_path="/";for(var i=0;i40){throw new FS.ErrnoError(40)}}}}return{path:current_path,node:current}},getPath:function(node){var path;while(true){if(FS.isRoot(node)){var mount=node.mount.mountpoint;if(!path)return mount;return mount[mount.length-1]!=="/"?mount+"/"+path:mount+path}path=path?node.name+"/"+path:node.name;node=node.parent}},hashName:function(parentid,name){var hash=0;for(var i=0;i>>0)%FS.nameTable.length},hashAddNode:function(node){var hash=FS.hashName(node.parent.id,node.name);node.name_next=FS.nameTable[hash];FS.nameTable[hash]=node},hashRemoveNode:function(node){var hash=FS.hashName(node.parent.id,node.name);if(FS.nameTable[hash]===node){FS.nameTable[hash]=node.name_next}else{var current=FS.nameTable[hash];while(current){if(current.name_next===node){current.name_next=node.name_next;break}current=current.name_next}}},lookupNode:function(parent,name){var err=FS.mayLookup(parent);if(err){throw new FS.ErrnoError(err,parent)}var hash=FS.hashName(parent.id,name);for(var node=FS.nameTable[hash];node;node=node.name_next){var nodeName=node.name;if(node.parent.id===parent.id&&nodeName===name){return node}}return FS.lookup(parent,name)},createNode:function(parent,name,mode,rdev){if(!FS.FSNode){FS.FSNode=function(parent,name,mode,rdev){if(!parent){parent=this}this.parent=parent;this.mount=parent.mount;this.mounted=null;this.id=FS.nextInode++;this.name=name;this.mode=mode;this.node_ops={};this.stream_ops={};this.rdev=rdev};FS.FSNode.prototype={};var readMode=292|73;var writeMode=146;Object.defineProperties(FS.FSNode.prototype,{read:{get:function(){return(this.mode&readMode)===readMode},set:function(val){val?this.mode|=readMode:this.mode&=~readMode}},write:{get:function(){return(this.mode&writeMode)===writeMode},set:function(val){val?this.mode|=writeMode:this.mode&=~writeMode}},isFolder:{get:function(){return FS.isDir(this.mode)}},isDevice:{get:function(){return FS.isChrdev(this.mode)}}})}var node=new FS.FSNode(parent,name,mode,rdev);FS.hashAddNode(node);return node},destroyNode:function(node){FS.hashRemoveNode(node)},isRoot:function(node){return node===node.parent},isMountpoint:function(node){return!!node.mounted},isFile:function(mode){return(mode&61440)===32768},isDir:function(mode){return(mode&61440)===16384},isLink:function(mode){return(mode&61440)===40960},isChrdev:function(mode){return(mode&61440)===8192},isBlkdev:function(mode){return(mode&61440)===24576},isFIFO:function(mode){return(mode&61440)===4096},isSocket:function(mode){return(mode&49152)===49152},flagModes:{"r":0,"rs":1052672,"r+":2,"w":577,"wx":705,"xw":705,"w+":578,"wx+":706,"xw+":706,"a":1089,"ax":1217,"xa":1217,"a+":1090,"ax+":1218,"xa+":1218},modeStringToFlags:function(str){var flags=FS.flagModes[str];if(typeof flags==="undefined"){throw new Error("Unknown file open mode: "+str)}return flags},flagsToPermissionString:function(flag){var perms=["r","w","rw"][flag&3];if(flag&512){perms+="w"}return perms},nodePermissions:function(node,perms){if(FS.ignorePermissions){return 0}if(perms.indexOf("r")!==-1&&!(node.mode&292)){return 13}else if(perms.indexOf("w")!==-1&&!(node.mode&146)){return 13}else if(perms.indexOf("x")!==-1&&!(node.mode&73)){return 13}return 0},mayLookup:function(dir){var err=FS.nodePermissions(dir,"x");if(err)return err;if(!dir.node_ops.lookup)return 13;return 0},mayCreate:function(dir,name){try{var node=FS.lookupNode(dir,name);return 17}catch(e){}return FS.nodePermissions(dir,"wx")},mayDelete:function(dir,name,isdir){var node;try{node=FS.lookupNode(dir,name)}catch(e){return e.errno}var err=FS.nodePermissions(dir,"wx");if(err){return err}if(isdir){if(!FS.isDir(node.mode)){return 20}if(FS.isRoot(node)||FS.getPath(node)===FS.cwd()){return 16}}else{if(FS.isDir(node.mode)){return 21}}return 0},mayOpen:function(node,flags){if(!node){return 2}if(FS.isLink(node.mode)){return 40}else if(FS.isDir(node.mode)){if(FS.flagsToPermissionString(flags)!=="r"||flags&512){return 21}}return FS.nodePermissions(node,FS.flagsToPermissionString(flags))},MAX_OPEN_FDS:4096,nextfd:function(fd_start,fd_end){fd_start=fd_start||0;fd_end=fd_end||FS.MAX_OPEN_FDS;for(var fd=fd_start;fd<=fd_end;fd++){if(!FS.streams[fd]){return fd}}throw new FS.ErrnoError(24)},getStream:function(fd){return FS.streams[fd]},createStream:function(stream,fd_start,fd_end){if(!FS.FSStream){FS.FSStream=function(){};FS.FSStream.prototype={};Object.defineProperties(FS.FSStream.prototype,{object:{get:function(){return this.node},set:function(val){this.node=val}},isRead:{get:function(){return(this.flags&2097155)!==1}},isWrite:{get:function(){return(this.flags&2097155)!==0}},isAppend:{get:function(){return this.flags&1024}}})}var newStream=new FS.FSStream;for(var p in stream){newStream[p]=stream[p]}stream=newStream;var fd=FS.nextfd(fd_start,fd_end);stream.fd=fd;FS.streams[fd]=stream;return stream},closeStream:function(fd){FS.streams[fd]=null},chrdev_stream_ops:{open:function(stream){var device=FS.getDevice(stream.node.rdev);stream.stream_ops=device.stream_ops;if(stream.stream_ops.open){stream.stream_ops.open(stream)}},llseek:function(){throw new FS.ErrnoError(29)}},major:function(dev){return dev>>8},minor:function(dev){return dev&255},makedev:function(ma,mi){return ma<<8|mi},registerDevice:function(dev,ops){FS.devices[dev]={stream_ops:ops}},getDevice:function(dev){return FS.devices[dev]},getMounts:function(mount){var mounts=[];var check=[mount];while(check.length){var m=check.pop();mounts.push(m);check.push.apply(check,m.mounts)}return mounts},syncfs:function(populate,callback){if(typeof populate==="function"){callback=populate;populate=false}FS.syncFSRequests++;if(FS.syncFSRequests>1){console.log("warning: "+FS.syncFSRequests+" FS.syncfs operations in flight at once, probably just doing extra work")}var mounts=FS.getMounts(FS.root.mount);var completed=0;function doCallback(err){FS.syncFSRequests--;return callback(err)}function done(err){if(err){if(!done.errored){done.errored=true;return doCallback(err)}return}if(++completed>=mounts.length){doCallback(null)}}mounts.forEach(function(mount){if(!mount.type.syncfs){return done(null)}mount.type.syncfs(mount,populate,done)})},mount:function(type,opts,mountpoint){var root=mountpoint==="/";var pseudo=!mountpoint;var node;if(root&&FS.root){throw new FS.ErrnoError(16)}else if(!root&&!pseudo){var lookup=FS.lookupPath(mountpoint,{follow_mount:false});mountpoint=lookup.path;node=lookup.node;if(FS.isMountpoint(node)){throw new FS.ErrnoError(16)}if(!FS.isDir(node.mode)){throw new FS.ErrnoError(20)}}var mount={type:type,opts:opts,mountpoint:mountpoint,mounts:[]};var mountRoot=type.mount(mount);mountRoot.mount=mount;mount.root=mountRoot;if(root){FS.root=mountRoot}else if(node){node.mounted=mount;if(node.mount){node.mount.mounts.push(mount)}}return mountRoot},unmount:function(mountpoint){var lookup=FS.lookupPath(mountpoint,{follow_mount:false});if(!FS.isMountpoint(lookup.node)){throw new FS.ErrnoError(22)}var node=lookup.node;var mount=node.mounted;var mounts=FS.getMounts(mount);Object.keys(FS.nameTable).forEach(function(hash){var current=FS.nameTable[hash];while(current){var next=current.name_next;if(mounts.indexOf(current.mount)!==-1){FS.destroyNode(current)}current=next}});node.mounted=null;var idx=node.mount.mounts.indexOf(mount);node.mount.mounts.splice(idx,1)},lookup:function(parent,name){return parent.node_ops.lookup(parent,name)},mknod:function(path,mode,dev){var lookup=FS.lookupPath(path,{parent:true});var parent=lookup.node;var name=PATH.basename(path);if(!name||name==="."||name===".."){throw new FS.ErrnoError(22)}var err=FS.mayCreate(parent,name);if(err){throw new FS.ErrnoError(err)}if(!parent.node_ops.mknod){throw new FS.ErrnoError(1)}return parent.node_ops.mknod(parent,name,mode,dev)},create:function(path,mode){mode=mode!==undefined?mode:438;mode&=4095;mode|=32768;return FS.mknod(path,mode,0)},mkdir:function(path,mode){mode=mode!==undefined?mode:511;mode&=511|512;mode|=16384;return FS.mknod(path,mode,0)},mkdirTree:function(path,mode){var dirs=path.split("/");var d="";for(var i=0;ithis.length-1||idx<0){return undefined}var chunkOffset=idx%this.chunkSize;var chunkNum=idx/this.chunkSize|0;return this.getter(chunkNum)[chunkOffset]};LazyUint8Array.prototype.setDataGetter=function LazyUint8Array_setDataGetter(getter){this.getter=getter};LazyUint8Array.prototype.cacheLength=function LazyUint8Array_cacheLength(){var xhr=new XMLHttpRequest;xhr.open("HEAD",url,false);xhr.send(null);if(!(xhr.status>=200&&xhr.status<300||xhr.status===304))throw new Error("Couldn't load "+url+". Status: "+xhr.status);var datalength=Number(xhr.getResponseHeader("Content-length"));var header;var hasByteServing=(header=xhr.getResponseHeader("Accept-Ranges"))&&header==="bytes";var usesGzip=(header=xhr.getResponseHeader("Content-Encoding"))&&header==="gzip";var chunkSize=1024*1024;if(!hasByteServing)chunkSize=datalength;var doXHR=function(from,to){if(from>to)throw new Error("invalid range ("+from+", "+to+") or no bytes requested!");if(to>datalength-1)throw new Error("only "+datalength+" bytes available! programmer error!");var xhr=new XMLHttpRequest;xhr.open("GET",url,false);if(datalength!==chunkSize)xhr.setRequestHeader("Range","bytes="+from+"-"+to);if(typeof Uint8Array!="undefined")xhr.responseType="arraybuffer";if(xhr.overrideMimeType){xhr.overrideMimeType("text/plain; charset=x-user-defined")}xhr.send(null);if(!(xhr.status>=200&&xhr.status<300||xhr.status===304))throw new Error("Couldn't load "+url+". Status: "+xhr.status);if(xhr.response!==undefined){return new Uint8Array(xhr.response||[])}else{return intArrayFromString(xhr.responseText||"",true)}};var lazyArray=this;lazyArray.setDataGetter(function(chunkNum){var start=chunkNum*chunkSize;var end=(chunkNum+1)*chunkSize-1;end=Math.min(end,datalength-1);if(typeof lazyArray.chunks[chunkNum]==="undefined"){lazyArray.chunks[chunkNum]=doXHR(start,end)}if(typeof lazyArray.chunks[chunkNum]==="undefined")throw new Error("doXHR failed!");return lazyArray.chunks[chunkNum]});if(usesGzip||!datalength){chunkSize=datalength=1;datalength=this.getter(0).length;chunkSize=datalength;console.log("LazyFiles on gzip forces download of the whole file when length is accessed")}this._length=datalength;this._chunkSize=chunkSize;this.lengthKnown=true};if(typeof XMLHttpRequest!=="undefined"){if(!ENVIRONMENT_IS_WORKER)throw"Cannot do synchronous binary XHRs outside webworkers in modern browsers. Use --embed-file or --preload-file in emcc";var lazyArray=new LazyUint8Array;Object.defineProperties(lazyArray,{length:{get:function(){if(!this.lengthKnown){this.cacheLength()}return this._length}},chunkSize:{get:function(){if(!this.lengthKnown){this.cacheLength()}return this._chunkSize}}});var properties={isDevice:false,contents:lazyArray}}else{var properties={isDevice:false,url:url}}var node=FS.createFile(parent,name,properties,canRead,canWrite);if(properties.contents){node.contents=properties.contents}else if(properties.url){node.contents=null;node.url=properties.url}Object.defineProperties(node,{usedBytes:{get:function(){return this.contents.length}}});var stream_ops={};var keys=Object.keys(node.stream_ops);keys.forEach(function(key){var fn=node.stream_ops[key];stream_ops[key]=function forceLoadLazyFile(){if(!FS.forceLoadFile(node)){throw new FS.ErrnoError(5)}return fn.apply(null,arguments)}});stream_ops.read=function stream_ops_read(stream,buffer,offset,length,position){if(!FS.forceLoadFile(node)){throw new FS.ErrnoError(5)}var contents=stream.node.contents;if(position>=contents.length)return 0;var size=Math.min(contents.length-position,length);if(contents.slice){for(var i=0;i>2]=stat.dev;HEAP32[buf+4>>2]=0;HEAP32[buf+8>>2]=stat.ino;HEAP32[buf+12>>2]=stat.mode;HEAP32[buf+16>>2]=stat.nlink;HEAP32[buf+20>>2]=stat.uid;HEAP32[buf+24>>2]=stat.gid;HEAP32[buf+28>>2]=stat.rdev;HEAP32[buf+32>>2]=0;tempI64=[stat.size>>>0,(tempDouble=stat.size,+Math_abs(tempDouble)>=1?tempDouble>0?(Math_min(+Math_floor(tempDouble/4294967296),4294967295)|0)>>>0:~~+Math_ceil((tempDouble-+(~~tempDouble>>>0))/4294967296)>>>0:0)],HEAP32[buf+40>>2]=tempI64[0],HEAP32[buf+44>>2]=tempI64[1];HEAP32[buf+48>>2]=4096;HEAP32[buf+52>>2]=stat.blocks;HEAP32[buf+56>>2]=stat.atime.getTime()/1e3|0;HEAP32[buf+60>>2]=0;HEAP32[buf+64>>2]=stat.mtime.getTime()/1e3|0;HEAP32[buf+68>>2]=0;HEAP32[buf+72>>2]=stat.ctime.getTime()/1e3|0;HEAP32[buf+76>>2]=0;tempI64=[stat.ino>>>0,(tempDouble=stat.ino,+Math_abs(tempDouble)>=1?tempDouble>0?(Math_min(+Math_floor(tempDouble/4294967296),4294967295)|0)>>>0:~~+Math_ceil((tempDouble-+(~~tempDouble>>>0))/4294967296)>>>0:0)],HEAP32[buf+80>>2]=tempI64[0],HEAP32[buf+84>>2]=tempI64[1];return 0},doMsync:function(addr,stream,len,flags){var buffer=new Uint8Array(HEAPU8.subarray(addr,addr+len));FS.msync(stream,buffer,0,len,flags)},doMkdir:function(path,mode){path=PATH.normalize(path);if(path[path.length-1]==="/")path=path.substr(0,path.length-1);FS.mkdir(path,mode,0);return 0},doMknod:function(path,mode,dev){switch(mode&61440){case 32768:case 8192:case 24576:case 4096:case 49152:break;default:return-22}FS.mknod(path,mode,dev);return 0},doReadlink:function(path,buf,bufsize){if(bufsize<=0)return-22;var ret=FS.readlink(path);var len=Math.min(bufsize,lengthBytesUTF8(ret));var endChar=HEAP8[buf+len];stringToUTF8(ret,buf,bufsize+1);HEAP8[buf+len]=endChar;return len},doAccess:function(path,amode){if(amode&~7){return-22}var node;var lookup=FS.lookupPath(path,{follow:true});node=lookup.node;if(!node){return-2}var perms="";if(amode&4)perms+="r";if(amode&2)perms+="w";if(amode&1)perms+="x";if(perms&&FS.nodePermissions(node,perms)){return-13}return 0},doDup:function(path,flags,suggestFD){var suggest=FS.getStream(suggestFD);if(suggest)FS.close(suggest);return FS.open(path,flags,0,suggestFD,suggestFD).fd},doReadv:function(stream,iov,iovcnt,offset){var ret=0;for(var i=0;i>2];var len=HEAP32[iov+(i*8+4)>>2];var curr=FS.read(stream,HEAP8,ptr,len,offset);if(curr<0)return-1;ret+=curr;if(curr>2];var len=HEAP32[iov+(i*8+4)>>2];var curr=FS.write(stream,HEAP8,ptr,len,offset);if(curr<0)return-1;ret+=curr}return ret},varargs:0,get:function(varargs){SYSCALLS.varargs+=4;var ret=HEAP32[SYSCALLS.varargs-4>>2];return ret},getStr:function(){var ret=UTF8ToString(SYSCALLS.get());return ret},getStreamFromFD:function(){var stream=FS.getStream(SYSCALLS.get());if(!stream)throw new FS.ErrnoError(9);return stream},get64:function(){var low=SYSCALLS.get(),high=SYSCALLS.get();return low},getZero:function(){SYSCALLS.get()}};function ___syscall140(which,varargs){SYSCALLS.varargs=varargs;try{var stream=SYSCALLS.getStreamFromFD(),offset_high=SYSCALLS.get(),offset_low=SYSCALLS.get(),result=SYSCALLS.get(),whence=SYSCALLS.get();var HIGH_OFFSET=4294967296;var offset=offset_high*HIGH_OFFSET+(offset_low>>>0);var DOUBLE_LIMIT=9007199254740992;if(offset<=-DOUBLE_LIMIT||offset>=DOUBLE_LIMIT){return-75}FS.llseek(stream,offset,whence);tempI64=[stream.position>>>0,(tempDouble=stream.position,+Math_abs(tempDouble)>=1?tempDouble>0?(Math_min(+Math_floor(tempDouble/4294967296),4294967295)|0)>>>0:~~+Math_ceil((tempDouble-+(~~tempDouble>>>0))/4294967296)>>>0:0)],HEAP32[result>>2]=tempI64[0],HEAP32[result+4>>2]=tempI64[1];if(stream.getdents&&offset===0&&whence===0)stream.getdents=null;return 0}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___syscall145(which,varargs){SYSCALLS.varargs=varargs;try{var stream=SYSCALLS.getStreamFromFD(),iov=SYSCALLS.get(),iovcnt=SYSCALLS.get();return SYSCALLS.doReadv(stream,iov,iovcnt)}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___syscall221(which,varargs){SYSCALLS.varargs=varargs;try{var stream=SYSCALLS.getStreamFromFD(),cmd=SYSCALLS.get();switch(cmd){case 0:{var arg=SYSCALLS.get();if(arg<0){return-22}var newStream;newStream=FS.open(stream.path,stream.flags,0,arg);return newStream.fd}case 1:case 2:return 0;case 3:return stream.flags;case 4:{var arg=SYSCALLS.get();stream.flags|=arg;return 0}case 12:{var arg=SYSCALLS.get();var offset=0;HEAP16[arg+offset>>1]=2;return 0}case 13:case 14:return 0;case 16:case 8:return-22;case 9:___setErrNo(22);return-1;default:{return-22}}}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___syscall5(which,varargs){SYSCALLS.varargs=varargs;try{var pathname=SYSCALLS.getStr(),flags=SYSCALLS.get(),mode=SYSCALLS.get();var stream=FS.open(pathname,flags,mode);return stream.fd}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___syscall54(which,varargs){SYSCALLS.varargs=varargs;try{var stream=SYSCALLS.getStreamFromFD(),op=SYSCALLS.get();switch(op){case 21509:case 21505:{if(!stream.tty)return-25;return 0}case 21510:case 21511:case 21512:case 21506:case 21507:case 21508:{if(!stream.tty)return-25;return 0}case 21519:{if(!stream.tty)return-25;var argp=SYSCALLS.get();HEAP32[argp>>2]=0;return 0}case 21520:{if(!stream.tty)return-25;return-22}case 21531:{var argp=SYSCALLS.get();return FS.ioctl(stream,op,argp)}case 21523:{if(!stream.tty)return-25;return 0}case 21524:{if(!stream.tty)return-25;return 0}default:abort("bad ioctl syscall "+op)}}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___syscall6(which,varargs){SYSCALLS.varargs=varargs;try{var stream=SYSCALLS.getStreamFromFD();FS.close(stream);return 0}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function __emscripten_syscall_munmap(addr,len){if(addr===-1||len===0){return-22}var info=SYSCALLS.mappings[addr];if(!info)return 0;if(len===info.len){var stream=FS.getStream(info.fd);SYSCALLS.doMsync(addr,stream,len,info.flags);FS.munmap(stream);SYSCALLS.mappings[addr]=null;if(info.allocated){_free(info.malloc)}}return 0}function ___syscall91(which,varargs){SYSCALLS.varargs=varargs;try{var addr=SYSCALLS.get(),len=SYSCALLS.get();return __emscripten_syscall_munmap(addr,len)}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___unlock(){}function _fd_write(stream,iov,iovcnt,pnum){try{stream=FS.getStream(stream);if(!stream)throw new FS.ErrnoError(9);var num=SYSCALLS.doWritev(stream,iov,iovcnt);HEAP32[pnum>>2]=num;return 0}catch(e){if(typeof FS==="undefined"||!(e instanceof FS.ErrnoError))abort(e);return-e.errno}}function ___wasi_fd_write(){return _fd_write.apply(null,arguments)}function _abort(){abort()}function _emscripten_get_heap_size(){return HEAP8.length}function emscripten_realloc_buffer(size){try{wasmMemory.grow(size-buffer.byteLength+65535>>16);updateGlobalBufferAndViews(wasmMemory.buffer);return 1}catch(e){}}function _emscripten_resize_heap(requestedSize){var oldSize=_emscripten_get_heap_size();var PAGE_MULTIPLE=65536;var LIMIT=2147483648-PAGE_MULTIPLE;if(requestedSize>LIMIT){return false}var MIN_TOTAL_MEMORY=16777216;var newSize=Math.max(oldSize,MIN_TOTAL_MEMORY);while(newSize0){var leap=__isLeapYear(newDate.getFullYear());var currentMonth=newDate.getMonth();var daysInCurrentMonth=(leap?__MONTH_DAYS_LEAP:__MONTH_DAYS_REGULAR)[currentMonth];if(days>daysInCurrentMonth-newDate.getDate()){days-=daysInCurrentMonth-newDate.getDate()+1;newDate.setDate(1);if(currentMonth<11){newDate.setMonth(currentMonth+1)}else{newDate.setMonth(0);newDate.setFullYear(newDate.getFullYear()+1)}}else{newDate.setDate(newDate.getDate()+days);return newDate}}return newDate}function _strftime(s,maxsize,format,tm){var tm_zone=HEAP32[tm+40>>2];var date={tm_sec:HEAP32[tm>>2],tm_min:HEAP32[tm+4>>2],tm_hour:HEAP32[tm+8>>2],tm_mday:HEAP32[tm+12>>2],tm_mon:HEAP32[tm+16>>2],tm_year:HEAP32[tm+20>>2],tm_wday:HEAP32[tm+24>>2],tm_yday:HEAP32[tm+28>>2],tm_isdst:HEAP32[tm+32>>2],tm_gmtoff:HEAP32[tm+36>>2],tm_zone:tm_zone?UTF8ToString(tm_zone):""};var pattern=UTF8ToString(format);var EXPANSION_RULES_1={"%c":"%a %b %d %H:%M:%S %Y","%D":"%m/%d/%y","%F":"%Y-%m-%d","%h":"%b","%r":"%I:%M:%S %p","%R":"%H:%M","%T":"%H:%M:%S","%x":"%m/%d/%y","%X":"%H:%M:%S","%Ec":"%c","%EC":"%C","%Ex":"%m/%d/%y","%EX":"%H:%M:%S","%Ey":"%y","%EY":"%Y","%Od":"%d","%Oe":"%e","%OH":"%H","%OI":"%I","%Om":"%m","%OM":"%M","%OS":"%S","%Ou":"%u","%OU":"%U","%OV":"%V","%Ow":"%w","%OW":"%W","%Oy":"%y"};for(var rule in EXPANSION_RULES_1){pattern=pattern.replace(new RegExp(rule,"g"),EXPANSION_RULES_1[rule])}var WEEKDAYS=["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"];var MONTHS=["January","February","March","April","May","June","July","August","September","October","November","December"];function leadingSomething(value,digits,character){var str=typeof value==="number"?value.toString():value||"";while(str.length0?1:0}var compare;if((compare=sgn(date1.getFullYear()-date2.getFullYear()))===0){if((compare=sgn(date1.getMonth()-date2.getMonth()))===0){compare=sgn(date1.getDate()-date2.getDate())}}return compare}function getFirstWeekStartDate(janFourth){switch(janFourth.getDay()){case 0:return new Date(janFourth.getFullYear()-1,11,29);case 1:return janFourth;case 2:return new Date(janFourth.getFullYear(),0,3);case 3:return new Date(janFourth.getFullYear(),0,2);case 4:return new Date(janFourth.getFullYear(),0,1);case 5:return new Date(janFourth.getFullYear()-1,11,31);case 6:return new Date(janFourth.getFullYear()-1,11,30)}}function getWeekBasedYear(date){var thisDate=__addDays(new Date(date.tm_year+1900,0,1),date.tm_yday);var janFourthThisYear=new Date(thisDate.getFullYear(),0,4);var janFourthNextYear=new Date(thisDate.getFullYear()+1,0,4);var firstWeekStartThisYear=getFirstWeekStartDate(janFourthThisYear);var firstWeekStartNextYear=getFirstWeekStartDate(janFourthNextYear);if(compareByDay(firstWeekStartThisYear,thisDate)<=0){if(compareByDay(firstWeekStartNextYear,thisDate)<=0){return thisDate.getFullYear()+1}else{return thisDate.getFullYear()}}else{return thisDate.getFullYear()-1}}var EXPANSION_RULES_2={"%a":function(date){return WEEKDAYS[date.tm_wday].substring(0,3)},"%A":function(date){return WEEKDAYS[date.tm_wday]},"%b":function(date){return MONTHS[date.tm_mon].substring(0,3)},"%B":function(date){return MONTHS[date.tm_mon]},"%C":function(date){var year=date.tm_year+1900;return leadingNulls(year/100|0,2)},"%d":function(date){return leadingNulls(date.tm_mday,2)},"%e":function(date){return leadingSomething(date.tm_mday,2," ")},"%g":function(date){return getWeekBasedYear(date).toString().substring(2)},"%G":function(date){return getWeekBasedYear(date)},"%H":function(date){return leadingNulls(date.tm_hour,2)},"%I":function(date){var twelveHour=date.tm_hour;if(twelveHour==0)twelveHour=12;else if(twelveHour>12)twelveHour-=12;return leadingNulls(twelveHour,2)},"%j":function(date){return leadingNulls(date.tm_mday+__arraySum(__isLeapYear(date.tm_year+1900)?__MONTH_DAYS_LEAP:__MONTH_DAYS_REGULAR,date.tm_mon-1),3)},"%m":function(date){return leadingNulls(date.tm_mon+1,2)},"%M":function(date){return leadingNulls(date.tm_min,2)},"%n":function(){return"\n"},"%p":function(date){if(date.tm_hour>=0&&date.tm_hour<12){return"AM"}else{return"PM"}},"%S":function(date){return leadingNulls(date.tm_sec,2)},"%t":function(){return"\t"},"%u":function(date){return date.tm_wday||7},"%U":function(date){var janFirst=new Date(date.tm_year+1900,0,1);var firstSunday=janFirst.getDay()===0?janFirst:__addDays(janFirst,7-janFirst.getDay());var endDate=new Date(date.tm_year+1900,date.tm_mon,date.tm_mday);if(compareByDay(firstSunday,endDate)<0){var februaryFirstUntilEndMonth=__arraySum(__isLeapYear(endDate.getFullYear())?__MONTH_DAYS_LEAP:__MONTH_DAYS_REGULAR,endDate.getMonth()-1)-31;var firstSundayUntilEndJanuary=31-firstSunday.getDate();var days=firstSundayUntilEndJanuary+februaryFirstUntilEndMonth+endDate.getDate();return leadingNulls(Math.ceil(days/7),2)}return compareByDay(firstSunday,janFirst)===0?"01":"00"},"%V":function(date){var janFourthThisYear=new Date(date.tm_year+1900,0,4);var janFourthNextYear=new Date(date.tm_year+1901,0,4);var firstWeekStartThisYear=getFirstWeekStartDate(janFourthThisYear);var firstWeekStartNextYear=getFirstWeekStartDate(janFourthNextYear);var endDate=__addDays(new Date(date.tm_year+1900,0,1),date.tm_yday);if(compareByDay(endDate,firstWeekStartThisYear)<0){return"53"}if(compareByDay(firstWeekStartNextYear,endDate)<=0){return"01"}var daysDifference;if(firstWeekStartThisYear.getFullYear()=0;off=Math.abs(off)/60;off=off/60*100+off%60;return(ahead?"+":"-")+String("0000"+off).slice(-4)},"%Z":function(date){return date.tm_zone},"%%":function(){return"%"}};for(var rule in EXPANSION_RULES_2){if(pattern.indexOf(rule)>=0){pattern=pattern.replace(new RegExp(rule,"g"),EXPANSION_RULES_2[rule](date))}}var bytes=intArrayFromString(pattern,false);if(bytes.length>maxsize){return 0}writeArrayToMemory(bytes,s);return bytes.length-1}function _strftime_l(s,maxsize,format,tm){return _strftime(s,maxsize,format,tm)}var ___dso_handle=73712;FS.staticInit();if(ENVIRONMENT_HAS_NODE){var fs=require("fs");var NODEJS_PATH=require("path");NODEFS.staticInit()}function intArrayFromString(stringy,dontAddNull,length){var len=length>0?length:lengthBytesUTF8(stringy)+1;var u8array=new Array(len);var numBytesWritten=stringToUTF8Array(stringy,u8array,0,u8array.length);if(dontAddNull)u8array.length=numBytesWritten;return u8array}function invoke_iii(index,a1,a2){var sp=stackSave();try{return dynCall_iii(index,a1,a2)}catch(e){stackRestore(sp);if(e!==e+0&&e!=="longjmp")throw e;_setThrew(1,0)}}function invoke_vi(index,a1){var sp=stackSave();try{dynCall_vi(index,a1)}catch(e){stackRestore(sp);if(e!==e+0&&e!=="longjmp")throw e;_setThrew(1,0)}}var asmGlobalArg={};var asmLibraryArg={"b":___assert_fail,"r":___cxa_pure_virtual,"q":___cxa_thread_atexit,"p":___cxa_uncaught_exceptions,"a":___dso_handle,"m":___lock,"H":___map_file,"G":___syscall140,"F":___syscall145,"l":___syscall221,"E":___syscall5,"D":___syscall54,"o":___syscall6,"C":___syscall91,"g":___unlock,"B":___wasi_fd_write,"__memory_base":1024,"__table_base":0,"c":_abort,"A":_emscripten_get_heap_size,"z":_emscripten_memcpy_big,"y":_emscripten_resize_heap,"j":_getenv,"f":_llvm_stackrestore,"e":_llvm_stacksave,"x":_llvm_trap,"i":_longjmp,"w":_pthread_cond_destroy,"u":_pthread_cond_signal,"n":_pthread_cond_wait,"t":_strftime_l,"d":abort,"k":getTempRet0,"v":invoke_iii,"s":invoke_vi,"memory":wasmMemory,"h":setTempRet0,"table":wasmTable};var asm=Module["asm"](asmGlobalArg,asmLibraryArg,buffer);Module["asm"]=asm;var __GLOBAL__sub_I_rlottie_wrapper_cpp=Module["__GLOBAL__sub_I_rlottie_wrapper_cpp"]=function(){return Module["asm"]["I"].apply(null,arguments)};var ___errno_location=Module["___errno_location"]=function(){return Module["asm"]["J"].apply(null,arguments)};var _free=Module["_free"]=function(){return Module["asm"]["K"].apply(null,arguments)};var _lottie_buffer=Module["_lottie_buffer"]=function(){return Module["asm"]["L"].apply(null,arguments)};var _lottie_destroy=Module["_lottie_destroy"]=function(){return Module["asm"]["M"].apply(null,arguments)};var _lottie_frame_count=Module["_lottie_frame_count"]=function(){return Module["asm"]["N"].apply(null,arguments)};var _lottie_init=Module["_lottie_init"]=function(){return Module["asm"]["O"].apply(null,arguments)};var _lottie_load_from_data=Module["_lottie_load_from_data"]=function(){return Module["asm"]["P"].apply(null,arguments)};var _lottie_render=Module["_lottie_render"]=function(){return Module["asm"]["Q"].apply(null,arguments)};var _lottie_resize=Module["_lottie_resize"]=function(){return Module["asm"]["R"].apply(null,arguments)};var _malloc=Module["_malloc"]=function(){return Module["asm"]["S"].apply(null,arguments)};var _setThrew=Module["_setThrew"]=function(){return Module["asm"]["T"].apply(null,arguments)};var stackAlloc=Module["stackAlloc"]=function(){return Module["asm"]["X"].apply(null,arguments)};var stackRestore=Module["stackRestore"]=function(){return Module["asm"]["Y"].apply(null,arguments)};var stackSave=Module["stackSave"]=function(){return Module["asm"]["Z"].apply(null,arguments)};var dynCall_iii=Module["dynCall_iii"]=function(){return Module["asm"]["U"].apply(null,arguments)};var dynCall_v=Module["dynCall_v"]=function(){return Module["asm"]["V"].apply(null,arguments)};var dynCall_vi=Module["dynCall_vi"]=function(){return Module["asm"]["W"].apply(null,arguments)};Module["asm"]=asm;Module["intArrayFromString"]=intArrayFromString;Module["cwrap"]=cwrap;Module["allocate"]=allocate;var calledRun;function ExitStatus(status){this.name="ExitStatus";this.message="Program terminated with exit("+status+")";this.status=status}dependenciesFulfilled=function runCaller(){if(!calledRun)run();if(!calledRun)dependenciesFulfilled=runCaller};function run(args){args=args||arguments_;if(runDependencies>0){return}preRun();if(runDependencies>0)return;function doRun(){if(calledRun)return;calledRun=true;if(ABORT)return;initRuntime();preMain();if(Module["onRuntimeInitialized"])Module["onRuntimeInitialized"]();postRun()}if(Module["setStatus"]){Module["setStatus"]("Running...");setTimeout(function(){setTimeout(function(){Module["setStatus"]("")},1);doRun()},1)}else{doRun()}}Module["run"]=run;if(Module["preInit"]){if(typeof Module["preInit"]=="function")Module["preInit"]=[Module["preInit"]];while(Module["preInit"].length>0){Module["preInit"].pop()()}}noExitRuntime=true;run(); diff --git a/MiniApp/wwwroot/js/rlottie-wasm.wasm b/MiniApp/wwwroot/js/rlottie-wasm.wasm new file mode 100644 index 0000000..49ed13d Binary files /dev/null and b/MiniApp/wwwroot/js/rlottie-wasm.wasm differ diff --git a/MiniApp/wwwroot/js/tgsticker-worker.js b/MiniApp/wwwroot/js/tgsticker-worker.js new file mode 100644 index 0000000..0b03dea --- /dev/null +++ b/MiniApp/wwwroot/js/tgsticker-worker.js @@ -0,0 +1,209 @@ +importScripts('rlottie-wasm.js'); +importScripts('pako-inflate.min.js'); + +function RLottieItem(reqId, jsString, width, height, fps) { + this.stringOnWasmHeap = null; + this.handle = null; + this.frameCount = 0; + + this.reqId = reqId; + this.width = width; + this.height = height; + this.fps = Math.max(1, Math.min(60, fps || 60)); + + this.dead = false; + + this.init(jsString, width, height); + + reply('loaded', this.reqId, this.frameCount, this.fps); +} + +RLottieItem.prototype.init = function(jsString) { + try { + this.handle = RLottieWorker.Api.init(); + + this.stringOnWasmHeap = allocate(intArrayFromString(jsString), 'i8', 0); + + this.frameCount = RLottieWorker.Api.loadFromData(this.handle, this.stringOnWasmHeap); + + RLottieWorker.Api.resize(this.handle, this.width, this.height); + } catch(e) { + console.error('init RLottieItem error:', e); + } +}; + +RLottieItem.prototype.render = function(frameNo, clamped) { + if (this.dead) return; + + var realFrameNo = frameNo; + if (frameNo < 0) { + realFrameNo = 0; + } else if (frameNo >= this.frameCount) { + realFrameNo = this.frameCount - 1; + } + + try { + RLottieWorker.Api.render(this.handle, realFrameNo); + + var bufferPointer = RLottieWorker.Api.buffer(this.handle); + + var data = Module.HEAPU8.subarray(bufferPointer, bufferPointer + (this.width * this.height * 4)); + + if(!clamped) { + clamped = new Uint8ClampedArray(data); + } else { + clamped.set(data); + } + + reply('frame', this.reqId, frameNo, clamped); + } catch(e) { + console.error('Render error:', e); + this.dead = true; + } +}; + +RLottieItem.prototype.destroy = function() { + this.dead = true; + + RLottieWorker.Api.destroy(this.handle); +}; + +var RLottieWorker = (function() { + var worker = {}; + worker.Api = {}; + + function initApi() { + worker.Api = { + init: Module.cwrap('lottie_init', '', []), + destroy: Module.cwrap('lottie_destroy', '', ['number']), + resize: Module.cwrap('lottie_resize', '', ['number', 'number', 'number']), + buffer: Module.cwrap('lottie_buffer', 'number', ['number']), + frameCount: Module.cwrap('lottie_frame_count', 'number', ['number']), + render: Module.cwrap('lottie_render', '', ['number', 'number']), + loadFromData: Module.cwrap('lottie_load_from_data', 'number', ['number', 'number']), + }; + } + + worker.init = function() { + initApi(); + reply('ready'); + }; + + return worker; +}()); + +Module.onRuntimeInitialized = function() { + RLottieWorker.init(); +}; + +var items = {}; +var queryableFunctions = { + loadFromData: function(reqId, url, width, height) { + getUrlContent(url, function(err, data) { + if (err) { + return console.warn('Can\'t fetch file ' + url, err); + } + try { + var json = pako.inflate(data, {to: 'string'}); + var json_parsed = JSON.parse(json); + items[reqId] = new RLottieItem(reqId, json, width, height, json_parsed.fr); + } catch (e) { + return console.warn('Invalid file ' + url); + } + }); + }, + destroy: function(reqId) { + items[reqId].destroy(); + delete items[reqId]; + }, + renderFrame: function(reqId, frameNo, clamped) { + items[reqId].render(frameNo, clamped); + } +}; + +function defaultReply(message) { + // your default PUBLIC function executed only when main page calls the queryableWorker.postMessage() method directly + // do something +} + +/** + * Returns true when run in WebKit derived browsers. + * This is used as a workaround for a memory leak in Safari caused by using Transferable objects to + * transfer data between WebWorkers and the main thread. + * https://github.com/mapbox/mapbox-gl-js/issues/8771 + * + * This should be removed once the underlying Safari issue is fixed. + * + * @private + * @param scope {WindowOrWorkerGlobalScope} Since this function is used both on the main thread and WebWorker context, + * let the calling scope pass in the global scope object. + * @returns {boolean} + */ +var _isSafari = null; +function isSafari(scope) { + if(_isSafari == null) { + var userAgent = scope.navigator ? scope.navigator.userAgent : null; + _isSafari = !!scope.safari || + !!(userAgent && (/\b(iPad|iPhone|iPod)\b/.test(userAgent) || (!!userAgent.match('Safari') && !userAgent.match('Chrome')))); + } + return _isSafari; +} + +function reply() { + if(arguments.length < 1) { + throw new TypeError('reply - not enough arguments'); + } + + var args = Array.prototype.slice.call(arguments, 1); + if(isSafari(self)) { + postMessage({ 'queryMethodListener': arguments[0], 'queryMethodArguments': args }); + } else { + var transfer = []; + for(var i = 0; i < args.length; i++) { + if(args[i] instanceof ArrayBuffer) { + transfer.push(args[i]); + } + + if(args[i].buffer && args[i].buffer instanceof ArrayBuffer) { + transfer.push(args[i].buffer); + } + } + + postMessage({ 'queryMethodListener': arguments[0], 'queryMethodArguments': args }, transfer); + } +} + +onmessage = function(oEvent) { + if(oEvent.data instanceof Object && oEvent.data.hasOwnProperty('queryMethod') && oEvent.data.hasOwnProperty('queryMethodArguments')) { + queryableFunctions[oEvent.data.queryMethod].apply(self, oEvent.data.queryMethodArguments); + } else { + defaultReply(oEvent.data); + } +}; + + + +function getUrlContent(path, callback) { + try { + var xhr = new XMLHttpRequest(); + xhr.open('GET', path, true); + if ('responseType' in xhr) { + xhr.responseType = 'arraybuffer'; + } + if (xhr.overrideMimeType) { + xhr.overrideMimeType('text/plain; charset=x-user-defined'); + } + xhr.onreadystatechange = function (event) { + if (xhr.readyState === 4) { + if (xhr.status === 200 || xhr.status === 0) { + callback(null, xhr.response || xhr.responseText); + } else { + callback(new Error('Ajax error: ' + this.status + ' ' + this.statusText)); + } + } + }; + xhr.send(); + } catch (e) { + callback(new Error(e)); + } +}; \ No newline at end of file diff --git a/MiniApp/wwwroot/js/webappdemo.js b/MiniApp/wwwroot/js/webappdemo.js new file mode 100644 index 0000000..411b141 --- /dev/null +++ b/MiniApp/wwwroot/js/webappdemo.js @@ -0,0 +1,552 @@ +var DemoApp = { + initData: Telegram.WebApp.initData || '', + initDataUnsafe: Telegram.WebApp.initDataUnsafe || {}, + MainButton: Telegram.WebApp.MainButton, + BackButton: Telegram.WebApp.BackButton, + SettingsButton: Telegram.WebApp.SettingsButton, + + init: function(options) { + $('body').css('visibility', ''); + Telegram.WebApp.ready(); + Telegram.WebApp.MainButton.setParams({ + text: 'CLOSE WEBVIEW', + is_visible: true + }).onClick(DemoApp.close); + Telegram.WebApp.BackButton.onClick(function() { + DemoApp.showAlert('Back button pressed'); + }); + Telegram.WebApp.SettingsButton.onClick(function() { + DemoApp.showAlert('Settings opened!'); + }); + }, + expand: function() { + Telegram.WebApp.expand(); + }, + close: function() { + Telegram.WebApp.close(); + }, + sendMessage: function(msg_id, with_webview) { + if (!DemoApp.initDataUnsafe.query_id) { + alert('WebViewQueryId not defined'); + return; + } + $('button').prop('disabled', true); + $('#btn_status').text('Sending...').removeClass('ok err').show(); + DemoApp.apiRequest('sendMessage', { + msg_id: msg_id || '', + with_webview: !DemoApp.initDataUnsafe.receiver && with_webview ? 1 : 0 + }, function(result) { + $('button').prop('disabled', false); + if (result.response) { + if (result.response.ok) { + $('#btn_status').text('Message sent successfully!').addClass('ok').show(); + } else { + $('#btn_status').text(result.response.description).addClass('err').show(); + alert(result.response.description); + } + } else if (result.error) { + $('#btn_status').text(result.error).addClass('err').show(); + alert(result.error); + } else { + $('#btn_status').text('Unknown error').addClass('err').show(); + alert('Unknown error'); + } + }); + }, + changeMenuButton: function(close) { + $('button').prop('disabled', true); + $('#btn_status').text('Changing button...').removeClass('ok err').show(); + DemoApp.apiRequest('changeMenuButton', {}, function(result) { + $('button').prop('disabled', false); + if (result.response) { + if (result.response.ok) { + $('#btn_status').text('Button changed!').addClass('ok').show(); + Telegram.WebApp.close(); + } else { + $('#btn_status').text(result.response.description).addClass('err').show(); + alert(result.response.description); + } + } else if (result.error) { + $('#btn_status').text(result.error).addClass('err').show(); + alert(result.error); + } else { + $('#btn_status').text('Unknown error').addClass('err').show(); + alert('Unknown error'); + } + }); + if (close) { + setTimeout(function() { + Telegram.WebApp.close(); + }, 50); + } + }, + checkInitData: function() { + if (DemoApp.initDataUnsafe.query_id && + DemoApp.initData && + $('#webview_data_status').hasClass('status_need')) { + $('#webview_data_status').removeClass('status_need'); + DemoApp.apiRequest('checkInitData', {}, function(result) { + if (result.ok) { + $('#webview_data_status').text('Hash is correct (async)').addClass('ok'); + } else { + $('#webview_data_status').text(result.error + ' (async)').addClass('err'); + } + }); + } + }, + + sendText: function(spam) { + var text = $('#text_field').val(); + if (!text.length) { + return $('#text_field').focus(); + } + if (byteLength(text) > 4096) { + return alert('Text is too long'); + } + var repeat = spam ? 10 : 1; + for (var i = 0; i < repeat; i++) { + Telegram.WebApp.sendData(text); + } + }, + sendTime: function(spam) { + var repeat = spam ? 10 : 1; + for (var i = 0; i < repeat; i++) { + Telegram.WebApp.sendData(new Date().toString()); + } + }, + switchInlineQuery: function(query, choose_chat) { + var choose_chat_types = false; + if (choose_chat) { + var choose_chat_types = []; + var types = ['users', 'bots', 'groups', 'channels']; + for (var i = 0; i < types.length; i++) { + if ($('#select-' + types[i]).prop('checked')) { + choose_chat_types.push(types[i]); + } + } + if (!choose_chat_types.length) { + return DemoApp.showAlert('Select chat types!'); + } + } + Telegram.WebApp.switchInlineQuery(query, choose_chat_types); + }, + requestLocation: function(el) { + if (navigator.geolocation) { + navigator.geolocation.getCurrentPosition(function (position) { + $(el).next('span').text('(' + position.coords.latitude + ', ' + position.coords.longitude + ')').attr('class', 'ok'); + }); + } else { + $(el).next('span').text('Geolocation is not supported in this browser.').attr('class', 'err'); + } + return false; + }, + requestVideo: function(el) { + if (navigator.mediaDevices) { + navigator.mediaDevices.getUserMedia({ audio: false, video: true }).then(function(stream) { + $(el).next('span').text('(Access granted)').attr('class', 'ok'); + }); + } else { + $(el).next('span').text('Media devices is not supported in this browser.').attr('class', 'err'); + } + return false; + }, + requestAudio: function(el) { + if (navigator.mediaDevices) { + navigator.mediaDevices.getUserMedia({ audio: true, video: false }).then(function(stream) { + $(el).next('span').text('(Access granted)').attr('class', 'ok'); + }); + } else { + $(el).next('span').text('Media devices is not supported in this browser.').attr('class', 'err'); + } + return false; + }, + requestAudioVideo: function(el) { + if (navigator.mediaDevices) { + navigator.mediaDevices.getUserMedia({ audio: true, video: true }).then(function(stream) { + $(el).next('span').text('(Access granted)').attr('class', 'ok'); + }); + } else { + $(el).next('span').text('Media devices is not supported in this browser.').attr('class', 'err'); + } + return false; + }, + testClipboard: function(el) { + Telegram.WebApp.readTextFromClipboard(function(clipText) { + if (clipText === null) { + $(el).next('span').text('Clipboard text unavailable.').attr('class', 'err'); + } else { + $(el).next('span').text('(Read from clipboard: «' + clipText + '»)').attr('class', 'ok'); + } + }); + return false; + }, + requestWriteAccess: function(el) { + Telegram.WebApp.requestWriteAccess(function(allowed) { + if (allowed) { + $(el).next('span').text('(Access granted)').attr('class', 'ok'); + } else { + $(el).next('span').text('(User declined this request)').attr('class', 'err'); + } + }); + }, + requestPhoneNumber: function(el) { + Telegram.WebApp.requestContact(function(sent, event) { + if (sent) { + $(el).next('span').text('(Phone number sent to the bot' + (event && event.responseUnsafe && event.responseUnsafe.contact && event.responseUnsafe.contact.phone_number ? ': +' + event.responseUnsafe.contact.phone_number : '') + ')').attr('class', 'ok'); + } else { + $(el).next('span').text('(User declined this request)').attr('class', 'err'); + } + }); + }, + requestServerTime: function(el) { + Telegram.WebApp.invokeCustomMethod('getCurrentTime', {}, function(err, time) { + if (err) { + $(el).next('span').text('(' + err + ')').attr('class', 'err'); + } else { + $(el).next('span').text('(' + (new Date(time*1000)).toString() + ')').attr('class', 'ok'); + } + }); + }, + cloudStorageKeys: {}, + cloudStorageItems: {}, + editCloudRow: function(el, event) { + event.preventDefault(); + var values = DemoApp.cloudStorageItems; + var key = $(el).parents('tr').attr('data-key'); + el.form.reset(); + el.form.key.value = key; + el.form.value.value = values[key]; + }, + deleteCloudRow: function(el, event) { + event.preventDefault(); + var key = $(el).parents('tr').attr('data-key'); + Telegram.WebApp.CloudStorage.removeItem(key, function(err, deleted) { + if (err) { + DemoApp.showAlert('Error: ' + err); + } else { + if (deleted) { + var index = DemoApp.cloudStorageKeys.indexOf(key); + if (index >= 0) { + DemoApp.cloudStorageKeys.splice(index, 1); + } + delete DemoApp.cloudStorageItems[key]; + } + el.form.reset(); + DemoApp.updateCloudRows(); + } + }); + }, + saveCloudForm: function(form, event) { + event.preventDefault(); + var key = form.key.value; + var value = form.value.value; + Telegram.WebApp.CloudStorage.setItem(key, value, function(err, saved) { + if (err) { + DemoApp.showAlert('Error: ' + err); + } else { + if (saved) { + if (typeof DemoApp.cloudStorageItems[key] === 'undefined') { + DemoApp.cloudStorageKeys.push(key); + } + DemoApp.cloudStorageItems[key] = value; + } + form.reset(); + DemoApp.updateCloudRows(); + } + }); + }, + updateCloudRows: function() { + var html = ''; + var keys = DemoApp.cloudStorageKeys; + var values = DemoApp.cloudStorageItems; + for (var i = 0; i < keys.length; i++) { + var key = keys[i]; + html += ''+cleanHTML(key)+''+cleanHTML(values[key])+''; + } + $('#cloud_rows').html(html); + }, + loadCloudKeys: function(el) { + Telegram.WebApp.CloudStorage.getKeys(function(err, keys) { + if (err) { + DemoApp.showAlert('Error: ' + err); + } else { + if (keys.length > 0) { + Telegram.WebApp.CloudStorage.getItems(keys, function(err, values) { + if (err) { + DemoApp.showAlert('Error: ' + err); + } else { + DemoApp.cloudStorageKeys = keys; + DemoApp.cloudStorageItems = {}; + for (var i = 0; i < keys.length; i++) { + var key = keys[i]; + DemoApp.cloudStorageItems[key] = values[key]; + } + DemoApp.updateCloudRows(); + } + }); + } + } + }); + }, + biometricInit: function(el) { + var biometricManager = Telegram.WebApp.BiometricManager; + if (!DemoApp.biometricInited) { + DemoApp.biometricInited = true; + Telegram.WebApp.onEvent('biometricManagerUpdated', function() { + $('#bm_inited').text(biometricManager.isInited ? 'true' : 'false'); + $('#bm_available').text(biometricManager.isBiometricAvailable ? 'true' : 'false'); + $('#bm_type').text(biometricManager.biometricType || ''); + $('#bm_access_requested').text(biometricManager.isAccessRequested ? 'true' : 'false'); + $('#bm_access_granted').text(biometricManager.isAccessGranted ? 'true' : 'false'); + $('#bm_token_saved').text(biometricManager.isBiometricTokenSaved ? 'true' : 'false'); + $('#bm_device_id').text(biometricManager.deviceId || ''); + $('#bm_settings').toggle(biometricManager.isBiometricAvailable && biometricManager.isAccessRequested && !biometricManager.isAccessGranted); + }); + } + biometricManager.init(); + }, + biometricRequestAccess: function(el) { + var biometricManager = Telegram.WebApp.BiometricManager; + if (!biometricManager.isInited) { + return DemoApp.showAlert('Biometric not inited yet!'); + } + biometricManager.requestAccess({reason: 'The bot uses biometrics for testing purposes.'}, function(access_granted) { + if (access_granted) { + $(el).next('span').text('(Access granted)').attr('class', 'ok'); + } else { + $(el).next('span').text('(Request declined)').attr('class', 'err'); + } + }); + }, + biometricRequestAuth: function(el) { + var biometricManager = Telegram.WebApp.BiometricManager; + if (!biometricManager.isInited) { + return DemoApp.showAlert('Biometric not inited yet!'); + } + $(el).next('span').text('').attr('class', ''); + biometricManager.authenticate({reason: 'The bot requests biometrics for testing purposes.'}, function(success, token) { + if (success) { + $(el).next('span').text('(Success, token: ' + token + ')').attr('class', 'ok'); + } else { + $(el).next('span').text('(Auth failed)').attr('class', 'err'); + } + }); + }, + biometricOpenSettings: function(el) { + var biometricManager = Telegram.WebApp.BiometricManager; + if (!biometricManager.isInited) { + return DemoApp.showAlert('Biometric not inited yet!'); + } + if (!biometricManager.isBiometricAvailable || + !biometricManager.isAccessRequested || + biometricManager.isAccessGranted) { + return false; + } + biometricManager.openSettings(); + }, + biometricSetToken: function(el) { + var biometricManager = Telegram.WebApp.BiometricManager; + if (!biometricManager.isInited) { + return DemoApp.showAlert('Biometric not inited yet!'); + } + var token = parseInt(Math.random().toString().substr(2)).toString(16); + biometricManager.updateBiometricToken(token, function(updated) { + if (updated) { + $('#bm_token_saved').text(biometricManager.isBiometricTokenSaved ? 'true' : 'false'); + $(el).nextAll('span').text('(Updated: ' + token + ')').attr('class', 'ok'); + } else { + $(el).next('span').text('(Failed)').attr('class', 'err'); + } + }); + }, + biometricRemoveToken: function(el) { + var biometricManager = Telegram.WebApp.BiometricManager; + if (!biometricManager.isInited) { + return DemoApp.showAlert('Biometric not inited yet!'); + } + biometricManager.updateBiometricToken('', function(updated) { + if (updated) { + $('#bm_token_saved').text(biometricManager.isBiometricTokenSaved ? 'true' : 'false'); + $(el).next('span').text('(Removed)').attr('class', 'ok'); + } else { + $(el).next('span').text('(Failed)').attr('class', 'err'); + } + }); + }, + toggleMainButton: function(el) { + if (DemoApp.MainButton.isVisible) { + DemoApp.MainButton.hide(); + el.innerHTML = 'Show Main Button'; + } else { + DemoApp.MainButton.show(); + el.innerHTML = 'Hide Main Button'; + } + }, + toggleBackButton: function(el) { + if (DemoApp.BackButton.isVisible) { + DemoApp.BackButton.hide(); + el.innerHTML = 'Show Back Button'; + } else { + DemoApp.BackButton.show(); + el.innerHTML = 'Hide Back Button'; + } + }, + toggleSettingsButton: function(el) { + if (DemoApp.SettingsButton.isVisible) { + DemoApp.SettingsButton.hide(); + el.innerHTML = 'Show Settings Button'; + } else { + DemoApp.SettingsButton.show(); + el.innerHTML = 'Hide Settings Button'; + } + }, + toggleSwipeBehavior: function(el) { + if (Telegram.WebApp.isVerticalSwipesEnabled) { + Telegram.WebApp.disableVerticalSwipes(); + el.innerHTML = 'Enable Vertical Swypes'; + } else { + Telegram.WebApp.enableVerticalSwipes(); + el.innerHTML = 'Disable Vertical Swypes'; + } + }, + showAlert: function(message) { + Telegram.WebApp.showAlert(message); + }, + showConfirm: function(message) { + Telegram.WebApp.showConfirm(message); + }, + showPopup: function() { + Telegram.WebApp.showPopup({ + title: 'Popup title', + message: 'Popup message', + buttons: [ + {id: 'delete', type: 'destructive', text: 'Delete all'}, + {id: 'faq', type: 'default', text: 'Open FAQ'}, + {type: 'cancel'}, + ] + }, function(button_id) { + if (button_id == 'delete') { + DemoApp.showAlert("'Delete all' selected"); + } else if (button_id == 'faq') { + Telegram.WebApp.openLink('https://telegram.org/faq'); + } + }); + }, + showScanQrPopup: function(links_only) { + Telegram.WebApp.showScanQrPopup({ + text: links_only ? 'with any link' : 'for test purposes' + }, function(text) { + if (links_only) { + var lower_text = text.toString().toLowerCase(); + if (lower_text.substr(0, 7) == 'http://' || + lower_text.substr(0, 8) == 'https://') { + setTimeout(function() { + Telegram.WebApp.openLink(text); + }, 50); + return true; + } + } else { + DemoApp.showAlert(text); + return true; + } + }); + }, + + apiRequest: function(method, data, onCallback) { + var authData = DemoApp.initData || ''; + $.ajax(DemoApp.apiUrl, { + type: 'POST', + data: $.extend(data, {_auth: authData, method: method}), + dataType: 'json', + xhrFields: { + withCredentials: true + }, + success: function(result) { + onCallback && onCallback(result); + }, + error: function(xhr) { + onCallback && onCallback({error: 'Server error'}); + } + }); + } +}; + +var DemoAppMenu = { + init: function() { + DemoApp.init(); + $('body').addClass('gray'); + Telegram.WebApp.setHeaderColor('secondary_bg_color'); + } +}; + +var DemoAppInitData = { + init: function() { + DemoApp.init(); + // $('body').addClass('gray'); + // Telegram.WebApp.setHeaderColor('secondary_bg_color'); + + Telegram.WebApp.onEvent('themeChanged', function() { + $('#theme_data').text(JSON.stringify(Telegram.WebApp.themeParams, null, 2)); + }); + $('#webview_data').text(JSON.stringify(DemoApp.initDataUnsafe, null, 2)); + $('#theme_data').text(JSON.stringify(Telegram.WebApp.themeParams, null, 2)); + DemoApp.checkInitData(); + + } +}; + +var DemoAppViewport = { + init: function() { + DemoApp.init(); + // $('body').addClass('gray'); + // Telegram.WebApp.setHeaderColor('secondary_bg_color'); + Telegram.WebApp.onEvent('viewportChanged', DemoAppViewport.setData); + DemoAppViewport.setData(); + }, + setData: function() { + $('.viewport-border').attr('text', window.innerWidth + ' x ' + round(Telegram.WebApp.viewportHeight, 2)); + $('.viewport-stable_border').attr('text', window.innerWidth + ' x ' + round(Telegram.WebApp.viewportStableHeight, 2) + ' | is_expanded: ' + (Telegram.WebApp.isExpanded ? 'true' : 'false')); + } +}; + +function cleanHTML(value) { + return value.replace(/&/g, '&').replace(//g, '>').replace(/"/g, '"').replace(/\n/g, '
'); +} + +function byteLength(str) { + if (window.Blob) { + try { return new Blob([str]).size; } catch (e) {} + } + var s = str.length; + for (var i=str.length-1; i>=0; i--) { + var code = str.charCodeAt(i); + if (code > 0x7f && code <= 0x7ff) s++; + else if (code > 0x7ff && code <= 0xffff) s+=2; + if (code >= 0xDC00 && code <= 0xDFFF) i--; + } + return s; +} + +function round(val, d) { + var k = Math.pow(10, d || 0); + return Math.round(val * k) / k; +} + +(function($) { + $.fn.cssProp = function(prop, val) { + if (typeof val !== 'undefined') { + return this.each(function() { + if (this.style && this.style.setProperty) { + this.style.setProperty(prop, val); + } + }); + } + return this.first().map(function() { + if (this.style && this.style.getPropertyValue) { + return this.style.getPropertyValue(prop); + } else { + return ''; + } + }).get(0) || ''; + }; +})(jQuery); \ No newline at end of file