⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 chrenderdata.cpp

📁 Windows上的MUD客户端程序
💻 CPP
📖 第 1 页 / 共 4 页
字号:
							all faces have 3 or more vertices, and all vertices are legal in
							the context of the current coordinate node. Someday we should put
							out insulting messages when this fails, but that's for later. */
	if(!state->getTopElement(QvState::Coordinate3Index))
	{							 // no coordinates!
		m_boolValid = false;
		return false;
	}
	QvCoordinate3 *pC3 = (QvCoordinate3*)(state->getTopElement(QvState::Coordinate3Index)->data);
	

	m_boolValid = true;
	if(ifs->coordIndex.num < 4) 
	{
		m_boolValid = false;
		return false;
	}
	int vertCount = 0;
	int faceCount = 0;
	
	for(int j = 0; j< ifs->coordIndex.num; j++)	   //coordIndex.values[j] != QV_END_FACE_INDEX
	{
		if( ifs->coordIndex.values[j] <	QV_END_FACE_INDEX)
		{
			m_boolValid = false;		// fail for illegal coord, gotta be -1 or non-neg
			break;
		}
		if( ifs->coordIndex.values[j] >= pC3->point.num)
		{
			m_boolValid = false;		// fail for illegal coord; out of range
			break;
		}
		if( ifs->coordIndex.values[j] !=	QV_END_FACE_INDEX) vertCount ++;
		else
		{
			if(vertCount < 3)
			{
				m_boolValid = false;		// fail for face with too few points
				break;
			}
			else
			{
				vertCount = 0;	// new face
				faceCount++;
			}
		}
	}
	if(vertCount > 2)
	{
		faceCount ++; // accept a trailing unterminated face if it has enough points
		vertCount = 0;
	}

									// fail for trailing trash or no faces
	if(vertCount != 0 || faceCount == 0) m_boolValid = false;
	return m_boolValid;
}


// Texture render data

ChQvTextureRenderData::ChQvTextureRenderData(QvNode* pTxt) :
	ChQvRenderBaseData(pTxt),	
	m_texture(0), 
	#if defined(CH_USE_3DR)
	m_hRC(0), 
	#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
	m_pImage(0)
	#endif	
{ }

ChQvTextureRenderData::~ChQvTextureRenderData()
{
	#if defined(CH_USE_3DR)
    if (m_texture && m_hRC ) R3dFreeTexture( m_hRC, (Dword_t)m_texture);
	#else
//	delete m_pImage;
	if ( m_pImage )
	{
		m_pImage->Release();
	}
	m_pImage = 0;
	// Textures themselves are usage counted, and we don't have to free them
	#endif
	m_texture = 0;
}

int ChQvTextureRenderData::GetURL(QvState *qvstate)
{
	// return true if this is a spawn request, else false
	if( ((ChQvState*)qvstate)->GetType() != ChQvState::spawnRequests)
	{
		return false;
	}

	QvTexture2 *pNode = (QvTexture2 *)GetNode();
	// Spawn a new http request and add it to the info's list of requests
	if(m_strURL.IsEmpty())
	{
		ChQvSpawnState *state = (ChQvSpawnState *)qvstate;
		m_strURL = pNode->filename.value.getString();

		// check if we need to fetch a texture from a WWW site
		if(!m_strURL.IsEmpty())	
		{

			ChMazeTextureHTTPReq *pHTTPReq = new ChMazeTextureHTTPReq ( 
									state->GetView(), m_strURL, GetNode() );
			pHTTPReq->SetPage(state->GetView()->GetCurrentPage());

		   	string defURL = state->GetDefaultURL();
			state->GetView()->GetURL( m_strURL, (chparam)pHTTPReq, LPCTSTR(defURL) );
		}
		else if ( pNode->image.size[0] && 
				  pNode->image.size[1] &&
				  pNode->image.numComponents  )
		{ // We have a field that contains an uncompressed 2-dimensional color or greyscale image
		  // convert the image to a ChSFImage and load the texture 
		  	ChRenderContext *pRenderContext = state->GetView()->GetRenderContext();

			if ( pRenderContext )
			{ // We have a valid render context, load the texture
		   		ChSFImage *pSFImage = new ChSFImage();
				ASSERT( pSFImage );

				if ( pSFImage->Create( pNode->image.size[0], 
				  				  pNode->image.size[1],
				  				  pNode->image.numComponents,
				  				  pNode->image.bytes ) )
				{  // Transparent pixel information is ignored in the current
				   // implementation
					LoadTexture( pRenderContext, pSFImage->GetDibImage(), 
								  0, ChMazeTextureHTTPReq::textureAutoSize );
					#if 0
					SetTextureHandle( pRenderContext->LoadDIBTexture( pSFImage, 
										 				  0, 
										 				  ChMazeTextureHTTPReq::textureShrink ));
					#endif
				}
				delete pSFImage;
			}

		}

	}
	return true;
}

