webgl_materials_skin.html 7.8 KB
Newer Older
M
Mr.doob 已提交
1
<!DOCTYPE html>
2 3 4 5
<html lang="en">
	<head>
		<title>three.js webgl - materials - skin [Lee Perry-Smith]</title>
		<meta charset="utf-8">
6
		<meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
M
Mr.doob 已提交
7
		<link type="text/css" rel="stylesheet" href="main.css">
8 9 10 11
	</head>
	<body>

		<div id="info">
M
Mr.doob 已提交
12
			<a href="http://threejs.org" target="_blank" rel="noopener">three.js</a> - webgl skin rendering demo.<br/>
13
			<a href="http://graphics.cs.williams.edu/data/meshes.xml#14" target="_blank" rel="noopener">Lee Perry-Smith</a> head.
14 15
		</div>

M
Mugen87 已提交
16
		<script type="module">
M
Mr.doob 已提交
17
			import * as THREE from '../build/three.module.js';
M
Mugen87 已提交
18 19 20 21 22 23 24 25 26 27 28

			import Stats from './jsm/libs/stats.module.js';

			import { GLTFLoader } from './jsm/loaders/GLTFLoader.js';
			import { EffectComposer } from './jsm/postprocessing/EffectComposer.js';
			import { RenderPass } from './jsm/postprocessing/RenderPass.js';
			import { ShaderPass } from './jsm/postprocessing/ShaderPass.js';
			import { BloomPass } from './jsm/postprocessing/BloomPass.js';
			import { TexturePass } from './jsm/postprocessing/TexturePass.js';

			import { SkinShaderAdvanced, SkinShaderBeckmann } from './jsm/shaders/SkinShader.js';
29

30
			var statsEnabled = true;
31 32 33 34 35 36 37

			var container, stats, loader;

			var camera, scene, renderer;

			var mesh;

38
			var composer, composerUV1, composerUV2, composerUV3, composerBeckmann;
39

L
Lewy Blue 已提交
40
			var directionalLight;
41 42 43 44 45 46 47

			var mouseX = 0, mouseY = 0;
			var targetX = 0, targetY = 0;

			var windowHalfX = window.innerWidth / 2;
			var windowHalfY = window.innerHeight / 2;

48 49
			var firstPass = true;

