Virtual Background Chromakey

Adds chromakey green screen background removal to Playcanvas

This example demonstates Chromakey green screen rendering options of a video source.

    <div class="flex w-full h-auto my-auto">
      <canvas id="app"></canvas>
  </div>
  <script type="module">
  	 

    const canvas = document.getElementById('app');

    const gfxOptions = {
        deviceTypes: ['webgl2'],
        glslangUrl: '/plugins/playcanvas/js/glslang/glslang.js',
        twgslUrl: '/plugins/playcanvas/js/twgsl/twgsl.js'
    };

    const device = await pc.createGraphicsDevice(canvas, gfxOptions);
    const createOptions = new pc.AppOptions();
    createOptions.graphicsDevice = device;

    createOptions.componentSystems = [
    pc.RenderComponentSystem,
    pc.CameraComponentSystem,
    pc.LightComponentSystem
];
    createOptions.resourceHandlers = [pc.TextureHandler, pc.ContainerHandler, pc.ScriptHandler];

    const app = new pc.AppBase(canvas);
    app.init(createOptions);

    const assets = {
    "playcanvas-virtual-background": new pc.Asset('playcanvas-virtual-background', 'script', { 'url': '../../js/playcanvas-virtual-background-1.70.js' }),
    "tv": new pc.Asset('tv', 'container', { 'url': '/plugins/playcanvas/assets/models/tv.glb' })
};


    const assetListLoader = new pc.AssetListLoader(Object.values(assets), app.assets);
    assetListLoader.load(async() => {
      app.start();

      // Set the canvas to fill the window and automatically change resolution to be the same as the canvas size
      app.setCanvasFillMode(pc.FILLMODE_FILL_WINDOW);
      app.setCanvasResolution(pc.RESOLUTION_AUTO);

      // Ensure canvas is resized when window changes size
      const resize = () => app.resizeCanvas();
      window.addEventListener('resize', resize);
      app.on('destroy', () => {
          window.removeEventListener('resize', resize);
      });

      app.scene.ambientLight = new pc.Color(0.2, 0.2, 0.2);

      // Create an Entity with a camera component
      const camera = new pc.Entity();
      camera.addComponent('camera', {
          clearColor: new pc.Color(0.4, 0.45, 0.5)
      });
      camera.translate(0, 0, 15);

      // Create an Entity with a omni light
      const light = new pc.Entity();
      light.addComponent('light', {
          type: 'omni',
          color: new pc.Color(1, 1, 1),
          range: 30
      });
      light.translate(5, 5, 10);

      app.root.addChild(camera);
      app.root.addChild(light);

        
        const video = document.createElement('video');
        video.id = 'vid';
        video.loop = true;

        // Muted so that we can autoplay
        video.muted = true;
        video.autoplay = true;

        // Inline needed for iOS otherwise it plays at fullscreen
        video.playsInline = true;

        video.crossOrigin = 'anonymous';

        // Make sure that the video is in view on the page otherwise it doesn't
        // load on some browsers, especially mobile
        video.setAttribute(
            'style',
            'display: block; width: 1px; height: 1px; position: absolute; opacity: 0; z-index: -1000; top: 0px; pointer-events: none'
        );

        document.body.append(video);
 

 

      // create an entity to render the tv mesh
const entity = assets.tv.resource.instantiateRenderEntity();
entity.setLocalEulerAngles(90, 0, -90);
app.root.addChild(entity);
const virtual = new pc.Entity();
virtual.addComponent("virtual-background", {
meshInstance: entity.render.meshInstances[1],
source: video,
renderType: 2,
bgImage: "../../textures/virtualbg.jpg"
});
app.root.addChild(virtual);

        video.src = "https://videos.electroteque.org/mediapipe/just%20do%20it.mp4"
 

 


        video.load();
        video.play();
 
      });
  </script>