Skip to content

TSL: Unable to use KTX2 textures #32019

@kekkorider

Description

@kekkorider

Description

Can't say if it's me or not, but it seems like KTX2 textures have issues with NodeMaterials.

I'm trying to use a KTX2 texture (took this one from the repo just to be sure it works) but it returns several errors saying

Cannot read properties of undefined (reading 'width')

Reproduction steps

  1. Open the demo
  2. Comment out line 47

Code

import * as THREE from "three/webgpu";
import { KTX2Loader } from "three/examples/jsm/loaders/KTX2Loader";
import { Fn, color, vec4, texture, uv } from "three/tsl";
import gsap from "gsap";
import "./styles.css";

const scene = new THREE.Scene();

const renderer = new THREE.WebGPURenderer({
  antialias: true,
  canvas: document.getElementById("canvas"),
});
renderer.toneMapping = THREE.ACESFilmicToneMapping;

const camera = new THREE.PerspectiveCamera(
  40,
  window.innerWidth / window.innerHeight,
  1,
  10
);
camera.position.set(0, 0, 3);

const loadingManager = new THREE.LoadingManager();
const textureLoader = new THREE.TextureLoader(loadingManager);
const ktx2Loader = new KTX2Loader();
ktx2Loader.setTranscoderPath("/public/basis/");
ktx2Loader.detectSupport(renderer);

textureLoader.load("/public/textures/bg_C.png", function (tex) {
  const material = new THREE.MeshBasicNodeMaterial();
  const geometry = new THREE.PlaneGeometry(1, 1);

  material.colorNode = Fn(() => {
    return texture(tex);
  })();

  const mesh = new THREE.Mesh(geometry, material);
  mesh.position.set(-0.6, 0, 0);
  scene.add(mesh);
});

ktx2Loader.load("/public/textures/2d_etc1s.ktx2", (tex) => {
  const material = new THREE.MeshBasicNodeMaterial();
  const geometry = new THREE.PlaneGeometry(1, 1);

  material.colorNode = Fn(() => {
    return color(uv(), 0.2); // Comment this line to see the error
    return texture(tex); // This triggers an error
  })();

  const mesh = new THREE.Mesh(geometry, material);
  mesh.position.set(0.6, 0, 0);
  scene.add(mesh);
});

gsap.ticker.fps(60);
gsap.ticker.add((time, delta) => {
  renderer.renderAsync(scene, camera);
});

handleResize();

window.addEventListener("resize", handleResize);

function handleResize() {
  const w = window.innerWidth;
  const h = window.innerHeight;

  camera.aspect = w / h;
  camera.updateProjectionMatrix();

  renderer.setSize(w, h);
}

Live example

Screenshots

Image

Version

r180

Device

Desktop

Browser

Chrome

OS

MacOS

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions