diff --git a/.github/workflows/static.yml b/.github/workflows/static.yml index 4a5946cc..a0a446f6 100644 --- a/.github/workflows/static.yml +++ b/.github/workflows/static.yml @@ -56,8 +56,17 @@ jobs: source ../../emsdk/emsdk_env.sh make + - name: otherasserts + working-directory: ${{ github.workspace }}/web/demo + run: | + sh download_asset.sh + cp UsdCookie.usdz ../dist + cp index.html ../dist + cp main.js ../dist + - name: Setup Pages uses: actions/configure-pages@v5 + - name: Upload artifact uses: actions/upload-pages-artifact@v3 with: diff --git a/web/demo/README.md b/web/demo/README.md new file mode 100644 index 00000000..cbb3c28b --- /dev/null +++ b/web/demo/README.md @@ -0,0 +1,3 @@ +See /.github/workflows/static.yaml + +UsdCookie.usdz : Each asset has a license declared in the readme, typically CC0 or something highly permissive diff --git a/web/demo/download_asset.sh b/web/demo/download_asset.sh new file mode 100644 index 00000000..6275f793 --- /dev/null +++ b/web/demo/download_asset.sh @@ -0,0 +1,2 @@ +wget https://github.com/usd-wg/assets/raw/main/full_assets/UsdCookie/UsdCookie.usdz + diff --git a/web/demo/main.js b/web/demo/main.js new file mode 100644 index 00000000..a9ab46f7 --- /dev/null +++ b/web/demo/main.js @@ -0,0 +1,89 @@ +import * as THREE from 'three'; + +import initTinyUSDZ from 'https://lighttransport.github.io/tinyusdz/tinyusdz.js'; + +const USDZ_FILEPATH = './UsdCookie.usdz'; + +const usd_res = await fetch(USDZ_FILEPATH); +const usd_data = await usd_res.arrayBuffer(); + +const usd_binary = new Uint8Array(usd_data); + +initTinyUSDZ().then(function(TinyUSDZLoader) { + + const usd = new TinyUSDZLoader.TinyUSDZLoader(usd_binary); + console.log(usd.numMeshes()); + + const scene = new THREE.Scene(); + const camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 0.1, 1000 ); + + const renderer = new THREE.WebGLRenderer(); + renderer.setSize( window.innerWidth, window.innerHeight ); + renderer.setAnimationLoop( animate ); + document.body.appendChild( renderer.domElement ); + + // First mesh only + const mesh = usd.getMesh(0); + console.log(mesh); + + //const geometry = new THREE.BoxGeometry( 1, 1, 1 ); + const geometry = new THREE.BufferGeometry(); + geometry.setAttribute( 'position', new THREE.BufferAttribute( mesh.points, 3 ) ); + // TODO: set normal from mesh + + if (mesh.hasOwnProperty('texcoords')) { + console.log(mesh.texcoords); + geometry.setAttribute( 'uv', new THREE.BufferAttribute( mesh.texcoords, 2 ) ); + } + + const usdMaterial = usd.getMaterial(mesh.materialId); + console.log("usdMat", usdMaterial); + if (usdMaterial.aaa) { + console.log("aaa"); + } + + var material; + + if (usdMaterial.hasOwnProperty('diffuseColorTextureId')) { + const diffTex = usd.getTexture(usdMaterial.diffuseColorTextureId); + + const img = usd.getImage(diffTex.textureImageId); + console.log(img); + + // assume RGBA for now. + let image8Array = new Uint8ClampedArray(img.data); + let imgData = new ImageData(image8Array, img.width, img.height); + + const texture = new THREE.DataTexture( imgData, img.width, img.height ); + texture.flipY = true; + texture.needsUpdate = true; + + material = new THREE.MeshBasicMaterial({ + map: texture + }); + } else { + material = new THREE.MeshNormalMaterial(); + } + + + // Assume triangulated indices. + geometry.setIndex( new THREE.Uint32BufferAttribute(mesh.faceVertexIndices, 1) ); + + geometry.computeVertexNormals(); + + //const material = new THREE.MeshBasicMaterial( { color: 0x00ff00 } ); + const cube = new THREE.Mesh( geometry, material ); + scene.add( cube ); + + //camera.position.z = 25; + camera.position.z = 1.0; + + function animate() { + + cube.rotation.x += 0.01; + cube.rotation.y += 0.01; + + renderer.render( scene, camera ); + + } +});