Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/chapterlist show more detailed upload dates for today and yesterday #222

Merged
merged 2 commits into from
Jan 7, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 8 additions & 7 deletions src/components/manga/ChapterCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,9 @@ import React from 'react';
import { Link } from 'react-router-dom';
import client from 'util/client';
import { BACK } from 'util/useBackTo';
import { getUploadDateString } from 'util/date';

interface IProps{
interface IProps {
chapter: IChapter
triggerChaptersUpdate: () => void
downloadChapter: IDownloadChapter | undefined
Expand All @@ -48,8 +49,6 @@ const ChapterCard: React.FC<IProps> = (props: IProps) => {
} = props;
const isSelecting = selected !== null;

const dateStr = chapter.uploadDate && new Date(chapter.uploadDate).toLocaleDateString();

const [anchorEl, setAnchorEl] = React.useState<null | HTMLElement>(null);

const handleMenuClick = (event: React.MouseEvent<HTMLButtonElement>) => {
Expand All @@ -69,7 +68,9 @@ const ChapterCard: React.FC<IProps> = (props: IProps) => {

const formData = new FormData();
formData.append(key, value);
if (key === 'read') { formData.append('lastPageRead', '1'); }
if (key === 'read') {
formData.append('lastPageRead', '1');
}
client.patch(`/api/v1/manga/${chapter.mangaId}/chapter/${chapter.index}`, formData)
.then(() => triggerChaptersUpdate());
};
Expand Down Expand Up @@ -131,13 +132,13 @@ const ChapterCard: React.FC<IProps> = (props: IProps) => {
{chapter.bookmarked && (
<BookmarkIcon color="primary" sx={{ mr: 0.5, position: 'relative', top: '0.15em' }} />
)}
{ showChapterNumber ? `Chapter ${chapter.chapterNumber}` : chapter.name}
{showChapterNumber ? `Chapter ${chapter.chapterNumber}` : chapter.name}
</Typography>
<Typography variant="caption">
{chapter.scanlator}
</Typography>
<Typography variant="caption">
{dateStr}
{getUploadDateString(chapter.uploadDate)}
{isDownloaded && ' • Downloaded'}
</Typography>
</Stack>
Expand Down Expand Up @@ -186,7 +187,7 @@ const ChapterCard: React.FC<IProps> = (props: IProps) => {
Download
</ListItemText>
</MenuItem>
) }
)}
<MenuItem onClick={() => sendChange('bookmarked', !chapter.bookmarked)}>
<ListItemIcon>
{chapter.bookmarked && <BookmarkRemove fontSize="small" />}
Expand Down
72 changes: 72 additions & 0 deletions src/util/date.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
/*
* Copyright (C) Contributors to the Suwayomi project
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
*/

export const isWithinLastXMillis = (date: Date, timeMS: number) => {
const timeDifference = Date.now() - date.getTime();
return timeDifference <= timeMS;
};

export const getElapsedTimeSinceStartOfDay = (date: Date) => {
const startOfDay = new Date(date.getFullYear(), date.getMonth(), date.getDate());
return date.getTime() - startOfDay.getTime();
};

/**
* Returns a string in localized format for the passed date.
*
* In case the date is from today or yesterday a special string will be returned including "Today"
* or "Yesterday" with the localized time of the passed date.
*
* @example
* const today = new Date();
* const yesterday = new Date(today.getTime() - 1000 * 60 * 60 * 24);
* const someDate = new Date(1337, 4, 20);
*
* const todayAsString = getDateString(today); // => "Today at 02:50 AM"
* const yesterdayAsString = getDateString(yesterday) // => "Yesterday at 02:50 AM"
* const someDate = getDateString(someDate) // => "04/20/1337"
*
*
* @param date
*/
export const getUploadDateString = (date: Date | number) => {
const uploadDate = date instanceof Date ? date : new Date(date);

const today = new Date();
const todayElapsedTime = getElapsedTimeSinceStartOfDay(today);
const yesterday = new Date(today.getTime() - todayElapsedTime - 1000 * 60 * 60 * 24);
const elapsedTimeSinceYesterday = today.getTime() - yesterday.getTime();

const wasUploadedToday = isWithinLastXMillis(uploadDate, todayElapsedTime);
const wasUploadedYesterday = isWithinLastXMillis(uploadDate, elapsedTimeSinceYesterday);

const addTimeString = wasUploadedToday || wasUploadedYesterday;
const timeString = addTimeString
? uploadDate.toLocaleTimeString(
undefined,
{
hour: '2-digit',
minute: '2-digit',
},
)
: '';

if (wasUploadedToday) {
return `Today at ${timeString}`;
}

if (wasUploadedYesterday) {
return `Yesterday at ${timeString}`;
}

return uploadDate.toLocaleDateString(undefined, {
year: 'numeric',
month: '2-digit',
day: '2-digit',
});
};