1 | Gerrit.install(plugin => {
|
---|
2 | const style = document.createElement('style');
|
---|
3 | style.innerHTML = `
|
---|
4 | @font-face {
|
---|
5 | font-family: 'Material Symbols Outlined';
|
---|
6 | font-style: normal;
|
---|
7 | src: url('https://haiku.movingborders.es/testbuild/test/material-icons.woff') format('woff');
|
---|
8 | }
|
---|
9 | `;
|
---|
10 | document.head.appendChild(style);
|
---|
11 |
|
---|
12 | // Full list: https://github.com/google/material-design-icons/blob/master/variablefont/MaterialSymbolsOutlined%5BFILL%2CGRAD%2Copsz%2Cwght%5D.codepoints
|
---|
13 | const ligatures = {
|
---|
14 | 'alternate_email': '\ue0e6',
|
---|
15 | 'arrow_drop_down': '\ue5c5',
|
---|
16 | 'arrow_drop_up': '\ue5c7',
|
---|
17 | 'arrow_forward': '\ue5c8',
|
---|
18 | 'arrow_right_alt': '\ue941',
|
---|
19 | 'block': '\uf326',
|
---|
20 | 'bug_report': '\ue868',
|
---|
21 | 'calendar_view_day': '\ue936',
|
---|
22 | 'cancel': '\ue888',
|
---|
23 | 'chat_bubble': '\ue0cb',
|
---|
24 | 'check': '\ue5ca',
|
---|
25 | 'check_circle': '\ue86c',
|
---|
26 | 'chevron_left': '\ue5cb',
|
---|
27 | 'chevron_right': '\ue5cc',
|
---|
28 | 'close': '\ue5cd',
|
---|
29 | 'code': '\ue86f',
|
---|
30 | 'content_copy': '\ue14d',
|
---|
31 | 'delete': '\ue872',
|
---|
32 | 'description': '\ue873',
|
---|
33 | 'done_all': '\ue877',
|
---|
34 | 'download': '\uf090',
|
---|
35 | 'edit': '\uf345',
|
---|
36 | 'empty_dashboard': '\uf844',
|
---|
37 | 'error': '\uf8b6',
|
---|
38 | 'expand': '\ue94f',
|
---|
39 | 'expand_all': '\ue946',
|
---|
40 | 'expand_less': '\ue5ce',
|
---|
41 | 'expand_more': '\ue5cf',
|
---|
42 | 'file_present': '\uea0e',
|
---|
43 | 'filter_alt': '\uef4f',
|
---|
44 | 'help': '\ue8fd',
|
---|
45 | 'history': '\ue8b3',
|
---|
46 | 'image': '\ue3f4',
|
---|
47 | 'info': '\ue88e',
|
---|
48 | 'label_important': '\ue948',
|
---|
49 | 'lightbulb': '\ue90f',
|
---|
50 | 'link': '\ue250',
|
---|
51 | 'mark_chat_read': '\uf18b',
|
---|
52 | 'mode_comment': '\ue253',
|
---|
53 | 'more_horiz': '\ue5d3',
|
---|
54 | 'more_vert': '\ue5d4',
|
---|
55 | 'move_item': '\uf1ff',
|
---|
56 | 'new_releases': '\uef76',
|
---|
57 | 'open_in_new': '\ue89e',
|
---|
58 | 'pause': '\ue034',
|
---|
59 | 'pending_actions': '\uf1bb',
|
---|
60 | 'play_arrow': '\ue037',
|
---|
61 | 'publish': '\ue255',
|
---|
62 | 'published_with_changes': '\uf232',
|
---|
63 | 'rate_review': '\ue560',
|
---|
64 | 'rebase': '\uf845',
|
---|
65 | 'rebase_edit': '\uf846',
|
---|
66 | 'schedule': '\uefd6',
|
---|
67 | 'search': '\ue8b6',
|
---|
68 | 'settings': '\ue8b8',
|
---|
69 | 'star': '\ue838',//\ue885,
|
---|
70 | 'stop': '\ue047',
|
---|
71 | 'style': '\ue41d',
|
---|
72 | 'swap_horiz': '\ue8d4',
|
---|
73 | 'system_update': '\uf072',
|
---|
74 | 'timelapse': '\ue422',
|
---|
75 | 'undo': '\ue166',
|
---|
76 | 'view_column_2': '\uf847',
|
---|
77 | 'visibility': '\ue8f4',
|
---|
78 | 'warning': '\uf083',
|
---|
79 | };
|
---|
80 |
|
---|
81 | function replaceIcon(element) {
|
---|
82 | const name = element.icon;
|
---|
83 | if (name == 'star' || name == '\ue838' || name == '\ue885')
|
---|
84 | element.icon = element.filled ? '\ue838' : '\ue885';
|
---|
85 | else {
|
---|
86 | const glyph = ligatures[name];
|
---|
87 | if (glyph != undefined)
|
---|
88 | element.icon = glyph;
|
---|
89 | else if (name && name.length > 1)
|
---|
90 | console.log('Unknown icon name:', name);
|
---|
91 | }
|
---|
92 | }
|
---|
93 |
|
---|
94 | function newIcon(icon) {
|
---|
95 | replaceIcon(icon);
|
---|
96 | iconObserver.observe(icon, {attributes: true, attributeFilter: ['icon', 'filled']});
|
---|
97 | }
|
---|
98 |
|
---|
99 | function iconMutation(mutationList, observer) {
|
---|
100 | for (const mutation of mutationList)
|
---|
101 | replaceIcon(mutation.target);
|
---|
102 | }
|
---|
103 |
|
---|
104 | function newFragment(fragment) {
|
---|
105 | fragmentObserver.observe(fragment, {childList: true, subtree: true});
|
---|
106 | replaceIcons(fragment);
|
---|
107 | }
|
---|
108 |
|
---|
109 | function replaceIcons(root = document.body) {
|
---|
110 | if (typeof root.querySelectorAll != 'function') return;
|
---|
111 | if (root.nodeName == 'GR-ICON')
|
---|
112 | newIcon(root);
|
---|
113 | else {
|
---|
114 | for (const icon of root.querySelectorAll('GR-ICON'))
|
---|
115 | newIcon(icon);
|
---|
116 | if (root.shadowRoot)
|
---|
117 | newFragment(root.shadowRoot);
|
---|
118 | for (const element of root.querySelectorAll('*')) {
|
---|
119 | if (element.shadowRoot)
|
---|
120 | newFragment(element.shadowRoot);
|
---|
121 | }
|
---|
122 | }
|
---|
123 | }
|
---|
124 |
|
---|
125 | function fragmentMutation(mutationList, observer) {
|
---|
126 | for (const mutation of mutationList) {
|
---|
127 | for (const node of mutation.addedNodes)
|
---|
128 | replaceIcons(node);
|
---|
129 | }
|
---|
130 | }
|
---|
131 |
|
---|
132 | const iconObserver = new MutationObserver(iconMutation);
|
---|
133 |
|
---|
134 | const fragmentObserver = new MutationObserver(fragmentMutation);
|
---|
135 |
|
---|
136 | addEventListener('load', (event) => replaceIcons());
|
---|
137 | });
|
---|