more chrome

This commit is contained in:
Chris Forbes
2009-11-17 19:41:34 +13:00
parent 2ce0437ebc
commit 34f56e1fb8
6 changed files with 166 additions and 103 deletions

View File

@@ -7,10 +7,11 @@ using OpenRa.Game.Support;
using System.Drawing; using System.Drawing;
using IjwFramework.Types; using IjwFramework.Types;
using IjwFramework.Collections; using IjwFramework.Collections;
using System.Windows.Forms;
namespace OpenRa.Game namespace OpenRa.Game
{ {
class Chrome class Chrome : IHandleInput
{ {
readonly Renderer renderer; readonly Renderer renderer;
readonly Sheet specialBin; readonly Sheet specialBin;
@@ -20,7 +21,7 @@ namespace OpenRa.Game
readonly SpriteRenderer buildPaletteRenderer; readonly SpriteRenderer buildPaletteRenderer;
readonly Animation cantBuild; readonly Animation cantBuild;
readonly List<Pair<Rectangle, string>> buildItems = new List<Pair<Rectangle, string>>(); readonly List<Pair<Rectangle, Action<bool>>> buildItems = new List<Pair<Rectangle, Action<bool>>>();
readonly Cache<string, Animation> clockAnimations; readonly Cache<string, Animation> clockAnimations;
readonly List<Sprite> digitSprites; readonly List<Sprite> digitSprites;
readonly Dictionary<string, Sprite[]> tabSprites; readonly Dictionary<string, Sprite[]> tabSprites;
@@ -62,7 +63,7 @@ namespace OpenRa.Game
}); });
digitSprites = Util.MakeArray(10, a => a) digitSprites = Util.MakeArray(10, a => a)
.Select(n => new Sprite(specialBin, new Rectangle(32 + 14 * n, 0, 14, 17), TextureChannel.Alpha)).ToList(); .Select(n => new Sprite(specialBin, new Rectangle(32 + 13 * n, 0, 13, 17), TextureChannel.Alpha)).ToList();
shimSprites = new [] shimSprites = new []
{ {
@@ -154,10 +155,15 @@ namespace OpenRa.Game
buildPaletteRenderer.DrawSprite(cantBuild.Image, Game.viewport.Location + new float2(rect.Location), 0); buildPaletteRenderer.DrawSprite(cantBuild.Image, Game.viewport.Location + new float2(rect.Location), 0);
if (currentItem != null && currentItem.Item == item) if (currentItem != null && currentItem.Item == item)
buildPaletteRenderer.DrawSprite(clockAnimations[queueName].Image, {
clockAnimations[queueName].Tick();
buildPaletteRenderer.DrawSprite(clockAnimations[queueName].Image,
Game.viewport.Location + new float2(rect.Location), 0); Game.viewport.Location + new float2(rect.Location), 0);
}
buildItems.Add(Pair.New(rect, item)); var closureItem = item;
buildItems.Add(Pair.New(rect,
(Action<bool>)(isLmb => HandleBuildPalette(closureItem, isLmb))));
if (++x == 3) { x = 0; y++; } if (++x == 3) { x = 0; y++; }
} }
@@ -169,5 +175,70 @@ namespace OpenRa.Game
chromeRenderer.DrawSprite(shimSprites[1], new float2(Game.viewport.Width - 192 - 9, 40 - 1 + 48 + 48 * y), 0); chromeRenderer.DrawSprite(shimSprites[1], new float2(Game.viewport.Width - 192 - 9, 40 - 1 + 48 + 48 * y), 0);
chromeRenderer.Flush(); chromeRenderer.Flush();
} }
void HandleBuildPalette(string item, bool isLmb)
{
var player = Game.LocalPlayer;
var group = Rules.UnitCategory[item];
var producing = player.Producing(group);
if (isLmb)
{
if (producing == null)
{
Game.controller.AddOrder(Order.StartProduction(player, item));
Game.PlaySound("abldgin1.aud", false);
}
else if (producing.Item == item)
{
if (producing.Done)
{
if (group == "Building" || group == "Defense")
Game.controller.orderGenerator = new PlaceBuilding(player, item);
}
else
Game.controller.AddOrder(Order.PauseProduction(player, item, false));
}
else
{
Game.PlaySound("progres1.aud", false);
}
}
else
{
if (producing == null) return;
if (item != producing.Item) return;
if (producing.Paused || producing.Done)
{
Game.PlaySound("cancld1.aud", false);
Game.controller.AddOrder(Order.CancelProduction(player, item));
}
else
{
Game.PlaySound("onhold1.aud", false);
Game.controller.AddOrder(Order.PauseProduction(player, item, true));
}
}
}
public bool HandleInput(MouseInput mi)
{
var action = buildItems.Where(a => a.First.Contains(mi.Location.ToPoint()))
.Select( a => a.Second ).FirstOrDefault();
if (action == null)
return false;
if (mi.Event == MouseInputEvent.Down)
action(mi.Button == MouseButtons.Left);
return true;
}
public bool HitTest(int2 mousePos)
{
return buildItems.Any(a => a.First.Contains(mousePos.ToPoint()));
}
} }
} }

