@codexo/exojs-aseprite 0.15.3 → 0.16.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.
@@ -0,0 +1,83 @@
1
+ import { AsepriteSheet } from "./AsepriteSheet.js";
2
+ import { Asset, AssetType, jsonSourceCodec } from "@codexo/exojs";
3
+
4
+ //#region src/asepriteType.ts
5
+ /** The JSON codec, narrowed to the two acquisition halves this type reuses verbatim. */
6
+ const jsonStringCodec = jsonSourceCodec;
7
+ /** Matches references that are already absolute: scheme, `//`, `/`, data/blob. */
8
+ const absoluteRefPattern = /^(?:[a-z][a-z\d+.-]*:|\/\/|\/)/i;
9
+ /** Matches a base that has an explicit scheme (absolute URL). */
10
+ const absoluteBasePattern = /^[a-z][a-z\d+.-]*:/i;
11
+ /** Synthetic origin used to borrow `URL`'s `../`/`./` collapsing. */
12
+ const syntheticOrigin = "https://exojs.invalid/";
13
+ /**
14
+ * Resolves `ref` (the image path read from an Aseprite JSON file) relative to
15
+ * `base` (the resolved location of the JSON file itself).
16
+ *
17
+ * - Absolute refs (scheme, `//`, `/`, `data:`, `blob:`) are returned as-is.
18
+ * - Absolute bases delegate to `new URL(ref, base).href`.
19
+ * - Relative bases use a synthetic origin to collapse `./` and `../` segments,
20
+ * then strips the origin from the result.
21
+ */
22
+ const resolveAsepriteUrl = (ref, base) => {
23
+ if (absoluteRefPattern.test(ref)) return ref;
24
+ if (absoluteBasePattern.test(base)) return new URL(ref, base).href;
25
+ const relative = new URL(ref, syntheticOrigin + base.replace(/^\/+/, "")).href.slice(22);
26
+ return base.startsWith("/") ? `/${relative}` : relative;
27
+ };
28
+ /**
29
+ * Thrown when an Aseprite JSON document does not match the expected shape.
30
+ * `source` is the URL of the file being parsed.
31
+ */
32
+ var AsepriteFormatError = class extends Error {
33
+ source;
34
+ constructor(source, message) {
35
+ super(`[AsepriteFormatError] ${source}: ${message}`);
36
+ this.name = "AsepriteFormatError";
37
+ this.source = source;
38
+ }
39
+ };
40
+ /**
41
+ * Validates an `unknown` value against the minimum required Aseprite JSON
42
+ * shape and narrows it to {@link AsepriteData}. Throws {@link AsepriteFormatError}
43
+ * on any mismatch.
44
+ */
45
+ const validateAsepriteData = (raw, source) => {
46
+ if (typeof raw !== "object" || raw === null) throw new AsepriteFormatError(source, "root must be an object");
47
+ const doc = raw;
48
+ if (!("frames" in doc)) throw new AsepriteFormatError(source, "missing required field \"frames\"");
49
+ if (!("meta" in doc) || typeof doc.meta !== "object" || doc.meta === null) throw new AsepriteFormatError(source, "missing required field \"meta\"");
50
+ const meta = doc.meta;
51
+ if (typeof meta.image !== "string" || meta.image.length === 0) throw new AsepriteFormatError(source, "\"meta.image\" must be a non-empty string");
52
+ const frames = doc.frames;
53
+ if (!Array.isArray(frames) && (typeof frames !== "object" || frames === null)) throw new AsepriteFormatError(source, "\"frames\" must be an array or an object");
54
+ return doc;
55
+ };
56
+ /**
57
+ * Aseprite JSON exports, together with the packed sheet they reference.
58
+ *
59
+ * The image URL is read from `meta.image` and resolved against the JSON file's
60
+ * own location; the texture is claimed by this sheet's dependency scope, so it
61
+ * lives exactly as long as the sheet does.
62
+ */
63
+ var AsepriteAssetType = class extends AssetType {
64
+ id = "asepriteSheet";
65
+ _token = AsepriteSheet;
66
+ codec = {
67
+ fromResponse: (response, context) => jsonStringCodec.fromResponse(response, context),
68
+ fromBytes: (bytes, context) => jsonStringCodec.fromBytes(bytes, context),
69
+ decode: (stored, context) => Promise.resolve(validateAsepriteData(JSON.parse(stored), context.locator))
70
+ };
71
+ createFactory() {
72
+ return { async create(source, context) {
73
+ const texture = await context.dependencies.load(Asset.type("texture", resolveAsepriteUrl(source.meta.image, context.source)));
74
+ return AsepriteSheet.parse(source, texture);
75
+ } };
76
+ }
77
+ };
78
+ /** The Aseprite sheet asset type. Install it through {@link asepriteExtension}. */
79
+ const asepriteType = new AsepriteAssetType();
80
+
81
+ //#endregion
82
+ export { AsepriteAssetType, AsepriteFormatError, asepriteType };
83
+ //# sourceMappingURL=asepriteType.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"asepriteType.js","names":[],"sources":["../../src/asepriteType.ts"],"sourcesContent":["import type { AssetFactory, AssetSourceCodec, Texture } from '@codexo/exojs';\nimport { Asset, AssetType, jsonSourceCodec } from '@codexo/exojs';\n\n/** The JSON codec, narrowed to the two acquisition halves this type reuses verbatim. */\nconst jsonStringCodec = jsonSourceCodec as Required<AssetSourceCodec<unknown, string>>;\n\nimport type { AsepriteData } from './AsepriteData';\nimport { AsepriteSheet } from './AsepriteSheet';\n\n// ── URL resolution ───────────────────────────────────────────────────────────\n\n/** Matches references that are already absolute: scheme, `//`, `/`, data/blob. */\nconst absoluteRefPattern = /^(?:[a-z][a-z\\d+.-]*:|\\/\\/|\\/)/i;\n\n/** Matches a base that has an explicit scheme (absolute URL). */\nconst absoluteBasePattern = /^[a-z][a-z\\d+.-]*:/i;\n\n/** Synthetic origin used to borrow `URL`'s `../`/`./` collapsing. */\nconst syntheticOrigin = 'https://exojs.invalid/';\n\n/**\n * Resolves `ref` (the image path read from an Aseprite JSON file) relative to\n * `base` (the resolved location of the JSON file itself).\n *\n * - Absolute refs (scheme, `//`, `/`, `data:`, `blob:`) are returned as-is.\n * - Absolute bases delegate to `new URL(ref, base).href`.\n * - Relative bases use a synthetic origin to collapse `./` and `../` segments,\n * then strips the origin from the result.\n */\nconst resolveAsepriteUrl = (ref: string, base: string): string => {\n if (absoluteRefPattern.test(ref)) {\n return ref;\n }\n\n if (absoluteBasePattern.test(base)) {\n return new URL(ref, base).href;\n }\n\n const resolved = new URL(ref, syntheticOrigin + base.replace(/^\\/+/, ''));\n const relative = resolved.href.slice(syntheticOrigin.length);\n\n // A root-relative base must produce a root-relative result again - dropping\n // the leading slash would make the browser re-resolve the reference against\n // the document base URL (e.g. `/site/assets/x.png` → `/site/site/assets/...`).\n return base.startsWith('/') ? `/${relative}` : relative;\n};\n\n// ── Validation ───────────────────────────────────────────────────────────────\n\n/**\n * Thrown when an Aseprite JSON document does not match the expected shape.\n * `source` is the URL of the file being parsed.\n */\nexport class AsepriteFormatError extends Error {\n public readonly source: string;\n\n public constructor(source: string, message: string) {\n super(`[AsepriteFormatError] ${source}: ${message}`);\n this.name = 'AsepriteFormatError';\n this.source = source;\n }\n}\n\n/**\n * Validates an `unknown` value against the minimum required Aseprite JSON\n * shape and narrows it to {@link AsepriteData}. Throws {@link AsepriteFormatError}\n * on any mismatch.\n */\nconst validateAsepriteData = (raw: unknown, source: string): AsepriteData => {\n if (typeof raw !== 'object' || raw === null) {\n throw new AsepriteFormatError(source, 'root must be an object');\n }\n\n const doc = raw as Record<string, unknown>;\n\n if (!('frames' in doc)) {\n throw new AsepriteFormatError(source, 'missing required field \"frames\"');\n }\n\n if (!('meta' in doc) || typeof doc.meta !== 'object' || doc.meta === null) {\n throw new AsepriteFormatError(source, 'missing required field \"meta\"');\n }\n\n const meta = doc.meta as Record<string, unknown>;\n\n if (typeof meta.image !== 'string' || meta.image.length === 0) {\n throw new AsepriteFormatError(source, '\"meta.image\" must be a non-empty string');\n }\n\n const frames = doc.frames;\n\n if (!Array.isArray(frames) && (typeof frames !== 'object' || frames === null)) {\n throw new AsepriteFormatError(source, '\"frames\" must be an array or an object');\n }\n\n return doc as unknown as AsepriteData;\n};\n\n/**\n * Aseprite JSON exports, together with the packed sheet they reference.\n *\n * The image URL is read from `meta.image` and resolved against the JSON file's\n * own location; the texture is claimed by this sheet's dependency scope, so it\n * lives exactly as long as the sheet does.\n */\nexport class AsepriteAssetType extends AssetType<AsepriteData, AsepriteSheet, undefined, string> {\n public readonly id = 'asepriteSheet';\n public override readonly _token = AsepriteSheet;\n // Stored as the text that arrived, like any JSON: a parsed value round-trips\n // through key order and number formatting the response never had.\n public override readonly codec: AssetSourceCodec<AsepriteData, string> = {\n fromResponse: (response, context) => jsonStringCodec.fromResponse(response, context),\n fromBytes: (bytes, context) => jsonStringCodec.fromBytes(bytes, context),\n decode: (stored, context) => Promise.resolve(validateAsepriteData(JSON.parse(stored), context.locator)),\n };\n\n public createFactory(): AssetFactory<AsepriteData, AsepriteSheet> {\n return {\n async create(source, context) {\n const texture: Texture = await context.dependencies.load(Asset.type('texture', resolveAsepriteUrl(source.meta.image, context.source)));\n\n return AsepriteSheet.parse(source, texture);\n },\n };\n }\n}\n\n/** The Aseprite sheet asset type. Install it through {@link asepriteExtension}. */\nexport const asepriteType = new AsepriteAssetType();\n"],"mappings":";;;;;AAIA,MAAM,kBAAkB;;AAQxB,MAAM,qBAAqB;;AAG3B,MAAM,sBAAsB;;AAG5B,MAAM,kBAAkB;;;;;;;;;;AAWxB,MAAM,sBAAsB,KAAa,SAAyB;CAChE,IAAI,mBAAmB,KAAK,GAAG,GAC7B,OAAO;CAGT,IAAI,oBAAoB,KAAK,IAAI,GAC/B,OAAO,IAAI,IAAI,KAAK,IAAI,CAAC,CAAC;CAI5B,MAAM,WAAW,IADI,IAAI,KAAK,kBAAkB,KAAK,QAAQ,QAAQ,EAAE,CAC/C,CAAC,CAAC,KAAK,MAAM,EAAsB;CAK3D,OAAO,KAAK,WAAW,GAAG,IAAI,IAAI,aAAa;AACjD;;;;;AAQA,IAAa,sBAAb,cAAyC,MAAM;CAC7C,AAAgB;CAEhB,AAAO,YAAY,QAAgB,SAAiB;EAClD,MAAM,yBAAyB,OAAO,IAAI,SAAS;EACnD,KAAK,OAAO;EACZ,KAAK,SAAS;CAChB;AACF;;;;;;AAOA,MAAM,wBAAwB,KAAc,WAAiC;CAC3E,IAAI,OAAO,QAAQ,YAAY,QAAQ,MACrC,MAAM,IAAI,oBAAoB,QAAQ,wBAAwB;CAGhE,MAAM,MAAM;CAEZ,IAAI,EAAE,YAAY,MAChB,MAAM,IAAI,oBAAoB,QAAQ,mCAAiC;CAGzE,IAAI,EAAE,UAAU,QAAQ,OAAO,IAAI,SAAS,YAAY,IAAI,SAAS,MACnE,MAAM,IAAI,oBAAoB,QAAQ,iCAA+B;CAGvE,MAAM,OAAO,IAAI;CAEjB,IAAI,OAAO,KAAK,UAAU,YAAY,KAAK,MAAM,WAAW,GAC1D,MAAM,IAAI,oBAAoB,QAAQ,2CAAyC;CAGjF,MAAM,SAAS,IAAI;CAEnB,IAAI,CAAC,MAAM,QAAQ,MAAM,MAAM,OAAO,WAAW,YAAY,WAAW,OACtE,MAAM,IAAI,oBAAoB,QAAQ,0CAAwC;CAGhF,OAAO;AACT;;;;;;;;AASA,IAAa,oBAAb,cAAuC,UAA0D;CAC/F,AAAgB,KAAK;CACrB,AAAyB,SAAS;CAGlC,AAAyB,QAAgD;EACvE,eAAe,UAAU,YAAY,gBAAgB,aAAa,UAAU,OAAO;EACnF,YAAY,OAAO,YAAY,gBAAgB,UAAU,OAAO,OAAO;EACvE,SAAS,QAAQ,YAAY,QAAQ,QAAQ,qBAAqB,KAAK,MAAM,MAAM,GAAG,QAAQ,OAAO,CAAC;CACxG;CAEA,AAAO,gBAA2D;EAChE,OAAO,EACL,MAAM,OAAO,QAAQ,SAAS;GAC5B,MAAM,UAAmB,MAAM,QAAQ,aAAa,KAAK,MAAM,KAAK,WAAW,mBAAmB,OAAO,KAAK,OAAO,QAAQ,MAAM,CAAC,CAAC;GAErI,OAAO,cAAc,MAAM,QAAQ,OAAO;EAC5C,EACF;CACF;AACF;;AAGA,MAAa,eAAe,IAAI,kBAAkB"}
@@ -1 +1,2 @@
1
1
  export * from './public';
