示例#1
0
        //-----------------------------------------------------------------------------------
        void heightFieldToChunk(HeightsGen hg, ref ExportResults results)
        {
            ECF.ECFChunkHolder chunkHolder = new ECF.ECFChunkHolder();
            chunkHolder.mDataMemStream = new MemoryStream();
            BinaryWriter binWriter = new BinaryWriter(chunkHolder.mDataMemStream);

            binWriter.Write(Xbox_EndianSwap.endSwapI32((int)hg.mHeightFieldAttributes.mWidth));
            binWriter.Write(Xbox_EndianSwap.endSwapI32((int)hg.mHeightFieldAttributes.mHeight));

            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mWorldMinY));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mWorldMaxY));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mWorldRangeY));

            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mBounds.min.X));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mBounds.min.Y));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mBounds.min.Z));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mBounds.max.X));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mBounds.max.Y));
            binWriter.Write(Xbox_EndianSwap.endSwapF32(hg.mHeightFieldAttributes.mBounds.max.Z));

            binWriteMatrix(binWriter, hg.mHeightFieldAttributes.mNormZToWorld);
            binWriteMatrix(binWriter, hg.mHeightFieldAttributes.mWorldToNormZ);


            binWriter.Write(Xbox_EndianSwap.endSwapI32(hg.mHeightFieldAttributes.mpTexelsHI.Length));
            int memSize = hg.mHeightFieldAttributes.mpTexelsHI.Length * 2 * sizeof(short);

            binWriter.Write(Xbox_EndianSwap.endSwapI32(memSize));

            //expect the texture as G16R16, NON FLOAT! Just 16 bits of short.
            int numShorts = hg.mHeightFieldAttributes.mpTexelsHI.Length * 2;

            short[] sArray = new short[numShorts];
            for (int i = 0; i < hg.mHeightFieldAttributes.mpTexelsHI.Length; i++)
            {
                sArray[i * 2 + 0] = (short)Xbox_EndianSwap.endSwapI16((ushort)hg.mHeightFieldAttributes.mpTexelsHI[i]);
                sArray[i * 2 + 1] = (short)Xbox_EndianSwap.endSwapI16((ushort)hg.mHeightFieldAttributes.mpTexelsLO[i]);
            }

            //tileswap
            short[] tempbytearray = new short[sArray.Length];
            sArray.CopyTo(tempbytearray, 0);
            ExportTo360.tileCopy(ref tempbytearray, tempbytearray, (int)hg.mHeightFieldAttributes.mWidth, (int)hg.mHeightFieldAttributes.mHeight, ExportTo360.eTileCopyFormats.cTCFMT_G16R16);
            //  tempbytearray.CopyTo(sArray, 0);
            for (int i = 0; i < tempbytearray.Length; i++)
            {
                binWriter.Write(tempbytearray[i]);
            }

            ExportTo360.mECF.addChunk((int)eXTH_ChunkID.cXTH_TerrainHeightfield, chunkHolder, binWriter.BaseStream.Length);
            binWriter.Close();
            binWriter = null;
            chunkHolder.Close();
            chunkHolder = null;

            results.terrainGPUHeighfieldMemory = memSize;
        }
示例#2
0
 public void endianSwap()
 {
     mHeaderMagic        = (uint)Xbox_EndianSwap.endSwapI32((int)mHeaderMagic);
     mHeaderSize         = (uint)Xbox_EndianSwap.endSwapI32((int)mHeaderSize);
     mHeaderAdler32      = (uint)Xbox_EndianSwap.endSwapI32((int)mHeaderAdler32);
     mFileSize           = (uint)Xbox_EndianSwap.endSwapI32((int)mFileSize);// totalheaderSize;
     mNumChunks          = (ushort)Xbox_EndianSwap.endSwapI16((ushort)mNumChunks);
     mFlags              = (ushort)Xbox_EndianSwap.endSwapI16((ushort)mFlags);
     mID                 = (uint)Xbox_EndianSwap.endSwapI32((int)mID);
     mChunkExtraDataSize = 0;
 }
