cvlights.cpp

来自「Windows上的MUD客户端程序」· C++ 代码 · 共 606 行 · 第 1/2 页

CPP
606
字号
		ChNrValue lin = ChNrLightGetLinearAttenuation(m_light);
		ChNrValue quad = ChNrLightGetQuadraticAttenuation(m_light);
		#endif
		ChNrFrameAddLight(m_frame, m_light);
		D3DRelease(m_light);

	}
};

#endif


ChQvDirectionalLightInstance::ChQvDirectionalLightInstance()
{ }

#if defined(CH_USE_3DR)
bool ChQvDirectionalLightInstance::traverse(ChRenderContext *pContext)
{ 
	bool boolSuccess = false;
	int iLightNum = pContext->GetNextLight();	  
	G3dHandle_t hGC = pContext->GetGC();
  	QvDirectionalLight *pNode = (QvDirectionalLight *)m_pNode;

	// We don't have directional lights in 3dr, so put a spot light very far away,
	// and leave it wide open angle-wise, with no attenuation
	if(iLightNum >= 0)
	{
		boolSuccess = true;
		Float_t		dimmer = 	int(pNode->on.value) ? 1. : 0.;
		float fIntensity = pNode->intensity.value;
		fIntensity = min(fIntensity, 1.);
		fIntensity = max(fIntensity, 0.);
		if(dimmer > 0. && fIntensity > 0.)
		{
			pContext->TurnOnALight();
			ColorFA_t	diffuse;		Qv2Native(pNode->color, diffuse);
			ColorF_t	specular;		Qv2Native(pNode->color,specular) ;

			// Transform light from model (vrml) to world coords for 3dr

			GxVec3f	dir;
			Qv2Gx(pNode->direction, dir);
			dir = Transform(dir);

			Float_t		infinity	=	1.e6;	// close enough (or far enough) for us
			PointFW_t	loc3dr;
			PointF_t	dir3dr;
			CopyPoint(dir, dir3dr);
			loc3dr.x = -dir.x() * infinity;
			loc3dr.y = -dir.y() * infinity;
			loc3dr.z = -dir.z() * infinity;
			loc3dr.w = 0.;				 // infinite light
	 		ColorF_t	ambient = {0.,0.,0.};
												 
			Float_t exponent	= 0.00;	   // no fall off
			Float_t angle		= 1.57;	   // leave the barn doors open
			Float_t attena 		= 1.00;	   // no attenuation
			Float_t attenb 		= 0.00;
			Float_t attenc 		= 0.00;

			specular.r *= fIntensity;
			specular.g *= fIntensity;
			specular.b *= fIntensity;

			diffuse.r *= fIntensity;
			diffuse.g *= fIntensity;
			diffuse.b *= fIntensity;


			G3dSetLight( hGC, iLightNum, G3DL_DIMMER,   	(Float_t *)&dimmer );			
			G3dSetLight( hGC, iLightNum, G3DL_AMBIENT, 		(Float_t *)&ambient );			
			G3dSetLight( hGC, iLightNum, G3DL_DIFFUSE,  	(Float_t *)&diffuse );			
			G3dSetLight( hGC, iLightNum, G3DL_SPECULAR, 	(Float_t *)&specular );			
			G3dSetLight( hGC, iLightNum, G3DL_DIRECTION,	(Float_t *)&dir3dr );			
			G3dSetLight( hGC, iLightNum, G3DL_LOCATION,		(Float_t *)&loc3dr );
			G3dSetLight( hGC, iLightNum, G3DL_ATTENA,  		(Float_t *)&attena );
			G3dSetLight( hGC, iLightNum, G3DL_ATTENB,  		(Float_t *)&attenb );
			G3dSetLight( hGC, iLightNum, G3DL_ATTENC,  		(Float_t *)&attenc );
			G3dSetLight( hGC, iLightNum, G3DL_SPOT_EXP, 	(Float_t *)&exponent );
			G3dSetLight( hGC, iLightNum, G3DL_SPOT_ANGLE,	(Float_t *)&angle );
		}
	}			
	return boolSuccess;
}
#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
void ChQvDirectionalLightInstance::Build(ChRenderContext *pRC)
{
  	QvDirectionalLight *pNode = (QvDirectionalLight *)m_pNode;
	float fIntensity = peg(pNode->intensity.value, float(0.), float(1.));
	if(pNode->on.value && fIntensity > 0.)
	{
		GxVec3f	dir(0,0,1), loc(0,0,0);

		Qv2Gx(pNode->direction, dir);
		ChColor	color;	Qv2Native(pNode->color, color) ;

		color *= fIntensity;

		CreateFrame(loc, dir);
		m_light = pRC->CreateLight(ChNrLightDirectional, *(color.GetNative()));
		ChNrFrameAddLight(m_frame, m_light);
		D3DRelease(m_light);
	}
};

