diff --git a/CHANGELOG b/CHANGELOG index 0fdffab12a..fb17e4ddea 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -11,11 +11,16 @@ NEW: Converted production exits to world coordinates. Converted weapon projectiles to world coordinates. Converted actor speed to world coordinates. + Added support for rectangular cells with forced perspective. + Added initial support for Tmp(TS) sprites. + Asset Browser: + Filenames are now listed in alphabetical order Mod / Custom map compatibility: Altitude is no longer parsed from actor templates in maps. Specify CenterPosition instead. Run `OpenRA.Utility.exe --upgrade-mod 20131223` to automatically upgrade mod rules. Run `OpenRA.Utility.exe --upgrade-map 20131223` to automatically upgrade custom map rules. Added a new trait Demolishable for buildings to handle the C4 demolition. + Mods that use custom TileSize must specify both width and height. 20131223: All mods: diff --git a/OpenRA.Editor/BrushTool.cs b/OpenRA.Editor/BrushTool.cs index 9028eccc5a..5139eac0eb 100644 --- a/OpenRA.Editor/BrushTool.cs +++ b/OpenRA.Editor/BrushTool.cs @@ -63,8 +63,8 @@ namespace OpenRA.Editor public void Preview(Surface surface, SGraphics g) { g.DrawImage(brushTemplate.Bitmap, - surface.TileSetRenderer.TileSize.Width * surface.GetBrushLocation().X * surface.Zoom + surface.GetOffset().X, - surface.TileSetRenderer.TileSize.Height * surface.GetBrushLocation().Y * surface.Zoom + surface.GetOffset().Y, + surface.TileSetRenderer.TileSize * surface.GetBrushLocation().X * surface.Zoom + surface.GetOffset().X, + surface.TileSetRenderer.TileSize * surface.GetBrushLocation().Y * surface.Zoom + surface.GetOffset().Y, brushTemplate.Bitmap.Width * surface.Zoom, brushTemplate.Bitmap.Height * surface.Zoom); } diff --git a/OpenRA.Editor/Form1.cs b/OpenRA.Editor/Form1.cs index 9745ca53d4..b3ffb39b5e 100644 --- a/OpenRA.Editor/Form1.cs +++ b/OpenRA.Editor/Form1.cs @@ -145,7 +145,7 @@ namespace OpenRA.Editor { Rules.LoadRules(manifest, map); tileset = Rules.TileSets[map.Tileset]; - tilesetRenderer = new TileSetRenderer(tileset, new Size(manifest.TileSize, manifest.TileSize)); + tilesetRenderer = new TileSetRenderer(tileset, manifest.TileSize); var shadowIndex = new int[] { 3, 4 }; var palette = new Palette(FileSystem.Open(tileset.Palette), shadowIndex); diff --git a/OpenRA.Editor/Surface.cs b/OpenRA.Editor/Surface.cs index 793d84145a..d5c235a99c 100644 --- a/OpenRA.Editor/Surface.cs +++ b/OpenRA.Editor/Surface.cs @@ -257,7 +257,7 @@ namespace OpenRA.Editor Bitmap RenderChunk(int u, int v) { - var bitmap = new Bitmap(ChunkSize * TileSetRenderer.TileSize.Width, ChunkSize * TileSetRenderer.TileSize.Height); + var bitmap = new Bitmap(ChunkSize * TileSetRenderer.TileSize, ChunkSize * TileSetRenderer.TileSize); var data = bitmap.LockBits(bitmap.Bounds(), ImageLockMode.WriteOnly, PixelFormat.Format32bppArgb); @@ -274,9 +274,9 @@ namespace OpenRA.Editor var tile = TileSetRenderer.Data(tr.Type); var index = (tr.Index < tile.Count) ? tr.Index : (byte)0; var rawImage = tile[index]; - for (var x = 0; x < TileSetRenderer.TileSize.Width; x++) - for (var y = 0; y < TileSetRenderer.TileSize.Height; y++) - p[(j * TileSetRenderer.TileSize.Width + y) * stride + i * TileSetRenderer.TileSize.Width + x] = Palette.GetColor(rawImage[x + TileSetRenderer.TileSize.Width * y]).ToArgb(); + for (var x = 0; x < TileSetRenderer.TileSize; x++) + for (var y = 0; y < TileSetRenderer.TileSize; y++) + p[(j * TileSetRenderer.TileSize + y) * stride + i * TileSetRenderer.TileSize + x] = Palette.GetColor(rawImage[x + TileSetRenderer.TileSize * y]).ToArgb(); if (Map.MapResources.Value[u * ChunkSize + i, v * ChunkSize + j].Type != 0) { @@ -287,12 +287,12 @@ namespace OpenRA.Editor int* q = (int*)srcdata.Scan0.ToPointer(); var srcstride = srcdata.Stride >> 2; - for (var x = 0; x < TileSetRenderer.TileSize.Width; x++) - for (var y = 0; y < TileSetRenderer.TileSize.Height; y++) + for (var x = 0; x < TileSetRenderer.TileSize; x++) + for (var y = 0; y < TileSetRenderer.TileSize; y++) { var c = q[y * srcstride + x]; if ((c & 0xff000000) != 0) /* quick & dirty, i cbf doing real alpha */ - p[(j * TileSetRenderer.TileSize.Width + y) * stride + i * TileSetRenderer.TileSize.Width + x] = c; + p[(j * TileSetRenderer.TileSize + y) * stride + i * TileSetRenderer.TileSize + x] = c; } resourceImage.UnlockBits(srcdata); @@ -303,14 +303,16 @@ namespace OpenRA.Editor bitmap.UnlockBits(data); if (ShowGrid) + { using (var g = SGraphics.FromImage(bitmap)) { + var ts = Game.modData.Manifest.TileSize; var rect = new Rectangle(0, 0, bitmap.Width, bitmap.Height); - ControlPaint.DrawGrid(g, rect, new Size(2, Game.CellSize), Color.DarkRed); - ControlPaint.DrawGrid(g, rect, new Size(Game.CellSize, 2), Color.DarkRed); - ControlPaint.DrawGrid(g, rect, new Size(Game.CellSize, Game.CellSize), Color.Red); + ControlPaint.DrawGrid(g, rect, new Size(2, ts.Height), Color.DarkRed); + ControlPaint.DrawGrid(g, rect, new Size(ts.Width, 2), Color.DarkRed); + ControlPaint.DrawGrid(g, rect, new Size(ts.Width, ts.Height), Color.Red); } - + } return bitmap; } @@ -318,15 +320,15 @@ namespace OpenRA.Editor { var vX = (int)Math.Floor((mousePos.X - Offset.X) / Zoom); var vY = (int)Math.Floor((mousePos.Y - Offset.Y) / Zoom); - return new CPos(vX / TileSetRenderer.TileSize.Width, vY / TileSetRenderer.TileSize.Height); + return new CPos(vX / TileSetRenderer.TileSize, vY / TileSetRenderer.TileSize); } public CPos GetBrushLocationBR() { var vX = (int)Math.Floor((mousePos.X - Offset.X) / Zoom); var vY = (int)Math.Floor((mousePos.Y - Offset.Y) / Zoom); - return new CPos((vX + TileSetRenderer.TileSize.Width - 1) / TileSetRenderer.TileSize.Width, - (vY + TileSetRenderer.TileSize.Height - 1) / TileSetRenderer.TileSize.Height); + return new CPos((vX + TileSetRenderer.TileSize - 1) / TileSetRenderer.TileSize, + (vY + TileSetRenderer.TileSize - 1) / TileSetRenderer.TileSize); } public void DrawActor(SGraphics g, CPos p, ActorTemplate t, ColorPalette cp) @@ -340,11 +342,11 @@ namespace OpenRA.Editor float2 GetDrawPosition(CPos location, Bitmap bmp, bool centered) { - float offsetX = centered ? bmp.Width / 2 - TileSetRenderer.TileSize.Width / 2 : 0; - float drawX = TileSetRenderer.TileSize.Width * location.X * Zoom + Offset.X - offsetX; + float offsetX = centered ? bmp.Width / 2 - TileSetRenderer.TileSize / 2 : 0; + float drawX = TileSetRenderer.TileSize * location.X * Zoom + Offset.X - offsetX; - float offsetY = centered ? bmp.Height / 2 - TileSetRenderer.TileSize.Height / 2 : 0; - float drawY = TileSetRenderer.TileSize.Height * location.Y * Zoom + Offset.Y - offsetY; + float offsetY = centered ? bmp.Height / 2 - TileSetRenderer.TileSize / 2 : 0; + float drawY = TileSetRenderer.TileSize * location.Y * Zoom + Offset.Y - offsetY; return new float2(drawX, drawY); } @@ -412,24 +414,24 @@ namespace OpenRA.Editor var bmp = Chunks[x]; - var drawX = TileSetRenderer.TileSize.Width * (float)ChunkSize * (float)x.X * Zoom + Offset.X; - var drawY = TileSetRenderer.TileSize.Height * (float)ChunkSize * (float)x.Y * Zoom + Offset.Y; + var drawX = TileSetRenderer.TileSize * (float)ChunkSize * (float)x.X * Zoom + Offset.X; + var drawY = TileSetRenderer.TileSize * (float)ChunkSize * (float)x.Y * Zoom + Offset.Y; RectangleF sourceRect = new RectangleF(0, 0, bmp.Width, bmp.Height); RectangleF destRect = new RectangleF(drawX, drawY, bmp.Width * Zoom, bmp.Height * Zoom); e.Graphics.DrawImage(bmp, destRect, sourceRect, GraphicsUnit.Pixel); } e.Graphics.DrawRectangle(CordonPen, - Map.Bounds.Left * TileSetRenderer.TileSize.Width * Zoom + Offset.X, - Map.Bounds.Top * TileSetRenderer.TileSize.Height * Zoom + Offset.Y, - Map.Bounds.Width * TileSetRenderer.TileSize.Width * Zoom, - Map.Bounds.Height * TileSetRenderer.TileSize.Height * Zoom); + Map.Bounds.Left * TileSetRenderer.TileSize * Zoom + Offset.X, + Map.Bounds.Top * TileSetRenderer.TileSize * Zoom + Offset.Y, + Map.Bounds.Width * TileSetRenderer.TileSize * Zoom, + Map.Bounds.Height * TileSetRenderer.TileSize * Zoom); e.Graphics.DrawRectangle(SelectionPen, - (SelectionStart.X * TileSetRenderer.TileSize.Width * Zoom) + Offset.X, - (SelectionStart.Y * TileSetRenderer.TileSize.Height * Zoom) + Offset.Y, - (SelectionEnd - SelectionStart).X * TileSetRenderer.TileSize.Width * Zoom, - (SelectionEnd - SelectionStart).Y * TileSetRenderer.TileSize.Height * Zoom); + (SelectionStart.X * TileSetRenderer.TileSize * Zoom) + Offset.X, + (SelectionStart.Y * TileSetRenderer.TileSize * Zoom) + Offset.Y, + (SelectionEnd - SelectionStart).X * TileSetRenderer.TileSize * Zoom, + (SelectionEnd - SelectionStart).Y * TileSetRenderer.TileSize * Zoom); if (IsPaste) { @@ -438,10 +440,10 @@ namespace OpenRA.Editor var height = Math.Abs((SelectionStart - SelectionEnd).Y); e.Graphics.DrawRectangle(PastePen, - (loc.X * TileSetRenderer.TileSize.Width * Zoom) + Offset.X, - (loc.Y * TileSetRenderer.TileSize.Height * Zoom) + Offset.Y, - width * (TileSetRenderer.TileSize.Width * Zoom), - height * (TileSetRenderer.TileSize.Height * Zoom)); + (loc.X * TileSetRenderer.TileSize * Zoom) + Offset.X, + (loc.Y * TileSetRenderer.TileSize * Zoom) + Offset.Y, + width * (TileSetRenderer.TileSize * Zoom), + height * (TileSetRenderer.TileSize * Zoom)); } foreach (var ar in Map.Actors.Value) @@ -457,8 +459,8 @@ namespace OpenRA.Editor foreach (var ar in Map.Actors.Value) if (!ar.Key.StartsWith("Actor")) // if it has a custom name e.Graphics.DrawStringContrast(Font, ar.Key, - (int)(ar.Value.Location().X * TileSetRenderer.TileSize.Width * Zoom + Offset.X), - (int)(ar.Value.Location().Y * TileSetRenderer.TileSize.Height * Zoom + Offset.Y), + (int)(ar.Value.Location().X * TileSetRenderer.TileSize * Zoom + Offset.X), + (int)(ar.Value.Location().Y * TileSetRenderer.TileSize * Zoom + Offset.Y), Brushes.White, Brushes.Black); @@ -468,7 +470,7 @@ namespace OpenRA.Editor { if (i % 8 == 0) { - PointF point = new PointF(i * TileSetRenderer.TileSize.Width * Zoom + Offset.X, (Map.Bounds.Top - 8) * TileSetRenderer.TileSize.Height * Zoom + Offset.Y); + PointF point = new PointF(i * TileSetRenderer.TileSize * Zoom + Offset.X, (Map.Bounds.Top - 8) * TileSetRenderer.TileSize * Zoom + Offset.Y); e.Graphics.DrawString((i - Map.Bounds.Left).ToString(), MarkerFont, TextBrush, point); } } @@ -477,7 +479,7 @@ namespace OpenRA.Editor { if (i % 8 == 0) { - PointF point = new PointF((Map.Bounds.Left - 8) * TileSetRenderer.TileSize.Width * Zoom + Offset.X, i * TileSetRenderer.TileSize.Height * Zoom + Offset.Y); + PointF point = new PointF((Map.Bounds.Left - 8) * TileSetRenderer.TileSize * Zoom + Offset.X, i * TileSetRenderer.TileSize * Zoom + Offset.Y); e.Graphics.DrawString((i - Map.Bounds.Left).ToString(), MarkerFont, TextBrush, point); } } diff --git a/OpenRA.Editor/TileSetRenderer.cs b/OpenRA.Editor/TileSetRenderer.cs index ef85c96bd9..0468a71d30 100644 --- a/OpenRA.Editor/TileSetRenderer.cs +++ b/OpenRA.Editor/TileSetRenderer.cs @@ -8,6 +8,7 @@ */ #endregion +using System; using System.Collections.Generic; using System.Drawing; using System.Drawing.Imaging; @@ -21,7 +22,27 @@ namespace OpenRA.Editor { public TileSet TileSet; Dictionary> templates; - public Size TileSize; + public readonly int TileSize; + + // Extract a square tile that the editor can render + byte[] ExtractSquareTile(ISpriteFrame frame) + { + var data = new byte[TileSize * TileSize]; + + // Invalid tile size: return blank tile + if (frame.Size.Width < TileSize || frame.Size.Height < TileSize) + return data; + + var frameData = frame.Data; + var xOffset = (frame.Size.Width - TileSize) / 2; + var yOffset = (frame.Size.Height - TileSize) / 2; + + for (var y = 0; y < TileSize; y++) + for (var x = 0; x < TileSize; x++) + data[y * TileSize + x] = frameData[(yOffset + y) * frame.Size.Width + x + xOffset]; + + return data; + } List LoadTemplate(string filename, string[] exts, Dictionary sourceCache, int[] frames) { @@ -42,18 +63,18 @@ namespace OpenRA.Editor var ret = new List(); var srcFrames = source.Frames.ToArray(); foreach (var i in frames) - ret.Add(srcFrames[i].Data); + ret.Add(ExtractSquareTile(srcFrames[i])); return ret; } - return source.Frames.Select(f => f.Data).ToList(); + return source.Frames.Select(f => ExtractSquareTile(f)).ToList(); } public TileSetRenderer(TileSet tileset, Size tileSize) { this.TileSet = tileset; - this.TileSize = tileSize; + this.TileSize = Math.Min(tileSize.Width, tileSize.Height); templates = new Dictionary>(); var sourceCache = new Dictionary(); @@ -66,7 +87,7 @@ namespace OpenRA.Editor var template = TileSet.Templates[id]; var templateData = templates[id]; - var bitmap = new Bitmap(TileSize.Width * template.Size.X, TileSize.Height * template.Size.Y, + var bitmap = new Bitmap(TileSize * template.Size.X, TileSize * template.Size.Y, PixelFormat.Format8bppIndexed); bitmap.Palette = p.AsSystemPalette(); @@ -86,15 +107,15 @@ namespace OpenRA.Editor var rawImage = templateData[u + v * template.Size.X]; if (rawImage != null && rawImage.Length > 0) { - for (var i = 0; i < TileSize.Width; i++) - for (var j = 0; j < TileSize.Height; j++) - q[(v * TileSize.Width + j) * stride + u * TileSize.Width + i] = rawImage[i + TileSize.Width * j]; + for (var i = 0; i < TileSize; i++) + for (var j = 0; j < TileSize; j++) + q[(v * TileSize + j) * stride + u * TileSize + i] = rawImage[i + TileSize * j]; } else { - for (var i = 0; i < TileSize.Width; i++) - for (var j = 0; j < TileSize.Height; j++) - q[(v * TileSize.Width + j) * stride + u * TileSize.Width + i] = 0; + for (var i = 0; i < TileSize; i++) + for (var j = 0; j < TileSize; j++) + q[(v * TileSize + j) * stride + u * TileSize + i] = 0; } } } diff --git a/OpenRA.FileFormats/FieldLoader.cs b/OpenRA.FileFormats/FieldLoader.cs index 824a70630b..d81a73fc60 100755 --- a/OpenRA.FileFormats/FieldLoader.cs +++ b/OpenRA.FileFormats/FieldLoader.cs @@ -282,6 +282,12 @@ namespace OpenRA.FileFormats return ret; } + else if (fieldType == typeof(Size)) + { + var parts = value.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries); + return new Size(int.Parse(parts[0]), int.Parse(parts[1])); + } + else if (fieldType == typeof(int2)) { var parts = value.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries); diff --git a/OpenRA.FileFormats/Graphics/SpriteSource.cs b/OpenRA.FileFormats/Graphics/SpriteSource.cs index 9c7f25a672..5442c8167f 100644 --- a/OpenRA.FileFormats/Graphics/SpriteSource.cs +++ b/OpenRA.FileFormats/Graphics/SpriteSource.cs @@ -29,7 +29,7 @@ namespace OpenRA.FileFormats bool CacheWhenLoadingTileset { get; } } - public enum SpriteType { Unknown, ShpTD, ShpTS, ShpD2, TmpTD, TmpRA, R8 } + public enum SpriteType { Unknown, ShpTD, ShpTS, ShpD2, TmpTD, TmpRA, TmpTS, R8 } public static class SpriteSource { static bool IsTmpRA(Stream s) @@ -57,6 +57,29 @@ namespace OpenRA.FileFormats return a == 0 && b == 0x0D1AFFFF; } + static bool IsTmpTS(Stream s) + { + var start = s.Position; + s.Position += 8; + var sx = s.ReadUInt32(); + var sy = s.ReadUInt32(); + + // Find the first frame + var offset = s.ReadUInt32(); + + if (offset > s.Length - 52) + { + s.Position = start; + return false; + } + + s.Position = offset + 12; + var test = s.ReadUInt32(); + + s.Position = start; + return test == sx * sy / 2 + 52; + } + static bool IsShpTS(Stream s) { var start = s.Position; @@ -204,6 +227,9 @@ namespace OpenRA.FileFormats if (IsTmpTD(s)) return SpriteType.TmpTD; + if (IsTmpTS(s)) + return SpriteType.TmpTS; + if (IsShpD2(s)) return SpriteType.ShpD2; @@ -225,6 +251,8 @@ namespace OpenRA.FileFormats return new TmpRAReader(s); case SpriteType.TmpTD: return new TmpTDReader(s); + case SpriteType.TmpTS: + return new TmpTSReader(s); case SpriteType.ShpD2: return new ShpD2Reader(s); case SpriteType.Unknown: diff --git a/OpenRA.FileFormats/Graphics/TmpTSReader.cs b/OpenRA.FileFormats/Graphics/TmpTSReader.cs new file mode 100644 index 0000000000..581cdeaafd --- /dev/null +++ b/OpenRA.FileFormats/Graphics/TmpTSReader.cs @@ -0,0 +1,75 @@ +#region Copyright & License Information +/* + * Copyright 2007-2013 The OpenRA Developers (see AUTHORS) + * This file is part of OpenRA, which is free software. It is made + * available to you under the terms of the GNU General Public License + * as published by the Free Software Foundation. For more information, + * see COPYING. + */ +#endregion + +using System; +using System.Collections.Generic; +using System.Drawing; +using System.IO; +using System.Linq; + +namespace OpenRA.FileFormats +{ + public class TmpTSTile : ISpriteFrame + { + public Size Size { get; private set; } + public Size FrameSize { get { return Size; } } + public float2 Offset { get { return float2.Zero; } } + public byte[] Data { get; set; } + + public TmpTSTile(Stream s, Size size) + { + Size = size; + + // Ignore tile header for now + s.Position += 52; + + Data = new byte[size.Width * size.Height]; + + // Unpack tile data + var width = 4; + for (var i = 0; i < size.Height; i++) + { + var start = i * size.Width + (size.Width - width) / 2; + for (var j = 0; j < width; j++) + Data[start + j] = s.ReadUInt8(); + + width += (i < size.Height / 2 - 1? 1 : -1) * 4; + } + + // Ignore Z-data for now + // Ignore extra data for now + } + } + + public class TmpTSReader : ISpriteSource + { + readonly List tiles = new List(); + public IEnumerable Frames { get { return tiles.Cast(); } } + public bool CacheWhenLoadingTileset { get { return false; } } + + public TmpTSReader(Stream s) + { + var templateWidth = s.ReadUInt32(); + var templateHeight = s.ReadUInt32(); + var tileWidth = s.ReadInt32(); + var tileHeight = s.ReadInt32(); + var size = new Size(tileWidth, tileHeight); + var offsets = new uint[templateWidth * templateHeight]; + for (var i = 0; i < offsets.Length; i++) + offsets[i] = s.ReadUInt32(); + + for (var i = 0; i < offsets.Length; i++) + { + s.Position = offsets[i]; + tiles.Add(new TmpTSTile(s, size)); + } + } + } +} diff --git a/OpenRA.FileFormats/Manifest.cs b/OpenRA.FileFormats/Manifest.cs index df1f8f7428..6ac3067248 100644 --- a/OpenRA.FileFormats/Manifest.cs +++ b/OpenRA.FileFormats/Manifest.cs @@ -9,6 +9,7 @@ #endregion using System.Collections.Generic; +using System.Drawing; using System.IO; using System.Linq; @@ -28,7 +29,7 @@ namespace OpenRA.FileFormats public readonly MiniYaml LoadScreen; public readonly MiniYaml LobbyDefaults; public readonly Dictionary> Fonts; - public readonly int TileSize = 24; + public readonly Size TileSize = new Size(24, 24); public Manifest(string mod) { @@ -68,7 +69,7 @@ namespace OpenRA.FileFormats int.Parse(x.Value.NodesDict["Size"].Value))); if (yaml.ContainsKey("TileSize")) - TileSize = int.Parse(yaml["TileSize"].Value); + TileSize = FieldLoader.GetValue("TileSize", yaml["TileSize"].Value); // Allow inherited mods to import parent maps. var compat = new List(); diff --git a/OpenRA.FileFormats/OpenRA.FileFormats.csproj b/OpenRA.FileFormats/OpenRA.FileFormats.csproj index cc8a5edf80..ce1a3bbf70 100644 --- a/OpenRA.FileFormats/OpenRA.FileFormats.csproj +++ b/OpenRA.FileFormats/OpenRA.FileFormats.csproj @@ -156,6 +156,7 @@ + diff --git a/OpenRA.Game/Game.cs b/OpenRA.Game/Game.cs index f15c436cac..7b2ee2870e 100644 --- a/OpenRA.Game/Game.cs +++ b/OpenRA.Game/Game.cs @@ -27,8 +27,6 @@ namespace OpenRA { public static class Game { - public static int CellSize { get { return modData.Manifest.TileSize; } } - public static MouseButtonPreference mouseButtonPreference = new MouseButtonPreference(); public static ModData modData; diff --git a/OpenRA.Game/Graphics/WorldRenderer.cs b/OpenRA.Game/Graphics/WorldRenderer.cs index 61f4389544..6085f8d3ad 100644 --- a/OpenRA.Game/Graphics/WorldRenderer.cs +++ b/OpenRA.Game/Graphics/WorldRenderer.cs @@ -235,8 +235,8 @@ namespace OpenRA.Graphics // Conversion between world and screen coordinates public float2 ScreenPosition(WPos pos) { - var c = Game.CellSize / 1024f; - return new float2(c * pos.X, c * (pos.Y - pos.Z)); + var ts = Game.modData.Manifest.TileSize; + return new float2(ts.Width * pos.X / 1024f, ts.Height * (pos.Y - pos.Z) / 1024f); } public int2 ScreenPxPosition(WPos pos) @@ -249,8 +249,8 @@ namespace OpenRA.Graphics // For scaling vectors to pixel sizes in the voxel renderer public float[] ScreenVector(WVec vec) { - var c = Game.CellSize / 1024f; - return new float[] { c * vec.X, c * vec.Y, c * vec.Z, 1 }; + var ts = Game.modData.Manifest.TileSize; + return new float[] { ts.Width * vec.X / 1024f, ts.Height * vec.Y / 1024f, ts.Height * vec.Z / 1024f, 1 }; } public int2 ScreenPxOffset(WVec vec) @@ -262,12 +262,14 @@ namespace OpenRA.Graphics public float ScreenZPosition(WPos pos, int offset) { - return (pos.Y + pos.Z + offset) * Game.CellSize / 1024f; + var ts = Game.modData.Manifest.TileSize; + return (pos.Y + pos.Z + offset) * ts.Height / 1024f; } public WPos Position(int2 screenPx) { - return new WPos(1024 * screenPx.X / Game.CellSize, 1024 * screenPx.Y / Game.CellSize, 0); + var ts = Game.modData.Manifest.TileSize; + return new WPos(1024 * screenPx.X / ts.Width, 1024 * screenPx.Y / ts.Height, 0); } } } diff --git a/OpenRA.Game/Traits/World/ScreenMap.cs b/OpenRA.Game/Traits/World/ScreenMap.cs index 2e7c676cbf..f0d8007bf3 100755 --- a/OpenRA.Game/Traits/World/ScreenMap.cs +++ b/OpenRA.Game/Traits/World/ScreenMap.cs @@ -36,8 +36,9 @@ namespace OpenRA.Traits public ScreenMap(World world, ScreenMapInfo info) { this.info = info; - cols = world.Map.MapSize.X * Game.CellSize / info.BinSize + 1; - rows = world.Map.MapSize.Y * Game.CellSize / info.BinSize + 1; + var ts = Game.modData.Manifest.TileSize; + cols = world.Map.MapSize.X * ts.Width / info.BinSize + 1; + rows = world.Map.MapSize.Y * ts.Height / info.BinSize + 1; frozen = new Cache[]>(InitializeFrozenActors); actors = new Dictionary[rows * cols]; diff --git a/OpenRA.Mods.RA/ShroudRenderer.cs b/OpenRA.Mods.RA/ShroudRenderer.cs index de9c9190e1..bbfaabb782 100644 --- a/OpenRA.Mods.RA/ShroudRenderer.cs +++ b/OpenRA.Mods.RA/ShroudRenderer.cs @@ -95,9 +95,9 @@ namespace OpenRA.Mods.RA // Synthesize unexplored tile if it isn't defined if (!info.Index.Contains(0)) { - var size = new Size(Game.modData.Manifest.TileSize, Game.modData.Manifest.TileSize); - var data = Exts.MakeArray(size.Width * size.Height, _ => (byte)info.ShroudColor); - var s = Game.modData.SheetBuilder.Add(data, size); + var ts = Game.modData.Manifest.TileSize; + var data = Exts.MakeArray(ts.Width * ts.Height, _ => (byte)info.ShroudColor); + var s = Game.modData.SheetBuilder.Add(data, ts); unexploredTile = new Sprite(s.sheet, s.bounds, s.offset, s.channel, info.ShroudBlend); } else diff --git a/OpenRA.Mods.RA/Widgets/Logic/AssetBrowserLogic.cs b/OpenRA.Mods.RA/Widgets/Logic/AssetBrowserLogic.cs index 44f88cbe9e..573cbae7e5 100644 --- a/OpenRA.Mods.RA/Widgets/Logic/AssetBrowserLogic.cs +++ b/OpenRA.Mods.RA/Widgets/Logic/AssetBrowserLogic.cs @@ -181,7 +181,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic if (assetSource == null) return; - var files = assetSource.AllFileNames(); + var files = assetSource.AllFileNames().OrderBy(s => s); foreach (var file in files) { if (AllowedExtensions.Any(ext => file.EndsWith(ext, true, CultureInfo.InvariantCulture))) diff --git a/OpenRA.Utility/UpgradeRules.cs b/OpenRA.Utility/UpgradeRules.cs index 811f7577de..b05cd084d9 100644 --- a/OpenRA.Utility/UpgradeRules.cs +++ b/OpenRA.Utility/UpgradeRules.cs @@ -43,7 +43,8 @@ namespace OpenRA.Utility static void ConvertPxToRange(ref string input, int scaleMult, int scaleDiv) { var value = int.Parse(input); - var world = value * 1024 * scaleMult / (scaleDiv * Game.CellSize); + var ts = Game.modData.Manifest.TileSize; + var world = value * 1024 * scaleMult / (scaleDiv * ts.Height); var cells = world / 1024; var subcells = world - 1024 * cells; @@ -59,7 +60,8 @@ namespace OpenRA.Utility static void ConvertInt2ToWVec(ref string input) { var offset = FieldLoader.GetValue("(value)", input); - var world = new WVec(offset.X * 1024 / Game.CellSize, offset.Y * 1024 / Game.CellSize, 0); + var ts = Game.modData.Manifest.TileSize; + var world = new WVec(offset.X * 1024 / ts.Width, offset.Y * 1024 / ts.Height, 0); input = world.ToString(); } diff --git a/mods/d2k/mod.yaml b/mods/d2k/mod.yaml index f445a4a54d..cf13825927 100644 --- a/mods/d2k/mod.yaml +++ b/mods/d2k/mod.yaml @@ -91,7 +91,7 @@ Notifications: TileSets: mods/d2k/tilesets/arrakis.yaml -TileSize: 32 +TileSize: 32,32 Music: mods/d2k/music.yaml diff --git a/mods/ts/bits/interior.mix b/mods/ts/bits/interior.mix deleted file mode 100644 index 99bcad6ac5..0000000000 Binary files a/mods/ts/bits/interior.mix and /dev/null differ diff --git a/mods/ts/maps/blank-conquest.oramap b/mods/ts/maps/blank-conquest.oramap index 4d29917ebe..53e2bef0f1 100644 Binary files a/mods/ts/maps/blank-conquest.oramap and b/mods/ts/maps/blank-conquest.oramap differ diff --git a/mods/ts/mod.yaml b/mods/ts/mod.yaml index 251fbe2b23..2f6ad1be61 100644 --- a/mods/ts/mod.yaml +++ b/mods/ts/mod.yaml @@ -19,8 +19,6 @@ MapFolders: ~^/maps/ts Packages: -# Red Alert - interior.mix # Tiberian Sun ~scores.mix:CRC32 ~sidenc01.mix:CRC32 @@ -132,7 +130,9 @@ Notifications: mods/ts/notifications.yaml TileSets: - mods/ra/tilesets/interior.yaml + mods/ts/tilesets/interior.yaml + +TileSize: 48,24 Music: mods/ts/music.yaml diff --git a/mods/ts/tilesets/interior.yaml b/mods/ts/tilesets/interior.yaml new file mode 100644 index 0000000000..0c02a60058 --- /dev/null +++ b/mods/ts/tilesets/interior.yaml @@ -0,0 +1,19 @@ +General: + Name: Interior + Id: INTERIOR + Extensions: .tem, .shp + Palette: isotem.pal + +Terrain: + TerrainType@Clear: + Type: Clear + AcceptsSmudgeType: Crater, Scorch + Color: 0, 0, 0 + +Templates: + Template@255: + Id: 255 + Image: clear01 + Size: 1,1 + Tiles: + 0: Clear