OSDN Git Service

Cache sculpts, re-enable hovertext.
authorLatif Khalifa <latifer@streamgrid.net>
Tue, 28 Jun 2011 09:40:02 +0000 (09:40 +0000)
committerLatif Khalifa <latifer@streamgrid.net>
Tue, 28 Jun 2011 09:40:02 +0000 (09:40 +0000)
git-svn-id: https://radegast.googlecode.com/svn/trunk@909 f7a694da-4d33-11de-9ad6-1127a62b9fcd

Radegast/GUI/Rendering/Rendering.cs
Radegast/GUI/Rendering/RenderingHelpers.cs

index 99a6a9c..d35fb6b 100644 (file)
@@ -91,6 +91,8 @@ namespace Radegast
         BlockingQueue<TextureLoadItem> PendingTextures = new BlockingQueue<TextureLoadItem>();\r
         float[] lightPos = new float[] { 0f, 0f, 1f, 0f };\r
         bool hasMipmap;\r
+        Font HoverTextFont = new Font(FontFamily.GenericSansSerif, 10f, FontStyle.Regular);\r
+        Dictionary<UUID, Bitmap> sculptCache = new Dictionary<UUID, Bitmap>();\r
 \r
         #endregion Private fields\r
 \r
@@ -138,6 +140,14 @@ namespace Radegast
                 glControl.Dispose();\r
             }\r
             glControl = null;\r
+\r
+            lock (sculptCache)\r
+            {\r
+                foreach (var img in sculptCache.Values)\r
+                    img.Dispose();\r
+                sculptCache.Clear();\r
+            }\r
+\r
             lock (Prims) Prims.Clear();\r
             TexturesPtrMap.Clear();\r
             GC.Collect();\r
@@ -198,6 +208,12 @@ namespace Radegast
 \r
         void Network_SimChanged(object sender, SimChangedEventArgs e)\r
         {\r
+            lock (sculptCache)\r
+            {\r
+                foreach (var img in sculptCache.Values)\r
+                    img.Dispose();\r
+                sculptCache.Clear();\r
+            }\r
             lock (Prims) Prims.Clear();\r
         }\r
 \r
@@ -427,7 +443,7 @@ namespace Radegast
 \r
         private void glControl_MouseDown(object sender, MouseEventArgs e)\r
         {\r
-            if (e.Button == MouseButtons.Left || e.Button == MouseButtons.Middle)\r
+            if (e.Button == MouseButtons.Left)\r
             {\r
                 dragging = true;\r
                 downX = dragX = e.X;\r
@@ -511,6 +527,7 @@ namespace Radegast
                         else if (ModifierKeys == Keys.Alt)\r
                         {\r
                             Camera.FocalPoint = PrimPos(picked.Prim);\r
+                            Cursor.Position = glControl.PointToScreen(new Point(glControl.Width / 2, glControl.Height / 2));\r
                             UpdateCamera();\r
                         }\r
                     }\r
@@ -691,34 +708,20 @@ namespace Radegast
             GluPerspective(50.0f * Camera.Zoom, dAspRat, 0.1f, (float)Camera.Far);\r
         }\r
 \r