#endif

#if defined(CH_USE_3DR)
void ChRenderContext::CreateHeadlight( GxVec3f& gloc, GxVec3f& gdir, QvState* state )
{
			  // TODO Fix this
	if(((ChMazeWnd*)GetWnd())->IsHeadlightOn())
	{
		//long wLightNum = ((ChQvState*)state)->NextLight();	  
		int wLightNum = GetNextLight();	  
		TurnOnALight();

		if( ((ChQvState*)state)->GetType() ==  ChQvState::draw)
		{
			G3dHandle_t hGC = ((ChQvState*)state)->GetView()->GetGC();
	  

			if(wLightNum < G3D_MAX_LIGHTS)
			{
				PointF_t dir = {gdir.x(), gdir.y(), gdir.z()};
				PointFW_t loc = {gloc.x(), gloc.y(), gloc.z()};
				Float_t		dimmer = 1.;
				float fIntensity = ((ChQvState*)state)->GetView()->GetHeadlightBrightness();
				ColorFA_t	diffuse 	= {1, 1, 1};		
				ColorF_t	specular 	= {1, 1, 1};
		 		ColorF_t	ambient 	= {0.,0.,0.};
				loc.w = 0.;				 // infinite light

				const float infinity_hack=10000.;
				loc.x -= dir.x * infinity_hack;
				loc.y -= dir.y * infinity_hack;
				loc.z -= dir.z * infinity_hack;
													 
				Float_t exponent	= 0.00;	   // no fall off
				Float_t angle		= 3.14 / 2;// leave the barn doors open; 180 deg beam
				Float_t attena 		= 1.00;	   // no attenuation
				Float_t attenb 		= 0.00;
				Float_t attenc 		= 0.00;

				specular.r *= fIntensity;
				specular.g *= fIntensity;
				specular.b *= fIntensity;

				diffuse.r *= fIntensity;
				diffuse.g *= fIntensity;
				diffuse.b *= fIntensity;


				G3dSetLight( hGC, wLightNum, G3DL_DIMMER,   	(Float_t *)&dimmer );			
				G3dSetLight( hGC, wLightNum, G3DL_AMBIENT, 		(Float_t *)&ambient );			
				G3dSetLight( hGC, wLightNum, G3DL_DIFFUSE,  	(Float_t *)&diffuse );			
				G3dSetLight( hGC, wLightNum, G3DL_SPECULAR, 	(Float_t *)&specular );			
				G3dSetLight( hGC, wLightNum, G3DL_DIRECTION,	(Float_t *)&dir );			
				G3dSetLight( hGC, wLightNum, G3DL_LOCATION,		(Float_t *)&loc );
				G3dSetLight( hGC, wLightNum, G3DL_ATTENA,  		(Float_t *)&attena );
				G3dSetLight( hGC, wLightNum, G3DL_ATTENB,  		(Float_t *)&attenb );
				G3dSetLight( hGC, wLightNum, G3DL_ATTENC,  		(Float_t *)&attenc );
				G3dSetLight( hGC, wLightNum, G3DL_SPOT_EXP, 	(Float_t *)&exponent );
				G3dSetLight( hGC, wLightNum, G3DL_SPOT_ANGLE,	(Float_t *)&angle );
			}			
		}
	}
}
#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
void HeadlightDestroyCallback(ChNrObject obj, void * arg)
{
	ChRenderContext *pRC = (ChRenderContext *)arg;
	pRC->DestroyHeadlight();
	//TRACE("Headlight Destroyed\n");

}

#define MAKE_IT_BRIGHT	1
//#define MAKE_IT_SUPER_BRIGHT	1

