webgl_materials_nodes.html 37 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659
  1. <!doctype html>
  2. <html lang="en">
  3. <head>
  4. <title>WebGL NodeMaterial</title>
  5. <meta charset="utf-8">
  6. <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
  7. <style>
  8. body {
  9. color: #fff;
  10. font-family:Monospace;
  11. font-size:13px;
  12. margin: 0px;
  13. text-align:center;
  14. overflow: hidden;
  15. }
  16. #info {
  17. color: #fff;
  18. position: absolute;
  19. top: 10px;
  20. width: 100%;
  21. text-align: center;
  22. display:block;
  23. }
  24. a { color: white }
  25. </style>
  26. </head>
  27. <body>
  28. <div id="container"></div>
  29. <div id="info">
  30. <a href="http://threejs.org" target="_blank">three.js</a> - Node-Based Material
  31. </div>
  32. <script src="../build/three.min.js"></script>
  33. <script src='js/geometries/TeapotBufferGeometry.js'></script>
  34. <script src="js/controls/OrbitControls.js"></script>
  35. <script src="js/libs/dat.gui.min.js"></script>
  36. <!-- NodeLibrary -->
  37. <script src="js/nodes/GLNode.js"></script>
  38. <script src="js/nodes/RawNode.js"></script>
  39. <script src="js/nodes/TempNode.js"></script>
  40. <script src="js/nodes/InputNode.js"></script>
  41. <script src="js/nodes/ConstNode.js"></script>
  42. <script src="js/nodes/FunctionNode.js"></script>
  43. <script src="js/nodes/FunctionCallNode.js"></script>
  44. <script src="js/nodes/BuilderNode.js"></script>
  45. <script src="js/nodes/NodeLib.js"></script>
  46. <script src="js/nodes/NodeMaterial.js"></script>
  47. <!-- Accessors -->
  48. <script src="js/nodes/accessors/PositionNode.js"></script>
  49. <script src="js/nodes/accessors/NormalNode.js"></script>
  50. <script src="js/nodes/accessors/UVNode.js"></script>
  51. <script src="js/nodes/accessors/ColorsNode.js"></script>
  52. <script src="js/nodes/accessors/CameraNode.js"></script>
  53. <script src="js/nodes/accessors/ReflectNode.js"></script>
  54. <script src="js/nodes/accessors/LightNode.js"></script>
  55. <!-- Inputs -->
  56. <script src="js/nodes/inputs/IntNode.js"></script>
  57. <script src="js/nodes/inputs/FloatNode.js"></script>
  58. <script src="js/nodes/inputs/ColorNode.js"></script>
  59. <script src="js/nodes/inputs/Vector2Node.js"></script>
  60. <script src="js/nodes/inputs/Vector3Node.js"></script>
  61. <script src="js/nodes/inputs/Vector4Node.js"></script>
  62. <script src="js/nodes/inputs/TextureNode.js"></script>
  63. <script src="js/nodes/inputs/CubeTextureNode.js"></script>
  64. <!-- Math -->
  65. <script src="js/nodes/math/Math1Node.js"></script>
  66. <script src="js/nodes/math/Math2Node.js"></script>
  67. <script src="js/nodes/math/Math3Node.js"></script>
  68. <script src="js/nodes/math/OperatorNode.js"></script>
  69. <!-- Utils -->
  70. <script src="js/nodes/utils/SwitchNode.js"></script>
  71. <script src="js/nodes/utils/JoinNode.js"></script>
  72. <script src="js/nodes/utils/TimerNode.js"></script>
  73. <script src="js/nodes/utils/RoughnessToBlinnExponentNode.js"></script>
  74. <script src="js/nodes/utils/VelocityNode.js"></script>
  75. <script src="js/nodes/utils/LuminanceNode.js"></script>
  76. <script src="js/nodes/utils/ColorAdjustmentNode.js"></script>
  77. <script src="js/nodes/utils/NoiseNode.js"></script>
  78. <!-- Phong Material -->
  79. <script src="js/nodes/materials/PhongNode.js"></script>
  80. <script src="js/nodes/materials/PhongNodeMaterial.js"></script>
  81. <!-- Standard Material -->
  82. <script src="js/nodes/materials/StandardNode.js"></script>
  83. <script src="js/nodes/materials/StandardNodeMaterial.js"></script>
  84. <script>
  85. var container = document.getElementById( 'container' );
  86. var renderer, scene, camera, clock = new THREE.Clock(), fov = 50;
  87. var teapot, mesh;
  88. var controls;
  89. var move = false;
  90. var gui, guiElements = [];
  91. var param = { example: 'standard' };
  92. var brick = new THREE.TextureLoader().load( 'textures/brick_diffuse.jpg' );
  93. var grass = new THREE.TextureLoader().load( 'textures/terrain/grasslight-big.jpg' );
  94. var grassNormal = new THREE.TextureLoader().load( 'textures/terrain/grasslight-big-nm.jpg' );
  95. var decalDiffuse = new THREE.TextureLoader().load( 'textures/decal/decal-diffuse.png' );
  96. decalDiffuse.wrapS = decalDiffuse.wrapT = THREE.RepeatWrapping;
  97. var cloud = new THREE.TextureLoader().load( 'textures/lava/cloud.png' );
  98. cloud.wrapS = cloud.wrapT = THREE.RepeatWrapping;
  99. var cubemap = function() {
  100. var path = "textures/cube/Park2/";
  101. var format = '.jpg';
  102. var urls = [
  103. path + 'posx' + format, path + 'negx' + format,
  104. path + 'posy' + format, path + 'negy' + format,
  105. path + 'posz' + format, path + 'negz' + format
  106. ];
  107. var textureCube = new THREE.CubeTextureLoader().load( urls );
  108. textureCube.format = THREE.RGBFormat;
  109. return textureCube;
  110. }();
  111. window.addEventListener( 'load', init );
  112. function init() {
  113. renderer = new THREE.WebGLRenderer( { antialias: true } );
  114. renderer.setPixelRatio( window.devicePixelRatio );
  115. renderer.setSize( window.innerWidth, window.innerHeight );
  116. container.appendChild( renderer.domElement );
  117. scene = new THREE.Scene();
  118. camera = new THREE.PerspectiveCamera( fov, window.innerWidth / window.innerHeight, 1, 1000 );
  119. camera.position.x = 50;
  120. camera.position.z = - 50;
  121. camera.position.y = 30;
  122. camera.target = new THREE.Vector3();
  123. controls = new THREE.OrbitControls( camera, renderer.domElement );
  124. controls.minDistance = 50;
  125. controls.maxDistance = 200;
  126. scene.add( new THREE.AmbientLight( 0x464646 ) );
  127. var light = new THREE.DirectionalLight( 0xffddcc, 1 );
  128. light.position.set( 1, 0.75, 0.5 );
  129. scene.add( light );
  130. var light = new THREE.DirectionalLight( 0xccccff, 1 );
  131. light.position.set( - 1, 0.75, - 0.5 );
  132. scene.add( light );
  133. teapot = new THREE.TeapotBufferGeometry( 15, 18 );
  134. mesh = new THREE.Mesh( teapot );
  135. scene.add( mesh );
  136. window.addEventListener( 'resize', onWindowResize, false );
  137. updateMaterial();
  138. onWindowResize();
  139. animate();
  140. }
  141. function clearGui() {
  142. if ( gui ) gui.destroy();
  143. gui = new dat.GUI();
  144. var example = gui.add( param, 'example', {
  145. 'basic / standard (PBR)': 'standard',
  146. 'basic / phong': 'phong',
  147. 'basic / layers': 'layers',
  148. 'basic / rim': 'rim',
  149. 'basic / color-adjustment': 'color-adjustment',
  150. 'adv / fresnel': 'fresnel',
  151. 'adv / saturation': 'saturation',
  152. 'adv / top-bottom': 'top-bottom',
  153. 'adv / skin': 'skin',
  154. 'adv / skin-phong': 'skin-phong',
  155. 'adv / caustic': 'caustic',
  156. 'adv / displace': 'displace',
  157. 'adv / plush': 'plush',
  158. 'adv / toon': 'toon',
  159. 'adv / camera-depth': 'camera-depth',
  160. 'adv / soft-body': 'soft-body',
  161. 'adv / wave': 'wave',
  162. 'misc / smoke' : 'smoke',
  163. 'misc / firefly' : 'firefly'
  164. } ).onFinishChange( function() {
  165. updateMaterial();
  166. } );
  167. gui.open();
  168. }
  169. function addGui( name, value, callback, isColor, min, max ) {
  170. var node;
  171. param[ name ] = value;
  172. if ( isColor ) {
  173. node = gui.addColor( param, name ).onChange( function() {
  174. callback( param[ name ] );
  175. } );
  176. }
  177. else if ( typeof value == 'object' ) {
  178. node = gui.add( param, name, value ).onChange( function() {
  179. callback( param[ name ] );
  180. } );
  181. }
  182. else {
  183. node = gui.add( param, name, min, max ).onChange( function() {
  184. callback( param[ name ] );
  185. } );
  186. }
  187. return node;
  188. }
  189. function updateMaterial() {
  190. move = false;
  191. if ( mesh.material ) mesh.material.dispose();
  192. var name = param.example;
  193. var mtl;
  194. clearGui();
  195. switch ( name ) {
  196. case 'phong':
  197. // MATERIAL
  198. mtl = new THREE.PhongNodeMaterial();
  199. //mtl.color = // albedo (vec3)
  200. //mtl.alpha = // opacity (float)
  201. //mtl.specular = // specular color (vec3)
  202. //mtl.shininess = // shininess (float)
  203. //mtl.normal = // normalmap (vec3)
  204. //mtl.normalScale = // normalmap scale (vec2)
  205. //mtl.emissive = // emissive color (vec3)
  206. //mtl.ambient = // ambient color (vec3)
  207. //mtl.shadow = // shadowmap (vec3)
  208. //mtl.light = // custom-light (vec3)
  209. //mtl.ao = // ambient occlusion (float)
  210. //mtl.light = // input/output light (vec3)
  211. //mtl.environment = // reflection/refraction (vec3)
  212. //mtl.environmentAlpha = // environment alpha (float)
  213. //mtl.transform = // vertex transformation (vec3)
  214. var mask = new THREE.SwitchNode( new THREE.TextureNode( decalDiffuse ), 'w' );
  215. mtl.color = new THREE.TextureNode( grass );
  216. mtl.specular = new THREE.FloatNode( .5 );
  217. mtl.shininess = new THREE.FloatNode( 15 );
  218. mtl.environment = new THREE.CubeTextureNode( cubemap );
  219. mtl.environmentAlpha = mask;
  220. mtl.normal = new THREE.TextureNode( grassNormal );
  221. mtl.normalScale = new THREE.Math1Node( mask, THREE.Math1Node.INVERT );
  222. break;
  223. case 'standard':
  224. // MATERIAL
  225. mtl = new THREE.StandardNodeMaterial();
  226. //mtl.color = // albedo (vec3)
  227. //mtl.alpha = // opacity (float)
  228. //mtl.roughness = // roughness (float)
  229. //mtl.metalness = // metalness (float)
  230. //mtl.normal = // normalmap (vec3)
  231. //mtl.normalScale = // normalmap scale (vec2)
  232. //mtl.emissive = // emissive color (vec3)
  233. //mtl.ambient = // ambient color (vec3)
  234. //mtl.shadow = // shadowmap (vec3)
  235. //mtl.light = // custom-light (vec3)
  236. //mtl.ao = // ambient occlusion (float)
  237. //mtl.environment = // reflection/refraction (vec3)
  238. //mtl.transform = // vertex transformation (vec3)
  239. var mask = new THREE.SwitchNode( new THREE.TextureNode( decalDiffuse ), 'w' );
  240. var normalScale = new THREE.FloatNode( .3 );
  241. var roughnessA = new THREE.FloatNode( .5 );
  242. var metalnessA = new THREE.FloatNode( .5 );
  243. var roughnessB = new THREE.FloatNode( 0 );
  244. var metalnessB = new THREE.FloatNode( 1 );
  245. var roughness = new THREE.Math3Node(
  246. roughnessA,
  247. roughnessB,
  248. mask,
  249. THREE.Math3Node.MIX
  250. );
  251. var metalness = new THREE.Math3Node(
  252. metalnessA,
  253. metalnessB,
  254. mask,
  255. THREE.Math3Node.MIX
  256. );
  257. var normalMask = new THREE.OperatorNode(
  258. new THREE.Math1Node( mask, THREE.Math1Node.INVERT ),
  259. normalScale,
  260. THREE.OperatorNode.MUL
  261. );
  262. mtl.color = new THREE.ColorNode( 0xFFFFFF );
  263. mtl.roughness = roughness;
  264. mtl.metalness = metalness;
  265. mtl.environment = new THREE.CubeTextureNode( cubemap );
  266. mtl.normal = new THREE.TextureNode( grassNormal );
  267. mtl.normalScale = normalMask;
  268. // GUI
  269. addGui( 'color', mtl.color.value.getHex(), function( val ) {
  270. mtl.color.value.setHex( val );
  271. }, true );
  272. addGui( 'roughnessA', roughnessA.number, function( val ) {
  273. roughnessA.number = val;
  274. }, false, 0, 1 );
  275. addGui( 'metalnessA', metalnessA.number, function( val ) {
  276. metalnessA.number = val;
  277. }, false, 0, 1 );
  278. addGui( 'roughnessB', roughnessB.number, function( val ) {
  279. roughnessB.number = val;
  280. }, false, 0, 1 );
  281. addGui( 'metalnessB', metalnessB.number, function( val ) {
  282. metalnessB.number = val;
  283. }, false, 0, 1 );
  284. addGui( 'normalScale', normalScale.number, function( val ) {
  285. normalScale.number = val;
  286. }, false, 0, 1 );
  287. break;
  288. case 'wave':
  289. // MATERIAL
  290. mtl = new THREE.PhongNodeMaterial();
  291. var time = new THREE.TimerNode();
  292. var speed = new THREE.FloatNode( 5 );
  293. var scale = new THREE.FloatNode( 1 );
  294. var worldScale = new THREE.FloatNode( .4 );
  295. var colorA = new THREE.ColorNode( 0xFFFFFF );
  296. var colorB = new THREE.ColorNode( 0x0054df );
  297. var uv = new THREE.UVNode();
  298. var timeScale = new THREE.OperatorNode(
  299. time,
  300. speed,
  301. THREE.OperatorNode.MUL
  302. );
  303. var worldScl = new THREE.OperatorNode(
  304. new THREE.PositionNode(),
  305. worldScale,
  306. THREE.OperatorNode.MUL
  307. );
  308. var posContinuous = new THREE.OperatorNode(
  309. worldScl,
  310. timeScale,
  311. THREE.OperatorNode.ADD
  312. );
  313. var wave = new THREE.Math1Node( posContinuous, THREE.Math1Node.SIN );
  314. wave = new THREE.SwitchNode( wave, 'x' );
  315. var waveScale = new THREE.OperatorNode(
  316. wave,
  317. scale,
  318. THREE.OperatorNode.MUL
  319. );
  320. var displaceY = new THREE.JoinNode(
  321. new THREE.FloatNode(),
  322. waveScale,
  323. new THREE.FloatNode()
  324. );
  325. var displace = new THREE.OperatorNode(
  326. new THREE.NormalNode(),
  327. displaceY,
  328. THREE.OperatorNode.MUL
  329. );
  330. var blend = new THREE.OperatorNode(
  331. new THREE.PositionNode(),
  332. displaceY,
  333. THREE.OperatorNode.ADD
  334. );
  335. var color = new THREE.Math3Node(
  336. colorB,
  337. colorA,
  338. wave,
  339. THREE.Math3Node.MIX
  340. );
  341. mtl.color = color;
  342. mtl.transform = blend;
  343. // GUI
  344. addGui( 'speed', speed.number, function( val ) {
  345. speed.number = val;
  346. }, false, 0, 10 );
  347. addGui( 'scale', scale.number, function( val ) {
  348. scale.number = val;
  349. }, false, 0, 3 );
  350. addGui( 'worldScale', worldScale.number, function( val ) {
  351. worldScale.number = val;
  352. }, false, 0, 1 );
  353. addGui( 'colorA', colorA.value.getHex(), function( val ) {
  354. colorA.value.setHex( val );
  355. }, true );
  356. addGui( 'colorB', colorB.value.getHex(), function( val ) {
  357. colorB.value.setHex( val );
  358. }, true );
  359. addGui( 'useNormals', false, function( val ) {
  360. blend.b = val ? displace : displaceY;
  361. mtl.build();
  362. } );
  363. break;
  364. case 'rim':
  365. // MATERIAL
  366. mtl = new THREE.PhongNodeMaterial();
  367. var intensity = 1.3;
  368. var power = new THREE.FloatNode( 3 );
  369. var color = new THREE.ColorNode( 0xFFFFFF );
  370. var viewZ = new THREE.Math2Node(
  371. new THREE.NormalNode( THREE.NormalNode.VIEW ),
  372. new THREE.Vector3Node( 0, 0, - intensity ),
  373. THREE.Math2Node.DOT
  374. );
  375. var rim = new THREE.OperatorNode(
  376. viewZ,
  377. new THREE.FloatNode( intensity ),
  378. THREE.OperatorNode.ADD
  379. );
  380. var rimPower = new THREE.Math2Node(
  381. rim,
  382. power,
  383. THREE.Math2Node.POW
  384. );
  385. var rimColor = new THREE.OperatorNode(
  386. rimPower,
  387. color,
  388. THREE.OperatorNode.MUL
  389. );
  390. mtl.color = new THREE.ColorNode( 0x111111 );
  391. mtl.emissive = rimColor;
  392. // GUI
  393. addGui( 'color', color.value.getHex(), function( val ) {
  394. color.value.setHex( val );
  395. }, true );
  396. addGui( 'intensity', intensity, function( val ) {
  397. intensity = val;
  398. viewZ.b.z = - intensity;
  399. rim.b.number = intensity;
  400. }, false, 0, 3 );
  401. addGui( 'power', power.number, function( val ) {
  402. power.number = val;
  403. }, false, 0, 6 );
  404. addGui( 'xray', false, function( val ) {
  405. if ( val ) {
  406. mtl.emissive = color;
  407. mtl.alpha = rimPower;
  408. mtl.blending = THREE.AdditiveBlending;
  409. mtl.depthWrite = false;
  410. }
  411. else {
  412. mtl.emissive = rimColor;
  413. mtl.alpha = null;
  414. mtl.blending = THREE.NormalBlending;
  415. mtl.depthWrite = true;
  416. }
  417. mtl.build();
  418. } );
  419. break;
  420. case 'color-adjustment':
  421. // MATERIAL
  422. mtl = new THREE.PhongNodeMaterial();
  423. var texture = new THREE.TextureNode( brick );
  424. var hue = new THREE.FloatNode();
  425. var sataturation = new THREE.FloatNode( 1 );
  426. var vibrance = new THREE.FloatNode();
  427. var brightness = new THREE.FloatNode( 0 );
  428. var contrast = new THREE.FloatNode( 1 );
  429. var hueNode = new THREE.ColorAdjustmentNode( texture, hue, THREE.ColorAdjustmentNode.HUE );
  430. var satNode = new THREE.ColorAdjustmentNode( hueNode, sataturation, THREE.ColorAdjustmentNode.SATURATION );
  431. var vibranceNode = new THREE.ColorAdjustmentNode( satNode, vibrance, THREE.ColorAdjustmentNode.VIBRANCE );
  432. var brightnessNode = new THREE.ColorAdjustmentNode( vibranceNode, brightness, THREE.ColorAdjustmentNode.BRIGHTNESS );
  433. var contrastNode = new THREE.ColorAdjustmentNode( brightnessNode, contrast, THREE.ColorAdjustmentNode.CONTRAST );
  434. mtl.color = contrastNode;
  435. // GUI
  436. addGui( 'hue', hue.number, function( val ) {
  437. hue.number = val;
  438. }, false, 0, Math.PI * 2 );
  439. addGui( 'saturation', sataturation.number, function( val ) {
  440. sataturation.number = val;
  441. }, false, 0, 2 );
  442. addGui( 'vibrance', vibrance.number, function( val ) {
  443. vibrance.number = val;
  444. }, false, - 1, 1 );
  445. addGui( 'brightness', brightness.number, function( val ) {
  446. brightness.number = val;
  447. }, false, 0, .5 );
  448. addGui( 'contrast', contrast.number, function( val ) {
  449. contrast.number = val;
  450. }, false, 0, 2 );
  451. break;
  452. case 'fresnel':
  453. // MATERIAL
  454. mtl = new THREE.PhongNodeMaterial();
  455. var reflectance = new THREE.FloatNode( 1.3 );
  456. var power = new THREE.FloatNode( 1 );
  457. var color = new THREE.CubeTextureNode( cubemap );
  458. var viewZ = new THREE.Math2Node(
  459. new THREE.NormalNode( THREE.NormalNode.VIEW ),
  460. new THREE.Vector3Node( 0, 0, - 1 ),
  461. THREE.Math2Node.DOT
  462. );
  463. var theta = new THREE.OperatorNode(
  464. viewZ,
  465. new THREE.FloatNode( 1 ),
  466. THREE.OperatorNode.ADD
  467. );
  468. var thetaPower = new THREE.Math2Node(
  469. theta,
  470. power,
  471. THREE.Math2Node.POW
  472. );
  473. var fresnel = new THREE.OperatorNode(
  474. reflectance,
  475. thetaPower,
  476. THREE.OperatorNode.MUL
  477. );
  478. mtl.color = new THREE.ColorNode( 0x3399FF );
  479. mtl.environment = color;
  480. mtl.environmentAlpha = new THREE.Math1Node( fresnel, THREE.Math1Node.SAT );
  481. // GUI
  482. addGui( 'reflectance', reflectance.number, function( val ) {
  483. reflectance.number = val;
  484. }, false, 0, 3 );
  485. addGui( 'power', power.number, function( val ) {
  486. power.number = val;
  487. }, false, 0, 5 );
  488. break;
  489. case 'layers':
  490. // MATERIAL
  491. mtl = new THREE.PhongNodeMaterial();
  492. var tex1 = new THREE.TextureNode( grass );
  493. var tex2 = new THREE.TextureNode( brick );
  494. var offset = new THREE.FloatNode( 0 );
  495. var scale = new THREE.FloatNode( 1 );
  496. var uv = new THREE.UVNode();
  497. var uvOffset = new THREE.OperatorNode(
  498. offset,
  499. uv,
  500. THREE.OperatorNode.ADD
  501. );
  502. var uvScale = new THREE.OperatorNode(
  503. uvOffset,
  504. scale,
  505. THREE.OperatorNode.MUL
  506. );
  507. var mask = new THREE.TextureNode( decalDiffuse, uvScale );
  508. var maskAlphaChannel = new THREE.SwitchNode( mask, 'w' );
  509. var blend = new THREE.Math3Node(
  510. tex1,
  511. tex2,
  512. maskAlphaChannel,
  513. THREE.Math3Node.MIX
  514. );
  515. mtl.color = blend;
  516. // GUI
  517. addGui( 'offset', offset.number, function( val ) {
  518. offset.number = val;
  519. }, false, 0, 1 );
  520. addGui( 'scale', scale.number, function( val ) {
  521. scale.number = val;
  522. }, false, 0, 10 );
  523. break;
  524. case 'saturation':
  525. // MATERIAL
  526. mtl = new THREE.StandardNodeMaterial();
  527. var tex = new THREE.TextureNode( brick );
  528. var sat = new THREE.FloatNode( 0 );
  529. var satrgb = new THREE.FunctionNode( [
  530. "vec3 satrgb(vec3 rgb, float adjustment) {",
  531. //"const vec3 W = vec3(0.2125, 0.7154, 0.0721);", // LUMA
  532. "vec3 intensity = vec3(dot(rgb, LUMA));",
  533. "return mix(intensity, rgb, adjustment);",
  534. "}"
  535. ].join( "\n" ) );
  536. var saturation = new THREE.FunctionCallNode( satrgb );
  537. saturation.inputs.rgb = tex;
  538. saturation.inputs.adjustment = sat;
  539. // or try
  540. //saturation.inputs[0] = tex;
  541. //saturation.inputs[1] = sat;
  542. mtl.color = saturation;
  543. mtl.environment = new THREE.CubeTextureNode( cubemap ); // optional
  544. // GUI
  545. addGui( 'saturation', sat.number, function( val ) {
  546. sat.number = val;
  547. }, false, 0, 2 );
  548. break;
  549. case 'top-bottom':
  550. // MATERIAL
  551. mtl = new THREE.PhongNodeMaterial();
  552. var top = new THREE.TextureNode( grass );
  553. var bottom = new THREE.TextureNode( brick );
  554. var normal = new THREE.NormalNode( THREE.NormalNode.WORLD );
  555. var normalY = new THREE.SwitchNode( normal, 'y' );
  556. var hard = new THREE.FloatNode( 9 );
  557. var offset = new THREE.FloatNode( - 2.5 );
  558. var hardClamp = new THREE.OperatorNode(
  559. normalY,
  560. hard,
  561. THREE.OperatorNode.MUL
  562. );
  563. var offsetClamp = new THREE.OperatorNode(
  564. hardClamp,
  565. offset,
  566. THREE.OperatorNode.ADD
  567. );
  568. var clamp0at1 = new THREE.Math1Node( offsetClamp, THREE.Math1Node.SAT );
  569. var blend = new THREE.Math3Node( top, bottom, clamp0at1, THREE.Math3Node.MIX );
  570. mtl.color = blend;
  571. // GUI
  572. addGui( 'hard', hard.number, function( val ) {
  573. hard.number = val;
  574. }, false, 0, 20 );
  575. addGui( 'offset', offset.number, function( val ) {
  576. offset.number = val;
  577. }, false, - 10, 10 );
  578. break;
  579. case 'displace':
  580. // MATERIAL
  581. mtl = new THREE.PhongNodeMaterial();
  582. var time = new THREE.TimerNode();
  583. var scale = new THREE.FloatNode( 2 );
  584. var speed = new THREE.FloatNode( .2 );
  585. var colorA = new THREE.ColorNode( 0xFFFFFF );
  586. var colorB = new THREE.ColorNode( 0x0054df );
  587. var uv = new THREE.UVNode();
  588. var timeScl = new THREE.OperatorNode(
  589. time,
  590. speed,
  591. THREE.OperatorNode.MUL
  592. );
  593. var displaceOffset = new THREE.OperatorNode(
  594. timeScl,
  595. uv,
  596. THREE.OperatorNode.ADD
  597. );
  598. var tex = new THREE.TextureNode( cloud, displaceOffset );
  599. var texArea = new THREE.SwitchNode( tex, 'w' );
  600. var displace = new THREE.OperatorNode(
  601. new THREE.NormalNode(),
  602. texArea,
  603. THREE.OperatorNode.MUL
  604. );
  605. var displaceScale = new THREE.OperatorNode(
  606. displace,
  607. scale,
  608. THREE.OperatorNode.MUL
  609. );
  610. var blend = new THREE.OperatorNode(
  611. new THREE.PositionNode(),
  612. displaceScale,
  613. THREE.OperatorNode.ADD
  614. );
  615. var color = new THREE.Math3Node(
  616. colorB,
  617. colorA,
  618. texArea,
  619. THREE.Math3Node.MIX
  620. );
  621. mtl.color = mtl.specular = new THREE.ColorNode( 0 );
  622. mtl.emissive = color;
  623. mtl.transform = blend;
  624. // GUI
  625. addGui( 'speed', speed.number, function( val ) {
  626. speed.number = val;
  627. }, false, 0, 1 );
  628. addGui( 'scale', scale.number, function( val ) {
  629. scale.number = val;
  630. }, false, 0, 10 );
  631. addGui( 'colorA', colorA.value.getHex(), function( val ) {
  632. colorA.value.setHex( val );
  633. }, true );
  634. addGui( 'colorB', colorB.value.getHex(), function( val ) {
  635. colorB.value.setHex( val );
  636. }, true );
  637. break;
  638. case 'smoke':
  639. // MATERIAL
  640. mtl = new THREE.PhongNodeMaterial();
  641. var time = new THREE.TimerNode();
  642. var uv = new THREE.UVNode();
  643. var timeSpeedA = new THREE.OperatorNode(
  644. time,
  645. new THREE.Vector2Node( 0.3, 0.1 ),
  646. THREE.OperatorNode.MUL
  647. );
  648. var timeSpeedB = new THREE.OperatorNode(
  649. time,
  650. new THREE.Vector2Node( 0.15, 0.4 ),
  651. THREE.OperatorNode.MUL
  652. );
  653. var uvOffsetA = new THREE.OperatorNode(
  654. timeSpeedA,
  655. uv,
  656. THREE.OperatorNode.ADD
  657. );
  658. var uvOffsetB = new THREE.OperatorNode(
  659. timeSpeedB,
  660. uv,
  661. THREE.OperatorNode.ADD
  662. );
  663. var cloudA = new THREE.TextureNode( cloud, uvOffsetA );
  664. var cloudB = new THREE.TextureNode( cloud, uvOffsetB );
  665. var clouds = new THREE.OperatorNode(
  666. cloudA,
  667. cloudB,
  668. THREE.OperatorNode.ADD
  669. );
  670. mtl.environment = new THREE.ColorNode( 0xFFFFFF );
  671. mtl.alpha = clouds;
  672. // GUI
  673. addGui( 'color', mtl.environment.value.getHex(), function( val ) {
  674. mtl.environment.value.setHex( val );
  675. }, true );
  676. break;
  677. case 'camera-depth':
  678. // MATERIAL
  679. var colorA = new THREE.ColorNode( 0xFFFFFF );
  680. var colorB = new THREE.ColorNode( 0x0054df );
  681. var depth = new THREE.CameraNode( THREE.CameraNode.DEPTH );
  682. depth.near.number = 1;
  683. depth.far.number = 200;
  684. var colors = new THREE.Math3Node(
  685. colorB,
  686. colorA,
  687. depth,
  688. THREE.Math3Node.MIX
  689. );
  690. mtl = new THREE.PhongNodeMaterial();
  691. mtl.color = colors;
  692. // GUI
  693. addGui( 'near', depth.near.number, function( val ) {
  694. depth.near.number = val;
  695. }, false, 1, 1200 );
  696. addGui( 'far', depth.far.number, function( val ) {
  697. depth.far.number = val;
  698. }, false, 1, 1200 );
  699. addGui( 'nearColor', colorA.value.getHex(), function( val ) {
  700. colorA.value.setHex( val );
  701. }, true );
  702. addGui( 'farColor', colorB.value.getHex(), function( val ) {
  703. colorB.value.setHex( val );
  704. }, true );
  705. break;
  706. case 'caustic':
  707. // MATERIAL
  708. mtl = new THREE.StandardNodeMaterial();
  709. var hash2 = new THREE.FunctionNode( [
  710. "vec2 hash2(vec2 p) {",
  711. "return fract(sin(vec2(dot(p, vec2(123.4, 748.6)), dot(p, vec2(547.3, 659.3))))*5232.85324);",
  712. "}"
  713. ].join( "\n" ) );
  714. var voronoi = new THREE.FunctionNode( [
  715. // Based off of iq's described here: http://www.iquilezles.org/www/articles/voronoili
  716. "float voronoi(vec2 p, in float time) {",
  717. "vec2 n = floor(p);",
  718. "vec2 f = fract(p);",
  719. "float md = 5.0;",
  720. "vec2 m = vec2(0.0);",
  721. "for (int i = -1; i <= 1; i++) {",
  722. "for (int j = -1; j <= 1; j++) {",
  723. "vec2 g = vec2(i, j);",
  724. "vec2 o = hash2(n + g);",
  725. "o = 0.5 + 0.5 * sin(time + 5.038 * o);",
  726. "vec2 r = g + o - f;",
  727. "float d = dot(r, r);",
  728. "if (d < md) {",
  729. "md = d;",
  730. "m = n+g+o;",
  731. "}",
  732. "}",
  733. "}",
  734. "return md;",
  735. "}"
  736. ].join( "\n" ), [ hash2 ] ); // define hash2 as dependencies
  737. var voronoiLayers = new THREE.FunctionNode( [
  738. // based on https://www.shadertoy.com/view/4tXSDf
  739. "float voronoiLayers(vec2 p, in float time) {",
  740. "float v = 0.0;",
  741. "float a = 0.4;",
  742. "for (int i = 0; i < 3; i++) {",
  743. "v += voronoi(p, time) * a;",
  744. "p *= 2.0;",
  745. "a *= 0.5;",
  746. "}",
  747. "return v;",
  748. "}"
  749. ].join( "\n" ), [ voronoi ] ); // define voronoi as dependencies
  750. var time = new THREE.TimerNode();
  751. var timeScale = new THREE.FloatNode( 2 );
  752. var alpha = new THREE.FloatNode( 1 );
  753. var scale = new THREE.FloatNode( .1 );
  754. var intensity = new THREE.FloatNode( 1.5 );
  755. var color = new THREE.ColorNode( 0xFFFFFF );
  756. var colorA = new THREE.ColorNode( 0xFFFFFF );
  757. var colorB = new THREE.ColorNode( 0x0054df );
  758. var worldPos = new THREE.PositionNode( THREE.PositionNode.WORLD );
  759. var worldPosTop = new THREE.SwitchNode( worldPos, 'xz' );
  760. var worldNormal = new THREE.NormalNode( THREE.NormalNode.WORLD );
  761. var mask = new THREE.SwitchNode( worldNormal, 'y' );
  762. // clamp0at1
  763. mask = new THREE.Math1Node( mask, THREE.Math1Node.SAT );
  764. var timeOffset = new THREE.OperatorNode(
  765. time,
  766. timeScale,
  767. THREE.OperatorNode.MUL
  768. );
  769. var uvPos = new THREE.OperatorNode(
  770. worldPosTop,
  771. scale,
  772. THREE.OperatorNode.MUL
  773. );
  774. var voronoi = new THREE.FunctionCallNode( voronoiLayers );
  775. voronoi.inputs.p = uvPos;
  776. voronoi.inputs.time = timeOffset;
  777. var maskCaustic = new THREE.OperatorNode(
  778. alpha,
  779. mask,
  780. THREE.OperatorNode.MUL
  781. );
  782. var voronoiIntensity = new THREE.OperatorNode(
  783. voronoi,
  784. intensity,
  785. THREE.OperatorNode.MUL
  786. );
  787. var voronoiColors = new THREE.Math3Node(
  788. colorB,
  789. colorA,
  790. new THREE.Math1Node( voronoiIntensity, THREE.Math1Node.SAT ), // mix needs clamp
  791. THREE.Math3Node.MIX
  792. );
  793. var caustic = new THREE.Math3Node(
  794. color,
  795. voronoiColors,
  796. maskCaustic,
  797. THREE.Math3Node.MIX
  798. );
  799. var causticLights = new THREE.OperatorNode(
  800. voronoiIntensity,
  801. maskCaustic,
  802. THREE.OperatorNode.MUL
  803. );
  804. mtl.color = caustic;
  805. mtl.ambient = causticLights;
  806. // GUI
  807. addGui( 'timeScale', timeScale.number, function( val ) {
  808. timeScale.number = val;
  809. }, false, 0, 5 );
  810. addGui( 'intensity', intensity.number, function( val ) {
  811. intensity.number = val;
  812. }, false, 0, 3 );
  813. addGui( 'scale', scale.number, function( val ) {
  814. scale.number = val;
  815. }, false, 0, 1 );
  816. addGui( 'alpha', alpha.number, function( val ) {
  817. alpha.number = val;
  818. }, false, 0, 1 );
  819. addGui( 'color', color.value.getHex(), function( val ) {
  820. color.value.setHex( val );
  821. }, true );
  822. addGui( 'colorA', colorA.value.getHex(), function( val ) {
  823. colorA.value.setHex( val );
  824. }, true );
  825. addGui( 'colorB', colorB.value.getHex(), function( val ) {
  826. colorB.value.setHex( val );
  827. }, true );
  828. break;
  829. case 'soft-body':
  830. // MATERIAL
  831. move = true;
  832. mtl = new THREE.StandardNodeMaterial();
  833. var scale = new THREE.FloatNode( 2 );
  834. var colorA = new THREE.ColorNode( 0xFF6633 );
  835. var colorB = new THREE.ColorNode( 0x3366FF );
  836. var pos = new THREE.PositionNode();
  837. var posNorm = new THREE.Math1Node( pos, THREE.Math1Node.NORMALIZE );
  838. var mask = new THREE.SwitchNode( posNorm, 'y' );
  839. var velocity = new THREE.VelocityNode( mesh, {
  840. type: 'elastic',
  841. spring: .8,
  842. friction: .9
  843. } );
  844. var velocityArea = new THREE.OperatorNode(
  845. mask,
  846. scale,
  847. THREE.OperatorNode.MUL
  848. );
  849. var softVelocity = new THREE.OperatorNode(
  850. velocity,
  851. velocityArea,
  852. THREE.OperatorNode.MUL
  853. );
  854. var softPosition = new THREE.OperatorNode(
  855. new THREE.PositionNode(),
  856. softVelocity,
  857. THREE.OperatorNode.ADD
  858. );
  859. var colors = new THREE.Math3Node(
  860. colorB,
  861. colorA,
  862. mask,
  863. THREE.Math3Node.MIX
  864. );
  865. mtl.color = colors;
  866. mtl.transform = softPosition;
  867. // GUI
  868. addGui( 'spring', velocity.params.spring, function( val ) {
  869. velocity.params.spring = val;
  870. }, false, 0, .9 );
  871. addGui( 'friction', velocity.params.friction, function( val ) {
  872. velocity.params.friction = val;
  873. }, false, 0, .9 );
  874. addGui( 'scale', scale.number, function( val ) {
  875. scale.number = val;
  876. }, false, 0, 3 );
  877. addGui( 'softBody', colorA.value.getHex(), function( val ) {
  878. colorA.value.setHex( val );
  879. }, true );
  880. addGui( 'hardBody', colorB.value.getHex(), function( val ) {
  881. colorB.value.setHex( val );
  882. }, true );
  883. break;
  884. case 'plush':
  885. // MATERIAL
  886. mtl = new THREE.PhongNodeMaterial();
  887. var color = new THREE.ColorNode( 0x8D8677 );
  888. var mildness = new THREE.FloatNode( 1.6 );
  889. var fur = new THREE.FloatNode( .5 );
  890. var posDirection = new THREE.Math1Node( new THREE.PositionNode( THREE.PositionNode.VIEW ), THREE.Math1Node.NORMALIZE );
  891. var norDirection = new THREE.Math1Node( new THREE.NormalNode( THREE.NormalNode.VIEW ), THREE.Math1Node.NORMALIZE );
  892. var viewZ = new THREE.Math2Node(
  893. posDirection,
  894. norDirection,
  895. THREE.Math2Node.DOT
  896. );
  897. // without luma correction for now
  898. var mildnessColor = new THREE.OperatorNode(
  899. color,
  900. mildness,
  901. THREE.OperatorNode.MUL
  902. );
  903. var furScale = new THREE.OperatorNode(
  904. viewZ,
  905. fur,
  906. THREE.OperatorNode.MUL
  907. );
  908. mtl.color = color;
  909. mtl.normal = new THREE.TextureNode( grassNormal );
  910. mtl.normalScale = furScale;
  911. mtl.environment = mildnessColor;
  912. mtl.environmentAlpha = new THREE.Math1Node( viewZ, THREE.Math1Node.INVERT );
  913. mtl.shininess = new THREE.FloatNode( 0 );
  914. // GUI
  915. addGui( 'color', color.value.getHex(), function( val ) {
  916. color.value.setHex( val );
  917. }, true );
  918. addGui( 'mildness', mildness.number, function( val ) {
  919. mildness.number = val;
  920. }, false, 1, 2 );
  921. addGui( 'fur', fur.number, function( val ) {
  922. fur.number = val;
  923. }, false, 0, 2 );
  924. break;
  925. case 'skin':
  926. case 'skin-phong':
  927. // MATERIAL
  928. mtl = name == 'skin' ? new THREE.StandardNodeMaterial() : new THREE.PhongNodeMaterial();
  929. var skinColor = new THREE.ColorNode( 0xFFC495 );
  930. var bloodColor = new THREE.ColorNode( 0x6b0602 );
  931. var wrapLight = new THREE.FloatNode( 1.5 );
  932. var wrapShadow = new THREE.FloatNode( 0 );
  933. var directLight = new THREE.LightNode();
  934. var lightLuminance = new THREE.LuminanceNode( directLight );
  935. var lightWrap = new THREE.Math3Node(
  936. wrapShadow,
  937. wrapLight,
  938. lightLuminance,
  939. THREE.Math3Node.SMOOTHSTEP
  940. );
  941. var lightTransition = new THREE.OperatorNode(
  942. lightWrap,
  943. new THREE.ConstNode( THREE.ConstNode.PI2 ),
  944. THREE.OperatorNode.MUL
  945. );
  946. var wrappedLight = new THREE.Math1Node( lightTransition, THREE.Math1Node.SIN );
  947. var wrappedLightColor = new THREE.OperatorNode(
  948. wrappedLight,
  949. bloodColor,
  950. THREE.OperatorNode.MUL
  951. );
  952. var bloodArea = new THREE.Math1Node( wrappedLightColor, THREE.Math1Node.SAT );
  953. var totalLight = new THREE.OperatorNode(
  954. directLight,
  955. bloodArea,
  956. THREE.OperatorNode.ADD
  957. );
  958. mtl.color = skinColor;
  959. mtl.light = totalLight;
  960. if ( name == 'skin' ) {
  961. // StandardNodeMaterial
  962. mtl.metalness = new THREE.FloatNode( .05 );
  963. mtl.roughness = new THREE.FloatNode( .5 );
  964. mtl.environment = new THREE.CubeTextureNode( cubemap );
  965. }
  966. else {
  967. // PhongNodeMaterial
  968. mtl.specular = new THREE.ColorNode( 0x2f2e2d );
  969. mtl.shininess = new THREE.FloatNode( 10 );
  970. }
  971. // GUI
  972. addGui( 'skinColor', skinColor.value.getHex(), function( val ) {
  973. skinColor.value.setHex( val );
  974. }, true );
  975. addGui( 'bloodColor', bloodColor.value.getHex(), function( val ) {
  976. bloodColor.value.setHex( val );
  977. }, true );
  978. addGui( 'wrapLight', wrapLight.number, function( val ) {
  979. wrapLight.number = val;
  980. }, false, 0, 3 );
  981. addGui( 'wrapShadow', wrapShadow.number, function( val ) {
  982. wrapShadow.number = val;
  983. }, false, -1, 0 );
  984. break;
  985. case 'toon':
  986. // MATERIAL
  987. mtl = new THREE.PhongNodeMaterial();
  988. var count = new THREE.FloatNode( 3.43 );
  989. var sceneDirectLight = new THREE.LightNode();
  990. var color = new THREE.ColorNode( 0xAABBFF );
  991. var lineColor = new THREE.ColorNode( 0xFF0000 );
  992. var lineSize = new THREE.FloatNode( 0.23 );
  993. var lineInner = new THREE.FloatNode( 0 );
  994. // CEL
  995. var lightLuminance = new THREE.LuminanceNode( sceneDirectLight );
  996. var preCelLight = new THREE.OperatorNode(
  997. lightLuminance,
  998. count,
  999. THREE.OperatorNode.MUL
  1000. );
  1001. var celLight = new THREE.Math1Node(
  1002. preCelLight,
  1003. THREE.Math1Node.CEIL
  1004. );
  1005. var posCelLight = new THREE.OperatorNode(
  1006. celLight,
  1007. count,
  1008. THREE.OperatorNode.DIV
  1009. );
  1010. // LINE
  1011. var posDirection = new THREE.Math1Node( new THREE.PositionNode( THREE.PositionNode.VIEW ), THREE.Math1Node.NORMALIZE );
  1012. var norDirection = new THREE.Math1Node( new THREE.NormalNode( THREE.NormalNode.VIEW ), THREE.Math1Node.NORMALIZE );
  1013. var viewZ = new THREE.Math2Node(
  1014. posDirection,
  1015. norDirection,
  1016. THREE.Math2Node.DOT
  1017. );
  1018. var lineOutside = new THREE.Math1Node(
  1019. viewZ,
  1020. THREE.Math1Node.ABS
  1021. );
  1022. var line = new THREE.OperatorNode(
  1023. lineOutside,
  1024. new THREE.FloatNode( 1 ),
  1025. THREE.OperatorNode.DIV
  1026. );
  1027. var lineScaled = new THREE.Math3Node(
  1028. line,
  1029. lineSize,
  1030. lineInner,
  1031. THREE.Math3Node.SMOOTHSTEP
  1032. );
  1033. var innerContour = new THREE.Math1Node( new THREE.Math1Node( lineScaled, THREE.Math1Node.SAT ), THREE.Math1Node.INVERT );
  1034. // APPLY
  1035. mtl.color = color;
  1036. mtl.light = posCelLight;
  1037. mtl.shininess = new THREE.FloatNode( 0 );
  1038. mtl.environment = lineColor;
  1039. mtl.environmentAlpha = innerContour;
  1040. // GUI
  1041. addGui( 'color', color.value.getHex(), function( val ) {
  1042. color.value.setHex( val );
  1043. }, true );
  1044. addGui( 'lineColor', lineColor.value.getHex(), function( val ) {
  1045. lineColor.value.setHex( val );
  1046. }, true );
  1047. addGui( 'count', count.number, function( val ) {
  1048. count.number = val;
  1049. }, false, 1, 8 );
  1050. addGui( 'lineSize', lineSize.number, function( val ) {
  1051. lineSize.number = val;
  1052. }, false, 0, 1 );
  1053. addGui( 'lineInner', lineInner.number, function( val ) {
  1054. lineInner.number = val;
  1055. }, false, 0, 1 );
  1056. addGui( 'ignoreIndirectLight', false, function( val ) {
  1057. mtl.ao = val ? new THREE.FloatNode() : undefined;
  1058. mtl.build();
  1059. } );
  1060. break;
  1061. case 'firefly':
  1062. // MATERIAL
  1063. mtl = new THREE.PhongNodeMaterial();
  1064. var time = new THREE.TimerNode();
  1065. var speed = new THREE.FloatNode( .5 );
  1066. var color = new THREE.ColorNode( 0x98ff00 );
  1067. var timeSpeed = new THREE.OperatorNode(
  1068. time,
  1069. speed,
  1070. THREE.OperatorNode.MUL
  1071. );
  1072. var sinCycleInSecs = new THREE.OperatorNode(
  1073. timeSpeed,
  1074. new THREE.ConstNode( THREE.ConstNode.PI2 ),
  1075. THREE.OperatorNode.MUL
  1076. );
  1077. var cycle = new THREE.Math1Node( sinCycleInSecs, THREE.Math1Node.SIN );
  1078. var cycleColor = new THREE.OperatorNode(
  1079. cycle,
  1080. color,
  1081. THREE.OperatorNode.MUL
  1082. );
  1083. var cos = new THREE.Math1Node( cycleColor, THREE.Math1Node.SIN );
  1084. mtl.color = new THREE.ColorNode( 0 );
  1085. mtl.emissive = cos;
  1086. // GUI
  1087. addGui( 'speed', speed.number, function( val ) {
  1088. speed.number = val;
  1089. }, false, 0, 3 );
  1090. break;
  1091. }
  1092. // build shader
  1093. mtl.build();
  1094. // set material
  1095. mesh.material = mtl;
  1096. }
  1097. function onWindowResize() {
  1098. camera.aspect = window.innerWidth / window.innerHeight;
  1099. camera.updateProjectionMatrix();
  1100. renderer.setSize( window.innerWidth, window.innerHeight );
  1101. }
  1102. function animate() {
  1103. var delta = clock.getDelta();
  1104. if ( move ) {
  1105. var time = Date.now() * 0.005;
  1106. mesh.position.z = Math.cos( time ) * 10;
  1107. mesh.position.y = Math.sin( time ) * 10;
  1108. }
  1109. else {
  1110. mesh.position.z = mesh.position.y = 0;
  1111. }
  1112. //mesh.rotation.z += .01;
  1113. // update material animation and/or gpu calcs (pre-renderer)
  1114. mesh.material.updateAnimation( delta );
  1115. renderer.render( scene, camera );
  1116. requestAnimationFrame( animate );
  1117. }
  1118. </script>
  1119. </body>
  1120. </html>