-        private OpenTK.Vector3 WorldToScreen(OpenTK.Vector3 world)\r
-        {\r
-            OpenTK.Vector3 screen;\r
-            double[] ModelViewMatrix = new double[16];\r
-            double[] ProjectionMatrix = new double[16];\r
-            int[] Viewport = new int[4];\r
-\r
-            GL.GetInteger(GetPName.Viewport, Viewport);\r
-            GL.GetDouble(GetPName.ModelviewMatrix, ModelViewMatrix);\r
-            GL.GetDouble(GetPName.ProjectionMatrix, ProjectionMatrix);\r
-\r
-#pragma warning disable 0618\r
-            OpenTK.Graphics.Glu.Project(world,\r
-                ModelViewMatrix,\r
-                ProjectionMatrix,\r
-                Viewport,\r
-                out screen);\r
-#pragma warning restore 0618\r
-\r
-            screen.Y = glControl.Height - screen.Y;\r
-            return screen;\r
-        }\r
 \r
 #pragma warning disable 0612\r
         OpenTK.Graphics.TextPrinter Printer = new OpenTK.Graphics.TextPrinter(OpenTK.Graphics.TextQuality.High);\r
 #pragma warning restore 0612\r
         private void RenderText()\r
         {\r
+            OpenTK.Matrix4 ModelViewMatrix;\r
+            OpenTK.Matrix4 ProjectionMatrix;\r
+            int[] Viewport = new int[4];\r
+\r
+            GL.GetFloat(GetPName.ProjectionMatrix, out ProjectionMatrix);\r
+            GL.GetFloat(GetPName.ModelviewMatrix, out ModelViewMatrix);\r
+            GL.GetInteger(GetPName.Viewport, Viewport);\r
+\r
             lock (Prims)\r
             {\r
                 int primNr = 0;\r
@@ -729,36 +732,32 @@ namespace Radegast
                     if (!string.IsNullOrEmpty(prim.Text))\r
                     {\r
                         string text = System.Text.RegularExpressions.Regex.Replace(prim.Text, "(\r?\n)+", "\n");\r
-                        OpenTK.Vector3 screenPos = OpenTK.Vector3.Zero;\r
-                        OpenTK.Vector3 primPos = OpenTK.Vector3.Zero;\r
+                        var newPrimPos = PrimPos(prim);\r
+                        OpenTK.Vector3 primPos = new OpenTK.Vector3(newPrimPos.X, newPrimPos.Y, newPrimPos.Z);\r
 \r
-                        // Is it child prim\r
-                        FacetedMesh parent = null;\r
-                        if (Prims.TryGetValue(prim.ParentID, out parent))\r
-                        {\r
-                            var newPrimPos = prim.Position * Matrix4.CreateFromQuaternion(parent.Prim.Rotation);\r
-                            primPos = new OpenTK.Vector3(newPrimPos.X, newPrimPos.Y, newPrimPos.Z);\r
-                        }\r
+                        if (Vector3.Distance(newPrimPos, Camera.Position) > 15) continue;\r
+\r
+                        primPos.Z += prim.Scale.Z * 0.8f;\r
+\r
+                        OpenTK.Vector3 screenPos;\r
+                        if (!Math3D.GluProject(primPos, ModelViewMatrix, ProjectionMatrix, Viewport, out screenPos)) continue;\r
+                        screenPos.Y = glControl.Height - screenPos.Y;\r
 \r
-                        primPos.Z += prim.Scale.Z * 0.7f;\r
-                        screenPos = WorldToScreen(primPos);\r
                         Printer.Begin();\r
 \r
                         Color color = Color.FromArgb((int)(prim.TextColor.A * 255), (int)(prim.TextColor.R * 255), (int)(prim.TextColor.G * 255), (int)(prim.TextColor.B * 255));\r
 \r
-                        using (Font f = new Font(FontFamily.GenericSansSerif, 10f, FontStyle.Bold))\r
-                        {\r
-                            var size = Printer.Measure(text, f);\r
-                            screenPos.X -= size.BoundingBox.Width / 2;\r
-                            screenPos.Y -= size.BoundingBox.Height;\r
+                        var size = Printer.Measure(text, HoverTextFont);\r
+                        screenPos.X -= size.BoundingBox.Width / 2;\r
+                        screenPos.Y -= size.BoundingBox.Height;\r
 \r
-                            // Shadow\r
-                            if (color != Color.Black)\r
-                            {\r
-                                Printer.Print(text, f, Color.Black, new RectangleF(screenPos.X + 1, screenPos.Y + 1, size.BoundingBox.Width, size.BoundingBox.Height), OpenTK.Graphics.TextPrinterOptions.Default, OpenTK.Graphics.TextAlignment.Center);\r
-                            }\r
-                            Printer.Print(text, f, color, new RectangleF(screenPos.X, screenPos.Y, size.BoundingBox.Width, size.BoundingBox.Height), OpenTK.Graphics.TextPrinterOptions.Default, OpenTK.Graphics.TextAlignment.Center);\r
+                        // Shadow\r
+                        if (color != Color.Black)\r
+                        {\r
+                            Printer.Print(text, HoverTextFont, Color.Black, new RectangleF(screenPos.X + 1, screenPos.Y + 1, size.BoundingBox.Width, size.BoundingBox.Height), OpenTK.Graphics.TextPrinterOptions.Default, OpenTK.Graphics.TextAlignment.Center);\r
                         }\r
+                        Printer.Print(text, HoverTextFont, color, new RectangleF(screenPos.X, screenPos.Y, size.BoundingBox.Width, size.BoundingBox.Height), OpenTK.Graphics.TextPrinterOptions.Default, OpenTK.Graphics.TextAlignment.Center);\r
+\r
                         Printer.End();\r
                     }\r
                 }\r
@@ -924,7 +923,7 @@ namespace Radegast
             {\r
                 RenderObjects(RenderPass.Simple);\r
                 RenderObjects(RenderPass.Alpha);\r
-                //RenderText();\r
+                RenderText();\r
             }\r
 \r
             // Pop the world matrix\r
@@ -1000,6 +999,7 @@ namespace Radegast
             if (Client.Network.CurrentSim.ObjectsAvatars.ContainsKey(prim.LocalID)) return;\r
 \r
             if (Vector3.Distance(PrimPos(prim), Client.Self.SimPosition) > 32 && !Prims.ContainsKey(prim.ParentID)) return;\r
+            if (prim.Textures == null) return;\r
 \r
             FacetedMesh mesh = null;\r
             FacetedMesh existingMesh = null;\r
@@ -1012,9 +1012,6 @@ namespace Radegast
                 }\r
             }\r
 \r
