@firecms/core 3.3.0-canary.1e1cce9 → 3.3.0-canary.289082f
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/dist/app/useApp.d.ts +1 -0
- package/dist/core/DefaultDrawer.d.ts +10 -3
- package/dist/core/field_configs.d.ts +1 -1
- package/dist/form/field_bindings/GeopointFieldBinding.d.ts +5 -0
- package/dist/form/index.d.ts +1 -0
- package/dist/index.es.js +1741 -492
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +1740 -491
- package/dist/index.umd.js.map +1 -1
- package/dist/locales/pl.d.ts +2 -0
- package/dist/preview/index.d.ts +1 -0
- package/dist/preview/property_previews/GeopointPropertyPreview.d.ts +4 -0
- package/dist/util/geopoint.d.ts +22 -0
- package/dist/util/index.d.ts +1 -0
- package/dist/util/navigation_blocking.d.ts +22 -0
- package/dist/util/navigation_from_path.d.ts +10 -0
- package/dist/util/navigation_utils.d.ts +20 -0
- package/package.json +14 -7
- package/src/app/Scaffold.tsx +34 -44
- package/src/app/useApp.tsx +1 -0
- package/src/components/VirtualTable/VirtualTable.tsx +19 -8
- package/src/components/common/useDataSourceTableController.tsx +25 -6
- package/src/core/DefaultDrawer.tsx +150 -64
- package/src/core/DrawerNavigationGroup.tsx +27 -29
- package/src/core/DrawerNavigationItem.tsx +10 -12
- package/src/core/EntityEditView.tsx +57 -32
- package/src/core/field_configs.tsx +15 -0
- package/src/form/field_bindings/GeopointFieldBinding.tsx +139 -0
- package/src/form/index.tsx +1 -0
- package/src/i18n/FireCMSi18nProvider.tsx +2 -0
- package/src/internal/useBuildSideEntityController.tsx +2 -1
- package/src/locales/pl.ts +730 -0
- package/src/preview/PropertyPreview.tsx +12 -0
- package/src/preview/index.ts +1 -0
- package/src/preview/property_previews/GeopointPropertyPreview.tsx +23 -0
- package/src/routes/FireCMSRoute.tsx +44 -25
- package/src/util/entities.ts +2 -0
- package/src/util/geopoint.ts +81 -0
- package/src/util/index.ts +1 -0
- package/src/util/navigation_blocking.ts +45 -0
- package/src/util/navigation_from_path.ts +23 -6
- package/src/util/navigation_utils.ts +36 -2
- package/src/util/parent_references_from_path.ts +4 -2
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
import React, { useEffect, useRef, useState } from "react";
|
|
2
|
+
|
|
3
|
+
import { CloseIcon, IconButton, TextField } from "@firecms/ui";
|
|
4
|
+
import { FieldProps, GeoPoint } from "../../types";
|
|
5
|
+
import { FieldHelperText, LabelWithIcon } from "../components";
|
|
6
|
+
import { PropertyIdCopyTooltip } from "../../components";
|
|
7
|
+
import { useClearRestoreValue } from "../useClearRestoreValue";
|
|
8
|
+
import { getIconForProperty } from "../../util";
|
|
9
|
+
import { formatGeoPoint, getGeoPointCoordinates, parseGeoPoint } from "../../util/geopoint";
|
|
10
|
+
|
|
11
|
+
type GeopointFieldBindingProps = FieldProps<GeoPoint>;
|
|
12
|
+
|
|
13
|
+
export function GeopointFieldBinding({
|
|
14
|
+
propertyKey,
|
|
15
|
+
value,
|
|
16
|
+
setValue,
|
|
17
|
+
error,
|
|
18
|
+
showError,
|
|
19
|
+
disabled,
|
|
20
|
+
autoFocus,
|
|
21
|
+
property,
|
|
22
|
+
includeDescription,
|
|
23
|
+
size = "large"
|
|
24
|
+
}: GeopointFieldBindingProps) {
|
|
25
|
+
|
|
26
|
+
const coordinates = getGeoPointCoordinates(value);
|
|
27
|
+
const canClear = Boolean((property as any).clearable);
|
|
28
|
+
const [latitude, setLatitude] = useState<string>(coordinates ? coordinates.latitude.toString() : "");
|
|
29
|
+
const [longitude, setLongitude] = useState<string>(coordinates ? coordinates.longitude.toString() : "");
|
|
30
|
+
const [localError, setLocalError] = useState<string | undefined>();
|
|
31
|
+
const skipSyncRef = useRef(false);
|
|
32
|
+
|
|
33
|
+
useClearRestoreValue({
|
|
34
|
+
property,
|
|
35
|
+
value,
|
|
36
|
+
setValue
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
useEffect(() => {
|
|
40
|
+
if (skipSyncRef.current) {
|
|
41
|
+
skipSyncRef.current = false;
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
const nextCoordinates = getGeoPointCoordinates(value);
|
|
45
|
+
setLatitude(nextCoordinates ? nextCoordinates.latitude.toString() : "");
|
|
46
|
+
setLongitude(nextCoordinates ? nextCoordinates.longitude.toString() : "");
|
|
47
|
+
}, [value]);
|
|
48
|
+
|
|
49
|
+
const updateGeoPoint = (nextLatitude: string, nextLongitude: string) => {
|
|
50
|
+
skipSyncRef.current = true;
|
|
51
|
+
setLatitude(nextLatitude);
|
|
52
|
+
setLongitude(nextLongitude);
|
|
53
|
+
|
|
54
|
+
const trimmedLatitude = nextLatitude.trim();
|
|
55
|
+
const trimmedLongitude = nextLongitude.trim();
|
|
56
|
+
|
|
57
|
+
if (!trimmedLatitude && !trimmedLongitude) {
|
|
58
|
+
setLocalError(undefined);
|
|
59
|
+
setValue(null);
|
|
60
|
+
return;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
const parsed = parseGeoPoint(`${trimmedLatitude}, ${trimmedLongitude}`);
|
|
64
|
+
|
|
65
|
+
if (parsed.error) {
|
|
66
|
+
setLocalError(parsed.error);
|
|
67
|
+
setValue(null);
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
setLocalError(undefined);
|
|
72
|
+
setValue(parsed.point);
|
|
73
|
+
};
|
|
74
|
+
|
|
75
|
+
const handleClear = (event?: React.MouseEvent) => {
|
|
76
|
+
if (event) {
|
|
77
|
+
event.preventDefault();
|
|
78
|
+
event.stopPropagation();
|
|
79
|
+
}
|
|
80
|
+
updateGeoPoint("", "");
|
|
81
|
+
};
|
|
82
|
+
|
|
83
|
+
const resolvedError = localError ?? error;
|
|
84
|
+
const shouldShowError = Boolean(resolvedError) || Boolean(showError && error);
|
|
85
|
+
|
|
86
|
+
return (
|
|
87
|
+
<>
|
|
88
|
+
<PropertyIdCopyTooltip propertyKey={propertyKey}>
|
|
89
|
+
<div className="flex flex-col gap-2">
|
|
90
|
+
<div className="mt-1">
|
|
91
|
+
<LabelWithIcon
|
|
92
|
+
icon={getIconForProperty(property, "small")}
|
|
93
|
+
required={property.validation?.required}
|
|
94
|
+
title={property.name}
|
|
95
|
+
className={shouldShowError ? "text-red-500 dark:text-red-500" : "text-text-secondary dark:text-text-secondary-dark"}
|
|
96
|
+
/>
|
|
97
|
+
</div>
|
|
98
|
+
<div className="grid grid-cols-1 gap-2 md:grid-cols-2">
|
|
99
|
+
<TextField
|
|
100
|
+
size={size}
|
|
101
|
+
value={latitude}
|
|
102
|
+
onChange={(event) => updateGeoPoint(event.target.value, longitude)}
|
|
103
|
+
autoFocus={autoFocus}
|
|
104
|
+
label={"Latitude"}
|
|
105
|
+
type="number"
|
|
106
|
+
disabled={disabled}
|
|
107
|
+
endAdornment={canClear ? (
|
|
108
|
+
<IconButton onClick={handleClear}>
|
|
109
|
+
<CloseIcon />
|
|
110
|
+
</IconButton>
|
|
111
|
+
) : undefined}
|
|
112
|
+
error={shouldShowError && Boolean(resolvedError)}
|
|
113
|
+
/>
|
|
114
|
+
<TextField
|
|
115
|
+
size={size}
|
|
116
|
+
value={longitude}
|
|
117
|
+
onChange={(event) => updateGeoPoint(latitude, event.target.value)}
|
|
118
|
+
label={"Longitude"}
|
|
119
|
+
type="number"
|
|
120
|
+
disabled={disabled}
|
|
121
|
+
error={shouldShowError && Boolean(resolvedError)}
|
|
122
|
+
/>
|
|
123
|
+
</div>
|
|
124
|
+
{value && !resolvedError && (
|
|
125
|
+
<div className="text-xs text-text-secondary dark:text-text-secondary-dark font-mono">
|
|
126
|
+
{formatGeoPoint(value)}
|
|
127
|
+
</div>
|
|
128
|
+
)}
|
|
129
|
+
</div>
|
|
130
|
+
</PropertyIdCopyTooltip>
|
|
131
|
+
|
|
132
|
+
<FieldHelperText includeDescription={includeDescription}
|
|
133
|
+
showError={shouldShowError}
|
|
134
|
+
error={resolvedError}
|
|
135
|
+
disabled={disabled}
|
|
136
|
+
property={property}/>
|
|
137
|
+
</>
|
|
138
|
+
);
|
|
139
|
+
}
|
package/src/form/index.tsx
CHANGED
|
@@ -11,6 +11,7 @@ export { StorageUploadFieldBinding } from "./field_bindings/StorageUploadFieldBi
|
|
|
11
11
|
export { TextFieldBinding } from "./field_bindings/TextFieldBinding";
|
|
12
12
|
export { SwitchFieldBinding } from "./field_bindings/SwitchFieldBinding";
|
|
13
13
|
export { DateTimeFieldBinding } from "./field_bindings/DateTimeFieldBinding";
|
|
14
|
+
export { GeopointFieldBinding } from "./field_bindings/GeopointFieldBinding";
|
|
14
15
|
export { ReferenceFieldBinding } from "./field_bindings/ReferenceFieldBinding";
|
|
15
16
|
export { ReferenceAsStringFieldBinding } from "./field_bindings/ReferenceAsStringFieldBinding";
|
|
16
17
|
export { MapFieldBinding } from "./field_bindings/MapFieldBinding";
|
|
@@ -8,6 +8,7 @@ import { fr } from "../locales/fr";
|
|
|
8
8
|
import { it } from "../locales/it";
|
|
9
9
|
import { hi } from "../locales/hi";
|
|
10
10
|
import { pt } from "../locales/pt";
|
|
11
|
+
import { pl } from "../locales/pl";
|
|
11
12
|
import { FireCMSTranslations } from "../types/translations";
|
|
12
13
|
|
|
13
14
|
const FIRECMS_NS = "firecms_core";
|
|
@@ -139,6 +140,7 @@ function buildResources(
|
|
|
139
140
|
it: { [FIRECMS_NS]: { ...it } },
|
|
140
141
|
hi: { [FIRECMS_NS]: { ...hi } },
|
|
141
142
|
pt: { [FIRECMS_NS]: { ...pt } },
|
|
143
|
+
pl: { [FIRECMS_NS]: { ...pl } },
|
|
142
144
|
};
|
|
143
145
|
|
|
144
146
|
if (!translations) return resources;
|
|
@@ -13,6 +13,7 @@ import {
|
|
|
13
13
|
import { getNavigationEntriesFromPath, NavigationViewInternal } from "../util/navigation_from_path";
|
|
14
14
|
import { useLocation } from "react-router-dom";
|
|
15
15
|
import {
|
|
16
|
+
encodeEntityId,
|
|
16
17
|
removeInitialAndTrailingSlashes,
|
|
17
18
|
resolveCollection,
|
|
18
19
|
resolveDefaultSelectedView,
|
|
@@ -277,7 +278,7 @@ const propsToSidePanel = (props: EntitySidePanelProps,
|
|
|
277
278
|
const collectionPath = removeInitialAndTrailingSlashes(props.path);
|
|
278
279
|
|
|
279
280
|
const urlPath = props.entityId
|
|
280
|
-
? buildUrlCollectionPath(`${collectionPath}/${props.entityId}${props.selectedTab ? "/" + props.selectedTab : ""}${locationSearch}#${SIDE_URL_HASH}`)
|
|
281
|
+
? buildUrlCollectionPath(`${collectionPath}/${encodeEntityId(props.entityId)}${props.selectedTab ? "/" + props.selectedTab : ""}${locationSearch}#${SIDE_URL_HASH}`)
|
|
281
282
|
: buildUrlCollectionPath(`${collectionPath}${locationSearch}#${NEW_URL_HASH}`);
|
|
282
283
|
|
|
283
284
|
const resolvedPanelProps: EntitySidePanelProps<any> = {
|