示例#3
0
        private int writeFlightHeights()
        {
            TerrainGlobals.getEditor().getSimRep().getFlightRep().recalculateHeights();

            ECF.ECFChunkHolder chunkHolder = new ECF.ECFChunkHolder();
            chunkHolder.mDataMemStream = new MemoryStream();
            BinaryWriter binWriter = new BinaryWriter(chunkHolder.mDataMemStream);


            int width      = (int)TerrainGlobals.getEditor().getSimRep().getFlightRep().getNumXPoints();
            int numXBlocks = width / 8;

            if (width % 8 != 0)
            {
                numXBlocks++;
            }
            int newWidth = numXBlocks * 8;

            //write our header information.
            float heightTileScale = TerrainGlobals.getEditor().getSimRep().getFlightRep().getTileScale();


            binWriter.Write(Xbox_EndianSwap.endSwapI32(width));                 //numHeightVerts
            binWriter.Write(Xbox_EndianSwap.endSwapI32(newWidth));              //numHeightVertsCacheFeriently
            binWriter.Write(Xbox_EndianSwap.endSwapF32(heightTileScale));       //height tile scale



            //swizzle our data to be more cache friendly..

            //first, padd our data to the next multiple of 8
            float[] tvals = new float[newWidth * newWidth];
            for (int i = 0; i < width; i++)
            {
                for (int k = 0; k < width; k++)
                {
                    int dstIndex = i + k * newWidth;
                    tvals[dstIndex] = TerrainGlobals.getEditor().getSimRep().getFlightRep().getCompositeHeight(k, i);// heights[srcIndex];
                }
            }


            ////now swizzle the bastard.
            int blockSize = 8;

            float[] kvals   = new float[newWidth * newWidth];
            int     dstIndx = 0;

            for (int x = 0; x < numXBlocks; x++)
            {
                for (int z = 0; z < numXBlocks; z++)
                {
                    int blockIndex = x + z * numXBlocks;
                    //swizzle create this block
                    for (int i = 0; i < blockSize; i++)
                    {
                        for (int j = 0; j < blockSize; j++)
                        {
                            int k = (z * blockSize) + j; // (blockSize - 1 - j);
                            int l = (x * blockSize) + i; // (blockSize - 1 - i);

                            int srcIndx = k * newWidth + l;
                            //int dstIndx = i * blockSize + j;
                            kvals[dstIndx++] = tvals[srcIndx];
                        }
                    }
                }
            }


            //convert to float16 & write to disk.
            float16[] sList = BMathLib.Float32To16Array(kvals);
            for (int c = 0; c < sList.Length; c++)
            {
                ushort s = ((ushort)sList[c].getInternalDat());
                binWriter.Write(Xbox_EndianSwap.endSwapI16(s));
            }


            ExportTo360.mECF.addChunk((int)eXSD_ChunkID.cXSD_FlightHeights, chunkHolder, binWriter.BaseStream.Length);
            binWriter.Close();
            binWriter = null;
            chunkHolder.Close();
            chunkHolder = null;

            return(tvals.Length * sizeof(ushort));
        }
