unreal-engine-mcp-server 0.3.1 → 0.4.3
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/.env.production +1 -1
- package/.github/copilot-instructions.md +45 -0
- package/.github/workflows/publish-mcp.yml +1 -1
- package/README.md +22 -7
- package/dist/index.js +137 -46
- package/dist/prompts/index.d.ts +10 -3
- package/dist/prompts/index.js +186 -7
- package/dist/resources/actors.d.ts +19 -1
- package/dist/resources/actors.js +55 -64
- package/dist/resources/assets.d.ts +3 -2
- package/dist/resources/assets.js +117 -109
- package/dist/resources/levels.d.ts +21 -3
- package/dist/resources/levels.js +31 -56
- package/dist/tools/actors.d.ts +3 -14
- package/dist/tools/actors.js +246 -302
- package/dist/tools/animation.d.ts +57 -102
- package/dist/tools/animation.js +429 -450
- package/dist/tools/assets.d.ts +13 -2
- package/dist/tools/assets.js +58 -46
- package/dist/tools/audio.d.ts +22 -13
- package/dist/tools/audio.js +467 -121
- package/dist/tools/blueprint.d.ts +32 -13
- package/dist/tools/blueprint.js +699 -448
- package/dist/tools/build_environment_advanced.d.ts +0 -1
- package/dist/tools/build_environment_advanced.js +236 -87
- package/dist/tools/consolidated-tool-definitions.d.ts +232 -15
- package/dist/tools/consolidated-tool-definitions.js +124 -255
- package/dist/tools/consolidated-tool-handlers.js +749 -766
- package/dist/tools/debug.d.ts +72 -10
- package/dist/tools/debug.js +170 -36
- package/dist/tools/editor.d.ts +9 -2
- package/dist/tools/editor.js +30 -44
- package/dist/tools/foliage.d.ts +34 -15
- package/dist/tools/foliage.js +97 -107
- package/dist/tools/introspection.js +19 -21
- package/dist/tools/landscape.d.ts +1 -2
- package/dist/tools/landscape.js +311 -168
- package/dist/tools/level.d.ts +3 -28
- package/dist/tools/level.js +642 -192
- package/dist/tools/lighting.d.ts +14 -3
- package/dist/tools/lighting.js +236 -123
- package/dist/tools/materials.d.ts +25 -7
- package/dist/tools/materials.js +102 -79
- package/dist/tools/niagara.d.ts +10 -12
- package/dist/tools/niagara.js +74 -94
- package/dist/tools/performance.d.ts +12 -4
- package/dist/tools/performance.js +38 -79
- package/dist/tools/physics.d.ts +34 -10
- package/dist/tools/physics.js +364 -292
- package/dist/tools/rc.js +98 -24
- package/dist/tools/sequence.d.ts +1 -0
- package/dist/tools/sequence.js +146 -24
- package/dist/tools/ui.d.ts +31 -4
- package/dist/tools/ui.js +83 -66
- package/dist/tools/visual.d.ts +11 -0
- package/dist/tools/visual.js +245 -30
- package/dist/types/tool-types.d.ts +0 -6
- package/dist/types/tool-types.js +1 -8
- package/dist/unreal-bridge.d.ts +32 -2
- package/dist/unreal-bridge.js +621 -127
- package/dist/utils/elicitation.d.ts +57 -0
- package/dist/utils/elicitation.js +104 -0
- package/dist/utils/error-handler.d.ts +0 -33
- package/dist/utils/error-handler.js +4 -111
- package/dist/utils/http.d.ts +2 -22
- package/dist/utils/http.js +12 -75
- package/dist/utils/normalize.d.ts +4 -4
- package/dist/utils/normalize.js +15 -7
- package/dist/utils/python-output.d.ts +18 -0
- package/dist/utils/python-output.js +290 -0
- package/dist/utils/python.d.ts +2 -0
- package/dist/utils/python.js +4 -0
- package/dist/utils/response-validator.d.ts +6 -1
- package/dist/utils/response-validator.js +66 -13
- package/dist/utils/result-helpers.d.ts +27 -0
- package/dist/utils/result-helpers.js +147 -0
- package/dist/utils/safe-json.d.ts +0 -2
- package/dist/utils/safe-json.js +0 -43
- package/dist/utils/validation.d.ts +16 -0
- package/dist/utils/validation.js +70 -7
- package/mcp-config-example.json +2 -2
- package/package.json +11 -10
- package/server.json +37 -14
- package/src/index.ts +146 -50
- package/src/prompts/index.ts +211 -13
- package/src/resources/actors.ts +59 -44
- package/src/resources/assets.ts +123 -102
- package/src/resources/levels.ts +37 -47
- package/src/tools/actors.ts +269 -313
- package/src/tools/animation.ts +556 -539
- package/src/tools/assets.ts +59 -45
- package/src/tools/audio.ts +507 -113
- package/src/tools/blueprint.ts +778 -462
- package/src/tools/build_environment_advanced.ts +312 -106
- package/src/tools/consolidated-tool-definitions.ts +136 -267
- package/src/tools/consolidated-tool-handlers.ts +871 -795
- package/src/tools/debug.ts +179 -38
- package/src/tools/editor.ts +35 -37
- package/src/tools/foliage.ts +110 -104
- package/src/tools/introspection.ts +24 -22
- package/src/tools/landscape.ts +334 -181
- package/src/tools/level.ts +683 -182
- package/src/tools/lighting.ts +244 -123
- package/src/tools/materials.ts +114 -83
- package/src/tools/niagara.ts +87 -81
- package/src/tools/performance.ts +49 -88
- package/src/tools/physics.ts +393 -299
- package/src/tools/rc.ts +103 -25
- package/src/tools/sequence.ts +157 -30
- package/src/tools/ui.ts +101 -70
- package/src/tools/visual.ts +250 -29
- package/src/types/tool-types.ts +0 -9
- package/src/unreal-bridge.ts +658 -140
- package/src/utils/elicitation.ts +129 -0
- package/src/utils/error-handler.ts +4 -159
- package/src/utils/http.ts +16 -115
- package/src/utils/normalize.ts +20 -10
- package/src/utils/python-output.ts +351 -0
- package/src/utils/python.ts +3 -0
- package/src/utils/response-validator.ts +68 -17
- package/src/utils/result-helpers.ts +193 -0
- package/src/utils/safe-json.ts +0 -50
- package/src/utils/validation.ts +94 -7
- package/tests/run-unreal-tool-tests.mjs +720 -0
- package/tsconfig.json +2 -2
- package/dist/python-utils.d.ts +0 -29
- package/dist/python-utils.js +0 -54
- package/dist/tools/tool-definitions.d.ts +0 -4919
- package/dist/tools/tool-definitions.js +0 -1065
- package/dist/tools/tool-handlers.d.ts +0 -47
- package/dist/tools/tool-handlers.js +0 -863
- package/dist/types/index.d.ts +0 -323
- package/dist/types/index.js +0 -28
- package/dist/utils/cache-manager.d.ts +0 -64
- package/dist/utils/cache-manager.js +0 -176
- package/dist/utils/errors.d.ts +0 -133
- package/dist/utils/errors.js +0 -256
- package/src/python/editor_compat.py +0 -181
- package/src/python-utils.ts +0 -57
- package/src/tools/tool-definitions.ts +0 -1081
- package/src/tools/tool-handlers.ts +0 -973
- package/src/types/index.ts +0 -414
- package/src/utils/cache-manager.ts +0 -213
- package/src/utils/errors.ts +0 -312
package/dist/tools/debug.d.ts
CHANGED
|
@@ -2,7 +2,6 @@ import { UnrealBridge } from '../unreal-bridge.js';
|
|
|
2
2
|
export declare class DebugVisualizationTools {
|
|
3
3
|
private bridge;
|
|
4
4
|
constructor(bridge: UnrealBridge);
|
|
5
|
-
private _executeCommand;
|
|
6
5
|
private pyDraw;
|
|
7
6
|
drawDebugLine(params: {
|
|
8
7
|
start: [number, number, number];
|
|
@@ -12,10 +11,17 @@ export declare class DebugVisualizationTools {
|
|
|
12
11
|
thickness?: number;
|
|
13
12
|
}): Promise<{
|
|
14
13
|
success: boolean;
|
|
15
|
-
|
|
14
|
+
action: string;
|
|
15
|
+
warnings: string[] | undefined;
|
|
16
|
+
details: string[] | undefined;
|
|
17
|
+
rawOutput: string | undefined;
|
|
18
|
+
raw: unknown;
|
|
19
|
+
message?: string;
|
|
20
|
+
error?: string;
|
|
16
21
|
} | {
|
|
17
22
|
success: boolean;
|
|
18
23
|
error: string;
|
|
24
|
+
action: string;
|
|
19
25
|
}>;
|
|
20
26
|
drawDebugBox(params: {
|
|
21
27
|
center: [number, number, number];
|
|
@@ -26,10 +32,17 @@ export declare class DebugVisualizationTools {
|
|
|
26
32
|
thickness?: number;
|
|
27
33
|
}): Promise<{
|
|
28
34
|
success: boolean;
|
|
29
|
-
|
|
35
|
+
action: string;
|
|
36
|
+
warnings: string[] | undefined;
|
|
37
|
+
details: string[] | undefined;
|
|
38
|
+
rawOutput: string | undefined;
|
|
39
|
+
raw: unknown;
|
|
40
|
+
message?: string;
|
|
41
|
+
error?: string;
|
|
30
42
|
} | {
|
|
31
43
|
success: boolean;
|
|
32
44
|
error: string;
|
|
45
|
+
action: string;
|
|
33
46
|
}>;
|
|
34
47
|
drawDebugSphere(params: {
|
|
35
48
|
center: [number, number, number];
|
|
@@ -40,10 +53,17 @@ export declare class DebugVisualizationTools {
|
|
|
40
53
|
thickness?: number;
|
|
41
54
|
}): Promise<{
|
|
42
55
|
success: boolean;
|
|
43
|
-
|
|
56
|
+
action: string;
|
|
57
|
+
warnings: string[] | undefined;
|
|
58
|
+
details: string[] | undefined;
|
|
59
|
+
rawOutput: string | undefined;
|
|
60
|
+
raw: unknown;
|
|
61
|
+
message?: string;
|
|
62
|
+
error?: string;
|
|
44
63
|
} | {
|
|
45
64
|
success: boolean;
|
|
46
65
|
error: string;
|
|
66
|
+
action: string;
|
|
47
67
|
}>;
|
|
48
68
|
drawDebugCapsule(params: {
|
|
49
69
|
center: [number, number, number];
|
|
@@ -54,10 +74,17 @@ export declare class DebugVisualizationTools {
|
|
|
54
74
|
duration?: number;
|
|
55
75
|
}): Promise<{
|
|
56
76
|
success: boolean;
|
|
57
|
-
|
|
77
|
+
action: string;
|
|
78
|
+
warnings: string[] | undefined;
|
|
79
|
+
details: string[] | undefined;
|
|
80
|
+
rawOutput: string | undefined;
|
|
81
|
+
raw: unknown;
|
|
82
|
+
message?: string;
|
|
83
|
+
error?: string;
|
|
58
84
|
} | {
|
|
59
85
|
success: boolean;
|
|
60
86
|
error: string;
|
|
87
|
+
action: string;
|
|
61
88
|
}>;
|
|
62
89
|
drawDebugCone(params: {
|
|
63
90
|
origin: [number, number, number];
|
|
@@ -70,10 +97,17 @@ export declare class DebugVisualizationTools {
|
|
|
70
97
|
duration?: number;
|
|
71
98
|
}): Promise<{
|
|
72
99
|
success: boolean;
|
|
73
|
-
|
|
100
|
+
action: string;
|
|
101
|
+
warnings: string[] | undefined;
|
|
102
|
+
details: string[] | undefined;
|
|
103
|
+
rawOutput: string | undefined;
|
|
104
|
+
raw: unknown;
|
|
105
|
+
message?: string;
|
|
106
|
+
error?: string;
|
|
74
107
|
} | {
|
|
75
108
|
success: boolean;
|
|
76
109
|
error: string;
|
|
110
|
+
action: string;
|
|
77
111
|
}>;
|
|
78
112
|
drawDebugString(params: {
|
|
79
113
|
location: [number, number, number];
|
|
@@ -83,10 +117,17 @@ export declare class DebugVisualizationTools {
|
|
|
83
117
|
fontSize?: number;
|
|
84
118
|
}): Promise<{
|
|
85
119
|
success: boolean;
|
|
86
|
-
|
|
120
|
+
action: string;
|
|
121
|
+
warnings: string[] | undefined;
|
|
122
|
+
details: string[] | undefined;
|
|
123
|
+
rawOutput: string | undefined;
|
|
124
|
+
raw: unknown;
|
|
125
|
+
message?: string;
|
|
126
|
+
error?: string;
|
|
87
127
|
} | {
|
|
88
128
|
success: boolean;
|
|
89
129
|
error: string;
|
|
130
|
+
action: string;
|
|
90
131
|
}>;
|
|
91
132
|
drawDebugArrow(params: {
|
|
92
133
|
start: [number, number, number];
|
|
@@ -97,10 +138,17 @@ export declare class DebugVisualizationTools {
|
|
|
97
138
|
thickness?: number;
|
|
98
139
|
}): Promise<{
|
|
99
140
|
success: boolean;
|
|
100
|
-
|
|
141
|
+
action: string;
|
|
142
|
+
warnings: string[] | undefined;
|
|
143
|
+
details: string[] | undefined;
|
|
144
|
+
rawOutput: string | undefined;
|
|
145
|
+
raw: unknown;
|
|
146
|
+
message?: string;
|
|
147
|
+
error?: string;
|
|
101
148
|
} | {
|
|
102
149
|
success: boolean;
|
|
103
150
|
error: string;
|
|
151
|
+
action: string;
|
|
104
152
|
}>;
|
|
105
153
|
drawDebugPoint(params: {
|
|
106
154
|
location: [number, number, number];
|
|
@@ -109,10 +157,17 @@ export declare class DebugVisualizationTools {
|
|
|
109
157
|
duration?: number;
|
|
110
158
|
}): Promise<{
|
|
111
159
|
success: boolean;
|
|
112
|
-
|
|
160
|
+
action: string;
|
|
161
|
+
warnings: string[] | undefined;
|
|
162
|
+
details: string[] | undefined;
|
|
163
|
+
rawOutput: string | undefined;
|
|
164
|
+
raw: unknown;
|
|
165
|
+
message?: string;
|
|
166
|
+
error?: string;
|
|
113
167
|
} | {
|
|
114
168
|
success: boolean;
|
|
115
169
|
error: string;
|
|
170
|
+
action: string;
|
|
116
171
|
}>;
|
|
117
172
|
drawDebugCoordinateSystem(params: {
|
|
118
173
|
location: [number, number, number];
|
|
@@ -132,10 +187,17 @@ export declare class DebugVisualizationTools {
|
|
|
132
187
|
duration?: number;
|
|
133
188
|
}): Promise<{
|
|
134
189
|
success: boolean;
|
|
135
|
-
|
|
190
|
+
action: string;
|
|
191
|
+
warnings: string[] | undefined;
|
|
192
|
+
details: string[] | undefined;
|
|
193
|
+
rawOutput: string | undefined;
|
|
194
|
+
raw: unknown;
|
|
195
|
+
message?: string;
|
|
196
|
+
error?: string;
|
|
136
197
|
} | {
|
|
137
198
|
success: boolean;
|
|
138
199
|
error: string;
|
|
200
|
+
action: string;
|
|
139
201
|
}>;
|
|
140
202
|
clearDebugDrawings(): Promise<any>;
|
|
141
203
|
showCollision(params: {
|
package/dist/tools/debug.js
CHANGED
|
@@ -1,41 +1,87 @@
|
|
|
1
|
+
import { bestEffortInterpretedText, coerceString, interpretStandardResult } from '../utils/result-helpers.js';
|
|
2
|
+
import { parseStandardResult } from '../utils/python-output.js';
|
|
1
3
|
export class DebugVisualizationTools {
|
|
2
4
|
bridge;
|
|
3
5
|
constructor(bridge) {
|
|
4
6
|
this.bridge = bridge;
|
|
5
7
|
}
|
|
6
|
-
// Execute console command (kept for legacy operations)
|
|
7
|
-
async _executeCommand(command) {
|
|
8
|
-
return this.bridge.httpCall('/remote/object/call', 'PUT', {
|
|
9
|
-
objectPath: '/Script/Engine.Default__KismetSystemLibrary',
|
|
10
|
-
functionName: 'ExecuteConsoleCommand',
|
|
11
|
-
parameters: {
|
|
12
|
-
WorldContextObject: null,
|
|
13
|
-
Command: command,
|
|
14
|
-
SpecificPlayer: null
|
|
15
|
-
},
|
|
16
|
-
generateTransaction: false
|
|
17
|
-
});
|
|
18
|
-
}
|
|
19
8
|
// Helper to draw via Python SystemLibrary with the editor world
|
|
20
|
-
async pyDraw(scriptBody) {
|
|
9
|
+
async pyDraw(scriptBody, meta) {
|
|
10
|
+
const action = (meta?.action || 'debug_draw').replace(/\\/g, '\\\\').replace(/'/g, "\\'");
|
|
11
|
+
const payloadObject = meta?.params ?? {};
|
|
12
|
+
const payloadJson = JSON.stringify(payloadObject).replace(/\\/g, '\\\\').replace(/'/g, "\\'");
|
|
13
|
+
const indentedBody = scriptBody
|
|
14
|
+
.split(/\r?\n/)
|
|
15
|
+
.map(line => ` ${line}`)
|
|
16
|
+
.join('\n');
|
|
21
17
|
const script = `
|
|
22
18
|
import unreal
|
|
23
|
-
|
|
19
|
+
import json
|
|
20
|
+
|
|
21
|
+
payload = json.loads('${payloadJson}')
|
|
24
22
|
ues = unreal.get_editor_subsystem(unreal.UnrealEditorSubsystem)
|
|
25
|
-
if ues:
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
world
|
|
30
|
-
|
|
23
|
+
if not ues:
|
|
24
|
+
raise Exception('UnrealEditorSubsystem not available')
|
|
25
|
+
world = ues.get_editor_world()
|
|
26
|
+
if not world:
|
|
27
|
+
raise Exception('Editor world unavailable')
|
|
28
|
+
try:
|
|
29
|
+
${indentedBody}
|
|
30
|
+
print('DEBUG_DRAW:' + json.dumps({'action': '${action}', 'params': payload}))
|
|
31
|
+
print('RESULT:' + json.dumps({'success': True, 'action': '${action}', 'params': payload}))
|
|
32
|
+
except Exception as e:
|
|
33
|
+
print('DEBUG_DRAW_ERROR:' + str(e))
|
|
34
|
+
print('RESULT:' + json.dumps({'success': False, 'action': '${action}', 'error': str(e)}))
|
|
31
35
|
`.trim()
|
|
32
36
|
.replace(/\r?\n/g, '\n');
|
|
33
37
|
try {
|
|
34
|
-
await this.bridge.executePython(script);
|
|
35
|
-
|
|
38
|
+
const response = await this.bridge.executePython(script);
|
|
39
|
+
let interpreted = interpretStandardResult(response, {
|
|
40
|
+
successMessage: `${action} executed`,
|
|
41
|
+
failureMessage: `${action} failed`
|
|
42
|
+
});
|
|
43
|
+
const parsed = parseStandardResult(response);
|
|
44
|
+
const parsedPayload = parsed.data ?? {};
|
|
45
|
+
const parsedSuccessValue = parsedPayload.success;
|
|
46
|
+
const normalizedSuccess = typeof parsedSuccessValue === 'string'
|
|
47
|
+
? ['true', '1', 'yes'].includes(parsedSuccessValue.toLowerCase())
|
|
48
|
+
: parsedSuccessValue === true;
|
|
49
|
+
if (!interpreted.success && normalizedSuccess) {
|
|
50
|
+
interpreted = {
|
|
51
|
+
...interpreted,
|
|
52
|
+
success: true,
|
|
53
|
+
error: undefined,
|
|
54
|
+
message: interpreted.message || `${action} executed`,
|
|
55
|
+
payload: { ...parsedPayload }
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
const finalSuccess = interpreted.success || normalizedSuccess;
|
|
59
|
+
const resolvedAction = coerceString(interpreted.payload.action) ?? action;
|
|
60
|
+
const fallbackOutput = typeof parsed.text === 'string' ? parsed.text : '';
|
|
61
|
+
const rawOutput = bestEffortInterpretedText(interpreted) ?? (fallbackOutput ? fallbackOutput : undefined);
|
|
62
|
+
if (finalSuccess) {
|
|
63
|
+
return {
|
|
64
|
+
...interpreted.payload,
|
|
65
|
+
success: true,
|
|
66
|
+
action: resolvedAction,
|
|
67
|
+
warnings: interpreted.warnings,
|
|
68
|
+
details: interpreted.details,
|
|
69
|
+
rawOutput,
|
|
70
|
+
raw: parsed.raw ?? interpreted.raw
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
return {
|
|
74
|
+
success: false,
|
|
75
|
+
action: resolvedAction,
|
|
76
|
+
error: interpreted.error ?? `${resolvedAction} failed`,
|
|
77
|
+
warnings: interpreted.warnings,
|
|
78
|
+
details: interpreted.details,
|
|
79
|
+
rawOutput,
|
|
80
|
+
raw: parsed.raw ?? interpreted.raw
|
|
81
|
+
};
|
|
36
82
|
}
|
|
37
83
|
catch (e) {
|
|
38
|
-
return { success: false, error: String(e) };
|
|
84
|
+
return { success: false, error: String(e), action: meta?.action || 'debug_draw' };
|
|
39
85
|
}
|
|
40
86
|
}
|
|
41
87
|
// Draw debug line using Python SystemLibrary
|
|
@@ -52,7 +98,16 @@ end = unreal.Vector(${ex}, ${ey}, ${ez})
|
|
|
52
98
|
color = unreal.LinearColor(${sr}/255.0, ${sg}/255.0, ${sb}/255.0, ${sa}/255.0)
|
|
53
99
|
unreal.SystemLibrary.draw_debug_line(world, start, end, color, ${duration}, ${thickness})
|
|
54
100
|
`;
|
|
55
|
-
return this.pyDraw(script
|
|
101
|
+
return this.pyDraw(script, {
|
|
102
|
+
action: 'debug_line',
|
|
103
|
+
params: {
|
|
104
|
+
start: params.start,
|
|
105
|
+
end: params.end,
|
|
106
|
+
color,
|
|
107
|
+
duration,
|
|
108
|
+
thickness
|
|
109
|
+
}
|
|
110
|
+
});
|
|
56
111
|
}
|
|
57
112
|
// Draw debug box using Python SystemLibrary
|
|
58
113
|
async drawDebugBox(params) {
|
|
@@ -71,7 +126,17 @@ rot = unreal.Rotator(${rp}, ${ry}, ${rr})
|
|
|
71
126
|
color = unreal.LinearColor(${cr}/255.0, ${cg}/255.0, ${cb}/255.0, ${ca}/255.0)
|
|
72
127
|
unreal.SystemLibrary.draw_debug_box(world, center, extent, color, rot, ${duration}, ${thickness})
|
|
73
128
|
`;
|
|
74
|
-
return this.pyDraw(script
|
|
129
|
+
return this.pyDraw(script, {
|
|
130
|
+
action: 'debug_box',
|
|
131
|
+
params: {
|
|
132
|
+
center: params.center,
|
|
133
|
+
extent: params.extent,
|
|
134
|
+
rotation,
|
|
135
|
+
color,
|
|
136
|
+
duration,
|
|
137
|
+
thickness
|
|
138
|
+
}
|
|
139
|
+
});
|
|
75
140
|
}
|
|
76
141
|
// Draw debug sphere using Python SystemLibrary
|
|
77
142
|
async drawDebugSphere(params) {
|
|
@@ -86,7 +151,17 @@ center = unreal.Vector(${cx}, ${cy}, ${cz})
|
|
|
86
151
|
color = unreal.LinearColor(${cr}/255.0, ${cg}/255.0, ${cb}/255.0, ${ca}/255.0)
|
|
87
152
|
unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segments}, color, ${duration}, ${thickness})
|
|
88
153
|
`;
|
|
89
|
-
return this.pyDraw(script
|
|
154
|
+
return this.pyDraw(script, {
|
|
155
|
+
action: 'debug_sphere',
|
|
156
|
+
params: {
|
|
157
|
+
center: params.center,
|
|
158
|
+
radius: params.radius,
|
|
159
|
+
segments,
|
|
160
|
+
color,
|
|
161
|
+
duration,
|
|
162
|
+
thickness
|
|
163
|
+
}
|
|
164
|
+
});
|
|
90
165
|
}
|
|
91
166
|
// The rest keep console-command fallbacks or editor helpers as before
|
|
92
167
|
async drawDebugCapsule(params) {
|
|
@@ -97,7 +172,17 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
97
172
|
const [rp, ry, rr] = rotation;
|
|
98
173
|
const [cr, cg, cb, ca] = color;
|
|
99
174
|
const script = `\ncenter = unreal.Vector(${cx}, ${cy}, ${cz})\nrot = unreal.Rotator(${rp}, ${ry}, ${rr})\ncolor = unreal.LinearColor(${cr}/255.0, ${cg}/255.0, ${cb}/255.0, ${ca}/255.0)\nunreal.SystemLibrary.draw_debug_capsule(world, center, ${params.halfHeight}, ${params.radius}, rot, color, ${duration}, 1.0)\n`;
|
|
100
|
-
return this.pyDraw(script
|
|
175
|
+
return this.pyDraw(script, {
|
|
176
|
+
action: 'debug_capsule',
|
|
177
|
+
params: {
|
|
178
|
+
center: params.center,
|
|
179
|
+
halfHeight: params.halfHeight,
|
|
180
|
+
radius: params.radius,
|
|
181
|
+
rotation,
|
|
182
|
+
color,
|
|
183
|
+
duration
|
|
184
|
+
}
|
|
185
|
+
});
|
|
101
186
|
}
|
|
102
187
|
async drawDebugCone(params) {
|
|
103
188
|
const color = params.color || [255, 0, 255, 255];
|
|
@@ -106,7 +191,19 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
106
191
|
const [dx, dy, dz] = params.direction;
|
|
107
192
|
const [cr, cg, cb, ca] = color;
|
|
108
193
|
const script = `\norigin = unreal.Vector(${ox}, ${oy}, ${oz})\ndir = unreal.Vector(${dx}, ${dy}, ${dz})\ncolor = unreal.LinearColor(${cr}/255.0, ${cg}/255.0, ${cb}/255.0, ${ca}/255.0)\nunreal.SystemLibrary.draw_debug_cone(world, origin, dir, ${params.length}, ${params.angleWidth}, ${params.angleHeight}, ${params.numSides || 12}, color, ${duration}, 1.0)\n`;
|
|
109
|
-
return this.pyDraw(script
|
|
194
|
+
return this.pyDraw(script, {
|
|
195
|
+
action: 'debug_cone',
|
|
196
|
+
params: {
|
|
197
|
+
origin: params.origin,
|
|
198
|
+
direction: params.direction,
|
|
199
|
+
length: params.length,
|
|
200
|
+
angleWidth: params.angleWidth,
|
|
201
|
+
angleHeight: params.angleHeight,
|
|
202
|
+
numSides: params.numSides || 12,
|
|
203
|
+
color,
|
|
204
|
+
duration
|
|
205
|
+
}
|
|
206
|
+
});
|
|
110
207
|
}
|
|
111
208
|
async drawDebugString(params) {
|
|
112
209
|
const color = params.color || [255, 255, 255, 255];
|
|
@@ -114,7 +211,16 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
114
211
|
const [x, y, z] = params.location;
|
|
115
212
|
const [r, g, b, a] = color;
|
|
116
213
|
const script = `\nloc = unreal.Vector(${x}, ${y}, ${z})\ncolor = unreal.LinearColor(${r}/255.0, ${g}/255.0, ${b}/255.0, ${a}/255.0)\nunreal.SystemLibrary.draw_debug_string(world, loc, "${params.text.replace(/"/g, '\\"')}", None, color, ${duration})\n`;
|
|
117
|
-
return this.pyDraw(script
|
|
214
|
+
return this.pyDraw(script, {
|
|
215
|
+
action: 'debug_string',
|
|
216
|
+
params: {
|
|
217
|
+
location: params.location,
|
|
218
|
+
text: params.text,
|
|
219
|
+
color,
|
|
220
|
+
duration,
|
|
221
|
+
fontSize: params.fontSize
|
|
222
|
+
}
|
|
223
|
+
});
|
|
118
224
|
}
|
|
119
225
|
async drawDebugArrow(params) {
|
|
120
226
|
const color = params.color || [0, 255, 255, 255];
|
|
@@ -124,7 +230,17 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
124
230
|
const [ex, ey, ez] = params.end;
|
|
125
231
|
const [r, g, b, a] = color;
|
|
126
232
|
const script = `\nstart = unreal.Vector(${sx}, ${sy}, ${sz})\nend = unreal.Vector(${ex}, ${ey}, ${ez})\ncolor = unreal.LinearColor(${r}/255.0, ${g}/255.0, ${b}/255.0, ${a}/255.0)\nunreal.SystemLibrary.draw_debug_arrow(world, start, end, ${params.arrowSize || 10.0}, color, ${duration}, ${thickness})\n`;
|
|
127
|
-
return this.pyDraw(script
|
|
233
|
+
return this.pyDraw(script, {
|
|
234
|
+
action: 'debug_arrow',
|
|
235
|
+
params: {
|
|
236
|
+
start: params.start,
|
|
237
|
+
end: params.end,
|
|
238
|
+
arrowSize: params.arrowSize || 10.0,
|
|
239
|
+
color,
|
|
240
|
+
duration,
|
|
241
|
+
thickness
|
|
242
|
+
}
|
|
243
|
+
});
|
|
128
244
|
}
|
|
129
245
|
async drawDebugPoint(params) {
|
|
130
246
|
const size = params.size || 10.0;
|
|
@@ -133,7 +249,15 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
133
249
|
const [x, y, z] = params.location;
|
|
134
250
|
const [r, g, b, a] = color;
|
|
135
251
|
const script = `\nloc = unreal.Vector(${x}, ${y}, ${z})\ncolor = unreal.LinearColor(${r}/255.0, ${g}/255.0, ${b}/255.0, ${a}/255.0)\nunreal.SystemLibrary.draw_debug_point(world, loc, ${size}, color, ${duration})\n`;
|
|
136
|
-
return this.pyDraw(script
|
|
252
|
+
return this.pyDraw(script, {
|
|
253
|
+
action: 'debug_point',
|
|
254
|
+
params: {
|
|
255
|
+
location: params.location,
|
|
256
|
+
size,
|
|
257
|
+
color,
|
|
258
|
+
duration
|
|
259
|
+
}
|
|
260
|
+
});
|
|
137
261
|
}
|
|
138
262
|
async drawDebugCoordinateSystem(params) {
|
|
139
263
|
const rotation = params.rotation || [0, 0, 0];
|
|
@@ -153,7 +277,19 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
153
277
|
const [rp, ry, rr] = params.rotation;
|
|
154
278
|
const [r, g, b, a] = color;
|
|
155
279
|
const script = `\norigin = unreal.Vector(${ox}, ${oy}, ${oz})\nrot = unreal.Rotator(${rp}, ${ry}, ${rr})\ncolor = unreal.LinearColor(${r}/255.0, ${g}/255.0, ${b}/255.0, ${a}/255.0)\nunreal.SystemLibrary.draw_debug_frustum(world, origin, rot, ${params.fov}, ${aspectRatio}, ${nearPlane}, ${farPlane}, color, ${duration})\n`;
|
|
156
|
-
return this.pyDraw(script
|
|
280
|
+
return this.pyDraw(script, {
|
|
281
|
+
action: 'debug_frustum',
|
|
282
|
+
params: {
|
|
283
|
+
origin: params.origin,
|
|
284
|
+
rotation: params.rotation,
|
|
285
|
+
fov: params.fov,
|
|
286
|
+
aspectRatio,
|
|
287
|
+
nearPlane,
|
|
288
|
+
farPlane,
|
|
289
|
+
color,
|
|
290
|
+
duration
|
|
291
|
+
}
|
|
292
|
+
});
|
|
157
293
|
}
|
|
158
294
|
async clearDebugDrawings() {
|
|
159
295
|
return this.bridge.executeConsoleCommand('FlushPersistentDebugLines');
|
|
@@ -167,9 +303,7 @@ unreal.SystemLibrary.draw_debug_sphere(world, center, ${params.radius}, ${segmen
|
|
|
167
303
|
else {
|
|
168
304
|
commands.push('show Collision 0');
|
|
169
305
|
}
|
|
170
|
-
|
|
171
|
-
await this.bridge.executeConsoleCommand(cmd);
|
|
172
|
-
}
|
|
306
|
+
await this.bridge.executeConsoleCommands(commands);
|
|
173
307
|
return { success: true, message: `Collision visualization ${params.enabled ? 'enabled' : 'disabled'}` };
|
|
174
308
|
}
|
|
175
309
|
async showBounds(params) {
|
package/dist/tools/editor.d.ts
CHANGED
|
@@ -42,12 +42,19 @@ export declare class EditorTools {
|
|
|
42
42
|
}>;
|
|
43
43
|
buildLighting(): Promise<{
|
|
44
44
|
success: boolean;
|
|
45
|
-
message:
|
|
45
|
+
message: string;
|
|
46
46
|
error?: undefined;
|
|
47
|
+
details?: undefined;
|
|
48
|
+
} | {
|
|
49
|
+
success: boolean;
|
|
50
|
+
error: string;
|
|
51
|
+
details: string | undefined;
|
|
52
|
+
message?: undefined;
|
|
47
53
|
} | {
|
|
48
54
|
success: boolean;
|
|
49
|
-
error:
|
|
55
|
+
error: string;
|
|
50
56
|
message?: undefined;
|
|
57
|
+
details?: undefined;
|
|
51
58
|
}>;
|
|
52
59
|
setViewportCamera(location?: {
|
|
53
60
|
x: number;
|
package/dist/tools/editor.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { toVec3Object, toRotObject } from '../utils/normalize.js';
|
|
2
|
+
import { bestEffortInterpretedText, coerceString, interpretStandardResult } from '../utils/result-helpers.js';
|
|
2
3
|
export class EditorTools {
|
|
3
4
|
bridge;
|
|
4
5
|
constructor(bridge) {
|
|
@@ -65,28 +66,13 @@ else:
|
|
|
65
66
|
print('RESULT:' + json.dumps({'success': False, 'error': 'LevelEditorSubsystem not available'}))
|
|
66
67
|
`.trim();
|
|
67
68
|
const resp = await this.bridge.executePython(pythonCmd);
|
|
68
|
-
const
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
return { success: true, message: `PIE started (via ${method})` };
|
|
76
|
-
}
|
|
77
|
-
}
|
|
78
|
-
catch {
|
|
79
|
-
try {
|
|
80
|
-
// Fallback: handle non-JSON python dict-style output
|
|
81
|
-
const sanitized = m[1].replace(/'/g, '"').replace(/\bTrue\b/g, 'true').replace(/\bFalse\b/g, 'false');
|
|
82
|
-
const parsed = JSON.parse(sanitized);
|
|
83
|
-
if (parsed.success) {
|
|
84
|
-
const method = parsed.method || 'LevelEditorSubsystem';
|
|
85
|
-
return { success: true, message: `PIE started (via ${method})` };
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
|
-
catch { }
|
|
89
|
-
}
|
|
69
|
+
const interpreted = interpretStandardResult(resp, {
|
|
70
|
+
successMessage: 'PIE started',
|
|
71
|
+
failureMessage: 'Failed to start PIE'
|
|
72
|
+
});
|
|
73
|
+
if (interpreted.success) {
|
|
74
|
+
const method = coerceString(interpreted.payload.method) ?? 'LevelEditorSubsystem';
|
|
75
|
+
return { success: true, message: `PIE started (via ${method})` };
|
|
90
76
|
}
|
|
91
77
|
// If not verified, fall through to fallback
|
|
92
78
|
}
|
|
@@ -125,20 +111,18 @@ else:
|
|
|
125
111
|
print('RESULT:' + json.dumps({'success': False, 'error': 'LevelEditorSubsystem not available'}))
|
|
126
112
|
`.trim();
|
|
127
113
|
const resp = await this.bridge.executePython(pythonCmd);
|
|
128
|
-
const
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
return { success: true, message: `PIE stopped via ${method}` };
|
|
136
|
-
}
|
|
137
|
-
}
|
|
138
|
-
catch { }
|
|
114
|
+
const interpreted = interpretStandardResult(resp, {
|
|
115
|
+
successMessage: 'PIE stopped successfully',
|
|
116
|
+
failureMessage: 'Failed to stop PIE'
|
|
117
|
+
});
|
|
118
|
+
if (interpreted.success) {
|
|
119
|
+
const method = coerceString(interpreted.payload.method) ?? 'LevelEditorSubsystem';
|
|
120
|
+
return { success: true, message: `PIE stopped via ${method}` };
|
|
139
121
|
}
|
|
140
|
-
|
|
141
|
-
|
|
122
|
+
if (interpreted.error) {
|
|
123
|
+
return { success: false, error: interpreted.error };
|
|
124
|
+
}
|
|
125
|
+
return { success: false, error: 'Failed to stop PIE' };
|
|
142
126
|
}
|
|
143
127
|
catch {
|
|
144
128
|
// Fallback to console command
|
|
@@ -193,16 +177,18 @@ except Exception as e:
|
|
|
193
177
|
print('RESULT:' + json.dumps({'success': False, 'error': str(e)}))
|
|
194
178
|
`.trim();
|
|
195
179
|
const resp = await this.bridge.executePython(py);
|
|
196
|
-
const
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
}
|
|
203
|
-
catch { }
|
|
180
|
+
const interpreted = interpretStandardResult(resp, {
|
|
181
|
+
successMessage: 'Lighting build started',
|
|
182
|
+
failureMessage: 'Failed to build lighting'
|
|
183
|
+
});
|
|
184
|
+
if (interpreted.success) {
|
|
185
|
+
return { success: true, message: interpreted.message };
|
|
204
186
|
}
|
|
205
|
-
return {
|
|
187
|
+
return {
|
|
188
|
+
success: false,
|
|
189
|
+
error: interpreted.error ?? 'Failed to build lighting',
|
|
190
|
+
details: bestEffortInterpretedText(interpreted)
|
|
191
|
+
};
|
|
206
192
|
}
|
|
207
193
|
catch (err) {
|
|
208
194
|
return { success: false, error: `Failed to build lighting: ${err}` };
|
package/dist/tools/foliage.d.ts
CHANGED
|
@@ -14,22 +14,32 @@ export declare class FoliageTools {
|
|
|
14
14
|
groundSlope?: number;
|
|
15
15
|
}): Promise<{
|
|
16
16
|
success: boolean;
|
|
17
|
-
error:
|
|
17
|
+
error: string;
|
|
18
|
+
note?: undefined;
|
|
19
|
+
created?: undefined;
|
|
20
|
+
exists?: undefined;
|
|
21
|
+
method?: undefined;
|
|
22
|
+
assetPath?: undefined;
|
|
23
|
+
usedMesh?: undefined;
|
|
24
|
+
message?: undefined;
|
|
25
|
+
} | {
|
|
26
|
+
success: boolean;
|
|
27
|
+
error: string;
|
|
28
|
+
note: string | undefined;
|
|
18
29
|
created?: undefined;
|
|
19
30
|
exists?: undefined;
|
|
20
31
|
method?: undefined;
|
|
21
32
|
assetPath?: undefined;
|
|
22
33
|
usedMesh?: undefined;
|
|
23
|
-
note?: undefined;
|
|
24
34
|
message?: undefined;
|
|
25
35
|
} | {
|
|
26
36
|
success: boolean;
|
|
27
|
-
created:
|
|
28
|
-
exists:
|
|
29
|
-
method:
|
|
30
|
-
assetPath:
|
|
31
|
-
usedMesh:
|
|
32
|
-
note:
|
|
37
|
+
created: boolean;
|
|
38
|
+
exists: boolean;
|
|
39
|
+
method: string;
|
|
40
|
+
assetPath: string | undefined;
|
|
41
|
+
usedMesh: string | undefined;
|
|
42
|
+
note: string | undefined;
|
|
33
43
|
message: string;
|
|
34
44
|
error?: undefined;
|
|
35
45
|
}>;
|
|
@@ -41,20 +51,29 @@ export declare class FoliageTools {
|
|
|
41
51
|
eraseMode?: boolean;
|
|
42
52
|
}): Promise<{
|
|
43
53
|
success: boolean;
|
|
44
|
-
error:
|
|
54
|
+
error: string;
|
|
55
|
+
note?: undefined;
|
|
56
|
+
added?: undefined;
|
|
57
|
+
actor?: undefined;
|
|
58
|
+
component?: undefined;
|
|
59
|
+
usedMesh?: undefined;
|
|
60
|
+
message?: undefined;
|
|
61
|
+
} | {
|
|
62
|
+
success: boolean;
|
|
63
|
+
error: string;
|
|
64
|
+
note: string | undefined;
|
|
45
65
|
added?: undefined;
|
|
46
66
|
actor?: undefined;
|
|
47
67
|
component?: undefined;
|
|
48
68
|
usedMesh?: undefined;
|
|
49
|
-
note?: undefined;
|
|
50
69
|
message?: undefined;
|
|
51
70
|
} | {
|
|
52
71
|
success: boolean;
|
|
53
|
-
added:
|
|
54
|
-
actor:
|
|
55
|
-
component:
|
|
56
|
-
usedMesh:
|
|
57
|
-
note:
|
|
72
|
+
added: number;
|
|
73
|
+
actor: string | undefined;
|
|
74
|
+
component: string | undefined;
|
|
75
|
+
usedMesh: string | undefined;
|
|
76
|
+
note: string | undefined;
|
|
58
77
|
message: string;
|
|
59
78
|
error?: undefined;
|
|
60
79
|
}>;
|