瀏覽代碼

changed to use less Reflect calls, fix AlphaMultiply shader add/remove, and correct pass name sync

Nicolas Cannasse 5 年之前
父節點
當前提交
3a6b19e055
共有 1 個文件被更改,包括 42 次插入40 次删除
  1. 42 40
      h3d/mat/PbrMaterial.hx

+ 42 - 40
h3d/mat/PbrMaterial.hx

@@ -61,7 +61,7 @@ typedef PbrProps = {
 	@:optional var alphaKill : Bool;
 	@:optional var emissive : Float;
 	@:optional var parallax : Float;
-	
+
 	var enableStencil : Bool;
 	@:optional var stencilCompare : PbrStencilCompare;
 	@:optional var stencilPassOp : PbrStencilOp;
@@ -80,6 +80,22 @@ class PbrMaterial extends Material {
 		if( mainPass != null ) {
 			mainPass.setBlendMode(b);
 			mainPass.depthWrite = b == None;
+			var am = mainPass.getShader(h3d.shader.pbr.AlphaMultiply);
+			if( b == AlphaMultiply ) {
+				if( am == null ) {
+					am = new h3d.shader.pbr.AlphaMultiply();
+					am.setPriority(-1);
+					mainPass.addShader(am);
+				}
+			} else if( am != null )
+				mainPass.removeShader(am);
+			if( props == null || (props:PbrProps).mode == PBR ) {
+				mainPass.setPassName(switch( b ) {
+				case Add, AlphaAdd, SoftAdd: "additive";
+				case Alpha, AlphaMultiply: "alpha";
+				default: "default";
+				});
+			}
 		}
 		return this.blendMode = b;
 	}
@@ -141,7 +157,10 @@ class PbrMaterial extends Material {
 		var props : PbrProps = getDefaultProps();
 		props.blend = switch( blendMode ) {
 			case None: None;
-			case Alpha: Alpha;
+			case Alpha:
+				// in PBR, Alpha blending is not correct - use alphaKill by default
+				props.alphaKill = true;
+				None;
 			case Add: Add;
 			case Multiply: Multiply;
 			case AlphaMultiply: AlphaMultiply;
@@ -170,9 +189,9 @@ class PbrMaterial extends Material {
 		mainPass.removeShader(mainPass.getShader(h3d.shader.Emissive));
 		mainPass.removeShader(mainPass.getShader(h3d.shader.pbr.GammaCorrect));
 		// Backward compatibility
-		if( !Reflect.hasField(props, "depthTest") ) Reflect.setField(props, "depthTest", Less);
-		if( !Reflect.hasField(props, "colorMask") ) Reflect.setField(props, "colorMask", 1 << 0 | 1 << 1 | 1 << 2 | 1 << 3);
-		if( !Reflect.hasField(props, "enableStencil") ) Reflect.setField(props, "enableStencil", false);
+		if( props.depthTest == null ) props.depthTest = Less;
+		if( (props:Dynamic).colorMask == null ) props.colorMask = 15;
+		if( (props:Dynamic).enableStencil == null ) props.enableStencil = false;
 		// Remove unused fields
 		if( props.emissive == 0 )
 			Reflect.deleteField(props,"emissive");
@@ -194,7 +213,7 @@ class PbrMaterial extends Material {
 		// Preset
 		switch( props.mode ) {
 		case PBR:
-			mainPass.setPassName("default");
+			// pass name set below (in set_blendMode)
 		case BeforeTonemapping:
 			mainPass.setPassName("beforeTonemapping");
 			if( props.emissive > 0 ) {
@@ -235,29 +254,12 @@ class PbrMaterial extends Material {
 
 		// Blend modes
 		switch( props.blend ) {
-		case None:
-			mainPass.setBlendMode(None);
-			mainPass.depthWrite = true;
-		case Alpha:
-			mainPass.setBlendMode(Alpha);
-			mainPass.depthWrite = false;
-		case Add:
-			mainPass.setBlendMode(Add);
-			mainPass.depthWrite = false;
-		case AlphaAdd:
-			mainPass.setBlendMode(AlphaAdd);
-			mainPass.depthWrite = false;
-		case Multiply:
-			mainPass.setBlendMode(Multiply);
-			mainPass.depthWrite = false;
-		case AlphaMultiply:
-			if( mainPass.getShader(h3d.shader.pbr.AlphaMultiply) == null ) {
-				var s = new h3d.shader.pbr.AlphaMultiply();
-				s.setPriority(-1);
-				mainPass.addShader(s);
-			}
-			mainPass.setBlendMode(AlphaMultiply);
-			mainPass.depthWrite = false;
+		case None: this.blendMode = None;
+		case Alpha: this.blendMode = Alpha;
+		case Add: this.blendMode = Add;
+		case AlphaAdd: this.blendMode = AlphaAdd;
+		case Multiply: this.blendMode = Multiply;
+		case AlphaMultiply: this.blendMode = AlphaMultiply;
 		}
 
 		// Enable/Disable AlphaKill
@@ -317,9 +319,9 @@ class PbrMaterial extends Material {
 
 	function setColorMask() {
 		var props : PbrProps = props;
-		mainPass.setColorMask(	props.colorMask & (1<<0) > 0 ? true : false, 
-								props.colorMask & (1<<1) > 0 ? true : false, 
-								props.colorMask & (1<<2) > 0 ? true : false, 
+		mainPass.setColorMask(	props.colorMask & (1<<0) > 0 ? true : false,
+								props.colorMask & (1<<1) > 0 ? true : false,
+								props.colorMask & (1<<2) > 0 ? true : false,
 								props.colorMask & (1<<3) > 0 ? true : false);
 	}
 
@@ -327,13 +329,13 @@ class PbrMaterial extends Material {
 		var props : PbrProps = props;
 		if( props.enableStencil ) {
 
-			if( !Reflect.hasField(props, "stencilFailOp") ) 	Reflect.setField(props, "stencilFailOp", Keep);
-			if( !Reflect.hasField(props, "depthFailOp") ) 		Reflect.setField(props, "depthFailOp", Keep);
-			if( !Reflect.hasField(props, "stencilPassOp") ) 	Reflect.setField(props, "stencilPassOp", Replace);
-			if( !Reflect.hasField(props, "stencilCompare") ) 	Reflect.setField(props, "stencilCompare", Always);
-			if( !Reflect.hasField(props, "stencilValue") ) 		Reflect.setField(props, "stencilValue", 0);
-			if( !Reflect.hasField(props, "stencilReadMask") ) 	Reflect.setField(props, "stencilReadMask", 0);
-			if( !Reflect.hasField(props, "stencilWriteMask") ) 	Reflect.setField(props, "stencilWriteMask", 0);
+			if( props.stencilFailOp == null ) props.stencilFailOp = Keep;
+			if( props.depthFailOp == null ) props.depthFailOp = Keep;
+			if( props.stencilPassOp == null ) props.stencilPassOp = Replace;
+			if( props.stencilCompare == null ) props.stencilCompare = Always;
+			if( props.stencilValue == null ) props.stencilValue = 0;
+			if( props.stencilReadMask == null ) props.stencilReadMask = 0;
+			if( props.stencilWriteMask == null ) props.stencilWriteMask = 0;
 
 			inline function getStencilOp( op : PbrStencilOp ) : Data.StencilOp {
 				return switch op {
@@ -418,7 +420,7 @@ class PbrMaterial extends Material {
 	override function clone( ?m : BaseMaterial ) : BaseMaterial {
 		var m = m == null ? new PbrMaterial() : cast m;
 		super.clone(m);
-			return m;
+		return m;
 	}
 
 	#if editor