@nodecraft/rendermite 1.6.0 → 1.6.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/blocks/cli.js +1 -1
- package/dist/blocks/entity-models.d.ts +45 -2
- package/dist/blocks/entity-models.js +1 -1
- package/dist/blocks/export.d.ts +1 -1
- package/dist/blocks/export.js +1 -1
- package/dist/{classfile-BwaQjnUM.d.ts → classfile-BdLIk4Pe.d.ts} +16 -0
- package/dist/{classfile-CAhS5qNf.js → classfile-Bo7FUrrD.js} +42 -10
- package/dist/{cli-BSKnXBPr.js → cli-D2KJc_yl.js} +6 -2
- package/dist/cli.js +1 -1
- package/dist/entities/classfile.d.ts +1 -1
- package/dist/entities/classfile.js +1 -1
- package/dist/entities/inherit.d.ts +2 -2
- package/dist/entities/inherit.js +1 -1
- package/dist/entities/jar-classes.d.ts +2 -26
- package/dist/entities/jar-classes.js +2 -2
- package/dist/entities/link.d.ts +2 -2
- package/dist/entities/link.js +1 -1
- package/dist/entities/merge.js +1 -1
- package/dist/entities/model-bytecode.d.ts +1 -1
- package/dist/entities/model-bytecode.js +1 -1
- package/dist/entities/model-code.d.ts +1 -1
- package/dist/entities/model-code.js +1 -1
- package/dist/{entity-models-B6-0r2gR.js → entity-models-_EZ3PVtN.js} +9 -5
- package/dist/{export-D8fLC1wS.d.ts → export-B8tPsf4K.d.ts} +1 -1
- package/dist/{export-DT_drDoI.js → export-BfEIwSxY.js} +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/{inherit-KkDsM2N_.js → inherit-ByHjOJX3.js} +3 -3
- package/dist/jar-classes-CSRrPAUy.d.ts +41 -0
- package/dist/{jar-classes-Bj15hjdr.js → jar-classes-DCtELr1i.js} +28 -1
- package/dist/{link-Bm5oQYh6.js → link-5GmBLTzk.js} +25 -1
- package/dist/{merge-3HkeQ_6A.js → merge-NDYxpmL8.js} +7 -5
- package/dist/{model-bytecode-C1nw2G8O.js → model-bytecode-gWy5_uCj.js} +13 -3
- package/dist/{model-code-BKMEMXxF.js → model-code-1Vuk-zj_.js} +1 -1
- package/dist/{model-code-B7jSFQqd.d.ts → model-code-BY44ao27.d.ts} +1 -1
- package/package.json +1 -1
- package/dist/entity-models-c2HpfdWV.d.ts +0 -49
package/dist/blocks/cli.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as runBlocksCli } from "../cli-
|
|
1
|
+
import { t as runBlocksCli } from "../cli-D2KJc_yl.js";
|
|
2
2
|
export { runBlocksCli };
|
|
@@ -1,2 +1,45 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
1
|
+
import { a as ResourceManager } from "../manager-exOIcdyx.js";
|
|
2
|
+
import { S as EntityPackModel } from "../pack-format-QcVFxG_b.js";
|
|
3
|
+
import { t as ClassSource } from "../jar-classes-CSRrPAUy.js";
|
|
4
|
+
//#region src/blocks/entity-models.d.ts
|
|
5
|
+
interface EntityGeometryResult {
|
|
6
|
+
/** Model id (the class it came from) → geometry. */
|
|
7
|
+
models: Record<string, EntityPackModel>;
|
|
8
|
+
/** Entity id → model id, for the entity table to point with. */
|
|
9
|
+
modelOf: Map<string, string>;
|
|
10
|
+
/** Entity sheets the models address, to be stitched into the pack's own atlas. */
|
|
11
|
+
spriteIds: Set<string>;
|
|
12
|
+
failures: Array<{
|
|
13
|
+
id: string;
|
|
14
|
+
reason: string;
|
|
15
|
+
}>;
|
|
16
|
+
}
|
|
17
|
+
interface CollectEntityGeometryOptions {
|
|
18
|
+
version: string;
|
|
19
|
+
/** Where mappings cache; the same directory the jars do. */
|
|
20
|
+
cacheDir: string;
|
|
21
|
+
classes: ClassSource;
|
|
22
|
+
/** Entity ids to look for, as the registry named them. */
|
|
23
|
+
entityIds: readonly string[];
|
|
24
|
+
/** The sheet each entity resolved to, from the entity registry, keyed by entity id. */
|
|
25
|
+
textureOf: ReadonlyMap<string, string>;
|
|
26
|
+
/**
|
|
27
|
+
* The assets, for the mods whose geometry is not in code at all.
|
|
28
|
+
*
|
|
29
|
+
* A GeckoLib mob ships Blockbench's bedrock format and registers it by resource location, so there
|
|
30
|
+
* is nothing for the interpreter to read; `entity-geo.ts` finds and converts it instead.
|
|
31
|
+
*/
|
|
32
|
+
resources?: ResourceManager;
|
|
33
|
+
onProgress?: (done: number, total: number) => void;
|
|
34
|
+
}
|
|
35
|
+
/**
|
|
36
|
+
* Recovers geometry for as many of `entityIds` as the code describes.
|
|
37
|
+
*
|
|
38
|
+
* Mappings are resolved once: downloaded for an obfuscated jar, and the identity for one that is not
|
|
39
|
+
* (from the 26 line the client ships in the clear, and a mod jar never was obfuscated). A version that
|
|
40
|
+
* is obfuscated *and* unmapped — 1.13.x — yields nothing, with the reason recorded once rather than
|
|
41
|
+
* per entity.
|
|
42
|
+
*/
|
|
43
|
+
declare function collectEntityGeometry(options: CollectEntityGeometryOptions): Promise<EntityGeometryResult>;
|
|
44
|
+
//#endregion
|
|
45
|
+
export { CollectEntityGeometryOptions, EntityGeometryResult, collectEntityGeometry };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as collectEntityGeometry } from "../entity-models-
|
|
1
|
+
import { t as collectEntityGeometry } from "../entity-models-_EZ3PVtN.js";
|
|
2
2
|
export { collectEntityGeometry };
|
package/dist/blocks/export.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { i as exportBlockPack, n as BlockPackResult, r as ExportBlockPackOptions, t as BlockPackFailure } from "../export-
|
|
1
|
+
import { i as exportBlockPack, n as BlockPackResult, r as ExportBlockPackOptions, t as BlockPackFailure } from "../export-B8tPsf4K.js";
|
|
2
2
|
export { BlockPackFailure, BlockPackResult, ExportBlockPackOptions, exportBlockPack };
|
package/dist/blocks/export.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as exportBlockPack } from "../export-
|
|
1
|
+
import { t as exportBlockPack } from "../export-BfEIwSxY.js";
|
|
2
2
|
export { exportBlockPack };
|
|
@@ -22,6 +22,10 @@ interface Constant {
|
|
|
22
22
|
nameAndTypeIndex?: number;
|
|
23
23
|
descriptorIndex?: number;
|
|
24
24
|
stringIndex?: number;
|
|
25
|
+
/** A `methodHandle`'s target: an index of a `methodref`, not of a `nameAndType`. */
|
|
26
|
+
referenceIndex?: number;
|
|
27
|
+
/** An `invokeDynamic`'s row in the `BootstrapMethods` attribute. */
|
|
28
|
+
bootstrapIndex?: number;
|
|
25
29
|
}
|
|
26
30
|
interface MethodInfo {
|
|
27
31
|
name: string;
|
|
@@ -45,6 +49,18 @@ interface ClassFile {
|
|
|
45
49
|
} | null;
|
|
46
50
|
/** The value an `ldc` of this index pushes: a number for numeric constants, a string for `string`. */
|
|
47
51
|
literal: (index: number) => string | number | bigint | null;
|
|
52
|
+
/**
|
|
53
|
+
* The method a lambda actually runs, for an `invokedynamic`'s pool index.
|
|
54
|
+
*
|
|
55
|
+
* A lambda compiles to a call through `LambdaMetafactory` with the real body in a synthetic method,
|
|
56
|
+
* so this is two hops: the pool entry names a row of the `BootstrapMethods` attribute, and that
|
|
57
|
+
* row's second argument is a method handle pointing at the body.
|
|
58
|
+
*/
|
|
59
|
+
lambdaTarget: (index: number) => {
|
|
60
|
+
owner: string;
|
|
61
|
+
name: string;
|
|
62
|
+
descriptor: string;
|
|
63
|
+
} | null;
|
|
48
64
|
}
|
|
49
65
|
declare function parseClassFile(bytes: Uint8Array): ClassFile;
|
|
50
66
|
//#endregion
|
|
@@ -150,7 +150,7 @@ function readConstantPool(reader) {
|
|
|
150
150
|
reader.skip(1);
|
|
151
151
|
constants.push({
|
|
152
152
|
tag,
|
|
153
|
-
|
|
153
|
+
referenceIndex: reader.u2()
|
|
154
154
|
});
|
|
155
155
|
break;
|
|
156
156
|
case "methodType":
|
|
@@ -160,23 +160,39 @@ function readConstantPool(reader) {
|
|
|
160
160
|
});
|
|
161
161
|
break;
|
|
162
162
|
case "dynamic":
|
|
163
|
-
case "invokeDynamic":
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
});
|
|
163
|
+
case "invokeDynamic": constants.push({
|
|
164
|
+
tag,
|
|
165
|
+
bootstrapIndex: reader.u2(),
|
|
166
|
+
nameAndTypeIndex: reader.u2()
|
|
167
|
+
});
|
|
169
168
|
}
|
|
170
169
|
}
|
|
171
170
|
return constants;
|
|
172
171
|
}
|
|
173
|
-
/**
|
|
174
|
-
|
|
172
|
+
/**
|
|
173
|
+
* Skips an attribute table, keeping the two that say what a method does: `Code`, and the class-level
|
|
174
|
+
* `BootstrapMethods` that a lambda's real body is reachable through.
|
|
175
|
+
*/
|
|
176
|
+
function readAttributes(reader, utf8, bootstraps) {
|
|
175
177
|
let code;
|
|
176
178
|
const count = reader.u2();
|
|
177
179
|
for (let index = 0; index < count; index++) {
|
|
178
180
|
const name = utf8(reader.u2());
|
|
179
181
|
const length = reader.u4();
|
|
182
|
+
if (name === "BootstrapMethods" && bootstraps) {
|
|
183
|
+
const rows = reader.u2();
|
|
184
|
+
for (let row = 0; row < rows; row++) {
|
|
185
|
+
const handleIndex = reader.u2();
|
|
186
|
+
const argumentCount = reader.u2();
|
|
187
|
+
const argumentIndexes = [];
|
|
188
|
+
for (let argument = 0; argument < argumentCount; argument++) argumentIndexes.push(reader.u2());
|
|
189
|
+
bootstraps.push({
|
|
190
|
+
handleIndex,
|
|
191
|
+
argumentIndexes
|
|
192
|
+
});
|
|
193
|
+
}
|
|
194
|
+
continue;
|
|
195
|
+
}
|
|
180
196
|
if (name !== "Code") {
|
|
181
197
|
reader.skip(length);
|
|
182
198
|
continue;
|
|
@@ -224,6 +240,8 @@ function parseClassFile(bytes) {
|
|
|
224
240
|
code
|
|
225
241
|
});
|
|
226
242
|
}
|
|
243
|
+
const bootstraps = [];
|
|
244
|
+
readAttributes(reader, utf8, bootstraps);
|
|
227
245
|
const reference = (index) => {
|
|
228
246
|
const entry = constants[index];
|
|
229
247
|
if (!entry || entry.classIndex === void 0 || entry.nameAndTypeIndex === void 0) return null;
|
|
@@ -241,6 +259,19 @@ function parseClassFile(bytes) {
|
|
|
241
259
|
if (entry.tag === "string") return utf8(index);
|
|
242
260
|
return entry.value ?? null;
|
|
243
261
|
};
|
|
262
|
+
const lambdaTarget = (index) => {
|
|
263
|
+
const entry = constants[index];
|
|
264
|
+
const row = entry?.bootstrapIndex === void 0 ? void 0 : bootstraps[entry.bootstrapIndex];
|
|
265
|
+
if (!row) return null;
|
|
266
|
+
for (const argument of row.argumentIndexes) {
|
|
267
|
+
const handle = constants[argument];
|
|
268
|
+
if (handle?.tag === "methodHandle" && handle.referenceIndex !== void 0) {
|
|
269
|
+
const target = reference(handle.referenceIndex);
|
|
270
|
+
if (target) return target;
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
return null;
|
|
274
|
+
};
|
|
244
275
|
return {
|
|
245
276
|
thisClass,
|
|
246
277
|
superClass,
|
|
@@ -248,7 +279,8 @@ function parseClassFile(bytes) {
|
|
|
248
279
|
methods,
|
|
249
280
|
utf8,
|
|
250
281
|
reference,
|
|
251
|
-
literal
|
|
282
|
+
literal,
|
|
283
|
+
lambdaTarget
|
|
252
284
|
};
|
|
253
285
|
}
|
|
254
286
|
//#endregion
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { n as builtinPackPath } from "./builtin-WkWjATeh.js";
|
|
2
2
|
import { n as LayeredResourceManager, t as FolderResourceManager } from "./manager-BNibYkmI.js";
|
|
3
|
-
import { t as exportBlockPack } from "./export-
|
|
4
|
-
import { t as JarClassReader } from "./jar-classes-
|
|
3
|
+
import { t as exportBlockPack } from "./export-BfEIwSxY.js";
|
|
4
|
+
import { n as layeredClasses, t as JarClassReader } from "./jar-classes-DCtELr1i.js";
|
|
5
5
|
import { n as prepareModResources } from "./prepare-Myd_ec4v.js";
|
|
6
6
|
import { t as downloadClientJar } from "./download-1wAfrGKx.js";
|
|
7
7
|
import { a as prepareVersionResources, r as compareVersions } from "./prepare-D49Gu4Lv.js";
|
|
@@ -155,6 +155,10 @@ async function runBlocksCli(argv) {
|
|
|
155
155
|
closeMods = () => prepared.close();
|
|
156
156
|
for (const { jar, reason } of prepared.rejected) console.error(`Rejected mod jar ${jar}: ${reason}`);
|
|
157
157
|
namespaces = values.namespace?.length ? values.namespace : prepared.namespaces;
|
|
158
|
+
if (!values["no-entity-geometry"]) {
|
|
159
|
+
const modClasses = values.mod.map((jar) => new JarClassReader(jar));
|
|
160
|
+
classes = layeredClasses(classes ? [classes, ...modClasses] : modClasses);
|
|
161
|
+
}
|
|
158
162
|
}
|
|
159
163
|
try {
|
|
160
164
|
const result = await exportBlockPack({
|
package/dist/cli.js
CHANGED
|
@@ -6,7 +6,7 @@ import { t as curatedModelOverrides } from "./models-CZjCOjs4.js";
|
|
|
6
6
|
import { n as harvestTintOverrides, t as curatedTintOverrides } from "./tints-BspVCz2G.js";
|
|
7
7
|
import { t as downloadClientJar } from "./download-1wAfrGKx.js";
|
|
8
8
|
import { a as prepareVersionResources, i as eraForVersion, n as GEOMETRY_DONOR_VERSIONS } from "./prepare-D49Gu4Lv.js";
|
|
9
|
-
import { t as runBlocksCli } from "./cli-
|
|
9
|
+
import { t as runBlocksCli } from "./cli-D2KJc_yl.js";
|
|
10
10
|
import { t as run } from "./run-BQJkqc5f.js";
|
|
11
11
|
import path from "node:path";
|
|
12
12
|
import os from "node:os";
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as parseClassFile, i as MethodInfo, n as Constant, r as ConstantTag, t as ClassFile } from "../classfile-
|
|
1
|
+
import { a as parseClassFile, i as MethodInfo, n as Constant, r as ConstantTag, t as ClassFile } from "../classfile-BdLIk4Pe.js";
|
|
2
2
|
export { ClassFile, Constant, ConstantTag, MethodInfo, parseClassFile };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as parseClassFile } from "../classfile-
|
|
1
|
+
import { t as parseClassFile } from "../classfile-Bo7FUrrD.js";
|
|
2
2
|
export { parseClassFile };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { r as ExtractedModel } from "../model-PnQ4gV0-.js";
|
|
2
|
-
import { t as ClassFile } from "../classfile-
|
|
3
|
-
import { t as ModelCode } from "../model-code-
|
|
2
|
+
import { t as ClassFile } from "../classfile-BdLIk4Pe.js";
|
|
3
|
+
import { t as ModelCode } from "../model-code-BY44ao27.js";
|
|
4
4
|
//#region src/entities/inherit.d.ts
|
|
5
5
|
interface Ancestry {
|
|
6
6
|
/** The class and its ancestors by internal name, parsed. */
|
package/dist/entities/inherit.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { n as extractInheritedModel, t as ancestryOf } from "../inherit-
|
|
1
|
+
import { n as extractInheritedModel, t as ancestryOf } from "../inherit-ByHjOJX3.js";
|
|
2
2
|
export { ancestryOf, extractInheritedModel };
|
|
@@ -1,26 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
* Reading `.class` entries out of a jar.
|
|
4
|
-
*
|
|
5
|
-
* `JarResourceManager` deliberately indexes only `assets/` and `data/` — it is a *resource* manager,
|
|
6
|
-
* and a class file is not a resource. But entity geometry lives in the code (see
|
|
7
|
-
* `docs/entity-geometry.md`), so the extractor needs the other half of the archive, and it needs it
|
|
8
|
-
* by internal class name rather than by resource locator.
|
|
9
|
-
*
|
|
10
|
-
* Same shape as the resource manager for the same reason: index the central directory once, then read
|
|
11
|
-
* entries on demand. A client jar holds around eight thousand classes and the extractor touches a
|
|
12
|
-
* hundred of them.
|
|
13
|
-
*/
|
|
14
|
-
/** Reads class files out of one jar, by internal name. */
|
|
15
|
-
declare class JarClassReader {
|
|
16
|
-
private readonly jarPath;
|
|
17
|
-
private index;
|
|
18
|
-
constructor(jarPath: string);
|
|
19
|
-
private getIndex;
|
|
20
|
-
/** Every class in the jar, for a sweep that does not know what it is looking for. */
|
|
21
|
-
list(): Promise<string[]>;
|
|
22
|
-
read(internalName: string): Promise<Uint8Array | null>;
|
|
23
|
-
close(): Promise<void>;
|
|
24
|
-
}
|
|
25
|
-
//#endregion
|
|
26
|
-
export { JarClassReader };
|
|
1
|
+
import { n as JarClassReader, r as layeredClasses, t as ClassSource } from "../jar-classes-CSRrPAUy.js";
|
|
2
|
+
export { ClassSource, JarClassReader, layeredClasses };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as JarClassReader } from "../jar-classes-
|
|
2
|
-
export { JarClassReader };
|
|
1
|
+
import { n as layeredClasses, t as JarClassReader } from "../jar-classes-DCtELr1i.js";
|
|
2
|
+
export { JarClassReader, layeredClasses };
|
package/dist/entities/link.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { t as ClassFile } from "../classfile-
|
|
1
|
+
import { t as ClassFile } from "../classfile-BdLIk4Pe.js";
|
|
2
2
|
import { t as Mappings } from "../mappings-DxX4KoZl.js";
|
|
3
3
|
//#region src/entities/link.d.ts
|
|
4
4
|
/**
|
|
@@ -38,7 +38,7 @@ interface EntityModelLink {
|
|
|
38
38
|
/** The class to actually read the bytecode of. */
|
|
39
39
|
obfuscated: string;
|
|
40
40
|
/** How it was found, so a report can say how much rests on the curated table. */
|
|
41
|
-
route: 'model-name' | 'renderer' | 'alias' | 'mod-name';
|
|
41
|
+
route: 'model-name' | 'renderer' | 'alias' | 'mod-name' | 'vanilla-name';
|
|
42
42
|
}
|
|
43
43
|
/**
|
|
44
44
|
* A class's simple name reduced to the entity it is about.
|
package/dist/entities/link.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as linkEntityModel, i as classReader, n as RENDERER_ALIASES, o as normaliseModelName, r as buildModelNameIndex, t as NO_MODEL } from "../link-
|
|
1
|
+
import { a as linkEntityModel, i as classReader, n as RENDERER_ALIASES, o as normaliseModelName, r as buildModelNameIndex, t as NO_MODEL } from "../link-5GmBLTzk.js";
|
|
2
2
|
export { NO_MODEL, RENDERER_ALIASES, buildModelNameIndex, classReader, linkEntityModel, normaliseModelName };
|
package/dist/entities/merge.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as slotsOf, i as mergeModels, n as countCubes, r as cubesOf, t as buildsOwnMesh } from "../merge-
|
|
1
|
+
import { a as slotsOf, i as mergeModels, n as countCubes, r as cubesOf, t as buildsOwnMesh } from "../merge-NDYxpmL8.js";
|
|
2
2
|
export { buildsOwnMesh, countCubes, cubesOf, mergeModels, slotsOf };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { r as ExtractedModel } from "../model-PnQ4gV0-.js";
|
|
2
|
-
import { t as ClassFile } from "../classfile-
|
|
2
|
+
import { t as ClassFile } from "../classfile-BdLIk4Pe.js";
|
|
3
3
|
//#region src/entities/model-bytecode.d.ts
|
|
4
4
|
/**
|
|
5
5
|
* Extracts whatever geometry a class's methods build.
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as extractModel } from "../model-bytecode-
|
|
1
|
+
import { t as extractModel } from "../model-bytecode-gWy5_uCj.js";
|
|
2
2
|
export { extractModel };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { n as isModelCode, r as loadModelCode, t as ModelCode } from "../model-code-
|
|
1
|
+
import { n as isModelCode, r as loadModelCode, t as ModelCode } from "../model-code-BY44ao27.js";
|
|
2
2
|
export { ModelCode, isModelCode, loadModelCode };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { n as loadModelCode, t as isModelCode } from "../model-code-
|
|
1
|
+
import { n as loadModelCode, t as isModelCode } from "../model-code-1Vuk-zj_.js";
|
|
2
2
|
export { isModelCode, loadModelCode };
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { t as findGeoForEntity } from "./entity-geo-B2CkuMWx.js";
|
|
2
|
-
import { n as extractInheritedModel } from "./inherit-
|
|
3
|
-
import { a as linkEntityModel, i as classReader, r as buildModelNameIndex } from "./link-
|
|
2
|
+
import { n as extractInheritedModel } from "./inherit-ByHjOJX3.js";
|
|
3
|
+
import { a as linkEntityModel, i as classReader, r as buildModelNameIndex } from "./link-5GmBLTzk.js";
|
|
4
4
|
import { s as resolveMappings, t as MappingsUnavailableError } from "./mappings-BEPVaiwE.js";
|
|
5
|
-
import { n as loadModelCode } from "./model-code-
|
|
5
|
+
import { n as loadModelCode } from "./model-code-1Vuk-zj_.js";
|
|
6
6
|
//#region src/blocks/entity-models.ts
|
|
7
7
|
/**
|
|
8
8
|
* Entity geometry for the pack: link each entity to the class that builds it, read that class's
|
|
@@ -93,10 +93,14 @@ async function collectEntityGeometry(options) {
|
|
|
93
93
|
for (const entityId of [...entityIds].toSorted((left, right) => left.localeCompare(right))) {
|
|
94
94
|
options.onProgress?.(++done, entityIds.length);
|
|
95
95
|
const link = await linkEntityModel(entityId, context);
|
|
96
|
-
const
|
|
96
|
+
const guessed = link?.route === "vanilla-name";
|
|
97
|
+
const found = link && !guessed ? {
|
|
97
98
|
id: link.className,
|
|
98
99
|
model: await geometryOf(link.obfuscated)
|
|
99
|
-
} : await geoFor(entityId)
|
|
100
|
+
} : await geoFor(entityId) ?? (link ? {
|
|
101
|
+
id: link.className,
|
|
102
|
+
model: await geometryOf(link.obfuscated)
|
|
103
|
+
} : null);
|
|
100
104
|
if (!found?.model) continue;
|
|
101
105
|
const { id: modelId, model } = found;
|
|
102
106
|
if (!models[modelId]) models[modelId] = {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { a as ResourceManager } from "./manager-exOIcdyx.js";
|
|
2
|
-
import { t as ClassSource } from "./
|
|
2
|
+
import { t as ClassSource } from "./jar-classes-CSRrPAUy.js";
|
|
3
3
|
//#region src/blocks/export.d.ts
|
|
4
4
|
interface ExportBlockPackOptions {
|
|
5
5
|
resources: ResourceManager;
|
|
@@ -3,7 +3,7 @@ import { n as ResourceLocator } from "./locator-COMEtEn9.js";
|
|
|
3
3
|
import { n as blockEntityGeometry, r as synthesizeVariants, t as INVISIBLE_BLOCKS } from "./block-entities-xv3bQpEX.js";
|
|
4
4
|
import { a as parseBlockState, n as collectModels } from "./blockstate-eval-BRQ3NWY2.js";
|
|
5
5
|
import { t as collectEntities } from "./entities-DvmA9fEV.js";
|
|
6
|
-
import { t as collectEntityGeometry } from "./entity-models-
|
|
6
|
+
import { t as collectEntityGeometry } from "./entity-models-_EZ3PVtN.js";
|
|
7
7
|
import { n as discoverItems } from "./discovery-CD0QqxSF.js";
|
|
8
8
|
import { a as salvageJson, i as resolveTexture, t as ModelLoader } from "./loader-C-NuJaEi.js";
|
|
9
9
|
import { t as collectItemSprites } from "./item-sprites-G-yikdfV.js";
|
package/dist/index.d.ts
CHANGED
|
@@ -8,7 +8,7 @@ import { a as resolveTexture, n as ModelResolutionError, o as salvageJson, r as
|
|
|
8
8
|
import { a as BlockStateMultipartCase, d as matchesCondition, f as parseBlockState, i as BlockStateError, l as collectModels, n as BlockProperties, o as BlockStateVariantCase, p as weightedVariantIndex, r as BlockStateDefinition, s as MultipartCondition, t as BlockModelVariant, u as evaluateBlockState } from "./blockstate-eval-BzznRcVY.js";
|
|
9
9
|
import { i as buildObjMesh, n as ObjMesh, r as ObjMeshError, t as MeshGroup } from "./obj-mesh-ydhVfLKs.js";
|
|
10
10
|
import { a as buildBlockTints, i as UNREGISTERED_TINTS, n as BlockTintPack, t as BlockTint } from "./tints-DoBv5S9v.js";
|
|
11
|
-
import { i as exportBlockPack, n as BlockPackResult, r as ExportBlockPackOptions, t as BlockPackFailure } from "./export-
|
|
11
|
+
import { i as exportBlockPack, n as BlockPackResult, r as ExportBlockPackOptions, t as BlockPackFailure } from "./export-B8tPsf4K.js";
|
|
12
12
|
import { s as builtinDynamicResources } from "./generators-BnIzAftW.js";
|
|
13
13
|
import { d as toFloatTexture, n as FloatTexture, u as toByteTexture } from "./blend-eT64Z6qm.js";
|
|
14
14
|
import { a as LightingProfileName, i as LightingProfile, r as LightSource, u as lightsForProfile } from "./lighting-3FGRC3Af.js";
|
package/dist/index.js
CHANGED
|
@@ -14,7 +14,7 @@ import { n as buildBlockTints, t as UNREGISTERED_TINTS } from "./tints-Cl0r-Ol3.
|
|
|
14
14
|
import { o as createAtlasResolver, s as parseAtlasSources, t as AtlasSourceError } from "./sources-BlUriDCs.js";
|
|
15
15
|
import { n as LayeredResourceManager, r as ResourceKind, t as FolderResourceManager } from "./manager-BNibYkmI.js";
|
|
16
16
|
import { n as TextureLoader, r as TextureResolutionError, t as AnimatedTexture } from "./loader-C18GpurU.js";
|
|
17
|
-
import { t as exportBlockPack } from "./export-
|
|
17
|
+
import { t as exportBlockPack } from "./export-BfEIwSxY.js";
|
|
18
18
|
import { n as UnsafeJarError, r as isUnsafeEntryPath, t as JarResourceManager } from "./jar-W2cV2ZVO.js";
|
|
19
19
|
import { n as prepareModResources } from "./prepare-Myd_ec4v.js";
|
|
20
20
|
import { a as prepareVersionResources, i as eraForVersion, r as compareVersions } from "./prepare-D49Gu4Lv.js";
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { t as parseClassFile } from "./classfile-
|
|
2
|
-
import { i as mergeModels } from "./merge-
|
|
3
|
-
import { t as extractModel } from "./model-bytecode-
|
|
1
|
+
import { t as parseClassFile } from "./classfile-Bo7FUrrD.js";
|
|
2
|
+
import { i as mergeModels } from "./merge-NDYxpmL8.js";
|
|
3
|
+
import { t as extractModel } from "./model-bytecode-gWy5_uCj.js";
|
|
4
4
|
//#region src/entities/inherit.ts
|
|
5
5
|
/**
|
|
6
6
|
* A model class read together with its ancestors.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
//#region src/entities/jar-classes.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* Reading `.class` entries out of a jar.
|
|
4
|
+
*
|
|
5
|
+
* `JarResourceManager` deliberately indexes only `assets/` and `data/` — it is a *resource* manager,
|
|
6
|
+
* and a class file is not a resource. But entity geometry lives in the code (see
|
|
7
|
+
* `docs/entity-geometry.md`), so the extractor needs the other half of the archive, and it needs it
|
|
8
|
+
* by internal class name rather than by resource locator.
|
|
9
|
+
*
|
|
10
|
+
* Same shape as the resource manager for the same reason: index the central directory once, then read
|
|
11
|
+
* entries on demand. A client jar holds around eight thousand classes and the extractor touches a
|
|
12
|
+
* hundred of them.
|
|
13
|
+
*/
|
|
14
|
+
/** What the extractor reads code out of: one jar, or several layered into one view. */
|
|
15
|
+
interface ClassSource {
|
|
16
|
+
list: () => Promise<string[]>;
|
|
17
|
+
read: (internalName: string) => Promise<Uint8Array | null>;
|
|
18
|
+
close: () => Promise<void>;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Several jars as one class view, first match winning — the same layering the resource managers use.
|
|
22
|
+
*
|
|
23
|
+
* A modded export needs this, and needed it before cross-jar linking did: the class source used to be
|
|
24
|
+
* the client jar alone, so a mod's own model classes were never read and its mobs came out as boxes
|
|
25
|
+
* however good the interpreter was. Layered, one view holds both, which is also what lets a mod entity
|
|
26
|
+
* link to a *vanilla* model — `ars_nouveau:summon_horse` is the game's own horse.
|
|
27
|
+
*/
|
|
28
|
+
declare function layeredClasses(sources: readonly ClassSource[]): ClassSource;
|
|
29
|
+
/** Reads class files out of one jar, by internal name. */
|
|
30
|
+
declare class JarClassReader {
|
|
31
|
+
private readonly jarPath;
|
|
32
|
+
private index;
|
|
33
|
+
constructor(jarPath: string);
|
|
34
|
+
private getIndex;
|
|
35
|
+
/** Every class in the jar, for a sweep that does not know what it is looking for. */
|
|
36
|
+
list(): Promise<string[]>;
|
|
37
|
+
read(internalName: string): Promise<Uint8Array | null>;
|
|
38
|
+
close(): Promise<void>;
|
|
39
|
+
}
|
|
40
|
+
//#endregion
|
|
41
|
+
export { JarClassReader as n, layeredClasses as r, ClassSource as t };
|
|
@@ -13,6 +13,33 @@ import { n as UnsafeJarError, r as isUnsafeEntryPath } from "./jar-W2cV2ZVO.js";
|
|
|
13
13
|
* entries on demand. A client jar holds around eight thousand classes and the extractor touches a
|
|
14
14
|
* hundred of them.
|
|
15
15
|
*/
|
|
16
|
+
/**
|
|
17
|
+
* Several jars as one class view, first match winning — the same layering the resource managers use.
|
|
18
|
+
*
|
|
19
|
+
* A modded export needs this, and needed it before cross-jar linking did: the class source used to be
|
|
20
|
+
* the client jar alone, so a mod's own model classes were never read and its mobs came out as boxes
|
|
21
|
+
* however good the interpreter was. Layered, one view holds both, which is also what lets a mod entity
|
|
22
|
+
* link to a *vanilla* model — `ars_nouveau:summon_horse` is the game's own horse.
|
|
23
|
+
*/
|
|
24
|
+
function layeredClasses(sources) {
|
|
25
|
+
return {
|
|
26
|
+
list: async () => {
|
|
27
|
+
const names = /* @__PURE__ */ new Set();
|
|
28
|
+
for (const source of sources) for (const name of await source.list()) names.add(name);
|
|
29
|
+
return [...names];
|
|
30
|
+
},
|
|
31
|
+
read: async (internalName) => {
|
|
32
|
+
for (const source of sources) {
|
|
33
|
+
const bytes = await source.read(internalName);
|
|
34
|
+
if (bytes) return bytes;
|
|
35
|
+
}
|
|
36
|
+
return null;
|
|
37
|
+
},
|
|
38
|
+
close: async () => {
|
|
39
|
+
for (const source of sources) await source.close();
|
|
40
|
+
}
|
|
41
|
+
};
|
|
42
|
+
}
|
|
16
43
|
/** Reads class files out of one jar, by internal name. */
|
|
17
44
|
var JarClassReader = class {
|
|
18
45
|
jarPath;
|
|
@@ -72,4 +99,4 @@ var JarClassReader = class {
|
|
|
72
99
|
}
|
|
73
100
|
};
|
|
74
101
|
//#endregion
|
|
75
|
-
export { JarClassReader as t };
|
|
102
|
+
export { layeredClasses as n, JarClassReader as t };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { t as parseClassFile } from "./classfile-
|
|
1
|
+
import { t as parseClassFile } from "./classfile-Bo7FUrrD.js";
|
|
2
2
|
//#region src/entities/link.ts
|
|
3
3
|
/**
|
|
4
4
|
* Which class holds a given entity's geometry.
|
|
@@ -257,6 +257,7 @@ function buildModelNameIndex(internalNames) {
|
|
|
257
257
|
*/
|
|
258
258
|
async function linkEntityModel(entityId, context) {
|
|
259
259
|
const name = entityId.includes(":") ? entityId.slice(entityId.indexOf(":") + 1) : entityId;
|
|
260
|
+
const modded = entityId.includes(":") && !entityId.startsWith("minecraft:");
|
|
260
261
|
const { mappings } = context;
|
|
261
262
|
const accept = async (className, route) => {
|
|
262
263
|
const obfuscated = mappings.obfuscatedOf.get(className);
|
|
@@ -309,8 +310,31 @@ async function linkEntityModel(entityId, context) {
|
|
|
309
310
|
route: "mod-name"
|
|
310
311
|
};
|
|
311
312
|
}
|
|
313
|
+
if (modded) for (const shorter of withTokensDropped(name)) {
|
|
314
|
+
const found = await linkEntityModel(shorter, context);
|
|
315
|
+
if (found) return {
|
|
316
|
+
...found,
|
|
317
|
+
route: "vanilla-name"
|
|
318
|
+
};
|
|
319
|
+
}
|
|
312
320
|
return null;
|
|
313
321
|
}
|
|
322
|
+
/**
|
|
323
|
+
* The name with some of its tokens dropped, longest first: `summon_horse` gives `summon` and `horse`.
|
|
324
|
+
*
|
|
325
|
+
* Capped at five tokens, because the subsets double with each one and no id is longer than that for a
|
|
326
|
+
* reason this would help with.
|
|
327
|
+
*/
|
|
328
|
+
function withTokensDropped(name) {
|
|
329
|
+
const tokens = name.split("_").filter((token) => token.length > 0);
|
|
330
|
+
if (tokens.length < 2 || tokens.length > 5) return [];
|
|
331
|
+
const found = [];
|
|
332
|
+
for (let size = tokens.length - 1; size >= 1; size--) for (let mask = 0; mask < 2 ** tokens.length; mask++) {
|
|
333
|
+
const kept = tokens.filter((token, index) => (mask & 1 << index) !== 0);
|
|
334
|
+
if (kept.length === size) found.push(kept.join("_"));
|
|
335
|
+
}
|
|
336
|
+
return [...new Set(found)];
|
|
337
|
+
}
|
|
314
338
|
/** Reads and caches classes out of an extracted jar directory or a jar reader. */
|
|
315
339
|
function classReader(load) {
|
|
316
340
|
const cache = /* @__PURE__ */ new Map();
|
|
@@ -27,13 +27,15 @@ function mergeModels(base, extra) {
|
|
|
27
27
|
const named = new Set(target.slots.map((part) => part.name));
|
|
28
28
|
const missing = source.slots.filter((part) => !named.has(part.name));
|
|
29
29
|
if (missing.length === 0) return base;
|
|
30
|
+
const parts = target.container ? [{
|
|
31
|
+
...target.container,
|
|
32
|
+
children: [...target.container.children, ...missing]
|
|
33
|
+
}] : [...target.slots, ...missing];
|
|
34
|
+
const notes = [.../* @__PURE__ */ new Set([...base.notes, ...extra.notes])].filter((note) => parts.length > 1 || !note.includes("disconnected roots"));
|
|
30
35
|
return {
|
|
31
36
|
textureSize: base.textureSize[0] === 64 && base.textureSize[1] === 32 ? extra.textureSize : base.textureSize,
|
|
32
|
-
parts
|
|
33
|
-
|
|
34
|
-
children: [...target.container.children, ...missing]
|
|
35
|
-
}] : [...target.slots, ...missing],
|
|
36
|
-
notes: [.../* @__PURE__ */ new Set([...base.notes, ...extra.notes])]
|
|
37
|
+
parts,
|
|
38
|
+
notes
|
|
37
39
|
};
|
|
38
40
|
}
|
|
39
41
|
function countCubes(part) {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { t as parseClassFile } from "./classfile-
|
|
2
|
-
import { i as mergeModels, r as cubesOf, t as buildsOwnMesh } from "./merge-
|
|
1
|
+
import { t as parseClassFile } from "./classfile-Bo7FUrrD.js";
|
|
2
|
+
import { i as mergeModels, r as cubesOf, t as buildsOwnMesh } from "./merge-NDYxpmL8.js";
|
|
3
3
|
//#region src/entities/model-bytecode.ts
|
|
4
4
|
/**
|
|
5
5
|
* Abstract interpretation of a boxy-model builder, enough to recover the geometry.
|
|
@@ -308,6 +308,12 @@ var Interpreter = class Interpreter {
|
|
|
308
308
|
});
|
|
309
309
|
return;
|
|
310
310
|
}
|
|
311
|
+
const lambda = taken.find((value) => value.kind === "lambda");
|
|
312
|
+
if (lambda?.kind === "lambda" && receiver?.kind === "object" && taken.length === 1) {
|
|
313
|
+
const applied = this.inline(lambda.owner, lambda.name, lambda.descriptor, null, [receiver]);
|
|
314
|
+
this.push(returns === "V" ? null : applied ?? receiver);
|
|
315
|
+
return;
|
|
316
|
+
}
|
|
311
317
|
if (args.length === 1 && args[0] === "Ljava/lang/String;" && returns.startsWith("L") && target) {
|
|
312
318
|
const name_ = taken[0].kind === "string" ? taken[0].value : "";
|
|
313
319
|
const found = target.children.find((child) => child.name === name_);
|
|
@@ -619,7 +625,11 @@ var Interpreter = class Interpreter {
|
|
|
619
625
|
returns: "V"
|
|
620
626
|
};
|
|
621
627
|
for (let count = 0; count < args.length; count++) this.pop();
|
|
622
|
-
|
|
628
|
+
const target = constants.lambdaTarget(index);
|
|
629
|
+
this.push(returns === "V" ? null : target ? {
|
|
630
|
+
kind: "lambda",
|
|
631
|
+
...target
|
|
632
|
+
} : { kind: "unknown" });
|
|
623
633
|
break;
|
|
624
634
|
}
|
|
625
635
|
case op >= 153 && op <= 166: {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nodecraft/rendermite",
|
|
3
|
-
"version": "1.6.
|
|
3
|
+
"version": "1.6.1",
|
|
4
4
|
"description": "Minecraft item icon renderer: renders inventory-identical item icons from vanilla and modded assets across game versions, outputting optimized PNG/WebP/AVIF plus CSS and a JSON item library.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -1,49 +0,0 @@
|
|
|
1
|
-
import { a as ResourceManager } from "./manager-exOIcdyx.js";
|
|
2
|
-
import { S as EntityPackModel } from "./pack-format-QcVFxG_b.js";
|
|
3
|
-
//#region src/blocks/entity-models.d.ts
|
|
4
|
-
/** What the exporter needs to read code out of; a jar, in practice. */
|
|
5
|
-
interface ClassSource {
|
|
6
|
-
list: () => Promise<string[]>;
|
|
7
|
-
read: (internalName: string) => Promise<Uint8Array | null>;
|
|
8
|
-
}
|
|
9
|
-
interface EntityGeometryResult {
|
|
10
|
-
/** Model id (the class it came from) → geometry. */
|
|
11
|
-
models: Record<string, EntityPackModel>;
|
|
12
|
-
/** Entity id → model id, for the entity table to point with. */
|
|
13
|
-
modelOf: Map<string, string>;
|
|
14
|
-
/** Entity sheets the models address, to be stitched into the pack's own atlas. */
|
|
15
|
-
spriteIds: Set<string>;
|
|
16
|
-
failures: Array<{
|
|
17
|
-
id: string;
|
|
18
|
-
reason: string;
|
|
19
|
-
}>;
|
|
20
|
-
}
|
|
21
|
-
interface CollectEntityGeometryOptions {
|
|
22
|
-
version: string;
|
|
23
|
-
/** Where mappings cache; the same directory the jars do. */
|
|
24
|
-
cacheDir: string;
|
|
25
|
-
classes: ClassSource;
|
|
26
|
-
/** Entity ids to look for, as the registry named them. */
|
|
27
|
-
entityIds: readonly string[];
|
|
28
|
-
/** The sheet each entity resolved to, from the entity registry, keyed by entity id. */
|
|
29
|
-
textureOf: ReadonlyMap<string, string>;
|
|
30
|
-
/**
|
|
31
|
-
* The assets, for the mods whose geometry is not in code at all.
|
|
32
|
-
*
|
|
33
|
-
* A GeckoLib mob ships Blockbench's bedrock format and registers it by resource location, so there
|
|
34
|
-
* is nothing for the interpreter to read; `entity-geo.ts` finds and converts it instead.
|
|
35
|
-
*/
|
|
36
|
-
resources?: ResourceManager;
|
|
37
|
-
onProgress?: (done: number, total: number) => void;
|
|
38
|
-
}
|
|
39
|
-
/**
|
|
40
|
-
* Recovers geometry for as many of `entityIds` as the code describes.
|
|
41
|
-
*
|
|
42
|
-
* Mappings are resolved once: downloaded for an obfuscated jar, and the identity for one that is not
|
|
43
|
-
* (from the 26 line the client ships in the clear, and a mod jar never was obfuscated). A version that
|
|
44
|
-
* is obfuscated *and* unmapped — 1.13.x — yields nothing, with the reason recorded once rather than
|
|
45
|
-
* per entity.
|
|
46
|
-
*/
|
|
47
|
-
declare function collectEntityGeometry(options: CollectEntityGeometryOptions): Promise<EntityGeometryResult>;
|
|
48
|
-
//#endregion
|
|
49
|
-
export { collectEntityGeometry as i, CollectEntityGeometryOptions as n, EntityGeometryResult as r, ClassSource as t };
|