@trackunit/filters-filter-bar 1.3.17 → 1.3.19

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.
package/index.cjs.js CHANGED
@@ -14,7 +14,6 @@ var sharedUtils = require('@trackunit/shared-utils');
14
14
  var tailwindMerge = require('tailwind-merge');
15
15
  var dequal = require('dequal');
16
16
  var isEqual = require('lodash/isEqual');
17
- var reduce = require('lodash/reduce');
18
17
  var geoJsonUtils = require('@trackunit/geo-json-utils');
19
18
  var zod = require('zod');
20
19
 
@@ -892,7 +891,7 @@ const mockFilterBar = {
892
891
  arrayIncludesValue: doNothing,
893
892
  getFilterTitle: doNothing,
894
893
  getFilterBarName: doNothing,
895
- initialState: { customerType: [] },
894
+ initialState: { filtered: { customerType: [] }, empty: { customerType: [] } },
896
895
  name: "test",
897
896
  objectArrayIncludesValue: doNothing,
898
897
  resetFiltersToInitialState: doNothing,
@@ -965,8 +964,11 @@ const createInitialState = (name, mainFilters, initialState, setValue) => {
965
964
  const type = curr.type;
966
965
  return {
967
966
  ...prev,
967
+ [key]:
968
968
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
969
- [key]: initialState[key] ?? curr.defaultValue ?? getInitialValueFromType(type),
969
+ "filtered" in initialState && initialState.filtered[key]
970
+ ? initialState.filtered[key]
971
+ : (curr.defaultValue ?? getInitialValueFromType(type)),
970
972
  };
971
973
  }, {});
972
974
  const setters = mainFilters.reduce((prev, curr) => {
@@ -976,23 +978,13 @@ const createInitialState = (name, mainFilters, initialState, setValue) => {
976
978
  [`set${stringTs.capitalize(key)}`]: (callback) => setValue(key, callback),
977
979
  };
978
980
  }, {});
979
- const updatedInitialState = mainFilters.reduce((prev, curr) => {
980
- const key = curr.filterKey;
981
- const type = curr.type;
982
- return {
983
- ...prev,
984
- // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
985
- [key]: initialState[key] ?? curr.defaultValue ?? getInitialValueFromType(type),
986
- };
987
- }, {});
988
- const newFilter = {
981
+ return {
989
982
  name,
990
- initialState: updatedInitialState,
983
+ initialState: { filtered: values, empty: "empty" in initialState ? initialState.empty : {} },
991
984
  starredFilterKeys: defaultStarredKeys,
992
985
  values,
993
986
  setters,
994
987
  };
995
- return newFilter;
996
988
  };
997
989
 
998
990
  const areaFilterGeoJsonGeometrySchema = zod.z.union([geoJsonUtils.geoJsonPolygonSchema, geoJsonUtils.geoJsonMultiPolygonSchema]);
@@ -1115,7 +1107,7 @@ const validateFilter = (filter, filterDefinitions) => {
1115
1107
  });
1116
1108
  stateKeys.sort((a, b) => a.localeCompare(b));
1117
1109
  const filterKeysNotEqual = !isEqual(stateKeys, filterDefinitions.map(f => f.filterKey).sort((a, b) => a.localeCompare(b)));
1118
- return inBadState || filterKeysNotEqual ? false : true;
1110
+ return !(inBadState || filterKeysNotEqual);
1119
1111
  };
1120
1112
 
1121
1113
  /**
@@ -1124,7 +1116,7 @@ const validateFilter = (filter, filterDefinitions) => {
1124
1116
  * @template TFilterBarDefinition - A generic type for the filter bar definition.
1125
1117
  * @returns {object} An object containing filter bar configuration and actions.
1126
1118
  */