2
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAEA,cAAc,UAAU,CAAC"}
package/dist/esm/index.js CHANGED
@@ -1,5 +1,6 @@
1
- export { AsepriteFormatError, asepriteBinding } from './asepriteBinding.js';
2
- export { isAsepriteArrayData } from './AsepriteData.js';
3
- export { asepriteExtension } from './asepriteExtension.js';
4
- export { AsepriteSheet } from './AsepriteSheet.js';
5
- //# sourceMappingURL=index.js.map
1
+ import { isAsepriteArrayData } from "./AsepriteData.js";
2
+ import { AsepriteSheet } from "./AsepriteSheet.js";
3
+ import { AsepriteAssetType, AsepriteFormatError, asepriteType } from "./asepriteType.js";
4
+ import { asepriteExtension } from "./asepriteExtension.js";
5
+
6
+ export { AsepriteAssetType, AsepriteFormatError, AsepriteSheet, asepriteExtension, asepriteType, isAsepriteArrayData };
@@ -1,8 +1,8 @@
1
- export { asepriteBinding, AsepriteFormatError } from './asepriteBinding';
2
1
  export type { AsepriteArrayData, AsepriteData, AsepriteDirection, AsepriteFrameData, AsepriteFrameTag, AsepriteHashData, AsepriteLayer, AsepriteMeta, AsepriteRect, AsepriteSize, AsepriteSlice, AsepriteSliceKey, } from './AsepriteData';
