@dative-gpi/foundation-core-components 1.0.35 → 1.0.37-report-v1

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 (84) hide show
  1. package/components/autocompletes/FSAutocompleteChart.vue +18 -8
  2. package/components/autocompletes/FSAutocompleteDashboard.vue +16 -6
  3. package/components/autocompletes/FSAutocompleteDashboardOrganisation.vue +7 -1
  4. package/components/autocompletes/FSAutocompleteDataCategory.vue +11 -5
  5. package/components/autocompletes/FSAutocompleteDataDefinition.vue +7 -1
  6. package/components/autocompletes/FSAutocompleteGroup.vue +7 -1
  7. package/components/autocompletes/FSAutocompleteLocation.vue +6 -0
  8. package/components/autocompletes/FSAutocompleteManufacturer.vue +8 -0
  9. package/components/autocompletes/FSAutocompleteModel.vue +9 -1
  10. package/components/autocompletes/FSAutocompleteOrganisationType.vue +7 -1
  11. package/components/autocompletes/FSAutocompleteRole.vue +17 -6
  12. package/components/autocompletes/FSAutocompleteServiceAccountRoleOrganisation.vue +7 -1
  13. package/components/autocompletes/FSAutocompleteUserOrganisation.vue +9 -1
  14. package/components/chips/FSChipGroupUserOrganisation.vue +61 -0
  15. package/components/chips/FSChipGroupUserOrganisationUI.vue +38 -0
  16. package/components/customProperties/FSMetaField.vue +31 -35
  17. package/components/customProperties/FSMetaHistory.vue +4 -4
  18. package/components/customProperties/FSMetaValue.vue +66 -33
  19. package/components/customProperties/helpers.ts +2 -1
  20. package/components/entities/FSBaseEntitiesList.vue +50 -0
  21. package/components/entities/FSDialogSelectEntities.vue +83 -0
  22. package/components/entities/FSEntityField.vue +203 -0
  23. package/components/entities/FSSelectEntitiesList.vue +209 -0
  24. package/components/entities/FSSimpleEntitiesList.vue +100 -0
  25. package/components/explorers/FSBaseDevicesExplorer.vue +310 -0
  26. package/components/explorers/FSBaseFoldersExplorer.vue +277 -0
  27. package/components/lists/FSDataTable.vue +23 -21
  28. package/components/lists/alerts/FSBaseAlertsList.vue +338 -0
  29. package/components/lists/alerts/FSButtonAcknowledgeAlert.vue +101 -0
  30. package/components/lists/authTokens/FSBaseAuthTokensList.vue +79 -0
  31. package/components/lists/chartOrganisationTypes/FSBaseChartOrganisationTypesList.vue +205 -0
  32. package/components/lists/chartOrganisations/FSBaseChartOrganisationsList.vue +206 -0
  33. package/components/lists/charts/FSBaseChartsList.vue +268 -0
  34. package/components/lists/comments/FSBaseCommentsList.vue +143 -0
  35. package/components/lists/connectivityScenarios/FSBaseConnectivityScenariosList.vue +128 -0
  36. package/components/lists/dashboardOrganisationTypes/FSBaseDashboardOrganisationTypesList.vue +179 -0
  37. package/components/lists/dashboards/FSBaseDashboardsList.vue +235 -0
  38. package/components/lists/dashboards/FSSimpleDashboardsList.vue +62 -0
  39. package/components/lists/dataCategories/FSBaseDataCategoriesList.vue +155 -0
  40. package/components/lists/dataDefinitions/FSBaseDataDefinitionsList.vue +130 -0
  41. package/components/lists/deviceOrganisations/FSBaseDeviceOrganisationsList.vue +378 -0
  42. package/components/lists/deviceOrganisations/FSSimpleDeviceOrganisationsList.vue +44 -0
  43. package/components/lists/folders/FSBaseFoldersList.vue +127 -0
  44. package/components/lists/folders/FSSimpleFoldersList.vue +44 -0
  45. package/components/lists/groups/FSBaseGroupsList.vue +136 -0
  46. package/components/lists/groups/FSSimpleGroupsList.vue +44 -0
  47. package/components/lists/locations/FSBaseLocationsList.vue +118 -0
  48. package/components/lists/locations/FSSimpleLocationsList.vue +44 -0
  49. package/components/lists/models/FSBaseModelsList.vue +155 -0
  50. package/components/lists/models/FSSimpleModelsList.vue +44 -0
  51. package/components/lists/reports/FSBaseReportExecutionsList.vue +137 -0
  52. package/components/lists/reports/FSBaseReportsList.vue +140 -0
  53. package/components/lists/roleOrganisationTypes/FSBaseRoleOrganisationTypesList.vue +128 -0
  54. package/components/lists/roleOrganisations/FSBaseRoleOrganisationsList.vue +128 -0
  55. package/components/lists/scenarioOrganisationTypes/FSBaseScenarioOrganisationTypesList.vue +157 -0
  56. package/components/lists/scenarioOrganisations/FSBaseScenarioOrganisationsList.vue +145 -0
  57. package/components/lists/scenarios/FSBaseScenariosList.vue +241 -0
  58. package/components/lists/serviceAccountOrganisations/FSBaseServiceAccountOrganisationsList.vue +155 -0
  59. package/components/lists/serviceAccountRoleOrganisations/FSBaseServiceAccountRoleOrganisationsList.vue +128 -0
  60. package/components/lists/userOrganisations/FSBaseUserOrganisationsList.vue +171 -0
  61. package/components/lists/userOrganisations/FSSimpleUserOrganisationsList.vue +45 -0
  62. package/components/tiles/FSChartTile.vue +70 -0
  63. package/components/tiles/FSDeviceOrganisationTile.vue +9 -2
  64. package/components/tiles/FSLocationTile.vue +66 -0
  65. package/components/treeviews/FSTreeViewFolder.vue +15 -3
  66. package/components/treeviews/FSTreeViewGroup.vue +22 -4
  67. package/package.json +9 -9
  68. package/utils/dashboards.ts +33 -5
  69. package/utils/index.ts +2 -2
  70. package/utils/permissions.ts +80 -0
  71. package/utils/roles.ts +4 -4
  72. package/utils/tables.ts +41 -0
  73. package/utils/users.ts +7 -4
  74. package/components/selects/FSAggregationSelector.vue +0 -51
  75. package/components/selects/FSAxisTypeSelector.vue +0 -48
  76. package/components/selects/FSDisplayAsSelector.vue +0 -52
  77. package/components/selects/FSFilterTypeSelector.vue +0 -53
  78. package/components/selects/FSHeatmapRuleSelector.vue +0 -52
  79. package/components/selects/FSOperationOnSelector.vue +0 -51
  80. package/components/selects/FSPlanningTypeSelector.vue +0 -51
  81. package/components/selects/FSPlotPerSelector.vue +0 -51
  82. package/components/selects/FSSelectSelectedEntities.vue +0 -59
  83. package/components/selects/FSSerieTypeSelector.vue +0 -51
  84. package/utils/charts.ts +0 -136
