novo-elements 13.1.0 → 13.2.0-next.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 (230) hide show
  1. package/addons/ckeditor/index.d.ts +3 -1
  2. package/elements/agenda/common/AgendaDateChange.scss +3 -3
  3. package/elements/agenda/common/AgendaHoursLayout.scss +2 -2
  4. package/elements/agenda/day/AgendaDayView.scss +3 -3
  5. package/elements/agenda/month/AgendaMonthView.scss +8 -8
  6. package/elements/agenda/week/AgendaWeekView.scss +4 -4
  7. package/elements/aside/aside.component.scss +17 -2
  8. package/elements/aside/index.d.ts +16 -8
  9. package/elements/autocomplete/autocomplete.component.scss +4 -0
  10. package/elements/avatar/Avatar.scss +2 -2
  11. package/elements/breadcrumbs/Breadcrumb.scss +5 -0
  12. package/elements/breadcrumbs/breadcrumb-item/BreadcrumbItem.scss +3 -3
  13. package/elements/button/styles/button-dialogue.scss +6 -5
  14. package/elements/button/styles/button-fab.scss +1 -1
  15. package/elements/button/styles/button-icon.scss +5 -5
  16. package/elements/button/styles/button-other.scss +5 -5
  17. package/elements/button/styles/button-primary.scss +11 -9
  18. package/elements/button/styles/button-secondary.scss +8 -9
  19. package/elements/button/styles/button-standard.scss +2 -2
  20. package/elements/button/styles/button.scss +18 -12
  21. package/elements/calendar/calendar.component.scss +13 -13
  22. package/elements/calendar/month-select/month-select.component.scss +3 -3
  23. package/elements/calendar/month-view/month-view.component.scss +7 -7
  24. package/elements/calendar/year-select/year-select.component.scss +3 -3
  25. package/elements/card/Card.scss +55 -12
  26. package/elements/card/CardContent.scss +1 -1
  27. package/elements/card/CardFooter.scss +2 -2
  28. package/elements/card/CardHeader.scss +2 -2
  29. package/elements/category-dropdown/CategoryDropdown.scss +9 -9
  30. package/elements/checkbox/CheckList.scss +3 -3
  31. package/elements/checkbox/Checkbox.scss +3 -3
  32. package/elements/chips/Chip.scss +17 -17
  33. package/elements/chips/Chips.scss +9 -9
  34. package/elements/chips/RowChips.scss +2 -2
  35. package/elements/chips/index.d.ts +3 -1
  36. package/elements/color-picker/color-picker.component.scss +1 -1
  37. package/elements/common/index.d.ts +11 -3
  38. package/elements/common/option/option.component.scss +14 -19
  39. package/elements/common/selection/pseudo-checkbox/pseudo-checkbox.component.scss +2 -2
  40. package/elements/common/typography/text.mixins.scss +19 -19
  41. package/elements/data-table/data-table.component.scss +32 -23
  42. package/elements/data-table/index.d.ts +2 -1
  43. package/elements/data-table/pagination/data-table-pagination.component.scss +6 -6
  44. package/elements/date-picker/DatePicker.scss +18 -18
  45. package/elements/date-picker/DatePickerInput.scss +5 -5
  46. package/elements/date-picker/DateRangeInput.scss +1 -1
  47. package/elements/date-picker/MultiDateInput.scss +2 -2
  48. package/elements/date-time-picker/_DateTimePicker.scss +5 -5
  49. package/elements/divider/divider.component.scss +3 -3
  50. package/elements/dropdown/Dropdown.scss +7 -5
  51. package/elements/expansion/_expansion-theme.scss +1 -1
  52. package/elements/expansion/expansion-panel.scss +1 -0
  53. package/elements/field/error/error.scss +1 -1
  54. package/elements/field/field-fill.scss +4 -4
  55. package/elements/field/field-list.scss +4 -4
  56. package/elements/field/field-outline.scss +6 -6
  57. package/elements/field/field-standard.scss +3 -3
  58. package/elements/field/field.scss +14 -1
  59. package/elements/form/ControlGroup.scss +7 -7
  60. package/elements/form/Form.scss +40 -40
  61. package/elements/form/extras/address/Address.scss +6 -6
  62. package/elements/form/extras/file/FileInput.scss +4 -4
  63. package/elements/form/fieldset-header.scss +3 -3
  64. package/elements/form/index.d.ts +1 -1
  65. package/elements/header/Header.scss +45 -10
  66. package/elements/icon/Icon.scss +1 -1
  67. package/elements/layout/collapsible-nav/collapsible-nav.component.scss +20 -0
  68. package/elements/layout/index.d.ts +38 -5
  69. package/elements/list/list-item-content.scss +1 -1
  70. package/elements/list/list-item-header-avatar.scss +1 -1
  71. package/elements/list/list-item.scss +6 -6
  72. package/elements/loading/NovoSpinner.scss +1 -1
  73. package/elements/menu/menu-content.component.scss +8 -7
  74. package/elements/modal/modal.component.scss +8 -8
  75. package/elements/modal/notification.component.scss +21 -21
  76. package/elements/multi-picker/_MultiPicker.scss +2 -2
  77. package/elements/picker/Picker.scss +13 -13
  78. package/elements/picker/extras/grouped-multi-picker-results/GroupedMultiPickerResults.scss +14 -14
  79. package/elements/picker/extras/mixed-multi-picker-results/MixedMultiPickerResults.scss +17 -17
  80. package/elements/picker/extras/picker-results/PickerResult.scss +1 -1
  81. package/elements/picker/extras/picker-results/PickerResults.scss +25 -21
  82. package/elements/picker/extras/skills-picker-results/SkillsSpecialtyPickerResults.scss +3 -3
  83. package/elements/places/index.d.ts +24 -14
  84. package/elements/places/places.component.scss +3 -3
  85. package/elements/popover/PopOver.scss +2 -1
  86. package/elements/progress/Progress.scss +2 -2
  87. package/elements/progress/ProgressBar.scss +13 -3
  88. package/elements/query-builder/condition-builder/condition-builder.component.scss +1 -20
  89. package/elements/query-builder/index.d.ts +67 -35
  90. package/elements/radio/Radio.scss +8 -8
  91. package/elements/radio/radio-group.scss +2 -2
  92. package/elements/search/SearchBox.scss +8 -9
  93. package/elements/select/Select.scss +15 -14
  94. package/elements/select-search/select-search.component.scss +1 -1
  95. package/elements/simple-table/PaginationOld.scss +5 -5
  96. package/elements/simple-table/table.scss +15 -10
  97. package/elements/stepper/step-header.component.scss +9 -9
  98. package/elements/stepper/stepper.component.scss +25 -7
  99. package/elements/switch/Switch.scss +15 -7
  100. package/elements/tabbed-group-picker/TabbedGroupPicker.scss +17 -8
  101. package/elements/tabbed-group-picker/index.d.ts +27 -14
  102. package/elements/tabs/tab-nav.scss +3 -3
  103. package/elements/tabs/tab.scss +35 -5
  104. package/elements/tiles/Tiles.scss +24 -5
  105. package/elements/time-picker/TimePicker.scss +6 -6
  106. package/elements/time-picker/TimePickerInput.scss +1 -1
  107. package/elements/tip-well/TipWell.scss +5 -6
  108. package/elements/toast/Toast.scss +19 -18
  109. package/elements/toolbar/toolbar.component.scss +24 -6
  110. package/elements/tooltip/Tooltip.scss +2 -2
  111. package/elements/value/Value.scss +5 -4
  112. package/fesm2022/novo-elements-addons-ckeditor.mjs +22 -12
  113. package/fesm2022/novo-elements-addons-ckeditor.mjs.map +1 -1
  114. package/fesm2022/novo-elements-elements-agenda.mjs +8 -8
  115. package/fesm2022/novo-elements-elements-agenda.mjs.map +1 -1
  116. package/fesm2022/novo-elements-elements-aside.mjs +24 -9
  117. package/fesm2022/novo-elements-elements-aside.mjs.map +1 -1
  118. package/fesm2022/novo-elements-elements-autocomplete.mjs +2 -2
  119. package/fesm2022/novo-elements-elements-autocomplete.mjs.map +1 -1
  120. package/fesm2022/novo-elements-elements-avatar.mjs +4 -4
  121. package/fesm2022/novo-elements-elements-avatar.mjs.map +1 -1
  122. package/fesm2022/novo-elements-elements-breadcrumbs.mjs +4 -4
  123. package/fesm2022/novo-elements-elements-breadcrumbs.mjs.map +1 -1
  124. package/fesm2022/novo-elements-elements-button.mjs +2 -2
  125. package/fesm2022/novo-elements-elements-button.mjs.map +1 -1
  126. package/fesm2022/novo-elements-elements-calendar.mjs +8 -8
  127. package/fesm2022/novo-elements-elements-calendar.mjs.map +1 -1
  128. package/fesm2022/novo-elements-elements-card.mjs +8 -8
  129. package/fesm2022/novo-elements-elements-card.mjs.map +1 -1
  130. package/fesm2022/novo-elements-elements-category-dropdown.mjs +2 -2
  131. package/fesm2022/novo-elements-elements-category-dropdown.mjs.map +1 -1
  132. package/fesm2022/novo-elements-elements-checkbox.mjs +4 -4
  133. package/fesm2022/novo-elements-elements-checkbox.mjs.map +1 -1
  134. package/fesm2022/novo-elements-elements-chips.mjs +12 -8
  135. package/fesm2022/novo-elements-elements-chips.mjs.map +1 -1
  136. package/fesm2022/novo-elements-elements-color-picker.mjs +4 -4
  137. package/fesm2022/novo-elements-elements-color-picker.mjs.map +1 -1
  138. package/fesm2022/novo-elements-elements-common.mjs +61 -21
  139. package/fesm2022/novo-elements-elements-common.mjs.map +1 -1
  140. package/fesm2022/novo-elements-elements-data-table.mjs +4 -4
  141. package/fesm2022/novo-elements-elements-data-table.mjs.map +1 -1
  142. package/fesm2022/novo-elements-elements-date-picker.mjs +8 -8
  143. package/fesm2022/novo-elements-elements-date-picker.mjs.map +1 -1
  144. package/fesm2022/novo-elements-elements-date-time-picker.mjs +2 -2
  145. package/fesm2022/novo-elements-elements-date-time-picker.mjs.map +1 -1
  146. package/fesm2022/novo-elements-elements-divider.mjs +2 -2
  147. package/fesm2022/novo-elements-elements-divider.mjs.map +1 -1
  148. package/fesm2022/novo-elements-elements-dropdown.mjs +2 -2
  149. package/fesm2022/novo-elements-elements-dropdown.mjs.map +1 -1
  150. package/fesm2022/novo-elements-elements-expansion.mjs +2 -2
  151. package/fesm2022/novo-elements-elements-expansion.mjs.map +1 -1
  152. package/fesm2022/novo-elements-elements-field.mjs +6 -6
  153. package/fesm2022/novo-elements-elements-field.mjs.map +1 -1
  154. package/fesm2022/novo-elements-elements-form.mjs +17 -15
  155. package/fesm2022/novo-elements-elements-form.mjs.map +1 -1
  156. package/fesm2022/novo-elements-elements-header.mjs +2 -2
  157. package/fesm2022/novo-elements-elements-header.mjs.map +1 -1
  158. package/fesm2022/novo-elements-elements-icon.mjs +2 -2
  159. package/fesm2022/novo-elements-elements-icon.mjs.map +1 -1
  160. package/fesm2022/novo-elements-elements-layout.mjs +90 -9
  161. package/fesm2022/novo-elements-elements-layout.mjs.map +1 -1
  162. package/fesm2022/novo-elements-elements-list.mjs +10 -10
  163. package/fesm2022/novo-elements-elements-list.mjs.map +1 -1
  164. package/fesm2022/novo-elements-elements-loading.mjs +2 -2
  165. package/fesm2022/novo-elements-elements-loading.mjs.map +1 -1
  166. package/fesm2022/novo-elements-elements-menu.mjs +2 -2
  167. package/fesm2022/novo-elements-elements-menu.mjs.map +1 -1
  168. package/fesm2022/novo-elements-elements-modal.mjs +4 -4
  169. package/fesm2022/novo-elements-elements-modal.mjs.map +1 -1
  170. package/fesm2022/novo-elements-elements-multi-picker.mjs +2 -2
  171. package/fesm2022/novo-elements-elements-multi-picker.mjs.map +1 -1
  172. package/fesm2022/novo-elements-elements-picker.mjs +14 -14
  173. package/fesm2022/novo-elements-elements-picker.mjs.map +1 -1
  174. package/fesm2022/novo-elements-elements-places.mjs +195 -187
  175. package/fesm2022/novo-elements-elements-places.mjs.map +1 -1
  176. package/fesm2022/novo-elements-elements-popover.mjs +2 -2
  177. package/fesm2022/novo-elements-elements-popover.mjs.map +1 -1
  178. package/fesm2022/novo-elements-elements-progress.mjs +4 -4
  179. package/fesm2022/novo-elements-elements-progress.mjs.map +1 -1
  180. package/fesm2022/novo-elements-elements-query-builder.mjs +67 -19
  181. package/fesm2022/novo-elements-elements-query-builder.mjs.map +1 -1
  182. package/fesm2022/novo-elements-elements-radio.mjs +4 -4
  183. package/fesm2022/novo-elements-elements-radio.mjs.map +1 -1
  184. package/fesm2022/novo-elements-elements-search.mjs +2 -2
  185. package/fesm2022/novo-elements-elements-search.mjs.map +1 -1
  186. package/fesm2022/novo-elements-elements-select.mjs +2 -2
  187. package/fesm2022/novo-elements-elements-select.mjs.map +1 -1
  188. package/fesm2022/novo-elements-elements-simple-table.mjs +6 -6
  189. package/fesm2022/novo-elements-elements-simple-table.mjs.map +1 -1
  190. package/fesm2022/novo-elements-elements-stepper.mjs +8 -8
  191. package/fesm2022/novo-elements-elements-stepper.mjs.map +1 -1
  192. package/fesm2022/novo-elements-elements-switch.mjs +2 -2
  193. package/fesm2022/novo-elements-elements-switch.mjs.map +1 -1
  194. package/fesm2022/novo-elements-elements-tabbed-group-picker.mjs +70 -10
  195. package/fesm2022/novo-elements-elements-tabbed-group-picker.mjs.map +1 -1
  196. package/fesm2022/novo-elements-elements-tabs.mjs +6 -6
  197. package/fesm2022/novo-elements-elements-tabs.mjs.map +1 -1
  198. package/fesm2022/novo-elements-elements-tiles.mjs +2 -2
  199. package/fesm2022/novo-elements-elements-tiles.mjs.map +1 -1
  200. package/fesm2022/novo-elements-elements-time-picker.mjs +4 -4
  201. package/fesm2022/novo-elements-elements-time-picker.mjs.map +1 -1
  202. package/fesm2022/novo-elements-elements-tip-well.mjs +2 -2
  203. package/fesm2022/novo-elements-elements-tip-well.mjs.map +1 -1
  204. package/fesm2022/novo-elements-elements-toast.mjs +2 -2
  205. package/fesm2022/novo-elements-elements-toast.mjs.map +1 -1
  206. package/fesm2022/novo-elements-elements-toolbar.mjs +2 -2
  207. package/fesm2022/novo-elements-elements-toolbar.mjs.map +1 -1
  208. package/fesm2022/novo-elements-elements-tooltip.mjs +2 -2
  209. package/fesm2022/novo-elements-elements-tooltip.mjs.map +1 -1
  210. package/fesm2022/novo-elements-elements-value.mjs +2 -2
  211. package/fesm2022/novo-elements-elements-value.mjs.map +1 -1
  212. package/fesm2022/novo-elements-services.mjs +1 -0
  213. package/fesm2022/novo-elements-services.mjs.map +1 -1
  214. package/fesm2022/novo-elements.mjs +14 -0
  215. package/fesm2022/novo-elements.mjs.map +1 -1
  216. package/index.d.ts +14 -0
  217. package/novo-elements.scss +7 -7
  218. package/package.json +1 -1
  219. package/services/index.d.ts +1 -0
  220. package/styles/base.scss +1 -0
  221. package/styles/content/code.scss +2 -2
  222. package/styles/content/forms.scss +2 -2
  223. package/styles/content/misc.scss +3 -3
  224. package/styles/content/range.scss +3 -3
  225. package/styles/iconography.scss +3 -3
  226. package/styles/themes/bh2026.scss +134 -0
  227. package/styles/themes/dark.scss +6 -1
  228. package/styles/themes/light.scss +4 -0
  229. package/styles/typography.scss +3 -3
  230. package/styles/variables.scss +6 -6