#if (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
// Iterator to propagate texture load info
class MyTextureDataIterator: public ChQvRenderBaseDataIterator
{
	public:
		MyTextureDataIterator( const ChQvTextureRenderData& rbd ) : ChQvRenderBaseDataIterator(rbd) {};


		virtual int DoInstance(ChQvInstance& inst)
		{
			inst.SetTexture((ChQvTextureRenderData*)m_pData);
			return true;
		};


   protected:

   private:
											/* Disable copy constructor and
												assignment operator */

      inline MyTextureDataIterator( const MyTextureDataIterator& ) {}
      inline MyTextureDataIterator& operator=( const MyTextureDataIterator& )
      			{
      				return *this;
      			}
};

#endif

ChQvTextureRenderData* ChQvTextureRenderData::LoadTexture(ChRenderContext *pContext, ChDib *pDibIn, chuint32 luChromaClr, chuint uOption)
{
#if defined(CH_USE_3DR)
	SetTextureHandle( pContext->LoadDIBTexture( pDibIn, luChromaClr, uOption ));
#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
	if(m_texture) return this;		// Something already there, do nothing for now
	bool boolLimit = false;			// Should we allow reduction for RLAB??

	m_pImage = new ChRLImage(pDibIn, boolLimit, uOption, luChromaClr);

	pContext->LockScene();

	m_texture = pContext->CreateTexture(pRLImage(*m_pImage));

	// Now propagate to all dependents 
	MyTextureDataIterator iterator(*this);
	iterator.IterateDependents();

	pContext->UnlockScene();

		  
#endif
	return this;
}

#if (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
void NrTextureDestroyCallback(ChNrObject obj, void * arg)
{
}
#endif

#if defined(CH_USE_3DR)
ChQvTextureRenderData* ChQvTextureRenderData::LoadTexture( ChRenderContext *pContext, ChTextureHandle texHandle )
#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
ChQvTextureRenderData* ChQvTextureRenderData::LoadTexture( ChRenderContext *pContext, ChRLImage* pRLImg )
#endif
{

#if defined(CH_USE_3DR)

	SetTextureHandle( texHandle );

#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))

	if(m_texture) 
	{
		// Delete the old texture we have
		//delete pRLImg;
		pRLImg->Release();
		return this;	  // Something already there, do nothing for now
	}		
	// Need to ask Jim why we are saving RLImage.
	m_pImage = pRLImg;

	pContext->LockScene();
	m_texture = pContext->CreateTexture(pRLImage(*m_pImage));
	// Add callback - Just for debugging for now
	ChNrObjectAddDestroyCallback(m_texture, NrTextureDestroyCallback, this);

	// Now propagate to all dependents 
	MyTextureDataIterator iterator(*this);
	iterator.IterateDependents();
	pContext->UnlockScene();
		  
#endif
	return this;
}

// Return whether it will -never- have a texture
bool ChQvTextureRenderData::IsEmpty()
{
	bool boolEmpty = true;
	QvTexture2 *pNode = (QvTexture2 *)GetNode();
	string strURL = string(pNode->filename.value.getString());
	if(!strURL.IsEmpty()) boolEmpty = false;
	if ( pNode->image.size[0] && 
				  pNode->image.size[0] &&
				  pNode->image.numComponents  ) boolEmpty = false;
	return boolEmpty;
}

