i32 CreateRect2D(Resources::CMesh* pMesh, const IInputLayout* pIL, const SRect2DOptions& Opts)
    {
        Vec3 vecScale( 100 ); 
        Vec2 vecWidth( 0, 100 );
        Vec2 vecHeight( 0, 100 );

        IndexBufferPtr pIB = pMesh->CreateIndexBuffer();
        VertexBufferPtr pVB = pMesh->CreateVertexBuffer();

        pVB->SetVertexCount( 4 );
        pVB->SetInputLayout( pIL );
        pVB->SetTopologyType( TopologyTypes::TRIANGLE_LIST );
        pVB->SetUsage( Opts.eUsage );

        pIB->SetIndexCount( 6 );
        pIB->SetUsage( BufferUsages::STATIC );

        pVB->Lock();
        CVertexData& VData = pVB->GetVertexData();

        if( pIL->IsPosition() )
        {
            VData.SetPosition( 0, Vec3( 0,			0,				0 ) );
            VData.SetPosition( 1, Vec3( vecScale.x, 0,				0 ) );
            VData.SetPosition( 2, Vec3( vecScale.x, -vecScale.y,	0 ) );
            VData.SetPosition( 3, Vec3( 0,			-vecScale.y,	0) );
        }

        if( pIL->IsColor() )
        {
            VData.SetColor( 0, Vec4( 1, 1, 1, 1 ) );
            VData.SetColor( 1, Vec4( 1, 1, 1, 1 ) );
            VData.SetColor( 2, Vec4( 1, 1, 1, 1 ) );
            VData.SetColor( 3, Vec4( 1, 1, 1, 1 ) );
        }

        if( pIL->IsTexCoord0() )
        {
            VData.SetTexCoord( 0, 0, Vec2( 0, 1 ) );
            VData.SetTexCoord( 1, 0, Vec2( 1, 1 ) );
            VData.SetTexCoord( 2, 0, Vec2( 0, 1 ) );
            VData.SetTexCoord( 3, 0, Vec2( 0, 0 ) );
        }

        pVB->Unlock();
        pVB->Create();

        pIB->Lock();
        CIndexData& IData = pIB->GetIndexData();

        IData.SetTriangle( 0, 0, 2, 3 );
        IData.SetTriangle( 1, 1, 2, 0 );

        return XST_OK;
    }
Beispiel #2
0
    void UnderWaterGodRay::_updateRays()
    {
        Camera * cam = World::Instance()->MainCamera();
        const Vec3 * corner = cam->GetCorner();
        float FarWidth   = (corner[4] - corner[5]).Length();
        float RaysLength = cam->GetFarClip();

        VertexBufferPtr vb = mRender.vxStream.GetStream(0);
        Vec3 * vert = (Vec3*)vb->Lock(0, 0, LOCK_DISCARD);

        Vec2 Pos;
        float Dis, RayLength;

        for(int k = 0; k < mNumberOfRays; k++)
        {
            Pos       = _calculateRayPosition(k);
            Dis       = mRaysSize * RaysLength;
            RayLength = RaysLength * (0.3f + Pos.Length());

            Pos *= FarWidth/2;

            // 4 Planes, 3 vertices each plane, 12 vertices per ray
            // ----> 1/4
            // 0
            *vert++ = Vec3(0, 0, 0);
            // A
            *vert++ = Vec3(Pos.x, Pos.y, -RayLength);
            // B
            *vert++ = Vec3(Pos.x+Dis, Pos.y, -RayLength);
            // ----> 2/4
            // 0
            *vert++ = Vec3(0, 0, 0);
            // D
            *vert++ = Vec3(Pos.x+Dis, Pos.y+Dis, -RayLength);
            // B
            *vert++ = Vec3(Pos.x+Dis, Pos.y, -RayLength);
            // ----> 3/4
            // 0
            *vert++ = Vec3(0, 0, 0);
            // C
            *vert++ = Vec3(Pos.x, Pos.y+Dis, -RayLength);
            // D
            *vert++ = Vec3(Pos.x+Dis, Pos.y+Dis, -RayLength);
            // ----> 4/4
            // 0
            *vert++ = Vec3(0, 0, 0);
            // C
            *vert++ = Vec3(Pos.x, Pos.y+Dis, -RayLength);
            // A
            *vert++ = Vec3(Pos.x, Pos.y, -RayLength);
        }

        vb->Unlock();
    }
Beispiel #3
0
void MeshLoader_v0::ReadVertexStream(VertexBufferPtr & vb, int & stride, int count, DataStreamPtr & stream)
{
    EXCEPTION_DEBUG(vb.IsNull(), "model file error.");

    stream->Read(&stride, sizeof(int));

    vb = VideoBufferManager::Instance()->CreateVertexBuffer(stride * count, stride);
    
    void * data = vb->Lock(0, 0, LOCK_DISCARD);

    stream->Read(data, stride * count);

    vb->Unlock();
}
Beispiel #4
0
    void UnderWaterGodRay::_createGodRays()
    {
        VertexStream * vxStream = &mRender.vxStream;
        IndexStream * ixStream = &mRender.ixStream;

        int iVertexCount = mNumberOfRays * 12;
        int iIndexCount = mNumberOfRays * 12;
        int iPrimCount = iIndexCount / 3;
        int iStride = 12;

        VertexDeclarationPtr decl = VideoBufferManager::Instance()->CreateVertexDeclaration();
        decl->AddElement(0, 0, DT_FLOAT3, DU_POSITION, 0);
        decl->Init();

        vxStream->SetDeclaration(decl);

        VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(iVertexCount * 20, 20, USAGE_DYNAMIC);
        IndexBufferPtr ib = VideoBufferManager::Instance()->CreateIndexBuffer(iIndexCount * sizeof(short));

        float * vert = (float *)vb->Lock(0, 0, LOCK_NORMAL);
        short * idx = (short *)ib->Lock(0, 0, LOCK_NORMAL);

        int index = 0;
        for (int j = 0; j < mNumberOfRays; ++j)
        {
            for (int i = 0; i < 12; ++i)
            {
                *vert++ = 0; *vert++ = 0; *vert++ = 0;
                *idx++ = index++; 
            }
        }

        vb->Unlock();
        ib->Unlock();

        vxStream->Bind(0,vb, iStride);
        vxStream->SetCount(iVertexCount);

        ixStream->Bind(ib, 0);
        ixStream->SetCount(iIndexCount);

        mRender.iPrimCount = iPrimCount;
        mRender.ePrimType = PRIM_TRIANGLELIST;
        mRender.rState.blendMode = BM_ADD;
        mRender.rState.cullMode = CULL_NONE;
        mRender.rState.fillMode = FILL_SOLID;
        mRender.rState.depthWrite = false;
        mRender.rState.depthCheck = DCM_NONE;
    }
Beispiel #5
0
    void Moon::_geometry()
    {
        VertexStream * vxStream = &mRender.vxStream;
        IndexStream * ixStream = &mRender.ixStream;

        int iVertexCount = 4;
        int iPrimCount = 2;

        VertexDeclarationPtr decl = VideoBufferManager::Instance()->CreateVertexDeclaration();
        decl->AddElement(0, 0, DT_FLOAT3, DU_POSITION, 0);
        decl->AddElement(0, 12, DT_FLOAT2, DU_TEXCOORD, 0);
        decl->Init();

        vxStream->SetDeclaration(decl);

        VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(iVertexCount * 20, 20);

        float * vert = (float *)vb->Lock(0, 0, LOCK_DISCARD);
        {
            float x = 0, y = 0, z = 0;

            *vert++ = x; *vert++ = y; *vert++ = z;
            *vert++ = 0; *vert++ = 0;

            *vert++ = x; *vert++ = y; *vert++ = z;
            *vert++ = 1; *vert++ = 0;

            *vert++ = x; *vert++ = y; *vert++ = z;
            *vert++ = 0; *vert++ = 1;

            *vert++ = x; *vert++ = y; *vert++ = z;
            *vert++ = 1; *vert++ = 1;
        }
        vb->Unlock();

        vxStream->Bind(0, vb, 20);
        vxStream->SetCount(iVertexCount);

        mRender.iPrimCount = iPrimCount;
        mRender.ePrimType = PRIM_TRIANGLESTRIP;

        mRender.rState.blendMode = BM_ALPHA_BLEND;
        mRender.rState.depthWrite = false;
        mRender.rState.depthCheck = DCM_LESS_EQUAL;
    }
