aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/PhysicsModules/Meshing/Meshmerizer')
-rw-r--r--OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/HelperTypes.cs2
-rw-r--r--OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Mesh.cs87
-rw-r--r--OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Meshmerizer.cs43
-rw-r--r--OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/PrimMesher.cs6
-rw-r--r--OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/SculptMap.cs60
5 files changed, 152 insertions, 46 deletions
diff --git a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/HelperTypes.cs b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/HelperTypes.cs
index 34a925d..a0e3b7f 100644
--- a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/HelperTypes.cs
+++ b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/HelperTypes.cs
@@ -31,7 +31,7 @@ using System.Diagnostics;
31using System.Globalization; 31using System.Globalization;
32using OpenMetaverse; 32using OpenMetaverse;
33using OpenSim.Region.PhysicsModules.SharedBase; 33using OpenSim.Region.PhysicsModules.SharedBase;
34using OpenSim.Region.PhysicsModules.Meshing; 34using OpenSim.Region.PhysicsModule.Meshing;
35 35
36public class Vertex : IComparable<Vertex> 36public class Vertex : IComparable<Vertex>
37{ 37{
diff --git a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Mesh.cs b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Mesh.cs
index bf397ee..42ba37e 100644
--- a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Mesh.cs
+++ b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Mesh.cs
@@ -33,7 +33,7 @@ using OpenSim.Region.PhysicsModules.SharedBase;
33using PrimMesher; 33using PrimMesher;
34using OpenMetaverse; 34using OpenMetaverse;
35 35
36namespace OpenSim.Region.PhysicsModules.Meshing 36namespace OpenSim.Region.PhysicsModule.Meshing
37{ 37{
38 public class Mesh : IMesh 38 public class Mesh : IMesh
39 { 39 {
@@ -46,11 +46,36 @@ namespace OpenSim.Region.PhysicsModules.Meshing
46 IntPtr m_indicesPtr = IntPtr.Zero; 46 IntPtr m_indicesPtr = IntPtr.Zero;
47 int m_indexCount = 0; 47 int m_indexCount = 0;
48 public float[] m_normals; 48 public float[] m_normals;
49 Vector3 _centroid;
50 int _centroidDiv;
51
52 private class vertexcomp : IEqualityComparer<Vertex>
53 {
54 public bool Equals(Vertex v1, Vertex v2)
55 {
56 if (v1.X == v2.X && v1.Y == v2.Y && v1.Z == v2.Z)
57 return true;
58 else
59 return false;
60 }
61 public int GetHashCode(Vertex v)
62 {
63 int a = v.X.GetHashCode();
64 int b = v.Y.GetHashCode();
65 int c = v.Z.GetHashCode();
66 return (a << 16) ^ (b << 8) ^ c;
67 }
68
69 }
49 70
50 public Mesh() 71 public Mesh()
51 { 72 {
52 m_vertices = new Dictionary<Vertex, int>(); 73 vertexcomp vcomp = new vertexcomp();
74
75 m_vertices = new Dictionary<Vertex, int>(vcomp);
53 m_triangles = new List<Triangle>(); 76 m_triangles = new List<Triangle>();
77 _centroid = Vector3.Zero;
78 _centroidDiv = 0;
54 } 79 }
55 80
56 public Mesh Clone() 81 public Mesh Clone()
@@ -61,7 +86,8 @@ namespace OpenSim.Region.PhysicsModules.Meshing
61 { 86 {
62 result.Add(new Triangle(t.v1.Clone(), t.v2.Clone(), t.v3.Clone())); 87 result.Add(new Triangle(t.v1.Clone(), t.v2.Clone(), t.v3.Clone()));
63 } 88 }
64 89 result._centroid = _centroid;
90 result._centroidDiv = _centroidDiv;
65 return result; 91 return result;
66 } 92 }
67 93
@@ -71,15 +97,63 @@ namespace OpenSim.Region.PhysicsModules.Meshing
71 throw new NotSupportedException("Attempt to Add to a pinned Mesh"); 97 throw new NotSupportedException("Attempt to Add to a pinned Mesh");
72 // If a vertex of the triangle is not yet in the vertices list, 98 // If a vertex of the triangle is not yet in the vertices list,
73 // add it and set its index to the current index count 99 // add it and set its index to the current index count
100 // vertex == seems broken
101 // skip colapsed triangles
102 if ((triangle.v1.X == triangle.v2.X && triangle.v1.Y == triangle.v2.Y && triangle.v1.Z == triangle.v2.Z)
103 || (triangle.v1.X == triangle.v3.X && triangle.v1.Y == triangle.v3.Y && triangle.v1.Z == triangle.v3.Z)
104 || (triangle.v2.X == triangle.v3.X && triangle.v2.Y == triangle.v3.Y && triangle.v2.Z == triangle.v3.Z)
105 )
106 {
107 return;
108 }
109
110 if (m_vertices.Count == 0)
111 {
112 _centroidDiv = 0;
113 _centroid = Vector3.Zero;
114 }
115
74 if (!m_vertices.ContainsKey(triangle.v1)) 116 if (!m_vertices.ContainsKey(triangle.v1))
117 {
75 m_vertices[triangle.v1] = m_vertices.Count; 118 m_vertices[triangle.v1] = m_vertices.Count;
119 _centroid.X += triangle.v1.X;
120 _centroid.Y += triangle.v1.Y;
121 _centroid.Z += triangle.v1.Z;
122 _centroidDiv++;
123 }
76 if (!m_vertices.ContainsKey(triangle.v2)) 124 if (!m_vertices.ContainsKey(triangle.v2))
125 {
77 m_vertices[triangle.v2] = m_vertices.Count; 126 m_vertices[triangle.v2] = m_vertices.Count;
127 _centroid.X += triangle.v2.X;
128 _centroid.Y += triangle.v2.Y;
129 _centroid.Z += triangle.v2.Z;
130 _centroidDiv++;
131 }
78 if (!m_vertices.ContainsKey(triangle.v3)) 132 if (!m_vertices.ContainsKey(triangle.v3))
133 {
79 m_vertices[triangle.v3] = m_vertices.Count; 134 m_vertices[triangle.v3] = m_vertices.Count;
135 _centroid.X += triangle.v3.X;
136 _centroid.Y += triangle.v3.Y;
137 _centroid.Z += triangle.v3.Z;
138 _centroidDiv++;
139 }
80 m_triangles.Add(triangle); 140 m_triangles.Add(triangle);
81 } 141 }
82 142
143 public Vector3 GetCentroid()
144 {
145 if (_centroidDiv > 0)
146 return new Vector3(_centroid.X / _centroidDiv, _centroid.Y / _centroidDiv, _centroid.Z / _centroidDiv);
147 else
148 return Vector3.Zero;
149 }
150
151 // not functional
152 public Vector3 GetOBB()
153 {
154 return new Vector3(0.5f, 0.5f, 0.5f);
155 }
156
83 public void CalcNormals() 157 public void CalcNormals()
84 { 158 {
85 int iTriangles = m_triangles.Count; 159 int iTriangles = m_triangles.Count;
@@ -185,6 +259,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
185 public void getVertexListAsPtrToFloatArray(out IntPtr vertices, out int vertexStride, out int vertexCount) 259 public void getVertexListAsPtrToFloatArray(out IntPtr vertices, out int vertexStride, out int vertexCount)
186 { 260 {
187 // A vertex is 3 floats 261 // A vertex is 3 floats
262
188 vertexStride = 3 * sizeof(float); 263 vertexStride = 3 * sizeof(float);
189 264
190 // If there isn't an unmanaged array allocated yet, do it now 265 // If there isn't an unmanaged array allocated yet, do it now
@@ -224,7 +299,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
224 { 299 {
225 if (m_pinnedIndex.IsAllocated) 300 if (m_pinnedIndex.IsAllocated)
226 return (int[])(m_pinnedIndex.Target); 301 return (int[])(m_pinnedIndex.Target);
227 302
228 int[] result = getIndexListAsInt(); 303 int[] result = getIndexListAsInt();
229 m_pinnedIndex = GCHandle.Alloc(result, GCHandleType.Pinned); 304 m_pinnedIndex = GCHandle.Alloc(result, GCHandleType.Pinned);
230 // Inform the garbage collector of this unmanaged allocation so it can schedule 305 // Inform the garbage collector of this unmanaged allocation so it can schedule
@@ -282,7 +357,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
282 { 357 {
283 if (m_pinnedIndex.IsAllocated || m_pinnedVertexes.IsAllocated || m_indicesPtr != IntPtr.Zero || m_verticesPtr != IntPtr.Zero) 358 if (m_pinnedIndex.IsAllocated || m_pinnedVertexes.IsAllocated || m_indicesPtr != IntPtr.Zero || m_verticesPtr != IntPtr.Zero)
284 throw new NotSupportedException("Attempt to Append to a pinned Mesh"); 359 throw new NotSupportedException("Attempt to Append to a pinned Mesh");
285 360
286 if (!(newMesh is Mesh)) 361 if (!(newMesh is Mesh))
287 return; 362 return;
288 363
@@ -295,7 +370,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
295 { 370 {
296 if (m_pinnedIndex.IsAllocated || m_pinnedVertexes.IsAllocated || m_indicesPtr != IntPtr.Zero || m_verticesPtr != IntPtr.Zero) 371 if (m_pinnedIndex.IsAllocated || m_pinnedVertexes.IsAllocated || m_indicesPtr != IntPtr.Zero || m_verticesPtr != IntPtr.Zero)
297 throw new NotSupportedException("Attempt to TransformLinear a pinned Mesh"); 372 throw new NotSupportedException("Attempt to TransformLinear a pinned Mesh");
298 373
299 foreach (Vertex v in m_vertices.Keys) 374 foreach (Vertex v in m_vertices.Keys)
300 { 375 {
301 if (v == null) 376 if (v == null)
diff --git a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Meshmerizer.cs b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Meshmerizer.cs
index 3a944d1..a90ef3b 100644
--- a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Meshmerizer.cs
+++ b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/Meshmerizer.cs
@@ -44,7 +44,7 @@ using log4net;
44using Nini.Config; 44using Nini.Config;
45using Mono.Addins; 45using Mono.Addins;
46 46
47namespace OpenSim.Region.PhysicsModules.Meshing 47namespace OpenSim.Region.PhysicsModule.Meshing
48{ 48{
49 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "Meshmerizer")] 49 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "Meshmerizer")]
50 public class Meshmerizer : IMesher, INonSharedRegionModule 50 public class Meshmerizer : IMesher, INonSharedRegionModule
@@ -66,7 +66,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
66 66
67 private bool cacheSculptMaps = true; 67 private bool cacheSculptMaps = true;
68 private string decodedSculptMapPath = null; 68 private string decodedSculptMapPath = null;
69 private bool useMeshiesPhysicsMesh = false; 69 private bool useMeshiesPhysicsMesh = true;
70 70
71 private float minSizeForComplexMesh = 0.2f; // prims with all dimensions smaller than this will have a bounding box mesh 71 private float minSizeForComplexMesh = 0.2f; // prims with all dimensions smaller than this will have a bounding box mesh
72 72
@@ -99,7 +99,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
99 99
100 IConfig mesh_config = source.Configs["Mesh"]; 100 IConfig mesh_config = source.Configs["Mesh"];
101 101
102 decodedSculptMapPath = "../caches/" + config.GetString("DecodedSculptMapPath", "j2kDecodeCache"); 102 decodedSculptMapPath = config.GetString("DecodedSculptMapPath", System.IO.Path.Combine(Util.cacheDir(), "j2kDecodeCache"));
103 cacheSculptMaps = config.GetBoolean("CacheSculptMaps", cacheSculptMaps); 103 cacheSculptMaps = config.GetBoolean("CacheSculptMaps", cacheSculptMaps);
104 if (mesh_config != null) 104 if (mesh_config != null)
105 { 105 {
@@ -247,13 +247,13 @@ namespace OpenSim.Region.PhysicsModules.Meshing
247 private void AddSubMesh(OSDMap subMeshData, Vector3 size, List<Coord> coords, List<Face> faces) 247 private void AddSubMesh(OSDMap subMeshData, Vector3 size, List<Coord> coords, List<Face> faces)
248 { 248 {
249 // Console.WriteLine("subMeshMap for {0} - {1}", primName, Util.GetFormattedXml((OSD)subMeshMap)); 249 // Console.WriteLine("subMeshMap for {0} - {1}", primName, Util.GetFormattedXml((OSD)subMeshMap));
250 250
251 // As per http://wiki.secondlife.com/wiki/Mesh/Mesh_Asset_Format, some Mesh Level 251 // As per http://wiki.secondlife.com/wiki/Mesh/Mesh_Asset_Format, some Mesh Level
252 // of Detail Blocks (maps) contain just a NoGeometry key to signal there is no 252 // of Detail Blocks (maps) contain just a NoGeometry key to signal there is no
253 // geometry for this submesh. 253 // geometry for this submesh.
254 if (subMeshData.ContainsKey("NoGeometry") && ((OSDBoolean)subMeshData["NoGeometry"])) 254 if (subMeshData.ContainsKey("NoGeometry") && ((OSDBoolean)subMeshData["NoGeometry"]))
255 return; 255 return;
256 256
257 OpenMetaverse.Vector3 posMax = ((OSDMap)subMeshData["PositionDomain"])["Max"].AsVector3(); 257 OpenMetaverse.Vector3 posMax = ((OSDMap)subMeshData["PositionDomain"])["Max"].AsVector3();
258 OpenMetaverse.Vector3 posMin = ((OSDMap)subMeshData["PositionDomain"])["Min"].AsVector3(); 258 OpenMetaverse.Vector3 posMin = ((OSDMap)subMeshData["PositionDomain"])["Min"].AsVector3();
259 ushort faceIndexOffset = (ushort)coords.Count; 259 ushort faceIndexOffset = (ushort)coords.Count;
@@ -264,15 +264,15 @@ namespace OpenSim.Region.PhysicsModules.Meshing
264 ushort uX = Utils.BytesToUInt16(posBytes, i); 264 ushort uX = Utils.BytesToUInt16(posBytes, i);
265 ushort uY = Utils.BytesToUInt16(posBytes, i + 2); 265 ushort uY = Utils.BytesToUInt16(posBytes, i + 2);
266 ushort uZ = Utils.BytesToUInt16(posBytes, i + 4); 266 ushort uZ = Utils.BytesToUInt16(posBytes, i + 4);
267 267
268 Coord c = new Coord( 268 Coord c = new Coord(
269 Utils.UInt16ToFloat(uX, posMin.X, posMax.X) * size.X, 269 Utils.UInt16ToFloat(uX, posMin.X, posMax.X) * size.X,
270 Utils.UInt16ToFloat(uY, posMin.Y, posMax.Y) * size.Y, 270 Utils.UInt16ToFloat(uY, posMin.Y, posMax.Y) * size.Y,
271 Utils.UInt16ToFloat(uZ, posMin.Z, posMax.Z) * size.Z); 271 Utils.UInt16ToFloat(uZ, posMin.Z, posMax.Z) * size.Z);
272 272
273 coords.Add(c); 273 coords.Add(c);
274 } 274 }
275 275
276 byte[] triangleBytes = subMeshData["TriangleList"].AsBinary(); 276 byte[] triangleBytes = subMeshData["TriangleList"].AsBinary();
277 for (int i = 0; i < triangleBytes.Length; i += 6) 277 for (int i = 0; i < triangleBytes.Length; i += 6)
278 { 278 {
@@ -436,9 +436,9 @@ namespace OpenSim.Region.PhysicsModules.Meshing
436 int convexSize = convexBlock["size"].AsInteger(); 436 int convexSize = convexBlock["size"].AsInteger();
437 437
438 byte[] convexBytes = new byte[convexSize]; 438 byte[] convexBytes = new byte[convexSize];
439 439
440 System.Buffer.BlockCopy(primShape.SculptData, convexOffset, convexBytes, 0, convexSize); 440 System.Buffer.BlockCopy(primShape.SculptData, convexOffset, convexBytes, 0, convexSize);
441 441
442 try 442 try
443 { 443 {
444 convexBlockOsd = DecompressOsd(convexBytes); 444 convexBlockOsd = DecompressOsd(convexBytes);
@@ -449,7 +449,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
449 //return false; 449 //return false;
450 } 450 }
451 } 451 }
452 452
453 if (convexBlockOsd != null && convexBlockOsd is OSDMap) 453 if (convexBlockOsd != null && convexBlockOsd is OSDMap)
454 { 454 {
455 convexBlock = convexBlockOsd as OSDMap; 455 convexBlock = convexBlockOsd as OSDMap;
@@ -762,7 +762,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
762 { 762 {
763 PrimMesh primMesh; 763 PrimMesh primMesh;
764 coords = new List<Coord>(); 764 coords = new List<Coord>();
765 faces = new List<Face>(); 765 faces = new List<Face>();
766 766
767 float pathShearX = primShape.PathShearX < 128 ? (float)primShape.PathShearX * 0.01f : (float)(primShape.PathShearX - 256) * 0.01f; 767 float pathShearX = primShape.PathShearX < 128 ? (float)primShape.PathShearX * 0.01f : (float)(primShape.PathShearX - 256) * 0.01f;
768 float pathShearY = primShape.PathShearY < 128 ? (float)primShape.PathShearY * 0.01f : (float)(primShape.PathShearY - 256) * 0.01f; 768 float pathShearY = primShape.PathShearY < 128 ? (float)primShape.PathShearY * 0.01f : (float)(primShape.PathShearY - 256) * 0.01f;
@@ -947,11 +947,21 @@ namespace OpenSim.Region.PhysicsModules.Meshing
947 return CreateMesh(primName, primShape, size, lod, false, true); 947 return CreateMesh(primName, primShape, size, lod, false, true);
948 } 948 }
949 949
950 public IMesh CreateMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical, bool shouldCache, bool convex, bool forOde)
951 {
952 return CreateMesh(primName, primShape, size, lod, false);
953 }
954
950 public IMesh CreateMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical) 955 public IMesh CreateMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical)
951 { 956 {
952 return CreateMesh(primName, primShape, size, lod, isPhysical, true); 957 return CreateMesh(primName, primShape, size, lod, isPhysical, true);
953 } 958 }
954 959
960 public IMesh CreateMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical, bool convex, bool forOde)
961 {
962 return CreateMesh(primName, primShape, size, lod, isPhysical, true);
963 }
964
955 public IMesh CreateMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical, bool shouldCache) 965 public IMesh CreateMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical, bool shouldCache)
956 { 966 {
957#if SPAM 967#if SPAM
@@ -984,7 +994,7 @@ namespace OpenSim.Region.PhysicsModules.Meshing
984 if ((!isPhysical) && size.X < minSizeForComplexMesh && size.Y < minSizeForComplexMesh && size.Z < minSizeForComplexMesh) 994 if ((!isPhysical) && size.X < minSizeForComplexMesh && size.Y < minSizeForComplexMesh && size.Z < minSizeForComplexMesh)
985 { 995 {
986#if SPAM 996#if SPAM
987 m_log.Debug("Meshmerizer: prim " + primName + " has a size of " + size.ToString() + " which is below threshold of " + 997 m_log.Debug("Meshmerizer: prim " + primName + " has a size of " + size.ToString() + " which is below threshold of " +
988 minSizeForComplexMesh.ToString() + " - creating simple bounding box"); 998 minSizeForComplexMesh.ToString() + " - creating simple bounding box");
989#endif 999#endif
990 mesh = CreateBoundingBoxMesh(mesh); 1000 mesh = CreateBoundingBoxMesh(mesh);
@@ -1005,6 +1015,13 @@ namespace OpenSim.Region.PhysicsModules.Meshing
1005 1015
1006 return mesh; 1016 return mesh;
1007 } 1017 }
1018 public IMesh GetMesh(String primName, PrimitiveBaseShape primShape, Vector3 size, float lod, bool isPhysical, bool convex)
1019 {
1020 return null;
1021 }
1008 1022
1023 public void ReleaseMesh(IMesh imesh) { }
1024 public void ExpireReleaseMeshs() { }
1025 public void ExpireFileCache() { }
1009 } 1026 }
1010} 1027}
diff --git a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/PrimMesher.cs b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/PrimMesher.cs
index 4049ee1..fd2b1ea 100644
--- a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/PrimMesher.cs
+++ b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/PrimMesher.cs
@@ -445,7 +445,7 @@ namespace PrimMesher
445 new Angle(1.0f, 1.0f, 0.0f) 445 new Angle(1.0f, 1.0f, 0.0f)
446 }; 446 };
447 447
448 private static Coord[] normals4 = 448 private static Coord[] normals4 =
449 { 449 {
450 new Coord(0.5f, 0.5f, 0.0f).Normalize(), 450 new Coord(0.5f, 0.5f, 0.0f).Normalize(),
451 new Coord(-0.5f, 0.5f, 0.0f).Normalize(), 451 new Coord(-0.5f, 0.5f, 0.0f).Normalize(),
@@ -2066,7 +2066,7 @@ namespace PrimMesher
2066 /// DEPRICATED - use Extrude(PathType.Linear) instead 2066 /// DEPRICATED - use Extrude(PathType.Linear) instead
2067 /// Extrudes a profile along a straight line path. Used for prim types box, cylinder, and prism. 2067 /// Extrudes a profile along a straight line path. Used for prim types box, cylinder, and prism.
2068 /// </summary> 2068 /// </summary>
2069 /// 2069 ///
2070 public void ExtrudeLinear() 2070 public void ExtrudeLinear()
2071 { 2071 {
2072 this.Extrude(PathType.Linear); 2072 this.Extrude(PathType.Linear);
@@ -2077,7 +2077,7 @@ namespace PrimMesher
2077 /// DEPRICATED - use Extrude(PathType.Circular) instead 2077 /// DEPRICATED - use Extrude(PathType.Circular) instead
2078 /// Extrude a profile into a circular path prim mesh. Used for prim types torus, tube, and ring. 2078 /// Extrude a profile into a circular path prim mesh. Used for prim types torus, tube, and ring.
2079 /// </summary> 2079 /// </summary>
2080 /// 2080 ///
2081 public void ExtrudeCircular() 2081 public void ExtrudeCircular()
2082 { 2082 {
2083 this.Extrude(PathType.Circular); 2083 this.Extrude(PathType.Circular);
diff --git a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/SculptMap.cs b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/SculptMap.cs
index 740424e..01d11f4 100644
--- a/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/SculptMap.cs
+++ b/OpenSim/Region/PhysicsModules/Meshing/Meshmerizer/SculptMap.cs
@@ -58,28 +58,24 @@ namespace PrimMesher
58 if (bmW == 0 || bmH == 0) 58 if (bmW == 0 || bmH == 0)
59 throw new Exception("SculptMap: bitmap has no data"); 59 throw new Exception("SculptMap: bitmap has no data");
60 60
61 int numLodPixels = lod * 2 * lod * 2; // (32 * 2)^2 = 64^2 pixels for default sculpt map image 61 int numLodPixels = lod * lod; // (32 * 2)^2 = 64^2 pixels for default sculpt map image
62 62
63 bool smallMap = bmW * bmH <= numLodPixels;
63 bool needsScaling = false; 64 bool needsScaling = false;
64 65
65 bool smallMap = bmW * bmH <= lod * lod;
66
67 width = bmW; 66 width = bmW;
68 height = bmH; 67 height = bmH;
69 while (width * height > numLodPixels) 68 while (width * height > numLodPixels * 4)
70 { 69 {
71 width >>= 1; 70 width >>= 1;
72 height >>= 1; 71 height >>= 1;
73 needsScaling = true; 72 needsScaling = true;
74 } 73 }
75 74
76
77
78 try 75 try
79 { 76 {
80 if (needsScaling) 77 if (needsScaling)
81 bm = ScaleImage(bm, width, height, 78 bm = ScaleImage(bm, width, height);
82 System.Drawing.Drawing2D.InterpolationMode.NearestNeighbor);
83 } 79 }
84 80
85 catch (Exception e) 81 catch (Exception e)
@@ -87,7 +83,7 @@ namespace PrimMesher
87 throw new Exception("Exception in ScaleImage(): e: " + e.ToString()); 83 throw new Exception("Exception in ScaleImage(): e: " + e.ToString());
88 } 84 }
89 85
90 if (width * height > lod * lod) 86 if (width * height > numLodPixels)
91 { 87 {
92 width >>= 1; 88 width >>= 1;
93 height >>= 1; 89 height >>= 1;
@@ -144,15 +140,17 @@ namespace PrimMesher
144 int rowNdx, colNdx; 140 int rowNdx, colNdx;
145 int smNdx = 0; 141 int smNdx = 0;
146 142
143
147 for (rowNdx = 0; rowNdx < numRows; rowNdx++) 144 for (rowNdx = 0; rowNdx < numRows; rowNdx++)
148 { 145 {
149 List<Coord> row = new List<Coord>(numCols); 146 List<Coord> row = new List<Coord>(numCols);
150 for (colNdx = 0; colNdx < numCols; colNdx++) 147 for (colNdx = 0; colNdx < numCols; colNdx++)
151 { 148 {
149
152 if (mirror) 150 if (mirror)
153 row.Add(new Coord(-(redBytes[smNdx] * pixScale - 0.5f), (greenBytes[smNdx] * pixScale - 0.5f), blueBytes[smNdx] * pixScale - 0.5f)); 151 row.Add(new Coord(-((float)redBytes[smNdx] * pixScale - 0.5f), ((float)greenBytes[smNdx] * pixScale - 0.5f), (float)blueBytes[smNdx] * pixScale - 0.5f));
154 else 152 else
155 row.Add(new Coord(redBytes[smNdx] * pixScale - 0.5f, greenBytes[smNdx] * pixScale - 0.5f, blueBytes[smNdx] * pixScale - 0.5f)); 153 row.Add(new Coord((float)redBytes[smNdx] * pixScale - 0.5f, (float)greenBytes[smNdx] * pixScale - 0.5f, (float)blueBytes[smNdx] * pixScale - 0.5f));
156 154
157 ++smNdx; 155 ++smNdx;
158 } 156 }
@@ -161,23 +159,39 @@ namespace PrimMesher
161 return rows; 159 return rows;
162 } 160 }
163 161
164 private Bitmap ScaleImage(Bitmap srcImage, int destWidth, int destHeight, 162 private Bitmap ScaleImage(Bitmap srcImage, int destWidth, int destHeight)
165 System.Drawing.Drawing2D.InterpolationMode interpMode)
166 { 163 {
167 Bitmap scaledImage = new Bitmap(srcImage, destWidth, destHeight);
168 scaledImage.SetResolution(96.0f, 96.0f);
169 164
170 Graphics grPhoto = Graphics.FromImage(scaledImage); 165 Bitmap scaledImage = new Bitmap(destWidth, destHeight, PixelFormat.Format24bppRgb);
171 grPhoto.InterpolationMode = interpMode;
172 166
173 grPhoto.DrawImage(srcImage, 167 Color c;
174 new Rectangle(0, 0, destWidth, destHeight), 168 float xscale = srcImage.Width / destWidth;
175 new Rectangle(0, 0, srcImage.Width, srcImage.Height), 169 float yscale = srcImage.Height / destHeight;
176 GraphicsUnit.Pixel);
177 170
178 grPhoto.Dispose(); 171 float sy = 0.5f;
172 for (int y = 0; y < destHeight; y++)
173 {
174 float sx = 0.5f;
175 for (int x = 0; x < destWidth; x++)
176 {
177 try
178 {
179 c = srcImage.GetPixel((int)(sx), (int)(sy));
180 scaledImage.SetPixel(x, y, Color.FromArgb(c.R, c.G, c.B));
181 }
182 catch (IndexOutOfRangeException)
183 {
184 }
185
186 sx += xscale;
187 }
188 sy += yscale;
189 }
190 srcImage.Dispose();
179 return scaledImage; 191 return scaledImage;
180 } 192 }
193
194 }
195
181 } 196 }
182}
183#endif 197#endif