1127
- const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState, loadAsync, }) => {
1119
+ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, loadAsync, initialState, }) => {
1128
1120
  const [internalFilterBarDefinitions, setInternalFilterBarDefinitions] = react.useState(filterBarDefinition);
1129
1121
  const { clientSideUserId } = reactCoreHooks.useCurrentUser();
1130
1122
  const setValue = react.useCallback((key, callback) => {
@@ -1145,14 +1137,11 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1145
1137
  if (storedFilters && storedFilters !== "undefined") {
1146
1138
  const loadedFilterBarConfig = JSON.parse(storedFilters);
1147
1139
  if (validateFilter(loadedFilterBarConfig, updatedFilterDefinitionsValues)) {
1148
- initialFilterBarConfig = {
1149
- ...loadedFilterBarConfig,
1150
- initialState: initialState || loadedFilterBarConfig.initialState,
1151
- };
1140
+ initialFilterBarConfig = createInitialState(loadedFilterBarConfig.name, updatedFilterDefinitionsValues, initialState || loadedFilterBarConfig.initialState, setValue);
1152
1141
  }
1153
1142
  }
1154
1143
  //WHY WE NEED THIS?
1155
- //For filters that are not visible and we want to set the default value to the initial state.
1144
+ //For filters that are not visible, and we want to set the default value to the initial state.
1156
1145
  //To do this for a changing default value as in customers and sites we would need to recreate the initialFilterBarConfig every time the default value changes.
1157
1146
  //This mean that filterbars that have this functionality wouldn't be able to save the state of the filterbar.
1158
1147
  //Another option would be to create a new filterbar for each customer or site. This also has its drawbacks. Would raise it with the frontend community.
@@ -1221,26 +1210,35 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1221
1210
  },
1222
1211
  get appliedFilterKeys() {
1223
1212
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1224
- const initialStateValues = filterBarConfig.initialState || {};
1213
+ const initialStateFilteredValues = JSON.parse(JSON.stringify(filterBarConfig.initialState?.filtered || {}));
1225
1214
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1226
- const currentFilters = filterBarConfig.values || {};
1227
- // parse and stringify to remove empty references before comparing
1228
- // eslint-disable-next-line local-rules/no-typescript-assertion
1229
- const currentValuesWithoutEmptyRefs = JSON.parse(JSON.stringify(currentFilters));
1230
- // eslint-disable-next-line local-rules/no-typescript-assertion
1231
- const initialStateValuesWithoutEmptyRefs = JSON.parse(JSON.stringify(initialStateValues));
1232
- return getKeysOfUnequalProperties(currentValuesWithoutEmptyRefs, initialStateValuesWithoutEmptyRefs).map(key => key.toString() // TODO: FilterName type should be PropertyKey instead of string to avoid this .toString() bs but out-of-scope for this round of improvements
1233
- );
1215
+ const initialStateEmptyValues = JSON.parse(JSON.stringify(filterBarConfig.initialState?.empty || {}));
1216
+ // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1217
+ const currentFilters = JSON.parse(JSON.stringify(filterBarConfig.values || {}));
1218
+ return sharedUtils.objectKeys(currentFilters)
1219
+ .filter(filterKey => {
1220
+ const isFilterValueEqualToInitialStateValue = dequal.dequal(currentFilters[filterKey], initialStateFilteredValues[filterKey]);
1221
+ const emptyStateValue = initialStateEmptyValues[filterKey];
1222
+ // If we passed an initialState's empty state, we have to compare whether this field is different
1223
+ // from the empty state. If the field is different from the empty state, it means that it is an active filter.
1224
+ if (emptyStateValue) {
1225
+ const isFilterValueEqualToEmptyStateValue = dequal.dequal(currentFilters[filterKey], emptyStateValue);
1226
+ return !isFilterValueEqualToEmptyStateValue;
1227
+ }
1228
+ // Otherwise, we need to check whether our filter's field value equals the initial state's field value
1229
+ // The initialState value is created based on the `initialState` passed to this hook, and some magic
1230
+ // done in the `createInitialState` function.
1231
+ return !isFilterValueEqualToInitialStateValue;
1232
+ })
1233
+ .map(key => String(key));
1234
1234
  },
1235
1235
  filterHasChanged(key) {
1236
+ const initialStateFilteredValue = JSON.parse(
1236
1237
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1237
- const initialStateValue = filterBarConfig.initialState[key] || {};
1238
+ JSON.stringify(filterBarConfig.initialState?.filtered?.[key] || {}));
1238
1239
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1239
- const currentValue = filterBarConfig.values[key] || {};
1240
- // parse and stringify to remove empty references before comparing
1241
- const currentValueWithoutEmptyRefs = JSON.parse(JSON.stringify(currentValue));
1242
- const initialStateValueWithoutEmptyRefs = JSON.parse(JSON.stringify(initialStateValue));
1243
- return !dequal.dequal(currentValueWithoutEmptyRefs, initialStateValueWithoutEmptyRefs);
1240
+ const currentFilter = JSON.parse(JSON.stringify(filterBarConfig.values[key] || {}));
1241
+ return !dequal.dequal(currentFilter, initialStateFilteredValue);
1244
1242
  },
1245
1243
  objectArrayIncludesValue(key, value) {
1246
1244
  const filter = filterBarConfig.values[key];
@@ -1251,7 +1249,13 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1251
1249
  return filter?.value === value || false;
1252
1250
  },
1253
1251
  };
1254
- }, [filterBarConfig.initialState, filterBarConfig.name, filterBarConfig.values, internalFilterBarDefinitions]);
1252
+ }, [
1253
+ filterBarConfig.initialState.empty,
1254
+ filterBarConfig.initialState.filtered,
1255
+ filterBarConfig.name,
1256
+ filterBarConfig.values,
1257
+ internalFilterBarDefinitions,
1258
+ ]);
1255
1259
  const filterMapActions = react.useMemo(() => {
1256
1260
  // Reset an individual filter to its initial state
1257
1261
  const resetIndividualFilterToInitialState = (key) => {
@@ -1275,15 +1279,13 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1275
1279
  starredFilterKeys: prevState.starredFilterKeys.filter(obj => obj !== filterKey),
1276
1280
  };
1277
1281
  }
1278
- else {
1279
- return {
1280
- ...prevState,
1281
- starredFilterKeys: [
1282
- ...prevState.starredFilterKeys,
1283
- filterKey,
1284
- ],
1285
- };
1286
- }
1282
+ return {
1283
+ ...prevState,
1284
+ starredFilterKeys: [
1285
+ ...prevState.starredFilterKeys,
1286
+ filterKey,
1287
+ ],
1288
+ };
1287
1289
  });
