Gltf模型在three.js中没有正确显示。

huangapple go评论83阅读模式
英文:

Gltf model does not looking properly in three.js

问题

以下是翻译的内容:

"我从sketchfab下载了以下模型,并导入到我的场景中,但模型似乎不正确,特别是玻璃模糊。

Gltf模型在three.js中没有正确显示。

Gltf模型在three.js中没有正确显示。

这是我的代码:

import "./sass/main.scss";

import { Scene, PerspectiveCamera, WebGLRenderer, DirectionalLight, ACESFilmicToneMapping, sRGBEncoding, Object3D, Mesh, MeshStandardMaterial, ReinhardToneMapping, AmbientLight, EquirectangularReflectionMapping,
} from "three";
import { GLTFLoader } from "three/examples/jsm/loaders/GLTFLoader";
import { RGBELoader } from "three/examples/jsm/loaders/RGBELoader";
import { OrbitControls } from "three/examples/jsm/controls/OrbitControls";

const scene = new Scene();
const camera = new PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
const renderer = new WebGLRenderer({
    canvas: document.querySelector("canvas#webgl"),
    antialias: true
});
renderer.toneMapping = ACESFilmicToneMapping;
renderer.outputEncoding = sRGBEncoding;
renderer.physicallyCorrectLights = true;
renderer.toneMappingExposure = 1
renderer.shadowMap.enabled = true;

const controls = new OrbitControls(camera, renderer.domElement);
camera.rotation.reorder("YXZ")
camera.position.set(2, 1.5, 3.5);
camera.rotation.set(-0.25, Math.PI * 0.25, 0);
renderer.setSize(window.innerWidth, window.innerHeight)

const gltfLoader = new GLTFLoader();
const rgbeLoader = new RGBELoader();

const environmentMap = await rgbeLoader.loadAsync("./assets/environment/puresky.hdr")
environmentMap.mapping = EquirectangularReflectionMapping;
scene.environment = environmentMap;

await gltfLoader.loadAsync("./assets/models/scene.gltf").then(gltf => {
    scene.add(gltf.scene);
});

mapAllElements();

function render() {

    renderer.render(scene, camera);

    requestAnimationFrame(render);
}

render();

function mapAllElements() {
    scene.traverse((child) => {
        if (child instanceof Mesh && child.material instanceof MeshStandardMaterial) {
            child.material.envMap = environmentMap;
            child.material.envMapIntensity = 1;
            child.material.needsUpdate = true;
        }
    })
}

我在互联网上搜索了我的问题,但没有找到有用的东西,我还尝试了sketchfab上的其他gltf模型,但其他模型也没有正确显示。

我的代码使用了顶级等待功能,并已从webpack.config.js启用。"

英文:

I downloaded the following model from sketchfab and imported to my scene but model does not seem looking correctly especially the glass blur.

Gltf模型在three.js中没有正确显示。

Gltf模型在three.js中没有正确显示。

here is my code

import "./sass/main.scss";
import { Scene, PerspectiveCamera, WebGLRenderer, DirectionalLight, ACESFilmicToneMapping, sRGBEncoding, Object3D, Mesh, MeshStandardMaterial, ReinhardToneMapping, AmbientLight, EquirectangularReflectionMapping,
} from "three";
import { GLTFLoader } from "three/examples/jsm/loaders/GLTFLoader";
import { RGBELoader } from "three/examples/jsm/loaders/RGBELoader";
import { OrbitControls } from "three/examples/jsm/controls/OrbitControls";
const scene = new Scene();
const camera = new PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
const renderer = new WebGLRenderer({
canvas: document.querySelector("canvas#webgl"),
antialias: true
});
renderer.toneMapping = ACESFilmicToneMapping;
renderer.outputEncoding = sRGBEncoding;
renderer.physicallyCorrectLights = true;
renderer.toneMappingExposure = 1
renderer.shadowMap.enabled = true;
const controls = new OrbitControls(camera, renderer.domElement);
camera.rotation.reorder("YXZ")
camera.position.set(2, 1.5, 3.5);
camera.rotation.set(-0.25, Math.PI * 0.25, 0);
renderer.setSize(window.innerWidth, window.innerHeight)
const gltfLoader = new GLTFLoader();
const rgbeLoader = new RGBELoader();
const environmentMap = await rgbeLoader.loadAsync("./assets/environment/puresky.hdr")
environmentMap.mapping = EquirectangularReflectionMapping;
scene.environment = environmentMap;
await gltfLoader.loadAsync("./assets/models/scene.gltf").then(gltf => {
scene.add(gltf.scene);
});
mapAllElements();
function render() {
renderer.render(scene, camera);
requestAnimationFrame(render);
}
render();
function mapAllElements() {
scene.traverse((child) => {
if (child instanceof Mesh && child.material instanceof MeshStandardMaterial) {
child.material.envMap = environmentMap;
child.material.envMapIntensity = 1;
child.material.needsUpdate = true;
}
})
}

I searched my problem on the internet but couldn't find anything useful and I also tried other gltf models from sketchfab but other models also does not looking properly.

My code is using top-level-await feature and I enabled from webpack.config.js

答案1

得分: 1

模型的外观与其加载的查看器有关。如果您想重新创建效果,可以使用THREE.MeshPhysicalMaterial类创建新的材质,这是一种可以模拟逼真的光照和材质的物理材质。

一个简单的示例如下:

scene.traverse((child) => {
    if (child instanceof Mesh && child.material instanceof MeshStandardMaterial) {
      if (child.name.includes("glass")) {
        // 为玻璃对象创建新的MeshPhysicalMaterial
        const glassMaterial = new THREE.MeshPhysicalMaterial({
          color: 0xffffff,
          metalness: 0,
          roughness: 0.1,
          transparent: true,
          transmission: 0.9,
          opacity: 0.7,
          envMap: environmentMap,
          envMapIntensity: 1,
          side: THREE.DoubleSide,
        });
        // 用新的玻璃材质替换现有材质
        child.material = glassMaterial;
      } else {
        // 对于非玻璃对象,只需添加环境映射
        child.material.envMap = environmentMap;
        child.material.envMapIntensity = 1;
      }
      child.material.needsUpdate = true;
    }
  });
}

如果您不想重复造轮子,还可以查看WebGi,在那里您可以通过一个可访问的插件系统获得更精细的控制。

英文:

The way the model looks is tied to the Viewer in which it is loaded. If you want to recreate the effects you can create a new material using the THREE.MeshPhysicalMaterial class, which is a physically-based material that can simulate realistic lighting and materials.

A barebones example is as follows:

scene.traverse((child) => {
    if (child instanceof Mesh && child.material instanceof MeshStandardMaterial) {
      if (child.name.includes("glass")) {
        // Create a new MeshPhysicalMaterial for the glass object
        const glassMaterial = new THREE.MeshPhysicalMaterial({
          color: 0xffffff,
          metalness: 0,
          roughness: 0.1,
          transparent: true,
          transmission: 0.9,
          opacity: 0.7,
          envMap: environmentMap,
          envMapIntensity: 1,
          side: THREE.DoubleSide,
        });
        // Replace the existing material with the new glass material
        child.material = glassMaterial;
      } else {
        // For non-glass objects, just add the environment map
        child.material.envMap = environmentMap;
        child.material.envMapIntensity = 1;
      }
      child.material.needsUpdate = true;
    }
  });
}

If you don't want to re-invent the wheel, you can also take a look at WebGi, where you have much finer grained control through an accessible plugin system.

huangapple
  • 本文由 发表于 2023年2月18日 22:27:34
  • 转载请务必保留本文链接:https://go.coder-hub.com/75493996.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定