3
2
  export { isAsepriteArrayData } from './AsepriteData';
4
3
  export { asepriteExtension } from './asepriteExtension';
5
4
  export { AsepriteSheet } from './AsepriteSheet';
5
+ export { AsepriteAssetType, AsepriteFormatError, asepriteType } from './asepriteType';
6
6
  import type { AsepriteSheet } from './AsepriteSheet';
7
7
  declare module '@codexo/exojs' {
8
8
  interface AssetDefinitions {
@@ -11,6 +11,8 @@ declare module '@codexo/exojs' {
11
11
  config: {
12
12
  source: string;
13
13
  };
14
+ isValue: true;
14
15
  };
15
16
  }
16
17
  }
18
+ //# sourceMappingURL=public.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"public.d.ts","sourceRoot":"","sources":["../../src/public.ts"],"names":[],"mappings":"AAGA,YAAY,EACV,iBAAiB,EACjB,YAAY,EACZ,iBAAiB,EACjB,iBAAiB,EACjB,gBAAgB,EAChB,gBAAgB,EAChB,aAAa,EACb,YAAY,EACZ,YAAY,EACZ,YAAY,EACZ,aAAa,EACb,gBAAgB,GACjB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,mBAAmB,EAAE,MAAM,gBAAgB,CAAC;AACrD,OAAO,EAAE,iBAAiB,EAAE,MAAM,qBAAqB,CAAC;AACxD,OAAO,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAChD,OAAO,EAAE,iBAAiB,EAAE,mBAAmB,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAGtF,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAErD,OAAO,QAAQ,eAAe,CAAC;IAC7B,UAAU,gBAAgB;QACxB,aAAa,EAAE;YACb,QAAQ,EAAE,aAAa,CAAC;YACxB,MAAM,EAAE;gBAAE,MAAM,EAAE,MAAM,CAAA;aAAE,CAAC;YAG3B,OAAO,EAAE,IAAI,CAAC;SACf,CAAC;KACH;CACF"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@codexo/exojs-aseprite",
3
- "version": "0.15.3",
3
+ "version": "0.16.0",
4
4
  "description": "Aseprite sprite sheet asset extension for ExoJS.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -8,9 +8,7 @@