示例#4
0
        public void exportRoads(ref ExportResults results)
        {
            DateTime n = DateTime.Now;

            //for each road,
            for (int roadIndex = 0; roadIndex < RoadManager.giveNumRoads(); roadIndex++)
            {
                List <RoadTriangle> triList = new List <RoadTriangle>();
                Road rd = RoadManager.giveRoad(roadIndex);

                if (rd.getNumControlPoints() == 0) //don't export roads w/o points on the map
                {
                    continue;
                }

                //Step 1, generate polygon lists////////////////////////////////////////////////////
                for (int rcpIndex = 0; rcpIndex < rd.getNumControlPoints(); rcpIndex++)
                {
                    roadControlPoint rcp = rd.getPoint(rcpIndex);
                    int numTris          = (int)(rcp.mVerts.Count / 3);
                    for (int triIndex = 0; triIndex < numTris; triIndex++)
                    {
                        RoadTriangle rt = new RoadTriangle();
                        rt.mVerts[0]      = new RoadVert();
                        rt.mVerts[0].mPos = new Vector3(rcp.mVerts[triIndex * 3 + 0].x, rcp.mVerts[triIndex * 3 + 0].y, rcp.mVerts[triIndex * 3 + 0].z);
                        rt.mVerts[0].mUv0 = new Vector2(rcp.mVerts[triIndex * 3 + 0].u0, rcp.mVerts[triIndex * 3 + 0].v0);

                        rt.mVerts[1]      = new RoadVert();
                        rt.mVerts[1].mPos = new Vector3(rcp.mVerts[triIndex * 3 + 1].x, rcp.mVerts[triIndex * 3 + 1].y, rcp.mVerts[triIndex * 3 + 1].z);
                        rt.mVerts[1].mUv0 = new Vector2(rcp.mVerts[triIndex * 3 + 1].u0, rcp.mVerts[triIndex * 3 + 1].v0);

                        rt.mVerts[2]      = new RoadVert();
                        rt.mVerts[2].mPos = new Vector3(rcp.mVerts[triIndex * 3 + 2].x, rcp.mVerts[triIndex * 3 + 2].y, rcp.mVerts[triIndex * 3 + 2].z);
                        rt.mVerts[2].mUv0 = new Vector2(rcp.mVerts[triIndex * 3 + 2].u0, rcp.mVerts[triIndex * 3 + 2].v0);


                        triList.Add(rt);
                    }
                }

                //now add our triStrip segments (into triLists)
                for (int segIndex = 0; segIndex < rd.getNumRoadSegments(); segIndex++)
                {
                    roadSegment rs        = rd.getRoadSegment(segIndex);
                    int         numTris   = rs.mNumVerts - 2;
                    int         vertIndex = rs.mStartVertInParentSegment + 2;
                    for (int i = 0; i < numTris; i++)
                    {
                        RoadTriangle rt = new RoadTriangle();
                        rt.mVerts[0]      = new RoadVert();
                        rt.mVerts[0].mPos = new Vector3(rd.mVerts[vertIndex - 2].x, rd.mVerts[vertIndex - 2].y, rd.mVerts[vertIndex - 2].z);
                        rt.mVerts[0].mUv0 = new Vector2(rd.mVerts[vertIndex - 2].u0, rd.mVerts[vertIndex - 2].v0);

                        rt.mVerts[1]      = new RoadVert();
                        rt.mVerts[1].mPos = new Vector3(rd.mVerts[vertIndex - 1].x, rd.mVerts[vertIndex - 1].y, rd.mVerts[vertIndex - 1].z);
                        rt.mVerts[1].mUv0 = new Vector2(rd.mVerts[vertIndex - 1].u0, rd.mVerts[vertIndex - 1].v0);

                        rt.mVerts[2]      = new RoadVert();
                        rt.mVerts[2].mPos = new Vector3(rd.mVerts[vertIndex].x, rd.mVerts[vertIndex].y, rd.mVerts[vertIndex].z);
                        rt.mVerts[2].mUv0 = new Vector2(rd.mVerts[vertIndex].u0, rd.mVerts[vertIndex].v0);



                        triList.Add(rt);
                        vertIndex++;
                    }
                }


                //Step 2, split Polygons////////////////////////////////////////////////////
                int width     = (int)(BTerrainQuadNode.cMaxWidth);
                int numPlanes = (int)(TerrainGlobals.getTerrain().getNumXVerts() / width);

                //Split along XPlane
                for (int planeIndex = 0; planeIndex < numPlanes; planeIndex++)
                {
                    Plane pl = Plane.FromPointNormal(new Vector3(planeIndex * width * TerrainGlobals.getTerrain().getTileScale(), 0, 0), BMathLib.unitX);
                    splitPolyListAgainstPlane(pl, triList);
                }

                //split along ZPlane
                for (int planeIndex = 0; planeIndex < numPlanes; planeIndex++)
                {
                    Plane pl = Plane.FromPointNormal(new Vector3(0, 0, planeIndex * width * TerrainGlobals.getTerrain().getTileScale()), BMathLib.unitZ);
                    splitPolyListAgainstPlane(pl, triList);
                }

                //Step 3, add polies to qn./////////////////////////////////////////////////
                List <RoadQN> roadQNs = new List <RoadQN>();
                int           numQNs  = (int)(TerrainGlobals.getTerrain().getNumXVerts() / width);
                int           qnWidth = (int)(width * TerrainGlobals.getTerrain().getTileScale());
                for (int qnX = 0; qnX < numQNs; qnX++)
                {
                    for (int qnZ = 0; qnZ < numQNs; qnZ++)
                    {
                        float  x   = qnX * qnWidth;
                        float  z   = qnZ * qnWidth;
                        RoadQN rqn = new RoadQN();

                        for (int triIndex = 0; triIndex < triList.Count; triIndex++)
                        {
                            if (triContainedInBox(triList[triIndex], x, z, x + qnWidth, z + qnWidth))
                            {
                                triList[triIndex].ensureWinding();
                                rqn.mTris.Add(triList[triIndex]);
                                rqn.mOwnerQNIndex = qnX * numQNs + qnZ;
                            }
                        }

                        if (rqn.mTris.Count != 0)
                        {
                            roadQNs.Add(rqn);
                        }
                    }
                }

                //Step 4, write road chunk to disk./////////////////////////////////////////////
                ECF.ECFChunkHolder chunkHolder = new ECF.ECFChunkHolder();
                chunkHolder.mDataMemStream = new MemoryStream();
                BinaryWriter binWriter = new BinaryWriter(chunkHolder.mDataMemStream);

                //Filename
                string fName = CoreGlobals.getWorkPaths().mRoadsPath + "\\" + rd.getRoadTextureName();
                fName = fName.Remove(0, CoreGlobals.getWorkPaths().mGameArtDirectory.Length + 1);
                char[] filename = new char[32];
                fName.CopyTo(0, filename, 0, fName.Length);
                binWriter.Write(filename);

                ExportTo360.addTextureChannelDependencies(CoreGlobals.getWorkPaths().mRoadsPath + "\\" + rd.getRoadTextureName());

                float zero        = 0;
                int   totalMemory = 0;
                //write our chunks
                binWriter.Write(Xbox_EndianSwap.endSwapI32(roadQNs.Count));
                for (int qnI = 0; qnI < roadQNs.Count; qnI++)
                {
                    binWriter.Write(Xbox_EndianSwap.endSwapI32(roadQNs[qnI].mOwnerQNIndex));
                    binWriter.Write(Xbox_EndianSwap.endSwapI32(roadQNs[qnI].mTris.Count));
                    int memSize = roadQNs[qnI].mTris.Count * (3 * (sizeof(short) * 6));
                    binWriter.Write(Xbox_EndianSwap.endSwapI32(memSize));

                    List <float> vList = new List <float>();
                    for (int c = 0; c < roadQNs[qnI].mTris.Count; c++)
                    {
                        for (int i = 0; i < 3; i++)
                        {
                            vList.Add(roadQNs[qnI].mTris[c].mVerts[i].mPos.X);
                            vList.Add(roadQNs[qnI].mTris[c].mVerts[i].mPos.Y);
                            vList.Add(roadQNs[qnI].mTris[c].mVerts[i].mPos.Z);
                            vList.Add(zero); //padd;
                            vList.Add(roadQNs[qnI].mTris[c].mVerts[i].mUv0.X);
                            vList.Add(roadQNs[qnI].mTris[c].mVerts[i].mUv0.Y);
                        }
                    }
                    float16[] sList = BMathLib.Float32To16Array(vList.ToArray());
                    for (int c = 0; c < vList.Count; c++)
                    {
                        ushort s = ((ushort)sList[c].getInternalDat());
                        binWriter.Write(Xbox_EndianSwap.endSwapI16(s));
                    }
                    totalMemory += memSize;
                }

                ExportTo360.mECF.addChunk((int)eXTT_ChunkID.cXTT_RoadsChunk, chunkHolder, binWriter.BaseStream.Length);
                binWriter.Close();
                binWriter = null;
                chunkHolder.Close();
                chunkHolder = null;

                roadQNs.Clear();
                triList.Clear();

                TimeSpan ts = DateTime.Now - n;
                results.terrainRoadTime   = ts.TotalMinutes;
                results.terrainRoadMemory = totalMemory;
            }
        }
