openvibers/openvibe.chat Commits
openvibe.chat names: a person's colour is mixed half-and-half with the theme's text colour so it reads on any background (raw colours were below 4.5:1 on the dark panel), and a room line's colour is checked as a hex colour before it reaches the style attribute — WS-T task 3
Changes
@@@ -40,7 +40,10 @@ h1 { font-size: 1.6rem; line-height: 1.25; margin: .3em 0 .2em; }.oc-compact .oc-msg { padding: 1px 10px; }.oc-time { display: none; color: var(--oc-muted); font-size: .8em; font-variant-numeric: tabular-nums; margin-right: 4px; }.oc-times .oc-time { display: inline; }--.oc-name { font-weight: 700; text-decoration: none; }++.oc-name { font-weight: 700; text-decoration: none; color: var(--nc, inherit); }++/* A person's own colour (--nc) mixed half-and-half with the theme's text colour: the hue stays theirs,++ and it reads on any theme's background (their raw colour was below 4.5:1 on the dark panel). */++.oc-name { color: color-mix(in oklab, var(--nc, var(--oc-text)) 50%, var(--oc-text)); }.oc-anon { color: var(--oc-muted); font-weight: 600; }.oc-where { color: var(--oc-muted); font-size: .8em; text-decoration: none; margin-left: 4px; }.oc-text { white-space: pre-wrap; }@@@ -58,7 +58,7 @@var handle = m.core_username || (m.user_id ? m.username : null);var name = m.display_name || m.username || m.anon_id || 'someone';var who;-- if (handle) { who = el('a', 'oc-name', name); who.href = LIVE + '/@' + encodeURIComponent(handle); if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.color = m.profile_color; }++ if (handle) { who = el('a', 'oc-name', name); who.href = LIVE + '/@' + encodeURIComponent(handle); if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.setProperty('--nc', m.profile_color); }else who = el('span', 'oc-name oc-anon', name);li.appendChild(who);var b = badge(m.role); if (b) li.appendChild(b);@@@ -167,7 +167,7 @@li.appendChild(clock(m.created_at)); li.appendChild(document.createTextNode(' '));var who = el('a', 'oc-name', m.display_name || m.username || 'someone');who.href = LIVE + '/@' + encodeURIComponent(m.username || '');-- if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.color = m.profile_color;++ if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.setProperty('--nc', m.profile_color);li.appendChild(who);var b = badge(m.user_role); if (b) li.appendChild(b);li.appendChild(document.createTextNode(' '));@@@ -69,7 +69,7 @@ function globalMessage(m) {const t = hhmm(m.timestamp);const handle = m.core_username || (m.user_id ? m.username : null);const name = esc(m.display_name || m.username || m.anon_id || 'someone');-- const who = handle ? `<a class="oc-name" href="${LIVE}/@${encodeURIComponent(handle)}" style="color:${esc(/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? m.profile_color : 'inherit')}">${name}</a>` : `<span class="oc-name oc-anon">${name}</span>`;++ const who = handle ? `<a class="oc-name" href="${LIVE}/@${encodeURIComponent(handle)}" style="--nc:${esc(/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? m.profile_color : 'inherit')}">${name}</a>` : `<span class="oc-name oc-anon">${name}</span>`;const where = m.stream_channel ? ` <a class="oc-where" href="${LIVE}/@${encodeURIComponent(m.stream_channel)}" title="Sent from ${esc(m.stream_channel)}'s channel">@${esc(m.stream_channel)}</a>` : '';return `<li class="oc-msg" data-id="${Number(m.id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> ${who}${roleBadge(m.role)}${where} <span class="oc-text">${linkify(m.message)}</span></li>`;}@@@ -312,7 +312,7 @@ ${volume('tts_sound_volume', 'Chat sound volume', tts.sound_volume)}const roomMessage = (m, can, slug, me) => {const t = hhmm(m.created_at);const del = (can.moderate || (me && m.user_id === me.id)) ? `<form class="oc-del" method="post" action="/r/${esc(slug)}/delete/${Number(m.id)}"><button type="submit" title="Delete this message" aria-label="Delete this message">×</button></form>` : '';-- return `<li class="oc-msg" data-id="${Number(m.id) || 0}" data-user="${Number(m.user_id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> <a class="oc-name" href="${LIVE}/@${encodeURIComponent(m.username || '')}"${/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? ` style="color:${esc(m.profile_color)}"` : ''}>${esc(m.display_name || m.username || 'someone')}</a>${roleBadge(m.user_role)} <span class="oc-text">${linkify(m.message)}</span>${del}</li>`;++ return `<li class="oc-msg" data-id="${Number(m.id) || 0}" data-user="${Number(m.user_id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> <a class="oc-name" href="${LIVE}/@${encodeURIComponent(m.username || '')}"${/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? ` style="--nc:${/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? esc(m.profile_color) : 'inherit'}"` : ''}>${esc(m.display_name || m.username || 'someone')}</a>${roleBadge(m.user_role)} <span class="oc-text">${linkify(m.message)}</span>${del}</li>`;};router.get('/rooms', async (req, res) => {
@@ -40,7 +40,10 @@ h1 { font-size: 1.6rem; line-height: 1.25; margin: .3em 0 .2em; }
@@ -40,7 +40,10 @@ h1 { font-size: 1.6rem; line-height: 1.25; margin: .3em 0 .2em; }
.oc-compact .oc-msg { padding: 1px 10px; }
.oc-compact .oc-msg { padding: 1px 10px; }
.oc-time { display: none; color: var(--oc-muted); font-size: .8em; font-variant-numeric: tabular-nums; margin-right: 4px; }
.oc-time { display: none; color: var(--oc-muted); font-size: .8em; font-variant-numeric: tabular-nums; margin-right: 4px; }
.oc-times .oc-time { display: inline; }
.oc-times .oc-time { display: inline; }
-.oc-name { font-weight: 700; text-decoration: none; }
+.oc-name { font-weight: 700; text-decoration: none; color: var(--nc, inherit); }
+/* A person's own colour (--nc) mixed half-and-half with the theme's text colour: the hue stays theirs,
+ and it reads on any theme's background (their raw colour was below 4.5:1 on the dark panel). */
+.oc-name { color: color-mix(in oklab, var(--nc, var(--oc-text)) 50%, var(--oc-text)); }
.oc-anon { color: var(--oc-muted); font-weight: 600; }
.oc-anon { color: var(--oc-muted); font-weight: 600; }
.oc-where { color: var(--oc-muted); font-size: .8em; text-decoration: none; margin-left: 4px; }
.oc-where { color: var(--oc-muted); font-size: .8em; text-decoration: none; margin-left: 4px; }
.oc-text { white-space: pre-wrap; }
.oc-text { white-space: pre-wrap; }
@@ -58,7 +58,7 @@
@@ -58,7 +58,7 @@
var handle = m.core_username || (m.user_id ? m.username : null);
var handle = m.core_username || (m.user_id ? m.username : null);
var name = m.display_name || m.username || m.anon_id || 'someone';
var name = m.display_name || m.username || m.anon_id || 'someone';
var who;
var who;
- if (handle) { who = el('a', 'oc-name', name); who.href = LIVE + '/@' + encodeURIComponent(handle); if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.color = m.profile_color; }
+ if (handle) { who = el('a', 'oc-name', name); who.href = LIVE + '/@' + encodeURIComponent(handle); if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.setProperty('--nc', m.profile_color); }
else who = el('span', 'oc-name oc-anon', name);
else who = el('span', 'oc-name oc-anon', name);
li.appendChild(who);
li.appendChild(who);
var b = badge(m.role); if (b) li.appendChild(b);
var b = badge(m.role); if (b) li.appendChild(b);
@@ -167,7 +167,7 @@
@@ -167,7 +167,7 @@
li.appendChild(clock(m.created_at)); li.appendChild(document.createTextNode(' '));
li.appendChild(clock(m.created_at)); li.appendChild(document.createTextNode(' '));
var who = el('a', 'oc-name', m.display_name || m.username || 'someone');
var who = el('a', 'oc-name', m.display_name || m.username || 'someone');
who.href = LIVE + '/@' + encodeURIComponent(m.username || '');
who.href = LIVE + '/@' + encodeURIComponent(m.username || '');
- if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.color = m.profile_color;
+ if (/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '')) who.style.setProperty('--nc', m.profile_color);
li.appendChild(who);
li.appendChild(who);
var b = badge(m.user_role); if (b) li.appendChild(b);
var b = badge(m.user_role); if (b) li.appendChild(b);
li.appendChild(document.createTextNode(' '));
li.appendChild(document.createTextNode(' '));
@@ -69,7 +69,7 @@ function globalMessage(m) {
@@ -69,7 +69,7 @@ function globalMessage(m) {
const t = hhmm(m.timestamp);
const t = hhmm(m.timestamp);
const handle = m.core_username || (m.user_id ? m.username : null);
const handle = m.core_username || (m.user_id ? m.username : null);
const name = esc(m.display_name || m.username || m.anon_id || 'someone');
const name = esc(m.display_name || m.username || m.anon_id || 'someone');
- const who = handle ? `<a class="oc-name" href="${LIVE}/@${encodeURIComponent(handle)}" style="color:${esc(/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? m.profile_color : 'inherit')}">${name}</a>` : `<span class="oc-name oc-anon">${name}</span>`;
+ const who = handle ? `<a class="oc-name" href="${LIVE}/@${encodeURIComponent(handle)}" style="--nc:${esc(/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? m.profile_color : 'inherit')}">${name}</a>` : `<span class="oc-name oc-anon">${name}</span>`;
const where = m.stream_channel ? ` <a class="oc-where" href="${LIVE}/@${encodeURIComponent(m.stream_channel)}" title="Sent from ${esc(m.stream_channel)}'s channel">@${esc(m.stream_channel)}</a>` : '';
const where = m.stream_channel ? ` <a class="oc-where" href="${LIVE}/@${encodeURIComponent(m.stream_channel)}" title="Sent from ${esc(m.stream_channel)}'s channel">@${esc(m.stream_channel)}</a>` : '';
return `<li class="oc-msg" data-id="${Number(m.id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> ${who}${roleBadge(m.role)}${where} <span class="oc-text">${linkify(m.message)}</span></li>`;
return `<li class="oc-msg" data-id="${Number(m.id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> ${who}${roleBadge(m.role)}${where} <span class="oc-text">${linkify(m.message)}</span></li>`;
}
}
@@ -312,7 +312,7 @@ ${volume('tts_sound_volume', 'Chat sound volume', tts.sound_volume)}
@@ -312,7 +312,7 @@ ${volume('tts_sound_volume', 'Chat sound volume', tts.sound_volume)}
const roomMessage = (m, can, slug, me) => {
const roomMessage = (m, can, slug, me) => {
const t = hhmm(m.created_at);
const t = hhmm(m.created_at);
const del = (can.moderate || (me && m.user_id === me.id)) ? `<form class="oc-del" method="post" action="/r/${esc(slug)}/delete/${Number(m.id)}"><button type="submit" title="Delete this message" aria-label="Delete this message">×</button></form>` : '';
const del = (can.moderate || (me && m.user_id === me.id)) ? `<form class="oc-del" method="post" action="/r/${esc(slug)}/delete/${Number(m.id)}"><button type="submit" title="Delete this message" aria-label="Delete this message">×</button></form>` : '';
- return `<li class="oc-msg" data-id="${Number(m.id) || 0}" data-user="${Number(m.user_id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> <a class="oc-name" href="${LIVE}/@${encodeURIComponent(m.username || '')}"${/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? ` style="color:${esc(m.profile_color)}"` : ''}>${esc(m.display_name || m.username || 'someone')}</a>${roleBadge(m.user_role)} <span class="oc-text">${linkify(m.message)}</span>${del}</li>`;
+ return `<li class="oc-msg" data-id="${Number(m.id) || 0}" data-user="${Number(m.user_id) || 0}"><time class="oc-time" datetime="${t.iso}">${t.text}</time> <a class="oc-name" href="${LIVE}/@${encodeURIComponent(m.username || '')}"${/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? ` style="--nc:${/^#[0-9a-f]{3,8}$/i.test(m.profile_color || '') ? esc(m.profile_color) : 'inherit'}"` : ''}>${esc(m.display_name || m.username || 'someone')}</a>${roleBadge(m.user_role)} <span class="oc-text">${linkify(m.message)}</span>${del}</li>`;
};
};
router.get('/rooms', async (req, res) => {
router.get('/rooms', async (req, res) => {