@internetarchive/collection-browser 0.0.1-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (203) hide show
  1. package/.editorconfig +29 -0
  2. package/.github/workflows/ci.yml +26 -0
  3. package/.husky/pre-commit +4 -0
  4. package/LICENSE +661 -0
  5. package/README.md +68 -0
  6. package/demo/app-root.ts +414 -0
  7. package/demo/index.html +26 -0
  8. package/dist/demo/app-root.d.ts +43 -0
  9. package/dist/demo/app-root.js +385 -0
  10. package/dist/demo/app-root.js.map +1 -0
  11. package/dist/index.d.ts +3 -0
  12. package/dist/index.js +3 -0
  13. package/dist/index.js.map +1 -0
  14. package/dist/src/assets/img/icons/audio.d.ts +1 -0
  15. package/dist/src/assets/img/icons/audio.js +9 -0
  16. package/dist/src/assets/img/icons/audio.js.map +1 -0
  17. package/dist/src/assets/img/icons/collection.d.ts +1 -0
  18. package/dist/src/assets/img/icons/collection.js +9 -0
  19. package/dist/src/assets/img/icons/collection.js.map +1 -0
  20. package/dist/src/assets/img/icons/etree.d.ts +1 -0
  21. package/dist/src/assets/img/icons/etree.js +9 -0
  22. package/dist/src/assets/img/icons/etree.js.map +1 -0
  23. package/dist/src/assets/img/icons/images.d.ts +1 -0
  24. package/dist/src/assets/img/icons/images.js +10 -0
  25. package/dist/src/assets/img/icons/images.js.map +1 -0
  26. package/dist/src/assets/img/icons/mediatype/account.d.ts +2 -0
  27. package/dist/src/assets/img/icons/mediatype/account.js +12 -0
  28. package/dist/src/assets/img/icons/mediatype/account.js.map +1 -0
  29. package/dist/src/assets/img/icons/mediatype/audio.d.ts +1 -0
  30. package/dist/src/assets/img/icons/mediatype/audio.js +11 -0
  31. package/dist/src/assets/img/icons/mediatype/audio.js.map +1 -0
  32. package/dist/src/assets/img/icons/mediatype/collection.d.ts +1 -0
  33. package/dist/src/assets/img/icons/mediatype/collection.js +9 -0
  34. package/dist/src/assets/img/icons/mediatype/collection.js.map +1 -0
  35. package/dist/src/assets/img/icons/mediatype/etree copy.d.ts +1 -0
  36. package/dist/src/assets/img/icons/mediatype/etree copy.js +9 -0
  37. package/dist/src/assets/img/icons/mediatype/etree copy.js.map +1 -0
  38. package/dist/src/assets/img/icons/mediatype/etree.d.ts +1 -0
  39. package/dist/src/assets/img/icons/mediatype/etree.js +9 -0
  40. package/dist/src/assets/img/icons/mediatype/etree.js.map +1 -0
  41. package/dist/src/assets/img/icons/mediatype/film.d.ts +1 -0
  42. package/dist/src/assets/img/icons/mediatype/film.js +13 -0
  43. package/dist/src/assets/img/icons/mediatype/film.js.map +1 -0
  44. package/dist/src/assets/img/icons/mediatype/images.d.ts +1 -0
  45. package/dist/src/assets/img/icons/mediatype/images.js +10 -0
  46. package/dist/src/assets/img/icons/mediatype/images.js.map +1 -0
  47. package/dist/src/assets/img/icons/mediatype/livemusic.d.ts +1 -0
  48. package/dist/src/assets/img/icons/mediatype/livemusic.js +7 -0
  49. package/dist/src/assets/img/icons/mediatype/livemusic.js.map +1 -0
  50. package/dist/src/assets/img/icons/mediatype/photos.d.ts +1 -0
  51. package/dist/src/assets/img/icons/mediatype/photos.js +7 -0
  52. package/dist/src/assets/img/icons/mediatype/photos.js.map +1 -0
  53. package/dist/src/assets/img/icons/mediatype/software.d.ts +1 -0
  54. package/dist/src/assets/img/icons/mediatype/software.js +10 -0
  55. package/dist/src/assets/img/icons/mediatype/software.js.map +1 -0
  56. package/dist/src/assets/img/icons/mediatype/texts.d.ts +1 -0
  57. package/dist/src/assets/img/icons/mediatype/texts.js +10 -0
  58. package/dist/src/assets/img/icons/mediatype/texts.js.map +1 -0
  59. package/dist/src/assets/img/icons/mediatype/tv.d.ts +1 -0
  60. package/dist/src/assets/img/icons/mediatype/tv.js +9 -0
  61. package/dist/src/assets/img/icons/mediatype/tv.js.map +1 -0
  62. package/dist/src/assets/img/icons/mediatype/video.d.ts +1 -0
  63. package/dist/src/assets/img/icons/mediatype/video.js +10 -0
  64. package/dist/src/assets/img/icons/mediatype/video.js.map +1 -0
  65. package/dist/src/assets/img/icons/mediatype/web.d.ts +1 -0
  66. package/dist/src/assets/img/icons/mediatype/web.js +10 -0
  67. package/dist/src/assets/img/icons/mediatype/web.js.map +1 -0
  68. package/dist/src/assets/img/icons/software.d.ts +1 -0
  69. package/dist/src/assets/img/icons/software.js +10 -0
  70. package/dist/src/assets/img/icons/software.js.map +1 -0
  71. package/dist/src/assets/img/icons/texts.d.ts +1 -0
  72. package/dist/src/assets/img/icons/texts.js +10 -0
  73. package/dist/src/assets/img/icons/texts.js.map +1 -0
  74. package/dist/src/assets/img/icons/tv.d.ts +1 -0
  75. package/dist/src/assets/img/icons/tv.js +9 -0
  76. package/dist/src/assets/img/icons/tv.js.map +1 -0
  77. package/dist/src/assets/img/icons/video.d.ts +1 -0
  78. package/dist/src/assets/img/icons/video.js +10 -0
  79. package/dist/src/assets/img/icons/video.js.map +1 -0
  80. package/dist/src/assets/img/icons/web.d.ts +1 -0
  81. package/dist/src/assets/img/icons/web.js +10 -0
  82. package/dist/src/assets/img/icons/web.js.map +1 -0
  83. package/dist/src/circular-activity-indicator.d.ts +5 -0
  84. package/dist/src/circular-activity-indicator.js +66 -0
  85. package/dist/src/circular-activity-indicator.js.map +1 -0
  86. package/dist/src/collection-browser.d.ts +151 -0
  87. package/dist/src/collection-browser.js +697 -0
  88. package/dist/src/collection-browser.js.map +1 -0
  89. package/dist/src/collection-facets.d.ts +34 -0
  90. package/dist/src/collection-facets.js +245 -0
  91. package/dist/src/collection-facets.js.map +1 -0
  92. package/dist/src/mediatype-icon.d.ts +9 -0
  93. package/dist/src/mediatype-icon.js +89 -0
  94. package/dist/src/mediatype-icon.js.map +1 -0
  95. package/dist/src/models.d.ts +23 -0
  96. package/dist/src/models.js +2 -0
  97. package/dist/src/models.js.map +1 -0
  98. package/dist/src/sort-filter-bar/alpha-bar.d.ts +10 -0
  99. package/dist/src/sort-filter-bar/alpha-bar.js +88 -0
  100. package/dist/src/sort-filter-bar/alpha-bar.js.map +1 -0
  101. package/dist/src/sort-filter-bar/sort-filter-bar.d.ts +24 -0
  102. package/dist/src/sort-filter-bar/sort-filter-bar.js +257 -0
  103. package/dist/src/sort-filter-bar/sort-filter-bar.js.map +1 -0
  104. package/dist/src/tiles/grid/account-tile.d.ts +7 -0
  105. package/dist/src/tiles/grid/account-tile.js +144 -0
  106. package/dist/src/tiles/grid/account-tile.js.map +1 -0
  107. package/dist/src/tiles/grid/collection-tile.d.ts +7 -0
  108. package/dist/src/tiles/grid/collection-tile.js +160 -0
  109. package/dist/src/tiles/grid/collection-tile.js.map +1 -0
  110. package/dist/src/tiles/grid/icons/account.d.ts +1 -0
  111. package/dist/src/tiles/grid/icons/account.js +12 -0
  112. package/dist/src/tiles/grid/icons/account.js.map +1 -0
  113. package/dist/src/tiles/grid/icons/favorite-filled.d.ts +1 -0
  114. package/dist/src/tiles/grid/icons/favorite-filled.js +11 -0
  115. package/dist/src/tiles/grid/icons/favorite-filled.js.map +1 -0
  116. package/dist/src/tiles/grid/icons/reviews.d.ts +1 -0
  117. package/dist/src/tiles/grid/icons/reviews.js +11 -0
  118. package/dist/src/tiles/grid/icons/reviews.js.map +1 -0
  119. package/dist/src/tiles/grid/icons/upload.d.ts +1 -0
  120. package/dist/src/tiles/grid/icons/upload.js +12 -0
  121. package/dist/src/tiles/grid/icons/upload.js.map +1 -0
  122. package/dist/src/tiles/grid/icons/views.d.ts +2 -0
  123. package/dist/src/tiles/grid/icons/views.js +11 -0
  124. package/dist/src/tiles/grid/icons/views.js.map +1 -0
  125. package/dist/src/tiles/grid/item-tile.d.ts +9 -0
  126. package/dist/src/tiles/grid/item-tile.js +240 -0
  127. package/dist/src/tiles/grid/item-tile.js.map +1 -0
  128. package/dist/src/tiles/list/tile-list-compact.d.ts +16 -0
  129. package/dist/src/tiles/list/tile-list-compact.js +125 -0
  130. package/dist/src/tiles/list/tile-list-compact.js.map +1 -0
  131. package/dist/src/tiles/list/tile-list-detail.d.ts +17 -0
  132. package/dist/src/tiles/list/tile-list-detail.js +181 -0
  133. package/dist/src/tiles/list/tile-list-detail.js.map +1 -0
  134. package/dist/src/tiles/list/tile-list.d.ts +21 -0
  135. package/dist/src/tiles/list/tile-list.js +229 -0
  136. package/dist/src/tiles/list/tile-list.js.map +1 -0
  137. package/dist/src/tiles/loading-tile.d.ts +5 -0
  138. package/dist/src/tiles/loading-tile.js +73 -0
  139. package/dist/src/tiles/loading-tile.js.map +1 -0
  140. package/dist/src/tiles/tile-dispatcher.d.ts +27 -0
  141. package/dist/src/tiles/tile-dispatcher.js +160 -0
  142. package/dist/src/tiles/tile-dispatcher.js.map +1 -0
  143. package/dist/src/utils/format-count.d.ts +7 -0
  144. package/dist/src/utils/format-count.js +76 -0
  145. package/dist/src/utils/format-count.js.map +1 -0
  146. package/dist/src/utils/format-date.d.ts +2 -0
  147. package/dist/src/utils/format-date.js +24 -0
  148. package/dist/src/utils/format-date.js.map +1 -0
  149. package/dist/src/utils/format-string.d.ts +2 -0
  150. package/dist/src/utils/format-string.js +7 -0
  151. package/dist/src/utils/format-string.js.map +1 -0
  152. package/dist/test/collection-browser.test.d.ts +0 -0
  153. package/dist/test/collection-browser.test.js +3 -0
  154. package/dist/test/collection-browser.test.js.map +1 -0
  155. package/dist/test/utils/format-count.test.d.ts +1 -0
  156. package/dist/test/utils/format-count.test.js +24 -0
  157. package/dist/test/utils/format-count.test.js.map +1 -0
  158. package/dist/test/utils/format-date.test.d.ts +1 -0
  159. package/dist/test/utils/format-date.test.js +18 -0
  160. package/dist/test/utils/format-date.test.js.map +1 -0
  161. package/dist/test/utils/format-string.test.d.ts +1 -0
  162. package/dist/test/utils/format-string.test.js +17 -0
  163. package/dist/test/utils/format-string.test.js.map +1 -0
  164. package/index.ts +3 -0
  165. package/package.json +95 -0
  166. package/src/assets/img/icons/mediatype/account.ts +12 -0
  167. package/src/assets/img/icons/mediatype/audio.ts +11 -0
  168. package/src/assets/img/icons/mediatype/collection.ts +9 -0
  169. package/src/assets/img/icons/mediatype/etree.ts +9 -0
  170. package/src/assets/img/icons/mediatype/film.ts +13 -0
  171. package/src/assets/img/icons/mediatype/foo.svg +5 -0
  172. package/src/assets/img/icons/mediatype/images.ts +10 -0
  173. package/src/assets/img/icons/mediatype/software.ts +10 -0
  174. package/src/assets/img/icons/mediatype/texts.ts +10 -0
  175. package/src/assets/img/icons/mediatype/tv.ts +9 -0
  176. package/src/assets/img/icons/mediatype/video.ts +10 -0
  177. package/src/assets/img/icons/mediatype/web.ts +10 -0
  178. package/src/circular-activity-indicator.ts +64 -0
  179. package/src/collection-browser.ts +756 -0
  180. package/src/collection-facets.ts +285 -0
  181. package/src/mediatype-icon.ts +83 -0
  182. package/src/models.ts +25 -0
  183. package/src/sort-filter-bar/alpha-bar.ts +86 -0
  184. package/src/sort-filter-bar/sort-filter-bar.ts +256 -0
  185. package/src/tiles/grid/account-tile.ts +141 -0
  186. package/src/tiles/grid/collection-tile.ts +157 -0
  187. package/src/tiles/grid/icons/account.ts +12 -0
  188. package/src/tiles/grid/icons/favorite-filled.ts +11 -0
  189. package/src/tiles/grid/icons/reviews.ts +11 -0
  190. package/src/tiles/grid/icons/upload.ts +12 -0
  191. package/src/tiles/grid/icons/views.ts +11 -0
  192. package/src/tiles/grid/item-tile.ts +254 -0
  193. package/src/tiles/list/tile-list.ts +227 -0
  194. package/src/tiles/loading-tile.ts +70 -0
  195. package/src/tiles/tile-dispatcher.ts +160 -0
  196. package/src/utils/format-count.ts +95 -0
  197. package/src/utils/format-date.ts +36 -0
  198. package/test/collection-browser.test.ts +1 -0
  199. package/test/utils/format-count.test.ts +32 -0
  200. package/test/utils/format-date.test.ts +22 -0
  201. package/tsconfig.json +20 -0
  202. package/web-dev-server.config.mjs +28 -0
  203. package/web-test-runner.config.mjs +41 -0
