fix: mobile styles + viewport

This commit is contained in:
Nicola Zambello 2023-02-18 20:37:37 +01:00
parent e0843fc89a
commit cf3b79d4aa
Signed by: nzambello
GPG key ID: 56E4A92C2C1E50BA
3 changed files with 191 additions and 122 deletions

View file

@ -1,3 +1,4 @@
import { Box, MediaQuery } from '@mantine/core';
import React, { useState, useEffect } from 'react'; import React, { useState, useEffect } from 'react';
export interface Props { export interface Props {
@ -33,8 +34,8 @@ const TimeElapsed = ({ startTime, endTime }: Props) => {
.padStart(2, '0')}`; .padStart(2, '0')}`;
return ( return (
<div <Box
style={{ sx={{
display: 'flex', display: 'flex',
alignItems: 'center', alignItems: 'center',
justifyContent: 'center', justifyContent: 'center',
@ -50,31 +51,38 @@ const TimeElapsed = ({ startTime, endTime }: Props) => {
> >
<code>{hoursString}</code> <code>{hoursString}</code>
</pre> </pre>
<p <MediaQuery
style={{ smallerThan="sm"
fontSize: '0.75rem', styles={{
margin: 0 display: 'none'
}} }}
> >
<span> <p
{Intl.DateTimeFormat('it-IT', { style={{
hour: '2-digit', fontSize: '0.75rem',
minute: '2-digit', margin: 0
hour12: false }}
}).format(new Date(startTime))} >
</span> <span>
<span dangerouslySetInnerHTML={{ __html: '&nbsp;&mdash;&nbsp;' }} /> {Intl.DateTimeFormat('it-IT', {
<span> hour: '2-digit',
{endTime minute: '2-digit',
? Intl.DateTimeFormat('it-IT', { hour12: false
hour: '2-digit', }).format(new Date(startTime))}
minute: '2-digit', </span>
hour12: false <span dangerouslySetInnerHTML={{ __html: '&nbsp;&mdash;&nbsp;' }} />
}).format(new Date(endTime)) <span>
: 'now'} {endTime
</span> ? Intl.DateTimeFormat('it-IT', {
</p> hour: '2-digit',
</div> minute: '2-digit',
hour12: false
}).format(new Date(endTime))
: 'now'}
</span>
</p>
</MediaQuery>
</Box>
); );
}; };

View file

@ -126,6 +126,17 @@ function Document({
<html lang="en"> <html lang="en">
<head> <head>
<meta charSet="utf-8" /> <meta charSet="utf-8" />
<meta
name="viewport"
content="minimum-scale=1, initial-scale=1, width=device-width, shrink-to-fit=no, user-scalable=no, viewport-fit=cover"
/>
<meta name="apple-mobile-web-app-capable" content="yes" />
<meta
name="apple-mobile-web-app-status-bar-style"
content="default"
/>
<meta name="format-detection" content="telephone=no" />
<meta name="mobile-web-app-capable" content="yes" />
{title ? <title>{title}</title> : null} {title ? <title>{title}</title> : null}
<StylesPlaceholder /> <StylesPlaceholder />
<Meta /> <Meta />
@ -355,7 +366,7 @@ function Layout({ children }: React.PropsWithChildren<{}>) {
</UnstyledButton> </UnstyledButton>
<UnstyledButton <UnstyledButton
component={Link} component={Link}
to="/" to="/importexport"
sx={(theme) => ({ sx={(theme) => ({
display: 'block', display: 'block',
width: '100%', width: '100%',
@ -379,7 +390,7 @@ function Layout({ children }: React.PropsWithChildren<{}>) {
<Upload size={16} /> <Upload size={16} />
</ThemeIcon> </ThemeIcon>
<Text size="sm">Import</Text> <Text size="sm">Import/Export</Text>
</Group> </Group>
</UnstyledButton> </UnstyledButton>
<UnstyledButton <UnstyledButton

View file

@ -14,7 +14,8 @@ import {
Progress, Progress,
Badge, Badge,
ThemeIcon, ThemeIcon,
Alert Alert,
Box
} from '@mantine/core'; } from '@mantine/core';
import { json, LoaderArgs, MetaFunction, redirect } from '@remix-run/node'; import { json, LoaderArgs, MetaFunction, redirect } from '@remix-run/node';
import { import {
@ -138,7 +139,8 @@ export default function TimeEntriesPage() {
style={{ style={{
display: 'flex', display: 'flex',
alignItems: 'flex-end', alignItems: 'flex-end',
justifyContent: 'space-between' justifyContent: 'space-between',
margin: '0.5rem 0'
}} }}
> >
<NativeSelect <NativeSelect
@ -248,123 +250,171 @@ export default function TimeEntriesPage() {
radius="md" radius="md"
mb="sm" mb="sm"
display="flex" display="flex"
style={{ sx={() => ({
alignItems: 'center', alignItems: 'center',
flexDirection: 'column' justifyContent: 'space-between',
}} flexDirection: 'row'
})}
> >
<div <Box
style={{ sx={() => ({
display: 'flex', display: 'flex',
alignItems: 'center', alignItems: 'flex-start',
flexDirection: 'column',
justifyContent: 'space-between', justifyContent: 'space-between',
width: '100%' flexGrow: 1,
}} width: '100%',
'@media (min-width: 601px)': {
alignItems: 'center',
flexDirection: 'row'
}
})}
> >
<span <Box
style={{ component="span"
marginRight: 'auto' sx={{
display: 'inline-block',
marginRight: 'auto',
'@media (max-width: 600px)': {
marginBottom: '0.33rem'
}
}} }}
> >
{timeEntry.description} {timeEntry.description}
</span> </Box>
{timeEntry.projectId && timeEntry.project && ( {timeEntry.projectId && timeEntry.project && (
<Badge color={timeEntry.project.color}> <Badge color={timeEntry.project.color}>
{timeEntry.project.name} {timeEntry.project.name}
</Badge> </Badge>
)} )}
</Box>
<Box
sx={{
display: 'flex',
alignItems: 'center',
flexDirection: 'column',
justifyContent: 'space-between',
flexShrink: 1,
flexGrow: 0,
'@media (min-width: 601px)': {
flexDirection: 'row'
}
}}
>
<TimeElapsed <TimeElapsed
startTime={timeEntry.startTime} startTime={timeEntry.startTime}
endTime={timeEntry.endTime} endTime={timeEntry.endTime}
/> />
<Menu shadow="md" width={200}> <Box
<Menu.Target> sx={{
<ActionIcon title="Edit" mr="xs"> display: 'flex',
<Settings size={14} /> flexShrink: 0,
</ActionIcon>
</Menu.Target>
<Menu.Dropdown> '@media (max-width: 600px)': {
<Menu.Label>Edit time entry</Menu.Label> marginTop: '0.33rem'
<Menu.Item }
component={Link} }}
to={`/time-entries/${timeEntry.id}`} >
icon={ <Menu shadow="md" width={200}>
<Edit3 size={14} color={theme.colors.yellow[8]} /> <Menu.Target>
} <ActionIcon
> title="Edit"
Edit mr="xs"
</Menu.Item> sx={{
marginLeft: 'auto'
}}
>
<Settings size={14} />
</ActionIcon>
</Menu.Target>
<Menu.Dropdown>
<Menu.Label>Edit time entry</Menu.Label>
<Menu.Item
component={Link}
to={`/time-entries/${timeEntry.id}`}
icon={
<Edit3 size={14} color={theme.colors.yellow[8]} />
}
>
Edit
</Menu.Item>
<Form
method="delete"
action={`/time-entries/${timeEntry.id}`}
>
<Menu.Item
component="button"
type="submit"
icon={
<Trash size={14} color={theme.colors.red[8]} />
}
>
Delete
</Menu.Item>
</Form>
</Menu.Dropdown>
</Menu>
{timeEntry.endTime ? (
<Form method="post" action="/time-entries/new">
<input
type="hidden"
name="startTime"
value={new Date(Date.now()).toISOString()}
/>
<input
type="hidden"
name="description"
value={timeEntry.description}
/>
<input
type="hidden"
name="projectId"
value={timeEntry.projectId}
/>
<input
type="hidden"
name="userId"
value={timeEntry.userId}
/>
<ActionIcon
type="submit"
title="Start new entry with same description"
>
<ThemeIcon variant="light">
<Play size={14} color={theme.colors.blue[7]} />
</ThemeIcon>
</ActionIcon>
</Form>
) : (
<Form <Form
method="delete" method="patch"
action={`/time-entries/${timeEntry.id}`} action={`/time-entries/${timeEntry.id}`}
> >
<Menu.Item <input
component="button" type="hidden"
name="endTime"
value={new Date().toISOString()}
/>
<ActionIcon
type="submit" type="submit"
icon={<Trash size={14} color={theme.colors.red[8]} />} variant="filled"
title="Stop"
style={{
backgroundColor: theme.colors.red[7],
color: 'white',
borderRadius: '50%'
}}
> >
Delete <Square size={12} fill="currentColor" />
</Menu.Item> </ActionIcon>
</Form> </Form>
</Menu.Dropdown> )}
</Menu> </Box>
{timeEntry.endTime ? ( </Box>
<Form method="post" action="/time-entries/new">
<input
type="hidden"
name="startTime"
value={new Date(Date.now()).toISOString()}
/>
<input
type="hidden"
name="description"
value={timeEntry.description}
/>
<input
type="hidden"
name="projectId"
value={timeEntry.projectId}
/>
<input
type="hidden"
name="userId"
value={timeEntry.userId}
/>
<ActionIcon
type="submit"
title="Start new entry with same description"
>
<ThemeIcon variant="light">
<Play size={14} color={theme.colors.blue[7]} />
</ThemeIcon>
</ActionIcon>
</Form>
) : (
<Form
method="patch"
action={`/time-entries/${timeEntry.id}`}
>
<input
type="hidden"
name="endTime"
value={new Date().toISOString()}
/>
<ActionIcon
type="submit"
variant="filled"
title="Stop"
style={{
backgroundColor: theme.colors.red[7],
color: 'white',
borderRadius: '50%'
}}
>
<Square size={12} fill="currentColor" />
</ActionIcon>
</Form>
)}
</div>
</Paper> </Paper>
))} ))}
</section> </section>