void ChRenderContext::CreateHeadlight(  )
{
	LockScene();
	#if 0
	if(m_cameraFrame && m_headlightFrame)
	{
		ChNrFrameRemoveChild(m_cameraFrame, m_headlightFrame);
		m_headlightFrame = 0;
	}
	#endif
	if(m_cameraFrame )
	{
		if(!m_headlightFrame)
		{
			m_headlightFrame = CreateFrame(m_cameraFrame);
			if(m_headlightFrame)
			{
				ChNrObjectAddDestroyCallback(m_headlightFrame, HeadlightDestroyCallback, this);
				D3DRelease(m_headlightFrame);

				TRACE("Headlight Created\n");

				#if defined(D3D_FLIP_LIGHTS) && defined(CH_USE_D3D)
				m_headlightFrame->AddRotation(CombineBefore, 0, 1, 0, 3.141593);
				#endif

				ChNrLightType type = ChNrLightDirectional; //  	 ChNrLightParallelPoint	ChNrLightPoint
				ChNrLight light1 = CreateLightRGB(type, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5));
			    ChNrFrameAddLight(m_headlightFrame, light1);
				D3DRelease(light1);
				#if 0 && defined(CH_USE_D3D)
				ChNrFrame frm = 0;
				HRESULT rval = light1->GetEnableFrame(&frm);
				rval = light1->SetEnableFrame(m_sceneFrame);
				D3DCOLOR color = light1->GetColor();
				#endif

				#if defined(MAKE_IT_BRIGHT)
				// Brighter light by ganging up beams
				ChNrLight light2 =	CreateLightRGB(type, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5));
				ChNrLight light3 =	CreateLightRGB(type, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5));
			    ChNrFrameAddLight(m_headlightFrame, light2);
			    ChNrFrameAddLight(m_headlightFrame, light3);
				D3DRelease(light2);
				D3DRelease(light3);
				#endif

				#if defined(MAKE_IT_SUPER_BRIGHT)
			    ChNrFrameAddLight(m_headlightFrame, CreateLightRGB(ChNrLightDirectional, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5)));
			    ChNrFrameAddLight(m_headlightFrame, CreateLightRGB(ChNrLightDirectional, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5)));
			    ChNrFrameAddLight(m_headlightFrame, CreateLightRGB(ChNrLightDirectional, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5)));
				#endif

				// Ambient light
			    ChNrLight light4 =	CreateLightRGB(ChNrLightAmbient, ChNrVal(0.5), ChNrVal(0.5), ChNrVal(0.5));
			    ChNrFrameAddLight(m_headlightFrame, light4);
				D3DRelease(light4);
			}
		}
		AdjustHeadlight();
	}
	UnlockScene();
}

void ChRenderContext::DestroyHeadlight( )
{
	m_headlightFrame = 0;
}

void ChRenderContext::AdjustHeadlight(  )
{
	ChNrLightArray	lights;
	int count;
	LockScene();
	if(GetWnd() && m_sceneFrame && m_headlightFrame)
	{
		ChNrFrameGetLights(m_headlightFrame, &count, &lights);

		#if defined(CH_USE_D3D)
		count = lights->GetSize();
		#endif

		if(count)
		{
			ChMazeWnd *pWnd = (ChMazeWnd *)GetWnd();
			float intensity = 	pWnd->GetHeadlightBrightness();
			int numLocal = 1;
			if(count > 1)
			{
				numLocal = count - 1;
			}
			//intensity  /= float(numLocal);	 // if more than 1, last is ammbient
			if(!pWnd->IsHeadlightOn()) intensity = 0;
			ChColor color(intensity,intensity,intensity);
    		ChNrLight elt;
			for(int j = 0; j < numLocal; j++)
			{
				ChNrLight light = GetElement(lights, (unsigned int)j, elt);
	    		ChNrLightSetColor( light, *(color.GetNative()) );
				D3DRelease(light);
			}
			if(count > 1)
			{
				float fillFactor = .21 * numLocal;

				#if defined(MAKE_IT_BRIGHT)
				//fillFactor *= 2;
				#endif
				ChNrLight light = GetElement(lights, (unsigned int)(count-1), elt);
				ChColor color(intensity * fillFactor,intensity * fillFactor,intensity * fillFactor);
	    		ChNrLightSetColor( light, *(color.GetNative()) );
				D3DRelease(light);
			}
		}
		ChNrFree(lights);
	}
	UnlockScene();
}

#endif

// end of file

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?