Beispiel #6
0
    void UnderWaterBubble::_geom()
    {
        VertexStream * vxStream = &mRender.vxStream;

        VertexBufferPtr vb = vxStream->GetStream(0);

        float * v = (float *)vb->Lock(0, 0, LOCK_DISCARD);
        {
            List<Bubble>::Iterator whr = mBubbles.Begin();
            List<Bubble>::Iterator end = mBubbles.End();

            while (whr != end)
            {
                const Bubble & b = *whr;
                *v++ = b.position.x;
                *v++ = b.position.y;
                *v++ = b.position.z;
                *v++ = b.size;
                *v++ = b.alpha;

                *v++ = b.position.x;
                *v++ = b.position.y;
                *v++ = b.position.z;
                *v++ = b.size;
                *v++ = b.alpha;

                *v++ = b.position.x;
                *v++ = b.position.y;
                *v++ = b.position.z;
                *v++ = b.size;
                *v++ = b.alpha;

                *v++ = b.position.x;
                *v++ = b.position.y;
                *v++ = b.position.z;
                *v++ = b.size;
                *v++ = b.alpha;

                ++whr;
            }
        }
        vb->Unlock();

        mRender.iPrimCount = mBubbles.Size() * 2;
    }
    i32 CreateCircle( Resources::CMesh* pMesh, const IInputLayout* pIL, const SCircleOptions& Options )
    {
        xst_vector< Vec3 > vPoints;
        f32 fAngle = 0.0f;
        for( u32 i = 0; i <= 360; i += Options.uStep )
        {
            fAngle = XST::Math::DegreesToRadians( (f32)i );
            vPoints.push_back( Vec3( XST::Math::Cos( fAngle ) * Options.fRadius, XST::Math::Sin( fAngle ) * Options.fRadius, 0.0f ) );
        }

        bool bIsNormal = pIL->IsNormal();
        ul32 ulVertCount = vPoints.size();
        VertexBufferPtr pVB = pMesh->CreateVertexBuffer();

        pVB->SetTopologyType( TopologyTypes::LINE_STRIP );
        pVB->SetUsage( BufferUsages::DEFAULT );
        pVB->SetVertexCount( ulVertCount );
        pVB->SetInputLayout( pIL );

        if( XST_FAILED( pVB->Lock() ) )
        {
            return XST_FAIL;
        }

        CVertexData& Data = pVB->GetVertexData();

        ul32 vs = pIL->GetVertexSize();

        for( u32 i = 0; i < vPoints.size(); ++i )
        {
            if( pIL->IsPosition() )
            {
                Data.SetPosition( i, vPoints[ i ] + Options.vecPos );
            }
        }

        if( XST_FAILED( pVB->Unlock() ) || XST_FAILED( pVB->Create() ) )
        {
            return XST_FAIL;
        }

        return XST_OK;
    }