示例#5
0
        private int simHeightsToChunk()
        {
            ECF.ECFChunkHolder chunkHolder = new ECF.ECFChunkHolder();
            chunkHolder.mDataMemStream = new MemoryStream();
            BinaryWriter binWriter = new BinaryWriter(chunkHolder.mDataMemStream);

            int width = (TerrainGlobals.getEditor().getSimRep().getNumXVerts() - 1) * cSimHeightResMultiplier + 1;


            //float[] heights = TerrainGlobals.getEditor().getSimRep().getHeightRep().get.getSimHeights();
            //CLM : INFACT! Don't even consider doing this....
            //our res is good enough..
            //if (cSimHeightResMultiplier!=1)
            //{
            //   heights = new float[width * width];

            //   //CLM Generate a higher res Sim Heights rep
            //   int xRes = 2048;
            //   float[] gpuHeightRepArray = new float[xRes * xRes];
            //   TerrainGlobals.getEditor().getSimRep().genHeightGPU(xRes, ref gpuHeightRepArray);

            //   float[] resPlusOne = ImageManipulation.resizeF32Img(gpuHeightRepArray, xRes, xRes, width - 1, width - 1, ImageManipulation.eFilterType.cFilter_Linear);//new float[xRes * xRes];
            //   for (int x = 0; x < width - 1; x++)
            //   {
            //      for (int z = 0; z < width - 1; z++)
            //      {
            //         heights[x * width + z] = resPlusOne[x * (width - 1) + z];
            //      }
            //   }

            //   //fill our edges with the previous height val.
            //   for (int q = 0; q < width - 1; q++)
            //   {
            //      heights[(width - 1) * width + q] = heights[(width - 2) * width + q];
            //      heights[q * width + (width - 1)] = heights[q * width + (width - 2)];
            //   }

            //   resPlusOne = null;
            //}

            //find our xbox specific terrain representation (close)
            float min   = 9000;
            float max   = -9000;
            float range = 0;

            findMaxsMinsRange(ref max, ref min, ref range);
            float adjustedMid = calcAdjustedMidValue(min);



            int numXBlocks = width / 8;

            if (width % 8 != 0)
            {
                numXBlocks++;
            }
            int newWidth = numXBlocks * 8;

            //swizzle our data to be more cache friendly..

            //first, padd our data to the next multiple of 8
            float[] tvals = new float[newWidth * newWidth];
            for (int i = 0; i < width; i++)
            {
                for (int k = 0; k < width; k++)
                {
                    int srcIndex = i + k * width;
                    int dstIndex = i + k * newWidth;
                    tvals[dstIndex] = TerrainGlobals.getEditor().getSimRep().getHeightRep().getCompositeHeight(k, i);//heights[srcIndex];

                    //  int v = (int)packPosTo32Bits(tvals[dstIndex], min, range);
                    //  unpackVisualToPos(v, ref tvals[dstIndex], ref adjustedMid, ref range);
                }
            }


            ////now swizzle the bastard.
            int blockSize = 8;

            float[] kvals   = new float[newWidth * newWidth];
            int     dstIndx = 0;

            for (int x = 0; x < numXBlocks; x++)
            {
                for (int z = 0; z < numXBlocks; z++)
                {
                    int blockIndex = x + z * numXBlocks;
                    //swizzle create this block
                    for (int i = 0; i < blockSize; i++)
                    {
                        for (int j = 0; j < blockSize; j++)
                        {
                            int k = (z * blockSize) + j; // (blockSize - 1 - j);
                            int l = (x * blockSize) + i; // (blockSize - 1 - i);

                            int srcIndx = k * newWidth + l;
                            //int dstIndx = i * blockSize + j;
                            kvals[dstIndx++] = tvals[srcIndx];
                        }
                    }
                }
            }

            //FileStream st = File.Open("outTT.raw", FileMode.OpenOrCreate, FileAccess.Write);
            //BinaryWriter ft = new BinaryWriter(st);

            //convert to float16 & write to disk.
            float16[] sList = BMathLib.Float32To16Array(kvals);
            for (int c = 0; c < sList.Length; c++)
            {
                ushort s = ((ushort)sList[c].getInternalDat());
                binWriter.Write(Xbox_EndianSwap.endSwapI16(s));
                //ft.Write(s);
            }
            //ft.Close();
            //st.Close();


            ExportTo360.mECF.addChunk((int)eXSD_ChunkID.cXSD_SimHeights, chunkHolder, binWriter.BaseStream.Length);
            binWriter.Close();
            binWriter = null;
            chunkHolder.Close();
            chunkHolder = null;

            //heights = null;

            return(tvals.Length * sizeof(ushort));
        }