1288
1290
  resetIndividualFilterToInitialState(filterKey);
1289
1291
  },
@@ -1299,15 +1301,13 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1299
1301
  },
1300
1302
  };
1301
1303
  }
1302
- else {
1303
- return {
1304
- ...prevState,
1305
- values: {
1306
- ...prevState.values,
1307
- [key]: filterValue ? [...filterValue, value] : [value],
1308
- },
1309
- };
1310
- }
1304
+ return {
1305
+ ...prevState,
1306
+ values: {
1307
+ ...prevState.values,
1308
+ [key]: filterValue ? [...filterValue, value] : [value],
1309
+ },
1310
+ };
1311
1311
  });
1312
1312
  },
1313
1313
  setStringValue(key, value) {
@@ -1487,14 +1487,6 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1487
1487
  };
1488
1488
  }, [filterBarConfig, filterMapActions, filterMapGetter, internalFilterBarDefinitions, dataLoaded]);
1489
1489
  };
1490
- const getKeysOfUnequalProperties = (obj1, obj2) => {
1491
- return reduce(obj1, (result, value, key) => {
1492
- if (!isEqual(value, obj2[key])) {
1493
- result.push(key);
1494
- }
1495
- return result;
1496
- }, []);
1497
- };
1498
1490
 
1499
1491
  /**
1500
1492
  * Handles the application of a URL search parameter as a filter in the system.
package/index.esm.js CHANGED
@@ -12,7 +12,6 @@ import { nonNullable, capitalize as capitalize$1, objectValues, truthy, objectKe
12
12
  import { twMerge } from 'tailwind-merge';
13
13
  import { dequal } from 'dequal';
14
14
  import isEqual from 'lodash/isEqual';
15
- import reduce from 'lodash/reduce';
16
15
  import { geoJsonPolygonSchema, geoJsonMultiPolygonSchema } from '@trackunit/geo-json-utils';
17
16
  import { z } from 'zod';
18
17
 
@@ -890,7 +889,7 @@ const mockFilterBar = {
890
889
  arrayIncludesValue: doNothing,
891
890
  getFilterTitle: doNothing,
892
891
  getFilterBarName: doNothing,
893
- initialState: { customerType: [] },
892
+ initialState: { filtered: { customerType: [] }, empty: { customerType: [] } },
894
893
  name: "test",
895
894
  objectArrayIncludesValue: doNothing,
896
895
  resetFiltersToInitialState: doNothing,
@@ -963,8 +962,11 @@ const createInitialState = (name, mainFilters, initialState, setValue) => {
963
962
  const type = curr.type;
964
963
  return {
965
964
  ...prev,
965
+ [key]:
966
966
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
967
- [key]: initialState[key] ?? curr.defaultValue ?? getInitialValueFromType(type),
967
+ "filtered" in initialState && initialState.filtered[key]
968
+ ? initialState.filtered[key]
969
+ : (curr.defaultValue ?? getInitialValueFromType(type)),
968
970
  };
969
971
  }, {});
970
972
  const setters = mainFilters.reduce((prev, curr) => {
@@ -974,23 +976,13 @@ const createInitialState = (name, mainFilters, initialState, setValue) => {
974
976
  [`set${capitalize(key)}`]: (callback) => setValue(key, callback),
975
977
  };
976
978
  }, {});
977
- const updatedInitialState = mainFilters.reduce((prev, curr) => {
978
- const key = curr.filterKey;
979
- const type = curr.type;
980
- return {
981
- ...prev,
982
- // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
983
- [key]: initialState[key] ?? curr.defaultValue ?? getInitialValueFromType(type),
984
- };
985
- }, {});
986
- const newFilter = {
979
+ return {
987
980
  name,
988
- initialState: updatedInitialState,
981
+ initialState: { filtered: values, empty: "empty" in initialState ? initialState.empty : {} },
989
982
  starredFilterKeys: defaultStarredKeys,
990
983
  values,
991
984
  setters,
992
985
  };
993
- return newFilter;
994
986
  };
995
987
 
996
988
  const areaFilterGeoJsonGeometrySchema = z.union([geoJsonPolygonSchema, geoJsonMultiPolygonSchema]);
@@ -1113,7 +1105,7 @@ const validateFilter = (filter, filterDefinitions) => {
1113
1105
  });
1114
1106
  stateKeys.sort((a, b) => a.localeCompare(b));
1115
1107
  const filterKeysNotEqual = !isEqual(stateKeys, filterDefinitions.map(f => f.filterKey).sort((a, b) => a.localeCompare(b)));
1116
- return inBadState || filterKeysNotEqual ? false : true;
1108
+ return !(inBadState || filterKeysNotEqual);
1117
1109
  };
1118
1110
 
1119
1111
  /**
@@ -1122,7 +1114,7 @@ const validateFilter = (filter, filterDefinitions) => {
1122
1114
  * @template TFilterBarDefinition - A generic type for the filter bar definition.
1123
1115
  * @returns {object} An object containing filter bar configuration and actions.
1124
1116
  */
