@teipublisher/pb-components 2.26.1-next.3 → 3.0.0-next-4.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 (262) hide show
  1. package/.github/workflows/docker-cypress.yml +54 -0
  2. package/.github/workflows/main.yml +6 -4
  3. package/.github/workflows/node.js.yml +56 -21
  4. package/.github/workflows/release.js.yml +19 -17
  5. package/.releaserc.json +1 -1
  6. package/CHANGELOG.md +346 -11
  7. package/Dockerfile +78 -70
  8. package/README.md +112 -4
  9. package/css/components.css +5 -5
  10. package/css/gridjs/mermaid.min.css +1 -1
  11. package/css/leaflet/Control.Geocoder.css +1 -126
  12. package/css/leaflet/images/layers.png +0 -0
  13. package/css/tify/tify.css +6 -5
  14. package/css/tom-select/tom-select.bootstrap4.min.css +1 -1
  15. package/css/tom-select/tom-select.bootstrap5.min.css +1 -1
  16. package/css/tom-select/tom-select.default.min.css +1 -1
  17. package/css/tom-select/tom-select.default.min.css.map +1 -0
  18. package/css/tom-select/tom-select.min.css +1 -1
  19. package/cypress.config.js +84 -0
  20. package/dist/api.html +1 -1
  21. package/dist/css/design-system.css +607 -0
  22. package/dist/demo/bundle-test.html +4 -3
  23. package/dist/demo/components.css +46 -1
  24. package/dist/demo/design-system.html +710 -0
  25. package/dist/demo/dts-client.html +2 -2
  26. package/dist/demo/pb-autocomplete.html +23 -11
  27. package/dist/demo/pb-autocomplete2.html +66 -55
  28. package/dist/demo/pb-autocomplete3.html +17 -8
  29. package/dist/demo/pb-blacklab-highlight.html +28 -11
  30. package/dist/demo/pb-blacklab-results.html +3 -2
  31. package/dist/demo/pb-browse-docs.html +24 -24
  32. package/dist/demo/pb-browse-docs2.html +3 -3
  33. package/dist/demo/pb-clipboard.html +32 -28
  34. package/dist/demo/pb-code-editor.html +6 -6
  35. package/dist/demo/pb-code-highlight.html +63 -63
  36. package/dist/demo/pb-codepen.html +1 -1
  37. package/dist/demo/pb-collapse.html +1 -1
  38. package/dist/demo/pb-collapse2.html +2 -2
  39. package/dist/demo/pb-combo-box.html +135 -130
  40. package/dist/demo/pb-custom-form.html +64 -55
  41. package/dist/demo/pb-dialog.html +12 -6
  42. package/dist/demo/pb-document.html +1 -1
  43. package/dist/demo/pb-download.html +68 -59
  44. package/dist/demo/pb-drawer.html +67 -46
  45. package/dist/demo/pb-drawer2.html +65 -58
  46. package/dist/demo/pb-edit-app.html +2 -2
  47. package/dist/demo/pb-edit-xml.html +1 -1
  48. package/dist/demo/pb-facsimile-2.html +26 -11
  49. package/dist/demo/pb-facsimile-3.html +25 -10
  50. package/dist/demo/pb-facsimile-dedup-test-2.html +48 -0
  51. package/dist/demo/pb-facsimile-dedup-test.html +48 -0
  52. package/dist/demo/pb-facsimile.html +4 -4
  53. package/dist/demo/pb-formula.html +1 -1
  54. package/dist/demo/pb-grid.html +22 -8
  55. package/dist/demo/pb-highlight.html +2 -2
  56. package/dist/demo/pb-i18n-simple.html +1 -0
  57. package/dist/demo/pb-i18n.html +15 -5
  58. package/dist/demo/pb-image-strip-standalone.html +2 -2
  59. package/dist/demo/pb-image-strip-view.html +2 -2
  60. package/dist/demo/pb-leaflet-map.html +3 -3
  61. package/dist/demo/pb-leaflet-map2.html +2 -2
  62. package/dist/demo/pb-leaflet-map3.html +3 -3
  63. package/dist/demo/pb-link.html +1 -1
  64. package/dist/demo/pb-load.html +2 -6
  65. package/dist/demo/pb-login.html +1 -3
  66. package/dist/demo/pb-manage-odds.html +9 -4
  67. package/dist/demo/pb-markdown.html +1 -1
  68. package/dist/demo/pb-media-query.html +2 -2
  69. package/dist/demo/pb-mei.html +2 -2
  70. package/dist/demo/pb-mei2.html +2 -2
  71. package/dist/demo/pb-message.html +2 -3
  72. package/dist/demo/pb-odd-editor.html +54 -52
  73. package/dist/demo/pb-page-header.html +27 -0
  74. package/dist/demo/pb-popover.html +1 -1
  75. package/dist/demo/pb-print-preview.html +2 -2
  76. package/dist/demo/pb-progress.html +4 -4
  77. package/dist/demo/pb-repeat.html +32 -36
  78. package/dist/demo/pb-search.html +16 -5
  79. package/dist/demo/pb-search2.html +4 -4
  80. package/dist/demo/pb-search3.html +3 -3
  81. package/dist/demo/pb-search4.html +3 -3
  82. package/dist/demo/pb-select-feature.html +4 -4
  83. package/dist/demo/pb-select-feature2.html +4 -4
  84. package/dist/demo/pb-select-feature3.html +2 -2
  85. package/dist/demo/pb-select-i18n.html +58 -53
  86. package/dist/demo/pb-select-odd.html +1 -1
  87. package/dist/demo/pb-select.html +190 -75
  88. package/dist/demo/pb-select2.html +91 -37
  89. package/dist/demo/pb-select3.html +109 -41
  90. package/dist/demo/pb-svg.html +1 -1
  91. package/dist/demo/pb-table-grid.html +26 -15
  92. package/dist/demo/pb-tabs.html +15 -7
  93. package/dist/demo/pb-tify.html +7 -7
  94. package/dist/demo/pb-timeline.html +1 -1
  95. package/dist/demo/pb-timeline2.html +1 -1
  96. package/dist/demo/pb-toggle-feature.html +26 -23
  97. package/dist/demo/pb-toggle-feature2.html +4 -4
  98. package/dist/demo/pb-toggle-feature3.html +2 -2
  99. package/dist/demo/pb-toggle-feature4.html +56 -54
  100. package/dist/demo/pb-version.html +2 -2
  101. package/dist/demo/pb-view.html +78 -40
  102. package/dist/demo/pb-view2.html +69 -46
  103. package/dist/demo/pb-view3.html +53 -48
  104. package/dist/demo/pb-view4.html +70 -49
  105. package/dist/demo/pb-zoom.html +2 -2
  106. package/dist/{es-global-bridge-d8ce175d.js → es-global-bridge-D8ZcUcx_.js} +0 -4
  107. package/dist/focus-mixin-VCsFap6b.js +768 -0
  108. package/dist/images/icons.svg +217 -0
  109. package/dist/jinn-codemirror-DETLdm08.js +1 -0
  110. package/dist/lib/openseadragon.min.js +80 -0
  111. package/dist/lib/openseadragon.min.js.map +1 -0
  112. package/dist/pb-code-editor.js +25 -20
  113. package/dist/pb-component-docs.js +414 -3225
  114. package/dist/pb-components-bundle.js +3046 -4402
  115. package/dist/pb-dialog-tklYGWfc.js +121 -0
  116. package/dist/pb-edit-app.js +208 -107
  117. package/dist/pb-elements.json +716 -249
  118. package/dist/pb-facsimile.js +46 -0
  119. package/dist/pb-i18n-C0NDma4h.js +1 -0
  120. package/dist/pb-leaflet-map.js +23 -23
  121. package/dist/pb-mei.js +152 -134
  122. package/dist/pb-mixin-DHoWQheB.js +1 -0
  123. package/dist/pb-odd-editor.js +1671 -1231
  124. package/dist/pb-tify.js +1 -27
  125. package/dist/unsafe-html-D5VGo9Oq.js +1 -0
  126. package/dist/urls-BEONu_g4.js +1 -0
  127. package/eslint.config.mjs +92 -0
  128. package/gh-pages.js +5 -3
  129. package/i18n/common/en.json +6 -0
  130. package/i18n/common/pl.json +2 -2
  131. package/images/icons.svg +217 -0
  132. package/index.html +0 -5
  133. package/lib/leaflet-src.js.map +1 -0
  134. package/lib/leaflet.markercluster-src.js.map +1 -0
  135. package/lib/openseadragon.min.js +6 -6
  136. package/package.json +56 -81
  137. package/pb-elements.json +716 -249
  138. package/rollup.config.mjs +312 -0
  139. package/src/assets/components.css +5 -5
  140. package/src/assets/design-system.css +607 -0
  141. package/src/authority/airtable.js +20 -21
  142. package/src/authority/anton.js +129 -129
  143. package/src/authority/custom.js +70 -27
  144. package/src/authority/geonames.js +38 -32
  145. package/src/authority/gnd.js +50 -42
  146. package/src/authority/kbga.js +136 -134
  147. package/src/authority/metagrid.js +44 -46
  148. package/src/authority/reconciliation.js +66 -68
  149. package/src/authority/registry.js +4 -4
  150. package/src/docs/demo-utils.js +91 -0
  151. package/src/docs/pb-component-docs.js +287 -147
  152. package/src/docs/pb-component-view.js +380 -273
  153. package/src/docs/pb-components-list.js +115 -51
  154. package/src/docs/pb-demo-snippet.js +199 -174
  155. package/src/dts-client.js +306 -303
  156. package/src/dts-select-endpoint.js +125 -85
  157. package/src/parse-date-service.js +184 -135
  158. package/src/pb-ajax.js +175 -173
  159. package/src/pb-authority-lookup.js +198 -158
  160. package/src/pb-autocomplete.js +731 -313
  161. package/src/pb-blacklab-highlight.js +266 -260
  162. package/src/pb-blacklab-results.js +230 -225
  163. package/src/pb-browse-docs.js +601 -484
  164. package/src/pb-browse.js +68 -65
  165. package/src/pb-clipboard.js +97 -76
  166. package/src/pb-code-editor.js +111 -103
  167. package/src/pb-code-highlight.js +234 -204
  168. package/src/pb-codepen.js +81 -73
  169. package/src/pb-collapse.js +265 -152
  170. package/src/pb-combo-box.js +191 -191
  171. package/src/pb-components-bundle.js +1 -7
  172. package/src/pb-components.js +2 -6
  173. package/src/pb-custom-form.js +230 -141
  174. package/src/pb-dialog.js +99 -63
  175. package/src/pb-document.js +118 -91
  176. package/src/pb-download.js +214 -198
  177. package/src/pb-drawer.js +146 -149
  178. package/src/pb-edit-app.js +471 -240
  179. package/src/pb-edit-xml.js +101 -98
  180. package/src/pb-events.js +126 -107
  181. package/src/pb-facs-link.js +130 -101
  182. package/src/pb-facsimile.js +494 -410
  183. package/src/pb-fetch.js +389 -0
  184. package/src/pb-formula.js +152 -154
  185. package/src/pb-geolocation.js +130 -132
  186. package/src/pb-grid-action.js +59 -56
  187. package/src/pb-grid.js +388 -228
  188. package/src/pb-highlight.js +142 -142
  189. package/src/pb-hotkeys.js +40 -42
  190. package/src/pb-i18n.js +115 -127
  191. package/src/pb-icon-button.js +108 -0
  192. package/src/pb-icon.js +283 -0
  193. package/src/pb-image-strip.js +85 -79
  194. package/src/pb-lang.js +142 -57
  195. package/src/pb-leaflet-map.js +551 -483
  196. package/src/pb-link.js +132 -126
  197. package/src/pb-load.js +495 -428
  198. package/src/pb-login.js +303 -248
  199. package/src/pb-manage-odds.js +384 -338
  200. package/src/pb-map-icon.js +90 -90
  201. package/src/pb-map-layer.js +86 -86
  202. package/src/pb-markdown.js +107 -110
  203. package/src/pb-media-query.js +75 -73
  204. package/src/pb-mei.js +523 -303
  205. package/src/pb-message.js +144 -98
  206. package/src/pb-mixin.js +268 -265
  207. package/src/pb-navigation.js +83 -96
  208. package/src/pb-observable.js +39 -39
  209. package/src/pb-odd-editor.js +1209 -948
  210. package/src/pb-odd-elementspec-editor.js +375 -310
  211. package/src/pb-odd-model-editor.js +1189 -941
  212. package/src/pb-odd-parameter-editor.js +269 -170
  213. package/src/pb-odd-rendition-editor.js +184 -131
  214. package/src/pb-page.js +451 -422
  215. package/src/pb-paginate.js +260 -178
  216. package/src/pb-panel.js +217 -183
  217. package/src/pb-popover-themes.js +16 -9
  218. package/src/pb-popover.js +297 -288
  219. package/src/pb-print-preview.js +128 -128
  220. package/src/pb-progress.js +52 -52
  221. package/src/pb-repeat.js +141 -108
  222. package/src/pb-restricted.js +85 -78
  223. package/src/pb-search.js +258 -230
  224. package/src/pb-select-feature.js +210 -126
  225. package/src/pb-select-odd.js +184 -118
  226. package/src/pb-select-template.js +113 -78
  227. package/src/pb-select.js +330 -229
  228. package/src/pb-split-list.js +181 -176
  229. package/src/pb-svg.js +81 -80
  230. package/src/pb-table-column.js +55 -55
  231. package/src/pb-table-grid.js +334 -205
  232. package/src/pb-tabs.js +238 -61
  233. package/src/pb-tify.js +3331 -126
  234. package/src/pb-timeline.js +394 -255
  235. package/src/pb-toggle-feature.js +196 -188
  236. package/src/pb-upload.js +201 -176
  237. package/src/pb-version.js +22 -34
  238. package/src/pb-view-annotate.js +138 -102
  239. package/src/pb-view.js +1722 -1272
  240. package/src/pb-zoom.js +144 -46
  241. package/src/search-result-service.js +256 -223
  242. package/src/seed-element.js +14 -22
  243. package/src/settings.js +4 -4
  244. package/src/theming.js +98 -91
  245. package/src/urls.js +403 -289
  246. package/src/utils.js +53 -51
  247. package/vite.config.js +86 -0
  248. package/css/pb-styles.css +0 -51
  249. package/dist/iron-form-3b8dcaa7.js +0 -210
  250. package/dist/jinn-codemirror-da0e2d1f.js +0 -1
  251. package/dist/paper-checkbox-515a5284.js +0 -1597
  252. package/dist/paper-icon-button-b1d31571.js +0 -398
  253. package/dist/paper-listbox-a3b7175c.js +0 -1265
  254. package/dist/pb-i18n-0611135a.js +0 -1
  255. package/dist/pb-mixin-b1caa22e.js +0 -158
  256. package/dist/polymer-hack.js +0 -1
  257. package/dist/vaadin-element-mixin-fe4a4883.js +0 -527
  258. package/lib/Control.Geocoder.min.js +0 -2
  259. package/lib/Control.Geocoder.min.js.map +0 -1
  260. package/src/assets/pb-styles.css +0 -51
  261. package/src/pb-light-dom.js +0 -41
  262. package/src/polymer-hack.js +0 -6
