示例#1
0
void CActor::PickupModeUpdate()
{
	if(!m_bPickupMode) return;
	if (GameID() != GAME_SINGLE) return;

	//подбирание объекта
	if(inventory().m_pTarget && inventory().m_pTarget->Useful() &&
		m_pUsableObject && m_pUsableObject->nonscript_usable() &&
		!Level().m_feel_deny.is_object_denied(smart_cast<CGameObject*>(inventory().m_pTarget)) )
	{
		NET_Packet P;
		u_EventGen(P, GE_OWNERSHIP_TAKE, ID());
		P.w_u16(inventory().m_pTarget->object().ID());
		u_EventSend(P);
	}

	//. ????? GetNearest ?????
	feel_touch_update	(Position(), /*inventory().GetTakeDist()*/m_fPickupInfoRadius);
	
	CFrustum frustum;
	frustum.CreateFromMatrix(Device.mFullTransform,FRUSTUM_P_LRTB|FRUSTUM_P_FAR);
	//. slow (ray-query test)
	for(xr_vector<CObject*>::iterator it = feel_touch.begin(); it != feel_touch.end(); it++)
		if (CanPickItem(frustum,Device.vCameraPosition,*it)) PickupInfoDraw(*it);
}
示例#2
0
///////////////////////////////////////////////////////////////////////////////
// Intersect with frustum by repeated slicing
void CBrush::Intersect(const CFrustum& frustum, CBrush& result) const
{
	ENSURE(&result != this);

	if (!frustum.GetNumPlanes())
	{
		result = *this;
		return;
	}

	CBrush buf;
	const CBrush* prev = this;
	CBrush* next;

	if (frustum.GetNumPlanes() & 1)
		next = &result;
	else
		next = &buf;

	for(size_t i = 0; i < frustum.GetNumPlanes(); ++i)
	{
		prev->Slice(frustum[i], *next);
		prev = next;
		if (prev == &buf)
			next = &result;
		else
			next = &buf;
	}

	ENSURE(prev == &result);
}
示例#3
0
void CActor::PickupModeUpdate()
{
	if(!m_bPickupMode)				return; // kUSE key pressed
	if(!IsGameTypeSingle())			return;

	//подбирание объекта
	if(	m_pObjectWeLookingAt									&& 
		m_pObjectWeLookingAt->cast_inventory_item()				&& 
		m_pObjectWeLookingAt->cast_inventory_item()->Useful()	&&
		m_pUsableObject											&& 
		!m_pUsableObject->nonscript_usable()					&&
		!Level().m_feel_deny.is_object_denied(m_pObjectWeLookingAt) )
	{
		m_pUsableObject->use(this);
		Game().SendPickUpEvent(ID(), m_pObjectWeLookingAt->ID());
	}

	feel_touch_update	(Position(), m_fPickupInfoRadius);
	
	CFrustum frustum;
	frustum.CreateFromMatrix(Device.mFullTransform, FRUSTUM_P_LRTB|FRUSTUM_P_FAR);

	for(xr_vector<CObject*>::iterator it = feel_touch.begin(); it != feel_touch.end(); it++)
	{
		if (CanPickItem(frustum, Device.vCameraPosition, *it)) 
			PickupInfoDraw(*it);
	}
}
void CInstanceMesh::Render()
{
  if ( !mStaticMesh || !GetActive() )
    return;

  Math::Mat44f lTransform = GetTransform();
  mCenter = lTransform* mStaticMesh->GetAABB().GetCenter();

  if( mIsDynamic )
  {    
      mPhysicActor->GetMat44( lTransform );
      Math::Vect3f lUp( 0.0f, -mStaticMesh->GetAABB().GetCenter().y, 0.0f );

      Math::Mat44f lCenterTransform;
      lCenterTransform.SetIdentity();

      lCenterTransform.Translate( lUp );
      lTransform = lTransform * lCenterTransform;
  }

  CFrustum lCameraFrustum = CameraMInstance->GetCurrentCamera()->GetFrustum();
  CGraphicsManager* lGM = GraphicsInstance;
  if ( lCameraFrustum.SphereVisible( D3DXVECTOR3( mCenter.u ), mRadius ) )
  {
    lGM ->SetTransform( lTransform );
    mStaticMesh->Render( lGM  );
    lGM ->SetTransform( Math::Mat44f() );
  }
}
示例#5
0
	void	Vision::feel_vision_query	(Fmatrix& mFull, Fvector& P)
	{
		CFrustum								Frustum		;
		Frustum.CreateFromMatrix				(mFull,FRUSTUM_P_LRTB|FRUSTUM_P_FAR);

		// Traverse object database
		r_spatial.clear_not_free				();
		g_SpatialSpace->q_frustum
			(
			r_spatial,
			0,
			STYPE_VISIBLEFORAI,
			Frustum
			);

		// Determine visibility for dynamic part of scene
		seen.clear_and_reserve					()	;
		for (u32 o_it=0; o_it<r_spatial.size(); o_it++)
		{
			ISpatial*	spatial								= r_spatial					[o_it];
			CObject*	object								= spatial->dcast_CObject	();
			if (object && feel_vision_isRelevant(object))	seen.push_back				(object);
		}
		if (seen.size()>1) 
		{
			std::sort							(seen.begin(),seen.end());
			xr_vector<CObject*>::iterator end	= std::unique	(seen.begin(),seen.end());
			if (end!=seen.end()) seen.erase		(end,seen.end());
		}
	}