1125
- const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState, loadAsync, }) => {
1117
+ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, loadAsync, initialState, }) => {
1126
1118
  const [internalFilterBarDefinitions, setInternalFilterBarDefinitions] = useState(filterBarDefinition);
1127
1119
  const { clientSideUserId } = useCurrentUser();
1128
1120
  const setValue = useCallback((key, callback) => {
@@ -1143,14 +1135,11 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1143
1135
  if (storedFilters && storedFilters !== "undefined") {
1144
1136
  const loadedFilterBarConfig = JSON.parse(storedFilters);
1145
1137
  if (validateFilter(loadedFilterBarConfig, updatedFilterDefinitionsValues)) {
1146
- initialFilterBarConfig = {
1147
- ...loadedFilterBarConfig,
1148
- initialState: initialState || loadedFilterBarConfig.initialState,
1149
- };
1138
+ initialFilterBarConfig = createInitialState(loadedFilterBarConfig.name, updatedFilterDefinitionsValues, initialState || loadedFilterBarConfig.initialState, setValue);
1150
1139
  }
1151
1140
  }
1152
1141
  //WHY WE NEED THIS?
1153
- //For filters that are not visible and we want to set the default value to the initial state.
1142
+ //For filters that are not visible, and we want to set the default value to the initial state.
1154
1143
  //To do this for a changing default value as in customers and sites we would need to recreate the initialFilterBarConfig every time the default value changes.
1155
1144
  //This mean that filterbars that have this functionality wouldn't be able to save the state of the filterbar.
1156
1145
  //Another option would be to create a new filterbar for each customer or site. This also has its drawbacks. Would raise it with the frontend community.
@@ -1219,26 +1208,35 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1219
1208
  },
1220
1209
  get appliedFilterKeys() {
1221
1210
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1222
- const initialStateValues = filterBarConfig.initialState || {};
1211
+ const initialStateFilteredValues = JSON.parse(JSON.stringify(filterBarConfig.initialState?.filtered || {}));
1223
1212
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1224
- const currentFilters = filterBarConfig.values || {};
1225
- // parse and stringify to remove empty references before comparing
1226
- // eslint-disable-next-line local-rules/no-typescript-assertion
1227
- const currentValuesWithoutEmptyRefs = JSON.parse(JSON.stringify(currentFilters));
1228
- // eslint-disable-next-line local-rules/no-typescript-assertion
1229
- const initialStateValuesWithoutEmptyRefs = JSON.parse(JSON.stringify(initialStateValues));
1230
- return getKeysOfUnequalProperties(currentValuesWithoutEmptyRefs, initialStateValuesWithoutEmptyRefs).map(key => key.toString() // TODO: FilterName type should be PropertyKey instead of string to avoid this .toString() bs but out-of-scope for this round of improvements
1231
- );
1213
+ const initialStateEmptyValues = JSON.parse(JSON.stringify(filterBarConfig.initialState?.empty || {}));
1214
+ // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1215
+ const currentFilters = JSON.parse(JSON.stringify(filterBarConfig.values || {}));
1216
+ return objectKeys(currentFilters)
1217
+ .filter(filterKey => {
1218
+ const isFilterValueEqualToInitialStateValue = dequal(currentFilters[filterKey], initialStateFilteredValues[filterKey]);
1219
+ const emptyStateValue = initialStateEmptyValues[filterKey];
1220
+ // If we passed an initialState's empty state, we have to compare whether this field is different
1221
+ // from the empty state. If the field is different from the empty state, it means that it is an active filter.
1222
+ if (emptyStateValue) {
1223
+ const isFilterValueEqualToEmptyStateValue = dequal(currentFilters[filterKey], emptyStateValue);
1224
+ return !isFilterValueEqualToEmptyStateValue;
1225
+ }
1226
+ // Otherwise, we need to check whether our filter's field value equals the initial state's field value
1227
+ // The initialState value is created based on the `initialState` passed to this hook, and some magic
1228
+ // done in the `createInitialState` function.
1229
+ return !isFilterValueEqualToInitialStateValue;
1230
+ })
1231
+ .map(key => String(key));
1232
1232
  },
1233
1233
  filterHasChanged(key) {
1234
+ const initialStateFilteredValue = JSON.parse(
1234
1235
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1235
- const initialStateValue = filterBarConfig.initialState[key] || {};
1236
+ JSON.stringify(filterBarConfig.initialState?.filtered?.[key] || {}));
1236
1237
  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
1237
- const currentValue = filterBarConfig.values[key] || {};
1238
- // parse and stringify to remove empty references before comparing
1239
- const currentValueWithoutEmptyRefs = JSON.parse(JSON.stringify(currentValue));
1240
- const initialStateValueWithoutEmptyRefs = JSON.parse(JSON.stringify(initialStateValue));
1241
- return !dequal(currentValueWithoutEmptyRefs, initialStateValueWithoutEmptyRefs);
1238
+ const currentFilter = JSON.parse(JSON.stringify(filterBarConfig.values[key] || {}));
1239
+ return !dequal(currentFilter, initialStateFilteredValue);
1242
1240
  },
1243
1241
  objectArrayIncludesValue(key, value) {
1244
1242
  const filter = filterBarConfig.values[key];
@@ -1249,7 +1247,13 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1249
1247
  return filter?.value === value || false;
1250
1248
  },
1251
1249
  };
1252
- }, [filterBarConfig.initialState, filterBarConfig.name, filterBarConfig.values, internalFilterBarDefinitions]);
1250
+ }, [
1251
+ filterBarConfig.initialState.empty,
1252
+ filterBarConfig.initialState.filtered,
1253
+ filterBarConfig.name,
1254
+ filterBarConfig.values,
1255
+ internalFilterBarDefinitions,
1256
+ ]);
1253
1257
  const filterMapActions = useMemo(() => {
1254
1258
  // Reset an individual filter to its initial state
1255
1259
  const resetIndividualFilterToInitialState = (key) => {
@@ -1273,15 +1277,13 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1273
1277
  starredFilterKeys: prevState.starredFilterKeys.filter(obj => obj !== filterKey),
1274
1278
  };
1275
1279
  }
1276
- else {
1277
- return {
1278
- ...prevState,
1279
- starredFilterKeys: [
1280
- ...prevState.starredFilterKeys,
1281
- filterKey,
1282
- ],
1283
- };
1284
- }
1280
+ return {
1281
+ ...prevState,
1282
+ starredFilterKeys: [
1283
+ ...prevState.starredFilterKeys,
1284
+ filterKey,
1285
+ ],
1286
+ };
1285
1287
  });
