diff options
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/TerrainCompressor.cs')
-rw-r--r-- | OpenSim/Region/Framework/Scenes/TerrainCompressor.cs | 59 |
1 files changed, 25 insertions, 34 deletions
diff --git a/OpenSim/Region/Framework/Scenes/TerrainCompressor.cs b/OpenSim/Region/Framework/Scenes/TerrainCompressor.cs index 2e856bc..511745d 100644 --- a/OpenSim/Region/Framework/Scenes/TerrainCompressor.cs +++ b/OpenSim/Region/Framework/Scenes/TerrainCompressor.cs | |||
@@ -113,22 +113,17 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
113 | // routines (like IClientAPI) only pass the float array of heights around. This entry | 113 | // routines (like IClientAPI) only pass the float array of heights around. This entry |
114 | // converts that legacy representation into the more compact represenation used in | 114 | // converts that legacy representation into the more compact represenation used in |
115 | // TerrainChannel. Someday fix the plumbing between here and the scene. | 115 | // TerrainChannel. Someday fix the plumbing between here and the scene. |
116 | public static LayerDataPacket CreateLandPacket(float[] heightmap, int patchX, int patchY, uint sizeX, uint sizeY) | 116 | public static LayerDataPacket CreateLandPacket(TerrainData terrData, int patchX, int patchY) |
117 | { | 117 | { |
118 | int[] xPieces = new int[1]; | 118 | int[] xPieces = new int[1]; |
119 | int[] yPieces = new int[1]; | 119 | int[] yPieces = new int[1]; |
120 | |||
121 | short[] newmap = new short[heightmap.Length]; | ||
122 | for (int ii = 0; ii < heightmap.Length; ii++) | ||
123 | newmap[ii] = TerrainChannel.ToCompressedHeight(heightmap[ii]); | ||
124 | |||
125 | xPieces[0] = patchX; // patch X dimension | 120 | xPieces[0] = patchX; // patch X dimension |
126 | yPieces[0] = patchY; | 121 | yPieces[0] = patchY; |
127 | 122 | ||
128 | m_log.DebugFormat("{0} CreateLandPacket. patchX={1}, patchY={2}, sizeX={3}, sizeY={4}", | 123 | m_log.DebugFormat("{0} CreateLandPacket. patchX={1}, patchY={2}, sizeX={3}, sizeY={4}", |
129 | LogHeader, patchX, patchY, sizeX, sizeY); | 124 | LogHeader, patchX, patchY, terrData.SizeX, terrData.SizeY); |
130 | 125 | ||
131 | return CreateLandPacket(newmap, xPieces, yPieces, (int)TerrainPatch.LayerType.Land, sizeX, sizeY); | 126 | return CreateLandPacket(terrData, xPieces, yPieces, (int)TerrainPatch.LayerType.Land); |
132 | } | 127 | } |
133 | 128 | ||
134 | /// <summary> | 129 | /// <summary> |
@@ -153,8 +148,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
153 | /// <param name="pRegionSizeX"></param> | 148 | /// <param name="pRegionSizeX"></param> |
154 | /// <param name="pRegionSizeY"></param> | 149 | /// <param name="pRegionSizeY"></param> |
155 | /// <returns></returns> | 150 | /// <returns></returns> |
156 | public static LayerDataPacket CreateLandPacket(short[] heightmap, int[] x, int[] y, byte type, | 151 | public static LayerDataPacket CreateLandPacket(TerrainData terrData, int[] x, int[] y, byte type) |
157 | uint pRegionSizeX, uint pRegionSizeY) | ||
158 | { | 152 | { |
159 | LayerDataPacket layer = new LayerDataPacket {LayerID = {Type = type}}; | 153 | LayerDataPacket layer = new LayerDataPacket {LayerID = {Type = type}}; |
160 | 154 | ||
@@ -168,7 +162,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
168 | bitpack.PackBits(type, 8); | 162 | bitpack.PackBits(type, 8); |
169 | 163 | ||
170 | for (int i = 0; i < x.Length; i++) | 164 | for (int i = 0; i < x.Length; i++) |
171 | CreatePatchFromHeightmap(bitpack, heightmap, x[i], y[i], pRegionSizeX, pRegionSizeY); | 165 | CreatePatchFromHeightmap(bitpack, terrData, x[i], y[i]); |
172 | 166 | ||
173 | bitpack.PackBits(END_OF_PATCHES, 8); | 167 | bitpack.PackBits(END_OF_PATCHES, 8); |
174 | 168 | ||
@@ -217,14 +211,13 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
217 | /// </param> | 211 | /// </param> |
218 | /// <param name="pRegionSizeX"></param> | 212 | /// <param name="pRegionSizeX"></param> |
219 | /// <param name="pRegionSizeY"></param> | 213 | /// <param name="pRegionSizeY"></param> |
220 | public static void CreatePatchFromHeightmap(BitPack output, short[] heightmap, int patchX, int patchY, | 214 | public static void CreatePatchFromHeightmap(BitPack output, TerrainData terrData, int patchX, int patchY) |
221 | uint pRegionSizeX, uint pRegionSizeY) | ||
222 | { | 215 | { |
223 | TerrainPatch.Header header = PrescanPatch(heightmap, patchX, patchY, pRegionSizeX, pRegionSizeY); | 216 | TerrainPatch.Header header = PrescanPatch(terrData, patchX, patchY); |
224 | header.QuantWBits = 136; | 217 | header.QuantWBits = 136; |
225 | 218 | ||
226 | // If larger than legacy region size, pack patch X and Y info differently. | 219 | // If larger than legacy region size, pack patch X and Y info differently. |
227 | if (pRegionSizeX > Constants.RegionSize || pRegionSizeY > Constants.RegionSize) | 220 | if (terrData.SizeX > Constants.RegionSize || terrData.SizeY > Constants.RegionSize) |
228 | { | 221 | { |
229 | header.PatchIDs = (patchY & 0xFFFF); | 222 | header.PatchIDs = (patchY & 0xFFFF); |
230 | header.PatchIDs += (patchX << 16); | 223 | header.PatchIDs += (patchX << 16); |
@@ -237,8 +230,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
237 | 230 | ||
238 | // NOTE: No idea what prequant and postquant should be or what they do | 231 | // NOTE: No idea what prequant and postquant should be or what they do |
239 | int wbits; | 232 | int wbits; |
240 | int[] patch = CompressPatch(heightmap, patchX, patchY, header, 10, pRegionSizeX, pRegionSizeY, out wbits); | 233 | int[] patch = CompressPatch(terrData, patchX, patchY, header, 10, out wbits); |
241 | wbits = EncodePatchHeader(output, header, patch, pRegionSizeX, pRegionSizeY, wbits); | 234 | wbits = EncodePatchHeader(output, header, patch, (uint)terrData.SizeX, (uint)terrData.SizeY, wbits); |
242 | EncodePatch(output, patch, 0, wbits); | 235 | EncodePatch(output, patch, 0, wbits); |
243 | } | 236 | } |
244 | 237 | ||
@@ -262,19 +255,18 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
262 | } | 255 | } |
263 | 256 | ||
264 | // Scan the height info we're returning and return a patch packet header for this patch. | 257 | // Scan the height info we're returning and return a patch packet header for this patch. |
265 | // TODO. Why are patches ordered Y,X rather than X,Y? | 258 | private static TerrainPatch.Header PrescanPatch(TerrainData terrData, int patchX, int patchY) |
266 | private static TerrainPatch.Header PrescanPatch(short[] heightmap, int patchX, int patchY, | ||
267 | uint pRegionSizeX, uint pRegionSizeY) | ||
268 | { | 259 | { |
269 | TerrainPatch.Header header = new TerrainPatch.Header(); | 260 | TerrainPatch.Header header = new TerrainPatch.Header(); |
270 | short zmax = -32767; | 261 | float zmax = -99999999.0f; |
271 | short zmin = 32767; | 262 | float zmin = 99999999.0f; |
272 | 263 | ||
273 | for (int j = patchY*16; j < (patchY + 1)*16; j++) | 264 | for (int j = patchY*16; j < (patchY + 1)*16; j++) |
274 | { | 265 | { |
275 | for (int i = patchX*16; i < (patchX + 1)*16; i++) | 266 | for (int i = patchX*16; i < (patchX + 1)*16; i++) |
276 | { | 267 | { |
277 | short val = heightmap[j*pRegionSizeX + i]; | 268 | // short val = heightmap[j*pRegionSizeX + i]; |
269 | float val = terrData[j, i]; | ||
278 | if (val > zmax) zmax = val; | 270 | if (val > zmax) zmax = val; |
279 | if (val < zmin) zmin = val; | 271 | if (val < zmin) zmin = val; |
280 | } | 272 | } |
@@ -282,8 +274,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
282 | 274 | ||
283 | // Since the the min and max values are the shorts, rescale to be real values. | 275 | // Since the the min and max values are the shorts, rescale to be real values. |
284 | // TODO: all this logic should go into the class wrapping the short values. | 276 | // TODO: all this logic should go into the class wrapping the short values. |
285 | header.DCOffset = TerrainChannel.FromCompressedHeight(zmin); | 277 | header.DCOffset = zmin; |
286 | header.Range = (int)(TerrainChannel.FromCompressedHeight(zmax) - TerrainChannel.FromCompressedHeight(zmin) + 1.0f); | 278 | header.Range = (int)(zmax - zmin + 1.0f); |
287 | 279 | ||
288 | return header; | 280 | return header; |
289 | } | 281 | } |
@@ -812,8 +804,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
812 | return itemp; | 804 | return itemp; |
813 | } | 805 | } |
814 | 806 | ||
815 | private static int[] CompressPatch(short[] heightmap, int patchX, int patchY, TerrainPatch.Header header, | 807 | private static int[] CompressPatch(TerrainData terrData, int patchX, int patchY, TerrainPatch.Header header, |
816 | int prequant, uint pRegionSizeX, uint pRegionSizeY, out int wbits) | 808 | int prequant, out int wbits) |
817 | { | 809 | { |
818 | float[] block = new float[Constants.TerrainPatchSize*Constants.TerrainPatchSize]; | 810 | float[] block = new float[Constants.TerrainPatchSize*Constants.TerrainPatchSize]; |
819 | int wordsize = prequant; | 811 | int wordsize = prequant; |
@@ -827,19 +819,17 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
827 | 819 | ||
828 | int k = 0; | 820 | int k = 0; |
829 | 821 | ||
830 | premult /= Constants.TerrainCompression; // put here short to float factor | ||
831 | |||
832 | int jPatchLimit = patchY; | 822 | int jPatchLimit = patchY; |
833 | if (patchY >= (pRegionSizeY / Constants.TerrainPatchSize)) | 823 | if (patchY >= (terrData.SizeY / Constants.TerrainPatchSize)) |
834 | { | 824 | { |
835 | jPatchLimit = (int)(pRegionSizeY - Constants.TerrainPatchSize) / Constants.TerrainPatchSize; | 825 | jPatchLimit = (int)(terrData.SizeY - Constants.TerrainPatchSize) / Constants.TerrainPatchSize; |
836 | } | 826 | } |
837 | jPatchLimit = (jPatchLimit + 1) * Constants.TerrainPatchSize; | 827 | jPatchLimit = (jPatchLimit + 1) * Constants.TerrainPatchSize; |
838 | 828 | ||
839 | int iPatchLimit = patchX; | 829 | int iPatchLimit = patchX; |
840 | if (patchX >= (pRegionSizeX / Constants.TerrainPatchSize)) | 830 | if (patchX >= (terrData.SizeX / Constants.TerrainPatchSize)) |
841 | { | 831 | { |
842 | iPatchLimit = (int)(pRegionSizeX - Constants.TerrainPatchSize) / Constants.TerrainPatchSize; | 832 | iPatchLimit = (int)(terrData.SizeX - Constants.TerrainPatchSize) / Constants.TerrainPatchSize; |
843 | } | 833 | } |
844 | iPatchLimit = (iPatchLimit + 1) * Constants.TerrainPatchSize; | 834 | iPatchLimit = (iPatchLimit + 1) * Constants.TerrainPatchSize; |
845 | 835 | ||
@@ -847,7 +837,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
847 | { | 837 | { |
848 | for (int i = patchX * Constants.TerrainPatchSize; i < iPatchLimit; i++) | 838 | for (int i = patchX * Constants.TerrainPatchSize; i < iPatchLimit; i++) |
849 | { | 839 | { |
850 | block[k++] = (heightmap[j*pRegionSizeX + i])*premult - sub; | 840 | // block[k++] = (heightmap[j*pRegionSizeX + i])*premult - sub; |
841 | block[k++] = terrData[j, i] - sub; | ||
851 | } | 842 | } |
852 | } | 843 | } |
853 | 844 | ||