示例#6
0
	void		walk		(ISpatial_NODE* N, Fvector& n_C, float n_R, u32 fmask)
	{
		// box
		float	n_vR	=		2*n_R;
		Fbox	BB;		BB.set	(n_C.x-n_vR, n_C.y-n_vR, n_C.z-n_vR, n_C.x+n_vR, n_C.y+n_vR, n_C.z+n_vR);
		if		(fcvNone==F->testAABB(BB.data(),fmask))	return;

		// test items
		xr_vector<ISpatial*>::iterator _it	=	N->items.begin	();
		xr_vector<ISpatial*>::iterator _end	=	N->items.end	();
		for (; _it!=_end; _it++)
		{
			ISpatial*		S	= *_it;
			if (0==(S->spatial.type&mask))	continue;

			Fvector&		sC		= S->spatial.sphere.P;
			float			sR		= S->spatial.sphere.R;
			u32				tmask	= fmask;
			if (fcvNone==F->testSphere(sC,sR,tmask))	continue;

			space->q_result->push_back	(S);
		}

		// recurse
		float	c_R		= n_R/2;
		for (u32 octant=0; octant<8; octant++)
		{
			if (0==N->children[octant])	continue;
			Fvector		c_C;			c_C.mad	(n_C,c_spatial_offset[octant],c_R);
			walk						(N->children[octant],c_C,c_R,fmask);
		}
	}
示例#7
0
///////////////////////////////////////////////////////////////////////////////
// Intersect with frustum by repeated slicing
void CBrush::Intersect(const CFrustum& frustum, CBrush& result) const
{
	ENSURE(&result != this);

	if (!frustum.GetNumPlanes())
	{
		result = *this;
		return;
	}

	CBrush buf;
	const CBrush* prev = this;
	CBrush* next;

	// Repeatedly slice this brush with each plane of the frustum, alternating between 'result' and 'buf' to 
	// save intermediate results. Set up the starting brush so that the final version always ends up in 'result'.

	if (frustum.GetNumPlanes() & 1)
		next = &result;
	else
		next = &buf;

	for(size_t i = 0; i < frustum.GetNumPlanes(); ++i)
	{
		prev->Slice(frustum[i], *next);
		prev = next;
		if (prev == &buf)
			next = &result;
		else
			next = &buf;
	}

	ENSURE(prev == &result);
}
void EDetailManager::UpdateSlotBBox(int sx, int sz, DetailSlot& slot)
{
	Fbox bbox;
    Frect rect;
    GetSlotRect			(rect,sx,sz);
    bbox.min.set		(rect.x1, m_BBox.min.y, rect.y1);
    bbox.max.set		(rect.x2, m_BBox.max.y, rect.y2);

    SBoxPickInfoVec pinf;
    ETOOLS::box_options(0);
    if (Scene->BoxPickObjects(bbox,pinf,&m_SnapObjects)){
		bbox.grow		(EPS_L_VAR);
    	Fplane			frustum_planes[4];
		frustum_planes[0].build(bbox.min,left_vec);
		frustum_planes[1].build(bbox.min,back_vec);
		frustum_planes[2].build(bbox.max,right_vec);
		frustum_planes[3].build(bbox.max,fwd_vec);

        CFrustum frustum;
        frustum.CreateFromPlanes(frustum_planes,4);

        float y_min		= flt_max;
        float y_max		= flt_min;
		for (SBoxPickInfoIt it=pinf.begin(); it!=pinf.end(); it++){
        	for (int k=0; k<(int)it->inf.size(); k++){
                float range;
                Fvector verts[3];
                it->e_obj->GetFaceWorld(it->s_obj->_Transform(),it->e_mesh,it->inf[k].id,verts);
                sPoly sSrc	(verts,3);
                sPoly sDest;
                sPoly* sRes = frustum.ClipPoly(sSrc, sDest);
                if (sRes){
                    for (u32 k=0; k<sRes->size(); k++){
                        float H = (*sRes)[k].y;
                        if (H>y_max) y_max = H+0.03f;
                        if (H<y_min) y_min = H-0.03f;
                    }
                    slot.w_y	(y_min,y_max-y_min);
                    slot.w_id(0,DetailSlot::ID_Empty);
                    slot.w_id(1,DetailSlot::ID_Empty);
                    slot.w_id(2,DetailSlot::ID_Empty);
                    slot.w_id(3,DetailSlot::ID_Empty);
                }
            }
	    }
    }else{
    	ZeroMemory(&slot,sizeof(DetailSlot));
    	slot.w_id(0,DetailSlot::ID_Empty);
    	slot.w_id(1,DetailSlot::ID_Empty);
    	slot.w_id(2,DetailSlot::ID_Empty);
    	slot.w_id(3,DetailSlot::ID_Empty);
    }
}
示例#9
0
文件: HOM.cpp 项目: 2asoft/xray-16
void __stdcall	CHOM::MT_RENDER()
{
	MT.Enter					();
	bool b_main_menu_is_active = (g_pGamePersistent->m_pMainMenu && g_pGamePersistent->m_pMainMenu->IsActive() );
	if (MT_frame_rendered!=Device.dwFrame && !b_main_menu_is_active)
	{
		CFrustum					ViewBase;
		ViewBase.CreateFromMatrix	(Device.mFullTransform, FRUSTUM_P_LRTB + FRUSTUM_P_FAR);
		Enable						();
		Render						(ViewBase);
	}
	MT.Leave					();
}
示例#10
0
///////////////////////////////////////////////////////////
// This callback is part of the Scene interface
// Submit all objects visible in the given frustum
void CGameView::EnumerateObjects(const CFrustum& frustum, SceneCollector* c)
{
	{
	PROFILE3("submit terrain");

	CTerrain* pTerrain = m->Game->GetWorld()->GetTerrain();
	float waterHeight = g_Renderer.GetWaterManager()->m_WaterHeight + 0.001f;
	const ssize_t patchesPerSide = pTerrain->GetPatchesPerSide();

	// find out which patches will be drawn
	for (ssize_t j=0; j<patchesPerSide; ++j)
	{
		for (ssize_t i=0; i<patchesPerSide; ++i)
		{
			CPatch* patch=pTerrain->GetPatch(i,j);	// can't fail

			// If the patch is underwater, calculate a bounding box that also contains the water plane
			CBoundingBoxAligned bounds = patch->GetWorldBounds();
			if(bounds[1].Y < waterHeight)
				bounds[1].Y = waterHeight;

			if (!m->Culling || frustum.IsBoxVisible(bounds))
				c->Submit(patch);
		}
	}
	}

	m->Game->GetSimulation2()->RenderSubmit(*c, frustum, m->Culling);
}
示例#11
0
	IC EFC_Visible	_box		(Fvector& C, Fvector& E, u32& mask)
	{
		Fvector		mM[2];
		mM[0].sub	(C,E);
		mM[1].add	(C,E);
		return F->testAABB		(&mM[0].x,mask);
	}
示例#12
0
	void			_prim		(DWORD prim)
	{
		if (bClass3)	{
			sPoly		src,dst;
			src.resize	(3);
			src[0]		= verts[ tris[prim].verts[0] ];
			src[1]		= verts[ tris[prim].verts[1] ];
			src[2]		= verts[ tris[prim].verts[2] ];
			if (F->ClipPoly(src,dst))
			{
				RESULT& R	= dest->r_add();
				R.id		= prim;
				R.verts[0]	= verts[ tris[prim].verts[0] ];
				R.verts[1]	= verts[ tris[prim].verts[1] ];
				R.verts[2]	= verts[ tris[prim].verts[2] ];
				R.dummy		= tris[prim].dummy;
			}
		} else {
			RESULT& R	= dest->r_add();
			R.id		= prim;
			R.verts[0]	= verts[ tris[prim].verts[0] ];
			R.verts[1]	= verts[ tris[prim].verts[1] ];
			R.verts[2]	= verts[ tris[prim].verts[2] ];
			R.dummy		= tris[prim].dummy;
		}
	}
示例#13
0
/**
* CABT::renderTree
* @date Modified Apr 17, 2006
*/
void CABT::renderTree(CFrustum& oFrustum, SABTNode* pNode, bool bContained)
{
	ACEASSERT(pNode);

	// Process subnodes
	CFrustum::EFrustumTest eTest = CFrustum::TEST_IN;
	eTest = oFrustum.containsAABB(pNode->m_oAABB);
	if(eTest == CFrustum::TEST_OUT)
		return;

	// Draw geometry, if the node is a leaf.
	if(pNode->m_bIsLeaf)
	{
		for(size_t v = 0; v < pNode->m_nVertCount/3; ++v)
			m_pRenderQueue->addRenderable(&pNode->m_pTris[v]);

		m_nNumTrianglesRendered += pNode->m_nVertCount / 3;

#ifdef _DEBUG
		static int i = 0;
		if(true)
		{
			drawBoundingBox(pNode->m_oAABB, D3DCOLOR_XRGB(255, 0, 0));
		}

#endif
	}

	if(pNode->m_pLeft) renderTree(oFrustum, pNode->m_pLeft, eTest == CFrustum::TEST_IN);
	if(pNode->m_pRight) renderTree(oFrustum, pNode->m_pRight, eTest == CFrustum::TEST_IN);
}
示例#14
0
void	ISpatial_DB::q_frustum		(xr_vector<ISpatial*>& R, u32 _o, u32 _mask, const CFrustum& _frustum)	
{
	cs.Enter			();
	q_result			= &R;
	q_result->clear_not_free();
	walker				W(this,_mask,&_frustum); W.walk(m_root,m_center,m_bounds,_frustum.getMask()); 
	cs.Leave			();
}
示例#15
0
void CQuake3BSP::RenderLevel(const CVector3 &vPos)
{
    // Reset our bitset so all the slots are zero.
    m_FacesDrawn.ClearAll();

    // Grab the leaf index that our camera is in
    int leafIndex = FindLeaf(vPos);

    // Grab the cluster that is assigned to the leaf
    int cluster = m_pLeafs[leafIndex].cluster;

    // Initialize our counter variables (start at the last leaf and work down)
    int i = m_numOfLeafs;
    g_VisibleFaces = 0;

    // Go through all the leafs and check their visibility
    while(i--)
    {
        // Get the current leaf that is to be tested for visibility from our camera's leaf
        tBSPLeaf *pLeaf = &(m_pLeafs[i]);

        // If the current leaf can't be seen from our cluster, go to the next leaf
        if(!IsClusterVisible(cluster, pLeaf->cluster))
            continue;

        // If the current leaf is not in the camera's frustum, go to the next leaf
        if(!g_Frustum.BoxInFrustum((float)pLeaf->min.x, (float)pLeaf->min.y, (float)pLeaf->min.z,
                                   (float)pLeaf->max.x, (float)pLeaf->max.y, (float)pLeaf->max.z))
            continue;

        // If we get here, the leaf we are testing must be visible in our camera's view.
        // Get the number of faces that this leaf is in charge of.
        int faceCount = pLeaf->numOfLeafFaces;

        // Loop through and render all of the faces in this leaf
        while(faceCount--)
        {
            // Grab the current face index from our leaf faces array
            int faceIndex = m_pLeafFaces[pLeaf->leafface + faceCount];

            // Before drawing this face, make sure it's a normal polygon
            if(m_pFaces[faceIndex].type != FACE_POLYGON) continue;

            // Since many faces are duplicated in other leafs, we need to
            // make sure this face already hasn't been drawn.
            if(!m_FacesDrawn.On(faceIndex))
            {
                // Increase the rendered face count to display for fun
                g_VisibleFaces++;

                // Set this face as drawn and render it
                m_FacesDrawn.Set(faceIndex);
                RenderFace(faceIndex);
            }
        }
    }
}
示例#16
0
/**
* CABT::renderTree
* @date Modified Apr 17, 2006
*/
void CABT::renderTree(CFrustum& oFrustum)
{
	if(!m_pRoot)
		return;

	m_nNumTrianglesRendered = 0;
	renderTree(oFrustum, m_pRoot);
	m_pRenderQueue->renderAll(oFrustum.getViewPosition());
}
示例#17
0
int ZQuadTree::_IsInFrustum(CGeoMapData &pHeightMap, Point &bottomLeft, CFrustum& pFrustum)
{
	bool b[4];
	bool bInSphere;

	bInSphere = pFrustum.SphereInFrustum(bottomLeft.x + m_nCenter.x, bottomLeft.y + m_nCenter.y, 0, m_fRadius);
	if(!bInSphere) return FRUSTUM_OUT;

	b[0] = pFrustum.PointInFrustum(bottomLeft.x + m_nCorner[0].x, bottomLeft.y + m_nCorner[0].y, 0);
	b[1] = pFrustum.PointInFrustum(bottomLeft.x + m_nCorner[1].x, bottomLeft.y + m_nCorner[1].y, 0);
	b[2] = pFrustum.PointInFrustum(bottomLeft.x + m_nCorner[2].x, bottomLeft.y + m_nCorner[2].y, 0);
	b[3] = pFrustum.PointInFrustum(bottomLeft.x + m_nCorner[3].x, bottomLeft.y + m_nCorner[3].y, 0);

	if(b[0] + b[1] + b[2] + b[3] == 4)
		return FRUSTUM_COMPLETELY_IN;

	return FRUSTUM_PRTIALLY_IN;
}
示例#18
0
void MK_Frustum(CFrustum& F, float FOV, float _FAR, float A, Fvector &P, Fvector &D, Fvector &U)
{
    float YFov	= deg2rad(FOV);
    float XFov	= deg2rad(FOV/A);

    // calc window extents in camera coords
    float wR=tanf(XFov*0.5f);
    float wL=-wR;
    float wT=tanf(YFov*0.5f);
    float wB=-wT;

    // calc x-axis (viewhoriz) and store cop
    // here we are assuring that vectors are perpendicular & normalized
    Fvector			R,COP;
    D.normalize		();
    R.crossproduct	(D,U);
    R.normalize		();
    U.crossproduct	(R,D);
    U.normalize		();
    COP.set			(P);

    // calculate the corner vertices of the window
    Fvector			sPts[4];  // silhouette points (corners of window)
    Fvector			Offset,T;
    Offset.add		(D,COP);

    sPts[0].mul(R,wR);
    T.mad(Offset,U,wT);
    sPts[0].add(T);
    sPts[1].mul(R,wL);
    T.mad(Offset,U,wT);
    sPts[1].add(T);
    sPts[2].mul(R,wL);
    T.mad(Offset,U,wB);
    sPts[2].add(T);
    sPts[3].mul(R,wR);
    T.mad(Offset,U,wB);
    sPts[3].add(T);

    // find projector direction vectors (from cop through silhouette pts)
    Fvector ProjDirs[4];
    ProjDirs[0].sub(sPts[0],COP);
    ProjDirs[1].sub(sPts[1],COP);
    ProjDirs[2].sub(sPts[2],COP);
    ProjDirs[3].sub(sPts[3],COP);

    Fvector _F[4];
    _F[0].mad(COP, ProjDirs[0], _FAR);
    _F[1].mad(COP, ProjDirs[1], _FAR);
    _F[2].mad(COP, ProjDirs[2], _FAR);
    _F[3].mad(COP, ProjDirs[3], _FAR);

    F.CreateFromPoints(_F,4,COP);
}
示例#19
0
bool CGroupObject::FrustumPick(const CFrustum& frustum)
{
    if (m_Objects.empty()){
        Fbox 		bb;
        GetBox		(bb);
        u32 mask	= u32(-1); 
        return (frustum.testAABB(bb.data(),mask));
    }else{
        for (ObjectIt it=m_Objects.begin(); it!=m_Objects.end(); it++)
            if ((*it)->FrustumPick(frustum)) return true;
    }
    return false;
}
示例#20
0
文件: EShape.cpp 项目: 2asoft/xray
bool CEditShape::FrustumPick(const CFrustum& frustum)
{
	const Fmatrix& M	= _Transform();
	for (ShapeIt it=shapes.begin(); it!=shapes.end(); it++){
		switch (it->type){
		case cfSphere:{
		    Fvector 	C;
            Fsphere&	T	= it->data.sphere;
		    M.transform_tiny(C,T.P);
        	if (frustum.testSphere_dirty(C,T.R*FScale.x)) return true;
		}break;
		case cfBox:{
        	Fbox 			box;
            box.identity	();
            Fmatrix B		= it->data.box;
            B.mulA_43 		(_Transform());
            box.xform		(B);
			u32 mask		= 0xff;
            if (frustum.testAABB(box.data(),mask)) return true;
		}break;
		}
    }
	return false;
}
示例#21
0
BOOL CFrustum::CreateFromClipPoly(Fvector* p, int count, Fvector& vBase, CFrustum& clip)
{
	VERIFY(count<FRUSTUM_MAXPLANES);
	VERIFY(count>=3);

	sPoly	poly1	(p,count);
	sPoly	poly2;
	sPoly*	dest	= clip.ClipPoly(poly1,poly2);

	// here we end up with complete frustum-polygon in 'dest'
	if (0==dest)	return false;

	CreateFromPoints(dest->begin(),dest->size(),vBase);
	return	true;
}
示例#22
0
文件: Renderer.cpp 项目: jnz/Lynx
void CRenderer::DrawScene(const CFrustum& frustum,
                          CWorld* world,
                          int localctrlid,
                          bool generateShadowMap)
{
    CObj* obj;
    OBJITER iter;

    // Draw the level
    if(!generateShadowMap && world->GetBSP()->IsLoaded())
    {
        // Draw the level with lightmapping?
        if(m_lightmapactive && m_shaderactive)
            glUniform1i(m_uselightmap, 1);

        world->GetBSP()->RenderGL(frustum.pos, frustum);

        if(m_shaderactive)
            glUniform1i(m_uselightmap, 0);
    }

    // Draw every object
    for(iter=world->ObjBegin();iter!=world->ObjEnd();++iter)
    {
        obj = (*iter).second;

        if((obj->GetFlags() & OBJ_FLAGS_GHOST) || // ghosts are invisible - duh
            obj->GetID() == localctrlid || // don't draw the player object
           !obj->GetMesh()) // object has no md5 model
            continue;

        // check if object is in view frustum
        if(!generateShadowMap && !frustum.TestSphere(obj->GetOrigin(), obj->GetRadius()))
            continue;

        glPushMatrix();
        glTranslatef(obj->GetOrigin().x, obj->GetOrigin().y, obj->GetOrigin().z);
        glTranslatef(0.0f, -obj->GetRadius(), 0.0f);
        glMultMatrixf(obj->GetRotMatrix()->pm);

        obj->GetMesh()->Render(obj->GetMeshState());
#ifdef DRAW_NORMALS
        obj->GetMesh()->RenderNormals(obj->GetMeshState()); // not implemented for md2s?
#endif
        glPopMatrix();
    }
}
示例#23
0
BOOL CActor::CanPickItem(const CFrustum& frustum, const Fvector& from, CObject* item)
{
	BOOL	bOverlaped		= FALSE;
	Fvector dir,to; 
	item->Center			(to);
	float range				= dir.sub(to,from).magnitude();
	if (range>0.25f){
		if (frustum.testSphere_dirty(to,item->Radius())){
			dir.div						(range);
			collide::ray_defs			RD(from, dir, range, CDB::OPT_CULL, collide::rqtBoth);
			VERIFY						(!fis_zero(RD.dir.square_magnitude()));
			RQR.r_clear					();
			Level().ObjectSpace.RayQuery(RQR,RD, info_trace_callback, &bOverlaped, NULL, item);
		}
	}
	return !bOverlaped;
}
示例#24
0
void RenderScene() 
{
	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
	glLoadIdentity();									// Reset The matrix

	// Position the camera
	g_Camera.Look();

	// Each frame we calculate the new frustum.  In reality you only need to
	// calculate the frustum when we move the camera.
	g_Frustum.CalculateFrustum();

	// Initialize the total node count that is being draw per frame
	g_TotalNodesDrawn = 0;

/////// * /////////// * /////////// * NEW * /////// * /////////// * /////////// *

	// Here we draw the octree, starting with the root node and recursing down each node.
	// This time, we pass in the root node and just the original world model.  You could
	// just store the world in the root node and not have to keep the original data around.
	// This is up to you.  I like this way better because it's easy, though it could be 
	// more error prone.
	g_Octree.DrawOctree(&g_Octree, &g_World);

	// Render the cubed nodes to visualize the octree (in wire frame mode)
	if( g_bDisplayNodes )
		g_Debug.RenderDebugLines();

	// Create a buffer to store the octree information for the title bar
	static char strBuffer[255] = {0};

	// Display in window mode the current subdivision information.  We now display the
	// max triangles per node, the max level of subdivision, total end nodes, current nodes drawn
	// and frames per second we are receiving.  
	sprintf(strBuffer, "Triangles: %d        Subdivisions: %d        EndNodes: %d          NodesDraw: %d          FPS: %s",
		                g_MaxTriangles,		 g_MaxSubdivisions,		 g_EndNodeCount,	   g_TotalNodesDrawn,	  g_strFrameRate);

/////// * /////////// * /////////// * NEW * /////// * /////////// * /////////// *


	// Set our window title bar to the subdivision information
	SetWindowText(g_hWnd, strBuffer);

	// Swap the backbuffers to the foreground
	SwapBuffers(g_hDC);									
}
示例#25
0
文件: Main.cpp 项目: 88er/tutorials
void RenderScene() 
{
	int i = 0;

	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);	// Clear The Screen And The Depth Buffer
	glLoadIdentity();									// Reset The matrix

	// Tell OpenGL where to look from our camera info
	g_Camera.Look();

	// Calculate our frustum to check the world data again for PVS and Portal Rendering
	g_Frustum.CalculateFrustum();

	// Render the level to the screen
	g_Level.RenderLevel(g_Camera.Position());

	// Swap the backbuffers to the foreground
	SwapBuffers(g_hDC);	
}
示例#26
0
void RenderScene()
{
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);	// Clear The Screen And The Depth Buffer
    glLoadIdentity();									// Reset The matrix

    // Give OpenGL our camera position
    g_Camera.Look();

/////// * /////////// * /////////// * NEW * /////// * /////////// * /////////// *

    // Each frame we calculate the new frustum.  In reality you only need to
    // calculate the frustum when we move the camera.
    g_Frustum.CalculateFrustum();

    // Initialize the total node count that is being draw per frame
    g_TotalNodesDrawn = 0;

/////// * /////////// * /////////// * NEW * /////// * /////////// * /////////// *

    // Here we draw the octree, starting with the root node and recursing down each node.
    // When we get to each of the end nodes we will draw the vertices assigned to them.
    g_Octree.DrawOctree(&g_Octree);

    // Render the cube'd nodes to visualize the octree (in wire frame mode)
    g_Debug.RenderDebugLines();

    SwapBuffers(g_hDC);									// Swap the backbuffers to the foreground

    char strBuffer[255] = {0};							// Create a character buffer

    // To view our octree information I set the window's title bar to the some basic
    // information such as the max triangles per node, the max subdivisions,
    // total end nodes and the total drawn end nodes that are currently in the frustum.

    // Display in window mode the current subdivision information
    sprintf(strBuffer, "MaxTriangles: %d     MaxSubdivisions: %d     TotalEndNodes: %d       TotalNodesDraw: %d",
            g_MaxTriangles,		 g_MaxSubdivisions,		 g_EndNodeCount,		 g_TotalNodesDrawn);

    // Set our window title bar to the subdivision data
    SetWindowText(g_hWnd, strBuffer);
}
示例#27
0
void COLLIDER::frustum_query(const MODEL *m_def, const CFrustum& F)
{
	m_def->syncronize		();

	// Get nodes
	const AABBNoLeafTree*	T	= (const AABBNoLeafTree*)m_def->tree->GetTree();
	const AABBNoLeafNode*	N	= T->GetNodes();
	const DWORD				mask= F.getMask();
	r_clear					();
	
	// Binary dispatcher
	if (frustum_mode&OPT_FULL_TEST) 
	{
		if (frustum_mode&OPT_ONLYFIRST)
		{
			frustum_collider<true,true> BC;
			BC._init	(this,m_def->verts,m_def->tris,&F);
			BC._stab	(N,mask);
		} else {
			frustum_collider<true,false> BC;
			BC._init	(this,m_def->verts,m_def->tris,&F);
			BC._stab	(N,mask);
		}
	} else {
		if (frustum_mode&OPT_ONLYFIRST)
		{
			frustum_collider<false,true> BC;
			BC._init	(this,m_def->verts,m_def->tris,&F);
			BC._stab	(N,mask);
		} else {
			frustum_collider<false,false> BC;
			BC._init	(this,m_def->verts,m_def->tris,&F);
			BC._stab	(N,mask);
		}
	}
}
示例#28
0
void RenderScene()
{

/////// * /////////// * /////////// * NEW * /////// * /////////// * /////////// *

    int spheresRendered = 0;							// This will hold how many spheres are being rendered
    char strText[255]= {0};								// This will hold the window title info

    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);	// Clear The Screen And The Depth Buffer
    glLoadIdentity();									// Reset The matrix

    // Give OpenGL our camera position
    g_Camera.Look();

    // We don't need to calculate this every frame, only when the camera view changes.
    // I just did it every frame anyway.  In this case it isn't a big deal.
    g_Frustum.CalculateFrustum();						// Calculate the frustum each frame

    // If you are unfamiliar with Quadrics, see the tutorial on Quadrics at www.GameTutorials.com.
    // They basically allow you to draw circles and cylinders fast and easily.

    GLUquadricObj *pObj = gluNewQuadric();				// Get a Quadric off the stack

    // Loop through all of our allowed spheres and render them to the screen if in the frustum.
    for(int i = 0; i < g_MaxSpheres; i++)				// g_MaxSpheres varies.
    {
        g_Spheres[i].zPos += SPHERE_SPEED;				// Increase the Z position of the sphere.

        // Below we check if the sphere needs to be draw or not.  If g_bIgnoreFrustum is TRUE,
        // it draws it regardless (which is SLOOOooOoW).  We just pass in the (X, Y, Z)
        // and the radius of the sphere to find out if it is inside of the frustum.

        if(g_bIgnoreFrustum || g_Frustum.SphereInFrustum(g_Spheres[i].xPos, g_Spheres[i].yPos, g_Spheres[i].zPos, g_Spheres[i].radius))
        {
            // Set the sphere's color
            glColor3ub(g_Spheres[i].r, g_Spheres[i].g, g_Spheres[i].b);

            // Create a new scope before positiong the sphere so we don't effect the other spheres.
            glPushMatrix();

            // Position the sphere on the screen at it's XYZ position.
            glTranslatef(g_Spheres[i].xPos, g_Spheres[i].yPos, g_Spheres[i].zPos);

            // Create a sphere with the desired radius chosen in the beginning.
            gluSphere(pObj, g_Spheres[i].radius, 20, 20);	// Draw the sphere with a radius of 0.5
            glPopMatrix();								// Close the scope of this matrix

            spheresRendered++;							// Increase the amount of spheres rendered
        }

        // Here we check to see if the sphere went out of our range,
        // If so, we need to set it back again with a new random position.
        if(g_Spheres[i].zPos > MAX_DISTANCE) {
            // Give the sphere a new random position back in the beginning.
            g_Spheres[i].xPos = (rand() % (MAX_DISTANCE * 10)) * 0.1f;
            g_Spheres[i].yPos = (rand() % (MAX_DISTANCE * 10)) * 0.1f;
            g_Spheres[i].zPos = -MAX_DISTANCE;			// Send it to the back again.

            // Give a 50/50 chance for the sphere to be to the left/right or above/below the XY axis.
            // This is because we are centered at the origin
            if(rand() % 2) g_Spheres[i].xPos = -g_Spheres[i].xPos;
            if(rand() % 2) g_Spheres[i].yPos = -g_Spheres[i].yPos;
        }
    }

    // Since I didn't want to add more code for a rendered font, I decided to just
    // render the frustum information in the title bar of the window.
    // The information tells you how many spheres were rendered and out of how many.
    // Use +/- to increase and decrease the max spheres tested.

    sprintf(strText, "www.GameTutorials.com - Spheres Rendered: %d / %d", spheresRendered, g_MaxSpheres);
    SetWindowText(g_hWnd, strText);						// Change the window title bar

