Sprite use png map . But it doesn't display properly when scene contains Bloom. What shound i do?

92 Views Asked by At

I loaded a Sprite in a scene with Bloom, the trouble is that my Sprite map is using an externally loaded Png texture. Not the usual solid color material. I know it's possible to make all the textures black first and then back to the original color. But if my material is using the png Map.what should I do? Let the Sprite display normally and not have Bloom .

enter image description here

<script type="module">
    import * as THREE from 'three';
    import { OrbitControls } from '../jsm/controls/OrbitControls.js';
    import Stats from '../jsm/libs/stats.module.js';
    import { GUI } from '../jsm/libs/lil-gui.module.min.js';
    import { EffectComposer } from '../jsm/postprocessing/EffectComposer.js';
    import { RenderPass } from '../jsm/postprocessing/RenderPass.js';
    import { UnrealBloomPass } from '../jsm/postprocessing/UnrealBloomPass.js';
    import { FBXLoader } from '../Loader/FBXLoader/FBXLoader.js';
    import { OBJLoader } from '../Loader/OBJLoader.js';
    import { MTLLoader } from '../Loader/MTLLoader.js'
    import { GLTFLoader } from "../Loader/GLTFLoader.js";
    import { ShaderPass } from '../jsm/postprocessing/ShaderPass.js';

    const ENTIRE_SCENE = 0, BLOOM_SCENE = 1;

    const bloomLayer = new THREE.Layers();
    bloomLayer.set(BLOOM_SCENE);

    let params = {
        exposure: 1,
        bloomThreshold: 0.41,
        bloomStrength: 0.66,
        bloomRadius: 0.05,
        scene: 'Scene with Glow'
    };

    //set MeshBasicMaterial
    const darkMaterial = new THREE.MeshBasicMaterial({ color: 'black' });
    const materials = {};

    /*--------renderer--------*/
    const renderer = new THREE.WebGLRenderer({ antialias: true });
    renderer.setPixelRatio(window.devicePixelRatio);
    renderer.setSize(window.innerWidth, window.innerHeight);
    document.body.appendChild(renderer.domElement);
    renderer.shadowMap.type = THREE.PCFSoftShadowMap;

    //add scene
    const scene = new THREE.Scene();

    /*--------camera--------*/
    const camera = new THREE.PerspectiveCamera(80, window.innerWidth / window.innerHeight, 0.1, 100000000);
    camera.position.set(0, 10, 10);
    camera.lookAt(0, 0, 0);

    //makeLabelCanvas
    function makeLabelCanvas(size, name) {
        const borderSize = 0;
        const ctx = document.createElement('canvas').getContext('2d');
        const font = `${size}px bold sans-serif`;
        ctx.font = font;

        // measure how long the name will be
        const doubleBorderSize = borderSize * 2;
        const width = ctx.measureText(name).width + doubleBorderSize;
        const height = 70 + doubleBorderSize;
        ctx.canvas.width = width;
        ctx.canvas.height = height;
        console.log(ctx);
        ctx.font = font;
        ctx.textBaseline = 'top';

        return ctx.canvas;
    }

    /*--------OrbitControls--------*/
    let controls = new OrbitControls(camera, renderer.domElement);
    controls.target.set(0, 0, 0);
    controls.enablePan = false;
    controls.maxPolarAngle = Math.PI / 2;
    controls.enableDamping = true;

    //Render
    const renderScene = new RenderPass(scene, camera);

    const bloomPass = new UnrealBloomPass(new THREE.Vector2(window.innerWidth, window.innerHeight), 1.5, 0.4, 0.85);
    bloomPass.threshold = params.bloomThreshold;
    bloomPass.strength = params.bloomStrength;
    bloomPass.radius = params.bloomRadius;

    const bloomComposer = new EffectComposer(renderer);
    bloomComposer.renderToScreen = false;
    bloomComposer.addPass(renderScene);
    bloomComposer.addPass(bloomPass);

    const finalPass = new ShaderPass(
        new THREE.ShaderMaterial({
            uniforms: {
                baseTexture: { value: null },
                bloomTexture: { value: bloomComposer.renderTarget2.texture }
            },
            vertexShader: document.getElementById('vertexshader').textContent,
            fragmentShader: document.getElementById('fragmentshader').textContent,
            defines: {}
        }), 'baseTexture'
    );
    finalPass.needsSwap = true;

    const finalComposer = new EffectComposer(renderer);
    finalComposer.addPass(renderScene);
    finalComposer.addPass(finalPass);

    /*--------Stats--------*/
    const stats = Stats();
    stats.showPanel(0);

    /*--------AmbientLight-1--------*/
    scene.add(new THREE.AmbientLight(0xffffff, 1));

    //light1
    const light1 = new THREE.PointLight(0xddffdd, 1);
    light1.position.z = 0;
    light1.position.y = 300;
    light1.position.x = 200;
    scene.add(light1);

    /*--------cube--------*/

    const geometry = new THREE.BoxGeometry(4, 4, 4);
    const material = new THREE.MeshBasicMaterial({ color: 0x000050 });
    const cube = new THREE.Mesh(geometry, material);
    scene.add(cube);

    /*--------label--------*/
    const canvas = makeLabelCanvas(100, 'name');
    const texture = new THREE.CanvasTexture(canvas);
    texture.wrapS = THREE.ClampToEdgeWrapping;
    texture.wrapT = THREE.ClampToEdgeWrapping;
    //Material
    const loader = new THREE.TextureLoader();
    const labelMaterial = new THREE.SpriteMaterial({
        map: loader.load('../img/moudle-lable/Wood-storage-tank/stokehold.png'),
        side: THREE.DoubleSide,
        transparent: true,
    });
    const label = new THREE.Sprite(labelMaterial);
    cube.add(label);

    label.position.x = -5;
    label.position.y = 3;
    label.position.z = 0;

    const label_BaseScale_X = 0.05;
    const label_BaseScale_Y = 0.05;

    label.scale.x = canvas.width * label_BaseScale_X;
    label.scale.y = canvas.height * label_BaseScale_Y;

    //window.onresize
    window.onresize = function () {
        camera.aspect = window.innerWidth / window.innerHeight;
        camera.updateProjectionMatrix();
        renderer.setSize(window.innerWidth, window.innerHeight);
    };

    function disposeMaterial(obj) {
        if (obj.material) {
            obj.material.dispose();
        }
    }

    //render
    function render() {
        switch (params.scene) {

            case 'Scene only':
                renderer.render(scene, camera);
                break;

            case 'Scene with Glow':

            default:
                // render scene with bloom
                renderBloom(true);

                // render the entire scene, then render bloom scene on top
                finalComposer.render();
                break;

        }

    }
    function renderBloom(mask) {

        if (mask === true) {
            renderer.setClearColor(0x000000); // all must be black, including background
            scene.traverse(darkenNonBloomed);
            bloomComposer.render();
            renderer.setClearColor(0xffffff); // set the color you want
            scene.traverse(restoreMaterial);
        } else {
            camera.layers.set(BLOOM_SCENE);
            bloomComposer.render();
            camera.layers.set(ENTIRE_SCENE);
        }
    }
    function darkenNonBloomed(obj) {
        if (obj.isMesh && bloomLayer.test(obj.layers) === false) {
            materials[obj.uuid] = obj.material;
            obj.material = darkMaterial;
        }
    }
    function restoreMaterial(obj) {
        if (materials[obj.uuid]) {
            obj.material = materials[obj.uuid];
            delete materials[obj.uuid];
        }
    }
    function animate() {
        render();
        requestAnimationFrame(animate);
    };
    animate();

    var axes = new THREE.AxisHelper(20);
    scene.add(axes);

