@fluid-topics/ft-search-bar 0.2.16 → 0.2.17

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.
@@ -34,6 +34,7 @@ export const DEFAULT_LABELS = {
34
34
  clearInputButton: "Clear",
35
35
  clearFilterButton: "Clear",
36
36
  displayMoreFilterValuesButton: "More",
37
+ noFilterValuesAvailable: "No values available",
37
38
  searchButton: "Search",
38
39
  noSuggestions: "No results found…",
39
40
  clearFilters: "Clear filters",
@@ -57,12 +58,15 @@ export class SearchStateChangeEvent extends CustomEvent {
57
58
  super("change", { detail: request });
58
59
  }
59
60
  }
61
+ const doNothing = () => {
62
+ };
60
63
  export class FtSearchBar extends FtLitElement {
61
64
  constructor() {
62
65
  super(...arguments);
63
66
  this.dense = false;
64
67
  this.mode = "auto";
65
68
  this.forceMobileMenuOpen = false;
69
+ this.forceMenuOpen = false;
66
70
  this.baseUrl = "";
67
71
  this.apiIntegrationIdentifier = "ft-search-bar";
68
72
  this.availableContentLocales = [];
@@ -79,7 +83,7 @@ export class FtSearchBar extends FtLitElement {
79
83
  this.mobileMenuOpen = false;
80
84
  this.facets = [];
81
85
  this.facetsInitialized = false;
82
- this.knownFacetLabels = {};
86
+ this.knownFacetLabels = new Map();
83
87
  this.query = "";
84
88
  this.suggestions = [];
85
89
  this.suggestionsLoaded = true;
@@ -101,7 +105,7 @@ export class FtSearchBar extends FtLitElement {
101
105
  && a.filters.every(fa => b.filters.some(fb => this.compareFilters(fa, fb)));
102
106
  }
103
107
  get isMobileMenuOpen() {
104
- return this.forceMobileMenuOpen || this.mobileMenuOpen;
108
+ return this.isMobile && (this.forceMobileMenuOpen || this.forceMenuOpen || this.mobileMenuOpen);
105
109
  }
106
110
  get recentSearchesStorageKey() {
107
111
  return this.baseUrl + ":ft:recent-search-queries";
@@ -177,8 +181,9 @@ export class FtSearchBar extends FtLitElement {
177
181
  "ft-search-bar--dense": !this.isMobile && this.dense,
178
182
  "ft-search-bar--mobile": this.isMobile,
179
183
  "ft-search-bar--desktop": !this.isMobile,
180
- "ft-search-bar--floating-panel-open": !this.isMobile && this.displayFacets,
184
+ "ft-search-bar--floating-panel-open": !this.isMobile && this.displayFacets && !this.forceMenuOpen,
181
185
  "ft-search-bar--mobile-menu-open": this.isMobileMenuOpen,
186
+ "ft-search-bar--forced-open": this.forceMenuOpen || this.forceMobileMenuOpen,
182
187
  };
183
188
  return this.facetsInitialized && this.availableContentLocalesInitialized ? html `
184
189
  <div class="${classMap(rootClasses)}" part="container" tabindex="-1">
@@ -268,7 +273,7 @@ export class FtSearchBar extends FtLitElement {
268
273
  </div>
269
274
  <ft-filter
270
275
  part="filters filter-ft-locale"
271
- exportparts=${this.getFilterExportParts("ft-locale")}
276
+ .exportpartsPrefixes=${["filter", "filter-ft-locale"]}
272
277
  class="ft-search-bar--content-locale"
273
278
  filterPlaceHolder="${this.labelResolver.resolve("filterInputPlaceHolder", this.labelResolver.resolve("contentLocaleSelector"))}"
274
279
  .options=${(this.contentLocalesAsFilterOptions())}
@@ -279,7 +284,7 @@ export class FtSearchBar extends FtLitElement {
279
284
  ${repeat(this.facets, facet => facet.key, facet => {
280
285
  const filter = facetToFilter(facet);
281
286
  const keyWithNoColumn = facet.key.replace(":", "-");
282
- return html `
287
+ return facet.rootNodes.length > 0 ? html `
283
288
  <ft-accordion-item data-facet-key="${facet.key}">
284
289
  <div class="ft-search-bar--filter-label" slot="toggle">
285
290
  <ft-typography variant="button">${facet.label}</ft-typography>
@@ -288,12 +293,13 @@ export class FtSearchBar extends FtLitElement {
288
293
  </ft-typography>
289
294
  </div>
290
295
  <ft-filter
291
- part="filters filter-${keyWithNoColumn}"
292
- exportparts=${this.getFilterExportParts(keyWithNoColumn)}
296
+ part="filters filter filter-${keyWithNoColumn}"
297
+ .exportpartsPrefixes=${["filter", "filter-" + keyWithNoColumn]}
293
298
  id="${filter.id}"
294
299
  filterPlaceHolder="${this.labelResolver.resolve("filterInputPlaceHolder", filter.label)}"
295
300
  clearButtonLabel="${this.labelResolver.resolve("clearFilterButton")}"
296
301
  moreValuesButtonLabel="${this.labelResolver.resolve("displayMoreFilterValuesButton")}"
302
+ noValuesLabel="${this.labelResolver.resolve("noFilterValuesAvailable")}"
297
303
  ?multivalued=${filter.multivalued}
298
304
  raiseSelectedOptions
299
305
  .options=${filter.options}
@@ -301,7 +307,7 @@ export class FtSearchBar extends FtLitElement {
301
307
  @change=${(e) => this.setFilter(filter.id, e.detail)}
302
308
  ></ft-filter>
303
309
  </ft-accordion-item>
304
- `;
310
+ ` : nothing;
305
311
  })}
306
312
  </ft-accordion>
307
313
  `;
@@ -331,25 +337,35 @@ export class FtSearchBar extends FtLitElement {
331
337
  ${this.renderSuggestions()}
332
338
  </div>
333
339
  ${this.renderDesktopSearchBarButtons()}
334
- <div class="ft-search-bar--floating-panel" @keyup=${this.onFloatingContainerKeyUp} tabindex="-1">
335
- ${this.renderFacetsActions()}
336
- ${this.renderDesktopFacets()}
337
- <div class="ft-search-bar--facets-actions">
338
- <ft-button class="ft-search-bar--launch-search"
339
- part="launch-search-in-panel"
340
- icon="search"
341
- @click=${this.launchSearch}>
342
- ${this.labelResolver.resolve("searchButton")}
343
- </ft-button>
344
- </div>
345
- </div>
340
+ ${this.forceMenuOpen ? nothing : html `
341
+ <div class="ft-search-bar--floating-panel" @keyup=${this.onFloatingContainerKeyUp}
342
+ tabindex="-1">
343
+ ${this.renderDesktopMenu()}
344
+ </div>`}
346
345
  </div>
347
- ${this.dense ? nothing : this.renderSelectedFacets()}
346
+ ${this.dense || this.forceMenuOpen ? (this.forceMenuOpen ? this.renderDesktopMenu() : nothing) : this.renderSelectedFacets()}
348
347
  `;
349
348
  }
349
+ renderDesktopMenu() {
350
+ return this.hasFacets ? html `
351
+ <div class="ft-search-bar--desktop-menu">
352
+ ${this.renderFacetsActions()}
353
+ ${this.renderDesktopFacets()}
354
+ <div class="ft-search-bar--facets-actions">
355
+ ${this.forceMenuOpen ? this.renderDesktopClearFilters() : nothing}
356
+ <ft-button class="ft-search-bar--launch-search"
357
+ part="launch-search-in-panel"
358
+ icon="search"
359
+ @click=${this.launchSearch}>
360
+ ${this.labelResolver.resolve("searchButton")}
361
+ </ft-button>
362
+ </div>
363
+ </div>
364
+ ` : nothing;
365
+ }
350
366
  renderSearchBarLeftAction() {
351
367
  if (this.hasFacets) {
352
- return html `
368
+ return this.forceMenuOpen ? nothing : html `
353
369
  <ft-button class="ft-search-bar--filters-opener ft-search-bar--left-action"
354
370
  part="filters-opener"
355
371
  trailingIcon
@@ -363,7 +379,7 @@ export class FtSearchBar extends FtLitElement {
363
379
  </ft-button>
364
380
  `;
365
381
  }
366
- if (this.hasLocaleSelector) {
382
+ else if (this.hasLocaleSelector) {
367
383
  return html `
368
384
  <ft-select outlined
369
385
  class="ft-search-bar--content-locale ft-search-bar--left-action"
@@ -423,16 +439,19 @@ export class FtSearchBar extends FtLitElement {
423
439
  `)}
424
440
  </ft-select>
425
441
  ` : nothing}
426
- ${this.searchFilters.length > 0 ? html `
427
- <ft-button part="facets-actions"
428
- @click=${this.clearFilters}>
429
- ${this.labelResolver.resolve("clearFilters")}
430
- </ft-button>
431
- ` : nothing}
432
442
  <slot name="facets-actions"></slot>
443
+ ${this.forceMenuOpen && !this.isMobile ? nothing : this.renderDesktopClearFilters()}
433
444
  </div>
434
445
  `;
435
446
  }
447
+ renderDesktopClearFilters() {
448
+ return this.searchFilters.length > 0 ? html `
449
+ <ft-button part="facets-actions"
450
+ @click=${this.clearFilters}>
451
+ ${this.labelResolver.resolve("clearFilters")}
452
+ </ft-button>
453
+ ` : nothing;
454
+ }
436
455
  renderDesktopFacets() {
437
456
  if (!this.hasFacets) {
438
457
  return nothing;
@@ -441,11 +460,11 @@ export class FtSearchBar extends FtLitElement {
441
460
  <ft-snap-scroll horizontal limitSize controls
442
461
  class="ft-search-bar--filters-container"
443
462
  part="filters-container"
444
- exportparts="controls:snap-scroll-controls">
463
+ exportpartsPrefix="filters-container">
445
464
  ${this.hasLocaleSelector ? html `
446
465
  <ft-filter class="ft-search-bar--content-locale"
447
466
  part="filters filter-ft-locale"
448
- exportparts=${this.getFilterExportParts("ft-locale")}
467
+ .exportpartsPrefixes=${["filter", "filter-ft-locale"]}
449
468
  label="${this.labelResolver.resolve("contentLocaleSelector")}"
450
469
  filterPlaceHolder="${this.labelResolver.resolve("filterInputPlaceHolder", this.labelResolver.resolve("contentLocaleSelector"))}"
451
470
  .options=${(this.contentLocalesAsFilterOptions())}
@@ -459,13 +478,14 @@ export class FtSearchBar extends FtLitElement {
459
478
  return html `
460
479
  <ft-filter
461
480
  class="${hierachical ? "ft-search-bar--hierarchical-filter" : ""}"
462
- part="filters filter-${keyWithNoColumn}"
463
- exportparts=${this.getFilterExportParts(keyWithNoColumn)}
481
+ part="filters filter filter-${keyWithNoColumn}"
482
+ .exportpartsPrefixes=${["filter", "filter-" + keyWithNoColumn]}
464
483
  id="${filter.id}"
465
484
  label="${filter.label}"
466
485
  filterPlaceHolder="${this.labelResolver.resolve("filterInputPlaceHolder", filter.label)}"
467
486
  clearButtonLabel="${this.labelResolver.resolve("clearFilterButton")}"
468
487
  moreValuesButtonLabel="${this.labelResolver.resolve("displayMoreFilterValuesButton")}"
488
+ noValuesLabel="${this.labelResolver.resolve("noFilterValuesAvailable")}"
469
489
  ?multivalued=${filter.multivalued}
470
490
  raiseSelectedOptions
471
491
  .options=${filter.options}
@@ -484,7 +504,7 @@ export class FtSearchBar extends FtLitElement {
484
504
  const useSnapScroll = (!this.isMobile && this.dense) || (this.isMobile && this.isMobileMenuOpen);
485
505
  const filters = html `
486
506
  ${this.hasLocaleSelector && (this.hasFacets || this.isMobile) ? html `
487
- <ft-chip part="selected-filters"
507
+ <ft-chip part="selected-filters selected-filter-ft-locale"
488
508
  ?dense=${this.dense && !this.isMobile}
489
509
  ?clickable=${this.isMobile}
490
510
  @click=${() => this.openMobileFilters("ft:contentLocale")}>
@@ -495,9 +515,10 @@ export class FtSearchBar extends FtLitElement {
495
515
  const values = getSelectedValues(facet);
496
516
  return repeat(values, value => {
497
517
  let label = facet.label + ": " + getBreadcrumbFromValue(value);
518
+ const keyWithNoColumn = facet.key.replace(":", "-");
498
519
  const chip = html `
499
520
  <ft-chip
500
- part="selected-filters"
521
+ part="selected-filters selected-filter-${keyWithNoColumn}"
501
522
  ?dense=${this.dense && !this.isMobile}
502
523
  ?clickable=${this.isMobile}
503
524
  ?removable=${!this.isMobile}
@@ -517,7 +538,7 @@ export class FtSearchBar extends FtLitElement {
517
538
  });
518
539
  })}
519
540
  ${this.isMobile ? html `
520
- <ft-chip part="selected-filters"
541
+ <ft-chip part="selected-filters mobile-filters-opener"
521
542
  icon="add"
522
543
  clickable
523
544
  @click=${() => {
@@ -533,7 +554,7 @@ export class FtSearchBar extends FtLitElement {
533
554
  <ft-snap-scroll horizontal controls hideScrollbar limitSize
534
555
  class="ft-search-bar--selected-filters"
535
556
  part="selected-filters-container"
536
- exportparts="controls:snap-scroll-controls">
557
+ exportpartsPrefix="selected-filters-container">
537
558
  ${filters}
538
559
  </ft-snap-scroll>
539
560
  `
@@ -650,6 +671,9 @@ export class FtSearchBar extends FtLitElement {
650
671
  this.setFiltersFromPreset(currentPreset);
651
672
  }
652
673
  }
674
+ if (props.has("contentLocale") && this.contentLocale != null) {
675
+ this.knownFacetLabels = new Map();
676
+ }
653
677
  if (["contentLocale", "searchFilters"].some(p => props.has(p))) {
654
678
  this.selectedPreset = (_f = ((_e = this.presets) !== null && _e !== void 0 ? _e : []).find(p => this.compareRequests(p, this.request))) === null || _f === void 0 ? void 0 : _f.name;
655
679
  }
@@ -704,9 +728,27 @@ export class FtSearchBar extends FtLitElement {
704
728
  if (this.facetsRequest.length > 0) {
705
729
  this.facetsLoaded = false;
706
730
  this.updateFacetsDebouncer.run(async () => {
707
- var _a, _b;
708
- this.facets = (_b = await ((_a = this.api) === null || _a === void 0 ? void 0 : _a.search({ ...this.request, query: "" }).then(r => r.facets).catch(() => []))) !== null && _b !== void 0 ? _b : [];
709
- this.facets.forEach(f => this.knownFacetLabels[f.key] = f.label);
731
+ var _a;
732
+ const retrievedFacets = new Map();
733
+ await ((_a = this.api) === null || _a === void 0 ? void 0 : _a.search({ ...this.request, query: "" }).then(r => r.facets.forEach(f => {
734
+ this.knownFacetLabels.set(f.key, f.label);
735
+ retrievedFacets.set(f.key, f);
736
+ })).catch(doNothing));
737
+ this.facets = [];
738
+ for (let r of this.facetsRequest) {
739
+ if (retrievedFacets.has(r.id)) {
740
+ this.facets.push(retrievedFacets.get(r.id));
741
+ }
742
+ else if (this.knownFacetLabels.has(r.id)) {
743
+ this.facets.push({
744
+ key: r.id,
745
+ label: this.knownFacetLabels.get(r.id),
746
+ rootNodes: [],
747
+ multiSelectionable: true,
748
+ hierarchical: false
749
+ });
750
+ }
751
+ }
710
752
  this.facetsLoaded = true;
711
753
  this.facetsInitialized = true;
712
754
  });
@@ -863,12 +905,6 @@ export class FtSearchBar extends FtLitElement {
863
905
  break;
864
906
  }
865
907
  }
866
- getFilterExportParts(metadataKey) {
867
- return ["container", "header", "clear-button", "input"].map(part => this.getFilterSubPartExportAttribute(part, metadataKey)).join(",");
868
- }
869
- getFilterSubPartExportAttribute(part, metadataKey) {
870
- return `${part}:filters-${part},${part}:filter-${metadataKey}-${part}`;
871
- }
872
908
  }
873
909
  FtSearchBar.elementDefinitions = {
874
910
  "ft-accordion": FtAccordion,
@@ -903,6 +939,9 @@ __decorate([
903
939
  __decorate([
904
940
  property({ type: Boolean })
905
941
  ], FtSearchBar.prototype, "forceMobileMenuOpen", void 0);
942
+ __decorate([
943
+ property({ type: Boolean })
944
+ ], FtSearchBar.prototype, "forceMenuOpen", void 0);
906
945
  __decorate([
907
946
  property()
908
947
  ], FtSearchBar.prototype, "baseUrl", void 0);