Browse Source

nodematerial revision

sunag 7 years ago
parent
commit
0cc3a3767d
42 changed files with 261 additions and 144 deletions
  1. 1 1
      examples/js/loaders/NodeMaterialLoader.js
  2. 1 0
      examples/js/nodes/Nodes.js
  3. 2 0
      examples/js/nodes/THREE.Nodes.js
  4. 2 2
      examples/js/nodes/accessors/CameraNode.js
  5. 2 2
      examples/js/nodes/bsdfs/BlinnExponentToRoughnessNode.js
  6. 1 1
      examples/js/nodes/bsdfs/BlinnShininessExponentNode.js
  7. 2 2
      examples/js/nodes/bsdfs/RoughnessToBlinnExponentNode.js
  8. 1 1
      examples/js/nodes/core/ConstNode.js
  9. 8 10
      examples/js/nodes/core/FunctionCallNode.js
  10. 16 2
      examples/js/nodes/core/GLNode.js
  11. 51 34
      examples/js/nodes/core/NodeBuilder.js
  12. 2 2
      examples/js/nodes/effects/BlurNode.js
  13. 1 1
      examples/js/nodes/effects/ColorAdjustmentNode.js
  14. 1 1
      examples/js/nodes/effects/LuminanceNode.js
  15. 2 2
      examples/js/nodes/inputs/CubeTextureNode.js
  16. 1 1
      examples/js/nodes/inputs/FloatNode.js
  17. 1 1
      examples/js/nodes/inputs/IntNode.js
  18. 57 0
      examples/js/nodes/inputs/PropertyNode.js
  19. 4 4
      examples/js/nodes/inputs/TextureNode.js
  20. 4 4
      examples/js/nodes/materials/MeshStandardNodeMaterial.js
  21. 2 2
      examples/js/nodes/materials/NodeMaterial.js
  22. 35 13
      examples/js/nodes/materials/nodes/MeshStandardNode.js
  23. 4 4
      examples/js/nodes/materials/nodes/PhongNode.js
  24. 1 1
      examples/js/nodes/materials/nodes/SpriteNode.js
  25. 7 7
      examples/js/nodes/materials/nodes/StandardNode.js
  26. 1 1
      examples/js/nodes/math/Math1Node.js
  27. 6 6
      examples/js/nodes/math/Math2Node.js
  28. 8 8
      examples/js/nodes/math/Math3Node.js
  29. 2 2
      examples/js/nodes/math/OperatorNode.js
  30. 2 2
      examples/js/nodes/misc/BumpMapNode.js
  31. 0 2
      examples/js/nodes/misc/NormalMapNode.js
  32. 2 2
      examples/js/nodes/misc/TextureCubeUVNode.js
  33. 1 1
      examples/js/nodes/procedural/NoiseNode.js
  34. 2 2
      examples/js/nodes/utils/BypassNode.js
  35. 4 4
      examples/js/nodes/utils/JoinNode.js
  36. 3 3
      examples/js/nodes/utils/SwitchNode.js
  37. 0 0
      examples/nodes/caustic.json
  38. 0 0
      examples/nodes/displace.json
  39. 0 0
      examples/nodes/wave.json
  40. 0 0
      examples/nodes/xray.json
  41. 18 10
      examples/webgl_materials_nodes.html
  42. 3 3
      examples/webgl_sprites_nodes.html

+ 1 - 1
examples/js/loaders/NodeMaterialLoader.js