@@ -0,0 +1,256 @@
1
+ import { SortParam } from '@internetarchive/search-service';
2
+ import { LitElement, html, css, nothing, PropertyValues } from 'lit';
3
+ import { customElement, property, state } from 'lit/decorators.js';
4
+ import { CollectionDisplayMode } from '../models';
5
+ import './alpha-bar';
6
+
7
+ @customElement('sort-filter-bar')
8
+ export class SortFilterBar extends LitElement {
9
+ @property({ type: String }) displayMode: CollectionDisplayMode = 'grid';
10
+
11
+ @property({ type: String }) sortDirection: 'asc' | 'desc' = 'desc';
12
+
13
+ @property({ type: String }) sortField = 'week';
14
+
15
+ @state() titleSelectorVisible: boolean = false;
16
+
17
+ @state() creatorSelectorVisible: boolean = false;
18
+
19
+ @state() dateSortSelectorVisible = false;
20
+
21
+ render() {
22
+ return html`
23
+ <div id="sort-bar">
24
+ <div id="sort-selector">
25
+ <ul>
26
+ <li>
27
+ <button
28
+ @click=${() => {
29
+ this.sortDirection = 'desc';
30
+ }}
31
+ >
32
+ Desc
33
+ </button>
34
+ <button
35
+ @click=${() => {
36
+ this.sortDirection = 'asc';
37
+ }}
38
+ >
39
+ Asc</button
40
+ >Sort By
41
+ </li>
42
+ <li>
43
+ <button
44
+ @click=${() => {
45
+ this.sortField = 'week';
46
+ }}
47
+ >
48
+ Views
49
+ </button>
50
+ </li>
51
+ <li>
52
+ <button
53
+ @click=${() => {
54
+ this.titleSelectorVisible = !this.titleSelectorVisible;
55
+ this.sortField = 'titleSorter';
56
+ }}
57
+ >
58
+ Title
59
+ </button>
60
+ </li>
61
+ <li>
62
+ <button
63
+ @click=${() => {
64
+ this.dateSortSelectorVisible = !this.dateSortSelectorVisible;
65
+ }}
66
+ >
67
+ Date Archived
68
+ </button>
69
+ </li>
70
+ <li>
71
+ <button
72
+ @click=${() => {
73
+ this.creatorSelectorVisible = !this.creatorSelectorVisible;
74
+ this.sortField = 'creatorSorter';
75
+ }}
76
+ >
77
+ Creator
78
+ </button>
79
+ </li>
80
+ </ul>
81
+ </div>
82
+
83
+ <div id="display-style">
84
+ <ul>
85
+ ${this.displayMode !== 'grid'
86
+ ? html`<li>
87
+ <input type="checkbox" @click=${this.detailSelected} />
88
+ Details
89
+ </li>`
90
+ : nothing}
91
+
92
+ <li>
93
+ <button id="grid-button" @click=${this.gridSelected}>Grid</button>
94
+ </li>
95
+ <li>
96
+ <button id="list-button" @click=${this.listSelected}>List</button>
97
+ </li>
98
+ </ul>
99
+ </div>
100
+ </div>
101
+
102
+ ${this.dateSortSelectorVisible ? this.dateSortSelector : nothing}
103
+ ${this.titleSelectorVisible ? this.titleSelectorBar : nothing}
104
+ ${this.creatorSelectorVisible ? this.creatorSelectorBar : nothing}
105
+ `;
106
+ }
107
+
108
+ updated(changed: PropertyValues) {
109
+ if (changed.has('displayMode')) {
110
+ this.displayModeChanged();
111
+ }
112
+
113
+ if (changed.has('sortDirection') || changed.has('sortField')) {
114
+ this.sortChanged();
115
+ }
116
+ }
117
+
118
+ private get dateSortSelector() {
119
+ return html`
120
+ <div id="date-sort-selector">
121
+ <ul>
122
+ <li>
123
+ <button
124
+ @click=${() => {
125
+ this.sortField = 'publicdate';
126
+ }}
127
+ >
128
+ Date Archived
129
+ </button>
130
+ </li>
131
+ <li>
132
+ <button
133
+ @click=${() => {
134
+ this.sortField = 'date';
135
+ }}
136
+ >
137
+ Date Published
138
+ </button>
139
+ </li>
140
+ <li>
141
+ <button
142
+ @click=${() => {
143
+ this.sortField = 'reviewdate';
144
+ }}
145
+ >
146
+ Date Reviewed
147
+ </button>
148
+ </li>
149
+ <li>
150
+ <button
151
+ @click=${() => {
152
+ this.sortField = 'addeddate';
153
+ }}
154
+ >
155
+ Date Added
156
+ </button>
157
+ </li>
158
+ </ul>
159
+ </div>
160
+ `;
161
+ }
162
+
163
+ private get titleSelectorBar() {
164
+ return html` <alpha-bar
165
+ headline="Title Starts With"
166
+ @letterChanged=${this.titleLetterChanged}
167
+ ></alpha-bar>`;
168
+ }
169
+
170
+ private get creatorSelectorBar() {
171
+ return html` <alpha-bar
172
+ headline="Creator Starts With"
173
+ @letterChanged=${this.creatorLetterChanged}
174
+ ></alpha-bar>`;
175
+ }
176
+
177
+ private titleLetterChanged(
178
+ e: CustomEvent<{ selectedLetter: string | undefined }>
179
+ ) {
180
+ const event = new CustomEvent('titleLetterChanged', {
181
+ detail: { selectedLetter: e.detail.selectedLetter },
182
+ });
183
+ this.dispatchEvent(event);
184
+ }
185
+
186
+ private creatorLetterChanged(
187
+ e: CustomEvent<{ selectedLetter: string | undefined }>
188
+ ) {
189
+ const event = new CustomEvent('creatorLetterChanged', {
190
+ detail: { selectedLetter: e.detail.selectedLetter },
191
+ });
192
+ this.dispatchEvent(event);
193
+ }
194
+
195
+ private gridSelected() {
196
+ this.displayMode = 'grid';
197
+ }
198
+
199
+ private listSelected() {
200
+ this.displayMode = 'list-compact';
201
+ }
202
+
203
+ private detailSelected(e: Event) {
204
+ this.displayMode = (e.target as HTMLInputElement).checked
205
+ ? 'list-detail'
206
+ : 'list-compact';
207
+ }
208
+
209
+ private displayModeChanged() {
210
+ const event = new CustomEvent('displayModeChanged', {
211
+ detail: { displayMode: this.displayMode },
212
+ });
213
+ this.dispatchEvent(event);
214
+ }
215
+
216
+ private sortChanged() {
217
+ const sort = new SortParam(this.sortField, this.sortDirection);
218
+ const event = new CustomEvent('sortChanged', {
219
+ detail: { sort },
220
+ });
221
+ this.dispatchEvent(event);
222
+ }
223
+
224
+ static styles = css`
225
+ #sort-bar {
226
+ display: flex;
227
+ justify-content: space-between;
228
+ }
229
+
230
+ ul {
231
+ list-style: none;
232
+ display: flex;
233
+ margin: 0;
234
+ padding: 0;
235
+ align-items: center;
236
+ }
237
+
238
+ li {
239
+ padding: 0.5rem 0 0.5rem 0;
240
+ }
241
+
242
+ #sort-selector li::after {
243
+ content: '•';
244
+ padding-left: 1rem;
245
+ padding-right: 1rem;
246
+ }
247
+
248
+ #sort-selector li:first-child::after {
249
+ content: '';
250
+ }
251
+
252
+ #sort-selector li:last-child::after {
253
+ content: '';
254
+ }
255
+ `;
256
+ }
@@ -0,0 +1,141 @@
1
+ import { css, html, LitElement } from 'lit';
2
+ import { customElement, property } from 'lit/decorators.js';
3
+ import { TileModel } from '../../models';
4
+
5
+ import { accountIcon } from './icons/account';
6
+ import { favoriteFilledIcon } from './icons/favorite-filled';
7
+ import { reviewsIcon } from './icons/reviews';
8
+ import { uploadIcon } from './icons/upload';
9
+
10
+ @customElement('account-tile')
11
+ export class UserTile extends LitElement {
12
+ @property({ type: Object }) model?: TileModel;
13
+
14
+ render() {
15
+ return html`
16
+ <div class="outer-holder">
17
+ <div class="inner-holder">
18
+ <div id="header-holder">
19
+ <div id="title-holder">
20
+ <h1>${this.model?.identifier}</h1>
21
+ </div>
22
+ <div id="avatar-holder">
23
+ <div
24
+ id="avatar"
25
+ style="background-image: url('https://archive.org/services/img/${this
26
+ .model?.identifier}')"
27
+ ></div>
28
+ </div>
29
+ </div>
30
+ <div id="year-holder">
31
+ <div id="archivist-since">
32
+ <h3>Archivist Since</h3>
33
+ </div>
34
+ <div id="year-holder">
35
+ <h3>${this.model?.dateAdded?.getFullYear()}</h3>
36
+ </div>
37
+ </div>
38
+ <div id="status-holder">
39
+ <div id="patron-icon">${accountIcon}</div>
40
+ <div class="stat-icon">
41
+ ${uploadIcon}
42
+ <h3>${this.model?.itemCount}</h3>
43
+ </div>
44
+ <div class="stat-icon">
45
+ ${favoriteFilledIcon}
46
+ <h3>${this.model?.favCount}</h3>
47
+ </div>
48
+ <div class="stat-icon">
49
+ ${reviewsIcon}
50
+ <h3>${this.model?.commentCount}</h3>
51
+ </div>
52
+ </div>
53
+ </div>
54
+ </div>
55
+ `;
56
+ }
57
+
58
+ static get styles() {
59
+ return css`
60
+ h1 {
61
+ color: black;
62
+ font-size: 16px;
63
+ margin: 0;
64
+ }
65
+
66
+ h3 {
67
+ font-size: 14px;
68
+ font-weight: bold;
69
+ color: #2c2c2c;
70
+ margin: 0px;
71
+ }
72
+
73
+ .outer-holder {
74
+ background-color: #fcf5e6;
75
+ border: 1px #2c2c2c;
76
+ border-radius: 4px;
77
+ box-shadow: 1px 1px 2px 0px;
78
+ height: 100%;
79
+ display: flex;
80
+ text-align: center;
81
+ width: 100%;
82
+ }
83
+
84
+ .inner-holder {
85
+ padding: 5px;
86
+ width: 100%;
87
+ display: flex;
88
+ flex-direction: column;
89
+ }
90
+
91
+ #header-holder {
92
+ flex: 1;
93
+ }
94
+
95
+ #title-holder {
96
+ height: 40px;
97
+ margin-bottom: 5px;
98
+ }
99
+
100
+ #avatar-holder {
101
+ margin-bottom: 5px;
102
+ display: flex;
103
+ align-items: center;
104
+ justify-content: center;
105
+ }
106
+
107
+ #avatar {
108
+ background-position: 50% 50%;
109
+ border-radius: 50%;
110
+ width: 160px;
111
+ height: 160px;
112
+ box-shadow: 1px 1px 2px #888888;
113
+ }
114
+
115
+ #year-holder {
116
+ margin-bottom: 5px;
117
+ height: 40px;
118
+ }
119
+
120
+ #year-holder {
121
+ margin: 0px;
122
+ }
123
+
124
+ #status-holder {
125
+ height: 25px;
126
+ display: flex;
127
+ justify-content: space-evenly;
128
+ }
129
+
130
+ #patron-icon {
131
+ height: 25px;
132
+ width: 25px;
133
+ }
134
+
135
+ .stat-icon {
136
+ height: 10px;
137
+ width: 10px;
138
+ }
139
+ `;
140
+ }
141
+ }
@@ -0,0 +1,157 @@
1
+ import { localized, msg } from '@lit/localize';
2
+ import { css, CSSResultGroup, html, LitElement } from 'lit';
3
+ import { customElement, property } from 'lit/decorators.js';
4
+ import { collectionIcon } from '../../assets/img/icons/mediatype/collection';
5
+ import { TileModel } from '../../models';
6
+
7
+ @localized()
8
+ @customElement('collection-tile')
9
+ export class CollectionTile extends LitElement {
10
+ @property({ type: Object }) model?: TileModel;
11
+
12
+ render() {
13
+ return html`
14
+ <div id="container">
15
+ <div id="collection-image-title">
16
+ <div id="collection-title">${this.model?.title}</div>
17
+ <div id="collection-image-container">
18
+ <div
19
+ id="collection-image"
20
+ style="background-image:url('https://archive.org/services/img/${this
21
+ .model?.identifier}')"
22
+ ></div>
23
+ </div>
24
+ </div>
25
+ <div id="item-count-container">
26
+ <div id="item-count-image-container">${collectionIcon}</div>
27
+ <div id="item-count-stacked-text">
28
+ <div id="item-count">${this.model?.itemCount.toLocaleString()}</div>
29
+ <div id="items-text">${msg('items')}</div>
30
+ </div>
31
+ </div>
32
+ </div>
33
+ `;
34
+ }
35
+
36
+ static get styles(): CSSResultGroup {
37
+ const cornerRadiusCss = css`var(--collectionTileCornerRadius, 4px)`;
38
+
39
+ return css`
40
+ #collection-image-container {
41
+ display: flex;
42
+ justify-content: center;
43
+ flex: 1;
44
+ }
45
+
46
+ #collection-image {
47
+ width: 16rem;
48
+ height: 16rem;
49
+ border-radius: 0.8rem;
50
+ overflow: hidden;
51
+ box-shadow: 1px 1px 2px 0px;
52
+ object-fit: cover;
53
+ background-position: center;
54
+ background-size: cover;
55
+ }
56
+
57
+ #item-count-image-container svg {
58
+ filter: invert(100%);
59
+ }
60
+
61
+ #collection-image-title {
62
+ background-color: #666;
63
+ border: 1px solid #2c2c2c;
64
+ padding: 0.5rem;
65
+ border-top-left-radius: ${cornerRadiusCss};
66
+ border-top-right-radius: ${cornerRadiusCss};
67
+ display: flex;
68
+ flex-direction: column;
69
+ flex: 1;
70
+ }
71
+
72
+ #collection-title {
73
+ font-weight: bold;
74
+ color: #fff;
75
+ font-size: 1.6rem;
76
+ text-align: center;
77
+ margin-bottom: 0.5rem;
78
+ overflow: hidden;
79
+ text-overflow: ellipsis;
80
+ display: -webkit-box;
81
+ -webkit-line-clamp: 2;
82
+ -webkit-box-orient: vertical;
83
+ line-height: 2rem;
84
+ height: 4rem;
85
+ }
86
+
87
+ #container {
88
+ box-shadow: 1px 1px 2px 0px;
89
+ border-radius: ${cornerRadiusCss};
90
+ height: 100%;
91
+ display: flex;
92
+ flex-direction: column;
93
+ }
94
+
95
+ #container:hover > #collection-image-title > #collection-title {
96
+ text-decoration: underline;
97
+ }
98
+
99
+ /* this is a workaround for Safari 15 where the hover effects are not working */
100
+ #collection-image-title:hover > #collection-title {
101
+ text-decoration: underline;
102
+ }
103
+
104
+ #container:hover > #collection-image-title {
105
+ background-color: #757575;
106
+ }
107
+
108
+ #item-count-container {
109
+ background-color: #444;
110
+ border-bottom: 1px solid #2c2c2c;
111
+ border-left: 1px solid #2c2c2c;
112
+ border-right: 1px solid #2c2c2c;
113
+ border-bottom-left-radius: ${cornerRadiusCss};
114
+ border-bottom-right-radius: ${cornerRadiusCss};
115
+ display: flex;
116
+ padding: 0rem 0.5rem;
117
+ height: 5.5rem;
118
+ align-items: center;
119
+ }
120
+
121
+ #item-count-image-container {
122
+ margin-right: 0.5rem;
123
+ }
124
+
125
+ #item-count-stacked-text {
126
+ display: flex;
127
+ align-items: baseline;
128
+ color: #fff;
129
+ }
130
+ #item-count-image-container svg {
131
+ height: 2.5rem;
132
+ align-items: baseline;
133
+ }
134
+
135
+ #container:hover > #item-count-container {
136
+ background-color: #575757;
137
+ }
138
+
139
+ #item-count {
140
+ font-size: 1.4rem;
141
+ font-weight: bold;
142
+ }
143
+
144
+ #item-count-image {
145
+ width: 3rem;
146
+ height: 3rem;
147
+ margin-right: 1rem;
148
+ }
149
+
150
+ #items-text {
151
+ font-size: 1.4rem;
152
+ font-weight: bold;
153
+ margin-left: 0.5rem;
154
+ }
155
+ `;
156
+ }
157
+ }
@@ -0,0 +1,12 @@
1
+ import { svg } from 'lit';
2
+
3
+ export const accountIcon = svg`
4
+ <svg viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
5
+ <path
6
+ d="m89.6854559 79.6500588c1.7300364 6.4823648 2.180423 13.3122689 3.3145441 20.3499412h-86c.5683151-15.8558542 2.98334063-30.7849367 15.1676149-41.6581341 22.9948067-20.518674 59.250299-9.0032844 67.517841 21.3081929zm-40.0998307-79.6500588c10.872402.0493248 19.9700408 9.25722341 19.917959 20.1421788-.0829413 11.042868-8.9616237 19.8492523-20.0602807 19.8578212-11.1181198 0-19.9397193-8.7904706-19.9397193-19.8908727-.0327543-11.11998815 9.0125781-20.17487063 20.082041-20.1091273z"
7
+ fill="#333"
8
+ fill-rule="evenodd"
9
+ />
10
+ <title>Icon of a person</title>
11
+ </svg>
12
+ `;
@@ -0,0 +1,11 @@
1
+ import { svg } from 'lit';
2
+
3
+ export const favoriteFilledIcon = svg`
4
+ <svg viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
5
+ <path
6
+ d="m81.0388846 100-30.9636029-22.5595033-30.7410319 22.5595033 10.6670595-37.3922042-30.0013093-25.2155916h37.5556428l12.5196389-37.3922042 12.3690754 37.3922042h37.5556429l-29.7034563 25.2155916z"
7
+ fill="#333"
8
+ />
9
+ <title>Icon of a star, filled in</title>
10
+ </svg>
11
+ `;
@@ -0,0 +1,11 @@
1
+ import { svg } from 'lit';
2
+
3
+ export const reviewsIcon = svg`
4
+ <svg viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
5
+ <path
6
+ d="m100 7.78013601c0-2.14552613-.7593357-3.978597-2.278007-5.4992126-1.5186713-1.52061561-3.3493984-2.28092341-5.4921813-2.28092341h-84.54977287c-2.08268321 0-3.88336049.7603078-5.40203183 2.28092341-1.51867133 1.5206156-2.278007 3.35368647-2.278007 5.4992126v51.49262709c0 2.0853495.75933567 3.8883321 2.278007 5.4089477 1.51867134 1.5206156 3.31934862 2.2809234 5.40203183 2.2809234h10.53361537l.3571304 33.0373658 32.4087237-33.0373658h41.2468361c2.1427829 0 3.97351-.7603078 5.4921813-2.2809234s2.278007-3.3235982 2.278007-5.4089477z"
7
+ fill="#333"
8
+ />
9
+ <title>Icon of a speech bubble</title>
10
+ </svg>
11
+ `;
@@ -0,0 +1,12 @@
1
+ import { svg } from 'lit';
2
+
3
+ export const uploadIcon = svg`
4
+ <svg viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
5
+ <path
6
+ d="m50 20 33.3333333 43.3333333h-20v36.6666667h-26.6666666v-36.6666667h-20zm50-20v13.3333333h-100v-13.3333333z"
7
+ fill="#333"
8
+ fill-rule="evenodd"
9
+ />
10
+ <title>Icon of an arrow pointing upwards</title>
11
+ </svg>
12
+ `;
@@ -0,0 +1,11 @@
1
+ import { html } from 'lit';
2
+
3
+ export default html`
4
+ <svg viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
5
+ <path
6
+ d="m98 50.5704143c-.2830293-.471515-.671154-1.1088947-1.1643742-1.9121392s-1.6003642-2.3617474-3.3214321-4.6755089c-1.7210678-2.3137614-3.522258-4.5325939-5.4035703-6.6564975-1.8813124-2.1239037-4.2828993-4.473133-7.2047606-7.0476881-2.9218612-2.5745551-5.8895067-4.7933876-8.9029363-6.6564976-3.0134295-1.86311-6.4628491-3.4330878-10.3482587-4.7099336-3.8854095-1.2768458-7.7822651-1.9142256-11.6905667-1.9121443-3.9083017.0020914-7.8051573.6154781-11.6905668 1.8401652-3.8854096 1.2246871-7.3702078 2.8301329-10.4543947 4.8163375-3.0841869 1.9862045-6.0278997 4.1695691-8.8311384 6.5500937s-5.2048256 4.7652219-7.2047605 7.1540919c-1.99993501 2.38887-3.75430043 4.5722346-5.26309632 6.5500938s-2.63883199 3.583305-3.39010829 4.8163374l-1.13003609 1.8401602c.2830293.4715149.67115403 1.1088946 1.16437421 1.9121391.49322017.8032445 1.5878776 2.3617475 3.28397229 4.6755089s3.47439274 4.521119 5.3348942 6.6220728c1.8605014 2.1009538 4.2506422 4.4387083 7.1704224 7.0132633 2.9197801 2.5745551 5.8874256 4.7819127 8.9029363 6.6220729 3.0155106 1.8401601 6.4774168 3.398663 10.3857184 4.6755088 3.9083017 1.2768458 7.8176438 1.9142256 11.7280266 1.9121443 3.9103827-.0020914 7.7957922-.6154781 11.6562286-1.8401652s7.3337886-2.818658 10.4200566-4.7819127 6.0299808-4.1351444 8.8311384-6.515669 5.2152311-4.7652219 7.2422203-7.1540919 3.8052873-4.5607597 5.3348942-6.515669c1.5296068-1.9549093 2.6721295-3.5488802 3.427568-4.7819127zm-24.5142913 0c0 6.467683-2.3079374 12.0152859-6.9238123 16.6428087s-10.1495139 6.9412843-16.600917 6.9412843c-6.4992683 0-12.0453939-2.3137615-16.6383767-6.9412843s-6.8894742-10.1751257-6.8894742-16.6428087 2.2964914-12.003811 6.8894742-16.608384 10.1391084-6.9068595 16.6383767-6.9068595c6.4534842 0 11.9871232 2.3022865 16.600917 6.9068595s6.9217312 10.140701 6.9238123 16.608384zm-23.5247293-10.552755c2.8261308 0 5.2870289 1.0619518 7.3826944 3.1858555 2.0956655 2.1239036 3.1434982 4.5795368 3.1434982 7.3668995 0 2.8332624-1.0478327 5.2888956-3.1434982 7.3668995-2.0956655 2.078004-4.5565636 3.1170059-7.3826944 3.1170059-2.873996 0-5.3348941-1.0264838-7.3826944-3.0794516-2.0478002-2.0529677-3.0717003-4.5200758-3.0717003-7.4013243 0-2.8332624 1.0239001-5.3003705 3.0717003-7.4013243 2.0478003-2.1009538 4.5086984-3.1514307 7.3826944-3.1514307z"
7
+ fill="#333"
8
+ />
9
+ <title>Eye icon</title>
10
+ </svg>
11
+ `;