public static byte[] packAOToDXT5A(float[] AoVals, int numXVerts) { byte[] inData = new byte[AoVals.Length * 4]; int c = 0; for (int x = 0; x < numXVerts; x++) { for (int z = 0; z < numXVerts; z++) { int dstIndex = 4 * (x * numXVerts + z); int srcIndex = (x + numXVerts * z); float k = AoVals[srcIndex] > 1 ? 1 : AoVals[srcIndex]; inData[dstIndex + 0] = 1; inData[dstIndex + 1] = 1; inData[dstIndex + 2] = 1; inData[dstIndex + 3] = (byte)(k * 255); } } //for (int i = 0; i < AoVals.Length; i++) //{ // float k = AoVals[i] > 1 ? 1 : AoVals[i]; // inData[c++] = 1; // inData[c++] = 1; // inData[c++] = 1; // inData[c++] = (byte)(k * 255); //} byte[] outDat = null; int outMemSize = 0; ExportTo360.toCompressedFormat(inData, numXVerts, numXVerts, sizeof(UInt32), BDXTFormat.cDXT5A, eDXTQuality.cDXTQualityBest, ref outDat, ref outMemSize); //endianswap this data... int count = outMemSize; for (int i = 0; i < count - 1; i += 2) { byte a = outDat[i]; outDat[i] = outDat[i + 1]; outDat[i + 1] = a; } //swizzle this data inData = null; return(outDat); }
private void writeLightData(ref ExportSettings settings, ref ExportResults results) { if (!LightManager.hasTerrainLightData()) { return; } DateTime n = DateTime.Now; int width = TerrainGlobals.getTerrain().getNumXVerts(); int height = TerrainGlobals.getTerrain().getNumZVerts(); Vector3 [] lht = new Vector3[width * height]; //CLM this needs to be changed for batch exporting! LightManager.rasterTerrainLightsToExportGrid(lht); //convert our data to a DXT1 texture! //CLM this is swapped all to shit... WTF!? byte[] inData = new byte[width * height * 4]; int c = 0; //for (int i = 0; i < lht.Length; i++) for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { //as an encoding step, divide by our overbright (2) //now convert back to srgb int i = x * width + y; Vector3 v = lht[i]; v.X = (float)Math.Sqrt(BMathLib.Clamp((float)(v.X * 0.5), 0, 1)); v.Y = (float)Math.Sqrt(BMathLib.Clamp((float)(v.Y * 0.5), 0, 1)); v.Z = (float)Math.Sqrt(BMathLib.Clamp((float)(v.Z * 0.5), 0, 1)); inData[c++] = (byte)(BMathLib.Clamp(v.Z * 255 + 0.5f, 0, 255)); inData[c++] = (byte)(BMathLib.Clamp(v.Y * 255 + 0.5f, 0, 255)); inData[c++] = (byte)(BMathLib.Clamp(v.X * 255 + 0.5f, 0, 255)); inData[c++] = 0; } } byte[] outDat = null; int outMemSize = 0; ExportTo360.toCompressedFormat(inData, width, height, sizeof(UInt32), BDXTFormat.cDXT1, settings.ExportTextureCompressionQuality, ref outDat, ref outMemSize); //endianswap this data... int count = outMemSize; for (int i = 0; i < count - 1; i += 2) { byte a = outDat[i]; outDat[i] = outDat[i + 1]; outDat[i + 1] = a; } //tileswap byte[] tempbytearray = new byte[outDat.Length]; outDat.CopyTo(tempbytearray, 0); ExportTo360.tileCopy(ref tempbytearray, tempbytearray, (int)width, (int)height, (int)ExportTo360.eTileCopyFormats.cTCFMT_DXT1); tempbytearray.CopyTo(outDat, 0); tempbytearray = null; //WRITE THE CHUNK ECF.ECFChunkHolder chunkHolder = new ECF.ECFChunkHolder(); chunkHolder.mDataMemStream = new MemoryStream(); BinaryWriter binWriter = new BinaryWriter(chunkHolder.mDataMemStream); //just write the DXT1 texture binWriter.Write(Xbox_EndianSwap.endSwapI32(outMemSize)); binWriter.Write(outDat); ExportTo360.mECF.addChunk((int)eXTD_ChunkID.cXTD_LightingChunk, chunkHolder, binWriter.BaseStream.Length); binWriter.Close(); binWriter = null; chunkHolder.Close(); chunkHolder = null; results.terrainLightingMemorySize = outMemSize; TimeSpan ts = DateTime.Now - n; results.terrainLightingTime = ts.TotalMinutes; lht = null; inData = null; outDat = null; }