expo / expo-three

Utilities for using THREE.js on Expo
MIT License
750 stars 92 forks source link

Post-processing #146

Open FunkSoulNinja opened 5 years ago

FunkSoulNinja commented 5 years ago

Is there currently no way to enable post-processing? The code below works on web and also works on native, but with the post-processing effects stripped/ignored.

import React from 'react'
import { GLView, ExpoWebGLRenderingContext } from 'expo-gl'
import { Renderer } from 'expo-three'
import {
  AmbientLight,
  BoxBufferGeometry,
  Fog,
  GridHelper,
  Mesh,
  MeshLambertMaterial,
  PerspectiveCamera,
  PointLight,
  Scene,
  SpotLight,
  Vector2,
  Color
} from 'three'

import { RenderPass } from 'three/examples/jsm/postprocessing/RenderPass'
import { EffectComposer } from 'three/examples/jsm/postprocessing/EffectComposer'
import { OutlinePass } from 'three/examples/jsm/postprocessing/OutlinePass'

const Test = () => {
  let timeout

  React.useEffect(() => {
    // Clear the animation loop when the component unmounts
    return () => clearTimeout(timeout)
  }, [])
  return (
    <GLView
      style={{ flex: 1 }}
      onContextCreate={async (gl: ExpoWebGLRenderingContext) => {
        const { drawingBufferWidth: width, drawingBufferHeight: height } = gl
        const sceneColor = 0x6ad6f0

        // Create a WebGLRenderer without a DOM element
        const renderer = new Renderer({ gl })
        renderer.setSize(width, height)
        renderer.setClearColor(sceneColor)

        const camera = new PerspectiveCamera(70, width / height, 0.01, 1000)
        camera.position.set(2, 5, 5)

        const scene = new Scene()
        scene.fog = new Fog(sceneColor, 1, 10000)
        scene.add(new GridHelper(10, 10))

        const composer = new EffectComposer(renderer)

        const renderPass = new RenderPass(scene, camera)
        composer.addPass(renderPass)

        const outlinePass = new OutlinePass(new Vector2(width, height), scene, camera)
        composer.addPass(outlinePass)

        outlinePass.edgeStrength = 5
        outlinePass.edgeThickness = 1
        outlinePass.edgeGlow = 1
        outlinePass.pulsePeriod = 4
        outlinePass.visibleEdgeColor = new Color('#ffffff')
        outlinePass.hiddenEdgeColor = new Color('#919191')

        const ambientLight = new AmbientLight(0x101010)
        scene.add(ambientLight)

        const pointLight = new PointLight(0xffffff, 2, 1000, 1)
        pointLight.position.set(0, 200, 200)
        scene.add(pointLight)

        const spotLight = new SpotLight(0xffffff, 0.5)
        spotLight.position.set(0, 500, 100)
        spotLight.lookAt(scene.position)
        scene.add(spotLight)

        const cube = new IconMesh()
        scene.add(cube)
        outlinePass.selectedObjects = [cube]

        camera.lookAt(cube.position)

        function update() {
          cube.rotation.y += 0.05
          cube.rotation.x += 0.025
        }

        // Setup an animation loop
        const render = () => {
          timeout = requestAnimationFrame(render)
          update()
          composer.render()
          gl.endFrameEXP()
        }
        render()
      }}
    />
  )
}

class IconMesh extends Mesh {
  constructor() {
    super(
      new BoxBufferGeometry(1.0, 1.0, 1.0),
      new MeshLambertMaterial({ color: 'blue' })
    )
  }
}

export default Test
timnlupo commented 4 years ago

Did you figure this out?

FunkSoulNinja commented 4 years ago

@timnlupo I wasn't able to figure it out. I decided to just not use post-processing at all because of the lack of support or documentation.

react-three-fiber looks like a promising project, but I haven't tried it and can't switch over now because I have most of my app built.

AmitBRD commented 4 years ago

Has anyone a working example for UnrealBloomPass and post processing or any working example? I can port over postprocessing effects once the problem is identified