game-data-gen 5.0.0 → 6.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +211 -76
- package/dist/consts.js +12 -0
- package/dist/lib/aos.js +13 -11
- package/dist/lib/group.js +46 -78
- package/dist/lib/soa.js +1 -14
- package/dist/lib/struct.js +38 -49
- package/dist/lib/utils.js +3 -0
- package/dist/main.js +17 -6
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -31,55 +31,106 @@ npm i -D game-data-gen
|
|
|
31
31
|
npx game-data-gen <input-file-path> <optional-output-file-path>
|
|
32
32
|
```
|
|
33
33
|
|
|
34
|
-
##
|
|
34
|
+
## Types
|
|
35
35
|
|
|
36
|
-
|
|
36
|
+
Each block in the Markdown file starts with a heading that defines the type, followed by a list of fields.
|
|
37
37
|
|
|
38
|
-
|
|
39
|
-
| ------------------ | ------------------------ |
|
|
40
|
-
| (none) | `- health` |
|
|
41
|
-
| `int8 <length>` | `- ids int8 64` |
|
|
42
|
-
| `int16 <length>` | `- ids int16 64` |
|
|
43
|
-
| `int32 <length>` | `- ids int32 64` |
|
|
44
|
-
| `uint8 <length>` | `- ids uint8 64` |
|
|
45
|
-
| `uint16 <length>` | `- ids uint16 64` |
|
|
46
|
-
| `uint32 <length>` | `- ids uint32 64` |
|
|
47
|
-
| `float32 <length>` | `- positions float32 64` |
|
|
48
|
-
| `float64 <length>` | `- positions float64 64` |
|
|
38
|
+
### Group
|
|
49
39
|
|
|
50
|
-
|
|
40
|
+
```
|
|
41
|
+
# <name> group
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
A set of module-level variables with individual setter and zero functions, plus a combined zero function.
|
|
45
|
+
|
|
46
|
+
| Field type | Description |
|
|
47
|
+
| ----------- | --------------------------- |
|
|
48
|
+
| `string` | A string primitive |
|
|
49
|
+
| `number` | A number primitive |
|
|
50
|
+
| `boolean` | A boolean primitive |
|
|
51
|
+
| `string[]` | A dynamic array of strings |
|
|
52
|
+
| `number[]` | A dynamic array of numbers |
|
|
53
|
+
| `boolean[]` | A dynamic array of booleans |
|
|
54
|
+
|
|
55
|
+
### Structure of Arrays (SOA)
|
|
56
|
+
|
|
57
|
+
```
|
|
58
|
+
# <name> soa <capacity>
|
|
59
|
+
```
|
|
51
60
|
|
|
52
|
-
|
|
61
|
+
A set of typed arrays of fixed capacity, ideal for cache-friendly iteration over many elements.
|
|
53
62
|
|
|
54
|
-
| Field type |
|
|
63
|
+
| Field type | Typed array |
|
|
55
64
|
| ---------- | -------------- |
|
|
56
|
-
| `int8` |
|
|
57
|
-
| `int16` |
|
|
58
|
-
| `int32` |
|
|
59
|
-
| `uint8` |
|
|
60
|
-
| `uint16` |
|
|
61
|
-
| `uint32` |
|
|
62
|
-
| `float32` |
|
|
63
|
-
| `float64` |
|
|
65
|
+
| `int8` | `Int8Array` |
|
|
66
|
+
| `int16` | `Int16Array` |
|
|
67
|
+
| `int32` | `Int32Array` |
|
|
68
|
+
| `uint8` | `Uint8Array` |
|
|
69
|
+
| `uint16` | `Uint16Array` |
|
|
70
|
+
| `uint32` | `Uint32Array` |
|
|
71
|
+
| `float32` | `Float32Array` |
|
|
72
|
+
| `float64` | `Float64Array` |
|
|
64
73
|
|
|
65
|
-
|
|
74
|
+
### Struct
|
|
75
|
+
|
|
76
|
+
```
|
|
77
|
+
# <name> struct
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
A TypeScript type with create and zero functions. Fields can be primitives, arrays, or other structs.
|
|
81
|
+
|
|
82
|
+
| Field type | Description |
|
|
83
|
+
| ------------ | ---------------------------------------------------- |
|
|
84
|
+
| `string` | A string primitive |
|
|
85
|
+
| `number` | A number primitive |
|
|
86
|
+
| `boolean` | A boolean primitive |
|
|
87
|
+
| `string[]` | A dynamic array of strings |
|
|
88
|
+
| `number[]` | A dynamic array of numbers |
|
|
89
|
+
| `boolean[]` | A dynamic array of booleans |
|
|
90
|
+
| `<name>` | A nested struct (must be defined before this struct) |
|
|
91
|
+
| `<name>[]` | A dynamic array of structs |
|
|
66
92
|
|
|
67
|
-
|
|
93
|
+
### Array of Structures (AOS)
|
|
68
94
|
|
|
69
|
-
|
|
95
|
+
```
|
|
96
|
+
# <name> aos <capacity> <struct>
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
A pre-allocated fixed-length array of struct objects.
|
|
100
|
+
|
|
101
|
+
## Example
|
|
102
|
+
|
|
103
|
+
Create a Markdown file somewhere in your source code, for example `src/data.md`:
|
|
70
104
|
|
|
71
105
|
```md
|
|
72
|
-
# game
|
|
106
|
+
# game group
|
|
107
|
+
|
|
108
|
+
- score number
|
|
109
|
+
- name string
|
|
110
|
+
- isPaused boolean
|
|
111
|
+
- enemies number[]
|
|
73
112
|
|
|
74
|
-
|
|
75
|
-
- enemies uint16 64
|
|
113
|
+
# particles soa 256
|
|
76
114
|
|
|
77
|
-
|
|
115
|
+
- x float32
|
|
116
|
+
- y float32
|
|
117
|
+
- lifetime float32
|
|
118
|
+
- type int8
|
|
78
119
|
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
-
|
|
82
|
-
-
|
|
120
|
+
# Vector2 struct
|
|
121
|
+
|
|
122
|
+
- x number
|
|
123
|
+
- y number
|
|
124
|
+
|
|
125
|
+
# Entity struct
|
|
126
|
+
|
|
127
|
+
- name string
|
|
128
|
+
- health number
|
|
129
|
+
- isActive boolean
|
|
130
|
+
- position Vector2
|
|
131
|
+
- tags string[]
|
|
132
|
+
|
|
133
|
+
# entities aos 64 Entity
|
|
83
134
|
```
|
|
84
135
|
|
|
85
136
|
Run the package with (consider making this a script in your package.json):
|
|
@@ -97,78 +148,162 @@ This will create or update the `src/data.ts` file (see below). The data and func
|
|
|
97
148
|
* --------------------------------------------------
|
|
98
149
|
*/
|
|
99
150
|
|
|
100
|
-
export let
|
|
101
|
-
export
|
|
102
|
-
export let
|
|
151
|
+
export let score = 0;
|
|
152
|
+
export let name = "";
|
|
153
|
+
export let isPaused = false;
|
|
154
|
+
export const enemies: number[] = [];
|
|
155
|
+
|
|
156
|
+
/** Set the value of the score field within the game group. */
|
|
157
|
+
export function setScore(v: number) {
|
|
158
|
+
score = v;
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
/** Set the value of the name field within the game group. */
|
|
162
|
+
export function setName(v: string) {
|
|
163
|
+
name = v;
|
|
164
|
+
}
|
|
103
165
|
|
|
104
|
-
/** Set the value of the
|
|
105
|
-
export function
|
|
106
|
-
|
|
166
|
+
/** Set the value of the isPaused field within the game group. */
|
|
167
|
+
export function setIsPaused(v: boolean) {
|
|
168
|
+
isPaused = v;
|
|
107
169
|
}
|
|
108
170
|
|
|
109
|
-
/**
|
|
110
|
-
export function
|
|
111
|
-
|
|
171
|
+
/** Zero the score field within the game group. */
|
|
172
|
+
export function zeroScore() {
|
|
173
|
+
score = 0;
|
|
112
174
|
}
|
|
113
175
|
|
|
114
|
-
/**
|
|
115
|
-
export function
|
|
116
|
-
|
|
176
|
+
/** Zero the name field within the game group. */
|
|
177
|
+
export function zeroName() {
|
|
178
|
+
name = "";
|
|
117
179
|
}
|
|
118
180
|
|
|
119
|
-
/** Zero the
|
|
120
|
-
export function
|
|
121
|
-
|
|
181
|
+
/** Zero the isPaused field within the game group. */
|
|
182
|
+
export function zeroIsPaused() {
|
|
183
|
+
isPaused = false;
|
|
122
184
|
}
|
|
123
185
|
|
|
124
186
|
/** Zero the enemies field within the game group. */
|
|
125
187
|
export function zeroEnemies() {
|
|
126
|
-
|
|
188
|
+
enemies.length = 0;
|
|
127
189
|
}
|
|
128
190
|
|
|
129
191
|
/** Zero all fields within the game group. */
|
|
130
192
|
export function zeroGame() {
|
|
131
|
-
|
|
132
|
-
|
|
193
|
+
score = 0;
|
|
194
|
+
name = "";
|
|
195
|
+
isPaused = false;
|
|
196
|
+
enemies.length = 0;
|
|
133
197
|
}
|
|
134
198
|
|
|
135
199
|
/*
|
|
136
200
|
* --------------------------------------------------
|
|
137
|
-
*
|
|
201
|
+
* particles (Structure Of Arrays)
|
|
138
202
|
* --------------------------------------------------
|
|
139
203
|
*/
|
|
140
204
|
|
|
141
|
-
export const
|
|
205
|
+
export const MAX_PARTICLES_COUNT = 256;
|
|
142
206
|
|
|
143
|
-
export const
|
|
144
|
-
export const
|
|
145
|
-
export const
|
|
146
|
-
export const
|
|
207
|
+
export const x = new Float32Array(256);
|
|
208
|
+
export const y = new Float32Array(256);
|
|
209
|
+
export const lifetime = new Float32Array(256);
|
|
210
|
+
export const type = new Int8Array(256);
|
|
147
211
|
|
|
148
|
-
/** Zero an index within the
|
|
149
|
-
export function
|
|
212
|
+
/** Zero an index within the particles structure of arrays. */
|
|
213
|
+
export function zeroParticlesAt(i: number) {
|
|
214
|
+
x[i] = 0;
|
|
215
|
+
y[i] = 0;
|
|
216
|
+
lifetime[i] = 0;
|
|
150
217
|
type[i] = 0;
|
|
151
|
-
posX[i] = 0;
|
|
152
|
-
posY[i] = 0;
|
|
153
|
-
health[i] = 0;
|
|
154
218
|
}
|
|
155
219
|
|
|
156
|
-
/** Zero all fields within the
|
|
157
|
-
export function
|
|
220
|
+
/** Zero all fields within the particles structure of arrays. */
|
|
221
|
+
export function zeroParticles() {
|
|
222
|
+
x.fill(0);
|
|
223
|
+
y.fill(0);
|
|
224
|
+
lifetime.fill(0);
|
|
158
225
|
type.fill(0);
|
|
159
|
-
posX.fill(0);
|
|
160
|
-
posY.fill(0);
|
|
161
|
-
health.fill(0);
|
|
162
226
|
}
|
|
163
|
-
```
|
|
164
227
|
|
|
165
|
-
|
|
228
|
+
/*
|
|
229
|
+
* --------------------------------------------------
|
|
230
|
+
* Vector2 (Struct)
|
|
231
|
+
* --------------------------------------------------
|
|
232
|
+
*/
|
|
166
233
|
|
|
167
|
-
|
|
168
|
-
|
|
234
|
+
export type Vector2 = {
|
|
235
|
+
x: number;
|
|
236
|
+
y: number;
|
|
237
|
+
};
|
|
238
|
+
|
|
239
|
+
/** Create a new Vector2 object. */
|
|
240
|
+
export function createVector2() {
|
|
241
|
+
const obj: Vector2 = Object.create(null);
|
|
242
|
+
obj.x = 0;
|
|
243
|
+
obj.y = 0;
|
|
244
|
+
return obj;
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
/** Zero the given Vector2 object. */
|
|
248
|
+
export function zeroVector2(obj: Vector2) {
|
|
249
|
+
obj.x = 0;
|
|
250
|
+
obj.y = 0;
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
/*
|
|
254
|
+
* --------------------------------------------------
|
|
255
|
+
* Entity (Struct)
|
|
256
|
+
* --------------------------------------------------
|
|
257
|
+
*/
|
|
258
|
+
|
|
259
|
+
export type Entity = {
|
|
260
|
+
name: string;
|
|
261
|
+
health: number;
|
|
262
|
+
isActive: boolean;
|
|
263
|
+
position: Vector2;
|
|
264
|
+
tags: string[];
|
|
265
|
+
};
|
|
266
|
+
|
|
267
|
+
/** Create a new Entity object. */
|
|
268
|
+
export function createEntity() {
|
|
269
|
+
const obj: Entity = Object.create(null);
|
|
270
|
+
obj.name = "";
|
|
271
|
+
obj.health = 0;
|
|
272
|
+
obj.isActive = false;
|
|
273
|
+
obj.position = createVector2();
|
|
274
|
+
obj.tags = [];
|
|
275
|
+
return obj;
|
|
276
|
+
}
|
|
277
|
+
|
|
278
|
+
/** Zero the given Entity object. */
|
|
279
|
+
export function zeroEntity(obj: Entity) {
|
|
280
|
+
obj.name = "";
|
|
281
|
+
obj.health = 0;
|
|
282
|
+
obj.isActive = false;
|
|
283
|
+
zeroVector2(obj.position);
|
|
284
|
+
obj.tags.length = 0;
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
/*
|
|
288
|
+
* --------------------------------------------------
|
|
289
|
+
* entities (Array Of Structures)
|
|
290
|
+
* --------------------------------------------------
|
|
291
|
+
*/
|
|
292
|
+
|
|
293
|
+
export const MAX_ENTITIES_COUNT = 64;
|
|
294
|
+
|
|
295
|
+
/** An array of Entity objects (structures). */
|
|
296
|
+
export const entities = Array.from({ length: 64 }, createEntity);
|
|
297
|
+
|
|
298
|
+
/** Zero all objects within the entities array of structures. */
|
|
299
|
+
export function zeroEntities() {
|
|
300
|
+
for (let i = 0; i < 64; i++) {
|
|
301
|
+
zeroEntity(entities[i]);
|
|
302
|
+
}
|
|
303
|
+
}
|
|
169
304
|
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
305
|
+
/** Zero an object at a specific index within the entities array of structures. */
|
|
306
|
+
export function zeroEntitiesAt(index: number) {
|
|
307
|
+
zeroEntity(entities[index]);
|
|
173
308
|
}
|
|
174
309
|
```
|
package/dist/consts.js
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
|
+
export var Type;
|
|
2
|
+
(function (Type) {
|
|
3
|
+
Type["GROUP"] = "group";
|
|
4
|
+
Type["STRUCT"] = "struct";
|
|
5
|
+
Type["STRUCTURE_OF_ARRAYS"] = "soa";
|
|
6
|
+
Type["ARRAY_OF_STRUCTURES"] = "aos";
|
|
7
|
+
})(Type || (Type = {}));
|
|
1
8
|
export var FieldType;
|
|
2
9
|
(function (FieldType) {
|
|
10
|
+
// Structure of Arrays
|
|
3
11
|
FieldType["INT_8"] = "int8";
|
|
4
12
|
FieldType["INT_16"] = "int16";
|
|
5
13
|
FieldType["INT_32"] = "int32";
|
|
@@ -8,4 +16,8 @@ export var FieldType;
|
|
|
8
16
|
FieldType["UINT_32"] = "uint32";
|
|
9
17
|
FieldType["FLOAT_32"] = "float32";
|
|
10
18
|
FieldType["FLOAT_64"] = "float64";
|
|
19
|
+
// Struct / Group
|
|
20
|
+
FieldType["STRING"] = "string";
|
|
21
|
+
FieldType["NUMBER"] = "number";
|
|
22
|
+
FieldType["BOOLEAN"] = "boolean";
|
|
11
23
|
})(FieldType || (FieldType = {}));
|
package/dist/lib/aos.js
CHANGED
|
@@ -1,31 +1,33 @@
|
|
|
1
1
|
import { addHeader, capitalize } from "./utils.js";
|
|
2
2
|
export function addArrayOfStructures(header, output) {
|
|
3
|
-
const [name, , length,
|
|
3
|
+
const [name, , length, struct] = header.split(" ");
|
|
4
4
|
addHeader(`${name} (Array Of Structures)`, output);
|
|
5
5
|
addFieldMaxLengthConstant(name, length, output);
|
|
6
|
-
addArrayOfStructuresDefinition(name,
|
|
7
|
-
addArrayOfStructuresZeroFunction(name,
|
|
8
|
-
addArrayOfStructuresZeroAtIndexFunction(name,
|
|
6
|
+
addArrayOfStructuresDefinition(name, struct, length, output);
|
|
7
|
+
addArrayOfStructuresZeroFunction(name, struct, length, output);
|
|
8
|
+
addArrayOfStructuresZeroAtIndexFunction(name, struct, output);
|
|
9
9
|
}
|
|
10
10
|
function addFieldMaxLengthConstant(name, length, output) {
|
|
11
11
|
output.push(`export const MAX_${name.toUpperCase()}_COUNT = ${length}`);
|
|
12
12
|
output.push("");
|
|
13
13
|
}
|
|
14
|
-
function addArrayOfStructuresDefinition(name,
|
|
15
|
-
output.push(`/** An array of ${
|
|
16
|
-
output.push(`export const ${name} = Array.from({ length: ${length} }, create${capitalize(
|
|
14
|
+
function addArrayOfStructuresDefinition(name, struct, length, output) {
|
|
15
|
+
output.push(`/** An array of ${struct} objects (structures). */`);
|
|
16
|
+
output.push(`export const ${name} = Array.from({ length: ${length} }, create${capitalize(struct)})`);
|
|
17
17
|
}
|
|
18
|
-
function addArrayOfStructuresZeroFunction(name,
|
|
18
|
+
function addArrayOfStructuresZeroFunction(name, struct, length, output) {
|
|
19
19
|
output.push("");
|
|
20
20
|
output.push(`/** Zero all objects within the ${name} array of structures. */`);
|
|
21
21
|
output.push(`export function zero${capitalize(name)}() {`);
|
|
22
|
-
output.push(`
|
|
22
|
+
output.push(` for (let i=0; i<${length}; i++) {`);
|
|
23
|
+
output.push(` zero${capitalize(struct)}(${name}[i])`);
|
|
24
|
+
output.push(" }");
|
|
23
25
|
output.push("}");
|
|
24
26
|
}
|
|
25
|
-
function addArrayOfStructuresZeroAtIndexFunction(name,
|
|
27
|
+
function addArrayOfStructuresZeroAtIndexFunction(name, struct, output) {
|
|
26
28
|
output.push("");
|
|
27
29
|
output.push(`/** Zero an object at a specific index within the ${name} array of structures. */`);
|
|
28
30
|
output.push(`export function zero${capitalize(name)}At(i: number) {`);
|
|
29
|
-
output.push(` zero${capitalize(
|
|
31
|
+
output.push(` zero${capitalize(struct)}(${name}[i])`);
|
|
30
32
|
output.push("}");
|
|
31
33
|
}
|
package/dist/lib/group.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { FieldType } from "../consts.js";
|
|
2
|
-
import { addHeader, capitalize } from "./utils.js";
|
|
2
|
+
import { addHeader, capitalize, isArrayType } from "./utils.js";
|
|
3
3
|
export function addGroup(header, fields, output) {
|
|
4
4
|
const [name] = header.split(" ");
|
|
5
5
|
addHeader(`${name} (Group)`, output);
|
|
@@ -9,92 +9,50 @@ export function addGroup(header, fields, output) {
|
|
|
9
9
|
for (const field of fields) {
|
|
10
10
|
addFieldSetFunction(name, field, output);
|
|
11
11
|
}
|
|
12
|
-
for (const field of fields) {
|
|
13
|
-
addFieldPushFunction(name, field, output);
|
|
14
|
-
}
|
|
15
|
-
for (const field of fields) {
|
|
16
|
-
addFieldPopFunction(name, field, output);
|
|
17
|
-
}
|
|
18
12
|
for (const field of fields) {
|
|
19
13
|
addFieldZeroFunction(name, field, output);
|
|
20
14
|
}
|
|
21
15
|
addZeroFunction(name, fields, output);
|
|
22
16
|
}
|
|
23
17
|
function addFieldDefinition(field, output) {
|
|
24
|
-
const [fieldName, fieldType
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
output.push(`export const ${fieldName} = new Int8Array(${fieldLength})`);
|
|
28
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
29
|
-
break;
|
|
30
|
-
case FieldType.INT_16:
|
|
31
|
-
output.push(`export const ${fieldName} = new Int16Array(${fieldLength})`);
|
|
32
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
33
|
-
break;
|
|
34
|
-
case FieldType.INT_32:
|
|
35
|
-
output.push(`export const ${fieldName} = new Int32Array(${fieldLength})`);
|
|
36
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
37
|
-
break;
|
|
38
|
-
case FieldType.UINT_8:
|
|
39
|
-
output.push(`export const ${fieldName} = new Uint8Array(${fieldLength})`);
|
|
40
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
41
|
-
break;
|
|
42
|
-
case FieldType.UINT_16:
|
|
43
|
-
output.push(`export const ${fieldName} = new Uint16Array(${fieldLength})`);
|
|
44
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
45
|
-
break;
|
|
46
|
-
case FieldType.UINT_32:
|
|
47
|
-
output.push(`export const ${fieldName} = new Uint32Array(${fieldLength})`);
|
|
48
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
49
|
-
break;
|
|
50
|
-
case FieldType.FLOAT_32:
|
|
51
|
-
output.push(`export const ${fieldName} = new Float32Array(${fieldLength})`);
|
|
52
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
53
|
-
break;
|
|
54
|
-
case FieldType.FLOAT_64:
|
|
55
|
-
output.push(`export const ${fieldName} = new Float64Array(${fieldLength})`);
|
|
56
|
-
output.push(`export let ${fieldName}Count = 0`);
|
|
57
|
-
break;
|
|
58
|
-
default:
|
|
59
|
-
output.push(`export let ${fieldName} = 0`);
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
function addFieldSetFunction(name, field, output) {
|
|
63
|
-
const [fieldName, , fieldLength] = field.split(" ");
|
|
64
|
-
if (!fieldLength) {
|
|
65
|
-
output.push("");
|
|
66
|
-
output.push(`/** Set the value of the ${fieldName} field within the ${name} group. */`);
|
|
67
|
-
output.push(`export function set${capitalize(fieldName)}(v: number) {`);
|
|
68
|
-
output.push(` ${fieldName} = v`);
|
|
69
|
-
output.push("}");
|
|
18
|
+
const [fieldName, fieldType] = field.split(" ");
|
|
19
|
+
if (isArrayType(fieldType)) {
|
|
20
|
+
output.push(`export const ${fieldName}: ${fieldType} = []`);
|
|
70
21
|
}
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
22
|
+
else {
|
|
23
|
+
switch (fieldType) {
|
|
24
|
+
case FieldType.STRING:
|
|
25
|
+
output.push(`export let ${fieldName} = ""`);
|
|
26
|
+
break;
|
|
27
|
+
case FieldType.NUMBER:
|
|
28
|
+
output.push(`export let ${fieldName} = 0`);
|
|
29
|
+
break;
|
|
30
|
+
case FieldType.BOOLEAN:
|
|
31
|
+
output.push(`export let ${fieldName} = false`);
|
|
32
|
+
break;
|
|
33
|
+
}
|
|
80
34
|
}
|
|
81
35
|
}
|
|
82
|
-
function
|
|
83
|
-
const [fieldName,
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
36
|
+
function addFieldSetFunction(name, field, output) {
|
|
37
|
+
const [fieldName, fieldType] = field.split(" ");
|
|
38
|
+
switch (fieldType) {
|
|
39
|
+
case FieldType.STRING:
|
|
40
|
+
case FieldType.NUMBER:
|
|
41
|
+
case FieldType.BOOLEAN:
|
|
42
|
+
output.push("");
|
|
43
|
+
output.push(`/** Set the value of the ${fieldName} field within the ${name} group. */`);
|
|
44
|
+
output.push(`export function set${capitalize(fieldName)}(v: ${fieldType}) {`);
|
|
45
|
+
output.push(` ${fieldName} = v`);
|
|
46
|
+
output.push("}");
|
|
47
|
+
break;
|
|
90
48
|
}
|
|
91
49
|
}
|
|
92
50
|
function addFieldZeroFunction(name, field, output) {
|
|
93
|
-
const [fieldName,
|
|
51
|
+
const [fieldName, fieldType] = field.split(" ");
|
|
94
52
|
output.push("");
|
|
95
53
|
output.push(`/** Zero the ${fieldName} field within the ${name} group. */`);
|
|
96
54
|
output.push(`export function zero${capitalize(fieldName)}() {`);
|
|
97
|
-
zeroField(fieldName,
|
|
55
|
+
zeroField(fieldName, fieldType, output);
|
|
98
56
|
output.push("}");
|
|
99
57
|
}
|
|
100
58
|
function addZeroFunction(name, fields, output) {
|
|
@@ -102,16 +60,26 @@ function addZeroFunction(name, fields, output) {
|
|
|
102
60
|
output.push(`/** Zero all fields within the ${name} group. */`);
|
|
103
61
|
output.push(`export function zero${capitalize(name)}() {`);
|
|
104
62
|
for (const field of fields) {
|
|
105
|
-
const [fieldName,
|
|
106
|
-
zeroField(fieldName,
|
|
63
|
+
const [fieldName, fieldType] = field.split(" ");
|
|
64
|
+
zeroField(fieldName, fieldType, output);
|
|
107
65
|
}
|
|
108
66
|
output.push("}");
|
|
109
67
|
}
|
|
110
|
-
function zeroField(name,
|
|
111
|
-
if (
|
|
112
|
-
output.push(` ${name}
|
|
68
|
+
function zeroField(name, type, output) {
|
|
69
|
+
if (isArrayType(type)) {
|
|
70
|
+
output.push(` ${name}.length = 0`);
|
|
113
71
|
}
|
|
114
72
|
else {
|
|
115
|
-
|
|
73
|
+
switch (type) {
|
|
74
|
+
case FieldType.STRING:
|
|
75
|
+
output.push(` ${name} = ""`);
|
|
76
|
+
break;
|
|
77
|
+
case FieldType.NUMBER:
|
|
78
|
+
output.push(` ${name} = 0`);
|
|
79
|
+
break;
|
|
80
|
+
case FieldType.BOOLEAN:
|
|
81
|
+
output.push(` ${name} = false`);
|
|
82
|
+
break;
|
|
83
|
+
}
|
|
116
84
|
}
|
|
117
85
|
}
|
package/dist/lib/soa.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { FieldType } from "../consts.js";
|
|
2
2
|
import { addHeader, capitalize } from "./utils.js";
|
|
3
3
|
export function addStructureOfArrays(header, fields, output) {
|
|
4
|
-
const [name, length] = header.split(" ");
|
|
4
|
+
const [name, , length] = header.split(" ");
|
|
5
5
|
addHeader(`${name} (Structure Of Arrays)`, output);
|
|
6
6
|
addFieldMaxLengthConstant(name, length, output);
|
|
7
7
|
for (const field of fields) {
|
|
@@ -9,7 +9,6 @@ export function addStructureOfArrays(header, fields, output) {
|
|
|
9
9
|
}
|
|
10
10
|
addZeroAtIndexFunction(name, fields, output);
|
|
11
11
|
addZeroFunction(name, fields, output);
|
|
12
|
-
addPrintAtIndexFunction(name, fields, output);
|
|
13
12
|
}
|
|
14
13
|
function addFieldMaxLengthConstant(name, length, output) {
|
|
15
14
|
output.push(`export const MAX_${name.toUpperCase()}_COUNT = ${length}`);
|
|
@@ -64,15 +63,3 @@ function addZeroAtIndexFunction(name, fields, output) {
|
|
|
64
63
|
}
|
|
65
64
|
output.push("}");
|
|
66
65
|
}
|
|
67
|
-
function addPrintAtIndexFunction(name, fields, output) {
|
|
68
|
-
output.push("");
|
|
69
|
-
output.push(`/** Print an index within the ${name} structure of arrays to the console. */`);
|
|
70
|
-
output.push(`export function print${capitalize(name)}At(i: number) {`);
|
|
71
|
-
output.push(" console.table({");
|
|
72
|
-
for (const field of fields) {
|
|
73
|
-
const [fieldName] = field.split(" ");
|
|
74
|
-
output.push(` ${fieldName}: ${fieldName}[i],`);
|
|
75
|
-
}
|
|
76
|
-
output.push(" })");
|
|
77
|
-
output.push("}");
|
|
78
|
-
}
|
package/dist/lib/struct.js
CHANGED
|
@@ -1,19 +1,17 @@
|
|
|
1
1
|
import { FieldType } from "../consts.js";
|
|
2
|
-
import { addHeader, capitalize,
|
|
2
|
+
import { addHeader, capitalize, isArrayType } from "./utils.js";
|
|
3
3
|
export function addStruct(header, fields, output) {
|
|
4
4
|
const [name] = header.split(" ");
|
|
5
5
|
addHeader(`${name} (Struct)`, output);
|
|
6
6
|
addStructTypeDefinition(name, fields, output);
|
|
7
7
|
addStructCreateFunction(name, fields, output);
|
|
8
|
-
addStructCopyFunction(name, fields, output);
|
|
9
|
-
addStructCloneFunction(name, output);
|
|
10
8
|
addStructZeroFunction(name, fields, output);
|
|
11
9
|
}
|
|
12
10
|
function addStructTypeDefinition(name, fields, output) {
|
|
13
11
|
output.push(`export type ${capitalize(name)} = {`);
|
|
14
12
|
for (const field of fields) {
|
|
15
13
|
const [fieldName, fieldType] = field.split(" ");
|
|
16
|
-
output.push(` ${fieldName}: ${
|
|
14
|
+
output.push(` ${fieldName}: ${fieldType}`);
|
|
17
15
|
}
|
|
18
16
|
output.push("}");
|
|
19
17
|
}
|
|
@@ -21,63 +19,54 @@ function addStructCreateFunction(name, fields, output) {
|
|
|
21
19
|
output.push("");
|
|
22
20
|
output.push(`/** Create a new ${capitalize(name)} object. */`);
|
|
23
21
|
output.push(`export function create${capitalize(name)}() {`);
|
|
24
|
-
output.push(` const obj: ${
|
|
22
|
+
output.push(` const obj: ${name} = Object.create(null)`);
|
|
25
23
|
for (const field of fields) {
|
|
26
24
|
const [fieldName, fieldType] = field.split(" ");
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
25
|
+
if (isArrayType(fieldType)) {
|
|
26
|
+
output.push(` obj.${fieldName} = []`);
|
|
27
|
+
}
|
|
28
|
+
else {
|
|
29
|
+
switch (fieldType) {
|
|
30
|
+
case FieldType.STRING:
|
|
31
|
+
output.push(` obj.${fieldName} = ""`);
|
|
32
|
+
break;
|
|
33
|
+
case FieldType.NUMBER:
|
|
34
|
+
output.push(` obj.${fieldName} = 0`);
|
|
35
|
+
break;
|
|
36
|
+
case FieldType.BOOLEAN:
|
|
37
|
+
output.push(` obj.${fieldName} = false`);
|
|
38
|
+
break;
|
|
39
|
+
default:
|
|
40
|
+
output.push(` obj.${fieldName} = create${capitalize(fieldType)}()`);
|
|
41
|
+
}
|
|
39
42
|
}
|
|
40
43
|
}
|
|
41
44
|
output.push(" return obj");
|
|
42
45
|
output.push("}");
|
|
43
46
|
}
|
|
44
|
-
function addStructCopyFunction(name, fields, output) {
|
|
45
|
-
output.push("");
|
|
46
|
-
output.push(`/** Copy the values of ${capitalize(name)} object b into ${capitalize(name)} object a. */`);
|
|
47
|
-
output.push(`export function copy${capitalize(name)}(a: ${getTypeName(name)}, b: ${getTypeName(name)}) {`);
|
|
48
|
-
for (const field of fields) {
|
|
49
|
-
const [fieldName] = field.split(" ");
|
|
50
|
-
output.push(` a.${fieldName} = b.${fieldName}`);
|
|
51
|
-
}
|
|
52
|
-
output.push("}");
|
|
53
|
-
}
|
|
54
|
-
function addStructCloneFunction(name, output) {
|
|
55
|
-
output.push("");
|
|
56
|
-
output.push(`/** Clone the given ${capitalize(name)} object. */`);
|
|
57
|
-
output.push(`export function clone${capitalize(name)}(obj: ${getTypeName(name)}) {`);
|
|
58
|
-
output.push(` const clone = create${capitalize(name)}()`);
|
|
59
|
-
output.push(` copy${capitalize(name)}(clone, obj)`);
|
|
60
|
-
output.push(" return clone");
|
|
61
|
-
output.push("}");
|
|
62
|
-
}
|
|
63
47
|
function addStructZeroFunction(name, fields, output) {
|
|
64
48
|
output.push("");
|
|
65
49
|
output.push(`/** Zero the given ${capitalize(name)} object. */`);
|
|
66
|
-
output.push(`export function zero${capitalize(name)}(obj: ${
|
|
50
|
+
output.push(`export function zero${capitalize(name)}(obj: ${name}) {`);
|
|
67
51
|
for (const field of fields) {
|
|
68
52
|
const [fieldName, fieldType] = field.split(" ");
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
53
|
+
if (isArrayType(fieldType)) {
|
|
54
|
+
output.push(` obj.${fieldName}.length = 0`);
|
|
55
|
+
}
|
|
56
|
+
else {
|
|
57
|
+
switch (fieldType) {
|
|
58
|
+
case FieldType.STRING:
|
|
59
|
+
output.push(` obj.${fieldName} = ""`);
|
|
60
|
+
break;
|
|
61
|
+
case FieldType.NUMBER:
|
|
62
|
+
output.push(` obj.${fieldName} = 0`);
|
|
63
|
+
break;
|
|
64
|
+
case FieldType.BOOLEAN:
|
|
65
|
+
output.push(` obj.${fieldName} = false`);
|
|
66
|
+
break;
|
|
67
|
+
default:
|
|
68
|
+
output.push(` zero${capitalize(fieldType)}(obj.${fieldName})`);
|
|
69
|
+
}
|
|
81
70
|
}
|
|
82
71
|
}
|
|
83
72
|
output.push("}");
|
package/dist/lib/utils.js
CHANGED
package/dist/main.js
CHANGED
|
@@ -1,8 +1,11 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import fs from "node:fs";
|
|
3
3
|
import { marked } from "marked";
|
|
4
|
+
import { Type } from "./consts.js";
|
|
5
|
+
import { addArrayOfStructures } from "./lib/aos.js";
|
|
4
6
|
import { addGroup } from "./lib/group.js";
|
|
5
7
|
import { addStructureOfArrays } from "./lib/soa.js";
|
|
8
|
+
import { addStruct } from "./lib/struct.js";
|
|
6
9
|
const inputFile = process.argv[2];
|
|
7
10
|
const outputFile = process.argv[3] || inputFile.replace(".md", ".ts");
|
|
8
11
|
const input = fs.readFileSync(inputFile, "utf-8");
|
|
@@ -37,12 +40,20 @@ for (const token of tokens) {
|
|
|
37
40
|
}
|
|
38
41
|
}
|
|
39
42
|
for (const { header, fields } of blocks) {
|
|
40
|
-
const [,
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
43
|
+
const [, type] = header.split(" ");
|
|
44
|
+
switch (type) {
|
|
45
|
+
case Type.GROUP:
|
|
46
|
+
addGroup(header, fields, output);
|
|
47
|
+
break;
|
|
48
|
+
case Type.STRUCT:
|
|
49
|
+
addStruct(header, fields, output);
|
|
50
|
+
break;
|
|
51
|
+
case Type.ARRAY_OF_STRUCTURES:
|
|
52
|
+
addArrayOfStructures(header, output);
|
|
53
|
+
break;
|
|
54
|
+
case Type.STRUCTURE_OF_ARRAYS:
|
|
55
|
+
addStructureOfArrays(header, fields, output);
|
|
56
|
+
break;
|
|
46
57
|
}
|
|
47
58
|
}
|
|
48
59
|
fs.writeFileSync(outputFile, output.join("\n"));
|