1286
1288
  resetIndividualFilterToInitialState(filterKey);
1287
1289
  },
@@ -1297,15 +1299,13 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1297
1299
  },
1298
1300
  };
1299
1301
  }
1300
- else {
1301
- return {
1302
- ...prevState,
1303
- values: {
1304
- ...prevState.values,
1305
- [key]: filterValue ? [...filterValue, value] : [value],
1306
- },
1307
- };
1308
- }
1302
+ return {
1303
+ ...prevState,
1304
+ values: {
1305
+ ...prevState.values,
1306
+ [key]: filterValue ? [...filterValue, value] : [value],
1307
+ },
1308
+ };
1309
1309
  });
1310
1310
  },
1311
1311
  setStringValue(key, value) {
@@ -1485,14 +1485,6 @@ const useFilterBar = ({ name, onValuesChange, filterBarDefinition, initialState,
1485
1485
  };
1486
1486
  }, [filterBarConfig, filterMapActions, filterMapGetter, internalFilterBarDefinitions, dataLoaded]);
1487
1487
  };
1488
- const getKeysOfUnequalProperties = (obj1, obj2) => {
1489
- return reduce(obj1, (result, value, key) => {
1490
- if (!isEqual(value, obj2[key])) {
1491
- result.push(key);
1492
- }
1493
- return result;
1494
- }, []);
1495
- };
1496
1488
 