-            if (prim.Textures == null)\r
-                return;\r
-\r
             try\r
             {\r
                 if (prim.Sculpt != null && prim.Sculpt.SculptTexture != UUID.Zero)\r
@@ -1022,8 +1019,27 @@ namespace Radegast
                     if (prim.Sculpt.Type != SculptType.Mesh)\r
                     { // Regular sculptie\r
                         Image img = null;\r
-                        if (!LoadTexture(prim.Sculpt.SculptTexture, ref img, true))\r
-                            return;\r
+                        \r
+                        lock (sculptCache)\r
+                        {\r
+                            if (sculptCache.ContainsKey(prim.Sculpt.SculptTexture))\r
+                            {\r
+                                img = sculptCache[prim.Sculpt.SculptTexture];\r
+                            }\r
+                        }\r
+\r
+                        if (img == null)\r
+                        {\r
+                            if (LoadTexture(prim.Sculpt.SculptTexture, ref img, true))\r
+                            {\r
+                                sculptCache[prim.Sculpt.SculptTexture] = (Bitmap)img;\r
+                            }\r
+                            else\r
+                            {\r
+                                return;\r
+                            }\r
+                        }\r
+\r
                         mesh = renderer.GenerateFacetedSculptMesh(prim, (Bitmap)img, DetailLevel.Highest);\r
                     }\r
                     else\r
index b15affa..fa51411 100644 (file)
@@ -272,5 +272,43 @@ namespace Radegast
 \r
             return mat;\r
         }\r
+\r
+        public static bool GluProject(OpenTK.Vector3 objPos, OpenTK.Matrix4 modelMatrix, OpenTK.Matrix4 projMatrix, int[] viewport, out OpenTK.Vector3 screenPos)\r
+        {\r
+            OpenTK.Vector4 _in;\r
+            OpenTK.Vector4 _out;\r
+\r
+            _in.X = objPos.X;\r
+            _in.Y = objPos.Y;\r
+            _in.Z = objPos.Z;\r
+            _in.W = 1.0f;\r
+\r
+            _out = OpenTK.Vector4.Transform(_in, modelMatrix);\r
+            _in = OpenTK.Vector4.Transform(_out, projMatrix);\r
+\r
+            if (_in.W <= 0.0)\r
+            {\r
+                screenPos = OpenTK.Vector3.Zero;\r
+                return false;\r
+            }\r
+\r
+            _in.X /= _in.W;\r
+            _in.Y /= _in.W;\r
+            _in.Z /= _in.W;\r
+            /* Map x, y and z to range 0-1 */\r
+            _in.X = _in.X * 0.5f + 0.5f;\r
+            _in.Y = _in.Y * 0.5f + 0.5f;\r
+            _in.Z = _in.Z * 0.5f + 0.5f;\r
+\r
+            /* Map x,y to viewport */\r
+            _in.X = _in.X * viewport[2] + viewport[0];\r
+            _in.Y = _in.Y * viewport[3] + viewport[1];\r
+\r
+            screenPos.X = _in.X;\r
+            screenPos.Y = _in.Y;\r
+            screenPos.Z = _in.Z;\r
+\r
+            return true;\r
+        }\r
     }\r
 }\r