Beispiel #8
0
SkinRenderer::SkinRenderer()
	: OnRender(RenderEvent::OnRenderGUI2, this, &SkinRenderer::Render)
{
	msInstance = this;

	mEnable = false;

	mRenderOp = new RenderOp;

	VertexDeclarationPtr vdecl = VideoBufferManager::Instance()->CreateVertexDeclaration();
	vdecl->AddElement(0, 0, DT_FLOAT2, DU_POSITION, 0);
	vdecl->Init();

	mRenderOp->vxStream.SetDeclaration(vdecl);

	VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(8 * 4, 8);

	float * vert = (float *)vb->Lock(0, 0, LOCK_NORMAL);
	{
		*vert++ = 0; *vert++ = 0;
		*vert++ = 1; *vert++ = 0;
		*vert++ = 0; *vert++ = 1;
		*vert++ = 1; *vert++ = 1;
	}
	vb->Unlock();

	mRenderOp->vxStream.Bind(0, vb);
	mRenderOp->vxStream.SetCount(4);

	mRenderOp->rState.depthCheck = DCM_NONE;
	mRenderOp->rState.depthWrite = false;
	mRenderOp->ePrimType = PRIM_TRIANGLESTRIP;
	mRenderOp->iPrimCount = 2;
	
	mTech = App::Instance()->GetShaderLib()->GetTechnique("SkinRenderer");

	d_assert (mTech != NULL);

	mBackTexture = VideoBufferManager::Instance()->Load2DTexture("BackgroundTile.png", "BackgroundTile.png");
}
Beispiel #9
0
EntityBound::EntityBound()
	: mRenderColMesh(NULL)
{
	mRenderAABB = new RenderOp();

	int iVertexCount = 8;
	int iIndexCount = 12 * 2;
	int iPrimCount = 12;

	mRenderAABB->vertexDeclarations[0].AddElement(eVertexSemantic::POSITION, eVertexType::FLOAT3);

	VertexBufferPtr vb = HWBufferManager::Instance()->NewVertexBuffer(iVertexCount, sizeof(float) * 3);
	float * vert = (float *)vb->Lock(eLockFlag::WRITE);
	{
		const float half_w = 0.5f;
		const float half_h = 0.5f;
		const float half_d = 0.5f;
		Float3 pos;

		//front
		pos = Float3(-half_w, half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Float3(half_w, half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Float3(-half_w, -half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Float3(half_w, -half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		//back
		pos = Float3(-half_w, half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Float3(half_w, half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Float3(-half_w, -half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Float3(half_w, -half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;
	}
	vb->Unlock();
	mRenderAABB->vertexBuffers[0] = vb;

	IndexBufferPtr ibuffer = HWBufferManager::Instance()->NewIndexBuffer(iIndexCount * sizeof(short));
	short * indices = (short *)ibuffer->Lock(eLockFlag::WRITE);
	{
		*indices++ = 0, *indices++ = 1;
		*indices++ = 2, *indices++ = 3;
		*indices++ = 0, *indices++ = 2;
		*indices++ = 1, *indices++ = 3;

		*indices++ = 4, *indices++ = 5;
		*indices++ = 6, *indices++ = 7;
		*indices++ = 4, *indices++ = 6;
		*indices++ = 5, *indices++ = 7;

		*indices++ = 0, *indices++ = 4;
		*indices++ = 1, *indices++ = 5;
		*indices++ = 2, *indices++ = 6;
		*indices++ = 3, *indices++ = 7;
	}
	ibuffer->Unlock();
	mRenderAABB->indexBuffer = ibuffer;

	mRenderAABB->primCount = iPrimCount;
	mRenderAABB->primType = ePrimType::LINE_LIST;

	Editor::Instance()->E_NodeSelect += new cListener0<EntityBound>(this, &EntityBound::OnShapeSelectedChanged);
	World::Instance()->E_RenderSolid += new cListener0<EntityBound>(this, &EntityBound::OnRender);
}
Beispiel #10
0
void SkyDome::_Initialize()
{
    int iVertexCount = (mRings + 1) * (mSegments + 1);
    int iIndexCount = mRings * mSegments * 6;
    int iPrimCount = iIndexCount / 3;

    debug_assert(iIndexCount < 65536, "index buffer too large.");

    VertexDeclarationPtr decl = VideoBufferManager::Instance().CreateVertexDeclaration();
    decl->AddElement(0, 0, DECLTYPE_FLOAT3, DECLMETHOD_DEFAULT, DECLUSAGE_POSITION, 0);
    decl->EndDecl();

    mVertexStream.SetDeclaration(decl);


    VertexBufferPtr buffer = VideoBufferManager::Instance().CreateVertexBuffer(iVertexCount * 12,
                                                                               USAGE_WRITEONLY,
                                                                               POOL_MANAGED);
    float * verteces;
    buffer->Lock(0, 0, (void**)&verteces, LOCK_DISCARD);
    {
        float fTileRingAngle = (Math::PI_1 / mRings);
        float fTileSegAngle = (Math::PI_2 / mSegments);
        float r;
        short i, j;
        Vec3 pos;

        for (i = 0; i <= mRings; ++i)
        {
            r = mRadius * Math::Sin(i * fTileRingAngle);
            pos.y = mRadius * Math::Cos(i * fTileRingAngle);

            for (j = 0; j <= mSegments; ++j)
            {
                pos.x = r * Math::Cos(j * fTileSegAngle);
                pos.z = r * Math::Sin(j * fTileSegAngle);

                *verteces++ = pos.x;
                *verteces++ = pos.y;
                *verteces++ = pos.z;
            }

        }
    }
    buffer->Unlock();

    mVertexStream.SetCount(iVertexCount);
    mVertexStream.Bind(0, buffer, 16);

    //index stream
    IndexBufferPtr ibuffer = VideoBufferManager::Instance().CreateIndexBuffer(iIndexCount * sizeof(short),
                                                                              USAGE_WRITEONLY,
                                                                              POOL_MANAGED,
                                                                              FMT_INDEX16);
    short * indices;
    ibuffer->Lock(0, 0, (void**)&indices, LOCK_DISCARD);
    {
        short row = 0, row_n = 0;
        short i, j;
        short iRings = (short)mRings;
        short iSegments = (short)mSegments;

        for (i = 0; i < iRings; ++i)
        {
            row_n = row + iSegments + 1;

            for (j = 0; j < iSegments; ++j)
            {
                *indices++ = row + j;
                *indices++ = row + j + 1;
                *indices++ = row_n + j;

                *indices++ = row_n + j;
                *indices++ = row + j + 1;
                *indices++ = row_n + j + 1;

            }

            row += iSegments + 1;
        }
    }
    ibuffer->Unlock();

    mIndexStream.SetCount(iIndexCount);
    mIndexStream.Bind(ibuffer, 0);

    SetPrimitiveCount(iPrimCount);
    SetPrimitiveType(PRIM_TRIANGLELIST);
}
Beispiel #11
0
	void MActorRes::_init()
	{
		_initMat();

		int iVertexCount = 0, iIndexCount = 0;
		mAabb = Aabb::Zero;

		//int numBoneForPrim = (DeviceCaps::Instance()->MaxVertexShaderConst() - K_NumNoSkinShaderConst) / 3;
		int numBoneForPrim = 50;

		MCore::Array<EMotionFX::HwShaderBuffer> hwShaderBufferArray;
		mActor->GenerateHardwareShaderBuffers(hwShaderBufferArray, 0, numBoneForPrim);

		mMeshCount = hwShaderBufferArray.Size();
		mMeshes = new SMesh[mMeshCount];

		for (int i = 0; i < mMeshCount; ++i)
		{
			EMotionFX::HwShaderBuffer & buffer = hwShaderBufferArray[i];

			int iVertexCount = buffer.GetNumVertices();
			bool skined = buffer.GetNumInfluences() > 0;
			int iStride = skined ? sizeof(VertexSkined) : sizeof(Vertex);

			VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(iStride * iVertexCount, iStride);

			void * vert = vb->Lock(0, 0, LOCK_DISCARD);

			if (skined)
				_fillVertexSkined(vert, buffer);
			else
				_fillVertexNoSkined(vert, buffer);
			
			vb->Unlock();

			int iIndexCount = buffer.GetNumIndices();
			d_assert(iIndexCount <= 65535);

			IndexBufferPtr ib = VideoBufferManager::Instance()->CreateIndexBuffer(sizeof(short) * iIndexCount);

			unsigned short * idx = (unsigned short *)ib->Lock(0, 0, LOCK_DISCARD);
			for (int k = 0; k < iIndexCount; ++k)
			{
				*idx++ = (unsigned short)buffer.GetIndex(k);
			}

			ib->Unlock();

			SMesh * smesh = &mMeshes[i];

			for (int b = 0; b < buffer.GetNumBones(); ++b)
			{
				smesh->BoneArray.PushBack(buffer.GetBone(b));
			}

			// update aabb
			for (int v = 0; v < iVertexCount; ++v)
			{
				EMotionFX::HwShaderVertex &	vtx		= buffer.GetVertex(v);
				EMotionFX::Mesh *			mesh	= vtx.GetMesh();
				MCore::Vector3 *			pPosAr	= mesh->GetPositions();
				const int					vtxNr	= vtx.GetVertexNumber();

				mAabb.Merge(Vec3(pPosAr[vtxNr].x, pPosAr[vtxNr].y, pPosAr[vtxNr].z));
			}

			const int numPrimitives = buffer.GetNumPrimitives();

			smesh->PrimCount = numPrimitives;
			smesh->Primitives = new SPrim[numPrimitives];

			for (int p=0; p<numPrimitives; ++p)
			{
				const EMotionFX::HwShaderPrimitive & bufferPrim	= buffer.GetPrimitive(p);
				SPrim & prim = smesh->Primitives[p];

				int StartVertex = bufferPrim.GetStartVertex();
				int NumVertices = bufferPrim.GetNumVertices();
				int StartIndex	= bufferPrim.GetStartIndex();
				int NumTriangles = bufferPrim.GetNumTriangles();

				prim.NodeId	= bufferPrim.GetNode()->GetID();
				prim.MaterialId	= bufferPrim.GetMaterialNr();
				
				prim.Rop.vxStream.SetDeclaration(MActorManager::Instance()->GetVertexDeclaration(skined));
				prim.Rop.vxStream.Bind(0, vb, iStride);
				prim.Rop.vxStream.SetStart(StartVertex);
				prim.Rop.vxStream.SetCount(NumVertices);

				prim.Rop.ixStream.Bind(ib, 0);
				prim.Rop.ixStream.SetStart(StartIndex);
				prim.Rop.ixStream.SetCount(iIndexCount);

				prim.Rop.iPrimCount = NumTriangles;
				prim.Rop.ePrimType = PRIM_TRIANGLELIST;

				SMtl * mtl = GetMaterial(prim.MaterialId);

				if (mtl->DoubleSide)
					prim.Rop.rState.cullMode = CULL_NONE;
			}
		}

		mSphere.center = mAabb.GetCenter();
		mSphere.radius = mSphere.center.Distance(mAabb.minimum);
	}
Beispiel #12
0
	Mesh * PS_MeshSet::_createCone(bool up)
	{
		Float3 offset = mCenter;
		int rings = (mRings + 3) / 4;
		int segments = mSegments;
		float radius = mRadius;
		float height = mHeight;

		if (rings < 1)
			return NULL;

		Mesh * pMesh = new Mesh;
		SubMesh * sm = pMesh->NewSubMesh();

		float h1 = up ? 0 : height;
		float h2 = up ? height : 0;

		int iVertexCount = 1 + (rings * 4 + 1);
		int iIndexCount = rings * 4 * 3;
		int iPrimCount = iIndexCount / 3;

		d_assert(iIndexCount < 65536);

		sm->GetRenderOp()->vertexDeclarations[0].AddElement(eVertexSemantic::POSITION, eVertexType::FLOAT3);
		sm->GetRenderOp()->vertexDeclarations[0].AddElement(eVertexSemantic::TEXCOORD0, eVertexType::FLOAT2);

		VertexBufferPtr buffer = HWBufferManager::Instance()->NewVertexBuffer(20, iVertexCount);

		float * vert = (float *)buffer->Lock(eLockFlag::WRITE);
		{
			float r_step = (PI2 / (rings * 4));
			float d_step = (radius * 2 / rings);
			float u_step = 1 / (float)rings;
			float v_step = u_step;
			float x, z;
			float rads = -PI * 0.25f;

			*vert++ = 0 + offset.x;
			*vert++ = h1 + offset.x;
			*vert++ = 0 + offset.z;
			*vert++ = 0.5f;
			*vert++ = 0.5f;

			// top
			for (int i = 0; i <= rings; ++i)
			{
				Math::SinCos(rads, z, x);

				x *= radius;
				z *= radius;

				*vert++ = x + offset.x;
				*vert++ = h2 + offset.y;
				*vert++ = z + offset.z;
				*vert++ = i * u_step;
				*vert++ = 0;

				rads += r_step;
			}

			// right
			for (int i = 1; i <= rings; ++i)
			{
				Math::SinCos(rads, z, x);

				x *= radius;
				z *= radius;

				*vert++ = x + offset.x;
				*vert++ = h2 + offset.y;
				*vert++ = z + offset.z;
				*vert++ = 1;
				*vert++ = i * v_step;

				rads += r_step;
			}

			// bottom
			for (int i = 1; i <= rings; ++i)
			{
				Math::SinCos(rads, z, x);

				x *= radius;
				z *= radius;

				*vert++ = x + offset.x;
				*vert++ = h2 + offset.y;
				*vert++ = z + offset.z;
				*vert++ = 1 - i * u_step;
				*vert++ = 1;

				rads += r_step;
			}

			// left
			for (int i = 1; i <= rings; ++i)
			{
				Math::SinCos(rads, z, x);

				x *= radius;
				z *= radius;

				*vert++ = x + offset.x;
				*vert++ = h2 + offset.y;
				*vert++ = z + offset.z;
				*vert++ = 0;
				*vert++ = 1 - i * u_step;

				rads += r_step;
			}
		}
		buffer->Unlock();

		IndexBufferPtr ibuffer = HWBufferManager::Instance()->NewIndexBuffer(iIndexCount);
		short * indices = (short *)ibuffer->Lock(eLockFlag::WRITE);
		{
			for (short i = 0; i < rings * 4; ++i)
			{
				*indices++ = i + 1;
				*indices++ = 0;
				*indices++ = i + 2;
			}
		}
		ibuffer->Unlock();

		sm->GetRenderOp()->vertexBuffers[0] = buffer;
		sm->GetRenderOp()->indexBuffer = ibuffer;
		sm->GetRenderOp()->primType = ePrimType::TRIANGLE_LIST;
		sm->GetRenderOp()->primCount = iPrimCount;

		sm->GetMaterial()->cullMode = eCullMode::NONE;
		sm->GetMaterial()->maps[eMapType::DIFFUSE] = RenderHelper::Instance()->GetWhiteTexture();

		pMesh->SetLocalAabb(Aabb(Float3(-radius, 0, -radius) + offset, Float3(radius, height, radius) + offset));

		return pMesh;
	}
Beispiel #13
0
	Mesh * PS_MeshSet::_createSphere()
	{
		Float3 offset = mCenter;
		int rings = mRings;
		int segments = mSegments;
		float radius = mRadius;

		if (rings < 1 || segments < 1)
			return NULL;

		Mesh * pMesh = new Mesh;
		SubMesh * sm = pMesh->NewSubMesh();

		int iVertexCount = (rings + 1) * (segments + 1);
		int iIndexCount = rings * segments * 6;
		int iPrimCount = iIndexCount / 3;

		d_assert(iIndexCount < 65536);

		sm->GetRenderOp()->vertexDeclarations[0].AddElement(eVertexSemantic::POSITION, eVertexType::FLOAT3);
		sm->GetRenderOp()->vertexDeclarations[0].AddElement(eVertexSemantic::TEXCOORD0, eVertexType::FLOAT2);

		VertexBufferPtr buffer = HWBufferManager::Instance()->NewVertexBuffer(20, iVertexCount);

		float * vert = (float *)buffer->Lock(eLockFlag::WRITE);
		{
			float fTileRingAngle = (PI / rings);
			float fTileSegAngle = (PI * 2 / segments);
			float u_step = 1 / (float)rings;
			float v_step = 1 / (float)segments;
			float r;
			short i, j;
			Float3 pos;

			for (i = 0; i <= rings; ++i)
			{
				r = radius * Math::Sin(i * fTileRingAngle);
				pos.y = radius * Math::Cos(i * fTileRingAngle);

				for (j = 0; j <= segments; ++j)
				{
					pos.x = r * Math::Cos(j * fTileSegAngle);
					pos.z = r * Math::Sin(j * fTileSegAngle);

					*vert++ = pos.x + offset.x;
					*vert++ = pos.y + offset.y;
					*vert++ = pos.z + offset.z;
					*vert++ = i * u_step;
					*vert++ = j * v_step;
				}

			}
		}
		buffer->Unlock();

		IndexBufferPtr ibuffer = HWBufferManager::Instance()->NewIndexBuffer(iIndexCount);
		short * indices = (short *)ibuffer->Lock(eLockFlag::WRITE);
		{
			short row = 0, row_n = 0;
			short i, j;

			for (i = 0; i < rings; ++i)
			{
				row_n = row + segments + 1;

				for (j = 0; j < segments; ++j)
				{
					*indices++ = row + j;
					*indices++ = row + j + 1;
					*indices++ = row_n + j;

					*indices++ = row_n + j;
					*indices++ = row + j + 1;
					*indices++ = row_n + j + 1;
				}

				row += segments + 1;
			}
		}
		ibuffer->Unlock();

		sm->GetRenderOp()->vertexBuffers[0] = buffer;
		sm->GetRenderOp()->indexBuffer = ibuffer;
		sm->GetRenderOp()->primCount = iPrimCount;
		sm->GetRenderOp()->primType= ePrimType::TRIANGLE_LIST;

		sm->GetMaterial()->maps[eMapType::DIFFUSE] = RenderHelper::Instance()->GetWhiteTexture();

		pMesh->SetLocalAabb(Aabb(Float3(-radius, -radius, -radius) + offset, Float3(radius, radius, radius) + offset));

		return pMesh;
	}
Beispiel #14
0
void MeshExporter::BuildMesh()
{
	for (int i = 0; i < mMMPairs.Size(); ++i)
	{
		MeshBuffer * mb = mMeshSource->NewMeshBuffer();
		RenderOp * rop = mb->GetRenderOp();
		int vertexCount = mMMPairs[i].mesh->mVertexList.Size();
		int indexCount = mMMPairs[i].mesh->mIndexList.Size();
		int vertexElems = mMMPairs[i].mesh->mVertexElems;

		if (vertexElems & MeshSerializer::VE_POSITION)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::POSITION, eVertexType::FLOAT3);
			
		if (vertexElems & MeshSerializer::VE_NORMAL)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::NORMAL, eVertexType::FLOAT3);
			
		if (vertexElems & MeshSerializer::VE_COLOR)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::COLOR, eVertexType::UBYTE4);
			
		if (vertexElems & MeshSerializer::VE_TANGENT)
			d_assert (0);
			
		if (vertexElems & MeshSerializer::VE_TEXCOORD)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::TEXCOORD0, eVertexType::FLOAT2);
			
		if (vertexElems & MeshSerializer::VE_LIGHTMAPUV)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::TEXCOORD1, eVertexType::FLOAT2);
			
		if (vertexElems & MeshSerializer::VE_BONEINDEX)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::BONE_INDEX, eVertexType::UBYTE4);
			
		if (vertexElems & MeshSerializer::VE_BONEWEIGHT)
			rop->vertexDeclarations[0].AddElement(eVertexSemantic::BONE_WEIGHT, eVertexType::FLOAT4);

		int stride = rop->vertexDeclarations[0].GetVertexSize();

		VertexBufferPtr vb = HWBufferManager::Instance()->NewVertexBuffer(stride, vertexCount);
		char * vdata = (char *)vb->Lock(eLockFlag::WRITE);
		for (int k = 0; k < vertexCount; ++k)
		{
			const Exporter::Vertex & v = mMMPairs[i].mesh->mVertexList.GetVertex(k);

			if (vertexElems & MeshSerializer::VE_POSITION)
				__vdata(vdata, &v.mPosition, sizeof(Float3));

			if (vertexElems & MeshSerializer::VE_NORMAL)
				__vdata(vdata, &v.mNormal, sizeof(Float3));

			if (vertexElems & MeshSerializer::VE_COLOR)
				__vdata(vdata, &v.mColor, sizeof(Float4));

			if (vertexElems & MeshSerializer::VE_TANGENT)
				__vdata(vdata, &v.mTangent, sizeof(Float3));

			if (vertexElems & MeshSerializer::VE_TEXCOORD)
				__vdata(vdata, &v.mTexcoord, sizeof(Float2));

			if (vertexElems & MeshSerializer::VE_LIGHTMAPUV)
				__vdata(vdata, &v.mLightmapUV, sizeof(Float2));

			if (vertexElems & MeshSerializer::VE_BONEINDEX)
				__vdata(vdata, &v.mBlendIndex, sizeof(Exporter::BlendIndex));

			if (vertexElems & MeshSerializer::VE_BONEWEIGHT)
				__vdata(vdata, &v.mBlendWeight, sizeof(Exporter::BlendWeight));
		}
		vb->Unlock();

		mb->GetBoneIdMap() = mMMPairs[i].mesh->mBoneIdMap;

		IndexBufferPtr ib = HWBufferManager::Instance()->NewIndexBuffer(indexCount);
		unsigned short * idata = (unsigned short *)ib->Lock(eLockFlag::WRITE);
		for (int k = 0; k < indexCount; ++k)
		{
			idata[k] = mMMPairs[i].mesh->mIndexList[k];
		}
		ib->Unlock();

		mb->GetRenderOp()->vertexBuffers[0] = vb;
		mb->GetRenderOp()->indexBuffer = ib;
		mb->GetRenderOp()->primCount = mMMPairs[i].mesh->mIndexList.Size() / 3;
		mb->GetRenderOp()->primType = ePrimType::TRIANGLE_LIST;

		if (mMMPairs[i].mtl != NULL)
		{
			_dumpMaterial(mb->GetMaterial(), mMMPairs[i].mtl);
		}
	}

	mMeshSource->GenAabbFromRenderMesh();

	for (int i = 0; i < mMMPairs.Size(); ++i)
	{
		delete mMMPairs[i].mesh;
	}

	mMMPairs.Clear();
}
Beispiel #15
0
void MeshLoader_v1::ReadSubMesh(SubMesh * sm, DataStreamPtr & stream)
{
	const int K_Version = 0;

	int iVersion;
	int iVertexCount;
	int iIndexCount;
	int iVertexElems;

	stream->Read(&iVersion, sizeof(int));

	d_assert (iVersion == K_SubMesh_Version || iVersion == K_SubMesh_Version_1);

	stream->Read(&iVertexCount, sizeof(int));
	stream->Read(&iIndexCount, sizeof(int));
	stream->Read(&iVertexElems, sizeof(int));

	int iPrimitiveCount = iIndexCount / 3;
	int iPrimitiveType = PRIM_TRIANGLELIST;

	d_assert (iVertexElems | VE_POSITION);

	sm->GetVertexStream()->SetCount(iVertexCount);
	sm->GetIndexStream()->SetCount(iIndexCount);
	sm->SetPrimitiveCount(iPrimitiveCount);
	sm->SetPrimitiveType((PRIMITIVE_TYPE)iPrimitiveType);

	VertexDeclarationPtr decl = VideoBufferManager::Instance()->CreateVertexDeclaration();
	
	int vstride = GenVertexDecl(decl, iVertexElems);

	VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(vstride * iVertexCount, vstride);

	void * vdata = vb->Lock(0, 0, LOCK_NORMAL);
	{
		stream->Read(vdata, vstride * iVertexCount);
	}
	vb->Unlock();

	bool index16 = true;
	if (iIndexCount > 65535)
		index16 = false;

	int istride = index16 ? 2 : 4;
	IndexBufferPtr ib = VideoBufferManager::Instance()->CreateIndexBuffer(istride * iIndexCount, index16);

	void * idata = ib->Lock(0, 0, LOCK_NORMAL);
	{
		stream->Read(idata, istride * iIndexCount);
	}
	ib->Unlock();

	sm->GetVertexStream()->SetDeclaration(decl);
	sm->GetVertexStream()->Bind(0, vb, vstride);
	sm->GetIndexStream()->Bind(ib, 0);

	if (iVersion >= K_SubMesh_Version_1)
	{
		Array<short> & boneMap = sm->GetBoneIdMap();

		int numBoneMap = 0;

		stream->Read(&numBoneMap, sizeof(int));

		if (numBoneMap > 0 && numBoneMap < MAX_BLEND_MATRIX_VS)
		{
			boneMap.Resize(numBoneMap);

			stream->Read(&boneMap[0], sizeof(short) * numBoneMap);
		}
	}

	ReadMaterial(sm, stream);
}
Beispiel #16
0
void SimpleObj::UpdateGeomtry()
{
    int decl_flag = _DECL_POSITION;

    if (m_normals.Size())
    {
        debug_assert(m_normals.Size() == mositions.Size(), "normal size != position size.");
        decl_flag |= _DECL_NORMAL;
    }

    if (m_colors.Size())
    {
        debug_assert(m_colors.Size() == mositions.Size(), "color size != position size.");
        decl_flag |= _DECL_COLOR;
    }

    if (m_texcoords.Size())
    {
        debug_assert(m_texcoords.Size() == mositions.Size(), "texcoord size != position size.");
        decl_flag |= _DECL_TEXCOORD;
    }

    int stride = 0;

    if (decl_flag != m_decl_flag)
    {
        VertexDeclarationPtr decl = VideoBufferManager::Instance().CreateVertexDeclaration();

        decl->AddElement(0, 0, DECLTYPE_FLOAT3, DECLMETHOD_DEFAULT, DECLUSAGE_POSITION, 0);
        stride += 12;

        if (decl_flag & _DECL_NORMAL)
        {
            decl->AddElement(0, stride, DECLTYPE_FLOAT3, DECLMETHOD_DEFAULT, DECLUSAGE_NORMAL, 0);
            stride += 12;
        }

        if (decl_flag & _DECL_COLOR)
        {
            decl->AddElement(0, stride, DECLTYPE_FLOAT4, DECLMETHOD_DEFAULT, DECLUSAGE_COLOR, 0);
            stride += 16;
        }

        if (decl_flag & _DECL_TEXCOORD)
        {
            decl->AddElement(0, stride, DECLTYPE_FLOAT2, DECLMETHOD_DEFAULT, DECLUSAGE_TEXCOORD, 0);
            stride += 8;
        }

        decl->EndDecl();

        m_decl_flag = decl_flag;

        mVertexStream.SetDeclaration(decl);
    }

    stride = mVertexStream.GetDeclaration()->GetStreamSize(0);

    int size = stride * mositions.Size();

    VertexBufferPtr buffer = mVertexStream.GetStream(0);

    if (buffer.IsNull() || buffer->GetSize() < size)
    {
        buffer = VideoBufferManager::Instance().CreateVertexBuffer(size, USAGE_WRITEONLY, POOL_MANAGED);
    }


    //Update Geomtry;

    Vector<Vec3>::Iterator      pi;
    Vector<Vec3>::Iterator      pe;
    Vector<Vec3>::Iterator      ni;
    Vector<Vec3>::Iterator      ne;
    Vector<Color4>::Iterator    ci;
    Vector<Color4>::Iterator    ce;
    Vector<Vec2>::Iterator      ti;
    Vector<Vec2>::Iterator      te;

    pi = mositions.Begin();
    pe = mositions.End();
    ni = m_normals.Begin();
    ne = m_normals.End();
    ci = m_colors.Begin();
    ce = m_colors.End();
    ti = m_texcoords.Begin();
    te = m_texcoords.End();

    char * verteces;
    buffer->Lock(0, 0, (void**)&verteces, LOCK_DISCARD);

    while (pi != pe)
    {
        int offset = 0;

        if (m_decl_flag & _DECL_POSITION)
        {
            float * position = (float*)(verteces + offset);

            if (pi != pe)
            {
                position[0] = pi->x;
                position[1] = pi->y;
                position[2] = pi->z;

                ++pi;
            }

            offset += sizeof(Vec3);
        }


        if (m_decl_flag & _DECL_NORMAL)
        {
            float * normal = (float*)(verteces + offset);

            if (ni != ne)
            {
                normal[0] = ni->x;
                normal[1] = ni->y;
                normal[2] = ni->z;

                ++ni;
            }

            offset += sizeof(Vec3);
        }

        if (m_decl_flag & _DECL_COLOR)
        {
            float * color = (float*)(verteces + offset);

            if (ci != ce)
            {
                color[0] = ci->r;
                color[1] = ci->g;
                color[2] = ci->b;
                color[3] = ci->a;

                ++ci;
            }

            offset += sizeof(Color4);
        }

        if (m_decl_flag & _DECL_TEXCOORD)
        {
            float * texcoord = (float*)(verteces + offset);

            if (ti != te)
            {
                texcoord[0] = ti->x;
                texcoord[1] = ti->y;

                ++ti;
            }
        }

        verteces += stride;
    }
    
    buffer->Unlock();

    mVertexStream.Bind(0, buffer, stride);
    mVertexStream.SetCount(mositions.Size());

    //update index buffer
    if (mndeces.Size())
    {
        debug_assert(mndeces.Size() < 65536, "Simple object index buffer is to large.");
        size = sizeof(short) * mndeces.Size();

        IndexBufferPtr ibuffer = mIndexStream.GetStream();
        
        if (mIndexStream.GetCount() < mndeces.Size())
        {
            ibuffer = VideoBufferManager::Instance().CreateIndexBuffer(size, USAGE_WRITEONLY, POOL_MANAGED, FMT_INDEX16);
        }

        short * indeces;
        ibuffer->Lock(0, 0, (void**)&indeces, LOCK_DISCARD);
        Memcpy(indeces, &mndeces[0], size);
        ibuffer->Unlock();

        mIndexStream.Bind(ibuffer, 0);
    }

    mIndexStream.SetCount(mndeces.Size());

    switch (mPrimType)
    {
    case PRIM_POINTLIST:
        SetPrimitiveCount(mndeces.Size() ? mndeces.Size() : mositions.Size());
        break;

    case PRIM_LINELIST:
        SetPrimitiveCount(mndeces.Size() ? mndeces.Size() / 2 : mositions.Size() / 2);
        break;

    case PRIM_LINESTRIP:
        SetPrimitiveCount(mndeces.Size() ? mndeces.Size() - 1 : mositions.Size() - 1);
        break;

    case PRIM_TRIANGLELIST:
        SetPrimitiveCount(mndeces.Size() ? mndeces.Size() / 3 : mositions.Size() / 3);
        break;

    case PRIM_TRIANGLESTRIP:
        SetPrimitiveCount(mndeces.Size() ? mndeces.Size() - 2 : mositions.Size() - 2);
        break;

    case PRIM_TRIANGLEFAN:
        SetPrimitiveCount(mndeces.Size() ? mndeces.Size() - 2 : mositions.Size() - 2);
        break;
    }
}
    i32 CreateBox(Resources::CMesh* pMesh, const IInputLayout* pIL, const SBoxOptions& Options)
    {
        bool bIsNormal = pIL->IsNormal();
        ul32 ulVertCount = ( bIsNormal )? 24 : 8; //if there are normals use more vertices
        ul32 ulIndexCount = 36;
        VertexBufferPtr pVB = pMesh->CreateVertexBuffer();
        
        pVB->SetTopologyType( TopologyTypes::TRIANGLE_LIST );
        pVB->SetUsage( BufferUsages::DEFAULT );
        pVB->SetVertexCount( ulVertCount );
        pVB->SetInputLayout( pIL );

        pVB->Lock();

        CVertexData& Data = pVB->GetVertexData();

        cf32 fUnit = 1.0f;
        ul32 vs = pIL->GetVertexSize();
        const Vec3 vecSize( Options.vecSize * 0.5f );
        const Vec3 vecPos( vecSize + Options.vecPos );

        if( pIL->IsPosition() )
        {
            if( bIsNormal )
            {
                Data.SetPosition( 0, Vec3( -vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos );
                Data.SetPosition( 1, Vec3( vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 2, Vec3( vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos  ); 
                Data.SetPosition( 3, Vec3( -vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos );

                Data.SetPosition( 4, Vec3( -vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos );
                Data.SetPosition( 5, Vec3( -vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 6, Vec3( -vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 7, Vec3( -vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos );

                Data.SetPosition( 8, Vec3( vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 9, Vec3( vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 10, Vec3( vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 11, Vec3( vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos ); 

                Data.SetPosition( 12, Vec3( -vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 13, Vec3( vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos );
                Data.SetPosition( 14, Vec3( vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 15, Vec3( -vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos );

                Data.SetPosition( 16, Vec3( -vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos );
                Data.SetPosition( 17, Vec3( vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos );
                Data.SetPosition( 18, Vec3( vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos  ); 
                Data.SetPosition( 19, Vec3( -vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos ); 

                Data.SetPosition( 20, Vec3( -vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 21, Vec3( vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 22, Vec3( vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 23, Vec3( -vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos ); 
                
            }
            else
            {
                Data.SetPosition( 0, Vec3( -vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 1, Vec3( vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 2, Vec3( vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 3, Vec3( -vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 4, Vec3( -vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 5, Vec3( vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 6, Vec3( vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos ); 
                Data.SetPosition( 7, Vec3( -vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos ); 
            }
        }

        if( pIL->IsColor() )
        {
            f32 fc = 0.05f;
            for(ul32 i = 0; i < ulVertCount; ++i)
            {
                /*Data.SetColor( 0, Vec4( 1, 0, 0, 1 ) ); 
                Data.SetColor( 1, Vec4( 1, 1, 1, 1 ) ); 
                Data.SetColor( 2, Vec4( 0, 1, 0, 1 ) ); 
                Data.SetColor( 3, Vec4( 0.5, 0.3, 1, 1 ) ); */
                Data.SetColor( i, Options.colColor.ToVector4() ); 
            }
        }

        if( bIsNormal )
        {
            Data.SetNormal( 0, Vec3( -1, 1, -1 ) ); 
            Data.SetNormal( 1, Vec3( 1, 1, -1 ) ); 
            Data.SetNormal( 2, Vec3( 1, 1, 1 ) ); 
            Data.SetNormal( 3, Vec3( -1, 1, 1 ) ); 
            Data.SetNormal( 4, Vec3( -1, -1, -1 ) ); 
            Data.SetNormal( 5, Vec3( 1, -1, -1 ) ); 
            Data.SetNormal( 6, Vec3( 1, -1, 1 ) ); 
            Data.SetNormal( 7, Vec3( -1, -1, 1 ) ); 
        }

        pVB->Unlock();
        pVB->Create();

        IndexBufferPtr pIB = pMesh->CreateIndexBuffer();
        pIB->SetUsage( BufferUsages::DEFAULT );
        pIB->SetIndexCount( ulIndexCount );
        pIB->Lock();

        CIndexData& IndexData = pIB->GetIndexData();

        if( bIsNormal )
        {
            //Front
            IndexData.AddTriangle( 3, 1, 0 );
            IndexData.AddTriangle( 2, 1, 3 );
            //Back
            IndexData.AddTriangle( 6, 4, 5 );
            IndexData.AddTriangle( 7, 4, 6 );
            //Top
            IndexData.AddTriangle( 11,9,8 );
            IndexData.AddTriangle( 10,9,11 );
            //Bottom
            IndexData.AddTriangle( 14,12,13 );
            IndexData.AddTriangle( 15,12,14 );
            //Left
            IndexData.AddTriangle( 19,17,16 );
            IndexData.AddTriangle( 18,17,19 );
            //Right
            IndexData.AddTriangle( 22,20,21 );
            IndexData.AddTriangle( 23,20,22 );
        }
        else
        {
            IndexData.AddTriangle( 3, 1, 0 );
            IndexData.AddTriangle( 2, 1, 3 );

            IndexData.AddTriangle( 0, 5, 4 );
            IndexData.AddTriangle( 1, 5, 0 );

            IndexData.AddTriangle( 3, 4, 7 );
            IndexData.AddTriangle( 0, 4, 3 );

            IndexData.AddTriangle( 1, 6, 5 );
            IndexData.AddTriangle( 2, 6, 1 );

            IndexData.AddTriangle( 2, 7, 6 );
            IndexData.AddTriangle( 3, 7, 2 );

            IndexData.AddTriangle( 6, 4, 5 );
            IndexData.AddTriangle( 7, 4, 6 );

        }

        XST_RET_FAIL( pIB->Unlock() );
        XST_RET_FAIL( pIB->Create() );

        CBoundingVolume Vol;
        Vol.BuildFromMinMax( -vecSize + Options.vecPos, vecSize + Options.vecPos );
        pMesh->SetBoundingVolume( Vol );

        return XST_OK;
    }
Beispiel #18
0
	Mesh * PS_MeshSet::_createClinder()
	{
		Float3 offset = mCenter;
		int rings = mRings;
		float radius = mRadius;
		float height = mHeight;

		if (rings < 1)
			return NULL;

		Mesh * pMesh = new Mesh;
		SubMesh * sm = pMesh->NewSubMesh();

		int iVertexCount = (rings + 1) * 2;
		int iIndexCount = rings * 6;
		int iPrimCount = iIndexCount / 3;

		d_assert(iIndexCount < 65536);

		sm->GetRenderOp()->vertexDeclarations[0].AddElement(eVertexSemantic::POSITION, eVertexType::FLOAT3);
		sm->GetRenderOp()->vertexDeclarations[0].AddElement(eVertexSemantic::TEXCOORD0, eVertexType::FLOAT2);

		VertexBufferPtr buffer = HWBufferManager::Instance()->NewVertexBuffer(20, iVertexCount);

		float * vert = (float *)buffer->Lock(eLockFlag::WRITE);
		{
			float r_step = (2 * PI / rings);
			float u_step = 1 / (float)rings;
			float x, z, rads;

			for (int i = 0; i <= rings; ++i)
			{
				rads = i * r_step;

				Math::SinCos(rads, z, x);

				x *= radius;
				z *= radius;

				*vert++ = x + offset.x;
				*vert++ = 0 + offset.y;
				*vert++ = z + offset.z;
				*vert++ = i * u_step;
				*vert++ = 1;

				*vert++ = x + offset.x;
				*vert++ = height + offset.y;
				*vert++ = z + offset.z;
				*vert++ = i * u_step;
				*vert++ = 0;
			}
		}
		buffer->Unlock();

		IndexBufferPtr ibuffer = HWBufferManager::Instance()->NewIndexBuffer(iIndexCount);
		short * indices = (short *)ibuffer->Lock(eLockFlag::WRITE);
		{
			for (short i = 0; i < rings; ++i)
			{
				int j = i * 2;

				*indices++ = j;
				*indices++ = j + 1;
				*indices++ = j + 2;

				*indices++ = j + 2;
				*indices++ = j + 1;
				*indices++ = j + 3;
			}
		}
		ibuffer->Unlock();

		sm->GetRenderOp()->vertexBuffers[0] = buffer;
		sm->GetRenderOp()->indexBuffer = ibuffer;
		sm->GetRenderOp()->primType = ePrimType::TRIANGLE_LIST;
		sm->GetRenderOp()->primCount = iPrimCount;

		sm->GetMaterial()->cullMode = eCullMode::NONE;
		sm->GetMaterial()->maps[eMapType::DIFFUSE] = RenderHelper::Instance()->GetWhiteTexture();

		pMesh->SetLocalAabb(Aabb(Float3(-radius, 0, -radius) + offset, Float3(radius, height, radius) + offset));

		return pMesh;
	}
    i32 CreateBox(Resources::CMesh* pMesh, const IInputLayout* pIL, const SLineBoxOptions& Options)
    {

        ul32 ulVertCount = 8; 
        ul32 ulIndexCount = 24; //8 * 2 + 2 * 4; 8 per front/back, 4 per left, right
        VertexBufferPtr pVB = pMesh->CreateVertexBuffer();
        
        pVB->SetTopologyType( TopologyTypes::LINE_LIST );
        pVB->SetUsage( BufferUsages::DEFAULT );
        pVB->SetVertexCount( ulVertCount );
        pVB->SetInputLayout( pIL );

        if( XST_FAILED( pVB->Lock() ) )
        {
            return XST_FAIL;
        }

        CVertexData& Data = pVB->GetVertexData();

        cf32 fUnit = 1.0f;
        ul32 vs = pIL->GetVertexSize();
        const Vec3 vecSize( Options.vecSize * 0.5f );
        const Vec3 vecPos( vecSize + Options.vecPos );

        Vec3 aCorners[ Resources::BoxCorners::_ENUM_COUNT ];
        aCorners[ Resources::BoxCorners::LEFT_BOTTOM_BACK ]	= Vec3( -vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::LEFT_BOTTOM_FRONT ]	= Vec3( -vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::LEFT_TOP_BACK ]		= Vec3( -vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::LEFT_TOP_FRONT ]		= Vec3( -vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::RIGHT_BOTTOM_BACK ]	= Vec3( vecSize.x, -vecSize.y, -vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::RIGHT_BOTTOM_FRONT ]	= Vec3( vecSize.x, -vecSize.y, vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::RIGHT_TOP_FRONT ]		= Vec3( vecSize.x, vecSize.y, vecSize.z ) + Options.vecPos;
        aCorners[ Resources::BoxCorners::RIGHT_TOP_BACK ]		= Vec3( vecSize.x, vecSize.y, -vecSize.z ) + Options.vecPos;

        /*for(i32 i = 0; i < BoxCorners::_ENUM_COUNT; ++i)
        {
            XST::CDebug::PrintDebugLN( XST::ToStr() << XST_GET_DBG_NAME( pMesh ) << (BOX_CORNER)i << aCorners[ i ] );
        }*/

        if( pIL->IsPosition() )
        {
            for(u32 i = 0; i < Resources::BoxCorners::_ENUM_COUNT; ++i)
            {
                Data.SetPosition( i, aCorners[ i ] );
            }
        }

        if( pIL->IsColor() )
        {
            f32 fc = 0.05f;
            for(ul32 i = 0; i < ulVertCount; ++i)
            {
                Data.SetColor( i, Options.colColor.ToVector4() ); 
            }
        }

        if( XST_FAILED( pVB->Unlock() ) )
        {
            return XST_FAIL;
        }

        IndexBufferPtr pIB = pMesh->CreateIndexBuffer();
        pIB->SetUsage( BufferUsages::DEFAULT );
        pIB->SetIndexCount( ulIndexCount );
        
        if( XST_FAILED( pIB->Lock() ) )
        {
            return XST_FAIL;
        }

        CIndexData& IData = pIB->GetIndexData();

        //Front
        IData.SetIndex( 0, Resources::BoxCorners::LEFT_BOTTOM_FRONT );
        IData.SetIndex( 1, Resources::BoxCorners::LEFT_TOP_FRONT );

        IData.SetIndex( 2, Resources::BoxCorners::LEFT_TOP_FRONT );
        IData.SetIndex( 3, Resources::BoxCorners::RIGHT_TOP_FRONT );

        IData.SetIndex( 4, Resources::BoxCorners::RIGHT_TOP_FRONT );
        IData.SetIndex( 5, Resources::BoxCorners::RIGHT_BOTTOM_FRONT );

        IData.SetIndex( 6, Resources::BoxCorners::RIGHT_BOTTOM_FRONT );
        IData.SetIndex( 7, Resources::BoxCorners::LEFT_BOTTOM_FRONT );
        
        //Back
        IData.SetIndex( 8, Resources::BoxCorners::LEFT_BOTTOM_BACK );
        IData.SetIndex( 9, Resources::BoxCorners::LEFT_TOP_BACK );

        IData.SetIndex( 10, Resources::BoxCorners::LEFT_TOP_BACK );
        IData.SetIndex( 11, Resources::BoxCorners::RIGHT_TOP_BACK );

        IData.SetIndex( 12, Resources::BoxCorners::RIGHT_TOP_BACK );
        IData.SetIndex( 13, Resources::BoxCorners::RIGHT_BOTTOM_BACK );

        IData.SetIndex( 14, Resources::BoxCorners::RIGHT_BOTTOM_BACK );
        IData.SetIndex( 15, Resources::BoxCorners::LEFT_BOTTOM_BACK );

        //Left
        IData.SetIndex( 16, Resources::BoxCorners::LEFT_BOTTOM_FRONT );
        IData.SetIndex( 17, Resources::BoxCorners::LEFT_BOTTOM_BACK );

        IData.SetIndex( 18, Resources::BoxCorners::LEFT_TOP_FRONT );
        IData.SetIndex( 19, Resources::BoxCorners::LEFT_TOP_BACK );

        //Right
        IData.SetIndex( 20, Resources::BoxCorners::RIGHT_BOTTOM_FRONT );
        IData.SetIndex( 21, Resources::BoxCorners::RIGHT_BOTTOM_BACK );

        IData.SetIndex( 22, Resources::BoxCorners::RIGHT_TOP_FRONT );
        IData.SetIndex( 23, Resources::BoxCorners::RIGHT_TOP_BACK );

        if( XST_FAILED( pIB->Unlock() ) )
        {
            return XST_FAIL;
        }

        CBoundingVolume Vol;
        Vol.BuildFromMinMax( aCorners[ Resources::BoxCorners::LEFT_BOTTOM_BACK ], aCorners[ Resources::BoxCorners::RIGHT_TOP_FRONT ] );
        pMesh->SetBoundingVolume( Vol );

        return XST_OK;
    }
Beispiel #20
0
void xObjBound::Init(Event * sender)
{
	mRenderAABB = new RenderOp();

	VertexStream * vxStream = &mRenderAABB->vxStream;
	IndexStream * ixStream = &mRenderAABB->ixStream;

	int iVertexCount = 8;
	int iIndexCount = 12 * 2;
	int iPrimCount = 12;

	VertexDeclarationPtr decl = VideoBufferManager::Instance()->CreateVertexDeclaration();
	decl->AddElement(0, 0, DT_FLOAT3, DU_POSITION, 0);
	decl->Init();

	vxStream->SetDeclaration(decl);

	VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(iVertexCount * 12, 12);

	float * vert = (float *)vb->Lock(0, 0, LOCK_DISCARD);
	{
		const float half_w = 0.5f;
		const float half_h = 0.5f;
		const float half_d = 0.5f;
		Vec3 pos;

		//front
		pos = Vec3(-half_w, half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Vec3(half_w, half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Vec3(-half_w, -half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Vec3(half_w, -half_h, -half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		//back
		pos = Vec3(-half_w, half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Vec3(half_w, half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Vec3(-half_w, -half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;

		pos = Vec3(half_w, -half_h, half_d);
		*vert++ = pos.x;
		*vert++ = pos.y;
		*vert++ = pos.z;
	}
	vb->Unlock();

	vxStream->Bind(0, vb, 12);
	vxStream->SetCount(iVertexCount);

	IndexBufferPtr ibuffer = VideoBufferManager::Instance()->CreateIndexBuffer(iIndexCount * sizeof(short));
	short * indices = (short *)ibuffer->Lock(0, 0, LOCK_DISCARD);
	{
		*indices++ = 0, *indices++ = 1;
		*indices++ = 2, *indices++ = 3;
		*indices++ = 0, *indices++ = 2;
		*indices++ = 1, *indices++ = 3;

		*indices++ = 4, *indices++ = 5;
		*indices++ = 6, *indices++ = 7;
		*indices++ = 4, *indices++ = 6;
		*indices++ = 5, *indices++ = 7;

		*indices++ = 0, *indices++ = 4;
		*indices++ = 1, *indices++ = 5;
		*indices++ = 2, *indices++ = 6;
		*indices++ = 3, *indices++ = 7;
	}
	ibuffer->Unlock();

	ixStream->SetCount(iIndexCount);
	ixStream->Bind(ibuffer, 0);

	mRenderAABB->iPrimCount = iPrimCount;
	mRenderAABB->ePrimType = PRIM_LINELIST;

	mRenderAABB->rState.cullMode = CULL_NONE;
	mRenderAABB->rState.blendMode = BM_OPATICY;

	mTech = Editor::Instance()->GetHelperShaderLib()->GetTechnique("Color");

	d_assert (mTech);

	mRenderColMesh = new RenderOp();
	mRenderColMesh->vxStream.SetDeclaration(decl);
	mRenderColMesh->ePrimType = PRIM_TRIANGLELIST;
	mRenderColMesh->rState.cullMode = CULL_NONE;
	mRenderColMesh->rState.fillMode = FILL_FRAME;
	mRenderColMesh->rState.blendMode = BM_OPATICY;
}
    i32 CreatePlane(Resources::CMesh* pMesh, const IInputLayout* pIL, const SPlaneOptions& Opts)
    {
        bool bIsNormal = pIL->IsNormal();
        u16 ulVVertCount = (u16)Opts.vecVertexCount.x;
        u16 ulHVertCount = (u16)Opts.vecVertexCount.y;
        ul32 ulVertCount = ulVVertCount * ulHVertCount;
        //ul32 ulIndexCount = 36;
        VertexBufferPtr pVB = pMesh->CreateVertexBuffer();
        pVB->SetInputLayout( pIL );
        
        pVB->SetTopologyType( TopologyTypes::TRIANGLE_STRIP );
        pVB->SetUsage( BufferUsages::DEFAULT );
        pVB->SetVertexCount( ulVertCount );
        pVB->SetInputLayout( pIL );

        pVB->Lock();

        CVertexData& Data = pVB->GetVertexData();

        cf32 fUnit = 1.0f;
        ul32 vs = pIL->GetVertexSize();
        Vec2 vecTC( Vec2::ZERO );
        Vec3 vecTmpPos;

        if( pIL->IsPosition() )
        {
            ul32 ulVertId = 0;
            Vec2 vecVertDist( Opts.vecSize.x / ( Opts.vecVertexCount.x - 1 ), Opts.vecSize.y / ( Opts.vecVertexCount.y - 1 ) );
            Vec2 vecPos( Vec2::ZERO );

            for(ul32 y = 0; y < ulVVertCount; ++y, vecPos.y += vecVertDist.y)
            {
                for(ul32 x = 0; x < ulHVertCount; ++x, vecPos.x += vecVertDist.x)
                {
                    vecTmpPos = Vec3( vecPos.x, 0, vecPos.y );
                    Data.SetPosition( ulVertId, vecTmpPos );
                    if( pIL->IsTexCoord0() )
                    {
                        vecTC.x = vecTmpPos.x / Opts.vecSize.x;
                        vecTC.y = vecTmpPos.z / Opts.vecSize.y;
                        Data.SetTexCoord0( ulVertId, vecTC );
                    }

                    ++ulVertId;
                }

                vecPos.x = 0.0f;
            }
        }

        if( pIL->IsColor() )
        {
            f32 fc = 0.05f;
            for(ul32 i = 0; i < ulVertCount; ++i)
            {
                Data.SetColor( i, XST::CColor::Random().ToVector4() + Vec4( 0.2f, 0.2f, 0.2f, 0.0f ) ); 
            }
        }

        if( bIsNormal )
        {
            for(u32 i = 0; i < ulVertCount; ++i)
            {
                Data.SetNormal( i, Opts.vecNormal );
            }
        }

        pVB->Unlock();
        pVB->Create();


        IndexBufferPtr pIB = pMesh->CreateIndexBuffer();
        pIB->SetUsage( BufferUsages::DEFAULT );
        u16 ulIndexCount = ( ulHVertCount * 2 ) * ( ulVVertCount - 1 ) + ( ulVVertCount - 2 );
        pIB->SetIndexCount( ulIndexCount );
        pIB->Lock();

        CIndexData& IndexData = pIB->GetIndexData();

        ul32 ulIndex = 0;
        for(u16 z = 0; z < ulVVertCount - 1; ++z)
        {
            if( z % 2 == 0 )
            {
                i16 x;
                for(x = 0; x < ulHVertCount; ++x )
                {
                    IndexData.SetIndex( ulIndex++, x + ( z * ulHVertCount ) );
                    IndexData.SetIndex( ulIndex++, x + ( z * ulHVertCount ) + ulHVertCount );
                }

                if( z != ulVVertCount - 2 )
                {
                    IndexData.SetIndex( ulIndex++, --x + ( z * ulHVertCount ) );
                }
            }
            else
            {
                i16 x;
                for(x = ulHVertCount - 1; x >= 0; --x )
                {
                    IndexData.SetIndex( ulIndex++, x + ( z * ulHVertCount ) );
                    IndexData.SetIndex( ulIndex++, x + ( z * ulHVertCount ) + ulHVertCount );
                }

                if( z != ulVVertCount - 2 )
                {
                    IndexData.SetIndex( ulIndex++, ++x + ( z * ulHVertCount ) );
                }
            }
        }

        pIB->Unlock();
        pIB->Create();

        return XST_OK;
    }
Beispiel #22
0
	void MeshGroup::_genMesh(const Array<Mesh *> & arr, int first, int last, bool hasLightingColor)
	{
		MeshSourcePtr source = arr[0]->GetSource();
		Mesh * mesh = new Mesh;

		for (int i = 0; i < source->GetMeshBufferCount(); ++i)
		{
			SubMesh * submesh = mesh->NewSubMesh();
			VertexBufferPtr srcVB = source->GetMeshBuffer(i)->GetRenderOp()->vertexBuffers[0];
			IndexBufferPtr srcIB = source->GetMeshBuffer(i)->GetRenderOp()->indexBuffer;
			int p_offset = source->GetMeshBuffer(i)->GetRenderOp()->vertexDeclarations[0].GetElementOffset(eVertexSemantic::POSITION);
			int n_offset = source->GetMeshBuffer(i)->GetRenderOp()->vertexDeclarations[0].GetElementOffset(eVertexSemantic::NORMAL);
			int stride = srcVB->GetStride();

			VertexBufferPtr vb = HWBufferManager::Instance()->NewVertexBuffer(stride, srcVB->GetCount() * (last - first));
			
			const char * v_src = (const char *)srcVB->Lock(eLockFlag::READ);
			char * v_dest = (char *)vb->Lock(eLockFlag::WRITE);
			for (int j = first; j < last; ++j)
			{
				const Mat4 & worldTM = arr[j]->GetWorldTM();
				bool hasScale = arr[j]->GetWorldScale() != Float3(1, 1, 1);

				for (int k = 0; k < srcVB->GetCount(); ++k)
				{
					memcpy(v_dest, v_src, stride);

					Float3 * position = (Float3 *)(v_dest + p_offset);
					position->TransformA(worldTM);
					
					if (n_offset != -1)
					{
						Float3 * normal = (Float3 *)(v_dest + n_offset);
						normal->TransformN(worldTM);

						if (hasScale)
						{
							normal->Normalize();
						}
					}

					v_dest += stride;
					v_src += stride;
				}
			}
			vb->Unlock();
			srcVB->Unlock();

			IndexBufferPtr ib = HWBufferManager::Instance()->NewIndexBuffer(srcIB->GetCount() * (last - first));

			int startVertex = 0;
			const short * i_src = (const short *)srcIB->Lock(eLockFlag::READ);
			char * i_dest = (char *)ib->Lock(eLockFlag::WRITE);
			for (int j = first; j < last; ++j)
			{
				for (int k = 0; k < srcIB->GetCount(); ++k)
				{
					*i_dest++ = (*i_src++) + startVertex;
				}

				startVertex += srcVB->GetCount();
			}
			ib->Unlock();
			srcIB->Unlock();
			
			submesh->GetRenderOp()->vertexDeclarations[0] = source->GetMeshBuffer(i)->GetRenderOp()->vertexDeclarations[0];
			submesh->GetRenderOp()->vertexBuffers[0] = vb;
			submesh->GetRenderOp()->indexBuffer = ib;
			submesh->GetRenderOp()->primCount = ib->GetCount() / 3;
			submesh->GetRenderOp()->primType = ePrimType::TRIANGLE_LIST;

			if (hasLightingColor)
			{
				int count = submesh->GetRenderOp()->vertexBuffers[0]->GetCount();
				submesh->GetRenderOp()->vertexDeclarations[LIGHTING_COLOR_STREAM].AddElement(eVertexSemantic::LIGHTING_COLOR, eVertexType::UBYTE4);
				submesh->GetRenderOp()->vertexBuffers[LIGHTING_COLOR_STREAM] = HWBufferManager::Instance()->NewVertexBuffer(4, count);

				Array<Rgba32> lightColors;
				Rgba32 * data = (Rgba32 *)submesh->GetRenderOp()->vertexBuffers[LIGHTING_COLOR_STREAM]->Lock(eLockFlag::WRITE);
				for (int j = first; j < last; ++j)
				{
					arr[j]->GetLightingColor(lightColors);
					d_assert (lightColors.Size() > 0);

					memcpy(data, &lightColors[0], 4 * count);

					startVertex += count;
					lightColors.Clear();
				}
				submesh->GetRenderOp()->vertexBuffers[LIGHTING_COLOR_STREAM]->Unlock();
			}

			*submesh->GetMaterial() = *source->GetMeshBuffer(i)->GetMaterial();

			submesh->SetMeshShader(source->GetMeshBuffer(i)->GetShader());
		}

		mesh->SetSLMode(hasLightingColor ? eStaticLightingMode::LIGHTING_COLOR : eStaticLightingMode::NONE);

		mMeshes.PushBack(mesh);
	}
Beispiel #23
0
	void WaterBlock::Init(Water* water, int x, int z)
	{
		Shudown();

		mWater = water;
		mIndexX = x;
		mIndexZ = z;

		Terrain * terrain = Environment::Instance()->GetTerrain();

		int startX = kBlockGridSize * x;
		int startZ = kBlockGridSize * z;
		int sizeZ = water->GetSizeZ() - 1;

		WaterIdentityVertex wiv;
		Array<unsigned short> indexArray;

		for (int j = startZ; j < startZ + kBlockGridSize; ++j)
		{
			for (int i = startX; i < startX + kBlockGridSize; ++i)
			{
				char flag = mWater->GetData(i, j);
				
				if (flag == 1)
				{
					int _x = i;
					int _y = sizeZ - j;

					Vec3 p0 = terrain->GetPosition(_x + 0, _y + 0);
					Vec3 p1 = terrain->GetPosition(_x + 1, _y + 0);
					Vec3 p2 = terrain->GetPosition(_x + 0, _y + 1);
					Vec3 p3 = terrain->GetPosition(_x + 1, _y + 1);

					int i0 = wiv.Add(_x + 0, _y + 0, p0);
					int i1 = wiv.Add(_x + 1, _y + 0, p1);
					int i2 = wiv.Add(_x + 0, _y + 1, p2);
					int i3 = wiv.Add(_x + 1, _y + 1, p3);

					indexArray.PushBack(i0);
					indexArray.PushBack(i1);
					indexArray.PushBack(i2);
					indexArray.PushBack(i3);

					mBound.Merge(p0);
					mBound.Merge(p1);
					mBound.Merge(p2);
					mBound.Merge(p3);
				}
			}
		}

		if (indexArray.Size() == 0)
			return ;

		mRenderOp = new RenderOp();

		mRenderOp->iPrimCount = indexArray.Size() - 2;
		mRenderOp->ePrimType = PRIM_TRIANGLELIST;

		int iVertexCount = wiv.vertArray.Size();
		int iIndexCount = mRenderOp->iPrimCount * 3;

		VertexDeclarationPtr vdecl = mWater->GetVertexDecl();

		VertexBufferPtr vb = VideoBufferManager::Instance()->CreateVertexBuffer(iVertexCount * sizeof(Vec3), sizeof(Vec3));
		Vec3 * vert = (Vec3 *)vb->Lock(0, 0, LOCK_DISCARD);
		{
			for (int i = 0; i < iVertexCount; ++i)
			{
				vert[i] = wiv.vertArray[i].position;
			}
		}
		vb->Unlock();

		mRenderOp->vxStream.SetDeclaration(vdecl);
		mRenderOp->vxStream.Bind(0, vb, sizeof(Vec3));
		mRenderOp->vxStream.SetCount(iVertexCount);

		IndexBufferPtr ib = VideoBufferManager::Instance()->CreateIndexBuffer(iIndexCount * sizeof(short));
		short * idx = (short *)ib->Lock(0, 0, LOCK_DISCARD);
		{
			for (int i = 0; i < indexArray.Size(); i += 4)
			{ 
				*idx++ = indexArray[i + 0];
				*idx++ = indexArray[i + 1];
				*idx++ = indexArray[i + 2];

				*idx++ = indexArray[i + 2];
				*idx++ = indexArray[i + 1];
				*idx++ = indexArray[i + 3];
			}
		}
		ib->Unlock();

		mRenderOp->ixStream.Bind(ib, 0);
		mRenderOp->ixStream.SetCount(iIndexCount);
	}