Skip to content

Commit d49d8a7

Browse files
committed
add new day marker
1 parent 0946407 commit d49d8a7

File tree

3 files changed

+136
-101
lines changed

3 files changed

+136
-101
lines changed

src/common/date.ts

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -36,13 +36,19 @@ export function formatTimestamp(timestamp: number) {
3636
}).format(date)} at ${pad(date.getHours())}:${pad(date.getMinutes())}`;
3737
}
3838
}
39+
40+
export const fullDate = (timestamp: number, month: "short" | "long" = "short", weekday?: "long") => {
41+
return Intl.DateTimeFormat("en-GB", {
42+
weekday: weekday,
43+
day: "2-digit",
44+
month,
45+
year: "numeric",
46+
}).format(timestamp);
47+
};
48+
3949
export const fullDateTime = (timestamp: number) => {
4050
const date = new Date(timestamp);
41-
return `${Intl.DateTimeFormat("en-GB", {
42-
day: "2-digit",
43-
month: "short",
44-
year: "numeric",
45-
}).format(date)} at ${pad(date.getHours())}:${pad(date.getMinutes())}`;
51+
return `${fullDate(timestamp)} at ${pad(date.getHours())}:${pad(date.getMinutes())}`;
4652
};
4753

4854
// get days ago from timestamp

src/components/message-pane/message-item/MessageItem.tsx

Lines changed: 117 additions & 96 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ import styles from "./styles.module.scss";
22
import { classNames, cn, conditionalClass } from "@/common/classNames";
33
import {
44
formatTimestamp,
5+
fullDate,
6+
fullDateTime,
57
millisecondsToHhMmSs,
68
timeElapsed,
79
timeSince,
@@ -279,6 +281,18 @@ const MessageItem = (props: MessageItemProps) => {
279281

280282
const { createPortal } = useCustomPortal();
281283

284+
const isNewDay = createMemo(() => {
285+
if (!props.beforeMessage) return true;
286+
const beforeCreatedAt = new Date(props.beforeMessage.createdAt);
287+
const createdAt = new Date(props.message.createdAt);
288+
289+
const nextDay = new Date(beforeCreatedAt);
290+
nextDay.setDate(nextDay.getDate() + 1);
291+
nextDay.setHours(0, 0, 0, 0);
292+
293+
return createdAt >= nextDay;
294+
});
295+
282296
const currentTime = props.message?.createdAt;
283297
const beforeMessageTime = () => props.beforeMessage?.createdAt!;
284298

@@ -397,110 +411,117 @@ const MessageItem = (props: MessageItemProps) => {
397411
};
398412

399413
return (
400-
<div
401-
class={classNames(
402-
styles.messageItem,
403-
conditionalClass(isCompact(), styles.compact),
404-
conditionalClass(isMentioned(), styles.mentioned),
405-
conditionalClass(isSomeoneMentioned(), styles.someoneMentioned),
406-
props.class,
407-
"messageItem"
408-
)}
409-
onContextMenu={props.contextMenu}
410-
onMouseEnter={() => setHovered(true)}
411-
onMouseLeave={() => setHovered(false)}
412-
id={`message-${props.message.id}`}
413-
>
414-
<Show when={!props.hideFloating}>
415-
<FloatOptions
416-
textAreaEl={props.textAreaEl}
417-
reactionPickerClick={props.reactionPickerClick}
418-
showContextMenu={props.contextMenu}
419-
isCompact={isCompact()}
420-
message={props.message}
421-
/>
414+
<>
415+
<Show when={isNewDay()}>
416+
<div class={styles.newDayMarker}>
417+
{fullDate(props.message.createdAt, "long", "long")}
418+
</div>
422419
</Show>
423-
<Switch
424-
fallback={
425-
<Show when={blockedMessage()}>
426-
<div
427-
onClick={() => setBlockedMessage(false)}
428-
class={classNames(
429-
styles.blockedMessage,
430-
conditionalClass(isCompact(), styles.compact)
431-
)}
432-
>
433-
You have blocked this user. Click to show.
434-
</div>
435-
</Show>
436-
}
420+
<div
421+
class={classNames(
422+
styles.messageItem,
423+
conditionalClass(isCompact(), styles.compact),
424+
conditionalClass(isMentioned(), styles.mentioned),
425+
conditionalClass(isSomeoneMentioned(), styles.someoneMentioned),
426+
props.class,
427+
"messageItem"
428+
)}
429+
onContextMenu={props.contextMenu}
430+
onMouseEnter={() => setHovered(true)}
431+
onMouseLeave={() => setHovered(false)}
432+
id={`message-${props.message.id}`}
437433
>
438-
<Match when={isSystemMessage()}>
439-
<SystemMessage message={props.message} />
440-
</Match>
441-
<Match when={!isSystemMessage() && !blockedMessage()}>
442-
<div class={styles.messageInner}>
443-
<MessageReplies message={props.message} />
444-
<div class={styles.messageInnerInner}>
445-
<Show when={!isCompact()}>
446-
<A
447-
onClick={showProfileFlyout}
448-
onContextMenu={props.userContextMenu}
449-
href={RouterEndpoints.PROFILE(props.message.createdBy.id)}
450-
class={classNames(styles.avatar, "trigger-profile-flyout")}
451-
>
452-
<Avatar
453-
animate={hovered()}
454-
user={props.message.createdBy}
455-
size={40}
456-
resize={96}
457-
/>
458-
</A>
459-
</Show>
460-
<div class={styles.messageInnerInnerInner}>
434+
<Show when={!props.hideFloating}>
435+
<FloatOptions
436+
textAreaEl={props.textAreaEl}
437+
reactionPickerClick={props.reactionPickerClick}
438+
showContextMenu={props.contextMenu}
439+
isCompact={isCompact()}
440+
message={props.message}
441+
/>
442+
</Show>
443+
<Switch
444+
fallback={
445+
<Show when={blockedMessage()}>
446+
<div
447+
onClick={() => setBlockedMessage(false)}
448+
class={classNames(
449+
styles.blockedMessage,
450+
conditionalClass(isCompact(), styles.compact)
451+
)}
452+
>
453+
You have blocked this user. Click to show.
454+
</div>
455+
</Show>
456+
}
457+
>
458+
<Match when={isSystemMessage()}>
459+
<SystemMessage message={props.message} />
460+
</Match>
461+
<Match when={!isSystemMessage() && !blockedMessage()}>
462+
<div class={styles.messageInner}>
463+
<MessageReplies message={props.message} />
464+
<div class={styles.messageInnerInner}>
461465
<Show when={!isCompact()}>
462-
<Details
463-
hovered={hovered()}
464-
message={props.message}
465-
isServerCreator={isServerCreator()}
466-
isSystemMessage={isSystemMessage()}
467-
serverMember={serverMember()}
468-
showProfileFlyout={showProfileFlyout}
469-
userContextMenu={props.userContextMenu}
470-
/>
466+
<A
467+
onClick={showProfileFlyout}
468+
onContextMenu={props.userContextMenu}
469+
href={RouterEndpoints.PROFILE(props.message.createdBy.id)}
470+
class={classNames(styles.avatar, "trigger-profile-flyout")}
471+
>
472+
<Avatar
473+
animate={hovered()}
474+
user={props.message.createdBy}
475+
size={40}
476+
resize={96}
477+
/>
478+
</A>
471479
</Show>
472-
<Content message={props.message} hovered={hovered()} />
473-
<Show when={translatedContent()}>
474-
<div class={styles.translationArea}>
475-
<span class={styles.title}>
476-
Translation{" "}
477-
<span class={styles.translationSource}>
478-
({translatedContent()?.src})
480+
<div class={styles.messageInnerInnerInner}>
481+
<Show when={!isCompact()}>
482+
<Details
483+
hovered={hovered()}
484+
message={props.message}
485+
isServerCreator={isServerCreator()}
486+
isSystemMessage={isSystemMessage()}
487+
serverMember={serverMember()}
488+
showProfileFlyout={showProfileFlyout}
489+
userContextMenu={props.userContextMenu}
490+
/>
491+
</Show>
492+
<Content message={props.message} hovered={hovered()} />
493+
<Show when={translatedContent()}>
494+
<div class={styles.translationArea}>
495+
<span class={styles.title}>
496+
Translation{" "}
497+
<span class={styles.translationSource}>
498+
({translatedContent()?.src})
499+
</span>
479500
</span>
480-
</span>
481-
<Markup
482-
text={translatedContent()?.translationString!}
483-
replaceCommandBotId
501+
<Markup
502+
text={translatedContent()?.translationString!}
503+
replaceCommandBotId
504+
/>
505+
</div>
506+
</Show>
507+
<Show when={props.message.uploadingAttachment}>
508+
<UploadAttachment message={props.message} />
509+
</Show>
510+
<Show when={props.message.reactions?.length}>
511+
<Reactions
512+
textAreaEl={props.textAreaEl}
513+
reactionPickerClick={props.reactionPickerClick}
514+
hovered={hovered()}
515+
message={props.message}
484516
/>
485-
</div>
486-
</Show>
487-
<Show when={props.message.uploadingAttachment}>
488-
<UploadAttachment message={props.message} />
489-
</Show>
490-
<Show when={props.message.reactions?.length}>
491-
<Reactions
492-
textAreaEl={props.textAreaEl}
493-
reactionPickerClick={props.reactionPickerClick}
494-
hovered={hovered()}
495-
message={props.message}
496-
/>
497-
</Show>
517+
</Show>
518+
</div>
498519
</div>
499520
</div>
500-
</div>
501-
</Match>
502-
</Switch>
503-
</div>
521+
</Match>
522+
</Switch>
523+
</div>
524+
</>
504525
);
505526
};
506527

src/components/message-pane/message-item/styles.module.scss

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,14 @@
77
}
88
}
99

10+
.newDayMarker {
11+
align-self: center;
12+
padding: 6px;
13+
border-radius: 6px;
14+
color: rgba(255, 255, 255, 0.8);
15+
background-color: rgba(0, 0, 0, 0.2);
16+
font-size: 12px;
17+
}
1018

1119
.translationArea {
1220
display: flex;

0 commit comments

Comments
 (0)