@drawtonomy/sdk 0.4.0 → 0.5.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/LICENSE +190 -0
- package/README.ja.md +2 -2
- package/README.md +29 -2
- package/dist/exporter/index.d.ts +9 -0
- package/dist/exporter/index.d.ts.map +1 -0
- package/dist/exporter/index.js +15 -0
- package/dist/exporter/index.js.map +1 -0
- package/dist/exporter/laneCenterline.d.ts +38 -0
- package/dist/exporter/laneCenterline.d.ts.map +1 -0
- package/dist/exporter/laneCenterline.js +94 -0
- package/dist/exporter/laneCenterline.js.map +1 -0
- package/dist/exporter/opendrive.d.ts +6 -0
- package/dist/exporter/opendrive.d.ts.map +1 -0
- package/dist/exporter/opendrive.js +565 -0
- package/dist/exporter/opendrive.js.map +1 -0
- package/dist/exporter/openscenario.d.ts +30 -0
- package/dist/exporter/openscenario.d.ts.map +1 -0
- package/dist/exporter/openscenario.js +393 -0
- package/dist/exporter/openscenario.js.map +1 -0
- package/dist/exporter/packageEsmini.d.ts +18 -0
- package/dist/exporter/packageEsmini.d.ts.map +1 -0
- package/dist/exporter/packageEsmini.js +23 -0
- package/dist/exporter/packageEsmini.js.map +1 -0
- package/dist/exporter/sanitize.d.ts +8 -0
- package/dist/exporter/sanitize.d.ts.map +1 -0
- package/dist/exporter/sanitize.js +29 -0
- package/dist/exporter/sanitize.js.map +1 -0
- package/dist/exporter/trajectory.d.ts +41 -0
- package/dist/exporter/trajectory.d.ts.map +1 -0
- package/dist/exporter/trajectory.js +200 -0
- package/dist/exporter/trajectory.js.map +1 -0
- package/dist/exporter/units.d.ts +16 -0
- package/dist/exporter/units.d.ts.map +1 -0
- package/dist/exporter/units.js +38 -0
- package/dist/exporter/units.js.map +1 -0
- package/dist/exporter/zip.d.ts +13 -0
- package/dist/exporter/zip.d.ts.map +1 -0
- package/dist/exporter/zip.js +137 -0
- package/dist/exporter/zip.js.map +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -0
- package/dist/index.js.map +1 -1
- package/dist/types.d.ts +22 -7
- package/dist/types.d.ts.map +1 -1
- package/package.json +9 -10
|
@@ -0,0 +1,393 @@
|
|
|
1
|
+
// OpenSCENARIO 1.3 (.xosc) exporter — emits scenario actors and trajectories
|
|
2
|
+
// from a snapshot. No external library dependencies.
|
|
3
|
+
//
|
|
4
|
+
// Design:
|
|
5
|
+
// - Each Vehicle / Pedestrian shape becomes a ScenarioObject
|
|
6
|
+
// - 3D rendering is delegated to the player; we only emit BoundingBox + category
|
|
7
|
+
// - Initial pose is a WorldPosition + TeleportAction
|
|
8
|
+
// - The road network is referenced via <LogicFile> pointing to the paired .xodr
|
|
9
|
+
// - Dynamic animations are emitted as <FollowTrajectoryAction> stories
|
|
10
|
+
import { buildPathTrajectory } from './trajectory';
|
|
11
|
+
import { escapeXml, fmt, pxToEnuX, pxToEnuY, pxToMeter } from './units';
|
|
12
|
+
/** Map a vehicle template id to a normalized form (legacy id rewrites). */
|
|
13
|
+
const LEGACY_TEMPLATE_ID_MAP = {
|
|
14
|
+
black: 'filled', // legacy "black" pedestrian template renamed to "filled"
|
|
15
|
+
};
|
|
16
|
+
/** Pedestrian template id patterns. */
|
|
17
|
+
const PEDESTRIAN_PATTERNS = [/^pedestrian/, /^walk/, /^simple/, /^filled/];
|
|
18
|
+
function defaultResolveTemplateId(id) {
|
|
19
|
+
return LEGACY_TEMPLATE_ID_MAP[id] || id;
|
|
20
|
+
}
|
|
21
|
+
function defaultIsPedestrianTemplate(id) {
|
|
22
|
+
const resolved = defaultResolveTemplateId(id || '');
|
|
23
|
+
return PEDESTRIAN_PATTERNS.some((re) => re.test(resolved));
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Map a vehicle template id to an OpenSCENARIO vehicleCategory.
|
|
27
|
+
* Spec values: car, van, truck, trailer, semitrailer, bus, motorbike, bicycle, train, tram.
|
|
28
|
+
*/
|
|
29
|
+
export function templateIdToVehicleCategory(templateId, resolver) {
|
|
30
|
+
const resolveId = resolver?.resolveTemplateId ?? defaultResolveTemplateId;
|
|
31
|
+
const id = resolveId(templateId);
|
|
32
|
+
switch (id) {
|
|
33
|
+
case 'sedan': return 'car';
|
|
34
|
+
case 'bus': return 'bus';
|
|
35
|
+
case 'truck': return 'truck';
|
|
36
|
+
case 'motorcycle':
|
|
37
|
+
case 'motorcycle2':
|
|
38
|
+
return 'motorbike';
|
|
39
|
+
case 'bicycle':
|
|
40
|
+
case 'bicycle2':
|
|
41
|
+
return 'bicycle';
|
|
42
|
+
case 'amr':
|
|
43
|
+
case 'amr2':
|
|
44
|
+
case 'robovac':
|
|
45
|
+
return 'car';
|
|
46
|
+
default:
|
|
47
|
+
return 'car';
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Default Performance values per category (matches esmini demo conventions).
|
|
52
|
+
*/
|
|
53
|
+
function defaultPerformance(category) {
|
|
54
|
+
switch (category) {
|
|
55
|
+
case 'truck':
|
|
56
|
+
case 'bus':
|
|
57
|
+
return { maxSpeed: 25, maxAccel: 2, maxDecel: 6 };
|
|
58
|
+
case 'motorbike':
|
|
59
|
+
return { maxSpeed: 60, maxAccel: 6, maxDecel: 9 };
|
|
60
|
+
case 'bicycle':
|
|
61
|
+
return { maxSpeed: 8, maxAccel: 2, maxDecel: 4 };
|
|
62
|
+
default:
|
|
63
|
+
return { maxSpeed: 50, maxAccel: 5, maxDecel: 10 };
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
function defaultAxles(length, width) {
|
|
67
|
+
const wheelbase = Math.max(length * 0.6, 0.3);
|
|
68
|
+
const trackWidth = Math.max(width * 0.85, 0.3);
|
|
69
|
+
return {
|
|
70
|
+
front: { positionX: wheelbase, trackWidth },
|
|
71
|
+
rear: { positionX: 0, trackWidth },
|
|
72
|
+
};
|
|
73
|
+
}
|
|
74
|
+
function collectEntities(snapshot, resolver) {
|
|
75
|
+
const out = [];
|
|
76
|
+
let counter = 0;
|
|
77
|
+
const isPedestrian = resolver?.isPedestrianTemplate ?? defaultIsPedestrianTemplate;
|
|
78
|
+
const resolveId = resolver?.resolveTemplateId ?? defaultResolveTemplateId;
|
|
79
|
+
// Path footprints are a canvas-side "trail preview" — multiple ghost copies
|
|
80
|
+
// of the same vehicle along a path. In a 3D scene we want a single moving
|
|
81
|
+
// vehicle, so only the leading footprint (footprintIds[0]) is exported as
|
|
82
|
+
// a ScenarioObject; the rest are dropped.
|
|
83
|
+
const followerFootprintIds = new Set();
|
|
84
|
+
for (const shape of snapshot.shapes) {
|
|
85
|
+
if (shape.type !== 'linestring')
|
|
86
|
+
continue;
|
|
87
|
+
const ls = shape;
|
|
88
|
+
if (!ls.props.isPath)
|
|
89
|
+
continue;
|
|
90
|
+
const ids = ls.props.footprintIds ?? [];
|
|
91
|
+
for (let i = 1; i < ids.length; i++)
|
|
92
|
+
followerFootprintIds.add(ids[i]);
|
|
93
|
+
}
|
|
94
|
+
for (const shape of snapshot.shapes) {
|
|
95
|
+
if (shape.type !== 'vehicle')
|
|
96
|
+
continue;
|
|
97
|
+
if (followerFootprintIds.has(shape.id))
|
|
98
|
+
continue;
|
|
99
|
+
const v = shape;
|
|
100
|
+
const id = resolveId(v.props.templateId || '');
|
|
101
|
+
const isPed = isPedestrian(v.props.templateId || '');
|
|
102
|
+
// Vehicle template orientation: front faces -Y in canvas space, so the
|
|
103
|
+
// shape's bbox dimensions map as length=h (front-back axis), width=w.
|
|
104
|
+
const widthM = pxToMeter(v.props.w);
|
|
105
|
+
const lengthM = pxToMeter(v.props.h);
|
|
106
|
+
const category = isPed ? 'pedestrian' : templateIdToVehicleCategory(id, resolver);
|
|
107
|
+
let heightM;
|
|
108
|
+
if (isPed)
|
|
109
|
+
heightM = 1.7;
|
|
110
|
+
else if (category === 'truck' || category === 'bus')
|
|
111
|
+
heightM = 3.0;
|
|
112
|
+
else if (category === 'motorbike')
|
|
113
|
+
heightM = 1.2;
|
|
114
|
+
else if (category === 'bicycle')
|
|
115
|
+
heightM = 1.2;
|
|
116
|
+
else
|
|
117
|
+
heightM = 1.5;
|
|
118
|
+
out.push({
|
|
119
|
+
shape: v,
|
|
120
|
+
isPedestrian: isPed,
|
|
121
|
+
name: isPed ? `Pedestrian_${counter++}` : `Vehicle_${counter++}`,
|
|
122
|
+
width: widthM,
|
|
123
|
+
length: lengthM,
|
|
124
|
+
height: heightM,
|
|
125
|
+
category,
|
|
126
|
+
worldX: pxToEnuX(v.x),
|
|
127
|
+
worldY: pxToEnuY(v.y),
|
|
128
|
+
// SVG template orientation: front faces -Y in canvas space, so a
|
|
129
|
+
// rotation=0 vehicle points "up" on the canvas. ENU has y-up and CCW
|
|
130
|
+
// positive headings, so canvas -Y maps to ENU +Y, i.e. heading=π/2
|
|
131
|
+
// when rotation=0. The π/2 offset and sign flip account for both.
|
|
132
|
+
heading: -((v.rotation || 0) * Math.PI) / 180 + Math.PI / 2,
|
|
133
|
+
});
|
|
134
|
+
}
|
|
135
|
+
return out;
|
|
136
|
+
}
|
|
137
|
+
function emitFileHeader() {
|
|
138
|
+
const date = new Date().toISOString();
|
|
139
|
+
return ` <FileHeader revMajor="1" revMinor="3" date="${date}" description="Generated by drawtonomy" author="drawtonomy"/>`;
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* Map a vehicleCategory to a bundled esmini 3D model path. An explicit
|
|
143
|
+
* model3d is required, otherwise scaleMode is ignored and the BoundingBox
|
|
144
|
+
* has no effect on rendering size.
|
|
145
|
+
*/
|
|
146
|
+
function getModel3d(category) {
|
|
147
|
+
switch (category) {
|
|
148
|
+
case 'truck': return '../models/truck_yellow.osgb';
|
|
149
|
+
case 'bus': return '../models/bus_blue.osgb';
|
|
150
|
+
case 'motorbike': return '../models/mc.osgb';
|
|
151
|
+
case 'bicycle': return '../models/cyclist.osgb';
|
|
152
|
+
case 'pedestrian': return '../models/walkman.osgb';
|
|
153
|
+
default: return '../models/car_white.osgb';
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
function emitVehicleEntity(e) {
|
|
157
|
+
const perf = defaultPerformance(e.category);
|
|
158
|
+
const axles = defaultAxles(e.length, e.width);
|
|
159
|
+
const model3d = getModel3d(e.category);
|
|
160
|
+
const lines = [];
|
|
161
|
+
lines.push(` <ScenarioObject name="${escapeXml(e.name)}">`);
|
|
162
|
+
lines.push(` <Vehicle name="${escapeXml(e.shape.props.templateId || 'vehicle')}" vehicleCategory="${e.category}" model3d="${model3d}">`);
|
|
163
|
+
lines.push(` <BoundingBox>`);
|
|
164
|
+
lines.push(` <Center x="${fmt(e.length / 2)}" y="0" z="${fmt(e.height / 2)}"/>`);
|
|
165
|
+
lines.push(` <Dimensions width="${fmt(e.width)}" length="${fmt(e.length)}" height="${fmt(e.height)}"/>`);
|
|
166
|
+
lines.push(` </BoundingBox>`);
|
|
167
|
+
lines.push(` <Performance maxSpeed="${fmt(perf.maxSpeed)}" maxAcceleration="${fmt(perf.maxAccel)}" maxDeceleration="${fmt(perf.maxDecel)}"/>`);
|
|
168
|
+
lines.push(` <Axles>`);
|
|
169
|
+
lines.push(` <FrontAxle maxSteering="0.5" wheelDiameter="0.5" trackWidth="${fmt(axles.front.trackWidth)}" positionX="${fmt(axles.front.positionX)}" positionZ="0.25"/>`);
|
|
170
|
+
lines.push(` <RearAxle maxSteering="0" wheelDiameter="0.5" trackWidth="${fmt(axles.rear.trackWidth)}" positionX="${fmt(axles.rear.positionX)}" positionZ="0.25"/>`);
|
|
171
|
+
lines.push(` </Axles>`);
|
|
172
|
+
// scaleMode=ModelToBB tells the player to deform the model so it matches
|
|
173
|
+
// the BoundingBox dimensions. Without it the model is drawn at its native
|
|
174
|
+
// size and the BoundingBox has no visual effect. The name is read as
|
|
175
|
+
// "Model is fitted To BoundingBox" — the model is what gets scaled.
|
|
176
|
+
lines.push(` <Properties>`);
|
|
177
|
+
lines.push(` <Property name="scaleMode" value="ModelToBB"/>`);
|
|
178
|
+
lines.push(` </Properties>`);
|
|
179
|
+
lines.push(` </Vehicle>`);
|
|
180
|
+
lines.push(` </ScenarioObject>`);
|
|
181
|
+
return lines.join('\n');
|
|
182
|
+
}
|
|
183
|
+
function emitPedestrianEntity(e) {
|
|
184
|
+
const model3d = getModel3d('pedestrian');
|
|
185
|
+
const lines = [];
|
|
186
|
+
lines.push(` <ScenarioObject name="${escapeXml(e.name)}">`);
|
|
187
|
+
lines.push(` <Pedestrian name="${escapeXml(e.shape.props.templateId || 'pedestrian')}" pedestrianCategory="pedestrian" mass="80" model3d="${model3d}">`);
|
|
188
|
+
lines.push(` <BoundingBox>`);
|
|
189
|
+
lines.push(` <Center x="0" y="0" z="${fmt(e.height / 2)}"/>`);
|
|
190
|
+
lines.push(` <Dimensions width="${fmt(e.width)}" length="${fmt(e.length)}" height="${fmt(e.height)}"/>`);
|
|
191
|
+
lines.push(` </BoundingBox>`);
|
|
192
|
+
lines.push(` <Properties>`);
|
|
193
|
+
lines.push(` <Property name="scaleMode" value="ModelToBB"/>`);
|
|
194
|
+
lines.push(` </Properties>`);
|
|
195
|
+
lines.push(` </Pedestrian>`);
|
|
196
|
+
lines.push(` </ScenarioObject>`);
|
|
197
|
+
return lines.join('\n');
|
|
198
|
+
}
|
|
199
|
+
function emitInitTeleport(e) {
|
|
200
|
+
return emitInitTeleportAt(e, e.worldX, e.worldY, e.heading);
|
|
201
|
+
}
|
|
202
|
+
function emitInitTeleportAt(e, x, y, heading) {
|
|
203
|
+
const lines = [];
|
|
204
|
+
lines.push(` <Private entityRef="${escapeXml(e.name)}">`);
|
|
205
|
+
lines.push(` <PrivateAction>`);
|
|
206
|
+
lines.push(` <TeleportAction>`);
|
|
207
|
+
lines.push(` <Position>`);
|
|
208
|
+
lines.push(` <WorldPosition x="${fmt(x)}" y="${fmt(y)}" z="0" h="${fmt(heading)}" p="0" r="0"/>`);
|
|
209
|
+
lines.push(` </Position>`);
|
|
210
|
+
lines.push(` </TeleportAction>`);
|
|
211
|
+
lines.push(` </PrivateAction>`);
|
|
212
|
+
lines.push(` </Private>`);
|
|
213
|
+
return lines.join('\n');
|
|
214
|
+
}
|
|
215
|
+
function collectPathAssignments(snapshot, entities) {
|
|
216
|
+
const out = [];
|
|
217
|
+
const shapeMap = new Map();
|
|
218
|
+
for (const s of snapshot.shapes)
|
|
219
|
+
shapeMap.set(s.id, s);
|
|
220
|
+
const shapeIdToEntityName = new Map();
|
|
221
|
+
for (const e of entities)
|
|
222
|
+
shapeIdToEntityName.set(e.shape.id, e.name);
|
|
223
|
+
let trajCounter = 0;
|
|
224
|
+
for (const shape of snapshot.shapes) {
|
|
225
|
+
if (shape.type !== 'linestring')
|
|
226
|
+
continue;
|
|
227
|
+
const ls = shape;
|
|
228
|
+
if (!ls.props.isPath)
|
|
229
|
+
continue;
|
|
230
|
+
const footprintIds = ls.props.footprintIds ?? [];
|
|
231
|
+
const fp = ls.props.footprint;
|
|
232
|
+
if (footprintIds.length === 0)
|
|
233
|
+
continue;
|
|
234
|
+
const headFootprintId = footprintIds[0];
|
|
235
|
+
const entityName = shapeIdToEntityName.get(headFootprintId);
|
|
236
|
+
if (!entityName)
|
|
237
|
+
continue;
|
|
238
|
+
const points = [];
|
|
239
|
+
for (const pid of ls.props.pointIds) {
|
|
240
|
+
const p = shapeMap.get(pid);
|
|
241
|
+
if (p)
|
|
242
|
+
points.push({ x: p.x, y: p.y });
|
|
243
|
+
}
|
|
244
|
+
if (points.length < 2)
|
|
245
|
+
continue;
|
|
246
|
+
const samples = buildPathTrajectory({
|
|
247
|
+
points,
|
|
248
|
+
tValues: fp?.tValues,
|
|
249
|
+
interval: fp?.interval,
|
|
250
|
+
offset: fp?.offset,
|
|
251
|
+
});
|
|
252
|
+
if (samples.length < 2)
|
|
253
|
+
continue;
|
|
254
|
+
out.push({
|
|
255
|
+
entityName,
|
|
256
|
+
trajectoryName: `path${trajCounter++}_${entityName}`,
|
|
257
|
+
samples,
|
|
258
|
+
});
|
|
259
|
+
}
|
|
260
|
+
return out;
|
|
261
|
+
}
|
|
262
|
+
function emitFollowTrajectoryStory(assignments) {
|
|
263
|
+
if (!assignments.length)
|
|
264
|
+
return [];
|
|
265
|
+
const lines = [];
|
|
266
|
+
lines.push(` <Story name="MovingStory">`);
|
|
267
|
+
lines.push(` <Act name="MovingAct">`);
|
|
268
|
+
for (const a of assignments) {
|
|
269
|
+
lines.push(` <ManeuverGroup name="MG_${escapeXml(a.entityName)}" maximumExecutionCount="1">`);
|
|
270
|
+
lines.push(` <Actors selectTriggeringEntities="false">`);
|
|
271
|
+
lines.push(` <EntityRef entityRef="${escapeXml(a.entityName)}"/>`);
|
|
272
|
+
lines.push(` </Actors>`);
|
|
273
|
+
lines.push(` <Maneuver name="MV_${escapeXml(a.entityName)}">`);
|
|
274
|
+
lines.push(` <Event name="EV_${escapeXml(a.entityName)}" priority="override">`);
|
|
275
|
+
lines.push(` <Action name="ACT_${escapeXml(a.entityName)}">`);
|
|
276
|
+
lines.push(` <PrivateAction>`);
|
|
277
|
+
lines.push(` <RoutingAction>`);
|
|
278
|
+
lines.push(` <FollowTrajectoryAction>`);
|
|
279
|
+
lines.push(` <TrajectoryRef>`);
|
|
280
|
+
lines.push(` <Trajectory name="${escapeXml(a.trajectoryName)}" closed="false">`);
|
|
281
|
+
lines.push(` <ParameterDeclarations/>`);
|
|
282
|
+
lines.push(` <Shape>`);
|
|
283
|
+
lines.push(` <Polyline>`);
|
|
284
|
+
for (const s of a.samples) {
|
|
285
|
+
lines.push(` <Vertex time="${fmt(s.time)}">`);
|
|
286
|
+
lines.push(` <Position>`);
|
|
287
|
+
lines.push(` <WorldPosition x="${fmt(s.x)}" y="${fmt(s.y)}" z="0" h="${fmt(s.heading)}" p="0" r="0"/>`);
|
|
288
|
+
lines.push(` </Position>`);
|
|
289
|
+
lines.push(` </Vertex>`);
|
|
290
|
+
}
|
|
291
|
+
lines.push(` </Polyline>`);
|
|
292
|
+
lines.push(` </Shape>`);
|
|
293
|
+
lines.push(` </Trajectory>`);
|
|
294
|
+
lines.push(` </TrajectoryRef>`);
|
|
295
|
+
lines.push(` <TimeReference>`);
|
|
296
|
+
lines.push(` <Timing domainAbsoluteRelative="absolute" scale="1.0" offset="0.0"/>`);
|
|
297
|
+
lines.push(` </TimeReference>`);
|
|
298
|
+
lines.push(` <TrajectoryFollowingMode followingMode="position"/>`);
|
|
299
|
+
lines.push(` </FollowTrajectoryAction>`);
|
|
300
|
+
lines.push(` </RoutingAction>`);
|
|
301
|
+
lines.push(` </PrivateAction>`);
|
|
302
|
+
lines.push(` </Action>`);
|
|
303
|
+
lines.push(` <StartTrigger>`);
|
|
304
|
+
lines.push(` <ConditionGroup>`);
|
|
305
|
+
lines.push(` <Condition name="Start_${escapeXml(a.entityName)}" delay="0" conditionEdge="none">`);
|
|
306
|
+
lines.push(` <ByValueCondition>`);
|
|
307
|
+
lines.push(` <SimulationTimeCondition value="0" rule="greaterOrEqual"/>`);
|
|
308
|
+
lines.push(` </ByValueCondition>`);
|
|
309
|
+
lines.push(` </Condition>`);
|
|
310
|
+
lines.push(` </ConditionGroup>`);
|
|
311
|
+
lines.push(` </StartTrigger>`);
|
|
312
|
+
lines.push(` </Event>`);
|
|
313
|
+
lines.push(` </Maneuver>`);
|
|
314
|
+
lines.push(` </ManeuverGroup>`);
|
|
315
|
+
}
|
|
316
|
+
lines.push(` <StartTrigger>`);
|
|
317
|
+
lines.push(` <ConditionGroup>`);
|
|
318
|
+
lines.push(` <Condition name="ActStart" delay="0" conditionEdge="none">`);
|
|
319
|
+
lines.push(` <ByValueCondition>`);
|
|
320
|
+
lines.push(` <SimulationTimeCondition value="0" rule="greaterOrEqual"/>`);
|
|
321
|
+
lines.push(` </ByValueCondition>`);
|
|
322
|
+
lines.push(` </Condition>`);
|
|
323
|
+
lines.push(` </ConditionGroup>`);
|
|
324
|
+
lines.push(` </StartTrigger>`);
|
|
325
|
+
lines.push(` </Act>`);
|
|
326
|
+
lines.push(` </Story>`);
|
|
327
|
+
return lines;
|
|
328
|
+
}
|
|
329
|
+
/**
|
|
330
|
+
* Build an OpenSCENARIO 1.3 XML document from a snapshot.
|
|
331
|
+
*/
|
|
332
|
+
export function exportToOpenScenario(snapshot, options = {}) {
|
|
333
|
+
const xodrFilename = options.xodrFilename ?? '';
|
|
334
|
+
const entities = collectEntities(snapshot, options.templateResolver);
|
|
335
|
+
const lines = [];
|
|
336
|
+
lines.push(`<?xml version="1.0" encoding="UTF-8"?>`);
|
|
337
|
+
lines.push(`<OpenSCENARIO>`);
|
|
338
|
+
lines.push(emitFileHeader());
|
|
339
|
+
lines.push(` <ParameterDeclarations/>`);
|
|
340
|
+
lines.push(` <CatalogLocations/>`);
|
|
341
|
+
lines.push(` <RoadNetwork>`);
|
|
342
|
+
if (xodrFilename) {
|
|
343
|
+
lines.push(` <LogicFile filepath="${escapeXml(xodrFilename)}"/>`);
|
|
344
|
+
}
|
|
345
|
+
else {
|
|
346
|
+
lines.push(` <LogicFile filepath=""/>`);
|
|
347
|
+
}
|
|
348
|
+
lines.push(` </RoadNetwork>`);
|
|
349
|
+
lines.push(` <Entities>`);
|
|
350
|
+
for (const e of entities) {
|
|
351
|
+
lines.push(e.isPedestrian ? emitPedestrianEntity(e) : emitVehicleEntity(e));
|
|
352
|
+
}
|
|
353
|
+
lines.push(` </Entities>`);
|
|
354
|
+
// For entities bound to a trajectory, snap the Init TeleportAction to the
|
|
355
|
+
// trajectory start so the entity does not "jump" once the trajectory takes
|
|
356
|
+
// over. The path assignments are computed before Init Actions are emitted.
|
|
357
|
+
const pathAssignments = collectPathAssignments(snapshot, entities);
|
|
358
|
+
const pathStartByEntity = new Map();
|
|
359
|
+
for (const a of pathAssignments) {
|
|
360
|
+
if (a.samples.length > 0)
|
|
361
|
+
pathStartByEntity.set(a.entityName, a.samples[0]);
|
|
362
|
+
}
|
|
363
|
+
lines.push(` <Storyboard>`);
|
|
364
|
+
lines.push(` <Init>`);
|
|
365
|
+
lines.push(` <Actions>`);
|
|
366
|
+
for (const e of entities) {
|
|
367
|
+
const pathStart = pathStartByEntity.get(e.name);
|
|
368
|
+
if (pathStart) {
|
|
369
|
+
lines.push(emitInitTeleportAt(e, pathStart.x, pathStart.y, pathStart.heading));
|
|
370
|
+
}
|
|
371
|
+
else {
|
|
372
|
+
lines.push(emitInitTeleport(e));
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
lines.push(` </Actions>`);
|
|
376
|
+
lines.push(` </Init>`);
|
|
377
|
+
for (const line of emitFollowTrajectoryStory(pathAssignments)) {
|
|
378
|
+
lines.push(line);
|
|
379
|
+
}
|
|
380
|
+
lines.push(` <StopTrigger>`);
|
|
381
|
+
lines.push(` <ConditionGroup>`);
|
|
382
|
+
lines.push(` <Condition name="StopCondition" delay="0" conditionEdge="rising">`);
|
|
383
|
+
lines.push(` <ByValueCondition>`);
|
|
384
|
+
lines.push(` <SimulationTimeCondition value="60" rule="greaterThan"/>`);
|
|
385
|
+
lines.push(` </ByValueCondition>`);
|
|
386
|
+
lines.push(` </Condition>`);
|
|
387
|
+
lines.push(` </ConditionGroup>`);
|
|
388
|
+
lines.push(` </StopTrigger>`);
|
|
389
|
+
lines.push(` </Storyboard>`);
|
|
390
|
+
lines.push(`</OpenSCENARIO>`);
|
|
391
|
+
return lines.join('\n');
|
|
392
|
+
}
|
|
393
|
+
//# sourceMappingURL=openscenario.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"openscenario.js","sourceRoot":"","sources":["../../src/exporter/openscenario.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { DrawtonomySnapshot } from '../types';
|
|
2
|
+
import { type TemplateResolver } from './openscenario';
|
|
3
|
+
export interface EsminiPackageOptions {
|
|
4
|
+
/**
|
|
5
|
+
* Base name (without extension). Sanitized before use; falls back to
|
|
6
|
+
* "drawtonomy" if the input is empty or only invalid characters.
|
|
7
|
+
*/
|
|
8
|
+
baseName?: string;
|
|
9
|
+
/** Optional template resolver hook for xosc. */
|
|
10
|
+
templateResolver?: TemplateResolver;
|
|
11
|
+
}
|
|
12
|
+
export interface EsminiPackageResult {
|
|
13
|
+
blob: Blob;
|
|
14
|
+
/** Sanitized base name actually used for the archive. */
|
|
15
|
+
baseName: string;
|
|
16
|
+
}
|
|
17
|
+
export declare function buildEsminiZip(snapshot: DrawtonomySnapshot, options?: EsminiPackageOptions): EsminiPackageResult;
|
|
18
|
+
//# sourceMappingURL=packageEsmini.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"packageEsmini.d.ts","sourceRoot":"","sources":["../../src/exporter/packageEsmini.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,UAAU,CAAA;AAElD,OAAO,EAAwB,KAAK,gBAAgB,EAAE,MAAM,gBAAgB,CAAA;AAI5E,MAAM,WAAW,oBAAoB;IACnC;;;OAGG;IACH,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,gDAAgD;IAChD,gBAAgB,CAAC,EAAE,gBAAgB,CAAA;CACpC;AAED,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,IAAI,CAAA;IACV,yDAAyD;IACzD,QAAQ,EAAE,MAAM,CAAA;CACjB;AAED,wBAAgB,cAAc,CAC5B,QAAQ,EAAE,kBAAkB,EAC5B,OAAO,GAAE,oBAAyB,GACjC,mBAAmB,CAarB"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
// One-shot helper that builds an esmini-friendly zip from a snapshot:
|
|
2
|
+
// `<baseName>.zip` containing `<baseName>/<baseName>.xodr` and
|
|
3
|
+
// `<baseName>/<baseName>.xosc`. The xosc <LogicFile> reference uses the same
|
|
4
|
+
// baseName so the bundle works without renames.
|
|
5
|
+
import { exportToOpenDrive } from './opendrive';
|
|
6
|
+
import { exportToOpenScenario } from './openscenario';
|
|
7
|
+
import { sanitizeFileBaseName } from './sanitize';
|
|
8
|
+
import { buildZip } from './zip';
|
|
9
|
+
export function buildEsminiZip(snapshot, options = {}) {
|
|
10
|
+
const sanitized = options.baseName ? sanitizeFileBaseName(options.baseName) : null;
|
|
11
|
+
const baseName = sanitized ?? 'drawtonomy';
|
|
12
|
+
const xodrXml = exportToOpenDrive(snapshot);
|
|
13
|
+
const xoscXml = exportToOpenScenario(snapshot, {
|
|
14
|
+
xodrFilename: `${baseName}.xodr`,
|
|
15
|
+
templateResolver: options.templateResolver,
|
|
16
|
+
});
|
|
17
|
+
const blob = buildZip([
|
|
18
|
+
{ path: `${baseName}/${baseName}.xodr`, data: xodrXml },
|
|
19
|
+
{ path: `${baseName}/${baseName}.xosc`, data: xoscXml },
|
|
20
|
+
]);
|
|
21
|
+
return { blob, baseName };
|
|
22
|
+
}
|
|
23
|
+
//# sourceMappingURL=packageEsmini.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"packageEsmini.js","sourceRoot":"","sources":["../../src/exporter/packageEsmini.ts"],"names":[],"mappings":"AAAA,sEAAsE;AACtE,+DAA+D;AAC/D,6EAA6E;AAC7E,gDAAgD;AAGhD,OAAO,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAA;AAC/C,OAAO,EAAE,oBAAoB,EAAyB,MAAM,gBAAgB,CAAA;AAC5E,OAAO,EAAE,oBAAoB,EAAE,MAAM,YAAY,CAAA;AACjD,OAAO,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAA;AAkBhC,MAAM,UAAU,cAAc,CAC5B,QAA4B,EAC5B,UAAgC,EAAE;IAElC,MAAM,SAAS,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,oBAAoB,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,IAAI,CAAA;IAClF,MAAM,QAAQ,GAAG,SAAS,IAAI,YAAY,CAAA;IAC1C,MAAM,OAAO,GAAG,iBAAiB,CAAC,QAAQ,CAAC,CAAA;IAC3C,MAAM,OAAO,GAAG,oBAAoB,CAAC,QAAQ,EAAE;QAC7C,YAAY,EAAE,GAAG,QAAQ,OAAO;QAChC,gBAAgB,EAAE,OAAO,CAAC,gBAAgB;KAC3C,CAAC,CAAA;IACF,MAAM,IAAI,GAAG,QAAQ,CAAC;QACpB,EAAE,IAAI,EAAE,GAAG,QAAQ,IAAI,QAAQ,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE;QACvD,EAAE,IAAI,EAAE,GAAG,QAAQ,IAAI,QAAQ,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE;KACxD,CAAC,CAAA;IACF,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,CAAA;AAC3B,CAAC"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Strip characters that are not OS / zip safe from a file base name.
|
|
3
|
+
* - /, \, :, *, ?, ", <, >, |, NUL, control chars → "_"
|
|
4
|
+
* - Runs of whitespace collapse to one space; outer whitespace / dots trim
|
|
5
|
+
* - Empty / "." / ".." returns null (caller falls back to a default name)
|
|
6
|
+
*/
|
|
7
|
+
export declare function sanitizeFileBaseName(input: string): string | null;
|
|
8
|
+
//# sourceMappingURL=sanitize.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sanitize.d.ts","sourceRoot":"","sources":["../../src/exporter/sanitize.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,wBAAgB,oBAAoB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAgBjE"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Strip characters that are not OS / zip safe from a file base name.
|
|
3
|
+
* - /, \, :, *, ?, ", <, >, |, NUL, control chars → "_"
|
|
4
|
+
* - Runs of whitespace collapse to one space; outer whitespace / dots trim
|
|
5
|
+
* - Empty / "." / ".." returns null (caller falls back to a default name)
|
|
6
|
+
*/
|
|
7
|
+
export function sanitizeFileBaseName(input) {
|
|
8
|
+
if (!input)
|
|
9
|
+
return null;
|
|
10
|
+
let s = input
|
|
11
|
+
// eslint-disable-next-line no-control-regex
|
|
12
|
+
.replace(/[\/\\:*?"<>|\x00-\x1f]/g, '_')
|
|
13
|
+
.replace(/\s+/g, ' ')
|
|
14
|
+
.trim()
|
|
15
|
+
.replace(/^\.+|\.+$/g, '');
|
|
16
|
+
if (!s)
|
|
17
|
+
return null;
|
|
18
|
+
if (s === '.' || s === '..')
|
|
19
|
+
return null;
|
|
20
|
+
// Reject pointless names made of only underscores / whitespace; the caller
|
|
21
|
+
// falls back to a default name in that case.
|
|
22
|
+
if (/^[_\s]+$/.test(s))
|
|
23
|
+
return null;
|
|
24
|
+
// Cap length to stay under typical OS filename limits.
|
|
25
|
+
if (s.length > 100)
|
|
26
|
+
s = s.slice(0, 100);
|
|
27
|
+
return s;
|
|
28
|
+
}
|
|
29
|
+
//# sourceMappingURL=sanitize.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sanitize.js","sourceRoot":"","sources":["../../src/exporter/sanitize.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,MAAM,UAAU,oBAAoB,CAAC,KAAa;IAChD,IAAI,CAAC,KAAK;QAAE,OAAO,IAAI,CAAA;IACvB,IAAI,CAAC,GAAG,KAAK;QACX,4CAA4C;SAC3C,OAAO,CAAC,yBAAyB,EAAE,GAAG,CAAC;SACvC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC;SACpB,IAAI,EAAE;SACN,OAAO,CAAC,YAAY,EAAE,EAAE,CAAC,CAAA;IAC5B,IAAI,CAAC,CAAC;QAAE,OAAO,IAAI,CAAA;IACnB,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,IAAI;QAAE,OAAO,IAAI,CAAA;IACxC,2EAA2E;IAC3E,6CAA6C;IAC7C,IAAI,UAAU,CAAC,IAAI,CAAC,CAAC,CAAC;QAAE,OAAO,IAAI,CAAA;IACnC,uDAAuD;IACvD,IAAI,CAAC,CAAC,MAAM,GAAG,GAAG;QAAE,CAAC,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,CAAA;IACvC,OAAO,CAAC,CAAA;AACV,CAAC"}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
export interface PathSamplePoint {
|
|
2
|
+
/** ENU x (m) */
|
|
3
|
+
x: number;
|
|
4
|
+
/** ENU y (m) */
|
|
5
|
+
y: number;
|
|
6
|
+
/** ENU heading (rad), 0 = +X, CCW positive */
|
|
7
|
+
heading: number;
|
|
8
|
+
/** Time since start (s) */
|
|
9
|
+
time: number;
|
|
10
|
+
}
|
|
11
|
+
export interface PathTrajectoryInput {
|
|
12
|
+
/** Path control points in canvas coordinates (px) */
|
|
13
|
+
points: {
|
|
14
|
+
x: number;
|
|
15
|
+
y: number;
|
|
16
|
+
}[];
|
|
17
|
+
/** Optional pre-computed normalized positions [0..1] along the path */
|
|
18
|
+
tValues?: number[];
|
|
19
|
+
/** Footprint interval (px), used when tValues is not provided */
|
|
20
|
+
interval?: number;
|
|
21
|
+
/** Footprint offset from the start (px), used when tValues is not provided */
|
|
22
|
+
offset?: number;
|
|
23
|
+
/** Default speed (m/s); falls back to DEFAULT_PATH_SPEED_MPS */
|
|
24
|
+
speedMps?: number;
|
|
25
|
+
}
|
|
26
|
+
export declare const DEFAULT_PATH_SPEED_MPS = 10;
|
|
27
|
+
/**
|
|
28
|
+
* Build the sample sequence used by <FollowTrajectoryAction> from a path.
|
|
29
|
+
*
|
|
30
|
+
* - tValues mode: each value is treated as a normalized position along the path,
|
|
31
|
+
* distributed across equal time slices over the total duration. A vertex at
|
|
32
|
+
* t=0 is prepended when the first tValue is non-zero so the trajectory starts
|
|
33
|
+
* from the path origin.
|
|
34
|
+
* - interval/offset mode: places samples at equal arc-length intervals and
|
|
35
|
+
* computes time as cumulative_distance / speed.
|
|
36
|
+
*
|
|
37
|
+
* In both cases time strictly increases (small back-steps are nudged forward
|
|
38
|
+
* by 1 ms because trajectory replay rejects non-monotonic timestamps).
|
|
39
|
+
*/
|
|
40
|
+
export declare function buildPathTrajectory(input: PathTrajectoryInput): PathSamplePoint[];
|
|
41
|
+
//# sourceMappingURL=trajectory.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"trajectory.d.ts","sourceRoot":"","sources":["../../src/exporter/trajectory.ts"],"names":[],"mappings":"AA2BA,MAAM,WAAW,eAAe;IAC9B,gBAAgB;IAChB,CAAC,EAAE,MAAM,CAAA;IACT,gBAAgB;IAChB,CAAC,EAAE,MAAM,CAAA;IACT,8CAA8C;IAC9C,OAAO,EAAE,MAAM,CAAA;IACf,2BAA2B;IAC3B,IAAI,EAAE,MAAM,CAAA;CACb;AAED,MAAM,WAAW,mBAAmB;IAClC,qDAAqD;IACrD,MAAM,EAAE;QAAE,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAA;KAAE,EAAE,CAAA;IAClC,uEAAuE;IACvE,OAAO,CAAC,EAAE,MAAM,EAAE,CAAA;IAClB,iEAAiE;IACjE,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,8EAA8E;IAC9E,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,gEAAgE;IAChE,QAAQ,CAAC,EAAE,MAAM,CAAA;CAClB;AAED,eAAO,MAAM,sBAAsB,KAAK,CAAA;AAqExC;;;;;;;;;;;;GAYG;AACH,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,mBAAmB,GAAG,eAAe,EAAE,CAoGjF"}
|