@contentful/experiences-visual-editor-react 1.0.4 → 1.0.5-beta.0
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/index.d.ts +5 -1
- package/dist/index.js +81 -6
- package/dist/index.js.map +1 -1
- package/dist/renderApp.js +83 -8
- package/dist/renderApp.js.map +1 -1
- package/package.json +4 -4
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
|
+
import { EntityStore } from '@contentful/experiences-core';
|
|
3
|
+
import { Experience } from '@contentful/experiences-core/types';
|
|
2
4
|
|
|
3
|
-
declare const VisualEditorRoot: (
|
|
5
|
+
declare const VisualEditorRoot: ({ experience }: {
|
|
6
|
+
experience?: Experience<EntityStore> | undefined;
|
|
7
|
+
}) => React.JSX.Element | null;
|
|
4
8
|
|
|
5
9
|
export { VisualEditorRoot as default };
|
package/dist/index.js
CHANGED
|
@@ -725,7 +725,7 @@ const builtInStyles = {
|
|
|
725
725
|
},
|
|
726
726
|
cfHyperlink: {
|
|
727
727
|
displayName: 'Hyperlink',
|
|
728
|
-
type: '
|
|
728
|
+
type: 'Hyperlink',
|
|
729
729
|
defaultValue: '',
|
|
730
730
|
validations: {
|
|
731
731
|
format: 'URL',
|
|
@@ -1185,6 +1185,56 @@ const lastPathNamedSegmentEq = (path, expectedName) => {
|
|
|
1185
1185
|
return secondLast === expectedName;
|
|
1186
1186
|
};
|
|
1187
1187
|
|
|
1188
|
+
const resolveHyperlinkPattern = (pattern, entry, locale) => {
|
|
1189
|
+
if (!entry || !locale)
|
|
1190
|
+
return null;
|
|
1191
|
+
const variables = {
|
|
1192
|
+
entry,
|
|
1193
|
+
locale,
|
|
1194
|
+
};
|
|
1195
|
+
return buildTemplate({ template: pattern, context: variables });
|
|
1196
|
+
};
|
|
1197
|
+
function getValue(obj, path) {
|
|
1198
|
+
return path
|
|
1199
|
+
.replace(/\[/g, '.')
|
|
1200
|
+
.replace(/\]/g, '')
|
|
1201
|
+
.split('.')
|
|
1202
|
+
.reduce((o, k) => (o || {})[k], obj);
|
|
1203
|
+
}
|
|
1204
|
+
function addLocale(str, locale) {
|
|
1205
|
+
const fieldsIndicator = 'fields';
|
|
1206
|
+
const fieldsIndex = str.indexOf(fieldsIndicator);
|
|
1207
|
+
if (fieldsIndex !== -1) {
|
|
1208
|
+
const dotIndex = str.indexOf('.', fieldsIndex + fieldsIndicator.length + 1); // +1 for '.'
|
|
1209
|
+
if (dotIndex !== -1) {
|
|
1210
|
+
return str.slice(0, dotIndex + 1) + locale + '.' + str.slice(dotIndex + 1);
|
|
1211
|
+
}
|
|
1212
|
+
}
|
|
1213
|
+
return str;
|
|
1214
|
+
}
|
|
1215
|
+
function getTemplateValue(ctx, path) {
|
|
1216
|
+
const pathWithLocale = addLocale(path, ctx.locale);
|
|
1217
|
+
const retrievedValue = getValue(ctx, pathWithLocale);
|
|
1218
|
+
return typeof retrievedValue === 'object' && retrievedValue !== null
|
|
1219
|
+
? retrievedValue[ctx.locale]
|
|
1220
|
+
: retrievedValue;
|
|
1221
|
+
}
|
|
1222
|
+
function buildTemplate({ template, context, }) {
|
|
1223
|
+
const localeVariable = /{\s*locale\s*}/g;
|
|
1224
|
+
// e.g. "{ page.sys.id }"
|
|
1225
|
+
const variables = /{\s*([\S]+?)\s*}/g;
|
|
1226
|
+
return (template
|
|
1227
|
+
// first replace the locale pattern
|
|
1228
|
+
.replace(localeVariable, context.locale)
|
|
1229
|
+
// then resolve the remaining variables
|
|
1230
|
+
.replace(variables, (_, path) => {
|
|
1231
|
+
const fallback = path + '_NOT_FOUND';
|
|
1232
|
+
const value = getTemplateValue(context, path) ?? fallback;
|
|
1233
|
+
// using _.result didn't gave proper results so we run our own version of it
|
|
1234
|
+
return String(typeof value === 'function' ? value() : value);
|
|
1235
|
+
}));
|
|
1236
|
+
}
|
|
1237
|
+
|
|
1188
1238
|
const sendMessage = (eventType, data) => {
|
|
1189
1239
|
if (typeof window === 'undefined') {
|
|
1190
1240
|
return;
|
|
@@ -1794,6 +1844,7 @@ const CF_STYLE_ATTRIBUTES = [
|
|
|
1794
1844
|
'cfBackgroundImageAlignmentHorizontal',
|
|
1795
1845
|
];
|
|
1796
1846
|
const EMPTY_CONTAINER_HEIGHT = '80px';
|
|
1847
|
+
const HYPERLINK_DEFAULT_PATTERN = `/{locale}/{entry.fields.slug}/`;
|
|
1797
1848
|
var PostMessageMethods$1;
|
|
1798
1849
|
(function (PostMessageMethods) {
|
|
1799
1850
|
PostMessageMethods["REQUEST_ENTITIES"] = "REQUEST_ENTITIES";
|
|
@@ -2248,11 +2299,15 @@ const createAssemblyRegistration = ({ definitionId, definitionName, component, }
|
|
|
2248
2299
|
|
|
2249
2300
|
const useEditorStore = create((set, get) => ({
|
|
2250
2301
|
dataSource: {},
|
|
2302
|
+
hyperLinkPattern: undefined,
|
|
2251
2303
|
unboundValues: {},
|
|
2252
2304
|
isDragging: false,
|
|
2253
2305
|
dragItem: '',
|
|
2254
2306
|
selectedNodeId: null,
|
|
2255
2307
|
locale: null,
|
|
2308
|
+
setHyperLinkPattern: (pattern) => {
|
|
2309
|
+
set({ hyperLinkPattern: pattern });
|
|
2310
|
+
},
|
|
2256
2311
|
setSelectedNodeId: (id) => {
|
|
2257
2312
|
set({ selectedNodeId: id });
|
|
2258
2313
|
},
|
|
@@ -2364,6 +2419,8 @@ const useEntityStore = create((set) => ({
|
|
|
2364
2419
|
|
|
2365
2420
|
const useComponentProps = ({ node, areEntitiesFetched, resolveDesignValue, renderDropzone, definition, userIsDragging, }) => {
|
|
2366
2421
|
const unboundValues = useEditorStore((state) => state.unboundValues);
|
|
2422
|
+
const hyperlinkPattern = useEditorStore((state) => state.hyperLinkPattern);
|
|
2423
|
+
const locale = useEditorStore((state) => state.locale);
|
|
2367
2424
|
const dataSource = useEditorStore((state) => state.dataSource);
|
|
2368
2425
|
const entityStore = useEntityStore((state) => state.entityStore);
|
|
2369
2426
|
const props = useMemo(() => {
|
|
@@ -2393,6 +2450,14 @@ const useComponentProps = ({ node, areEntitiesFetched, resolveDesignValue, rende
|
|
|
2393
2450
|
[variableName]: designValue,
|
|
2394
2451
|
};
|
|
2395
2452
|
}
|
|
2453
|
+
else if (variableMapping.type === 'HyperlinkValue') {
|
|
2454
|
+
const binding = dataSource[variableMapping.linkTargetKey];
|
|
2455
|
+
const hyperlinkEntry = entityStore.getEntryOrAsset(binding, variableMapping.linkTargetKey);
|
|
2456
|
+
return {
|
|
2457
|
+
...acc,
|
|
2458
|
+
[variableName]: resolveHyperlinkPattern(definition.hyperlinkPattern || hyperlinkPattern || HYPERLINK_DEFAULT_PATTERN, hyperlinkEntry, locale),
|
|
2459
|
+
};
|
|
2460
|
+
}
|
|
2396
2461
|
else if (variableMapping.type === 'BoundValue') {
|
|
2397
2462
|
const [, uuid, path] = variableMapping.path.split('/');
|
|
2398
2463
|
const binding = dataSource[uuid];
|
|
@@ -2431,15 +2496,14 @@ const useComponentProps = ({ node, areEntitiesFetched, resolveDesignValue, rende
|
|
|
2431
2496
|
}
|
|
2432
2497
|
}, {});
|
|
2433
2498
|
}, [
|
|
2499
|
+
hyperlinkPattern,
|
|
2500
|
+
node,
|
|
2501
|
+
locale,
|
|
2434
2502
|
definition,
|
|
2435
|
-
node.data.props,
|
|
2436
|
-
node.children,
|
|
2437
|
-
node.data.blockId,
|
|
2438
2503
|
resolveDesignValue,
|
|
2439
2504
|
dataSource,
|
|
2440
2505
|
areEntitiesFetched,
|
|
2441
2506
|
unboundValues,
|
|
2442
|
-
node.type,
|
|
2443
2507
|
entityStore,
|
|
2444
2508
|
]);
|
|
2445
2509
|
const cfStyles = buildCfStyles(props, node.data.blockId);
|
|
@@ -2616,6 +2680,11 @@ const deserializeAssemblyNode = ({ node, nodeId, nodeLocation, parentId, assembl
|
|
|
2616
2680
|
path: instanceProperty.path,
|
|
2617
2681
|
};
|
|
2618
2682
|
}
|
|
2683
|
+
else if (instanceProperty?.type === 'HyperlinkValue') {
|
|
2684
|
+
const componentInstanceValue = componentInstanceDataSource[instanceProperty.linkTargetKey];
|
|
2685
|
+
dataSource[instanceProperty.linkTargetKey] == componentInstanceValue;
|
|
2686
|
+
childNodeVariable[variableName] = instanceProperty;
|
|
2687
|
+
}
|
|
2619
2688
|
}
|
|
2620
2689
|
}
|
|
2621
2690
|
const isAssembly = assembliesRegistry.has(node.definitionId);
|
|
@@ -4513,10 +4582,16 @@ const useInitializeEditor = () => {
|
|
|
4513
4582
|
return initialized;
|
|
4514
4583
|
};
|
|
4515
4584
|
|
|
4516
|
-
const VisualEditorRoot = () => {
|
|
4585
|
+
const VisualEditorRoot = ({ experience }) => {
|
|
4517
4586
|
const initialized = useInitializeEditor();
|
|
4587
|
+
const setHyperLinkPattern = useEditorStore((state) => state.setHyperLinkPattern);
|
|
4518
4588
|
const setMousePosition = useDraggedItemStore((state) => state.setMousePosition);
|
|
4519
4589
|
const setHoveringZone = useZoneStore((state) => state.setHoveringZone);
|
|
4590
|
+
useEffect(() => {
|
|
4591
|
+
if (experience?.hyperlinkPattern) {
|
|
4592
|
+
setHyperLinkPattern(experience.hyperlinkPattern);
|
|
4593
|
+
}
|
|
4594
|
+
}, [experience?.hyperlinkPattern, setHyperLinkPattern]);
|
|
4520
4595
|
useEffect(() => {
|
|
4521
4596
|
const onMouseMove = (e) => {
|
|
4522
4597
|
setMousePosition(e.clientX, e.clientY);
|