improve mobile style and initial blocked screen loading

This commit is contained in:
Sean Yesmunt 2021-03-04 01:03:58 -05:00
parent eb0e0cb7cc
commit 84bab875bc
9 changed files with 154 additions and 159 deletions

View file

@ -1589,5 +1589,9 @@
"Interacting as %channelName%": "Interacting as %channelName%", "Interacting as %channelName%": "Interacting as %channelName%",
"Page Not Found": "Page Not Found", "Page Not Found": "Page Not Found",
"Transaction limit reached. Try reducing the Description length.": "Transaction limit reached. Try reducing the Description length.", "Transaction limit reached. Try reducing the Description length.": "Transaction limit reached. Try reducing the Description length.",
"You do not have any muted channels": "You do not have any muted channels",
"You do not have any blocked channels": "You do not have any blocked channels",
"Blocked channels will be invisible to you in the app. They will not be able to comment on your content, or reply to you comments left on other channels' content.": "Blocked channels will be invisible to you in the app. They will not be able to comment on your content, or reply to you comments left on other channels' content.",
"Muted channels will be invisible to you in the app. They will not know they are muted and can still interact with you and your content.": "Muted channels will be invisible to you in the app. They will not know they are muted and can still interact with you and your content.",
"--end--": "--end--" "--end--": "--end--"
} }

View file

