0

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

jImmy
  • 15
  • 5
  • You can look at the [selective bloom example](https://threejs.org/examples/#webgl_postprocessing_unreal_bloom_selective) to see a demo of how to disable bloom on specific items. – M - Jun 08 '22 at 16:26
  • Ya , I know that example, I made it with reference to this example, and the strange thing is that after using PlaneGeometry to paste the picture, Lable magically doesn't have Bloom, but unfortunately, this is not the effect I want, you Can you give me some ideas? I'll reduce this example a bit more and attach the code and results using PlaneGeometry . – jImmy Jun 08 '22 at 23:31
  • I simplified it a bit and updated example. – jImmy Jun 08 '22 at 23:52

0 Answers0