8
8
  "directory": "packages/exojs-aseprite"
9
9
  },
10
10
  "type": "module",
11
- "sideEffects": [
12
- "./dist/esm/register.js"
13
- ],
11
+ "sideEffects": false,
14
12
  "main": "./dist/esm/index.js",
15
13
  "module": "./dist/esm/index.js",
16
14
  "types": "./dist/esm/index.d.ts",
@@ -20,11 +18,6 @@
20
18
  "import": "./dist/esm/index.js",
21
19
  "default": "./dist/esm/index.js"
22
20
  },
23
- "./register": {
24
- "types": "./dist/esm/register.d.ts",
25
- "import": "./dist/esm/register.js",
26
- "default": "./dist/esm/register.js"
27
- },
28
21
  "./package.json": "./package.json"
29
22
  },
30
23
  "files": [
@@ -33,20 +26,20 @@
33
26
  "LICENSE"
34
27
  ],
35
28
  "peerDependencies": {
36
- "@codexo/exojs": "0.15.x"
29
+ "@codexo/exojs": "0.16.x"
37
30
  },
38
31
  "devDependencies": {
39
- "@codexo/exojs-config": "0.0.0",
40
- "@codexo/exojs": "0.15.3"
32
+ "@codexo/exojs": "0.16.0",
33
+ "@codexo/exojs-config": "0.0.0"
41
34
  },
