Recent Stickers: Limit amount (#1167)
This commit is contained in:
parent
eee06bdd03
commit
6cd13db35f
@ -68,6 +68,7 @@ export async function init(_onUpdate: OnApiUpdate, sessionData?: ApiSessionData)
|
|||||||
firstAndLastNames: onRequestRegistration,
|
firstAndLastNames: onRequestRegistration,
|
||||||
qrCode: onRequestQrCode,
|
qrCode: onRequestQrCode,
|
||||||
onError: onAuthError,
|
onError: onAuthError,
|
||||||
|
initialMethod: 'qrCode',
|
||||||
});
|
});
|
||||||
|
|
||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
|
|||||||
@ -5,6 +5,7 @@ import { invokeRequest } from './client';
|
|||||||
import { buildStickerFromDocument, buildStickerSet, buildStickerSetCovered } from '../apiBuilders/symbols';
|
import { buildStickerFromDocument, buildStickerSet, buildStickerSetCovered } from '../apiBuilders/symbols';
|
||||||
import { buildInputStickerSet, buildInputDocument } from '../gramjsBuilders';
|
import { buildInputStickerSet, buildInputDocument } from '../gramjsBuilders';
|
||||||
import { buildVideoFromDocument } from '../apiBuilders/messages';
|
import { buildVideoFromDocument } from '../apiBuilders/messages';
|
||||||
|
import { RECENT_STICKERS_LIMIT } from '../../../config';
|
||||||
|
|
||||||
import localDb from '../localDb';
|
import localDb from '../localDb';
|
||||||
|
|
||||||
@ -42,7 +43,7 @@ export async function fetchRecentStickers({ hash }: { hash: number }) {
|
|||||||
|
|
||||||
return {
|
return {
|
||||||
hash: result.hash,
|
hash: result.hash,
|
||||||
stickers: processStickerResult(result.stickers),
|
stickers: processStickerResult(result.stickers.slice(0, RECENT_STICKERS_LIMIT)),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -1,4 +1,3 @@
|
|||||||
export { default as AuthCode } from '../components/auth/AuthCode';
|
export { default as AuthCode } from '../components/auth/AuthCode';
|
||||||
export { default as AuthPassword } from '../components/auth/AuthPassword';
|
export { default as AuthPassword } from '../components/auth/AuthPassword';
|
||||||
export { default as AuthRegister } from '../components/auth/AuthRegister';
|
export { default as AuthRegister } from '../components/auth/AuthRegister';
|
||||||
export { default as AuthQrCode } from '../components/auth/AuthQrCode';
|
|
||||||
|
|||||||
@ -9,6 +9,10 @@
|
|||||||
@media (min-width: 600px) and (min-height: 450px) {
|
@media (min-width: 600px) and (min-height: 450px) {
|
||||||
padding: 1.5rem;
|
padding: 1.5rem;
|
||||||
padding-top: 6.8rem;
|
padding-top: 6.8rem;
|
||||||
|
|
||||||
|
&.qr {
|
||||||
|
padding-top: 5rem;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#logo, .AvatarEditable label {
|
#logo, .AvatarEditable label {
|
||||||
@ -104,12 +108,14 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
#auth-qr-form {
|
#auth-qr-form {
|
||||||
.qr-container {
|
.qr-container, .qr-loading {
|
||||||
height: 280px;
|
height: 280px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.qr-container {
|
||||||
opacity: 1;
|
opacity: 1;
|
||||||
transform: scale(1);
|
transform: scale(1);
|
||||||
transition: transform .3s cubic-bezier(0.34, 1.56, 0.64, 1), opacity .3s;
|
transition: transform 300ms cubic-bezier(0.34, 1.56, 0.64, 1), opacity 300ms;
|
||||||
|
|
||||||
&.pre-animate {
|
&.pre-animate {
|
||||||
opacity: 0.5;
|
opacity: 0.5;
|
||||||
|
|||||||
@ -11,7 +11,7 @@ import AuthPhoneNumber from './AuthPhoneNumber';
|
|||||||
import AuthCode from './AuthCode.async';
|
import AuthCode from './AuthCode.async';
|
||||||
import AuthPassword from './AuthPassword.async';
|
import AuthPassword from './AuthPassword.async';
|
||||||
import AuthRegister from './AuthRegister.async';
|
import AuthRegister from './AuthRegister.async';
|
||||||
import AuthQrCode from './AuthQrCode.async';
|
import AuthQrCode from './AuthQrCode';
|
||||||
|
|
||||||
import './Auth.scss';
|
import './Auth.scss';
|
||||||
|
|
||||||
@ -24,9 +24,6 @@ const Auth: FC<StateProps & DispatchProps> = ({ authState, reset, initApi }) =>
|
|||||||
initApi();
|
initApi();
|
||||||
}, [reset, initApi]);
|
}, [reset, initApi]);
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
switch (authState) {
|
switch (authState) {
|
||||||
case 'authorizationStateWaitCode':
|
case 'authorizationStateWaitCode':
|
||||||
return <UiLoader page="authCode" key="authCode"><AuthCode /></UiLoader>;
|
return <UiLoader page="authCode" key="authCode"><AuthCode /></UiLoader>;
|
||||||
@ -34,11 +31,11 @@ const Auth: FC<StateProps & DispatchProps> = ({ authState, reset, initApi }) =>
|
|||||||
return <UiLoader page="authPassword" key="authPassword"><AuthPassword /></UiLoader>;
|
return <UiLoader page="authPassword" key="authPassword"><AuthPassword /></UiLoader>;
|
||||||
case 'authorizationStateWaitRegistration':
|
case 'authorizationStateWaitRegistration':
|
||||||
return <AuthRegister />;
|
return <AuthRegister />;
|
||||||
case 'authorizationStateWaitQrCode':
|
|
||||||
return <UiLoader page="authQrCode" key="authQrCode"><AuthQrCode /></UiLoader>;
|
|
||||||
case 'authorizationStateWaitPhoneNumber':
|
case 'authorizationStateWaitPhoneNumber':
|
||||||
default:
|
|
||||||
return <UiLoader page="authPhoneNumber" key="authPhoneNumber"><AuthPhoneNumber /></UiLoader>;
|
return <UiLoader page="authPhoneNumber" key="authPhoneNumber"><AuthPhoneNumber /></UiLoader>;
|
||||||
|
case 'authorizationStateWaitQrCode':
|
||||||
|
default:
|
||||||
|
return <UiLoader page="authQrCode" key="authQrCode"><AuthQrCode /></UiLoader>;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@ -25,7 +25,7 @@ type StateProps = Pick<GlobalState, (
|
|||||||
'authPhoneNumber' | 'authIsLoading' | 'authIsLoadingQrCode' | 'authError' | 'authRememberMe' | 'authNearestCountry'
|
'authPhoneNumber' | 'authIsLoading' | 'authIsLoadingQrCode' | 'authError' | 'authRememberMe' | 'authNearestCountry'
|
||||||
)>;
|
)>;
|
||||||
type DispatchProps = Pick<GlobalActions, (
|
type DispatchProps = Pick<GlobalActions, (
|
||||||
'setAuthPhoneNumber' | 'setAuthRememberMe' | 'loadNearestCountry' | 'clearAuthError' | 'gotToAuthQrCode'
|
'setAuthPhoneNumber' | 'setAuthRememberMe' | 'loadNearestCountry' | 'clearAuthError' | 'goToAuthQrCode'
|
||||||
)>;
|
)>;
|
||||||
|
|
||||||
const MIN_NUMBER_LENGTH = 7;
|
const MIN_NUMBER_LENGTH = 7;
|
||||||
@ -45,7 +45,7 @@ const AuthPhoneNumber: FC<StateProps & DispatchProps> = ({
|
|||||||
setAuthRememberMe,
|
setAuthRememberMe,
|
||||||
loadNearestCountry,
|
loadNearestCountry,
|
||||||
clearAuthError,
|
clearAuthError,
|
||||||
gotToAuthQrCode,
|
goToAuthQrCode,
|
||||||
}) => {
|
}) => {
|
||||||
// eslint-disable-next-line no-null/no-null
|
// eslint-disable-next-line no-null/no-null
|
||||||
const inputRef = useRef<HTMLInputElement>(null);
|
const inputRef = useRef<HTMLInputElement>(null);
|
||||||
@ -183,7 +183,7 @@ const AuthPhoneNumber: FC<StateProps & DispatchProps> = ({
|
|||||||
)
|
)
|
||||||
)}
|
)}
|
||||||
{isAuthReady && (
|
{isAuthReady && (
|
||||||
<Button isText ripple isLoading={authIsLoadingQrCode} onClick={gotToAuthQrCode}>
|
<Button isText ripple isLoading={authIsLoadingQrCode} onClick={goToAuthQrCode}>
|
||||||
Log in by QR code
|
Log in by QR code
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
@ -209,6 +209,6 @@ export default memo(withGlobal(
|
|||||||
'setAuthRememberMe',
|
'setAuthRememberMe',
|
||||||
'clearAuthError',
|
'clearAuthError',
|
||||||
'loadNearestCountry',
|
'loadNearestCountry',
|
||||||
'gotToAuthQrCode',
|
'goToAuthQrCode',
|
||||||
]),
|
]),
|
||||||
)(AuthPhoneNumber));
|
)(AuthPhoneNumber));
|
||||||
|
|||||||
@ -1,13 +0,0 @@
|
|||||||
import React, { FC, memo } from '../../lib/teact/teact';
|
|
||||||
import { Bundles } from '../../util/moduleLoader';
|
|
||||||
|
|
||||||
import useModuleLoader from '../../hooks/useModuleLoader';
|
|
||||||
import Loading from '../ui/Loading';
|
|
||||||
|
|
||||||
const AuthQrCodeAsync: FC = () => {
|
|
||||||
const AuthQrCode = useModuleLoader(Bundles.Auth, 'AuthQrCode');
|
|
||||||
|
|
||||||
return AuthQrCode ? <AuthQrCode /> : <Loading />;
|
|
||||||
};
|
|
||||||
|
|
||||||
export default memo(AuthQrCodeAsync);
|
|
||||||
@ -9,7 +9,6 @@ import { pick } from '../../util/iteratees';
|
|||||||
|
|
||||||
import Loading from '../ui/Loading';
|
import Loading from '../ui/Loading';
|
||||||
import Button from '../ui/Button';
|
import Button from '../ui/Button';
|
||||||
import buildClassName from '../../util/buildClassName';
|
|
||||||
import useHistoryBack from '../../hooks/useHistoryBack';
|
import useHistoryBack from '../../hooks/useHistoryBack';
|
||||||
|
|
||||||
type StateProps = Pick<GlobalState, 'connectionState' | 'authQrCode'>;
|
type StateProps = Pick<GlobalState, 'connectionState' | 'authQrCode'>;
|
||||||
@ -32,6 +31,7 @@ const AuthCode: FC<StateProps & DispatchProps> = ({
|
|||||||
|
|
||||||
container.innerHTML = '';
|
container.innerHTML = '';
|
||||||
container.classList.remove('pre-animate');
|
container.classList.remove('pre-animate');
|
||||||
|
|
||||||
QrCreator.render({
|
QrCreator.render({
|
||||||
text: `${DATA_PREFIX}${authQrCode.token}`,
|
text: `${DATA_PREFIX}${authQrCode.token}`,
|
||||||
radius: 0.5,
|
radius: 0.5,
|
||||||
@ -45,11 +45,13 @@ const AuthCode: FC<StateProps & DispatchProps> = ({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div id="auth-qr-form" className="custom-scroll">
|
<div id="auth-qr-form" className="custom-scroll">
|
||||||
<div className="auth-form">
|
<div className="auth-form qr">
|
||||||
<div className={buildClassName('qr-container', authQrCode && 'pre-animate')} ref={qrCodeRef}>
|
{authQrCode ? (
|
||||||
{!authQrCode && <Loading />}
|
<div key="qr-container" className="qr-container pre-animate" ref={qrCodeRef} />
|
||||||
</div>
|
) : (
|
||||||
<h3> Log in to Telegram by QR Code</h3>
|
<div key="qr-loading" className="qr-loading"><Loading /></div>
|
||||||
|
)}
|
||||||
|
<h3>Log in to Telegram by QR Code</h3>
|
||||||
<ol>
|
<ol>
|
||||||
<li><span>Open Telegram on your phone</span></li>
|
<li><span>Open Telegram on your phone</span></li>
|
||||||
<li><span>Go to <b>Settings</b> > <b>Devices</b> > <b>Scan QR</b></span></li>
|
<li><span>Go to <b>Settings</b> > <b>Devices</b> > <b>Scan QR</b></span></li>
|
||||||
|
|||||||
@ -54,6 +54,7 @@ import fastSmoothScroll, { isAnimatingScroll } from '../../util/fastSmoothScroll
|
|||||||
import renderText from '../common/helpers/renderText';
|
import renderText from '../common/helpers/renderText';
|
||||||
import useLang, { LangFn } from '../../hooks/useLang';
|
import useLang, { LangFn } from '../../hooks/useLang';
|
||||||
import useWindowSize from '../../hooks/useWindowSize';
|
import useWindowSize from '../../hooks/useWindowSize';
|
||||||
|
import useBackgroundMode from '../../hooks/useBackgroundMode';
|
||||||
|
|
||||||
import Loading from '../ui/Loading';
|
import Loading from '../ui/Loading';
|
||||||
import MessageScroll from './MessageScroll';
|
import MessageScroll from './MessageScroll';
|
||||||
@ -227,6 +228,8 @@ const MessageList: FC<OwnProps & StateProps & DispatchProps> = ({
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
useBackgroundMode(freezeForReading, unfreezeForReading);
|
||||||
|
|
||||||
useOnChange(() => {
|
useOnChange(() => {
|
||||||
memoFocusingIdRef.current = focusingId;
|
memoFocusingIdRef.current = focusingId;
|
||||||
|
|
||||||
|
|||||||
@ -1,7 +1,5 @@
|
|||||||
import { MutableRefObject } from 'react';
|
import { MutableRefObject } from 'react';
|
||||||
import React, {
|
import React, { FC, useCallback, useRef } from '../../lib/teact/teact';
|
||||||
FC, useCallback, useEffect, useRef,
|
|
||||||
} from '../../lib/teact/teact';
|
|
||||||
|
|
||||||
import { MESSAGE_LIST_SENSITIVE_AREA } from '../../config';
|
import { MESSAGE_LIST_SENSITIVE_AREA } from '../../config';
|
||||||
import resetScroll from '../../util/resetScroll';
|
import resetScroll from '../../util/resetScroll';
|
||||||
@ -25,9 +23,6 @@ type OwnProps = {
|
|||||||
const FAB_THRESHOLD = 50;
|
const FAB_THRESHOLD = 50;
|
||||||
const TOOLS_FREEZE_TIMEOUT = 100;
|
const TOOLS_FREEZE_TIMEOUT = 100;
|
||||||
|
|
||||||
// Local flag is used because `freeze/unfreeze` methods are controlled by heavy animation
|
|
||||||
let areToolsFrozen = false;
|
|
||||||
|
|
||||||
const MessageScroll: FC<OwnProps> = ({
|
const MessageScroll: FC<OwnProps> = ({
|
||||||
containerRef,
|
containerRef,
|
||||||
className,
|
className,
|
||||||
@ -49,10 +44,6 @@ const MessageScroll: FC<OwnProps> = ({
|
|||||||
const fabTriggerRef = useRef<HTMLDivElement>(null);
|
const fabTriggerRef = useRef<HTMLDivElement>(null);
|
||||||
|
|
||||||
const toggleScrollTools = useCallback(() => {
|
const toggleScrollTools = useCallback(() => {
|
||||||
if (areToolsFrozen) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!messageIds || !messageIds.length) {
|
if (!messageIds || !messageIds.length) {
|
||||||
onFabToggle(false);
|
onFabToggle(false);
|
||||||
onNotchToggle(false);
|
onNotchToggle(false);
|
||||||
@ -118,35 +109,33 @@ const MessageScroll: FC<OwnProps> = ({
|
|||||||
|
|
||||||
const {
|
const {
|
||||||
observe: observeIntersectionForNotch,
|
observe: observeIntersectionForNotch,
|
||||||
|
freeze: freezeForNotch,
|
||||||
|
unfreeze: unfreezeForNotch,
|
||||||
} = useIntersectionObserver({
|
} = useIntersectionObserver({
|
||||||
rootRef: containerRef,
|
rootRef: containerRef,
|
||||||
}, toggleScrollTools);
|
}, toggleScrollTools);
|
||||||
|
|
||||||
useOnIntersect(fabTriggerRef, observeIntersectionForNotch);
|
useOnIntersect(fabTriggerRef, observeIntersectionForNotch);
|
||||||
|
|
||||||
// Do not load more and show FAB when focusing
|
|
||||||
useOnChange(() => {
|
useOnChange(() => {
|
||||||
if (focusingId) {
|
if (focusingId) {
|
||||||
freezeForLoadMore();
|
freezeForLoadMore();
|
||||||
freezeForFab();
|
|
||||||
} else {
|
} else {
|
||||||
unfreezeForFab();
|
|
||||||
unfreezeForLoadMore();
|
unfreezeForLoadMore();
|
||||||
}
|
}
|
||||||
}, [focusingId]);
|
}, [focusingId]);
|
||||||
|
|
||||||
// Workaround for FAB and notch flickering with tall incoming message
|
// Workaround for FAB and notch flickering with tall incoming message
|
||||||
useOnChange(() => {
|
useOnChange(() => {
|
||||||
areToolsFrozen = true;
|
freezeForFab();
|
||||||
|
freezeForNotch();
|
||||||
|
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
areToolsFrozen = false;
|
unfreezeForNotch();
|
||||||
|
unfreezeForFab();
|
||||||
}, TOOLS_FREEZE_TIMEOUT);
|
}, TOOLS_FREEZE_TIMEOUT);
|
||||||
}, [messageIds]);
|
}, [messageIds]);
|
||||||
|
|
||||||
// Workaround for stuck FAB when many unread messages
|
|
||||||
useEffect(toggleScrollTools, [firstUnreadId]);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={className} teactFastList>
|
<div className={className} teactFastList>
|
||||||
<div ref={backwardsTriggerRef} key="backwards-trigger" className="backwards-trigger" />
|
<div ref={backwardsTriggerRef} key="backwards-trigger" className="backwards-trigger" />
|
||||||
|
|||||||
@ -1,11 +1,10 @@
|
|||||||
import React, { FC, useCallback, useEffect } from '../../../lib/teact/teact';
|
import React, { FC, useCallback } from '../../../lib/teact/teact';
|
||||||
|
|
||||||
import { ApiMessage } from '../../../api/types';
|
import { ApiMessage } from '../../../api/types';
|
||||||
import { IAnchorPosition } from '../../../types';
|
import { IAnchorPosition } from '../../../types';
|
||||||
|
|
||||||
import { getMessageCopyOptions } from './helpers/copyOptions';
|
import { getMessageCopyOptions } from './helpers/copyOptions';
|
||||||
import useContextMenuPosition from '../../../hooks/useContextMenuPosition';
|
import useContextMenuPosition from '../../../hooks/useContextMenuPosition';
|
||||||
import { dispatchHeavyAnimationEvent } from '../../../hooks/useHeavyAnimationCheck';
|
|
||||||
import useLang from '../../../hooks/useLang';
|
import useLang from '../../../hooks/useLang';
|
||||||
|
|
||||||
import Menu from '../../ui/Menu';
|
import Menu from '../../ui/Menu';
|
||||||
@ -46,7 +45,6 @@ type OwnProps = {
|
|||||||
onCopyLink?: () => void;
|
onCopyLink?: () => void;
|
||||||
};
|
};
|
||||||
|
|
||||||
const ANIMATION_DURATION = 200;
|
|
||||||
const SCROLLBAR_WIDTH = 10;
|
const SCROLLBAR_WIDTH = 10;
|
||||||
|
|
||||||
const MessageContextMenu: FC<OwnProps> = ({
|
const MessageContextMenu: FC<OwnProps> = ({
|
||||||
@ -81,10 +79,6 @@ const MessageContextMenu: FC<OwnProps> = ({
|
|||||||
onCloseAnimationEnd,
|
onCloseAnimationEnd,
|
||||||
onCopyLink,
|
onCopyLink,
|
||||||
}) => {
|
}) => {
|
||||||
useEffect(() => {
|
|
||||||
dispatchHeavyAnimationEvent(ANIMATION_DURATION);
|
|
||||||
}, [isOpen]);
|
|
||||||
|
|
||||||
const copyOptions = getMessageCopyOptions(message, onClose, canCopyLink ? onCopyLink : undefined);
|
const copyOptions = getMessageCopyOptions(message, onClose, canCopyLink ? onCopyLink : undefined);
|
||||||
|
|
||||||
const getTriggerElement = useCallback(() => {
|
const getTriggerElement = useCallback(() => {
|
||||||
|
|||||||
@ -104,6 +104,7 @@ export const STICKER_SIZE_MODAL = 64;
|
|||||||
export const STICKER_SIZE_TWO_FA = 160;
|
export const STICKER_SIZE_TWO_FA = 160;
|
||||||
export const STICKER_SIZE_DISCUSSION_GROUPS = 140;
|
export const STICKER_SIZE_DISCUSSION_GROUPS = 140;
|
||||||
export const STICKER_SIZE_FOLDER_SETTINGS = 80;
|
export const STICKER_SIZE_FOLDER_SETTINGS = 80;
|
||||||
|
export const RECENT_STICKERS_LIMIT = 20;
|
||||||
export const MEMOJI_STICKER_ID = 'MEMOJI_STICKER';
|
export const MEMOJI_STICKER_ID = 'MEMOJI_STICKER';
|
||||||
|
|
||||||
export const MENU_TRANSITION_DURATION = 200;
|
export const MENU_TRANSITION_DURATION = 200;
|
||||||
|
|||||||
@ -401,7 +401,7 @@ export type ActionTypes = (
|
|||||||
'toggleSafeLinkModal' | 'openHistoryCalendar' | 'closeHistoryCalendar' |
|
'toggleSafeLinkModal' | 'openHistoryCalendar' | 'closeHistoryCalendar' |
|
||||||
// auth
|
// auth
|
||||||
'setAuthPhoneNumber' | 'setAuthCode' | 'setAuthPassword' | 'signUp' | 'returnToAuthPhoneNumber' | 'signOut' |
|
'setAuthPhoneNumber' | 'setAuthCode' | 'setAuthPassword' | 'signUp' | 'returnToAuthPhoneNumber' | 'signOut' |
|
||||||
'setAuthRememberMe' | 'clearAuthError' | 'uploadProfilePhoto' | 'gotToAuthQrCode' | 'clearCache' |
|
'setAuthRememberMe' | 'clearAuthError' | 'uploadProfilePhoto' | 'goToAuthQrCode' | 'clearCache' |
|
||||||
// chats
|
// chats
|
||||||
'preloadTopChatMessages' | 'loadChats' | 'loadMoreChats' | 'openChat' | 'openChatWithInfo' |
|
'preloadTopChatMessages' | 'loadChats' | 'loadMoreChats' | 'openChat' | 'openChatWithInfo' |
|
||||||
'openSupportChat' | 'openTipsChat' |
|
'openSupportChat' | 'openTipsChat' |
|
||||||
|
|||||||
@ -7,8 +7,10 @@ let timeout: number | undefined;
|
|||||||
let isAnimating = false;
|
let isAnimating = false;
|
||||||
|
|
||||||
export const dispatchHeavyAnimationEvent = (duration: number) => {
|
export const dispatchHeavyAnimationEvent = (duration: number) => {
|
||||||
document.dispatchEvent(new Event(ANIMATION_START_EVENT));
|
if (!isAnimating) {
|
||||||
isAnimating = true;
|
isAnimating = true;
|
||||||
|
document.dispatchEvent(new Event(ANIMATION_START_EVENT));
|
||||||
|
}
|
||||||
|
|
||||||
if (timeout) {
|
if (timeout) {
|
||||||
clearTimeout(timeout);
|
clearTimeout(timeout);
|
||||||
|
|||||||
@ -41,19 +41,23 @@ export function useIntersectionObserver({
|
|||||||
}, rootCallback?: RootCallback): Response {
|
}, rootCallback?: RootCallback): Response {
|
||||||
const controllerRef = useRef<IntersectionController>();
|
const controllerRef = useRef<IntersectionController>();
|
||||||
const rootCallbackRef = useRef<RootCallback>();
|
const rootCallbackRef = useRef<RootCallback>();
|
||||||
const isFrozenRef = useRef<boolean>();
|
const freezeFlagsRef = useRef(0);
|
||||||
const onUnfreezeRef = useRef<NoneToVoidFunction>();
|
const onUnfreezeRef = useRef<NoneToVoidFunction>();
|
||||||
|
|
||||||
rootCallbackRef.current = rootCallback;
|
rootCallbackRef.current = rootCallback;
|
||||||
|
|
||||||
const freeze = useCallback(() => {
|
const freeze = useCallback(() => {
|
||||||
isFrozenRef.current = true;
|
freezeFlagsRef.current++;
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
const unfreeze = useCallback(() => {
|
const unfreeze = useCallback(() => {
|
||||||
isFrozenRef.current = false;
|
if (!freezeFlagsRef.current) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (onUnfreezeRef.current) {
|
freezeFlagsRef.current--;
|
||||||
|
|
||||||
|
if (!freezeFlagsRef.current && onUnfreezeRef.current) {
|
||||||
onUnfreezeRef.current();
|
onUnfreezeRef.current();
|
||||||
onUnfreezeRef.current = undefined;
|
onUnfreezeRef.current = undefined;
|
||||||
}
|
}
|
||||||
@ -104,7 +108,7 @@ export function useIntersectionObserver({
|
|||||||
entriesAccumulator.set(entry.target, entry);
|
entriesAccumulator.set(entry.target, entry);
|
||||||
});
|
});
|
||||||
|
|
||||||
if (isFrozenRef.current) {
|
if (freezeFlagsRef.current) {
|
||||||
onUnfreezeRef.current = () => {
|
onUnfreezeRef.current = () => {
|
||||||
observerCallback();
|
observerCallback();
|
||||||
};
|
};
|
||||||
|
|||||||
@ -13,6 +13,7 @@ export interface UserAuthParams {
|
|||||||
qrCode: (qrCode: { token: Buffer; expires: number }) => Promise<void>;
|
qrCode: (qrCode: { token: Buffer; expires: number }) => Promise<void>;
|
||||||
onError: (err: Error) => void;
|
onError: (err: Error) => void;
|
||||||
forceSMS?: boolean;
|
forceSMS?: boolean;
|
||||||
|
initialMethod?: 'phoneNumber' | 'qrCode';
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface BotAuthParams {
|
export interface BotAuthParams {
|
||||||
@ -24,6 +25,7 @@ interface ApiCredentials {
|
|||||||
apiHash: string;
|
apiHash: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const DEFAULT_INITIAL_METHOD = 'phoneNumber';
|
||||||
const QR_CODE_TIMEOUT = 30000;
|
const QR_CODE_TIMEOUT = 30000;
|
||||||
|
|
||||||
export async function authFlow(
|
export async function authFlow(
|
||||||
@ -31,11 +33,20 @@ export async function authFlow(
|
|||||||
apiCredentials: ApiCredentials,
|
apiCredentials: ApiCredentials,
|
||||||
authParams: UserAuthParams | BotAuthParams,
|
authParams: UserAuthParams | BotAuthParams,
|
||||||
) {
|
) {
|
||||||
const me = 'phoneNumber' in authParams
|
let me: Api.TypeUser;
|
||||||
? await signInUser(client, apiCredentials, authParams)
|
|
||||||
: await signInBot(client, apiCredentials, authParams);
|
if ('botAuthToken' in authParams) {
|
||||||
|
me = await signInBot(client, apiCredentials, authParams);
|
||||||
|
} else {
|
||||||
|
const { initialMethod = DEFAULT_INITIAL_METHOD } = authParams;
|
||||||
|
|
||||||
|
if (initialMethod === 'phoneNumber') {
|
||||||
|
me = await signInUser(client, apiCredentials, authParams);
|
||||||
|
} else {
|
||||||
|
me = await signInUserWithQrCode(client, apiCredentials, authParams);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// TODO @logger
|
|
||||||
client._log.info('Signed in successfully as', utils.getDisplayName(me));
|
client._log.info('Signed in successfully as', utils.getDisplayName(me));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -101,7 +101,7 @@ addReducer('returnToAuthPhoneNumber', (global) => {
|
|||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
addReducer('gotToAuthQrCode', (global) => {
|
addReducer('goToAuthQrCode', (global) => {
|
||||||
void callApi('restartAuthWithQr');
|
void callApi('restartAuthWithQr');
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user