1 line
258 KiB
Plaintext
1 line
258 KiB
Plaintext
{"version":3,"sources":["webpack:///./src/helpers/dom/cancelEvent.ts","webpack:///./src/helpers/dom/clickEvent.ts","webpack:///./src/components/button.ts","webpack:///./src/lib/appManagers/appStateManager.ts","webpack:///./src/helpers/touchSupport.ts","webpack:///./src/components/misc.ts","webpack:///./src/helpers/mediaSizes.ts","webpack:///./src/components/ripple.ts","webpack:///./src/lib/rlottie/rlottie.worker.ts","webpack:///./src/lib/lottieLoader.ts","webpack:///./src/helpers/date.ts","webpack:///./src/pages/pagesManager.ts","webpack:///./src/pages/page.ts","webpack:///./src/components/appNavigationController.ts","webpack:///./src/helpers/fastSmoothScroll.ts","webpack:///./src/hooks/useHeavyAnimationCheck.ts","webpack:///./src/helpers/dom/isInDOM.ts","webpack:///./src/helpers/dom/whichChild.ts","webpack:///./src/components/animationIntersector.ts","webpack:///./src/helpers/dom/toggleDisability.ts","webpack:///./src/pages/pageIm.ts","webpack:///./src/helpers/number.ts","webpack:///./src/helpers/sequentialDom.ts","webpack:///./src/lib/mtproto/serverTimeManager.ts","webpack:///./src/countries.ts","webpack:///./src/lib/mtproto/passwordManager.ts","webpack:///./src/pages/loginPage.ts","webpack:///./src/helpers/calcImageInBox.ts","webpack:///./src/components/horizontalMenu.ts","webpack:///./src/components/transition.ts","webpack:///./src/helpers/animation.ts","webpack:///./src/components/passwordInputField.ts","webpack:///./src/helpers/dom/findUpAsChild.ts","webpack:///./src/pages/pagePassword.ts","webpack:///./src/components/monkeys/password.ts"],"names":["cancelEvent","event","window","originalEvent","stopPropagation","preventDefault","returnValue","cancelBubble","err","CLICK_EVENT_NAME","attachClickEvent","elem","callback","options","add","listenerSetter","bind","addEventListener","removeManual","removeEventListener","touchMouseDown","detachClickEvent","className","button","document","createElement","asDiv","icon","noRipple","rippleSquare","classList","onlyMobile","disabled","setAttribute","text","append","STATE_VERSION","version","STATE_INIT","allDialogsLoaded","pinnedOrders","contactsList","updates","filters","maxSeenMsgId","stateCreatedTime","Date","now","recentEmoji","topPeers","recentSearch","authState","_","hiddenPinnedMessages","settings","messagesTextSize","sendShortcut","animationsEnabled","autoDownload","contacts","private","groups","channels","autoPlay","gifs","videos","stickers","suggest","loop","emoji","big","themes","name","background","type","blur","slug","highlightningColor","color","theme","notifications","sound","keepSigned","ALL_KEYS","Object","keys","REFRESH_KEYS","REFRESH_KEYS_WEEK","AppStateManager","super","log","neededPeers","Map","singlePeerMap","storages","users","chats","dialogs","storagesResults","storage","this","loadSavedState","loaded","console","time","Promise","resolve","storagesKeys","storagesPromises","map","key","getAll","promises","get","concat","all","then","arr","state","i","length","value","undefined","pushToState","splice","auth","shift","shiftedWebKAuth","push","values","dcID","baseDcId","id","obj","forEach","idx","set","localStorage","getItem","JSON","parse","getFromCache","error","dispatchEvent","r","s","hasOwnProperty","nightTheme","find","t","missingKey","timeEnd","catch","first","split","direct","peerId","limit","has","Set","keepPeerSingle","existsPeerId","delete","size","appStateManager","isTouchSupported","DocumentTouch","putPreloader","returnDiv","html","div","innerHTML","appendChild","insertAdjacentHTML","lastElementChild","setButtonLoader","remove","removeAttribute","sortedCountries","formatPhoneNumber","str","phoneCode","replace","slice","sort","a","b","country","c","indexOf","pattern","symbol","formatted","onMouseMove","e","rect","openedMenu","getBoundingClientRect","clientX","clientY","diffX","right","left","diffY","bottom","top","closeBtnMenu","onClick","parentElement","menuOverlay","openedMenuOnClose","removeByType","openBtnMenu","menuElement","onClose","pushItem","onPop","canAnimate","insertBefore","once","positionMenu","pageX","pageY","side","scrollWidth","menuWidth","scrollHeight","menuHeight","body","windowWidth","width","windowHeight","height","isMobile","verticalSide","sides","x","intermediateX","y","intermediateY","possibleSides","style","attachContextMenuListener","element","timeout","capture","onCancel","clearTimeout","touches","setTimeout","ScreenSize","MediaSize","boxSize","fitted","aspect","makeMediaSize","MediaSizes","screenSizes","mobile","medium","large","sizes","handhelds","regular","webpage","album","esgSticker","animatedSticker","staticSticker","emojiSticker","desktop","handleResize","innerWidth","activeScreen","wasScreen","active","rAF","cancelAnimationFrame","requestAnimationFrame","mediaSizes","rippleClickId","ripple","onEnd","prepend","querySelector","handler","contains","drawRipple","startTime","clickId","duration","getComputedStyle","getPropertyValue","elapsedTime","cb","mutate","delay","Math","max","touchStartFired","clickX","clickY","sqrt","abs","isRippleUnneeded","target","includes","tagName","touchEnd","passive","dataset","Worker_fn","Worker","convert","round","min","el","worker","reqId","paused","direction","speed","autoplay","group","frames","cachingDelta","skipRatio","_loop","_autoplay","skipDelta","pixelRatio","devicePixelRatio","needUpscale","noCache","Infinity","canvas","context","getContext","clamped","Uint8ClampedArray","imageData","ImageData","methodName","args","sendQuery","jsonString","setMainLoop","clearPendingRAF","rafId","renderFirstFrame","pause","curFrame","frameCount","requestFrame","stop","play","lottieLoader","onDestroy","frame","frameNo","data","putImageData","frInterval","delta","frThen","renderFrame2","renderFrame","fps","method","mainLoopForwards","mainLoopBackwards","currentMethod","frameListener","listenerResults","diff","defaultListener","onError","onerror","onmessage","queryMethodListener","queryMethodArguments","call","message","postMessage","terminate","queryMethod","transfer","arg","ArrayBuffer","buffer","isWebAssemblySupported","loadPromise","reject","workersLimit","players","workers","curWorkerNum","logger","Error","onPlayerLoaded","rlPlayer","debug","onLoad","warn","onFrame","onPlayerError","animationIntersector","getAnimations","animation","checkAnimation","player","remain","object","toneIndex","replacements","COLORREPLACEMENTS","checkSmth","smth","ty","k","foundReplacement","p","applyTo","iterateIt","it","layer","layers","shapes","shape","params","url","loadLottieWorkers","fetch","res","arrayBuffer","gzipUncompress","loadAnimationWorker","assign","animationData","race","newAnimationData","applyReplacements","stringify","parseInt","container","initPlayer","addAnimation","loadFromData","months","days","ONE_DAY","getWeekNumber","date","d","UTC","getFullYear","getMonth","getDate","dayNum","getUTCDay","setUTCDate","getUTCDate","yearStart","getUTCFullYear","ceil","getTime","formatDateAccordingToToday","timestamp","timeStr","getHours","getMinutes","getDay","formatDateAccordingToTodayNew","today","hour","minute","year","day","month","weekday","IntlDateElement","formatTime","getFullDate","joiner","monthAsNumber","noSeconds","getSeconds","leadingZero","noTime","tsNow","seconds","floor","yearPattern","RegExp","monthYearOrDayPattern","yearOrDayAndMonthPattern","shortDate","longDate","numberOfDaysEachMonth","fillTipDates","query","dates","q","trim","toLowerCase","setFullYear","setHours","minDate","maxDate","title","dayOfWeek","setDate","formatWeekLong","getDayOfWeek","distance","setTime","matches","exec","g1","g2","createForDayMonth","createForMonthYear","selectedYear","currentYear","g3","validDateForMonth","formatterYearMax","k1","setMonth","formatterMonthYear","formatterDayMonth","pagesManager","pageId","pagesDiv","getElementById","scrollableDiv","selectTab","horizontalMenu","page","onShown","isAuthPage","display","whichChild","pageEl","fastSmoothScroll","firstElementChild","onFirstMount","onMount","installed","setPage","appNavigationController","navigations","manual","currentHash","location","hash","isPossibleSwipe","onHashChange","replaceState","pushState","item","pop","handleItem","onEscape","back","detach","onTouchEnd","onTouchMove","moved","history","scrollRestoration","good","noBlurOnPop","index","ret","findItemByType","noHistory","origin","pathname","findAndSplice","single","FocusDirection","position","margin","maxDistance","forceDirection","forceDuration","axis","Static","scrollWithJs","elementRect","containerRect","offsetTop","scrollTop","Up","Down","promise","rectStartKey","rectEndKey","sizeKey","scrollSizeKey","scrollPositionKey","elementPosition","elementSize","containerSize","scrollPosition","scrollSize","path","remainingPath","startAt","tick","currentPath","transition","isAnimating","heavyAnimationPromise","promisesInQueue","dispatchHeavyAnimationEvent","finally","filter","Boolean","perf","performance","_heavyAnimationPromise","isFulfilled","onHeavyAnimationEnd","interruptHeavyAnimation","getHeavyAnimationPromise","handleAnimationStart","handleAnimationEnd","isInDOM","isConnected","parentNode","previousElementSibling","visible","byGroups","lockedGroups","onlyOnePlayableGroup","intersectionLockedGroups","videosLocked","observer","IntersectionObserver","entries","idle","isIDLE","entry","isIntersecting","clearCache","doc","checkAnimations","found","HTMLVideoElement","src","load","unobserve","observe","blurred","destroy","removeAnimation","animations","refreshGroup","toggleDisability","elements","disable","m","default","requestedServerLanguage","getCacheLangPack","langPack","local","getLangPack","lang_code","numberThousandSplitter","parts","toString","join","formatBytes","bytes","decimals","dm","parseFloat","pow","toFixed","formatNumber","clamp","v","sequentialDom","raf","scheduled","kind","scheduleFlush","do","read","write","serverTimeManager","timestampNow","midnightNoOffset","midnightOffseted","midnightOffset","serverTimeOffset","timeParams","to","Countries","PhoneCodesMain","passwordManager","invokeApi","result","getState","currentHashPromise","newHashPromise","password","new_settings","hint","email","currentPassword","computeSRP","newAlgo","new_algo","salt1","Uint8Array","randomize","newPassword","hashes","new_password_hash","inputCheckPassword","saveApiUser","user","setUserAuth","code","LoginPage","imageDiv","titleLangKey","subtitle","subtitleLangKey","withInputWrapper","inputWrapper","calcImageInBox","imageW","imageH","boxW","boxH","noZoom","boxedImageW","boxedImageH","tabs","content","onTransitionEnd","transitionTime","scrollableX","proxy","Proxy","apply","that","animate","children","selectTarget","tabContent","canChange","scrollIntoViewNew","prevId","prev","useStripe","indicator","currentIndicator","shiftLeft","offsetLeft","scaleFactor","clientWidth","transform","tab","slideNavigation","prevTabContent","toRight","reverse","offsetWidth","slideTabs","scrollableContainer","overflowY","TransitionSlider","isHeavy","animationFunction","Transition","onTransitionEndCallbacks","animationDeferred","animationStarted","from","self","HTMLElement","_from","onTransitionEndCallback","toggle","instances","cancelAnimationByKey","instance","getAnimationInstance","isCancelled","deferred","animateSingle","createAnimationInstance","PasswordInputField","plainText","passwordVisible","onVisibilityClick","toggleVisible","input","onVisibilityClickAdditional","autocomplete","stealthy","tabIndex","cloneNode","nextSibling","findUpAsChild","parent","passwordInput","btnNext","btnNextI18n","IntlElement","passwordInputField","label","getStateInterval","setInterval","_state","wrapEmojiText","setLabel","onSubmit","update","preloader","check","response","clearInterval","mount","monkey","select","focus","PasswordMonkey","needFrame","loadAnimationFromURL","_animation","currentFrame","setSpeed","setDirection","waitForFirstFrame"],"mappings":"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","file":"12.e677043f95889b5f293f.chunk.js","sourcesContent":["/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n * \r\n * Originally from:\r\n * https://github.com/zhukov/webogram\r\n * Copyright (C) 2014 Igor Zhukov <igor.beatle@gmail.com>\r\n * https://github.com/zhukov/webogram/blob/master/LICENSE\r\n */\r\n\r\nexport function cancelEvent(event: Event) {\r\n event = event || window.event;\r\n if(event) {\r\n // @ts-ignore\r\n event = event.originalEvent || event;\r\n\r\n try {\r\n if(event.stopPropagation) event.stopPropagation();\r\n if(event.preventDefault) event.preventDefault();\r\n event.returnValue = false;\r\n event.cancelBubble = true;\r\n } catch(err) {}\r\n }\r\n\r\n return false;\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport type ListenerSetter from \"../listenerSetter\";\r\nimport { isTouchSupported } from \"../touchSupport\";\r\n\r\nexport const CLICK_EVENT_NAME: 'mousedown' | 'touchend' | 'click' = (isTouchSupported ? 'mousedown' : 'click') as any;\r\nexport type AttachClickOptions = AddEventListenerOptions & Partial<{listenerSetter: ListenerSetter, touchMouseDown: true}>;\r\nexport function attachClickEvent(elem: HTMLElement, callback: (e: TouchEvent | MouseEvent) => void, options: AttachClickOptions = {}) {\r\n const add = options.listenerSetter ? options.listenerSetter.add.bind(options.listenerSetter, elem) : elem.addEventListener.bind(elem);\r\n const remove = options.listenerSetter ? options.listenerSetter.removeManual.bind(options.listenerSetter, elem) : elem.removeEventListener.bind(elem);\r\n\r\n options.touchMouseDown = true;\r\n /* if(options.touchMouseDown && CLICK_EVENT_NAME === 'touchend') {\r\n add('mousedown', callback, options);\r\n } else if(CLICK_EVENT_NAME === 'touchend') {\r\n const o = {...options, once: true};\r\n\r\n const onTouchStart = (e: TouchEvent) => {\r\n const onTouchMove = (e: TouchEvent) => {\r\n remove('touchmove', onTouchMove, o);\r\n remove('touchend', onTouchEnd, o);\r\n };\r\n \r\n const onTouchEnd = (e: TouchEvent) => {\r\n remove('touchmove', onTouchMove, o);\r\n callback(e);\r\n if(options.once) {\r\n remove('touchstart', onTouchStart);\r\n }\r\n };\r\n \r\n add('touchend', onTouchEnd, o);\r\n add('touchmove', onTouchMove, o);\r\n };\r\n\r\n add('touchstart', onTouchStart);\r\n } else {\r\n add(CLICK_EVENT_NAME, callback, options);\r\n } */\r\n add(CLICK_EVENT_NAME, callback, options);\r\n}\r\n\r\nexport function detachClickEvent(elem: HTMLElement, callback: (e: TouchEvent | MouseEvent) => void, options?: AddEventListenerOptions) {\r\n if(CLICK_EVENT_NAME === 'touchend') {\r\n elem.removeEventListener('touchstart', callback, options);\r\n } else {\r\n elem.removeEventListener(CLICK_EVENT_NAME, callback, options);\r\n }\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { i18n, LangPackKey } from \"../lib/langPack\";\r\nimport { ripple } from \"./ripple\";\r\n\r\nconst Button = (className: string, options: Partial<{\r\n noRipple: true, \r\n onlyMobile: true, \r\n icon: string, \r\n rippleSquare: true, \r\n text: LangPackKey, \r\n disabled: boolean,\r\n asDiv: boolean\r\n}> = {}) => {\r\n const button: HTMLButtonElement = document.createElement(options.asDiv ? 'div' : 'button') as any;\r\n button.className = className + (options.icon ? ' tgico-' + options.icon : '');\r\n\r\n if(!options.noRipple) {\r\n if(options.rippleSquare) {\r\n button.classList.add('rp-square');\r\n }\r\n\r\n ripple(button);\r\n }\r\n\r\n if(options.onlyMobile) {\r\n button.classList.add('only-handhelds');\r\n }\r\n\r\n if(options.disabled) {\r\n button.setAttribute('disabled', 'true');\r\n }\r\n\r\n if(options.text) {\r\n button.append(i18n(options.text));\r\n }\r\n\r\n return button;\r\n};\r\n\r\nexport default Button;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport type { Dialog } from './appMessagesManager';\r\nimport type { UserAuth } from '../mtproto/mtproto_config';\r\nimport type { User } from './appUsersManager';\r\nimport type { AuthState } from '../../types';\r\nimport type FiltersStorage from '../storages/filters';\r\nimport type DialogsStorage from '../storages/dialogs';\r\nimport EventListenerBase from '../../helpers/eventListenerBase';\r\nimport rootScope from '../rootScope';\r\nimport stateStorage from '../stateStorage';\r\nimport { logger } from '../logger';\r\nimport { copy, setDeepProperty, validateInitObject } from '../../helpers/object';\r\nimport App from '../../config/app';\r\nimport DEBUG, { MOUNT_CLASS_TO } from '../../config/debug';\r\nimport AppStorage from '../storage';\r\nimport { Chat } from '../../layer';\r\nimport { isMobile } from '../../helpers/userAgent';\r\nimport DATABASE_STATE from '../../config/databases/state';\r\nimport sessionStorage from '../sessionStorage';\r\n\r\nconst REFRESH_EVERY = 24 * 60 * 60 * 1000; // 1 day\r\nconst REFRESH_EVERY_WEEK = 24 * 60 * 60 * 1000 * 7; // 7 days\r\nconst STATE_VERSION = App.version;\r\n\r\nexport type Background = {\r\n type: 'color' | 'image' | 'default',\r\n blur: boolean,\r\n highlightningColor?: string,\r\n color?: string,\r\n slug?: string,\r\n};\r\n\r\nexport type Theme = {\r\n name: 'day' | 'night' | 'system',\r\n background: Background\r\n};\r\n\r\nexport type State = {\r\n allDialogsLoaded: DialogsStorage['allDialogsLoaded'],\r\n pinnedOrders: DialogsStorage['pinnedOrders'],\r\n contactsList: number[],\r\n updates: Partial<{\r\n seq: number,\r\n pts: number,\r\n date: number\r\n }>,\r\n filters: FiltersStorage['filters'],\r\n maxSeenMsgId: number,\r\n stateCreatedTime: number,\r\n recentEmoji: string[],\r\n topPeers: number[],\r\n recentSearch: number[],\r\n version: typeof STATE_VERSION,\r\n authState: AuthState,\r\n hiddenPinnedMessages: {[peerId: string]: number},\r\n settings: {\r\n messagesTextSize: number,\r\n sendShortcut: 'enter' | 'ctrlEnter',\r\n animationsEnabled: boolean,\r\n autoDownload: {\r\n contacts: boolean\r\n private: boolean\r\n groups: boolean\r\n channels: boolean\r\n },\r\n autoPlay: {\r\n gifs: boolean,\r\n videos: boolean\r\n },\r\n stickers: {\r\n suggest: boolean,\r\n loop: boolean\r\n },\r\n emoji: {\r\n suggest: boolean,\r\n big: boolean\r\n },\r\n background?: Background, // ! DEPRECATED\r\n themes: Theme[],\r\n theme: Theme['name'],\r\n notifications: {\r\n sound: boolean\r\n },\r\n nightTheme?: boolean, // ! DEPRECATED\r\n },\r\n keepSigned: boolean\r\n};\r\n\r\nexport const STATE_INIT: State = {\r\n allDialogsLoaded: {},\r\n pinnedOrders: {},\r\n contactsList: [],\r\n updates: {},\r\n filters: {},\r\n maxSeenMsgId: 0,\r\n stateCreatedTime: Date.now(),\r\n recentEmoji: [],\r\n topPeers: [],\r\n recentSearch: [],\r\n version: STATE_VERSION,\r\n authState: {\r\n _: isMobile ? 'authStateSignIn' : 'authStateSignQr'\r\n },\r\n hiddenPinnedMessages: {},\r\n settings: {\r\n messagesTextSize: 16,\r\n sendShortcut: 'enter',\r\n animationsEnabled: true,\r\n autoDownload: {\r\n contacts: true,\r\n private: true,\r\n groups: true,\r\n channels: true\r\n },\r\n autoPlay: {\r\n gifs: true,\r\n videos: true\r\n },\r\n stickers: {\r\n suggest: true,\r\n loop: true\r\n },\r\n emoji: {\r\n suggest: true,\r\n big: true\r\n },\r\n themes: [{\r\n name: 'day',\r\n background: {\r\n type: 'image',\r\n blur: false,\r\n slug: 'ByxGo2lrMFAIAAAAmkJxZabh8eM', // * new blurred camomile,\r\n highlightningColor: 'hsla(85.5319, 36.9171%, 40.402%, 0.4)'\r\n }\r\n }, {\r\n name: 'night',\r\n background: {\r\n type: 'color',\r\n blur: false,\r\n color: '#0f0f0f',\r\n highlightningColor: 'hsla(0, 0%, 3.82353%, 0.4)'\r\n }\r\n }],\r\n theme: 'system',\r\n notifications: {\r\n sound: false\r\n }\r\n },\r\n keepSigned: true\r\n};\r\n\r\nconst ALL_KEYS = Object.keys(STATE_INIT) as any as Array<keyof State>;\r\n\r\nconst REFRESH_KEYS = ['contactsList', 'stateCreatedTime',\r\n 'maxSeenMsgId', 'filters', 'topPeers'] as any as Array<keyof State>;\r\n\r\nconst REFRESH_KEYS_WEEK = ['dialogs', 'allDialogsLoaded', 'updates', 'pinnedOrders'] as any as Array<keyof State>;\r\n\r\nexport class AppStateManager extends EventListenerBase<{\r\n save: (state: State) => Promise<void>,\r\n peerNeeded: (peerId: number) => void,\r\n peerUnneeded: (peerId: number) => void,\r\n}> {\r\n public static STATE_INIT = STATE_INIT;\r\n private loaded: Promise<State>;\r\n private log = logger('STATE'/* , LogLevels.error */);\r\n\r\n private state: State;\r\n\r\n private neededPeers: Map<number, Set<string>> = new Map();\r\n private singlePeerMap: Map<string, number> = new Map();\r\n\r\n public storages = {\r\n users: new AppStorage<Record<number, User>, typeof DATABASE_STATE>(DATABASE_STATE, 'users'),\r\n chats: new AppStorage<Record<number, Chat>, typeof DATABASE_STATE>(DATABASE_STATE, 'chats'),\r\n dialogs: new AppStorage<Record<number, Dialog>, typeof DATABASE_STATE>(DATABASE_STATE, 'dialogs')\r\n };\r\n\r\n public storagesResults: {[key in keyof AppStateManager['storages']]: any[]} = {} as any;\r\n\r\n public storage = stateStorage;\r\n\r\n constructor() {\r\n super();\r\n this.loadSavedState();\r\n }\r\n\r\n public loadSavedState(): Promise<State> {\r\n if(this.loaded) return this.loaded;\r\n console.time('load state');\r\n this.loaded = new Promise((resolve) => {\r\n const storagesKeys = Object.keys(this.storages) as Array<keyof AppStateManager['storages']>;\r\n const storagesPromises: Promise<any>[] = storagesKeys.map(key => this.storages[key].getAll());\r\n\r\n const promises: Promise<any>[] = ALL_KEYS.map(key => stateStorage.get(key))\r\n .concat(sessionStorage.get('user_auth'))\r\n .concat(stateStorage.get('user_auth' as any)) // support old webk format\r\n .concat(storagesPromises);\r\n\r\n Promise.all(promises).then(async(arr) => {\r\n /* const self = this;\r\n const skipHandleKeys = new Set(['isProxy', 'filters', 'drafts']);\r\n const getHandler = (path?: string) => {\r\n return {\r\n get(target: any, key: any) {\r\n if(key === 'isProxy') {\r\n return true;\r\n }\r\n\r\n const prop = target[key];\r\n\r\n if(prop !== undefined && !skipHandleKeys.has(key) && !prop.isProxy && typeof(prop) === 'object') {\r\n target[key] = new Proxy(prop, getHandler(path || key));\r\n return target[key];\r\n }\r\n \r\n return prop;\r\n },\r\n set(target: any, key: any, value: any) {\r\n console.log('Setting', target, `.${key} to equal`, value, path);\r\n \r\n target[key] = value;\r\n\r\n // @ts-ignore\r\n self.pushToState(path || key, path ? self.state[path] : value, false);\r\n\r\n return true;\r\n }\r\n };\r\n }; */\r\n\r\n let state: State = this.state = {} as any;\r\n\r\n // ! then can't store false values\r\n for(let i = 0, length = ALL_KEYS.length; i < length; ++i) {\r\n const key = ALL_KEYS[i];\r\n const value = arr[i];\r\n if(value !== undefined) {\r\n // @ts-ignore\r\n state[key] = value;\r\n } else {\r\n this.pushToState(key, copy(STATE_INIT[key]));\r\n }\r\n }\r\n\r\n arr.splice(0, ALL_KEYS.length);\r\n\r\n // * Read auth\r\n let auth = arr.shift() as UserAuth | number;\r\n let shiftedWebKAuth = arr.shift() as UserAuth | number;\r\n if(!auth && shiftedWebKAuth) { // support old webk auth\r\n auth = shiftedWebKAuth;\r\n const keys: string[] = ['dc', 'server_time_offset', 'xt_instance'];\r\n for(let i = 1; i <= 5; ++i) {\r\n keys.push(`dc${i}_server_salt`);\r\n keys.push(`dc${i}_auth_key`);\r\n }\r\n\r\n const values = await Promise.all(keys.map(key => stateStorage.get(key as any)));\r\n keys.push('user_auth');\r\n values.push(typeof(auth) === 'number' ? {dcID: values[0] || App.baseDcId, id: auth} : auth);\r\n\r\n let obj: any = {};\r\n keys.forEach((key, idx) => {\r\n obj[key] = values[idx];\r\n });\r\n\r\n await sessionStorage.set(obj);\r\n }\r\n \r\n if(!auth) { // try to read Webogram's session from localStorage\r\n try {\r\n const keys = Object.keys(localStorage);\r\n for(let i = 0; i < keys.length; ++i) {\r\n const key = keys[i];\r\n let value: any;\r\n try {\r\n value = localStorage.getItem(key);\r\n value = JSON.parse(value);\r\n } catch(err) {\r\n //console.error(err);\r\n }\r\n\r\n sessionStorage.set({\r\n [key as any]: value\r\n });\r\n }\r\n\r\n auth = sessionStorage.getFromCache('user_auth');\r\n } catch(err) {\r\n this.log.error('localStorage import error', err);\r\n }\r\n }\r\n\r\n if(auth) {\r\n // ! Warning ! DON'T delete this\r\n state.authState = {_: 'authStateSignedIn'};\r\n rootScope.dispatchEvent('user_auth', typeof(auth) === 'number' ? {dcID: 0, id: auth} : auth); // * support old version\r\n }\r\n\r\n // * Read storages\r\n for(let i = 0, length = storagesKeys.length; i < length; ++i) {\r\n this.storagesResults[storagesKeys[i]] = arr[i] as any;\r\n }\r\n\r\n arr.splice(0, storagesKeys.length);\r\n\r\n const time = Date.now();\r\n if((state.stateCreatedTime + REFRESH_EVERY) < time) {\r\n if(DEBUG) {\r\n this.log('will refresh state', state.stateCreatedTime, time);\r\n }\r\n\r\n const r = (keys: typeof REFRESH_KEYS) => {\r\n keys.forEach(key => {\r\n this.pushToState(key, copy(STATE_INIT[key]));\r\n \r\n // @ts-ignore\r\n const s = this.storagesResults[key];\r\n if(s && s.length) {\r\n s.length = 0;\r\n }\r\n });\r\n };\r\n \r\n r(REFRESH_KEYS);\r\n\r\n if((state.stateCreatedTime + REFRESH_EVERY_WEEK) < time) {\r\n if(DEBUG) {\r\n this.log('will refresh updates');\r\n }\r\n\r\n r(REFRESH_KEYS_WEEK);\r\n }\r\n }\r\n \r\n //state = this.state = new Proxy(state, getHandler());\r\n\r\n // * support old version\r\n if(!state.settings.hasOwnProperty('theme') && state.settings.hasOwnProperty('nightTheme')) {\r\n state.settings.theme = state.settings.nightTheme ? 'night' : 'day';\r\n this.pushToState('settings', state.settings);\r\n }\r\n\r\n // * support old version\r\n if(!state.settings.hasOwnProperty('themes') && state.settings.background) {\r\n state.settings.themes = copy(STATE_INIT.settings.themes);\r\n const theme = state.settings.themes.find(t => t.name === state.settings.theme);\r\n if(theme) {\r\n theme.background = state.settings.background;\r\n this.pushToState('settings', state.settings);\r\n }\r\n }\r\n\r\n validateInitObject(STATE_INIT, state, (missingKey) => {\r\n // @ts-ignore\r\n this.pushToState(missingKey, state[missingKey]);\r\n });\r\n\r\n if(state.version !== STATE_VERSION) {\r\n this.pushToState('version', STATE_VERSION);\r\n }\r\n\r\n // ! probably there is better place for it\r\n rootScope.settings = state.settings;\r\n\r\n if(DEBUG) {\r\n this.log('state res', state, copy(state));\r\n }\r\n \r\n //return resolve();\r\n\r\n console.timeEnd('load state');\r\n resolve(state);\r\n }).catch(resolve);\r\n });\r\n\r\n return this.loaded;\r\n }\r\n\r\n public getState() {\r\n return this.state === undefined ? this.loadSavedState() : Promise.resolve(this.state);\r\n }\r\n\r\n public setByKey(key: string, value: any) {\r\n setDeepProperty(this.state, key, value);\r\n rootScope.dispatchEvent('settings_updated', {key, value});\r\n\r\n const first = key.split('.')[0];\r\n // @ts-ignore\r\n this.pushToState(first, this.state[first]);\r\n }\r\n\r\n public pushToState<T extends keyof State>(key: T, value: State[T], direct = true) {\r\n if(direct) {\r\n this.state[key] = value;\r\n }\r\n\r\n this.storage.set({\r\n [key]: value\r\n });\r\n }\r\n\r\n public requestPeer(peerId: number, type: string, limit?: number) {\r\n let set = this.neededPeers.get(peerId);\r\n if(set && set.has(type)) {\r\n return;\r\n }\r\n\r\n if(!set) {\r\n set = new Set();\r\n this.neededPeers.set(peerId, set);\r\n }\r\n\r\n set.add(type);\r\n this.dispatchEvent('peerNeeded', peerId);\r\n\r\n if(limit !== undefined) {\r\n this.keepPeerSingle(peerId, type);\r\n }\r\n }\r\n\r\n public isPeerNeeded(peerId: number) {\r\n return this.neededPeers.has(peerId);\r\n }\r\n\r\n public keepPeerSingle(peerId: number, type: string) {\r\n const existsPeerId = this.singlePeerMap.get(type);\r\n if(existsPeerId && existsPeerId !== peerId && this.neededPeers.has(existsPeerId)) {\r\n const set = this.neededPeers.get(existsPeerId);\r\n set.delete(type);\r\n\r\n if(!set.size) {\r\n this.neededPeers.delete(existsPeerId);\r\n this.dispatchEvent('peerUnneeded', existsPeerId);\r\n }\r\n }\r\n\r\n if(peerId) {\r\n this.singlePeerMap.set(type, peerId);\r\n }\r\n }\r\n\r\n /* public resetState() {\r\n for(let i in this.state) {\r\n // @ts-ignore\r\n this.state[i] = false;\r\n }\r\n sessionStorage.set(this.state).then(() => {\r\n location.reload();\r\n });\r\n } */\r\n}\r\n\r\n//console.trace('appStateManager include');\r\n\r\nconst appStateManager = new AppStateManager();\r\nMOUNT_CLASS_TO.appStateManager = appStateManager;\r\nexport default appStateManager;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\n// @ts-ignore\r\nexport const isTouchSupported = ('ontouchstart' in window) || (window.DocumentTouch && document instanceof DocumentTouch)/* || true */;","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport Countries, { Country, PhoneCodesMain } from \"../countries\";\r\nimport { cancelEvent } from \"../helpers/dom/cancelEvent\";\r\nimport { CLICK_EVENT_NAME } from \"../helpers/dom/clickEvent\";\r\nimport ListenerSetter from \"../helpers/listenerSetter\";\r\nimport mediaSizes from \"../helpers/mediaSizes\";\r\nimport { isTouchSupported } from \"../helpers/touchSupport\";\r\nimport { isApple, isMobileSafari, isSafari } from \"../helpers/userAgent\";\r\nimport appNavigationController from \"./appNavigationController\";\r\n\r\nexport function putPreloader(elem: Element, returnDiv = false): HTMLElement {\r\n const html = `\r\n <svg xmlns=\"http://www.w3.org/2000/svg\" class=\"preloader-circular\" viewBox=\"25 25 50 50\">\r\n <circle class=\"preloader-path\" cx=\"50\" cy=\"50\" r=\"20\" fill=\"none\" stroke-miterlimit=\"10\"/>\r\n </svg>`;\r\n\r\n if(returnDiv) {\r\n const div = document.createElement('div');\r\n div.classList.add('preloader');\r\n div.innerHTML = html;\r\n\r\n if(elem) {\r\n elem.appendChild(div);\r\n }\r\n\r\n return div;\r\n }\r\n \r\n elem.insertAdjacentHTML('beforeend', html);\r\n return elem.lastElementChild as HTMLElement;\r\n}\r\n\r\nMOUNT_CLASS_TO.putPreloader = putPreloader;\r\n\r\nexport function setButtonLoader(elem: HTMLButtonElement, icon = 'check') {\r\n elem.classList.remove('tgico-' + icon);\r\n elem.disabled = true;\r\n putPreloader(elem);\r\n\r\n return () => {\r\n elem.innerHTML = '';\r\n elem.classList.add('tgico-' + icon);\r\n elem.removeAttribute('disabled');\r\n };\r\n}\r\n\r\nlet sortedCountries: Country[];\r\nexport function formatPhoneNumber(str: string) {\r\n str = str.replace(/\\D/g, '');\r\n let phoneCode = str.slice(0, 6);\r\n \r\n ////console.log('str', str, phoneCode);\r\n if(!sortedCountries) {\r\n sortedCountries = Countries.slice().sort((a, b) => b.phoneCode.length - a.phoneCode.length);\r\n }\r\n \r\n let country = sortedCountries.find((c) => {\r\n return c.phoneCode.split(' and ').find((c) => phoneCode.indexOf(c.replace(/\\D/g, '')) === 0);\r\n });\r\n\r\n if(!country) return {formatted: str, country};\r\n\r\n country = PhoneCodesMain[country.phoneCode] || country;\r\n \r\n let pattern = country.pattern || country.phoneCode;\r\n pattern.split('').forEach((symbol, idx) => {\r\n if(symbol === ' ' && str[idx] !== ' ' && str.length > idx) {\r\n str = str.slice(0, idx) + ' ' + str.slice(idx);\r\n }\r\n });\r\n \r\n /* if(country.pattern) {\r\n str = str.slice(0, country.pattern.length);\r\n } */\r\n \r\n return {formatted: str, country};\r\n}\r\n\r\n/* export function parseMenuButtonsTo(to: {[name: string]: HTMLElement}, elements: HTMLCollection | NodeListOf<HTMLElement>) {\r\n Array.from(elements).forEach(el => {\r\n const match = el.className.match(/(?:^|\\s)menu-(.+?)(?:$|\\s)/);\r\n if(!match) return;\r\n to[match[1]] = el as HTMLElement;\r\n });\r\n} */\r\n\r\nlet onMouseMove = (e: MouseEvent) => {\r\n let rect = openedMenu.getBoundingClientRect();\r\n let {clientX, clientY} = e;\r\n \r\n let diffX = clientX >= rect.right ? clientX - rect.right : rect.left - clientX;\r\n let diffY = clientY >= rect.bottom ? clientY - rect.bottom : rect.top - clientY;\r\n \r\n if(diffX >= 100 || diffY >= 100) {\r\n closeBtnMenu();\r\n //openedMenu.parentElement.click();\r\n }\r\n //console.log('mousemove', diffX, diffY);\r\n};\r\n\r\nconst onClick = (e: MouseEvent | TouchEvent) => {\r\n //cancelEvent(e);\r\n closeBtnMenu();\r\n};\r\n\r\n// ! no need in this due to the same handler in appNavigationController\r\n/* const onKeyDown = (e: KeyboardEvent) => {\r\n if(e.key === 'Escape') {\r\n closeBtnMenu();\r\n cancelEvent(e);\r\n }\r\n}; */\r\n\r\nexport const closeBtnMenu = () => {\r\n if(openedMenu) {\r\n openedMenu.classList.remove('active');\r\n openedMenu.parentElement.classList.remove('menu-open');\r\n //openedMenu.previousElementSibling.remove(); // remove overlay\r\n if(menuOverlay) menuOverlay.remove();\r\n openedMenu = null;\r\n }\r\n \r\n if(openedMenuOnClose) {\r\n openedMenuOnClose();\r\n openedMenuOnClose = null;\r\n }\r\n\r\n if(!isTouchSupported) {\r\n window.removeEventListener('mousemove', onMouseMove);\r\n //window.removeEventListener('keydown', onKeyDown, {capture: true});\r\n window.removeEventListener('contextmenu', onClick);\r\n }\r\n\r\n document.removeEventListener(CLICK_EVENT_NAME, onClick);\r\n\r\n if(!isMobileSafari) {\r\n appNavigationController.removeByType('menu');\r\n }\r\n};\r\n\r\nwindow.addEventListener('resize', () => {\r\n if(openedMenu) {\r\n closeBtnMenu();\r\n }\r\n \r\n /* if(openedMenu && (openedMenu.style.top || openedMenu.style.left)) {\r\n const rect = openedMenu.getBoundingClientRect();\r\n const {innerWidth, innerHeight} = window;\r\n\r\n console.log(innerWidth, innerHeight, rect);\r\n } */\r\n});\r\n\r\nlet openedMenu: HTMLElement = null, openedMenuOnClose: () => void = null, menuOverlay: HTMLElement = null;\r\nexport function openBtnMenu(menuElement: HTMLElement, onClose?: () => void) {\r\n closeBtnMenu();\r\n\r\n if(!isMobileSafari) {\r\n appNavigationController.pushItem({\r\n type: 'menu',\r\n onPop: (canAnimate) => {\r\n closeBtnMenu();\r\n }\r\n });\r\n }\r\n \r\n openedMenu = menuElement;\r\n openedMenu.classList.add('active');\r\n openedMenu.parentElement.classList.add('menu-open');\r\n\r\n if(!menuOverlay) {\r\n menuOverlay = document.createElement('div');\r\n menuOverlay.classList.add('btn-menu-overlay');\r\n\r\n // ! because this event must be canceled, and can't cancel on menu click (below)\r\n menuOverlay.addEventListener(CLICK_EVENT_NAME, (e) => {\r\n cancelEvent(e);\r\n onClick(e);\r\n });\r\n }\r\n\r\n openedMenu.parentElement.insertBefore(menuOverlay, openedMenu);\r\n\r\n //document.body.classList.add('disable-hover');\r\n \r\n openedMenuOnClose = onClose;\r\n\r\n if(!isTouchSupported) {\r\n window.addEventListener('mousemove', onMouseMove);\r\n //window.addEventListener('keydown', onKeyDown, {capture: true});\r\n window.addEventListener('contextmenu', onClick, {once: true});\r\n }\r\n\r\n /* // ! because this event must be canceled, and can't cancel on menu click (below)\r\n overlay.addEventListener(CLICK_EVENT_NAME, (e) => {\r\n cancelEvent(e);\r\n onClick(e);\r\n }); */\r\n \r\n // ! safari iOS doesn't handle window click event on overlay, idk why\r\n document.addEventListener(CLICK_EVENT_NAME, onClick);\r\n}\r\n\r\nconst PADDING_TOP = 8;\r\nconst PADDING_LEFT = 8;\r\nexport function positionMenu({pageX, pageY}: MouseEvent | Touch, elem: HTMLElement, side?: 'left' | 'right' | 'center') {\r\n //let {clientX, clientY} = e;\r\n\r\n // * side mean the OPEN side\r\n\r\n let {scrollWidth: menuWidth, scrollHeight: menuHeight} = elem;\r\n //let {innerWidth: windowWidth, innerHeight: windowHeight} = window;\r\n const rect = document.body.getBoundingClientRect();\r\n const windowWidth = rect.width;\r\n const windowHeight = rect.height;\r\n\r\n side = mediaSizes.isMobile ? 'right' : 'left';\r\n let verticalSide: 'top' /* | 'bottom' */ | 'center' = 'top';\r\n\r\n const getSides = () => {\r\n return {\r\n x: {\r\n left: pageX,\r\n right: pageX - menuWidth\r\n },\r\n intermediateX: side === 'right' ? PADDING_LEFT : windowWidth - menuWidth - PADDING_LEFT,\r\n //intermediateX: clientX < windowWidth / 2 ? PADDING_LEFT : windowWidth - menuWidth - PADDING_LEFT,\r\n y: {\r\n top: pageY,\r\n bottom: pageY - menuHeight\r\n },\r\n //intermediateY: verticalSide === 'top' ? PADDING_TOP : windowHeight - menuHeight - PADDING_TOP,\r\n intermediateY: pageY < windowHeight / 2 ? PADDING_TOP : windowHeight - menuHeight - PADDING_TOP,\r\n };\r\n };\r\n\r\n const sides = getSides();\r\n\r\n const possibleSides = {\r\n x: {\r\n left: sides.x.left + menuWidth + PADDING_LEFT <= windowWidth,\r\n right: sides.x.right >= PADDING_LEFT\r\n },\r\n y: {\r\n top: sides.y.top + menuHeight + PADDING_TOP <= windowHeight,\r\n bottom: sides.y.bottom - PADDING_TOP >= PADDING_TOP\r\n }\r\n };\r\n\r\n /* if(side === undefined) {\r\n if((clientX + menuWidth + PADDING_LEFT) > windowWidth) {\r\n side = 'right';\r\n }\r\n } */\r\n\r\n {\r\n /* const x = sides.x;\r\n\r\n const s = Object.keys(x) as (keyof typeof possibleSides.x)[];\r\n if(side) {\r\n s.findAndSplice(s => s === side);\r\n s.unshift(side);\r\n }\r\n\r\n const possibleSide = s.find(s => possibleSides.x[s]); */\r\n let left: number;\r\n /* if(possibleSide) {\r\n left = x[possibleSide];\r\n side = possibleSide;\r\n } else {\r\n left = sides.intermediateX;\r\n side = undefined;\r\n } */\r\n left = possibleSides.x[side] ? sides.x[side] : (side = 'center', sides.intermediateX);\r\n \r\n elem.style.left = left + 'px';\r\n }\r\n\r\n /* if((clientY + menuHeight + PADDING_TOP) > windowHeight) {\r\n elem.style.top = clamp(clientY - menuHeight, PADDING_TOP, windowHeight - menuHeight - PADDING_TOP) + 'px';\r\n // elem.style.top = (innerHeight - scrollHeight - PADDING_TOP) + 'px';\r\n verticalSide = 'bottom';\r\n } else {\r\n elem.style.top = Math.max(PADDING_TOP, clientY) + 'px';\r\n verticalSide = 'top';\r\n } */\r\n\r\n {\r\n let top: number;\r\n\r\n top = possibleSides.y[verticalSide] ? sides.y[verticalSide] : (verticalSide = 'center', sides.intermediateY);\r\n \r\n elem.style.top = top + 'px';\r\n }\r\n \r\n elem.className = elem.className.replace(/(top|center|bottom)-(left|center|right)/g, '');\r\n elem.classList.add(\r\n //(verticalSide === 'center' ? verticalSide : (verticalSide === 'bottom' ? 'top' : 'bottom')) +\r\n (verticalSide === 'center' ? verticalSide : 'bottom') +\r\n '-' +\r\n (side === 'center' ? side : (side === 'left' ? 'right' : 'left')));\r\n}\r\n\r\nexport function attachContextMenuListener(element: HTMLElement, callback: (e: Touch | MouseEvent) => void, listenerSetter?: ListenerSetter) {\r\n const add = listenerSetter ? listenerSetter.add.bind(listenerSetter, element) : element.addEventListener.bind(element);\r\n const remove = listenerSetter ? listenerSetter.removeManual.bind(listenerSetter, element) : element.removeEventListener.bind(element);\r\n\r\n if(isApple && isTouchSupported) {\r\n let timeout: number;\r\n\r\n const options: any = /* null */{capture: true};\r\n\r\n const onCancel = () => {\r\n clearTimeout(timeout);\r\n remove('touchmove', onCancel, options);\r\n remove('touchend', onCancel, options);\r\n remove('touchcancel', onCancel, options);\r\n };\r\n\r\n add('touchstart', (e: TouchEvent) => {\r\n if(e.touches.length > 1) {\r\n onCancel();\r\n return;\r\n }\r\n \r\n add('touchmove', onCancel, options);\r\n add('touchend', onCancel, options);\r\n add('touchcancel', onCancel, options);\r\n\r\n timeout = window.setTimeout(() => {\r\n callback(e.touches[0]);\r\n onCancel();\r\n\r\n if(openedMenu) {\r\n element.addEventListener('touchend', cancelEvent, {once: true}); // * fix instant closing\r\n }\r\n }, .4e3);\r\n });\r\n\r\n /* if(!isSafari) {\r\n add('contextmenu', (e: any) => {\r\n cancelEvent(e);\r\n }, {passive: false, capture: true});\r\n } */\r\n } else {\r\n add('contextmenu', isTouchSupported ? (e: any) => {\r\n callback(e);\r\n\r\n if(openedMenu) {\r\n element.addEventListener('touchend', cancelEvent, {once: true}); // * fix instant closing\r\n }\r\n } : callback);\r\n }\r\n};\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport calcImageInBox from \"./calcImageInBox\";\r\nimport EventListenerBase from \"./eventListenerBase\";\r\n\r\nexport class MediaSize {\r\n constructor(public width = 0, public height = width) {\r\n\r\n }\r\n\r\n public aspect(boxSize: MediaSize, fitted: boolean) {\r\n return calcImageInBox(this.width, this.height, boxSize.width, boxSize.height, fitted);\r\n }\r\n\r\n public aspectFitted(boxSize: MediaSize) {\r\n return this.aspect(boxSize, true);\r\n }\r\n\r\n public aspectCovered(boxSize: MediaSize) {\r\n return this.aspect(boxSize, false);\r\n }\r\n}\r\n\r\nexport function makeMediaSize(width?: number, height?: number): MediaSize {\r\n return new MediaSize(width, height);\r\n}\r\n\r\ntype MediaTypeSizes = {\r\n regular: MediaSize,\r\n webpage: MediaSize,\r\n album: MediaSize,\r\n esgSticker: MediaSize,\r\n animatedSticker: MediaSize,\r\n staticSticker: MediaSize,\r\n emojiSticker: MediaSize\r\n};\r\n\r\nexport enum ScreenSize {\r\n mobile,\r\n medium,\r\n large\r\n}\r\n\r\nconst MOBILE_SIZE = 600;\r\nconst MEDIUM_SIZE = 1275;\r\nconst LARGE_SIZE = 1680;\r\n\r\nclass MediaSizes extends EventListenerBase<{\r\n changeScreen: (from: ScreenSize, to: ScreenSize) => void\r\n}> {\r\n private screenSizes: {key: ScreenSize, value: number}[] = [\r\n {key: ScreenSize.mobile, value: MOBILE_SIZE},\r\n {key: ScreenSize.medium, value: MEDIUM_SIZE},\r\n {key: ScreenSize.large, value: LARGE_SIZE}\r\n ];\r\n\r\n private sizes: {[k in 'desktop' | 'handhelds']: MediaTypeSizes} = {\r\n handhelds: {\r\n regular: makeMediaSize(270, 270),\r\n webpage: makeMediaSize(270, 200),\r\n album: makeMediaSize(270, 0),\r\n esgSticker: makeMediaSize(68, 68),\r\n animatedSticker: makeMediaSize(180, 180),\r\n staticSticker: makeMediaSize(180, 180),\r\n emojiSticker: makeMediaSize(112, 112)\r\n },\r\n desktop: {\r\n regular: makeMediaSize(400, 320),\r\n webpage: makeMediaSize(400, 320),\r\n album: makeMediaSize(420, 0),\r\n esgSticker: makeMediaSize(80, 80),\r\n animatedSticker: makeMediaSize(200, 200),\r\n staticSticker: makeMediaSize(200, 200),\r\n emojiSticker: makeMediaSize(112, 112)\r\n }\r\n };\r\n\r\n public isMobile = false;\r\n public active: MediaTypeSizes;\r\n public activeScreen: ScreenSize;\r\n public rAF: number;\r\n\r\n constructor() {\r\n super();\r\n\r\n window.addEventListener('resize', () => {\r\n if(this.rAF) window.cancelAnimationFrame(this.rAF);\r\n this.rAF = window.requestAnimationFrame(() => {\r\n this.handleResize();\r\n this.rAF = 0;\r\n });\r\n });\r\n this.handleResize();\r\n }\r\n\r\n private handleResize = () => {\r\n const innerWidth = window.innerWidth;\r\n //this.isMobile = innerWidth <= 720;\r\n \r\n let activeScreen = this.screenSizes[0].key;\r\n for(let i = this.screenSizes.length - 1; i >= 0; --i) {\r\n if(this.screenSizes[i].value < innerWidth) {\r\n activeScreen = (this.screenSizes[i + 1] || this.screenSizes[i]).key;\r\n break;\r\n }\r\n }\r\n\r\n const wasScreen = this.activeScreen;\r\n this.activeScreen = activeScreen;\r\n this.isMobile = this.activeScreen === ScreenSize.mobile;\r\n this.active = this.isMobile ? this.sizes.handhelds : this.sizes.desktop;\r\n\r\n //console.time('esg');\r\n //const computedStyle = window.getComputedStyle(document.documentElement);\r\n //this.active.esgSticker.width = parseFloat(computedStyle.getPropertyValue('--esg-sticker-size'));\r\n //console.timeEnd('esg');\r\n\r\n if(wasScreen !== activeScreen) {\r\n //console.log('changeScreen', this.activeScreen, activeScreen);\r\n\r\n if(wasScreen !== undefined) {\r\n this.dispatchEvent('changeScreen', this.activeScreen, activeScreen);\r\n }\r\n }\r\n\r\n /* if(this.isMobile) {\r\n for(let i in this.active) {\r\n // @ts-ignore\r\n let size = this.active[i];\r\n size.width = innerWidth \r\n }\r\n } */\r\n };\r\n}\r\n\r\nconst mediaSizes = new MediaSizes();\r\nMOUNT_CLASS_TO.mediaSizes = mediaSizes;\r\nexport default mediaSizes;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport findUpClassName from \"../helpers/dom/findUpClassName\";\r\nimport sequentialDom from \"../helpers/sequentialDom\";\r\nimport {isTouchSupported} from \"../helpers/touchSupport\";\r\nimport rootScope from \"../lib/rootScope\";\r\n\r\nlet rippleClickId = 0;\r\nexport function ripple(elem: HTMLElement, callback: (id: number) => Promise<boolean | void> = () => Promise.resolve(), onEnd: (id: number) => void = null, prepend = false) {\r\n //return;\r\n if(elem.querySelector('.c-ripple')) return;\r\n elem.classList.add('rp');\r\n \r\n let r = document.createElement('div');\r\n r.classList.add('c-ripple');\r\n\r\n const isSquare = elem.classList.contains('rp-square');\r\n if(isSquare) {\r\n r.classList.add('is-square');\r\n }\r\n\r\n elem[prepend ? 'prepend' : 'append'](r);\r\n\r\n let handler: () => void;\r\n //let animationEndPromise: Promise<number>;\r\n const drawRipple = (clientX: number, clientY: number) => {\r\n const startTime = Date.now();\r\n const elem = document.createElement('div');\r\n\r\n const clickId = rippleClickId++;\r\n \r\n //console.log('ripple drawRipple');\r\n \r\n const duration = +window.getComputedStyle(r).getPropertyValue('--ripple-duration').replace('s', '') * 1000;\r\n //console.log('ripple duration', duration);\r\n\r\n handler = () => {\r\n //handler = () => animationEndPromise.then((duration) => {\r\n //console.log('ripple animation was:', duration);\r\n\r\n //const duration = isSquare || mediaSizes.isMobile ? 200 : 700;\r\n //return;\r\n let elapsedTime = Date.now() - startTime;\r\n const cb = () => {\r\n //console.log('ripple elapsedTime total pre-remove:', Date.now() - startTime);\r\n sequentialDom.mutate(() => {\r\n elem.remove();\r\n });\r\n \r\n if(onEnd) onEnd(clickId);\r\n };\r\n if(elapsedTime < duration) {\r\n let delay = Math.max(duration - elapsedTime, duration / 2);\r\n setTimeout(() => elem.classList.add('hiding'), Math.max(delay - duration / 2, 0));\r\n\r\n setTimeout(cb, delay);\r\n } else {\r\n elem.classList.add('hiding');\r\n setTimeout(cb, duration / 2);\r\n }\r\n\r\n if(!isTouchSupported) {\r\n window.removeEventListener('contextmenu', handler);\r\n }\r\n\r\n handler = null;\r\n touchStartFired = false;\r\n };\r\n //});\r\n\r\n callback && callback(clickId);\r\n\r\n /* callback().then((bad) => {\r\n if(bad) {\r\n span.remove();\r\n return;\r\n } */\r\n \r\n //console.log('ripple after promise', Date.now() - startTime);\r\n //console.log('ripple tooSlow:', tooSlow);\r\n /* if(tooSlow) {\r\n span.remove();\r\n return;\r\n } */\r\n\r\n window.requestAnimationFrame(() => {\r\n const rect = r.getBoundingClientRect();\r\n elem.classList.add('c-ripple__circle');\r\n\r\n const clickX = clientX - rect.left;\r\n const clickY = clientY - rect.top;\r\n\r\n const radius = Math.sqrt((Math.abs(clickY - rect.height / 2) + rect.height / 2) ** 2 + (Math.abs(clickX - rect.width / 2) + rect.width / 2) ** 2);\r\n const size = radius;\r\n\r\n // center of circle\r\n const x = clickX - size / 2;\r\n const y = clickY - size / 2;\r\n\r\n //console.log('ripple click', offsetFromCenter, size, clickX, clickY);\r\n\r\n elem.style.width = elem.style.height = size + 'px';\r\n elem.style.left = x + 'px';\r\n elem.style.top = y + 'px';\r\n\r\n // нижний код выполняется с задержкой\r\n /* animationEndPromise = new Promise((resolve) => {\r\n span.addEventListener('animationend', () => {\r\n // 713 -> 700\r\n resolve(((Date.now() - startTime) / 100 | 0) * 100);\r\n }, {once: true});\r\n }); */\r\n \r\n // нижний код не всегда включает анимацию ПРИ КЛИКЕ НА ТАЧПАД БЕЗ ТАПТИК ЭНЖИНА\r\n /* span.style.display = 'none';\r\n r.append(span);\r\n duration = +window.getComputedStyle(span).getPropertyValue('animation-duration').replace('s', '') * 1000;\r\n span.style.display = ''; */\r\n\r\n r.append(elem);\r\n\r\n //r.classList.add('active');\r\n //handler();\r\n });\r\n //});\r\n };\r\n\r\n const isRippleUnneeded = (e: Event) => e.target !== elem && (\r\n ['BUTTON', 'A'].includes((e.target as HTMLElement).tagName) \r\n || findUpClassName(e.target as HTMLElement, 'c-ripple') !== r\r\n );\r\n\r\n // TODO: rename this variable\r\n let touchStartFired = false;\r\n if(isTouchSupported) {\r\n let touchEnd = () => {\r\n handler && handler();\r\n };\r\n \r\n elem.addEventListener('touchstart', (e) => {\r\n if(!rootScope.settings.animationsEnabled) {\r\n return;\r\n }\r\n\r\n //console.log('ripple touchstart', e);\r\n if(e.touches.length > 1 || touchStartFired || isRippleUnneeded(e)) {\r\n return;\r\n }\r\n \r\n //console.log('touchstart', e);\r\n touchStartFired = true;\r\n \r\n let {clientX, clientY} = e.touches[0];\r\n drawRipple(clientX, clientY);\r\n elem.addEventListener('touchend', touchEnd, {once: true});\r\n \r\n window.addEventListener('touchmove', (e) => {\r\n e.cancelBubble = true;\r\n e.stopPropagation();\r\n touchEnd();\r\n elem.removeEventListener('touchend', touchEnd);\r\n }, {once: true});\r\n }, {passive: true});\r\n } else {\r\n elem.addEventListener('mousedown', (e) => {\r\n if(![0, 2].includes(e.button)) { // only left and right buttons\r\n return;\r\n }\r\n\r\n if(!rootScope.settings.animationsEnabled) {\r\n return;\r\n }\r\n //console.log('ripple mousedown', e, e.target, findUpClassName(e.target as HTMLElement, 'c-ripple') === r);\r\n\r\n if(elem.dataset.ripple === '0' || isRippleUnneeded(e)) {\r\n return;\r\n } else if(touchStartFired) {\r\n touchStartFired = false;\r\n return;\r\n }\r\n \r\n let {clientX, clientY} = e;\r\n drawRipple(clientX, clientY);\r\n window.addEventListener('mouseup', handler, {once: true, passive: true});\r\n window.addEventListener('contextmenu', handler, {once: true, passive: true});\r\n }, {passive: true});\r\n }\r\n}\r\n","export default function Worker_fn() {\n return new Worker(__webpack_public_path__ + \"rlottie.worker.86bed2789739b353d39d.bundle.worker.js\");\n}\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport RLottieWorker from 'worker-loader!./rlottie/rlottie.worker';\r\nimport animationIntersector from \"../components/animationIntersector\";\r\nimport { MOUNT_CLASS_TO } from '../config/debug';\r\nimport EventListenerBase from \"../helpers/eventListenerBase\";\r\nimport mediaSizes from \"../helpers/mediaSizes\";\r\nimport { clamp } from '../helpers/number';\r\nimport { pause } from '../helpers/schedulers';\r\nimport { isAndroid, isApple, isAppleMobile, isSafari } from \"../helpers/userAgent\";\r\nimport { logger, LogTypes } from \"./logger\";\r\nimport apiManager from \"./mtproto/mtprotoworker\";\r\n\r\nlet convert = (value: number) => {\r\n\treturn Math.round(Math.min(Math.max(value, 0), 1) * 255);\r\n};\r\n\r\ntype RLottiePlayerListeners = 'enterFrame' | 'ready' | 'firstFrame' | 'cached';\r\ntype RLottieOptions = {\r\n container: HTMLElement, \r\n autoplay?: boolean, \r\n animationData: string, \r\n loop?: boolean, \r\n width?: number,\r\n height?: number,\r\n group?: string,\r\n noCache?: true,\r\n needUpscale?: true,\r\n skipRatio?: number\r\n};\r\n\r\nexport class RLottiePlayer extends EventListenerBase<{\r\n enterFrame: (frameNo: number) => void,\r\n ready: () => void,\r\n firstFrame: () => void,\r\n cached: () => void\r\n}> {\r\n public static reqId = 0;\r\n\r\n public reqId = 0;\r\n public curFrame: number;\r\n public frameCount: number;\r\n public fps: number;\r\n public skipDelta: number;\r\n\r\n public worker: QueryableWorker;\r\n \r\n public width = 0;\r\n public height = 0;\r\n\r\n public el: HTMLElement;\r\n public canvas: HTMLCanvasElement;\r\n public context: CanvasRenderingContext2D;\r\n\r\n public paused = true;\r\n //public paused = false;\r\n public direction = 1;\r\n public speed = 1;\r\n public autoplay = true;\r\n public _autoplay: boolean; // ! will be used to store original value for settings.stickers.loop\r\n public loop = true;\r\n public _loop: boolean; // ! will be used to store original value for settings.stickers.loop\r\n public group = '';\r\n\r\n private frInterval: number;\r\n private frThen: number;\r\n private rafId: number;\r\n\r\n //private caching = false;\r\n //private removed = false;\r\n\r\n private frames: {[frameNo: string]: Uint8ClampedArray} = {};\r\n public imageData: ImageData;\r\n public clamped: Uint8ClampedArray;\r\n public cachingDelta = 0;\r\n\r\n //private playedTimes = 0;\r\n\r\n private currentMethod: RLottiePlayer['mainLoopForwards'] | RLottiePlayer['mainLoopBackwards'];\r\n private frameListener: () => void;\r\n\r\n constructor({el, worker, options}: {\r\n el: HTMLElement,\r\n worker: QueryableWorker,\r\n options: RLottieOptions\r\n }) {\r\n super(true);\r\n\r\n this.reqId = ++RLottiePlayer['reqId'];\r\n this.el = el;\r\n this.worker = worker;\r\n\r\n for(let i in options) {\r\n if(this.hasOwnProperty(i)) {\r\n // @ts-ignore\r\n this[i] = options[i];\r\n }\r\n }\r\n\r\n this._loop = this.loop;\r\n this._autoplay = this.autoplay;\r\n\r\n // * Skip ratio (30fps)\r\n let skipRatio: number;\r\n if(options.skipRatio !== undefined) skipRatio = options.skipRatio;\r\n else if((isAndroid || isAppleMobile || (isApple && !isSafari)) && this.width < 100 && this.height < 100) {\r\n skipRatio = 0.5;\r\n }\r\n\r\n this.skipDelta = skipRatio !== undefined ? 1 / skipRatio | 0 : 1;\r\n\r\n //options.needUpscale = true;\r\n\r\n // * Pixel ratio\r\n //const pixelRatio = window.devicePixelRatio;\r\n const pixelRatio = clamp(window.devicePixelRatio, 1, 2);\r\n if(pixelRatio > 1) {\r\n //this.cachingEnabled = true;//this.width < 100 && this.height < 100;\r\n if(options.needUpscale) {\r\n this.width = Math.round(this.width * pixelRatio);\r\n this.height = Math.round(this.height * pixelRatio);\r\n } else if(pixelRatio > 1) {\r\n if(this.width > 100 && this.height > 100) {\r\n if(isApple || !mediaSizes.isMobile) {\r\n /* this.width = Math.round(this.width * (pixelRatio - 1));\r\n this.height = Math.round(this.height * (pixelRatio - 1)); */\r\n this.width = Math.round(this.width * pixelRatio);\r\n this.height = Math.round(this.height * pixelRatio);\r\n } else if(pixelRatio > 2.5) {\r\n this.width = Math.round(this.width * (pixelRatio - 1.5));\r\n this.height = Math.round(this.height * (pixelRatio - 1.5));\r\n }\r\n } else {\r\n this.width = Math.round(this.width * Math.max(1.5, pixelRatio - 1.5));\r\n this.height = Math.round(this.height * Math.max(1.5, pixelRatio - 1.5));\r\n }\r\n }\r\n }\r\n\r\n //options.noCache = true;\r\n \r\n // * Cache frames params\r\n if(!options.noCache/* && false */) {\r\n // проверка на размер уже после скейлинга, сделано для попапа и сайдбара, где стикеры 80х80 и 68х68, туда нужно 75%\r\n if(isApple && this.width > 100 && this.height > 100) {\r\n this.cachingDelta = 2; //2 // 50%\r\n } else if(this.width < 100 && this.height < 100) {\r\n this.cachingDelta = Infinity; // 100%\r\n } else {\r\n this.cachingDelta = 4; // 75%\r\n }\r\n }\r\n \r\n // this.cachingDelta = Infinity;\r\n // if(isApple) {\r\n // this.cachingDelta = 0; //2 // 50%\r\n // }\r\n\r\n /* this.width *= 0.8;\r\n this.height *= 0.8; */\r\n \r\n //console.log(\"RLottiePlayer width:\", this.width, this.height, options);\r\n this.canvas = document.createElement('canvas');\r\n this.canvas.classList.add('rlottie');\r\n this.canvas.width = this.width;\r\n this.canvas.height = this.height;\r\n this.context = this.canvas.getContext('2d');\r\n\r\n this.clamped = new Uint8ClampedArray(this.width * this.height * 4);\r\n this.imageData = new ImageData(this.width, this.height);\r\n }\r\n\r\n public clearCache() {\r\n this.frames = {};\r\n }\r\n\r\n public sendQuery(methodName: string, ...args: any[]) {\r\n //console.trace('RLottie sendQuery:', methodName);\r\n this.worker.sendQuery(methodName, this.reqId, ...args);\r\n }\r\n\r\n public loadFromData(jsonString: string) {\r\n this.sendQuery('loadFromData', jsonString, this.width, this.height/* , this.canvas.transferControlToOffscreen() */);\r\n }\r\n\r\n public play() {\r\n if(!this.paused) return;\r\n\r\n //return;\r\n\r\n //console.log('RLOTTIE PLAY' + this.reqId);\r\n\r\n this.paused = false;\r\n this.setMainLoop();\r\n }\r\n\r\n public pause(clearPendingRAF = true) {\r\n if(this.paused) return;\r\n\r\n this.paused = true;\r\n if(clearPendingRAF) {\r\n clearTimeout(this.rafId);\r\n }\r\n //window.cancelAnimationFrame(this.rafId);\r\n }\r\n\r\n public stop(renderFirstFrame = true) {\r\n this.pause();\r\n\r\n this.curFrame = this.direction === 1 ? 0 : this.frameCount;\r\n if(renderFirstFrame) {\r\n this.requestFrame(this.curFrame);\r\n //this.sendQuery('renderFrame', this.curFrame);\r\n }\r\n }\r\n\r\n public restart() {\r\n this.stop(false);\r\n this.play();\r\n }\r\n\r\n public setSpeed(speed: number) {\r\n this.speed = speed;\r\n\r\n if(!this.paused) {\r\n this.setMainLoop();\r\n }\r\n }\r\n\r\n public setDirection(direction: number) {\r\n this.direction = direction;\r\n \r\n if(!this.paused) {\r\n this.setMainLoop();\r\n }\r\n }\r\n\r\n public remove() {\r\n //alert('remove');\r\n lottieLoader.onDestroy(this.reqId);\r\n this.pause();\r\n this.sendQuery('destroy');\r\n //this.removed = true;\r\n }\r\n\r\n public renderFrame2(frame: Uint8ClampedArray, frameNo: number) {\r\n /* this.setListenerResult('enterFrame', frameNo);\r\n return; */\r\n\r\n try {\r\n this.imageData.data.set(frame);\r\n \r\n //this.context.putImageData(new ImageData(frame, this.width, this.height), 0, 0);\r\n //let perf = performance.now();\r\n this.context.putImageData(this.imageData, 0, 0);\r\n //console.log('renderFrame2 perf:', performance.now() - perf);\r\n } catch(err) {\r\n console.error('RLottiePlayer renderFrame error:', err/* , frame */, this.width, this.height);\r\n this.autoplay = false;\r\n this.pause();\r\n return;\r\n }\r\n \r\n //console.log('set result enterFrame', frameNo);\r\n this.dispatchEvent('enterFrame', frameNo);\r\n }\r\n\r\n public renderFrame(frame: Uint8ClampedArray, frameNo: number) {\r\n //console.log('renderFrame', frameNo, this);\r\n if(this.cachingDelta && (frameNo % this.cachingDelta || !frameNo) && !this.frames[frameNo]) {\r\n this.frames[frameNo] = new Uint8ClampedArray(frame);//frame;\r\n }\r\n\r\n /* if(!this.listenerResults.hasOwnProperty('cached')) {\r\n this.setListenerResult('enterFrame', frameNo);\r\n if(frameNo === (this.frameCount - 1)) {\r\n this.setListenerResult('cached');\r\n }\r\n\r\n return;\r\n } */\r\n\r\n if(this.frInterval) {\r\n const now = Date.now(), delta = now - this.frThen;\r\n //console.log(`renderFrame delta${this.reqId}:`, this, delta, this.frInterval);\r\n\r\n if(delta < 0) {\r\n if(this.rafId) clearTimeout(this.rafId);\r\n return this.rafId = window.setTimeout(() => {\r\n this.renderFrame2(frame, frameNo);\r\n }, this.frInterval > -delta ? -delta % this.frInterval : this.frInterval);\r\n //await new Promise((resolve) => setTimeout(resolve, -delta % this.frInterval));\r\n }\r\n }\r\n\r\n this.renderFrame2(frame, frameNo);\r\n }\r\n\r\n public requestFrame(frameNo: number) {\r\n if(this.frames[frameNo]) {\r\n this.renderFrame(this.frames[frameNo], frameNo);\r\n } else if(isSafari) {\r\n this.sendQuery('renderFrame', frameNo);\r\n } else {\r\n if(!this.clamped.length) { // fix detached\r\n this.clamped = new Uint8ClampedArray(this.width * this.height * 4);\r\n }\r\n \r\n this.sendQuery('renderFrame', frameNo, this.clamped);\r\n }\r\n }\r\n\r\n private mainLoopForwards() {\r\n const frame = (this.curFrame + this.skipDelta) >= this.frameCount ? this.curFrame = 0 : this.curFrame += this.skipDelta;\r\n //console.log('mainLoopForwards', this.curFrame, this.skipDelta, frame);\r\n\r\n this.requestFrame(frame);\r\n if((frame + this.skipDelta) >= this.frameCount) {\r\n //this.playedTimes++;\r\n\r\n if(!this.loop) {\r\n this.pause(false);\r\n return false;\r\n }\r\n }\r\n\r\n return true;\r\n }\r\n \r\n private mainLoopBackwards() {\r\n const frame = (this.curFrame - this.skipDelta) < 0 ? this.curFrame = this.frameCount - 1 : this.curFrame -= this.skipDelta;\r\n //console.log('mainLoopBackwards', this.curFrame, this.skipDelta, frame);\r\n\r\n this.requestFrame(frame);\r\n if((frame - this.skipDelta) < 0) {\r\n //this.playedTimes++;\r\n\r\n if(!this.loop) {\r\n this.pause(false);\r\n return false;\r\n }\r\n }\r\n\r\n return true;\r\n }\r\n\r\n public setMainLoop() {\r\n //window.cancelAnimationFrame(this.rafId);\r\n clearTimeout(this.rafId);\r\n\r\n this.frInterval = 1000 / this.fps / this.speed * this.skipDelta;\r\n this.frThen = Date.now() - this.frInterval;\r\n\r\n //console.trace('setMainLoop', this.frInterval, this.direction, this, JSON.stringify(this.listenerResults), this.listenerResults);\r\n\r\n const method = (this.direction === 1 ? this.mainLoopForwards : this.mainLoopBackwards).bind(this);\r\n this.currentMethod = method;\r\n //this.frameListener && this.removeListener('enterFrame', this.frameListener);\r\n\r\n //setTimeout(() => {\r\n //this.addListener('enterFrame', this.frameListener);\r\n //}, 0);\r\n\r\n if(this.frameListener && this.listenerResults.hasOwnProperty('enterFrame')) {\r\n this.frameListener();\r\n }\r\n \r\n //this.mainLoop(method);\r\n //this.r(method);\r\n //method();\r\n }\r\n\r\n public async onLoad(frameCount: number, fps: number) {\r\n this.curFrame = this.direction === 1 ? 0 : frameCount - 1;\r\n this.frameCount = frameCount;\r\n this.fps = fps;\r\n\r\n // * Handle 30fps stickers if 30fps set\r\n if(this.fps < 60 && this.skipDelta !== 1) {\r\n const diff = 60 / fps;\r\n this.skipDelta = this.skipDelta / diff | 0;\r\n }\r\n\r\n this.frInterval = 1000 / this.fps / this.speed * this.skipDelta;\r\n this.frThen = Date.now() - this.frInterval;\r\n //this.sendQuery('renderFrame', 0);\r\n \r\n // Кешировать сразу не получится, рендер стикера (тайгер) занимает 519мс, \r\n // если рендерить 75% с получением каждого кадра из воркера, будет 475мс, т.е. при 100% было бы 593мс, потеря на передаче 84мс. \r\n\r\n /* console.time('cache' + this.reqId);\r\n for(let i = 0; i < frameCount; ++i) {\r\n //if(this.removed) return;\r\n \r\n if(i % 4) {\r\n await new Promise((resolve) => {\r\n delete this.listenerResults.enterFrame;\r\n this.addListener('enterFrame', resolve, true);\r\n this.requestFrame(i);\r\n }); \r\n }\r\n }\r\n \r\n console.timeEnd('cache' + this.reqId); */\r\n //console.log('cached');\r\n /* this.el.innerHTML = '';\r\n this.el.append(this.canvas);\r\n return; */\r\n\r\n this.requestFrame(0);\r\n this.dispatchEvent('ready');\r\n this.addEventListener('enterFrame', () => {\r\n this.dispatchEvent('firstFrame');\r\n\r\n this.el.appendChild(this.canvas);\r\n\r\n //console.log('enterFrame firstFrame');\r\n \r\n //let lastTime = this.frThen;\r\n this.frameListener = () => {\r\n if(this.paused) {\r\n return;\r\n }\r\n\r\n const time = Date.now();\r\n //console.log(`enterFrame handle${this.reqId}`, time, (time - lastTime), this.frInterval);\r\n /* if(Math.round(time - lastTime + this.frInterval * 0.25) < Math.round(this.frInterval)) {\r\n return;\r\n } */\r\n\r\n //lastTime = time;\r\n\r\n this.frThen = time + this.frInterval;\r\n const canContinue = this.currentMethod();\r\n if(!canContinue && !this.loop && this.autoplay) {\r\n this.autoplay = false;\r\n }\r\n };\r\n\r\n this.addEventListener('enterFrame', this.frameListener);\r\n }, true);\r\n }\r\n}\r\n\r\nclass QueryableWorker extends EventListenerBase<any> {\r\n constructor(private worker: Worker, private defaultListener: (data: any) => void = () => {}, onError?: (error: any) => void) {\r\n super();\r\n\r\n if(onError) {\r\n this.worker.onerror = onError;\r\n }\r\n\r\n this.worker.onmessage = (event) => {\r\n //return;\r\n //console.log('worker onmessage', event.data);\r\n if(event.data instanceof Object &&\r\n event.data.hasOwnProperty('queryMethodListener') &&\r\n event.data.hasOwnProperty('queryMethodArguments')) {\r\n /* if(event.data.queryMethodListener === 'frame') {\r\n return;\r\n } */\r\n\r\n this.dispatchEvent(event.data.queryMethodListener, ...event.data.queryMethodArguments);\r\n } else {\r\n this.defaultListener.call(this, event.data);\r\n }\r\n };\r\n }\r\n\r\n public postMessage(message: any) {\r\n this.worker.postMessage(message);\r\n }\r\n\r\n public terminate() {\r\n this.worker.terminate();\r\n }\r\n\r\n public sendQuery(queryMethod: string, ...args: any[]) {\r\n if(isSafari) {\r\n this.worker.postMessage({\r\n 'queryMethod': queryMethod,\r\n 'queryMethodArguments': args\r\n });\r\n } else {\r\n //const transfer: (ArrayBuffer | OffscreenCanvas)[] = [];\r\n const transfer: ArrayBuffer[] = [];\r\n args.forEach(arg => {\r\n if(arg instanceof ArrayBuffer) {\r\n transfer.push(arg);\r\n }\r\n \r\n if(arg.buffer && arg.buffer instanceof ArrayBuffer) {\r\n transfer.push(arg.buffer);\r\n }\r\n });\r\n \r\n //console.log('transfer', transfer);\r\n this.worker.postMessage({\r\n 'queryMethod': queryMethod,\r\n 'queryMethodArguments': args\r\n }, transfer as PostMessageOptions);\r\n }\r\n }\r\n}\r\n\r\ntype LottieShape = {\r\n c: {\r\n k: number[]\r\n },\r\n ty: 'st' | 'fl',\r\n it?: LottieShape[]\r\n};\r\nclass LottieLoader {\r\n public isWebAssemblySupported = typeof(WebAssembly) !== 'undefined';\r\n public loadPromise: Promise<void> = !this.isWebAssemblySupported ? Promise.reject() : undefined;\r\n public loaded = false;\r\n\r\n // https://github.com/telegramdesktop/tdesktop/blob/97d8ee75d51874fcb74a9bfadc79f835c82be54a/Telegram/SourceFiles/chat_helpers/stickers_emoji_pack.cpp#L46\r\n private static COLORREPLACEMENTS = [\r\n [\r\n [0xf77e41, 0xcb7b55],\r\n\t\t\t[0xffb139, 0xf6b689],\r\n\t\t\t[0xffd140, 0xffcda7],\r\n\t\t\t[0xffdf79, 0xffdfc5],\r\n ],\r\n\r\n [\r\n [0xf77e41, 0xa45a38],\r\n\t\t\t[0xffb139, 0xdf986b],\r\n\t\t\t[0xffd140, 0xedb183],\r\n\t\t\t[0xffdf79, 0xf4c3a0],\r\n ],\r\n\r\n [\r\n [0xf77e41, 0x703a17],\r\n\t\t\t[0xffb139, 0xab673d],\r\n\t\t\t[0xffd140, 0xc37f4e],\r\n\t\t\t[0xffdf79, 0xd89667],\r\n ],\r\n\r\n [\r\n [0xf77e41, 0x4a2409],\r\n\t\t\t[0xffb139, 0x7d3e0e],\r\n\t\t\t[0xffd140, 0x965529],\r\n\t\t\t[0xffdf79, 0xa96337],\r\n ],\r\n\r\n [\r\n\t\t\t[0xf77e41, 0x200f0a],\r\n\t\t\t[0xffb139, 0x412924],\r\n\t\t\t[0xffd140, 0x593d37],\r\n\t\t\t[0xffdf79, 0x63453f],\r\n ]\r\n ];\r\n\r\n private workersLimit = 4;\r\n private players: {[reqId: number]: RLottiePlayer} = {};\r\n\r\n private workers: QueryableWorker[] = [];\r\n private curWorkerNum = 0;\r\n\r\n private log = logger('LOTTIE', LogTypes.Error);\r\n\r\n public getAnimation(element: HTMLElement) {\r\n for(const i in this.players) {\r\n if(this.players[i].el === element) {\r\n return this.players[i];\r\n }\r\n }\r\n\r\n return null;\r\n }\r\n\r\n public setLoop(loop: boolean) {\r\n for(const i in this.players) {\r\n const player = this.players[i];\r\n player.loop = loop;\r\n player.autoplay = player._autoplay;\r\n }\r\n }\r\n\r\n public loadLottieWorkers() {\r\n if(this.loadPromise) {\r\n return this.loadPromise;\r\n }\r\n\r\n return this.loadPromise = new Promise((resolve, reject) => {\r\n let remain = this.workersLimit;\r\n for(let i = 0; i < this.workersLimit; ++i) {\r\n const worker = this.workers[i] = new QueryableWorker(new RLottieWorker());\r\n\r\n worker.addEventListener('ready', () => {\r\n this.log('worker #' + i + ' ready');\r\n\r\n worker.addEventListener('frame', this.onFrame);\r\n worker.addEventListener('loaded', this.onPlayerLoaded);\r\n worker.addEventListener('error', this.onPlayerError);\r\n\r\n --remain;\r\n if(!remain) {\r\n this.log('workers ready');\r\n resolve();\r\n this.loaded = true;\r\n }\r\n });\r\n }\r\n });\r\n }\r\n\r\n private applyReplacements(object: {\r\n layers: Array<{shapes: LottieShape[]}>\r\n }, toneIndex: number) {\r\n const replacements = LottieLoader.COLORREPLACEMENTS[Math.max(toneIndex - 1, 0)];\r\n\r\n const applyTo = (smth: LottieShape) => {\r\n const k = smth.c.k;\r\n const color = convert(k[2]) | (convert(k[1]) << 8) | (convert(k[0]) << 16);\r\n\r\n const foundReplacement = replacements.find(p => p[0] === color);\r\n if(foundReplacement) {\r\n k[0] = ((foundReplacement[1] >> 16) & 255) / 255;\r\n k[1] = ((foundReplacement[1] >> 8) & 255) / 255;\r\n k[2] = (foundReplacement[1] & 255) / 255;\r\n }\r\n\r\n //console.log('foundReplacement!', foundReplacement, color.toString(16), k);\r\n };\r\n\r\n const checkSmth = (smth: LottieShape) => {\r\n switch(smth.ty) {\r\n case 'st':\r\n case 'fl':\r\n applyTo(smth);\r\n break;\r\n }\r\n\r\n if(smth.hasOwnProperty('it')) {\r\n iterateIt(smth.it);\r\n }\r\n };\r\n\r\n const iterateIt = (it: LottieShape['it']) => {\r\n for(const smth of it) {\r\n checkSmth(smth);\r\n }\r\n };\r\n\r\n try {\r\n for(const layer of object.layers) {\r\n if(!layer.shapes) continue;\r\n \r\n for(const shape of layer.shapes) {\r\n if(!shape.it) {\r\n checkSmth(shape);\r\n continue;\r\n }\r\n\r\n iterateIt(shape.it);\r\n }\r\n }\r\n } catch(err) {\r\n this.log.warn('cant apply replacements', err, object, toneIndex);\r\n }\r\n }\r\n\r\n public loadAnimationFromURL(params: Omit<RLottieOptions, 'animationData'>, url: string): Promise<RLottiePlayer> {\r\n if(!this.isWebAssemblySupported) {\r\n return this.loadPromise as any;\r\n }\r\n \r\n if(!this.loaded) {\r\n this.loadLottieWorkers();\r\n }\r\n \r\n return fetch(url)\r\n .then(res => res.arrayBuffer())\r\n .then(data => apiManager.gzipUncompress<string>(data, true))\r\n /* .then(str => {\r\n return new Promise<string>((resolve) => setTimeout(() => resolve(str), 2e3));\r\n }) */\r\n .then(str => {\r\n return this.loadAnimationWorker(Object.assign(params, {animationData: str/* JSON.parse(str) */, needUpscale: true}));\r\n });\r\n }\r\n\r\n public waitForFirstFrame(player: RLottiePlayer): Promise<void> {\r\n return Promise.race([\r\n /* new Promise<void>((resolve) => {\r\n player.addEventListener('firstFrame', () => {\r\n setTimeout(() => resolve(), 1500);\r\n }, true);\r\n }) */\r\n new Promise<void>((resolve) => {\r\n player.addEventListener('firstFrame', resolve, true);\r\n }),\r\n pause(2500)\r\n ]);\r\n }\r\n\r\n public async loadAnimationWorker(params: RLottieOptions, group = '', toneIndex = -1): Promise<RLottiePlayer> {\r\n if(!this.isWebAssemblySupported) {\r\n return this.loadPromise as any;\r\n }\r\n //params.autoplay = true;\r\n\r\n if(toneIndex >= 1 && toneIndex <= 5) {\r\n /* params.animationData = copy(params.animationData);\r\n this.applyReplacements(params.animationData, toneIndex); */\r\n\r\n const newAnimationData = JSON.parse(params.animationData);\r\n this.applyReplacements(newAnimationData, toneIndex);\r\n params.animationData = JSON.stringify(newAnimationData);\r\n }\r\n\r\n if(!this.loaded) {\r\n await this.loadLottieWorkers();\r\n }\r\n\r\n if(!params.width || !params.height) {\r\n params.width = parseInt(params.container.style.width);\r\n params.height = parseInt(params.container.style.height);\r\n }\r\n\r\n if(!params.width || !params.height) {\r\n throw new Error('No size for sticker!');\r\n }\r\n\r\n params.group = group;\r\n\r\n const player = this.initPlayer(params.container, params);\r\n animationIntersector.addAnimation(player, group);\r\n\r\n return player;\r\n }\r\n\r\n private onPlayerLoaded = (reqId: number, frameCount: number, fps: number) => {\r\n const rlPlayer = this.players[reqId];\r\n if(!rlPlayer) {\r\n this.log.warn('onPlayerLoaded on destroyed player:', reqId, frameCount);\r\n return;\r\n }\r\n\r\n this.log.debug('onPlayerLoaded');\r\n rlPlayer.onLoad(frameCount, fps);\r\n //rlPlayer.addListener('firstFrame', () => {\r\n //animationIntersector.addAnimation(player, group);\r\n //}, true);\r\n };\r\n\r\n private onFrame = (reqId: number, frameNo: number, frame: Uint8ClampedArray) => {\r\n const rlPlayer = this.players[reqId];\r\n if(!rlPlayer) {\r\n this.log.warn('onFrame on destroyed player:', reqId, frameNo);\r\n return;\r\n }\r\n\r\n rlPlayer.clamped = frame;\r\n rlPlayer.renderFrame(frame, frameNo);\r\n };\r\n\r\n private onPlayerError = (reqId: number, error: Error) => {\r\n const rlPlayer = this.players[reqId];\r\n if(rlPlayer) {\r\n // ! will need refactoring later, this is not the best way to remove the animation\r\n const animations = animationIntersector.getAnimations(rlPlayer.el);\r\n animations.forEach(animation => {\r\n animationIntersector.checkAnimation(animation, true, true);\r\n });\r\n }\r\n };\r\n\r\n public onDestroy(reqId: number) {\r\n delete this.players[reqId];\r\n }\r\n\r\n public destroyWorkers() {\r\n this.workers.forEach((worker, idx) => {\r\n worker.terminate();\r\n this.log('worker #' + idx + ' terminated');\r\n });\r\n\r\n this.log('workers destroyed');\r\n this.workers.length = 0;\r\n }\r\n\r\n private initPlayer(el: HTMLElement, options: RLottieOptions) {\r\n const rlPlayer = new RLottiePlayer({\r\n el, \r\n worker: this.workers[this.curWorkerNum++],\r\n options\r\n });\r\n\r\n this.players[rlPlayer.reqId] = rlPlayer;\r\n if(this.curWorkerNum >= this.workers.length) {\r\n this.curWorkerNum = 0;\r\n }\r\n\r\n rlPlayer.loadFromData(options.animationData);\r\n\r\n return rlPlayer;\r\n }\r\n}\r\n\r\nconst lottieLoader = new LottieLoader();\r\nMOUNT_CLASS_TO.lottieLoader = lottieLoader;\r\nexport default lottieLoader;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport I18n from \"../lib/langPack\";\r\n\r\nexport const months = ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'];\r\nexport const days = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'];\r\n\r\nexport const ONE_DAY = 86400;\r\n\r\n// https://stackoverflow.com/a/6117889\r\nexport const getWeekNumber = (date: Date) => {\r\n const d = new Date(Date.UTC(date.getFullYear(), date.getMonth(), date.getDate()));\r\n const dayNum = d.getUTCDay() || 7;\r\n d.setUTCDate(d.getUTCDate() + 4 - dayNum);\r\n const yearStart = new Date(Date.UTC(d.getUTCFullYear(), 0, 1));\r\n return Math.ceil((((d.getTime() - yearStart.getTime()) / ONE_DAY) + 1) / 7);\r\n};\r\n\r\nexport const formatDateAccordingToToday = (time: Date) => {\r\n const date = new Date();\r\n const now = date.getTime() / 1000 | 0;\r\n const timestamp = time.getTime() / 1000 | 0;\r\n\r\n let timeStr: string;\r\n if((now - timestamp) < ONE_DAY && date.getDate() === time.getDate()) { // if the same day\r\n timeStr = ('0' + time.getHours()).slice(-2) + ':' + ('0' + time.getMinutes()).slice(-2);\r\n } else if(date.getFullYear() !== time.getFullYear()) { // different year\r\n timeStr = time.getDate() + '.' + ('0' + (time.getMonth() + 1)).slice(-2) + '.' + ('' + time.getFullYear()).slice(-2);\r\n } else if((now - timestamp) < (ONE_DAY * 7) && getWeekNumber(date) === getWeekNumber(time)) { // current week\r\n timeStr = days[time.getDay()].slice(0, 3);\r\n } else { // same year\r\n timeStr = months[time.getMonth()].slice(0, 3) + ' ' + ('0' + time.getDate()).slice(-2);\r\n }\r\n\r\n return timeStr;\r\n};\r\n\r\nexport function formatDateAccordingToTodayNew(time: Date) {\r\n const today = new Date();\r\n const now = today.getTime() / 1000 | 0;\r\n const timestamp = time.getTime() / 1000 | 0;\r\n\r\n const options: Intl.DateTimeFormatOptions = {};\r\n if((now - timestamp) < ONE_DAY && today.getDate() === time.getDate()) { // if the same day\r\n options.hour = options.minute = '2-digit';\r\n } else if(today.getFullYear() !== time.getFullYear()) { // different year\r\n options.year = options.day = 'numeric';\r\n options.month = '2-digit';\r\n } else if((now - timestamp) < (ONE_DAY * 7) && getWeekNumber(today) === getWeekNumber(time)) { // current week\r\n options.weekday = 'short';\r\n } else { // same year\r\n options.month = 'short';\r\n options.day = 'numeric';\r\n }\r\n\r\n return new I18n.IntlDateElement({\r\n date: time,\r\n options\r\n }).element;\r\n}\r\n\r\nexport function formatTime(date: Date) {\r\n return new I18n.IntlDateElement({\r\n date,\r\n options: {\r\n hour: '2-digit',\r\n minute: '2-digit'\r\n }\r\n }).element;\r\n}\r\n\r\nMOUNT_CLASS_TO && (MOUNT_CLASS_TO.formatDateAccordingToTodayNew = formatDateAccordingToTodayNew);\r\n\r\nexport const getFullDate = (date: Date, options: Partial<{\r\n noTime: true, \r\n noSeconds: true,\r\n monthAsNumber: true,\r\n leadingZero: true\r\n}> = {}) => {\r\n const joiner = options.monthAsNumber ? '.' : ' ';\r\n const time = ('0' + date.getHours()).slice(-2) + ':' + ('0' + date.getMinutes()).slice(-2) + (options.noSeconds ? '' : ':' + ('0' + date.getSeconds()).slice(-2));\r\n\r\n return (options.leadingZero ? ('0' + date.getDate()).slice(-2) : date.getDate()) + \r\n joiner + (options.monthAsNumber ? ('0' + (date.getMonth() + 1)).slice(-2) : months[date.getMonth()]) + \r\n joiner + date.getFullYear() + \r\n (options.noTime ? '' : ', ' + time);\r\n};\r\n\r\nexport function tsNow(seconds?: true) {\r\n const t = Date.now();\r\n return seconds ? Math.floor(t / 1000) : t;\r\n}\r\n\r\n// https://github.com/DrKLO/Telegram/blob/d52b2c921abd3c1e8d6368858313ad0cb0468c07/TMessagesProj/src/main/java/org/telegram/ui/Adapters/FiltersView.java\r\nconst minYear = 2013;\r\nconst yearPattern = new RegExp(\"20[0-9]{1,2}\");\r\nconst monthYearOrDayPattern = new RegExp(\"(\\\\w{3,}) ([0-9]{0,4})\", 'i');\r\nconst yearOrDayAndMonthPattern = new RegExp(\"([0-9]{0,4}) (\\\\w{2,})\", 'i');\r\nconst shortDate = new RegExp(\"^([0-9]{1,4})(\\\\.| |/|\\\\-)([0-9]{1,4})$\", 'i');\r\nconst longDate = new RegExp(\"^([0-9]{1,2})(\\\\.| |/|\\\\-)([0-9]{1,2})(\\\\.| |/|\\\\-)([0-9]{1,4})$\", 'i');\r\nconst numberOfDaysEachMonth = [31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];\r\nexport type DateData = {\r\n title: string,\r\n minDate: number,\r\n maxDate: number,\r\n};\r\nexport function fillTipDates(query: string, dates: DateData[]) {\r\n const q = query.trim().toLowerCase();\r\n\r\n if(q.length < 3) {\r\n return;\r\n }\r\n\r\n if(\"today\".indexOf(q) === 0) {\r\n const date = new Date();\r\n const year = date.getFullYear();\r\n const month = date.getMonth();\r\n const day = date.getDate();\r\n date.setFullYear(year, month, day);\r\n date.setHours(0, 0, 0);\r\n\r\n const minDate = date.getTime();\r\n date.setFullYear(year, month, day + 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const maxDate = date.getTime() - 1;\r\n dates.push({\r\n title: 'Today',\r\n minDate,\r\n maxDate\r\n });\r\n return;\r\n }\r\n\r\n if(\"yesterday\".indexOf(q) === 0) {\r\n const date = new Date();\r\n const year = date.getFullYear();\r\n const month = date.getMonth();\r\n const day = date.getDate();\r\n date.setFullYear(year, month, day);\r\n date.setHours(0, 0, 0);\r\n\r\n const minDate = date.getTime() - 86400000;\r\n date.setFullYear(year, month, day + 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const maxDate = date.getTime() - 86400001;\r\n dates.push({\r\n title: 'Yesterday',\r\n minDate,\r\n maxDate\r\n });\r\n return;\r\n }\r\n\r\n const dayOfWeek = getDayOfWeek(q);\r\n if(dayOfWeek >= 0) {\r\n const date = new Date();\r\n const now = date.getTime();\r\n const currentDay = date.getDay();\r\n const distance = dayOfWeek - currentDay;\r\n date.setDate(date.getDate() + distance);\r\n if(date.getTime() > now) {\r\n date.setTime(date.getTime() - 604800000);\r\n }\r\n const year = date.getFullYear()\r\n const month = date.getMonth();\r\n const day = date.getDate();\r\n date.setFullYear(year, month, day);\r\n date.setHours(0, 0, 0);\r\n\r\n const minDate = date.getTime();\r\n date.setFullYear(year, month, day + 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const maxDate = date.getTime() - 1;\r\n dates.push({\r\n title: formatWeekLong(minDate),\r\n minDate,\r\n maxDate\r\n });\r\n return;\r\n }\r\n\r\n let matches: any[];\r\n if((matches = shortDate.exec(q)) !== null) {\r\n const g1 = matches[1];\r\n const g2 = matches[3];\r\n const k = parseInt(g1);\r\n const k1 = parseInt(g2);\r\n if(k > 0 && k <= 31) {\r\n if(k1 >= minYear && k <= 12) {\r\n const selectedYear = k1;\r\n const month = k - 1;\r\n createForMonthYear(dates, month, selectedYear);\r\n return;\r\n } else if (k1 <= 12) {\r\n const day = k - 1;\r\n const month = k1 - 1;\r\n createForDayMonth(dates, day, month);\r\n }\r\n } else if (k >= minYear && k1 <= 12) {\r\n const selectedYear = k;\r\n const month = k1 - 1;\r\n createForMonthYear(dates, month, selectedYear);\r\n }\r\n\r\n return;\r\n }\r\n\r\n if((matches = longDate.exec(q)) !== null) {\r\n const g1 = matches[1];\r\n const g2 = matches[3];\r\n const g3 = matches[5];\r\n if(!matches[2] === matches[4]) {\r\n return;\r\n }\r\n\r\n const day = parseInt(g1);\r\n const month = parseInt(g2) - 1;\r\n let year = parseInt(g3);\r\n if(year >= 10 && year <= 99) {\r\n year += 2000;\r\n }\r\n\r\n const currentYear = new Date().getFullYear();\r\n if(validDateForMonth(day - 1, month) && year >= minYear && year <= currentYear) {\r\n const date = new Date();\r\n date.setFullYear(year, month, day);\r\n date.setHours(0, 0, 0);\r\n \r\n const minDate = date.getTime();\r\n date.setFullYear(year, month, day + 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const maxDate = date.getTime() - 1;\r\n dates.push({\r\n title: formatterYearMax(minDate),\r\n minDate,\r\n maxDate\r\n });\r\n return;\r\n }\r\n\r\n return;\r\n }\r\n\r\n if((matches = yearPattern.exec(q)) !== null) {\r\n let selectedYear = +q;\r\n const currentYear = new Date().getFullYear();\r\n if(selectedYear < minYear) {\r\n selectedYear = minYear;\r\n for(let i = currentYear; i >= selectedYear; i--) {\r\n const date = new Date();\r\n date.setFullYear(i, 0, 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const minDate = date.getTime();\r\n date.setFullYear(i + 1, 0, 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const maxDate = date.getTime() - 1;\r\n dates.push({\r\n title: '' + i,\r\n minDate,\r\n maxDate\r\n });\r\n }\r\n } else if(selectedYear <= currentYear) {\r\n const date = new Date();\r\n date.setFullYear(selectedYear, 0, 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const minDate = date.getTime();\r\n date.setFullYear(selectedYear + 1, 0, 1);\r\n date.setHours(0, 0, 0);\r\n\r\n const maxDate = date.getTime() - 1;\r\n dates.push({\r\n title: '' + selectedYear,\r\n minDate,\r\n maxDate\r\n });\r\n }\r\n\r\n return;\r\n }\r\n\r\n if((matches = monthYearOrDayPattern.exec(q)) !== null) {\r\n const g1 = matches[1];\r\n const g2 = matches[2];\r\n const month = getMonth(g1);\r\n if(month >= 0) {\r\n const k = +g2;\r\n if(k > 0 && k <= 31) {\r\n const day = k - 1;\r\n createForDayMonth(dates, day, month);\r\n return;\r\n } else if(k >= minYear) {\r\n const selectedYear = k;\r\n createForMonthYear(dates, month, selectedYear);\r\n return;\r\n }\r\n }\r\n }\r\n\r\n if((matches = yearOrDayAndMonthPattern.exec(q)) !== null) {\r\n const g1 = matches[1];\r\n const g2 = matches[2];\r\n const month = getMonth(g2);\r\n if(month >= 0) {\r\n const k = +g1;\r\n if(k > 0 && k <= 31) {\r\n const day = k - 1;\r\n createForDayMonth(dates, day, month);\r\n return;\r\n } else if (k >= minYear) {\r\n const selectedYear = k;\r\n createForMonthYear(dates, month, selectedYear);\r\n }\r\n }\r\n }\r\n}\r\n\r\nfunction createForMonthYear(dates: DateData[], month: number, selectedYear: number) {\r\n const currentYear = new Date().getFullYear();\r\n const today = Date.now();\r\n if(selectedYear >= minYear && selectedYear <= currentYear) {\r\n const date = new Date();\r\n date.setFullYear(selectedYear, month, 1);\r\n date.setHours(0, 0, 0);\r\n const minDate = date.getTime();\r\n if(minDate > today) {\r\n return;\r\n }\r\n date.setMonth(date.getMonth() + 1);\r\n const maxDate = date.getTime() - 1;\r\n\r\n dates.push({\r\n title: formatterMonthYear(minDate),\r\n minDate,\r\n maxDate\r\n });\r\n }\r\n}\r\n\r\nfunction createForDayMonth(dates: DateData[], day: number, month: number) {\r\n if(validDateForMonth(day, month)) {\r\n const currentYear = new Date().getFullYear();\r\n const today = Date.now();\r\n \r\n for(let i = currentYear; i >= minYear; i--) {\r\n if(month === 1 && day === 28 && !isLeapYear(i)) {\r\n continue;\r\n }\r\n\r\n const date = new Date();\r\n date.setFullYear(i, month, day + 1);\r\n date.setHours(0, 0, 0);\r\n \r\n const minDate = date.getTime();\r\n if(minDate > today) {\r\n continue;\r\n }\r\n\r\n date.setFullYear(i, month, day + 2);\r\n date.setHours(0, 0, 0);\r\n const maxDate = date.getTime() - 1;\r\n if(i === currentYear) {\r\n dates.push({\r\n title: formatterDayMonth(minDate),\r\n minDate,\r\n maxDate\r\n });\r\n } else {\r\n dates.push({\r\n title: formatterYearMax(minDate),\r\n minDate,\r\n maxDate\r\n });\r\n }\r\n }\r\n }\r\n}\r\n\r\nfunction formatterMonthYear(timestamp: number) {\r\n const date = new Date(timestamp);\r\n return months[date.getMonth()].slice(0, 3) + ' ' + date.getFullYear();\r\n}\r\n\r\nfunction formatterDayMonth(timestamp: number) {\r\n const date = new Date(timestamp);\r\n return months[date.getMonth()].slice(0, 3) + ' ' + date.getDate();\r\n}\r\n\r\nfunction formatterYearMax(timestamp: number) {\r\n const date = new Date(timestamp);\r\n return ('0' + date.getDate()).slice(-2) + '.' + ('0' + (date.getMonth() + 1)).slice(-2) + '.' + date.getFullYear();\r\n}\r\n\r\nfunction formatWeekLong(timestamp: number) {\r\n const date = new Date(timestamp);\r\n return days[date.getDay()];\r\n}\r\n\r\nfunction validDateForMonth(day: number, month: number) {\r\n if(month >= 0 && month < 12) {\r\n if(day >= 0 && day < numberOfDaysEachMonth[month]) {\r\n return true;\r\n }\r\n }\r\n return false;\r\n}\r\n\r\nfunction isLeapYear(year: number) {\r\n return ((year % 4 === 0) && (year % 100 !== 0)) || (year % 400 === 0);\r\n}\r\n\r\nfunction getMonth(q: string) {\r\n /* String[] months = new String[]{\r\n LocaleController.getString(\"January\", R.string.January).toLowerCase(),\r\n LocaleController.getString(\"February\", R.string.February).toLowerCase(),\r\n LocaleController.getString(\"March\", R.string.March).toLowerCase(),\r\n LocaleController.getString(\"April\", R.string.April).toLowerCase(),\r\n LocaleController.getString(\"May\", R.string.May).toLowerCase(),\r\n LocaleController.getString(\"June\", R.string.June).toLowerCase(),\r\n LocaleController.getString(\"July\", R.string.July).toLowerCase(),\r\n LocaleController.getString(\"August\", R.string.August).toLowerCase(),\r\n LocaleController.getString(\"September\", R.string.September).toLowerCase(),\r\n LocaleController.getString(\"October\", R.string.October).toLowerCase(),\r\n LocaleController.getString(\"November\", R.string.November).toLowerCase(),\r\n LocaleController.getString(\"December\", R.string.December).toLowerCase()\r\n }; */\r\n\r\n /* String[] monthsEng = new String[12];\r\n Calendar c = Calendar.getInstance();\r\n for (int i = 1; i <= 12; i++) {\r\n c.set(0, 0, 0, 0, 0, 0);\r\n c.set(Calendar.MONTH, i);\r\n monthsEng[i - 1] = c.getDisplayName(Calendar.MONTH, Calendar.LONG, Locale.ENGLISH).toLowerCase();\r\n } */\r\n\r\n q = q.toLowerCase();\r\n for(let i = 0; i < 12; i++) {\r\n const month = months[i].toLowerCase();\r\n if(month.indexOf(q) === 0) {\r\n return i;\r\n }\r\n }\r\n return -1;\r\n}\r\n\r\nfunction getDayOfWeek(q: string) {\r\n const c = new Date();\r\n if(q.length <= 3) {\r\n return -1;\r\n }\r\n \r\n for(let i = 0; i < 7; i++) {\r\n c.setDate(c.getDate() + 1);\r\n \r\n if(formatWeekLong(c.getTime()).toLowerCase().indexOf(q) === 0) {\r\n return c.getDay();\r\n }\r\n }\r\n return -1;\r\n}\r\n\r\nMOUNT_CLASS_TO.fillTipDates = fillTipDates;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport Page from \"./page\";\r\nimport lottieLoader from \"../lib/lottieLoader\";\r\nimport { horizontalMenu } from \"../components/horizontalMenu\";\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport fastSmoothScroll from \"../helpers/fastSmoothScroll\";\r\nimport whichChild from \"../helpers/dom/whichChild\";\r\n\r\nclass PagesManager {\r\n private pageId = -1;\r\n private page: Page;\r\n\r\n private selectTab: ReturnType<typeof horizontalMenu>;\r\n public pagesDiv: HTMLDivElement;\r\n public scrollableDiv: HTMLElement;\r\n\r\n constructor() {\r\n this.pagesDiv = document.getElementById('auth-pages') as HTMLDivElement;\r\n this.scrollableDiv = this.pagesDiv.querySelector('.scrollable') as HTMLElement;\r\n this.selectTab = horizontalMenu(null, this.scrollableDiv.querySelector('.tabs-container') as HTMLDivElement, null, () => {\r\n if(this.page?.onShown) {\r\n this.page.onShown();\r\n }\r\n });\r\n }\r\n\r\n public setPage(page: Page) {\r\n if(page.isAuthPage) {\r\n this.pagesDiv.style.display = '';\r\n\r\n let id = whichChild(page.pageEl);\r\n if(this.pageId === id) return;\r\n\r\n this.selectTab(id);\r\n\r\n if(this.pageId !== -1 && id > 1) {\r\n lottieLoader.loadLottieWorkers();\r\n }\r\n\r\n\r\n\r\n this.pageId = id;\r\n\r\n if(this.scrollableDiv) {\r\n fastSmoothScroll(this.scrollableDiv, this.scrollableDiv.firstElementChild as HTMLElement, 'start');\r\n }\r\n } else {\r\n this.pagesDiv.style.display = 'none';\r\n page.pageEl.style.display = '';\r\n\r\n this.pageId = -1;\r\n }\r\n\r\n this.page = page;\r\n }\r\n}\r\n\r\nconst pagesManager = new PagesManager();\r\nMOUNT_CLASS_TO.pagesManager = pagesManager;\r\nexport default pagesManager;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport pagesManager from \"./pagesManager\";\r\n\r\nexport default class Page {\r\n public pageEl: HTMLDivElement;\r\n private installed = false;\r\n\r\n constructor(className: string, public isAuthPage: boolean, private onFirstMount?: (...args: any[]) => Promise<any> | void, private onMount?: (...args: any[]) => void, public onShown?: () => void) {\r\n this.pageEl = document.body.querySelector('.' + className) as HTMLDivElement;\r\n }\r\n\r\n public async mount(...args: any[]) {\r\n //this.pageEl.style.display = '';\r\n\r\n if(this.onMount) {\r\n this.onMount(...args);\r\n }\r\n\r\n if(!this.installed) {\r\n if(this.onFirstMount) {\r\n try {\r\n const res = this.onFirstMount(...args);\r\n if(res instanceof Promise) {\r\n await res;\r\n }\r\n } catch(err) {\r\n console.error('PAGE MOUNT ERROR:', err);\r\n }\r\n }\r\n \r\n this.installed = true;\r\n }\r\n\r\n pagesManager.setPage(this);\r\n }\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport { isMobileSafari } from \"../helpers/userAgent\";\r\nimport { logger } from \"../lib/logger\";\r\nimport { doubleRaf } from \"../helpers/schedulers\";\r\nimport blurActiveElement from \"../helpers/dom/blurActiveElement\";\r\nimport { cancelEvent } from \"../helpers/dom/cancelEvent\";\r\n\r\nexport type NavigationItem = {\r\n type: 'left' | 'right' | 'im' | 'chat' | 'popup' | 'media' | 'menu' | \r\n 'esg' | 'multiselect' | 'input-helper' | 'autocomplete-helper' | 'markup' | 'global-search',\r\n onPop: (canAnimate: boolean) => boolean | void,\r\n onEscape?: () => boolean,\r\n noHistory?: boolean,\r\n noBlurOnPop?: boolean,\r\n};\r\n\r\nexport class AppNavigationController {\r\n private navigations: Array<NavigationItem> = [];\r\n private id = Date.now();\r\n private manual = false;\r\n private log = logger('NC');\r\n private debug = true;\r\n private currentHash = window.location.hash;\r\n public onHashChange: () => void;\r\n\r\n constructor() {\r\n let isPossibleSwipe = false;\r\n window.addEventListener('popstate', (e) => {\r\n this.debug && this.log('popstate', e, isPossibleSwipe);\r\n\r\n if(window.location.hash !== this.currentHash) {\r\n this.onHashChange && this.onHashChange();\r\n this.replaceState();\r\n return;\r\n }\r\n this.currentHash = window.location.hash;\r\n\r\n const id: number = e.state;\r\n if(id !== this.id/* && !this.navigations.length */) {\r\n this.pushState();\r\n return;\r\n }\r\n\r\n const item = this.navigations.pop();\r\n if(!item) {\r\n this.pushState();\r\n return;\r\n }\r\n\r\n this.manual = !isPossibleSwipe;\r\n this.handleItem(item);\r\n //this.pushState(); // * prevent adding forward arrow\r\n });\r\n\r\n window.addEventListener('keydown', (e) => {\r\n const item = this.navigations[this.navigations.length - 1];\r\n if(!item) return;\r\n if(e.key === 'Escape' && (item.onEscape ? item.onEscape() : true)) {\r\n cancelEvent(e);\r\n this.back(item.type);\r\n }\r\n }, {capture: true, passive: false});\r\n\r\n if(isMobileSafari) {\r\n const options = {passive: true};\r\n window.addEventListener('touchstart', (e) => {\r\n if(e.touches.length > 1) return;\r\n this.debug && this.log('touchstart');\r\n\r\n const detach = () => {\r\n window.removeEventListener('touchend', onTouchEnd);\r\n window.removeEventListener('touchmove', onTouchMove);\r\n };\r\n\r\n let moved = false;\r\n const onTouchMove = (e: TouchEvent) => {\r\n this.debug && this.log('touchmove');\r\n if(e.touches.length > 1) {\r\n detach();\r\n return;\r\n }\r\n\r\n moved = true;\r\n };\r\n\r\n const onTouchEnd = (e: TouchEvent) => {\r\n this.debug && this.log('touchend');\r\n if(e.touches.length > 1 || !moved) {\r\n detach();\r\n return;\r\n }\r\n\r\n isPossibleSwipe = true;\r\n doubleRaf().then(() => {\r\n isPossibleSwipe = false;\r\n });\r\n\r\n detach();\r\n };\r\n\r\n window.addEventListener('touchend', onTouchEnd, options);\r\n window.addEventListener('touchmove', onTouchMove, options);\r\n }, options);\r\n }\r\n\r\n history.scrollRestoration = 'manual';\r\n\r\n this.pushState(); // * push init state\r\n }\r\n\r\n private handleItem(item: NavigationItem) {\r\n const good = item.onPop(!this.manual ? false : undefined);\r\n this.debug && this.log('popstate, navigation:', item, this.navigations);\r\n if(good === false) {\r\n this.pushItem(item);\r\n } else if(!item.noBlurOnPop) {\r\n blurActiveElement(); // no better place for it\r\n }\r\n\r\n this.manual = false;\r\n }\r\n\r\n public findItemByType(type: NavigationItem['type']) {\r\n for(let i = this.navigations.length - 1; i >= 0; --i) {\r\n const item = this.navigations[i];\r\n if(item.type === type) {\r\n return {item, index: i};\r\n }\r\n }\r\n }\r\n\r\n public back(type?: NavigationItem['type']) {\r\n if(type) {\r\n const ret = this.findItemByType(type);\r\n if(ret) {\r\n this.manual = true;\r\n // ! commented because 'popstate' event will be fired with delay\r\n //if(ret.index !== (this.navigations.length - 1)) {\r\n this.navigations.splice(ret.index, 1);\r\n this.handleItem(ret.item);\r\n return;\r\n //}\r\n }\r\n }\r\n\r\n history.back();\r\n }\r\n\r\n public pushItem(item: NavigationItem) {\r\n this.navigations.push(item);\r\n this.debug && this.log('pushstate', item, this.navigations);\r\n\r\n if(!item.noHistory) {\r\n this.pushState();\r\n }\r\n }\r\n\r\n private pushState() {\r\n this.manual = false;\r\n history.pushState(this.id, '');\r\n }\r\n\r\n public replaceState() {\r\n history.replaceState(this.id, '', location.origin + location.pathname);\r\n }\r\n\r\n public removeItem(item: NavigationItem) {\r\n this.navigations.findAndSplice(i => i === item);\r\n }\r\n\r\n public removeByType(type: NavigationItem['type'], single = false) {\r\n for(let i = this.navigations.length - 1; i >= 0; --i) {\r\n const item = this.navigations[i];\r\n if(item.type === type) {\r\n this.navigations.splice(i, 1);\r\n\r\n if(single) {\r\n break;\r\n }\r\n }\r\n }\r\n }\r\n}\r\n\r\nconst appNavigationController = new AppNavigationController();\r\nMOUNT_CLASS_TO.appNavigationController = appNavigationController;\r\nexport default appNavigationController;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\n// * Jolly Cobra's fastSmoothScroll slightly patched\r\n\r\nimport { dispatchHeavyAnimationEvent } from '../hooks/useHeavyAnimationCheck';\r\nimport { fastRaf } from './schedulers';\r\nimport { animateSingle, cancelAnimationByKey } from './animation';\r\nimport rootScope from '../lib/rootScope';\r\nimport isInDOM from './dom/isInDOM';\r\n\r\nconst MAX_DISTANCE = 1500;\r\nconst MIN_JS_DURATION = 250;\r\nconst MAX_JS_DURATION = 600;\r\n\r\nexport enum FocusDirection {\r\n Up,\r\n Down,\r\n Static,\r\n};\r\n\r\nexport default function fastSmoothScroll(\r\n container: HTMLElement,\r\n element: HTMLElement,\r\n position: ScrollLogicalPosition,\r\n margin = 0,\r\n maxDistance = MAX_DISTANCE,\r\n forceDirection?: FocusDirection,\r\n forceDuration?: number,\r\n axis: 'x' | 'y' = 'y'\r\n) {\r\n //return;\r\n\r\n if(!rootScope.settings.animationsEnabled) {\r\n forceDirection = FocusDirection.Static;\r\n }\r\n\r\n if(forceDirection === FocusDirection.Static) {\r\n forceDuration = 0;\r\n return scrollWithJs(container, element, position, margin, forceDuration, axis);\r\n /* return Promise.resolve();\r\n\r\n element.scrollIntoView({ block: position });\r\n\r\n cancelAnimationByKey(container);\r\n return Promise.resolve(); */\r\n }\r\n\r\n if(axis === 'y' && element !== container && isInDOM(element) && container.getBoundingClientRect) {\r\n const elementRect = element.getBoundingClientRect();\r\n const containerRect = container.getBoundingClientRect();\r\n \r\n const offsetTop = elementRect.top - containerRect.top;\r\n if(forceDirection === undefined) {\r\n if(offsetTop < -maxDistance) {\r\n container.scrollTop += (offsetTop + maxDistance);\r\n } else if(offsetTop > maxDistance) {\r\n container.scrollTop += (offsetTop - maxDistance);\r\n }\r\n } else if(forceDirection === FocusDirection.Up) { // * not tested yet\r\n container.scrollTop = offsetTop + container.scrollTop + maxDistance;\r\n } else if(forceDirection === FocusDirection.Down) { // * not tested yet\r\n container.scrollTop = Math.max(0, offsetTop + container.scrollTop - maxDistance);\r\n }\r\n /* const { offsetTop } = element;\r\n\r\n if(forceDirection === undefined) {\r\n const offset = offsetTop - container.scrollTop;\r\n\r\n if(offset < -maxDistance) {\r\n container.scrollTop += (offset + maxDistance);\r\n } else if(offset > maxDistance) {\r\n container.scrollTop += (offset - maxDistance);\r\n }\r\n } else if(forceDirection === FocusDirection.Up) {\r\n container.scrollTop = offsetTop + maxDistance;\r\n } else if(forceDirection === FocusDirection.Down) {\r\n container.scrollTop = Math.max(0, offsetTop - maxDistance);\r\n } */\r\n }\r\n\r\n const promise = new Promise((resolve) => {\r\n fastRaf(() => {\r\n scrollWithJs(container, element, position, margin, forceDuration, axis)\r\n .then(resolve);\r\n });\r\n });\r\n\r\n return axis === 'y' ? dispatchHeavyAnimationEvent(promise) : promise;\r\n}\r\n\r\nfunction scrollWithJs(\r\n container: HTMLElement, element: HTMLElement, position: ScrollLogicalPosition, margin = 0, forceDuration?: number, axis: 'x' | 'y' = 'y'\r\n) {\r\n if(!isInDOM(element)) {\r\n cancelAnimationByKey(container);\r\n return Promise.resolve();\r\n }\r\n \r\n const rectStartKey = axis === 'y' ? 'top' : 'left';\r\n const rectEndKey = axis === 'y' ? 'bottom' : 'right';\r\n const sizeKey = axis === 'y' ? 'height' : 'width';\r\n const scrollSizeKey = axis === 'y' ? 'scrollHeight' : 'scrollWidth';\r\n const scrollPositionKey = axis === 'y' ? 'scrollTop' : 'scrollLeft';\r\n\r\n //const { offsetTop: elementTop, offsetHeight: elementHeight } = element;\r\n const elementRect = element.getBoundingClientRect();\r\n const containerRect = container.getBoundingClientRect ? container.getBoundingClientRect() : document.body.getBoundingClientRect();\r\n\r\n //const transformable = container.firstElementChild as HTMLElement;\r\n\r\n const elementPosition = elementRect[rectStartKey] - containerRect[rectStartKey];\r\n const elementSize = element[scrollSizeKey]; // margin is exclusive in DOMRect\r\n\r\n const containerSize = containerRect[sizeKey];\r\n\r\n const scrollPosition = container[scrollPositionKey];\r\n const scrollSize = container[scrollSizeKey];\r\n /* const elementPosition = element.offsetTop;\r\n const elementSize = element.offsetHeight;\r\n\r\n const scrollPosition = container[scrollPositionKey];\r\n const scrollSize = container[scrollSizeKey];\r\n const containerSize = container.offsetHeight; */\r\n\r\n let path!: number;\r\n\r\n switch(position) {\r\n case 'start':\r\n path = elementPosition - margin;\r\n break;\r\n case 'end':\r\n path = elementRect[rectEndKey] + (elementSize - elementRect[sizeKey]) - containerRect[rectEndKey];\r\n break;\r\n // 'nearest' is not supported yet\r\n case 'nearest':\r\n case 'center':\r\n path = elementSize < containerSize\r\n ? (elementPosition + elementSize / 2) - (containerSize / 2)\r\n : elementPosition - margin;\r\n break;\r\n }\r\n /* switch (position) {\r\n case 'start':\r\n path = (elementPosition - margin) - scrollPosition;\r\n break;\r\n case 'end':\r\n path = (elementPosition + elementSize + margin) - (scrollPosition + containerSize);\r\n break;\r\n // 'nearest' is not supported yet\r\n case 'nearest':\r\n case 'center':\r\n path = elementSize < containerSize\r\n ? (elementPosition + elementSize / 2) - (scrollPosition + containerSize / 2)\r\n : (elementPosition - margin) - scrollPosition;\r\n break;\r\n } */\r\n\r\n // console.log('scrollWithJs: will scroll path:', path, element);\r\n\r\n /* let existsTransform = 0;\r\n const currentTransform = transformable.style.transform;\r\n if(currentTransform) {\r\n existsTransform = parseInt(currentTransform.match(/\\((.+?), (.+?), .+\\)/)[2]);\r\n //path += existsTransform;\r\n } */\r\n\r\n if(path < 0) {\r\n const remainingPath = -scrollPosition;\r\n path = Math.max(path, remainingPath);\r\n } else if(path > 0) {\r\n const remainingPath = scrollSize - (scrollPosition + containerSize);\r\n path = Math.min(path, remainingPath);\r\n }\r\n\r\n const target = container[scrollPositionKey] + path;\r\n const duration = forceDuration ?? (\r\n MIN_JS_DURATION + (Math.abs(path) / MAX_DISTANCE) * (MAX_JS_DURATION - MIN_JS_DURATION)\r\n );\r\n const startAt = Date.now();\r\n\r\n /* transformable.classList.add('no-transition');\r\n\r\n const tickTransform = () => {\r\n const t = duration ? Math.min((Date.now() - startAt) / duration, 1) : 1;\r\n const currentPath = path * transition(t);\r\n\r\n transformable.style.transform = `translate3d(0, ${-currentPath}px, 0)`;\r\n container.dataset.translate = '' + -currentPath;\r\n\r\n const willContinue = t < 1;\r\n if(!willContinue) {\r\n fastRaf(() => {\r\n delete container.dataset.transform;\r\n container.dataset.transform = '';\r\n transformable.style.transform = '';\r\n void transformable.offsetLeft; // reflow\r\n transformable.classList.remove('no-transition');\r\n void transformable.offsetLeft; // reflow\r\n container[scrollPositionKey] = Math.round(target);\r\n });\r\n }\r\n\r\n return willContinue;\r\n };\r\n \r\n return animateSingle(tickTransform, container); */\r\n\r\n /* return new Promise((resolve) => {\r\n fastRaf(() => {\r\n transformable.style.transform = '';\r\n transformable.style.transition = '';\r\n\r\n setTimeout(resolve, duration);\r\n });\r\n });\r\n\r\n const transformableHeight = transformable.scrollHeight;\r\n //transformable.style.minHeight = `${transformableHeight}px`;\r\n */\r\n\r\n const tick = () => {\r\n const t = duration ? Math.min((Date.now() - startAt) / duration, 1) : 1;\r\n\r\n const currentPath = path * (1 - transition(t));\r\n container[scrollPositionKey] = Math.round(target - currentPath);\r\n \r\n return t < 1;\r\n };\r\n\r\n if(!duration || !path) {\r\n cancelAnimationByKey(container);\r\n tick();\r\n return Promise.resolve();\r\n }\r\n\r\n /* return new Promise((resolve) => {\r\n setTimeout(resolve, duration);\r\n }).then(() => {\r\n transformable.classList.add('no-transition');\r\n void transformable.offsetLeft; // reflow\r\n transformable.style.transform = '';\r\n transformable.style.transition = '';\r\n void transformable.offsetLeft; // reflow\r\n transformable.classList.remove('no-transition');\r\n void transformable.offsetLeft; // reflow\r\n fastRaf(() => {\r\n \r\n container[scrollPositionKey] = Math.round(target);\r\n //transformable.style.minHeight = ``;\r\n });\r\n \r\n }); */\r\n\r\n return animateSingle(tick, container);\r\n}\r\n\r\nfunction transition(t: number) {\r\n return 1 - ((1 - t) ** 3.5);\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\n// * Jolly Cobra's useHeavyAnimationCheck.ts, patched\r\n\r\nimport { AnyToVoidFunction } from '../types';\r\nimport ListenerSetter from '../helpers/listenerSetter';\r\nimport { CancellablePromise, deferredPromise } from '../helpers/cancellablePromise';\r\nimport { pause } from '../helpers/schedulers';\r\nimport rootScope from '../lib/rootScope';\r\nimport DEBUG from '../config/debug';\r\n\r\nconst ANIMATION_START_EVENT = 'event-heavy-animation-start';\r\nconst ANIMATION_END_EVENT = 'event-heavy-animation-end';\r\n\r\nlet isAnimating = false;\r\nlet heavyAnimationPromise: CancellablePromise<void> = deferredPromise<void>();\r\nlet promisesInQueue = 0;\r\n\r\nheavyAnimationPromise.resolve();\r\n\r\nconst log = console.log.bind(console.log, '[HEAVY-ANIMATION]:');\r\n\r\nexport function dispatchHeavyAnimationEvent(promise: Promise<any>, timeout?: number) {\r\n if(!isAnimating) {\r\n heavyAnimationPromise = deferredPromise<void>();\r\n rootScope.dispatchEvent(ANIMATION_START_EVENT);\r\n isAnimating = true;\r\n DEBUG && log('start');\r\n }\r\n \r\n ++promisesInQueue;\r\n DEBUG && log('attach promise, length:', promisesInQueue, timeout);\r\n\r\n const promises = [\r\n timeout !== undefined ? pause(timeout) : undefined,\r\n promise.finally(() => {})\r\n ].filter(Boolean);\r\n\r\n const perf = performance.now();\r\n const _heavyAnimationPromise = heavyAnimationPromise;\r\n Promise.race(promises).then(() => {\r\n if(heavyAnimationPromise !== _heavyAnimationPromise || heavyAnimationPromise.isFulfilled) { // interrupted\r\n return;\r\n }\r\n\r\n --promisesInQueue;\r\n DEBUG && log('promise end, length:', promisesInQueue, performance.now() - perf);\r\n if(promisesInQueue <= 0) {\r\n onHeavyAnimationEnd();\r\n }\r\n });\r\n\r\n return heavyAnimationPromise;\r\n}\r\n\r\nfunction onHeavyAnimationEnd() {\r\n if(heavyAnimationPromise.isFulfilled) {\r\n return;\r\n }\r\n\r\n isAnimating = false;\r\n promisesInQueue = 0;\r\n rootScope.dispatchEvent(ANIMATION_END_EVENT);\r\n heavyAnimationPromise.resolve();\r\n\r\n DEBUG && log('end');\r\n}\r\n\r\nexport function interruptHeavyAnimation() {\r\n onHeavyAnimationEnd();\r\n}\r\n\r\nexport function getHeavyAnimationPromise() {\r\n return heavyAnimationPromise;\r\n}\r\n\r\nexport default function(\r\n handleAnimationStart: AnyToVoidFunction,\r\n handleAnimationEnd: AnyToVoidFunction,\r\n listenerSetter?: ListenerSetter\r\n) {\r\n //useEffect(() => {\r\n if(isAnimating) {\r\n handleAnimationStart();\r\n }\r\n\r\n const add = listenerSetter ? listenerSetter.add.bind(listenerSetter, rootScope) : rootScope.addEventListener.bind(rootScope);\r\n const remove = listenerSetter ? listenerSetter.removeManual.bind(listenerSetter, rootScope) : rootScope.removeEventListener.bind(rootScope);\r\n add(ANIMATION_START_EVENT, handleAnimationStart);\r\n add(ANIMATION_END_EVENT, handleAnimationEnd);\r\n\r\n return () => {\r\n remove(ANIMATION_END_EVENT, handleAnimationEnd);\r\n remove(ANIMATION_START_EVENT, handleAnimationStart);\r\n };\r\n //}, [handleAnimationEnd, handleAnimationStart]);\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n * \r\n * Originally from:\r\n * https://github.com/zhukov/webogram\r\n * Copyright (C) 2014 Igor Zhukov <igor.beatle@gmail.com>\r\n * https://github.com/zhukov/webogram/blob/master/LICENSE\r\n */\r\n\r\n/* export function isInDOM(element: Element, parentNode?: HTMLElement): boolean {\r\n if(!element) {\r\n return false;\r\n }\r\n\r\n parentNode = parentNode || document.body;\r\n if(element === parentNode) {\r\n return true;\r\n }\r\n return isInDOM(element.parentNode as HTMLElement, parentNode);\r\n} */\r\nexport default function isInDOM(element: Element): boolean {\r\n return element?.isConnected;\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nexport default function whichChild(elem: Node) {\r\n if(!elem.parentNode) {\r\n return -1;\r\n }\r\n \r\n let i = 0;\r\n // @ts-ignore\r\n while((elem = elem.previousElementSibling) !== null) ++i;\r\n return i;\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { RLottiePlayer } from \"../lib/lottieLoader\";\r\nimport rootScope from \"../lib/rootScope\";\r\nimport { isSafari } from \"../helpers/userAgent\";\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport isInDOM from \"../helpers/dom/isInDOM\";\r\n\r\nexport interface AnimationItem {\r\n el: HTMLElement,\r\n group: string,\r\n animation: RLottiePlayer | HTMLVideoElement\r\n};\r\n\r\nexport class AnimationIntersector {\r\n public observer: IntersectionObserver;\r\n private visible: Set<AnimationItem> = new Set();\r\n\r\n private byGroups: {[group: string]: AnimationItem[]} = {};\r\n private lockedGroups: {[group: string]: true} = {};\r\n private onlyOnePlayableGroup: string = '';\r\n \r\n private intersectionLockedGroups: {[group: string]: true} = {};\r\n private videosLocked = false;\r\n\r\n constructor() {\r\n this.observer = new IntersectionObserver((entries) => {\r\n if(rootScope.idle.isIDLE) return;\r\n\r\n for(const entry of entries) {\r\n const target = entry.target;\r\n\r\n for(const group in this.byGroups) {\r\n if(this.intersectionLockedGroups[group]) {\r\n continue;\r\n }\r\n\r\n const player = this.byGroups[group].find(p => p.el === target);\r\n if(player) {\r\n if(entry.isIntersecting) {\r\n this.visible.add(player);\r\n this.checkAnimation(player, false);\r\n } else {\r\n this.visible.delete(player);\r\n this.checkAnimation(player, true);\r\n\r\n if(player.animation instanceof RLottiePlayer/* && player.animation.cachingDelta === 2 */) {\r\n //console.warn('will clear cache', player);\r\n player.animation.clearCache();\r\n }\r\n }\r\n\r\n break;\r\n }\r\n }\r\n }\r\n });\r\n\r\n rootScope.addEventListener('audio_play', ({doc}) => {\r\n if(doc.type === 'round') {\r\n this.videosLocked = true;\r\n this.checkAnimations();\r\n }\r\n });\r\n\r\n rootScope.addEventListener('audio_pause', () => {\r\n if(this.videosLocked) {\r\n this.videosLocked = false;\r\n this.checkAnimations();\r\n }\r\n });\r\n }\r\n\r\n public getAnimations(element: HTMLElement) {\r\n const found: AnimationItem[] = [];\r\n for(const group in this.byGroups) {\r\n for(const player of this.byGroups[group]) {\r\n if(player.el === element) {\r\n found.push(player);\r\n }\r\n }\r\n }\r\n\r\n return found;\r\n }\r\n\r\n public removeAnimation(player: AnimationItem) {\r\n //console.log('destroy animation');\r\n const {el, animation} = player;\r\n animation.remove();\r\n\r\n if(animation instanceof HTMLVideoElement && isSafari) {\r\n setTimeout(() => { // TODO: очистка по очереди, а не все вместе с этим таймаутом\r\n animation.src = '';\r\n animation.load();\r\n }, 1e3);\r\n }\r\n\r\n for(const group in this.byGroups) {\r\n this.byGroups[group].findAndSplice(p => p === player);\r\n }\r\n \r\n this.observer.unobserve(el);\r\n this.visible.delete(player);\r\n }\r\n\r\n public addAnimation(animation: RLottiePlayer | HTMLVideoElement, group = '') {\r\n const player = {\r\n el: animation instanceof RLottiePlayer ? animation.el : animation, \r\n animation: animation, \r\n group\r\n };\r\n\r\n if(animation instanceof RLottiePlayer) {\r\n if(!rootScope.settings.stickers.loop && animation.loop) {\r\n animation.loop = rootScope.settings.stickers.loop;\r\n }\r\n }\r\n\r\n (this.byGroups[group] ?? (this.byGroups[group] = [])).push(player);\r\n this.observer.observe(player.el);\r\n }\r\n\r\n public checkAnimations(blurred?: boolean, group?: string, destroy = false) {\r\n if(rootScope.idle.isIDLE) return;\r\n \r\n const groups = group /* && false */ ? [group] : Object.keys(this.byGroups);\r\n\r\n if(group && !this.byGroups[group]) {\r\n //console.warn('no animation group:', group);\r\n this.byGroups[group] = [];\r\n return;\r\n }\r\n\r\n for(const group of groups) {\r\n const animations = this.byGroups[group];\r\n\r\n animations.forEach(player => {\r\n this.checkAnimation(player, blurred, destroy);\r\n });\r\n }\r\n }\r\n\r\n public checkAnimation(player: AnimationItem, blurred = false, destroy = false) {\r\n const {el, animation, group} = player;\r\n //return;\r\n if((destroy || (!isInDOM(el) && !this.lockedGroups[group]))/* && false */) {\r\n this.removeAnimation(player);\r\n return;\r\n }\r\n\r\n if(blurred || (this.onlyOnePlayableGroup && this.onlyOnePlayableGroup !== group) || (animation instanceof HTMLVideoElement && this.videosLocked)) {\r\n if(!animation.paused) {\r\n //console.warn('pause animation:', animation);\r\n animation.pause();\r\n }\r\n } else if(animation.paused && \r\n this.visible.has(player) && \r\n animation.autoplay && \r\n (!this.onlyOnePlayableGroup || this.onlyOnePlayableGroup === group)\r\n ) {\r\n //console.warn('play animation:', animation);\r\n animation.play();\r\n }\r\n }\r\n\r\n public setOnlyOnePlayableGroup(group: string) {\r\n this.onlyOnePlayableGroup = group;\r\n }\r\n\r\n public lockGroup(group: string) {\r\n this.lockedGroups[group] = true;\r\n }\r\n\r\n public unlockGroup(group: string) {\r\n delete this.lockedGroups[group];\r\n this.checkAnimations(undefined, group);\r\n }\r\n\r\n public refreshGroup(group: string) {\r\n const animations = this.byGroups[group];\r\n if(animations && animations.length) {\r\n animations.forEach(animation => {\r\n this.observer.unobserve(animation.el);\r\n });\r\n\r\n window.requestAnimationFrame(() => {\r\n animations.forEach(animation => {\r\n this.observer.observe(animation.el);\r\n });\r\n });\r\n }\r\n }\r\n\r\n public lockIntersectionGroup(group: string) {\r\n this.intersectionLockedGroups[group] = true;\r\n }\r\n\r\n public unlockIntersectionGroup(group: string) {\r\n delete this.intersectionLockedGroups[group];\r\n this.refreshGroup(group);\r\n }\r\n}\r\n\r\nconst animationIntersector = new AnimationIntersector();\r\nif(MOUNT_CLASS_TO) {\r\n MOUNT_CLASS_TO.animationIntersector = animationIntersector;\r\n}\r\nexport default animationIntersector;","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nexport default function toggleDisability(elements: HTMLElement[], disable: boolean) {\r\n if(disable) {\r\n elements.forEach(el => el.setAttribute('disabled', 'true'));\r\n } else {\r\n elements.forEach(el => el.removeAttribute('disabled'));\r\n }\r\n\r\n return () => toggleDisability(elements, !disable);\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport blurActiveElement from \"../helpers/dom/blurActiveElement\";\r\nimport loadFonts from \"../helpers/dom/loadFonts\";\r\nimport appStateManager from \"../lib/appManagers/appStateManager\";\r\nimport I18n from \"../lib/langPack\";\r\nimport Page from \"./page\";\r\n\r\nlet onFirstMount = () => {\r\n //return;\r\n appStateManager.pushToState('authState', {_: 'authStateSignedIn'});\r\n // ! TOO SLOW\r\n /* appStateManager.saveState(); */\r\n\r\n import('../lib/rootScope').then(m => {\r\n m.default.dispatchEvent('im_mount');\r\n });\r\n\r\n if(!I18n.requestedServerLanguage) {\r\n I18n.getCacheLangPack().then(langPack => {\r\n if(langPack.local) {\r\n I18n.getLangPack(langPack.lang_code);\r\n }\r\n });\r\n }\r\n\r\n blurActiveElement();\r\n return loadFonts().then(() => {\r\n return new Promise<void>((resolve) => {\r\n window.requestAnimationFrame(() => {\r\n const promise = import('../lib/appManagers/appDialogsManager');\r\n promise.finally(async() => {\r\n //alert('pageIm!');\r\n resolve();\r\n \r\n //AudioContext && global.navigator && global.navigator.mediaDevices && global.navigator.mediaDevices.getUserMedia && global.WebAssembly;\r\n \r\n /* // @ts-ignore\r\n var AudioContext = globalThis.AudioContext || globalThis.webkitAudioContext;\r\n alert('AudioContext:' + typeof(AudioContext));\r\n // @ts-ignore\r\n alert('global.navigator:' + typeof(navigator));\r\n alert('navigator.mediaDevices:' + typeof(navigator.mediaDevices));\r\n alert('navigator.mediaDevices.getUserMedia:' + typeof(navigator.mediaDevices?.getUserMedia));\r\n alert('global.WebAssembly:' + typeof(WebAssembly)); */\r\n \r\n //(Array.from(document.getElementsByClassName('rp')) as HTMLElement[]).forEach(el => ripple(el));\r\n });\r\n });\r\n });\r\n });\r\n\r\n //let promise = /* Promise.resolve() */.then(() => {//import('../lib/services').then(services => {\r\n /* fetch('assets/img/camomile.jpg')\r\n .then(res => res.blob())\r\n .then(blob => {\r\n let img = new Image();\r\n let url = URL.createObjectURL(blob);\r\n img.src = url;\r\n img.onload = () => {\r\n let id = 'chat-background-canvas';\r\n var canvas = document.getElementById(id) as HTMLCanvasElement;\r\n //URL.revokeObjectURL(url);\r\n \r\n let elements = ['.chat-container'].map(selector => {\r\n return document.querySelector(selector) as HTMLDivElement;\r\n });\r\n \r\n stackBlurImage(img, id, 15, 0);\r\n \r\n canvas.toBlob(blob => {\r\n //let dataUrl = canvas.toDataURL('image/jpeg', 1);\r\n let dataUrl = URL.createObjectURL(blob);\r\n \r\n elements.forEach(el => {\r\n el.style.backgroundImage = 'url(' + dataUrl + ')';\r\n });\r\n }, 'image/jpeg', 1);\r\n };\r\n }); */\r\n //});\r\n};\r\n\r\nconst page = new Page('page-chats', false, onFirstMount);\r\nexport default page;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nexport function numberThousandSplitter(x: number, joiner = ' ') {\r\n const parts = x.toString().split(\".\");\r\n parts[0] = parts[0].replace(/\\B(?=(\\d{3})+(?!\\d))/g, joiner);\r\n return parts.join(\".\");\r\n}\r\n\r\nexport function formatBytes(bytes: number, decimals = 2) {\r\n if(bytes === 0) return '0 Bytes';\r\n\r\n const k = 1024;\r\n const dm = decimals < 0 ? 0 : decimals;\r\n const sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];\r\n\r\n const i = Math.floor(Math.log(bytes) / Math.log(k));\r\n\r\n return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + ' ' + sizes[i];\r\n}\r\n\r\nexport function formatNumber(bytes: number, decimals = 2) {\r\n if(bytes === 0) return '0';\r\n\r\n const k = 1000;\r\n const dm = decimals < 0 ? 0 : decimals;\r\n const sizes = ['', 'K', 'M', 'B', 'T'];\r\n\r\n const i = Math.floor(Math.log(bytes) / Math.log(k));\r\n\r\n return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + sizes[i];\r\n}\r\n\r\nexport function clamp(v: number, min: number, max: number): number {\r\n return v < min ? min : ((v > max) ? max : v);\r\n}\r\n\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { fastRaf } from \"./schedulers\";\r\nimport { CancellablePromise, deferredPromise } from \"./cancellablePromise\";\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\nimport isInDOM from \"./dom/isInDOM\";\r\n\r\nclass SequentialDom {\r\n private promises: Partial<{\r\n read: CancellablePromise<void>,\r\n write: CancellablePromise<void>\r\n }> = {};\r\n private raf = fastRaf.bind(null);\r\n private scheduled = false;\r\n\r\n private do(kind: keyof SequentialDom['promises'], callback?: VoidFunction) {\r\n let promise = this.promises[kind];\r\n if(!promise) {\r\n this.scheduleFlush();\r\n promise = this.promises[kind] = deferredPromise<void>();\r\n }\r\n\r\n if(callback !== undefined) {\r\n promise.then(() => callback());\r\n }\r\n \r\n return promise;\r\n }\r\n\r\n public measure(callback?: VoidFunction) {\r\n return this.do('read', callback);\r\n }\r\n\r\n public mutate(callback?: VoidFunction) {\r\n return this.do('write', callback);\r\n }\r\n\r\n /**\r\n * Will fire instantly if element is not connected\r\n * @param element \r\n * @param callback \r\n */\r\n public mutateElement(element: HTMLElement, callback?: VoidFunction) {\r\n const promise = isInDOM(element) ? this.mutate() : Promise.resolve();\r\n\r\n if(callback !== undefined) {\r\n promise.then(() => callback());\r\n }\r\n\r\n return promise;\r\n }\r\n\r\n private scheduleFlush() {\r\n if(!this.scheduled) {\r\n this.scheduled = true;\r\n\r\n this.raf(() => {\r\n this.promises.read && this.promises.read.resolve();\r\n this.promises.write && this.promises.write.resolve();\r\n\r\n this.scheduled = false;\r\n this.promises = {};\r\n });\r\n }\r\n }\r\n}\r\n\r\nconst sequentialDom = new SequentialDom();\r\nMOUNT_CLASS_TO && (MOUNT_CLASS_TO.sequentialDom = sequentialDom);\r\nexport default sequentialDom;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n * \r\n * Originally from:\r\n * https://github.com/zhukov/webogram\r\n * Copyright (C) 2014 Igor Zhukov <igor.beatle@gmail.com>\r\n * https://github.com/zhukov/webogram/blob/master/LICENSE\r\n */\r\n\r\nimport { MOUNT_CLASS_TO } from '../../config/debug';\r\nimport { tsNow } from '../../helpers/date';\r\nimport sessionStorage from '../sessionStorage';\r\n\r\nexport class ServerTimeManager {\r\n public timestampNow = tsNow(true);\r\n public midnightNoOffset = this.timestampNow - (this.timestampNow % 86400);\r\n public midnightOffseted = new Date();\r\n\r\n public midnightOffset = this.midnightNoOffset - (Math.floor(+this.midnightOffseted / 1000));\r\n\r\n public serverTimeOffset = 0; // in seconds\r\n public timeParams = {\r\n midnightOffset: this.midnightOffset,\r\n serverTimeOffset: this.serverTimeOffset\r\n };\r\n\r\n constructor() {\r\n this.midnightOffseted.setHours(0, 0, 0, 0);\r\n\r\n sessionStorage.get('server_time_offset').then((to) => {\r\n if(to) {\r\n this.serverTimeOffset = to;\r\n this.timeParams.serverTimeOffset = to;\r\n }\r\n });\r\n }\r\n}\r\n\r\nconst serverTimeManager = new ServerTimeManager();\r\nMOUNT_CLASS_TO && (MOUNT_CLASS_TO.serverTimeManager = serverTimeManager);\r\nexport default serverTimeManager;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { MOUNT_CLASS_TO } from \"./config/debug\";\r\n\r\nexport type Country = {\r\n phoneCode: string,\r\n code: string,\r\n name: string,\r\n pattern: string,\r\n emoji: string\r\n};\r\n\r\nconst Countries: Country[] = [{\"phoneCode\":\"7 840\",\"code\":\"AB\",\"name\":\"Abkhazia\",\"pattern\":\"\",\"emoji\":\"\"},{\"phoneCode\":\"93\",\"code\":\"AF\",\"name\":\"Afghanistan\",\"pattern\":\"93 XXX XXX XXX\",\"emoji\":\"🇦🇫\"},{\"phoneCode\":\"358 18\",\"code\":\"AX\",\"name\":\"Aland Islands\",\"pattern\":\"\",\"emoji\":\"🇦🇽\"},{\"phoneCode\":\"355\",\"code\":\"AL\",\"name\":\"Albania\",\"pattern\":\"355 XX XXX XXXX\",\"emoji\":\"🇦🇱\"},{\"phoneCode\":\"213\",\"code\":\"DZ\",\"name\":\"Algeria\",\"pattern\":\"213 XXX XX XX XX\",\"emoji\":\"🇩🇿\"},{\"phoneCode\":\"1 684\",\"code\":\"AS\",\"name\":\"American Samoa\",\"pattern\":\"1684 XXX XXXX\",\"emoji\":\"🇦🇸\"},{\"phoneCode\":\"376\",\"code\":\"AD\",\"name\":\"Andorra\",\"pattern\":\"376 XX XX XX\",\"emoji\":\"🇦🇩\"},{\"phoneCode\":\"244\",\"code\":\"AO\",\"name\":\"Angola\",\"pattern\":\"244 XXX XXX XXX\",\"emoji\":\"🇦🇴\"},{\"phoneCode\":\"1 264\",\"code\":\"AI\",\"name\":\"Anguilla\",\"pattern\":\"1264 XXX XXXX\",\"emoji\":\"🇦🇮\"},{\"phoneCode\":\"1 268\",\"code\":\"AG\",\"name\":\"Antigua & Barbuda\",\"pattern\":\"1268 XXX XXXX\",\"emoji\":\"🇦🇬\"},{\"phoneCode\":\"54\",\"code\":\"AR\",\"name\":\"Argentina\",\"pattern\":\"\",\"emoji\":\"🇦🇷\"},{\"phoneCode\":\"374\",\"code\":\"AM\",\"name\":\"Armenia\",\"pattern\":\"374 XX XXX XXX\",\"emoji\":\"🇦🇲\"},{\"phoneCode\":\"297\",\"code\":\"AW\",\"name\":\"Aruba\",\"pattern\":\"297 XXX XXXX\",\"emoji\":\"🇦🇼\"},{\"phoneCode\":\"247\",\"code\":\"SH\",\"name\":\"Ascension\",\"pattern\":\"290 XX XXX\",\"emoji\":\"🇸🇭\"},{\"phoneCode\":\"61\",\"code\":\"AU\",\"name\":\"Australia\",\"pattern\":\"61 XXX XXX XXX\",\"emoji\":\"🇦🇺\"},{\"phoneCode\":\"672\",\"code\":\"AU\",\"name\":\"Australian External Territories\",\"pattern\":\"61 XXX XXX XXX\",\"emoji\":\"🇦🇺\"},{\"phoneCode\":\"43\",\"code\":\"AT\",\"name\":\"Austria\",\"pattern\":\"\",\"emoji\":\"🇦🇹\"},{\"phoneCode\":\"994\",\"code\":\"AZ\",\"name\":\"Azerbaijan\",\"pattern\":\"994 XX XXX XX XX\",\"emoji\":\"🇦🇿\"},{\"phoneCode\":\"1 242\",\"code\":\"BS\",\"name\":\"Bahamas\",\"pattern\":\"1242 XXX XXXX\",\"emoji\":\"🇧🇸\"},{\"phoneCode\":\"973\",\"code\":\"BH\",\"name\":\"Bahrain\",\"pattern\":\"973 XXXX XXXX\",\"emoji\":\"🇧🇭\"},{\"phoneCode\":\"880\",\"code\":\"BD\",\"name\":\"Bangladesh\",\"pattern\":\"\",\"emoji\":\"🇧🇩\"},{\"phoneCode\":\"1 246\",\"code\":\"BB\",\"name\":\"Barbados\",\"pattern\":\"1246 XXX XXXX\",\"emoji\":\"🇧🇧\"},{\"phoneCode\":\"1 268\",\"code\":\"AG\",\"name\":\"Barbuda\",\"pattern\":\"1268 XXX XXXX\",\"emoji\":\"🇦🇬\"},{\"phoneCode\":\"375\",\"code\":\"BY\",\"name\":\"Belarus\",\"pattern\":\"375 XX XXX XXXX\",\"emoji\":\"🇧🇾\"},{\"phoneCode\":\"32\",\"code\":\"BE\",\"name\":\"Belgium\",\"pattern\":\"32 XXX XX XX XX\",\"emoji\":\"🇧🇪\"},{\"phoneCode\":\"501\",\"code\":\"BZ\",\"name\":\"Belize\",\"pattern\":\"\",\"emoji\":\"🇧🇿\"},{\"phoneCode\":\"229\",\"code\":\"BJ\",\"name\":\"Benin\",\"pattern\":\"229 XX XXX XXX\",\"emoji\":\"🇧🇯\"},{\"phoneCode\":\"1 441\",\"code\":\"BM\",\"name\":\"Bermuda\",\"pattern\":\"1441 XXX XXXX\",\"emoji\":\"🇧🇲\"},{\"phoneCode\":\"975\",\"code\":\"BT\",\"name\":\"Bhutan\",\"pattern\":\"\",\"emoji\":\"🇧🇹\"},{\"phoneCode\":\"591\",\"code\":\"BO\",\"name\":\"Bolivia\",\"pattern\":\"591 X XXX XXXX\",\"emoji\":\"🇧🇴\"},{\"phoneCode\":\"599 7\",\"code\":\"BQ\",\"name\":\"Caribbean Netherlands\",\"pattern\":\"\",\"emoji\":\"🇧🇶\"},{\"phoneCode\":\"387\",\"code\":\"BA\",\"name\":\"Bosnia & Herzegovina\",\"pattern\":\"\",\"emoji\":\"🇧🇦\"},{\"phoneCode\":\"267\",\"code\":\"BW\",\"name\":\"Botswana\",\"pattern\":\"267 XX XXX XXX\",\"emoji\":\"🇧🇼\"},{\"phoneCode\":\"55\",\"code\":\"BR\",\"name\":\"Brazil\",\"pattern\":\"55 XX XXXXX XXXX\",\"emoji\":\"🇧🇷\"},{\"phoneCode\":\"246\",\"code\":\"IO\",\"name\":\"British Indian Ocean Territory\",\"pattern\":\"246 XXX XXXX\",\"emoji\":\"🇮🇴\"},{\"phoneCode\":\"1 284\",\"code\":\"VG\",\"name\":\"British Virgin Islands\",\"pattern\":\"1284 XXX XXXX\",\"emoji\":\"🇻🇬\"},{\"phoneCode\":\"673\",\"code\":\"BN\",\"name\":\"Brunei\",\"pattern\":\"673 XXX XXXX\",\"emoji\":\"🇧🇳\"},{\"phoneCode\":\"359\",\"code\":\"BG\",\"name\":\"Bulgaria\",\"pattern\":\"\",\"emoji\":\"🇧🇬\"},{\"phoneCode\":\"226\",\"code\":\"BF\",\"name\":\"Burkina Faso\",\"pattern\":\"226 XX XX XX XX\",\"emoji\":\"🇧🇫\"},{\"phoneCode\":\"95\",\"code\":\"MM\",\"name\":\"Myanmar (Burma)\",\"pattern\":\"\",\"emoji\":\"🇲🇲\"},{\"phoneCode\":\"257\",\"code\":\"BI\",\"name\":\"Burundi\",\"pattern\":\"257 XX XX XXXX\",\"emoji\":\"🇧🇮\"},{\"phoneCode\":\"855\",\"code\":\"KH\",\"name\":\"Cambodia\",\"pattern\":\"\",\"emoji\":\"🇰🇭\"},{\"phoneCode\":\"237\",\"code\":\"CM\",\"name\":\"Cameroon\",\"pattern\":\"237 XXXX XXXX\",\"emoji\":\"🇨🇲\"},{\"phoneCode\":\"1\",\"code\":\"CA\",\"name\":\"Canada\",\"pattern\":\"1 XXX XXX XXXX\",\"emoji\":\"🇨🇦\"},{\"phoneCode\":\"238\",\"code\":\"CV\",\"name\":\"Cape Verde\",\"pattern\":\"238 XXX XXXX\",\"emoji\":\"🇨🇻\"},{\"phoneCode\":\"1 345\",\"code\":\"KY\",\"name\":\"Cayman Islands\",\"pattern\":\"1345 XXX XXXX\",\"emoji\":\"🇰🇾\"},{\"phoneCode\":\"236\",\"code\":\"CF\",\"name\":\"Central African Republic\",\"pattern\":\"236 XX XX XX XX\",\"emoji\":\"🇨🇫\"},{\"phoneCode\":\"235\",\"code\":\"TD\",\"name\":\"Chad\",\"pattern\":\"235 XX XX XX XX\",\"emoji\":\"🇹🇩\"},{\"phoneCode\":\"56\",\"code\":\"CL\",\"name\":\"Chile\",\"pattern\":\"56 X XXXX XXXX\",\"emoji\":\"🇨🇱\"},{\"phoneCode\":\"86\",\"code\":\"CN\",\"name\":\"China\",\"pattern\":\"86 XXX XXXX XXXX\",\"emoji\":\"🇨🇳\"},{\"phoneCode\":\"61\",\"code\":\"CX\",\"name\":\"Christmas Island\",\"pattern\":\"\",\"emoji\":\"🇨🇽\"},{\"phoneCode\":\"61\",\"code\":\"CC\",\"name\":\"Cocos (Keeling) Islands\",\"pattern\":\"\",\"emoji\":\"🇨🇨\"},{\"phoneCode\":\"57\",\"code\":\"CO\",\"name\":\"Colombia\",\"pattern\":\"57 XXX XXX XXXX\",\"emoji\":\"🇨🇴\"},{\"phoneCode\":\"269\",\"code\":\"KM\",\"name\":\"Comoros\",\"pattern\":\"269 XXX XXXX\",\"emoji\":\"🇰🇲\"},{\"phoneCode\":\"242\",\"code\":\"CG\",\"name\":\"Congo - Brazzaville\",\"pattern\":\"242 XX XXX XXXX\",\"emoji\":\"🇨🇬\"},{\"phoneCode\":\"243\",\"code\":\"CD\",\"name\":\"Congo - Kinshasa\",\"pattern\":\"243 XX XXX XXXX\",\"emoji\":\"🇨🇩\"},{\"phoneCode\":\"682\",\"code\":\"CK\",\"name\":\"Cook Islands\",\"pattern\":\"\",\"emoji\":\"🇨🇰\"},{\"phoneCode\":\"506\",\"code\":\"CR\",\"name\":\"Costa Rica\",\"pattern\":\"\",\"emoji\":\"🇨🇷\"},{\"phoneCode\":\"225\",\"code\":\"CI\",\"name\":\"Cote d’Ivoire\",\"pattern\":\"225 XX XXX XXX\",\"emoji\":\"🇨🇮\"},{\"phoneCode\":\"385\",\"code\":\"HR\",\"name\":\"Croatia\",\"pattern\":\"\",\"emoji\":\"🇭🇷\"},{\"phoneCode\":\"53\",\"code\":\"CU\",\"name\":\"Cuba\",\"pattern\":\"53 XXXX XXXX\",\"emoji\":\"🇨🇺\"},{\"phoneCode\":\"599 9\",\"code\":\"CW\",\"name\":\"Curacao\",\"pattern\":\"\",\"emoji\":\"🇨🇼\"},{\"phoneCode\":\"357\",\"code\":\"CY\",\"name\":\"Cyprus\",\"pattern\":\"357 XXXX XXXX\",\"emoji\":\"🇨🇾\"},{\"phoneCode\":\"420\",\"code\":\"CZ\",\"name\":\"Czech Republic\",\"pattern\":\"\",\"emoji\":\"🇨🇿\"},{\"phoneCode\":\"45\",\"code\":\"DK\",\"name\":\"Denmark\",\"pattern\":\"45 XXXX XXXX\",\"emoji\":\"🇩🇰\"},{\"phoneCode\":\"246\",\"code\":\"DG\",\"name\":\"Diego Garcia\",\"pattern\":\"\",\"emoji\":\"🇩🇬\"},{\"phoneCode\":\"253\",\"code\":\"DJ\",\"name\":\"Djibouti\",\"pattern\":\"253 XX XX XX XX\",\"emoji\":\"🇩🇯\"},{\"phoneCode\":\"1 767\",\"code\":\"DM\",\"name\":\"Dominica\",\"pattern\":\"1767 XXX XXXX\",\"emoji\":\"🇩🇲\"},{\"phoneCode\":\"1 809 and 1 829\",\"code\":\"DO\",\"name\":\"Dominican Republic\",\"pattern\":\"1 XXX XXX XXXX\",\"emoji\":\"🇩🇴\"},{\"phoneCode\":\"670\",\"code\":\"TL\",\"name\":\"Timor-Leste\",\"pattern\":\"\",\"emoji\":\"🇹🇱\"},{\"phoneCode\":\"593\",\"code\":\"EC\",\"name\":\"Ecuador\",\"pattern\":\"\",\"emoji\":\"🇪🇨\"},{\"phoneCode\":\"20\",\"code\":\"EG\",\"name\":\"Egypt\",\"pattern\":\"20 XX XXX XXXX\",\"emoji\":\"🇪🇬\"},{\"phoneCode\":\"503\",\"code\":\"SV\",\"name\":\"El Salvador\",\"pattern\":\"503 XXXX XXXX\",\"emoji\":\"🇸🇻\"},{\"phoneCode\":\"240\",\"code\":\"GQ\",\"name\":\"Equatorial Guinea\",\"pattern\":\"240 XXX XXX XXX\",\"emoji\":\"🇬🇶\"},{\"phoneCode\":\"291\",\"code\":\"ER\",\"name\":\"Eritrea\",\"pattern\":\"291 X XXX XXX\",\"emoji\":\"🇪🇷\"},{\"phoneCode\":\"372\",\"code\":\"EE\",\"name\":\"Estonia\",\"pattern\":\"\",\"emoji\":\"🇪🇪\"},{\"phoneCode\":\"251\",\"code\":\"ET\",\"name\":\"Ethiopia\",\"pattern\":\"251 XX XXX XXXX\",\"emoji\":\"🇪🇹\"},{\"phoneCode\":\"500\",\"code\":\"FK\",\"name\":\"Falkland Islands\",\"pattern\":\"\",\"emoji\":\"🇫🇰\"},{\"phoneCode\":\"298\",\"code\":\"FO\",\"name\":\"Faroe Islands\",\"pattern\":\"298 XXX XXX\",\"emoji\":\"🇫🇴\"},{\"phoneCode\":\"679\",\"code\":\"FJ\",\"name\":\"Fiji\",\"pattern\":\"\",\"emoji\":\"🇫🇯\"},{\"phoneCode\":\"358\",\"code\":\"FI\",\"name\":\"Finland\",\"pattern\":\"\",\"emoji\":\"🇫🇮\"},{\"phoneCode\":\"33\",\"code\":\"FR\",\"name\":\"France\",\"pattern\":\"33 X XX XX XX XX\",\"emoji\":\"🇫🇷\"},{\"phoneCode\":\"594\",\"code\":\"GF\",\"name\":\"French Guiana\",\"pattern\":\"\",\"emoji\":\"🇬🇫\"},{\"phoneCode\":\"689\",\"code\":\"PF\",\"name\":\"French Polynesia\",\"pattern\":\"\",\"emoji\":\"🇵🇫\"},{\"phoneCode\":\"241\",\"code\":\"GA\",\"name\":\"Gabon\",\"pattern\":\"241 X XX XX XX\",\"emoji\":\"🇬🇦\"},{\"phoneCode\":\"220\",\"code\":\"GM\",\"name\":\"Gambia\",\"pattern\":\"220 XXX XXXX\",\"emoji\":\"🇬🇲\"},{\"phoneCode\":\"995\",\"code\":\"GE\",\"name\":\"Georgia\",\"pattern\":\"\",\"emoji\":\"🇬🇪\"},{\"phoneCode\":\"49\",\"code\":\"DE\",\"name\":\"Germany\",\"pattern\":\"49 XXX XXXXXXXX\",\"emoji\":\"🇩🇪\"},{\"phoneCode\":\"233\",\"code\":\"GH\",\"name\":\"Ghana\",\"pattern\":\"\",\"emoji\":\"🇬🇭\"},{\"phoneCode\":\"350\",\"code\":\"GI\",\"name\":\"Gibraltar\",\"pattern\":\"350 XXXX XXXX\",\"emoji\":\"🇬🇮\"},{\"phoneCode\":\"30\",\"code\":\"GR\",\"name\":\"Greece\",\"pattern\":\"30 XX XXXX XXXX\",\"emoji\":\"🇬🇷\"},{\"phoneCode\":\"299\",\"code\":\"GL\",\"name\":\"Greenland\",\"pattern\":\"299 XXX XXX\",\"emoji\":\"🇬🇱\"},{\"phoneCode\":\"1 473\",\"code\":\"GD\",\"name\":\"Grenada\",\"pattern\":\"1473 XXX XXXX\",\"emoji\":\"🇬🇩\"},{\"phoneCode\":\"590\",\"code\":\"GP\",\"name\":\"Guadeloupe\",\"pattern\":\"\",\"emoji\":\"🇬🇵\"},{\"phoneCode\":\"1 671\",\"code\":\"GU\",\"name\":\"Guam\",\"pattern\":\"1671 XXX XXXX\",\"emoji\":\"🇬🇺\"},{\"phoneCode\":\"502\",\"code\":\"GT\",\"name\":\"Guatemala\",\"pattern\":\"502 X XXX XXXX\",\"emoji\":\"🇬🇹\"},{\"phoneCode\":\"44\",\"code\":\"GG\",\"name\":\"Guernsey\",\"pattern\":\"\",\"emoji\":\"🇬🇬\"},{\"phoneCode\":\"224\",\"code\":\"GN\",\"name\":\"Guinea\",\"pattern\":\"224 XXX XXX XXX\",\"emoji\":\"🇬🇳\"},{\"phoneCode\":\"245\",\"code\":\"GW\",\"name\":\"Guinea-Bissau\",\"pattern\":\"245 XXX XXXX\",\"emoji\":\"🇬🇼\"},{\"phoneCode\":\"592\",\"code\":\"GY\",\"name\":\"Guyana\",\"pattern\":\"\",\"emoji\":\"🇬🇾\"},{\"phoneCode\":\"509\",\"code\":\"HT\",\"name\":\"Haiti\",\"pattern\":\"\",\"emoji\":\"🇭🇹\"},{\"phoneCode\":\"504\",\"code\":\"HN\",\"name\":\"Honduras\",\"pattern\":\"504 XXXX XXXX\",\"emoji\":\"🇭🇳\"},{\"phoneCode\":\"852\",\"code\":\"HK\",\"name\":\"Hong Kong SAR China\",\"pattern\":\"\",\"emoji\":\"🇭🇰\"},{\"phoneCode\":\"36\",\"code\":\"HU\",\"name\":\"Hungary\",\"pattern\":\"36 XX XXX XXXX\",\"emoji\":\"🇭🇺\"},{\"phoneCode\":\"354\",\"code\":\"IS\",\"name\":\"Iceland\",\"pattern\":\"354 XXX XXXX\",\"emoji\":\"🇮🇸\"},{\"phoneCode\":\"91\",\"code\":\"IN\",\"name\":\"India\",\"pattern\":\"91 XXXXX XXXXX\",\"emoji\":\"🇮🇳\"},{\"phoneCode\":\"62\",\"code\":\"ID\",\"name\":\"Indonesia\",\"pattern\":\"\",\"emoji\":\"🇮🇩\"},{\"phoneCode\":\"98\",\"code\":\"IR\",\"name\":\"Iran\",\"pattern\":\"98 XXX XXX XXXX\",\"emoji\":\"🇮🇷\"},{\"phoneCode\":\"964\",\"code\":\"IQ\",\"name\":\"Iraq\",\"pattern\":\"964 XXX XXX XXXX\",\"emoji\":\"🇮🇶\"},{\"phoneCode\":\"353\",\"code\":\"IE\",\"name\":\"Ireland\",\"pattern\":\"353 XX XXX XXXX\",\"emoji\":\"🇮🇪\"},{\"phoneCode\":\"972\",\"code\":\"IL\",\"name\":\"Israel\",\"pattern\":\"972 XX XXX XXXX\",\"emoji\":\"🇮🇱\"},{\"phoneCode\":\"39\",\"code\":\"IT\",\"name\":\"Italy\",\"pattern\":\"39 XXX XXX XXXX\",\"emoji\":\"🇮🇹\"},{\"phoneCode\":\"1 876\",\"code\":\"JM\",\"name\":\"Jamaica\",\"pattern\":\"1876 XXX XXXX\",\"emoji\":\"🇯🇲\"},{\"phoneCode\":\"47 79\",\"code\":\"SJ\",\"name\":\"Svalbard & Jan Mayen\",\"pattern\":\"\",\"emoji\":\"🇸🇯\"},{\"phoneCode\":\"81\",\"code\":\"JP\",\"name\":\"Japan\",\"pattern\":\"81 XX XXXX XXXX\",\"emoji\":\"🇯🇵\"},{\"phoneCode\":\"44\",\"code\":\"JE\",\"name\":\"Jersey\",\"pattern\":\"\",\"emoji\":\"🇯🇪\"},{\"phoneCode\":\"962\",\"code\":\"JO\",\"name\":\"Jordan\",\"pattern\":\"962 X XXXX XXXX\",\"emoji\":\"🇯🇴\"},{\"phoneCode\":\"7 7\",\"code\":\"KZ\",\"name\":\"Kazakhstan\",\"pattern\":\"7 XXX XXX XX XX\",\"emoji\":\"🇰🇿\"},{\"phoneCode\":\"254\",\"code\":\"KE\",\"name\":\"Kenya\",\"pattern\":\"254 XXX XXX XXX\",\"emoji\":\"🇰🇪\"},{\"phoneCode\":\"686\",\"code\":\"KI\",\"name\":\"Kiribati\",\"pattern\":\"\",\"emoji\":\"🇰🇮\"},{\"phoneCode\":\"850\",\"code\":\"KP\",\"name\":\"North Korea\",\"pattern\":\"\",\"emoji\":\"🇰🇵\"},{\"phoneCode\":\"82\",\"code\":\"KR\",\"name\":\"South Korea\",\"pattern\":\"\",\"emoji\":\"🇰🇷\"},{\"phoneCode\":\"965\",\"code\":\"KW\",\"name\":\"Kuwait\",\"pattern\":\"965 XXXX XXXX\",\"emoji\":\"🇰🇼\"},{\"phoneCode\":\"996\",\"code\":\"KG\",\"name\":\"Kyrgyzstan\",\"pattern\":\"\",\"emoji\":\"🇰🇬\"},{\"phoneCode\":\"856\",\"code\":\"LA\",\"name\":\"Laos\",\"pattern\":\"\",\"emoji\":\"🇱🇦\"},{\"phoneCode\":\"371\",\"code\":\"LV\",\"name\":\"Latvia\",\"pattern\":\"371 XXX XXXXX\",\"emoji\":\"🇱🇻\"},{\"phoneCode\":\"961\",\"code\":\"LB\",\"name\":\"Lebanon\",\"pattern\":\"\",\"emoji\":\"🇱🇧\"},{\"phoneCode\":\"266\",\"code\":\"LS\",\"name\":\"Lesotho\",\"pattern\":\"266 XX XXX XXX\",\"emoji\":\"🇱🇸\"},{\"phoneCode\":\"231\",\"code\":\"LR\",\"name\":\"Liberia\",\"pattern\":\"\",\"emoji\":\"🇱🇷\"},{\"phoneCode\":\"218\",\"code\":\"LY\",\"name\":\"Libya\",\"pattern\":\"218 XX XXX XXXX\",\"emoji\":\"🇱🇾\"},{\"phoneCode\":\"423\",\"code\":\"LI\",\"name\":\"Liechtenstein\",\"pattern\":\"\",\"emoji\":\"🇱🇮\"},{\"phoneCode\":\"370\",\"code\":\"LT\",\"name\":\"Lithuania\",\"pattern\":\"370 XXX XXXXX\",\"emoji\":\"🇱🇹\"},{\"phoneCode\":\"352\",\"code\":\"LU\",\"name\":\"Luxembourg\",\"pattern\":\"\",\"emoji\":\"🇱🇺\"},{\"phoneCode\":\"853\",\"code\":\"MO\",\"name\":\"Macau SAR China\",\"pattern\":\"\",\"emoji\":\"🇲🇴\"},{\"phoneCode\":\"389\",\"code\":\"MK\",\"name\":\"Macedonia\",\"pattern\":\"\",\"emoji\":\"🇲🇰\"},{\"phoneCode\":\"261\",\"code\":\"MG\",\"name\":\"Madagascar\",\"pattern\":\"261 XX XX XXX XX\",\"emoji\":\"🇲🇬\"},{\"phoneCode\":\"265\",\"code\":\"MW\",\"name\":\"Malawi\",\"pattern\":\"\",\"emoji\":\"🇲🇼\"},{\"phoneCode\":\"60\",\"code\":\"MY\",\"name\":\"Malaysia\",\"pattern\":\"\",\"emoji\":\"🇲🇾\"},{\"phoneCode\":\"960\",\"code\":\"MV\",\"name\":\"Maldives\",\"pattern\":\"\",\"emoji\":\"🇲🇻\"},{\"phoneCode\":\"223\",\"code\":\"ML\",\"name\":\"Mali\",\"pattern\":\"223 XXXX XXXX\",\"emoji\":\"🇲🇱\"},{\"phoneCode\":\"356\",\"code\":\"MT\",\"name\":\"Malta\",\"pattern\":\"356 XX XX XX XX\",\"emoji\":\"🇲🇹\"},{\"phoneCode\":\"692\",\"code\":\"MH\",\"name\":\"Marshall Islands\",\"pattern\":\"\",\"emoji\":\"🇲🇭\"},{\"phoneCode\":\"596\",\"code\":\"MQ\",\"name\":\"Martinique\",\"pattern\":\"\",\"emoji\":\"🇲🇶\"},{\"phoneCode\":\"222\",\"code\":\"MR\",\"name\":\"Mauritania\",\"pattern\":\"222 XXXX XXXX\",\"emoji\":\"🇲🇷\"},{\"phoneCode\":\"230\",\"code\":\"MU\",\"name\":\"Mauritius\",\"pattern\":\"\",\"emoji\":\"🇲🇺\"},{\"phoneCode\":\"262\",\"code\":\"YT\",\"name\":\"Mayotte\",\"pattern\":\"\",\"emoji\":\"🇾🇹\"},{\"phoneCode\":\"52\",\"code\":\"MX\",\"name\":\"Mexico\",\"pattern\":\"\",\"emoji\":\"🇲🇽\"},{\"phoneCode\":\"691\",\"code\":\"FM\",\"name\":\"Micronesia\",\"pattern\":\"\",\"emoji\":\"🇫🇲\"},{\"phoneCode\":\"373\",\"code\":\"MD\",\"name\":\"Moldova\",\"pattern\":\"373 XX XXX XXX\",\"emoji\":\"🇲🇩\"},{\"phoneCode\":\"377\",\"code\":\"MC\",\"name\":\"Monaco\",\"pattern\":\"377 XXXX XXXX\",\"emoji\":\"🇲🇨\"},{\"phoneCode\":\"976\",\"code\":\"MN\",\"name\":\"Mongolia\",\"pattern\":\"\",\"emoji\":\"🇲🇳\"},{\"phoneCode\":\"382\",\"code\":\"ME\",\"name\":\"Montenegro\",\"pattern\":\"\",\"emoji\":\"🇲🇪\"},{\"phoneCode\":\"1 664\",\"code\":\"MS\",\"name\":\"Montserrat\",\"pattern\":\"1664 XXX XXXX\",\"emoji\":\"🇲🇸\"},{\"phoneCode\":\"212\",\"code\":\"MA\",\"name\":\"Morocco\",\"pattern\":\"212 XX XXX XXXX\",\"emoji\":\"🇲🇦\"},{\"phoneCode\":\"258\",\"code\":\"MZ\",\"name\":\"Mozambique\",\"pattern\":\"258 XX XXX XXXX\",\"emoji\":\"🇲🇿\"},{\"phoneCode\":\"264\",\"code\":\"NA\",\"name\":\"Namibia\",\"pattern\":\"264 XX XXX XXXX\",\"emoji\":\"🇳🇦\"},{\"phoneCode\":\"674\",\"code\":\"NR\",\"name\":\"Nauru\",\"pattern\":\"\",\"emoji\":\"🇳🇷\"},{\"phoneCode\":\"977\",\"code\":\"NP\",\"name\":\"Nepal\",\"pattern\":\"\",\"emoji\":\"🇳🇵\"},{\"phoneCode\":\"31\",\"code\":\"NL\",\"name\":\"Netherlands\",\"pattern\":\"31 X XX XX XX XX\",\"emoji\":\"🇳🇱\"},{\"phoneCode\":\"687\",\"code\":\"NC\",\"name\":\"New Caledonia\",\"pattern\":\"\",\"emoji\":\"🇳🇨\"},{\"phoneCode\":\"64\",\"code\":\"NZ\",\"name\":\"New Zealand\",\"pattern\":\"\",\"emoji\":\"🇳🇿\"},{\"phoneCode\":\"505\",\"code\":\"NI\",\"name\":\"Nicaragua\",\"pattern\":\"505 XXXX XXXX\",\"emoji\":\"🇳🇮\"},{\"phoneCode\":\"227\",\"code\":\"NE\",\"name\":\"Niger\",\"pattern\":\"227 XX XX XX XX\",\"emoji\":\"🇳🇪\"},{\"phoneCode\":\"234\",\"code\":\"NG\",\"name\":\"Nigeria\",\"pattern\":\"\",\"emoji\":\"🇳🇬\"},{\"phoneCode\":\"683\",\"code\":\"NU\",\"name\":\"Niue\",\"pattern\":\"\",\"emoji\":\"🇳🇺\"},{\"phoneCode\":\"672\",\"code\":\"NF\",\"name\":\"Norfolk Island\",\"pattern\":\"\",\"emoji\":\"🇳🇫\"},{\"phoneCode\":\"1 670\",\"code\":\"MP\",\"name\":\"Northern Mariana Islands\",\"pattern\":\"1670 XXX XXXX\",\"emoji\":\"🇲🇵\"},{\"phoneCode\":\"47\",\"code\":\"NO\",\"name\":\"Norway\",\"pattern\":\"47 XXXX XXXX\",\"emoji\":\"🇳🇴\"},{\"phoneCode\":\"968\",\"code\":\"OM\",\"name\":\"Oman\",\"pattern\":\"968 XXXX XXXX\",\"emoji\":\"🇴🇲\"},{\"phoneCode\":\"92\",\"code\":\"PK\",\"name\":\"Pakistan\",\"pattern\":\"92 XXX XXX XXXX\",\"emoji\":\"🇵🇰\"},{\"phoneCode\":\"680\",\"code\":\"PW\",\"name\":\"Palau\",\"pattern\":\"\",\"emoji\":\"🇵🇼\"},{\"phoneCode\":\"970\",\"code\":\"PS\",\"name\":\"Palestinian Territories\",\"pattern\":\"970 XXX XX XXXX\",\"emoji\":\"🇵🇸\"},{\"phoneCode\":\"507\",\"code\":\"PA\",\"name\":\"Panama\",\"pattern\":\"507 XXXX XXXX\",\"emoji\":\"🇵🇦\"},{\"phoneCode\":\"675\",\"code\":\"PG\",\"name\":\"Papua New Guinea\",\"pattern\":\"\",\"emoji\":\"🇵🇬\"},{\"phoneCode\":\"595\",\"code\":\"PY\",\"name\":\"Paraguay\",\"pattern\":\"595 XXX XXX XXX\",\"emoji\":\"🇵🇾\"},{\"phoneCode\":\"51\",\"code\":\"PE\",\"name\":\"Peru\",\"pattern\":\"51 XXX XXX XXX\",\"emoji\":\"🇵🇪\"},{\"phoneCode\":\"63\",\"code\":\"PH\",\"name\":\"Philippines\",\"pattern\":\"63 XXX XXX XXXX\",\"emoji\":\"🇵🇭\"},{\"phoneCode\":\"64\",\"code\":\"PN\",\"name\":\"Pitcairn Islands\",\"pattern\":\"\",\"emoji\":\"🇵🇳\"},{\"phoneCode\":\"48\",\"code\":\"PL\",\"name\":\"Poland\",\"pattern\":\"48 XXX XXX XXX\",\"emoji\":\"🇵🇱\"},{\"phoneCode\":\"351\",\"code\":\"PT\",\"name\":\"Portugal\",\"pattern\":\"351 X XXXX XXXX\",\"emoji\":\"🇵🇹\"},{\"phoneCode\":\"1 787 and 1 939\",\"code\":\"PR\",\"name\":\"Puerto Rico\",\"pattern\":\"1 XXX XXX XXXX\",\"emoji\":\"🇵🇷\"},{\"phoneCode\":\"974\",\"code\":\"QA\",\"name\":\"Qatar\",\"pattern\":\"\",\"emoji\":\"🇶🇦\"},{\"phoneCode\":\"262\",\"code\":\"RE\",\"name\":\"Reunion\",\"pattern\":\"262 XXX XXX XXX\",\"emoji\":\"🇷🇪\"},{\"phoneCode\":\"40\",\"code\":\"RO\",\"name\":\"Romania\",\"pattern\":\"40 XXX XXX XXX\",\"emoji\":\"🇷🇴\"},{\"phoneCode\":\"7\",\"code\":\"RU\",\"name\":\"Russia\",\"pattern\":\"7 XXX XXX XX XX\",\"emoji\":\"🇷🇺\"},{\"phoneCode\":\"250\",\"code\":\"RW\",\"name\":\"Rwanda\",\"pattern\":\"250 XXX XXX XXX\",\"emoji\":\"🇷🇼\"},{\"phoneCode\":\"590\",\"code\":\"BL\",\"name\":\"St. Barthelemy\",\"pattern\":\"\",\"emoji\":\"🇧🇱\"},{\"phoneCode\":\"290\",\"code\":\"SH\",\"name\":\"St. Helena\",\"pattern\":\"290 XX XXX\",\"emoji\":\"🇸🇭\"},{\"phoneCode\":\"1 869\",\"code\":\"KN\",\"name\":\"St. Kitts & Nevis\",\"pattern\":\"1869 XXX XXXX\",\"emoji\":\"🇰🇳\"},{\"phoneCode\":\"1 758\",\"code\":\"LC\",\"name\":\"St. Lucia\",\"pattern\":\"1758 XXX XXXX\",\"emoji\":\"🇱🇨\"},{\"phoneCode\":\"590\",\"code\":\"MF\",\"name\":\"St. Martin (France)\",\"pattern\":\"\",\"emoji\":\"🇲🇫\"},{\"phoneCode\":\"508\",\"code\":\"PM\",\"name\":\"St. Pierre and Miquelon\",\"pattern\":\"\",\"emoji\":\"🇵🇲\"},{\"phoneCode\":\"1 784\",\"code\":\"VC\",\"name\":\"St. Vincent and the Grenadines\",\"pattern\":\"1784 XXX XXXX\",\"emoji\":\"🇻🇨\"},{\"phoneCode\":\"685\",\"code\":\"WS\",\"name\":\"Samoa\",\"pattern\":\"\",\"emoji\":\"🇼🇸\"},{\"phoneCode\":\"378\",\"code\":\"SM\",\"name\":\"San Marino\",\"pattern\":\"378 XXX XXX XXXX\",\"emoji\":\"🇸🇲\"},{\"phoneCode\":\"239\",\"code\":\"ST\",\"name\":\"São Tome & Principe\",\"pattern\":\"239 XX XXXXX\",\"emoji\":\"🇸🇹\"},{\"phoneCode\":\"966\",\"code\":\"SA\",\"name\":\"Saudi Arabia\",\"pattern\":\"\",\"emoji\":\"🇸🇦\"},{\"phoneCode\":\"221\",\"code\":\"SN\",\"name\":\"Senegal\",\"pattern\":\"221 XX XXX XXXX\",\"emoji\":\"🇸🇳\"},{\"phoneCode\":\"381\",\"code\":\"RS\",\"name\":\"Serbia\",\"pattern\":\"381 XX XXX XXXX\",\"emoji\":\"🇷🇸\"},{\"phoneCode\":\"248\",\"code\":\"SC\",\"name\":\"Seychelles\",\"pattern\":\"248 X XX XX XX\",\"emoji\":\"🇸🇨\"},{\"phoneCode\":\"232\",\"code\":\"SL\",\"name\":\"Sierra Leone\",\"pattern\":\"232 XX XXX XXX\",\"emoji\":\"🇸🇱\"},{\"phoneCode\":\"65\",\"code\":\"SG\",\"name\":\"Singapore\",\"pattern\":\"65 XXXX XXXX\",\"emoji\":\"🇸🇬\"},{\"phoneCode\":\"599 3\",\"code\":\"BQ\",\"name\":\"Sint Eustatius\",\"pattern\":\"\",\"emoji\":\"🇧🇶\"},{\"phoneCode\":\"1 721\",\"code\":\"SX\",\"name\":\"Sint Maarten\",\"pattern\":\"1721 XXX XXXX\",\"emoji\":\"🇸🇽\"},{\"phoneCode\":\"421\",\"code\":\"SK\",\"name\":\"Slovakia\",\"pattern\":\"\",\"emoji\":\"🇸🇰\"},{\"phoneCode\":\"386\",\"code\":\"SI\",\"name\":\"Slovenia\",\"pattern\":\"\",\"emoji\":\"🇸🇮\"},{\"phoneCode\":\"677\",\"code\":\"SB\",\"name\":\"Solomon Islands\",\"pattern\":\"\",\"emoji\":\"🇸🇧\"},{\"phoneCode\":\"252\",\"code\":\"SO\",\"name\":\"Somalia\",\"pattern\":\"252 XX XXX XXX\",\"emoji\":\"🇸🇴\"},{\"phoneCode\":\"27\",\"code\":\"ZA\",\"name\":\"South Africa\",\"pattern\":\"27 XX XXX XXXX\",\"emoji\":\"🇿🇦\"},{\"phoneCode\":\"500\",\"code\":\"GS\",\"name\":\"South Georgia & South Sandwich Islands\",\"pattern\":\"\",\"emoji\":\"🇬🇸\"},{\"phoneCode\":\"995 34\",\"code\":\"\",\"name\":\"South Ossetia\",\"pattern\":\"\",\"emoji\":\"\"},{\"phoneCode\":\"211\",\"code\":\"SS\",\"name\":\"South Sudan\",\"pattern\":\"211 XX XXX XXXX\",\"emoji\":\"🇸🇸\"},{\"phoneCode\":\"34\",\"code\":\"ES\",\"name\":\"Spain\",\"pattern\":\"34 XXX XXX XXX\",\"emoji\":\"🇪🇸\"},{\"phoneCode\":\"94\",\"code\":\"LK\",\"name\":\"Sri Lanka\",\"pattern\":\"94 XX XXX XXXX\",\"emoji\":\"🇱🇰\"},{\"phoneCode\":\"249\",\"code\":\"SD\",\"name\":\"Sudan\",\"pattern\":\"249 XX XXX XXXX\",\"emoji\":\"🇸🇩\"},{\"phoneCode\":\"597\",\"code\":\"SR\",\"name\":\"Suriname\",\"pattern\":\"597 XXX XXXX\",\"emoji\":\"🇸🇷\"},{\"phoneCode\":\"47 79\",\"code\":\"SJ\",\"name\":\"Svalbard\",\"pattern\":\"\",\"emoji\":\"🇸🇯\"},{\"phoneCode\":\"268\",\"code\":\"SZ\",\"name\":\"Swaziland\",\"pattern\":\"268 XXXX XXXX\",\"emoji\":\"🇸🇿\"},{\"phoneCode\":\"46\",\"code\":\"SE\",\"name\":\"Sweden\",\"pattern\":\"46 XX XXX XXXX\",\"emoji\":\"🇸🇪\"},{\"phoneCode\":\"41\",\"code\":\"CH\",\"name\":\"Switzerland\",\"pattern\":\"41 XX XXX XXXX\",\"emoji\":\"🇨🇭\"},{\"phoneCode\":\"963\",\"code\":\"SY\",\"name\":\"Syria\",\"pattern\":\"\",\"emoji\":\"🇸🇾\"},{\"phoneCode\":\"886\",\"code\":\"TW\",\"name\":\"Taiwan\",\"pattern\":\"\",\"emoji\":\"🇹🇼\"},{\"phoneCode\":\"992\",\"code\":\"TJ\",\"name\":\"Tajikistan\",\"pattern\":\"\",\"emoji\":\"🇹🇯\"},{\"phoneCode\":\"255\",\"code\":\"TZ\",\"name\":\"Tanzania\",\"pattern\":\"255 XX XXX XXXX\",\"emoji\":\"🇹🇿\"},{\"phoneCode\":\"66\",\"code\":\"TH\",\"name\":\"Thailand\",\"pattern\":\"66 X XXXX XXXX\",\"emoji\":\"🇹🇭\"},{\"phoneCode\":\"228\",\"code\":\"TG\",\"name\":\"Togo\",\"pattern\":\"228 XX XXX XXX\",\"emoji\":\"🇹🇬\"},{\"phoneCode\":\"690\",\"code\":\"TK\",\"name\":\"Tokelau\",\"pattern\":\"\",\"emoji\":\"🇹🇰\"},{\"phoneCode\":\"676\",\"code\":\"TO\",\"name\":\"Tonga\",\"pattern\":\"\",\"emoji\":\"🇹🇴\"},{\"phoneCode\":\"1 868\",\"code\":\"TT\",\"name\":\"Trinidad & Tobago\",\"pattern\":\"1868 XXX XXXX\",\"emoji\":\"🇹🇹\"},{\"phoneCode\":\"216\",\"code\":\"TN\",\"name\":\"Tunisia\",\"pattern\":\"216 XX XXX XXX\",\"emoji\":\"🇹🇳\"},{\"phoneCode\":\"90\",\"code\":\"TR\",\"name\":\"Turkey\",\"pattern\":\"90 XXX XXX XXXX\",\"emoji\":\"🇹🇷\"},{\"phoneCode\":\"993\",\"code\":\"TM\",\"name\":\"Turkmenistan\",\"pattern\":\"993 XX XXXXXX\",\"emoji\":\"🇹🇲\"},{\"phoneCode\":\"1 649\",\"code\":\"TC\",\"name\":\"Turks & Caicos Islands\",\"pattern\":\"1649 XXX XXXX\",\"emoji\":\"🇹🇨\"},{\"phoneCode\":\"688\",\"code\":\"TV\",\"name\":\"Tuvalu\",\"pattern\":\"\",\"emoji\":\"🇹🇻\"},{\"phoneCode\":\"256\",\"code\":\"UG\",\"name\":\"Uganda\",\"pattern\":\"256 XX XXX XXXX\",\"emoji\":\"🇺🇬\"},{\"phoneCode\":\"380\",\"code\":\"UA\",\"name\":\"Ukraine\",\"pattern\":\"380 XX XXX XX XX\",\"emoji\":\"🇺🇦\"},{\"phoneCode\":\"971\",\"code\":\"AE\",\"name\":\"United Arab Emirates\",\"pattern\":\"971 XX XXX XXXX\",\"emoji\":\"🇦🇪\"},{\"phoneCode\":\"44\",\"code\":\"GB\",\"name\":\"United Kingdom\",\"pattern\":\"44 XXXX XXXXXX\",\"emoji\":\"🇬🇧\"},{\"phoneCode\":\"1\",\"code\":\"US\",\"name\":\"United States\",\"pattern\":\"1 XXX XXX XXXX\",\"emoji\":\"🇺🇸\"},{\"phoneCode\":\"598\",\"code\":\"UY\",\"name\":\"Uruguay\",\"pattern\":\"598 XXXX XXXX\",\"emoji\":\"🇺🇾\"},{\"phoneCode\":\"1 340\",\"code\":\"VI\",\"name\":\"U.S. Virgin Islands\",\"pattern\":\"1340 XXX XXXX\",\"emoji\":\"🇻🇮\"},{\"phoneCode\":\"998\",\"code\":\"UZ\",\"name\":\"Uzbekistan\",\"pattern\":\"998 XX XXXXXXX\",\"emoji\":\"🇺🇿\"},{\"phoneCode\":\"678\",\"code\":\"VU\",\"name\":\"Vanuatu\",\"pattern\":\"\",\"emoji\":\"🇻🇺\"},{\"phoneCode\":\"58\",\"code\":\"VE\",\"name\":\"Venezuela\",\"pattern\":\"58 XXX XXX XXXX\",\"emoji\":\"🇻🇪\"},{\"phoneCode\":\"39 06 698\",\"code\":\"VA\",\"name\":\"Vatican City\",\"pattern\":\"\",\"emoji\":\"🇻🇦\"},{\"phoneCode\":\"84\",\"code\":\"VN\",\"name\":\"Vietnam\",\"pattern\":\"\",\"emoji\":\"🇻🇳\"},{\"phoneCode\":\"681\",\"code\":\"WF\",\"name\":\"Wallis & Futuna\",\"pattern\":\"\",\"emoji\":\"🇼🇫\"},{\"phoneCode\":\"967\",\"code\":\"YE\",\"name\":\"Yemen\",\"pattern\":\"967 XXX XXX XXX\",\"emoji\":\"🇾🇪\"},{\"phoneCode\":\"260\",\"code\":\"ZM\",\"name\":\"Zambia\",\"pattern\":\"260 XX XXX XXXX\",\"emoji\":\"🇿🇲\"},{\"phoneCode\":\"255\",\"code\":\"\",\"name\":\"Zanzibar\",\"pattern\":\"\",\"emoji\":\"\"},{\"phoneCode\":\"263\",\"code\":\"ZW\",\"name\":\"Zimbabwe\",\"pattern\":\"263 XX XXX XXXX\",\"emoji\":\"🇿🇼\"}];\r\nconst PhoneCodesMain: {[phoneCode: string]: Country} = {\r\n '1': Countries.find(c => c.name === 'United States'),\r\n '44': Countries.find(c => c.name === 'United Kingdom'),\r\n '61': Countries.find(c => c.name === 'Australia'),\r\n '64': Countries.find(c => c.name === 'New Zealand'),\r\n '246': Countries.find(c => c.name === 'Diego Garcia'),\r\n '255': Countries.find(c => c.name === 'Tanzania'),\r\n '262': Countries.find(c => c.name === 'Reunion'),\r\n '500': Countries.find(c => c.name === 'Falkland Islands'),\r\n '590': Countries.find(c => c.name === 'Guadeloupe'),\r\n '672': Countries.find(c => c.name === 'Norfolk Island'),\r\n '1 268': Countries.find(c => c.name === 'Antigua & Barbuda'),\r\n};\r\n\r\n/* \r\nconst toInt = (str) => {\r\n return parseInt(str.replace(/ /g, ''));\r\n};\r\nvar arr = window.Countries.sort((a, b) => toInt(a.phoneCode) - toInt(b.phoneCode));\r\narr.forEach((el, idx) => {\r\n if(idx === (arr.length - 1)) {\r\n return;\r\n }\r\n\r\n if(toInt(arr[idx + 1].phoneCode) === toInt(el.phoneCode)) {\r\n console.log('duplicate', el, arr[idx + 1]);\r\n }\r\n});\r\n*/\r\n\r\nMOUNT_CLASS_TO.Countries = Countries;\r\n\r\nexport default Countries;\r\nexport {PhoneCodesMain};","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n * \r\n * Originally from:\r\n * https://github.com/zhukov/webogram\r\n * Copyright (C) 2014 Igor Zhukov <igor.beatle@gmail.com>\r\n * https://github.com/zhukov/webogram/blob/master/LICENSE\r\n */\r\n\r\nimport type { AccountPassword, AccountPasswordInputSettings, AccountUpdatePasswordSettings, InputCheckPasswordSRP, PasswordKdfAlgo } from '../../layer';\r\nimport type CryptoWorkerMethods from '../crypto/crypto_methods';\r\nimport { MOUNT_CLASS_TO } from '../../config/debug';\r\nimport appUsersManager from '../appManagers/appUsersManager';\r\nimport apiManager from './mtprotoworker';\r\n//import { computeCheck } from \"../crypto/srp\";\r\n\r\nexport class PasswordManager {\r\n public getState(): Promise<AccountPassword> {\r\n return apiManager.invokeApi('account.getPassword').then((result) => {\r\n return result;\r\n });\r\n }\r\n\r\n public updateSettings(settings: {\r\n hint?: string,\r\n email?: string,\r\n newPassword?: string,\r\n currentPassword?: string\r\n } = {}) {\r\n //state = Object.assign({}, state);\r\n //state.new_algo = Object.assign({}, state.new_algo);\r\n\r\n return this.getState().then(state => {\r\n let currentHashPromise: ReturnType<CryptoWorkerMethods['computeSRP']>;\r\n let newHashPromise: Promise<Uint8Array>;\r\n const params: AccountUpdatePasswordSettings = {\r\n password: null,\r\n new_settings: {\r\n _: 'account.passwordInputSettings',\r\n hint: settings.hint,\r\n email: settings.email\r\n }\r\n };\r\n \r\n if(settings.currentPassword) {\r\n currentHashPromise = apiManager.computeSRP(settings.currentPassword, state);\r\n } else {\r\n currentHashPromise = Promise.resolve({\r\n _: 'inputCheckPasswordEmpty'\r\n });\r\n }\r\n \r\n // * https://core.telegram.org/api/srp#setting-a-new-2fa-password, but still there is a mistake, TDesktop passes 'new_algo' everytime\r\n const newAlgo = state.new_algo as PasswordKdfAlgo.passwordKdfAlgoSHA256SHA256PBKDF2HMACSHA512iter100000SHA256ModPow;\r\n const salt1 = new Uint8Array(newAlgo.salt1.length + 32);\r\n salt1.randomize();\r\n salt1.set(newAlgo.salt1, 0);\r\n newAlgo.salt1 = salt1;\r\n \r\n if(settings.newPassword) {\r\n newHashPromise = apiManager.computeSRP(settings.newPassword, state, true) as any;\r\n } else {\r\n newHashPromise = Promise.resolve(new Uint8Array());\r\n }\r\n \r\n return Promise.all([currentHashPromise, newHashPromise]).then((hashes) => {\r\n params.password = hashes[0];\r\n params.new_settings.new_algo = newAlgo;\r\n params.new_settings.new_password_hash = hashes[1];\r\n \r\n return apiManager.invokeApi('account.updatePasswordSettings', params);\r\n });\r\n });\r\n }\r\n\r\n public check(password: string, state: AccountPassword, options: any = {}) {\r\n return apiManager.computeSRP(password, state).then((inputCheckPassword) => {\r\n //console.log('SRP', inputCheckPassword);\r\n return apiManager.invokeApi('auth.checkPassword', {\r\n password: inputCheckPassword\r\n }, options).then(auth => {\r\n if(auth._ === 'auth.authorization') {\r\n appUsersManager.saveApiUser(auth.user);\r\n apiManager.setUserAuth(auth.user.id);\r\n }\r\n\r\n return auth;\r\n });\r\n });\r\n }\r\n\r\n public confirmPasswordEmail(code: string) {\r\n return apiManager.invokeApi('account.confirmPasswordEmail', {code});\r\n }\r\n\r\n public resendPasswordEmail() {\r\n return apiManager.invokeApi('account.resendPasswordEmail');\r\n }\r\n\r\n public cancelPasswordEmail() {\r\n return apiManager.invokeApi('account.cancelPasswordEmail');\r\n }\r\n\r\n /* public requestRecovery(options: any = {}) {\r\n return apiManager.invokeApi('auth.requestPasswordRecovery', {}, options);\r\n }\r\n\r\n public recover(code: any, options: any = {}) {\r\n return apiManager.invokeApi('auth.recoverPassword', {\r\n code\r\n }, options);\r\n } */\r\n}\r\n\r\nconst passwordManager = new PasswordManager();\r\nMOUNT_CLASS_TO.passwordManager = passwordManager;\r\nexport default passwordManager;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { LangPackKey, i18n } from \"../lib/langPack\";\r\n\r\nexport default class LoginPage {\r\n public element: HTMLElement;\r\n public container: HTMLElement;\r\n public imageDiv: HTMLElement;\r\n public inputWrapper: HTMLElement;\r\n public title: HTMLElement;\r\n public subtitle: HTMLParagraphElement;\r\n\r\n constructor(options: {\r\n className: string,\r\n withInputWrapper?: boolean,\r\n titleLangKey?: LangPackKey,\r\n subtitleLangKey?: LangPackKey,\r\n }) {\r\n this.element = document.body.querySelector('.' + options.className) as HTMLDivElement;\r\n //this.element = document.createElement('div');\r\n //this.element.className = 'page-' + options.className;\r\n\r\n this.container = document.createElement('div');\r\n this.container.className = 'container center-align';\r\n\r\n this.imageDiv = document.createElement('div');\r\n this.imageDiv.className = 'auth-image';\r\n\r\n this.title = document.createElement('h4');\r\n if(options.titleLangKey) {\r\n this.title.append(i18n(options.titleLangKey));\r\n }\r\n\r\n this.subtitle = document.createElement('p');\r\n this.subtitle.className = 'subtitle';\r\n if(options.subtitleLangKey) {\r\n this.subtitle.append(i18n(options.subtitleLangKey));\r\n }\r\n \r\n this.container.append(this.imageDiv, this.title, this.subtitle);\r\n\r\n if(options.withInputWrapper) {\r\n this.inputWrapper = document.createElement('div');\r\n this.inputWrapper.className = 'input-wrapper';\r\n this.container.append(this.inputWrapper);\r\n }\r\n\r\n this.element.append(this.container);\r\n }\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n * \r\n * Originally from:\r\n * https://github.com/zhukov/webogram\r\n * Copyright (C) 2014 Igor Zhukov <igor.beatle@gmail.com>\r\n * https://github.com/zhukov/webogram/blob/master/LICENSE\r\n */\r\n\r\nimport { makeMediaSize } from \"./mediaSizes\";\r\nimport { MOUNT_CLASS_TO } from \"../config/debug\";\r\n\r\nexport default function calcImageInBox(imageW: number, imageH: number, boxW: number, boxH: number, noZoom = true) {\r\n if(imageW < boxW && imageH < boxH && noZoom) {\r\n return makeMediaSize(imageW, imageH);\r\n }\r\n\r\n let boxedImageW = boxW;\r\n let boxedImageH = boxH;\r\n\r\n if((imageW / imageH) > (boxW / boxH)) {\r\n boxedImageH = (imageH * boxW / imageW) | 0;\r\n } else {\r\n boxedImageW = (imageW * boxH / imageH) | 0;\r\n if(boxedImageW > boxW) {\r\n boxedImageH = (boxedImageH * boxW / boxedImageW) | 0;\r\n boxedImageW = boxW;\r\n }\r\n }\r\n\r\n // if (Config.Navigator.retina) {\r\n // imageW = Math.floor(imageW / 2)\r\n // imageH = Math.floor(imageH / 2)\r\n // }\r\n\r\n if(noZoom && boxedImageW >= imageW && boxedImageH >= imageH) {\r\n boxedImageW = imageW;\r\n boxedImageH = imageH;\r\n }\r\n\r\n return makeMediaSize(boxedImageW, boxedImageH);\r\n}\r\n\r\nMOUNT_CLASS_TO.calcImageInBox = calcImageInBox;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { TransitionSlider } from \"./transition\";\r\nimport { ScrollableX } from \"./scrollable\";\r\nimport rootScope from \"../lib/rootScope\";\r\nimport { fastRaf } from \"../helpers/schedulers\";\r\nimport { FocusDirection } from \"../helpers/fastSmoothScroll\";\r\nimport findUpAsChild from \"../helpers/dom/findUpAsChild\";\r\nimport whichChild from \"../helpers/dom/whichChild\";\r\n\r\nexport function horizontalMenu(tabs: HTMLElement, content: HTMLElement, onClick?: (id: number, tabContent: HTMLDivElement, animate: boolean) => void | boolean, onTransitionEnd?: () => void, transitionTime = 250, scrollableX?: ScrollableX) {\r\n const selectTab = TransitionSlider(content, tabs || content.dataset.animation === 'tabs' ? 'tabs' : 'navigation', transitionTime, onTransitionEnd);\r\n\r\n if(tabs) {\r\n const proxy = new Proxy(selectTab, {\r\n apply: (target, that, args) => {\r\n const id = +args[0];\r\n const animate = args[1] !== undefined ? args[1] : true;\r\n \r\n const el = (tabs.querySelector(`[data-tab=\"${id}\"]`) || tabs.children[id]) as HTMLElement;\r\n selectTarget(el, id, animate);\r\n }\r\n });\r\n\r\n const selectTarget = (target: HTMLElement, id: number, animate = true) => {\r\n const tabContent = content.children[id] as HTMLDivElement;\r\n\r\n if(onClick) {\r\n const canChange = onClick(id, tabContent, animate);\r\n if(canChange !== undefined && !canChange) {\r\n return;\r\n }\r\n }\r\n\r\n if(scrollableX) {\r\n scrollableX.scrollIntoViewNew(target.parentElement.children[id] as HTMLElement, 'center', undefined, undefined, animate ? undefined : FocusDirection.Static, transitionTime, 'x');\r\n }\r\n\r\n if(!rootScope.settings.animationsEnabled) {\r\n animate = false;\r\n }\r\n\r\n const prevId = selectTab.prevId();\r\n if(target.classList.contains('active') || id === prevId) {\r\n return false;\r\n }\r\n \r\n const prev = tabs.querySelector(tagName.toLowerCase() + '.active') as HTMLElement;\r\n\r\n fastRaf(() => {\r\n prev && prev.classList.remove('active');\r\n });\r\n \r\n // stripe from ZINCHUK\r\n if(useStripe && prevId !== -1 && animate) {\r\n fastRaf(() => {\r\n const indicator = target.querySelector('i')!;\r\n const currentIndicator = target.parentElement.children[prevId].querySelector('i')!;\r\n \r\n currentIndicator.classList.remove('animate');\r\n indicator.classList.remove('animate');\r\n \r\n // We move and resize our indicator so it repeats the position and size of the previous one.\r\n const shiftLeft = currentIndicator.parentElement.parentElement.offsetLeft - indicator.parentElement.parentElement.offsetLeft;\r\n const scaleFactor = currentIndicator.clientWidth / indicator.clientWidth;\r\n indicator.style.transform = `translate3d(${shiftLeft}px, 0, 0) scale3d(${scaleFactor}, 1, 1)`;\r\n \r\n //console.log(`translate3d(${shiftLeft}px, 0, 0) scale3d(${scaleFactor}, 1, 1)`);\r\n \r\n requestAnimationFrame(() => {\r\n // Now we remove the transform to let it animate to its own position and size.\r\n indicator.classList.add('animate');\r\n indicator.style.transform = 'none';\r\n });\r\n });\r\n }\r\n // stripe END\r\n\r\n fastRaf(() => {\r\n target.classList.add('active');\r\n });\r\n \r\n selectTab(id, animate);\r\n };\r\n\r\n const useStripe = !tabs.classList.contains('no-stripe');\r\n\r\n //const tagName = tabs.classList.contains('menu-horizontal-div') ? 'BUTTON' : 'LI';\r\n const tagName = tabs.firstElementChild.tagName;\r\n tabs.addEventListener('click', function(e) {\r\n let target = e.target as HTMLElement;\r\n \r\n target = findUpAsChild(target, tabs);\r\n \r\n //console.log('tabs click:', target);\r\n \r\n if(!target) return false;\r\n\r\n let id: number;\r\n if(target.dataset.tab) {\r\n id = +target.dataset.tab;\r\n if(id === -1) {\r\n return false;\r\n }\r\n } else {\r\n id = whichChild(target);\r\n }\r\n\r\n selectTarget(target, id);\r\n });\r\n\r\n return proxy;\r\n }\r\n \r\n return selectTab;\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport rootScope from \"../lib/rootScope\";\r\nimport { CancellablePromise, deferredPromise } from \"../helpers/cancellablePromise\";\r\nimport { dispatchHeavyAnimationEvent } from \"../hooks/useHeavyAnimationCheck\";\r\nimport whichChild from \"../helpers/dom/whichChild\";\r\nimport findUpClassName from \"../helpers/dom/findUpClassName\";\r\nimport { isSafari } from \"../helpers/userAgent\";\r\n\r\nfunction slideNavigation(tabContent: HTMLElement, prevTabContent: HTMLElement, toRight: boolean) {\r\n const width = prevTabContent.getBoundingClientRect().width;\r\n const elements = [tabContent, prevTabContent];\r\n if(toRight) elements.reverse();\r\n elements[0].style.filter = `brightness(80%)`;\r\n elements[0].style.transform = `translate3d(${-width * .25}px, 0, 0)`;\r\n elements[1].style.transform = `translate3d(${width}px, 0, 0)`;\r\n \r\n tabContent.classList.add('active');\r\n void tabContent.offsetWidth; // reflow\r\n\r\n tabContent.style.transform = '';\r\n tabContent.style.filter = '';\r\n\r\n return () => {\r\n prevTabContent.style.transform = prevTabContent.style.filter = '';\r\n };\r\n}\r\n\r\nfunction slideTabs(tabContent: HTMLElement, prevTabContent: HTMLElement, toRight: boolean) {\r\n // Jolly Cobra's // Workaround for scrollable content flickering during animation.\r\n const scrollableContainer = findUpClassName(tabContent, 'scrollable-y');\r\n if(scrollableContainer && scrollableContainer.style.overflowY !== 'hidden') {\r\n // const scrollBarWidth = scrollableContainer.offsetWidth - scrollableContainer.clientWidth;\r\n scrollableContainer.style.overflowY = 'hidden';\r\n // scrollableContainer.style.paddingRight = `${scrollBarWidth}px`;\r\n // this.container.classList.add('sliding');\r\n }\r\n\r\n //window.requestAnimationFrame(() => {\r\n const width = prevTabContent.getBoundingClientRect().width;\r\n /* tabContent.style.setProperty('--width', width + 'px');\r\n prevTabContent.style.setProperty('--width', width + 'px');\r\n\r\n tabContent.classList.add('active'); */\r\n //void tabContent.offsetWidth; // reflow\r\n const elements = [tabContent, prevTabContent];\r\n if(toRight) elements.reverse();\r\n elements[0].style.transform = `translate3d(${-width}px, 0, 0)`;\r\n elements[1].style.transform = `translate3d(${width}px, 0, 0)`;\r\n \r\n tabContent.classList.add('active');\r\n void tabContent.offsetWidth; // reflow\r\n \r\n tabContent.style.transform = '';\r\n //});\r\n \r\n return () => {\r\n prevTabContent.style.transform = '';\r\n\r\n if(scrollableContainer) {\r\n // Jolly Cobra's // Workaround for scrollable content flickering during animation.\r\n if(isSafari) { // ! safari doesn't respect sticky header, so it flicks when overflow is changing\r\n scrollableContainer.style.display = 'none';\r\n }\r\n\r\n scrollableContainer.style.overflowY = '';\r\n\r\n if(isSafari) {\r\n void scrollableContainer.offsetLeft; // reflow\r\n scrollableContainer.style.display = '';\r\n }\r\n\r\n // scrollableContainer.style.paddingRight = '0';\r\n // this.container.classList.remove('sliding');\r\n }\r\n };\r\n}\r\n\r\nexport const TransitionSlider = (content: HTMLElement, type: 'tabs' | 'navigation' | 'zoom-fade' | 'slide-fade' | 'none'/* | 'counter' */, transitionTime: number, onTransitionEnd?: (id: number) => void, isHeavy = true) => {\r\n let animationFunction: TransitionFunction = null;\r\n\r\n switch(type) {\r\n case 'tabs':\r\n animationFunction = slideTabs;\r\n break;\r\n case 'navigation':\r\n animationFunction = slideNavigation;\r\n break;\r\n /* default:\r\n break; */\r\n }\r\n\r\n content.dataset.animation = type;\r\n \r\n return Transition(content, animationFunction, transitionTime, onTransitionEnd, isHeavy);\r\n};\r\n\r\ntype TransitionFunction = (tabContent: HTMLElement, prevTabContent: HTMLElement, toRight: boolean) => void | (() => void);\r\n\r\nconst Transition = (content: HTMLElement, animationFunction: TransitionFunction, transitionTime: number, onTransitionEnd?: (id: number) => void, isHeavy = true) => {\r\n const onTransitionEndCallbacks: Map<HTMLElement, Function> = new Map();\r\n let animationDeferred: CancellablePromise<void>;\r\n let animationStarted = 0;\r\n let from: HTMLElement = null;\r\n\r\n // TODO: check for transition type (transform, etc) using by animationFunction\r\n content.addEventListener(animationFunction ? 'transitionend' : 'animationend', (e) => {\r\n if((e.target as HTMLElement).parentElement !== content) {\r\n return;\r\n }\r\n \r\n //console.log('Transition: transitionend', /* content, */ e, selectTab.prevId, performance.now() - animationStarted);\r\n\r\n const callback = onTransitionEndCallbacks.get(e.target as HTMLElement);\r\n if(callback) callback();\r\n\r\n if(e.target !== from) {\r\n return;\r\n }\r\n\r\n if(!animationDeferred && isHeavy) return;\r\n\r\n if(animationDeferred) {\r\n animationDeferred.resolve();\r\n animationDeferred = undefined;\r\n }\r\n\r\n if(onTransitionEnd) {\r\n onTransitionEnd(selectTab.prevId());\r\n }\r\n\r\n content.classList.remove('animating', 'backwards', 'disable-hover');\r\n });\r\n\r\n function selectTab(id: number | HTMLElement, animate = true) {\r\n const self = selectTab;\r\n\r\n if(id instanceof HTMLElement) {\r\n id = whichChild(id);\r\n }\r\n \r\n const prevId = self.prevId();\r\n if(id === prevId) return false;\r\n\r\n //console.log('selectTab id:', id);\r\n\r\n const _from = from;\r\n const to = content.children[id] as HTMLElement;\r\n\r\n if(!rootScope.settings.animationsEnabled || prevId === -1) {\r\n animate = false;\r\n }\r\n\r\n if(!animate) {\r\n if(_from) _from.classList.remove('active', 'to', 'from'); \r\n if(to) {\r\n to.classList.remove('to', 'from');\r\n to.classList.add('active');\r\n }\r\n\r\n content.classList.remove('animating', 'backwards', 'disable-hover');\r\n\r\n from = to;\r\n\r\n if(onTransitionEnd) onTransitionEnd(id);\r\n return;\r\n }\r\n\r\n if(from) {\r\n from.classList.remove('to');\r\n from.classList.add('from');\r\n }\r\n\r\n content.classList.add('animating', 'disable-hover');\r\n const toRight = prevId < id;\r\n content.classList.toggle('backwards', !toRight);\r\n\r\n let onTransitionEndCallback: ReturnType<TransitionFunction>;\r\n if(!to) {\r\n //prevTabContent.classList.remove('active');\r\n } else {\r\n if(animationFunction) {\r\n onTransitionEndCallback = animationFunction(to, from, toRight);\r\n } else {\r\n to.classList.add('active');\r\n }\r\n\r\n to.classList.remove('from');\r\n to.classList.add('to');\r\n }\r\n \r\n if(to) {\r\n onTransitionEndCallbacks.set(to, () => {\r\n to.classList.remove('to');\r\n onTransitionEndCallbacks.delete(to);\r\n });\r\n }\r\n\r\n if(_from/* && false */) {\r\n const callback = () => {\r\n _from.classList.remove('active', 'from');\r\n\r\n if(onTransitionEndCallback) {\r\n onTransitionEndCallback();\r\n }\r\n\r\n onTransitionEndCallbacks.delete(_from);\r\n };\r\n\r\n if(to) {\r\n onTransitionEndCallbacks.set(_from, callback);\r\n } else {\r\n const timeout = window.setTimeout(callback, transitionTime);\r\n onTransitionEndCallbacks.set(_from, () => {\r\n clearTimeout(timeout);\r\n });\r\n }\r\n\r\n if(isHeavy) {\r\n if(!animationDeferred) {\r\n animationDeferred = deferredPromise<void>();\r\n animationStarted = performance.now();\r\n }\r\n \r\n dispatchHeavyAnimationEvent(animationDeferred, transitionTime * 2);\r\n }\r\n }\r\n \r\n from = to;\r\n }\r\n\r\n //selectTab.prevId = -1;\r\n selectTab.prevId = () => from ? whichChild(from) : -1;\r\n \r\n return selectTab;\r\n};\r\n\r\nexport default Transition;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\n// * Jolly Cobra's animation.ts\r\n\r\nimport { fastRaf } from './schedulers';\r\nimport { CancellablePromise, deferredPromise } from './cancellablePromise';\r\n\r\ninterface AnimationInstance {\r\n isCancelled: boolean;\r\n deferred: CancellablePromise<void>\r\n}\r\n\r\ntype AnimationInstanceKey = any;\r\nconst instances: Map<AnimationInstanceKey, AnimationInstance> = new Map();\r\n\r\nexport function createAnimationInstance(key: AnimationInstanceKey) {\r\n cancelAnimationByKey(key);\r\n\r\n const instance: AnimationInstance = {\r\n isCancelled: false, \r\n deferred: deferredPromise<void>()\r\n };\r\n\r\n instances.set(key, instance);\r\n instance.deferred.then(() => {\r\n instances.delete(key);\r\n });\r\n\r\n return instance;\r\n}\r\n\r\nexport function getAnimationInstance(key: AnimationInstanceKey) {\r\n return instances.get(key);\r\n}\r\n\r\nexport function cancelAnimationByKey(key: AnimationInstanceKey) {\r\n const instance = getAnimationInstance(key);\r\n if(instance) {\r\n instance.isCancelled = true;\r\n instance.deferred.resolve();\r\n }\r\n}\r\n\r\nexport function animateSingle(tick: Function, key: AnimationInstanceKey, instance?: AnimationInstance) {\r\n if(!instance) {\r\n instance = createAnimationInstance(key);\r\n }\r\n\r\n fastRaf(() => {\r\n if(instance.isCancelled) {\r\n return;\r\n }\r\n \r\n if(tick()) {\r\n animateSingle(tick, key, instance);\r\n } else {\r\n instance.deferred.resolve();\r\n }\r\n });\r\n\r\n return instance.deferred;\r\n}\r\n\r\nexport function animate(tick: Function) {\r\n fastRaf(() => {\r\n if(tick()) {\r\n animate(tick);\r\n }\r\n });\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { cancelEvent } from \"../helpers/dom/cancelEvent\";\r\nimport InputField, { InputFieldOptions } from \"./inputField\";\r\n\r\nexport default class PasswordInputField extends InputField {\r\n public passwordVisible = false;\r\n public toggleVisible: HTMLElement;\r\n public onVisibilityClickAdditional: () => void;\r\n\r\n constructor(options: InputFieldOptions = {}) {\r\n super({\r\n plainText: true,\r\n ...options\r\n });\r\n\r\n const input = this.input as HTMLInputElement;\r\n input.type = 'password';\r\n input.setAttribute('required', '');\r\n input.autocomplete = 'off';\r\n /* input.readOnly = true;\r\n\r\n input.addEventListener('focus', () => {\r\n input.removeAttribute('readonly');\r\n }, {once: true}); */\r\n\r\n // * https://stackoverflow.com/a/35949954/6758968\r\n const stealthy = document.createElement('input');\r\n stealthy.classList.add('stealthy');\r\n stealthy.tabIndex = -1;\r\n stealthy.type = 'password';\r\n input.parentElement.prepend(stealthy);\r\n input.parentElement.insertBefore(stealthy.cloneNode(), input.nextSibling);\r\n\r\n const toggleVisible = this.toggleVisible = document.createElement('span');\r\n toggleVisible.classList.add('toggle-visible', 'tgico');\r\n\r\n this.container.classList.add('input-field-password');\r\n this.container.append(toggleVisible);\r\n\r\n toggleVisible.addEventListener('click', this.onVisibilityClick);\r\n toggleVisible.addEventListener('touchend', this.onVisibilityClick);\r\n }\r\n\r\n public onVisibilityClick = (e: Event) => {\r\n cancelEvent(e);\r\n this.passwordVisible = !this.passwordVisible;\r\n\r\n this.toggleVisible.classList.toggle('eye-hidden', this.passwordVisible);\r\n (this.input as HTMLInputElement).type = this.passwordVisible ? 'text' : 'password';\r\n this.onVisibilityClickAdditional && this.onVisibilityClickAdditional();\r\n };\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nexport default function findUpAsChild(el: any, parent: any) {\r\n if(el.parentElement === parent) return el;\r\n \r\n while(el.parentElement) {\r\n el = el.parentElement;\r\n if(el.parentElement === parent) {\r\n return el;\r\n }\r\n }\r\n\r\n return null;\r\n}\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport { putPreloader } from '../components/misc';\r\nimport mediaSizes from '../helpers/mediaSizes';\r\nimport { AccountPassword } from '../layer';\r\nimport appStateManager from '../lib/appManagers/appStateManager';\r\nimport passwordManager from '../lib/mtproto/passwordManager';\r\nimport Page from './page';\r\nimport pageIm from './pageIm';\r\nimport Button from '../components/button';\r\nimport PasswordInputField from '../components/passwordInputField';\r\nimport PasswordMonkey from '../components/monkeys/password';\r\nimport RichTextProcessor from '../lib/richtextprocessor';\r\nimport I18n from '../lib/langPack';\r\nimport LoginPage from './loginPage';\r\nimport { cancelEvent } from '../helpers/dom/cancelEvent';\r\nimport { attachClickEvent } from '../helpers/dom/clickEvent';\r\nimport htmlToSpan from '../helpers/dom/htmlToSpan';\r\nimport replaceContent from '../helpers/dom/replaceContent';\r\nimport toggleDisability from '../helpers/dom/toggleDisability';\r\n\r\nconst TEST = false;\r\nlet passwordInput: HTMLInputElement;\r\n\r\nlet onFirstMount = (): Promise<any> => {\r\n const page = new LoginPage({\r\n className: 'page-password',\r\n withInputWrapper: true,\r\n titleLangKey: 'Login.Password.Title',\r\n subtitleLangKey: 'Login.Password.Subtitle'\r\n });\r\n\r\n const btnNext = Button('btn-primary btn-color-primary');\r\n const btnNextI18n = new I18n.IntlElement({key: 'Login.Next'});\r\n\r\n btnNext.append(btnNextI18n.element);\r\n\r\n const passwordInputField = new PasswordInputField({\r\n label: 'LoginPassword',\r\n name: 'password'\r\n });\r\n\r\n passwordInput = passwordInputField.input as HTMLInputElement;\r\n\r\n page.inputWrapper.append(passwordInputField.container, btnNext);\r\n\r\n let getStateInterval: number;\r\n\r\n let getState = () => {\r\n // * just to check session relevance\r\n if(!getStateInterval) {\r\n getStateInterval = window.setInterval(getState, 10e3);\r\n }\r\n\r\n return !TEST && passwordManager.getState().then(_state => {\r\n state = _state;\r\n\r\n if(state.hint) {\r\n replaceContent(passwordInputField.label, htmlToSpan(RichTextProcessor.wrapEmojiText(state.hint)));\r\n } else {\r\n passwordInputField.setLabel();\r\n }\r\n });\r\n };\r\n\r\n let state: AccountPassword;\r\n \r\n const onSubmit = (e?: Event) => {\r\n if(e) {\r\n cancelEvent(e);\r\n }\r\n\r\n if(!passwordInput.value.length) {\r\n passwordInput.classList.add('error');\r\n return;\r\n }\r\n\r\n const toggle = toggleDisability([passwordInput, btnNext], true);\r\n let value = passwordInput.value;\r\n\r\n btnNextI18n.update({key: 'PleaseWait'});\r\n const preloader = putPreloader(btnNext);\r\n\r\n passwordManager.check(value, state).then((response) => {\r\n //console.log('passwordManager response:', response);\r\n \r\n switch(response._) {\r\n case 'auth.authorization':\r\n clearInterval(getStateInterval);\r\n pageIm.mount();\r\n if(monkey) monkey.remove();\r\n break;\r\n default:\r\n btnNext.removeAttribute('disabled');\r\n btnNextI18n.update({key: response._ as any});\r\n preloader.remove();\r\n break;\r\n }\r\n }).catch((err: any) => {\r\n toggle();\r\n passwordInputField.input.classList.add('error');\r\n \r\n switch(err.type) {\r\n default:\r\n //btnNext.innerText = err.type;\r\n btnNextI18n.update({key: 'PASSWORD_HASH_INVALID'});\r\n passwordInput.select();\r\n break;\r\n }\r\n\r\n preloader.remove();\r\n \r\n getState();\r\n });\r\n };\r\n \r\n attachClickEvent(btnNext, onSubmit);\r\n\r\n passwordInput.addEventListener('keypress', function(this, e) {\r\n this.classList.remove('error');\r\n btnNextI18n.update({key: 'Login.Next'});\r\n\r\n if(e.key === 'Enter') {\r\n return onSubmit();\r\n }\r\n });\r\n\r\n const size = mediaSizes.isMobile ? 100 : 166;\r\n const monkey = new PasswordMonkey(passwordInputField, size);\r\n page.imageDiv.append(monkey.container);\r\n return Promise.all([\r\n monkey.load(),\r\n getState()\r\n ]);\r\n};\r\n\r\nconst page = new Page('page-password', true, onFirstMount, null, () => {\r\n //if(!isAppleMobile) {\r\n passwordInput.focus();\r\n //}\r\n\r\n appStateManager.pushToState('authState', {_: 'authStatePassword'});\r\n});\r\n\r\nexport default page;\r\n","/*\r\n * https://github.com/morethanwords/tweb\r\n * Copyright (C) 2019-2021 Eduard Kuzmenko\r\n * https://github.com/morethanwords/tweb/blob/master/LICENSE\r\n */\r\n\r\nimport lottieLoader, { RLottiePlayer } from \"../../lib/lottieLoader\";\r\nimport PasswordInputField from \"../passwordInputField\";\r\n\r\nexport default class PasswordMonkey {\r\n public container: HTMLElement;\r\n public animation: RLottiePlayer;\r\n public needFrame = 0;\r\n protected loadPromise: Promise<void>;\r\n\r\n constructor(protected passwordInputField: PasswordInputField, protected size: number) {\r\n this.container = document.createElement('div');\r\n this.container.classList.add('media-sticker-wrapper');\r\n }\r\n\r\n public load() {\r\n if(this.loadPromise) return this.loadPromise;\r\n return this.loadPromise = lottieLoader.loadAnimationFromURL({\r\n container: this.container,\r\n loop: false,\r\n autoplay: false,\r\n width: this.size,\r\n height: this.size,\r\n noCache: true\r\n //}, 'assets/img/TwoFactorSetupMonkeyClose.tgs').then(_animation => {\r\n }, 'assets/img/TwoFactorSetupMonkeyPeek.tgs').then(_animation => {\r\n //return;\r\n this.animation = _animation;\r\n this.animation.addEventListener('enterFrame', currentFrame => {\r\n //console.log('enterFrame', currentFrame, this.needFrame);\r\n\r\n if((this.animation.direction === 1 && currentFrame >= this.needFrame) ||\r\n (this.animation.direction === -1 && currentFrame <= this.needFrame)) {\r\n this.animation.setSpeed(1);\r\n this.animation.pause();\r\n } \r\n });\r\n\r\n this.passwordInputField.onVisibilityClickAdditional = () => {\r\n if(this.passwordInputField.passwordVisible) {\r\n this.animation.setDirection(1);\r\n this.animation.curFrame = 0;\r\n this.needFrame = 16;\r\n this.animation.play();\r\n } else {\r\n this.animation.setDirection(-1);\r\n this.animation.curFrame = 16;\r\n this.needFrame = 0;\r\n this.animation.play();\r\n }\r\n };\r\n\r\n return lottieLoader.waitForFirstFrame(_animation);\r\n });\r\n }\r\n\r\n public remove() {\r\n if(this.animation) {\r\n this.animation.remove();\r\n }\r\n }\r\n}\r\n"],"sourceRoot":""} |