@almadar/ui 2.17.0 → 2.19.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/index.cjs +1004 -1000
- package/dist/components/index.js +143 -139
- package/dist/components/organisms/game/three/index.cjs +121 -123
- package/dist/components/organisms/game/three/index.js +4 -6
- package/dist/hooks/index.cjs +221 -223
- package/dist/hooks/index.js +3 -5
- package/dist/marketing/index.cjs +8 -2
- package/dist/marketing/index.js +8 -2
- package/dist/providers/EventBusProvider.d.ts +2 -8
- package/dist/providers/index.cjs +5 -4
- package/dist/providers/index.js +4 -3
- package/dist/runtime/OrbPreview.d.ts +39 -0
- package/dist/runtime/index.cjs +139 -2
- package/dist/runtime/index.d.ts +1 -0
- package/dist/runtime/index.js +138 -2
- package/package.json +1 -1
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var React7 = require('react');
|
|
4
4
|
var fiber = require('@react-three/fiber');
|
|
5
5
|
var THREE6 = require('three');
|
|
6
6
|
var jsxRuntime = require('react/jsx-runtime');
|
|
@@ -9,6 +9,7 @@ var GLTFLoader = require('three/examples/jsm/loaders/GLTFLoader');
|
|
|
9
9
|
var OrbitControls_js = require('three/examples/jsm/controls/OrbitControls.js');
|
|
10
10
|
var GLTFLoader_js = require('three/examples/jsm/loaders/GLTFLoader.js');
|
|
11
11
|
var OBJLoader_js = require('three/examples/jsm/loaders/OBJLoader.js');
|
|
12
|
+
var providers = require('@almadar/ui/providers');
|
|
12
13
|
var clsx = require('clsx');
|
|
13
14
|
var tailwindMerge = require('tailwind-merge');
|
|
14
15
|
|
|
@@ -32,7 +33,7 @@ function _interopNamespace(e) {
|
|
|
32
33
|
return Object.freeze(n);
|
|
33
34
|
}
|
|
34
35
|
|
|
35
|
-
var
|
|
36
|
+
var React7__default = /*#__PURE__*/_interopDefault(React7);
|
|
36
37
|
var THREE6__namespace = /*#__PURE__*/_interopNamespace(THREE6);
|
|
37
38
|
|
|
38
39
|
var __defProp = Object.defineProperty;
|
|
@@ -40,8 +41,8 @@ var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { en
|
|
|
40
41
|
var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
|
|
41
42
|
function Scene3D({ background = "#1a1a2e", fog, children }) {
|
|
42
43
|
const { scene } = fiber.useThree();
|
|
43
|
-
const initializedRef =
|
|
44
|
-
|
|
44
|
+
const initializedRef = React7.useRef(false);
|
|
45
|
+
React7.useEffect(() => {
|
|
45
46
|
if (initializedRef.current) return;
|
|
46
47
|
initializedRef.current = true;
|
|
47
48
|
if (background.startsWith("#") || background.startsWith("rgb")) {
|
|
@@ -62,7 +63,7 @@ function Scene3D({ background = "#1a1a2e", fog, children }) {
|
|
|
62
63
|
}, [scene, background, fog]);
|
|
63
64
|
return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children });
|
|
64
65
|
}
|
|
65
|
-
var Camera3D =
|
|
66
|
+
var Camera3D = React7.forwardRef(
|
|
66
67
|
({
|
|
67
68
|
mode = "isometric",
|
|
68
69
|
position = [10, 10, 10],
|
|
@@ -75,10 +76,10 @@ var Camera3D = React8.forwardRef(
|
|
|
75
76
|
onChange
|
|
76
77
|
}, ref) => {
|
|
77
78
|
const { camera, set, viewport } = fiber.useThree();
|
|
78
|
-
const controlsRef =
|
|
79
|
-
const initialPosition =
|
|
80
|
-
const initialTarget =
|
|
81
|
-
|
|
79
|
+
const controlsRef = React7.useRef(null);
|
|
80
|
+
const initialPosition = React7.useRef(new THREE6__namespace.Vector3(...position));
|
|
81
|
+
const initialTarget = React7.useRef(new THREE6__namespace.Vector3(...target));
|
|
82
|
+
React7.useEffect(() => {
|
|
82
83
|
let newCamera;
|
|
83
84
|
if (mode === "isometric") {
|
|
84
85
|
const aspect = viewport.aspect;
|
|
@@ -109,7 +110,7 @@ var Camera3D = React8.forwardRef(
|
|
|
109
110
|
onChange(camera);
|
|
110
111
|
}
|
|
111
112
|
});
|
|
112
|
-
|
|
113
|
+
React7.useImperativeHandle(ref, () => ({
|
|
113
114
|
getCamera: () => camera,
|
|
114
115
|
setPosition: (x, y, z) => {
|
|
115
116
|
camera.position.set(x, y, z);
|
|
@@ -250,7 +251,7 @@ function Canvas3DLoadingState({
|
|
|
250
251
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "canvas-3d-loading__background", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "bg__grid" }) })
|
|
251
252
|
] });
|
|
252
253
|
}
|
|
253
|
-
var Canvas3DErrorBoundary = class extends
|
|
254
|
+
var Canvas3DErrorBoundary = class extends React7.Component {
|
|
254
255
|
constructor(props) {
|
|
255
256
|
super(props);
|
|
256
257
|
__publicField(this, "handleReset", () => {
|
|
@@ -329,12 +330,12 @@ function detectAssetRoot(modelUrl) {
|
|
|
329
330
|
return modelUrl.substring(0, modelUrl.lastIndexOf("/") + 1);
|
|
330
331
|
}
|
|
331
332
|
function useGLTFModel(url, resourceBasePath) {
|
|
332
|
-
const [state, setState] =
|
|
333
|
+
const [state, setState] = React7.useState({
|
|
333
334
|
model: null,
|
|
334
335
|
isLoading: false,
|
|
335
336
|
error: null
|
|
336
337
|
});
|
|
337
|
-
|
|
338
|
+
React7.useEffect(() => {
|
|
338
339
|
if (!url) {
|
|
339
340
|
setState({ model: null, isLoading: false, error: null });
|
|
340
341
|
return;
|
|
@@ -383,7 +384,7 @@ function ModelLoader({
|
|
|
383
384
|
resourceBasePath
|
|
384
385
|
}) {
|
|
385
386
|
const { model: loadedModel, isLoading, error } = useGLTFModel(url, resourceBasePath);
|
|
386
|
-
const model =
|
|
387
|
+
const model = React7.useMemo(() => {
|
|
387
388
|
if (!loadedModel) return null;
|
|
388
389
|
const cloned = loadedModel.clone();
|
|
389
390
|
cloned.traverse((child) => {
|
|
@@ -394,13 +395,13 @@ function ModelLoader({
|
|
|
394
395
|
});
|
|
395
396
|
return cloned;
|
|
396
397
|
}, [loadedModel, castShadow, receiveShadow]);
|
|
397
|
-
const scaleArray =
|
|
398
|
+
const scaleArray = React7.useMemo(() => {
|
|
398
399
|
if (typeof scale === "number") {
|
|
399
400
|
return [scale, scale, scale];
|
|
400
401
|
}
|
|
401
402
|
return scale;
|
|
402
403
|
}, [scale]);
|
|
403
|
-
const rotationRad =
|
|
404
|
+
const rotationRad = React7.useMemo(() => {
|
|
404
405
|
return [
|
|
405
406
|
rotation[0] * Math.PI / 180,
|
|
406
407
|
rotation[1] * Math.PI / 180,
|
|
@@ -486,8 +487,8 @@ function PhysicsObject3D({
|
|
|
486
487
|
onGroundHit,
|
|
487
488
|
onCollision
|
|
488
489
|
}) {
|
|
489
|
-
const groupRef =
|
|
490
|
-
const physicsStateRef =
|
|
490
|
+
const groupRef = React7.useRef(null);
|
|
491
|
+
const physicsStateRef = React7.useRef({
|
|
491
492
|
id: entityId,
|
|
492
493
|
x: initialPosition[0],
|
|
493
494
|
y: initialPosition[1],
|
|
@@ -504,8 +505,8 @@ function PhysicsObject3D({
|
|
|
504
505
|
mass,
|
|
505
506
|
state: "Active"
|
|
506
507
|
});
|
|
507
|
-
const groundHitRef =
|
|
508
|
-
|
|
508
|
+
const groundHitRef = React7.useRef(false);
|
|
509
|
+
React7.useEffect(() => {
|
|
509
510
|
if (groupRef.current) {
|
|
510
511
|
groupRef.current.position.set(
|
|
511
512
|
initialPosition[0],
|
|
@@ -786,21 +787,21 @@ var DEFAULT_OPTIONS = {
|
|
|
786
787
|
};
|
|
787
788
|
function useThree3(options = {}) {
|
|
788
789
|
const opts = { ...DEFAULT_OPTIONS, ...options };
|
|
789
|
-
const containerRef =
|
|
790
|
-
const canvasRef =
|
|
791
|
-
const rendererRef =
|
|
792
|
-
const sceneRef =
|
|
793
|
-
const cameraRef =
|
|
794
|
-
const controlsRef =
|
|
795
|
-
const gridHelperRef =
|
|
796
|
-
const rafRef =
|
|
797
|
-
const [isReady, setIsReady] =
|
|
798
|
-
const [dimensions, setDimensions] =
|
|
799
|
-
const initialCameraPosition =
|
|
790
|
+
const containerRef = React7.useRef(null);
|
|
791
|
+
const canvasRef = React7.useRef(null);
|
|
792
|
+
const rendererRef = React7.useRef(null);
|
|
793
|
+
const sceneRef = React7.useRef(null);
|
|
794
|
+
const cameraRef = React7.useRef(null);
|
|
795
|
+
const controlsRef = React7.useRef(null);
|
|
796
|
+
const gridHelperRef = React7.useRef(null);
|
|
797
|
+
const rafRef = React7.useRef(0);
|
|
798
|
+
const [isReady, setIsReady] = React7.useState(false);
|
|
799
|
+
const [dimensions, setDimensions] = React7.useState({ width: 0, height: 0 });
|
|
800
|
+
const initialCameraPosition = React7.useMemo(
|
|
800
801
|
() => new THREE6__namespace.Vector3(...opts.cameraPosition),
|
|
801
802
|
[]
|
|
802
803
|
);
|
|
803
|
-
|
|
804
|
+
React7.useEffect(() => {
|
|
804
805
|
if (!containerRef.current) return;
|
|
805
806
|
const container = containerRef.current;
|
|
806
807
|
const { clientWidth, clientHeight } = container;
|
|
@@ -893,7 +894,7 @@ function useThree3(options = {}) {
|
|
|
893
894
|
scene.clear();
|
|
894
895
|
};
|
|
895
896
|
}, []);
|
|
896
|
-
|
|
897
|
+
React7.useEffect(() => {
|
|
897
898
|
if (!cameraRef.current || !containerRef.current) return;
|
|
898
899
|
const container = containerRef.current;
|
|
899
900
|
const { clientWidth, clientHeight } = container;
|
|
@@ -928,20 +929,20 @@ function useThree3(options = {}) {
|
|
|
928
929
|
animate();
|
|
929
930
|
}
|
|
930
931
|
}, [opts.cameraMode]);
|
|
931
|
-
const setCameraPosition =
|
|
932
|
+
const setCameraPosition = React7.useCallback((x, y, z) => {
|
|
932
933
|
if (cameraRef.current) {
|
|
933
934
|
cameraRef.current.position.set(x, y, z);
|
|
934
935
|
controlsRef.current?.update();
|
|
935
936
|
}
|
|
936
937
|
}, []);
|
|
937
|
-
const lookAt =
|
|
938
|
+
const lookAt = React7.useCallback((x, y, z) => {
|
|
938
939
|
if (cameraRef.current) {
|
|
939
940
|
cameraRef.current.lookAt(x, y, z);
|
|
940
941
|
controlsRef.current?.target.set(x, y, z);
|
|
941
942
|
controlsRef.current?.update();
|
|
942
943
|
}
|
|
943
944
|
}, []);
|
|
944
|
-
const resetCamera =
|
|
945
|
+
const resetCamera = React7.useCallback(() => {
|
|
945
946
|
if (cameraRef.current) {
|
|
946
947
|
cameraRef.current.position.copy(initialCameraPosition);
|
|
947
948
|
cameraRef.current.lookAt(0, 0, 0);
|
|
@@ -951,7 +952,7 @@ function useThree3(options = {}) {
|
|
|
951
952
|
}
|
|
952
953
|
}
|
|
953
954
|
}, [initialCameraPosition]);
|
|
954
|
-
const fitView =
|
|
955
|
+
const fitView = React7.useCallback(
|
|
955
956
|
(bounds) => {
|
|
956
957
|
if (!cameraRef.current) return;
|
|
957
958
|
const centerX = (bounds.minX + bounds.maxX) / 2;
|
|
@@ -982,20 +983,20 @@ function useThree3(options = {}) {
|
|
|
982
983
|
}
|
|
983
984
|
function useAssetLoader(options = {}) {
|
|
984
985
|
const { preloadUrls = [], loader: customLoader } = options;
|
|
985
|
-
const loaderRef =
|
|
986
|
-
const [state, setState] =
|
|
986
|
+
const loaderRef = React7.useRef(customLoader || new AssetLoader());
|
|
987
|
+
const [state, setState] = React7.useState({
|
|
987
988
|
isLoading: false,
|
|
988
989
|
progress: 0,
|
|
989
990
|
loaded: 0,
|
|
990
991
|
total: 0,
|
|
991
992
|
errors: []
|
|
992
993
|
});
|
|
993
|
-
|
|
994
|
+
React7.useEffect(() => {
|
|
994
995
|
if (preloadUrls.length > 0) {
|
|
995
996
|
preload(preloadUrls);
|
|
996
997
|
}
|
|
997
998
|
}, []);
|
|
998
|
-
const updateProgress =
|
|
999
|
+
const updateProgress = React7.useCallback((loaded, total) => {
|
|
999
1000
|
setState((prev) => ({
|
|
1000
1001
|
...prev,
|
|
1001
1002
|
loaded,
|
|
@@ -1003,7 +1004,7 @@ function useAssetLoader(options = {}) {
|
|
|
1003
1004
|
progress: total > 0 ? Math.round(loaded / total * 100) : 0
|
|
1004
1005
|
}));
|
|
1005
1006
|
}, []);
|
|
1006
|
-
const loadModel =
|
|
1007
|
+
const loadModel = React7.useCallback(
|
|
1007
1008
|
async (url) => {
|
|
1008
1009
|
setState((prev) => ({ ...prev, isLoading: true }));
|
|
1009
1010
|
try {
|
|
@@ -1026,7 +1027,7 @@ function useAssetLoader(options = {}) {
|
|
|
1026
1027
|
},
|
|
1027
1028
|
[]
|
|
1028
1029
|
);
|
|
1029
|
-
const loadOBJ =
|
|
1030
|
+
const loadOBJ = React7.useCallback(
|
|
1030
1031
|
async (url) => {
|
|
1031
1032
|
setState((prev) => ({ ...prev, isLoading: true }));
|
|
1032
1033
|
try {
|
|
@@ -1049,7 +1050,7 @@ function useAssetLoader(options = {}) {
|
|
|
1049
1050
|
},
|
|
1050
1051
|
[]
|
|
1051
1052
|
);
|
|
1052
|
-
const loadTexture =
|
|
1053
|
+
const loadTexture = React7.useCallback(
|
|
1053
1054
|
async (url) => {
|
|
1054
1055
|
setState((prev) => ({ ...prev, isLoading: true }));
|
|
1055
1056
|
try {
|
|
@@ -1072,7 +1073,7 @@ function useAssetLoader(options = {}) {
|
|
|
1072
1073
|
},
|
|
1073
1074
|
[]
|
|
1074
1075
|
);
|
|
1075
|
-
const preload =
|
|
1076
|
+
const preload = React7.useCallback(
|
|
1076
1077
|
async (urls) => {
|
|
1077
1078
|
setState((prev) => ({
|
|
1078
1079
|
...prev,
|
|
@@ -1111,27 +1112,27 @@ function useAssetLoader(options = {}) {
|
|
|
1111
1112
|
},
|
|
1112
1113
|
[updateProgress]
|
|
1113
1114
|
);
|
|
1114
|
-
const hasModel =
|
|
1115
|
+
const hasModel = React7.useCallback((url) => {
|
|
1115
1116
|
return loaderRef.current.hasModel(url);
|
|
1116
1117
|
}, []);
|
|
1117
|
-
const hasTexture =
|
|
1118
|
+
const hasTexture = React7.useCallback((url) => {
|
|
1118
1119
|
return loaderRef.current.hasTexture(url);
|
|
1119
1120
|
}, []);
|
|
1120
|
-
const getModel =
|
|
1121
|
+
const getModel = React7.useCallback((url) => {
|
|
1121
1122
|
try {
|
|
1122
1123
|
return loaderRef.current.getModel(url);
|
|
1123
1124
|
} catch {
|
|
1124
1125
|
return void 0;
|
|
1125
1126
|
}
|
|
1126
1127
|
}, []);
|
|
1127
|
-
const getTexture =
|
|
1128
|
+
const getTexture = React7.useCallback((url) => {
|
|
1128
1129
|
try {
|
|
1129
1130
|
return loaderRef.current.getTexture(url);
|
|
1130
1131
|
} catch {
|
|
1131
1132
|
return void 0;
|
|
1132
1133
|
}
|
|
1133
1134
|
}, []);
|
|
1134
|
-
const clearCache =
|
|
1135
|
+
const clearCache = React7.useCallback(() => {
|
|
1135
1136
|
loaderRef.current.clearCache();
|
|
1136
1137
|
setState({
|
|
1137
1138
|
isLoading: false,
|
|
@@ -1155,25 +1156,25 @@ function useAssetLoader(options = {}) {
|
|
|
1155
1156
|
};
|
|
1156
1157
|
}
|
|
1157
1158
|
function useSceneGraph() {
|
|
1158
|
-
const nodesRef =
|
|
1159
|
-
const addNode =
|
|
1159
|
+
const nodesRef = React7.useRef(/* @__PURE__ */ new Map());
|
|
1160
|
+
const addNode = React7.useCallback((node) => {
|
|
1160
1161
|
const existing = nodesRef.current.get(node.id);
|
|
1161
1162
|
if (existing) {
|
|
1162
1163
|
existing.mesh.removeFromParent();
|
|
1163
1164
|
}
|
|
1164
1165
|
nodesRef.current.set(node.id, node);
|
|
1165
1166
|
}, []);
|
|
1166
|
-
const removeNode =
|
|
1167
|
+
const removeNode = React7.useCallback((id) => {
|
|
1167
1168
|
const node = nodesRef.current.get(id);
|
|
1168
1169
|
if (node) {
|
|
1169
1170
|
node.mesh.removeFromParent();
|
|
1170
1171
|
nodesRef.current.delete(id);
|
|
1171
1172
|
}
|
|
1172
1173
|
}, []);
|
|
1173
|
-
const getNode =
|
|
1174
|
+
const getNode = React7.useCallback((id) => {
|
|
1174
1175
|
return nodesRef.current.get(id);
|
|
1175
1176
|
}, []);
|
|
1176
|
-
const updateNodePosition =
|
|
1177
|
+
const updateNodePosition = React7.useCallback(
|
|
1177
1178
|
(id, x, y, z) => {
|
|
1178
1179
|
const node = nodesRef.current.get(id);
|
|
1179
1180
|
if (node) {
|
|
@@ -1183,7 +1184,7 @@ function useSceneGraph() {
|
|
|
1183
1184
|
},
|
|
1184
1185
|
[]
|
|
1185
1186
|
);
|
|
1186
|
-
const updateNodeGridPosition =
|
|
1187
|
+
const updateNodeGridPosition = React7.useCallback(
|
|
1187
1188
|
(id, gridX, gridZ) => {
|
|
1188
1189
|
const node = nodesRef.current.get(id);
|
|
1189
1190
|
if (node) {
|
|
@@ -1192,7 +1193,7 @@ function useSceneGraph() {
|
|
|
1192
1193
|
},
|
|
1193
1194
|
[]
|
|
1194
1195
|
);
|
|
1195
|
-
const getNodeAtGrid =
|
|
1196
|
+
const getNodeAtGrid = React7.useCallback(
|
|
1196
1197
|
(x, z, type) => {
|
|
1197
1198
|
return Array.from(nodesRef.current.values()).find((node) => {
|
|
1198
1199
|
const matchesGrid = node.gridPosition.x === x && node.gridPosition.z === z;
|
|
@@ -1201,10 +1202,10 @@ function useSceneGraph() {
|
|
|
1201
1202
|
},
|
|
1202
1203
|
[]
|
|
1203
1204
|
);
|
|
1204
|
-
const getNodesByType =
|
|
1205
|
+
const getNodesByType = React7.useCallback((type) => {
|
|
1205
1206
|
return Array.from(nodesRef.current.values()).filter((node) => node.type === type);
|
|
1206
1207
|
}, []);
|
|
1207
|
-
const getNodesInBounds =
|
|
1208
|
+
const getNodesInBounds = React7.useCallback(
|
|
1208
1209
|
(minX, maxX, minZ, maxZ) => {
|
|
1209
1210
|
return Array.from(nodesRef.current.values()).filter((node) => {
|
|
1210
1211
|
const { x, z } = node.gridPosition;
|
|
@@ -1213,13 +1214,13 @@ function useSceneGraph() {
|
|
|
1213
1214
|
},
|
|
1214
1215
|
[]
|
|
1215
1216
|
);
|
|
1216
|
-
const clearNodes =
|
|
1217
|
+
const clearNodes = React7.useCallback(() => {
|
|
1217
1218
|
nodesRef.current.forEach((node) => {
|
|
1218
1219
|
node.mesh.removeFromParent();
|
|
1219
1220
|
});
|
|
1220
1221
|
nodesRef.current.clear();
|
|
1221
1222
|
}, []);
|
|
1222
|
-
const countNodes =
|
|
1223
|
+
const countNodes = React7.useCallback((type) => {
|
|
1223
1224
|
if (!type) {
|
|
1224
1225
|
return nodesRef.current.size;
|
|
1225
1226
|
}
|
|
@@ -1241,9 +1242,9 @@ function useSceneGraph() {
|
|
|
1241
1242
|
}
|
|
1242
1243
|
function useRaycaster(options) {
|
|
1243
1244
|
const { camera, canvas, cellSize = 1, offsetX = 0, offsetZ = 0 } = options;
|
|
1244
|
-
const raycaster =
|
|
1245
|
-
const mouse =
|
|
1246
|
-
const clientToNDC =
|
|
1245
|
+
const raycaster = React7.useRef(new THREE6__namespace.Raycaster());
|
|
1246
|
+
const mouse = React7.useRef(new THREE6__namespace.Vector2());
|
|
1247
|
+
const clientToNDC = React7.useCallback(
|
|
1247
1248
|
(clientX, clientY) => {
|
|
1248
1249
|
if (!canvas) {
|
|
1249
1250
|
return { x: 0, y: 0 };
|
|
@@ -1256,7 +1257,7 @@ function useRaycaster(options) {
|
|
|
1256
1257
|
},
|
|
1257
1258
|
[canvas]
|
|
1258
1259
|
);
|
|
1259
|
-
const isWithinCanvas =
|
|
1260
|
+
const isWithinCanvas = React7.useCallback(
|
|
1260
1261
|
(clientX, clientY) => {
|
|
1261
1262
|
if (!canvas) return false;
|
|
1262
1263
|
const rect = canvas.getBoundingClientRect();
|
|
@@ -1264,7 +1265,7 @@ function useRaycaster(options) {
|
|
|
1264
1265
|
},
|
|
1265
1266
|
[canvas]
|
|
1266
1267
|
);
|
|
1267
|
-
const getIntersection =
|
|
1268
|
+
const getIntersection = React7.useCallback(
|
|
1268
1269
|
(clientX, clientY, objects) => {
|
|
1269
1270
|
if (!camera || !canvas) return null;
|
|
1270
1271
|
const ndc = clientToNDC(clientX, clientY);
|
|
@@ -1287,7 +1288,7 @@ function useRaycaster(options) {
|
|
|
1287
1288
|
},
|
|
1288
1289
|
[camera, canvas, clientToNDC]
|
|
1289
1290
|
);
|
|
1290
|
-
const getAllIntersections =
|
|
1291
|
+
const getAllIntersections = React7.useCallback(
|
|
1291
1292
|
(clientX, clientY, objects) => {
|
|
1292
1293
|
if (!camera || !canvas) return [];
|
|
1293
1294
|
const ndc = clientToNDC(clientX, clientY);
|
|
@@ -1306,7 +1307,7 @@ function useRaycaster(options) {
|
|
|
1306
1307
|
},
|
|
1307
1308
|
[camera, canvas, clientToNDC]
|
|
1308
1309
|
);
|
|
1309
|
-
const getGridCoordinates =
|
|
1310
|
+
const getGridCoordinates = React7.useCallback(
|
|
1310
1311
|
(clientX, clientY) => {
|
|
1311
1312
|
if (!camera || !canvas) return null;
|
|
1312
1313
|
const ndc = clientToNDC(clientX, clientY);
|
|
@@ -1324,7 +1325,7 @@ function useRaycaster(options) {
|
|
|
1324
1325
|
},
|
|
1325
1326
|
[camera, canvas, cellSize, offsetX, offsetZ, clientToNDC]
|
|
1326
1327
|
);
|
|
1327
|
-
const getTileAtPosition =
|
|
1328
|
+
const getTileAtPosition = React7.useCallback(
|
|
1328
1329
|
(clientX, clientY, scene) => {
|
|
1329
1330
|
if (!camera || !canvas) return null;
|
|
1330
1331
|
const tileMeshes = [];
|
|
@@ -1373,9 +1374,6 @@ function useRaycaster(options) {
|
|
|
1373
1374
|
isWithinCanvas
|
|
1374
1375
|
};
|
|
1375
1376
|
}
|
|
1376
|
-
var EventBusContext = React8.createContext(null);
|
|
1377
|
-
|
|
1378
|
-
// hooks/useEventBus.ts
|
|
1379
1377
|
function getGlobalEventBus() {
|
|
1380
1378
|
if (typeof window !== "undefined") {
|
|
1381
1379
|
return window.__kflowEventBus ?? null;
|
|
@@ -1443,12 +1441,12 @@ var fallbackEventBus = {
|
|
|
1443
1441
|
}
|
|
1444
1442
|
};
|
|
1445
1443
|
function useEventBus() {
|
|
1446
|
-
const context =
|
|
1444
|
+
const context = React7.useContext(providers.EventBusContext);
|
|
1447
1445
|
return context ?? getGlobalEventBus() ?? fallbackEventBus;
|
|
1448
1446
|
}
|
|
1449
1447
|
function useEmitEvent() {
|
|
1450
1448
|
const eventBus = useEventBus();
|
|
1451
|
-
return
|
|
1449
|
+
return React7.useCallback(
|
|
1452
1450
|
(type, payload) => {
|
|
1453
1451
|
eventBus.emit(type, payload);
|
|
1454
1452
|
},
|
|
@@ -1475,9 +1473,9 @@ function useGameCanvas3DEvents(options) {
|
|
|
1475
1473
|
onUnitAnimation
|
|
1476
1474
|
} = options;
|
|
1477
1475
|
const emit = useEmitEvent();
|
|
1478
|
-
const optionsRef =
|
|
1476
|
+
const optionsRef = React7.useRef(options);
|
|
1479
1477
|
optionsRef.current = options;
|
|
1480
|
-
const handleTileClick =
|
|
1478
|
+
const handleTileClick = React7.useCallback(
|
|
1481
1479
|
(tile, event) => {
|
|
1482
1480
|
if (tileClickEvent) {
|
|
1483
1481
|
emit(tileClickEvent, {
|
|
@@ -1493,7 +1491,7 @@ function useGameCanvas3DEvents(options) {
|
|
|
1493
1491
|
},
|
|
1494
1492
|
[tileClickEvent, emit]
|
|
1495
1493
|
);
|
|
1496
|
-
const handleUnitClick =
|
|
1494
|
+
const handleUnitClick = React7.useCallback(
|
|
1497
1495
|
(unit, event) => {
|
|
1498
1496
|
if (unitClickEvent) {
|
|
1499
1497
|
emit(unitClickEvent, {
|
|
@@ -1512,7 +1510,7 @@ function useGameCanvas3DEvents(options) {
|
|
|
1512
1510
|
},
|
|
1513
1511
|
[unitClickEvent, emit]
|
|
1514
1512
|
);
|
|
1515
|
-
const handleFeatureClick =
|
|
1513
|
+
const handleFeatureClick = React7.useCallback(
|
|
1516
1514
|
(feature, event) => {
|
|
1517
1515
|
if (featureClickEvent) {
|
|
1518
1516
|
emit(featureClickEvent, {
|
|
@@ -1527,7 +1525,7 @@ function useGameCanvas3DEvents(options) {
|
|
|
1527
1525
|
},
|
|
1528
1526
|
[featureClickEvent, emit]
|
|
1529
1527
|
);
|
|
1530
|
-
const handleCanvasClick =
|
|
1528
|
+
const handleCanvasClick = React7.useCallback(
|
|
1531
1529
|
(event) => {
|
|
1532
1530
|
if (canvasClickEvent) {
|
|
1533
1531
|
emit(canvasClickEvent, {
|
|
@@ -1540,7 +1538,7 @@ function useGameCanvas3DEvents(options) {
|
|
|
1540
1538
|
},
|
|
1541
1539
|
[canvasClickEvent, emit]
|
|
1542
1540
|
);
|
|
1543
|
-
const handleTileHover =
|
|
1541
|
+
const handleTileHover = React7.useCallback(
|
|
1544
1542
|
(tile, event) => {
|
|
1545
1543
|
if (tile) {
|
|
1546
1544
|
if (tileHoverEvent) {
|
|
@@ -1560,7 +1558,7 @@ function useGameCanvas3DEvents(options) {
|
|
|
1560
1558
|
},
|
|
1561
1559
|
[tileHoverEvent, tileLeaveEvent, emit]
|
|
1562
1560
|
);
|
|
1563
|
-
const handleUnitAnimation =
|
|
1561
|
+
const handleUnitAnimation = React7.useCallback(
|
|
1564
1562
|
(unitId, state) => {
|
|
1565
1563
|
if (unitAnimationEvent) {
|
|
1566
1564
|
emit(unitAnimationEvent, {
|
|
@@ -1573,7 +1571,7 @@ function useGameCanvas3DEvents(options) {
|
|
|
1573
1571
|
},
|
|
1574
1572
|
[unitAnimationEvent, emit]
|
|
1575
1573
|
);
|
|
1576
|
-
const handleCameraChange =
|
|
1574
|
+
const handleCameraChange = React7.useCallback(
|
|
1577
1575
|
(position) => {
|
|
1578
1576
|
if (cameraChangeEvent) {
|
|
1579
1577
|
emit(cameraChangeEvent, {
|
|
@@ -1619,17 +1617,17 @@ function TileRenderer({
|
|
|
1619
1617
|
validMoves = [],
|
|
1620
1618
|
attackTargets = []
|
|
1621
1619
|
}) {
|
|
1622
|
-
const meshRef =
|
|
1623
|
-
const geometry =
|
|
1620
|
+
const meshRef = React7.useRef(null);
|
|
1621
|
+
const geometry = React7.useMemo(() => {
|
|
1624
1622
|
return new THREE6__namespace.BoxGeometry(cellSize * 0.95, 0.2, cellSize * 0.95);
|
|
1625
1623
|
}, [cellSize]);
|
|
1626
|
-
const material =
|
|
1624
|
+
const material = React7.useMemo(() => {
|
|
1627
1625
|
return new THREE6__namespace.MeshStandardMaterial({
|
|
1628
1626
|
roughness: 0.8,
|
|
1629
1627
|
metalness: 0.1
|
|
1630
1628
|
});
|
|
1631
1629
|
}, []);
|
|
1632
|
-
const { positions, colors, tileMap } =
|
|
1630
|
+
const { positions, colors, tileMap } = React7.useMemo(() => {
|
|
1633
1631
|
const pos = [];
|
|
1634
1632
|
const cols = [];
|
|
1635
1633
|
const map = /* @__PURE__ */ new Map();
|
|
@@ -1659,7 +1657,7 @@ function TileRenderer({
|
|
|
1659
1657
|
});
|
|
1660
1658
|
return { positions: pos, colors: cols, tileMap: map };
|
|
1661
1659
|
}, [tiles, cellSize, offsetX, offsetZ, terrainColors, selectedTileIds, validMoves, attackTargets]);
|
|
1662
|
-
|
|
1660
|
+
React7.useEffect(() => {
|
|
1663
1661
|
if (!meshRef.current || !useInstancing) return;
|
|
1664
1662
|
const mesh = meshRef.current;
|
|
1665
1663
|
mesh.count = positions.length;
|
|
@@ -1763,10 +1761,10 @@ function TileRenderer({
|
|
|
1763
1761
|
return /* @__PURE__ */ jsxRuntime.jsx("group", { children: renderIndividualTiles() });
|
|
1764
1762
|
}
|
|
1765
1763
|
function UnitVisual({ unit, position, isSelected, onClick }) {
|
|
1766
|
-
const groupRef =
|
|
1767
|
-
const [animationState, setAnimationState] =
|
|
1768
|
-
const [isHovered, setIsHovered] =
|
|
1769
|
-
const teamColor =
|
|
1764
|
+
const groupRef = React7.useRef(null);
|
|
1765
|
+
const [animationState, setAnimationState] = React7.useState("idle");
|
|
1766
|
+
const [isHovered, setIsHovered] = React7.useState(false);
|
|
1767
|
+
const teamColor = React7.useMemo(() => {
|
|
1770
1768
|
if (unit.faction === "player" || unit.team === "player") return 4491519;
|
|
1771
1769
|
if (unit.faction === "enemy" || unit.team === "enemy") return 16729156;
|
|
1772
1770
|
if (unit.faction === "neutral" || unit.team === "neutral") return 16777028;
|
|
@@ -1778,11 +1776,11 @@ function UnitVisual({ unit, position, isSelected, onClick }) {
|
|
|
1778
1776
|
groupRef.current.position.y = y;
|
|
1779
1777
|
}
|
|
1780
1778
|
});
|
|
1781
|
-
const healthPercent =
|
|
1779
|
+
const healthPercent = React7.useMemo(() => {
|
|
1782
1780
|
if (unit.health === void 0 || unit.maxHealth === void 0) return 1;
|
|
1783
1781
|
return Math.max(0, Math.min(1, unit.health / unit.maxHealth));
|
|
1784
1782
|
}, [unit.health, unit.maxHealth]);
|
|
1785
|
-
const healthColor =
|
|
1783
|
+
const healthColor = React7.useMemo(() => {
|
|
1786
1784
|
if (healthPercent > 0.5) return "#44aa44";
|
|
1787
1785
|
if (healthPercent > 0.25) return "#aaaa44";
|
|
1788
1786
|
return "#ff4444";
|
|
@@ -1843,7 +1841,7 @@ function UnitRenderer({
|
|
|
1843
1841
|
onAnimationStateChange,
|
|
1844
1842
|
animationSpeed = 1
|
|
1845
1843
|
}) {
|
|
1846
|
-
const handleUnitClick =
|
|
1844
|
+
const handleUnitClick = React7__default.default.useCallback(
|
|
1847
1845
|
(unit) => {
|
|
1848
1846
|
onUnitClick?.(unit);
|
|
1849
1847
|
},
|
|
@@ -2056,10 +2054,10 @@ function detectAssetRoot3(modelUrl) {
|
|
|
2056
2054
|
return modelUrl.substring(0, modelUrl.lastIndexOf("/") + 1);
|
|
2057
2055
|
}
|
|
2058
2056
|
function useGLTFModel2(url) {
|
|
2059
|
-
const [model, setModel] =
|
|
2060
|
-
const [isLoading, setIsLoading] =
|
|
2061
|
-
const [error, setError] =
|
|
2062
|
-
|
|
2057
|
+
const [model, setModel] = React7.useState(null);
|
|
2058
|
+
const [isLoading, setIsLoading] = React7.useState(false);
|
|
2059
|
+
const [error, setError] = React7.useState(null);
|
|
2060
|
+
React7.useEffect(() => {
|
|
2063
2061
|
if (!url) {
|
|
2064
2062
|
setModel(null);
|
|
2065
2063
|
return;
|
|
@@ -2091,9 +2089,9 @@ function FeatureModel({
|
|
|
2091
2089
|
onClick,
|
|
2092
2090
|
onHover
|
|
2093
2091
|
}) {
|
|
2094
|
-
const groupRef =
|
|
2092
|
+
const groupRef = React7.useRef(null);
|
|
2095
2093
|
const { model: loadedModel, isLoading } = useGLTFModel2(feature.assetUrl);
|
|
2096
|
-
const model =
|
|
2094
|
+
const model = React7.useMemo(() => {
|
|
2097
2095
|
if (!loadedModel) return null;
|
|
2098
2096
|
const cloned = loadedModel.clone();
|
|
2099
2097
|
cloned.scale.setScalar(0.3);
|
|
@@ -2211,7 +2209,7 @@ function CameraController({
|
|
|
2211
2209
|
onCameraChange
|
|
2212
2210
|
}) {
|
|
2213
2211
|
const { camera } = fiber.useThree();
|
|
2214
|
-
|
|
2212
|
+
React7.useEffect(() => {
|
|
2215
2213
|
if (onCameraChange) {
|
|
2216
2214
|
onCameraChange({
|
|
2217
2215
|
x: camera.position.x,
|
|
@@ -2222,7 +2220,7 @@ function CameraController({
|
|
|
2222
2220
|
}, [camera.position, onCameraChange]);
|
|
2223
2221
|
return null;
|
|
2224
2222
|
}
|
|
2225
|
-
var GameCanvas3D =
|
|
2223
|
+
var GameCanvas3D = React7.forwardRef(
|
|
2226
2224
|
({
|
|
2227
2225
|
tiles = [],
|
|
2228
2226
|
units = [],
|
|
@@ -2267,10 +2265,10 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2267
2265
|
selectedUnitId = null,
|
|
2268
2266
|
children
|
|
2269
2267
|
}, ref) => {
|
|
2270
|
-
const containerRef =
|
|
2271
|
-
const controlsRef =
|
|
2272
|
-
const [hoveredTile, setHoveredTile] =
|
|
2273
|
-
const [internalError, setInternalError] =
|
|
2268
|
+
const containerRef = React7.useRef(null);
|
|
2269
|
+
const controlsRef = React7.useRef(null);
|
|
2270
|
+
const [hoveredTile, setHoveredTile] = React7.useState(null);
|
|
2271
|
+
const [internalError, setInternalError] = React7.useState(null);
|
|
2274
2272
|
const { isLoading: assetsLoading, progress, loaded, total } = useAssetLoader({
|
|
2275
2273
|
preloadUrls: preloadAssets,
|
|
2276
2274
|
loader: customAssetLoader
|
|
@@ -2291,7 +2289,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2291
2289
|
onTileHover,
|
|
2292
2290
|
onUnitAnimation
|
|
2293
2291
|
});
|
|
2294
|
-
const gridBounds =
|
|
2292
|
+
const gridBounds = React7.useMemo(() => {
|
|
2295
2293
|
if (tiles.length === 0) {
|
|
2296
2294
|
return { minX: 0, maxX: 10, minZ: 0, maxZ: 10 };
|
|
2297
2295
|
}
|
|
@@ -2304,14 +2302,14 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2304
2302
|
maxZ: Math.max(...zs)
|
|
2305
2303
|
};
|
|
2306
2304
|
}, [tiles]);
|
|
2307
|
-
const cameraTarget =
|
|
2305
|
+
const cameraTarget = React7.useMemo(() => {
|
|
2308
2306
|
return [
|
|
2309
2307
|
(gridBounds.minX + gridBounds.maxX) / 2,
|
|
2310
2308
|
0,
|
|
2311
2309
|
(gridBounds.minZ + gridBounds.maxZ) / 2
|
|
2312
2310
|
];
|
|
2313
2311
|
}, [gridBounds]);
|
|
2314
|
-
const gridConfig =
|
|
2312
|
+
const gridConfig = React7.useMemo(
|
|
2315
2313
|
() => ({
|
|
2316
2314
|
...DEFAULT_GRID_CONFIG,
|
|
2317
2315
|
offsetX: -(gridBounds.maxX - gridBounds.minX) / 2,
|
|
@@ -2319,7 +2317,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2319
2317
|
}),
|
|
2320
2318
|
[gridBounds]
|
|
2321
2319
|
);
|
|
2322
|
-
const gridToWorld2 =
|
|
2320
|
+
const gridToWorld2 = React7.useCallback(
|
|
2323
2321
|
(x, z, y = 0) => {
|
|
2324
2322
|
const worldX = (x - gridBounds.minX) * gridConfig.cellSize;
|
|
2325
2323
|
const worldZ = (z - gridBounds.minZ) * gridConfig.cellSize;
|
|
@@ -2327,7 +2325,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2327
2325
|
},
|
|
2328
2326
|
[gridBounds, gridConfig]
|
|
2329
2327
|
);
|
|
2330
|
-
|
|
2328
|
+
React7.useImperativeHandle(ref, () => ({
|
|
2331
2329
|
getCameraPosition: () => {
|
|
2332
2330
|
if (controlsRef.current) {
|
|
2333
2331
|
const pos = controlsRef.current.object.position;
|
|
@@ -2365,19 +2363,19 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2365
2363
|
features
|
|
2366
2364
|
})
|
|
2367
2365
|
}));
|
|
2368
|
-
const handleTileClick =
|
|
2366
|
+
const handleTileClick = React7.useCallback(
|
|
2369
2367
|
(tile, event) => {
|
|
2370
2368
|
eventHandlers.handleTileClick(tile, event);
|
|
2371
2369
|
},
|
|
2372
2370
|
[eventHandlers]
|
|
2373
2371
|
);
|
|
2374
|
-
const handleUnitClick =
|
|
2372
|
+
const handleUnitClick = React7.useCallback(
|
|
2375
2373
|
(unit, event) => {
|
|
2376
2374
|
eventHandlers.handleUnitClick(unit, event);
|
|
2377
2375
|
},
|
|
2378
2376
|
[eventHandlers]
|
|
2379
2377
|
);
|
|
2380
|
-
const handleFeatureClick =
|
|
2378
|
+
const handleFeatureClick = React7.useCallback(
|
|
2381
2379
|
(feature, event) => {
|
|
2382
2380
|
if (event) {
|
|
2383
2381
|
eventHandlers.handleFeatureClick(feature, event);
|
|
@@ -2385,7 +2383,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2385
2383
|
},
|
|
2386
2384
|
[eventHandlers]
|
|
2387
2385
|
);
|
|
2388
|
-
const handleTileHover =
|
|
2386
|
+
const handleTileHover = React7.useCallback(
|
|
2389
2387
|
(tile, event) => {
|
|
2390
2388
|
setHoveredTile(tile);
|
|
2391
2389
|
if (event) {
|
|
@@ -2394,7 +2392,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2394
2392
|
},
|
|
2395
2393
|
[eventHandlers]
|
|
2396
2394
|
);
|
|
2397
|
-
const cameraConfig =
|
|
2395
|
+
const cameraConfig = React7.useMemo(() => {
|
|
2398
2396
|
const size = Math.max(
|
|
2399
2397
|
gridBounds.maxX - gridBounds.minX,
|
|
2400
2398
|
gridBounds.maxZ - gridBounds.minZ
|
|
@@ -2419,7 +2417,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2419
2417
|
};
|
|
2420
2418
|
}
|
|
2421
2419
|
}, [cameraMode, gridBounds]);
|
|
2422
|
-
const DefaultTileRenderer =
|
|
2420
|
+
const DefaultTileRenderer = React7.useCallback(
|
|
2423
2421
|
({ tile, position }) => {
|
|
2424
2422
|
const isSelected = tile.id ? selectedTileIds.includes(tile.id) : false;
|
|
2425
2423
|
const isHovered = hoveredTile?.id === tile.id;
|
|
@@ -2457,7 +2455,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2457
2455
|
},
|
|
2458
2456
|
[selectedTileIds, hoveredTile, validMoves, attackTargets, handleTileClick, handleTileHover]
|
|
2459
2457
|
);
|
|
2460
|
-
const DefaultUnitRenderer =
|
|
2458
|
+
const DefaultUnitRenderer = React7.useCallback(
|
|
2461
2459
|
({ unit, position }) => {
|
|
2462
2460
|
const isSelected = selectedUnitId === unit.id;
|
|
2463
2461
|
const color = unit.faction === "player" ? 4491519 : unit.faction === "enemy" ? 16729156 : 16777028;
|
|
@@ -2515,7 +2513,7 @@ var GameCanvas3D = React8.forwardRef(
|
|
|
2515
2513
|
},
|
|
2516
2514
|
[selectedUnitId, handleUnitClick]
|
|
2517
2515
|
);
|
|
2518
|
-
const DefaultFeatureRenderer =
|
|
2516
|
+
const DefaultFeatureRenderer = React7.useCallback(
|
|
2519
2517
|
({
|
|
2520
2518
|
feature,
|
|
2521
2519
|
position
|
|
@@ -2822,7 +2820,7 @@ var positionStyles = {
|
|
|
2822
2820
|
fixed: "fixed",
|
|
2823
2821
|
sticky: "sticky"
|
|
2824
2822
|
};
|
|
2825
|
-
var Box =
|
|
2823
|
+
var Box = React7__default.default.forwardRef(
|
|
2826
2824
|
({
|
|
2827
2825
|
padding,
|
|
2828
2826
|
paddingX,
|
|
@@ -2851,20 +2849,20 @@ var Box = React8__default.default.forwardRef(
|
|
|
2851
2849
|
...rest
|
|
2852
2850
|
}, ref) => {
|
|
2853
2851
|
const eventBus = useEventBus();
|
|
2854
|
-
const handleClick =
|
|
2852
|
+
const handleClick = React7.useCallback((e) => {
|
|
2855
2853
|
if (action) {
|
|
2856
2854
|
e.stopPropagation();
|
|
2857
2855
|
eventBus.emit(`UI:${action}`, actionPayload ?? {});
|
|
2858
2856
|
}
|
|
2859
2857
|
onClick?.(e);
|
|
2860
2858
|
}, [action, actionPayload, eventBus, onClick]);
|
|
2861
|
-
const handleMouseEnter =
|
|
2859
|
+
const handleMouseEnter = React7.useCallback((e) => {
|
|
2862
2860
|
if (hoverEvent) {
|
|
2863
2861
|
eventBus.emit(`UI:${hoverEvent}`, { hovered: true });
|
|
2864
2862
|
}
|
|
2865
2863
|
onMouseEnter?.(e);
|
|
2866
2864
|
}, [hoverEvent, eventBus, onMouseEnter]);
|
|
2867
|
-
const handleMouseLeave =
|
|
2865
|
+
const handleMouseLeave = React7.useCallback((e) => {
|
|
2868
2866
|
if (hoverEvent) {
|
|
2869
2867
|
eventBus.emit(`UI:${hoverEvent}`, { hovered: false });
|
|
2870
2868
|
}
|