42
35
  "license": "MIT",
43
36
  "publishConfig": {
44
37
  "access": "public"
45
38
  },
46
39
  "scripts": {
47
- "build": "tsx ../../node_modules/rollup/dist/bin/rollup -c --environment EXOJS_ENV:production",
48
- "build:dev": "tsx ../../node_modules/rollup/dist/bin/rollup -c --environment EXOJS_ENV:development",
49
- "typecheck": "tsc --noEmit",
40
+ "build": "tsx ../../scripts/build-extension.ts",
41
+ "build:dev": "tsx ../../scripts/build-extension.ts --dev",
42
+ "typecheck": "tsc --noEmit && tsc --noEmit -p tsconfig.test.json",
50
43
  "lint": "eslint \"src/**/*.ts\"",
51
44
  "test": "vitest run --root ../.. --project=exojs-aseprite"
52
45
  }
@@ -1,27 +0,0 @@
1
- import { AsepriteSheet } from './AsepriteSheet';
2
- /**
3
- * Thrown when an Aseprite JSON document does not match the expected shape.
4
- * `source` is the URL of the file being parsed.
5
- */
6
- export declare class AsepriteFormatError extends Error {
7
- readonly source: string;
8
- constructor(source: string, message: string);
9
- }
10
- /**
11
- * Declarative asset binding for {@link AsepriteSheet}.
12
- *
13
- * `loader.load(AsepriteSheet, 'hero.aseprite.json')` fetches and validates the
14
- * Aseprite JSON export, resolves the packed image URL from `meta.image`
15
- * (relative to the JSON source), loads the {@link Texture} via the Loader's
16
- * sub-load deduplication, and constructs a fully-parsed {@link AsepriteSheet}.
17
- *
18
- * The `aseprite` type name enables the asset-config shorthand:
19
- * `{ type: 'aseprite', source: 'hero.aseprite.json' }`.
20
- */
21
- export declare const asepriteBinding: {
22
- type: typeof AsepriteSheet;
23
- typeNames: string[];
24
- create(): {
25
- load(req: import("@codexo/exojs").AssetLoadRequest<undefined>, ctx: import("@codexo/exojs").AssetLoaderContext): Promise<AsepriteSheet>;
26
- };
27
- };
@@ -1,106 +0,0 @@
1
- import { Texture } from '@codexo/exojs';
2
- import { AsepriteSheet } from './AsepriteSheet.js';
3
-
4
- // Relative-path resolution for Aseprite image references (JSON → PNG).
5
- // Mirrors the approach used in @codexo/exojs-tiled: Aseprite stores the image
6
- // path relative to the JSON file; asset sources are often themselves relative,
7
- // so plain `new URL(ref, base)` cannot be used when `base` has no scheme.
8
- // ── URL resolution ───────────────────────────────────────────────────────────
9
- /** Matches references that are already absolute: scheme, `//`, `/`, data/blob. */
10
- const absoluteRefPattern = /^(?:[a-z][a-z\d+.-]*:|\/\/|\/)/i;
11
- /** Matches a base that has an explicit scheme (absolute URL). */
12
- const absoluteBasePattern = /^[a-z][a-z\d+.-]*:/i;
13
- /** Synthetic origin used to borrow `URL`'s `../`/`./` collapsing. */
14
- const syntheticOrigin = 'https://exojs.invalid/';
15
- /**
16
- * Resolves `ref` (the image path read from an Aseprite JSON file) relative to
17
- * `base` (the resolved location of the JSON file itself).
18
- *
19
- * - Absolute refs (scheme, `//`, `/`, `data:`, `blob:`) are returned as-is.
20
- * - Absolute bases delegate to `new URL(ref, base).href`.
21
- * - Relative bases use a synthetic origin to collapse `./` and `../` segments,
22
- * then strips the origin from the result.
23
- */
24
- function resolveAsepriteUrl(ref, base) {
25
- if (absoluteRefPattern.test(ref)) {
26
- return ref;
27
- }
28
- if (absoluteBasePattern.test(base)) {
29
- return new URL(ref, base).href;
30
- }
31
- const resolved = new URL(ref, syntheticOrigin + base.replace(/^\/+/, ''));
32
- const relative = resolved.href.slice(syntheticOrigin.length);
33
- // A root-relative base must produce a root-relative result again — dropping
34
- // the leading slash would make the browser re-resolve the reference against
35
- // the document base URL (e.g. `/site/assets/x.png` → `/site/site/assets/…`).
36
- return base.startsWith('/') ? `/${relative}` : relative;
37
- }
38
- // ── Validation ───────────────────────────────────────────────────────────────
39
- /**
40
- * Thrown when an Aseprite JSON document does not match the expected shape.
41
- * `source` is the URL of the file being parsed.
42
- */
43
- class AsepriteFormatError extends Error {
44
- source;
45
- constructor(source, message) {
46
- super(`[AsepriteFormatError] ${source}: ${message}`);
47
- this.name = 'AsepriteFormatError';
48
- this.source = source;
49
- }
50
- }
51
- /**
52
- * Validates an `unknown` value against the minimum required Aseprite JSON
53
- * shape and narrows it to {@link AsepriteData}. Throws {@link AsepriteFormatError}
54
- * on any mismatch.
55
- */
56
- function validateAsepriteData(raw, source) {
57
- if (typeof raw !== 'object' || raw === null) {
58
- throw new AsepriteFormatError(source, 'root must be an object');
59
- }
60
- const doc = raw;
61
- if (!('frames' in doc)) {
62
- throw new AsepriteFormatError(source, 'missing required field "frames"');
63
- }
64
- if (!('meta' in doc) || typeof doc.meta !== 'object' || doc.meta === null) {
65
- throw new AsepriteFormatError(source, 'missing required field "meta"');
66
- }
67
- const meta = doc.meta;
68
- if (typeof meta.image !== 'string' || meta.image.length === 0) {
69
- throw new AsepriteFormatError(source, '"meta.image" must be a non-empty string');
70
- }
71
- const frames = doc.frames;
72
- if (!Array.isArray(frames) && (typeof frames !== 'object' || frames === null)) {
73
- throw new AsepriteFormatError(source, '"frames" must be an array or an object');
74
- }
75
- return doc;
76
- }
77
- // ── Asset binding ─────────────────────────────────────────────────────────────
78
- /**
79
- * Declarative asset binding for {@link AsepriteSheet}.
80
- *
81
- * `loader.load(AsepriteSheet, 'hero.aseprite.json')` fetches and validates the
82
- * Aseprite JSON export, resolves the packed image URL from `meta.image`
83
- * (relative to the JSON source), loads the {@link Texture} via the Loader's
84
- * sub-load deduplication, and constructs a fully-parsed {@link AsepriteSheet}.
85
- *
86
- * The `aseprite` type name enables the asset-config shorthand:
87
- * `{ type: 'aseprite', source: 'hero.aseprite.json' }`.
88
- */
89
- const asepriteBinding = {
90
- type: AsepriteSheet,
91
- typeNames: ['asepriteSheet'],
92
- create() {
93
- return {
94
- async load(req, ctx) {
95
- const raw = await ctx.fetchJson(req.source);
96
- const data = validateAsepriteData(raw, req.source);
97
- const imageUrl = resolveAsepriteUrl(data.meta.image, req.source);
98
- const texture = (await ctx.loader.load(Texture, imageUrl));
99
- return AsepriteSheet.parse(data, texture);
100
- },
101
- };
102
- },
103
- };
104
-
105
- export { AsepriteFormatError, asepriteBinding };
106
- //# sourceMappingURL=asepriteBinding.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"asepriteBinding.js","sources":["../../../src/asepriteBinding.ts"],"sourcesContent":[null],"names":[],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;"}
@@ -1 +0,0 @@
1
- export * from './public';
@@ -1,15 +0,0 @@
1
- import { ExtensionRegistry } from '@codexo/exojs/extensions';
2
- import { asepriteExtension } from './asepriteExtension.js';
3
- export { AsepriteFormatError, asepriteBinding } from './asepriteBinding.js';
4
- export { isAsepriteArrayData } from './AsepriteData.js';
5
- export { AsepriteSheet } from './AsepriteSheet.js';
6
-
7
- // @codexo/exojs-aseprite/register — explicit registration entry.
8
- // Importing this entry registers the default asepriteExtension descriptor
9
- // in the global ExtensionRegistry. Subsequently constructed Applications
10
- // that use global defaults will receive the Aseprite extension.
11
- // This is the only side-effectful entry in this package.
12
- ExtensionRegistry.register(asepriteExtension);
13
-
14
- export { asepriteExtension };
15
- //# sourceMappingURL=register.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"register.js","sources":["../../../src/register.ts"],"sourcesContent":[null],"names":[],"mappings":";;;;;;AAAA;AACA;AACA;AACA;AACA;AAMA,iBAAiB,CAAC,QAAQ,CAAC,iBAAiB,CAAC;;;;"}