@@ -1,11 +1,11 @@
1
- import * as i3 from '@angular/common';
2
- import { isPlatformBrowser, CommonModule } from '@angular/common';
3
1
  import * as i0 from '@angular/core';
4
- import { PLATFORM_ID, Inject, Injectable, forwardRef, EventEmitter, Output, Input, Component, NgModule, InjectionToken } from '@angular/core';
2
+ import { PLATFORM_ID, Inject, Injectable, InjectionToken, forwardRef, EventEmitter, Output, Input, Optional, Component, NgModule } from '@angular/core';
5
3
  import { NG_VALUE_ACCESSOR, FormsModule } from '@angular/forms';
6
4
  import { BasePickerResults } from 'novo-elements/elements/picker';
7
5
  import * as i2 from 'novo-elements/services';
8
- import { Observable } from 'rxjs';
6
+ import { NEVER } from 'rxjs';
7
+ import * as i3 from '@angular/common';
8
+ import { isPlatformBrowser, CommonModule } from '@angular/common';
9
9
  import * as i1 from '@angular/common/http';
10
10
  import { provideHttpClient, withInterceptorsFromDi } from '@angular/common/http';
11
11
  import * as i4 from 'novo-elements/elements/list';
@@ -18,23 +18,58 @@ class GooglePlacesService {
18
18
  this._global = _global;
19
19
  this._localStorageService = _localStorageService;
20
20
  }
