Exemplo n.º 1
0
// if this function changes, please also check SupportsReShading, PreShade and PostShade
// end - ke/mjm - 03.16.00 - merge reshading code
// [attilas|29.5.2000] if this function changes, please also check EvalColorStdChannel
void CompositeMat::Shade(ShadeContext& sc)
{
	Mtl *sm1 = NULL;
	int id =0; 
//	float gamount;
	if (gbufID){
		sc.SetGBufferID(gbufID);
		id = gbufID;
	}

	Interval iv;
	int first = 1;
	ShadeOutput out1;
	int nEles = sc.NRenderElements();
	
	for (int i = 0; i < MAX_NUM_MTLS; i++){
		BOOL enabled;
		float amount;
		if (i==0) enabled = 1;
		else pblock2->GetValue(compmat_map_on,sc.CurTime(),enabled,iv,i-1);
		if (enabled){
			pblock2->GetValue(compmat_mtls,sc.CurTime(),sm1,iv,i);
			if (sm1 != NULL){
				if (i==0) amount = 100.f;
				else pblock2->GetValue(compmat_amount,sc.CurTime(),amount,iv,i-1);
				amount = amount*0.01f;
				int type;
				if (i==0) type = 2;
				else pblock2->GetValue(compmat_type,sc.CurTime(),type,iv,i-1);

				if (first ==1){	// first material
					first = 0;
					sm1->Shade(sc); // sc.out already reset for first
					out1 = sc.out;
					if (type == 0){
						out1.t.r += 1.0f-amount;
						out1.t.g += 1.0f-amount;
						out1.t.b += 1.0f-amount;
						out1.c *= amount;
						out1.t.ClampMinMax();

						// render elements
						for( int i = 0; i < nEles; ++i )
							out1.elementVals[i] *= amount;

					}
					out1.ior *= amount;

//					gamount = 1.0f-(out1.t.r + out1.t.g + out1.t.b)/3.0f;
				
				} else {	// not first material
//					pblock2->GetValue(compmat_mtls,sc.CurTime(),sm2,iv,i);
//					sc.out.ior = s*a.ior + f*ior;
//					if (f<=0.5f) gbufId = a.gbufId;
					sc.ResetOutput();
					sm1->Shade(sc);
					ShadeOutput out2 = sc.out;

					if (type == 0){  // additive
						out2.t.r += 1.0f-amount;
						out2.t.g += 1.0f-amount;
						out2.t.b += 1.0f-amount;
						out2.c *= amount;
						out2.t.ClampMinMax();

						out2.ior *= amount;

						float f1 = 1.0f-(out1.t.r + out1.t.g + out1.t.b)/3.0f; 
						float f2 = 1.0f-(out2.t.r + out2.t.g + out2.t.b)/3.0f; 

						out1.c =  out1.c *(1.0f-f2) + out2.c * (f1); 
						out1.t =  out1.t- (1.0f-out2.t);
						out1.ior = out1.ior + out2.ior;
//						if (f2 > gamount) {
//							gamount = f2;
//							out1.gbufId = out1.gbufId;//?? ke 6.13.00
//						}
						out1.t.ClampMinMax();
			
						// render elements
						for( int i = 0; i < nEles; ++i )
							out1.elementVals[i] = out1.elementVals[i] * (1.0f-f2) + out2.elementVals[i] * f1;
				
					} else if (type == 1) { // subtractive
						//NB: as of 6.13.00 this is SAME as additive case
						out2.t.r += 1.0f-amount;
						out2.t.g += 1.0f-amount;
						out2.t.b += 1.0f-amount;
						out2.c *= amount;

						out2.t.ClampMinMax();

						out2.ior *= amount;

						float f1 = 1.0f-(out1.t.r + out1.t.g + out1.t.b)/3.0f; 
						float f2 = 1.0f-(out2.t.r + out2.t.g + out2.t.b)/3.0f; 

						out1.c =  out1.c *(1.0f-f2) - out2.c * f1; 
						out1.t =  out1.t- (1.0f-out2.t);
						out1.ior = out1.ior + out2.ior;
//						if (f2 > gamount){
//							gamount = f2;
//							out1.gbufId = out1.gbufId;	//?? ke 6.13.00
//						}
						out1.t.ClampMinMax();

						// render elements
						for( int i = 0; i < nEles; ++i )
							out1.elementVals[i] = out1.elementVals[i] * (1.0f-f2) + out2.elementVals[i] * f1;
					
					} else { //mix

						// mixIn handles render elements
						out1.MixIn(out2,1.0f-amount);
					}
				}// end, not first mtl
			} // end, sm1 not null
		}// end, enabled
	} // end, for each material

	sc.out = out1;
}
Exemplo n.º 2
0
void M3Mat::PostShade(ShadeContext& sc, IReshadeFragment* pFrag, int& nextTexIndex, IllumParams* ip)
{
	int i; 
	IReshading* pReshading;

	TimeValue t = sc.CurTime();
	Interval valid = FOREVER;

	pblockMat->GetValue(100,t,i,FOREVER);

	Mtl *sm1 = mTex[100];
	float total(0.0f);
	ShadeOutput	sDatabase[100];
	float u[100];
	ShadeOutput sFinal; 

	// handle no base mat
	if(!sm1) 
	{
		sc.ResetOutput();
		sc.out.c = black;
		sc.out.t = black;
		return;
	}

	if(i==0 || (i==1 && inRender) )
	{
		for( i=0; i<100; i++)
		{
			pblockMat->GetValue(i,t,u[i],valid);
			u[i] /= 100.0f;

			if( mTex[i]!=NULL && u[i]!=0 && mapOn[i] )
			{
				Mtl *comb = mTex[i];
				pReshading = (IReshading*)(comb->GetInterface(IID_IReshading));
				if( pReshading ) 
					pReshading->PostShade(sc, pFrag, nextTexIndex, ip );
				sDatabase[i] = sc.out;
				sc.ResetOutput();
				total += u[i];
			}
		}

		sc.ResetOutput();
		pReshading = (IReshading*)(sm1->GetInterface(IID_IReshading));
		if( pReshading ) 
			pReshading->PostShade(sc, pFrag, nextTexIndex, ip );

		sFinal.c = black;
		sFinal.t = black;
		sFinal.ior = 0.0f;

		for( i=0;i<100;i++)
		{
			if(mTex[i]!=NULL && u[i]!=0 && mapOn[i])
			{
				sc.out.flags |= sDatabase[i].flags;
			
				if(total>1.0f){
					sFinal.c += u[i]/total * sDatabase[i].c;
					sFinal.t += u[i]/total * sDatabase[i].t;
					sFinal.ior += u[i]/total * sDatabase[i].ior;
				}
				else{
					sFinal.c += u[i] * sDatabase[i].c;
					sFinal.t += u[i] * sDatabase[i].t;
					sFinal.ior += u[i] * sDatabase[i].ior;
				}
			}
		}
		if(total) {
			sc.out.MixIn(sFinal, 1.0f-total);
		}
		
	}
	else {
		pReshading = (IReshading*)(sm1->GetInterface(IID_IReshading));
		if( pReshading ) 
			pReshading->PostShade(sc, pFrag, nextTexIndex, ip );
	}
}
Exemplo n.º 3
0
void CompositeMat::PostShade(ShadeContext& sc, IReshadeFragment* pFrag, int& nextTexIndex, IllumParams* )
{
	int i(0), type(2);
	Mtl* submtl = NULL;
	BOOL enabled(TRUE);
	ShadeOutput out1, out2;
	float amount(100.0f); // , gamount(0.0f);

	char texLengths[12];

	int* pI = (int*)&texLengths[0];
	pI[0] = pFrag->GetIntChannel(nextTexIndex++);
	pI[1] = pFrag->GetIntChannel(nextTexIndex++);
	pI[2] = pFrag->GetIntChannel(nextTexIndex++);



	// postshade any submaterials
	for ( i=0; i<MAX_NUM_MTLS; i++)
	{
		if( i>0 )
			pblock2->GetValue(compmat_map_on, sc.CurTime(), enabled, FOREVER, i-1);
		else 
			enabled = TRUE;

		pblock2->GetValue(compmat_mtls, sc.CurTime(), submtl, FOREVER, i);
		if ( enabled && submtl ){
			if( i > 0 ){
				pblock2->GetValue(compmat_amount, sc.CurTime(), amount, FOREVER, i-1);
				pblock2->GetValue(compmat_type, sc.CurTime(), type, FOREVER, i-1);
			}
			amount = amount * 0.01f;
			sc.ResetOutput();
			IReshading* pReshading = (IReshading*)(submtl->GetInterface(IID_IReshading));
			if( pReshading ) 
				pReshading->PostShade(sc, pFrag, nextTexIndex);
			
			// first check for base material
			if( i > 0 ) {
				// not base material, composite the next material
				out2 = sc.out;
					
				if (type == 0) // additive
				{
					out2.t.r += 1.0f-amount;
					out2.t.g += 1.0f-amount;
					out2.t.b += 1.0f-amount;
					out2.c *= amount;
					out2.t.ClampMinMax();
					out2.ior *= amount;

					float f1 = 1.0f - (out1.t.r + out1.t.g + out1.t.b) / 3.0f; 
					float f2 = 1.0f - (out2.t.r + out2.t.g + out2.t.b) / 3.0f; 
					out1.c = out1.c * (1.0f-f2) + out2.c * f1;
					out1.t = out1.t - (1.0f-out2.t);
					out1.ior = out1.ior + out2.ior;
					out1.t.ClampMinMax();
				}
				else if (type == 1) // subtractive
				{
					out2.t.r += 1.0f-amount;
					out2.t.g += 1.0f-amount;
					out2.t.b += 1.0f-amount;
					out2.c *= amount;
					out2.t.ClampMinMax();
					out2.ior *= amount;

					float f1 = 1.0f - (out1.t.r + out1.t.g + out1.t.b) / 3.0f;
					float f2 = 1.0f - (out2.t.r + out2.t.g + out2.t.b) / 3.0f;

					out1.c = out1.c * (1.0f-f2) - out2.c * f1;
					out1.t = out1.t - (1.0f-out2.t);
					out1.ior = out1.ior + out2.ior;

					out1.t.ClampMinMax();
				}
				else //mix
				{
					out1.MixIn(out2, 1.0f-amount);
				}
			}// end, not base mtl
			else {
				// base material.
				out1 = sc.out;
				out1.ior *= amount;
			}

		}// end, if has submtl & enabled
		else {
			nextTexIndex += texLengths[i];
		}

	}// end, for each mtl

	sc.out = out1;
}
Exemplo n.º 4
0
void M3Mat::Shade(ShadeContext& sc) {
	int i; 

	TimeValue t = sc.CurTime();
	Interval valid = FOREVER;

	pblockMat->GetValue(100,t,i,FOREVER);

	Mtl *sm1 = mTex[100];
	float total(0.0f);
	ShadeOutput sFinal( sc.out.nElements ); // get nElements correctly
	ShadeOutput	sDatabase[100];
//	for(  i = 0; i < 100; ++i )
//		sDatabase[i] = sFinal;	

	float u[100];

	// handle no base mat
	if(!sm1) 
	{
		sc.ResetOutput();
		sc.out.c = black;
		sc.out.t = black;
		return;
	}

	if(i==0||(i==1&&inRender))
	{
		for( i=0;i<100;i++)
		{
			pblockMat->GetValue(i,t,u[i],valid);
			u[i] /= 100.0f;

			if(mTex[i]!=NULL&&u[i]!=0&&mapOn[i])
			{
				Mtl *comb = mTex[i];
				comb->Shade(sc);
				sDatabase[i] = sc.out;
				sc.ResetOutput();
				total += u[i];
			}
		}

		sc.ResetOutput();
		sm1->Shade(sc);
		sFinal.c = black;
		sFinal.t = black;
		sFinal.ior = 0.0f;

		for( i=0;i<100;i++)
		{
			if(mTex[i]!=NULL&&u[i]!=0&&mapOn[i])
			{
				sc.out.flags |= sDatabase[i].flags;
			
				if(total>1.0f){
					sFinal.c += u[i]/total * sDatabase[i].c;
					sFinal.t += u[i]/total * sDatabase[i].t;
					sFinal.ior += u[i]/total * sDatabase[i].ior;
				}
				else{
					sFinal.c += u[i] * sDatabase[i].c;
					sFinal.t += u[i] * sDatabase[i].t;
					sFinal.ior += u[i] * sDatabase[i].ior;
				}
			}
		}
		if(total) {
			sc.out.MixIn(sFinal, 1.0f-total);
		}
		
	}
	else {
		sm1->Shade(sc);
	}
}