@@ -1,19 +1,15 @@
1
- import { html, css } from 'lit-element';
1
+ import { html, css } from 'lit';
2
2
  import { PbLoad } from './pb-load.js';
3
3
  import { waitOnce } from './pb-mixin.js';
4
- import { translate } from "./pb-i18n.js";
5
- import { themableMixin } from "./theming.js";
4
+ import { translate } from './pb-i18n.js';
5
+ import { themableMixin } from './theming.js';
6
6
  import { cmpVersion } from './utils.js';
7
- import { registry } from "./urls.js";
7
+ import { registry } from './urls.js';
8
+ import './pb-icon.js';
9
+ import './pb-dialog.js';
10
+ import './pb-autocomplete.js';
8
11
 
9
- import '@polymer/paper-input/paper-input.js';
10
- import '@polymer/paper-button';
11
- import '@polymer/paper-dropdown-menu/paper-dropdown-menu.js';
12
- import '@polymer/paper-listbox';
13
- import '@polymer/paper-dialog';
14
- import '@polymer/paper-dialog-scrollable';
15
- import '@polymer/iron-ajax';
16
- import '@cwmr/paper-autocomplete/paper-autocomplete-suggestions.js';
12
+ import './pb-fetch.js';
17
13
 
18
14
  /**
19
15
  * Component to browse through a collection of documents with sorting, filtering and facets.
@@ -21,520 +17,641 @@ import '@cwmr/paper-autocomplete/paper-autocomplete-suggestions.js';
21
17
  * @slot toolbar - toolbar area
22
18
  * @slot - unnamed default slot
23
19
  * @slot footer - footer area
24
- *
20
+ *
25
21
  * @fires pb-collection - Sent to inform e.g. pb-upload about current collection
26
22
  * @fires pb-search-resubmit - When received, set facet values as received from the event
27
23
  * @fires pb-login - When received, refresh the view if the user changed
28
- *
24
+ *
29
25
  * @cssprop --pb-search-suggestions-background - Background for the autocomplete suggestions for the filter field
30
26
  * @cssprop --pb-search-suggestions-color - Text color for the autocomplete suggestion for the filter field
31
27
  * @cssprop --pb-search-label-color - Determines the color of small label above the sort by/filter by/filter fields
32
28
  * @cssprop --pb-search-input-color - Determines the color of the text in the sort by/filter by/filter fields
33
29
  * @cssprop --pb-search-focus-color - Color of the field labels and underline when in focus
34
30
  * @cssprop --pb-browse-toolbar-justify-content - How to justify the browse toolbar content, following flexbox justify-content property e.g. center, space-evenly, start...
35
- *
31
+ *
36
32
  * @csspart delete-button - the delete button
37
33
  * @csspart sort-dropdown - dropdown for sorting
38
34
  * @csspart filter-dropdown - dropdown for filtering
39
35
  * @csspart filter-input - input for filtering
40
36
  */
