mirror of
https://github.com/Phantop/LADXHD.git
synced 2024-11-01 04:14:22 +00:00
201 lines
9.7 KiB
C#
201 lines
9.7 KiB
C#
|
using System;
|
|||
|
using Microsoft.Xna.Framework;
|
|||
|
using Microsoft.Xna.Framework.Graphics;
|
|||
|
using ProjectZ.InGame.Map;
|
|||
|
using ProjectZ.InGame.SaveLoad;
|
|||
|
|
|||
|
namespace ProjectZ.InGame.Things
|
|||
|
{
|
|||
|
class DrawHelper
|
|||
|
{
|
|||
|
// more then 1000 will only make sense on a high resolution with a small game scale
|
|||
|
public const int MaxShadowIndices = 1000;
|
|||
|
public static int CurrentShadowIndex;
|
|||
|
public static short[] IndexDataShadow = new short[MaxShadowIndices * 6];
|
|||
|
public static float ShadowHeight;
|
|||
|
public static float ShadowOffset;
|
|||
|
public static Texture2D LastShadowTexture;
|
|||
|
|
|||
|
private static Matrix projectionMatrix;
|
|||
|
private static Matrix outMatrix;
|
|||
|
public static VertexPositionPositionColorTexture[] ShadowVertexArray = new VertexPositionPositionColorTexture[MaxShadowIndices * 4];
|
|||
|
|
|||
|
public static void StartShadowDrawing()
|
|||
|
{
|
|||
|
//projectionMatrix = Matrix.CreateOrthographicOffCenter(0,
|
|||
|
// Game1.Graphics.PreferredBackBufferWidth, Game1.Graphics.PreferredBackBufferHeight, 0, 0, -1);
|
|||
|
//outMatrix = MapManager.Camera.TransformMatrix * projectionMatrix;
|
|||
|
|
|||
|
//Resources.NextShadowEffect.Parameters["WorldViewProjection"].SetValue(outMatrix);
|
|||
|
|
|||
|
//Game1.SpriteBatch.Begin(SpriteSortMode.Deferred, null, null, null, null, Resources.NextShadowEffect, MapManager.Camera.TransformMatrix);
|
|||
|
|
|||
|
LastShadowTexture = null;
|
|||
|
CurrentShadowIndex = 0;
|
|||
|
}
|
|||
|
|
|||
|
public static void EndShadowDrawing()
|
|||
|
{
|
|||
|
//Game1.SpriteBatch.End();
|
|||
|
|
|||
|
if (CurrentShadowIndex > 0)
|
|||
|
DrawIndexedDataNew();
|
|||
|
}
|
|||
|
|
|||
|
// TODO_End: this should be done using normal spritebatch.Draw()
|
|||
|
public static void DrawShadow(Texture2D sprImage, Vector2 drawPosition, Rectangle sourceRectangle,
|
|||
|
float drawWidth, float drawHeight, bool mirror, float height, float rotation, Color color)
|
|||
|
{
|
|||
|
//Game1.SpriteBatch.Draw(sprImage, drawPosition, sourceRectangle, color);
|
|||
|
|
|||
|
if (LastShadowTexture != null && (LastShadowTexture != sprImage ||
|
|||
|
CurrentShadowIndex >= MaxShadowIndices || ShadowHeight != height || ShadowOffset != rotation))
|
|||
|
{
|
|||
|
// draw the stored data
|
|||
|
DrawIndexedDataNew();
|
|||
|
CurrentShadowIndex = 0;
|
|||
|
}
|
|||
|
|
|||
|
SetVertexPtIndexed(ShadowVertexArray, CurrentShadowIndex * 4, drawPosition, sourceRectangle,
|
|||
|
drawWidth, drawHeight, sprImage.Width, sprImage.Height, mirror, color);
|
|||
|
|
|||
|
SetIndexBuffer(IndexDataShadow, CurrentShadowIndex * 6, CurrentShadowIndex * 4);
|
|||
|
|
|||
|
CurrentShadowIndex++;
|
|||
|
|
|||
|
ShadowHeight = height;
|
|||
|
ShadowOffset = rotation;
|
|||
|
LastShadowTexture = sprImage;
|
|||
|
}
|
|||
|
|
|||
|
public struct VertexPositionPositionColorTexture : IVertexType
|
|||
|
{
|
|||
|
public Vector2 Position;
|
|||
|
public Vector2 TextureCoordinate;
|
|||
|
public Vector2 UpperLeftPosition;
|
|||
|
public Vector2 SourceSize;
|
|||
|
public Color Color;
|
|||
|
|
|||
|
public VertexPositionPositionColorTexture(
|
|||
|
Vector2 position, Vector2 textureCoordinate, Vector2 upperLeftPosition, Vector2 sourceSize, Color color)
|
|||
|
{
|
|||
|
Position = position;
|
|||
|
TextureCoordinate = textureCoordinate;
|
|||
|
UpperLeftPosition = upperLeftPosition;
|
|||
|
SourceSize = sourceSize;
|
|||
|
Color = color;
|
|||
|
}
|
|||
|
|
|||
|
public static readonly VertexDeclaration VertexDeclaration;
|
|||
|
|
|||
|
VertexDeclaration IVertexType.VertexDeclaration => VertexDeclaration;
|
|||
|
|
|||
|
static VertexPositionPositionColorTexture()
|
|||
|
{
|
|||
|
var elements = new[]
|
|||
|
{
|
|||
|
new VertexElement(0, VertexElementFormat.Vector2, VertexElementUsage.Position, 0),
|
|||
|
new VertexElement(8, VertexElementFormat.Vector2, VertexElementUsage.TextureCoordinate, 0),
|
|||
|
new VertexElement(16, VertexElementFormat.Vector2, VertexElementUsage.TextureCoordinate, 1),
|
|||
|
new VertexElement(24, VertexElementFormat.Vector2, VertexElementUsage.TextureCoordinate, 2),
|
|||
|
new VertexElement(32, VertexElementFormat.Color, VertexElementUsage.Color, 0),
|
|||
|
};
|
|||
|
VertexDeclaration = new VertexDeclaration(elements);
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
public static void SetVertexPtIndexed(
|
|||
|
VertexPositionPositionColorTexture[] buffer, int index,
|
|||
|
Vector2 position, Rectangle sourceRectangle, float drawWidth, float drawHeight,
|
|||
|
int textureWidth, int textureHeight, bool mirror, Color color)
|
|||
|
{
|
|||
|
var posLeft = position.X;
|
|||
|
var posRight = position.X + drawWidth;// sourceRectangle.Width;
|
|||
|
var posTop = position.Y;
|
|||
|
var posBottom = position.Y + drawHeight;// sourceRectangle.Height;
|
|||
|
|
|||
|
var left = (!mirror ? sourceRectangle.X : sourceRectangle.Right) / (float)textureWidth;
|
|||
|
var right = (!mirror ? sourceRectangle.Right : sourceRectangle.X) / (float)textureWidth;
|
|||
|
var top = sourceRectangle.Y / (float)textureHeight;
|
|||
|
var bottom = sourceRectangle.Bottom / (float)textureHeight;
|
|||
|
|
|||
|
buffer[index + 0] = new VertexPositionPositionColorTexture(
|
|||
|
new Vector2(posLeft, posTop), new Vector2(left, top), position,
|
|||
|
new Vector2(sourceRectangle.Width, sourceRectangle.Height), color);
|
|||
|
buffer[index + 1] = new VertexPositionPositionColorTexture(
|
|||
|
new Vector2(posRight, posTop), new Vector2(right, top), position,
|
|||
|
new Vector2(sourceRectangle.Width, sourceRectangle.Height), color);
|
|||
|
buffer[index + 2] = new VertexPositionPositionColorTexture(
|
|||
|
new Vector2(posLeft, posBottom), new Vector2(left, bottom), position,
|
|||
|
new Vector2(sourceRectangle.Width, sourceRectangle.Height), color);
|
|||
|
buffer[index + 3] = new VertexPositionPositionColorTexture(
|
|||
|
new Vector2(posRight, posBottom), new Vector2(right, bottom), position,
|
|||
|
new Vector2(sourceRectangle.Width, sourceRectangle.Height), color);
|
|||
|
}
|
|||
|
|
|||
|
public static void DrawIndexedDataNew()
|
|||
|
{
|
|||
|
projectionMatrix = Matrix.CreateOrthographicOffCenter(0,
|
|||
|
Game1.GameManager.CurrentRenderWidth, Game1.GameManager.CurrentRenderHeight, 0, 0, -1);
|
|||
|
outMatrix = MapManager.Camera.TransformMatrix * projectionMatrix;
|
|||
|
|
|||
|
Resources.FullShadowEffect.Parameters["xViewProjection"].SetValue(outMatrix);
|
|||
|
Resources.FullShadowEffect.Parameters["height"].SetValue(ShadowHeight);
|
|||
|
Resources.FullShadowEffect.Parameters["offsetX"].SetValue(ShadowOffset);
|
|||
|
|
|||
|
foreach (var pass in Resources.FullShadowEffect.CurrentTechnique.Passes)
|
|||
|
{
|
|||
|
pass.Apply();
|
|||
|
Game1.Graphics.GraphicsDevice.Textures[0] = LastShadowTexture;
|
|||
|
Game1.Graphics.GraphicsDevice.DrawUserIndexedPrimitives(
|
|||
|
PrimitiveType.TriangleList, ShadowVertexArray, 0, CurrentShadowIndex * 4, IndexDataShadow, 0, CurrentShadowIndex * 2);
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
public static void SetIndexBuffer(short[] buffer, int position, int offset)
|
|||
|
{
|
|||
|
buffer[position + 0] = (short)(offset + 0);
|
|||
|
buffer[position + 1] = (short)(offset + 1);
|
|||
|
buffer[position + 2] = (short)(offset + 2);
|
|||
|
|
|||
|
buffer[position + 3] = (short)(offset + 2);
|
|||
|
buffer[position + 4] = (short)(offset + 1);
|
|||
|
buffer[position + 5] = (short)(offset + 3);
|
|||
|
}
|
|||
|
|
|||
|
public static void DrawLight(SpriteBatch spriteBatch, Rectangle lightRectangle, Color lightColor)
|
|||
|
{
|
|||
|
spriteBatch.Draw(Resources.SprLight, lightRectangle, lightColor);
|
|||
|
}
|
|||
|
|
|||
|
public static void DrawCenter(SpriteBatch spriteBatch, Texture2D sprTexture, Point offset,
|
|||
|
Rectangle centerRectangle, Rectangle sourceRectangle, int scale)
|
|||
|
{
|
|||
|
spriteBatch.Draw(sprTexture, new Rectangle(
|
|||
|
offset.X + (centerRectangle.X + centerRectangle.Width / 2 - sourceRectangle.Width / 2) * scale,
|
|||
|
offset.Y + (centerRectangle.Y + centerRectangle.Height / 2 - sourceRectangle.Height / 2) * scale,
|
|||
|
sourceRectangle.Width * scale,
|
|||
|
sourceRectangle.Height * scale), sourceRectangle, Color.White);
|
|||
|
}
|
|||
|
|
|||
|
public static void DrawNormalized(SpriteBatch spriteBatch, Texture2D texture,
|
|||
|
Vector2 position, Rectangle sourceRectangle, Color color, float scale = 1.0f)
|
|||
|
{
|
|||
|
var normalizedPosition = new Vector2(
|
|||
|
(float)Math.Round(position.X * MapManager.Camera.Scale) / MapManager.Camera.Scale,
|
|||
|
(float)Math.Round(position.Y * MapManager.Camera.Scale) / MapManager.Camera.Scale);
|
|||
|
|
|||
|
spriteBatch.Draw(texture, normalizedPosition, sourceRectangle, color, 0, Vector2.Zero, new Vector2(scale), SpriteEffects.None, 0);
|
|||
|
}
|
|||
|
|
|||
|
public static void DrawNormalized(SpriteBatch spriteBatch, DictAtlasEntry sprite, Vector2 position, Color color)
|
|||
|
{
|
|||
|
var normalizedPosition = new Vector2(
|
|||
|
(float)Math.Round(position.X * MapManager.Camera.Scale) / MapManager.Camera.Scale,
|
|||
|
(float)Math.Round(position.Y * MapManager.Camera.Scale) / MapManager.Camera.Scale);
|
|||
|
|
|||
|
spriteBatch.Draw(sprite.Texture, normalizedPosition, sprite.ScaledRectangle, color, 0, sprite.Origin, new Vector2(sprite.Scale), SpriteEffects.None, 0);
|
|||
|
}
|
|||
|
}
|
|||
|
}
|