Merge pull request #631 from ente-io/plan-selector-ui-fixes

Plan selector UI fixes
This commit is contained in:
Manav 2022-07-05 17:49:36 +05:30 committed by GitHub
commit aaec3e0592
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 183 additions and 94 deletions

View file

@ -0,0 +1,48 @@
import { Stack } from '@mui/material';
import Box from '@mui/material/Box';
import Typography from '@mui/material/Typography';
import React from 'react';
import constants from 'utils/strings/constants';
import { PeriodToggler } from '../periodToggler';
import Plans from '../plans';
export default function FreeSubscriptionPlanSelectorCard({
plans,
subscription,
closeModal,
planPeriod,
togglePeriod,
onPlanSelect,
}) {
return (
<>
<Typography variant="h3" fontWeight={'bold'}>
{constants.CHOOSE_PLAN}
</Typography>
<Box>
<Stack spacing={3}>
<Box>
<PeriodToggler
planPeriod={planPeriod}
togglePeriod={togglePeriod}
/>
<Typography
variant="body2"
mt={0.5}
color="text.secondary">
{constants.TWO_MONTHS_FREE}
</Typography>
</Box>
<Plans
plans={plans}
planPeriod={planPeriod}
onPlanSelect={onPlanSelect}
subscription={subscription}
closeModal={closeModal}
/>
</Stack>
</Box>
</>
);
}

View file

