diff --git a/Vocaluxe/Lib/Draw/CDirect3D.cs b/Vocaluxe/Lib/Draw/CDirect3D.cs
index 446e600f..8d0f4b75 100644
--- a/Vocaluxe/Lib/Draw/CDirect3D.cs
+++ b/Vocaluxe/Lib/Draw/CDirect3D.cs
@@ -15,6 +15,7 @@
// along with Vocaluxe. If not, see .
#endregion
+using System.Diagnostics;
using SlimDX;
using SlimDX.Direct3D9;
using System;
@@ -420,13 +421,41 @@ namespace Vocaluxe.Lib.Draw
return _Device.Viewport.Height;
}
+ ///
+ /// Adds a texture to the vertext buffer
+ ///
+ /// Texture to draw
+ /// Coordinates to draw on
+ /// Color to use
+ /// If true, then color is faded out in y direction
+ private void _DrawTexture(CD3DTexture texture, SDrawCoords dc, SColorF color, bool isReflection = false)
+ {
+ color.A *= CGraphics.GlobalAlpha;
+ int c = color.AsColor().ToArgb();
+ int c2;
+ if (isReflection)
+ {
+ color.A = 0;
+ c2 = color.AsColor().ToArgb();
+ }
+ else
+ c2 = c;
+
+ var vert = new STexturedColoredVertex[4];
+ vert[0] = new STexturedColoredVertex(new Vector3(dc.Wx1, -dc.Wy1, dc.Wz), new Vector2(dc.Tx1, dc.Ty1), c);
+ vert[1] = new STexturedColoredVertex(new Vector3(dc.Wx1, -dc.Wy2, dc.Wz), new Vector2(dc.Tx1, dc.Ty2), c2);
+ vert[2] = new STexturedColoredVertex(new Vector3(dc.Wx2, -dc.Wy2, dc.Wz), new Vector2(dc.Tx2, dc.Ty2), c2);
+ vert[3] = new STexturedColoredVertex(new Vector3(dc.Wx2, -dc.Wy1, dc.Wz), new Vector2(dc.Tx2, dc.Ty1), c);
+ _DrawTexture(vert, texture.D3DTexture, _CalculateRotationMatrix(dc.Rotation, dc.Wx1, dc.Wx2, dc.Wy1, dc.Wy2));
+ }
+
///
/// Adds a quad a list which will be added and rendered to the vertexbuffer when calling RenderToVertexBuffer to reduce vertexbuffer calls each frame to a minimum
///
/// A TexturedColoredVertex array containg 4 vertices
/// The texture the vertex should be textured with
/// The vertices' rotation
- private void _AddToVertexBuffer(STexturedColoredVertex[] vertices, Texture tex, Matrix rotation)
+ private void _DrawTexture(STexturedColoredVertex[] vertices, Texture tex, Matrix rotation)
{
//The vertexbuffer is full, so we need to flush it before we can continue
if (_Vertices.Count >= CSettings.VertexBufferElements)
@@ -593,41 +622,16 @@ namespace Vocaluxe.Lib.Draw
/// True if the texture should be mirrored
public void DrawTexture(CTextureRef textureRef, SRectF rect, SColorF color, bool mirrored = false)
{
- if (rect.W < 1 || rect.H < 1)
+ if (Math.Abs(color.A) < 0.01)
return;
-
+ SDrawCoords dc;
CD3DTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
+ if (!_CalcDrawCoords(texture, rect, out dc, mirrored))
+ return;
- //Calculate the position
- const float x1 = 0;
- float x2 = texture.WidthRatio;
- float y1 = 0;
- float y2 = texture.HeightRatio;
-
- //Calculate the size
- float rx1 = rect.X;
- float rx2 = rect.X + rect.W;
- float ry1 = rect.Y;
- float ry2 = rect.Y + rect.H;
-
- color.A *= CGraphics.GlobalAlpha;
-
- Color c = color.AsColor();
-
- if (mirrored)
- {
- float tmp = y2;
- y2 = y1;
- y1 = tmp;
- }
- var vert = new STexturedColoredVertex[4];
- vert[0] = new STexturedColoredVertex(new Vector3(rx1, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x1, y1), c.ToArgb());
- vert[1] = new STexturedColoredVertex(new Vector3(rx1, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x1, y2), c.ToArgb());
- vert[2] = new STexturedColoredVertex(new Vector3(rx2, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x2, y2), c.ToArgb());
- vert[3] = new STexturedColoredVertex(new Vector3(rx2, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x2, y1), c.ToArgb());
- _AddToVertexBuffer(vert, texture.D3DTexture, _CalculateRotationMatrix(rect.Rotation, rx1, rx2, ry1, ry2));
+ _DrawTexture(texture, dc, color);
}
///
@@ -640,71 +644,16 @@ namespace Vocaluxe.Lib.Draw
/// True if the texture should be mirrored
public void DrawTexture(CTextureRef textureRef, SRectF rect, SColorF color, SRectF bounds, bool mirrored = false)
{
- if (Math.Abs(rect.W) < 1 || Math.Abs(rect.H) < 1 || Math.Abs(bounds.H) < 1 || Math.Abs(bounds.W) < 1 ||
- Math.Abs(color.A) < 0.01)
+ if (Math.Abs(color.A) < 0.01)
return;
-
- if (bounds.X > rect.X + rect.W || bounds.X + bounds.W < rect.X)
- return;
-
- if (bounds.Y > rect.Y + rect.H || bounds.Y + bounds.H < rect.Y)
- return;
-
+ SDrawCoords dc;
CD3DTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
+ if (!_CalcDrawCoords(texture, rect, bounds, out dc))
+ return;
- //Calculate the position
- float x1 = (bounds.X - rect.X) / rect.W * texture.WidthRatio;
- float x2 = (bounds.X + bounds.W - rect.X) / rect.W * texture.WidthRatio;
- float y1 = (bounds.Y - rect.Y) / rect.H * texture.HeightRatio;
- float y2 = (bounds.Y + bounds.H - rect.Y) / rect.H * texture.HeightRatio;
-
- if (x1 < 0)
- x1 = 0f;
-
- if (x2 > texture.WidthRatio)
- x2 = texture.WidthRatio;
-
- if (y1 < 0)
- y1 = 0f;
-
- if (y2 > texture.HeightRatio)
- y2 = texture.HeightRatio;
-
- //Calculate the size
- float rx1 = rect.X;
- float rx2 = rect.X + rect.W;
- float ry1 = rect.Y;
- float ry2 = rect.Y + rect.H;
-
- if (rx1 < bounds.X)
- rx1 = bounds.X;
-
- if (rx2 > bounds.X + bounds.W)
- rx2 = bounds.X + bounds.W;
-
- if (ry1 < bounds.Y)
- ry1 = bounds.Y;
-
- if (ry2 > bounds.Y + bounds.H)
- ry2 = bounds.Y + bounds.H;
-
- color.A *= CGraphics.GlobalAlpha;
-
- Color c = color.AsColor();
-
- if (mirrored)
- {
- y1 = -y1;
- y2 = -y2;
- }
- var vert = new STexturedColoredVertex[4];
- vert[0] = new STexturedColoredVertex(new Vector3(rx1, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x1, y1), c.ToArgb());
- vert[1] = new STexturedColoredVertex(new Vector3(rx1, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x1, y2), c.ToArgb());
- vert[2] = new STexturedColoredVertex(new Vector3(rx2, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x2, y2), c.ToArgb());
- vert[3] = new STexturedColoredVertex(new Vector3(rx2, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x2, y1), c.ToArgb());
- _AddToVertexBuffer(vert, texture.D3DTexture, _CalculateRotationMatrix(rect.Rotation, rx1, rx2, ry1, ry2));
+ _DrawTexture(texture, dc, color);
}
///
@@ -717,36 +666,16 @@ namespace Vocaluxe.Lib.Draw
/// A Value ranging from 0 to 1 containing the ending of the texture
public void DrawTexture(CTextureRef textureRef, SRectF rect, SColorF color, float begin, float end)
{
+ if (Math.Abs(color.A) < 0.01)
+ return;
+ SDrawCoords dc;
CD3DTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
+ if (!_CalcDrawCoords(texture, rect, out dc, false, begin, end))
+ return;
- float x1 = 0f + begin * texture.WidthRatio;
- float x2 = texture.WidthRatio * end;
- const float y1 = 0f;
- float y2 = texture.HeightRatio;
-
- float rx1 = rect.X + begin * rect.W;
- float rx2 = rect.X + end * rect.W;
- float ry1 = rect.Y;
- float ry2 = rect.Y + rect.H;
-
- //Align the pixels because Direct3D expects the pixels to be the left top corner
- rx1 -= 0.5f;
- ry1 -= 0.5f;
- rx2 -= 0.5f;
- ry2 -= 0.5f;
-
- color.A *= CGraphics.GlobalAlpha;
-
- Color c = color.AsColor();
-
- var vert = new STexturedColoredVertex[4];
- vert[0] = new STexturedColoredVertex(new Vector3(rx1, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x1, y1), c.ToArgb());
- vert[1] = new STexturedColoredVertex(new Vector3(rx1, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x1, y2), c.ToArgb());
- vert[2] = new STexturedColoredVertex(new Vector3(rx2, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x2, y2), c.ToArgb());
- vert[3] = new STexturedColoredVertex(new Vector3(rx2, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x2, y1), c.ToArgb());
- _AddToVertexBuffer(vert, texture.D3DTexture, _CalculateRotationMatrix(rect.Rotation, rx1, rx2, ry1, ry2));
+ _DrawTexture(texture, dc, color);
}
///
@@ -760,75 +689,25 @@ namespace Vocaluxe.Lib.Draw
/// The height of the reflection
public void DrawTextureReflection(CTextureRef textureRef, SRectF rect, SColorF color, SRectF bounds, float space, float height)
{
+ Debug.Assert(height >= 0);
+
+ if (Math.Abs(color.A) < 0.01 || height < 1)
+ return;
+ SDrawCoords dc;
CD3DTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
-
- if (Math.Abs(rect.W) < float.Epsilon || Math.Abs(rect.H) < float.Epsilon || Math.Abs(bounds.H) < float.Epsilon || Math.Abs(bounds.W) < float.Epsilon ||
- Math.Abs(color.A) < float.Epsilon || height <= 0f)
+ if (!_CalcDrawCoords(texture, rect, bounds, out dc, true))
return;
- if (bounds.X > rect.X + rect.W || bounds.X + bounds.W < rect.X)
- return;
+ if (height > rect.H)
+ height = rect.H;
- if (bounds.Y > rect.Y + rect.H || bounds.Y + bounds.H < rect.Y)
- return;
-
- if (height > bounds.H)
- height = bounds.H;
-
- float x1 = (bounds.X - rect.X) / rect.W * texture.WidthRatio;
- float x2 = (bounds.X + bounds.W - rect.X) / rect.W * texture.WidthRatio;
- float y1 = (bounds.Y - rect.Y + rect.H - height) / rect.H * texture.HeightRatio;
- float y2 = (bounds.Y + bounds.H - rect.Y) / rect.H * texture.HeightRatio;
-
- if (x1 < 0)
- x1 = 0f;
-
- if (x2 > texture.WidthRatio)
- x2 = texture.WidthRatio;
-
- if (y1 < 0)
- y1 = 0f;
-
- if (y2 > texture.HeightRatio)
- y2 = texture.HeightRatio;
-
-
- float rx1 = rect.X;
- float rx2 = rect.X + rect.W;
- float ry1 = rect.Y + rect.H + space;
- float ry2 = rect.Y + rect.H + space + height;
-
- if (rx1 < bounds.X)
- rx1 = bounds.X;
-
- if (rx2 > bounds.X + bounds.W)
- rx2 = bounds.X + bounds.W;
-
- if (ry1 < bounds.Y + space)
- ry1 = bounds.Y + space;
-
- if (ry2 > bounds.Y + bounds.H + space + height)
- ry2 = bounds.Y + bounds.H + space + height;
-
- //Align the pixels because Direct3D expects the pixels to be the left top corner
- rx1 -= 0.5f;
- ry1 -= 0.5f;
- rx2 -= 0.5f;
- ry2 -= 0.5f;
-
- color.A *= CGraphics.GlobalAlpha;
- Color c = color.AsColor();
- color.A = 0;
- Color transparent = color.AsColor();
-
- var vert = new STexturedColoredVertex[4];
- vert[0] = new STexturedColoredVertex(new Vector3(rx1, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x1, y2), c.ToArgb());
- vert[1] = new STexturedColoredVertex(new Vector3(rx1, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x1, y1), transparent.ToArgb());
- vert[2] = new STexturedColoredVertex(new Vector3(rx2, -ry2, rect.Z + CGraphics.ZOffset), new Vector2(x2, y1), transparent.ToArgb());
- vert[3] = new STexturedColoredVertex(new Vector3(rx2, -ry1, rect.Z + CGraphics.ZOffset), new Vector2(x2, y2), c.ToArgb());
- _AddToVertexBuffer(vert, texture.D3DTexture, _CalculateRotationMatrix(rect.Rotation, rx1, rx2, ry1, ry2));
+ dc.Wy1 += rect.H + space; // Move from start of rect to end of rect with spacing
+ dc.Wy2 += space + height; // Move from end of rect
+ dc.Ty2 += (rect.H - height) / rect.H; // Adjust so not all of the start of the texture is drawn (mirrored--> Ty1>Ty2)
+ if (dc.Ty2 < dc.Ty1) // Make sure we actually draw something
+ _DrawTexture(texture, dc, color, true);
}
#endregion drawing
diff --git a/Vocaluxe/Lib/Draw/CDrawBase.cs b/Vocaluxe/Lib/Draw/CDrawBase.cs
index 2b3ee242..19017a5f 100644
--- a/Vocaluxe/Lib/Draw/CDrawBase.cs
+++ b/Vocaluxe/Lib/Draw/CDrawBase.cs
@@ -213,6 +213,116 @@ namespace Vocaluxe.Lib.Draw
#region Textures
#region private/protected
+ ///
+ /// Struct that contains texture and world coordinates for drawing
+ ///
+ protected struct SDrawCoords
+ {
+ ///
+ /// Texture coordinates
+ ///
+ public float Tx1, Tx2, Ty1, Ty2;
+ ///
+ /// World coordinates
+ ///
+ public float Wx1, Wx2, Wy1, Wy2, Wz;
+ public float Rotation;
+ }
+
+ ///
+ /// Calculates the texture and world coordinates for drawing the texture in the rect cropping at the the bounds
+ ///
+ ///
+ /// Rect to draw the texture (might stretch the texture)
+ /// Rect to stay in (might crop the texture)
+ /// Struct for the coordinates
+ /// Mirror on y-axis
+ /// True if anything will be dawn
+ protected bool _CalcDrawCoords(TTextureType texture, SRectF rect, SRectF bounds, out SDrawCoords drawCoords, bool mirrored = false)
+ {
+ drawCoords = new SDrawCoords();
+ if (Math.Abs(rect.W) < 1 || Math.Abs(rect.H) < 1 || Math.Abs(bounds.H) < 1 || Math.Abs(bounds.W) < 1)
+ return false;
+
+ if (bounds.X >= rect.Right || bounds.Right <= rect.X)
+ return false;
+
+ if (bounds.Y >= rect.Bottom || bounds.Bottom <= rect.Y)
+ return false;
+
+ drawCoords.Tx1 = Math.Max(0, (bounds.X - rect.X) / rect.W * texture.WidthRatio);
+ drawCoords.Wx1 = Math.Max(rect.X, bounds.X);
+ drawCoords.Tx2 = Math.Min(1, (bounds.Right - rect.X) / rect.W) * texture.WidthRatio;
+ drawCoords.Wx2 = Math.Min(rect.Right, bounds.Right);
+
+ drawCoords.Ty1 = Math.Max(0, (bounds.Y - rect.Y) / rect.H * texture.HeightRatio);
+ drawCoords.Wy1 = Math.Max(rect.Y, bounds.Y);
+ drawCoords.Ty2 = Math.Min(1, (bounds.Bottom - rect.Y) / rect.H) * texture.HeightRatio;
+ drawCoords.Wy2 = Math.Min(rect.Bottom, bounds.Bottom);
+
+ //TODO: Check this:
+ /*//Align the pixels because Direct3D expects the pixels to be the left top corner
+ rx1 -= 0.5f;
+ ry1 -= 0.5f;
+ rx2 -= 0.5f;
+ ry2 -= 0.5f;*/
+
+ if (mirrored)
+ {
+ float tmp = drawCoords.Ty1;
+ drawCoords.Ty1 = drawCoords.Ty2;
+ drawCoords.Ty2 = tmp;
+ }
+
+ drawCoords.Wz = rect.Z + CGraphics.ZOffset;
+ drawCoords.Rotation = rect.Rotation;
+
+ return true;
+ }
+
+ ///
+ /// Calculates the texture and world coordinates for drawing (a part of) the texture in the rect
+ ///
+ /// Texture to draw
+ /// Rect to draw in (might stretch the texture)
+ /// Struct for the coordinates
+ /// Mirror on y axis
+ /// Position of the texture to begin drawing (0 <=x<=1)
+ /// Position of the texture to end drawing (0 <=x<=1)
+ /// True if anything will be dawn
+ protected bool _CalcDrawCoords(TTextureType texture, SRectF rect, out SDrawCoords drawCoords, bool mirrored = false, float begin = 0, float end = 1)
+ {
+ drawCoords = new SDrawCoords();
+ if (Math.Abs(rect.W) < 1 || Math.Abs(rect.H) < 1)
+ return false;
+ if (begin >= 1 || begin >= end)
+ return false;
+
+ Debug.Assert(begin.IsInRange(0, 1) && end.IsInRange(0, 1));
+
+ drawCoords.Tx1 = begin * texture.WidthRatio;
+ drawCoords.Wx1 = rect.X + begin * rect.W;
+ drawCoords.Tx2 = end * texture.WidthRatio;
+ drawCoords.Wx2 = rect.X + end * rect.W;
+
+ drawCoords.Ty1 = 0;
+ drawCoords.Wy1 = rect.Y;
+ drawCoords.Ty2 = texture.HeightRatio;
+ drawCoords.Wy2 = rect.Bottom;
+
+ if (mirrored)
+ {
+ float tmp = drawCoords.Ty1;
+ drawCoords.Ty1 = drawCoords.Ty2;
+ drawCoords.Ty2 = tmp;
+ }
+
+ drawCoords.Wz = rect.Z + CGraphics.ZOffset;
+ drawCoords.Rotation = rect.Rotation;
+
+ return true;
+ }
+
///
/// Returns the maximum area allowed for a texture based on the current quality
///
diff --git a/Vocaluxe/Lib/Draw/COpenGL.cs b/Vocaluxe/Lib/Draw/COpenGL.cs
index 4096572e..91cd3e31 100644
--- a/Vocaluxe/Lib/Draw/COpenGL.cs
+++ b/Vocaluxe/Lib/Draw/COpenGL.cs
@@ -15,6 +15,7 @@
// along with Vocaluxe. If not, see .
#endregion
+using System.Diagnostics;
using System.Drawing.Imaging;
using OpenTK;
using OpenTK.Graphics;
@@ -437,290 +438,137 @@ namespace Vocaluxe.Lib.Draw
}
#region drawing
+ private static void _DrawTexture(COGLTexture texture, SDrawCoords dc, SColorF color, bool isReflection = false)
+ {
+ GL.BindTexture(TextureTarget.Texture2D, texture.Name);
+
+ GL.Enable(EnableCap.Blend);
+
+ GL.MatrixMode(MatrixMode.Texture);
+ GL.PushMatrix();
+
+ if (Math.Abs(dc.Rotation) > float.Epsilon)
+ {
+ GL.Translate(0.5f, 0.5f, 0);
+ GL.Rotate(-dc.Rotation, 0f, 0f, 1f);
+ GL.Translate(-0.5f, -0.5f, 0);
+ }
+
+ GL.Begin(BeginMode.Quads);
+
+ GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
+ GL.TexCoord2(dc.Tx1, dc.Ty1);
+ GL.Vertex3(dc.Wx1, dc.Wy1, dc.Wz);
+
+ if (isReflection)
+ GL.Color4(color.R, color.G, color.B, 0);
+ GL.TexCoord2(dc.Tx1, dc.Ty2);
+ GL.Vertex3(dc.Wx1, dc.Wy2, dc.Wz);
+
+ GL.TexCoord2(dc.Tx2, dc.Ty2);
+ GL.Vertex3(dc.Wx2, dc.Wy2, dc.Wz);
+
+ if (isReflection)
+ GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
+ GL.TexCoord2(dc.Tx2, dc.Ty1);
+ GL.Vertex3(dc.Wx2, dc.Wy1, dc.Wz);
+
+ GL.End();
+
+ GL.PopMatrix();
+
+ GL.Disable(EnableCap.Blend);
+ GL.BindTexture(TextureTarget.Texture2D, 0);
+ }
+
public void DrawTexture(CTextureRef textureRef, SRectF rect, SColorF color, bool mirrored = false)
{
+ if (Math.Abs(color.A) < 0.01)
+ return;
+ SDrawCoords dc;
COGLTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
-
- if (Math.Abs(rect.W) < 1 || Math.Abs(rect.H) < 1 || Math.Abs(color.A) < 0.01)
+ if (!_CalcDrawCoords(texture, rect, out dc, mirrored))
return;
- GL.BindTexture(TextureTarget.Texture2D, texture.Name);
-
- const float x1 = 0;
- float x2 = texture.WidthRatio;
- float y1 = 0;
- float y2 = texture.HeightRatio;
-
- float rx1 = rect.X;
- float rx2 = rect.X + rect.W;
- float ry1 = rect.Y;
- float ry2 = rect.Y + rect.H;
-
- GL.Enable(EnableCap.Blend);
- GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
-
- GL.MatrixMode(MatrixMode.Texture);
- GL.PushMatrix();
-
- if (Math.Abs(rect.Rotation) > float.Epsilon)
- {
- GL.Translate(0.5f, 0.5f, 0);
- GL.Rotate(-rect.Rotation, 0f, 0f, 1f);
- GL.Translate(-0.5f, -0.5f, 0);
- }
-
- if (mirrored)
- {
- float tmp = y2;
- y2 = y1;
- y1 = tmp;
- }
-
- GL.Begin(BeginMode.Quads);
-
- GL.TexCoord2(x1, y1);
- GL.Vertex3(rx1, ry1, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(x1, y2);
- GL.Vertex3(rx1, ry2, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(x2, y2);
- GL.Vertex3(rx2, ry2, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(x2, y1);
- GL.Vertex3(rx2, ry1, rect.Z + CGraphics.ZOffset);
-
- GL.End();
-
- GL.PopMatrix();
-
- GL.Disable(EnableCap.Blend);
- GL.BindTexture(TextureTarget.Texture2D, 0);
+ _DrawTexture(texture, dc, color);
}
+ ///
+ /// Draws a texture
+ ///
+ /// The texture to be drawn
+ /// A SRectF struct containing the destination coordinates
+ /// A SColorF struct containing a color which the texture will be colored in
+ /// A SRectF struct containing which part of the texture should be drawn
+ /// True if the texture should be mirrored
public void DrawTexture(CTextureRef textureRef, SRectF rect, SColorF color, SRectF bounds, bool mirrored = false)
{
+ if (Math.Abs(color.A) < 0.01)
+ return;
+ SDrawCoords dc;
COGLTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
-
- if (Math.Abs(rect.W) < 1 || Math.Abs(rect.H) < 1 || Math.Abs(bounds.H) < 1 || Math.Abs(bounds.W) < 1 ||
- Math.Abs(color.A) < 0.01)
+ if (!_CalcDrawCoords(texture, rect, bounds, out dc))
return;
- if (bounds.X > rect.X + rect.W || bounds.X + bounds.W < rect.X)
- return;
-
- if (bounds.Y > rect.Y + rect.H || bounds.Y + bounds.H < rect.Y)
- return;
-
- GL.BindTexture(TextureTarget.Texture2D, texture.Name);
-
- float x1 = (bounds.X - rect.X) / rect.W * texture.WidthRatio;
- float x2 = (bounds.X + bounds.W - rect.X) / rect.W * texture.WidthRatio;
- float y1 = (bounds.Y - rect.Y) / rect.H * texture.HeightRatio;
- float y2 = (bounds.Y + bounds.H - rect.Y) / rect.H * texture.HeightRatio;
-
- if (x1 < 0)
- x1 = 0f;
-
- if (x2 > texture.WidthRatio)
- x2 = texture.WidthRatio;
-
- if (y1 < 0)
- y1 = 0f;
-
- if (y2 > texture.HeightRatio)
- y2 = texture.HeightRatio;
-
-
- float rx1 = rect.X;
- float rx2 = rect.X + rect.W;
- float ry1 = rect.Y;
- float ry2 = rect.Y + rect.H;
-
- if (rx1 < bounds.X)
- rx1 = bounds.X;
-
- if (rx2 > bounds.X + bounds.W)
- rx2 = bounds.X + bounds.W;
-
- if (ry1 < bounds.Y)
- ry1 = bounds.Y;
-
- if (ry2 > bounds.Y + bounds.H)
- ry2 = bounds.Y + bounds.H;
-
- GL.Enable(EnableCap.Blend);
- GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
-
- GL.MatrixMode(MatrixMode.Texture);
- GL.PushMatrix();
-
- if (Math.Abs(rect.Rotation) > float.Epsilon)
- {
- GL.Translate(0.5f, 0.5f, 0);
- GL.Rotate(-rect.Rotation, 0f, 0f, 1f);
- GL.Translate(-0.5f, -0.5f, 0);
- }
-
- if (mirrored)
- {
- float tmp = y2;
- y2 = y1;
- y1 = tmp;
- }
-
- GL.Begin(BeginMode.Quads);
-
- GL.TexCoord2(x1, y1);
- GL.Vertex3(rx1, ry1, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(x1, y2);
- GL.Vertex3(rx1, ry2, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(x2, y2);
- GL.Vertex3(rx2, ry2, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(x2, y1);
- GL.Vertex3(rx2, ry1, rect.Z + CGraphics.ZOffset);
-
- GL.End();
-
- GL.PopMatrix();
-
- GL.Disable(EnableCap.Blend);
- GL.BindTexture(TextureTarget.Texture2D, 0);
+ _DrawTexture(texture, dc, color);
}
+ ///
+ /// Draws a texture
+ ///
+ /// The texture to be drawn
+ /// A SRectF struct containing the destination coordinates
+ /// A SColorF struct containing a color which the texture will be colored in
+ /// A Value ranging from 0 to 1 containing the beginning of the texture
+ /// A Value ranging from 0 to 1 containing the ending of the texture
public void DrawTexture(CTextureRef textureRef, SRectF rect, SColorF color, float begin, float end)
{
+ if (Math.Abs(color.A) < 0.01)
+ return;
+ SDrawCoords dc;
COGLTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
+ if (!_CalcDrawCoords(texture, rect, out dc, false, begin, end))
+ return;
- GL.BindTexture(TextureTarget.Texture2D, texture.Name);
-
- GL.Enable(EnableCap.Blend);
- GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
-
-
- GL.Begin(BeginMode.Quads);
-
- GL.TexCoord2(0f + begin * texture.WidthRatio, 0f);
- GL.Vertex3(rect.X + begin * rect.W, rect.Y, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(0f + begin * texture.WidthRatio, texture.HeightRatio);
- GL.Vertex3(rect.X + begin * rect.W, rect.Y + rect.H, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(texture.WidthRatio * end, texture.HeightRatio);
- GL.Vertex3(rect.X + end * rect.W, rect.Y + rect.H, rect.Z + CGraphics.ZOffset);
-
- GL.TexCoord2(texture.WidthRatio * end, 0f);
- GL.Vertex3(rect.X + end * rect.W, rect.Y, rect.Z + CGraphics.ZOffset);
-
- GL.End();
-
- GL.Disable(EnableCap.Blend);
- GL.BindTexture(TextureTarget.Texture2D, 0);
+ _DrawTexture(texture, dc, color);
}
+ ///
+ /// Draws a reflection of a texture
+ ///
+ /// The texture of which a reflection should be drawn
+ /// A SRectF struct containing the destination coordinates
+ /// A SColorF struct containing a color which the texture will be colored in
+ /// A SRectF struct containing which part of the texture should be drawn
+ /// The space between the texture and the reflection
+ /// The height of the reflection
public void DrawTextureReflection(CTextureRef textureRef, SRectF rect, SColorF color, SRectF bounds, float space, float height)
{
+ Debug.Assert(height >= 0);
+
+ if (Math.Abs(color.A) < 0.01 || height < 1)
+ return;
+ SDrawCoords dc;
COGLTexture texture;
if (!_GetTexture(textureRef, out texture))
return;
-
- if (Math.Abs(rect.W) < float.Epsilon || Math.Abs(rect.H) < float.Epsilon || Math.Abs(bounds.H) < float.Epsilon || Math.Abs(bounds.W) < float.Epsilon ||
- Math.Abs(color.A) < float.Epsilon || height <= float.Epsilon)
+ if (!_CalcDrawCoords(texture, rect, bounds, out dc, true))
return;
- if (bounds.X > rect.X + rect.W || bounds.X + bounds.W < rect.X)
- return;
+ if (height > rect.H)
+ height = rect.H;
- if (bounds.Y > rect.Y + rect.H || bounds.Y + bounds.H < rect.Y)
- return;
-
- if (height > bounds.H)
- height = bounds.H;
-
- GL.BindTexture(TextureTarget.Texture2D, texture.Name);
-
- float x1 = (bounds.X - rect.X) / rect.W * texture.WidthRatio;
- float x2 = (bounds.X + bounds.W - rect.X) / rect.W * texture.WidthRatio;
- float y1 = (bounds.Y - rect.Y + rect.H - height) / rect.H * texture.HeightRatio;
- float y2 = (bounds.Y + bounds.H - rect.Y) / rect.H * texture.HeightRatio;
-
- if (x1 < 0)
- x1 = 0f;
-
- if (x2 > texture.WidthRatio)
- x2 = texture.WidthRatio;
-
- if (y1 < 0)
- y1 = 0f;
-
- if (y2 > texture.HeightRatio)
- y2 = texture.HeightRatio;
-
-
- float rx1 = rect.X;
- float rx2 = rect.X + rect.W;
- float ry1 = rect.Y + rect.H + space;
- float ry2 = rect.Y + rect.H + space + height;
-
- if (rx1 < bounds.X)
- rx1 = bounds.X;
-
- if (rx2 > bounds.X + bounds.W)
- rx2 = bounds.X + bounds.W;
-
- if (ry1 < bounds.Y + space)
- ry1 = bounds.Y + space;
-
- if (ry2 > bounds.Y + bounds.H + space + height)
- ry2 = bounds.Y + bounds.H + space + height;
-
- GL.Enable(EnableCap.Blend);
-
- GL.MatrixMode(MatrixMode.Texture);
- GL.PushMatrix();
-
- if (Math.Abs(rect.Rotation) > float.Epsilon)
- {
- GL.Translate(0.5f, 0.5f, 0);
- GL.Rotate(-rect.Rotation, 0f, 0f, 1f);
- GL.Translate(-0.5f, -0.5f, 0);
- }
-
-
- GL.Begin(BeginMode.Quads);
-
- GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
- GL.TexCoord2(x2, y2);
- GL.Vertex3(rx2, ry1, rect.Z + CGraphics.ZOffset);
-
- GL.Color4(color.R, color.G, color.B, 0f);
- GL.TexCoord2(x2, y1);
- GL.Vertex3(rx2, ry2, rect.Z + CGraphics.ZOffset);
-
- GL.Color4(color.R, color.G, color.B, 0f);
- GL.TexCoord2(x1, y1);
- GL.Vertex3(rx1, ry2, rect.Z + CGraphics.ZOffset);
-
- GL.Color4(color.R, color.G, color.B, color.A * CGraphics.GlobalAlpha);
- GL.TexCoord2(x1, y2);
- GL.Vertex3(rx1, ry1, rect.Z + CGraphics.ZOffset);
-
- GL.End();
-
-
- GL.PopMatrix();
-
- GL.Disable(EnableCap.Blend);
- GL.BindTexture(TextureTarget.Texture2D, 0);
+ dc.Wy1 += rect.H + space; // Move from start of rect to end of rect with spacing
+ dc.Wy2 += space + height; // Move from end of rect
+ dc.Ty2 += (rect.H - height) / rect.H; // Adjust so not all of the start of the texture is drawn (mirrored--> Ty1>Ty2)
+ if (dc.Ty2 < dc.Ty1) // Make sure we actually draw something
+ _DrawTexture(texture, dc, color, true);
}
#endregion drawing
diff --git a/Vocaluxe/Lib/Draw/CTextureBase.cs b/Vocaluxe/Lib/Draw/CTextureBase.cs
index eb9d11bf..ab4850b3 100644
--- a/Vocaluxe/Lib/Draw/CTextureBase.cs
+++ b/Vocaluxe/Lib/Draw/CTextureBase.cs
@@ -62,11 +62,11 @@ namespace Vocaluxe.Lib.Draw
private void _CalcRatios()
{
- // OpenGL has a problem with partial (NPOT) textures, so we remove 1 pixel
if (_DataSize.Width == W2)
WidthRatio = 1f;
else
{
+ // OpenGL has a problem with partial (NPOT) textures, so we remove 1 pixel
int mod = 0;
if (_DataSize.Width > 1)
mod = -1;