50 51 52 53 54 55 56 57
			init();
			animate();

			function init() {

				container = document.createElement( 'div' );
				document.body.appendChild( container );

M
Mr.doob 已提交
58
				camera = new THREE.PerspectiveCamera( 35, window.innerWidth / window.innerHeight, 1, 10000 );
59
				camera.position.z = 900;
60

M
Mr.doob 已提交
61 62
				scene = new THREE.Scene();
				scene.background = new THREE.Color( 0x050505 );
63 64 65

				// LIGHTS

M
Mr.doob 已提交
66
				directionalLight = new THREE.DirectionalLight( 0xffeedd, 1.5 );
M
Mr.doob 已提交
67
				directionalLight.position.set( 1, 0.5, 1 );
68
				scene.add( directionalLight );
69

M
Mr.doob 已提交
70
				directionalLight = new THREE.DirectionalLight( 0xddddff, 0.5 );
L
Lewy Blue 已提交
71
				directionalLight.position.set( - 1, 0.5, - 1 );
72 73 74 75
				scene.add( directionalLight );

				// MATERIALS

L
Lewy Blue 已提交
76
				var diffuse = 0xbbbbbb, specular = 0x555555;
77

M
Mugen87 已提交
78
				var shader = SkinShaderAdvanced;
79

M
Mr.doob 已提交
80
				var uniformsUV = THREE.UniformsUtils.clone( shader.uniforms );
81

M
Mr.doob 已提交
82
				var textureLoader = new THREE.TextureLoader();
83

84
				uniformsUV[ "tNormal" ].value = textureLoader.load( "models/gltf/LeePerrySmith/Infinite-Level_02_Tangent_SmoothUV.jpg" );
L
Lewy Blue 已提交
85
				uniformsUV[ "uNormalScale" ].value = - 1.5;
86

87
				uniformsUV[ "tDiffuse" ].value = textureLoader.load( "models/gltf/LeePerrySmith/Map-COL.jpg" );
88 89 90

				uniformsUV[ "passID" ].value = 0;

B
Ben Houston 已提交
91 92
				uniformsUV[ "diffuse" ].value.setHex( diffuse );
				uniformsUV[ "specular" ].value.setHex( specular );
93

94
				uniformsUV[ "uRoughness" ].value = 0.185;
95
				uniformsUV[ "uSpecularBrightness" ].value = 0.7;
96

97

M
Mr.doob 已提交
98
				var uniforms = THREE.UniformsUtils.clone( uniformsUV );
99 100 101 102
				uniforms[ "tDiffuse" ].value = uniformsUV[ "tDiffuse" ].value;
				uniforms[ "tNormal" ].value = uniformsUV[ "tNormal" ].value;
				uniforms[ "passID" ].value = 1;

103

104 105
				var parameters = { fragmentShader: shader.fragmentShader, vertexShader: shader.vertexShader, uniforms: uniforms, lights: true };
				var parametersUV = { fragmentShader: shader.fragmentShader, vertexShader: shader.vertexShaderUV, uniforms: uniformsUV, lights: true };
106

M
Mr.doob 已提交
107
				var material = new THREE.ShaderMaterial( parameters );
108 109
				material.extensions.derivatives = true;

M
Mr.doob 已提交
110
				var materialUV = new THREE.ShaderMaterial( parametersUV );
111
				materialUV.extensions.derivatives = true;
112 113 114

				// LOADER

M
Mugen87 已提交
115
				loader = new GLTFLoader();
L
Lewy Blue 已提交
116
				loader.load( "models/gltf/LeePerrySmith/LeePerrySmith.glb", function ( gltf ) {
M
Mr.doob 已提交
117

118
					createScene( gltf.scene.children[ 0 ].geometry, 100, material );
M
Mr.doob 已提交
119 120

				} );
121 122 123

				// RENDERER

M
Mr.doob 已提交
124
				renderer = new THREE.WebGLRenderer();
125
				renderer.setPixelRatio( window.devicePixelRatio );
T
tschw 已提交
126
				renderer.setSize( window.innerWidth, window.innerHeight );
127 128 129 130 131 132 133 134 135
				renderer.autoClear = false;

				container.appendChild( renderer.domElement );

				// STATS

				if ( statsEnabled ) {

					stats = new Stats();
M
Mr.doob 已提交
136
					container.appendChild( stats.dom );
137 138 139 140 141 142 143 144 145

				}

				// EVENTS

				document.addEventListener( 'mousemove', onDocumentMouseMove, false );

				// POSTPROCESSING

M
Mr.doob 已提交
146
				var renderModelUV = new RenderPass( scene, camera, materialUV, new THREE.Color( 0x575757 ) );
147

M
Mugen87 已提交
148 149 150
				var effectBloom1 = new BloomPass( 1, 15, 2, 512 );
				var effectBloom2 = new BloomPass( 1, 25, 3, 512 );
				var effectBloom3 = new BloomPass( 1, 25, 4, 512 );
151 152 153 154 155 156 157

				effectBloom1.clear = true;
				effectBloom2.clear = true;
				effectBloom3.clear = true;

				//

M
Mr.doob 已提交
158
				var pars = {
159
					generateMipmaps: true,
M
Mr.doob 已提交
160 161 162
					minFilter: THREE.LinearMipMapLinearFilter,
					magFilter: THREE.LinearFilter,
					format: THREE.RGBFormat,
M
Mr.doob 已提交
163 164 165
					stencilBuffer: false
				};

166 167 168 169 170
				var rtwidth = 512;
				var rtheight = 512;

				//

M
Mr.doob 已提交
171
				composer = new EffectComposer( renderer, new THREE.WebGLRenderTarget( rtwidth, rtheight, pars ) );
M
Mr.doob 已提交
172
				composer.addPass( renderModelUV );
173
				composer.renderToScreen = false;
174

M
Mugen87 已提交
175
				var renderScene = new TexturePass( composer.renderTarget2.texture );
176 177 178

				//

M
Mr.doob 已提交
179
				composerUV1 = new EffectComposer( renderer, new THREE.WebGLRenderTarget( rtwidth, rtheight, pars ) );
180 181 182

				composerUV1.addPass( renderScene );
				composerUV1.addPass( effectBloom1 );
183
				composerUV1.renderToScreen = false;
184

M
Mr.doob 已提交
185
				composerUV2 = new EffectComposer( renderer, new THREE.WebGLRenderTarget( rtwidth, rtheight, pars ) );
186 187 188

				composerUV2.addPass( renderScene );
				composerUV2.addPass( effectBloom2 );
189
				composerUV2.renderToScreen = false;
190

M
Mr.doob 已提交
191
				composerUV3 = new EffectComposer( renderer, new THREE.WebGLRenderTarget( rtwidth, rtheight, pars ) );
192 193 194

				composerUV3.addPass( renderScene );
				composerUV3.addPass( effectBloom3 );
195
				composerUV3.renderToScreen = false;
196 197 198

				//

M
Mugen87 已提交
199
				var effectBeckmann = new ShaderPass( SkinShaderBeckmann );
M
Mr.doob 已提交
200
				composerBeckmann = new EffectComposer( renderer, new THREE.WebGLRenderTarget( rtwidth, rtheight, pars ) );
201 202 203 204
				composerBeckmann.addPass( effectBeckmann );

				//

M
Mr.doob 已提交
205
				uniforms[ "tBlur1" ].value = composer.renderTarget2.texture;
206 207 208
				uniforms[ "tBlur2" ].value = composerUV1.renderTarget2.texture;
				uniforms[ "tBlur3" ].value = composerUV2.renderTarget2.texture;
				uniforms[ "tBlur4" ].value = composerUV3.renderTarget2.texture;
209

210
				uniforms[ "tBeckmann" ].value = composerBeckmann.renderTarget1.texture;
211

A
alteredq 已提交
212 213 214 215 216 217 218 219 220 221 222 223 224 225 226
				//

				window.addEventListener( 'resize', onWindowResize, false );

			}

			function onWindowResize() {

				windowHalfX = window.innerWidth / 2;
				windowHalfY = window.innerHeight / 2;

				camera.aspect = window.innerWidth / window.innerHeight;
				camera.updateProjectionMatrix();

				renderer.setSize( window.innerWidth, window.innerHeight );
227 228 229 230 231

			}

			function createScene( geometry, scale, material ) {

M
Mr.doob 已提交
232
				mesh = new THREE.Mesh( geometry, material );
233 234 235 236 237 238 239
				mesh.position.y = - 50;
				mesh.scale.set( scale, scale, scale );

				scene.add( mesh );

			}

240
			function onDocumentMouseMove( event ) {
241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271

				mouseX = ( event.clientX - windowHalfX );
				mouseY = ( event.clientY - windowHalfY );

			}

			//

			function animate() {

				requestAnimationFrame( animate );

				render();
				if ( statsEnabled ) stats.update();

			}

			function render() {

				targetX = mouseX * .001;
				targetY = mouseY * .001;

				if ( mesh ) {

					mesh.rotation.y += 0.05 * ( targetX - mesh.rotation.y );
					mesh.rotation.x += 0.05 * ( targetY - mesh.rotation.x );

				}

				renderer.clear();

272 273 274 275 276 277
				if ( firstPass ) {

					composerBeckmann.render();
					firstPass = false;

				}
278

M
Mr.doob 已提交
279
				composer.render();
280 281 282 283 284 285 286 287 288 289 290 291 292

				composerUV1.render();
				composerUV2.render();
				composerUV3.render();

				renderer.render( scene, camera );

			}

		</script>

	</body>
</html>