@@ -0,0 +1,209 @@
1
+ <template>
2
+ <FSCol
3
+ gap="24px"
4
+ >
5
+ <FSCol>
6
+ <FSText
7
+ font="text-button"
8
+ >
9
+ {{ $tr("ui.common.selection-reminder", "Selection reminder") }}
10
+ </FSText>
11
+ <FSRow
12
+ align="center-left"
13
+ height="50px"
14
+ >
15
+ <FSSlideGroup
16
+ v-if="$props.modelValue && $props.modelValue.length > 0"
17
+ >
18
+ <FSSimpleEntitiesList
19
+ :entity-type="$props.entityType"
20
+ :filters="simpleListFilters"
21
+ :showEdit="false"
22
+ :showRemove="showRemove"
23
+ @click:remove="onRemove"
24
+ direction="row"
25
+ />
26
+ </FSSlideGroup>
27
+ <FSText
28
+ v-else
29
+ >
30
+ {{ $tr("ui.common.no-selection", "No selection") }}
31
+ </FSText>
32
+ </FSRow>
33
+ </FSCol>
34
+
35
+ <FSCol>
36
+ <FSText
37
+ font="text-button"
38
+ >
39
+ {{ $tr("ui.common.entities-list", "Entities list") }}
40
+ </FSText>
41
+ <FSBaseEntitiesList
42
+ :singleSelect="$props.singleSelect"
43
+ :entity-type="$props.entityType"
44
+ :tableCode="tableCode"
45
+ :modelValue="$props.modelValue"
46
+ @update:modelValue="$emit('update:modelValue', $event)"
47
+ v-bind="baseTableAttrs"
48
+ />
49
+ </FSCol>
50
+ </FSCol>
51
+ </template>
52
+
53
+ <script lang="ts">
54
+ import { defineComponent, type PropType, computed } from "vue";
55
+
56
+ import { EntityType } from "@dative-gpi/foundation-shared-domain/enums";
57
+ import type { DashboardOrganisationFilters, DashboardOrganisationTypeFilters, DeviceOrganisationFilters, FolderFilters, GroupFilters, LocationFilters, ModelFilters, UserOrganisationFilters } from "@dative-gpi/foundation-core-domain/models";
58
+
59
+ import { TABLES as T } from "../../utils";
60
+
61
+ import FSSlideGroup from "@dative-gpi/foundation-shared-components/components/FSSlideGroup.vue";
62
+ import FSCol from "@dative-gpi/foundation-shared-components/components/FSCol.vue";
63
+ import FSRow from "@dative-gpi/foundation-shared-components/components/FSRow.vue";
64
+ import FSText from "@dative-gpi/foundation-shared-components/components/FSText.vue";
65
+
66
+
67
+ import FSSimpleEntitiesList from "./FSSimpleEntitiesList.vue";
68
+ import FSBaseEntitiesList from "./FSBaseEntitiesList.vue";
69
+
70
+ export default defineComponent({
71
+ name: "FSSelectEntitiesList",
72
+ components: {
73
+ FSSimpleEntitiesList,
74
+ FSBaseEntitiesList,
75
+ FSSlideGroup,
76
+ FSCol,
77
+ FSRow,
78
+ FSText
79
+ },
80
+ emits: ["update:modelValue"],
81
+ props: {
82
+ entityType: {
83
+ type: Number as PropType<EntityType>,
84
+ required: true
85
+ },
86
+ singleSelect: {
87
+ type: Boolean,
88
+ required: false,
89
+ default: false
90
+ },
91
+ modelValue: {
92
+ type: Array as PropType<string[]>,
93
+ required: false,
94
+ default: () => []
95
+ },
96
+ filters: {
97
+ type: Object,
98
+ required: false,
99
+ default: null
100
+ },
101
+ showRemove: {
102
+ type: Boolean,
103
+ required: false,
104
+ default: false
105
+ }
106
+ },
107
+ setup(props, { emit, attrs }){
108
+ const simpleListFilters = computed(() => {
109
+ switch(props.entityType) {
110
+ case EntityType.Device:
111
+ return {
112
+ deviceOrganisationsIds: props.modelValue
113
+ } satisfies DeviceOrganisationFilters;
114
+ case EntityType.Dashboard:
115
+ return {
116
+ dashboardOrganisationsIds: props.modelValue,
117
+ dashboardOrganisationTypesIds: props.modelValue
118
+ } satisfies DashboardOrganisationFilters & DashboardOrganisationTypeFilters;
119
+ case EntityType.Group:
120
+ return {
121
+ groupsIds: props.modelValue
122
+ } satisfies GroupFilters;
123
+ case EntityType.Folder:
124
+ return {
125
+ foldersIds: props.modelValue
126
+ } satisfies FolderFilters;
127
+ case EntityType.Location:
128
+ return {
129
+ locationsIds: props.modelValue
130
+ } satisfies LocationFilters;
131
+ case EntityType.User:
132
+ return {
133
+ userOrganisationsIds: props.modelValue
134
+ } satisfies UserOrganisationFilters;
135
+ case EntityType.Model:
136
+ return {
137
+ modelsIds: props.modelValue
138
+ } satisfies ModelFilters;
139
+ default:
140
+ return undefined;
141
+ };
142
+ })
143
+
144
+ const tableCode = computed(() => {
145
+ switch(props.entityType) {
146
+ case EntityType.Device:
147
+ return T.DEVICES_SELECT;
148
+ default:
149
+ return null;
150
+ };
151
+ })
152
+
153
+ const baseTableAttrs = computed(() => {
154
+ switch(props.entityType) {
155
+ case EntityType.Device:
156
+ return {
157
+ deviceOrganisationFilters: props.filters,
158
+ ...attrs
159
+ };
160
+ case EntityType.Dashboard:
161
+ return {
162
+ dashboardShallowsFilters: props.filters,
163
+ dashboardOrganisationsFilters: props.filters,
164
+ dashboardOrganisationTypeFetchFilter: props.filters,
165
+ ...attrs
166
+ };
167
+ case EntityType.Group:
168
+ return {
169
+ groupsFilters: props.filters,
170
+ ...attrs
171
+ };
172
+ case EntityType.Folder:
173
+ return {
174
+ foldersFilters: props.filters,
175
+ ...attrs
176
+ };
177
+ case EntityType.Location:
178
+ return {
179
+ locationsFilters: props.filters,
180
+ ...attrs
181
+ };
182
+ case EntityType.User:
183
+ return {
184
+ userOrganisationsFilters: props.filters,
185
+ ...attrs
186
+ };
187
+ case EntityType.Model:
188
+ return {
189
+ modelsFilters: props.filters,
190
+ ...attrs
191
+ };
192
+ default:
193
+ return null;
194
+ };
195
+ });
196
+
197
+ const onRemove = (id: string) => {
198
+ emit("update:modelValue", props.modelValue.filter((i) => i !== id));
199
+ }
200
+
201
+ return {
202
+ simpleListFilters,
203
+ baseTableAttrs,
204
+ tableCode,
205
+ onRemove
206
+ }
207
+ }
208
+ });
209
+ </script>
@@ -0,0 +1,100 @@
1
+ <template>
2
+ <component
3
+ :is="component"
4
+ v-bind="componentProps"
5
+ />
6
+ </template>
7
+
8
+
9
+ <script lang="ts">
10
+ import { defineComponent, defineAsyncComponent, type PropType, computed } from "vue";
11
+
12
+ import { EntityType } from "@dative-gpi/foundation-shared-domain/enums";
13
+
14
+ export default defineComponent({
15
+ name: "FSSimpleEntitiesList",
16
+ components: {
17
+ },
18
+ props: {
19
+ entityType: {
20
+ type: Number as PropType<EntityType>,
21
+ required: true
22
+ },
23
+ filters: {
24
+ type: Object,
25
+ required: false,
26
+ default: null
27
+ }
28
+ },
29
+ setup(props, { attrs }) {
30
+ const component = computed(() => {
31
+ switch(props.entityType) {
32
+ case EntityType.Device:
33
+ return defineAsyncComponent(() => import("../lists/deviceOrganisations/FSSimpleDeviceOrganisationsList.vue"));
34
+ case EntityType.Dashboard:
35
+ return defineAsyncComponent(() => import("../lists/dashboards/FSSimpleDashboardsList.vue"));
36
+ case EntityType.Folder:
37
+ return defineAsyncComponent(() => import("../lists/folders/FSSimpleFoldersList.vue"));
38
+ case EntityType.User:
39
+ return defineAsyncComponent(() => import("../lists/userOrganisations/FSSimpleUserOrganisationsList.vue"));
40
+ case EntityType.Group:
41
+ return defineAsyncComponent(() => import("../lists/groups/FSSimpleGroupsList.vue"));
42
+ case EntityType.Location:
43
+ return defineAsyncComponent(() => import("../lists/locations/FSSimpleLocationsList.vue"));
44
+ case EntityType.Model:
45
+ return defineAsyncComponent(() => import("../lists/models/FSSimpleModelsList.vue"));
46
+ default:
47
+ return null;
48
+ };
49
+ });
50
+
51
+ const componentProps = computed(() => {
52
+ switch(props.entityType) {
53
+ case EntityType.Device:
54
+ return {
55
+ ...attrs,
56
+ deviceOrganisationFilters : props.filters
57
+ };
58
+ case EntityType.Dashboard:
59
+ return {
60
+ ...attrs,
61
+ dashboardOrganisationFilters : props.filters,
62
+ dashboardOrganisationTypeFilters : props.filters
63
+ };
64
+ case EntityType.Folder:
65
+ return {
66
+ ...attrs,
67
+ folderFilters : props.filters
68
+ };
69
+ case EntityType.User:
70
+ return {
71
+ ...attrs,
72
+ userFilters : props.filters
73
+ };
74
+ case EntityType.Group:
75
+ return {
76
+ ...attrs,
77
+ groupFilters : props.filters
78
+ };
79
+ case EntityType.Location:
80
+ return {
81
+ ...attrs,
82
+ locationFilters : props.filters
83
+ };
84
+ case EntityType.Model:
85
+ return {
86
+ ...attrs,
87
+ modelFilters : props.filters
88
+ };
89
+ default:
90
+ return null;
91
+ }
92
+ });
93
+
94
+ return {
95
+ component,
96
+ componentProps
97
+ }
98
+ }
99
+ });
100
+ </script>
@@ -0,0 +1,310 @@
1
+ <template>
2
+ <FSDataTable
3
+ defaultMode="iterator"
4
+ :loading="fetchingDeviceExplorerElements"
5
+ :singleSelect="$props.singleSelect"
6
+ :items="deviceExplorerElements"
7
+ :showSelect="$props.editable"
8
+ :tableCode="$props.tableCode"
9
+ :itemTo="$props.itemTo"
10
+ :noSearch="$props.recursiveSearch"
11
+ :modelValue="$props.modelValue"
12
+ @update:modelValue="onUpdate"
13
+ v-model:search="search"
14
+ v-bind="$attrs"
15
+ >
16
+ <template
17
+ v-for="(_, name) in $slots"
18
+ v-slot:[name]="slotData"
19
+ >
20
+ <slot
21
+ :name="name"
22
+ v-bind="slotData"
23
+ />
24
+ </template>
25
+ <template
26
+ #header.imageId-title
27
+ >
28
+ <FSIcon>
29
+ mdi-panorama-variant-outline
30
+ </FSIcon>
31
+ </template>
32
+ <template
33
+ #header.connectivity-title
34
+ >
35
+ <FSIcon>
36
+ mdi-wifi
37
+ </FSIcon>
38
+ </template>
39
+ <template
40
+ #item.imageId="{ item }"
41
+ >
42
+ <FSImage
43
+ v-if="item.imageId"
44
+ height="32px"
45
+ width="32px"
46
+ :imageId="item.imageId"
47
+ :thumbnail="true"
48
+ />
49
+ </template>
50
+ <template
51
+ #item.tags="{ item }"
52
+ >
53
+ <FSTagGroup
54
+ variant="slide"
55
+ :editable="false"
56
+ :tags="item.tags"
57
+ />
58
+ </template>
59
+ <template
60
+ #item.type="{ item }"
61
+ >
62
+ <FSIcon
63
+ v-if="item.type === DeviceExplorerElementType.Group"
64
+ >
65
+ mdi-folder-outline
66
+ </FSIcon>
67
+ <FSIcon
68
+ v-else
69
+ >
70
+ mdi-widgets-outline
71
+ </FSIcon>
72
+ </template>
73
+
74
+ <template
75
+ #item.icon="{ item }"
76
+ >
77
+ <FSIcon
78
+ v-if="item.type === DeviceExplorerElementType.Group"
79
+ >
80
+ {{ item.icon }}
81
+ </FSIcon>
82
+ </template>
83
+ <template
84
+ #item.connectivity="{ item }"
85
+ >
86
+ <FSCol
87
+ v-if="item.type === DeviceExplorerElementType.DeviceOrganisation"
88
+ >
89
+ <FSConnectivity
90
+ v-if="item.connectivity.status != ConnectivityStatus.None"
91
+ :deviceConnectivity="item.connectivity"
92
+ />
93
+ </FSCol>
94
+ </template>
95
+ <template
96
+ #item.worstAlert="{ item }"
97
+ >
98
+ <FSWorstAlert
99
+ v-if="item.worstAlert"
100
+ :deviceWorstAlert="item.worstAlert"
101
+ :deviceAlerts="item.alerts"
102
+ :alertTo="$props.alertTo"
103
+ />
104
+ <div
105
+ v-else
106
+ />
107
+ </template>
108
+ <template
109
+ #item.alerts="{ item }"
110
+ >
111
+ <FSWorstAlert
112
+ v-if="item.worstAlert"
113
+ :deviceWorstAlert="item.worstAlert"
114
+ :deviceAlerts="item.alerts"
115
+ :alertTo="$props.alertTo"
116
+ />
117
+ <div
118
+ v-else
119
+ />
120
+ </template>
121
+ <template
122
+ #item.status="{ item }"
123
+ >
124
+ <FSStatusesCarousel
125
+ v-if="item.type === DeviceExplorerElementType.DeviceOrganisation"
126
+ :modelStatuses="item.modelStatuses"
127
+ :deviceStatuses="item.status.statuses"
128
+ />
129
+ </template>
130
+
131
+ <template
132
+ #item.tile="{ item, toggleSelect }"
133
+ >
134
+ <FSGroupTileUI
135
+ v-if="item.type === DeviceExplorerElementType.Group"
136
+ :to="$props.itemTo && $props.itemTo(item)"
137
+ :modelValue="isSelected(item.id)"
138
+ @update:modelValue="toggleSelect(item)"
139
+ v-bind="item"
140
+ />
141
+ <FSDeviceOrganisationTileUI
142
+ v-if="item.type === DeviceExplorerElementType.DeviceOrganisation"
143
+ :to="$props.itemTo && $props.itemTo(item)"
144
+ :deviceConnectivity="item.connectivity"
145
+ :deviceStatuses="item.status.statuses"
146
+ :deviceWorstAlert="item.worstAlert"
147
+ :deviceAlerts="item.alerts"
148
+ :alertTo="$props.alertTo"
149
+ :modelValue="isSelected(item.id)"
150
+ @update:modelValue="toggleSelect(item)"
151
+ v-bind="item"
152
+ />
153
+ </template>
154
+ </FSDataTable>
155
+ </template>
156
+
157
+ <script lang="ts">
158
+ import { computed, defineComponent, type PropType, ref, watch } from "vue";
159
+ import { type RouteLocation } from "vue-router";
160
+ import _ from "lodash";
161
+
162
+ import { ConnectivityStatus, DeviceExplorerElementType } from "@dative-gpi/foundation-shared-domain/enums";
163
+ import { useDeviceExplorerElements } from "@dative-gpi/foundation-core-services/composables";
164
+ import { type DeviceExplorerElementInfos} from "@dative-gpi/foundation-core-domain/models";
165
+ import { useDebounce } from "@dative-gpi/foundation-shared-components/composables";
166
+
167
+ import FSDeviceOrganisationTileUI from "@dative-gpi/foundation-shared-components/components/tiles/FSDeviceOrganisationTileUI.vue";
168
+ import FSStatusesCarousel from "@dative-gpi/foundation-shared-components/components/deviceOrganisations/FSStatusesCarousel.vue";
169
+ import FSConnectivity from "@dative-gpi/foundation-shared-components/components/deviceOrganisations/FSConnectivity.vue";
170
+ import FSWorstAlert from "@dative-gpi/foundation-shared-components/components/deviceOrganisations/FSWorstAlert.vue";
171
+ import FSGroupTileUI from "@dative-gpi/foundation-shared-components/components/tiles/FSGroupTileUI.vue";
172
+ import FSTagGroup from "@dative-gpi/foundation-shared-components/components/FSTagGroup.vue";
173
+ import FSImage from "@dative-gpi/foundation-shared-components/components/FSImage.vue";
174
+
175
+ import FSDataTable from "../lists/FSDataTable.vue";
176
+
177
+ export default defineComponent({
178
+ name: "FSBaseDevicesExplorer",
179
+ components: {
180
+ FSDeviceOrganisationTileUI,
181
+ FSStatusesCarousel,
182
+ FSConnectivity,
183
+ FSGroupTileUI,
184
+ FSWorstAlert,
185
+ FSDataTable,
186
+ FSTagGroup,
187
+ FSImage
188
+ },
189
+ props: {
190
+ tableCode: {
191
+ type: String as PropType<string | null>,
192
+ required: false,
193
+ default: null
194
+ },
195
+ recursiveSearch: {
196
+ type: Boolean,
197
+ required: false,
198
+ default: true
199
+ },
200
+ parentId: {
201
+ type: String as PropType<string | null>,
202
+ required: false,
203
+ default: null
204
+ },
205
+ root: {
206
+ type: Boolean,
207
+ required: false,
208
+ default: true
209
+ },
210
+ connectedOnly: {
211
+ type: Boolean,
212
+ required: false,
213
+ default: false
214
+ },
215
+ itemTo: {
216
+ type: Function as PropType<(item: DeviceExplorerElementInfos) => Partial<RouteLocation>>,
217
+ required: false
218
+ },
219
+ alertTo: {
220
+ type: Function,
221
+ required: false,
222
+ default: null
223
+ },
224
+ editable: {
225
+ type: Boolean,
226
+ required: false,
227
+ default: true
228
+ },
229
+ singleSelect: {
230
+ type: Boolean,
231
+ required: false,
232
+ default: false
233
+ },
234
+ modelValue: {
235
+ type: Array as PropType<string[]>,
236
+ default: () => [],
237
+ required: false
238
+ }
239
+ },
240
+ emits: ["update:modelValue", "update:types"],
241
+ setup(props, { emit }) {
242
+ const { entities, fetching: fetchingDeviceExplorerElements, getMany: getManyDeviceExplorerElements } = useDeviceExplorerElements();
243
+ const { debounce } = useDebounce();
244
+
245
+ const search = ref("");
246
+
247
+ const deviceExplorerElements = computed((): DeviceExplorerElementInfos[] => {
248
+ let elements = entities.value.slice();
249
+ if (props.connectedOnly) {
250
+ elements = elements.filter(dee =>
251
+ dee.type === DeviceExplorerElementType.Group ||
252
+ (dee.connectivity != null && dee.connectivity.status != ConnectivityStatus.None)
253
+ );
254
+ }
255
+ return elements.sort((a, b) => a.type - b.type);
256
+ });
257
+
258
+ const isSelected = (id: string): boolean => {
259
+ return props.modelValue.includes(id);
260
+ };
261
+
262
+ const onUpdate = (value: string[]): void => {
263
+ const types = value.map(id => entities.value.find(dee => dee.id === id)?.type);
264
+ emit("update:types", types);
265
+
266
+ emit("update:modelValue", value);
267
+ }
268
+
269
+ const fetch = () => {
270
+ if (props.recursiveSearch && search.value) {
271
+ getManyDeviceExplorerElements({
272
+ ancestorId: props.parentId,
273
+ search: search.value
274
+ });
275
+ }
276
+ else {
277
+ getManyDeviceExplorerElements({
278
+ parentId: props.parentId,
279
+ root: props.root
280
+ });
281
+ }
282
+ }
283
+
284
+ // Delay to wait before fetching after a search change
285
+ const debounceFetch = (): void => debounce(fetch, 1000);
286
+
287
+ watch([() => props.parentId, () => props.root], (next, previous) => {
288
+ if ((!next && !previous) || !_.isEqual(next, previous)) {
289
+ fetch();
290
+ }
291
+ }, { immediate: true });
292
+
293
+ watch(search, (next, previous) => {
294
+ if (props.recursiveSearch && next !== previous) {
295
+ debounceFetch();
296
+ }
297
+ });
298
+
299
+ return {
300
+ fetchingDeviceExplorerElements,
301
+ DeviceExplorerElementType,
302
+ deviceExplorerElements,
303
+ ConnectivityStatus,
304
+ search,
305
+ isSelected,
306
+ onUpdate
307
+ };
308
+ }
309
+ });
310
+ </script>