@ -1,4 +1,3 @@
import { PeriodToggler } from './periodToggler';
import React, { useContext, useEffect, useMemo, useState } from 'react'; import React, { useContext, useEffect, useMemo, useState } from 'react';
import constants from 'utils/strings/constants'; import constants from 'utils/strings/constants';
import { Plan } from 'types/billing'; import { Plan } from 'types/billing';
@ -13,9 +12,8 @@ import {
hasPaypalSubscription, hasPaypalSubscription,
getLocalUserSubscription, getLocalUserSubscription,
hasPaidSubscription, hasPaidSubscription,
convertBytesToGBs,
getTotalFamilyUsage, getTotalFamilyUsage,
makeHumanReadableStorage, isPartOfFamily,
} from 'utils/billing'; } from 'utils/billing';
import { reverseString } from 'utils/common'; import { reverseString } from 'utils/common';
import { GalleryContext } from 'pages/gallery'; import { GalleryContext } from 'pages/gallery';
@ -23,15 +21,13 @@ import billingService from 'services/billingService';
import { SetLoading } from 'types/gallery'; import { SetLoading } from 'types/gallery';
import { logError } from 'utils/sentry'; import { logError } from 'utils/sentry';
import { AppContext } from 'pages/_app'; import { AppContext } from 'pages/_app';
import Plans from './plans'; import { Stack } from '@mui/material';
import { Box, IconButton, Stack, Typography } from '@mui/material';
import { useLocalState } from 'hooks/useLocalState'; import { useLocalState } from 'hooks/useLocalState';
import { LS_KEYS } from 'utils/storage/localStorage'; import { LS_KEYS } from 'utils/storage/localStorage';
import { getLocalUserDetails } from 'utils/user'; import { getLocalUserDetails } from 'utils/user';
import { ManageSubscription } from './manageSubscription';
import { SpaceBetweenFlex } from 'components/Container';
import Close from '@mui/icons-material/Close';
import { PLAN_PERIOD } from 'constants/gallery'; import { PLAN_PERIOD } from 'constants/gallery';
import FreeSubscriptionPlanSelectorCard from './free';
import PaidSubscriptionPlanSelectorCard from './paid';
interface Props { interface Props {
closeModal: any; closeModal: any;
@ -48,9 +44,11 @@ function PlanSelectorCard(props: Props) {
const galleryContext = useContext(GalleryContext); const galleryContext = useContext(GalleryContext);
const appContext = useContext(AppContext); const appContext = useContext(AppContext);
const totalFamilyUsage = useMemo(() => { const usage = useMemo(() => {
const familyData = getLocalUserDetails()?.familyData; const userDetails = getLocalUserDetails();
return familyData ? getTotalFamilyUsage(familyData) : 0; return isPartOfFamily(userDetails?.familyData)
? getTotalFamilyUsage(userDetails?.familyData)
: userDetails.usage;
}, []); }, []);
const togglePeriod = () => { const togglePeriod = () => {
@ -158,84 +156,25 @@ function PlanSelectorCard(props: Props) {
return ( return (
<> <>
<Stack spacing={3} p={1.5}> <Stack spacing={3} p={1.5}>
<Box py={0.5} px={1.5}>
{hasPaidSubscription(subscription) ? ( {hasPaidSubscription(subscription) ? (
<SpaceBetweenFlex> <PaidSubscriptionPlanSelectorCard
<Box> plans={plans}
<Typography variant="h3" fontWeight={'bold'}> subscription={subscription}
{constants.SUBSCRIPTION} closeModal={props.closeModal}
</Typography>
<Typography
variant="body2"
color={'text.secondary'}>
{convertBytesToGBs(subscription.storage, 2)}{' '}
{constants.GB}
</Typography>
</Box>
<IconButton onClick={props.closeModal}>
<Close />
</IconButton>
</SpaceBetweenFlex>
) : (
<Typography variant="h3" fontWeight={'bold'}>
{constants.CHOOSE_PLAN}
</Typography>
)}
</Box>
{totalFamilyUsage > 0 && (
<Box px={1.5}>
<Typography
color={'text.secondary'}
fontWeight={'bold'}>
{constants.CURRENT_USAGE(
makeHumanReadableStorage(totalFamilyUsage)
)}
</Typography>
</Box>
)}
<Box>
<Stack
spacing={3}
border={(theme) =>
hasPaidSubscription(subscription) &&
`1px solid ${theme.palette.divider}`
}
p={1.5}
borderRadius={(theme) =>
`${theme.shape.borderRadius}px`
}>
<Box>
<PeriodToggler
planPeriod={planPeriod} planPeriod={planPeriod}
togglePeriod={togglePeriod} togglePeriod={togglePeriod}
/>
<Typography mt={0.5} color="text.secondary">
{constants.TWO_MONTHS_FREE}
</Typography>
</Box>
<Plans
plans={plans}
planPeriod={planPeriod}
onPlanSelect={onPlanSelect} onPlanSelect={onPlanSelect}
subscription={subscription}
closeModal={props.closeModal}
/>
</Stack>
{hasPaidSubscription(subscription) && (
<Box py={1} px={1.5}>
<Typography color={'text.secondary'}>
{constants.RENEWAL_ACTIVE_SUBSCRIPTION_INFO(
subscription.expiryTime
)}
</Typography>
</Box>
)}
</Box>
{hasPaidSubscription(subscription) && (
<ManageSubscription
subscription={subscription}
closeModal={props.closeModal}
setLoading={props.setLoading} setLoading={props.setLoading}
usage={usage}
/>
) : (
<FreeSubscriptionPlanSelectorCard
plans={plans}
subscription={subscription}
closeModal={props.closeModal}
planPeriod={planPeriod}
togglePeriod={togglePeriod}
onPlanSelect={onPlanSelect}
/> />
)} )}
</Stack> </Stack>

View file

@ -0,0 +1,93 @@
import Close from '@mui/icons-material/Close';
import { IconButton, Stack } from '@mui/material';
import Box from '@mui/material/Box';
import Typography from '@mui/material/Typography';
import { SpaceBetweenFlex } from 'components/Container';
import React from 'react';
import { convertBytesToGBs } from 'utils/billing';
import constants from 'utils/strings/constants';
import { ManageSubscription } from '../manageSubscription';
import { PeriodToggler } from '../periodToggler';
import Plans from '../plans';
export default function PaidSubscriptionPlanSelectorCard({
plans,
subscription,
closeModal,
usage,
planPeriod,
togglePeriod,
onPlanSelect,
setLoading,
}) {
return (
<>
<Box px={1.5} py={0.5}>
<SpaceBetweenFlex>
<Box>
<Typography variant="h3" fontWeight={'bold'}>
{constants.SUBSCRIPTION}
</Typography>
<Typography variant="body2" color={'text.secondary'}>
{convertBytesToGBs(subscription.storage, 2)}{' '}
{constants.GB}
</Typography>
</Box>
<IconButton onClick={closeModal}>
<Close />
</IconButton>
</SpaceBetweenFlex>
</Box>
<Box px={1.5}>
<Typography color={'text.secondary'} fontWeight={'bold'}>
{constants.CURRENT_USAGE(
`${convertBytesToGBs(usage, 2)} ${constants.GB}`
)}
</Typography>
</Box>
<Box>
<Stack
spacing={3}
border={(theme) => `1px solid ${theme.palette.divider}`}
p={1.5}
borderRadius={(theme) => `${theme.shape.borderRadius}px`}>
<Box>
<PeriodToggler
planPeriod={planPeriod}
togglePeriod={togglePeriod}
/>
<Typography
variant="body2"
mt={0.5}
color="text.secondary">
{constants.TWO_MONTHS_FREE}
</Typography>
</Box>
<Plans
plans={plans}
planPeriod={planPeriod}
onPlanSelect={onPlanSelect}
subscription={subscription}
closeModal={closeModal}
/>
</Stack>
<Box py={1} px={1.5}>
<Typography color={'text.secondary'}>
{constants.RENEWAL_ACTIVE_SUBSCRIPTION_INFO(
subscription.expiryTime
)}
</Typography>
</Box>
</Box>
<ManageSubscription
subscription={subscription}
closeModal={closeModal}
setLoading={setLoading}
/>
</>
);
}

View file

@ -8,6 +8,7 @@ const CustomToggleButton = styled(ToggleButton)(({ theme }) => ({
padding: '12px 16px', padding: '12px 16px',
borderRadius: '4px', borderRadius: '4px',
backgroundColor: theme.palette.fill.dark, backgroundColor: theme.palette.fill.dark,
border: `1px solid transparent`,
color: theme.palette.text.disabled, color: theme.palette.text.disabled,
'&.Mui-selected': { '&.Mui-selected': {
backgroundColor: theme.palette.accent.main, backgroundColor: theme.palette.accent.main,

View file

@ -79,16 +79,24 @@ export function PlanRow({
</FlexWrapper> </FlexWrapper>
</TopAlignedFluidContainer> </TopAlignedFluidContainer>
<Box width="136px"> <Box width="136px">
<PlanButton size="large" onClick={handleClick}> <PlanButton
<Box> sx={{
justifyContent: 'flex-end',
borderTopLeftRadius: 0,
borderBottomLeftRadius: 0,
}}
size="large"
onClick={handleClick}>
<Box textAlign={'right'}>
<Typography fontWeight={'bold'} variant="h4"> <Typography fontWeight={'bold'} variant="h4">
{plan.price}{' '} {plan.price}{' '}
</Typography>{' '} </Typography>{' '}
<Typography color="text.secondary" variant="body2"> <Typography color="text.secondary" variant="body2">
/ $ {`/ ${
{plan.period === PLAN_PERIOD.MONTH plan.period === PLAN_PERIOD.MONTH
? constants.MONTH_SHORT ? constants.MONTH_SHORT
: constants.YEAR_SHORT} : constants.YEAR
}`}
</Typography> </Typography>
</Box> </Box>
</PlanButton> </PlanButton>

View file

@ -279,7 +279,7 @@ const englishConstants = {
FAMILY_SUBSCRIPTION_INFO: 'You are on a family plan managed by', FAMILY_SUBSCRIPTION_INFO: 'You are on a family plan managed by',
RENEWAL_ACTIVE_SUBSCRIPTION_INFO: (expiryTime) => ( RENEWAL_ACTIVE_SUBSCRIPTION_INFO: (expiryTime) => (
<>Renew on {dateString(expiryTime)}</> <>Renews on {dateString(expiryTime)}</>
), ),
RENEWAL_CANCELLED_SUBSCRIPTION_INFO: (expiryTime) => ( RENEWAL_CANCELLED_SUBSCRIPTION_INFO: (expiryTime) => (
@ -750,7 +750,7 @@ const englishConstants = {
FREE: 'free', FREE: 'free',
OF: 'of', OF: 'of',
MONTH_SHORT: 'mo', MONTH_SHORT: 'mo',
YEAR_SHORT: 'yr', YEAR: 'year',
FAMILY_PLAN: 'Family plan', FAMILY_PLAN: 'Family plan',
DOWNLOAD_LOGS: 'Download logs', DOWNLOAD_LOGS: 'Download logs',
DOWNLOAD_LOGS_MESSAGE: () => ( DOWNLOAD_LOGS_MESSAGE: () => (