@magicpixelart/cli 0.5.6 → 0.5.8

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,162 @@
1
+ /**
2
+ * Unity `.meta` generation for CLI-synced sprites.
3
+ *
4
+ * MIRROR: the TextureImporter body below is byte-identical to the in-app
5
+ * engine's (`src/utils/unitySync/unityMeta.ts`) so both sync paths produce the
6
+ * same pixel-art-correct importer settings. A sync test
7
+ * (`src/utils/unitySync/__tests__/unityMetaMirror.test.ts`) fails if they
8
+ * drift. The duplication is deliberate: the CLI is published as a standalone
9
+ * npm package and cannot import from the web app's source tree.
10
+ *
11
+ * GUIDs are derived deterministically from the asset identity, so re-running
12
+ * sync never changes a sprite's GUID and Unity scene/prefab references survive.
13
+ */
14
+ import { createHash } from 'node:crypto';
15
+ import { existsSync } from 'node:fs';
16
+ import { writeFile } from 'node:fs/promises';
17
+ export const DEFAULT_UNITY_PPU = 32;
18
+ /** 32-char hex GUID, stable for a given seed. */
19
+ export function unityGuid(seed) {
20
+ return createHash('sha256').update(seed).digest('hex').slice(0, 32);
21
+ }
22
+ /**
23
+ * TextureImporter meta tuned for pixel art:
24
+ * - textureType 8 (Sprite), single sprite mode
25
+ * - filterMode 0 (Point — no filtering)
26
+ * - textureCompression 0 (none)
27
+ * - mipmaps off, nPOTScale 0 (keep original size), wrap clamp
28
+ * - alphaIsTransparency 1
29
+ */
30
+ export function buildTextureImporterMeta(guid, ppu) {
31
+ return `fileFormatVersion: 2
32
+ guid: ${guid}
33
+ TextureImporter:
34
+ internalIDToNameTable: []
35
+ externalObjects: {}
36
+ serializedVersion: 12
37
+ mipmaps:
38
+ mipMapMode: 0
39
+ enableMipMap: 0
40
+ sRGBTexture: 1
41
+ linearTexture: 0
42
+ fadeOut: 0
43
+ borderMipMap: 0
44
+ mipMapsPreserveCoverage: 0
45
+ alphaTestReferenceValue: 0.5
46
+ mipMapFadeDistanceStart: 1
47
+ mipMapFadeDistanceEnd: 3
48
+ bumpmap:
49
+ convertToNormalMap: 0
50
+ externalNormalMap: 0
51
+ heightScale: 0.25
52
+ normalMapFilter: 0
53
+ flipGreenChannel: 0
54
+ isReadable: 0
55
+ streamingMipmaps: 0
56
+ streamingMipmapsPriority: 0
57
+ vTOnly: 0
58
+ ignoreMipmapLimit: 0
59
+ grayScaleToAlpha: 0
60
+ generateCubemap: 6
61
+ cubemapConvolution: 0
62
+ seamlessCubemap: 0
63
+ textureFormat: 1
64
+ maxTextureSize: 2048
65
+ textureSettings:
66
+ serializedVersion: 2
67
+ filterMode: 0
68
+ aniso: 1
69
+ mipBias: 0
70
+ wrapU: 1
71
+ wrapV: 1
72
+ wrapW: 1
73
+ nPOTScale: 0
74
+ lightmap: 0
75
+ compressionQuality: 50
76
+ spriteMode: 1
77
+ spriteExtrude: 1
78
+ spriteMeshType: 1
79
+ alignment: 0
80
+ spritePivot: {x: 0.5, y: 0.5}
81
+ spritePixelsToUnits: ${ppu}
82
+ spriteBorder: {x: 0, y: 0, z: 0, w: 0}
83
+ spriteGenerateFallbackPhysicsShape: 1
84
+ alphaUsage: 1
85
+ alphaIsTransparency: 1
86
+ spriteTessellationDetail: -1
87
+ textureType: 8
88
+ textureShape: 1
89
+ singleChannelComponent: 0
90
+ flipbookRows: 1
91
+ flipbookColumns: 1
92
+ maxTextureSizeSet: 0
93
+ compressionQualitySet: 0
94
+ textureFormatSet: 0
95
+ ignorePngGamma: 0
96
+ applyGammaDecoding: 0
97
+ swizzle: 50462976
98
+ cookieLightType: 0
99
+ platformSettings:
100
+ - serializedVersion: 4
101
+ buildTarget: DefaultTexturePlatform
102
+ maxTextureSize: 16384
103
+ resizeAlgorithm: 0
104
+ textureFormat: -1
105
+ textureCompression: 0
106
+ compressionQuality: 50
107
+ crunchedCompression: 0
108
+ allowsAlphaSplitting: 0
109
+ overridden: 0
110
+ ignorePlatformSupport: 0
111
+ androidETC2FallbackOverride: 0
112
+ forceMaximumCompressionQuality_BC6H_BC7: 0
113
+ spriteSheet:
114
+ serializedVersion: 2
115
+ sprites: []
116
+ outline: []
117
+ customData:
118
+ physicsShape: []
119
+ bones: []
120
+ spriteID:
121
+ internalID: 0
122
+ vertices: []
123
+ indices:
124
+ edges: []
125
+ weights: []
126
+ secondaryTextures: []
127
+ spriteCustomMetadata:
128
+ entries: []
129
+ nameFileIdTable: {}
130
+ mipmapLimitGroupName:
131
+ pSDRemoveMatte: 0
132
+ userData:
133
+ assetBundleName:
134
+ assetBundleVariant:
135
+ `;
136
+ }
137
+ /**
138
+ * Write `<file>.png.meta` beside each synced PNG that doesn't have one yet.
139
+ *
140
+ * Existing `.meta` files are never overwritten: once Unity has imported a
141
+ * sprite the user may have tweaked its importer settings (pivot, slicing,
142
+ * PPU) and clobbering that on every sync would be hostile. Delete the `.meta`
143
+ * to regenerate it.
144
+ */
145
+ export async function writeMissingUnityMetas(sprites, ppu = DEFAULT_UNITY_PPU) {
146
+ const result = { written: 0, failed: 0 };
147
+ for (const sprite of sprites) {
148
+ const metaPath = `${sprite.pngPath}.meta`;
149
+ if (!existsSync(sprite.pngPath) || existsSync(metaPath))
150
+ continue;
151
+ try {
152
+ await writeFile(metaPath, buildTextureImporterMeta(unityGuid(sprite.id), ppu));
153
+ result.written++;
154
+ }
155
+ catch {
156
+ // Non-fatal: Unity generates its own default .meta on import. Counted
157
+ // so `sync` can surface a single warning line instead of failing.
158
+ result.failed++;
159
+ }
160
+ }
161
+ return result;
162
+ }
package/package.json CHANGED
@@ -1,12 +1,17 @@
1
1
  {
2
2
  "name": "@magicpixelart/cli",
3
- "version": "0.5.6",
3
+ "version": "0.5.8",
4
4
  "description": "Sync MagicPixel pixel-art assets to your local project.",
5
5
  "type": "module",
6
6
  "bin": {
7
7
  "magicpixel": "dist/index.js"
8
8
  },
9
- "files": ["dist", "README.md", "CHANGELOG.md", "LICENSE"],
9
+ "files": [
10
+ "dist",
11
+ "README.md",
12
+ "CHANGELOG.md",
13
+ "LICENSE"
14
+ ],
10
15
  "scripts": {
11
16
  "build": "tsc && chmod +x dist/index.js",
12
17
  "dev": "tsx src/index.ts",