@ -10,7 +10,7 @@ function FileAuthor(props: Props) {
const { channelUri } = props; const { channelUri } = props;
return channelUri ? ( return channelUri ? (
<ClaimPreview uri={channelUri} type="inline" properties={false} /> <ClaimPreview uri={channelUri} type="inline" properties={false} hideMenu />
) : ( ) : (
<div className="claim-preview--inline claim-preview__title">{__('Anonymous')}</div> <div className="claim-preview--inline claim-preview__title">{__('Anonymous')}</div>
); );

View file

@ -176,7 +176,7 @@ const Header = (props: Props) => {
: __('Your Wallet') : __('Your Wallet')
} }
navigate={`/$/${PAGES.WALLET}`} navigate={`/$/${PAGES.WALLET}`}
className={balanceButtonProps.className} className={classnames(balanceButtonProps.className, 'header__navigation-item--balance')}
label={hideBalance || Number(roundedBalance) === 0 ? __('Your Wallet') : roundedBalance} label={hideBalance || Number(roundedBalance) === 0 ? __('Your Wallet') : roundedBalance}
icon={ICONS.LBC} icon={ICONS.LBC}
// @if TARGET='app' // @if TARGET='app'
@ -212,7 +212,7 @@ const Header = (props: Props) => {
/> />
{backTitle && <h1 className="header__auth-title">{isMobile ? simpleBackTitle || backTitle : backTitle}</h1>} {backTitle && <h1 className="header__auth-title">{isMobile ? simpleBackTitle || backTitle : backTitle}</h1>}
{authenticated || !IS_WEB ? ( {authenticated || !IS_WEB ? (
<BalanceButton className="header__navigation-item menu__title header__navigation-item--balance" /> <BalanceButton className="header__navigation-item menu__title" />
) : ( ) : (
loginButtons loginButtons
)} )}
@ -275,10 +275,6 @@ const Header = (props: Props) => {
history={history} history={history}
handleThemeToggle={handleThemeToggle} handleThemeToggle={handleThemeToggle}
currentTheme={currentTheme} currentTheme={currentTheme}
activeChannelUrl={activeChannelUrl}
openSignOutModal={openSignOutModal}
email={email}
signOut={signOut}
/> />
</div> </div>
)} )}
@ -287,133 +283,17 @@ const Header = (props: Props) => {
{!authHeader && !backout ? ( {!authHeader && !backout ? (
<div className={classnames('header__menu', { 'header__menu--with-balance': !IS_WEB || authenticated })}> <div className={classnames('header__menu', { 'header__menu--with-balance': !IS_WEB || authenticated })}>
{(!IS_WEB || authenticated) && ( {(!IS_WEB || authenticated) && (
<BalanceButton className="header__navigation-item menu__title header__navigation-item--balance mobile-hidden" /> <BalanceButton className="header__navigation-item menu__title mobile-hidden" />
)} )}
{IS_WEB && !authenticated && loginButtons} {IS_WEB && !authenticated && loginButtons}
</div>
) : (
!isVerifyPage &&
!hideCancel && (
<div className="header__menu">
{/* Add an empty span here so we can use the same style as above */}
{/* This pushes the close button to the right side */}
<span />
<Button
title={__('Go Back')}
button="alt"
// className="button--header-close"
icon={ICONS.REMOVE}
{...closeButtonNavigationProps}
// @if TARGET='app'
onDoubleClick={(e) => {
e.stopPropagation();
}}
// @endif
/>
</div>
)
)}
</>
)}
</div>
</header>
);
};
type HeaderMenuButtonProps = {
authenticated: boolean,
notificationsEnabled: boolean,
history: { push: (string) => void },
handleThemeToggle: (string) => void,
currentTheme: string,
activeChannelUrl: ?string,
openSignOutModal: () => void,
email: ?string,
signOut: () => void,
};
function HeaderMenuButtons(props: HeaderMenuButtonProps) {
const {
authenticated,
notificationsEnabled,
history,
handleThemeToggle,
currentTheme,
activeChannelUrl,
openSignOutModal,
email,
signOut,
} = props;
return (
<div className="header__buttons">
{(authenticated || !IS_WEB) && (
<Menu>
<MenuButton
aria-label={__('Publish a file, or create a channel')}
title={__('Publish a file, or create a channel')}
className="header__navigation-item menu__title header__navigation-item--icon mobile-hidden"
// @if TARGET='app'
onDoubleClick={(e) => {
e.stopPropagation();
}}
// @endif
>
<Icon size={18} icon={ICONS.PUBLISH} aria-hidden />
</MenuButton>
<MenuList className="menu__list--header">
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.UPLOAD}`)}>
<Icon aria-hidden icon={ICONS.PUBLISH} />
{__('Upload')}
</MenuItem>
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.CHANNEL_NEW}`)}>
<Icon aria-hidden icon={ICONS.CHANNEL} />
{__('New Channel')}
</MenuItem>
</MenuList>
</Menu>
)}
{notificationsEnabled && <NotificationHeaderButton />}
<Menu>
<MenuButton
aria-label={__('Settings')}
title={__('Settings')}
className="header__navigation-item menu__title header__navigation-item--icon mobile-hidden"
// @if TARGET='app'
onDoubleClick={(e) => {
e.stopPropagation();
}}
// @endif
>
<Icon size={18} icon={ICONS.SETTINGS} aria-hidden />
</MenuButton>
<MenuList className="menu__list--header">
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.SETTINGS}`)}>
<Icon aria-hidden tootlip icon={ICONS.SETTINGS} />
{__('Settings')}
</MenuItem>
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.HELP}`)}>
<Icon aria-hidden icon={ICONS.HELP} />
{__('Help')}
</MenuItem>
<MenuItem className="menu__link" onSelect={handleThemeToggle}>
<Icon icon={currentTheme === 'light' ? ICONS.DARK : ICONS.LIGHT} />
{currentTheme === 'light' ? __('Dark') : __('Light')}
</MenuItem>
</MenuList>
</Menu>
{(authenticated || !IS_WEB) && ( {(authenticated || !IS_WEB) && (
<Menu> <Menu>
<MenuButton <MenuButton
aria-label={__('Your account')} aria-label={__('Your account')}
title={__('Your account')} title={__('Your account')}
className={classnames('header__navigation-item mobile-hidden', { className={classnames('header__navigation-item', {
'menu__title header__navigation-item--icon': !activeChannelUrl, 'menu__title header__navigation-item--icon': !activeChannelUrl,
'header__navigation-item--profile-pic': activeChannelUrl, 'header__navigation-item--profile-pic': activeChannelUrl,
})} })}
@ -475,6 +355,108 @@ function HeaderMenuButtons(props: HeaderMenuButtonProps) {
</Menu> </Menu>
)} )}
</div> </div>
) : (
!isVerifyPage &&
!hideCancel && (
<div className="header__menu">
{/* Add an empty span here so we can use the same style as above */}
{/* This pushes the close button to the right side */}
<span />
<Button
title={__('Go Back')}
button="alt"
// className="button--header-close"
icon={ICONS.REMOVE}
{...closeButtonNavigationProps}
// @if TARGET='app'
onDoubleClick={(e) => {
e.stopPropagation();
}}
// @endif
/>
</div>
)
)}
</>
)}
</div>
</header>
);
};
type HeaderMenuButtonProps = {
authenticated: boolean,
notificationsEnabled: boolean,
history: { push: (string) => void },
handleThemeToggle: (string) => void,
currentTheme: string,
};
function HeaderMenuButtons(props: HeaderMenuButtonProps) {
const { authenticated, notificationsEnabled, history, handleThemeToggle, currentTheme } = props;
return (
<div className="header__buttons">
{(authenticated || !IS_WEB) && (
<Menu>
<MenuButton
aria-label={__('Publish a file, or create a channel')}
title={__('Publish a file, or create a channel')}
className="header__navigation-item menu__title header__navigation-item--icon mobile-hidden"
// @if TARGET='app'
onDoubleClick={(e) => {
e.stopPropagation();
}}
// @endif
>
<Icon size={18} icon={ICONS.PUBLISH} aria-hidden />
</MenuButton>
<MenuList className="menu__list--header">
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.UPLOAD}`)}>
<Icon aria-hidden icon={ICONS.PUBLISH} />
{__('Upload')}
</MenuItem>
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.CHANNEL_NEW}`)}>
<Icon aria-hidden icon={ICONS.CHANNEL} />
{__('New Channel')}
</MenuItem>
</MenuList>
</Menu>
)}
{notificationsEnabled && <NotificationHeaderButton />}
<Menu>
<MenuButton
aria-label={__('Settings')}
title={__('Settings')}
className="header__navigation-item menu__title header__navigation-item--icon mobile-hidden"
// @if TARGET='app'
onDoubleClick={(e) => {
e.stopPropagation();
}}
// @endif
>
<Icon size={18} icon={ICONS.SETTINGS} aria-hidden />
</MenuButton>
<MenuList className="menu__list--header">
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.SETTINGS}`)}>
<Icon aria-hidden tootlip icon={ICONS.SETTINGS} />
{__('Settings')}
</MenuItem>
<MenuItem className="menu__link" onSelect={() => history.push(`/$/${PAGES.HELP}`)}>
<Icon aria-hidden icon={ICONS.HELP} />
{__('Help')}
</MenuItem>
<MenuItem className="menu__link" onSelect={handleThemeToggle}>
<Icon icon={currentTheme === 'light' ? ICONS.DARK : ICONS.LIGHT} />
{currentTheme === 'light' ? __('Dark') : __('Light')}
</MenuItem>
</MenuList>
</Menu>
</div>
); );
} }

View file

@ -58,6 +58,7 @@ export default function RecommendedContent(props: Props) {
type="small" type="small"
loading={isSearching} loading={isSearching}
uris={recommendedContent} uris={recommendedContent}
hideMenu={isMobile}
injectedItem={ injectedItem={
SHOW_ADS && IS_WEB ? ( SHOW_ADS && IS_WEB ? (
SIMPLE_SITE ? ( SIMPLE_SITE ? (

View file

@ -6,10 +6,10 @@ import ClaimList from 'component/claimList';
import Page from 'component/page'; import Page from 'component/page';
import Spinner from 'component/spinner'; import Spinner from 'component/spinner';
import Button from 'component/button'; import Button from 'component/button';
import usePrevious from 'effects/use-previous';
import usePersistedState from 'effects/use-persisted-state'; import usePersistedState from 'effects/use-persisted-state';
import ChannelBlockButton from 'component/channelBlockButton'; import ChannelBlockButton from 'component/channelBlockButton';
import ChannelMuteButton from 'component/channelMuteButton'; import ChannelMuteButton from 'component/channelMuteButton';
import Yrbl from 'component/yrbl';
type Props = { type Props = {
mutedUris: ?Array<string>, mutedUris: ?Array<string>,
@ -22,27 +22,19 @@ const VIEW_MUTED = 'muted';
function ListBlocked(props: Props) { function ListBlocked(props: Props) {
const { mutedUris, blockedUris, fetchingModerationBlockList } = props; const { mutedUris, blockedUris, fetchingModerationBlockList } = props;
const [viewMode, setViewMode] = usePersistedState('blocked-muted:display', VIEW_BLOCKED); const [viewMode, setViewMode] = usePersistedState('blocked-muted:display', VIEW_BLOCKED);
const [loading, setLoading] = React.useState(!blockedUris || !blockedUris.length);
// Keep a local list to allow for undoing actions in this component // Keep a local list to allow for undoing actions in this component
const [localBlockedList, setLocalBlockedList] = React.useState(undefined); const [localBlockedList, setLocalBlockedList] = React.useState(undefined);
const [localMutedList, setLocalMutedList] = React.useState(undefined); const [localMutedList, setLocalMutedList] = React.useState(undefined);
const previousFetchingModBlockList = usePrevious(fetchingModerationBlockList);
const hasLocalMuteList = localMutedList && localMutedList.length > 0; const hasLocalMuteList = localMutedList && localMutedList.length > 0;
const hasLocalBlockList = localBlockedList && localBlockedList.length > 0; const hasLocalBlockList = localBlockedList && localBlockedList.length > 0;
const stringifiedMutedChannels = JSON.stringify(mutedUris); const stringifiedMutedChannels = JSON.stringify(mutedUris);
const justMuted = localMutedList && mutedUris && localMutedList.length < mutedUris.length; const justMuted = localMutedList && mutedUris && localMutedList.length < mutedUris.length;
const justBlocked = localBlockedList && blockedUris && localBlockedList.length < blockedUris.length; const justBlocked = localBlockedList && blockedUris && localBlockedList.length < blockedUris.length;
const stringifiedBlockedChannels = JSON.stringify(blockedUris); const stringifiedBlockedChannels = JSON.stringify(blockedUris);
const showUris = (viewMode === VIEW_MUTED && hasLocalMuteList) || (viewMode === VIEW_BLOCKED && hasLocalBlockList);
React.useEffect(() => {
if (previousFetchingModBlockList && !fetchingModerationBlockList) {
setLoading(false);
}
}, [setLoading, previousFetchingModBlockList, fetchingModerationBlockList]);
React.useEffect(() => { React.useEffect(() => {
const jsonMutedChannels = stringifiedMutedChannels && JSON.parse(stringifiedMutedChannels); const jsonMutedChannels = stringifiedMutedChannels && JSON.parse(stringifiedMutedChannels);
@ -70,15 +62,22 @@ function ListBlocked(props: Props) {
} }
}, [stringifiedBlockedChannels, justBlocked, setLocalBlockedList]); }, [stringifiedBlockedChannels, justBlocked, setLocalBlockedList]);
const mutedHelpText = __(
'Muted channels will be invisible to you in the app. They will not know they are muted and can still interact with you and your content.'
);
const blockedHelpText = __(
"Blocked channels will be invisible to you in the app. They will not be able to comment on your content, or reply to you comments left on other channels' content."
);
return ( return (
<Page> <Page>
{loading && ( {fetchingModerationBlockList && (
<div className="main--empty"> <div className="main--empty">
<Spinner /> <Spinner />
</div> </div>
)} )}
{!loading && ( {!fetchingModerationBlockList && (
<> <>
<div className="section__header--actions"> <div className="section__header--actions">
<div className="section__actions--inline"> <div className="section__actions--inline">
@ -102,15 +101,10 @@ function ListBlocked(props: Props) {
/> />
</div> </div>
</div> </div>
<div className="help--notice">
{viewMode === VIEW_MUTED {showUris && <div className="help--notice">{viewMode === VIEW_MUTED ? mutedHelpText : blockedHelpText}</div>}
? __(
'Muted channels will be invisible to you in the app. They will not know they are muted and can still interact with you and your content.' {showUris ? (
)
: __(
"Blocked channels will be invisible to you in the app. They will not be able to comment on your content, or reply to you comments left on other channels' content."
)}
</div>
<ClaimList <ClaimList
uris={viewMode === VIEW_MUTED ? localMutedList : localBlockedList} uris={viewMode === VIEW_MUTED ? localMutedList : localBlockedList}
showUnresolvedClaims showUnresolvedClaims
@ -134,6 +128,23 @@ function ListBlocked(props: Props) {
); );
}} }}
/> />
) : (
<div className="main--empty">
<Yrbl
title={
viewMode === VIEW_MUTED
? __('You do not have any muted channels')
: __('You do not have any blocked channels')
}
subtitle={viewMode === VIEW_MUTED ? mutedHelpText : blockedHelpText}
actions={
<div className="section__actions">
<Button button="primary" label={__('Go Home')} navigate="/" />
</div>
}
/>
</div>
)}
</> </>
)} )}
</Page> </Page>

View file

@ -561,9 +561,12 @@ export function doFetchModBlockedList() {
dispatch({ dispatch({
type: ACTIONS.COMMENT_MODERATION_BLOCK_LIST_COMPLETED, type: ACTIONS.COMMENT_MODERATION_BLOCK_LIST_COMPLETED,
data: { data: {
blockList: globalBlockList blockList:
globalBlockList.length > 0
? globalBlockList
.sort((a, b) => new Date(a.blockedAt) - new Date(b.blockedAt)) .sort((a, b) => new Date(a.blockedAt) - new Date(b.blockedAt))
.map((blockedChannel) => blockedChannel.channelUri), .map((blockedChannel) => blockedChannel.channelUri)
: null,
}, },
}); });
}) })

View file

@ -456,9 +456,8 @@
.claim-tile__title { .claim-tile__title {
position: relative; position: relative;
padding: var(--spacing-s); padding: var(--spacing-s);
padding-right: var(--spacing-m); padding-right: var(--spacing-l);
padding-bottom: 0; padding-bottom: 0;
margin-bottom: var(--spacing-s); margin-bottom: var(--spacing-s);
@ -474,6 +473,7 @@
@media (min-width: $breakpoint-small) { @media (min-width: $breakpoint-small) {
min-height: 2.5rem; min-height: 2.5rem;
padding-right: var(--spacing-m);
} }
} }
@ -601,9 +601,11 @@
stroke: var(--color-text); stroke: var(--color-text);
} }
@media (min-width: $breakpoint-small) {
&:not([aria-expanded='true']) { &:not([aria-expanded='true']) {
display: none; display: none;
} }
}
} }
.claim__menu-button--inline { .claim__menu-button--inline {

View file

@ -101,35 +101,27 @@
} }
.header__navigation-item--profile-pic { .header__navigation-item--profile-pic {
margin-left: var(--spacing-m);
.channel-thumbnail { .channel-thumbnail {
height: var(--height-button); height: var(--height-button);
width: var(--height-button); width: var(--height-button);
margin-right: 0; margin-right: 0;
transition: border-radius var(--animation-duration);
border-radius: calc(var(--height-button) / 2);
img {
transition: border-radius var(--animation-duration);
border-radius: calc(var(--height-button) / 2);
}
} }
&:hover { &:hover {
opacity: 0.7; opacity: 0.7;
.channel-thumbnail {
border-radius: var(--border-radius);
img {
border-radius: var(--border-radius);
}
}
} }
} }
.header__navigation-item--balance { .header__navigation-item--balance {
@extend .button--link; @extend .button--file-action;
margin-left: var(--spacing-m); margin: 0 var(--spacing-s);
color: var(--color-text);
&:hover {
color: var(--color-text);
}
} }
.header__navigation-item--forward { .header__navigation-item--forward {

View file

@ -49,7 +49,7 @@
--color-input-color: #111111; --color-input-color: #111111;
--color-input-label: var(--color-gray-5); --color-input-label: var(--color-gray-5);
--color-input-placeholder: #212529; --color-input-placeholder: #212529;
--color-input-bg: #f4f4f4; --color-input-bg: var(--color-gray-1);
--color-input-bg-copyable: #434b53; --color-input-bg-copyable: #434b53;
--color-input-border: var(--color-border); --color-input-border: var(--color-border);
--color-input-border-active: var(--color-secondary); --color-input-border-active: var(--color-secondary);