@needle-tools/gltf-build-pipeline 1.5.0-alpha.6 → 1.5.0-alpha.7

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/CHANGELOG.md CHANGED
@@ -4,8 +4,13 @@ All notable changes to this package will be documented in this file.
4
4
  The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/)
5
5
  and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html).
6
6
 
7
+ ## [1.5.0-alpha.7] - 2023-05-16
8
+ - fix: external resources that are KTX2 compressed are now saved with a `.ktx2` extension
9
+ - change: toktx now uses compression "auto" mode to select uastc or etc1s
10
+ - change: toktx now checks the slots and increases quality for `metallicRoughnessTexture` and `normalTexture` but keeps using ETC1S for smaller file size
11
+
7
12
  ## [1.5.0-alpha.6] - 2023-05-15
8
- - fix: If not further specified then automatically use UASTC for textures that are in either `normalTexture` or `metallicOcclusionTexture` slots
13
+ - fix: If not further specified then automatically use UASTC for textures that are in either `normalTexture` or `metallicRoughnessTexture` slots
9
14
 
10
15
  ## [1.5.0-alpha.5] - 2023-05-04
11
16
  - fix: NEEDLE_opaque should handle if VRM texture index is negative
@@ -1,6 +1,7 @@
1
1
  import { Document, Texture } from '@gltf-transform/core';
2
2
  import { NEEDLE_compression_texture_schema } from '../extensions/index.js';
3
3
  export interface NeedleTransformContext {
4
+ /** full path to the file being processed */
4
5
  file: string;
5
6
  debug?: boolean;
6
7
  useCache: boolean;
@@ -5,6 +5,8 @@ import { addToCache, getKey, tryGetFromCache } from "../cache/index.js";
5
5
  import { NeedleWebPContext } from "./needle_webp.js";
6
6
  import { NeedleToktxContext } from "./needle_toktx.js";
7
7
  import { createTransform } from "@gltf-transform/functions";
8
+ import { dirname } from "path";
9
+ import { existsSync, rmSync } from "fs";
8
10
  export async function resizeTextureIfNecessary(texture) {
9
11
  const ext = texture.getExtension(NEEDLE_compression_texture.EXTENSION_NAME);
10
12
  if (ext?.model) {
@@ -96,6 +98,7 @@ async function processTexture(texture, index, document, logger, context) {
96
98
  }
97
99
  let successFullyProcessed = false;
98
100
  const canRunToktx = context.noToktx !== true;
101
+ const originalUri = texture.getURI();
99
102
  if (compressionSettings && compressionSettings.mode !== "auto") {
100
103
  switch (compressionSettings.mode) {
101
104
  case "webp":
@@ -167,4 +170,15 @@ async function processTexture(texture, index, document, logger, context) {
167
170
  if (data)
168
171
  addToCache(key, data);
169
172
  }
173
+ if (successFullyProcessed) {
174
+ const newUri = texture.getURI();
175
+ if (originalUri && originalUri != newUri) {
176
+ const fileDirectory = dirname(context.file);
177
+ const originalPath = fileDirectory + "/" + originalUri;
178
+ if (existsSync(originalPath)) {
179
+ console.log(`INFO: Texture moved \"${originalUri}\" → \"${newUri}\"`);
180
+ rmSync(originalPath);
181
+ }
182
+ }
183
+ }
170
184
  }
@@ -114,16 +114,29 @@ export class NeedleToktxContext {
114
114
  // const inBytes = image.byteLength;
115
115
  await fs.writeFile(inPath, Buffer.from(image));
116
116
  let mode = Mode.ETC1S;
117
+ let quality = 128;
118
+ let compression = 1;
117
119
  if (settings) {
118
- mode = settings.mode === "ETC1S" ? Mode.ETC1S : Mode.UASTC;
120
+ if (settings.mode === "auto") {
121
+ const useUASTC = slots.includes("normalTexture") || slots.includes("metallicRoughnessTexture");
122
+ mode = useUASTC ? Mode.UASTC : Mode.ETC1S;
123
+ }
124
+ else {
125
+ mode = settings.mode === "ETC1S" ? Mode.ETC1S : Mode.UASTC;
126
+ }
119
127
  }
120
128
  else if (slots) {
121
- const useUASTC = slots.includes("normalTexture") || slots.includes("metallicRoughnessTexture");
122
- mode = useUASTC ? Mode.UASTC : Mode.ETC1S;
129
+ const betterQuality = slots.includes("normalTexture") || slots.includes("metallicRoughnessTexture");
130
+ // mode = useUASTC ? Mode.UASTC : Mode.ETC1S;
131
+ mode = Mode.ETC1S;
132
+ // https://github.khronos.org/KTX-Software/ktxtools/toktx.html
133
+ quality = betterQuality ? 255 : 128;
134
+ // ETC1S / BasisLZ compression level, an encoding speed vs. quality tradeoff. Range is [0,5], default is 1. Higher values are slower but give higher quality.
135
+ compression = betterQuality ? 4 : 1;
123
136
  }
124
137
  const defaults = mode === Mode.ETC1S ? ETC1S_DEFAULTS : UASTC_DEFAULTS;
125
138
  //@ts-ignore
126
- const toktxParams = createParams(slots, channels, size, logger, this.numTextures, { ...defaults, mode }, this.version);
139
+ const toktxParams = createParams(slots, channels, size, logger, this.numTextures, { ...defaults, mode, quality, compression }, this.version);
127
140
  const params = [
128
141
  ...toktxParams,
129
142
  outPath,
@@ -141,6 +154,13 @@ export class NeedleToktxContext {
141
154
  else {
142
155
  const result = await fs.readFile(outPath);
143
156
  texture.setImage(result).setMimeType('image/ktx2');
157
+ // TODO: we also need to remove the old file when the extension has changed - this should probably be done outside of this method to also support webp
158
+ // If this is a texture that was loaded from a file, we need to update the URI
159
+ if (texture.getURI()) {
160
+ const oldUri = texture.getURI();
161
+ const newUri = FileUtils.basename(oldUri) + '.ktx2';
162
+ texture.setURI(newUri);
163
+ }
144
164
  return true;
145
165
  }
146
166
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@needle-tools/gltf-build-pipeline",
3
- "version": "1.5.0-alpha.6",
3
+ "version": "1.5.0-alpha.7",
4
4
  "description": "Pipeline and tools for optimizing gltf files using gltf-transform and compression settings within glTF extensions",
5
5
  "main": "index.mjs",
6
6
  "type": "module",