1497
1489
  /**
1498
1490
  * Handles the application of a URL search parameter as a filter in the system.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@trackunit/filters-filter-bar",
3
- "version": "1.3.17",
3
+ "version": "1.3.19",
4
4
  "repository": "https://github.com/Trackunit/manager",
5
5
  "license": "SEE LICENSE IN LICENSE.txt",
6
6
  "engines": {
@@ -14,15 +14,15 @@
14
14
  "tailwind-merge": "^2.0.0",
15
15
  "string-ts": "^2.0.0",
16
16
  "zod": "3.22.4",
17
- "@trackunit/react-components": "1.4.13",
18
- "@trackunit/react-core-hooks": "1.3.14",
19
- "@trackunit/react-filter-components": "1.3.14",
20
- "@trackunit/react-date-and-time-components": "1.3.14",
21
- "@trackunit/shared-utils": "1.5.13",
22
- "@trackunit/react-form-components": "1.3.14",
23
- "@trackunit/react-core-contexts-api": "1.4.14",
24
- "@trackunit/geo-json-utils": "1.3.14",
25
- "@trackunit/i18n-library-translation": "1.3.14"
17
+ "@trackunit/react-components": "1.4.14",
18
+ "@trackunit/react-core-hooks": "1.3.15",
19
+ "@trackunit/react-filter-components": "1.3.15",
20
+ "@trackunit/react-date-and-time-components": "1.3.15",
21
+ "@trackunit/shared-utils": "1.5.14",
22
+ "@trackunit/react-form-components": "1.3.15",
23
+ "@trackunit/react-core-contexts-api": "1.4.15",
24
+ "@trackunit/geo-json-utils": "1.3.15",
25
+ "@trackunit/i18n-library-translation": "1.3.15"
26
26
  },
27
27
  "module": "./index.esm.js",
28
28
  "main": "./index.cjs.js",
@@ -1,5 +1,5 @@
1
1
  import { AreaFilterGeoJsonGeometry, BooleanValue, DateRangeValue, FilterBarDefinition, FilterStateValues, FilterValueType, InitialState, MinMaxFilterValue, NumberValue, ValueName } from "../types/FilterTypes";
2
- export interface FilterBarProps<TFilterBarDefinition extends FilterBarDefinition> {
2
+ export type FilterBarProps<TFilterBarDefinition extends FilterBarDefinition> = {
3
3
  /**
4
4
  * The name of the filter bar.
5
5
  */