View File

@@ -6,10 +6,11 @@ using System.Windows.Forms;
using IjwFramework.Types; using IjwFramework.Types;
using System.Drawing; using System.Drawing;
using OpenRa.Game.Traits; using OpenRa.Game.Traits;
using OpenRa.Game.Graphics;
namespace OpenRa.Game namespace OpenRa.Game
{ {
class Controller class Controller : IHandleInput
{ {
public IOrderGenerator orderGenerator; public IOrderGenerator orderGenerator;
@@ -45,7 +46,7 @@ namespace OpenRa.Game
} }
float2 dragStart, dragEnd; float2 dragStart, dragEnd;
public void HandleMouseInput(MouseInput mi) public bool HandleInput(MouseInput mi)
{ {
var xy = Game.viewport.ViewToWorld(mi); var xy = Game.viewport.ViewToWorld(mi);
@@ -91,6 +92,8 @@ namespace OpenRa.Game
if (mi.Button == MouseButtons.Right && mi.Event == MouseInputEvent.Down) if (mi.Button == MouseButtons.Right && mi.Event == MouseInputEvent.Down)
ApplyOrders(xy, false); ApplyOrders(xy, false);
return true;
} }
public Pair<float2, float2>? SelectionBox public Pair<float2, float2>? SelectionBox

View File

@@ -4,6 +4,11 @@ using System.Linq;
namespace OpenRa.Game.Graphics namespace OpenRa.Game.Graphics
{ {
interface IHandleInput
{
bool HandleInput(MouseInput mi);
}
class Viewport class Viewport
{ {
readonly float2 screenSize; readonly float2 screenSize;
@@ -20,29 +25,22 @@ namespace OpenRa.Game.Graphics
int2 mousePos; int2 mousePos;
float cursorFrame = 0f; float cursorFrame = 0f;
readonly float2 scrollLowBounds, scrollHighBounds;
public void Scroll(float2 delta) public void Scroll(float2 delta)
{ {
scrollPosition = scrollPosition + delta;// (scrollPosition + delta).Constrain(scrollLowBounds, scrollHighBounds); scrollPosition = scrollPosition + delta;
} }
public IEnumerable<IHandleInput> regions { get { return new IHandleInput[] { Game.chrome, Game.controller }; } }
public Viewport(float2 screenSize, int2 mapStart, int2 mapEnd, Renderer renderer) public Viewport(float2 screenSize, int2 mapStart, int2 mapEnd, Renderer renderer)
{ {
this.screenSize = screenSize; this.screenSize = screenSize;
// this.scrollLowBounds = Game.CellSize * mapStart;
// this.scrollHighBounds = float2.Max( scrollLowBounds, Game.CellSize * mapEnd - ( screenSize /*- new float2( 128, 0 )*/ ) );
this.renderer = renderer; this.renderer = renderer;
cursorRenderer = new SpriteRenderer(renderer, true); cursorRenderer = new SpriteRenderer(renderer, true);
this.scrollPosition = Game.CellSize* mapStart; this.scrollPosition = Game.CellSize* mapStart;
// this.scrollPosition = scrollLowBounds;
} }
List<Region> regions = new List<Region>();
public void AddRegion(Region r) { regions.Add(r); }
public void DrawRegions() public void DrawRegions()
{ {
float2 r1 = new float2(2, -2) / screenSize; float2 r1 = new float2(2, -2) / screenSize;
@@ -50,12 +48,10 @@ namespace OpenRa.Game.Graphics
renderer.BeginFrame(r1, r2, scrollPosition); renderer.BeginFrame(r1, r2, scrollPosition);
foreach (Region region in regions) Game.worldRenderer.Draw();
region.Draw(renderer);
Game.chrome.Draw(); Game.chrome.Draw();
var c = (Game.worldRenderer.region.Contains(mousePos)) ? cursor : Cursor.Default; var c = Game.chrome.HitTest(mousePos) ? Cursor.Default : cursor;
cursorRenderer.DrawSprite(c.GetSprite((int)cursorFrame), mousePos + Location - c.GetHotspot(), 0); cursorRenderer.DrawSprite(c.GetSprite((int)cursorFrame), mousePos + Location - c.GetHotspot(), 0);
cursorRenderer.Flush(); cursorRenderer.Flush();
@@ -67,23 +63,19 @@ namespace OpenRa.Game.Graphics
cursorFrame += 0.5f; cursorFrame += 0.5f;
} }
Region dragRegion = null; IHandleInput dragRegion = null;
public void DispatchMouseInput(MouseInput mi) public void DispatchMouseInput(MouseInput mi)
{ {
if (mi.Event == MouseInputEvent.Move) if (mi.Event == MouseInputEvent.Move)
mousePos = mi.Location; mousePos = mi.Location;
if (dragRegion != null) { if (dragRegion != null) {
dragRegion.HandleMouseInput( mi ); dragRegion.HandleInput( mi );
if (mi.Event == MouseInputEvent.Up) dragRegion = null; if (mi.Event == MouseInputEvent.Up) dragRegion = null;
return; return;
} }
if (mi.Event == MouseInputEvent.Move) dragRegion = regions.FirstOrDefault(r => r.HandleInput(mi));
foreach (var reg in regions.Where(r => r.AlwaysWantMovement))
reg.HandleMouseInput(mi);
dragRegion = regions.FirstOrDefault(r => r.Contains(mi.Location) && r.HandleMouseInput(mi));
if (mi.Event != MouseInputEvent.Down) if (mi.Event != MouseInputEvent.Down)
dragRegion = null; dragRegion = null;
} }

View File

@@ -13,7 +13,7 @@ namespace OpenRa.Game.Graphics
public readonly TerrainRenderer terrainRenderer; public readonly TerrainRenderer terrainRenderer;
public readonly SpriteRenderer spriteRenderer; public readonly SpriteRenderer spriteRenderer;
public readonly LineRenderer lineRenderer; public readonly LineRenderer lineRenderer;
public readonly Region region; //public readonly Region region;
public readonly UiOverlay uiOverlay; public readonly UiOverlay uiOverlay;
readonly Renderer renderer; readonly Renderer renderer;
@@ -24,9 +24,9 @@ namespace OpenRa.Game.Graphics
terrainRenderer = new TerrainRenderer(renderer, Game.map); terrainRenderer = new TerrainRenderer(renderer, Game.map);
// TODO: this is layout policy. it belongs at a higher level than this. // TODO: this is layout policy. it belongs at a higher level than this.
region = Region.Create(Game.viewport, DockStyle.Left, //region = Region.Create(Game.viewport, DockStyle.Left,
Game.viewport.Width, Draw, Game.controller.HandleMouseInput); // Game.viewport.Width, Draw, Game.controller.HandleInput);
Game.viewport.AddRegion(region); //Game.viewport.AddRegion(Game.controller);
this.renderer = renderer; this.renderer = renderer;
spriteRenderer = new SpriteRenderer(renderer, true); spriteRenderer = new SpriteRenderer(renderer, true);
@@ -54,8 +54,9 @@ namespace OpenRa.Game.Graphics
{ {
terrainRenderer.Draw(Game.viewport); terrainRenderer.Draw(Game.viewport);
var rect = new RectangleF((region.Position + Game.viewport.Location).ToPointF(), var rect = new RectangleF(
region.Size.ToSizeF()); Game.viewport.Location.ToPointF(),
new SizeF( Game.viewport.Width, Game.viewport.Height ));
foreach (Actor a in Game.world.Actors.OrderBy(u => u.CenterLocation.Y)) foreach (Actor a in Game.world.Actors.OrderBy(u => u.CenterLocation.Y))
DrawSpriteList(rect, a.Render()); DrawSpriteList(rect, a.Render());

View File

@@ -118,7 +118,6 @@
<Compile Include="PathFinder.cs" /> <Compile Include="PathFinder.cs" />
<Compile Include="Graphics\Sequence.cs" /> <Compile Include="Graphics\Sequence.cs" />
<Compile Include="Order.cs" /> <Compile Include="Order.cs" />
<Compile Include="Graphics\Region.cs" />
<Compile Include="Graphics\SequenceProvider.cs" /> <Compile Include="Graphics\SequenceProvider.cs" />
<Compile Include="Graphics\SheetBuilder.cs" /> <Compile Include="Graphics\SheetBuilder.cs" />
<Compile Include="Graphics\HardwarePalette.cs" /> <Compile Include="Graphics\HardwarePalette.cs" />

View File

@@ -8,8 +8,6 @@ using System.Linq;
namespace OpenRa.Game namespace OpenRa.Game
{ {
using GRegion = OpenRa.Game.Graphics.Region;
class Sidebar class Sidebar
{ {
Player player; Player player;
@@ -19,7 +17,6 @@ namespace OpenRa.Game
Sprite blank; Sprite blank;
Animation ready; Animation ready;
Animation cantBuild; Animation cantBuild;
readonly GRegion region;
public float Width { get { return spriteWidth * 2; } } public float Width { get { return spriteWidth * 2; } }
Dictionary<string, Sprite> sprites = new Dictionary<string,Sprite>(); Dictionary<string, Sprite> sprites = new Dictionary<string,Sprite>();
@@ -33,30 +30,30 @@ namespace OpenRa.Game
public Sidebar( Renderer renderer, Player player ) public Sidebar( Renderer renderer, Player player )
{ {
this.player = player; //this.player = player;
this.renderer = renderer; //this.renderer = renderer;
region = GRegion.Create(Game.viewport, DockStyle.Right, /*128*/0, Paint, MouseHandler); //region = GRegion.Create(Game.viewport, DockStyle.Right, /*128*/0, Paint, MouseHandler);
region.UseScissor = false; //region.UseScissor = false;
region.AlwaysWantMovement = true; //region.AlwaysWantMovement = true;
Game.viewport.AddRegion( region ); //Game.viewport.AddRegion( region );
spriteRenderer = new SpriteRenderer(renderer, false); //spriteRenderer = new SpriteRenderer(renderer, false);
clockRenderer = new SpriteRenderer(renderer, true); //clockRenderer = new SpriteRenderer(renderer, true);
for( int i = 0 ; i < groups.Length ; i++ ) //for( int i = 0 ; i < groups.Length ; i++ )
LoadSprites( groups[ i ] ); // LoadSprites( groups[ i ] );
foreach (string group in groups) //foreach (string group in groups)
{ //{
clockAnimations.Add( group, new Animation( "clock" ) ); // clockAnimations.Add( group, new Animation( "clock" ) );
clockAnimations[ group ].PlayFetchIndex( "idle", ClockAnimFrame( group ) ); // clockAnimations[ group ].PlayFetchIndex( "idle", ClockAnimFrame( group ) );
} //}
blank = SheetBuilder.Add(new Size((int)spriteWidth, (int)spriteHeight), 16); //blank = SheetBuilder.Add(new Size((int)spriteWidth, (int)spriteHeight), 16);
ready = new Animation("pips"); //ready = new Animation("pips");
ready.PlayRepeating("ready"); //ready.PlayRepeating("ready");
cantBuild = new Animation("clock"); //cantBuild = new Animation("clock");
cantBuild.PlayFetchIndex("idle", () => 0); //cantBuild.PlayFetchIndex("idle", () => 0);
} }
const int NumClockFrames = 54; const int NumClockFrames = 54;
@@ -130,59 +127,59 @@ namespace OpenRa.Game
void Paint() void Paint()
{ {
PopulateItemList(); //PopulateItemList();
foreach( var i in items ) /* draw the buttons */ ////foreach( var i in items ) /* draw the buttons */
i.Paint(spriteRenderer, region.Location); //// i.Paint(spriteRenderer, region.Location);
spriteRenderer.Flush(); //spriteRenderer.Flush();
foreach( var i in items ) /* draw the status overlays */ //foreach( var i in items ) /* draw the status overlays */
{ //{
var group = Rules.UnitCategory[ i.Tag ]; // var group = Rules.UnitCategory[ i.Tag ];
var producing = player.Producing( group ); // var producing = player.Producing( group );
if( producing != null && producing.Item == i.Tag ) // if( producing != null && producing.Item == i.Tag )
{ // {
clockAnimations[ group ].Tick(); // clockAnimations[ group ].Tick();
clockRenderer.DrawSprite( clockAnimations[ group ].Image, region.Location.ToFloat2() + i.location, 0 ); // clockRenderer.DrawSprite( clockAnimations[ group ].Image, region.Location.ToFloat2() + i.location, 0 );
if (producing.Done) // if (producing.Done)
{ // {
ready.Play("ready"); // ready.Play("ready");
clockRenderer.DrawSprite(ready.Image, region.Location.ToFloat2() + i.location + new float2((64 - ready.Image.size.X) / 2, 2), 0); // clockRenderer.DrawSprite(ready.Image, region.Location.ToFloat2() + i.location + new float2((64 - ready.Image.size.X) / 2, 2), 0);
} // }
else if (producing.Paused) // else if (producing.Paused)
{ // {
ready.Play("hold"); // ready.Play("hold");
clockRenderer.DrawSprite(ready.Image, region.Location.ToFloat2() + i.location + new float2((64 - ready.Image.size.X) / 2, 2), 0); // clockRenderer.DrawSprite(ready.Image, region.Location.ToFloat2() + i.location + new float2((64 - ready.Image.size.X) / 2, 2), 0);
} // }
} // }
else if (producing != null) // else if (producing != null)
clockRenderer.DrawSprite(cantBuild.Image, region.Location.ToFloat2() + i.location, 0); // clockRenderer.DrawSprite(cantBuild.Image, region.Location.ToFloat2() + i.location, 0);
} //}
Fill(region.Size.Y + region.Location.Y, new float2(region.Location.X, buildPos + region.Location.Y)); //Fill(region.Size.Y + region.Location.Y, new float2(region.Location.X, buildPos + region.Location.Y));
Fill(region.Size.Y + region.Location.Y, new float2(region.Location.X + spriteWidth, unitPos + region.Location.Y)); //Fill(region.Size.Y + region.Location.Y, new float2(region.Location.X + spriteWidth, unitPos + region.Location.Y));
spriteRenderer.Flush(); //spriteRenderer.Flush();
clockRenderer.Flush(); //clockRenderer.Flush();
if (mouseOverItem != null) //if (mouseOverItem != null)
{ //{
/* draw the sidebar help for this item */ // /* draw the sidebar help for this item */
/* todo: draw a solid background of the appropriate color */ // /* todo: draw a solid background of the appropriate color */
var ui = Rules.UnitInfo[mouseOverItem.Tag]; // var ui = Rules.UnitInfo[mouseOverItem.Tag];
var text = string.Format(ui.Cost > 0 ? "{0} ($ {1})" : "{0}", /* abilities! */ // var text = string.Format(ui.Cost > 0 ? "{0} ($ {1})" : "{0}", /* abilities! */
ui.Description, ui.Cost); // ui.Description, ui.Cost);
var size = renderer.MeasureText(text); // var size = renderer.MeasureText(text);
var pos = region.Position + mouseOverItem.location.ToInt2() -new int2(size.X+ 10, 0); // var pos = region.Position + mouseOverItem.location.ToInt2() -new int2(size.X+ 10, 0);
renderer.DrawText( text, pos + new int2(0,-1), Color.Black ); // renderer.DrawText( text, pos + new int2(0,-1), Color.Black );
renderer.DrawText(text, pos + new int2(0, 1), Color.Black); // renderer.DrawText(text, pos + new int2(0, 1), Color.Black);
renderer.DrawText(text, pos + new int2(1, 0), Color.Black); // renderer.DrawText(text, pos + new int2(1, 0), Color.Black);
renderer.DrawText(text, pos + new int2(-1, 0), Color.Black); // renderer.DrawText(text, pos + new int2(-1, 0), Color.Black);
renderer.DrawText(text, pos , Color.White); // renderer.DrawText(text, pos , Color.White);
} //}
} }
public SidebarItem GetItem(float2 point) public SidebarItem GetItem(float2 point)