main f6d8405

smileys.ts RawHistoryFolder

1/**
2 * AIM "Yellow Smiley" set (AIM 4.x/5.x). Typed codes become the original
3 * 19×19 GIFs from /static/smileys (local-only, AOL artwork). When a GIF is
4 * missing the browser shows the img alt text, which is the Unicode emoji.
5 */
6export interface Smiley {
7	file: string;
8	codes: string[];
9	label: string;
10	emoji: string;
11}
12
13export const SMILEYS: Smiley[] = [
14	{ file: '01', codes: [':-)', ':)'], label: 'Content', emoji: '🙂' },
15	{ file: '02', codes: [';-)', ';)'], label: 'Clin d’œil', emoji: '😉' },
16	{ file: '03', codes: [':-(', ':('], label: 'Triste', emoji: '🙁' },
17	{ file: '04', codes: [':-P', ':-p', ':P', ':p'], label: 'Langue', emoji: '😛' },
18	{ file: '05', codes: ['=-O', '=-o'], label: 'Surpris', emoji: '😮' },
19	{ file: '06', codes: [':-*'], label: 'Bisou', emoji: '😘' },
20	{ file: '07', codes: ['>:o'], label: 'Crie', emoji: '😠' },
21	{ file: '08', codes: [':-D', ':D'], label: 'Rire', emoji: '😁' },
22	{ file: '09', codes: [':-$'], label: 'Radin', emoji: '🤑' },
23	{ file: '10', codes: [':-!'], label: 'Gaffe', emoji: '😬' },
24	{ file: '11', codes: [':-['], label: 'Gêné', emoji: '😳' },
25	{ file: '12', codes: ['O:-)'], label: 'Innocent', emoji: '😇' },
26	{ file: '13', codes: [':-\\'], label: 'Indécis', emoji: '😕' },
27	{ file: '14', codes: [":'("], label: 'Pleure', emoji: '😢' },
28	{ file: '15', codes: [':-X', ':-x'], label: 'Bouche cousue', emoji: '🤐' },
29	{ file: '16', codes: ['8-)'], label: 'Cool', emoji: '😎' }
30];
31
32const escape = (text: string) =>
33	text
34		.replace(/&/g, '&')
35		.replace(/</g, '&lt;')
36		.replace(/>/g, '&gt;')
37		.replace(/"/g, '&quot;')
38		.replace(/'/g, '&#039;');
39
40// Codes are matched on already-escaped HTML, so match their escaped form.
41const byEscapedCode = new Map<string, Smiley>();
42for (const smiley of SMILEYS)
43	for (const code of smiley.codes) byEscapedCode.set(escape(code), smiley);
44
45const pattern = new RegExp(
46	// Longest first so "O:-)" wins over ":-)"; codes must not touch letters/digits.
47	`(^|[^\\w])(${[...byEscapedCode.keys()]
48		.sort((a, b) => b.length - a.length)
49		.map((c) => c.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'))
50		.join('|')})(?=$|[^\\w])`,
51	'g'
52);
53
54export function smileyImg(smiley: Smiley) {
55	return `<img class="aim-smiley" src="/smileys/${smiley.file}.gif" alt="${smiley.emoji}" title="${escape(smiley.codes[0])}" width="19" height="19" draggable="false">`;
56}
57
58/**
59 * Replace smiley codes in escaped HTML text. Only text between tags is
60 * touched so attributes (style="color: …") are never rewritten.
61 */
62export function replaceSmileys(html: string): string {
63	return html
64		.split(/(<[^>]*>)/)
65		.map((part) =>
66			part.startsWith('<')
67				? part
68				: part.replace(pattern, (_, before: string, code: string) => {
69						const smiley = byEscapedCode.get(code);
70						return smiley ? before + smileyImg(smiley) : _;
71					})
72		)
73		.join('');
74}

Keyboard shortcuts

Single-key shortcuts are on. ctrl k and esc work whatever this says.

ctrl k :
go to a section, branch, tag, file or repository
?
this list
j k
move the row cursor down / up
enter
open the row under the cursor; on Files, a directory opens or closes in place
↑ ↓ ← → home end
in the file tree (focus on a row): previous / next row, close / open a directory or go to its parent / first entry, first / last row. They never open a file
l h
on Files: open a directory or a file / close a directory or go up to its parent, then to the parent page. Elsewhere: into the side panel (on a merge request, its files) / back to the content; there j k move between its controls
g g G
first / last row
/
filter the list; on Files, find a file anywhere in the repository (esc clears, enter opens the best match)
b
switch branch or tag
g s g f g c g b g m g i g r g a
tabs: summary, files, commits, branches & tags, merge requests, issues, releases, actions (when available)
g h
home
w
wide mode: use the whole width of the screen, or not (remembered)
y
copy a permalink pinned to the commit
d u x
diff: split / unified / collapse or expand all
e E
diff: the whole file in view / every file, with the lines the hunks hide
n
merge request: next note in the diff
esc
close a dialog, leave a field

Branches 3

Tags 8

↑↓ moveenter openesc close