@@ -124,7 +124,7 @@ Object.assign( THREE.NodeMaterialLoader.prototype, {
 			
 			case "string":
 			
-				if (/^\w{8}-\w{4}-\w{4}-\w{4}-\w{12}$/i.test(json)) {
+				if (/^\w{8}-\w{4}-\w{4}-\w{4}-\w{12}$/i.test(json) || this.library[ json ]) {
 					
 					return this.getNode( json );
 					

+ 1 - 0
examples/js/nodes/Nodes.js

@@ -31,6 +31,7 @@ export { TextureNode } from './inputs/TextureNode.js';
 export { CubeTextureNode } from './inputs/CubeTextureNode.js';
 export { ScreenNode } from './inputs/ScreenNode.js';
 export { ReflectorNode } from './inputs/ReflectorNode.js';
+export { PropertyNode } from './inputs/PropertyNode.js';
 
 // accessors
 

+ 2 - 0
examples/js/nodes/THREE.Nodes.js

@@ -31,6 +31,7 @@ import {
 	CubeTextureNode,
 	ScreenNode,
 	ReflectorNode,
+	PropertyNode,
 	
 	// accessors
 	
@@ -133,6 +134,7 @@ THREE.TextureNode = TextureNode;
 THREE.CubeTextureNode = CubeTextureNode;
 THREE.ScreenNode = ScreenNode;
 THREE.ReflectorNode = ReflectorNode;
+THREE.PropertyNode = PropertyNode;
 
 // accessors
 

+ 2 - 2
examples/js/nodes/accessors/CameraNode.js

@@ -93,7 +93,7 @@ CameraNode.prototype.getType = function ( builder ) {
 
 		case CameraNode.DEPTH:
 		
-			return 'fv1';
+			return 'f';
 
 	}
 
@@ -146,7 +146,7 @@ CameraNode.prototype.generate = function ( builder, output ) {
 
 			var depthColor = builder.include( CameraNode.Nodes.depthColor );
 
-			result = depthColor + '( ' + this.near.build( builder, 'fv1' ) + ', ' + this.far.build( builder, 'fv1' ) + ' )';
+			result = depthColor + '( ' + this.near.build( builder, 'f' ) + ', ' + this.far.build( builder, 'f' ) + ' )';
 
 			break;
 

+ 2 - 2
examples/js/nodes/bsdfs/BlinnExponentToRoughnessNode.js

@@ -7,7 +7,7 @@ import { BlinnShininessExponentNode } from './BlinnShininessExponentNode.js';
 
 function BlinnExponentToRoughnessNode( blinnExponent ) {
 
-	TempNode.call( this, 'fv1' );
+	TempNode.call( this, 'f' );
 
 	this.blinnExponent = blinnExponent || new BlinnShininessExponentNode();
 
@@ -19,7 +19,7 @@ BlinnExponentToRoughnessNode.prototype.nodeType = "BlinnExponentToRoughness";
 
 BlinnExponentToRoughnessNode.prototype.generate = function ( builder, output ) {
 
-	return builder.format( 'BlinnExponentToGGXRoughness( ' + this.blinnExponent.build( builder, 'fv1' ) + ' )', this.type, output );
+	return builder.format( 'BlinnExponentToGGXRoughness( ' + this.blinnExponent.build( builder, 'f' ) + ' )', this.type, output );
 
 };
 

+ 1 - 1
examples/js/nodes/bsdfs/BlinnShininessExponentNode.js

@@ -6,7 +6,7 @@ import { TempNode } from '../core/TempNode.js';
 
 function BlinnShininessExponentNode() {
 
-	TempNode.call( this, 'fv1' );
+	TempNode.call( this, 'f' );
 
 };
 

+ 2 - 2
examples/js/nodes/bsdfs/RoughnessToBlinnExponentNode.js

@@ -9,7 +9,7 @@ import { BlinnShininessExponentNode } from './BlinnShininessExponentNode.js';
  
 function RoughnessToBlinnExponentNode( texture ) {
 
-	TempNode.call( this, 'fv1' );
+	TempNode.call( this, 'f' );
 
 	this.texture = texture;
 
@@ -52,7 +52,7 @@ RoughnessToBlinnExponentNode.prototype.generate = function ( builder, output ) {
 	
 		var getSpecularMIPLevel = builder.include( RoughnessToBlinnExponentNode.Nodes.getSpecularMIPLevel );
 
-		return builder.format( getSpecularMIPLevel + '( ' + this.blinnShininessExponent.build( builder, 'fv1' ) + ', ' + this.maxMIPLevel.build( builder, 'fv1' ) + ' )', this.type, output );
+		return builder.format( getSpecularMIPLevel + '( ' + this.blinnShininessExponent.build( builder, 'f' ) + ', ' + this.maxMIPLevel.build( builder, 'f' ) + ' )', this.type, output );
 
 	} else {
 

+ 1 - 1
examples/js/nodes/core/ConstNode.js

@@ -50,7 +50,7 @@ ConstNode.prototype.eval = function ( src, useDefine ) {
 	} else {
 
 		name = this.src;
-		type = 'fv1';
+		type = 'f';
 
 	}
 

+ 8 - 10
examples/js/nodes/core/FunctionCallNode.js

@@ -37,18 +37,16 @@ FunctionCallNode.prototype.getType = function ( builder ) {
 
 FunctionCallNode.prototype.generate = function ( builder, output ) {
 
-	var material = builder.material;
+	var type = this.getType( builder ),
+		func = this.value;
 
-	var type = this.getType( builder );
-	var func = this.value;
-
-	var code = func.build( builder, output ) + '( ';
-	var params = [];
+	var code = func.build( builder, output ) + '( ',
+		params = [];
 
 	for ( var i = 0; i < func.inputs.length; i ++ ) {
 
-		var inpt = func.inputs[ i ];
-		var param = this.inputs[ i ] || this.inputs[ inpt.name ];
+		var inpt = func.inputs[ i ],
+			param = this.inputs[ i ] || this.inputs[ inpt.name ];
 
 		params.push( param.build( builder, builder.getTypeByFormat( inpt.type ) ) );
 
@@ -92,8 +90,8 @@ FunctionCallNode.prototype.toJSON = function ( meta ) {
 
 			for ( var i = 0; i < func.inputs.length; i ++ ) {
 
-				var inpt = func.inputs[ i ];
-				var node = this.inputs[ i ] || this.inputs[ inpt.name ];
+				var inpt = func.inputs[ i ],
+					node = this.inputs[ i ] || this.inputs[ inpt.name ];
 
 				data.inputs[ inpt.name ] = node.toJSON( meta ).uuid;
 

+ 16 - 2
examples/js/nodes/core/GLNode.js

@@ -89,7 +89,7 @@ GLNode.prototype = {
 
 		data.deps = ( data.deps || 0 ) + 1;
 
-		var outputLen = builder.getFormatLength( output );
+		var outputLen = builder.getTypeLength( output );
 
 		if ( outputLen > ( data.outputMax || 0 ) || this.getType( builder, output ) ) {
 
@@ -100,6 +100,20 @@ GLNode.prototype = {
 	
 	},
 	
+	setName: function( name ) {
+		
+		this.name = name;
+		
+		return this;
+		
+	},
+	
+	getName: function( builder ) {
+		
+		return this.name;
+		
+	},
+	
 	getType: function ( builder, output ) {
 
 		return output === 'sampler2D' || output === 'samplerCube' ? output : this.type;
@@ -155,7 +169,7 @@ GLNode.prototype = {
 
 		return this.getJSONNode( meta ) || this.createJSONNode( meta );
 	
-	},
+	}
 	
 };
 

+ 51 - 34
examples/js/nodes/core/NodeBuilder.js

@@ -14,23 +14,22 @@ import { Vector4Node } from '../inputs/Vector4Node.js';
 import { TextureNode } from '../inputs/TextureNode.js';
 import { CubeTextureNode } from '../inputs/CubeTextureNode.js';
 
- 
 var elements = NodeUtils.elements,
 	constructors = [ 'float', 'vec2', 'vec3', 'vec4' ],
-	formatToType = {
-		float: 'fv1',
+	convertFormatToType = {
+		float: 'f',
 		vec2: 'v2',
 		vec3: 'v3',
 		vec4: 'v4',
 		mat4: 'v4',
-		int: 'iv1'
+		int: 'i'
 	},
-	typeToFormat = {
+	convertTypeToFormat = {
 		t: 'sampler2D',
 		tc: 'samplerCube',
-		bv1: 'bool',
-		iv1: 'int',
-		fv1: 'float',
+		b: 'bool',
+		i: 'int',
+		f: 'float',
 		c: 'vec3',
 		v2: 'vec2',
 		v3: 'vec3',
@@ -132,10 +131,10 @@ function NodeBuilder() {
 	
 	this.extensions = {};
 	
-	this.nodes = [];
-	
 	this.updaters = [];
 	
+	this.nodes = [];
+	
 	// --
 	
 	this.parsing = false;
@@ -657,11 +656,17 @@ NodeBuilder.prototype = {
 
 	},
 
-	colorToVector: function ( color ) {
+	colorToVectorProperties: function ( color ) {
 
 		return color.replace( 'r', 'x' ).replace( 'g', 'y' ).replace( 'b', 'z' ).replace( 'a', 'w' );
 
 	},
+	
+	colorToVector: function ( color ) {
+
+		return color.replace( /c/g, 'v3' );
+
+	},
 
 	getIncludes: function ( type, shader ) {
 
@@ -704,32 +709,44 @@ NodeBuilder.prototype = {
 
 	},
 
-	getFormatName: function ( format ) {
-
-		return format.replace( /c/g, 'v3' ).replace( /fv1/g, 'v1' ).replace( /iv1/g, 'i' );
-
-	},
-
-	isFormatMatrix: function ( format ) {
+	isTypeMatrix: function ( format ) {
 
 		return /^m/.test( format );
 
 	},
 
-	getFormatLength: function ( format ) {
+	getTypeLength: function ( type ) {
 
-		return parseInt( this.getFormatName( format ).substr( 1 ) );
+		if ( type === 'f' ) return 1;
+	
+		return parseInt( this.colorToVector( type ).substr( 1 ) );
 
 	},
 
-	getFormatFromLength: function ( len ) {
+	getTypeFromLength: function ( len ) {
 
-		if ( len === 1 ) return 'fv1';
+		if ( len === 1 ) return 'f';
 
 		return 'v' + len;
 
 	},
 	
+	findNode: function() {
+		
+		for(var i = 0; i < arguments.length; i++) {
+			
+			var nodeCandidate = arguments[i];
+			
+			if (nodeCandidate !== undefined && nodeCandidate.isNode) {
+				
+				return nodeCandidate;
+				
+			}
+			
+		}
+		
+	},
+	
 	resolve: function() {
 		
 		for(var i = 0; i < arguments.length; i++) {
@@ -788,31 +805,31 @@ NodeBuilder.prototype = {
 
 	format: function ( code, from, to ) {
 
-		var format = this.getFormatName( to + ' = ' + from );
+		var typeToType = this.colorToVector( to + ' = ' + from );
 
-		switch ( format ) {
+		switch ( typeToType ) {
 
-			case 'v1 = v2': return code + '.x';
-			case 'v1 = v3': return code + '.x';
-			case 'v1 = v4': return code + '.x';
-			case 'v1 = i': return 'float( ' + code + ' )';
+			case 'f = v2': return code + '.x';
+			case 'f = v3': return code + '.x';
+			case 'f = v4': return code + '.x';
+			case 'f = i': return 'float( ' + code + ' )';
 
-			case 'v2 = v1': return 'vec2( ' + code + ' )';
+			case 'v2 = f': return 'vec2( ' + code + ' )';
 			case 'v2 = v3': return code + '.xy';
 			case 'v2 = v4': return code + '.xy';
 			case 'v2 = i': return 'vec2( float( ' + code + ' ) )';
 
-			case 'v3 = v1': return 'vec3( ' + code + ' )';
+			case 'v3 = f': return 'vec3( ' + code + ' )';
 			case 'v3 = v2': return 'vec3( ' + code + ', 0.0 )';
 			case 'v3 = v4': return code + '.xyz';
 			case 'v3 = i': return 'vec2( float( ' + code + ' ) )';
 
-			case 'v4 = v1': return 'vec4( ' + code + ' )';
+			case 'v4 = f': return 'vec4( ' + code + ' )';
 			case 'v4 = v2': return 'vec4( ' + code + ', 0.0, 1.0 )';
 			case 'v4 = v3': return 'vec4( ' + code + ', 1.0 )';
 			case 'v4 = i': return 'vec4( float( ' + code + ' ) )';
 
-			case 'i = v1': return 'int( ' + code + ' )';
+			case 'i = f': return 'int( ' + code + ' )';
 			case 'i = v2': return 'int( ' + code + '.x )';
 			case 'i = v3': return 'int( ' + code + '.x )';
 			case 'i = v4': return 'int( ' + code + '.x )';
@@ -825,13 +842,13 @@ NodeBuilder.prototype = {
 
 	getTypeByFormat: function ( format ) {
 
-		return formatToType[ format ] || format;
+		return convertFormatToType[ format ] || format;
 
 	},
 	
 	getFormatByType: function ( type ) {
 
-		return typeToFormat[ type ] || type;
+		return convertTypeToFormat[ type ] || type;
 
 	},
 

+ 2 - 2
examples/js/nodes/effects/BlurNode.js

@@ -101,13 +101,13 @@ BlurNode.prototype.generate = function ( builder, output ) {
 		
 		if ( this.blurX ) {
 
-			blurCode.push( blurX + '( ' + this.value.build( builder, 'sampler2D' ) + ', ' + this.coord.build( builder, 'v2' ) + ', ' + this.horizontal.build( builder, 'fv1' ) + ' )' );
+			blurCode.push( blurX + '( ' + this.value.build( builder, 'sampler2D' ) + ', ' + this.coord.build( builder, 'v2' ) + ', ' + this.horizontal.build( builder, 'f' ) + ' )' );
 
 		}
 
 		if ( this.blurY ) {
 
-			blurCode.push( blurY + '( ' + this.value.build( builder, 'sampler2D' ) + ', ' + this.coord.build( builder, 'v2' ) + ', ' + this.vertical.build( builder, 'fv1' ) + ' )' );
+			blurCode.push( blurY + '( ' + this.value.build( builder, 'sampler2D' ) + ', ' + this.coord.build( builder, 'v2' ) + ', ' + this.vertical.build( builder, 'f' ) + ' )' );
 
 		}
 

+ 1 - 1
examples/js/nodes/effects/ColorAdjustmentNode.js

@@ -81,7 +81,7 @@ ColorAdjustmentNode.prototype.nodeType = "ColorAdjustment";
 ColorAdjustmentNode.prototype.generate = function ( builder, output ) {
 
 	var rgb = this.rgb.build( builder, 'v3' ),
-		adjustment = this.adjustment.build( builder, 'fv1' );
+		adjustment = this.adjustment.build( builder, 'f' );
 
 	switch ( this.method ) {
 

+ 1 - 1
examples/js/nodes/effects/LuminanceNode.js

@@ -8,7 +8,7 @@ import { FunctionNode } from '../core/FunctionNode.js';
 
 function LuminanceNode( rgb ) {
 
-	TempNode.call( this, 'fv1' );
+	TempNode.call( this, 'f' );
 
 	this.rgb = rgb;
 

+ 2 - 2
examples/js/nodes/inputs/CubeTextureNode.js

@@ -35,11 +35,11 @@ CubeTextureNode.prototype.generate = function ( builder, output ) {
 
 	var cubetex = this.getTexture( builder, output );
 	var coord = this.coord.build( builder, 'v3' );
-	var bias = this.bias ? this.bias.build( builder, 'fv1' ) : undefined;
+	var bias = this.bias ? this.bias.build( builder, 'f' ) : undefined;
 
 	if ( bias === undefined && builder.context.bias ) {
 
-		bias = new builder.context.bias( this ).build( builder, 'fv1' );
+		bias = new builder.context.bias( this ).build( builder, 'f' );
 
 	}
 

+ 1 - 1
examples/js/nodes/inputs/FloatNode.js

@@ -6,7 +6,7 @@ import { InputNode } from '../core/InputNode.js';
 
 function FloatNode( value ) {
 
-	InputNode.call( this, 'fv1' );
+	InputNode.call( this, 'f' );
 
 	this.value = value || 0;
 

+ 1 - 1
examples/js/nodes/inputs/IntNode.js

@@ -6,7 +6,7 @@ import { InputNode } from '../core/InputNode.js';
 
 function IntNode( value ) {
 
-	InputNode.call( this, 'iv1' );
+	InputNode.call( this, 'i' );
 
 	this.value = Math.floor( value || 0 );
 

+ 57 - 0
examples/js/nodes/inputs/PropertyNode.js

@@ -0,0 +1,57 @@
+/**
+ * @author sunag / http://www.sunag.com.br/
+ */
+
+import { InputNode } from '../core/InputNode.js';
+ 
+function PropertyNode( object, property, type ) {
+
+	InputNode.call( this, type );
+	
+	this.object = object;
+	this.property = property;
+
+};
+
+PropertyNode.prototype = Object.create( InputNode.prototype );
+PropertyNode.prototype.constructor = PropertyNode;
+PropertyNode.prototype.nodeType = "Property";
+
+Object.defineProperties( PropertyNode.prototype, {
+
+	value: {
+		
+		get: function () {
+
+			return this.object[ this.property ];
+
+		},
+		
+		set: function ( val ) { 
+		
+			this.object[ this.property ] = val;
+		
+		}
+		
+	}
+
+} );
+
+PropertyNode.prototype.toJSON = function ( meta ) {
+
+	var data = this.getJSONNode( meta );
+
+	if ( ! data ) {
+
+		data = this.createJSONNode( meta );
+
+		data.value = this.value;
+		data.property = this.property;
+
+	}
+
+	return data;
+
+};
+
+export { PropertyNode };

+ 4 - 4
examples/js/nodes/inputs/TextureNode.js

@@ -35,13 +35,13 @@ TextureNode.prototype.generate = function ( builder, output ) {
 
 	}
 
-	var tex = this.getTexture( builder, output );
-	var coord = this.coord.build( builder, this.project ? 'v4' : 'v2' );
-	var bias = this.bias ? this.bias.build( builder, 'fv1' ) : undefined;
+	var tex = this.getTexture( builder, output ),
+		coord = this.coord.build( builder, this.project ? 'v4' : 'v2' ),
+		bias = this.bias ? this.bias.build( builder, 'f' ) : undefined;
 
 	if ( bias == undefined && builder.context.bias ) {
 
-		bias = new builder.context.bias( this ).build( builder, 'fv1' );
+		bias = new builder.context.bias( this ).build( builder, 'f' );
 
 	}
 

+ 4 - 4
examples/js/nodes/materials/MeshStandardNodeMaterial.js

@@ -20,12 +20,12 @@ MeshStandardNodeMaterial.prototype = Object.create( NodeMaterial.prototype );
 MeshStandardNodeMaterial.prototype.constructor = MeshStandardNodeMaterial;
 
 NodeUtils.addShortcuts( MeshStandardNodeMaterial.prototype, 'properties', [
-	"color.value",
-	"roughness.value",
-	"metalness.value",
+	"color",
+	"roughness",
+	"metalness",
 	"map",
 	"normalMap",
-	"normalScale.value",
+	"normalScale",
 	"metalnessMap",
 	"roughnessMap",
 	"envMap"

+ 2 - 2
examples/js/nodes/materials/NodeMaterial.js

@@ -71,8 +71,9 @@ NodeMaterial.prototype.build = function ( params ) {
 	params = params || {};
 	params.dispose = params.dispose !== undefined ? params.dispose : true;
 
-	var builder = new NodeBuilder().setMaterial( this, params.renderer );
+	var builder = params.builder || new NodeBuilder();
 	
+	builder.setMaterial( this, params.renderer );
 	builder.build( this.vertex, this.fragment );
 	
 	this.vertexShader = builder.getCode('vertex');
@@ -81,7 +82,6 @@ NodeMaterial.prototype.build = function ( params ) {
 	this.defines = builder.defines;
 	this.uniforms = builder.uniforms;
 	this.extensions = builder.extensions;
-	this.nodes = builder.nodes;
 	this.updaters = builder.updaters;
 	
 	this.fog = builder.requires.fog;

+ 35 - 13
examples/js/nodes/materials/nodes/MeshStandardNode.js

@@ -3,9 +3,7 @@
  */
 
 import { StandardNode } from './StandardNode.js';
-import { FloatNode } from '../../inputs/FloatNode.js';
-import { ColorNode } from '../../inputs/ColorNode.js';
-import { Vector2Node } from '../../inputs/Vector2Node.js';
+import { PropertyNode } from '../../inputs/PropertyNode.js';
 import { OperatorNode } from '../../math/OperatorNode.js';
 import { SwitchNode } from '../../utils/SwitchNode.js';
 import { NormalMapNode } from '../../misc/NormalMapNode.js';
@@ -15,21 +13,29 @@ function MeshStandardNode() {
 	StandardNode.call( this );
 
 	this.properties = {
-		color: new ColorNode( 0xffffff ),
-		roughness: new FloatNode( 0.5 ),
-		metalness: new FloatNode( 0.5 ),
-		normalScale: new Vector2Node( 1, 1 )
+		color: new THREE.Color( 0xffffff ),
+		roughness: 0.5,
+		metalness: 0.5,
+		normalScale: new THREE.Vector2( 1, 1 )
+	};
+	
+	this.inputs = {
+		color: new PropertyNode( this.properties, 'color', 'c' ),
+		roughness: new PropertyNode( this.properties, 'roughness', 'f' ),
+		metalness: new PropertyNode( this.properties, 'metalness', 'f' ),
+		normalScale: new PropertyNode( this.properties, 'normalScale', 'v2' )
 	};
 
 };
 
 MeshStandardNode.prototype = Object.create( StandardNode.prototype );
 MeshStandardNode.prototype.constructor = MeshStandardNode;
+MeshStandardNode.prototype.nodeType = "MeshStandard";
 
 MeshStandardNode.prototype.build = function ( builder ) {
 
-	var material = builder.material,
-		props = this.properties;
+	var props = this.properties,
+		inputs = this.inputs;
 
 	if ( builder.isShader('fragment') ) {
 		
@@ -37,7 +43,7 @@ MeshStandardNode.prototype.build = function ( builder ) {
 		// * color
 		// * map
 		
-		var color = builder.resolve( props.color.value, props.color ),
+		var color = builder.findNode( props.color, inputs.color ),
 			map = builder.resolve( props.map );
 		
 		this.color = map ? new OperatorNode( color, map, OperatorNode.MUL ) : color;
@@ -46,7 +52,7 @@ MeshStandardNode.prototype.build = function ( builder ) {
 		// * roughness
 		// * roughnessMap
 		
-		var roughness = builder.resolve( props.roughness.value, props.roughness ),
+		var roughness = builder.findNode( props.roughness, inputs.roughness ),
 			roughnessMap = builder.resolve( props.roughnessMap );
 		
 		this.roughness = roughnessMap ? new OperatorNode( roughness, new SwitchNode( roughnessMap, "g" ), OperatorNode.MUL ) : roughness;
@@ -55,7 +61,7 @@ MeshStandardNode.prototype.build = function ( builder ) {
 		// * metalness
 		// * metalnessMap
 		
-		var metalness = builder.resolve( props.metalness.value, props.metalness ),
+		var metalness = builder.findNode( props.metalness, inputs.metalness ),
 			metalnessMap = builder.resolve( props.metalnessMap );
 		
 		this.metalness = metalnessMap ? new OperatorNode( metalness, new SwitchNode( metalnessMap, "b" ), OperatorNode.MUL ) : metalness;
@@ -67,7 +73,7 @@ MeshStandardNode.prototype.build = function ( builder ) {
 		if ( props.normalMap ) {
 			
 			this.normal = new NormalMapNode( builder.resolve( props.normalMap ) );
-			this.normal.scale = builder.resolve( props.normalScale );
+			this.normal.scale = builder.findNode( props.normalScale, inputs.normalScale )
 
 		}
 
@@ -84,4 +90,20 @@ MeshStandardNode.prototype.build = function ( builder ) {
 
 };
 
+MeshStandardNode.prototype.toJSON = function ( meta ) {
+
+	var data = this.getJSONNode( meta );
+
+	if ( ! data ) {
+
+		data = this.createJSONNode( meta );
+		
+		console.warn(".toJSON not implemented in", this);
+		
+	}
+
+	return data;
+
+};
+
 export { MeshStandardNode };

+ 4 - 4
examples/js/nodes/materials/nodes/PhongNode.js

@@ -125,22 +125,22 @@ PhongNode.prototype.build = function ( builder ) {
 
 		var color = this.color.buildCode( builder, 'c', { slot: 'color' } );
 		var specular = this.specular.buildCode( builder, 'c' );
-		var shininess = this.shininess.buildCode( builder, 'fv1' );
+		var shininess = this.shininess.buildCode( builder, 'f' );
 
-		var alpha = this.alpha ? this.alpha.buildCode( builder, 'fv1' ) : undefined;
+		var alpha = this.alpha ? this.alpha.buildCode( builder, 'f' ) : undefined;
 
 		var normal = this.normal ? this.normal.buildCode( builder, 'v3' ) : undefined;
 		var normalScale = this.normalScale && this.normal ? this.normalScale.buildCode( builder, 'v2' ) : undefined;
 
 		var light = this.light ? this.light.buildCode( builder, 'v3', { cache: 'light' } ) : undefined;
 
-		var ao = this.ao ? this.ao.buildCode( builder, 'fv1' ) : undefined;
+		var ao = this.ao ? this.ao.buildCode( builder, 'f' ) : undefined;
 		var ambient = this.ambient ? this.ambient.buildCode( builder, 'c' ) : undefined;
 		var shadow = this.shadow ? this.shadow.buildCode( builder, 'c' ) : undefined;
 		var emissive = this.emissive ? this.emissive.buildCode( builder, 'c', { slot: 'emissive' } ) : undefined;
 
 		var environment = this.environment ? this.environment.buildCode( builder, 'c', { slot: 'environment' } ) : undefined;
-		var environmentAlpha = this.environmentAlpha && this.environment ? this.environmentAlpha.buildCode( builder, 'fv1' ) : undefined;
+		var environmentAlpha = this.environmentAlpha && this.environment ? this.environmentAlpha.buildCode( builder, 'f' ) : undefined;
 
 		builder.requires.transparent = alpha != undefined;
 

+ 1 - 1
examples/js/nodes/materials/nodes/SpriteNode.js

@@ -117,7 +117,7 @@ SpriteNode.prototype.build = function ( builder ) {
 		// build code
 
 		var color = this.color.buildCode( builder, 'c', { slot: 'color' } );
-		var alpha = this.alpha ? this.alpha.buildCode( builder, 'fv1' ) : undefined;
+		var alpha = this.alpha ? this.alpha.buildCode( builder, 'f' ) : undefined;
 
 		output = [ color.code ];
 

+ 7 - 7
examples/js/nodes/materials/nodes/StandardNode.js

@@ -146,22 +146,22 @@ StandardNode.prototype.build = function ( builder ) {
 		// build code
 
 		var color = this.color.buildCode( builder, 'c', { slot: 'color', context: contextGammaOnly } );
-		var roughness = this.roughness.buildCode( builder, 'fv1' );
-		var metalness = this.metalness.buildCode( builder, 'fv1' );
+		var roughness = this.roughness.buildCode( builder, 'f' );
+		var metalness = this.metalness.buildCode( builder, 'f' );
 
-		var alpha = this.alpha ? this.alpha.buildCode( builder, 'fv1' ) : undefined;
+		var alpha = this.alpha ? this.alpha.buildCode( builder, 'f' ) : undefined;
 
 		var normal = this.normal ? this.normal.buildCode( builder, 'v3' ) : undefined;
 		var normalScale = this.normalScale && this.normal ? this.normalScale.buildCode( builder, 'v2' ) : undefined;
 
-		var clearCoat = this.clearCoat ? this.clearCoat.buildCode( builder, 'fv1' ) : undefined;
-		var clearCoatRoughness = this.clearCoatRoughness ? this.clearCoatRoughness.buildCode( builder, 'fv1' ) : undefined;
+		var clearCoat = this.clearCoat ? this.clearCoat.buildCode( builder, 'f' ) : undefined;
+		var clearCoatRoughness = this.clearCoatRoughness ? this.clearCoatRoughness.buildCode( builder, 'f' ) : undefined;
 
-		var reflectivity = this.reflectivity ? this.reflectivity.buildCode( builder, 'fv1' ) : undefined;
+		var reflectivity = this.reflectivity ? this.reflectivity.buildCode( builder, 'f' ) : undefined;
 
 		var light = this.light ? this.light.buildCode( builder, 'v3', { cache: 'light' } ) : undefined;
 
-		var ao = this.ao ? this.ao.buildCode( builder, 'fv1' ) : undefined;
+		var ao = this.ao ? this.ao.buildCode( builder, 'f' ) : undefined;
 		var ambient = this.ambient ? this.ambient.buildCode( builder, 'c' ) : undefined;
 		var shadow = this.shadow ? this.shadow.buildCode( builder, 'c' ) : undefined;
 		var emissive = this.emissive ? this.emissive.buildCode( builder, 'c', { slot: 'emissive' } ) : undefined;

+ 1 - 1
examples/js/nodes/math/Math1Node.js

@@ -49,7 +49,7 @@ Math1Node.prototype.getType = function ( builder ) {
 
 		case Math1Node.LENGTH:
 		
-			return 'fv1';
+			return 'f';
 
 	}
 

+ 6 - 6
examples/js/nodes/math/Math2Node.js

@@ -33,7 +33,7 @@ Math2Node.prototype.getInputType = function ( builder ) {
 
 	// use the greater length vector
 	
-	if ( builder.getFormatLength( this.b.getType( builder ) ) > builder.getFormatLength( this.a.getType( builder ) ) ) {
+	if ( builder.getTypeLength( this.b.getType( builder ) ) > builder.getTypeLength( this.a.getType( builder ) ) ) {
 
 		return this.b.getType( builder );
 
@@ -50,7 +50,7 @@ Math2Node.prototype.getType = function ( builder ) {
 		case Math2Node.DISTANCE:
 		case Math2Node.DOT:
 		
-			return 'fv1';
+			return 'f';
 
 		case Math2Node.CROSS:
 		
@@ -66,8 +66,8 @@ Math2Node.prototype.generate = function ( builder, output ) {
 
 	var a, b, 
 		type = this.getInputType( builder ),
-		al = builder.getFormatLength( this.a.getType( builder ) ),
-		bl = builder.getFormatLength( this.b.getType( builder ) );
+		al = builder.getTypeLength( this.a.getType( builder ) ),
+		bl = builder.getTypeLength( this.b.getType( builder ) );
 		
 	// optimzer
 
@@ -82,7 +82,7 @@ Math2Node.prototype.generate = function ( builder, output ) {
 
 		case Math2Node.STEP:
 		
-			a = this.a.build( builder, al === 1 ? 'fv1' : type );
+			a = this.a.build( builder, al === 1 ? 'f' : type );
 			b = this.b.build( builder, type );
 			
 			break;
@@ -92,7 +92,7 @@ Math2Node.prototype.generate = function ( builder, output ) {
 		case Math2Node.MOD:
 		
 			a = this.a.build( builder, type );
-			b = this.b.build( builder, bl === 1 ? 'fv1' : type );
+			b = this.b.build( builder, bl === 1 ? 'f' : type );
 			
 			break;
 

+ 8 - 8
examples/js/nodes/math/Math3Node.js

@@ -27,9 +27,9 @@ Math3Node.prototype.nodeType = "Math3";
 
 Math3Node.prototype.getType = function ( builder ) {
 
-	var a = builder.getFormatLength( this.a.getType( builder ) );
-	var b = builder.getFormatLength( this.b.getType( builder ) );
-	var c = builder.getFormatLength( this.c.getType( builder ) );
+	var a = builder.getTypeLength( this.a.getType( builder ) );
+	var b = builder.getTypeLength( this.b.getType( builder ) );
+	var c = builder.getTypeLength( this.c.getType( builder ) );
 
 	if ( a > b && a > c ) {
 		
@@ -48,9 +48,9 @@ Math3Node.prototype.getType = function ( builder ) {
 Math3Node.prototype.generate = function ( builder, output ) {
 
 	var a, b, c,
-		al = builder.getFormatLength( this.a.getType( builder ) ),
-		bl = builder.getFormatLength( this.b.getType( builder ) ),
-		cl = builder.getFormatLength( this.c.getType( builder ) ),
+		al = builder.getTypeLength( this.a.getType( builder ) ),
+		bl = builder.getTypeLength( this.b.getType( builder ) ),
+		cl = builder.getTypeLength( this.c.getType( builder ) ),
 		type = this.getType( builder );
 
 	// optimzer
@@ -61,7 +61,7 @@ Math3Node.prototype.generate = function ( builder, output ) {
 		
 			a = this.a.build( builder, type );
 			b = this.b.build( builder, type );
-			c = this.c.build( builder, 'fv1' );
+			c = this.c.build( builder, 'f' );
 			
 			break;
 
@@ -69,7 +69,7 @@ Math3Node.prototype.generate = function ( builder, output ) {
 		
 			a = this.a.build( builder, type );
 			b = this.b.build( builder, type );
-			c = this.c.build( builder, cl === 1 ? 'fv1' : type );
+			c = this.c.build( builder, cl === 1 ? 'f' : type );
 			
 			break;
 

+ 2 - 2
examples/js/nodes/math/OperatorNode.js

@@ -28,11 +28,11 @@ OperatorNode.prototype.getType = function ( builder ) {
 	var a = this.a.getType( builder ),
 		b = this.b.getType( builder );
 
-	if ( builder.isFormatMatrix( a ) ) {
+	if ( builder.isTypeMatrix( a ) ) {
 
 		return 'v4';
 
-	} else if ( builder.getFormatLength( b ) > builder.getFormatLength( a ) ) {
+	} else if ( builder.getTypeLength( b ) > builder.getTypeLength( a ) ) {
 
 		// use the greater length vector
 

+ 2 - 2
examples/js/nodes/misc/BumpMapNode.js

@@ -107,7 +107,7 @@ BumpMapNode.prototype.generate = function ( builder, output ) {
 		
 			return builder.format( bumpToNormal + '( ' + this.value.build( builder, 'sampler2D' ) + ', ' +
 				this.value.coord.build( builder, 'v2' ) + ', ' +
-				this.scale.build( builder, 'fv1' ) + ' )', this.getType( builder ), output );
+				this.scale.build( builder, 'f' ) + ' )', this.getType( builder ), output );
 				
 		} else {
 			
@@ -119,7 +119,7 @@ BumpMapNode.prototype.generate = function ( builder, output ) {
 		
 			var derivativeHeightCode = derivativeHeight + '( ' + this.value.build( builder, 'sampler2D' ) + ', ' +
 				this.value.coord.build( builder, 'v2' ) + ', ' +
-				this.scale.build( builder, 'fv1' ) + ' )';
+				this.scale.build( builder, 'f' ) + ' )';
 
 			return builder.format( perturbNormalArb + '( -' + this.position.build( builder, 'v3' ) + ', ' +
 				this.normal.build( builder, 'v3' ) + ', ' +

+ 0 - 2
examples/js/nodes/misc/NormalMapNode.js

@@ -64,8 +64,6 @@ NormalMapNode.prototype.nodeType = "NormalMap";
 
 NormalMapNode.prototype.generate = function ( builder, output ) {
 
-	var material = builder.material;
-
 	if ( builder.isShader( 'fragment' ) ) {
 
 		var perturbNormal2Arb = builder.include( NormalMapNode.Nodes.perturbNormal2Arb );

+ 2 - 2
examples/js/nodes/misc/TextureCubeUVNode.js

@@ -175,8 +175,8 @@ TextureCubeUVNode.prototype.generate = function ( builder, output ) {
 		var textureCubeUV = builder.include( TextureCubeUVNode.Nodes.textureCubeUV );
 	
 		return builder.format( textureCubeUV + '( ' + this.coord.build( builder, 'v3' ) + ', ' +
-			this.blinnExponentToRoughness.build( builder, 'fv1' ) + ', ' +
-			this.textureSize.build( builder, 'fv1' ) + ' )', this.getType( builder ), output );
+			this.blinnExponentToRoughness.build( builder, 'f' ) + ', ' +
+			this.textureSize.build( builder, 'f' ) + ' )', this.getType( builder ), output );
 			
 	} else {
 

+ 1 - 1
examples/js/nodes/procedural/NoiseNode.js

@@ -8,7 +8,7 @@ import { UVNode } from '../accessors/UVNode.js';
 
 function NoiseNode( coord ) {
 
-	TempNode.call( this, 'fv1' );
+	TempNode.call( this, 'f' );
 
 	this.coord = coord || new UVNode();
 

+ 2 - 2
examples/js/nodes/utils/BypassNode.js

@@ -25,7 +25,7 @@ BypassNode.prototype.getType = function ( builder ) {
 		
 	} else if (builder.isShader( 'fragment' )) {
 		
-		return 'fv1';
+		return 'f';
 		
 	}
 	
@@ -49,7 +49,7 @@ BypassNode.prototype.generate = function ( builder, output ) {
 		
 	} else {
 		
-		return this.value ? this.value.build( builder, output ) : builder.format( '0.0', 'fv1', output );
+		return this.value ? this.value.build( builder, output ) : builder.format( '0.0', 'f', output );
 		
 	}
 

+ 4 - 4
examples/js/nodes/utils/JoinNode.js

@@ -9,7 +9,7 @@ var inputs = NodeUtils.elements;
  
 function JoinNode( x, y, z, w ) {
 
-	TempNode.call( this, 'fv1' );
+	TempNode.call( this, 'f' );
 
 	this.x = x;
 	this.y = y;
@@ -44,7 +44,7 @@ JoinNode.prototype.getNumElements = function () {
 
 JoinNode.prototype.getType = function ( builder ) {
 
-	return builder.getFormatFromLength( this.getNumElements() );
+	return builder.getTypeFromLength( this.getNumElements() );
 
 };
 
@@ -58,7 +58,7 @@ JoinNode.prototype.generate = function ( builder, output ) {
 
 		var elm = this[ inputs[ i ] ];
 
-		outputs.push( elm ? elm.build( builder, 'fv1' ) : '0.0' );
+		outputs.push( elm ? elm.build( builder, 'f' ) : '0.0' );
 
 	}
 
@@ -70,7 +70,7 @@ JoinNode.prototype.generate = function ( builder, output ) {
 
 JoinNode.prototype.copy = function ( source ) {
 			
-	GLNode.prototype.copy.call( this, source );
+	TempNode.prototype.copy.call( this, source );
 	
 	for ( var prop in source.inputs ) {
 

+ 3 - 3
examples/js/nodes/utils/SwitchNode.js

@@ -19,7 +19,7 @@ SwitchNode.prototype.nodeType = "Switch";
 
 SwitchNode.prototype.getType = function ( builder ) {
 
-	return builder.getFormatFromLength( this.components.length );
+	return builder.getTypeFromLength( this.components.length );
 
 };
 
@@ -27,14 +27,14 @@ SwitchNode.prototype.generate = function ( builder, output ) {
 
 	var type = this.node.getType( builder ),
 		node = this.node.build( builder, type ),
-		inputLength = builder.getFormatLength( type ) - 1;
+		inputLength = builder.getTypeLength( type ) - 1;
 
 	if ( inputLength > 0 ) {
 
 		// get max length
 
 		var outputLength = 0,
-			components = builder.colorToVector( this.components );
+			components = builder.colorToVectorProperties( this.components );
 
 		var i, len = components.length;
 

File diff suppressed because it is too large
+ 0 - 0
examples/nodes/caustic.json


File diff suppressed because it is too large
+ 0 - 0
examples/nodes/displace.json


File diff suppressed because it is too large
+ 0 - 0
examples/nodes/wave.json


File diff suppressed because it is too large
+ 0 - 0
examples/nodes/xray.json


+ 18 - 10
examples/webgl_materials_nodes.html

@@ -31,7 +31,7 @@
 		<div id="container"></div>
 		<div id="info">
 			<a href="http://threejs.org" target="_blank" rel="noopener">three.js</a> - Node-Based Material</br>
-			<a id="serialize" onclick="toggleSerialize()" href="javascript:void(0);">Serialize and apply</a>
+			<a id="serialize" href="javascript:void(0);">Serialize and apply</a>
 		</div>
 
 		<script src="../build/three.js"></script>
@@ -2369,14 +2369,14 @@
 
 		}
 
-		function toggleSerialize() {
+		document.getElementById( 'serialize' ).addEventListener('click', function () {
 
 			if ( serialized ) reset();
 			else serialize();
 
 			serialized = ! serialized;
 
-		}
+		});
 
 		function reset() {
 
@@ -2391,21 +2391,29 @@
 
 		function serialize() {
 
-			var json = mesh.material.toJSON(),
-				jsonStr = JSON.stringify( json );
+			var json = mesh.material.toJSON();
 				
-			// replace uuid to url (facilitates the load of textures using url otherside uuid)
-			// example:
+			// replace uuid to url (facilitates the load of textures using url otherside uuid) e.g:
 
-			//THREE.NodeMaterialLoaderUtils.replaceUUID( json, getTexture( "cloud" ), "cloud" );
+			var cloud = getTexture( "cloud" );
+			
+			THREE.NodeMaterialLoaderUtils.replaceUUID( json, cloud, "cloud" );
 
+			library[ "cloud" ] = cloud;
+			
+			// --
+			
+			var jsonStr = JSON.stringify( json );
+			
+			console.log( jsonStr );
+			
 			var loader = new THREE.NodeMaterialLoader( null, library ),
 				material = loader.parse( json );
 			
+			mesh.material.dispose();
+			
 			mesh.material = material;
 			
-			//console.log( jsonStr );
-
 			// gui
 
 			var div = document.getElementById( 'serialize' );

+ 3 - 3
examples/webgl_sprites_nodes.html

@@ -187,9 +187,9 @@
 			//	Test serialization
 			//
 
-			//spriteToJSON( sprite1 );
-			//spriteToJSON( sprite2 );
-			//spriteToJSON( sprite3 );
+			spriteToJSON( sprite1 );
+			spriteToJSON( sprite2 );
+			spriteToJSON( sprite3 );
 
 			//
 			// Events

Some files were not shown because too many files changed in this diff