Improve when time is shown and improve post UI

This commit introduces a heuristic for when to show time, introduces a
date separator and tweaks the margins of posts.
This commit is contained in:
Midgard 2022-06-11 17:25:12 +02:00
parent 8d0d0dd3a7
commit f7344dc63f
Signed by: midgard
GPG key ID: 511C112F1331BBB4
3 changed files with 89 additions and 22 deletions

View file

@ -215,15 +215,25 @@ ul#server_selection_list {
margin-bottom: 0.5em; margin-bottom: 0.5em;
} }
.date_separator {
font-weight: bold;
margin-top: 0.3em;
font-size: 75%;
text-align: center;
color: #555;
border-top: 1px solid #ccc;
}
.post { .post {
padding: 0.1em; padding: 0.2em;
margin: 0.6em 0 0.2em; margin-top: 0.3em;
display: grid; display: grid;
grid-template-rows: auto auto; grid-template-rows: auto auto auto;
grid-template-columns: auto auto; grid-template-columns: auto auto;
min-height: 3ex;
} }
.post.same_author { .post.same_author {
margin-top: 0.2em; margin-top: 0;
} }
.post:first-child { .post:first-child {
margin-top: 8px; margin-top: 8px;
@ -234,6 +244,9 @@ ul#server_selection_list {
.post:hover { .post:hover {
background-color: #e4e4e4; background-color: #e4e4e4;
} }
.post:not(.show_time) {
position: relative;
}
.post .author { .post .author {
grid-row: 1; grid-row: 1;
@ -242,7 +255,7 @@ ul#server_selection_list {
font-weight: bold; font-weight: bold;
align-self: end; align-self: end;
} }
.post.same_author .author { .post.same_author:not(.show_time) .author {
display: none; display: none;
} }
@ -254,8 +267,16 @@ ul#server_selection_list {
color: #888; color: #888;
align-self: end; align-self: end;
} }
.post.same_author .create_at { .post:not(.show_time) .create_at {
display: none; display: none;
position: absolute;
background-color: #e4e4e4;
padding: 0 0.2em;
right: 0;
top: 0;
}
.post:not(.show_time):hover .create_at {
display: block;
} }
.post .message { .post .message {
@ -264,8 +285,15 @@ ul#server_selection_list {
grid-column-start: 1; grid-column-start: 1;
grid-column-end: 3; grid-column-end: 3;
} }
.post.special .message {
color: #555;
font-size: 75%;
}
.post ul.attachments { .post ul.attachments {
grid-row: 3;
grid-column-start: 1;
grid-column-end: 3;
margin: 0; margin: 0;
padding: 0; padding: 0;
list-style: none; list-style: none;

View file

@ -90,8 +90,9 @@ function toTimeZone(date, timezoneString) {
return new Date(date.toLocaleString("en-US", {timeZone: timezoneString})); return new Date(date.toLocaleString("en-US", {timeZone: timezoneString}));
} }
function formatDdddMmYy(date) { function formatYyyyMmDdWeekday(date) {
return `${date.getFullYear()}-${padLeft(date.getMonth() + 1, 2, "0")}-${padLeft(date.getDate(), 2, "0")}`; const weekday = ["Su", "Mo", "Tu", "We", "Th", "Fr", "Sa"][date.getDay()];
return `${date.getFullYear()}-${padLeft(date.getMonth() + 1, 2, "0")}-${padLeft(date.getDate(), 2, "0")}, ${weekday}`;
} }
function formatHhMm(date) { function formatHhMm(date) {

View file

@ -8,25 +8,63 @@ function transformMessageText(message) {
} }
function shouldShowTime(lastShownTime, time) {
const sim = dateSimilarity(lastShownTime, time);
if (sim < DATE_SIMILARITY.date) {
return {date: true, time: true};
}
const minutesSinceLastShown = (time - lastShownTime) / 1000 / 60;
if (minutesSinceLastShown >= 15) {
return {date: false, time: true};
}
return {date: false, time: false};
}
async function createMessageElement(client, post, lastTime, lastAuthor) { async function createMessageElement(client, post, lastTime, lastAuthor) {
let nodes = [];
const users = await client.getUsers(); const users = await client.getUsers();
const isThreadReply = !!post.parent_id; const isThreadReply = !!post.parent_id;
const createAt = new Date(post.create_at);
let createAtLocalized = createAt;
let lastTimeLocalized = lastTime;
try {
if (client.me.timezone.useAutomaticTimezone !== "true") {
createAtLocalized = toTimeZone(createAt, client.me.timezone.manualTimezone);
lastTimeLocalized = toTimeZone(lastTime, client.me.timezone.manualTimezone);
}
} catch(e) {}
const showTime = shouldShowTime(lastTimeLocalized, createAtLocalized);
if (showTime.time) {
lastTime = createAt;
}
const postDiv = document.createElement("div");
postDiv.className = "post";
if (post.type !== "") {
postDiv.className += " special";
}
if (showTime.date) {
const dateElement = document.createElement("div");
dateElement.className = "date_separator";
dateElement.innerText = formatYyyyMmDdWeekday(createAtLocalized);
nodes.push(dateElement);
}
if (showTime.time) {
postDiv.className += " show_time";
}
const messageDiv = document.createElement("div"); const messageDiv = document.createElement("div");
messageDiv.className = "message"; messageDiv.className = "message";
messageDiv.innerText = transformMessageText(post.message); messageDiv.innerText = transformMessageText(post.message);
let createAt = new Date(post.create_at);
if (client.me.timezone.useAutomaticTimezone !== "true") {
createAt = toTimeZone(createAt, client.me.timezone.manualTimezone);
}
const createAtDiv = document.createElement("time"); const createAtDiv = document.createElement("time");
createAtDiv.className = "create_at"; createAtDiv.className = "create_at";
const sim = dateSimilarity(lastTime, createAt); let createAtText = formatHhMm(createAtLocalized);
lastTime = createAt;
let createAtText = "";
if (sim < DATE_SIMILARITY.date) createAtText += formatDdddMmYy(createAt);
if (sim < DATE_SIMILARITY.minutes) createAtText += " " + formatHhMm(createAt);
createAtDiv.title = createAt.toString(); createAtDiv.title = createAt.toString();
createAtDiv.innerText = createAtText; createAtDiv.innerText = createAtText;
createAtDiv.dateTime = createAt.toISOString(); createAtDiv.dateTime = createAt.toISOString();
@ -36,8 +74,6 @@ async function createMessageElement(client, post, lastTime, lastAuthor) {
authorDiv.className = "author"; authorDiv.className = "author";
authorDiv.innerText = authorName; authorDiv.innerText = authorName;
const postDiv = document.createElement("div");
postDiv.className = "post";
if (lastAuthor === post.user_id) { if (lastAuthor === post.user_id) {
postDiv.className += " same_author"; postDiv.className += " same_author";
} }
@ -72,7 +108,9 @@ async function createMessageElement(client, post, lastTime, lastAuthor) {
postDiv.appendChild(attachmentsUl); postDiv.appendChild(attachmentsUl);
} }
return {postDiv, lastTime, lastAuthor}; nodes.push(postDiv);
return {nodes, lastTime, lastAuthor};
} }
@ -84,7 +122,7 @@ async function populateChannelContents(client, channel, contents) {
let nodes = []; let nodes = [];
for (let id of contents.order) { for (let id of contents.order) {
result = await createMessageElement(client, contents.posts[id], result.lastTime, result.lastAuthor); result = await createMessageElement(client, contents.posts[id], result.lastTime, result.lastAuthor);
nodes.push(result.postDiv); nodes.push(...result.nodes);
} }
byId("channel_contents").dataset["server"] = client.endpoint; byId("channel_contents").dataset["server"] = client.endpoint;
@ -106,7 +144,7 @@ async function addMessage(client, post) {
); );
byId("channel_contents").dataset["lastTime"] = result.lastTime.getTime(); byId("channel_contents").dataset["lastTime"] = result.lastTime.getTime();
byId("channel_contents").dataset["lastAuthor"] = result.lastAuthor; byId("channel_contents").dataset["lastAuthor"] = result.lastAuthor;
byId("channel_contents").appendChild(result.postDiv); byId("channel_contents").append(...result.nodes);
if (shouldScroll) { if (shouldScroll) {
scrollToBottom(); scrollToBottom();