/////// * /////////// * /////////// * NEW * /////// * /////////// * /////////// *

    SwapBuffers(g_hDC);									// Swap the backbuffers to the foreground
    gluDeleteQuadric(pObj);								// Free the Quadric
}
示例#29
0
void WaterManager::RenderWaves(const CFrustum& frustrum)
{
#if CONFIG2_GLES
#warning Fix WaterManager::RenderWaves on GLES
#else
	if (g_Renderer.m_SkipSubmit || !m_WaterFancyEffects)
		return;
		
	pglBindFramebufferEXT(GL_FRAMEBUFFER_EXT, m_FancyEffectsFBO);
		
	GLuint attachments[2] = { GL_COLOR_ATTACHMENT0_EXT, GL_COLOR_ATTACHMENT1_EXT };
	pglDrawBuffers(2, attachments);
		
	glClearColor(0.0f,0.0f, 0.0f,0.0f);
	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
		
	glEnable(GL_BLEND);
	glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
	glEnable(GL_DEPTH_TEST);
	glDepthFunc(GL_ALWAYS);
	
	CShaderDefines none;
	CShaderProgramPtr shad = g_Renderer.GetShaderManager().LoadProgram("glsl/waves", none);
	
	shad->Bind();
	
	shad->BindTexture(str_waveTex, m_WaveTex);
	shad->BindTexture(str_foamTex, m_FoamTex);
	
	shad->Uniform(str_time, (float)m_WaterTexTimer);
	shad->Uniform(str_transform, g_Renderer.GetViewCamera().GetViewProjection());

	for (size_t a = 0; a < m_ShoreWaves.size(); ++a)
	{
		if (!frustrum.IsBoxVisible(m_ShoreWaves[a]->m_AABB))
			continue;
		
		CVertexBuffer::VBChunk* VBchunk = m_ShoreWaves[a]->m_VBvertices;
		SWavesVertex* base = (SWavesVertex*)VBchunk->m_Owner->Bind();
		
		// setup data pointers
		GLsizei stride = sizeof(SWavesVertex);
		shad->VertexPointer(3, GL_FLOAT, stride, &base[VBchunk->m_Index].m_BasePosition);
		shad->TexCoordPointer(GL_TEXTURE0, 2, GL_UNSIGNED_BYTE, stride, &base[VBchunk->m_Index].m_UV);
		//	NormalPointer(gl_FLOAT, stride, &base[m_VBWater->m_Index].m_UV)
		pglVertexAttribPointerARB(2, 2, GL_FLOAT, GL_TRUE, stride, &base[VBchunk->m_Index].m_PerpVect);	// replaces commented above because my normal is vec2
		shad->VertexAttribPointer(str_a_apexPosition, 3, GL_FLOAT, false, stride, &base[VBchunk->m_Index].m_ApexPosition);
		shad->VertexAttribPointer(str_a_splashPosition, 3, GL_FLOAT, false, stride, &base[VBchunk->m_Index].m_SplashPosition);
		shad->VertexAttribPointer(str_a_retreatPosition, 3, GL_FLOAT, false, stride, &base[VBchunk->m_Index].m_RetreatPosition);
		
		shad->AssertPointersBound();
		
		shad->Uniform(str_translation, m_ShoreWaves[a]->m_TimeDiff);
		shad->Uniform(str_width, (int)m_ShoreWaves[a]->m_Width);

		u8* indexBase = m_ShoreWaves_VBIndices->m_Owner->Bind();
		glDrawElements(GL_TRIANGLES, (GLsizei) (m_ShoreWaves[a]->m_Width-1)*(7*6),
					   GL_UNSIGNED_SHORT, indexBase + sizeof(u16)*(m_ShoreWaves_VBIndices->m_Index));
		
		shad->Uniform(str_translation, m_ShoreWaves[a]->m_TimeDiff + 6.0f);
		
		// TODO: figure out why this doesn't work.
		//g_Renderer.m_Stats.m_DrawCalls++;
		//g_Renderer.m_Stats.m_WaterTris += m_ShoreWaves_VBIndices->m_Count / 3;
		
		CVertexBuffer::Unbind();
	}
	shad->Unbind();
	pglBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);

	glDisable(GL_BLEND);
	glDepthFunc(GL_LEQUAL);
#endif
}
示例#30
0
//////////////////////////////////////////////////////////////////////////
// sub-space rendering - shortcut to render with frustum extracted from matrix
void	R_dsgraph_structure::r_dsgraph_render_subspace	(IRender_Sector* _sector, Fmatrix& mCombined, Fvector& _cop, BOOL _dynamic, BOOL _precise_portals)
{
	CFrustum	temp;
	temp.CreateFromMatrix			(mCombined,	FRUSTUM_P_ALL);
	r_dsgraph_render_subspace		(_sector,&temp,mCombined,_cop,_dynamic,_precise_portals);
}