#if (defined(CH_USE_RLAB) || defined(CH_USE_D3D)) || defined(CH_USE_D3D)
bool ChQvTextureRenderData::IsChromaKey() 
{ 
	return m_pImage ? m_pImage->IsChromaKey() : false; 
};

ChColor ChQvTextureRenderData::GetChromaKey() 
{ 
	return m_pImage ? m_pImage->GetChromaKey() : ChColor(0); 
};

#endif		
/////////////////////////////////////////////////////////////////////////
ChQvTexture2TransformRenderData::ChQvTexture2TransformRenderData(QvNode* pNode) : ChQvRenderBaseData(pNode)
{
	SetDirty();
};

ChQvTexture2TransformRenderData *ChQvTexture2TransformRenderData::Transform(float &s, float& t)
{
	if(m_boolDefault) return this;

	QvTexture2Transform * pNode = (QvTexture2Transform*)m_pNode;
	// Far from optimal - need to cache 3x3 homo matrix for better results
	float tmp;
	s -= pNode->center.value[0];
	t -= pNode->center.value[1];

	s *= pNode->scaleFactor.value[0];
	t *= pNode->scaleFactor.value[1];


	tmp = m_cosa * s - m_sina * t;
	t = m_sina * s + m_cosa * t;
	s = tmp;

	s += pNode->center.value[0];
	t += pNode->center.value[1];

	s += pNode->translation.value[0];
	t += pNode->translation.value[1];
	
	return this;
}

ChQvTexture2TransformRenderData *ChQvTexture2TransformRenderData::CheckForDefault()
{
	QvTexture2Transform * pNode = (QvTexture2Transform*)m_pNode;
	m_boolDefault = true;

	if(pNode->scaleFactor.value[0] != 0.0 || pNode->scaleFactor.value[1] != 0.0)
		m_boolDefault = false;
	if(pNode->rotation.value != 0.0)
		m_boolDefault = false;
	if(pNode->translation.value[0] != 0.0 || pNode->translation.value[1] != 0.0)
		m_boolDefault = false;

	return this;
}

void ChQvTexture2TransformRenderData::SetDirty(bool boolDirty )
{
	if(boolDirty)
	{
		QvTexture2Transform * pNode = (QvTexture2Transform*)m_pNode;
		m_cosa = cos(pNode->rotation.value);
		m_sina = sin(pNode->rotation.value);
		CheckForDefault();
	}
	return;
}; 

// WWWInline
ChQvWWWInlineRenderData::~ChQvWWWInlineRenderData()
{
	if(m_pParseInfo)
	{
		m_pParseInfo->Abort();
		m_pParseInfo->SetUserData(0);
		m_pParseInfo = 0;
	}
	if(GetReq())
	{
		GetReq()->Cancel();
		GetReq()->SetInlineNode(0);
		SetReq(0);
	}
}
ChQvWWWInlineRenderData* ChQvWWWInlineRenderData::Instantiate(ChMazeWnd * pWnd, QvNode *pNewChild)
{
	// Walk the list of WWWInline instances, instantiating the new subtree that came in
	if (!m_instances.IsEmpty())
	{
		ChPosition pos = m_instances.GetHeadPosition();
		while(pos)
		{
			ChQvWWWInlineInstance *pInst = (ChQvWWWInlineInstance *)(m_instances.GetNext(pos));
			ChQvBuildState bldIt(pWnd);
			bldIt.SetCurrentParent(pInst);
			pInst->SetupTraversalState(bldIt);
			pNewChild->traverse(&bldIt);

			// Now construct them for RLab 
			#if (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
			pWnd->GetRenderContext()->StartConstruction(pInst);
			#endif
		}
	}
	return this;
}