@@ -8,10 +8,6 @@ export interface FilterBarProps<TFilterBarDefinition extends FilterBarDefinition
8
8
  * An optional callback function that gets called when filter values change.
9
9
  */
10
10
  onValuesChange?: (values: FilterStateValues<TFilterBarDefinition>) => void;
11
- /**
12
- * An optional initial state for the filter bar.
13
- */
14
- initialState?: InitialState<TFilterBarDefinition>;
15
11
  /**
16
12
  * The filters that should potentially be used in the filter bar
17
13
  */
@@ -20,14 +16,21 @@ export interface FilterBarProps<TFilterBarDefinition extends FilterBarDefinition
20
16
  * Whether the filter bar should be loaded asynchronously
21
17
  */
22
18
  loadAsync?: boolean;
23
- }
19
+ /**
20
+ * An initial state for the filter bar.
21
+ */
22
+ initialState?: {
23
+ filtered: InitialState<TFilterBarDefinition>;
24
+ empty: InitialState<TFilterBarDefinition>;
25
+ };
26
+ };
24
27
  /**
25
28
  * Custom hook for managing a filter bar's state and actions.
26
29
  *
27
30
  * @template TFilterBarDefinition - A generic type for the filter bar definition.
28
31
  * @returns {object} An object containing filter bar configuration and actions.
29
32
  */
