From 5a6769b613bda0e1681188f70b7b6476462fde34 Mon Sep 17 00:00:00 2001 From: Frenkie Nguyen Date: Mon, 16 Dec 2024 19:22:10 +0700 Subject: [PATCH 1/4] [Issue-161][Mythical Telegram App] Update loading animation for some screens (Leaderboard Screen) --- .../src/Popup/Home/LeaderboardTemp/index.tsx | 143 ++++++++++++++---- .../Mythical/Leaderboard/TopAccountItem.tsx | 66 ++++++-- 2 files changed, 163 insertions(+), 46 deletions(-) diff --git a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx index 1da7bef9f1..701962d415 100644 --- a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx +++ b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx @@ -12,7 +12,7 @@ import { TERM_AND_CONDITION_MODAL_ID, TermAndConditionModal } from '@subwallet/e import { TopThreeArea } from '@subwallet/extension-koni-ui/Popup/Home/LeaderboardTemp/TopThreeArea'; import { ThemeProps } from '@subwallet/extension-koni-ui/types'; import { openInNewTab } from '@subwallet/extension-koni-ui/utils'; -import { ModalContext } from '@subwallet/react-ui'; +import { ModalContext, Skeleton } from '@subwallet/react-ui'; import React, { useCallback, useContext, useEffect, useState } from 'react'; import { useTranslation } from 'react-i18next'; import styled from 'styled-components'; @@ -108,24 +108,47 @@ const Component = ({ className }: Props): React.ReactElement => { return (
- - - - ) - } - title={currentLeaderboardInfo?.name || t('Leaderboard')} - /> - - {leaderboardInfo?.endTimeTs && leaderboardInfo?.specialTime &&
- -
} + {isLoading + ? ( +
+ +
+ ) + : ( + + + + ) + } + title={currentLeaderboardInfo?.name || t('Leaderboard')} + /> + ) } + + {leaderboardInfo?.endTimeTs && leaderboardInfo?.specialTime && +
+ {isLoading + ? ( + + ) + : ( + + )} +
}
{ isLoading={isLoading} leaderboardPersonItems={leaderboardPersonItems} /> + {isLoading + ? ( + + ) + : ( + + )} + + {isLoading + ? ( +
+ {Array.from({ length: 3 }).map((_, index) => ( + + ))} +
+ ) + : ( + + )} - - -
(({ theme: { extendToken, token overflow: 'auto', height: '100%', + '.skeleton-list': { + display: 'flex', + flexDirection: 'column', + width: '100%', + height: 54 + }, + + '.skeleton-header': { + paddingBottom: 20, + width: '100%', + display: 'flex', + flexDirection: 'column' + }, + + '.skeleton-banner': { + width: '100%', + paddingTop: 12, + paddingBottom: 12 + }, + '.main-screen-header': { '.__screen-title': { maxWidth: 250, @@ -183,6 +262,8 @@ const Leaderboard = styled(Component)(({ theme: { extendToken, token }, '.time-remaining-wrapper': { + display: 'flex', + flexDirection: 'column', paddingLeft: 16, paddingRight: 16, marginBottom: 12 diff --git a/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx b/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx index 031b8317b4..17845aace9 100644 --- a/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx +++ b/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx @@ -4,6 +4,7 @@ import { GameAccountAvatar } from '@subwallet/extension-koni-ui/components/Mythical'; import { ThemeProps } from '@subwallet/extension-koni-ui/types'; import { toDisplayNumber } from '@subwallet/extension-koni-ui/utils'; +import { Skeleton } from '@subwallet/react-ui'; import CN from 'classnames'; import React from 'react'; import styled from 'styled-components'; @@ -28,29 +29,58 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi '-is-first': isFirst })} > - - {rank} -
- )} - /> + {isLoading + ? + : + {rank} + + )} + /> }
- {name} + {isLoading + ? + : name}
- {`${toDisplayNumber(point)}`} + {isLoading + ? + : `${toDisplayNumber(point)}`}
-
- {`+${toDisplayNumber(tokenValue)} Myth`} -
+ {isLoading + ? () + : ( +
+ {`+${toDisplayNumber(tokenValue)} Myth`} +
+ )}
@@ -59,6 +89,9 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi const TopAccountItem = styled(Component)(({ theme: { extendToken, token } }: ThemeProps) => { return { + display: 'flex', + alignItems: 'center', + flexDirection: 'column', '.__avatar-wrapper': { marginLeft: 'auto', marginRight: 'auto', @@ -85,6 +118,9 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to right: 0, top: 0 }, + '.skeleton': { + backgroundColor: 'red' + }, '.__account-name': { overflow: 'hidden', From f0d586e9273a415c6d73a9417fccb691a499fa88 Mon Sep 17 00:00:00 2001 From: Frenkie Nguyen Date: Tue, 17 Dec 2024 11:26:54 +0700 Subject: [PATCH 2/4] [Issue-161][Mythical Telegram App] Update loading animation for some screens (Leaderboard Screen) --- .../src/Popup/Home/LeaderboardTemp/index.tsx | 73 ++++++------------- .../Mythical/Common/TimeRemaining.tsx | 2 +- .../Mythical/Leaderboard/TopAccountItem.tsx | 10 +-- .../src/contexts/ThemeContext.tsx | 22 ++++++ .../src/utils/common/date.ts | 6 +- 5 files changed, 55 insertions(+), 58 deletions(-) diff --git a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx index 701962d415..4f548b765e 100644 --- a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx +++ b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx @@ -107,48 +107,27 @@ const Component = ({ className }: Props): React.ReactElement => { }, []); return ( -
- {isLoading - ? ( -
- -
+
( + + + + ) + } + title={currentLeaderboardInfo?.name || t('Leaderboard')} + /> ) - : ( - - - - ) - } - title={currentLeaderboardInfo?.name || t('Leaderboard')} - /> - ) } - - {leaderboardInfo?.endTimeTs && leaderboardInfo?.specialTime && -
- {isLoading - ? ( - - ) - : ( - - )} -
} + + { +
+ +
}
{ size={'large'} style={{ width: '100%', - height: 83, - background: 'linear-gradient(136deg, rgba(31, 31, 35, 0.00) 23.06%, rgba(224, 224, 224, 0.30) 81.89%)' + height: 83 }} /> ) @@ -191,7 +169,6 @@ const Component = ({ className }: Props): React.ReactElement => { style={{ width: '100%', height: 54, - background: 'linear-gradient(136deg, rgba(31, 31, 35, 0.00) 23.06%, rgba(224, 224, 224, 0.30) 81.89%)', marginBottom: index < 2 ? 4 : 0 }} /> @@ -262,8 +239,6 @@ const Leaderboard = styled(Component)(({ theme: { extendToken, token }, '.time-remaining-wrapper': { - display: 'flex', - flexDirection: 'column', paddingLeft: 16, paddingRight: 16, marginBottom: 12 @@ -272,13 +247,13 @@ const Leaderboard = styled(Component)(({ theme: { extendToken, token '.scroll-container': { flex: 1, overflow: 'auto', - paddingTop: 8 + paddingTop: 4 }, '.top-three-area': { paddingLeft: 24, - paddingRight: 24, - paddingBottom: token.size + paddingRight: 24 + // paddingBottom: token.size }, '.call-to-action': { diff --git a/packages/extension-koni-ui/src/components/Mythical/Common/TimeRemaining.tsx b/packages/extension-koni-ui/src/components/Mythical/Common/TimeRemaining.tsx index a178f7a394..1927b4db15 100644 --- a/packages/extension-koni-ui/src/components/Mythical/Common/TimeRemaining.tsx +++ b/packages/extension-koni-ui/src/components/Mythical/Common/TimeRemaining.tsx @@ -11,7 +11,7 @@ import styled from 'styled-components'; import { ClockIcon } from '../Icon'; type Props = ThemeProps & { - endTime: string; + endTime?: string; }; const apiSDK = BookaSdk.instance; diff --git a/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx b/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx index 17845aace9..a924ae6303 100644 --- a/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx +++ b/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx @@ -34,7 +34,6 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi active={true} shape={'circle'} size={58} - style={{ background: 'linear-gradient(136deg, rgba(31, 31, 35, 0.00) 23.06%, rgba(224, 224, 224, 0.30) 81.89%)' }} /> : : name}
@@ -62,8 +60,7 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi ? : `${toDisplayNumber(point)}`}
@@ -73,8 +70,7 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi ? () : (
diff --git a/packages/extension-koni-ui/src/contexts/ThemeContext.tsx b/packages/extension-koni-ui/src/contexts/ThemeContext.tsx index 4d31c43efa..72af643faf 100644 --- a/packages/extension-koni-ui/src/contexts/ThemeContext.tsx +++ b/packages/extension-koni-ui/src/contexts/ThemeContext.tsx @@ -50,6 +50,28 @@ const GlobalStyle = createGlobalStyle(({ theme }) => { border: 0 }, + '.ant-skeleton-input-lg.ant-skeleton-input-lg.ant-skeleton-input-lg': { + background: 'rgba(224, 224, 224, 0.30) 81.89%' + // ':after': { + // background: 'linear-gradient(136deg, rgba(31, 31, 35, 0.00) 23.06%, rgba(224, 224, 224, 0.30) 81.89%)', + // animationDuration: '2.4s' + // } + }, + + '.ant-skeleton-input-sm.ant-skeleton-input-sm.ant-skeleton-input-sm': { + background: 'rgba(224, 224, 224, 0.30) 81.89%' + // ':after': { + // background: 'rgba(31, 31, 35, 0.00) 23.06%' + // } + }, + + '.ant-skeleton-avatar-circle.ant-skeleton-avatar-circle.ant-skeleton-avatar-circle': { + background: 'rgba(224, 224, 224, 0.30) 81.89%' + // ':after': { + // background: 'rgba(31, 31, 35, 0.00) 23.06%' + // } + }, + '.ant-sw-modal .ant-sw-modal-header': { borderRadius: '24px 24px 0 0' }, diff --git a/packages/extension-koni-ui/src/utils/common/date.ts b/packages/extension-koni-ui/src/utils/common/date.ts index ff3f8dcefb..6f8e7f2ffc 100644 --- a/packages/extension-koni-ui/src/utils/common/date.ts +++ b/packages/extension-koni-ui/src/utils/common/date.ts @@ -250,7 +250,11 @@ export const formatHistoryDate = (dateMilli: string | number | Date, language: L return customFormatDate(dateMilli, '#MMM# #DD#, #YYYY#', 'en'); }; -export function getTimeRemaining (dateNow: number, targetTime: string): string { +export function getTimeRemaining (dateNow: number, targetTime?: string): string { + if (!targetTime) { + return '---'; + } + const end = new Date(targetTime).getTime(); if (isNaN(end)) { From 91f946ab438998d458f0667d04b9b7b6ea06da08 Mon Sep 17 00:00:00 2001 From: Frenkie Nguyen Date: Tue, 17 Dec 2024 11:35:55 +0700 Subject: [PATCH 3/4] [Issue-161][Mythical Telegram App] rollback css --- .../src/Popup/Home/LeaderboardTemp/index.tsx | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx index 4f548b765e..df370d0c04 100644 --- a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx +++ b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx @@ -247,13 +247,13 @@ const Leaderboard = styled(Component)(({ theme: { extendToken, token '.scroll-container': { flex: 1, overflow: 'auto', - paddingTop: 4 + paddingTop: 8 }, '.top-three-area': { paddingLeft: 24, - paddingRight: 24 - // paddingBottom: token.size + paddingRight: 24, + paddingBottom: token.size }, '.call-to-action': { From f60e64f50eecba140edcede3d586f0985c027963 Mon Sep 17 00:00:00 2001 From: lw Date: Tue, 17 Dec 2024 16:03:40 +0700 Subject: [PATCH 4/4] [Issue-161] Upload loading for leaderboard screen --- .../src/Popup/Home/LeaderboardTemp/index.tsx | 89 +++++++----- .../Mythical/Leaderboard/TopAccountItem.tsx | 131 ++++++++++++------ .../src/contexts/ThemeContext.tsx | 49 ++++--- packages/webapp/public/assets/reset.css | 18 +++ 4 files changed, 185 insertions(+), 102 deletions(-) diff --git a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx index df370d0c04..b91fdc83ec 100644 --- a/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx +++ b/packages/extension-koni-ui/src/Popup/Home/LeaderboardTemp/index.tsx @@ -66,20 +66,25 @@ const Component = ({ className }: Props): React.ReactElement => { useEffect(() => { let isSync = true; - setIsLoading(true); - - currentLeaderboardInfo && apiSDK.fetchLeaderboard(currentLeaderboardInfo.id, {}) - .then((data) => { - if (!isSync) { - return; - } - - setLeaderboardPersonItems(data.results); - setLeaderboardInfo(data.filter); - - setIsLoading(false); - }) - .catch(() => console.log('error')); + if (currentLeaderboardInfo) { + setIsLoading(true); + + apiSDK.fetchLeaderboard(currentLeaderboardInfo.id, {}) + .then((data) => { + if (!isSync) { + return; + } + + setLeaderboardPersonItems(data.results); + setLeaderboardInfo(data.filter); + }) + .catch((e) => console.log('apiSDK.fetchLeaderboard error', e)) + .finally(() => { + if (isSync) { + setIsLoading(false); + } + }); + } return () => { isSync = false; @@ -107,7 +112,7 @@ const Component = ({ className }: Props): React.ReactElement => { }, []); return ( -
( +
{ } title={currentLeaderboardInfo?.name || t('Leaderboard')} /> - ) {
- +
}
@@ -160,17 +166,12 @@ const Component = ({ className }: Props): React.ReactElement => { {isLoading ? (
- {Array.from({ length: 3 }).map((_, index) => ( + {Array.from({ length: 10 }).map((_, index) => ( ))}
@@ -181,7 +182,6 @@ const Component = ({ className }: Props): React.ReactElement => { leaderboardPersonItems={leaderboardPersonItems} /> )} -
(({ theme: { extendToken, token overflow: 'auto', height: '100%', - '.skeleton-list': { - display: 'flex', - flexDirection: 'column', - width: '100%', - height: 54 + '.skeleton-list-item': { + display: 'block !important', + height: '54px !important', + + '&.ant-skeleton': { + marginLeft: 8, + marginRight: 8 + }, + + '.ant-skeleton-input': { + width: '100% !important' + } }, - '.skeleton-header': { - paddingBottom: 20, - width: '100%', - display: 'flex', - flexDirection: 'column' + '.skeleton-list-item + .skeleton-list-item': { + marginTop: 4 }, '.skeleton-banner': { - width: '100%', - paddingTop: 12, - paddingBottom: 12 + display: 'block !important', + height: '83px !important', + + '&.ant-skeleton': { + marginLeft: 8, + marginRight: 8, + marginBottom: 12 + }, + + '.ant-skeleton-input': { + width: '100% !important' + } }, '.main-screen-header': { diff --git a/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx b/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx index a924ae6303..be52c887da 100644 --- a/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx +++ b/packages/extension-koni-ui/src/components/Mythical/Leaderboard/TopAccountItem.tsx @@ -30,50 +30,61 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi })} > {isLoading - ? - : - {rank} -
- )} - /> } + ? ( +
+ +
+ ) + : ( + + {rank} +
+ )} + /> + ) + }
{isLoading - ? + ? ( + + ) : name}
{isLoading - ? + ? ( + + ) : `${toDisplayNumber(point)}`}
-
+
{isLoading - ? () + ? ( + + ) : ( -
+
{`+${toDisplayNumber(tokenValue)} Myth`}
)} @@ -85,9 +96,6 @@ const Component = ({ avatarSrc, className, isFirst, isLoading, name = '---', poi const TopAccountItem = styled(Component)(({ theme: { extendToken, token } }: ThemeProps) => { return { - display: 'flex', - alignItems: 'center', - flexDirection: 'column', '.__avatar-wrapper': { marginLeft: 'auto', marginRight: 'auto', @@ -114,8 +122,20 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to right: 0, top: 0 }, - '.skeleton': { - backgroundColor: 'red' + + '.ant-skeleton.ant-skeleton.ant-skeleton .ant-skeleton-input': { + width: '100%', + minWidth: 0 + }, + + '.__skeleton-content.ant-skeleton.ant-skeleton': { + width: '100%', + + '.ant-skeleton-input': { + height: '100%', + lineHeight: 'inherit', + borderRadius: 32 + } }, '.__account-name': { @@ -138,12 +158,12 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to marginBottom: 6 }, - '.__token-Value-wrapper': { + '.__token-value-wrapper': { display: 'flex', justifyContent: 'center' }, - '.__token-Value': { + '.__token-value': { color: token.colorWhite, textAlign: 'center', fontFamily: extendToken.fontBarlowCondensed, @@ -157,6 +177,13 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to padding: '4px 12px' }, + '.__token-value-skeleton.__token-value-skeleton.__token-value-skeleton.__token-value-skeleton': { + height: 16, + width: 70, + borderRadius: 100, + lineHeight: 'inherit' + }, + '&:not(.-is-first)': { '.__avatar-wrapper': { paddingTop: 3.5 @@ -169,7 +196,7 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to lineHeight: '16px' }, - '.__avatar-image': { + '.__avatar-image, .__avatar-image-skeleton .ant-skeleton-avatar': { width: 57, height: 57 }, @@ -177,13 +204,21 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to '.__account-name': { fontSize: '14px', lineHeight: '16px', - letterSpacing: '0.28px' + letterSpacing: '0.28px', + + '.__skeleton-content': { + height: 16 + } }, '.__point': { fontSize: '16px', lineHeight: '18px', - letterSpacing: '-0.16px' + letterSpacing: '-0.16px', + + '.__skeleton-content': { + height: 18 + } } }, @@ -199,7 +234,7 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to lineHeight: '20px' }, - '.__avatar-image': { + '.__avatar-image, .__avatar-image-skeleton .ant-skeleton-avatar': { width: 74, height: 74 }, @@ -207,13 +242,21 @@ const TopAccountItem = styled(Component)(({ theme: { extendToken, to '.__account-name': { fontSize: '16px', lineHeight: '20px', - letterSpacing: '0.32px' + letterSpacing: '0.32px', + + '.__skeleton-content': { + height: 20 + } }, '.__point': { fontSize: '20px', lineHeight: '22px', - letterSpacing: '-0.6px' + letterSpacing: '-0.6px', + + '.__skeleton-content': { + height: 22 + } } } }; diff --git a/packages/extension-koni-ui/src/contexts/ThemeContext.tsx b/packages/extension-koni-ui/src/contexts/ThemeContext.tsx index 72af643faf..a98b7ae2f3 100644 --- a/packages/extension-koni-ui/src/contexts/ThemeContext.tsx +++ b/packages/extension-koni-ui/src/contexts/ThemeContext.tsx @@ -50,26 +50,35 @@ const GlobalStyle = createGlobalStyle(({ theme }) => { border: 0 }, - '.ant-skeleton-input-lg.ant-skeleton-input-lg.ant-skeleton-input-lg': { - background: 'rgba(224, 224, 224, 0.30) 81.89%' - // ':after': { - // background: 'linear-gradient(136deg, rgba(31, 31, 35, 0.00) 23.06%, rgba(224, 224, 224, 0.30) 81.89%)', - // animationDuration: '2.4s' - // } - }, - - '.ant-skeleton-input-sm.ant-skeleton-input-sm.ant-skeleton-input-sm': { - background: 'rgba(224, 224, 224, 0.30) 81.89%' - // ':after': { - // background: 'rgba(31, 31, 35, 0.00) 23.06%' - // } - }, - - '.ant-skeleton-avatar-circle.ant-skeleton-avatar-circle.ant-skeleton-avatar-circle': { - background: 'rgba(224, 224, 224, 0.30) 81.89%' - // ':after': { - // background: 'rgba(31, 31, 35, 0.00) 23.06%' - // } + '.ant-skeleton.ant-skeleton.ant-skeleton': { + '.ant-skeleton-input, .ant-skeleton-avatar': { + backgroundColor: 'rgba(224, 224, 224, 0.30)', + + '&:after': { + display: 'none' + } + }, + + '.ant-skeleton-input': { + borderRadius: 4 + } + }, + + '.ant-skeleton.ant-skeleton.ant-skeleton.-line': { + '.ant-skeleton-input': { + borderRadius: 32 + } + }, + + '.ant-skeleton.ant-skeleton.ant-skeleton-active': { + '.ant-skeleton-input, .ant-skeleton-avatar': { + backgroundImage: 'linear-gradient(97deg, rgba(224, 224, 224,0) 25%, rgba(224, 224, 224, 0.3) 37%, rgba(224, 224, 224,0) 63%)', + backgroundSize: '400% 100%', + animationName: 'skeleton-loading', + animationDuration: '1.4s', + animationTimingFunction: 'ease', + animationIterationCount: 'infinite' + } }, '.ant-sw-modal .ant-sw-modal-header': { diff --git a/packages/webapp/public/assets/reset.css b/packages/webapp/public/assets/reset.css index 11560a63fd..35be9b2523 100644 --- a/packages/webapp/public/assets/reset.css +++ b/packages/webapp/public/assets/reset.css @@ -905,3 +905,21 @@ div.ant-notification-notice { .ant-sw-qr-scanner-footer .ant-btn.ant-btn { border-radius: 52px } + +@keyframes skeleton-loading { + 0% { + background-position: 100% 50%; + } + 100% { + background-position: 0 50%; + } +} + +@keyframes skeleton-loading { + 0% { + background-position: 100% 50%; + } + 100% { + background-position: 0 50%; + } +}