41
37
  export class PbBrowseDocs extends themableMixin(PbLoad) {
38
+ static get properties() {
39
+ return {
40
+ ...super.properties,
41
+ sortBy: {
42
+ type: String,
43
+ attribute: 'sort-by',
44
+ },
45
+ sortOptions: {
46
+ type: Array,
47
+ attribute: 'sort-options',
48
+ },
49
+ sortLabel: {
50
+ type: String,
51
+ },
52
+ filter: {
53
+ type: String,
54
+ },
55
+ filterBy: {
56
+ type: String,
57
+ attribute: 'filter-by',
58
+ },
59
+ filterOptions: {
60
+ type: Array,
61
+ attribute: 'filter-options',
62
+ },
63
+ filterByLabel: {
64
+ type: String,
65
+ },
66
+ filterPlaceholderLabel: {
67
+ type: String,
68
+ },
69
+ collection: {
70
+ type: String,
71
+ },
72
+ facets: {
73
+ type: Object,
74
+ },
75
+ /** Id of the pb-login element to connect to */
76
+ login: {
77
+ type: String,
78
+ },
79
+ /**
80
+ * If set, requires the logged in user to be member of
81
+ * the given group.
82
+ */
83
+ group: {
84
+ type: String,
85
+ },
86
+ subforms: {
87
+ type: String,
88
+ },
89
+ /**
90
+ * If set, rewrite URLs to load pages as static HTML files,
91
+ * so no TEI Publisher instance is required
92
+ */
93
+ static: {
94
+ type: Boolean,
95
+ },
96
+ _file: {
97
+ type: String,
98
+ },
99
+ _selected: {
100
+ type: Array,
101
+ },
102
+ _allowModification: {
103
+ type: Boolean,
104
+ },
105
+ };
106
+ }
107
+
108
+ constructor() {
109
+ super();
110
+ this.sortOptions = [];
111
+ this.sortLabel = 'browse.sort';
112
+ this.sortBy = 'default';
113
+ this.filter = '';
114
+ this.filterOptions = [
115
+ {
116
+ label: 'Title',
117
+ value: 'title',
118
+ },
119
+ ];
120
+ this.filterByLabel = 'browse.filter';
121
+ this.filterPlaceholderLabel = 'browse.filterPlaceholder';
122
+
123
+ this.filterBy = 'title';
124
+ this._allowModification = false;
125
+
126
+ this.static = false;
127
+ }
128
+
129
+ connectedCallback() {
130
+ super.connectedCallback();
131
+
132
+ waitOnce('pb-page-ready', () => {
133
+ if (registry.state.sort) {
134
+ this.sortBy = registry.state.sort;
135
+ }
136
+
137
+ if (registry.state.filter) {
138
+ this.filter = registry.state.filter;
139
+ this.filterBy = registry.state.filterBy || this.filterBy;
140
+ }
141
+
142
+ this.facets = {};
143
+ // registry get state by regex
144
+ // this.facets = registry.getParametersMatching(this, /^facet-.*$/)
145
+ Object.keys(registry.state).forEach(key => {
146
+ if (/^facet-.*$/.test(key)) {
147
+ const param = registry.state[key];
148
+ if (this.facets[key]) {
149
+ this.facets[key].push(param);
150
+ } else if (Array.isArray(param)) {
151
+ this.facets[key] = param;
152
+ } else {
153
+ this.facets[key] = [param];
154
+ }
155
+ }
156
+ });
42
157
 
43
- static get properties() {
44
- return {
45
- ...super.properties,
46
- sortBy: {
47
- type: String,
48
- attribute: 'sort-by'
49
- },
50
- sortOptions: {
51
- type: Array,
52
- attribute: 'sort-options'
53
- },
54
- sortLabel: {
55
- type: String
56
- },
57
- filter: {
58
- type: String
59
- },
60
- filterBy: {
61
- type: String,
62
- attribute: 'filter-by'
63
- },
64
- filterOptions: {
65
- type: Array,
66
- attribute: 'filter-options'
67
- },
68
- filterByLabel: {
69
- type: String
70
- },
71
- filterPlaceholderLabel: {
72
- type: String
73
- },
74
- collection: {
75
- type: String
76
- },
77
- facets: {
78
- type: Object
79
- },
80
- /** Id of the pb-login element to connect to */
81
- login: {
82
- type: String
83
- },
84
- /**
85
- * If set, requires the logged in user to be member of
86
- * the given group.
87
- */
88
- group: {
89
- type: String
90
- },
91
- subforms: {
92
- type: String
93
- },
94
- /**
95
- * If set, rewrite URLs to load pages as static HTML files,
96
- * so no TEI Publisher instance is required
97
- */
98
- static: {
99
- type: Boolean
100
- },
101
- _file: {
102
- type: String
103
- },
104
- _selected: {
105
- type: Array
106
- },
107
- _allowModification: {
108
- type: Boolean,
109
- },
110
- _suggestions: {
111
- type: Array
112
- }
113
- };
114
- }
115
-
116
- constructor() {
117
- super();
118
- this.sortOptions = [];
119
- this.sortLabel = 'browse.sort';
120
- this.sortBy = 'default';
121
- this.filter = '';
122
- this.filterOptions = [
123
- {
124
- label: 'Title',
125
- value: 'title'
126
- }
127
- ];
128
- this.filterByLabel = 'browse.filter';
129
- this.filterPlaceholderLabel = 'browse.filterPlaceholder';
130
-
131
- this.filterBy = 'title';
132
- this._allowModification = false;
133
- this._suggestions = [];
134
-
135
- this.static = false;
136
- }
137
-
138
- connectedCallback() {
139
- super.connectedCallback();
140
-
141
- waitOnce('pb-page-ready', () => {
142
- if (registry.state.sort) {
143
- this.sortBy = registry.state.sort;
144
- }
145
-
146
- if (registry.state.filter) {
147
- this.filter = registry.state.filter;
148
- this.filterBy = registry.state.filterBy || this.filterBy;
149
- }
150
-
151
- this.facets = {};
152
- // registry get state by regex
153
- // this.facets = registry.getParametersMatching(this, /^facet-.*$/)
154
- Object.keys(registry.state).forEach((key) => {
155
- if (/^facet-.*$/.test(key)) {
156
- const param = registry.state[key];
157
- if (this.facets[key]) {
158
- this.facets[key].push(param);
159
- } else if (Array.isArray(param)) {
160
- this.facets[key] = param;
161
- } else {
162
- this.facets[key] = [param];
163
- }
164
- }
165
- });
166
-
167
- this.collection = registry.state.collection;
168
-
169
- if (this.collection) {
170
- registry.replace(this, {
171
- collection: this.collection
172
- });
173
- }
174
- registry.subscribe(this, (state) => {
175
- this.collection = state.collection;
176
- this.load();
177
- });
178
- });
179
-
180
- this.subscribeTo('pb-search-resubmit', this._facets.bind(this));
181
- this.subscribeTo('pb-login', (ev) => {
182
- if (ev.detail.userChanged) {
183
- this._facets(ev);
184
- }
185
- }, []);
186
- document.addEventListener('pb-i18n-update', () => {
187
- // clear paper-listbox selection after language updates
188
- const lb = this.shadowRoot.getElementById('sort-list');
189
- let old = lb.selected;
190
- lb.selected = undefined;
191
- lb.selected = old;
192
-
193
- const fl = this.shadowRoot.getElementById('filter-list');
194
- old = fl.selected;
195
- fl.selected = undefined;
196
- fl.selected = old;
197
- });
198
- }
158
+ this.collection = registry.state.collection;
199
159
 
200
- firstUpdated() {
201
- waitOnce('pb-page-ready', (options) => {
202
- const loader = this.shadowRoot.getElementById('autocompleteLoader');
203
- if (cmpVersion(options.apiVersion, '1.0.0') >= 0) {
204
- loader.url = `${options.endpoint}/api/search/autocomplete`;
205
- if (!this.url) {
206
- this.url = 'api/collection';
207
- }
208
- } else {
209
- loader.url = `${options.endpoint}/modules/autocomplete.xql`;
210
- if (!this.url) {
211
- this.url = 'collection/';
212
- }
213
- }
160
+ if (this.collection) {
161
+ registry.replace(this, {
162
+ collection: this.collection,
214
163
  });
215
- this.shadowRoot.getElementById('autocomplete').addEventListener('autocomplete-change', this._autocomplete.bind(this));
216
-
217
- if (this.login) {
218
- const login = document.getElementById(this.login);
219
- if (!login) {
220
- console.error('<pb-browse-docs> connected pb-login element not found!');
221
- } else {
222
- this.subscribeTo('pb-login', (ev) => {
223
- this._allowModification = this._loggedIn(ev.detail.user, ev.detail.group);
224
- }, []);
225
- this._allowModification = login.loggedIn && this._loggedIn(login.user, login.groups);
226
- }
164
+ }
165
+ registry.subscribe(this, state => {
166
+ this.collection = state.collection;
167
+ this.load();
168
+ });
169
+ });
170
+
171
+ this.subscribeTo('pb-search-resubmit', this._facets.bind(this));
172
+ this.subscribeTo(
173
+ 'pb-login',
174
+ ev => {
175
+ if (ev.detail.userChanged) {
176
+ this._facets(ev);
227
177
  }
228
-
229
- this.shadowRoot.getElementById('sort-list').addEventListener('selected-item-changed', this._sort.bind(this));
230
- this.shadowRoot.getElementById('delete').addEventListener('click', this._handleDelete.bind(this));
231
- super.firstUpdated();
178
+ },
179
+ [],
180
+ );
181
+ this.subscribeTo(
182
+ 'pb-i18n-update',
183
+ () => {
184
+ this.requestUpdate();
185
+ },
186
+ [],
187
+ );
188
+ }
189
+
190
+ firstUpdated() {
191
+ waitOnce('pb-page-ready', options => {
192
+ const autocomplete = this.shadowRoot.getElementById('filterString');
193
+ let autocompleteUrl;
194
+ if (cmpVersion(options.apiVersion, '1.0.0') >= 0) {
195
+ autocompleteUrl = `${options.endpoint}/api/search/autocomplete`;
196
+ if (!this.url) {
197
+ this.url = 'api/collection';
198
+ }
199
+ } else {
200
+ autocompleteUrl = `${options.endpoint}/modules/autocomplete.xql`;
201
+ if (!this.url) {
202
+ this.url = 'collection/';
203
+ }
204
+ }
205
+ if (autocomplete) {
206
+ autocomplete.source = autocompleteUrl;
207
+ autocomplete.substring = true;
208
+ autocomplete.requestParams = { field: this.filterBy };
209
+ }
210
+ });
211
+
212
+ const autocomplete = this.shadowRoot.getElementById('filterString');
213
+ if (autocomplete) {
214
+ autocomplete.addEventListener(
215
+ 'pb-autocomplete-selected',
216
+ this._handleAutocompleteSelected.bind(this),
217
+ );
218
+ autocomplete.addEventListener(
219
+ 'pb-autocomplete-input',
220
+ this._handleAutocompleteInput.bind(this),
221
+ );
232
222
  }
233
223
 
234
- render() {
235
- return html`
236
- <custom-style>
237
- <style>
238
- :host {
239
- --suggestions-item: {
240
- color: var(--pb-search-suggestions-color, black);
241
- };
242
- --suggestions-wrapper: {
243
- background: var(--pb-search-suggestions-background, white);
244
- }
245
- }
246
- </style>
247
- </custom-style>
248
- <slot name="header"></slot>
249
- <div class="toolbar">
250
- <paper-dropdown-menu id="sort" label="${translate(this.sortLabel)}" part="sort-dropdown">
251
- <paper-listbox id="sort-list" selected="${this.sortBy}" slot="dropdown-content" class="dropdown-content" attr-for-selected="value">
252
- ${this.sortOptions.map(option =>
253
- html`<paper-item value="${option.value}">${translate(option.label)}</paper-item>`
254
- )}
255
- </paper-listbox>
256
- </paper-dropdown-menu>
257
- <div>
258
- <paper-dropdown-menu id="filterSelect" label="${translate(this.filterByLabel)}" part="filter-dropdown">
259
- <paper-listbox id="filter-list" selected="${this.filterBy}" slot="dropdown-content" class="dropdown-content" attr-for-selected="value" @selected-item-changed="${this._filterChanged}">
260
- ${this.filterOptions.map(option =>
261
- html`<paper-item value="${option.value}">${translate(option.label)}</paper-item>`
262
- )}
263
- </paper-listbox>
264
- </paper-dropdown-menu>
265
- <paper-input id="filterString" type="search" name="filter" label="${translate(this.filterPlaceholderLabel)}" value="${this.filter}"
266
- @keyup="${this._handleEnter}" part="filter-input">
267
- <iron-icon icon="search" @click="${this._filter}" slot="prefix"></iron-icon>
268
- </paper-input>
269
- <paper-autocomplete-suggestions id="autocomplete" for="filterString" source="${this._suggestions}" remote-source></paper-autocomplete-suggestions>
270
- </div>
271
- </div>
272
- <div class="toolbar">
273
- <slot name="toolbar"></slot>
274
- <paper-button id="delete" part="delete-button" title="${translate('browse.delete')}" class="${this._canModify(this._allowModification)}">
275
- <iron-icon icon="delete"></iron-icon>
276
- <span class="label">${translate('browse.delete')}</span>
277
- </paper-button>
278
- </div>
279
- <slot></slot>
280
- <slot name="footer"></slot>
281
-
282
- <iron-ajax
283
- id="loadContent"
284
- verbose
285
- handle-as="text"
286
- method="get"
287
- with-credentials
288
- @response="${this._handleContent}"
289
- @error="${this._handleError}"></iron-ajax>
290
- <iron-ajax
291
- id="autocompleteLoader"
292
- verbose
293
- handle-as="json"
294
- method="get"
295
- with-credentials
296
- @response="${this._updateSuggestions}"></iron-ajax>
297
-
298
- <paper-dialog id="deleteDialog">
299
- <h2>${translate('browse.delete')}</h2>
300
- <paper-dialog-scrollable>
301
- <p>${translate('browse.confirmDeletion', { count: (this._selected ? this._selected.length : 0) })}</p>
302
- </paper-dialog-scrollable>
303
- <div class="buttons">
304
- <paper-button dialog-confirm="dialog-confirm" autofocus @click="${this._confirmDelete}">${translate('dialogs.yes')}</paper-button>
305
- <paper-button dialog-confirm="dialog-cancel">${translate('dialogs.no')}</paper-button>
306
- </div>
307
- </paper-dialog>
308
- <paper-dialog id="errorDialog">
309
- <h2>${translate('dialogs.error')}</h2>
310
- <paper-dialog-scrollable></paper-dialog-scrollable>
311
- <div class="buttons">
312
- <paper-button dialog-confirm="dialog-confirm" autofocus="autofocus">
313
- ${translate('dialogs.close')}
314
- </paper-button>
315
- </div>
316
- </paper-dialog>
317
- `;
224
+ const sortSelect = this.shadowRoot.getElementById('sortSelect');
225
+ if (sortSelect) {
226
+ sortSelect.addEventListener('change', this._sort.bind(this));
318
227
  }
319
228
 
320
- static get styles() {
321
- return css`
322
- :host {
323
- display: block;
324
- --paper-input-container-color: var(--pb-search-label-color, var(--paper-grey-500, #303030));
325
- --paper-input-container-input-color: var(--pb-search-input-color, var(--pb-color-primary, #000000));
326
- --paper-input-container-focus-color: var(--pb-search-focus-color, var(--paper-grey-500, #303030));
327
- }
328
-
329
- .toolbar {
330
- display: flex;
331
- justify-content: var(--pb-browse-toolbar-justify-content);
332
- }
333
-
334
- [name="toolbar"] {
335
- flex: 1 0;
336
- }
337
-
338
- #sort {
339
- display: block;
340
- }
341
-
342
- #filterString {
343
- position: relative;
344
- display: inline-block;
345
- vertical-align: bottom;
346
- }
347
-
348
- .hidden {
349
- display: none;
350
- }
351
- `;
229
+ if (this.login) {
230
+ const login = document.getElementById(this.login);
231
+ if (!login) {
232
+ console.error('<pb-browse-docs> connected pb-login element not found!');
233
+ } else {
234
+ this.subscribeTo(
235
+ 'pb-login',
236
+ ev => {
237
+ this._allowModification = this._loggedIn(ev.detail.user, ev.detail.group);
238
+ },
239
+ [],
240
+ );
241
+ this._allowModification = login.loggedIn && this._loggedIn(login.user, login.groups);
242
+ }
352
243
  }
353
-
354
- getURL(params) {
355
- if (this.static) {
356
- // use a static URL
357
- return `collections/${this.collection ? this.collection + '/' : ''}${params.start || '1'}.html`;
358
- }
359
- const url = super.getURL(params);
360
- return this.collection ? `${url}/${this.collection}` : url;
244
+ this.shadowRoot
245
+ .getElementById('delete')
246
+ .addEventListener('click', this._handleDelete.bind(this));
247
+ super.firstUpdated();
248
+ }
249
+
250
+ render() {
251
+ return html`
252
+ <slot name="header"></slot>
253
+ <div class="toolbar toolbar--primary">
254
+ <div class="toolbar__group">
255
+ <label class="field">
256
+ <span class="field__label">${translate(this.sortLabel)}</span>
257
+ <select
258
+ id="sortSelect"
259
+ class="field__select"
260
+ @change="${this._sort}"
261
+ .value=${this.sortBy || ''}
262
+ >
263
+ ${this.sortOptions.map(
264
+ option => html`<option value="${option.value}">${translate(option.label)}</option>`,
265
+ )}
266
+ </select>
267
+ </label>
268
+ </div>
269
+ <div class="toolbar__group toolbar__group--filter">
270
+ <label class="field">
271
+ <span class="field__label">${translate(this.filterByLabel)}</span>
272
+ <select
273
+ id="filterSelect"
274
+ class="field__select"
275
+ @change="${this._filterChanged}"
276
+ .value=${this.filterBy || ''}
277
+ >
278
+ ${this.filterOptions.map(
279
+ option => html`<option value="${option.value}">${translate(option.label)}</option>`,
280
+ )}
281
+ </select>
282
+ </label>
283
+ <div class="filter-control">
284
+ <pb-autocomplete
285
+ id="filterString"
286
+ class="filter-control__input"
287
+ name="filter"
288
+ .value=${this.filter || ''}
289
+ placeholder="${translate(this.filterPlaceholderLabel)}"
290
+ icon="search"
291
+ @keydown=${this._handleEnter}
292
+ ></pb-autocomplete>
293
+ <button
294
+ class="pb-button pb-button--icon filter-control__submit"
295
+ type="button"
296
+ @click=${this._filter}
297
+ aria-label="${translate('browse.filter')}"
298
+ title="${translate('browse.filter')}"
299
+ >
300
+ <pb-icon icon="search" decorative></pb-icon>
301
+ </button>
302
+ </div>
303
+ </div>
304
+ </div>
305
+ <div class="toolbar toolbar--secondary">
306
+ <slot name="toolbar"></slot>
307
+ <button
308
+ id="delete"
309
+ part="delete-button"
310
+ type="button"
311
+ class="pb-button pb-button--text ${this._canModify(this._allowModification)}"
312
+ title="${translate('browse.delete')}"
313
+ >
314
+ <pb-icon icon="delete" decorative></pb-icon>
315
+ <span class="label">${translate('browse.delete')}</span>
316
+ </button>
317
+ </div>
318
+ <slot></slot>
319
+ <slot name="footer"></slot>
320
+
321
+ <pb-fetch
322
+ id="loadContent"
323
+ verbose
324
+ handle-as="text"
325
+ method="get"
326
+ with-credentials
327
+ @response="${this._handleContent}"
328
+ @error="${this._handleError}"
329
+ ></pb-fetch>
330
+ <pb-dialog id="deleteDialog" title="${translate('browse.delete')}">
331
+ <p>
332
+ ${translate('browse.confirmDeletion', {
333
+ count: this._selected ? this._selected.length : 0,
334
+ })}
335
+ </p>
336
+ <div slot="footer" class="buttons">
337
+ <button
338
+ class="pb-button pb-button--text"
339
+ type="button"
340
+ autofocus
341
+ @click="${this._confirmDelete}"
342
+ >
343
+ ${translate('dialogs.yes')}
344
+ </button>
345
+ <button class="pb-button pb-button--text" type="button" rel="prev">
346
+ ${translate('dialogs.no')}
347
+ </button>
348
+ </div>
349
+ </pb-dialog>
350
+ <pb-dialog id="errorDialog" title="${translate('dialogs.error')}">
351
+ <p id="errorMessage"></p>
352
+ <div slot="footer">
353
+ <button class="pb-button pb-button--text" type="button" rel="prev">
354
+ ${translate('dialogs.close')}
355
+ </button>
356
+ </div>
357
+ </pb-dialog>
358
+ `;
359
+ }
360
+
361
+ static get styles() {
362
+ return css`
363
+ :host {
364
+ display: block;
365
+ }
366
+
367
+ .toolbar {
368
+ display: flex;
369
+ flex-wrap: wrap;
370
+ gap: 1rem;
371
+ align-items: flex-end;
372
+ justify-content: var(--pb-browse-toolbar-justify-content, space-between);
373
+ margin-bottom: 1rem;
374
+ }
375
+
376
+ .toolbar--secondary {
377
+ align-items: center;
378
+ }
379
+
380
+ .toolbar__group {
381
+ display: flex;
382
+ align-items: flex-end;
383
+ flex-wrap: wrap;
384
+ gap: 1rem;
385
+ }
386
+
387
+ .toolbar__group--filter {
388
+ flex: 1 1 320px;
389
+ justify-content: flex-end;
390
+ }
391
+
392
+ .field {
393
+ display: flex;
394
+ flex-direction: column;
395
+ gap: 0.35rem;
396
+ min-width: 160px;
397
+ }
398
+
399
+ .field__label {
400
+ font-size: 0.8rem;
401
+ font-weight: 600;
402
+ letter-spacing: 0.05em;
403
+ text-transform: uppercase;
404
+ color: rgba(0, 0, 0, 0.6);
405
+ }
406
+
407
+ .field__select {
408
+ appearance: none;
409
+ min-width: 160px;
410
+ padding: 0.45rem 2.25rem 0.45rem 0.75rem;
411
+ border-radius: 8px;
412
+ border: 1px solid rgba(0, 0, 0, 0.16);
413
+ background-image: linear-gradient(45deg, transparent 50%, rgba(0, 0, 0, 0.5) 50%),
414
+ linear-gradient(135deg, rgba(0, 0, 0, 0.5) 50%, transparent 50%),
415
+ linear-gradient(to right, rgba(0, 0, 0, 0.1), rgba(0, 0, 0, 0.1));
416
+ background-position: calc(100% - 18px) calc(1em + 2px), calc(100% - 13px) calc(1em + 2px),
417
+ calc(100% - 2.5rem) 0.5em;
418
+ background-size: 5px 5px, 5px 5px, 1px 2.25em;
419
+ background-repeat: no-repeat;
420
+ font: inherit;
421
+ color: inherit;
422
+ line-height: 1.2;
423
+ }
424
+
425
+ .field__select:focus {
426
+ outline: none;
427
+ border-color: #1976d2;
428
+ box-shadow: 0 0 0 3px rgba(25, 118, 210, 0.16);
429
+ }
430
+
431
+ .filter-control {
432
+ display: inline-flex;
433
+ align-items: center;
434
+ gap: 0.5rem;
435
+ flex: 1 1 280px;
436
+ }
437
+
438
+ .filter-control__input {
439
+ flex: 1 1 auto;
440
+ }
441
+
442
+ .filter-control__submit {
443
+ margin-bottom: 4px;
444
+ }
445
+
446
+ .filter-control__submit pb-icon {
447
+ --pb-icon-size: 1.25rem;
448
+ }
449
+
450
+ [name='toolbar'] {
451
+ flex: 1 0;
452
+ }
453
+
454
+ .hidden {
455
+ display: none !important;
456
+ }
457
+ `;
458
+ }
459
+
460
+ getURL(params) {
461
+ if (this.static) {
462
+ // use a static URL
463
+ return `collections/${this.collection ? `${this.collection}/` : ''}${
464
+ params.start || '1'
465
+ }.html`;
361
466
  }
362
-
363
- prepareParameters(params) {
364
- params = this._paramsFromSubforms(params);
365
- params.sort = this.sortBy;
366
- if (this.filter) {
367
- params.filter = this.filter;
368
- params.browse = this.filterBy;
369
- }
370
- if (this.facets) {
371
- params = Object.assign(params, this.facets);
372
- }
373
- return params;
467
+ const url = super.getURL(params);
468
+ return this.collection ? `${url}/${this.collection}` : url;
469
+ }
470
+
471
+ prepareParameters(params) {
472
+ params = this._paramsFromSubforms(params);
473
+ params.sort = this.sortBy;
474
+ if (this.filter) {
475
+ params.filter = this.filter;
476
+ params.browse = this.filterBy;
374
477
  }
375
-
376
- _paramsFromSubforms(params) {
377
- if (this.subforms) {
378
- document.querySelectorAll(this.subforms).forEach((form) => {
379
- if (form.serializeForm) {
380
- Object.assign(params, form.serializeForm());
381
- }
382
- });
383
- }
384
- return params;
478
+ if (this.facets) {
479
+ params = Object.assign(params, this.facets);
385
480
  }
386
-
387
- /**
388
- * returns selected documents.
389
- *
390
- * @returns {Array}
391
- */
392
- getSelected() {
393
- const selected = [];
394
- if (this.container) {
395
- document.querySelectorAll(this.container).forEach((container) =>
396
- container.querySelectorAll('.document-select paper-checkbox[checked]').forEach((checkbox) => {
397
- selected.push(checkbox.value);
398
- })
399
- );
400
- } else {
401
- this.querySelectorAll('.document-select paper-checkbox[checked]').forEach((checkbox) => {
402
- selected.push(checkbox.value);
403
- });
481
+ return params;
482
+ }
483
+
484
+ _paramsFromSubforms(params) {
485
+ if (this.subforms) {
486
+ document.querySelectorAll(this.subforms).forEach(form => {
487
+ if (form.serializeForm) {
488
+ Object.assign(params, form.serializeForm());
404
489
  }
405
- return selected;
490
+ });
406
491
  }
407
-
408
- _filter() {
409
- const filter = this.shadowRoot.getElementById('filterString').value;
410
- const filterBy = this.shadowRoot.getElementById('filter-list').selected;
411
- if (typeof filter !== 'undefined') {
412
- console.log('<pb-browse-docs> Filter by %s', filter);
413
- this.filter = filter;
414
- registry.commit(this, { filter, filterBy })
415
- this.load();
416
- }
492
+ return params;
493
+ }
494
+
495
+ /**
496
+ * returns selected documents.
497
+ *
498
+ * @returns {Array}
499
+ */
500
+ getSelected() {
501
+ const selected = [];
502
+ if (this.container) {
503
+ document.querySelectorAll(this.container).forEach(container =>
504
+ container
505
+ .querySelectorAll('.document-select input[type="checkbox"]:checked')
506
+ .forEach(checkbox => {
507
+ selected.push(checkbox.value);
508
+ }),
509
+ );
510
+ } else {
511
+ this.querySelectorAll('.document-select input[type="checkbox"]:checked').forEach(checkbox => {
512
+ selected.push(checkbox.value);
513
+ });
417
514
  }
418
-
419
- _filterChanged() {
420
- const filterBy = this.shadowRoot.getElementById('filter-list').selected;
421
- if (filterBy && filterBy !== this.filterBy) {
422
- console.log('<pb-browse-docs> Filtering on %s', filterBy);
423
- this.filterBy = filterBy;
424
- }
515
+ return selected;
516
+ }
517
+
518
+ _filter() {
519
+ const filterInput = this.shadowRoot.getElementById('filterString');
520
+ const filterSelect = this.shadowRoot.getElementById('filterSelect');
521
+ const filter = filterInput ? filterInput.value : this.filter;
522
+ const filterBy = filterSelect ? filterSelect.value : this.filterBy;
523
+ if (typeof filter !== 'undefined') {
524
+ console.log('<pb-browse-docs> Filter by %s', filter);
525
+ this.filter = filter;
526
+ registry.commit(this, { filter, filterBy });
527
+ this.load();
425
528
  }
426
-
427
- _sort() {
428
- const sortBy = this.shadowRoot.getElementById('sort-list').selected;
429
- if (sortBy && sortBy !== this.sortBy) {
430
- console.log('<pb-browse-docs> Sorting by %s', sortBy);
431
- this.sortBy = sortBy;
432
- registry.commit(this, { sort: sortBy })
433
-
434
- this.load();
435
- }
529
+ }
530
+
531
+ _filterChanged(ev) {
532
+ const filterSelect = ev?.target ?? this.shadowRoot.getElementById('filterSelect');
533
+ const filterBy = filterSelect ? filterSelect.value : null;
534
+ if (filterBy && filterBy !== this.filterBy) {
535
+ console.log('<pb-browse-docs> Filtering on %s', filterBy);
536
+ this.filterBy = filterBy;
537
+ const autocomplete = this.shadowRoot.getElementById('filterString');
538
+ if (autocomplete) {
539
+ autocomplete.requestParams = { field: this.filterBy };
540
+ }
436
541
  }
542
+ }
437
543
 
438
- _facets(ev) {
439
- if (ev.detail && ev.detail.params) {
440
- registry.clearParametersMatching(this, /^(all-|facet-).*/);
441
- this.facets = ev.detail.params;
442
- this.start = 1;
443
- registry.commit(this, ev.detail.params)
444
- }
445
- this.load();
446
- }
544
+ _sort(ev) {
545
+ const sortSelect = ev?.target ?? this.shadowRoot.getElementById('sortSelect');
546
+ const sortBy = sortSelect ? sortSelect.value : null;
547
+ if (sortBy && sortBy !== this.sortBy) {
548
+ console.log('<pb-browse-docs> Sorting by %s', sortBy);
549
+ this.sortBy = sortBy;
550
+ registry.commit(this, { sort: sortBy });
447
551
 
448
- _onLoad(content) {
449
- window.scrollTo(0, 0);
450
- const div = content.querySelector('[data-root]');
451
- const collection = div && div.getAttribute('data-root');
452
- const writable = div && div.classList.contains('writable');
453
- this.emitTo('pb-collection', {
454
- writable,
455
- collection
456
- });
457
- document.querySelectorAll('[can-write]').forEach((elem) => {
458
- elem.disabled = !writable;
459
- });
460
- content.querySelectorAll('[data-collection]').forEach(link => {
461
- link.addEventListener('click', (ev) => {
462
- ev.preventDefault();
463
- this.collection = link.getAttribute('data-collection');
464
- this.start = 1;
465
- registry.commit(this, { collection: this.collection });
466
- console.log('<pb-browse-docs> loading collection %s', this.collection);
467
- this.load();
468
- });
469
- });
552
+ this.load();
470
553
  }
471
-
472
- _handleDelete(target, ev) {
473
- const deleteDialog = this.shadowRoot.getElementById('deleteDialog');
474
- const selected = this.getSelected();
475
- if (selected.length > 0) {
476
- this._selected = selected;
477
- deleteDialog.open();
478
- }
554
+ }
555
+
556
+ _facets(ev) {
557
+ if (ev.detail && ev.detail.params) {
558
+ registry.clearParametersMatching(this, /^(all-|facet-).*/);
559
+ this.facets = ev.detail.params;
560
+ this.start = 1;
561
+ registry.commit(this, ev.detail.params);
479
562
  }
480
-
481
- _confirmDelete() {
482
- if (!(this._file || this._selected)) {
483
- return;
484
- }
485
-
486
- let files;
487
- if (this._selected) {
488
- files = this._selected;
489
- } else {
490
- files = [this._file];
491
- }
492
- console.log('<pb-browse-docs> Deleting %o', this._file);
493
- const params = {
494
- action: 'delete',
495
- 'docs[]': files
496
- };
497
- this._file = null;
498
- this._selected = null;
499
- this.load(params);
563
+ this.load();
564
+ }
565
+
566
+ _onLoad(content) {
567
+ window.scrollTo(0, 0);
568
+ const div = content.querySelector('[data-root]');
569
+ const collection = div && div.getAttribute('data-root');
570
+ const writable = div && div.classList.contains('writable');
571
+ this.emitTo('pb-collection', {
572
+ writable,
573
+ collection,
574
+ });
575
+ document.querySelectorAll('[can-write]').forEach(elem => {
576
+ elem.disabled = !writable;
577
+ });
578
+ content.querySelectorAll('[data-collection]').forEach(link => {
579
+ link.addEventListener('click', ev => {
580
+ ev.preventDefault();
581
+ this.collection = link.getAttribute('data-collection');
582
+ this.start = 1;
583
+ registry.commit(this, { collection: this.collection });
584
+ console.log('<pb-browse-docs> loading collection %s', this.collection);
585
+ this.load();
586
+ });
587
+ });
588
+ }
589
+
590
+ _handleDelete(target, ev) {
591
+ const deleteDialog = this.shadowRoot.getElementById('deleteDialog');
592
+ const selected = this.getSelected();
593
+ if (selected.length > 0) {
594
+ this._selected = selected;
595
+ deleteDialog.openDialog();
500
596
  }
597
+ }
501
598
 
502
- _loggedIn(user, groups) {
503
- if (user == null) {
504
- return false;
505
- }
506
- if (this.group) {
507
- if (!groups) {
508
- return false;
509
- }
510
- return groups.indexOf(this.group) > -1;
511
- }
512
- return true;
599
+ _confirmDelete() {
600
+ if (!(this._file || this._selected)) {
601
+ return;
513
602
  }
514
603
 
515
- _canModify(allowModification) {
516
- return allowModification ? '' : 'hidden';
604
+ let files;
605
+ if (this._selected) {
606
+ files = this._selected;
607
+ } else {
608
+ files = [this._file];
517
609
  }
518
-
519
- _autocomplete(ev) {
520
- const autocompleteLoader = this.shadowRoot.getElementById('autocompleteLoader');
521
- autocompleteLoader.params = {
522
- query: ev.detail.option.text,
523
- field: this.filterBy
524
- };
525
- autocompleteLoader.generateRequest();
610
+ console.log('<pb-browse-docs> Deleting %o', this._file);
611
+ const params = {
612
+ action: 'delete',
613
+ 'docs[]': files,
614
+ };
615
+ this._file = null;
616
+ this._selected = null;
617
+ this.load(params);
618
+ }
619
+
620
+ _loggedIn(user, groups) {
621
+ if (user == null) {
622
+ return false;
526
623
  }
527
-
528
- _updateSuggestions() {
529
- const autocomplete = this.shadowRoot.getElementById('autocomplete');
530
- const autocompleteLoader = this.shadowRoot.getElementById('autocompleteLoader');
531
- autocomplete.suggestions(autocompleteLoader.lastResponse);
624
+ if (this.group) {
625
+ if (!groups) {
626
+ return false;
627
+ }
628
+ return groups.indexOf(this.group) > -1;
532
629
  }
533
-
534
- _handleEnter(e) {
535
- if (e.keyCode === 13) {
536
- this._filter();
537
- }
630
+ return true;
631
+ }
632
+
633
+ _canModify(allowModification) {
634
+ return allowModification ? '' : 'hidden';
635
+ }
636
+
637
+ _handleAutocompleteInput(ev) {
638
+ const detail = ev.detail || {};
639
+ const value = detail.value ?? detail.text ?? '';
640
+ this.filter = value;
641
+ }
642
+
643
+ _handleAutocompleteSelected(ev) {
644
+ const detail = ev.detail || {};
645
+ const value = detail.value ?? detail.text ?? '';
646
+ this.filter = value;
647
+ this._filter();
648
+ }
649
+
650
+ _handleEnter(e) {
651
+ const key = e.key || e.code || e.keyCode;
652
+ if (key === 'Enter' || key === 'NumpadEnter' || key === 13) {
653
+ this._filter();
538
654
  }
655
+ }
539
656
  }
540
- customElements.define('pb-browse-docs', PbBrowseDocs);
657
+ customElements.define('pb-browse-docs', PbBrowseDocs);