30
- export declare const useFilterBar: <TFilterBarDefinition extends FilterBarDefinition>({ name, onValuesChange, filterBarDefinition, initialState, loadAsync, }: FilterBarProps<TFilterBarDefinition>) => {
33
+ export declare const useFilterBar: <TFilterBarDefinition extends FilterBarDefinition>({ name, onValuesChange, filterBarDefinition, loadAsync, initialState, }: FilterBarProps<TFilterBarDefinition>) => {
31
34
  filterBarConfig: {
32
35
  getFilterTitle: (key: string) => string;
33
36
  getFilterBarName: () => string;
@@ -54,7 +57,10 @@ export declare const useFilterBar: <TFilterBarDefinition extends FilterBarDefini
54
57
  resetFiltersToInitialState: () => void;
55
58
  resetIndividualFilterToInitialState: (key: string) => void;
56
59
  name: string;
57
- initialState: InitialState<TFilterBarDefinition>;
60
+ initialState: {
61
+ filtered: InitialState<TFilterBarDefinition>;
62
+ empty: InitialState<TFilterBarDefinition>;
63
+ };
58
64
  starredFilterKeys: Extract<keyof TFilterBarDefinition, string>[];
59
65
  values: FilterStateValues<TFilterBarDefinition>;
60
66
  setters: import("../types/FilterTypes").FilterStateSetters<TFilterBarDefinition>;
@@ -1,5 +1,6 @@
1
1
  import { ReactNode } from "react";
2
2
  import { z } from "zod";
3
+ import { FilterBarProps } from "../hooks/useFilterBar";
3
4
  export type ValueName = {
4
5
  value: string;
5
6
  name: string;
@@ -16,7 +17,11 @@ export type MinMaxFilterValue = {
16
17
  };
17
18
  export declare const areaFilterGeoJsonGeometrySchema: z.ZodUnion<[z.ZodObject<{
18
19
  type: z.ZodLiteral<"Polygon">;
19
- coordinates: z.ZodArray<z.ZodEffects<z.ZodArray<z.ZodTuple<[z.ZodNumber, z.ZodNumber], null>, "many">, [number, number][], [number, number][]>, "many">;
20
+ coordinates: z.ZodArray<z.ZodEffects<z.
21
+ /**
22
+ * A function that determines if the filter should be displayed in the starred filter menu.
23
+ */
24
+ ZodArray<z.ZodTuple<[z.ZodNumber, z.ZodNumber], null>, "many">, [number, number][], [number, number][]>, "many">;
20
25
  }, "strict", z.ZodTypeAny, {
21
26
  type: "Polygon";
22
27
  coordinates: [number, number][][];
@@ -227,7 +232,7 @@ export interface FilterBarConfig<T extends FilterBarDefinition> extends FilterSt
227
232
  /**
228
233
  * The initial state of the filters in this filter list.
229
234
  */
230
- initialState: InitialState<T>;
235
+ initialState: NonNullable<FilterBarProps<T>["initialState"]>;
231
236
  /**
232
237
  * Filter names that should be starred for this filter list.
233
238
  */
@@ -1,4 +1,5 @@
1
- import { FilterBarConfig, FilterBarDefinition, FilterBarInferredValue, FilterDefinition, InitialState, ValueName } from "../types/FilterTypes";
1
+ import { FilterBarProps } from "../hooks/useFilterBar";
2
+ import { FilterBarConfig, FilterBarDefinition, FilterBarInferredValue, FilterDefinition, ValueName } from "../types/FilterTypes";
2
3
  type InitialTypes = {
3
4
  Arg: "string";
4
5
  Init: "";
@@ -42,5 +43,5 @@ export declare const getInitialValueFromType: <TInitialType extends InitialTypes
42
43
  * @template TFilterBarDefinition - The type representing the filter bar definition.
43
44
  * @returns {FilterBarConfig<TFilterBarDefinition>} - Returns an initial filter bar configuration object.
44
45
  */
45
- export declare const createInitialState: <TFilterBarDefinition extends FilterBarDefinition>(name: string, mainFilters: FilterDefinition[], initialState: InitialState<TFilterBarDefinition>, setValue: (key: string, callback: (prev: FilterBarInferredValue<TFilterBarDefinition, never> | undefined) => FilterBarInferredValue<TFilterBarDefinition, never> | undefined) => void) => FilterBarConfig<TFilterBarDefinition>;
46
+ export declare const createInitialState: <TFilterBarDefinition extends FilterBarDefinition>(name: string, mainFilters: FilterDefinition[], initialState: NonNullable<FilterBarProps<TFilterBarDefinition>["initialState"]> | {}, setValue: (key: string, callback: (prev: FilterBarInferredValue<TFilterBarDefinition, never> | undefined) => FilterBarInferredValue<TFilterBarDefinition, never> | undefined) => void) => FilterBarConfig<TFilterBarDefinition>;
46
47
  export {};