@nice2dev/game-engine 1.0.2 → 1.0.4
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/cjs/ai/BehaviorTree.js +1215 -0
- package/dist/cjs/ai/BehaviorTree.js.map +1 -0
- package/dist/cjs/ai/StateMachine.js +783 -0
- package/dist/cjs/ai/StateMachine.js.map +1 -0
- package/dist/cjs/editor/ShaderGraph.js +1616 -0
- package/dist/cjs/editor/ShaderGraph.js.map +1 -0
- package/dist/cjs/editor/TimelineEditor.js +819 -0
- package/dist/cjs/editor/TimelineEditor.js.map +1 -0
- package/dist/cjs/export/GodotExporter.js +1102 -0
- package/dist/cjs/export/GodotExporter.js.map +1 -0
- package/dist/cjs/export/PlatformExporter.js +236 -0
- package/dist/cjs/export/PlatformExporter.js.map +1 -0
- package/dist/cjs/export/ThreeJSExporter.js +1116 -0
- package/dist/cjs/export/ThreeJSExporter.js.map +1 -0
- package/dist/cjs/export/UnityExporter.js +1193 -0
- package/dist/cjs/export/UnityExporter.js.map +1 -0
- package/dist/cjs/export/WebExporter.js +1036 -0
- package/dist/cjs/export/WebExporter.js.map +1 -0
- package/dist/cjs/export/index.js +58 -0
- package/dist/cjs/export/index.js.map +1 -0
- package/dist/cjs/import/AsepriteImporter.js +761 -0
- package/dist/cjs/import/AsepriteImporter.js.map +1 -0
- package/dist/cjs/import/DragonBonesImporter.js +499 -0
- package/dist/cjs/import/DragonBonesImporter.js.map +1 -0
- package/dist/cjs/import/GameMakerImporter.js +559 -0
- package/dist/cjs/import/GameMakerImporter.js.map +1 -0
- package/dist/cjs/import/GodotSceneImporter.js +824 -0
- package/dist/cjs/import/GodotSceneImporter.js.map +1 -0
- package/dist/cjs/import/LDtkImporter.js +481 -0
- package/dist/cjs/import/LDtkImporter.js.map +1 -0
- package/dist/cjs/import/Live2DImporter.js +553 -0
- package/dist/cjs/import/Live2DImporter.js.map +1 -0
- package/dist/cjs/import/NdgFormat.js +499 -0
- package/dist/cjs/import/NdgFormat.js.map +1 -0
- package/dist/cjs/import/OgmoImporter.js +529 -0
- package/dist/cjs/import/OgmoImporter.js.map +1 -0
- package/dist/cjs/import/RPGMakerImporter.js +520 -0
- package/dist/cjs/import/RPGMakerImporter.js.map +1 -0
- package/dist/cjs/import/SceneImporter.js +449 -0
- package/dist/cjs/import/SceneImporter.js.map +1 -0
- package/dist/cjs/import/SpineImporter.js +583 -0
- package/dist/cjs/import/SpineImporter.js.map +1 -0
- package/dist/cjs/import/SpriterImporter.js +652 -0
- package/dist/cjs/import/SpriterImporter.js.map +1 -0
- package/dist/cjs/import/TiledMapImporter.js +859 -0
- package/dist/cjs/import/TiledMapImporter.js.map +1 -0
- package/dist/cjs/import/UnitySceneImporter.js +732 -0
- package/dist/cjs/import/UnitySceneImporter.js.map +1 -0
- package/dist/cjs/import/index.js +305 -0
- package/dist/cjs/import/index.js.map +1 -0
- package/dist/cjs/index.js +201 -0
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/scripting/GraphToAST.js +567 -0
- package/dist/cjs/scripting/GraphToAST.js.map +1 -0
- package/dist/cjs/scripting/LanguageExporter.js +321 -0
- package/dist/cjs/scripting/LanguageExporter.js.map +1 -0
- package/dist/cjs/scripting/ScriptAST.js +67 -0
- package/dist/cjs/scripting/ScriptAST.js.map +1 -0
- package/dist/cjs/scripting/VisualScripting2.js +1140 -0
- package/dist/cjs/scripting/VisualScripting2.js.map +1 -0
- package/dist/cjs/scripting/exporters/CSharpExporter.js +503 -0
- package/dist/cjs/scripting/exporters/CSharpExporter.js.map +1 -0
- package/dist/cjs/scripting/exporters/GDScriptExporter.js +452 -0
- package/dist/cjs/scripting/exporters/GDScriptExporter.js.map +1 -0
- package/dist/cjs/scripting/exporters/LuaExporter.js +457 -0
- package/dist/cjs/scripting/exporters/LuaExporter.js.map +1 -0
- package/dist/cjs/scripting/exporters/PythonExporter.js +565 -0
- package/dist/cjs/scripting/exporters/PythonExporter.js.map +1 -0
- package/dist/cjs/scripting/exporters/RustExporter.js +525 -0
- package/dist/cjs/scripting/exporters/RustExporter.js.map +1 -0
- package/dist/cjs/scripting/exporters/TypeScriptExporter.js +570 -0
- package/dist/cjs/scripting/exporters/TypeScriptExporter.js.map +1 -0
- package/dist/cjs/systems/ParticleSystem2.js +1478 -0
- package/dist/cjs/systems/ParticleSystem2.js.map +1 -0
- package/dist/esm/ai/BehaviorTree.js +1186 -0
- package/dist/esm/ai/BehaviorTree.js.map +1 -0
- package/dist/esm/ai/StateMachine.js +767 -0
- package/dist/esm/ai/StateMachine.js.map +1 -0
- package/dist/esm/editor/ShaderGraph.js +1606 -0
- package/dist/esm/editor/ShaderGraph.js.map +1 -0
- package/dist/esm/editor/TimelineEditor.js +800 -0
- package/dist/esm/editor/TimelineEditor.js.map +1 -0
- package/dist/esm/export/GodotExporter.js +1100 -0
- package/dist/esm/export/GodotExporter.js.map +1 -0
- package/dist/esm/export/PlatformExporter.js +230 -0
- package/dist/esm/export/PlatformExporter.js.map +1 -0
- package/dist/esm/export/ThreeJSExporter.js +1114 -0
- package/dist/esm/export/ThreeJSExporter.js.map +1 -0
- package/dist/esm/export/UnityExporter.js +1191 -0
- package/dist/esm/export/UnityExporter.js.map +1 -0
- package/dist/esm/export/WebExporter.js +1033 -0
- package/dist/esm/export/WebExporter.js.map +1 -0
- package/dist/esm/export/index.js +44 -0
- package/dist/esm/export/index.js.map +1 -0
- package/dist/esm/import/AsepriteImporter.js +759 -0
- package/dist/esm/import/AsepriteImporter.js.map +1 -0
- package/dist/esm/import/DragonBonesImporter.js +496 -0
- package/dist/esm/import/DragonBonesImporter.js.map +1 -0
- package/dist/esm/import/GameMakerImporter.js +556 -0
- package/dist/esm/import/GameMakerImporter.js.map +1 -0
- package/dist/esm/import/GodotSceneImporter.js +822 -0
- package/dist/esm/import/GodotSceneImporter.js.map +1 -0
- package/dist/esm/import/LDtkImporter.js +479 -0
- package/dist/esm/import/LDtkImporter.js.map +1 -0
- package/dist/esm/import/Live2DImporter.js +550 -0
- package/dist/esm/import/Live2DImporter.js.map +1 -0
- package/dist/esm/import/NdgFormat.js +490 -0
- package/dist/esm/import/NdgFormat.js.map +1 -0
- package/dist/esm/import/OgmoImporter.js +526 -0
- package/dist/esm/import/OgmoImporter.js.map +1 -0
- package/dist/esm/import/RPGMakerImporter.js +517 -0
- package/dist/esm/import/RPGMakerImporter.js.map +1 -0
- package/dist/esm/import/SceneImporter.js +441 -0
- package/dist/esm/import/SceneImporter.js.map +1 -0
- package/dist/esm/import/SpineImporter.js +580 -0
- package/dist/esm/import/SpineImporter.js.map +1 -0
- package/dist/esm/import/SpriterImporter.js +649 -0
- package/dist/esm/import/SpriterImporter.js.map +1 -0
- package/dist/esm/import/TiledMapImporter.js +857 -0
- package/dist/esm/import/TiledMapImporter.js.map +1 -0
- package/dist/esm/import/UnitySceneImporter.js +730 -0
- package/dist/esm/import/UnitySceneImporter.js.map +1 -0
- package/dist/esm/import/index.js +279 -0
- package/dist/esm/import/index.js.map +1 -0
- package/dist/esm/index.js +36 -0
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/scripting/GraphToAST.js +564 -0
- package/dist/esm/scripting/GraphToAST.js.map +1 -0
- package/dist/esm/scripting/LanguageExporter.js +311 -0
- package/dist/esm/scripting/LanguageExporter.js.map +1 -0
- package/dist/esm/scripting/ScriptAST.js +52 -0
- package/dist/esm/scripting/ScriptAST.js.map +1 -0
- package/dist/esm/scripting/VisualScripting2.js +1130 -0
- package/dist/esm/scripting/VisualScripting2.js.map +1 -0
- package/dist/esm/scripting/exporters/CSharpExporter.js +501 -0
- package/dist/esm/scripting/exporters/CSharpExporter.js.map +1 -0
- package/dist/esm/scripting/exporters/GDScriptExporter.js +450 -0
- package/dist/esm/scripting/exporters/GDScriptExporter.js.map +1 -0
- package/dist/esm/scripting/exporters/LuaExporter.js +455 -0
- package/dist/esm/scripting/exporters/LuaExporter.js.map +1 -0
- package/dist/esm/scripting/exporters/PythonExporter.js +563 -0
- package/dist/esm/scripting/exporters/PythonExporter.js.map +1 -0
- package/dist/esm/scripting/exporters/RustExporter.js +523 -0
- package/dist/esm/scripting/exporters/RustExporter.js.map +1 -0
- package/dist/esm/scripting/exporters/TypeScriptExporter.js +568 -0
- package/dist/esm/scripting/exporters/TypeScriptExporter.js.map +1 -0
- package/dist/esm/systems/ParticleSystem2.js +1471 -0
- package/dist/esm/systems/ParticleSystem2.js.map +1 -0
- package/dist/types/ai/BehaviorTree.d.ts +375 -0
- package/dist/types/ai/StateMachine.d.ts +296 -0
- package/dist/types/editor/ShaderGraph.d.ts +207 -0
- package/dist/types/editor/TimelineEditor.d.ts +393 -0
- package/dist/types/export/GodotExporter.d.ts +56 -0
- package/dist/types/export/PlatformExporter.d.ts +201 -0
- package/dist/types/export/ThreeJSExporter.d.ts +40 -0
- package/dist/types/export/UnityExporter.d.ts +69 -0
- package/dist/types/export/WebExporter.d.ts +58 -0
- package/dist/types/export/index.d.ts +19 -0
- package/dist/types/import/AsepriteImporter.d.ts +46 -0
- package/dist/types/import/DragonBonesImporter.d.ts +331 -0
- package/dist/types/import/GameMakerImporter.d.ts +375 -0
- package/dist/types/import/GodotSceneImporter.d.ts +34 -0
- package/dist/types/import/LDtkImporter.d.ts +177 -0
- package/dist/types/import/Live2DImporter.d.ts +237 -0
- package/dist/types/import/NdgFormat.d.ts +387 -0
- package/dist/types/import/OgmoImporter.d.ts +237 -0
- package/dist/types/import/RPGMakerImporter.d.ts +186 -0
- package/dist/types/import/SceneImporter.d.ts +276 -0
- package/dist/types/import/SpineImporter.d.ts +372 -0
- package/dist/types/import/SpriterImporter.d.ts +230 -0
- package/dist/types/import/TiledMapImporter.d.ts +57 -0
- package/dist/types/import/UnitySceneImporter.d.ts +87 -0
- package/dist/types/import/index.d.ts +59 -0
- package/dist/types/index.d.ts +29 -17
- package/dist/types/scripting/GraphToAST.d.ts +55 -0
- package/dist/types/scripting/LanguageExporter.d.ts +136 -0
- package/dist/types/scripting/ScriptAST.d.ts +312 -0
- package/dist/types/scripting/VisualScripting2.d.ts +353 -0
- package/dist/types/scripting/exporters/CSharpExporter.d.ts +44 -0
- package/dist/types/scripting/exporters/GDScriptExporter.d.ts +46 -0
- package/dist/types/scripting/exporters/LuaExporter.d.ts +46 -0
- package/dist/types/scripting/exporters/PythonExporter.d.ts +49 -0
- package/dist/types/scripting/exporters/RustExporter.d.ts +46 -0
- package/dist/types/scripting/exporters/TypeScriptExporter.d.ts +48 -0
- package/dist/types/scripting/exporters/index.d.ts +8 -0
- package/dist/types/scripting/index.d.ts +11 -0
- package/dist/types/systems/ParticleSystem2.d.ts +646 -0
- package/package.json +3 -3
|
@@ -0,0 +1,783 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @file StateMachine.ts
|
|
5
|
+
* @description Finite State Machine System with Graphical Editor Support
|
|
6
|
+
* PRO-1.4: Professional Editor Features
|
|
7
|
+
*
|
|
8
|
+
* Features:
|
|
9
|
+
* - Hierarchical state machines (HSM)
|
|
10
|
+
* - Transitions with conditions and actions
|
|
11
|
+
* - Entry/Exit/Update callbacks
|
|
12
|
+
* - Transition triggers and events
|
|
13
|
+
* - Visual editor integration
|
|
14
|
+
* - Debugging and history
|
|
15
|
+
* - Parallel states
|
|
16
|
+
* - Animation state machine support
|
|
17
|
+
*/
|
|
18
|
+
// ============================================================
|
|
19
|
+
// State Machine Runtime
|
|
20
|
+
// ============================================================
|
|
21
|
+
class StateMachine {
|
|
22
|
+
constructor(definition) {
|
|
23
|
+
this.layerStates = new Map();
|
|
24
|
+
this.activeTransitions = new Map();
|
|
25
|
+
this.parameters = new Map();
|
|
26
|
+
this.triggers = new Set();
|
|
27
|
+
/** Callbacks */
|
|
28
|
+
this.onEnter = new Map();
|
|
29
|
+
this.onExit = new Map();
|
|
30
|
+
this.onUpdate = new Map();
|
|
31
|
+
this.onTransitionStart = [];
|
|
32
|
+
this.onTransitionComplete = [];
|
|
33
|
+
/** Event listeners */
|
|
34
|
+
this.eventListeners = new Map();
|
|
35
|
+
/** Debugging */
|
|
36
|
+
this.history = [];
|
|
37
|
+
this.historyLimit = 100;
|
|
38
|
+
this.debugMode = false;
|
|
39
|
+
this.definition = definition;
|
|
40
|
+
this.initializeParameters();
|
|
41
|
+
this.initializeLayers();
|
|
42
|
+
}
|
|
43
|
+
initializeParameters() {
|
|
44
|
+
for (const param of this.definition.parameters) {
|
|
45
|
+
this.parameters.set(param.name, param.value);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
initializeLayers() {
|
|
49
|
+
for (const layer of this.definition.layers) {
|
|
50
|
+
if (!layer.active)
|
|
51
|
+
continue;
|
|
52
|
+
// Find default state or entry state
|
|
53
|
+
let initialState = layer.states.find((s) => s.isDefault);
|
|
54
|
+
if (!initialState) {
|
|
55
|
+
initialState = layer.states.find((s) => s.type === 'entry');
|
|
56
|
+
}
|
|
57
|
+
if (!initialState && layer.defaultState) {
|
|
58
|
+
initialState = layer.states.find((s) => s.id === layer.defaultState);
|
|
59
|
+
}
|
|
60
|
+
if (!initialState && layer.states.length > 0) {
|
|
61
|
+
initialState = layer.states[0];
|
|
62
|
+
}
|
|
63
|
+
if (initialState) {
|
|
64
|
+
this.layerStates.set(layer.id, {
|
|
65
|
+
stateId: initialState.id,
|
|
66
|
+
layerId: layer.id,
|
|
67
|
+
enterTime: 0,
|
|
68
|
+
elapsedTime: 0,
|
|
69
|
+
normalizedTime: 0,
|
|
70
|
+
isTransitioning: false,
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
// ─── Parameter Control ───────────────────────────
|
|
76
|
+
setParameter(name, value) {
|
|
77
|
+
const oldValue = this.parameters.get(name);
|
|
78
|
+
this.parameters.set(name, value);
|
|
79
|
+
if (oldValue !== value) {
|
|
80
|
+
this.emit('parameter-changed', { name, oldValue, newValue: value }, '');
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
getParameter(name) {
|
|
84
|
+
return this.parameters.get(name);
|
|
85
|
+
}
|
|
86
|
+
setBool(name, value) {
|
|
87
|
+
this.setParameter(name, value);
|
|
88
|
+
}
|
|
89
|
+
getBool(name) {
|
|
90
|
+
var _a;
|
|
91
|
+
return (_a = this.parameters.get(name)) !== null && _a !== void 0 ? _a : false;
|
|
92
|
+
}
|
|
93
|
+
setFloat(name, value) {
|
|
94
|
+
this.setParameter(name, value);
|
|
95
|
+
}
|
|
96
|
+
getFloat(name) {
|
|
97
|
+
var _a;
|
|
98
|
+
return (_a = this.parameters.get(name)) !== null && _a !== void 0 ? _a : 0;
|
|
99
|
+
}
|
|
100
|
+
setInteger(name, value) {
|
|
101
|
+
this.setParameter(name, Math.floor(value));
|
|
102
|
+
}
|
|
103
|
+
getInteger(name) {
|
|
104
|
+
var _a;
|
|
105
|
+
return Math.floor((_a = this.parameters.get(name)) !== null && _a !== void 0 ? _a : 0);
|
|
106
|
+
}
|
|
107
|
+
setTrigger(name) {
|
|
108
|
+
this.triggers.add(name);
|
|
109
|
+
this.setParameter(name, true);
|
|
110
|
+
}
|
|
111
|
+
resetTrigger(name) {
|
|
112
|
+
this.triggers.delete(name);
|
|
113
|
+
this.setParameter(name, false);
|
|
114
|
+
}
|
|
115
|
+
// ─── Update ──────────────────────────────────────
|
|
116
|
+
update(context) {
|
|
117
|
+
for (const layer of this.definition.layers) {
|
|
118
|
+
if (!layer.active)
|
|
119
|
+
continue;
|
|
120
|
+
this.updateLayer(layer, context);
|
|
121
|
+
}
|
|
122
|
+
// Clear triggers after processing
|
|
123
|
+
this.triggers.clear();
|
|
124
|
+
for (const param of this.definition.parameters) {
|
|
125
|
+
if (param.type === 'trigger') {
|
|
126
|
+
this.parameters.set(param.name, false);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
updateLayer(layer, context) {
|
|
131
|
+
const stateInstance = this.layerStates.get(layer.id);
|
|
132
|
+
if (!stateInstance)
|
|
133
|
+
return;
|
|
134
|
+
const currentState = layer.states.find((s) => s.id === stateInstance.stateId);
|
|
135
|
+
if (!currentState)
|
|
136
|
+
return;
|
|
137
|
+
// Update elapsed time
|
|
138
|
+
stateInstance.elapsedTime += context.dt;
|
|
139
|
+
// Check for transitions
|
|
140
|
+
const activeTransition = this.activeTransitions.get(layer.id);
|
|
141
|
+
if (activeTransition) {
|
|
142
|
+
// Update transition progress
|
|
143
|
+
activeTransition.progress += context.dt / activeTransition.duration;
|
|
144
|
+
if (activeTransition.progress >= 1) {
|
|
145
|
+
// Complete transition
|
|
146
|
+
this.completeTransition(layer, activeTransition, context);
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
else {
|
|
150
|
+
// Check for new transitions
|
|
151
|
+
const transition = this.findValidTransition(layer, currentState);
|
|
152
|
+
if (transition) {
|
|
153
|
+
this.startTransition(layer, transition, context);
|
|
154
|
+
}
|
|
155
|
+
else {
|
|
156
|
+
// Update current state
|
|
157
|
+
stateInstance.isTransitioning = false;
|
|
158
|
+
this.callOnUpdate(currentState, context);
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
findValidTransition(layer, currentState) {
|
|
163
|
+
// Sort by priority (lower = higher priority)
|
|
164
|
+
const allTransitions = [
|
|
165
|
+
...layer.anyStateTransitions,
|
|
166
|
+
...layer.transitions.filter((t) => t.from === currentState.id),
|
|
167
|
+
].sort((a, b) => a.priority - b.priority);
|
|
168
|
+
for (const transition of allTransitions) {
|
|
169
|
+
if (transition.muted)
|
|
170
|
+
continue;
|
|
171
|
+
// Check if can interrupt
|
|
172
|
+
const activeTransition = this.activeTransitions.get(layer.id);
|
|
173
|
+
if (activeTransition && !transition.canInterrupt)
|
|
174
|
+
continue;
|
|
175
|
+
// Check trigger
|
|
176
|
+
if (transition.trigger && !this.triggers.has(transition.trigger)) {
|
|
177
|
+
continue;
|
|
178
|
+
}
|
|
179
|
+
// Check conditions
|
|
180
|
+
if (this.evaluateConditions(transition.conditions)) {
|
|
181
|
+
return transition;
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
return null;
|
|
185
|
+
}
|
|
186
|
+
evaluateConditions(groups) {
|
|
187
|
+
if (groups.length === 0)
|
|
188
|
+
return true;
|
|
189
|
+
for (const group of groups) {
|
|
190
|
+
const groupResult = this.evaluateConditionGroup(group);
|
|
191
|
+
if (!groupResult)
|
|
192
|
+
return false;
|
|
193
|
+
}
|
|
194
|
+
return true;
|
|
195
|
+
}
|
|
196
|
+
evaluateConditionGroup(group) {
|
|
197
|
+
if (group.conditions.length === 0)
|
|
198
|
+
return true;
|
|
199
|
+
const results = group.conditions.map((c) => this.evaluateCondition(c));
|
|
200
|
+
if (group.mode === 'and') {
|
|
201
|
+
return results.every((r) => r);
|
|
202
|
+
}
|
|
203
|
+
else {
|
|
204
|
+
return results.some((r) => r);
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
evaluateCondition(condition) {
|
|
208
|
+
const paramValue = this.parameters.get(condition.parameter);
|
|
209
|
+
if (paramValue === undefined)
|
|
210
|
+
return false;
|
|
211
|
+
switch (condition.operator) {
|
|
212
|
+
case 'equals':
|
|
213
|
+
return paramValue === condition.value;
|
|
214
|
+
case 'notEquals':
|
|
215
|
+
return paramValue !== condition.value;
|
|
216
|
+
case 'greater':
|
|
217
|
+
return paramValue > condition.value;
|
|
218
|
+
case 'less':
|
|
219
|
+
return paramValue < condition.value;
|
|
220
|
+
case 'greaterEqual':
|
|
221
|
+
return paramValue >= condition.value;
|
|
222
|
+
case 'lessEqual':
|
|
223
|
+
return paramValue <= condition.value;
|
|
224
|
+
default:
|
|
225
|
+
return false;
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
startTransition(layer, transition, context) {
|
|
229
|
+
const stateInstance = this.layerStates.get(layer.id);
|
|
230
|
+
if (!stateInstance)
|
|
231
|
+
return;
|
|
232
|
+
const fromState = layer.states.find((s) => s.id === stateInstance.stateId);
|
|
233
|
+
const toState = layer.states.find((s) => s.id === transition.to);
|
|
234
|
+
if (!toState)
|
|
235
|
+
return;
|
|
236
|
+
// Call exit on current state
|
|
237
|
+
if (fromState) {
|
|
238
|
+
this.callOnExit(fromState, context);
|
|
239
|
+
}
|
|
240
|
+
// Create transition instance
|
|
241
|
+
const transitionInstance = {
|
|
242
|
+
transitionId: transition.id,
|
|
243
|
+
fromState: stateInstance.stateId,
|
|
244
|
+
toState: transition.to,
|
|
245
|
+
startTime: context.time,
|
|
246
|
+
duration: transition.duration,
|
|
247
|
+
progress: 0,
|
|
248
|
+
};
|
|
249
|
+
this.activeTransitions.set(layer.id, transitionInstance);
|
|
250
|
+
stateInstance.isTransitioning = true;
|
|
251
|
+
// Call transition callbacks
|
|
252
|
+
for (const cb of this.onTransitionStart) {
|
|
253
|
+
cb(context, transition);
|
|
254
|
+
}
|
|
255
|
+
this.emit('transition-start', { transition, from: fromState, to: toState }, layer.id);
|
|
256
|
+
// If instant transition, complete immediately
|
|
257
|
+
if (transition.duration === 0) {
|
|
258
|
+
this.completeTransition(layer, transitionInstance, context);
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
completeTransition(layer, transitionInstance, context) {
|
|
262
|
+
const stateInstance = this.layerStates.get(layer.id);
|
|
263
|
+
if (!stateInstance)
|
|
264
|
+
return;
|
|
265
|
+
const toState = layer.states.find((s) => s.id === transitionInstance.toState);
|
|
266
|
+
const transition = layer.transitions.find((t) => t.id === transitionInstance.transitionId) ||
|
|
267
|
+
layer.anyStateTransitions.find((t) => t.id === transitionInstance.transitionId);
|
|
268
|
+
if (!toState)
|
|
269
|
+
return;
|
|
270
|
+
// Update state
|
|
271
|
+
stateInstance.stateId = transitionInstance.toState;
|
|
272
|
+
stateInstance.enterTime = context.time;
|
|
273
|
+
stateInstance.elapsedTime = 0;
|
|
274
|
+
stateInstance.normalizedTime = (transition === null || transition === void 0 ? void 0 : transition.targetOffset) || 0;
|
|
275
|
+
stateInstance.isTransitioning = false;
|
|
276
|
+
// Remove active transition
|
|
277
|
+
this.activeTransitions.delete(layer.id);
|
|
278
|
+
// Call enter on new state
|
|
279
|
+
this.callOnEnter(toState, context);
|
|
280
|
+
// Call transition complete callbacks
|
|
281
|
+
if (transition) {
|
|
282
|
+
for (const cb of this.onTransitionComplete) {
|
|
283
|
+
cb(context, transition);
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
this.emit('transition-complete', { transition, state: toState }, layer.id);
|
|
287
|
+
}
|
|
288
|
+
// ─── Callbacks ───────────────────────────────────
|
|
289
|
+
callOnEnter(state, context) {
|
|
290
|
+
const callbacks = this.onEnter.get(state.id);
|
|
291
|
+
if (callbacks) {
|
|
292
|
+
for (const cb of callbacks) {
|
|
293
|
+
cb(context, state);
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
this.emit('state-enter', { state }, state.id);
|
|
297
|
+
}
|
|
298
|
+
callOnExit(state, context) {
|
|
299
|
+
const callbacks = this.onExit.get(state.id);
|
|
300
|
+
if (callbacks) {
|
|
301
|
+
for (const cb of callbacks) {
|
|
302
|
+
cb(context, state);
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
this.emit('state-exit', { state }, state.id);
|
|
306
|
+
}
|
|
307
|
+
callOnUpdate(state, context) {
|
|
308
|
+
const callbacks = this.onUpdate.get(state.id);
|
|
309
|
+
if (callbacks) {
|
|
310
|
+
for (const cb of callbacks) {
|
|
311
|
+
cb(context, state);
|
|
312
|
+
}
|
|
313
|
+
}
|
|
314
|
+
this.emit('state-update', { state }, state.id);
|
|
315
|
+
}
|
|
316
|
+
// ─── Registration ────────────────────────────────
|
|
317
|
+
registerOnEnter(stateId, callback) {
|
|
318
|
+
let callbacks = this.onEnter.get(stateId);
|
|
319
|
+
if (!callbacks) {
|
|
320
|
+
callbacks = [];
|
|
321
|
+
this.onEnter.set(stateId, callbacks);
|
|
322
|
+
}
|
|
323
|
+
callbacks.push(callback);
|
|
324
|
+
}
|
|
325
|
+
registerOnExit(stateId, callback) {
|
|
326
|
+
let callbacks = this.onExit.get(stateId);
|
|
327
|
+
if (!callbacks) {
|
|
328
|
+
callbacks = [];
|
|
329
|
+
this.onExit.set(stateId, callbacks);
|
|
330
|
+
}
|
|
331
|
+
callbacks.push(callback);
|
|
332
|
+
}
|
|
333
|
+
registerOnUpdate(stateId, callback) {
|
|
334
|
+
let callbacks = this.onUpdate.get(stateId);
|
|
335
|
+
if (!callbacks) {
|
|
336
|
+
callbacks = [];
|
|
337
|
+
this.onUpdate.set(stateId, callbacks);
|
|
338
|
+
}
|
|
339
|
+
callbacks.push(callback);
|
|
340
|
+
}
|
|
341
|
+
registerOnTransitionStart(callback) {
|
|
342
|
+
this.onTransitionStart.push(callback);
|
|
343
|
+
}
|
|
344
|
+
registerOnTransitionComplete(callback) {
|
|
345
|
+
this.onTransitionComplete.push(callback);
|
|
346
|
+
}
|
|
347
|
+
// ─── Events ──────────────────────────────────────
|
|
348
|
+
on(event, listener) {
|
|
349
|
+
let listeners = this.eventListeners.get(event);
|
|
350
|
+
if (!listeners) {
|
|
351
|
+
listeners = [];
|
|
352
|
+
this.eventListeners.set(event, listeners);
|
|
353
|
+
}
|
|
354
|
+
listeners.push(listener);
|
|
355
|
+
}
|
|
356
|
+
off(event, listener) {
|
|
357
|
+
const listeners = this.eventListeners.get(event);
|
|
358
|
+
if (listeners) {
|
|
359
|
+
const idx = listeners.indexOf(listener);
|
|
360
|
+
if (idx >= 0) {
|
|
361
|
+
listeners.splice(idx, 1);
|
|
362
|
+
}
|
|
363
|
+
}
|
|
364
|
+
}
|
|
365
|
+
emit(type, data, layerId) {
|
|
366
|
+
const event = {
|
|
367
|
+
type,
|
|
368
|
+
timestamp: Date.now(),
|
|
369
|
+
layerId,
|
|
370
|
+
data,
|
|
371
|
+
};
|
|
372
|
+
// Record history
|
|
373
|
+
if (this.debugMode) {
|
|
374
|
+
this.history.push(event);
|
|
375
|
+
if (this.history.length > this.historyLimit) {
|
|
376
|
+
this.history.shift();
|
|
377
|
+
}
|
|
378
|
+
}
|
|
379
|
+
// Notify listeners
|
|
380
|
+
const listeners = this.eventListeners.get(type);
|
|
381
|
+
if (listeners) {
|
|
382
|
+
for (const listener of listeners) {
|
|
383
|
+
listener(event);
|
|
384
|
+
}
|
|
385
|
+
}
|
|
386
|
+
}
|
|
387
|
+
// ─── State Queries ───────────────────────────────
|
|
388
|
+
getCurrentState(layerId) {
|
|
389
|
+
var _a;
|
|
390
|
+
const targetLayerId = layerId || ((_a = this.definition.layers[0]) === null || _a === void 0 ? void 0 : _a.id);
|
|
391
|
+
if (!targetLayerId)
|
|
392
|
+
return null;
|
|
393
|
+
const stateInstance = this.layerStates.get(targetLayerId);
|
|
394
|
+
if (!stateInstance)
|
|
395
|
+
return null;
|
|
396
|
+
const layer = this.definition.layers.find((l) => l.id === targetLayerId);
|
|
397
|
+
if (!layer)
|
|
398
|
+
return null;
|
|
399
|
+
return layer.states.find((s) => s.id === stateInstance.stateId) || null;
|
|
400
|
+
}
|
|
401
|
+
getCurrentStateId(layerId) {
|
|
402
|
+
const state = this.getCurrentState(layerId);
|
|
403
|
+
return (state === null || state === void 0 ? void 0 : state.id) || null;
|
|
404
|
+
}
|
|
405
|
+
isInState(stateId, layerId) {
|
|
406
|
+
const currentId = this.getCurrentStateId(layerId);
|
|
407
|
+
return currentId === stateId;
|
|
408
|
+
}
|
|
409
|
+
isTransitioning(layerId) {
|
|
410
|
+
var _a;
|
|
411
|
+
const targetLayerId = layerId || ((_a = this.definition.layers[0]) === null || _a === void 0 ? void 0 : _a.id);
|
|
412
|
+
if (!targetLayerId)
|
|
413
|
+
return false;
|
|
414
|
+
return this.activeTransitions.has(targetLayerId);
|
|
415
|
+
}
|
|
416
|
+
getTransitionProgress(layerId) {
|
|
417
|
+
var _a;
|
|
418
|
+
const targetLayerId = layerId || ((_a = this.definition.layers[0]) === null || _a === void 0 ? void 0 : _a.id);
|
|
419
|
+
if (!targetLayerId)
|
|
420
|
+
return 0;
|
|
421
|
+
const transition = this.activeTransitions.get(targetLayerId);
|
|
422
|
+
return (transition === null || transition === void 0 ? void 0 : transition.progress) || 0;
|
|
423
|
+
}
|
|
424
|
+
getStateTime(layerId) {
|
|
425
|
+
var _a;
|
|
426
|
+
const targetLayerId = layerId || ((_a = this.definition.layers[0]) === null || _a === void 0 ? void 0 : _a.id);
|
|
427
|
+
if (!targetLayerId)
|
|
428
|
+
return 0;
|
|
429
|
+
const stateInstance = this.layerStates.get(targetLayerId);
|
|
430
|
+
return (stateInstance === null || stateInstance === void 0 ? void 0 : stateInstance.elapsedTime) || 0;
|
|
431
|
+
}
|
|
432
|
+
// ─── Manual Control ──────────────────────────────
|
|
433
|
+
forceState(stateId, layerId) {
|
|
434
|
+
var _a;
|
|
435
|
+
const targetLayerId = layerId || ((_a = this.definition.layers[0]) === null || _a === void 0 ? void 0 : _a.id);
|
|
436
|
+
if (!targetLayerId)
|
|
437
|
+
return;
|
|
438
|
+
const layer = this.definition.layers.find((l) => l.id === targetLayerId);
|
|
439
|
+
if (!layer)
|
|
440
|
+
return;
|
|
441
|
+
const state = layer.states.find((s) => s.id === stateId);
|
|
442
|
+
if (!state)
|
|
443
|
+
return;
|
|
444
|
+
// Clear any active transition
|
|
445
|
+
this.activeTransitions.delete(targetLayerId);
|
|
446
|
+
// Set state directly
|
|
447
|
+
this.layerStates.set(targetLayerId, {
|
|
448
|
+
stateId,
|
|
449
|
+
layerId: targetLayerId,
|
|
450
|
+
enterTime: 0,
|
|
451
|
+
elapsedTime: 0,
|
|
452
|
+
normalizedTime: 0,
|
|
453
|
+
isTransitioning: false,
|
|
454
|
+
});
|
|
455
|
+
}
|
|
456
|
+
reset() {
|
|
457
|
+
this.layerStates.clear();
|
|
458
|
+
this.activeTransitions.clear();
|
|
459
|
+
this.triggers.clear();
|
|
460
|
+
this.initializeParameters();
|
|
461
|
+
this.initializeLayers();
|
|
462
|
+
this.history = [];
|
|
463
|
+
}
|
|
464
|
+
// ─── Debugging ───────────────────────────────────
|
|
465
|
+
getHistory() {
|
|
466
|
+
return [...this.history];
|
|
467
|
+
}
|
|
468
|
+
clearHistory() {
|
|
469
|
+
this.history = [];
|
|
470
|
+
}
|
|
471
|
+
getDebugInfo() {
|
|
472
|
+
const layers = this.definition.layers.map((layer) => {
|
|
473
|
+
const stateInstance = this.layerStates.get(layer.id);
|
|
474
|
+
const transition = this.activeTransitions.get(layer.id);
|
|
475
|
+
return {
|
|
476
|
+
id: layer.id,
|
|
477
|
+
name: layer.name,
|
|
478
|
+
currentState: (stateInstance === null || stateInstance === void 0 ? void 0 : stateInstance.stateId) || null,
|
|
479
|
+
isTransitioning: !!transition,
|
|
480
|
+
transitionProgress: (transition === null || transition === void 0 ? void 0 : transition.progress) || 0,
|
|
481
|
+
};
|
|
482
|
+
});
|
|
483
|
+
const parameters = {};
|
|
484
|
+
for (const [name, value] of this.parameters) {
|
|
485
|
+
parameters[name] = value;
|
|
486
|
+
}
|
|
487
|
+
return { layers, parameters };
|
|
488
|
+
}
|
|
489
|
+
// ─── Serialization ───────────────────────────────
|
|
490
|
+
getDefinition() {
|
|
491
|
+
return this.definition;
|
|
492
|
+
}
|
|
493
|
+
clone() {
|
|
494
|
+
return new StateMachine(JSON.parse(JSON.stringify(this.definition)));
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
// ============================================================
|
|
498
|
+
// Animation State Machine
|
|
499
|
+
// ============================================================
|
|
500
|
+
/** Extended state machine for animation control */
|
|
501
|
+
class AnimatorController extends StateMachine {
|
|
502
|
+
constructor(definition) {
|
|
503
|
+
super(definition);
|
|
504
|
+
this.motionValues = new Map();
|
|
505
|
+
this.blendTrees = new Map();
|
|
506
|
+
}
|
|
507
|
+
/** Get blended motion value for animation sampling */
|
|
508
|
+
getMotionValue(layerId) {
|
|
509
|
+
return this.motionValues.get(layerId) || 0;
|
|
510
|
+
}
|
|
511
|
+
/** Get current motion/clip name */
|
|
512
|
+
getMotionClip(layerId) {
|
|
513
|
+
const state = this.getCurrentState(layerId);
|
|
514
|
+
return (state === null || state === void 0 ? void 0 : state.motion) || null;
|
|
515
|
+
}
|
|
516
|
+
/** Register a blend tree for a state */
|
|
517
|
+
registerBlendTree(stateId, blendTree) {
|
|
518
|
+
this.blendTrees.set(stateId, blendTree);
|
|
519
|
+
}
|
|
520
|
+
/** Sample blend tree for current parameters */
|
|
521
|
+
sampleBlendTree(stateId) {
|
|
522
|
+
const blendTree = this.blendTrees.get(stateId);
|
|
523
|
+
if (!blendTree)
|
|
524
|
+
return null;
|
|
525
|
+
const params = {};
|
|
526
|
+
for (const [name, value] of this.getParameterMap()) {
|
|
527
|
+
if (typeof value === 'number') {
|
|
528
|
+
params[name] = value;
|
|
529
|
+
}
|
|
530
|
+
}
|
|
531
|
+
return blendTree.sample(params);
|
|
532
|
+
}
|
|
533
|
+
getParameterMap() {
|
|
534
|
+
const map = new Map();
|
|
535
|
+
const definition = this.getDefinition();
|
|
536
|
+
for (const param of definition.parameters) {
|
|
537
|
+
const value = this.getParameter(param.name);
|
|
538
|
+
if (value !== undefined) {
|
|
539
|
+
map.set(param.name, value);
|
|
540
|
+
}
|
|
541
|
+
}
|
|
542
|
+
return map;
|
|
543
|
+
}
|
|
544
|
+
}
|
|
545
|
+
class BlendTree {
|
|
546
|
+
constructor(type, parameterX, parameterY) {
|
|
547
|
+
this.motions = [];
|
|
548
|
+
this.type = type;
|
|
549
|
+
this.parameterX = parameterX;
|
|
550
|
+
this.parameterY = parameterY;
|
|
551
|
+
}
|
|
552
|
+
addMotion(motion) {
|
|
553
|
+
this.motions.push(motion);
|
|
554
|
+
}
|
|
555
|
+
sample(parameters) {
|
|
556
|
+
const paramX = parameters[this.parameterX] || 0;
|
|
557
|
+
const paramY = this.parameterY ? parameters[this.parameterY] || 0 : 0;
|
|
558
|
+
switch (this.type) {
|
|
559
|
+
case '1d':
|
|
560
|
+
return this.sample1D(paramX);
|
|
561
|
+
case '2d-simple':
|
|
562
|
+
case '2d-freeform':
|
|
563
|
+
return this.sample2D(paramX, paramY);
|
|
564
|
+
case 'direct':
|
|
565
|
+
return this.sampleDirect(parameters);
|
|
566
|
+
default:
|
|
567
|
+
return { clips: [] };
|
|
568
|
+
}
|
|
569
|
+
}
|
|
570
|
+
sample1D(value) {
|
|
571
|
+
if (this.motions.length === 0)
|
|
572
|
+
return { clips: [] };
|
|
573
|
+
// Sort by threshold/position
|
|
574
|
+
const sorted = [...this.motions].sort((a, b) => a.position - b.position);
|
|
575
|
+
// Find two motions to blend between
|
|
576
|
+
let lower = sorted[0];
|
|
577
|
+
let upper = sorted[sorted.length - 1];
|
|
578
|
+
for (let i = 0; i < sorted.length - 1; i++) {
|
|
579
|
+
const posLower = sorted[i].position;
|
|
580
|
+
const posUpper = sorted[i + 1].position;
|
|
581
|
+
if (value >= posLower && value <= posUpper) {
|
|
582
|
+
lower = sorted[i];
|
|
583
|
+
upper = sorted[i + 1];
|
|
584
|
+
break;
|
|
585
|
+
}
|
|
586
|
+
}
|
|
587
|
+
const posLower = lower.position;
|
|
588
|
+
const posUpper = upper.position;
|
|
589
|
+
// Calculate blend weight
|
|
590
|
+
let t = 0;
|
|
591
|
+
if (posUpper !== posLower) {
|
|
592
|
+
t = (value - posLower) / (posUpper - posLower);
|
|
593
|
+
}
|
|
594
|
+
t = Math.max(0, Math.min(1, t));
|
|
595
|
+
const clips = [];
|
|
596
|
+
if (t < 1) {
|
|
597
|
+
clips.push({
|
|
598
|
+
clip: lower.clip,
|
|
599
|
+
weight: 1 - t,
|
|
600
|
+
speed: lower.speed || 1,
|
|
601
|
+
mirror: lower.mirror || false,
|
|
602
|
+
});
|
|
603
|
+
}
|
|
604
|
+
if (t > 0 && upper !== lower) {
|
|
605
|
+
clips.push({
|
|
606
|
+
clip: upper.clip,
|
|
607
|
+
weight: t,
|
|
608
|
+
speed: upper.speed || 1,
|
|
609
|
+
mirror: upper.mirror || false,
|
|
610
|
+
});
|
|
611
|
+
}
|
|
612
|
+
return { clips };
|
|
613
|
+
}
|
|
614
|
+
sample2D(x, y) {
|
|
615
|
+
if (this.motions.length === 0)
|
|
616
|
+
return { clips: [] };
|
|
617
|
+
// Calculate weights using inverse distance weighting
|
|
618
|
+
const clips = [];
|
|
619
|
+
const weights = [];
|
|
620
|
+
let totalWeight = 0;
|
|
621
|
+
for (const motion of this.motions) {
|
|
622
|
+
const pos = motion.position;
|
|
623
|
+
const dx = x - pos.x;
|
|
624
|
+
const dy = y - pos.y;
|
|
625
|
+
const dist = Math.sqrt(dx * dx + dy * dy);
|
|
626
|
+
// Inverse distance (with small epsilon to avoid division by zero)
|
|
627
|
+
const weight = 1 / (dist + 0.001);
|
|
628
|
+
weights.push(weight);
|
|
629
|
+
totalWeight += weight;
|
|
630
|
+
}
|
|
631
|
+
// Normalize weights and create result
|
|
632
|
+
for (let i = 0; i < this.motions.length; i++) {
|
|
633
|
+
const motion = this.motions[i];
|
|
634
|
+
const normalizedWeight = weights[i] / totalWeight;
|
|
635
|
+
if (normalizedWeight > 0.001) {
|
|
636
|
+
clips.push({
|
|
637
|
+
clip: motion.clip,
|
|
638
|
+
weight: normalizedWeight,
|
|
639
|
+
speed: motion.speed || 1,
|
|
640
|
+
mirror: motion.mirror || false,
|
|
641
|
+
});
|
|
642
|
+
}
|
|
643
|
+
}
|
|
644
|
+
return { clips };
|
|
645
|
+
}
|
|
646
|
+
sampleDirect(parameters) {
|
|
647
|
+
const clips = [];
|
|
648
|
+
let totalWeight = 0;
|
|
649
|
+
for (const motion of this.motions) {
|
|
650
|
+
const weight = parameters[motion.clip] || 0;
|
|
651
|
+
if (weight > 0) {
|
|
652
|
+
totalWeight += weight;
|
|
653
|
+
clips.push({
|
|
654
|
+
clip: motion.clip,
|
|
655
|
+
weight,
|
|
656
|
+
speed: motion.speed || 1,
|
|
657
|
+
mirror: motion.mirror || false,
|
|
658
|
+
});
|
|
659
|
+
}
|
|
660
|
+
}
|
|
661
|
+
// Normalize
|
|
662
|
+
if (totalWeight > 0) {
|
|
663
|
+
for (const clip of clips) {
|
|
664
|
+
clip.weight /= totalWeight;
|
|
665
|
+
}
|
|
666
|
+
}
|
|
667
|
+
return { clips };
|
|
668
|
+
}
|
|
669
|
+
}
|
|
670
|
+
// ============================================================
|
|
671
|
+
// Factory Functions
|
|
672
|
+
// ============================================================
|
|
673
|
+
function createStateMachine(definition) {
|
|
674
|
+
return new StateMachine(definition);
|
|
675
|
+
}
|
|
676
|
+
function createAnimatorController(definition) {
|
|
677
|
+
return new AnimatorController(definition);
|
|
678
|
+
}
|
|
679
|
+
function createBlendTree1D(parameter) {
|
|
680
|
+
return new BlendTree('1d', parameter);
|
|
681
|
+
}
|
|
682
|
+
function createBlendTree2D(parameterX, parameterY, type = '2d-simple') {
|
|
683
|
+
return new BlendTree(type, parameterX, parameterY);
|
|
684
|
+
}
|
|
685
|
+
function createSMDefinition(name) {
|
|
686
|
+
return {
|
|
687
|
+
id: `sm_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`,
|
|
688
|
+
name,
|
|
689
|
+
description: '',
|
|
690
|
+
parameters: [],
|
|
691
|
+
layers: [],
|
|
692
|
+
};
|
|
693
|
+
}
|
|
694
|
+
function createSMLayer(name) {
|
|
695
|
+
return {
|
|
696
|
+
id: `layer_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`,
|
|
697
|
+
name,
|
|
698
|
+
weight: 1,
|
|
699
|
+
blendMode: 'override',
|
|
700
|
+
active: true,
|
|
701
|
+
states: [],
|
|
702
|
+
transitions: [],
|
|
703
|
+
anyStateTransitions: [],
|
|
704
|
+
};
|
|
705
|
+
}
|
|
706
|
+
function createSMState(name, type = 'normal') {
|
|
707
|
+
return {
|
|
708
|
+
id: `state_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`,
|
|
709
|
+
name,
|
|
710
|
+
type,
|
|
711
|
+
position: { x: 0, y: 0 },
|
|
712
|
+
speed: 1,
|
|
713
|
+
};
|
|
714
|
+
}
|
|
715
|
+
function createSMTransition(from, to) {
|
|
716
|
+
return {
|
|
717
|
+
id: `trans_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`,
|
|
718
|
+
from,
|
|
719
|
+
to,
|
|
720
|
+
conditions: [],
|
|
721
|
+
duration: 0.1,
|
|
722
|
+
priority: 0,
|
|
723
|
+
canInterrupt: false,
|
|
724
|
+
};
|
|
725
|
+
}
|
|
726
|
+
function createSMParameter(name, type, value) {
|
|
727
|
+
let defaultValue;
|
|
728
|
+
switch (type) {
|
|
729
|
+
case 'bool':
|
|
730
|
+
case 'trigger':
|
|
731
|
+
defaultValue = value !== undefined ? value : false;
|
|
732
|
+
break;
|
|
733
|
+
case 'int':
|
|
734
|
+
defaultValue = value !== undefined ? Math.floor(value) : 0;
|
|
735
|
+
break;
|
|
736
|
+
case 'float':
|
|
737
|
+
defaultValue = value !== undefined ? value : 0;
|
|
738
|
+
break;
|
|
739
|
+
}
|
|
740
|
+
return {
|
|
741
|
+
name,
|
|
742
|
+
type,
|
|
743
|
+
value: defaultValue,
|
|
744
|
+
};
|
|
745
|
+
}
|
|
746
|
+
function createSMCondition(parameter, operator, value) {
|
|
747
|
+
return {
|
|
748
|
+
id: `cond_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`,
|
|
749
|
+
parameter,
|
|
750
|
+
operator,
|
|
751
|
+
value,
|
|
752
|
+
};
|
|
753
|
+
}
|
|
754
|
+
function createSMConditionGroup(mode = 'and') {
|
|
755
|
+
return {
|
|
756
|
+
id: `group_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`,
|
|
757
|
+
mode,
|
|
758
|
+
conditions: [],
|
|
759
|
+
};
|
|
760
|
+
}
|
|
761
|
+
function createSMContext(params) {
|
|
762
|
+
return {
|
|
763
|
+
...params,
|
|
764
|
+
services: new Map(),
|
|
765
|
+
};
|
|
766
|
+
}
|
|
767
|
+
|
|
768
|
+
exports.AnimatorController = AnimatorController;
|
|
769
|
+
exports.BlendTree = BlendTree;
|
|
770
|
+
exports.StateMachine = StateMachine;
|
|
771
|
+
exports.createAnimatorController = createAnimatorController;
|
|
772
|
+
exports.createBlendTree1D = createBlendTree1D;
|
|
773
|
+
exports.createBlendTree2D = createBlendTree2D;
|
|
774
|
+
exports.createSMCondition = createSMCondition;
|
|
775
|
+
exports.createSMConditionGroup = createSMConditionGroup;
|
|
776
|
+
exports.createSMContext = createSMContext;
|
|
777
|
+
exports.createSMDefinition = createSMDefinition;
|
|
778
|
+
exports.createSMLayer = createSMLayer;
|
|
779
|
+
exports.createSMParameter = createSMParameter;
|
|
780
|
+
exports.createSMState = createSMState;
|
|
781
|
+
exports.createSMTransition = createSMTransition;
|
|
782
|
+
exports.createStateMachine = createStateMachine;
|
|
783
|
+
//# sourceMappingURL=StateMachine.js.map
|