</script>

this is my png enter image description here

And this is use PlaneBufferGeometry do .

<script type="module">
    import * as THREE from 'three';
    import { OrbitControls } from '../jsm/controls/OrbitControls.js';
    import Stats from '../jsm/libs/stats.module.js';
    import { GUI } from '../jsm/libs/lil-gui.module.min.js';
    import { EffectComposer } from '../jsm/postprocessing/EffectComposer.js';
    import { RenderPass } from '../jsm/postprocessing/RenderPass.js';
    import { UnrealBloomPass } from '../jsm/postprocessing/UnrealBloomPass.js';
    import { FBXLoader } from '../Loader/FBXLoader/FBXLoader.js';
    import { OBJLoader } from '../Loader/OBJLoader.js';
    import { MTLLoader } from '../Loader/MTLLoader.js'
    import { GLTFLoader } from "../Loader/GLTFLoader.js";
    import { ShaderPass } from '../jsm/postprocessing/ShaderPass.js';

    const ENTIRE_SCENE = 0, BLOOM_SCENE = 1;

    const bloomLayer = new THREE.Layers();
    bloomLayer.set(BLOOM_SCENE);

    let params = {
        exposure: 1,
        bloomThreshold: 0.41,
        bloomStrength: 0.66,
        bloomRadius: 0.05,
        scene: 'Scene with Glow'
    };

    //set MeshBasicMaterial
    const darkMaterial = new THREE.MeshBasicMaterial({ color: 'black' });
    const materials = {};

    /*--------renderer--------*/
    const renderer = new THREE.WebGLRenderer({ antialias: true });
    renderer.setPixelRatio(window.devicePixelRatio);
    renderer.setSize(window.innerWidth, window.innerHeight);
    document.body.appendChild(renderer.domElement);
    renderer.shadowMap.type = THREE.PCFSoftShadowMap;

    //add scene
    const scene = new THREE.Scene();

    /*--------camera--------*/
    const camera = new THREE.PerspectiveCamera(80, window.innerWidth / window.innerHeight, 0.1, 100000000);
    camera.position.set(0, 10, 10);
    camera.lookAt(0, 0, 0);

    //makeLabelCanvas
    function makeLabelCanvas(size, name) {
        const borderSize = 0;
        const ctx = document.createElement('canvas').getContext('2d');
        const font = `${size}px bold sans-serif`;
        ctx.font = font;

        // measure how long the name will be
        const doubleBorderSize = borderSize * 2;
        const width = ctx.measureText(name).width + doubleBorderSize;
        const height = 70 + doubleBorderSize;
        ctx.canvas.width = width;
        ctx.canvas.height = height;
        console.log(ctx);
        ctx.font = font;
        ctx.textBaseline = 'top';

        return ctx.canvas;
    }

    /*--------OrbitControls--------*/
    let controls = new OrbitControls(camera, renderer.domElement);
    controls.target.set(0, 0, 0);
    controls.enablePan = false;
    controls.maxPolarAngle = Math.PI / 2;
    controls.enableDamping = true;

    //Render
    const renderScene = new RenderPass(scene, camera);

    const bloomPass = new UnrealBloomPass(new THREE.Vector2(window.innerWidth, window.innerHeight), 1.5, 0.4, 0.85);
    bloomPass.threshold = params.bloomThreshold;
    bloomPass.strength = params.bloomStrength;
    bloomPass.radius = params.bloomRadius;

    const bloomComposer = new EffectComposer(renderer);
    bloomComposer.renderToScreen = false;
    bloomComposer.addPass(renderScene);
    bloomComposer.addPass(bloomPass);

    const finalPass = new ShaderPass(
        new THREE.ShaderMaterial({
            uniforms: {
                baseTexture: { value: null },
                bloomTexture: { value: bloomComposer.renderTarget2.texture }
            },
            vertexShader: document.getElementById('vertexshader').textContent,
            fragmentShader: document.getElementById('fragmentshader').textContent,
            defines: {}
        }), 'baseTexture'
    );
    finalPass.needsSwap = true;

    const finalComposer = new EffectComposer(renderer);
    finalComposer.addPass(renderScene);
    finalComposer.addPass(finalPass);

    /*--------Stats--------*/
    const stats = Stats();
    stats.showPanel(0);

    /*--------AmbientLight-1--------*/
    scene.add(new THREE.AmbientLight(0xffffff, 1));

    //light1
    const light1 = new THREE.PointLight(0xddffdd, 1);
    light1.position.z = 0;
    light1.position.y = 300;
    light1.position.x = 200;
    scene.add(light1);

    /*--------cube--------*/

    const geometry = new THREE.BoxGeometry(4, 4, 4);
    const material = new THREE.MeshBasicMaterial({ color: 0x000050 });
    const cube = new THREE.Mesh(geometry, material);
    scene.add(cube);

    /*--------label--------*/
    const labelGeometry = new THREE.PlaneBufferGeometry(1, 1);

    const canvas = makeLabelCanvas(100, 'name');
    const texture = new THREE.CanvasTexture(canvas);
    texture.wrapS = THREE.ClampToEdgeWrapping;
    texture.wrapT = THREE.ClampToEdgeWrapping;
    //Material
    const loader = new THREE.TextureLoader();
    const labelMaterial = new THREE.MeshBasicMaterial({
        map: loader.load('../img/moudle-lable/Wood-storage-tank/stokehold.png'),
        side: THREE.DoubleSide,
        transparent: true,
    });
    const label = new THREE.Mesh(labelGeometry, labelMaterial);
    cube.add(label);

    label.position.x = -5;
    label.position.y = 3;
    label.position.z = 0;

    const label_BaseScale_X = 0.05;
    const label_BaseScale_Y = 0.05;

    label.scale.x = canvas.width * label_BaseScale_X;
    label.scale.y = canvas.height * label_BaseScale_Y;

    //window.onresize
    window.onresize = function () {
        camera.aspect = window.innerWidth / window.innerHeight;
        camera.updateProjectionMatrix();
        renderer.setSize(window.innerWidth, window.innerHeight);
    };

    function disposeMaterial(obj) {
        if (obj.material) {
            obj.material.dispose();
        }
    }

    //render
    function render() {
        switch (params.scene) {

            case 'Scene only':
                renderer.render(scene, camera);
                break;

            case 'Scene with Glow':

            default:
                // render scene with bloom
                renderBloom(true);

                // render the entire scene, then render bloom scene on top
                finalComposer.render();
                break;

        }

    }
    function renderBloom(mask) {

        if (mask === true) {
            renderer.setClearColor(0x000000); // all must be black, including background
            scene.traverse(darkenNonBloomed);
            bloomComposer.render();
            renderer.setClearColor(0xffffff); // set the color you want
            scene.traverse(restoreMaterial);
        } else {
            camera.layers.set(BLOOM_SCENE);
            bloomComposer.render();
            camera.layers.set(ENTIRE_SCENE);
        }
    }
    function darkenNonBloomed(obj) {
        if (obj.isMesh && bloomLayer.test(obj.layers) === false) {
            materials[obj.uuid] = obj.material;
            obj.material = darkMaterial;
        }
    }
    function restoreMaterial(obj) {
        if (materials[obj.uuid]) {
            obj.material = materials[obj.uuid];
            delete materials[obj.uuid];
        }
    }
    function animate() {
        controls.update();
        render();
        requestAnimationFrame(animate);
    };
    animate();

    var axes = new THREE.AxisHelper(20);
    scene.add(axes);

</script>

It displays normally, but the PlaneBufferGeometry doesn't always face the camera.

enter image description here Here are examples if needed https://smile881225.github.io/AskQuestions/backup/標籤發光問題.html

0

There are 0 best solutions below