/////////////////////////////////////////////////////////////////////////////////
ChQvSwitchRenderData::ChQvSwitchRenderData(QvNode* pNode) : 
	ChQvGroupRenderData(pNode)
{
#if defined(CH_VRML_EVENTS)
	if(!m_pDispatcher)
	{
		m_pDispatcher = new	ChVrmlDispatcher;
		Init();
	}
#endif
};


void ChQvSwitchRenderData::Init()
{
	//ChQvGroupRenderData::Init();
	#if defined(CH_VRML_EVENTS)
	AddVrmlDispatcher("set_whichChild", SFLong, OnSetWhichChild);
	#endif
};

ChQvSwitchRenderData::~ChQvSwitchRenderData()
{
}

void ChQvSwitchRenderData::Term()
{
#if defined(CH_VRML_EVENTS)
	delete m_pDispatcher;
	m_pDispatcher = 0;
#endif
}

bool ChQvSwitchRenderData::OnSetWhichChild(ChRenderContext *pRC, ChApplet * pApplet, ChIVrmlEvent *pEventList)
{
	bool boolSuccess = true;
#if defined(CH_VRML_EVENTS)
	long lChild;
	ChLongEvent *pEvent = (ChLongEvent *)pEventList;
	pEvent->GetValue(lChild);

	QvSwitch *pNode = (QvSwitch *)m_pNode;
	pNode->whichChild.value = lChild;

	// Now the hard part; 
	// If this is the cameras node, the camera is on our list, so select it there
	// Otherwise, if this child contains a camera somewhere, select it. Do not add it
	// to the list.

	if(lChild >= 0 && lChild < pNode->getNumChildren())
	{
		if(pNode->getName() == "Cameras")
		{
			pRC->SelectCamera(int (lChild));
		}
		else
		{
			// Search for a camera. If found, set it.
			QvNode *pChild = pNode->getChild(int(lChild));
		}
	}
#endif

	return boolSuccess;
}

// Background ala 2.0 render data

ChQvBackgroundData::ChQvBackgroundData() :	
	#if (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
	m_pImage(0)
	#endif	
{
	for(int j=0; j<6; j++)
	{
		m_panTextures[j] = 0;
	} 
}

ChQvBackgroundData::~ChQvBackgroundData()
{
	#if (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
	//delete m_pImage;
	if ( m_pImage )
	{
		m_pImage->Release();
	}
	m_pImage = 0;
	// Textures themselves are usage counted, and we don't have to free them ????
	#endif
	for(int j=0; j<6; j++)
	{
		m_panTextures[j] = 0;
	} 
}

int ChQvBackgroundData::GetURL(QvState *qvstate)
{
	// return true if this is a spawn request, else false
	if( ((ChQvState*)qvstate)->GetType() != ChQvState::spawnRequests)
	{
		return false;
	}

	// Spawn a new http request and add it to the info's list of requests
	if(m_strURL.IsEmpty())
	{
		ChQvSpawnState *state = (ChQvSpawnState *)qvstate;
		QvBackground *pNode = (QvBackground *)GetNode();
		m_strURL = string(pNode->panorama.values[0].getString());

		// check if we need to fetch a texture from a WWW site
		if(!m_strURL.IsEmpty())	
		{

			#if NOT_YET
			ChMazeTextureHTTPReq *pHTTPReq = new ChMazeTextureHTTPReq ( 
									state->GetView(), m_strURL, m_pTexture2 );
			pHTTPReq->SetPage(state->GetView()->GetCurrentPage());

		   	string defURL = state->GetDefaultURL();
			state->GetView()->GetURL( m_strURL, (chparam)pHTTPReq, LPCTSTR(defURL) );
			#endif
		}

	}
	return true;
}


ChQvBackgroundData* ChQvBackgroundData::LoadTexture(ChRenderContext *pContext, ChDib *pDibIn, chuint32 luChromaClr, chuint uOption)
{
#if defined(CH_USE_3DR)
#elif (defined(CH_USE_RLAB) || defined(CH_USE_D3D))
	#if NOT_YET

⌨️ 快捷键说明

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