|
@@ -9,8 +9,7 @@ THREE.LensFlarePlugin = function ( renderer, flares ) {
|
|
|
var state = renderer.state;
|
|
|
|
|
|
var vertexBuffer, elementBuffer;
|
|
|
- var program, attributes, uniforms;
|
|
|
- var hasVertexTexture;
|
|
|
+ var shader, program, attributes, uniforms;
|
|
|
|
|
|
var tempTexture, occlusionTexture;
|
|
|
|
|
@@ -58,193 +57,99 @@ THREE.LensFlarePlugin = function ( renderer, flares ) {
|
|
|
gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST );
|
|
|
gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST );
|
|
|
|
|
|
- hasVertexTexture = gl.getParameter( gl.MAX_VERTEX_TEXTURE_IMAGE_UNITS ) > 0;
|
|
|
+ shader = {
|
|
|
|
|
|
- var shader;
|
|
|
+ vertexShader: [
|
|
|
|
|
|
- if ( hasVertexTexture ) {
|
|
|
+ "uniform lowp int renderType;",
|
|
|
|
|
|
- shader = {
|
|
|
+ "uniform vec3 screenPosition;",
|
|
|
+ "uniform vec2 scale;",
|
|
|
+ "uniform float rotation;",
|
|
|
|
|
|
- vertexShader: [
|
|
|
+ "uniform sampler2D occlusionMap;",
|
|
|
|
|
|
- "uniform lowp int renderType;",
|
|
|
+ "attribute vec2 position;",
|
|
|
+ "attribute vec2 uv;",
|
|
|
|
|
|
- "uniform vec3 screenPosition;",
|
|
|
- "uniform vec2 scale;",
|
|
|
- "uniform float rotation;",
|
|
|
+ "varying vec2 vUV;",
|
|
|
+ "varying float vVisibility;",
|
|
|
|
|
|
- "uniform sampler2D occlusionMap;",
|
|
|
+ "void main() {",
|
|
|
|
|
|
- "attribute vec2 position;",
|
|
|
- "attribute vec2 uv;",
|
|
|
+ "vUV = uv;",
|
|
|
|
|
|
- "varying vec2 vUV;",
|
|
|
- "varying float vVisibility;",
|
|
|
+ "vec2 pos = position;",
|
|
|
|
|
|
- "void main() {",
|
|
|
+ "if ( renderType == 2 ) {",
|
|
|
|
|
|
- "vUV = uv;",
|
|
|
+ "vec4 visibility = texture2D( occlusionMap, vec2( 0.1, 0.1 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.5, 0.1 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.9, 0.1 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.9, 0.5 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.9, 0.9 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.5, 0.9 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.1, 0.9 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.1, 0.5 ) );",
|
|
|
+ "visibility += texture2D( occlusionMap, vec2( 0.5, 0.5 ) );",
|
|
|
|
|
|
- "vec2 pos = position;",
|
|
|
+ "vVisibility = visibility.r / 9.0;",
|
|
|
+ "vVisibility *= 1.0 - visibility.g / 9.0;",
|
|
|
+ "vVisibility *= visibility.b / 9.0;",
|
|
|
+ "vVisibility *= 1.0 - visibility.a / 9.0;",
|
|
|
|
|
|
- "if ( renderType == 2 ) {",
|
|
|
+ "pos.x = cos( rotation ) * position.x - sin( rotation ) * position.y;",
|
|
|
+ "pos.y = sin( rotation ) * position.x + cos( rotation ) * position.y;",
|
|
|
|
|
|
- "vec4 visibility = texture2D( occlusionMap, vec2( 0.1, 0.1 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.5, 0.1 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.9, 0.1 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.9, 0.5 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.9, 0.9 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.5, 0.9 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.1, 0.9 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.1, 0.5 ) );",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.5, 0.5 ) );",
|
|
|
+ "}",
|
|
|
|
|
|
- "vVisibility = visibility.r / 9.0;",
|
|
|
- "vVisibility *= 1.0 - visibility.g / 9.0;",
|
|
|
- "vVisibility *= visibility.b / 9.0;",
|
|
|
- "vVisibility *= 1.0 - visibility.a / 9.0;",
|
|
|
+ "gl_Position = vec4( ( pos * scale + screenPosition.xy ).xy, screenPosition.z, 1.0 );",
|
|
|
|
|
|
- "pos.x = cos( rotation ) * position.x - sin( rotation ) * position.y;",
|
|
|
- "pos.y = sin( rotation ) * position.x + cos( rotation ) * position.y;",
|
|
|
+ "}"
|
|
|
|
|
|
- "}",
|
|
|
+ ].join( "\n" ),
|
|
|
|
|
|
- "gl_Position = vec4( ( pos * scale + screenPosition.xy ).xy, screenPosition.z, 1.0 );",
|
|
|
+ fragmentShader: [
|
|
|
|
|
|
- "}"
|
|
|
+ "uniform lowp int renderType;",
|
|
|
|
|
|
- ].join( "\n" ),
|
|
|
+ "uniform sampler2D map;",
|
|
|
+ "uniform float opacity;",
|
|
|
+ "uniform vec3 color;",
|
|
|
|
|
|
- fragmentShader: [
|
|
|
+ "varying vec2 vUV;",
|
|
|
+ "varying float vVisibility;",
|
|
|
|
|
|
- "uniform lowp int renderType;",
|
|
|
+ "void main() {",
|
|
|
|
|
|
- "uniform sampler2D map;",
|
|
|
- "uniform float opacity;",
|
|
|
- "uniform vec3 color;",
|
|
|
+ // pink square
|
|
|
|
|
|
- "varying vec2 vUV;",
|
|
|
- "varying float vVisibility;",
|
|
|
+ "if ( renderType == 0 ) {",
|
|
|
|
|
|
- "void main() {",
|
|
|
+ "gl_FragColor = vec4( 1.0, 0.0, 1.0, 0.0 );",
|
|
|
|
|
|
- // pink square
|
|
|
+ // restore
|
|
|
|
|
|
- "if ( renderType == 0 ) {",
|
|
|
+ "} else if ( renderType == 1 ) {",
|
|
|
|
|
|
- "gl_FragColor = vec4( 1.0, 0.0, 1.0, 0.0 );",
|
|
|
+ "gl_FragColor = texture2D( map, vUV );",
|
|
|
|
|
|
- // restore
|
|
|
+ // flare
|
|
|
|
|
|
- "} else if ( renderType == 1 ) {",
|
|
|
+ "} else {",
|
|
|
|
|
|
- "gl_FragColor = texture2D( map, vUV );",
|
|
|
+ "vec4 texture = texture2D( map, vUV );",
|
|
|
+ "texture.a *= opacity * vVisibility;",
|
|
|
+ "gl_FragColor = texture;",
|
|
|
+ "gl_FragColor.rgb *= color;",
|
|
|
|
|
|
- // flare
|
|
|
+ "}",
|
|
|
|
|
|
- "} else {",
|
|
|
+ "}"
|
|
|
|
|
|
- "vec4 texture = texture2D( map, vUV );",
|
|
|
- "texture.a *= opacity * vVisibility;",
|
|
|
- "gl_FragColor = texture;",
|
|
|
- "gl_FragColor.rgb *= color;",
|
|
|
+ ].join( "\n" )
|
|
|
|
|
|
- "}",
|
|
|
-
|
|
|
- "}"
|
|
|
-
|
|
|
- ].join( "\n" )
|
|
|
-
|
|
|
- };
|
|
|
-
|
|
|
- } else {
|
|
|
-
|
|
|
- shader = {
|
|
|
-
|
|
|
- vertexShader: [
|
|
|
-
|
|
|
- "uniform lowp int renderType;",
|
|
|
-
|
|
|
- "uniform vec3 screenPosition;",
|
|
|
- "uniform vec2 scale;",
|
|
|
- "uniform float rotation;",
|
|
|
-
|
|
|
- "attribute vec2 position;",
|
|
|
- "attribute vec2 uv;",
|
|
|
-
|
|
|
- "varying vec2 vUV;",
|
|
|
-
|
|
|
- "void main() {",
|
|
|
-
|
|
|
- "vUV = uv;",
|
|
|
-
|
|
|
- "vec2 pos = position;",
|
|
|
-
|
|
|
- "if ( renderType == 2 ) {",
|
|
|
-
|
|
|
- "pos.x = cos( rotation ) * position.x - sin( rotation ) * position.y;",
|
|
|
- "pos.y = sin( rotation ) * position.x + cos( rotation ) * position.y;",
|
|
|
-
|
|
|
- "}",
|
|
|
-
|
|
|
- "gl_Position = vec4( ( pos * scale + screenPosition.xy ).xy, screenPosition.z, 1.0 );",
|
|
|
-
|
|
|
- "}"
|
|
|
-
|
|
|
- ].join( "\n" ),
|
|
|
-
|
|
|
- fragmentShader: [
|
|
|
-
|
|
|
- "precision mediump float;",
|
|
|
-
|
|
|
- "uniform lowp int renderType;",
|
|
|
-
|
|
|
- "uniform sampler2D map;",
|
|
|
- "uniform sampler2D occlusionMap;",
|
|
|
- "uniform float opacity;",
|
|
|
- "uniform vec3 color;",
|
|
|
-
|
|
|
- "varying vec2 vUV;",
|
|
|
-
|
|
|
- "void main() {",
|
|
|
-
|
|
|
- // pink square
|
|
|
-
|
|
|
- "if ( renderType == 0 ) {",
|
|
|
-
|
|
|
- "gl_FragColor = vec4( texture2D( map, vUV ).rgb, 0.0 );",
|
|
|
-
|
|
|
- // restore
|
|
|
-
|
|
|
- "} else if ( renderType == 1 ) {",
|
|
|
-
|
|
|
- "gl_FragColor = texture2D( map, vUV );",
|
|
|
-
|
|
|
- // flare
|
|
|
-
|
|
|
- "} else {",
|
|
|
-
|
|
|
- "float visibility = texture2D( occlusionMap, vec2( 0.5, 0.1 ) ).a;",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.9, 0.5 ) ).a;",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.5, 0.9 ) ).a;",
|
|
|
- "visibility += texture2D( occlusionMap, vec2( 0.1, 0.5 ) ).a;",
|
|
|
- "visibility = ( 1.0 - visibility / 4.0 );",
|
|
|
-
|
|
|
- "vec4 texture = texture2D( map, vUV );",
|
|
|
- "texture.a *= opacity * visibility;",
|
|
|
- "gl_FragColor = texture;",
|
|
|
- "gl_FragColor.rgb *= color;",
|
|
|
-
|
|
|
- "}",
|
|
|
-
|
|
|
- "}"
|
|
|
-
|
|
|
- ].join( "\n" )
|
|
|
-
|
|
|
- };
|
|
|
-
|
|
|
- }
|
|
|
+ };
|
|
|
|
|
|
program = createProgram( shader );
|
|
|
|
|
@@ -288,7 +193,10 @@ THREE.LensFlarePlugin = function ( renderer, flares ) {
|
|
|
var screenPosition = new THREE.Vector3( 1, 1, 0 ),
|
|
|
screenPositionPixels = new THREE.Vector2( 1, 1 );
|
|
|
|
|
|
- var areaToCopy = new THREE.Vector2();
|
|
|
+ var validArea = new THREE.Box2();
|
|
|
+
|
|
|
+ validArea.min.set( 0, 0 );
|
|
|
+ validArea.max.set( viewport.z - 16, viewport.w - 16 );
|
|
|
|
|
|
if ( program === undefined ) {
|
|
|
|
|
@@ -336,18 +244,14 @@ THREE.LensFlarePlugin = function ( renderer, flares ) {
|
|
|
|
|
|
screenPosition.copy( tempPosition );
|
|
|
|
|
|
- screenPositionPixels.x = screenPosition.x * halfViewportWidth + halfViewportWidth;
|
|
|
- screenPositionPixels.y = screenPosition.y * halfViewportHeight + halfViewportHeight;
|
|
|
+ // horizontal and vertical coordinate of the lower left corner of the pixels to copy
|
|
|
|
|
|
- areaToCopy.x = viewport.x + screenPositionPixels.x - 8; // horizontal coordinate of the lower left corner of the pixels to copy
|
|
|
- areaToCopy.y = viewport.y + screenPositionPixels.y - 8; // vertical coordinate of the lower left corner of the pixels to copy
|
|
|
+ screenPositionPixels.x = viewport.x + ( screenPosition.x * halfViewportWidth ) + halfViewportWidth - 8;
|
|
|
+ screenPositionPixels.y = viewport.y + ( screenPosition.y * halfViewportHeight ) + halfViewportHeight - 8;
|
|
|
|
|
|
// screen cull
|
|
|
|
|
|
- if ( areaToCopy.x > 0 &&
|
|
|
- areaToCopy.x < ( viewport.z - 16 ) &&
|
|
|
- areaToCopy.y > 0 &&
|
|
|
- areaToCopy.y < ( viewport.w - 16 ) ) {
|
|
|
+ if ( validArea.containsPoint( screenPositionPixels ) === true ) {
|
|
|
|
|
|
// save current RGB to temp texture
|
|
|
|
|
@@ -355,7 +259,7 @@ THREE.LensFlarePlugin = function ( renderer, flares ) {
|
|
|
state.bindTexture( gl.TEXTURE_2D, null );
|
|
|
state.activeTexture( gl.TEXTURE1 );
|
|
|
state.bindTexture( gl.TEXTURE_2D, tempTexture );
|
|
|
- gl.copyTexImage2D( gl.TEXTURE_2D, 0, gl.RGB, areaToCopy.x, areaToCopy.y, 16, 16, 0 );
|
|
|
+ gl.copyTexImage2D( gl.TEXTURE_2D, 0, gl.RGB, screenPositionPixels.x, screenPositionPixels.y, 16, 16, 0 );
|
|
|
|
|
|
|
|
|
// render pink quad
|
|
@@ -374,7 +278,7 @@ THREE.LensFlarePlugin = function ( renderer, flares ) {
|
|
|
|
|
|
state.activeTexture( gl.TEXTURE0 );
|
|
|
state.bindTexture( gl.TEXTURE_2D, occlusionTexture );
|
|
|
- gl.copyTexImage2D( gl.TEXTURE_2D, 0, gl.RGBA, areaToCopy.x, areaToCopy.y, 16, 16, 0 );
|
|
|
+ gl.copyTexImage2D( gl.TEXTURE_2D, 0, gl.RGBA, screenPositionPixels.x, screenPositionPixels.y, 16, 16, 0 );
|
|
|
|
|
|
|
|
|
// restore graphics
|