@neo4j-nvl/react 0.2.27 → 0.2.29
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/lib/basic-wrapper/BasicNvlWrapper.d.ts +1 -1
- package/lib/basic-wrapper/BasicNvlWrapper.js +23 -21
- package/lib/interactive-nvl-wrapper/InteractiveNvlWrapper.d.ts +3 -3
- package/lib/interactive-nvl-wrapper/InteractiveNvlWrapper.js +8 -7
- package/lib/utils/graphComparison.js +10 -8
- package/package.json +1 -1
|
@@ -109,5 +109,5 @@ export interface BasicReactWrapperProps {
|
|
|
109
109
|
* For more about interactivity, check out the {@link NVL}.hittest method,
|
|
110
110
|
* the Interaction Handlers module module and the {@link InteractiveNvlWrapper}.
|
|
111
111
|
*/
|
|
112
|
-
export declare const BasicNvlWrapper: React.MemoExoticComponent<React.ForwardRefExoticComponent<BasicReactWrapperProps & React.RefAttributes<IncludeMethods<NVL>>>>;
|
|
112
|
+
export declare const BasicNvlWrapper: React.MemoExoticComponent<React.ForwardRefExoticComponent<Pick<BasicReactWrapperProps & React.HTMLProps<HTMLDivElement>, "max" | "required" | "type" | "data" | "default" | "high" | "low" | "key" | "id" | "media" | "height" | "width" | "start" | "open" | "name" | "color" | "content" | "translate" | "value" | "hidden" | "cite" | "form" | "label" | "slot" | "span" | "style" | "summary" | "title" | "dir" | "pattern" | "acceptCharset" | "action" | "method" | "noValidate" | "rel" | "target" | "accessKey" | "draggable" | "lang" | "className" | "prefix" | "role" | "children" | "contentEditable" | "inputMode" | "nonce" | "tabIndex" | "async" | "disabled" | "multiple" | "size" | "manifest" | "wrap" | "accept" | "allowFullScreen" | "allowTransparency" | "alt" | "as" | "autoComplete" | "autoFocus" | "autoPlay" | "capture" | "cellPadding" | "cellSpacing" | "charSet" | "challenge" | "checked" | "classID" | "cols" | "colSpan" | "controls" | "coords" | "crossOrigin" | "dateTime" | "defer" | "download" | "encType" | "formAction" | "formEncType" | "formMethod" | "formNoValidate" | "formTarget" | "frameBorder" | "headers" | "href" | "hrefLang" | "htmlFor" | "httpEquiv" | "integrity" | "keyParams" | "keyType" | "kind" | "list" | "loop" | "marginHeight" | "marginWidth" | "maxLength" | "mediaGroup" | "min" | "minLength" | "muted" | "optimum" | "defaultChecked" | "defaultValue" | "suppressContentEditableWarning" | "suppressHydrationWarning" | "contextMenu" | "placeholder" | "spellCheck" | "radioGroup" | "about" | "datatype" | "inlist" | "property" | "resource" | "typeof" | "vocab" | "autoCapitalize" | "autoCorrect" | "autoSave" | "itemProp" | "itemScope" | "itemType" | "itemID" | "itemRef" | "results" | "security" | "unselectable" | "is" | "aria-activedescendant" | "aria-atomic" | "aria-autocomplete" | "aria-busy" | "aria-checked" | "aria-colcount" | "aria-colindex" | "aria-colspan" | "aria-controls" | "aria-current" | "aria-describedby" | "aria-details" | "aria-disabled" | "aria-dropeffect" | "aria-errormessage" | "aria-expanded" | "aria-flowto" | "aria-grabbed" | "aria-haspopup" | "aria-hidden" | "aria-invalid" | "aria-keyshortcuts" | "aria-label" | "aria-labelledby" | "aria-level" | "aria-live" | "aria-modal" | "aria-multiline" | "aria-multiselectable" | "aria-orientation" | "aria-owns" | "aria-placeholder" | "aria-posinset" | "aria-pressed" | "aria-readonly" | "aria-relevant" | "aria-required" | "aria-roledescription" | "aria-rowcount" | "aria-rowindex" | "aria-rowspan" | "aria-selected" | "aria-setsize" | "aria-sort" | "aria-valuemax" | "aria-valuemin" | "aria-valuenow" | "aria-valuetext" | "playsInline" | "poster" | "preload" | "readOnly" | "reversed" | "rows" | "rowSpan" | "sandbox" | "scope" | "scoped" | "scrolling" | "seamless" | "selected" | "shape" | "sizes" | "src" | "srcDoc" | "srcLang" | "srcSet" | "step" | "useMap" | "wmode" | "dangerouslySetInnerHTML" | "onCopy" | "onCopyCapture" | "onCut" | "onCutCapture" | "onPaste" | "onPasteCapture" | "onCompositionEnd" | "onCompositionEndCapture" | "onCompositionStart" | "onCompositionStartCapture" | "onCompositionUpdate" | "onCompositionUpdateCapture" | "onFocus" | "onFocusCapture" | "onBlur" | "onBlurCapture" | "onChange" | "onChangeCapture" | "onBeforeInput" | "onBeforeInputCapture" | "onInput" | "onInputCapture" | "onReset" | "onResetCapture" | "onSubmit" | "onSubmitCapture" | "onInvalid" | "onInvalidCapture" | "onLoad" | "onLoadCapture" | "onError" | "onErrorCapture" | "onKeyDown" | "onKeyDownCapture" | "onKeyPress" | "onKeyPressCapture" | "onKeyUp" | "onKeyUpCapture" | "onAbort" | "onAbortCapture" | "onCanPlay" | "onCanPlayCapture" | "onCanPlayThrough" | "onCanPlayThroughCapture" | "onDurationChange" | "onDurationChangeCapture" | "onEmptied" | "onEmptiedCapture" | "onEncrypted" | "onEncryptedCapture" | "onEnded" | "onEndedCapture" | "onLoadedData" | "onLoadedDataCapture" | "onLoadedMetadata" | "onLoadedMetadataCapture" | "onLoadStart" | "onLoadStartCapture" | "onPause" | "onPauseCapture" | "onPlay" | "onPlayCapture" | "onPlaying" | "onPlayingCapture" | "onProgress" | "onProgressCapture" | "onRateChange" | "onRateChangeCapture" | "onResize" | "onResizeCapture" | "onSeeked" | "onSeekedCapture" | "onSeeking" | "onSeekingCapture" | "onStalled" | "onStalledCapture" | "onSuspend" | "onSuspendCapture" | "onTimeUpdate" | "onTimeUpdateCapture" | "onVolumeChange" | "onVolumeChangeCapture" | "onWaiting" | "onWaitingCapture" | "onAuxClick" | "onAuxClickCapture" | "onClick" | "onClickCapture" | "onContextMenu" | "onContextMenuCapture" | "onDoubleClick" | "onDoubleClickCapture" | "onDrag" | "onDragCapture" | "onDragEnd" | "onDragEndCapture" | "onDragEnter" | "onDragEnterCapture" | "onDragExit" | "onDragExitCapture" | "onDragLeave" | "onDragLeaveCapture" | "onDragOver" | "onDragOverCapture" | "onDragStart" | "onDragStartCapture" | "onDrop" | "onDropCapture" | "onMouseDown" | "onMouseDownCapture" | "onMouseEnter" | "onMouseLeave" | "onMouseMove" | "onMouseMoveCapture" | "onMouseOut" | "onMouseOutCapture" | "onMouseOver" | "onMouseOverCapture" | "onMouseUp" | "onMouseUpCapture" | "onSelect" | "onSelectCapture" | "onTouchCancel" | "onTouchCancelCapture" | "onTouchEnd" | "onTouchEndCapture" | "onTouchMove" | "onTouchMoveCapture" | "onTouchStart" | "onTouchStartCapture" | "onPointerDown" | "onPointerDownCapture" | "onPointerMove" | "onPointerMoveCapture" | "onPointerUp" | "onPointerUpCapture" | "onPointerCancel" | "onPointerCancelCapture" | "onPointerEnter" | "onPointerEnterCapture" | "onPointerLeave" | "onPointerLeaveCapture" | "onPointerOver" | "onPointerOverCapture" | "onPointerOut" | "onPointerOutCapture" | "onGotPointerCapture" | "onGotPointerCaptureCapture" | "onLostPointerCapture" | "onLostPointerCaptureCapture" | "onScroll" | "onScrollCapture" | "onWheel" | "onWheelCapture" | "onAnimationStart" | "onAnimationStartCapture" | "onAnimationEnd" | "onAnimationEndCapture" | "onAnimationIteration" | "onAnimationIterationCapture" | "onTransitionEnd" | "onTransitionEndCapture" | keyof BasicReactWrapperProps> & React.RefAttributes<IncludeMethods<NVL>>>>;
|
|
113
113
|
export {};
|
|
@@ -99,26 +99,25 @@ import { useDeepCompareEffect } from '../utils/hooks';
|
|
|
99
99
|
*/
|
|
100
100
|
export const BasicNvlWrapper = memo(forwardRef((_a, ref) => {
|
|
101
101
|
var { nodes, rels, layout, layoutOptions, nvlCallbacks = {}, nvlOptions = {}, onInitializationError } = _a, nvlEvents = __rest(_a, ["nodes", "rels", "layout", "layoutOptions", "nvlCallbacks", "nvlOptions", "onInitializationError"]);
|
|
102
|
+
const nvlRef = useRef(null);
|
|
102
103
|
useImperativeHandle(ref, () => {
|
|
104
|
+
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions
|
|
103
105
|
const nvlMethods = Object.getOwnPropertyNames(NVL.prototype);
|
|
104
|
-
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
105
106
|
// @ts-ignore revisit better typing for reduce function
|
|
106
|
-
return nvlMethods.reduce((current, method) => (Object.assign(Object.assign({}, current), {
|
|
107
|
-
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
107
|
+
return nvlMethods.reduce((current, method) => (Object.assign(Object.assign({}, current), { [method]: (...args) =>
|
|
108
108
|
// @ts-ignore suppress the type casting error on spreading
|
|
109
|
-
|
|
109
|
+
nvlRef !== undefined && nvlRef.current !== null && nvlRef.current[method](...args) })), {});
|
|
110
110
|
});
|
|
111
111
|
const containerRef = useRef();
|
|
112
|
-
const nvlRef = useRef();
|
|
113
112
|
const [currentNodes, setCurrentNodes] = useState(nodes);
|
|
114
113
|
const [currentRels, setCurrentRels] = useState(rels);
|
|
115
114
|
useEffect(() => {
|
|
116
|
-
|
|
115
|
+
let newNvl;
|
|
116
|
+
if (nvlRef.current === null) {
|
|
117
117
|
const combinedOptions = Object.assign(Object.assign({}, nvlOptions), { layoutOptions });
|
|
118
|
-
if (layout) {
|
|
118
|
+
if (layout !== undefined) {
|
|
119
119
|
combinedOptions.layout = layout;
|
|
120
120
|
}
|
|
121
|
-
let newNvl;
|
|
122
121
|
try {
|
|
123
122
|
newNvl = new NVL(containerRef.current, currentNodes, currentRels, combinedOptions, nvlCallbacks);
|
|
124
123
|
nvlRef.current = newNvl;
|
|
@@ -133,13 +132,14 @@ export const BasicNvlWrapper = memo(forwardRef((_a, ref) => {
|
|
|
133
132
|
throw e;
|
|
134
133
|
}
|
|
135
134
|
}
|
|
136
|
-
return () => {
|
|
137
|
-
newNvl === null || newNvl === void 0 ? void 0 : newNvl.destroy();
|
|
138
|
-
};
|
|
139
135
|
}
|
|
136
|
+
return () => {
|
|
137
|
+
newNvl === null || newNvl === void 0 ? void 0 : newNvl.destroy();
|
|
138
|
+
};
|
|
140
139
|
}, []);
|
|
141
140
|
useEffect(() => {
|
|
142
|
-
|
|
141
|
+
var _a, _b, _c;
|
|
142
|
+
if (nvlRef.current === null) {
|
|
143
143
|
return;
|
|
144
144
|
}
|
|
145
145
|
const nodeChanges = getMapDifferences(currentNodes, nodes);
|
|
@@ -147,23 +147,25 @@ export const BasicNvlWrapper = memo(forwardRef((_a, ref) => {
|
|
|
147
147
|
const relChanges = getMapDifferences(currentRels, rels);
|
|
148
148
|
setCurrentRels(rels);
|
|
149
149
|
setCurrentNodes(nodes);
|
|
150
|
-
nvlRef.current
|
|
151
|
-
|
|
152
|
-
nvlRef.current
|
|
153
|
-
nvlRef.current.removeRelationshipsWithIds(relChanges.removed.map((r) => r.id));
|
|
154
|
-
nvlRef.current && nvlRef.current.removeNodesWithIds(nodeChanges.removed.map((n) => n.id));
|
|
150
|
+
(_a = nvlRef.current) === null || _a === void 0 ? void 0 : _a.addAndUpdateElementsInGraph([...nodeChanges.added, ...nodeDiff], [...relChanges.added, ...relChanges.updated]);
|
|
151
|
+
(_b = nvlRef.current) === null || _b === void 0 ? void 0 : _b.removeRelationshipsWithIds(relChanges.removed.map((r) => r.id));
|
|
152
|
+
(_c = nvlRef.current) === null || _c === void 0 ? void 0 : _c.removeNodesWithIds(nodeChanges.removed.map((n) => n.id));
|
|
155
153
|
}, [nodes, rels]);
|
|
156
154
|
useEffect(() => {
|
|
157
|
-
|
|
155
|
+
var _a;
|
|
156
|
+
(_a = nvlRef.current) === null || _a === void 0 ? void 0 : _a.setLayout(layout);
|
|
158
157
|
}, [layout]);
|
|
159
158
|
useDeepCompareEffect(() => {
|
|
160
|
-
|
|
159
|
+
var _a;
|
|
160
|
+
(_a = nvlRef.current) === null || _a === void 0 ? void 0 : _a.setLayoutOptions(layoutOptions);
|
|
161
161
|
}, [layoutOptions]);
|
|
162
162
|
useEffect(() => {
|
|
163
|
-
|
|
163
|
+
var _a;
|
|
164
|
+
(_a = nvlRef.current) === null || _a === void 0 ? void 0 : _a.setUseWebGLRenderer(nvlOptions.useWebGL);
|
|
164
165
|
}, [nvlOptions.useWebGL]);
|
|
165
166
|
useEffect(() => {
|
|
166
|
-
|
|
167
|
+
var _a;
|
|
168
|
+
(_a = nvlRef.current) === null || _a === void 0 ? void 0 : _a.setDisableWebGL(nvlOptions.disableWebGL);
|
|
167
169
|
}, [nvlOptions.disableWebGL]);
|
|
168
170
|
return React.createElement("div", Object.assign({ ref: containerRef, style: { height: '100%', outline: '0' } }, nvlEvents));
|
|
169
171
|
}));
|
|
@@ -39,9 +39,9 @@ export interface InteractiveNvlWrapperProps extends BasicReactWrapperProps {
|
|
|
39
39
|
* nodes={nodes}
|
|
40
40
|
* rels={relationships}
|
|
41
41
|
* mouseEventCallbacks={{
|
|
42
|
-
*
|
|
43
|
-
*
|
|
44
|
-
*
|
|
42
|
+
* onHover: (element) => console.log(element),
|
|
43
|
+
* onNodeClick: (node) => console.log(node),
|
|
44
|
+
* onMultiSelect: multiSelect
|
|
45
45
|
* }}
|
|
46
46
|
* />
|
|
47
47
|
* </>
|
|
@@ -8,7 +8,8 @@ const options = {
|
|
|
8
8
|
excludeNodeMargin: true
|
|
9
9
|
};
|
|
10
10
|
const destroyInteraction = (interactionRef) => {
|
|
11
|
-
|
|
11
|
+
var _a;
|
|
12
|
+
(_a = interactionRef.current) === null || _a === void 0 ? void 0 : _a.destroy();
|
|
12
13
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
13
14
|
// @ts-ignore
|
|
14
15
|
interactionRef.current = null;
|
|
@@ -16,8 +17,8 @@ const destroyInteraction = (interactionRef) => {
|
|
|
16
17
|
const useInteractionEffect = (interaction, interactionRef, callback, eventName, nvlRef, interactionOptions) => {
|
|
17
18
|
useEffect(() => {
|
|
18
19
|
setTimeout(() => {
|
|
19
|
-
if (callback) {
|
|
20
|
-
if (
|
|
20
|
+
if (callback === true || typeof callback === 'function') {
|
|
21
|
+
if (interactionRef.current === null || interactionRef.current === undefined) {
|
|
21
22
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
22
23
|
// @ts-ignore
|
|
23
24
|
interactionRef.current = new interaction(nvlRef.current, interactionOptions);
|
|
@@ -60,15 +61,15 @@ const useInteractionEffect = (interaction, interactionRef, callback, eventName,
|
|
|
60
61
|
* nodes={nodes}
|
|
61
62
|
* rels={relationships}
|
|
62
63
|
* mouseEventCallbacks={{
|
|
63
|
-
*
|
|
64
|
-
*
|
|
65
|
-
*
|
|
64
|
+
* onHover: (element) => console.log(element),
|
|
65
|
+
* onNodeClick: (node) => console.log(node),
|
|
66
|
+
* onMultiSelect: multiSelect
|
|
66
67
|
* }}
|
|
67
68
|
* />
|
|
68
69
|
* </>
|
|
69
70
|
* ```
|
|
70
71
|
*/
|
|
71
|
-
export const InteractiveNvlWrapper = memo(forwardRef(({ nodes, rels, layout, layoutOptions, mouseEventCallbacks, nvlCallbacks, nvlOptions = {}, interactionOptions = options }, nvlRef) => {
|
|
72
|
+
export const InteractiveNvlWrapper = memo(forwardRef(({ nodes, rels, layout, layoutOptions, mouseEventCallbacks = {}, nvlCallbacks = {}, nvlOptions = {}, interactionOptions = options }, nvlRef) => {
|
|
72
73
|
const myNvlRef = nvlRef !== null ? nvlRef : useRef(null);
|
|
73
74
|
const { onHover, onNodeClick, onNodeDoubleClick, onNodeRightClick, onRelationshipClick, onRelationshipDoubleClick, onRelationshipRightClick, onCanvasClick, onCanvasRightClick, onPan, onZoom, onDrag, onDragStart, onDragEnd, onDrawEnd, onMultiSelect } = mouseEventCallbacks;
|
|
74
75
|
const hoverInteraction = useRef();
|
|
@@ -16,23 +16,25 @@ const getMapDifferences = (prevGraphElements, newGraphElements) => {
|
|
|
16
16
|
if (!isEqual(prevMap[prevId], currentMap[currId])) {
|
|
17
17
|
updated.push(currId);
|
|
18
18
|
}
|
|
19
|
-
i
|
|
20
|
-
j
|
|
19
|
+
i += 1;
|
|
20
|
+
j += 1;
|
|
21
21
|
}
|
|
22
22
|
else if (prevId < currId) {
|
|
23
23
|
removed.push(prevId);
|
|
24
|
-
i
|
|
24
|
+
i += 1;
|
|
25
25
|
}
|
|
26
26
|
else {
|
|
27
27
|
added.push(currId);
|
|
28
|
-
j
|
|
28
|
+
j += 1;
|
|
29
29
|
}
|
|
30
30
|
}
|
|
31
31
|
while (i < prevIds.length) {
|
|
32
|
-
removed.push(prevIds[i
|
|
32
|
+
removed.push(prevIds[i]);
|
|
33
|
+
i += 1;
|
|
33
34
|
}
|
|
34
35
|
while (j < currentIds.length) {
|
|
35
|
-
added.push(currentIds[j
|
|
36
|
+
added.push(currentIds[j]);
|
|
37
|
+
j += 1;
|
|
36
38
|
}
|
|
37
39
|
return {
|
|
38
40
|
added: added.map((id) => currentMap[id]),
|
|
@@ -45,7 +47,7 @@ const getNodeAttributeDifferences = (prevNodes, newNodes) => {
|
|
|
45
47
|
return newNodes
|
|
46
48
|
.map((nodeToUpdate) => {
|
|
47
49
|
const previousNode = prevNodeMap[nodeToUpdate.id];
|
|
48
|
-
if (
|
|
50
|
+
if (previousNode === undefined) {
|
|
49
51
|
return null;
|
|
50
52
|
}
|
|
51
53
|
return transform(nodeToUpdate, (result, value, key) => {
|
|
@@ -54,6 +56,6 @@ const getNodeAttributeDifferences = (prevNodes, newNodes) => {
|
|
|
54
56
|
}
|
|
55
57
|
});
|
|
56
58
|
})
|
|
57
|
-
.filter((n) => n && Object.keys(n).length > 1);
|
|
59
|
+
.filter((n) => n !== null && Object.keys(n).length > 1);
|
|
58
60
|
};
|
|
59
61
|
export { getNodeAttributeDifferences, getMapDifferences };
|