@biki-dev/okve 0.1.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/components/KnowledgeGraph/KnowledgeGraph.d.ts +2 -0
- package/dist/components/KnowledgeGraph/index.d.ts +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/okve.cjs +6 -0
- package/dist/okve.css +2 -0
- package/dist/okve.js +361 -0
- package/dist/types/index.d.ts +24 -0
- package/dist/utils/graphLayout.d.ts +9 -0
- package/package.json +42 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { KnowledgeGraph } from './KnowledgeGraph';
|
package/dist/index.d.ts
ADDED
package/dist/okve.cjs
ADDED
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});var e=Object.create,t=Object.defineProperty,n=Object.getOwnPropertyDescriptor,r=Object.getOwnPropertyNames,i=Object.getPrototypeOf,a=Object.prototype.hasOwnProperty,o=(e,t)=>()=>(t||e((t={exports:{}}).exports,t),t.exports),s=(e,i,o,s)=>{if(i&&typeof i==`object`||typeof i==`function`)for(var c=r(i),l=0,u=c.length,d;l<u;l++)d=c[l],!a.call(e,d)&&d!==o&&t(e,d,{get:(e=>i[e]).bind(null,d),enumerable:!(s=n(i,d))||s.enumerable});return e},c=(n,r,a)=>(a=n==null?{}:e(i(n)),s(r||!n||!n.__esModule?t(a,`default`,{value:n,enumerable:!0}):a,n));let l=require(`react`),u=require(`d3`);u=c(u);function d(e,t,n){let r=Math.max(e.length,1),i=Math.max(Math.min(t,n)*.28,120),a=t/2,o=n/2;return e.map((e,t)=>{let n=t/r*Math.PI*2-Math.PI/2;return{...e,x:a+Math.cos(n)*i,y:o+Math.sin(n)*i,vx:0,vy:0}})}function f(e,t){let n=new Set,r=new Set;return t?(n.add(t),e.edges.forEach(e=>{(e.source===t||e.target===t)&&(r.add(e.id),n.add(e.source),n.add(e.target))}),{highlightedNodeIds:n,highlightedEdgeIds:r}):(e.nodes.forEach(e=>n.add(e.id)),e.edges.forEach(e=>r.add(e.id)),{highlightedNodeIds:n,highlightedEdgeIds:r})}var p=o((e=>{var t=Symbol.for(`react.transitional.element`),n=Symbol.for(`react.fragment`);function r(e,n,r){var i=null;if(r!==void 0&&(i=``+r),n.key!==void 0&&(i=``+n.key),`key`in n)for(var a in r={},n)a!==`key`&&(r[a]=n[a]);else r=n;return n=r.ref,{$$typeof:t,type:e,key:i,ref:n===void 0?null:n,props:r}}e.Fragment=n,e.jsx=r,e.jsxs=r})),m=o((e=>{process.env.NODE_ENV!==`production`&&(function(){function t(e){if(e==null)return null;if(typeof e==`function`)return e.$$typeof===O?null:e.displayName||e.name||null;if(typeof e==`string`)return e;switch(e){case _:return`Fragment`;case y:return`Profiler`;case v:return`StrictMode`;case C:return`Suspense`;case w:return`SuspenseList`;case D:return`Activity`}if(typeof e==`object`)switch(typeof e.tag==`number`&&console.error(`Received an unexpected object in getComponentNameFromType(). This is likely a bug in React. Please file an issue.`),e.$$typeof){case g:return`Portal`;case x:return e.displayName||`Context`;case b:return(e._context.displayName||`Context`)+`.Consumer`;case S:var n=e.render;return e=e.displayName,e||=(e=n.displayName||n.name||``,e===``?`ForwardRef`:`ForwardRef(`+e+`)`),e;case T:return n=e.displayName||null,n===null?t(e.type)||`Memo`:n;case E:n=e._payload,e=e._init;try{return t(e(n))}catch{}}return null}function n(e){return``+e}function r(e){try{n(e);var t=!1}catch{t=!0}if(t){t=console;var r=t.error,i=typeof Symbol==`function`&&Symbol.toStringTag&&e[Symbol.toStringTag]||e.constructor.name||`Object`;return r.call(t,`The provided key is an unsupported type %s. This value must be coerced to a string before using it here.`,i),n(e)}}function i(e){if(e===_)return`<>`;if(typeof e==`object`&&e&&e.$$typeof===E)return`<...>`;try{var n=t(e);return n?`<`+n+`>`:`<...>`}catch{return`<...>`}}function a(){var e=k.A;return e===null?null:e.getOwner()}function o(){return Error(`react-stack-top-frame`)}function s(e){if(A.call(e,`key`)){var t=Object.getOwnPropertyDescriptor(e,`key`).get;if(t&&t.isReactWarning)return!1}return e.key!==void 0}function c(e,t){function n(){N||(N=!0,console.error("%s: `key` is not a prop. Trying to access it will result in `undefined` being returned. If you need to access the same value within the child component, you should pass it as a different prop. (https://react.dev/link/special-props)",t))}n.isReactWarning=!0,Object.defineProperty(e,`key`,{get:n,configurable:!0})}function l(){var e=t(this.type);return P[e]||(P[e]=!0,console.error(`Accessing element.ref was removed in React 19. ref is now a regular prop. It will be removed from the JSX Element type in a future release.`)),e=this.props.ref,e===void 0?null:e}function u(e,t,n,r,i,a){var o=n.ref;return e={$$typeof:h,type:e,key:t,props:n,_owner:r},(o===void 0?null:o)===null?Object.defineProperty(e,`ref`,{enumerable:!1,value:null}):Object.defineProperty(e,`ref`,{enumerable:!1,get:l}),e._store={},Object.defineProperty(e._store,`validated`,{configurable:!1,enumerable:!1,writable:!0,value:0}),Object.defineProperty(e,`_debugInfo`,{configurable:!1,enumerable:!1,writable:!0,value:null}),Object.defineProperty(e,`_debugStack`,{configurable:!1,enumerable:!1,writable:!0,value:i}),Object.defineProperty(e,`_debugTask`,{configurable:!1,enumerable:!1,writable:!0,value:a}),Object.freeze&&(Object.freeze(e.props),Object.freeze(e)),e}function d(e,n,i,o,l,d){var p=n.children;if(p!==void 0)if(o)if(j(p)){for(o=0;o<p.length;o++)f(p[o]);Object.freeze&&Object.freeze(p)}else console.error(`React.jsx: Static children should always be an array. You are likely explicitly calling React.jsxs or React.jsxDEV. Use the Babel transform instead.`);else f(p);if(A.call(n,`key`)){p=t(e);var m=Object.keys(n).filter(function(e){return e!==`key`});o=0<m.length?`{key: someKey, `+m.join(`: ..., `)+`: ...}`:`{key: someKey}`,L[p+o]||(m=0<m.length?`{`+m.join(`: ..., `)+`: ...}`:`{}`,console.error(`A props object containing a "key" prop is being spread into JSX:
|
|
2
|
+
let props = %s;
|
|
3
|
+
<%s {...props} />
|
|
4
|
+
React keys must be passed directly to JSX without using spread:
|
|
5
|
+
let props = %s;
|
|
6
|
+
<%s key={someKey} {...props} />`,o,p,m,p),L[p+o]=!0)}if(p=null,i!==void 0&&(r(i),p=``+i),s(n)&&(r(n.key),p=``+n.key),`key`in n)for(var h in i={},n)h!==`key`&&(i[h]=n[h]);else i=n;return p&&c(i,typeof e==`function`?e.displayName||e.name||`Unknown`:e),u(e,p,i,a(),l,d)}function f(e){p(e)?e._store&&(e._store.validated=1):typeof e==`object`&&e&&e.$$typeof===E&&(e._payload.status===`fulfilled`?p(e._payload.value)&&e._payload.value._store&&(e._payload.value._store.validated=1):e._store&&(e._store.validated=1))}function p(e){return typeof e==`object`&&!!e&&e.$$typeof===h}var m=require(`react`),h=Symbol.for(`react.transitional.element`),g=Symbol.for(`react.portal`),_=Symbol.for(`react.fragment`),v=Symbol.for(`react.strict_mode`),y=Symbol.for(`react.profiler`),b=Symbol.for(`react.consumer`),x=Symbol.for(`react.context`),S=Symbol.for(`react.forward_ref`),C=Symbol.for(`react.suspense`),w=Symbol.for(`react.suspense_list`),T=Symbol.for(`react.memo`),E=Symbol.for(`react.lazy`),D=Symbol.for(`react.activity`),O=Symbol.for(`react.client.reference`),k=m.__CLIENT_INTERNALS_DO_NOT_USE_OR_WARN_USERS_THEY_CANNOT_UPGRADE,A=Object.prototype.hasOwnProperty,j=Array.isArray,M=console.createTask?console.createTask:function(){return null};m={react_stack_bottom_frame:function(e){return e()}};var N,P={},F=m.react_stack_bottom_frame.bind(m,o)(),I=M(i(o)),L={};e.Fragment=_,e.jsx=function(e,t,n){var r=1e4>k.recentlyCreatedOwnerStacks++;return d(e,t,n,!1,r?Error(`react-stack-top-frame`):F,r?M(i(e)):I)},e.jsxs=function(e,t,n){var r=1e4>k.recentlyCreatedOwnerStacks++;return d(e,t,n,!0,r?Error(`react-stack-top-frame`):F,r?M(i(e)):I)}})()})),h=o(((e,t)=>{process.env.NODE_ENV===`production`?t.exports=p():t.exports=m()}))(),g=960,_=640,v=18,y=`okve-arrowhead`;function b(e){let[t,n]=(0,l.useState)({width:g,height:_});return(0,l.useEffect)(()=>{let t=e.current;if(!t)return;let r=()=>{let{width:e,height:r}=t.getBoundingClientRect();n({width:e||g,height:r||_})};r();let i=new ResizeObserver(()=>{r()});return i.observe(t),()=>{i.disconnect()}},[e]),t}function x(e,t){(0,l.useEffect)(()=>{let n=e.current,r=t.current;if(!n||!r)return;let i=u.zoom().scaleExtent([.5,4]).on(`zoom`,e=>{u.select(r).attr(`transform`,e.transform.toString())}),a=u.select(n);return a.call(i),()=>{a.on(`.zoom`,null)}},[t,e])}function S(e,t,n){let[r,i]=(0,l.useState)({nodes:[],edges:[]});return(0,l.useEffect)(()=>{if(e.nodes.length===0){i({nodes:[],edges:[]});return}let r=d(e.nodes,t,n).map(e=>({...e})),a=e.edges.map(e=>({...e})),o=u.forceSimulation(r).force(`link`,u.forceLink(a).id(e=>e.id).distance(e=>e.weight?Math.max(100,180-e.weight*16):170).strength(.2)).force(`charge`,u.forceManyBody().strength(-360)).force(`center`,u.forceCenter(t/2,n/2)).force(`collision`,u.forceCollide(v*2.2)),s=()=>{i({nodes:r.map(e=>({...e})),edges:a.map(e=>({...e}))})};return o.on(`tick`,s),s(),()=>{o.stop()}},[e,n,t]),r}function C(...e){return e.filter(Boolean).join(` `)}function w({data:e,width:t=`100%`,height:n=640,onNodeClick:r,onEdgeClick:i}){let a=(0,l.useRef)(null),o=(0,l.useRef)(null),s=(0,l.useRef)(null),[c,u]=(0,l.useState)(null),{width:d,height:p}=b(a),m=S(e,d,p),g=(0,l.useMemo)(()=>f(e,c),[e,c]),_=(0,l.useMemo)(()=>new Map(e.nodes.map(e=>[e.id,e])),[e.nodes]),w=(0,l.useMemo)(()=>new Map(e.edges.map(e=>[e.id,e])),[e.edges]);return x(o,s),(0,h.jsx)(`div`,{ref:a,className:`okve-graph`,style:{width:t,height:n},children:(0,h.jsxs)(`svg`,{ref:o,className:`okve-graph__svg`,width:`100%`,height:`100%`,viewBox:`0 0 ${d} ${p}`,preserveAspectRatio:`xMidYMid meet`,role:`img`,"aria-label":`Interactive knowledge graph`,children:[(0,h.jsx)(`defs`,{children:(0,h.jsx)(`marker`,{id:y,markerWidth:`10`,markerHeight:`10`,refX:`8`,refY:`5`,orient:`auto`,markerUnits:`strokeWidth`,children:(0,h.jsx)(`path`,{d:`M 0 0 L 10 5 L 0 10 z`})})}),(0,h.jsxs)(`g`,{ref:s,className:`okve-graph__content`,children:[m.edges.map(e=>{let t=typeof e.source==`string`?e.source:e.source.id,n=typeof e.target==`string`?e.target:e.target.id,r=m.nodes.find(e=>e.id===t),a=m.nodes.find(e=>e.id===n);if(!r||!a)return null;let o=c?g.highlightedEdgeIds.has(e.id):!0;return(0,h.jsx)(`line`,{className:C(`okve-edge`,o&&`okve-edge--highlighted`,(c?!o:!1)&&`okve-edge--dimmed`),x1:r.x??0,y1:r.y??0,x2:a.x??0,y2:a.y??0,strokeWidth:e.weight?1.5+Math.min(e.weight,4)*.75:1.5,markerEnd:e.directed?`url(#${y})`:void 0,onClick:()=>{i?.(w.get(e.id)??e)}},e.id)}),m.nodes.map(e=>{let t=_.get(e.id)??e,n=c?g.highlightedNodeIds.has(e.id):!0,i=c?!n:!1;return(0,h.jsxs)(`g`,{className:C(`okve-node-group`,i&&`okve-node-group--dimmed`),transform:`translate(${e.x??0}, ${e.y??0})`,onMouseEnter:()=>{u(e.id)},onMouseLeave:()=>{u(null)},onClick:()=>{r?.(t)},children:[(0,h.jsx)(`circle`,{r:v,className:C(`okve-node`,c===e.id&&`okve-node--hovered`,i&&`okve-node--dimmed`)}),(0,h.jsx)(`text`,{className:C(`okve-label`,c===e.id&&`okve-label--hovered`,i&&`okve-label--dimmed`),x:v+10,y:0,dominantBaseline:`middle`,children:t.label}),(0,h.jsx)(`title`,{children:t.label})]},e.id)})]})]})})}exports.KnowledgeGraph=w;
|
package/dist/okve.css
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
.okve-graph{color:#e2e8f0;background:radial-gradient(circle at top,#4f8ef738,#0000 36%),linear-gradient(#0f1117 0%,#0b0d12 100%);border-radius:16px;position:relative;overflow:hidden;box-shadow:0 24px 80px #01040c73}.okve-graph__svg{display:block}.okve-graph__content{cursor:grab}.okve-graph__content:active{cursor:grabbing}.okve-edge{stroke:var(--okve-edge-color,#4a5568);stroke-linecap:round;opacity:.85;transition:stroke .16s,opacity .16s}.okve-edge--highlighted{stroke:var(--okve-edge-highlight-color,#f7c94f);opacity:1}.okve-edge--dimmed{opacity:.12}.okve-node{fill:var(--okve-node-color,#4f8ef7);stroke:#ffffff1a;stroke-width:1px;cursor:pointer;transition:fill .16s,transform .16s,opacity .16s}.okve-node--hovered{fill:var(--okve-node-hover-color,#f7c94f)}.okve-node--dimmed{opacity:.15}.okve-label{fill:#e2e8f0;letter-spacing:.01em;pointer-events:none;-webkit-user-select:none;user-select:none;font-size:12px;font-weight:600}.okve-label--hovered{fill:#fff2bf}.okve-label--dimmed{opacity:.2}.okve-node-group{transition:opacity .16s}.okve-node-group--dimmed{opacity:.15}
|
|
2
|
+
/*$vite$:1*/
|
package/dist/okve.js
ADDED
|
@@ -0,0 +1,361 @@
|
|
|
1
|
+
import { useEffect as e, useMemo as t, useRef as n, useState as r } from "react";
|
|
2
|
+
import * as i from "d3";
|
|
3
|
+
//#region \0rolldown/runtime.js
|
|
4
|
+
var a = (e, t) => () => (t || e((t = { exports: {} }).exports, t), t.exports), o = /* @__PURE__ */ ((e) => typeof require < "u" ? require : typeof Proxy < "u" ? new Proxy(e, { get: (e, t) => (typeof require < "u" ? require : e)[t] }) : e)(function(e) {
|
|
5
|
+
if (typeof require < "u") return require.apply(this, arguments);
|
|
6
|
+
throw Error("Calling `require` for \"" + e + "\" in an environment that doesn't expose the `require` function. See https://rolldown.rs/in-depth/bundling-cjs#require-external-modules for more details.");
|
|
7
|
+
});
|
|
8
|
+
//#endregion
|
|
9
|
+
//#region src/utils/graphLayout.ts
|
|
10
|
+
function s(e, t, n) {
|
|
11
|
+
let r = Math.max(e.length, 1), i = Math.max(Math.min(t, n) * .28, 120), a = t / 2, o = n / 2;
|
|
12
|
+
return e.map((e, t) => {
|
|
13
|
+
let n = t / r * Math.PI * 2 - Math.PI / 2;
|
|
14
|
+
return {
|
|
15
|
+
...e,
|
|
16
|
+
x: a + Math.cos(n) * i,
|
|
17
|
+
y: o + Math.sin(n) * i,
|
|
18
|
+
vx: 0,
|
|
19
|
+
vy: 0
|
|
20
|
+
};
|
|
21
|
+
});
|
|
22
|
+
}
|
|
23
|
+
function c(e, t) {
|
|
24
|
+
let n = /* @__PURE__ */ new Set(), r = /* @__PURE__ */ new Set();
|
|
25
|
+
return t ? (n.add(t), e.edges.forEach((e) => {
|
|
26
|
+
(e.source === t || e.target === t) && (r.add(e.id), n.add(e.source), n.add(e.target));
|
|
27
|
+
}), {
|
|
28
|
+
highlightedNodeIds: n,
|
|
29
|
+
highlightedEdgeIds: r
|
|
30
|
+
}) : (e.nodes.forEach((e) => n.add(e.id)), e.edges.forEach((e) => r.add(e.id)), {
|
|
31
|
+
highlightedNodeIds: n,
|
|
32
|
+
highlightedEdgeIds: r
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
//#endregion
|
|
36
|
+
//#region ../../node_modules/react/cjs/react-jsx-runtime.production.js
|
|
37
|
+
var l = /* @__PURE__ */ a(((e) => {
|
|
38
|
+
var t = Symbol.for("react.transitional.element"), n = Symbol.for("react.fragment");
|
|
39
|
+
function r(e, n, r) {
|
|
40
|
+
var i = null;
|
|
41
|
+
if (r !== void 0 && (i = "" + r), n.key !== void 0 && (i = "" + n.key), "key" in n) for (var a in r = {}, n) a !== "key" && (r[a] = n[a]);
|
|
42
|
+
else r = n;
|
|
43
|
+
return n = r.ref, {
|
|
44
|
+
$$typeof: t,
|
|
45
|
+
type: e,
|
|
46
|
+
key: i,
|
|
47
|
+
ref: n === void 0 ? null : n,
|
|
48
|
+
props: r
|
|
49
|
+
};
|
|
50
|
+
}
|
|
51
|
+
e.Fragment = n, e.jsx = r, e.jsxs = r;
|
|
52
|
+
})), u = /* @__PURE__ */ a(((e) => {
|
|
53
|
+
process.env.NODE_ENV !== "production" && (function() {
|
|
54
|
+
function t(e) {
|
|
55
|
+
if (e == null) return null;
|
|
56
|
+
if (typeof e == "function") return e.$$typeof === k ? null : e.displayName || e.name || null;
|
|
57
|
+
if (typeof e == "string") return e;
|
|
58
|
+
switch (e) {
|
|
59
|
+
case v: return "Fragment";
|
|
60
|
+
case b: return "Profiler";
|
|
61
|
+
case y: return "StrictMode";
|
|
62
|
+
case w: return "Suspense";
|
|
63
|
+
case T: return "SuspenseList";
|
|
64
|
+
case O: return "Activity";
|
|
65
|
+
}
|
|
66
|
+
if (typeof e == "object") switch (typeof e.tag == "number" && console.error("Received an unexpected object in getComponentNameFromType(). This is likely a bug in React. Please file an issue."), e.$$typeof) {
|
|
67
|
+
case _: return "Portal";
|
|
68
|
+
case S: return e.displayName || "Context";
|
|
69
|
+
case x: return (e._context.displayName || "Context") + ".Consumer";
|
|
70
|
+
case C:
|
|
71
|
+
var n = e.render;
|
|
72
|
+
return e = e.displayName, e ||= (e = n.displayName || n.name || "", e === "" ? "ForwardRef" : "ForwardRef(" + e + ")"), e;
|
|
73
|
+
case E: return n = e.displayName || null, n === null ? t(e.type) || "Memo" : n;
|
|
74
|
+
case D:
|
|
75
|
+
n = e._payload, e = e._init;
|
|
76
|
+
try {
|
|
77
|
+
return t(e(n));
|
|
78
|
+
} catch {}
|
|
79
|
+
}
|
|
80
|
+
return null;
|
|
81
|
+
}
|
|
82
|
+
function n(e) {
|
|
83
|
+
return "" + e;
|
|
84
|
+
}
|
|
85
|
+
function r(e) {
|
|
86
|
+
try {
|
|
87
|
+
n(e);
|
|
88
|
+
var t = !1;
|
|
89
|
+
} catch {
|
|
90
|
+
t = !0;
|
|
91
|
+
}
|
|
92
|
+
if (t) {
|
|
93
|
+
t = console;
|
|
94
|
+
var r = t.error, i = typeof Symbol == "function" && Symbol.toStringTag && e[Symbol.toStringTag] || e.constructor.name || "Object";
|
|
95
|
+
return r.call(t, "The provided key is an unsupported type %s. This value must be coerced to a string before using it here.", i), n(e);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
function i(e) {
|
|
99
|
+
if (e === v) return "<>";
|
|
100
|
+
if (typeof e == "object" && e && e.$$typeof === D) return "<...>";
|
|
101
|
+
try {
|
|
102
|
+
var n = t(e);
|
|
103
|
+
return n ? "<" + n + ">" : "<...>";
|
|
104
|
+
} catch {
|
|
105
|
+
return "<...>";
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
function a() {
|
|
109
|
+
var e = A.A;
|
|
110
|
+
return e === null ? null : e.getOwner();
|
|
111
|
+
}
|
|
112
|
+
function s() {
|
|
113
|
+
return Error("react-stack-top-frame");
|
|
114
|
+
}
|
|
115
|
+
function c(e) {
|
|
116
|
+
if (j.call(e, "key")) {
|
|
117
|
+
var t = Object.getOwnPropertyDescriptor(e, "key").get;
|
|
118
|
+
if (t && t.isReactWarning) return !1;
|
|
119
|
+
}
|
|
120
|
+
return e.key !== void 0;
|
|
121
|
+
}
|
|
122
|
+
function l(e, t) {
|
|
123
|
+
function n() {
|
|
124
|
+
P || (P = !0, console.error("%s: `key` is not a prop. Trying to access it will result in `undefined` being returned. If you need to access the same value within the child component, you should pass it as a different prop. (https://react.dev/link/special-props)", t));
|
|
125
|
+
}
|
|
126
|
+
n.isReactWarning = !0, Object.defineProperty(e, "key", {
|
|
127
|
+
get: n,
|
|
128
|
+
configurable: !0
|
|
129
|
+
});
|
|
130
|
+
}
|
|
131
|
+
function u() {
|
|
132
|
+
var e = t(this.type);
|
|
133
|
+
return F[e] || (F[e] = !0, console.error("Accessing element.ref was removed in React 19. ref is now a regular prop. It will be removed from the JSX Element type in a future release.")), e = this.props.ref, e === void 0 ? null : e;
|
|
134
|
+
}
|
|
135
|
+
function d(e, t, n, r, i, a) {
|
|
136
|
+
var o = n.ref;
|
|
137
|
+
return e = {
|
|
138
|
+
$$typeof: g,
|
|
139
|
+
type: e,
|
|
140
|
+
key: t,
|
|
141
|
+
props: n,
|
|
142
|
+
_owner: r
|
|
143
|
+
}, (o === void 0 ? null : o) === null ? Object.defineProperty(e, "ref", {
|
|
144
|
+
enumerable: !1,
|
|
145
|
+
value: null
|
|
146
|
+
}) : Object.defineProperty(e, "ref", {
|
|
147
|
+
enumerable: !1,
|
|
148
|
+
get: u
|
|
149
|
+
}), e._store = {}, Object.defineProperty(e._store, "validated", {
|
|
150
|
+
configurable: !1,
|
|
151
|
+
enumerable: !1,
|
|
152
|
+
writable: !0,
|
|
153
|
+
value: 0
|
|
154
|
+
}), Object.defineProperty(e, "_debugInfo", {
|
|
155
|
+
configurable: !1,
|
|
156
|
+
enumerable: !1,
|
|
157
|
+
writable: !0,
|
|
158
|
+
value: null
|
|
159
|
+
}), Object.defineProperty(e, "_debugStack", {
|
|
160
|
+
configurable: !1,
|
|
161
|
+
enumerable: !1,
|
|
162
|
+
writable: !0,
|
|
163
|
+
value: i
|
|
164
|
+
}), Object.defineProperty(e, "_debugTask", {
|
|
165
|
+
configurable: !1,
|
|
166
|
+
enumerable: !1,
|
|
167
|
+
writable: !0,
|
|
168
|
+
value: a
|
|
169
|
+
}), Object.freeze && (Object.freeze(e.props), Object.freeze(e)), e;
|
|
170
|
+
}
|
|
171
|
+
function f(e, n, i, o, s, u) {
|
|
172
|
+
var f = n.children;
|
|
173
|
+
if (f !== void 0) if (o) if (M(f)) {
|
|
174
|
+
for (o = 0; o < f.length; o++) p(f[o]);
|
|
175
|
+
Object.freeze && Object.freeze(f);
|
|
176
|
+
} else console.error("React.jsx: Static children should always be an array. You are likely explicitly calling React.jsxs or React.jsxDEV. Use the Babel transform instead.");
|
|
177
|
+
else p(f);
|
|
178
|
+
if (j.call(n, "key")) {
|
|
179
|
+
f = t(e);
|
|
180
|
+
var m = Object.keys(n).filter(function(e) {
|
|
181
|
+
return e !== "key";
|
|
182
|
+
});
|
|
183
|
+
o = 0 < m.length ? "{key: someKey, " + m.join(": ..., ") + ": ...}" : "{key: someKey}", R[f + o] || (m = 0 < m.length ? "{" + m.join(": ..., ") + ": ...}" : "{}", console.error("A props object containing a \"key\" prop is being spread into JSX:\n let props = %s;\n <%s {...props} />\nReact keys must be passed directly to JSX without using spread:\n let props = %s;\n <%s key={someKey} {...props} />", o, f, m, f), R[f + o] = !0);
|
|
184
|
+
}
|
|
185
|
+
if (f = null, i !== void 0 && (r(i), f = "" + i), c(n) && (r(n.key), f = "" + n.key), "key" in n) for (var h in i = {}, n) h !== "key" && (i[h] = n[h]);
|
|
186
|
+
else i = n;
|
|
187
|
+
return f && l(i, typeof e == "function" ? e.displayName || e.name || "Unknown" : e), d(e, f, i, a(), s, u);
|
|
188
|
+
}
|
|
189
|
+
function p(e) {
|
|
190
|
+
m(e) ? e._store && (e._store.validated = 1) : typeof e == "object" && e && e.$$typeof === D && (e._payload.status === "fulfilled" ? m(e._payload.value) && e._payload.value._store && (e._payload.value._store.validated = 1) : e._store && (e._store.validated = 1));
|
|
191
|
+
}
|
|
192
|
+
function m(e) {
|
|
193
|
+
return typeof e == "object" && !!e && e.$$typeof === g;
|
|
194
|
+
}
|
|
195
|
+
var h = o("react"), g = Symbol.for("react.transitional.element"), _ = Symbol.for("react.portal"), v = Symbol.for("react.fragment"), y = Symbol.for("react.strict_mode"), b = Symbol.for("react.profiler"), x = Symbol.for("react.consumer"), S = Symbol.for("react.context"), C = Symbol.for("react.forward_ref"), w = Symbol.for("react.suspense"), T = Symbol.for("react.suspense_list"), E = Symbol.for("react.memo"), D = Symbol.for("react.lazy"), O = Symbol.for("react.activity"), k = Symbol.for("react.client.reference"), A = h.__CLIENT_INTERNALS_DO_NOT_USE_OR_WARN_USERS_THEY_CANNOT_UPGRADE, j = Object.prototype.hasOwnProperty, M = Array.isArray, N = console.createTask ? console.createTask : function() {
|
|
196
|
+
return null;
|
|
197
|
+
};
|
|
198
|
+
h = { react_stack_bottom_frame: function(e) {
|
|
199
|
+
return e();
|
|
200
|
+
} };
|
|
201
|
+
var P, F = {}, I = h.react_stack_bottom_frame.bind(h, s)(), L = N(i(s)), R = {};
|
|
202
|
+
e.Fragment = v, e.jsx = function(e, t, n) {
|
|
203
|
+
var r = 1e4 > A.recentlyCreatedOwnerStacks++;
|
|
204
|
+
return f(e, t, n, !1, r ? Error("react-stack-top-frame") : I, r ? N(i(e)) : L);
|
|
205
|
+
}, e.jsxs = function(e, t, n) {
|
|
206
|
+
var r = 1e4 > A.recentlyCreatedOwnerStacks++;
|
|
207
|
+
return f(e, t, n, !0, r ? Error("react-stack-top-frame") : I, r ? N(i(e)) : L);
|
|
208
|
+
};
|
|
209
|
+
})();
|
|
210
|
+
})), d = (/* @__PURE__ */ a(((e, t) => {
|
|
211
|
+
process.env.NODE_ENV === "production" ? t.exports = l() : t.exports = u();
|
|
212
|
+
})))(), f = 960, p = 640, m = 18, h = "okve-arrowhead";
|
|
213
|
+
function g(t) {
|
|
214
|
+
let [n, i] = r({
|
|
215
|
+
width: f,
|
|
216
|
+
height: p
|
|
217
|
+
});
|
|
218
|
+
return e(() => {
|
|
219
|
+
let e = t.current;
|
|
220
|
+
if (!e) return;
|
|
221
|
+
let n = () => {
|
|
222
|
+
let { width: t, height: n } = e.getBoundingClientRect();
|
|
223
|
+
i({
|
|
224
|
+
width: t || f,
|
|
225
|
+
height: n || p
|
|
226
|
+
});
|
|
227
|
+
};
|
|
228
|
+
n();
|
|
229
|
+
let r = new ResizeObserver(() => {
|
|
230
|
+
n();
|
|
231
|
+
});
|
|
232
|
+
return r.observe(e), () => {
|
|
233
|
+
r.disconnect();
|
|
234
|
+
};
|
|
235
|
+
}, [t]), n;
|
|
236
|
+
}
|
|
237
|
+
function _(t, n) {
|
|
238
|
+
e(() => {
|
|
239
|
+
let e = t.current, r = n.current;
|
|
240
|
+
if (!e || !r) return;
|
|
241
|
+
let a = i.zoom().scaleExtent([.5, 4]).on("zoom", (e) => {
|
|
242
|
+
i.select(r).attr("transform", e.transform.toString());
|
|
243
|
+
}), o = i.select(e);
|
|
244
|
+
return o.call(a), () => {
|
|
245
|
+
o.on(".zoom", null);
|
|
246
|
+
};
|
|
247
|
+
}, [n, t]);
|
|
248
|
+
}
|
|
249
|
+
function v(t, n, a) {
|
|
250
|
+
let [o, c] = r({
|
|
251
|
+
nodes: [],
|
|
252
|
+
edges: []
|
|
253
|
+
});
|
|
254
|
+
return e(() => {
|
|
255
|
+
if (t.nodes.length === 0) {
|
|
256
|
+
c({
|
|
257
|
+
nodes: [],
|
|
258
|
+
edges: []
|
|
259
|
+
});
|
|
260
|
+
return;
|
|
261
|
+
}
|
|
262
|
+
let e = s(t.nodes, n, a).map((e) => ({ ...e })), r = t.edges.map((e) => ({ ...e })), o = i.forceSimulation(e).force("link", i.forceLink(r).id((e) => e.id).distance((e) => e.weight ? Math.max(100, 180 - e.weight * 16) : 170).strength(.2)).force("charge", i.forceManyBody().strength(-360)).force("center", i.forceCenter(n / 2, a / 2)).force("collision", i.forceCollide(m * 2.2)), l = () => {
|
|
263
|
+
c({
|
|
264
|
+
nodes: e.map((e) => ({ ...e })),
|
|
265
|
+
edges: r.map((e) => ({ ...e }))
|
|
266
|
+
});
|
|
267
|
+
};
|
|
268
|
+
return o.on("tick", l), l(), () => {
|
|
269
|
+
o.stop();
|
|
270
|
+
};
|
|
271
|
+
}, [
|
|
272
|
+
t,
|
|
273
|
+
a,
|
|
274
|
+
n
|
|
275
|
+
]), o;
|
|
276
|
+
}
|
|
277
|
+
function y(...e) {
|
|
278
|
+
return e.filter(Boolean).join(" ");
|
|
279
|
+
}
|
|
280
|
+
function b({ data: e, width: i = "100%", height: a = 640, onNodeClick: o, onEdgeClick: s }) {
|
|
281
|
+
let l = n(null), u = n(null), f = n(null), [p, b] = r(null), { width: x, height: S } = g(l), C = v(e, x, S), w = t(() => c(e, p), [e, p]), T = t(() => new Map(e.nodes.map((e) => [e.id, e])), [e.nodes]), E = t(() => new Map(e.edges.map((e) => [e.id, e])), [e.edges]);
|
|
282
|
+
return _(u, f), /* @__PURE__ */ (0, d.jsx)("div", {
|
|
283
|
+
ref: l,
|
|
284
|
+
className: "okve-graph",
|
|
285
|
+
style: {
|
|
286
|
+
width: i,
|
|
287
|
+
height: a
|
|
288
|
+
},
|
|
289
|
+
children: /* @__PURE__ */ (0, d.jsxs)("svg", {
|
|
290
|
+
ref: u,
|
|
291
|
+
className: "okve-graph__svg",
|
|
292
|
+
width: "100%",
|
|
293
|
+
height: "100%",
|
|
294
|
+
viewBox: `0 0 ${x} ${S}`,
|
|
295
|
+
preserveAspectRatio: "xMidYMid meet",
|
|
296
|
+
role: "img",
|
|
297
|
+
"aria-label": "Interactive knowledge graph",
|
|
298
|
+
children: [/* @__PURE__ */ (0, d.jsx)("defs", { children: /* @__PURE__ */ (0, d.jsx)("marker", {
|
|
299
|
+
id: h,
|
|
300
|
+
markerWidth: "10",
|
|
301
|
+
markerHeight: "10",
|
|
302
|
+
refX: "8",
|
|
303
|
+
refY: "5",
|
|
304
|
+
orient: "auto",
|
|
305
|
+
markerUnits: "strokeWidth",
|
|
306
|
+
children: /* @__PURE__ */ (0, d.jsx)("path", { d: "M 0 0 L 10 5 L 0 10 z" })
|
|
307
|
+
}) }), /* @__PURE__ */ (0, d.jsxs)("g", {
|
|
308
|
+
ref: f,
|
|
309
|
+
className: "okve-graph__content",
|
|
310
|
+
children: [C.edges.map((e) => {
|
|
311
|
+
let t = typeof e.source == "string" ? e.source : e.source.id, n = typeof e.target == "string" ? e.target : e.target.id, r = C.nodes.find((e) => e.id === t), i = C.nodes.find((e) => e.id === n);
|
|
312
|
+
if (!r || !i) return null;
|
|
313
|
+
let a = p ? w.highlightedEdgeIds.has(e.id) : !0;
|
|
314
|
+
return /* @__PURE__ */ (0, d.jsx)("line", {
|
|
315
|
+
className: y("okve-edge", a && "okve-edge--highlighted", (p ? !a : !1) && "okve-edge--dimmed"),
|
|
316
|
+
x1: r.x ?? 0,
|
|
317
|
+
y1: r.y ?? 0,
|
|
318
|
+
x2: i.x ?? 0,
|
|
319
|
+
y2: i.y ?? 0,
|
|
320
|
+
strokeWidth: e.weight ? 1.5 + Math.min(e.weight, 4) * .75 : 1.5,
|
|
321
|
+
markerEnd: e.directed ? `url(#${h})` : void 0,
|
|
322
|
+
onClick: () => {
|
|
323
|
+
s?.(E.get(e.id) ?? e);
|
|
324
|
+
}
|
|
325
|
+
}, e.id);
|
|
326
|
+
}), C.nodes.map((e) => {
|
|
327
|
+
let t = T.get(e.id) ?? e, n = p ? w.highlightedNodeIds.has(e.id) : !0, r = p ? !n : !1;
|
|
328
|
+
return /* @__PURE__ */ (0, d.jsxs)("g", {
|
|
329
|
+
className: y("okve-node-group", r && "okve-node-group--dimmed"),
|
|
330
|
+
transform: `translate(${e.x ?? 0}, ${e.y ?? 0})`,
|
|
331
|
+
onMouseEnter: () => {
|
|
332
|
+
b(e.id);
|
|
333
|
+
},
|
|
334
|
+
onMouseLeave: () => {
|
|
335
|
+
b(null);
|
|
336
|
+
},
|
|
337
|
+
onClick: () => {
|
|
338
|
+
o?.(t);
|
|
339
|
+
},
|
|
340
|
+
children: [
|
|
341
|
+
/* @__PURE__ */ (0, d.jsx)("circle", {
|
|
342
|
+
r: m,
|
|
343
|
+
className: y("okve-node", p === e.id && "okve-node--hovered", r && "okve-node--dimmed")
|
|
344
|
+
}),
|
|
345
|
+
/* @__PURE__ */ (0, d.jsx)("text", {
|
|
346
|
+
className: y("okve-label", p === e.id && "okve-label--hovered", r && "okve-label--dimmed"),
|
|
347
|
+
x: m + 10,
|
|
348
|
+
y: 0,
|
|
349
|
+
dominantBaseline: "middle",
|
|
350
|
+
children: t.label
|
|
351
|
+
}),
|
|
352
|
+
/* @__PURE__ */ (0, d.jsx)("title", { children: t.label })
|
|
353
|
+
]
|
|
354
|
+
}, e.id);
|
|
355
|
+
})]
|
|
356
|
+
})]
|
|
357
|
+
})
|
|
358
|
+
});
|
|
359
|
+
}
|
|
360
|
+
//#endregion
|
|
361
|
+
export { b as KnowledgeGraph };
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export interface GraphNode {
|
|
2
|
+
id: string;
|
|
3
|
+
label: string;
|
|
4
|
+
group?: string;
|
|
5
|
+
metadata?: Record<string, unknown>;
|
|
6
|
+
}
|
|
7
|
+
export interface GraphEdge {
|
|
8
|
+
id: string;
|
|
9
|
+
source: string;
|
|
10
|
+
target: string;
|
|
11
|
+
directed?: boolean;
|
|
12
|
+
weight?: number;
|
|
13
|
+
}
|
|
14
|
+
export interface GraphData {
|
|
15
|
+
nodes: GraphNode[];
|
|
16
|
+
edges: GraphEdge[];
|
|
17
|
+
}
|
|
18
|
+
export interface KnowledgeGraphProps {
|
|
19
|
+
data: GraphData;
|
|
20
|
+
width?: number | string;
|
|
21
|
+
height?: number | string;
|
|
22
|
+
onNodeClick?: (node: GraphNode) => void;
|
|
23
|
+
onEdgeClick?: (edge: GraphEdge) => void;
|
|
24
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { SimulationNodeDatum } from 'd3';
|
|
2
|
+
import { GraphData, GraphNode } from '../types';
|
|
3
|
+
export type PositionedGraphNode = GraphNode & SimulationNodeDatum;
|
|
4
|
+
export interface HighlightState {
|
|
5
|
+
highlightedNodeIds: Set<string>;
|
|
6
|
+
highlightedEdgeIds: Set<string>;
|
|
7
|
+
}
|
|
8
|
+
export declare function seedNodePositions(nodes: GraphNode[], width: number, height: number): PositionedGraphNode[];
|
|
9
|
+
export declare function buildHighlightState(data: GraphData, hoveredNodeId: string | null): HighlightState;
|
package/package.json
ADDED
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@biki-dev/okve",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"private": false,
|
|
5
|
+
"type": "module",
|
|
6
|
+
"description": "Open Knowledge Visualization Engine, a reusable React knowledge graph component.",
|
|
7
|
+
"main": "./dist/okve.cjs",
|
|
8
|
+
"module": "./dist/okve.js",
|
|
9
|
+
"types": "./dist/index.d.ts",
|
|
10
|
+
"exports": {
|
|
11
|
+
".": {
|
|
12
|
+
"types": "./dist/index.d.ts",
|
|
13
|
+
"import": "./dist/okve.js",
|
|
14
|
+
"require": "./dist/okve.cjs"
|
|
15
|
+
}
|
|
16
|
+
},
|
|
17
|
+
"publishConfig": {
|
|
18
|
+
"access": "public"
|
|
19
|
+
},
|
|
20
|
+
"files": ["dist"],
|
|
21
|
+
"scripts": {
|
|
22
|
+
"build": "vite build",
|
|
23
|
+
"dev": "vite",
|
|
24
|
+
"prepublishOnly": "npm run build"
|
|
25
|
+
},
|
|
26
|
+
"dependencies": {
|
|
27
|
+
"d3": "^7.9.0"
|
|
28
|
+
},
|
|
29
|
+
"peerDependencies": {
|
|
30
|
+
"react": "^19.0.0",
|
|
31
|
+
"react-dom": "^19.0.0"
|
|
32
|
+
},
|
|
33
|
+
"devDependencies": {
|
|
34
|
+
"@types/d3": "^7.4.3",
|
|
35
|
+
"@types/react": "^19.0.0",
|
|
36
|
+
"@types/react-dom": "^19.0.0",
|
|
37
|
+
"@vitejs/plugin-react": "^6.0.1",
|
|
38
|
+
"typescript": "^5.9.3",
|
|
39
|
+
"vite": "^8.0.1",
|
|
40
|
+
"vite-plugin-dts": "^4.5.4"
|
|
41
|
+
}
|
|
42
|
+
}
|