21
- getPredictions(url, query) {
22
- return new Promise((resolve) => {
23
- const separator = url.includes('?') ? '&' : '?';
24
- this._http.get(url + separator + 'query=' + query).subscribe((data) => {
25
- if (data) {
26
- resolve(data);
27
- }
28
- else {
29
- resolve(false);
21
+ // Ensure the Google Maps JS SDK is available before any window.google usage.
22
+ // No-ops when the SDK is already present (host script tag) or no key is configured (search-service path).
23
+ loadGoogleMaps(settings) {
24
+ const _window = this._global.nativeGlobal;
25
+ if (_window?.google?.maps?.places) {
26
+ return Promise.resolve();
27
+ }
28
+ if (!isPlatformBrowser(this.platformId) || !settings?.googleApiKey) {
29
+ return Promise.resolve();
30
+ }
31
+ if (!this.mapsLoad) {
32
+ this.mapsLoadKey = settings.googleApiKey;
33
+ this.mapsLoad = this.injectGoogleMapsScript(settings);
34
+ }
35
+ else if (this.mapsLoadKey && this.mapsLoadKey !== settings.googleApiKey) {
36
+ // The Maps JS API can only be loaded once per page; a second, different key is ignored.
37
+ console.warn('GooglePlacesService: the Google Maps SDK is already loading with a different key; ignoring the new googleApiKey.');
38
+ }
39
+ return this.mapsLoad;
40
+ }
41
+ injectGoogleMapsScript(settings) {
42
+ return new Promise((resolve, reject) => {
43
+ const _window = this._global.nativeGlobal;
44
+ // Build params one at a time so undefined override values are dropped instead of serialized as "undefined".
45
+ // The component uses the legacy Places API (AutocompleteService, PlacesService) which requires the
46
+ // synchronous library load — google.maps.places is fully populated when onload fires.
47
+ const params = new URLSearchParams();
48
+ params.set('key', settings.googleApiKey);
49
+ params.set('libraries', 'places');
50
+ for (const [key, value] of Object.entries(settings.googleMapsLoaderParams ?? {})) {
51
+ if (value !== undefined && value !== null) {
52
+ params.set(key, value);
30
53
  }
31
- });
54
+ }
55
+ const script = document.createElement('script');
56
+ script.src = `https://maps.googleapis.com/maps/api/js?${params.toString()}`;
57
+ script.async = true;
58
+ script.onload = () => resolve();
59
+ script.onerror = () => {
60
+ // Clear both cached fields so a later attempt can retry with any key.
61
+ this.mapsLoad = undefined;
62
+ this.mapsLoadKey = undefined;
63
+ reject(new Error('Failed to load the Google Maps JavaScript API.'));
64
+ };
65
+ document.head.appendChild(script);
32
66
  });
33
67
  }
34
- getLatLngDetail(url, lat, lng) {
68
+ getPredictions(url, query, sessionToken) {
35
69
  return new Promise((resolve) => {
36
70
  const separator = url.includes('?') ? '&' : '?';
37
- this._http.get(url + separator + 'lat=' + lat + '&lng=' + lng).subscribe((data) => {
71
+ const sessionParam = sessionToken ? '&sessionToken=' + sessionToken : '';
72
+ this._http.get(url + separator + 'query=' + query + sessionParam).subscribe((data) => {
38
73
  if (data) {
39
74
  resolve(data);
40
75
  }
@@ -44,10 +79,11 @@ class GooglePlacesService {
44
79
  });
45
80
  });
46
81
  }
47
- getPlaceDetails(url, placeId) {
82
+ getPlaceDetails(url, placeId, sessionToken) {
48
83
  return new Promise((resolve) => {
49
84
  const separator = url.includes('?') ? '&' : '?';
50
- this._http.get(url + separator + 'query=' + placeId).subscribe((data) => {
85
+ const sessionParam = sessionToken ? '&sessionToken=' + sessionToken : '';
86
+ this._http.get(url + separator + 'query=' + placeId + sessionParam).subscribe((data) => {
51
87
  if (data) {
52
88
  resolve(data);
53
89
  }
@@ -57,51 +93,6 @@ class GooglePlacesService {
57
93
  });
58
94
  });
59
95
  }
60
- getGeoCurrentLocation() {
61
- return new Promise((resolve) => {
62
- if (isPlatformBrowser(this.platformId)) {
63
- const _window = this._global.nativeGlobal;
64
- if (_window.navigator.geolocation) {
65
- _window.navigator.geolocation.getCurrentPosition((pos) => {
66
- const latlng = { lat: parseFloat(pos.coords.latitude + ''), lng: parseFloat(pos.coords.longitude + '') };
67
- resolve(latlng);
68
- });
69
- }
70
- else {
71
- resolve(false);
72
- }
73
- }
74
- else {
75
- resolve(false);
76
- }
77
- });
78
- }
79
- getGeoLatLngDetail(latlng) {
80
- return new Promise((resolve) => {
81
- if (isPlatformBrowser(this.platformId)) {
82
- const _window = this._global.nativeGlobal;
83
- const geocoder = new _window.google.maps.Geocoder();
84
- geocoder.geocode({ location: latlng }, (results, status) => {
85
- if (status === 'OK') {
86
- this.getGeoPlaceDetail(results[0].place_id).then((result) => {
87
- if (result) {
88
- resolve(result);
89
- }
90
- else {
91
- resolve(false);
92
- }
93
- });
94
- }
95
- else {
96
- resolve(false);
97
- }
98
- });
99
- }
100
- else {
101
- resolve(false);
102
- }
103
- });
104
- }
105
96
  getGeoPrediction(params) {
106
97
  return new Promise((resolve) => {
107
98
  if (isPlatformBrowser(this.platformId)) {
@@ -162,14 +153,12 @@ class GooglePlacesService {
162
153
  const _window = this._global.nativeGlobal;
163
154
  const placesService = new _window.google.maps.places.PlacesService(document.createElement('div'));
164
155
  placesService.getDetails({ placeId }, (result) => {
165
- if (result === null || result.length === 0) {
156
+ if (result === null) {
157
+ resolve(false);
158
+ }
159
+ else if (result.length === 0) {
166
160
  this.getGeoPaceDetailByReferance(result.referance).then((referanceData) => {
167
- if (!referanceData) {
168
- resolve(false);
169
- }
170
- else {
171
- resolve(referanceData);
172
- }
161
+ resolve(referanceData || false);
173
162
  });
174
163
  }
175
164
  else {
@@ -241,7 +230,7 @@ class GooglePlacesService {
241
230
  geocoder.geocode({ location: placeDetail.geometry.location }, (results, status) => {
242
231
  if (status === 'OK' && results.length) {
243
232
  resolve(results.reduce((postalCodes, result) => {
244
- const postalCodeComponent = result.address_components.find(item => item.types.includes('postal_code'));
233
+ const postalCodeComponent = result.address_components.find((item) => item.types.includes('postal_code'));
245
234
  if (postalCodeComponent && !postalCodes.includes(postalCodeComponent.long_name)) {
246
235
  postalCodes.push(postalCodeComponent.long_name);
247
236
  }
@@ -280,6 +269,9 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.19", ngImpo
280
269
  args: [PLATFORM_ID]
281
270
  }] }, { type: i2.GlobalRef }, { type: i2.LocalStorageService }] });
282
271
 
272
+ /** App-wide address-lookup config; when provided, every novo-address enables autocomplete on Address 1. */
273
+ const NOVO_ADDRESS_CONFIG = new InjectionToken('NOVO_ADDRESS_CONFIG');
274
+
283
275
  // NG2
284
276
  // Value accessor for the component (supports ngModel)
285
277
  const PLACES_VALUE_ACCESSOR = {
@@ -288,18 +280,20 @@ const PLACES_VALUE_ACCESSOR = {
288
280
  multi: true,
289
281
  };
290
282
  class PlacesListComponent extends BasePickerResults {
291
- constructor(platformId, _elmRef, _global, _googlePlacesService, cdr) {
283
+ static { this.SESSION_TOKEN_TIMEOUT_MS = 3 * 60 * 1000; }
284
+ constructor(_elmRef, _global, _googlePlacesService, cdr,
285
+ // Fallback config from the app-wide token; used when [userSettings] does not provide a field.
286
+ addressConfig = null) {
292
287
  super(_elmRef, cdr);
293
- this.platformId = platformId;
294
288
  this._elmRef = _elmRef;
295
289
  this._global = _global;
296
290
  this._googlePlacesService = _googlePlacesService;
297
291
  this.cdr = cdr;
292
+ this.addressConfig = addressConfig;
298
293
  this.termChange = new EventEmitter();
299
294
  this.select = new EventEmitter();
300
295
  this.matchesUpdated = new EventEmitter();
301
296
  this.locationInput = '';
302
- this.gettingCurrentLocationFlag = false;
303
297
  this.dropdownOpen = false;
304
298
  this.recentDropdownOpen = false;
305
299
  this.isSettingsError = false;
@@ -309,6 +303,8 @@ class PlacesListComponent extends BasePickerResults {
309
303
  this.selectedDataIndex = -1;
310
304
  this.recentSearchData = [];
311
305
  this.userSelectedOption = '';
306
+ this.sessionToken = '';
307
+ this.sessionTokenStartedAt = 0;
312
308
  this.defaultSettings = {
313
309
  geoPredictionServerUrl: '',
314
310
  geoLatLangServiceUrl: '',
@@ -332,6 +328,8 @@ class PlacesListComponent extends BasePickerResults {
332
328
  currentLocIconUrl: '',
333
329
  searchIconUrl: '',
334
330
  locationIconUrl: '',
331
+ googleApiKey: '',
332
+ googleMapsLoaderParams: {},
335
333
  };
336
334
  this.onModelChange = () => { };
337
335
  this.onModelTouched = () => { };
@@ -369,6 +367,7 @@ class PlacesListComponent extends BasePickerResults {
369
367
  }
370
368
  else {
371
369
  this.matches = [];
370
+ this.clearSessionToken();
372
371
  if (this.userSelectedOption) {
373
372
  this.userQuerySubmit('false');
374
373
  }
@@ -425,21 +424,40 @@ class PlacesListComponent extends BasePickerResults {
425
424
  // this.select.emit(false);
426
425
  }
427
426
  }
428
- // function to get user current location from the device.
429
- currentLocationSelected() {
430
- if (isPlatformBrowser(this.platformId)) {
431
- this.gettingCurrentLocationFlag = true;
432
- this.dropdownOpen = false;
433
- this._googlePlacesService.getGeoCurrentLocation().then((result) => {
434
- if (!result) {
435
- this.gettingCurrentLocationFlag = false;
436
- }
437
- else {
438
- this.getCurrentLocationInfo(result);
427
+ // Fold a raw Google/REST/recent record into the internal AddressLookupPrediction shape.
428
+ normalizePrediction(raw) {
429
+ return {
430
+ placeId: raw?.placeId || raw?.place_id,
431
+ primaryText: raw?.primaryText || raw?.structured_formatting?.main_text || raw?.displayAddress || raw?.description || '',
432
+ secondaryText: raw?.secondaryText || raw?.structured_formatting?.secondary_text || '',
433
+ displayAddress: raw?.displayAddress || raw?.description,
434
+ types: raw?.types,
435
+ raw,
436
+ };
437
+ }
438
+ onKeyDown(event) {
439
+ if (this.dropdownOpen) {
440
+ if (event.key === "ArrowUp" /* Key.ArrowUp */) {
441
+ this.prevActiveMatch();
442
+ return;
443
+ }
444
+ if (event.key === "ArrowDown" /* Key.ArrowDown */) {
445
+ this.nextActiveMatch();
446
+ return;
447
+ }
448
+ if (event.key === "Enter" /* Key.Enter */) {
449
+ // Only select when a prediction is highlighted.
450
+ if (this.activeMatch) {
451
+ this.selectMatch(this.activeMatch);
439
452
  }
440
- });
453
+ return;
454
+ }
441
455
  }
442
456
  }
457
+ search(term, mode) {
458
+ // Disable the base search term functionality here since it is handled by the places picker separately
459
+ return NEVER;
460
+ }
443
461
  // module initialization happens. function called by ngOninit and ngOnChange
444
462
  moduleInit() {
445
463
  this.settings = this.setUserSettings();
@@ -458,6 +476,10 @@ class PlacesListComponent extends BasePickerResults {
458
476
  if (this.settings.showRecentSearch) {
459
477
  this.getRecentLocations();
460
478
  }
479
+ if (this.settings.useGoogleGeoApi && !this.settings.googleApiKey) {
480
+ console.warn('google-places-list: No googleApiKey configured — Google Places autocomplete is disabled. ' +
481
+ 'Pass address.googleApiKey to NovoElementProviders.forRoot() to enable it.');
482
+ }
461
483
  if (!this.settings.useGoogleGeoApi) {
462
484
  if (!this.settings.geoPredictionServerUrl) {
463
485
  this.isSettingsError = true;
@@ -489,21 +511,25 @@ class PlacesListComponent extends BasePickerResults {
489
511
  }
490
512
  }
491
513
  // function to set user settings if it is available.
514
+ // Priority: [userSettings] input > NOVO_ADDRESS_CONFIG token > defaultSettings.
492
515
  setUserSettings() {
493
516
  const _tempObj = {};
494
- if (this.userSettings && typeof this.userSettings === 'object') {
495
- const keys = Object.keys(this.defaultSettings);
496
- for (const value of keys) {
497
- _tempObj[value] = this.userSettings[value] !== undefined ? this.userSettings[value] : this.defaultSettings[value];
517
+ const keys = Object.keys(this.defaultSettings);
518
+ for (const value of keys) {
519
+ if (this.userSettings?.[value] !== undefined) {
520
+ _tempObj[value] = this.userSettings[value];
521
+ }
522
+ else if (this.addressConfig?.[value] !== undefined) {
523
+ _tempObj[value] = this.addressConfig[value];
524
+ }
525
+ else {
526
+ _tempObj[value] = this.defaultSettings[value];
498
527
  }
499
- return _tempObj;
500
- }
501
- else {
502
- return this.defaultSettings;
503
528
  }
529
+ return _tempObj;
504
530
  }
505
531
  // function to get the autocomplete list based on user input.
506
- getListQuery(value) {
532
+ async getListQuery(value) {
507
533
  this.recentDropdownOpen = false;
508
534
  if (this.settings.useGoogleGeoApi) {
509
535
  const _tempParams = {
@@ -515,17 +541,59 @@ class PlacesListComponent extends BasePickerResults {
515
541
  _tempParams.geoLocation = this.settings.geoLocation;
516
542
  _tempParams.radius = this.settings.geoRadius;
517
543
  }
518
- this._googlePlacesService.getGeoPrediction(_tempParams).then((result) => {
544
+ try {
545
+ await this._googlePlacesService.loadGoogleMaps(this.settings);
546
+ if (!this._global.nativeGlobal?.google?.maps?.places) {
547
+ this.updateListItem([]);
548
+ return;
549
+ }
550
+ const result = await this._googlePlacesService.getGeoPrediction(_tempParams);
519
551
  this.updateListItem(result);
520
- });
552
+ }
553
+ catch (err) {
554
+ console.error('Failed to load Google Maps for address predictions', err);
555
+ this.updateListItem([]);
556
+ }
521
557
  }
522
558
  else {
523
- this._googlePlacesService.getPredictions(this.settings.geoPredictionServerUrl, value).then((result) => {
559
+ this._googlePlacesService.getPredictions(this.settings.geoPredictionServerUrl, value, this.ensureSessionToken()).then((result) => {
524
560
  result = this.extractServerList(this.settings.serverResponseListHierarchy, result);
525
561
  this.updateListItem(result);
562
+ }).catch((err) => {
563
+ console.error('Failed to load address predictions from server', err);
564
+ this.updateListItem([]);
526
565
  });
527
566
  }
528
567
  }
568
+ // Returns the active billing-session token for prediction calls, minting a fresh UUID v4 when
569
+ // none exists or the previous one has gone stale (~3 min of inactivity). Each call refreshes the
570
+ // inactivity window.
571
+ ensureSessionToken() {
572
+ const now = Date.now();
573
+ if (!this.sessionToken || now - this.sessionTokenStartedAt > PlacesListComponent.SESSION_TOKEN_TIMEOUT_MS) {
574
+ this.sessionToken = this.generateSessionToken();
575
+ }
576
+ this.sessionTokenStartedAt = now;
577
+ return this.sessionToken;
578
+ }
579
+ // Mints a v4 UUID for the Google Places billing session. Prefers the built-in crypto.randomUUID(),
580
+ // which exists only in secure contexts (HTTPS / localhost). Falls back to a locally generated UUID for
581
+ // insecure-context local development (e.g. localhost development); the token only needs to be a unique
582
+ // opaque string, so Math.random() is acceptable there.
583
+ generateSessionToken() {
584
+ if (typeof crypto !== 'undefined' && typeof crypto.randomUUID === 'function') {
585
+ return crypto.randomUUID();
586
+ }
587
+ return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (char) => {
588
+ const random = (Math.random() * 16) | 0;
589
+ const value = char === 'x' ? random : (random & 0x3) | 0x8;
590
+ return value.toString(16);
591
+ });
592
+ }
593
+ clearSessionToken() {
594
+ this.sessionToken = '';
595
+ this.sessionTokenStartedAt = 0;
596
+ }
529
597
  // function to extratc custom data which is send by the server.
530
598
  extractServerList(arrayList, data) {
531
599
  if (arrayList.length) {
@@ -556,49 +624,44 @@ class PlacesListComponent extends BasePickerResults {
556
624
  this.matches = (result || []).map((item) => this.normalizePrediction(item));
557
625
  });
558
626
  }
559
- // function to execute to get location detail based on latitude and longitude.
560
- getCurrentLocationInfo(latlng) {
561
- if (this.settings.useGoogleGeoApi) {
562
- this._googlePlacesService.getGeoLatLngDetail(latlng).then((result) => {
563
- if (result) {
564
- this.setRecentLocation(result);
565
- }
566
- this.gettingCurrentLocationFlag = false;
567
- });
568
- }
569
- else {
570
- this._googlePlacesService.getLatLngDetail(this.settings.geoLatLangServiceUrl, latlng.lat, latlng.lng).then((result) => {
571
- if (result) {
572
- result = this.extractServerList(this.settings.serverResponseatLangHierarchy, result);
573
- this.setRecentLocation(result);
574
- }
575
- this.gettingCurrentLocationFlag = false;
576
- });
577
- }
578
- }
579
627
  // function to retrieve the location info based on google place id.
580
- getPlaceLocationInfo(selectedData) {
628
+ async getPlaceLocationInfo(selectedData) {
581
629
  const placeId = selectedData.placeId;
582
630
  if (this.settings.useGoogleGeoApi) {
583
- this._googlePlacesService.getGeoPlaceDetail(placeId).then((data) => {
631
+ try {
632
+ // Ensure the SDK is loaded before getGeoPlaceDetail touches window.google.
633
+ await this._googlePlacesService.loadGoogleMaps(this.settings);
634
+ const data = await this._googlePlacesService.getGeoPlaceDetail(placeId);
584
635
  if (data) {
585
636
  this.setRecentLocation(data);
586
637
  }
587
- });
638
+ }
639
+ catch (err) {
640
+ console.error('Failed to load Google Maps for place details', err);
641
+ }
588
642
  }
589
643
  else {
590
- this._googlePlacesService.getPlaceDetails(this.settings.geoLocDetailServerUrl, placeId).then((result) => {
644
+ try {
645
+ let result = await this._googlePlacesService.getPlaceDetails(this.settings.geoLocDetailServerUrl, placeId, this.sessionToken);
591
646
  if (result) {
592
647
  result = this.extractServerList(this.settings.serverResponseDetailHierarchy, result);
593
648
  this.setRecentLocation(result);
594
649
  }
595
- });
650
+ }
651
+ catch (err) {
652
+ console.error('Failed to load place details from server', err);
653
+ }
654
+ finally {
655
+ // The details call ends the Google billing session; clear the token even if the request
656
+ // failed so the next interaction starts a fresh session.
657
+ this.clearSessionToken();
658
+ }
596
659
  }
597
660
  }
598
661
  // function to store the selected user search in the localstorage.
599
662
  setRecentLocation(data) {
600
663
  data = JSON.parse(JSON.stringify(data));
601
- data.description = data.description ? data.description : (data.formattedAddress || data.formatted_address);
664
+ data.description = data.description ? data.description : data.formattedAddress || data.formatted_address;
602
665
  data.active = false;
603
666
  this.selectedDataIndex = -1;
604
667
  this.locationInput = data.description;
@@ -619,70 +682,18 @@ class PlacesListComponent extends BasePickerResults {
619
682
  this.recentSearchData = data && data.length ? data : [];
620
683
  });
621
684
  }
622
- // Fold a raw Google/REST/recent record into the internal AddressLookupPrediction shape.
623
- normalizePrediction(raw) {
624
- return {
625
- placeId: raw?.placeId || raw?.place_id,
626
- primaryText: raw?.primaryText || raw?.structured_formatting?.main_text || raw?.displayAddress || raw?.description || '',
627
- secondaryText: raw?.secondaryText || raw?.structured_formatting?.secondary_text || '',
628
- displayAddress: raw?.displayAddress || raw?.description,
629
- types: raw?.types,
630
- raw,
631
- };
632
- }
633
- onKeyDown(event) {
634
- if (this.dropdownOpen) {
635
- if (event.key === "ArrowUp" /* Key.ArrowUp */) {
636
- this.prevActiveMatch();
637
- return;
638
- }
639
- if (event.key === "ArrowDown" /* Key.ArrowDown */) {
640
- this.nextActiveMatch();
641
- return;
642
- }
643
- if (event.key === "Enter" /* Key.Enter */) {
644
- // Only select when a prediction is highlighted.
645
- if (this.activeMatch) {
646
- this.selectMatch(this.activeMatch);
647
- }
648
- return;
649
- }
650
- }
651
- }
652
- search(term, mode) {
653
- // Disable the base search term functionality here since it is handled by the places picker separately
654
- return new Observable();
655
- }
656
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.19", ngImport: i0, type: PlacesListComponent, deps: [{ token: PLATFORM_ID }, { token: i0.ElementRef }, { token: i2.GlobalRef }, { token: GooglePlacesService }, { token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component }); }
657
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.19", type: PlacesListComponent, isStandalone: false, selector: "google-places-list", inputs: { userSettings: "userSettings" }, outputs: { termChange: "termChange", select: "select", matchesUpdated: "matchesUpdated" }, providers: [PLACES_VALUE_ACCESSOR], usesInheritance: true, usesOnChanges: true, ngImport: i0, template: `
658
- <novo-list direction="vertical">
659
- <novo-list-item *ngFor="let data of matches; let $index = index" (click)="selectedListNode($event, $index)" [ngClass]="{ active: data === activeMatch }">
660
- <item-header>
661
- <item-avatar icon="location"></item-avatar>
662
- <item-title>{{ data.primaryText }}</item-title>
663
- </item-header>
664
- <item-content>{{ data.secondaryText }}</item-content>
665
- </novo-list-item>
666
- </novo-list>
667
- `, isInline: true, styles: [":host{display:grid}:host novo-list{border:1px solid #4a89dc;background-color:#fff}:host novo-list novo-list-item{cursor:pointer;flex:0 0;transition:background-color .25s}:host novo-list novo-list-item>div{width:100%}:host novo-list novo-list-item.active{background-color:#e0ebf9}:host novo-list novo-list-item:hover{background-color:#f1f6fc}:host novo-list novo-list-item item-content{flex-flow:row wrap}:host novo-list novo-list-item item-content>*{flex:0 0 33%;white-space:nowrap}\n"], dependencies: [{ kind: "directive", type: i3.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i3.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "component", type: i4.NovoListElement, selector: "novo-list", inputs: ["theme", "direction"] }, { kind: "component", type: i4.NovoListItemElement, selector: "novo-list-item, a[list-item], button[list-item]" }, { kind: "component", type: i4.NovoItemAvatarElement, selector: "item-avatar, novo-item-avatar", inputs: ["icon", "color"] }, { kind: "component", type: i4.NovoItemTitleElement, selector: "item-title, novo-item-title" }, { kind: "component", type: i4.NovoItemHeaderElement, selector: "item-header, novo-item-header" }, { kind: "component", type: i4.NovoItemContentElement, selector: "item-content, novo-item-content", inputs: ["direction"] }] }); }
685
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.19", ngImport: i0, type: PlacesListComponent, deps: [{ token: i0.ElementRef }, { token: i2.GlobalRef }, { token: GooglePlacesService }, { token: i0.ChangeDetectorRef }, { token: NOVO_ADDRESS_CONFIG, optional: true }], target: i0.ɵɵFactoryTarget.Component }); }
686
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.19", type: PlacesListComponent, isStandalone: false, selector: "google-places-list", inputs: { userSettings: "userSettings" }, outputs: { termChange: "termChange", select: "select", matchesUpdated: "matchesUpdated" }, providers: [PLACES_VALUE_ACCESSOR], usesInheritance: true, usesOnChanges: true, ngImport: i0, template: "<novo-list direction=\"vertical\">\n @for (data of matches; track $index) {\n <novo-list-item (click)=\"selectedListNode($event, $index)\" [ngClass]=\"{ active: data === activeMatch }\">\n <item-header>\n <item-avatar icon=\"location\"></item-avatar>\n <item-title>{{ data.primaryText }}</item-title>\n </item-header>\n <item-content>{{ data.secondaryText }}</item-content>\n </novo-list-item>\n }\n</novo-list>\n", styles: [":host{display:grid}:host novo-list{border:1px solid #4a89dc;background-color:var(--background-body)}:host novo-list novo-list-item{cursor:pointer;flex:0 0;transition:background-color .25s}:host novo-list novo-list-item>div{width:100%}:host novo-list novo-list-item.active{background-color:hsl(from var(--color-positive) h s calc(l + 35))}:host novo-list novo-list-item:hover{background-color:hsl(from var(--color-positive) h s calc(l + 39))}:host novo-list novo-list-item item-content{flex-flow:row wrap}:host novo-list novo-list-item item-content>*{flex:0 0 33%;white-space:nowrap}\n"], dependencies: [{ kind: "directive", type: i3.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "component", type: i4.NovoListElement, selector: "novo-list", inputs: ["theme", "direction"] }, { kind: "component", type: i4.NovoListItemElement, selector: "novo-list-item, a[list-item], button[list-item]" }, { kind: "component", type: i4.NovoItemAvatarElement, selector: "item-avatar, novo-item-avatar", inputs: ["icon", "color"] }, { kind: "component", type: i4.NovoItemTitleElement, selector: "item-title, novo-item-title" }, { kind: "component", type: i4.NovoItemHeaderElement, selector: "item-header, novo-item-header" }, { kind: "component", type: i4.NovoItemContentElement, selector: "item-content, novo-item-content", inputs: ["direction"] }] }); }
668
687
  }
669
688
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.19", ngImport: i0, type: PlacesListComponent, decorators: [{
670
689
  type: Component,
671
- args: [{ selector: 'google-places-list', providers: [PLACES_VALUE_ACCESSOR], template: `
672
- <novo-list direction="vertical">
673
- <novo-list-item *ngFor="let data of matches; let $index = index" (click)="selectedListNode($event, $index)" [ngClass]="{ active: data === activeMatch }">
674
- <item-header>
675
- <item-avatar icon="location"></item-avatar>
676
- <item-title>{{ data.primaryText }}</item-title>
677
- </item-header>
678
- <item-content>{{ data.secondaryText }}</item-content>
679
- </novo-list-item>
680
- </novo-list>
681
- `, standalone: false, styles: [":host{display:grid}:host novo-list{border:1px solid #4a89dc;background-color:#fff}:host novo-list novo-list-item{cursor:pointer;flex:0 0;transition:background-color .25s}:host novo-list novo-list-item>div{width:100%}:host novo-list novo-list-item.active{background-color:#e0ebf9}:host novo-list novo-list-item:hover{background-color:#f1f6fc}:host novo-list novo-list-item item-content{flex-flow:row wrap}:host novo-list novo-list-item item-content>*{flex:0 0 33%;white-space:nowrap}\n"] }]
682
- }], ctorParameters: () => [{ type: Object, decorators: [{
690
+ args: [{ selector: 'google-places-list', providers: [PLACES_VALUE_ACCESSOR], standalone: false, template: "<novo-list direction=\"vertical\">\n @for (data of matches; track $index) {\n <novo-list-item (click)=\"selectedListNode($event, $index)\" [ngClass]=\"{ active: data === activeMatch }\">\n <item-header>\n <item-avatar icon=\"location\"></item-avatar>\n <item-title>{{ data.primaryText }}</item-title>\n </item-header>\n <item-content>{{ data.secondaryText }}</item-content>\n </novo-list-item>\n }\n</novo-list>\n", styles: [":host{display:grid}:host novo-list{border:1px solid #4a89dc;background-color:var(--background-body)}:host novo-list novo-list-item{cursor:pointer;flex:0 0;transition:background-color .25s}:host novo-list novo-list-item>div{width:100%}:host novo-list novo-list-item.active{background-color:hsl(from var(--color-positive) h s calc(l + 35))}:host novo-list novo-list-item:hover{background-color:hsl(from var(--color-positive) h s calc(l + 39))}:host novo-list novo-list-item item-content{flex-flow:row wrap}:host novo-list novo-list-item item-content>*{flex:0 0 33%;white-space:nowrap}\n"] }]
691
+ }], ctorParameters: () => [{ type: i0.ElementRef }, { type: i2.GlobalRef }, { type: GooglePlacesService }, { type: i0.ChangeDetectorRef }, { type: undefined, decorators: [{
692
+ type: Optional
693
+ }, {
683
694
  type: Inject,
684
- args: [PLATFORM_ID]
685
- }] }, { type: i0.ElementRef }, { type: i2.GlobalRef }, { type: GooglePlacesService }, { type: i0.ChangeDetectorRef }], propDecorators: { userSettings: [{
695
+ args: [NOVO_ADDRESS_CONFIG]
696
+ }] }], propDecorators: { userSettings: [{
686
697
  type: Input
687
698
  }], termChange: [{
688
699
  type: Output
@@ -703,9 +714,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.19", ngImpo
703
714
  exports: [PlacesListComponent], imports: [CommonModule, FormsModule, NovoListModule], providers: [GooglePlacesService, provideHttpClient(withInterceptorsFromDi())] }]
704
715
  }] });
705
716
 
706
- /** App-wide address-lookup config; when provided, every novo-address enables autocomplete on Address 1. */
707
- const NOVO_ADDRESS_CONFIG = new InjectionToken('NOVO_ADDRESS_CONFIG');
708
-
709
717
  /**
710
718
  * Generated bundle index. Do not edit.
711
719
  */