Refactoring to remove static Rules & SequenceProvider
This commit is contained in:
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -29,7 +29,7 @@ namespace OpenRA.Editor
|
|||||||
|
|
||||||
currentMod = args.FirstOrDefault() ?? "ra";
|
currentMod = args.FirstOrDefault() ?? "ra";
|
||||||
|
|
||||||
toolStripComboBox1.Items.AddRange(Mod.AllMods.Keys.ToArray());
|
toolStripComboBox1.Items.AddRange(ModInformation.AllMods.Keys.ToArray());
|
||||||
|
|
||||||
toolStripComboBox1.SelectedIndexChanged += (_, e) =>
|
toolStripComboBox1.SelectedIndexChanged += (_, e) =>
|
||||||
{
|
{
|
||||||
@@ -48,7 +48,7 @@ namespace OpenRA.Editor
|
|||||||
|
|
||||||
Game.modData = new ModData(currentMod);
|
Game.modData = new ModData(currentMod);
|
||||||
GlobalFileSystem.LoadFromManifest(Game.modData.Manifest);
|
GlobalFileSystem.LoadFromManifest(Game.modData.Manifest);
|
||||||
Rules.LoadRules(Game.modData.Manifest, new Map());
|
Program.Rules = Game.modData.RulesetCache.LoadDefaultRules();
|
||||||
|
|
||||||
var mod = Game.modData.Manifest.Mod;
|
var mod = Game.modData.Manifest.Mod;
|
||||||
Text = "{0} Mod Version: {1} - OpenRA Editor".F(mod.Title, mod.Version);
|
Text = "{0} Mod Version: {1} - OpenRA Editor".F(mod.Title, mod.Version);
|
||||||
@@ -69,7 +69,8 @@ namespace OpenRA.Editor
|
|||||||
void OnMapChanged()
|
void OnMapChanged()
|
||||||
{
|
{
|
||||||
MakeDirty();
|
MakeDirty();
|
||||||
miniMapBox.Image = Minimap.AddStaticResources(surface1.Map, Minimap.TerrainBitmap(surface1.Map, true));
|
var tileSet = Program.Rules.TileSets[surface1.Map.Tileset];
|
||||||
|
miniMapBox.Image = Minimap.AddStaticResources(tileSet, surface1.Map, Minimap.TerrainBitmap(tileSet, surface1.Map, true));
|
||||||
cashToolStripStatusLabel.Text = CalculateTotalResource().ToString();
|
cashToolStripStatusLabel.Text = CalculateTotalResource().ToString();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -84,7 +85,7 @@ namespace OpenRA.Editor
|
|||||||
var objSaved = kv.Value.Save();
|
var objSaved = kv.Value.Save();
|
||||||
|
|
||||||
// TODO: make this work properly
|
// TODO: make this work properly
|
||||||
foreach (var init in Rules.Info[kv.Value.Type].GetInitKeys())
|
foreach (var init in Program.Rules.Actors[kv.Value.Type].GetInitKeys())
|
||||||
apd.AddRow(init.First,
|
apd.AddRow(init.First,
|
||||||
apd.MakeEditorControl(init.Second,
|
apd.MakeEditorControl(init.Second,
|
||||||
() => objSaved.NodesDict.ContainsKey(init.First) ? objSaved.NodesDict[init.First].Value : null,
|
() => objSaved.NodesDict.ContainsKey(init.First) ? objSaved.NodesDict[init.First].Value : null,
|
||||||
@@ -120,7 +121,7 @@ namespace OpenRA.Editor
|
|||||||
if (map.Players.Count == 0)
|
if (map.Players.Count == 0)
|
||||||
map.MakeDefaultPlayers();
|
map.MakeDefaultPlayers();
|
||||||
|
|
||||||
PrepareMapResources(Game.modData.Manifest, map);
|
PrepareMapResources(Game.modData, map);
|
||||||
|
|
||||||
// Calculate total net worth of resources in cash
|
// Calculate total net worth of resources in cash
|
||||||
cashToolStripStatusLabel.Text = CalculateTotalResource().ToString();
|
cashToolStripStatusLabel.Text = CalculateTotalResource().ToString();
|
||||||
@@ -135,17 +136,18 @@ namespace OpenRA.Editor
|
|||||||
resourcePalette.Controls.Clear();
|
resourcePalette.Controls.Clear();
|
||||||
|
|
||||||
loadedMapName = null;
|
loadedMapName = null;
|
||||||
PrepareMapResources(Game.modData.Manifest, map);
|
PrepareMapResources(Game.modData, map);
|
||||||
|
|
||||||
MakeDirty();
|
MakeDirty();
|
||||||
}
|
}
|
||||||
|
|
||||||
// this code is insanely stupid, and mostly my fault -- chrisf
|
// this code is insanely stupid, and mostly my fault -- chrisf
|
||||||
void PrepareMapResources(Manifest manifest, Map map)
|
void PrepareMapResources(ModData modData, Map map)
|
||||||
{
|
{
|
||||||
Rules.LoadRules(manifest, map);
|
Program.Rules = map.Rules;
|
||||||
tileset = Rules.TileSets[map.Tileset];
|
|
||||||
tilesetRenderer = new TileSetRenderer(tileset, manifest.TileSize);
|
tileset = Program.Rules.TileSets[map.Tileset];
|
||||||
|
tilesetRenderer = new TileSetRenderer(tileset, modData.Manifest.TileSize);
|
||||||
var shadowIndex = new int[] { 3, 4 };
|
var shadowIndex = new int[] { 3, 4 };
|
||||||
var palette = new Palette(GlobalFileSystem.Open(tileset.Palette), shadowIndex);
|
var palette = new Palette(GlobalFileSystem.Open(tileset.Palette), shadowIndex);
|
||||||
|
|
||||||
@@ -208,11 +210,11 @@ namespace OpenRA.Editor
|
|||||||
|
|
||||||
var actorTemplates = new List<ActorTemplate>();
|
var actorTemplates = new List<ActorTemplate>();
|
||||||
|
|
||||||
foreach (var a in Rules.Info.Keys)
|
foreach (var a in Program.Rules.Actors.Keys)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var info = Rules.Info[a];
|
var info = Program.Rules.Actors[a];
|
||||||
if (!info.Traits.Contains<RenderSimpleInfo>()) continue;
|
if (!info.Traits.Contains<RenderSimpleInfo>()) continue;
|
||||||
|
|
||||||
var etf = info.Traits.GetOrDefault<EditorTilesetFilterInfo>();
|
var etf = info.Traits.GetOrDefault<EditorTilesetFilterInfo>();
|
||||||
@@ -253,7 +255,7 @@ namespace OpenRA.Editor
|
|||||||
|
|
||||||
var resourceTemplates = new List<ResourceTemplate>();
|
var resourceTemplates = new List<ResourceTemplate>();
|
||||||
|
|
||||||
foreach (var a in Rules.Info["world"].Traits.WithInterface<ResourceTypeInfo>())
|
foreach (var a in Program.Rules.Actors["world"].Traits.WithInterface<ResourceTypeInfo>())
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -286,7 +288,7 @@ namespace OpenRA.Editor
|
|||||||
p.ResumeLayout();
|
p.ResumeLayout();
|
||||||
}
|
}
|
||||||
|
|
||||||
miniMapBox.Image = Minimap.AddStaticResources(surface1.Map, Minimap.TerrainBitmap(surface1.Map, true));
|
miniMapBox.Image = Minimap.AddStaticResources(tileset, surface1.Map, Minimap.TerrainBitmap(tileset, surface1.Map, true));
|
||||||
|
|
||||||
propertiesToolStripMenuItem.Enabled = true;
|
propertiesToolStripMenuItem.Enabled = true;
|
||||||
toolStripMenuItemProperties.Enabled = true;
|
toolStripMenuItemProperties.Enabled = true;
|
||||||
@@ -388,12 +390,12 @@ namespace OpenRA.Editor
|
|||||||
using (var nmd = new NewMapDialog())
|
using (var nmd = new NewMapDialog())
|
||||||
{
|
{
|
||||||
nmd.TheaterBox.Items.Clear();
|
nmd.TheaterBox.Items.Clear();
|
||||||
nmd.TheaterBox.Items.AddRange(Rules.TileSets.Select(a => a.Value.Id).ToArray());
|
nmd.TheaterBox.Items.AddRange(Program.Rules.TileSets.Select(a => a.Value.Id).ToArray());
|
||||||
nmd.TheaterBox.SelectedIndex = 0;
|
nmd.TheaterBox.SelectedIndex = 0;
|
||||||
|
|
||||||
if (DialogResult.OK == nmd.ShowDialog())
|
if (DialogResult.OK == nmd.ShowDialog())
|
||||||
{
|
{
|
||||||
var tileset = OpenRA.Rules.TileSets[nmd.TheaterBox.SelectedItem as string];
|
var tileset = Program.Rules.TileSets[nmd.TheaterBox.SelectedItem as string];
|
||||||
var map = Map.FromTileset(tileset);
|
var map = Map.FromTileset(tileset);
|
||||||
|
|
||||||
map.Resize((int)nmd.MapWidth.Value, (int)nmd.MapHeight.Value);
|
map.Resize((int)nmd.MapWidth.Value, (int)nmd.MapHeight.Value);
|
||||||
@@ -402,7 +404,7 @@ namespace OpenRA.Editor
|
|||||||
|
|
||||||
map.Players.Clear();
|
map.Players.Clear();
|
||||||
map.MakeDefaultPlayers();
|
map.MakeDefaultPlayers();
|
||||||
map.FixOpenAreas();
|
map.FixOpenAreas(Program.Rules);
|
||||||
|
|
||||||
NewMap(map);
|
NewMap(map);
|
||||||
}
|
}
|
||||||
@@ -485,7 +487,7 @@ namespace OpenRA.Editor
|
|||||||
void FixOpenAreas(object sender, EventArgs e)
|
void FixOpenAreas(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
dirty = true;
|
dirty = true;
|
||||||
surface1.Map.FixOpenAreas();
|
surface1.Map.FixOpenAreas(Program.Rules);
|
||||||
surface1.Chunks.Clear();
|
surface1.Chunks.Clear();
|
||||||
surface1.Invalidate();
|
surface1.Invalidate();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -75,7 +75,8 @@ namespace OpenRA.Editor
|
|||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
MiniMapBox.Image = Minimap.AddStaticResources(map, Minimap.TerrainBitmap(map, true));
|
var tileset = Program.Rules.TileSets[map.Tileset];
|
||||||
|
MiniMapBox.Image = Minimap.AddStaticResources(tileset, map, Minimap.TerrainBitmap(tileset, map, true));
|
||||||
}
|
}
|
||||||
catch (Exception ed)
|
catch (Exception ed)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -19,6 +19,8 @@ namespace OpenRA.Editor
|
|||||||
{
|
{
|
||||||
static class Program
|
static class Program
|
||||||
{
|
{
|
||||||
|
public static MapRuleset Rules;
|
||||||
|
|
||||||
[STAThread]
|
[STAThread]
|
||||||
static void Main(string[] args)
|
static void Main(string[] args)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -379,7 +379,7 @@ namespace OpenRA.Editor
|
|||||||
ColorPalette GetPaletteForPlayerInner(string name)
|
ColorPalette GetPaletteForPlayerInner(string name)
|
||||||
{
|
{
|
||||||
var pr = Map.Players[name];
|
var pr = Map.Players[name];
|
||||||
var pcpi = Rules.Info["player"].Traits.Get<PlayerColorPaletteInfo>();
|
var pcpi = Program.Rules.Actors["player"].Traits.Get<PlayerColorPaletteInfo>();
|
||||||
var remap = new PlayerColorRemap(pcpi.RemapIndex, pr.Color, pcpi.Ramp);
|
var remap = new PlayerColorRemap(pcpi.RemapIndex, pr.Color, pcpi.Ramp);
|
||||||
return new Palette(PlayerPalette, remap).AsSystemPalette();
|
return new Palette(PlayerPalette, remap).AsSystemPalette();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -69,10 +69,10 @@ namespace OpenRA
|
|||||||
|
|
||||||
if (name != null)
|
if (name != null)
|
||||||
{
|
{
|
||||||
if (!Rules.Info.ContainsKey(name.ToLowerInvariant()))
|
if (!world.Map.Rules.Actors.ContainsKey(name.ToLowerInvariant()))
|
||||||
throw new NotImplementedException("No rules definition for unit {0}".F(name.ToLowerInvariant()));
|
throw new NotImplementedException("No rules definition for unit {0}".F(name.ToLowerInvariant()));
|
||||||
|
|
||||||
Info = Rules.Info[name.ToLowerInvariant()];
|
Info = world.Map.Rules.Actors[name.ToLowerInvariant()];
|
||||||
foreach (var trait in Info.TraitsInConstructOrder())
|
foreach (var trait in Info.TraitsInConstructOrder())
|
||||||
AddTrait(trait.Create(init));
|
AddTrait(trait.Create(init));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -117,6 +117,7 @@ namespace OpenRA
|
|||||||
}, parent, id);
|
}, parent, id);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: Delayed actions shouldn't be static or at least should be cleared when the map/world is changed
|
||||||
static ActionQueue delayedActions = new ActionQueue();
|
static ActionQueue delayedActions = new ActionQueue();
|
||||||
public static void RunAfterTick(Action a) { delayedActions.Add(a); }
|
public static void RunAfterTick(Action a) { delayedActions.Add(a); }
|
||||||
public static void RunAfterDelay(int delay, Action a) { delayedActions.Add(a, delay); }
|
public static void RunAfterDelay(int delay, Action a) { delayedActions.Add(a, delay); }
|
||||||
@@ -151,8 +152,11 @@ namespace OpenRA
|
|||||||
using (new PerfSample("render_widgets"))
|
using (new PerfSample("render_widgets"))
|
||||||
{
|
{
|
||||||
Ui.Draw();
|
Ui.Draw();
|
||||||
|
if (modData != null && modData.CursorProvider != null)
|
||||||
|
{
|
||||||
var cursorName = Ui.Root.GetCursorOuter(Viewport.LastMousePos) ?? "default";
|
var cursorName = Ui.Root.GetCursorOuter(Viewport.LastMousePos) ?? "default";
|
||||||
CursorProvider.DrawCursor(Renderer, cursorName, Viewport.LastMousePos, (int)cursorFrame);
|
modData.CursorProvider.DrawCursor(Renderer, cursorName, Viewport.LastMousePos, (int)cursorFrame);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
using (new PerfSample("render_flip"))
|
using (new PerfSample("render_flip"))
|
||||||
@@ -248,6 +252,7 @@ namespace OpenRA
|
|||||||
BeforeGameStart();
|
BeforeGameStart();
|
||||||
|
|
||||||
Map map;
|
Map map;
|
||||||
|
|
||||||
using (new PerfTimer("PrepareMap"))
|
using (new PerfTimer("PrepareMap"))
|
||||||
map = modData.PrepareMap(mapUID);
|
map = modData.PrepareMap(mapUID);
|
||||||
using (new PerfTimer("NewWorld"))
|
using (new PerfTimer("NewWorld"))
|
||||||
@@ -354,7 +359,7 @@ namespace OpenRA
|
|||||||
}
|
}
|
||||||
|
|
||||||
Console.WriteLine("Available mods:");
|
Console.WriteLine("Available mods:");
|
||||||
foreach (var mod in Mod.AllMods)
|
foreach (var mod in ModInformation.AllMods)
|
||||||
Console.WriteLine("\t{0}: {1} ({2})", mod.Key, mod.Value.Title, mod.Value.Version);
|
Console.WriteLine("\t{0}: {1} ({2})", mod.Key, mod.Value.Title, mod.Value.Version);
|
||||||
|
|
||||||
InitializeWithMod(Settings.Game.Mod, args.GetValue("Launch.Replay", null));
|
InitializeWithMod(Settings.Game.Mod, args.GetValue("Launch.Replay", null));
|
||||||
@@ -379,7 +384,7 @@ namespace OpenRA
|
|||||||
orderManager.Dispose();
|
orderManager.Dispose();
|
||||||
|
|
||||||
// Fall back to default if the mod doesn't exist
|
// Fall back to default if the mod doesn't exist
|
||||||
if (!Mod.AllMods.ContainsKey(mod))
|
if (!ModInformation.AllMods.ContainsKey(mod))
|
||||||
mod = new GameSettings().Mod;
|
mod = new GameSettings().Mod;
|
||||||
|
|
||||||
Console.WriteLine("Loading mod: {0}", mod);
|
Console.WriteLine("Loading mod: {0}", mod);
|
||||||
|
|||||||
@@ -17,34 +17,10 @@ using OpenRA.Support;
|
|||||||
|
|
||||||
namespace OpenRA
|
namespace OpenRA
|
||||||
{
|
{
|
||||||
public static class Rules
|
public class RulesetCache
|
||||||
{
|
|
||||||
public static Dictionary<string, ActorInfo> Info { get { return Game.modData.Rules.Actors; } }
|
|
||||||
public static Dictionary<string, WeaponInfo> Weapons { get { return Game.modData.Rules.Weapons; } }
|
|
||||||
public static Dictionary<string, SoundInfo> Voices { get { return Game.modData.Rules.Voices; } }
|
|
||||||
public static Dictionary<string, SoundInfo> Notifications { get { return Game.modData.Rules.Notifications; } }
|
|
||||||
public static Dictionary<string, MusicInfo> Music { get { return Game.modData.Rules.Music; } }
|
|
||||||
public static Dictionary<string, string> Movies { get { return Game.modData.Rules.Movies; } }
|
|
||||||
public static Dictionary<string, TileSet> TileSets { get { return Game.modData.Rules.TileSets; } }
|
|
||||||
|
|
||||||
public static void LoadRules(Manifest m, Map map)
|
|
||||||
{
|
|
||||||
// HACK: Fallback for code that hasn't been updated yet
|
|
||||||
Game.modData.Rules = new ModRules(Game.modData);
|
|
||||||
Game.modData.Rules.ActivateMap(map);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static IEnumerable<KeyValuePair<string, MusicInfo>> InstalledMusic { get { return Music.Where(m => m.Value.Exists); } }
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public class ModRules
|
|
||||||
{
|
{
|
||||||
readonly ModData modData;
|
readonly ModData modData;
|
||||||
|
|
||||||
//
|
|
||||||
// These contain all unique instances created from each mod/map combination
|
|
||||||
//
|
|
||||||
readonly Dictionary<string, ActorInfo> actorCache = new Dictionary<string, ActorInfo>();
|
readonly Dictionary<string, ActorInfo> actorCache = new Dictionary<string, ActorInfo>();
|
||||||
readonly Dictionary<string, WeaponInfo> weaponCache = new Dictionary<string, WeaponInfo>();
|
readonly Dictionary<string, WeaponInfo> weaponCache = new Dictionary<string, WeaponInfo>();
|
||||||
readonly Dictionary<string, SoundInfo> voiceCache = new Dictionary<string, SoundInfo>();
|
readonly Dictionary<string, SoundInfo> voiceCache = new Dictionary<string, SoundInfo>();
|
||||||
@@ -53,40 +29,60 @@ namespace OpenRA
|
|||||||
readonly Dictionary<string, string> movieCache = new Dictionary<string, string>();
|
readonly Dictionary<string, string> movieCache = new Dictionary<string, string>();
|
||||||
readonly Dictionary<string, TileSet> tileSetCache = new Dictionary<string, TileSet>();
|
readonly Dictionary<string, TileSet> tileSetCache = new Dictionary<string, TileSet>();
|
||||||
|
|
||||||
//
|
public Action OnProgress = () => { if (Game.modData != null && Game.modData.LoadScreen != null) Game.modData.LoadScreen.Display(); };
|
||||||
// These are the instances needed for the current map
|
|
||||||
//
|
|
||||||
public Dictionary<string, ActorInfo> Actors { get; private set; }
|
|
||||||
public Dictionary<string, WeaponInfo> Weapons { get; private set; }
|
|
||||||
public Dictionary<string, SoundInfo> Voices { get; private set; }
|
|
||||||
public Dictionary<string, SoundInfo> Notifications { get; private set; }
|
|
||||||
public Dictionary<string, MusicInfo> Music { get; private set; }
|
|
||||||
public Dictionary<string, string> Movies { get; private set; }
|
|
||||||
public Dictionary<string, TileSet> TileSets { get; private set; }
|
|
||||||
|
|
||||||
|
public RulesetCache(ModData modData)
|
||||||
public ModRules(ModData modData)
|
|
||||||
{
|
{
|
||||||
this.modData = modData;
|
this.modData = modData;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void ActivateMap(Map map)
|
public ModRuleset LoadModRules()
|
||||||
{
|
{
|
||||||
var m = modData.Manifest;
|
var m = modData.Manifest;
|
||||||
using (new PerfTimer("Actors"))
|
|
||||||
Actors = LoadYamlRules(actorCache, m.Rules, map.Rules, (k, y) => new ActorInfo(k.Key.ToLowerInvariant(), k.Value, y));
|
Dictionary<string, MusicInfo> music;
|
||||||
using (new PerfTimer("Weapons"))
|
Dictionary<string, string> movies;
|
||||||
Weapons = LoadYamlRules(weaponCache, m.Weapons, map.Weapons, (k, _) => new WeaponInfo(k.Key.ToLowerInvariant(), k.Value));
|
Dictionary<string, TileSet> tileSets;
|
||||||
using (new PerfTimer("Voices"))
|
|
||||||
Voices = LoadYamlRules(voiceCache, m.Voices, map.Voices, (k, _) => new SoundInfo(k.Value));
|
|
||||||
using (new PerfTimer("Notifications"))
|
|
||||||
Notifications = LoadYamlRules(notificationCache, m.Notifications, map.Notifications, (k, _) => new SoundInfo(k.Value));
|
|
||||||
using (new PerfTimer("Music"))
|
using (new PerfTimer("Music"))
|
||||||
Music = LoadYamlRules(musicCache, m.Music, new List<MiniYamlNode>(), (k, _) => new MusicInfo(k.Key, k.Value));
|
music = LoadYamlRules(musicCache, m.Music, new List<MiniYamlNode>(), (k, _) => new MusicInfo(k.Key, k.Value));
|
||||||
using (new PerfTimer("Movies"))
|
using (new PerfTimer("Movies"))
|
||||||
Movies = LoadYamlRules(movieCache, m.Movies, new List<MiniYamlNode>(), (k, v) => k.Value.Value);
|
movies = LoadYamlRules(movieCache, m.Movies, new List<MiniYamlNode>(), (k, v) => k.Value.Value);
|
||||||
using (new PerfTimer("TileSets"))
|
using (new PerfTimer("TileSets"))
|
||||||
TileSets = LoadTileSets(tileSetCache, m.TileSets);
|
tileSets = LoadTileSets(tileSetCache, m.TileSets);
|
||||||
|
|
||||||
|
return new ModRuleset(music, movies, tileSets);
|
||||||
|
}
|
||||||
|
|
||||||
|
public MapRuleset LoadDefaultRules()
|
||||||
|
{
|
||||||
|
return LoadMapRules(new Map());
|
||||||
|
}
|
||||||
|
|
||||||
|
public MapRuleset LoadMapRules(Map map)
|
||||||
|
{
|
||||||
|
var m = modData.Manifest;
|
||||||
|
|
||||||
|
Dictionary<string, ActorInfo> actors;
|
||||||
|
Dictionary<string, WeaponInfo> weapons;
|
||||||
|
Dictionary<string, SoundInfo> voices;
|
||||||
|
Dictionary<string, SoundInfo> notifications;
|
||||||
|
|
||||||
|
OnProgress();
|
||||||
|
using (new PerfTimer("Actors"))
|
||||||
|
actors = LoadYamlRules(actorCache, m.Rules, map.RuleDefinitions, (k, y) => new ActorInfo(k.Key.ToLowerInvariant(), k.Value, y));
|
||||||
|
OnProgress();
|
||||||
|
using (new PerfTimer("Weapons"))
|
||||||
|
weapons = LoadYamlRules(weaponCache, m.Weapons, map.WeaponDefinitions, (k, _) => new WeaponInfo(k.Key.ToLowerInvariant(), k.Value));
|
||||||
|
OnProgress();
|
||||||
|
using (new PerfTimer("Voices"))
|
||||||
|
voices = LoadYamlRules(voiceCache, m.Voices, map.VoiceDefinitions, (k, _) => new SoundInfo(k.Value));
|
||||||
|
OnProgress();
|
||||||
|
using (new PerfTimer("Notifications"))
|
||||||
|
notifications = LoadYamlRules(notificationCache, m.Notifications, map.NotificationDefinitions, (k, _) => new SoundInfo(k.Value));
|
||||||
|
|
||||||
|
OnProgress();
|
||||||
|
return new MapRuleset(LoadModRules(), actors, weapons, voices, notifications);
|
||||||
}
|
}
|
||||||
|
|
||||||
Dictionary<string, T> LoadYamlRules<T>(
|
Dictionary<string, T> LoadYamlRules<T>(
|
||||||
@@ -131,7 +127,7 @@ namespace OpenRA
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
t = new TileSet(file);
|
t = new TileSet(modData, file);
|
||||||
itemCache.Add(file, t);
|
itemCache.Add(file, t);
|
||||||
|
|
||||||
items.Add(t.Id, t);
|
items.Add(t.Id, t);
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -28,6 +28,9 @@ namespace OpenRA.Graphics
|
|||||||
|
|
||||||
public string Name { get { return name; } }
|
public string Name { get { return name; } }
|
||||||
|
|
||||||
|
readonly SequenceProvider sequenceProvider;
|
||||||
|
static SequenceProvider lastSequenceProvider;
|
||||||
|
|
||||||
public Animation(string name)
|
public Animation(string name)
|
||||||
: this(name, () => 0) {}
|
: this(name, () => 0) {}
|
||||||
|
|
||||||
@@ -36,6 +39,17 @@ namespace OpenRA.Graphics
|
|||||||
this.name = name.ToLowerInvariant();
|
this.name = name.ToLowerInvariant();
|
||||||
this.tickFunc = () => {};
|
this.tickFunc = () => {};
|
||||||
this.facingFunc = facingFunc;
|
this.facingFunc = facingFunc;
|
||||||
|
|
||||||
|
// TODO: This is wrong, don't use the static
|
||||||
|
if (Game.orderManager != null && Game.orderManager.world != null && Game.orderManager.world.Map != null)
|
||||||
|
sequenceProvider = Game.orderManager.world.Map.SequenceProvider;
|
||||||
|
// HACK: This just makes sure we have a sequence provider in between map changes for delayed actions
|
||||||
|
// It sucks but it can only be removed when we don't use the statics above but replace them with
|
||||||
|
// a possible parameter on this constructor.
|
||||||
|
if (sequenceProvider == null)
|
||||||
|
sequenceProvider = lastSequenceProvider;
|
||||||
|
else
|
||||||
|
lastSequenceProvider = sequenceProvider;
|
||||||
}
|
}
|
||||||
|
|
||||||
int CurrentFrame { get { return backwards ? CurrentSequence.Start + CurrentSequence.Length - frame - 1 : frame; } }
|
int CurrentFrame { get { return backwards ? CurrentSequence.Start + CurrentSequence.Length - frame - 1 : frame; } }
|
||||||
@@ -66,7 +80,7 @@ namespace OpenRA.Graphics
|
|||||||
{
|
{
|
||||||
backwards = false;
|
backwards = false;
|
||||||
tickAlways = false;
|
tickAlways = false;
|
||||||
CurrentSequence = SequenceProvider.GetSequence(name, sequenceName);
|
CurrentSequence = sequenceProvider.GetSequence(name, sequenceName);
|
||||||
frame = 0;
|
frame = 0;
|
||||||
tickFunc = () =>
|
tickFunc = () =>
|
||||||
{
|
{
|
||||||
@@ -81,7 +95,7 @@ namespace OpenRA.Graphics
|
|||||||
if (!HasSequence(sequenceName))
|
if (!HasSequence(sequenceName))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
CurrentSequence = SequenceProvider.GetSequence(name, sequenceName);
|
CurrentSequence = sequenceProvider.GetSequence(name, sequenceName);
|
||||||
frame %= CurrentSequence.Length;
|
frame %= CurrentSequence.Length;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -90,7 +104,7 @@ namespace OpenRA.Graphics
|
|||||||
{
|
{
|
||||||
backwards = false;
|
backwards = false;
|
||||||
tickAlways = false;
|
tickAlways = false;
|
||||||
CurrentSequence = SequenceProvider.GetSequence(name, sequenceName);
|
CurrentSequence = sequenceProvider.GetSequence(name, sequenceName);
|
||||||
frame = 0;
|
frame = 0;
|
||||||
tickFunc = () =>
|
tickFunc = () =>
|
||||||
{
|
{
|
||||||
@@ -114,7 +128,7 @@ namespace OpenRA.Graphics
|
|||||||
{
|
{
|
||||||
backwards = false;
|
backwards = false;
|
||||||
tickAlways = true;
|
tickAlways = true;
|
||||||
CurrentSequence = SequenceProvider.GetSequence(name, sequenceName);
|
CurrentSequence = sequenceProvider.GetSequence(name, sequenceName);
|
||||||
frame = func();
|
frame = func();
|
||||||
tickFunc = () => frame = func();
|
tickFunc = () => frame = func();
|
||||||
}
|
}
|
||||||
@@ -128,7 +142,7 @@ namespace OpenRA.Graphics
|
|||||||
Tick(40); // tick one frame
|
Tick(40); // tick one frame
|
||||||
}
|
}
|
||||||
|
|
||||||
public bool HasSequence(string seq) { return SequenceProvider.HasSequence(name, seq); }
|
public bool HasSequence(string seq) { return sequenceProvider.HasSequence(name, seq); }
|
||||||
|
|
||||||
public void Tick(int t)
|
public void Tick(int t)
|
||||||
{
|
{
|
||||||
@@ -159,7 +173,7 @@ namespace OpenRA.Graphics
|
|||||||
|
|
||||||
public Sequence GetSequence(string sequenceName)
|
public Sequence GetSequence(string sequenceName)
|
||||||
{
|
{
|
||||||
return SequenceProvider.GetSequence(name, sequenceName);
|
return sequenceProvider.GetSequence(name, sequenceName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,23 +16,18 @@ using OpenRA.Primitives;
|
|||||||
|
|
||||||
namespace OpenRA.Graphics
|
namespace OpenRA.Graphics
|
||||||
{
|
{
|
||||||
public static class CursorProvider
|
public class CursorProvider
|
||||||
{
|
{
|
||||||
static HardwarePalette palette;
|
HardwarePalette palette;
|
||||||
static Dictionary<string, CursorSequence> cursors;
|
Dictionary<string, CursorSequence> cursors;
|
||||||
static Cache<string, PaletteReference> palettes;
|
Cache<string, PaletteReference> palettes;
|
||||||
|
|
||||||
static PaletteReference CreatePaletteReference(string name)
|
public Action OnProgress = () => { if (Game.modData != null && Game.modData.LoadScreen != null) Game.modData.LoadScreen.Display(); };
|
||||||
|
|
||||||
|
public CursorProvider(ModData modData)
|
||||||
{
|
{
|
||||||
var pal = palette.GetPalette(name);
|
var sequenceFiles = modData.Manifest.Cursors;
|
||||||
if (pal == null)
|
|
||||||
throw new InvalidOperationException("Palette `{0}` does not exist".F(name));
|
|
||||||
|
|
||||||
return new PaletteReference(name, palette.GetPaletteIndex(name), pal);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void Initialize(string[] sequenceFiles)
|
|
||||||
{
|
|
||||||
cursors = new Dictionary<string, CursorSequence>();
|
cursors = new Dictionary<string, CursorSequence>();
|
||||||
palettes = new Cache<string, PaletteReference>(CreatePaletteReference);
|
palettes = new Cache<string, PaletteReference>(CreatePaletteReference);
|
||||||
var sequences = new MiniYaml(null, sequenceFiles.Select(s => MiniYaml.FromFile(s)).Aggregate(MiniYaml.MergeLiberal));
|
var sequences = new MiniYaml(null, sequenceFiles.Select(s => MiniYaml.FromFile(s)).Aggregate(MiniYaml.MergeLiberal));
|
||||||
@@ -49,26 +44,37 @@ namespace OpenRA.Graphics
|
|||||||
foreach (var p in sequences.NodesDict["Palettes"].Nodes)
|
foreach (var p in sequences.NodesDict["Palettes"].Nodes)
|
||||||
palette.AddPalette(p.Key, new Palette(GlobalFileSystem.Open(p.Value.Value), shadowIndex), false);
|
palette.AddPalette(p.Key, new Palette(GlobalFileSystem.Open(p.Value.Value), shadowIndex), false);
|
||||||
|
|
||||||
|
|
||||||
|
var spriteLoader = new SpriteLoader(new string[0], new SheetBuilder(SheetType.Indexed));
|
||||||
foreach (var s in sequences.NodesDict["Cursors"].Nodes)
|
foreach (var s in sequences.NodesDict["Cursors"].Nodes)
|
||||||
LoadSequencesForCursor(s.Key, s.Value);
|
LoadSequencesForCursor(spriteLoader, s.Key, s.Value);
|
||||||
|
|
||||||
palette.Initialize();
|
palette.Initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void LoadSequencesForCursor(string cursorSrc, MiniYaml cursor)
|
PaletteReference CreatePaletteReference(string name)
|
||||||
{
|
{
|
||||||
Game.modData.LoadScreen.Display();
|
var pal = palette.GetPalette(name);
|
||||||
|
if (pal == null)
|
||||||
|
throw new InvalidOperationException("Palette `{0}` does not exist".F(name));
|
||||||
|
|
||||||
foreach (var sequence in cursor.Nodes)
|
return new PaletteReference(name, palette.GetPaletteIndex(name), pal);
|
||||||
cursors.Add(sequence.Key, new CursorSequence(cursorSrc, cursor.Value, sequence.Value));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static bool HasCursorSequence(string cursor)
|
void LoadSequencesForCursor(SpriteLoader loader, string cursorSrc, MiniYaml cursor)
|
||||||
|
{
|
||||||
|
OnProgress();
|
||||||
|
|
||||||
|
foreach (var sequence in cursor.Nodes)
|
||||||
|
cursors.Add(sequence.Key, new CursorSequence(loader, cursorSrc, cursor.Value, sequence.Value));
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool HasCursorSequence(string cursor)
|
||||||
{
|
{
|
||||||
return cursors.ContainsKey(cursor);
|
return cursors.ContainsKey(cursor);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void DrawCursor(Renderer renderer, string cursorName, int2 lastMousePos, int cursorFrame)
|
public void DrawCursor(Renderer renderer, string cursorName, int2 lastMousePos, int cursorFrame)
|
||||||
{
|
{
|
||||||
var cursorSequence = GetCursorSequence(cursorName);
|
var cursorSequence = GetCursorSequence(cursorName);
|
||||||
var cursorSprite = cursorSequence.GetSprite(cursorFrame);
|
var cursorSprite = cursorSequence.GetSprite(cursorFrame);
|
||||||
@@ -80,13 +86,12 @@ namespace OpenRA.Graphics
|
|||||||
cursorSprite.size);
|
cursorSprite.size);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static CursorSequence GetCursorSequence(string cursor)
|
public CursorSequence GetCursorSequence(string cursor)
|
||||||
{
|
{
|
||||||
try { return cursors[cursor]; }
|
try { return cursors[cursor]; }
|
||||||
catch (KeyNotFoundException)
|
catch (KeyNotFoundException)
|
||||||
{
|
{
|
||||||
throw new InvalidOperationException(
|
throw new InvalidOperationException("Cursor does not have a sequence `{0}`".F(cursor));
|
||||||
"Cursor does not have a sequence `{0}`".F(cursor));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -25,9 +25,9 @@ namespace OpenRA.Graphics
|
|||||||
|
|
||||||
Sprite[] sprites;
|
Sprite[] sprites;
|
||||||
|
|
||||||
public CursorSequence(string cursorSrc, string palette, MiniYaml info)
|
public CursorSequence(SpriteLoader loader, string cursorSrc, string palette, MiniYaml info)
|
||||||
{
|
{
|
||||||
sprites = Game.modData.SpriteLoader.LoadAllSprites(cursorSrc);
|
sprites = loader.LoadAllSprites(cursorSrc);
|
||||||
var d = info.NodesDict;
|
var d = info.NodesDict;
|
||||||
|
|
||||||
start = Exts.ParseIntegerInvariant(d["start"].Value);
|
start = Exts.ParseIntegerInvariant(d["start"].Value);
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -19,14 +19,8 @@ namespace OpenRA.Graphics
|
|||||||
{
|
{
|
||||||
public class Minimap
|
public class Minimap
|
||||||
{
|
{
|
||||||
public static Bitmap TerrainBitmap(Map map)
|
public static Bitmap TerrainBitmap(TileSet tileset, Map map, bool actualSize = false)
|
||||||
{
|
{
|
||||||
return TerrainBitmap(map, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Bitmap TerrainBitmap(Map map, bool actualSize)
|
|
||||||
{
|
|
||||||
var tileset = Rules.TileSets[map.Tileset];
|
|
||||||
var width = map.Bounds.Width;
|
var width = map.Bounds.Width;
|
||||||
var height = map.Bounds.Height;
|
var height = map.Bounds.Height;
|
||||||
|
|
||||||
@@ -61,10 +55,9 @@ namespace OpenRA.Graphics
|
|||||||
|
|
||||||
// Add the static resources defined in the map; if the map lives
|
// Add the static resources defined in the map; if the map lives
|
||||||
// in a world use AddCustomTerrain instead
|
// in a world use AddCustomTerrain instead
|
||||||
public static Bitmap AddStaticResources(Map map, Bitmap terrainBitmap)
|
public static Bitmap AddStaticResources(TileSet tileset, Map map, Bitmap terrainBitmap)
|
||||||
{
|
{
|
||||||
Bitmap terrain = new Bitmap(terrainBitmap);
|
Bitmap terrain = new Bitmap(terrainBitmap);
|
||||||
var tileset = Rules.TileSets[map.Tileset];
|
|
||||||
|
|
||||||
var bitmapData = terrain.LockBits(terrain.Bounds(),
|
var bitmapData = terrain.LockBits(terrain.Bounds(),
|
||||||
ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
|
ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
|
||||||
@@ -81,7 +74,7 @@ namespace OpenRA.Graphics
|
|||||||
if (map.MapResources.Value[mapX, mapY].Type == 0)
|
if (map.MapResources.Value[mapX, mapY].Type == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
var res = Rules.Info["world"].Traits.WithInterface<ResourceTypeInfo>()
|
var res = map.Rules.Actors["world"].Traits.WithInterface<ResourceTypeInfo>()
|
||||||
.Where(t => t.ResourceType == map.MapResources.Value[mapX, mapY].Type)
|
.Where(t => t.ResourceType == map.MapResources.Value[mapX, mapY].Type)
|
||||||
.Select(t => t.TerrainType).FirstOrDefault();
|
.Select(t => t.TerrainType).FirstOrDefault();
|
||||||
if (res == null)
|
if (res == null)
|
||||||
@@ -185,10 +178,10 @@ namespace OpenRA.Graphics
|
|||||||
return bitmap;
|
return bitmap;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Bitmap RenderMapPreview(Map map, bool actualSize)
|
public static Bitmap RenderMapPreview(TileSet tileset, Map map, bool actualSize)
|
||||||
{
|
{
|
||||||
Bitmap terrain = TerrainBitmap(map, actualSize);
|
Bitmap terrain = TerrainBitmap(tileset, map, actualSize);
|
||||||
return AddStaticResources(map, terrain);
|
return AddStaticResources(tileset, map, terrain);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ namespace OpenRA.Graphics
|
|||||||
public readonly int ShadowZOffset;
|
public readonly int ShadowZOffset;
|
||||||
public readonly int[] Frames;
|
public readonly int[] Frames;
|
||||||
|
|
||||||
public Sequence(string unit, string name, MiniYaml info)
|
public Sequence(SpriteLoader loader, string unit, string name, MiniYaml info)
|
||||||
{
|
{
|
||||||
var srcOverride = info.Value;
|
var srcOverride = info.Value;
|
||||||
Name = name;
|
Name = name;
|
||||||
@@ -50,7 +50,7 @@ namespace OpenRA.Graphics
|
|||||||
|
|
||||||
// Apply offset to each sprite in the sequence
|
// Apply offset to each sprite in the sequence
|
||||||
// Different sequences may apply different offsets to the same frame
|
// Different sequences may apply different offsets to the same frame
|
||||||
sprites = Game.modData.SpriteLoader.LoadAllSprites(srcOverride ?? unit).Select(
|
sprites = loader.LoadAllSprites(srcOverride ?? unit).Select(
|
||||||
s => new Sprite(s.sheet, s.bounds, s.offset + offset, s.channel, blendMode)).ToArray();
|
s => new Sprite(s.sheet, s.bounds, s.offset + offset, s.channel, blendMode)).ToArray();
|
||||||
|
|
||||||
if (!d.ContainsKey("Length"))
|
if (!d.ContainsKey("Length"))
|
||||||
|
|||||||
@@ -17,102 +17,101 @@ using OpenRA.Primitives;
|
|||||||
|
|
||||||
namespace OpenRA.Graphics
|
namespace OpenRA.Graphics
|
||||||
{
|
{
|
||||||
public static class SequenceProvider
|
public class SequenceProvider
|
||||||
{
|
{
|
||||||
public static Sequence GetSequence(string unitName, string sequenceName)
|
readonly Lazy<IReadOnlyDictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>>> sequences;
|
||||||
|
|
||||||
|
public SequenceProvider(Map map)
|
||||||
{
|
{
|
||||||
return Game.modData.SequenceProvider.GetSequence(unitName, sequenceName);
|
this.sequences = Exts.Lazy(() => map.Rules.TileSets[map.Tileset].Data.SequenceCache.LoadSequences(map));
|
||||||
}
|
}
|
||||||
|
|
||||||
public static bool HasSequence(string unitName, string sequenceName)
|
public Sequence GetSequence(string unitName, string sequenceName)
|
||||||
{
|
{
|
||||||
return Game.modData.SequenceProvider.HasSequence(unitName, sequenceName);
|
try
|
||||||
|
{
|
||||||
|
return sequences.Value[unitName].Value[sequenceName];
|
||||||
}
|
}
|
||||||
|
catch (KeyNotFoundException)
|
||||||
public static IEnumerable<string> Sequences(string unitName)
|
|
||||||
{
|
{
|
||||||
return Game.modData.SequenceProvider.Sequences(unitName);
|
if (sequences.Value.ContainsKey(unitName))
|
||||||
|
throw new InvalidOperationException("Unit `{0}` does not have a sequence `{1}`".F(unitName, sequenceName));
|
||||||
|
else
|
||||||
|
throw new InvalidOperationException("Unit `{0}` does not have all sequences defined.".F(unitName));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class ModSequenceProvider
|
public bool HasSequence(string unitName, string sequenceName)
|
||||||
|
{
|
||||||
|
if (!sequences.Value.ContainsKey(unitName))
|
||||||
|
throw new InvalidOperationException("Unit `{0}` does not have sequence `{1}` defined.".F(unitName, sequenceName));
|
||||||
|
|
||||||
|
return sequences.Value[unitName].Value.ContainsKey(sequenceName);
|
||||||
|
}
|
||||||
|
|
||||||
|
public IEnumerable<string> Sequences(string unitName)
|
||||||
|
{
|
||||||
|
if (!sequences.Value.ContainsKey(unitName))
|
||||||
|
throw new InvalidOperationException("Unit `{0}` does not have all sequences defined.".F(unitName));
|
||||||
|
|
||||||
|
return sequences.Value[unitName].Value.Keys;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class SequenceCache
|
||||||
{
|
{
|
||||||
readonly ModData modData;
|
readonly ModData modData;
|
||||||
|
readonly TileSet tileSet;
|
||||||
|
|
||||||
readonly Dictionary<string, Lazy<Dictionary<string, Sequence>>> sequenceCache = new Dictionary<string, Lazy<Dictionary<string, Sequence>>>();
|
readonly Dictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>> sequenceCache = new Dictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>>();
|
||||||
Dictionary<string, Lazy<Dictionary<string, Sequence>>> sequences;
|
|
||||||
|
|
||||||
public ModSequenceProvider(ModData modData)
|
public Action OnProgress = () => { if (Game.modData != null && Game.modData.LoadScreen != null) Game.modData.LoadScreen.Display(); };
|
||||||
|
|
||||||
|
public SequenceCache(ModData modData, TileSet tileSet)
|
||||||
{
|
{
|
||||||
this.modData = modData;
|
this.modData = modData;
|
||||||
|
this.tileSet = tileSet;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void ActivateMap(Map map)
|
public IReadOnlyDictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>> LoadSequences(Map map)
|
||||||
{
|
{
|
||||||
sequences = Load(modData.Manifest.Sequences, map.Tileset, map.Sequences);
|
using (new Support.PerfTimer("LoadSequences"))
|
||||||
|
return Load(map.SequenceDefinitions);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Dictionary<string, Lazy<Dictionary<string, Sequence>>> Load(string[] sequenceFiles, string tileset, List<MiniYamlNode> sequenceNodes)
|
IReadOnlyDictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>> Load(List<MiniYamlNode> sequenceNodes)
|
||||||
{
|
{
|
||||||
Game.modData.LoadScreen.Display();
|
OnProgress();
|
||||||
|
|
||||||
|
var sequenceFiles = modData.Manifest.Sequences;
|
||||||
|
|
||||||
var nodes = sequenceFiles
|
var nodes = sequenceFiles
|
||||||
.Select(s => MiniYaml.FromFile(s))
|
.Select(s => MiniYaml.FromFile(s))
|
||||||
.Aggregate(sequenceNodes, MiniYaml.MergeLiberal);
|
.Aggregate(sequenceNodes, MiniYaml.MergeLiberal);
|
||||||
|
|
||||||
var items = new Dictionary<string, Lazy<Dictionary<string, Sequence>>>();
|
var items = new Dictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>>();
|
||||||
foreach (var node in nodes)
|
foreach (var node in nodes)
|
||||||
{
|
{
|
||||||
// Sequence loading uses the active SpriteLoader that depends on the current map's tileset
|
var key = node.Value.ToLines(node.Key).JoinWith("|");
|
||||||
|
|
||||||
var key = tileset + node.Value.ToLines(node.Key).JoinWith("|");
|
Lazy<IReadOnlyDictionary<string, Sequence>> t;
|
||||||
|
|
||||||
Lazy<Dictionary<string, Sequence>> t;
|
|
||||||
if (sequenceCache.TryGetValue(key, out t))
|
if (sequenceCache.TryGetValue(key, out t))
|
||||||
{
|
{
|
||||||
items.Add(node.Key, t);
|
items.Add(node.Key, t);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
t = Exts.Lazy(() => node.Value.NodesDict.ToDictionary(x => x.Key, x => new Sequence(node.Key, x.Key, x.Value)));
|
t = Exts.Lazy(() => (IReadOnlyDictionary<string, Sequence>)new ReadOnlyDictionary<string, Sequence>(
|
||||||
|
node.Value.NodesDict.ToDictionary(x => x.Key, x =>
|
||||||
|
new Sequence(tileSet.Data.SpriteLoader, node.Key, x.Key, x.Value))));
|
||||||
sequenceCache.Add(key, t);
|
sequenceCache.Add(key, t);
|
||||||
items.Add(node.Key, t);
|
items.Add(node.Key, t);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
OnProgress();
|
||||||
}
|
}
|
||||||
|
|
||||||
return items;
|
return new ReadOnlyDictionary<string, Lazy<IReadOnlyDictionary<string, Sequence>>>(items);
|
||||||
}
|
|
||||||
|
|
||||||
public Sequence GetSequence(string unitName, string sequenceName)
|
|
||||||
{
|
|
||||||
try { return sequences[unitName].Value[sequenceName]; }
|
|
||||||
catch (KeyNotFoundException)
|
|
||||||
{
|
|
||||||
if (sequences.ContainsKey(unitName))
|
|
||||||
throw new InvalidOperationException(
|
|
||||||
"Unit `{0}` does not have a sequence `{1}`".F(unitName, sequenceName));
|
|
||||||
else
|
|
||||||
throw new InvalidOperationException(
|
|
||||||
"Unit `{0}` does not have all sequences defined.".F(unitName));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public bool HasSequence(string unitName, string sequenceName)
|
|
||||||
{
|
|
||||||
if (!sequences.ContainsKey(unitName))
|
|
||||||
throw new InvalidOperationException(
|
|
||||||
"Unit `{0}` does not have sequence `{1}` defined.".F(unitName, sequenceName));
|
|
||||||
|
|
||||||
return sequences[unitName].Value.ContainsKey(sequenceName);
|
|
||||||
}
|
|
||||||
|
|
||||||
public IEnumerable<string> Sequences(string unitName)
|
|
||||||
{
|
|
||||||
if (!sequences.ContainsKey(unitName))
|
|
||||||
throw new InvalidOperationException(
|
|
||||||
"Unit `{0}` does not have all sequences defined.".F(unitName));
|
|
||||||
|
|
||||||
return sequences[unitName].Value.Keys;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -18,7 +18,7 @@ namespace OpenRA.Graphics
|
|||||||
{
|
{
|
||||||
public class SpriteLoader
|
public class SpriteLoader
|
||||||
{
|
{
|
||||||
readonly SheetBuilder SheetBuilder;
|
public readonly SheetBuilder SheetBuilder;
|
||||||
readonly Cache<string, Sprite[]> sprites;
|
readonly Cache<string, Sprite[]> sprites;
|
||||||
readonly string[] exts;
|
readonly string[] exts;
|
||||||
|
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ namespace OpenRA
|
|||||||
// Describes what is to be loaded in order to run a mod
|
// Describes what is to be loaded in order to run a mod
|
||||||
public class Manifest
|
public class Manifest
|
||||||
{
|
{
|
||||||
public readonly Mod Mod;
|
public readonly ModInformation Mod;
|
||||||
public readonly string[]
|
public readonly string[]
|
||||||
Folders, MapFolders, Rules, ServerTraits,
|
Folders, MapFolders, Rules, ServerTraits,
|
||||||
Sequences, VoxelSequences, Cursors, Chrome, Assemblies, ChromeLayout,
|
Sequences, VoxelSequences, Cursors, Chrome, Assemblies, ChromeLayout,
|
||||||
@@ -38,7 +38,7 @@ namespace OpenRA
|
|||||||
var path = new[] { "mods", mod, "mod.yaml" }.Aggregate(Path.Combine);
|
var path = new[] { "mods", mod, "mod.yaml" }.Aggregate(Path.Combine);
|
||||||
var yaml = new MiniYaml(null, MiniYaml.FromFile(path)).NodesDict;
|
var yaml = new MiniYaml(null, MiniYaml.FromFile(path)).NodesDict;
|
||||||
|
|
||||||
Mod = FieldLoader.Load<Mod>(yaml["Metadata"]);
|
Mod = FieldLoader.Load<ModInformation>(yaml["Metadata"]);
|
||||||
Mod.Id = mod;
|
Mod.Id = mod;
|
||||||
|
|
||||||
// TODO: Use fieldloader
|
// TODO: Use fieldloader
|
||||||
|
|||||||
@@ -18,6 +18,7 @@ using System.Text;
|
|||||||
using OpenRA.FileSystem;
|
using OpenRA.FileSystem;
|
||||||
using OpenRA.Network;
|
using OpenRA.Network;
|
||||||
using OpenRA.Traits;
|
using OpenRA.Traits;
|
||||||
|
using OpenRA.Graphics;
|
||||||
|
|
||||||
namespace OpenRA
|
namespace OpenRA
|
||||||
{
|
{
|
||||||
@@ -94,13 +95,13 @@ namespace OpenRA
|
|||||||
[FieldLoader.Ignore] public Dictionary<string, PlayerReference> Players = new Dictionary<string, PlayerReference>();
|
[FieldLoader.Ignore] public Dictionary<string, PlayerReference> Players = new Dictionary<string, PlayerReference>();
|
||||||
[FieldLoader.Ignore] public Lazy<List<SmudgeReference>> Smudges;
|
[FieldLoader.Ignore] public Lazy<List<SmudgeReference>> Smudges;
|
||||||
|
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> Rules = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> RuleDefinitions = new List<MiniYamlNode>();
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> Sequences = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> SequenceDefinitions = new List<MiniYamlNode>();
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> VoxelSequences = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> VoxelSequenceDefinitions = new List<MiniYamlNode>();
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> Weapons = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> WeaponDefinitions = new List<MiniYamlNode>();
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> Voices = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> VoiceDefinitions = new List<MiniYamlNode>();
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> Notifications = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> NotificationDefinitions = new List<MiniYamlNode>();
|
||||||
[FieldLoader.Ignore] public List<MiniYamlNode> Translations = new List<MiniYamlNode>();
|
[FieldLoader.Ignore] public List<MiniYamlNode> TranslationDefinitions = new List<MiniYamlNode>();
|
||||||
|
|
||||||
// Binary map data
|
// Binary map data
|
||||||
[FieldLoader.Ignore] public byte TileFormat = 1;
|
[FieldLoader.Ignore] public byte TileFormat = 1;
|
||||||
@@ -110,6 +111,10 @@ namespace OpenRA
|
|||||||
[FieldLoader.Ignore] public Lazy<TileReference<byte, byte>[,]> MapResources;
|
[FieldLoader.Ignore] public Lazy<TileReference<byte, byte>[,]> MapResources;
|
||||||
[FieldLoader.Ignore] public string[,] CustomTerrain;
|
[FieldLoader.Ignore] public string[,] CustomTerrain;
|
||||||
|
|
||||||
|
[FieldLoader.Ignore] Lazy<MapRuleset> rules;
|
||||||
|
public MapRuleset Rules { get { return rules != null ? rules.Value : null; } }
|
||||||
|
public SequenceProvider SequenceProvider { get; private set; }
|
||||||
|
|
||||||
public static Map FromTileset(TileSet tileset)
|
public static Map FromTileset(TileSet tileset)
|
||||||
{
|
{
|
||||||
var tile = tileset.Templates.First();
|
var tile = tileset.Templates.First();
|
||||||
@@ -128,6 +133,7 @@ namespace OpenRA
|
|||||||
Actors = Exts.Lazy(() => new Dictionary<string, ActorReference>()),
|
Actors = Exts.Lazy(() => new Dictionary<string, ActorReference>()),
|
||||||
Smudges = Exts.Lazy(() => new List<SmudgeReference>())
|
Smudges = Exts.Lazy(() => new List<SmudgeReference>())
|
||||||
};
|
};
|
||||||
|
map.PostInit();
|
||||||
|
|
||||||
return map;
|
return map;
|
||||||
}
|
}
|
||||||
@@ -210,13 +216,13 @@ namespace OpenRA
|
|||||||
return ret;
|
return ret;
|
||||||
});
|
});
|
||||||
|
|
||||||
Rules = MiniYaml.NodesOrEmpty(yaml, "Rules");
|
RuleDefinitions = MiniYaml.NodesOrEmpty(yaml, "Rules");
|
||||||
Sequences = MiniYaml.NodesOrEmpty(yaml, "Sequences");
|
SequenceDefinitions = MiniYaml.NodesOrEmpty(yaml, "Sequences");
|
||||||
VoxelSequences = MiniYaml.NodesOrEmpty(yaml, "VoxelSequences");
|
VoxelSequenceDefinitions = MiniYaml.NodesOrEmpty(yaml, "VoxelSequences");
|
||||||
Weapons = MiniYaml.NodesOrEmpty(yaml, "Weapons");
|
WeaponDefinitions = MiniYaml.NodesOrEmpty(yaml, "Weapons");
|
||||||
Voices = MiniYaml.NodesOrEmpty(yaml, "Voices");
|
VoiceDefinitions = MiniYaml.NodesOrEmpty(yaml, "Voices");
|
||||||
Notifications = MiniYaml.NodesOrEmpty(yaml, "Notifications");
|
NotificationDefinitions = MiniYaml.NodesOrEmpty(yaml, "Notifications");
|
||||||
Translations = MiniYaml.NodesOrEmpty(yaml, "Translations");
|
TranslationDefinitions = MiniYaml.NodesOrEmpty(yaml, "Translations");
|
||||||
|
|
||||||
CustomTerrain = new string[MapSize.X, MapSize.Y];
|
CustomTerrain = new string[MapSize.X, MapSize.Y];
|
||||||
|
|
||||||
@@ -233,6 +239,19 @@ namespace OpenRA
|
|||||||
|
|
||||||
if (Container.Exists("map.png"))
|
if (Container.Exists("map.png"))
|
||||||
CustomPreview = new Bitmap(Container.GetContent("map.png"));
|
CustomPreview = new Bitmap(Container.GetContent("map.png"));
|
||||||
|
|
||||||
|
PostInit();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PostInit()
|
||||||
|
{
|
||||||
|
rules = Exts.Lazy(() => Game.modData.RulesetCache.LoadMapRules(this));
|
||||||
|
SequenceProvider = new SequenceProvider(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public MapRuleset PreloadRules()
|
||||||
|
{
|
||||||
|
return rules.Value;
|
||||||
}
|
}
|
||||||
|
|
||||||
public CPos[] GetSpawnPoints()
|
public CPos[] GetSpawnPoints()
|
||||||
@@ -282,13 +301,13 @@ namespace OpenRA
|
|||||||
);
|
);
|
||||||
|
|
||||||
root.Add(new MiniYamlNode("Smudges", MiniYaml.FromList<SmudgeReference>(Smudges.Value)));
|
root.Add(new MiniYamlNode("Smudges", MiniYaml.FromList<SmudgeReference>(Smudges.Value)));
|
||||||
root.Add(new MiniYamlNode("Rules", null, Rules));
|
root.Add(new MiniYamlNode("Rules", null, RuleDefinitions));
|
||||||
root.Add(new MiniYamlNode("Sequences", null, Sequences));
|
root.Add(new MiniYamlNode("Sequences", null, SequenceDefinitions));
|
||||||
root.Add(new MiniYamlNode("VoxelSequences", null, VoxelSequences));
|
root.Add(new MiniYamlNode("VoxelSequences", null, VoxelSequenceDefinitions));
|
||||||
root.Add(new MiniYamlNode("Weapons", null, Weapons));
|
root.Add(new MiniYamlNode("Weapons", null, WeaponDefinitions));
|
||||||
root.Add(new MiniYamlNode("Voices", null, Voices));
|
root.Add(new MiniYamlNode("Voices", null, VoiceDefinitions));
|
||||||
root.Add(new MiniYamlNode("Notifications", null, Notifications));
|
root.Add(new MiniYamlNode("Notifications", null, NotificationDefinitions));
|
||||||
root.Add(new MiniYamlNode("Translations", null, Translations));
|
root.Add(new MiniYamlNode("Translations", null, TranslationDefinitions));
|
||||||
|
|
||||||
var entries = new Dictionary<string, byte[]>();
|
var entries = new Dictionary<string, byte[]>();
|
||||||
entries.Add("map.bin", SaveBinaryData());
|
entries.Add("map.bin", SaveBinaryData());
|
||||||
@@ -452,7 +471,7 @@ namespace OpenRA
|
|||||||
|
|
||||||
public void MakeDefaultPlayers()
|
public void MakeDefaultPlayers()
|
||||||
{
|
{
|
||||||
var firstRace = OpenRA.Rules.Info["world"].Traits
|
var firstRace = Rules.Actors["world"].Traits
|
||||||
.WithInterface<CountryInfo>().First(c => c.Selectable).Race;
|
.WithInterface<CountryInfo>().First(c => c.Selectable).Race;
|
||||||
|
|
||||||
if (!Players.ContainsKey("Neutral"))
|
if (!Players.ContainsKey("Neutral"))
|
||||||
@@ -489,10 +508,10 @@ namespace OpenRA
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public void FixOpenAreas()
|
public void FixOpenAreas(MapRuleset rules)
|
||||||
{
|
{
|
||||||
var r = new Random();
|
var r = new Random();
|
||||||
var tileset = OpenRA.Rules.TileSets[Tileset];
|
var tileset = rules.TileSets[Tileset];
|
||||||
|
|
||||||
for (var j = Bounds.Top; j < Bounds.Bottom; j++)
|
for (var j = Bounds.Top; j < Bounds.Bottom; j++)
|
||||||
{
|
{
|
||||||
|
|||||||
14
OpenRA.Game/Map/MapCache.cs
Executable file → Normal file
14
OpenRA.Game/Map/MapCache.cs
Executable file → Normal file
@@ -27,30 +27,30 @@ namespace OpenRA
|
|||||||
{
|
{
|
||||||
public static readonly MapPreview UnknownMap = new MapPreview(null, null);
|
public static readonly MapPreview UnknownMap = new MapPreview(null, null);
|
||||||
readonly Cache<string, MapPreview> previews;
|
readonly Cache<string, MapPreview> previews;
|
||||||
readonly Manifest manifest;
|
readonly ModData modData;
|
||||||
readonly SheetBuilder sheetBuilder;
|
readonly SheetBuilder sheetBuilder;
|
||||||
Thread previewLoaderThread;
|
Thread previewLoaderThread;
|
||||||
object syncRoot = new object();
|
object syncRoot = new object();
|
||||||
Queue<MapPreview> generateMinimap = new Queue<MapPreview>();
|
Queue<MapPreview> generateMinimap = new Queue<MapPreview>();
|
||||||
|
|
||||||
public MapCache(Manifest m)
|
public MapCache(ModData modData)
|
||||||
{
|
{
|
||||||
manifest = m;
|
this.modData = modData;
|
||||||
previews = new Cache<string, MapPreview>(uid => new MapPreview(uid, this));
|
previews = new Cache<string, MapPreview>(uid => new MapPreview(uid, this));
|
||||||
sheetBuilder = new SheetBuilder(SheetType.BGRA);
|
sheetBuilder = new SheetBuilder(SheetType.BGRA);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void LoadMaps()
|
public void LoadMaps()
|
||||||
{
|
{
|
||||||
var paths = manifest.MapFolders.SelectMany(f => FindMapsIn(f));
|
var paths = modData.Manifest.MapFolders.SelectMany(f => FindMapsIn(f));
|
||||||
foreach (var path in paths)
|
foreach (var path in paths)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
using (new Support.PerfTimer(path))
|
using (new Support.PerfTimer(path))
|
||||||
{
|
{
|
||||||
var map = new Map(path, manifest.Mod.Id);
|
var map = new Map(path, modData.Manifest.Mod.Id);
|
||||||
if (manifest.MapCompatibility.Contains(map.RequiresMod))
|
if (modData.Manifest.MapCompatibility.Contains(map.RequiresMod))
|
||||||
previews[map.Uid].UpdateFromMap(map);
|
previews[map.Uid].UpdateFromMap(map);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -149,7 +149,7 @@ namespace OpenRA
|
|||||||
// the next render cycle.
|
// the next render cycle.
|
||||||
// (d) Any partially written bytes from the next minimap is in an
|
// (d) Any partially written bytes from the next minimap is in an
|
||||||
// unallocated area, and will be committed in the next cycle.
|
// unallocated area, and will be committed in the next cycle.
|
||||||
var bitmap = p.CustomPreview ?? Minimap.RenderMapPreview(p.Map, true);
|
var bitmap = p.CustomPreview ?? Minimap.RenderMapPreview(modData.ModRules.TileSets[p.Map.Tileset], p.Map, true);
|
||||||
p.Minimap = sheetBuilder.Add(bitmap);
|
p.Minimap = sheetBuilder.Add(bitmap);
|
||||||
|
|
||||||
lock (syncRoot)
|
lock (syncRoot)
|
||||||
|
|||||||
65
OpenRA.Game/Map/Ruleset.cs
Normal file
65
OpenRA.Game/Map/Ruleset.cs
Normal file
@@ -0,0 +1,65 @@
|
|||||||
|
#region Copyright & License Information
|
||||||
|
/*
|
||||||
|
* Copyright 2007-2014 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.Linq;
|
||||||
|
using OpenRA.GameRules;
|
||||||
|
|
||||||
|
namespace OpenRA
|
||||||
|
{
|
||||||
|
public class ModRuleset
|
||||||
|
{
|
||||||
|
public readonly IReadOnlyDictionary<string, MusicInfo> Music;
|
||||||
|
public readonly IReadOnlyDictionary<string, string> Movies;
|
||||||
|
public readonly IReadOnlyDictionary<string, TileSet> TileSets;
|
||||||
|
|
||||||
|
public ModRuleset(ModRuleset other)
|
||||||
|
{
|
||||||
|
this.Music = other.Music;
|
||||||
|
this.Movies = other.Movies;
|
||||||
|
this.TileSets = other.TileSets;
|
||||||
|
}
|
||||||
|
|
||||||
|
public ModRuleset(
|
||||||
|
IDictionary<string, MusicInfo> music,
|
||||||
|
IDictionary<string, string> movies,
|
||||||
|
IDictionary<string, TileSet> tileSets)
|
||||||
|
{
|
||||||
|
this.Music = new ReadOnlyDictionary<string, MusicInfo>(music);
|
||||||
|
this.Movies = new ReadOnlyDictionary<string, string>(movies);
|
||||||
|
this.TileSets = new ReadOnlyDictionary<string, TileSet>(tileSets);
|
||||||
|
}
|
||||||
|
|
||||||
|
public IEnumerable<KeyValuePair<string, MusicInfo>> InstalledMusic { get { return Music.Where(m => m.Value.Exists); } }
|
||||||
|
}
|
||||||
|
|
||||||
|
public class MapRuleset : ModRuleset
|
||||||
|
{
|
||||||
|
public readonly IReadOnlyDictionary<string, ActorInfo> Actors;
|
||||||
|
public readonly IReadOnlyDictionary<string, WeaponInfo> Weapons;
|
||||||
|
public readonly IReadOnlyDictionary<string, SoundInfo> Voices;
|
||||||
|
public readonly IReadOnlyDictionary<string, SoundInfo> Notifications;
|
||||||
|
|
||||||
|
public MapRuleset(
|
||||||
|
ModRuleset modRuleset,
|
||||||
|
IDictionary<string, ActorInfo> actors,
|
||||||
|
IDictionary<string, WeaponInfo> weapons,
|
||||||
|
IDictionary<string, SoundInfo> voices,
|
||||||
|
IDictionary<string, SoundInfo> notifications)
|
||||||
|
: base(modRuleset)
|
||||||
|
{
|
||||||
|
this.Actors = new ReadOnlyDictionary<string, ActorInfo>(actors);
|
||||||
|
this.Weapons = new ReadOnlyDictionary<string, WeaponInfo>(weapons);
|
||||||
|
this.Voices = new ReadOnlyDictionary<string, SoundInfo>(voices);
|
||||||
|
this.Notifications = new ReadOnlyDictionary<string, SoundInfo>(notifications);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -8,21 +8,23 @@
|
|||||||
*/
|
*/
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
using OpenRA.Graphics;
|
||||||
|
|
||||||
namespace OpenRA
|
namespace OpenRA
|
||||||
{
|
{
|
||||||
public class TerrainTypeInfo
|
public class TerrainTypeInfo
|
||||||
{
|
{
|
||||||
public string Type;
|
public readonly string Type;
|
||||||
public string[] TargetTypes = { };
|
public readonly string[] TargetTypes = { };
|
||||||
public string[] AcceptsSmudgeType = { };
|
public readonly string[] AcceptsSmudgeType = { };
|
||||||
public bool IsWater = false; // TODO: Remove this
|
public readonly bool IsWater = false; // TODO: Remove this
|
||||||
public Color Color;
|
public readonly Color Color;
|
||||||
public string CustomCursor;
|
public readonly string CustomCursor;
|
||||||
|
|
||||||
public TerrainTypeInfo() { }
|
public TerrainTypeInfo() { }
|
||||||
public TerrainTypeInfo(MiniYaml my) { FieldLoader.Load(this, my); }
|
public TerrainTypeInfo(MiniYaml my) { FieldLoader.Load(this, my); }
|
||||||
@@ -32,19 +34,26 @@ namespace OpenRA
|
|||||||
|
|
||||||
public class TileTemplate
|
public class TileTemplate
|
||||||
{
|
{
|
||||||
public ushort Id;
|
public readonly ushort Id;
|
||||||
public string Image;
|
public readonly string Image;
|
||||||
public int[] Frames;
|
public readonly int[] Frames;
|
||||||
public int2 Size;
|
public readonly int2 Size;
|
||||||
public bool PickAny;
|
public readonly bool PickAny;
|
||||||
public string Category;
|
public readonly string Category;
|
||||||
|
|
||||||
[FieldLoader.LoadUsing("LoadTiles")]
|
[FieldLoader.LoadUsing("LoadTiles")]
|
||||||
public Dictionary<byte, string> Tiles = new Dictionary<byte, string>();
|
public readonly Dictionary<byte, string> Tiles = new Dictionary<byte, string>();
|
||||||
|
|
||||||
public TileTemplate() { }
|
public TileTemplate() { }
|
||||||
public TileTemplate(MiniYaml my) { FieldLoader.Load(this, my); }
|
public TileTemplate(MiniYaml my) { FieldLoader.Load(this, my); }
|
||||||
|
|
||||||
|
public TileTemplate(ushort id, string image, int2 size)
|
||||||
|
{
|
||||||
|
this.Id = id;
|
||||||
|
this.Image = image;
|
||||||
|
this.Size = size;
|
||||||
|
}
|
||||||
|
|
||||||
static object LoadTiles(MiniYaml y)
|
static object LoadTiles(MiniYaml y)
|
||||||
{
|
{
|
||||||
return y.NodesDict["Tiles"].NodesDict.ToDictionary(
|
return y.NodesDict["Tiles"].NodesDict.ToDictionary(
|
||||||
@@ -73,24 +82,39 @@ namespace OpenRA
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class TileSetData
|
||||||
|
{
|
||||||
|
Lazy<SpriteLoader> spriteLoader;
|
||||||
|
public SpriteLoader SpriteLoader { get { return spriteLoader.Value; } }
|
||||||
|
|
||||||
|
public readonly SequenceCache SequenceCache;
|
||||||
|
|
||||||
|
public TileSetData(ModData modData, TileSet tileSet)
|
||||||
|
{
|
||||||
|
spriteLoader = Exts.Lazy(() => new SpriteLoader(tileSet.Extensions, new SheetBuilder(SheetType.Indexed)));
|
||||||
|
SequenceCache = new SequenceCache(modData, tileSet);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public class TileSet
|
public class TileSet
|
||||||
{
|
{
|
||||||
public string Name;
|
public readonly string Name;
|
||||||
public string Id;
|
public readonly string Id;
|
||||||
public int SheetSize = 512;
|
public readonly int SheetSize = 512;
|
||||||
public string Palette;
|
public readonly string Palette;
|
||||||
public string PlayerPalette;
|
public readonly string PlayerPalette;
|
||||||
public string[] Extensions;
|
public readonly string[] Extensions;
|
||||||
public int WaterPaletteRotationBase = 0x60;
|
public readonly int WaterPaletteRotationBase = 0x60;
|
||||||
public Dictionary<string, TerrainTypeInfo> Terrain = new Dictionary<string, TerrainTypeInfo>();
|
public readonly Dictionary<string, TerrainTypeInfo> Terrain = new Dictionary<string, TerrainTypeInfo>();
|
||||||
public Dictionary<ushort, TileTemplate> Templates = new Dictionary<ushort, TileTemplate>();
|
public readonly Dictionary<ushort, TileTemplate> Templates = new Dictionary<ushort, TileTemplate>();
|
||||||
public string[] EditorTemplateOrder;
|
public readonly string[] EditorTemplateOrder;
|
||||||
|
|
||||||
static readonly string[] Fields = { "Name", "Id", "SheetSize", "Palette", "Extensions" };
|
static readonly string[] Fields = { "Name", "Id", "SheetSize", "Palette", "Extensions" };
|
||||||
|
|
||||||
public TileSet() { }
|
[FieldLoader.IgnoreAttribute]
|
||||||
|
public readonly TileSetData Data;
|
||||||
|
|
||||||
public TileSet(string filepath)
|
public TileSet(ModData modData, string filepath)
|
||||||
{
|
{
|
||||||
var yaml = MiniYaml.DictFromFile(filepath);
|
var yaml = MiniYaml.DictFromFile(filepath);
|
||||||
|
|
||||||
@@ -104,6 +128,16 @@ namespace OpenRA
|
|||||||
// Templates
|
// Templates
|
||||||
Templates = yaml["Templates"].NodesDict.Values
|
Templates = yaml["Templates"].NodesDict.Values
|
||||||
.Select(y => new TileTemplate(y)).ToDictionary(t => t.Id);
|
.Select(y => new TileTemplate(y)).ToDictionary(t => t.Id);
|
||||||
|
|
||||||
|
Data = new TileSetData(modData, this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public TileSet(string name, string id, string palette, string[] extensions)
|
||||||
|
{
|
||||||
|
this.Name = name;
|
||||||
|
this.Id = id;
|
||||||
|
this.Palette = palette;
|
||||||
|
this.Extensions = extensions;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Save(string filepath)
|
public void Save(string filepath)
|
||||||
@@ -139,5 +173,7 @@ namespace OpenRA
|
|||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
37
OpenRA.Game/ModData.cs
Executable file → Normal file
37
OpenRA.Game/ModData.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -25,11 +25,14 @@ namespace OpenRA
|
|||||||
public readonly WidgetLoader WidgetLoader;
|
public readonly WidgetLoader WidgetLoader;
|
||||||
public readonly MapCache MapCache;
|
public readonly MapCache MapCache;
|
||||||
public ILoadScreen LoadScreen = null;
|
public ILoadScreen LoadScreen = null;
|
||||||
public SheetBuilder SheetBuilder;
|
|
||||||
public SpriteLoader SpriteLoader;
|
|
||||||
public VoxelLoader VoxelLoader;
|
public VoxelLoader VoxelLoader;
|
||||||
public ModSequenceProvider SequenceProvider;
|
public readonly RulesetCache RulesetCache;
|
||||||
public ModRules Rules;
|
public CursorProvider CursorProvider { get; private set; }
|
||||||
|
|
||||||
|
Lazy<ModRuleset> modRules;
|
||||||
|
public ModRuleset ModRules { get { return modRules.Value; } }
|
||||||
|
Lazy<MapRuleset> defaultRules;
|
||||||
|
public MapRuleset DefaultRules { get { return defaultRules.Value; } }
|
||||||
|
|
||||||
public ModData(string mod)
|
public ModData(string mod)
|
||||||
{
|
{
|
||||||
@@ -40,14 +43,16 @@ namespace OpenRA
|
|||||||
LoadScreen.Init(Manifest, Manifest.LoadScreen.NodesDict.ToDictionary(x => x.Key, x => x.Value.Value));
|
LoadScreen.Init(Manifest, Manifest.LoadScreen.NodesDict.ToDictionary(x => x.Key, x => x.Value.Value));
|
||||||
LoadScreen.Display();
|
LoadScreen.Display();
|
||||||
WidgetLoader = new WidgetLoader(this);
|
WidgetLoader = new WidgetLoader(this);
|
||||||
MapCache = new MapCache(Manifest);
|
RulesetCache = new RulesetCache(this);
|
||||||
SequenceProvider = new ModSequenceProvider(this);
|
MapCache = new MapCache(this);
|
||||||
Rules = new ModRules(this);
|
|
||||||
|
|
||||||
// HACK: Mount only local folders so we have a half-working environment for the asset installer
|
// HACK: Mount only local folders so we have a half-working environment for the asset installer
|
||||||
GlobalFileSystem.UnmountAll();
|
GlobalFileSystem.UnmountAll();
|
||||||
foreach (var dir in Manifest.Folders)
|
foreach (var dir in Manifest.Folders)
|
||||||
GlobalFileSystem.Mount(dir);
|
GlobalFileSystem.Mount(dir);
|
||||||
|
|
||||||
|
modRules = Exts.Lazy(() => RulesetCache.LoadModRules());
|
||||||
|
defaultRules = Exts.Lazy(() => RulesetCache.LoadDefaultRules());
|
||||||
}
|
}
|
||||||
|
|
||||||
public void InitializeLoaders()
|
public void InitializeLoaders()
|
||||||
@@ -56,10 +61,9 @@ namespace OpenRA
|
|||||||
// horribly when you use ModData in unexpected ways.
|
// horribly when you use ModData in unexpected ways.
|
||||||
ChromeMetrics.Initialize(Manifest.ChromeMetrics);
|
ChromeMetrics.Initialize(Manifest.ChromeMetrics);
|
||||||
ChromeProvider.Initialize(Manifest.Chrome);
|
ChromeProvider.Initialize(Manifest.Chrome);
|
||||||
SheetBuilder = new SheetBuilder(SheetType.Indexed);
|
|
||||||
SpriteLoader = new SpriteLoader(new string[0], SheetBuilder);
|
|
||||||
VoxelLoader = new VoxelLoader();
|
VoxelLoader = new VoxelLoader();
|
||||||
CursorProvider.Initialize(Manifest.Cursors);
|
|
||||||
|
CursorProvider = new CursorProvider(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<string> Languages { get; private set; }
|
public IEnumerable<string> Languages { get; private set; }
|
||||||
@@ -79,7 +83,7 @@ namespace OpenRA
|
|||||||
var yaml = Manifest.Translations.Select(MiniYaml.FromFile).Aggregate(MiniYaml.MergeLiberal);
|
var yaml = Manifest.Translations.Select(MiniYaml.FromFile).Aggregate(MiniYaml.MergeLiberal);
|
||||||
Languages = yaml.Select(t => t.Key).ToArray();
|
Languages = yaml.Select(t => t.Key).ToArray();
|
||||||
|
|
||||||
yaml = MiniYaml.MergeLiberal(map.Translations, yaml);
|
yaml = MiniYaml.MergeLiberal(map.TranslationDefinitions, yaml);
|
||||||
|
|
||||||
foreach (var y in yaml)
|
foreach (var y in yaml)
|
||||||
{
|
{
|
||||||
@@ -122,14 +126,11 @@ namespace OpenRA
|
|||||||
// Mount map package so custom assets can be used. TODO: check priority.
|
// Mount map package so custom assets can be used. TODO: check priority.
|
||||||
GlobalFileSystem.Mount(GlobalFileSystem.OpenPackage(map.Path, null, int.MaxValue));
|
GlobalFileSystem.Mount(GlobalFileSystem.OpenPackage(map.Path, null, int.MaxValue));
|
||||||
|
|
||||||
using (new Support.PerfTimer("Rules.ActivateMap"))
|
using (new Support.PerfTimer("Map.LoadRules"))
|
||||||
Rules.ActivateMap(map);
|
map.PreloadRules();
|
||||||
SpriteLoader = new SpriteLoader(Rules.TileSets[map.Tileset].Extensions, SheetBuilder);
|
|
||||||
|
|
||||||
using (new Support.PerfTimer("SequenceProvider.ActivateMap"))
|
VoxelProvider.Initialize(Manifest.VoxelSequences, map.VoxelSequenceDefinitions);
|
||||||
SequenceProvider.ActivateMap(map);
|
|
||||||
|
|
||||||
VoxelProvider.Initialize(Manifest.VoxelSequences, map.VoxelSequences);
|
|
||||||
return map;
|
return map;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -14,9 +14,9 @@ using System.Linq;
|
|||||||
|
|
||||||
namespace OpenRA
|
namespace OpenRA
|
||||||
{
|
{
|
||||||
public class Mod
|
public class ModInformation
|
||||||
{
|
{
|
||||||
public static readonly Dictionary<string, Mod> AllMods = ValidateMods(Directory.GetDirectories("mods").Select(x => x.Substring(5)).ToArray());
|
public static readonly Dictionary<string, ModInformation> AllMods = ValidateMods(Directory.GetDirectories("mods").Select(x => x.Substring(5)).ToArray());
|
||||||
|
|
||||||
public string Id;
|
public string Id;
|
||||||
public string Title;
|
public string Title;
|
||||||
@@ -24,9 +24,9 @@ namespace OpenRA
|
|||||||
public string Version;
|
public string Version;
|
||||||
public string Author;
|
public string Author;
|
||||||
|
|
||||||
public static Dictionary<string, Mod> ValidateMods(string[] mods)
|
public static Dictionary<string, ModInformation> ValidateMods(string[] mods)
|
||||||
{
|
{
|
||||||
var ret = new Dictionary<string, Mod>();
|
var ret = new Dictionary<string, ModInformation>();
|
||||||
foreach (var m in mods)
|
foreach (var m in mods)
|
||||||
{
|
{
|
||||||
var yamlPath = new[] { "mods", m, "mod.yaml" }.Aggregate(Path.Combine);
|
var yamlPath = new[] { "mods", m, "mod.yaml" }.Aggregate(Path.Combine);
|
||||||
@@ -37,7 +37,7 @@ namespace OpenRA
|
|||||||
if (!yaml.NodesDict.ContainsKey("Metadata"))
|
if (!yaml.NodesDict.ContainsKey("Metadata"))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
var mod = FieldLoader.Load<Mod>(yaml.NodesDict["Metadata"]);
|
var mod = FieldLoader.Load<ModInformation>(yaml.NodesDict["Metadata"]);
|
||||||
mod.Id = m;
|
mod.Id = m;
|
||||||
|
|
||||||
ret.Add(m, mod);
|
ret.Add(m, mod);
|
||||||
@@ -99,7 +99,6 @@
|
|||||||
<Compile Include="Game.cs" />
|
<Compile Include="Game.cs" />
|
||||||
<Compile Include="GameRules\ActorInfo.cs" />
|
<Compile Include="GameRules\ActorInfo.cs" />
|
||||||
<Compile Include="GameRules\MusicInfo.cs" />
|
<Compile Include="GameRules\MusicInfo.cs" />
|
||||||
<Compile Include="GameRules\Rules.cs" />
|
|
||||||
<Compile Include="GameRules\SoundInfo.cs" />
|
<Compile Include="GameRules\SoundInfo.cs" />
|
||||||
<Compile Include="GameRules\WeaponInfo.cs" />
|
<Compile Include="GameRules\WeaponInfo.cs" />
|
||||||
<Compile Include="Graphics\Animation.cs" />
|
<Compile Include="Graphics\Animation.cs" />
|
||||||
@@ -244,6 +243,10 @@
|
|||||||
<Compile Include="Scripting\ScriptMemberExts.cs" />
|
<Compile Include="Scripting\ScriptMemberExts.cs" />
|
||||||
<Compile Include="Scripting\ScriptPlayerInterface.cs" />
|
<Compile Include="Scripting\ScriptPlayerInterface.cs" />
|
||||||
<Compile Include="Traits\Player\FixedColorPalette.cs" />
|
<Compile Include="Traits\Player\FixedColorPalette.cs" />
|
||||||
|
<Compile Include="Primitives\ReadOnlyDictionary.cs" />
|
||||||
|
<Compile Include="ModInformation.cs" />
|
||||||
|
<Compile Include="Map\Ruleset.cs" />
|
||||||
|
<Compile Include="GameRules\RulesetCache.cs" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Compile Include="FileSystem\D2kSoundResources.cs" />
|
<Compile Include="FileSystem\D2kSoundResources.cs" />
|
||||||
@@ -303,7 +306,6 @@
|
|||||||
<Compile Include="Hotkey.cs" />
|
<Compile Include="Hotkey.cs" />
|
||||||
<Compile Include="Keycode.cs" />
|
<Compile Include="Keycode.cs" />
|
||||||
<Compile Include="MiniYaml.cs" />
|
<Compile Include="MiniYaml.cs" />
|
||||||
<Compile Include="Mod.cs" />
|
|
||||||
<Compile Include="Platform.cs" />
|
<Compile Include="Platform.cs" />
|
||||||
<Compile Include="StreamExts.cs" />
|
<Compile Include="StreamExts.cs" />
|
||||||
<Compile Include="Map\Map.cs" />
|
<Compile Include="Map\Map.cs" />
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ namespace OpenRA
|
|||||||
|
|
||||||
static CountryInfo ChooseCountry(World world, string name)
|
static CountryInfo ChooseCountry(World world, string name)
|
||||||
{
|
{
|
||||||
var selectableCountries = Rules.Info["world"].Traits
|
var selectableCountries = world.Map.Rules.Actors["world"].Traits
|
||||||
.WithInterface<CountryInfo>().Where( c => c.Selectable )
|
.WithInterface<CountryInfo>().Where( c => c.Selectable )
|
||||||
.ToArray();
|
.ToArray();
|
||||||
|
|
||||||
|
|||||||
90
OpenRA.Game/Primitives/ReadOnlyDictionary.cs
Normal file
90
OpenRA.Game/Primitives/ReadOnlyDictionary.cs
Normal file
@@ -0,0 +1,90 @@
|
|||||||
|
#region Copyright & License Information
|
||||||
|
/*
|
||||||
|
* Copyright 2007-2014 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;
|
||||||
|
|
||||||
|
namespace OpenRA
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// A minimal read only dictionary interface for .NET 4
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// .NET 4.5 has an implementation built-in, this code is not meant to
|
||||||
|
/// duplicate it but provide a compatible interface that can be replaced
|
||||||
|
/// when we switch to .NET 4.5 or higher.
|
||||||
|
/// </remarks>
|
||||||
|
public interface IReadOnlyDictionary<TKey, TValue> : IEnumerable<KeyValuePair<TKey, TValue>>
|
||||||
|
{
|
||||||
|
int Count { get; }
|
||||||
|
TValue this[TKey key] { get; }
|
||||||
|
IEnumerable<TKey> Keys { get; }
|
||||||
|
IEnumerable<TValue> Values { get; }
|
||||||
|
|
||||||
|
bool ContainsKey(TKey key);
|
||||||
|
bool TryGetValue(TKey key, out TValue value);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// A minimal read only dictionary for .NET 4 implemented as a wrapper
|
||||||
|
/// around an IDictionary.
|
||||||
|
/// </summary>
|
||||||
|
public class ReadOnlyDictionary<TKey, TValue> : IReadOnlyDictionary<TKey, TValue>
|
||||||
|
{
|
||||||
|
private readonly IDictionary<TKey, TValue> dict;
|
||||||
|
|
||||||
|
public ReadOnlyDictionary()
|
||||||
|
: this(new Dictionary<TKey, TValue>())
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
public ReadOnlyDictionary(IDictionary<TKey, TValue> dict)
|
||||||
|
{
|
||||||
|
if (dict == null)
|
||||||
|
throw new ArgumentNullException("dict");
|
||||||
|
|
||||||
|
this.dict = dict;
|
||||||
|
}
|
||||||
|
|
||||||
|
#region IReadOnlyDictionary implementation
|
||||||
|
public bool ContainsKey(TKey key)
|
||||||
|
{
|
||||||
|
return dict.ContainsKey(key);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool TryGetValue(TKey key, out TValue value)
|
||||||
|
{
|
||||||
|
return dict.TryGetValue(key, out value);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int Count { get { return dict.Count; } }
|
||||||
|
|
||||||
|
public TValue this[TKey key] { get { return dict[key]; } }
|
||||||
|
|
||||||
|
public IEnumerable<TKey> Keys { get { return dict.Keys; } }
|
||||||
|
|
||||||
|
public IEnumerable<TValue> Values { get { return dict.Values; } }
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region IEnumerable implementation
|
||||||
|
public IEnumerator<KeyValuePair<TKey, TValue>> GetEnumerator()
|
||||||
|
{
|
||||||
|
return dict.GetEnumerator();
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region IEnumerable implementation
|
||||||
|
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
|
||||||
|
{
|
||||||
|
return dict.GetEnumerator();
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -296,15 +296,18 @@ namespace OpenRA
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Returns true if played successfully
|
// Returns true if played successfully
|
||||||
public static bool PlayPredefined(Player p, Actor voicedUnit, string type, string definition, string variant, bool relative, WPos pos, float volumeModifier, bool attenuateVolume)
|
public static bool PlayPredefined(MapRuleset ruleset, Player p, Actor voicedUnit, string type, string definition, string variant, bool relative, WPos pos, float volumeModifier, bool attenuateVolume)
|
||||||
{
|
{
|
||||||
|
if (ruleset == null)
|
||||||
|
throw new ArgumentNullException("ruleset");
|
||||||
|
|
||||||
if (definition == null)
|
if (definition == null)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (Rules.Voices == null || Rules.Notifications == null)
|
if (ruleset.Voices == null || ruleset.Notifications == null)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
var rules = (voicedUnit != null) ? Rules.Voices[type] : Rules.Notifications[type];
|
var rules = (voicedUnit != null) ? ruleset.Voices[type] : ruleset.Notifications[type];
|
||||||
if (rules == null)
|
if (rules == null)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@@ -366,7 +369,7 @@ namespace OpenRA
|
|||||||
return false;
|
return false;
|
||||||
|
|
||||||
var type = mi.Voice.ToLowerInvariant();
|
var type = mi.Voice.ToLowerInvariant();
|
||||||
return PlayPredefined(null, voicedUnit, type, phrase, variant, true, WPos.Zero, 1f, true);
|
return PlayPredefined(voicedUnit.World.Map.Rules, null, voicedUnit, type, phrase, variant, true, WPos.Zero, 1f, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static bool PlayVoiceLocal(string phrase, Actor voicedUnit, string variant, WPos pos, float volume)
|
public static bool PlayVoiceLocal(string phrase, Actor voicedUnit, string variant, WPos pos, float volume)
|
||||||
@@ -379,15 +382,18 @@ namespace OpenRA
|
|||||||
return false;
|
return false;
|
||||||
|
|
||||||
var type = mi.Voice.ToLowerInvariant();
|
var type = mi.Voice.ToLowerInvariant();
|
||||||
return PlayPredefined(null, voicedUnit, type, phrase, variant, false, pos, volume, true);
|
return PlayPredefined(voicedUnit.World.Map.Rules, null, voicedUnit, type, phrase, variant, false, pos, volume, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static bool PlayNotification(Player player, string type, string notification, string variant)
|
public static bool PlayNotification(MapRuleset rules, Player player, string type, string notification, string variant)
|
||||||
{
|
{
|
||||||
|
if (rules == null)
|
||||||
|
throw new ArgumentNullException("rules");
|
||||||
|
|
||||||
if (type == null || notification == null)
|
if (type == null || notification == null)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return PlayPredefined(player, null, type.ToLowerInvariant(), notification, variant, true, WPos.Zero, 1f, false);
|
return PlayPredefined(rules, player, null, type.ToLowerInvariant(), notification, variant, true, WPos.Zero, 1f, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2012 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -118,7 +118,7 @@ namespace OpenRA.Traits
|
|||||||
{
|
{
|
||||||
if (Ore > 0.8 * OreCapacity)
|
if (Ore > 0.8 * OreCapacity)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(Owner, "Speech", "SilosNeeded", Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, Owner, "Speech", "SilosNeeded", Owner.Country.Race);
|
||||||
AlertSilo = true;
|
AlertSilo = true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -163,14 +163,14 @@ namespace OpenRA.Traits
|
|||||||
public void playCashTickUp(Actor self)
|
public void playCashTickUp(Actor self)
|
||||||
{
|
{
|
||||||
if (Game.Settings.Sound.CashTicks)
|
if (Game.Settings.Sound.CashTicks)
|
||||||
Sound.PlayNotification(self.Owner, "Sounds", "CashTickUp", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Sounds", "CashTickUp", self.Owner.Country.Race);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void playCashTickDown(Actor self)
|
public void playCashTickDown(Actor self)
|
||||||
{
|
{
|
||||||
if (Game.Settings.Sound.CashTicks && nextCashTickTime == 0)
|
if (Game.Settings.Sound.CashTicks && nextCashTickTime == 0)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(self.Owner, "Sounds", "CashTickDown", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Sounds", "CashTickDown", self.Owner.Country.Race);
|
||||||
nextCashTickTime = 2;
|
nextCashTickTime = 2;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -32,7 +32,7 @@ namespace OpenRA.Traits
|
|||||||
|
|
||||||
public PipType PipColor = PipType.Yellow;
|
public PipType PipColor = PipType.Yellow;
|
||||||
|
|
||||||
public object Create(ActorInitializer init) { return new ResourceType(this); }
|
public object Create(ActorInitializer init) { return new ResourceType(this, init); }
|
||||||
}
|
}
|
||||||
|
|
||||||
public class ResourceType : IWorldLoaded
|
public class ResourceType : IWorldLoaded
|
||||||
@@ -41,13 +41,13 @@ namespace OpenRA.Traits
|
|||||||
public PaletteReference Palette { get; private set; }
|
public PaletteReference Palette { get; private set; }
|
||||||
public readonly Dictionary<string, Sprite[]> Variants;
|
public readonly Dictionary<string, Sprite[]> Variants;
|
||||||
|
|
||||||
public ResourceType(ResourceTypeInfo info)
|
public ResourceType(ResourceTypeInfo info, ActorInitializer init)
|
||||||
{
|
{
|
||||||
this.Info = info;
|
this.Info = info;
|
||||||
Variants = new Dictionary<string, Sprite[]>();
|
Variants = new Dictionary<string, Sprite[]>();
|
||||||
foreach (var v in info.Variants)
|
foreach (var v in info.Variants)
|
||||||
{
|
{
|
||||||
var seq = SequenceProvider.GetSequence("resources", v);
|
var seq = init.world.Map.SequenceProvider.GetSequence("resources", v);
|
||||||
var sprites = Exts.MakeArray(seq.Length, x => seq.GetSprite(x));
|
var sprites = Exts.MakeArray(seq.Length, x => seq.GetSprite(x));
|
||||||
Variants.Add(v, sprites);
|
Variants.Add(v, sprites);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -11,6 +11,8 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using OpenRA.FileFormats;
|
using OpenRA.FileFormats;
|
||||||
|
using OpenRA.Graphics;
|
||||||
|
using OpenRA.Network;
|
||||||
|
|
||||||
namespace OpenRA.Widgets
|
namespace OpenRA.Widgets
|
||||||
{
|
{
|
||||||
@@ -53,8 +55,13 @@ namespace OpenRA.Widgets
|
|||||||
public Action OnDoubleClick = () => {};
|
public Action OnDoubleClick = () => {};
|
||||||
public Action<KeyInput> OnKeyPress = _ => {};
|
public Action<KeyInput> OnKeyPress = _ => {};
|
||||||
|
|
||||||
public ButtonWidget()
|
readonly MapRuleset rules;
|
||||||
|
|
||||||
|
[ObjectCreator.UseCtor]
|
||||||
|
public ButtonWidget(MapRuleset rules)
|
||||||
{
|
{
|
||||||
|
this.rules = rules;
|
||||||
|
|
||||||
GetText = () => { return Text; };
|
GetText = () => { return Text; };
|
||||||
GetColor = () => TextColor;
|
GetColor = () => TextColor;
|
||||||
GetColorDisabled = () => TextColorDisabled;
|
GetColorDisabled = () => TextColorDisabled;
|
||||||
@@ -70,6 +77,8 @@ namespace OpenRA.Widgets
|
|||||||
protected ButtonWidget(ButtonWidget other)
|
protected ButtonWidget(ButtonWidget other)
|
||||||
: base(other)
|
: base(other)
|
||||||
{
|
{
|
||||||
|
this.rules = other.rules;
|
||||||
|
|
||||||
Text = other.Text;
|
Text = other.Text;
|
||||||
Font = other.Font;
|
Font = other.Font;
|
||||||
TextColor = other.TextColor;
|
TextColor = other.TextColor;
|
||||||
@@ -113,10 +122,10 @@ namespace OpenRA.Widgets
|
|||||||
if (!IsDisabled())
|
if (!IsDisabled())
|
||||||
{
|
{
|
||||||
OnKeyPress(e);
|
OnKeyPress(e);
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickSound", null);
|
Sound.PlayNotification(rules, null, "Sounds", "ClickSound", null);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickDisabledSound", null);
|
Sound.PlayNotification(rules, null, "Sounds", "ClickDisabledSound", null);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -153,12 +162,12 @@ namespace OpenRA.Widgets
|
|||||||
{
|
{
|
||||||
OnMouseDown(mi);
|
OnMouseDown(mi);
|
||||||
Depressed = true;
|
Depressed = true;
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickSound", null);
|
Sound.PlayNotification(rules, null, "Sounds", "ClickSound", null);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
YieldMouseFocus(mi);
|
YieldMouseFocus(mi);
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickDisabledSound", null);
|
Sound.PlayNotification(rules, null, "Sounds", "ClickDisabledSound", null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (mi.Event == MouseInputEvent.Move && HasMouseFocus)
|
else if (mi.Event == MouseInputEvent.Move && HasMouseFocus)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -11,6 +11,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using OpenRA.Graphics;
|
using OpenRA.Graphics;
|
||||||
|
using OpenRA.Network;
|
||||||
|
|
||||||
namespace OpenRA.Widgets
|
namespace OpenRA.Widgets
|
||||||
{
|
{
|
||||||
@@ -23,7 +24,9 @@ namespace OpenRA.Widgets
|
|||||||
public int CheckOffset = 2;
|
public int CheckOffset = 2;
|
||||||
public bool HasPressedState = ChromeMetrics.Get<bool>("CheckboxPressedState");
|
public bool HasPressedState = ChromeMetrics.Get<bool>("CheckboxPressedState");
|
||||||
|
|
||||||
public CheckboxWidget()
|
[ObjectCreator.UseCtor]
|
||||||
|
public CheckboxWidget(MapRuleset rules)
|
||||||
|
: base(rules)
|
||||||
{
|
{
|
||||||
GetCheckType = () => CheckType;
|
GetCheckType = () => CheckType;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -12,6 +12,7 @@ using System;
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using OpenRA.Graphics;
|
using OpenRA.Graphics;
|
||||||
|
using OpenRA.Network;
|
||||||
|
|
||||||
namespace OpenRA.Widgets
|
namespace OpenRA.Widgets
|
||||||
{
|
{
|
||||||
@@ -20,7 +21,9 @@ namespace OpenRA.Widgets
|
|||||||
Widget panel;
|
Widget panel;
|
||||||
MaskWidget fullscreenMask;
|
MaskWidget fullscreenMask;
|
||||||
|
|
||||||
public DropDownButtonWidget() { }
|
[ObjectCreator.UseCtor]
|
||||||
|
public DropDownButtonWidget(MapRuleset rules)
|
||||||
|
: base(rules) { }
|
||||||
|
|
||||||
protected DropDownButtonWidget(DropDownButtonWidget widget) : base(widget) { }
|
protected DropDownButtonWidget(DropDownButtonWidget widget) : base(widget) { }
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -9,6 +9,8 @@
|
|||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
|
using OpenRA.Graphics;
|
||||||
|
using OpenRA.Network;
|
||||||
|
|
||||||
namespace OpenRA.Widgets
|
namespace OpenRA.Widgets
|
||||||
{
|
{
|
||||||
@@ -17,7 +19,9 @@ namespace OpenRA.Widgets
|
|||||||
public string ItemKey;
|
public string ItemKey;
|
||||||
public string BaseName = "scrollitem";
|
public string BaseName = "scrollitem";
|
||||||
|
|
||||||
public ScrollItemWidget()
|
[ObjectCreator.UseCtor]
|
||||||
|
public ScrollItemWidget(MapRuleset rules)
|
||||||
|
: base(rules)
|
||||||
{
|
{
|
||||||
IsVisible = () => false;
|
IsVisible = () => false;
|
||||||
VisualHeight = 0;
|
VisualHeight = 0;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -18,10 +18,13 @@ namespace OpenRA
|
|||||||
{
|
{
|
||||||
public class WidgetLoader
|
public class WidgetLoader
|
||||||
{
|
{
|
||||||
Dictionary<string, MiniYamlNode> widgets = new Dictionary<string, MiniYamlNode>();
|
readonly Dictionary<string, MiniYamlNode> widgets = new Dictionary<string, MiniYamlNode>();
|
||||||
|
readonly ModData modData;
|
||||||
|
|
||||||
public WidgetLoader(ModData modData)
|
public WidgetLoader(ModData modData)
|
||||||
{
|
{
|
||||||
|
this.modData = modData;
|
||||||
|
|
||||||
foreach (var file in modData.Manifest.ChromeLayout.Select(a => MiniYaml.FromFile(a)))
|
foreach (var file in modData.Manifest.ChromeLayout.Select(a => MiniYaml.FromFile(a)))
|
||||||
foreach( var w in file )
|
foreach( var w in file )
|
||||||
{
|
{
|
||||||
@@ -55,6 +58,8 @@ namespace OpenRA
|
|||||||
if (child.Key != "Children")
|
if (child.Key != "Children")
|
||||||
FieldLoader.LoadField(widget, child.Key, child.Value.Value);
|
FieldLoader.LoadField(widget, child.Key, child.Value.Value);
|
||||||
|
|
||||||
|
if (!args.ContainsKey("rules"))
|
||||||
|
args = new WidgetArgs(args) { { "rules", modData.DefaultRules } };
|
||||||
widget.Initialize(args);
|
widget.Initialize(args);
|
||||||
|
|
||||||
foreach (var child in node.Value.Nodes)
|
foreach (var child in node.Value.Nodes)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -125,7 +125,7 @@ namespace OpenRA
|
|||||||
orderGenerator_ = new UnitOrderGenerator();
|
orderGenerator_ = new UnitOrderGenerator();
|
||||||
Map = map;
|
Map = map;
|
||||||
|
|
||||||
TileSet = Rules.TileSets[Map.Tileset];
|
TileSet = map.Rules.TileSets[Map.Tileset];
|
||||||
SharedRandom = new XRandom(orderManager.LobbyInfo.GlobalSettings.RandomSeed);
|
SharedRandom = new XRandom(orderManager.LobbyInfo.GlobalSettings.RandomSeed);
|
||||||
|
|
||||||
WorldActor = CreateActor("World", new TypeDictionary());
|
WorldActor = CreateActor("World", new TypeDictionary());
|
||||||
|
|||||||
@@ -151,7 +151,7 @@ namespace OpenRA
|
|||||||
var selectable = a.Info.Traits.GetOrDefault<SelectableInfo>();
|
var selectable = a.Info.Traits.GetOrDefault<SelectableInfo>();
|
||||||
if (selectable == null) return null;
|
if (selectable == null) return null;
|
||||||
var v = selectable.Voice;
|
var v = selectable.Voice;
|
||||||
return (v == null) ? null : Rules.Voices[v.ToLowerInvariant()];
|
return (v == null) ? null : a.World.Map.Rules.Voices[v.ToLowerInvariant()];
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void PlayVoiceForOrders(this World w, Order[] orders)
|
public static void PlayVoiceForOrders(this World w, Order[] orders)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -69,7 +69,7 @@ namespace OpenRA.Lint
|
|||||||
|
|
||||||
foreach (var testMap in maps)
|
foreach (var testMap in maps)
|
||||||
{
|
{
|
||||||
if (testMap.Rules.Count < 1)
|
if (testMap.RuleDefinitions.Count < 1)
|
||||||
{
|
{
|
||||||
if (verbose)
|
if (verbose)
|
||||||
Console.WriteLine("No custom rules detected. Omitting Map: {0}".F(testMap.Title));
|
Console.WriteLine("No custom rules detected. Omitting Map: {0}".F(testMap.Title));
|
||||||
@@ -79,7 +79,7 @@ namespace OpenRA.Lint
|
|||||||
|
|
||||||
if (verbose)
|
if (verbose)
|
||||||
Console.WriteLine("Map: {0}".F(testMap.Title));
|
Console.WriteLine("Map: {0}".F(testMap.Title));
|
||||||
Rules.LoadRules(Game.modData.Manifest, testMap);
|
testMap.PreloadRules();
|
||||||
|
|
||||||
foreach (var customPassType in Game.modData.ObjectCreator
|
foreach (var customPassType in Game.modData.ObjectCreator
|
||||||
.GetTypesImplementing<ILintPass>())
|
.GetTypesImplementing<ILintPass>())
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -40,7 +40,7 @@ namespace OpenRA.Mods.Cnc
|
|||||||
if (r == null) return;
|
if (r == null) return;
|
||||||
if (!info.Resources.Contains(r.Info.Name)) return;
|
if (!info.Resources.Contains(r.Info.Name)) return;
|
||||||
|
|
||||||
var weapon = Rules.Weapons[info.Weapon.ToLowerInvariant()];
|
var weapon = self.World.Map.Rules.Weapons[info.Weapon.ToLowerInvariant()];
|
||||||
|
|
||||||
self.InflictDamage(self.World.WorldActor, weapon.Warheads[0].Damage, weapon.Warheads[0]);
|
self.InflictDamage(self.World.WorldActor, weapon.Warheads[0].Damage, weapon.Warheads[0]);
|
||||||
poisonTicks = weapon.ROF;
|
poisonTicks = weapon.ROF;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -52,7 +52,7 @@ namespace OpenRA.Mods.Cnc
|
|||||||
|
|
||||||
owner.World.AddFrameEndTask(w =>
|
owner.World.AddFrameEndTask(w =>
|
||||||
{
|
{
|
||||||
var altitude = Rules.Info[actorType].Traits.Get<PlaneInfo>().CruiseAltitude;
|
var altitude = self.World.Map.Rules.Actors[actorType].Traits.Get<PlaneInfo>().CruiseAltitude;
|
||||||
var a = w.CreateActor(actorType, new TypeDictionary
|
var a = w.CreateActor(actorType, new TypeDictionary
|
||||||
{
|
{
|
||||||
new CenterPositionInit(startPos.CenterPosition + new WVec(WRange.Zero, WRange.Zero, altitude)),
|
new CenterPositionInit(startPos.CenterPosition + new WVec(WRange.Zero, WRange.Zero, altitude)),
|
||||||
@@ -69,7 +69,7 @@ namespace OpenRA.Mods.Cnc
|
|||||||
|
|
||||||
rb.PlayCustomAnimRepeating(self, "idle");
|
rb.PlayCustomAnimRepeating(self, "idle");
|
||||||
self.World.AddFrameEndTask(ww => DoProduction(self, producee, exit));
|
self.World.AddFrameEndTask(ww => DoProduction(self, producee, exit));
|
||||||
Sound.PlayNotification(self.Owner, "Speech", (Info as ProductionAirdropInfo).ReadyAudio, self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", (Info as ProductionAirdropInfo).ReadyAudio, self.Owner.Country.Race);
|
||||||
}));
|
}));
|
||||||
|
|
||||||
a.QueueActivity(new Fly(a, Target.FromCell(endPos)));
|
a.QueueActivity(new Fly(a, Target.FromCell(endPos)));
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -22,7 +22,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
public class CncIngameChromeLogic
|
public class CncIngameChromeLogic
|
||||||
{
|
{
|
||||||
Widget ingameRoot;
|
Widget ingameRoot;
|
||||||
World world;
|
readonly World world;
|
||||||
|
|
||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public CncIngameChromeLogic(Widget widget, World world)
|
public CncIngameChromeLogic(Widget widget, World world)
|
||||||
@@ -95,7 +95,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
.Any(a => a.Actor.Owner == world.LocalPlayer && a.Trait.IsActive);
|
.Any(a => a.Actor.Owner == world.LocalPlayer && a.Trait.IsActive);
|
||||||
|
|
||||||
if (radarEnabled != cachedRadarEnabled)
|
if (radarEnabled != cachedRadarEnabled)
|
||||||
Sound.PlayNotification(null, "Sounds", radarEnabled ? "RadarUp" : "RadarDown", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", radarEnabled ? "RadarUp" : "RadarDown", null);
|
||||||
cachedRadarEnabled = radarEnabled;
|
cachedRadarEnabled = radarEnabled;
|
||||||
|
|
||||||
// Switch to observer mode after win/loss
|
// Switch to observer mode after win/loss
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -12,6 +12,7 @@ using System;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using OpenRA.Graphics;
|
using OpenRA.Graphics;
|
||||||
using OpenRA.Mods.RA;
|
using OpenRA.Mods.RA;
|
||||||
|
using OpenRA.Mods.RA.Widgets.Logic;
|
||||||
using OpenRA.Traits;
|
using OpenRA.Traits;
|
||||||
using OpenRA.Widgets;
|
using OpenRA.Widgets;
|
||||||
|
|
||||||
@@ -39,7 +40,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
// TODO: Create a mechanism to do things like this cleaner. Also needed for scripted missions
|
// TODO: Create a mechanism to do things like this cleaner. Also needed for scripted missions
|
||||||
Action onQuit = () =>
|
Action onQuit = () =>
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(null, "Speech", "Leave", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Speech", "Leave", null);
|
||||||
resumeDisabled = true;
|
resumeDisabled = true;
|
||||||
Game.RunAfterDelay(1200, () => mpe.Fade(MenuPaletteEffect.EffectType.Black));
|
Game.RunAfterDelay(1200, () => mpe.Fade(MenuPaletteEffect.EffectType.Black));
|
||||||
Game.RunAfterDelay(1200 + 40 * mpe.Info.FadeLength, () =>
|
Game.RunAfterDelay(1200 + 40 * mpe.Info.FadeLength, () =>
|
||||||
@@ -64,10 +65,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
menu.Get<ButtonWidget>("MUSIC_BUTTON").OnClick = () =>
|
menu.Get<ButtonWidget>("MUSIC_BUTTON").OnClick = () =>
|
||||||
{
|
{
|
||||||
hideButtons = true;
|
hideButtons = true;
|
||||||
Ui.OpenWindow("MUSIC_PANEL", new WidgetArgs()
|
MusicPlayerLogic.OpenWindow(world, () => hideButtons = false);
|
||||||
{
|
|
||||||
{ "onExit", () => hideButtons = false },
|
|
||||||
});
|
|
||||||
};
|
};
|
||||||
|
|
||||||
menu.Get<ButtonWidget>("SETTINGS_BUTTON").OnClick = () =>
|
menu.Get<ButtonWidget>("SETTINGS_BUTTON").OnClick = () =>
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -20,7 +20,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
public class CncInstallMusicLogic
|
public class CncInstallMusicLogic
|
||||||
{
|
{
|
||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public CncInstallMusicLogic(Widget widget, Action onExit)
|
public CncInstallMusicLogic(Widget widget, MapRuleset rules, Action onExit)
|
||||||
{
|
{
|
||||||
var installButton = widget.GetOrNull<ButtonWidget>("INSTALL_BUTTON");
|
var installButton = widget.GetOrNull<ButtonWidget>("INSTALL_BUTTON");
|
||||||
if (installButton != null)
|
if (installButton != null)
|
||||||
@@ -33,7 +33,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
GlobalFileSystem.Mount(Path.Combine(path, "scores.mix"));
|
GlobalFileSystem.Mount(Path.Combine(path, "scores.mix"));
|
||||||
GlobalFileSystem.Mount(Path.Combine(path, "transit.mix"));
|
GlobalFileSystem.Mount(Path.Combine(path, "transit.mix"));
|
||||||
|
|
||||||
Rules.Music.Do(m => m.Value.Reload());
|
rules.Music.Do(m => m.Value.Reload());
|
||||||
|
|
||||||
var musicPlayerLogic = (MusicPlayerLogic)installButton.Parent.LogicObject;
|
var musicPlayerLogic = (MusicPlayerLogic)installButton.Parent.LogicObject;
|
||||||
musicPlayerLogic.BuildMusicTable();
|
musicPlayerLogic.BuildMusicTable();
|
||||||
@@ -50,7 +50,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
{ "filesToCopy", new[] { "SCORES.MIX" } },
|
{ "filesToCopy", new[] { "SCORES.MIX" } },
|
||||||
{ "filesToExtract", new[] { "transit.mix" } },
|
{ "filesToExtract", new[] { "transit.mix" } },
|
||||||
});
|
});
|
||||||
installButton.IsVisible = () => Rules.InstalledMusic.ToArray().Length < 3; // HACK around music being split between transit.mix and scores.mix
|
installButton.IsVisible = () => rules.InstalledMusic.ToArray().Length < 3; // HACK around music being split between transit.mix and scores.mix
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -16,7 +16,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
public class ProductionTabsLogic
|
public class ProductionTabsLogic
|
||||||
{
|
{
|
||||||
ProductionTabsWidget tabs;
|
ProductionTabsWidget tabs;
|
||||||
World world;
|
readonly World world;
|
||||||
|
|
||||||
void SetupProductionGroupButton(ProductionTypeButtonWidget button)
|
void SetupProductionGroupButton(ProductionTypeButtonWidget button)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
public class ProductionTooltipLogic
|
public class ProductionTooltipLogic
|
||||||
{
|
{
|
||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public ProductionTooltipLogic(Widget widget, TooltipContainerWidget tooltipContainer, ProductionPaletteWidget palette)
|
public ProductionTooltipLogic(Widget widget, MapRuleset rules, TooltipContainerWidget tooltipContainer, ProductionPaletteWidget palette)
|
||||||
{
|
{
|
||||||
var pm = palette.World.LocalPlayer.PlayerActor.Trait<PowerManager>();
|
var pm = palette.World.LocalPlayer.PlayerActor.Trait<PowerManager>();
|
||||||
var pr = palette.World.LocalPlayer.PlayerActor.Trait<PlayerResources>();
|
var pr = palette.World.LocalPlayer.PlayerActor.Trait<PlayerResources>();
|
||||||
@@ -45,7 +45,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
if (actor == null || actor == lastActor)
|
if (actor == null || actor == lastActor)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
var info = Rules.Info[actor];
|
var info = rules.Actors[actor];
|
||||||
var tooltip = info.Traits.Get<TooltipInfo>();
|
var tooltip = info.Traits.Get<TooltipInfo>();
|
||||||
var buildable = info.Traits.Get<BuildableInfo>();
|
var buildable = info.Traits.Get<BuildableInfo>();
|
||||||
var cost = info.Traits.Get<ValuedInfo>().Cost;
|
var cost = info.Traits.Get<ValuedInfo>().Cost;
|
||||||
@@ -53,7 +53,7 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
|
|
||||||
nameLabel.GetText = () => tooltip.Name;
|
nameLabel.GetText = () => tooltip.Name;
|
||||||
|
|
||||||
var prereqs = buildable.Prerequisites.Select(a => ActorName(a));
|
var prereqs = buildable.Prerequisites.Select(a => ActorName(rules, a));
|
||||||
var requiresString = prereqs.Any() ? requiresLabel.Text.F(prereqs.JoinWith(", ")) : "";
|
var requiresString = prereqs.Any() ? requiresLabel.Text.F(prereqs.JoinWith(", ")) : "";
|
||||||
requiresLabel.GetText = () => requiresString;
|
requiresLabel.GetText = () => requiresString;
|
||||||
|
|
||||||
@@ -92,11 +92,10 @@ namespace OpenRA.Mods.Cnc.Widgets.Logic
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
static string ActorName(string a)
|
static string ActorName(MapRuleset rules, string a)
|
||||||
{
|
{
|
||||||
ActorInfo ai;
|
ActorInfo ai;
|
||||||
Rules.Info.TryGetValue(a.ToLowerInvariant(), out ai);
|
if (rules.Actors.TryGetValue(a.ToLowerInvariant(), out ai) && ai.Traits.Contains<TooltipInfo>())
|
||||||
if (ai != null && ai.Traits.Contains<TooltipInfo>())
|
|
||||||
return ai.Traits.Get<TooltipInfo>().Name;
|
return ai.Traits.Get<TooltipInfo>().Name;
|
||||||
|
|
||||||
return a;
|
return a;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -114,7 +114,7 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
if (mi.Event != MouseInputEvent.Down)
|
if (mi.Event != MouseInputEvent.Down)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
var actor = Rules.Info[icon.Name];
|
var actor = World.Map.Rules.Actors[icon.Name];
|
||||||
var first = icon.Queued.FirstOrDefault();
|
var first = icon.Queued.FirstOrDefault();
|
||||||
|
|
||||||
if (mi.Button == MouseButton.Left)
|
if (mi.Button == MouseButton.Left)
|
||||||
@@ -135,7 +135,7 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
{
|
{
|
||||||
// Queue a new item
|
// Queue a new item
|
||||||
Sound.Play(TabClick);
|
Sound.Play(TabClick);
|
||||||
Sound.PlayNotification(World.LocalPlayer, "Speech", CurrentQueue.Info.QueuedAudio, World.LocalPlayer.Country.Race);
|
Sound.PlayNotification(World.Map.Rules, World.LocalPlayer, "Speech", CurrentQueue.Info.QueuedAudio, World.LocalPlayer.Country.Race);
|
||||||
World.IssueOrder(Order.StartProduction(CurrentQueue.self, icon.Name,
|
World.IssueOrder(Order.StartProduction(CurrentQueue.self, icon.Name,
|
||||||
Game.GetModifierKeys().HasModifier(Modifiers.Shift) ? 5 : 1));
|
Game.GetModifierKeys().HasModifier(Modifiers.Shift) ? 5 : 1));
|
||||||
}
|
}
|
||||||
@@ -152,13 +152,13 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
// instant cancel of things we havent started yet and things that are finished
|
// instant cancel of things we havent started yet and things that are finished
|
||||||
if (first.Paused || first.Done || first.TotalCost == first.RemainingCost)
|
if (first.Paused || first.Done || first.TotalCost == first.RemainingCost)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(World.LocalPlayer, "Speech", CurrentQueue.Info.CancelledAudio, World.LocalPlayer.Country.Race);
|
Sound.PlayNotification(World.Map.Rules, World.LocalPlayer, "Speech", CurrentQueue.Info.CancelledAudio, World.LocalPlayer.Country.Race);
|
||||||
World.IssueOrder(Order.CancelProduction(CurrentQueue.self, icon.Name,
|
World.IssueOrder(Order.CancelProduction(CurrentQueue.self, icon.Name,
|
||||||
Game.GetModifierKeys().HasModifier(Modifiers.Shift) ? 5 : 1));
|
Game.GetModifierKeys().HasModifier(Modifiers.Shift) ? 5 : 1));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(World.LocalPlayer, "Speech", CurrentQueue.Info.OnHoldAudio, World.LocalPlayer.Country.Race);
|
Sound.PlayNotification(World.Map.Rules, World.LocalPlayer, "Speech", CurrentQueue.Info.OnHoldAudio, World.LocalPlayer.Country.Race);
|
||||||
World.IssueOrder(Order.PauseProduction(CurrentQueue.self, icon.Name, true));
|
World.IssueOrder(Order.PauseProduction(CurrentQueue.self, icon.Name, true));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -60,6 +60,8 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
|
|
||||||
class ProductionTabsWidget : Widget
|
class ProductionTabsWidget : Widget
|
||||||
{
|
{
|
||||||
|
readonly World world;
|
||||||
|
|
||||||
public readonly string PaletteWidget = null;
|
public readonly string PaletteWidget = null;
|
||||||
public readonly string TypesContainer = null;
|
public readonly string TypesContainer = null;
|
||||||
|
|
||||||
@@ -79,7 +81,9 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public ProductionTabsWidget(World world)
|
public ProductionTabsWidget(World world)
|
||||||
{
|
{
|
||||||
Groups = Rules.Info.Values.SelectMany(a => a.Traits.WithInterface<ProductionQueueInfo>())
|
this.world = world;
|
||||||
|
|
||||||
|
Groups = world.Map.Rules.Actors.Values.SelectMany(a => a.Traits.WithInterface<ProductionQueueInfo>())
|
||||||
.Select(q => q.Group).Distinct().ToDictionary(g => g, g => new ProductionTabGroup() { Group = g });
|
.Select(q => q.Group).Distinct().ToDictionary(g => g, g => new ProductionTabGroup() { Group = g });
|
||||||
|
|
||||||
// Only visible if the production palette has icons to display
|
// Only visible if the production palette has icons to display
|
||||||
@@ -93,7 +97,7 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
if (queueGroup == null)
|
if (queueGroup == null)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickSound", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "ClickSound", null);
|
||||||
|
|
||||||
// Prioritize alerted queues
|
// Prioritize alerted queues
|
||||||
var queues = Groups[queueGroup].Tabs.Select(t => t.Queue)
|
var queues = Groups[queueGroup].Tabs.Select(t => t.Queue)
|
||||||
@@ -253,9 +257,9 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
if (leftPressed || rightPressed)
|
if (leftPressed || rightPressed)
|
||||||
{
|
{
|
||||||
if ((leftPressed && !leftDisabled) || (rightPressed && !rightDisabled))
|
if ((leftPressed && !leftDisabled) || (rightPressed && !rightDisabled))
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickSound", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "ClickSound", null);
|
||||||
else
|
else
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickDisabledSound", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "ClickDisabledSound", null);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check production tabs
|
// Check production tabs
|
||||||
@@ -263,7 +267,7 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
if (offsetloc.X > 0 && offsetloc.X < contentWidth)
|
if (offsetloc.X > 0 && offsetloc.X < contentWidth)
|
||||||
{
|
{
|
||||||
CurrentQueue = Groups[queueGroup].Tabs[offsetloc.X / (TabWidth - 1)].Queue;
|
CurrentQueue = Groups[queueGroup].Tabs[offsetloc.X / (TabWidth - 1)].Queue;
|
||||||
Sound.PlayNotification(null, "Sounds", "ClickSound", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "ClickSound", null);
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -9,6 +9,8 @@
|
|||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
using OpenRA.Widgets;
|
using OpenRA.Widgets;
|
||||||
|
using OpenRA.Graphics;
|
||||||
|
using OpenRA.Network;
|
||||||
|
|
||||||
namespace OpenRA.Mods.Cnc.Widgets
|
namespace OpenRA.Mods.Cnc.Widgets
|
||||||
{
|
{
|
||||||
@@ -16,7 +18,10 @@ namespace OpenRA.Mods.Cnc.Widgets
|
|||||||
{
|
{
|
||||||
public readonly string ProductionGroup;
|
public readonly string ProductionGroup;
|
||||||
|
|
||||||
public ProductionTypeButtonWidget() { }
|
[ObjectCreator.UseCtor]
|
||||||
|
public ProductionTypeButtonWidget(MapRuleset rules)
|
||||||
|
: base(rules) { }
|
||||||
|
|
||||||
protected ProductionTypeButtonWidget(ProductionTypeButtonWidget other)
|
protected ProductionTypeButtonWidget(ProductionTypeButtonWidget other)
|
||||||
: base(other)
|
: base(other)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -39,7 +39,7 @@ namespace OpenRA.Mods.Cnc
|
|||||||
{
|
{
|
||||||
this.info = info;
|
this.info = info;
|
||||||
health = self.Trait<Health>();
|
health = self.Trait<Health>();
|
||||||
weapon = Rules.Weapons[info.Weapon.ToLowerInvariant()];
|
weapon = self.World.Map.Rules.Weapons[info.Weapon.ToLowerInvariant()];
|
||||||
}
|
}
|
||||||
|
|
||||||
public void AddedToWorld(Actor self)
|
public void AddedToWorld(Actor self)
|
||||||
|
|||||||
@@ -40,7 +40,7 @@ namespace OpenRA.Mods.D2k
|
|||||||
{
|
{
|
||||||
foreach (var name in info.Weapons)
|
foreach (var name in info.Weapons)
|
||||||
{
|
{
|
||||||
var wep = Rules.Weapons[name];
|
var wep = self.World.Map.Rules.Weapons[name];
|
||||||
var pieces = self.World.SharedRandom.Next(info.Pieces[0], info.Pieces[1]);
|
var pieces = self.World.SharedRandom.Next(info.Pieces[0], info.Pieces[1]);
|
||||||
var range = self.World.SharedRandom.Next(info.Range[0].Range, info.Range[1].Range);
|
var range = self.World.SharedRandom.Next(info.Range[0].Range, info.Range[1].Range);
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -68,9 +68,9 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
|
|
||||||
// Place the building
|
// Place the building
|
||||||
var type = BuildingType.Building;
|
var type = BuildingType.Building;
|
||||||
if (Rules.Info[currentBuilding.Item].Traits.Contains<AttackBaseInfo>())
|
if (ai.Map.Rules.Actors[currentBuilding.Item].Traits.Contains<AttackBaseInfo>())
|
||||||
type = BuildingType.Defense;
|
type = BuildingType.Defense;
|
||||||
else if (Rules.Info[currentBuilding.Item].Traits.Contains<OreRefineryInfo>())
|
else if (ai.Map.Rules.Actors[currentBuilding.Item].Traits.Contains<OreRefineryInfo>())
|
||||||
type = BuildingType.Refinery;
|
type = BuildingType.Refinery;
|
||||||
|
|
||||||
var location = ai.ChooseBuildLocation(currentBuilding.Item, type);
|
var location = ai.ChooseBuildLocation(currentBuilding.Item, type);
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -83,7 +83,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
|
|
||||||
static object LoadBuildingLimits(MiniYaml y) { return LoadList<int>(y, "BuildingLimits"); }
|
static object LoadBuildingLimits(MiniYaml y) { return LoadList<int>(y, "BuildingLimits"); }
|
||||||
|
|
||||||
public object Create(ActorInitializer init) { return new HackyAI(this); }
|
public object Create(ActorInitializer init) { return new HackyAI(this, init); }
|
||||||
}
|
}
|
||||||
|
|
||||||
public class Enemy { public int Aggro; }
|
public class Enemy { public int Aggro; }
|
||||||
@@ -119,15 +119,18 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
const int MaxBaseDistance = 40;
|
const int MaxBaseDistance = 40;
|
||||||
public const int feedbackTime = 30; // ticks; = a bit over 1s. must be >= netlag.
|
public const int feedbackTime = 30; // ticks; = a bit over 1s. must be >= netlag.
|
||||||
|
|
||||||
public World world { get { return p.PlayerActor.World; } }
|
//public World world { get { return p.PlayerActor.World; } }
|
||||||
|
public readonly World world;
|
||||||
|
public Map Map { get { return world.Map; } }
|
||||||
IBotInfo IBot.Info { get { return this.Info; } }
|
IBotInfo IBot.Info { get { return this.Info; } }
|
||||||
|
|
||||||
public HackyAI(HackyAIInfo info)
|
public HackyAI(HackyAIInfo info, ActorInitializer init)
|
||||||
{
|
{
|
||||||
Info = info;
|
Info = info;
|
||||||
|
world = init.world;
|
||||||
|
|
||||||
// Temporary hack.
|
// Temporary hack.
|
||||||
rallypointTestBuilding = Rules.Info[Info.RallypointTestBuilding].Traits.Get<BuildingInfo>();
|
rallypointTestBuilding = Map.Rules.Actors[Info.RallypointTestBuilding].Traits.Get<BuildingInfo>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void BotDebug(string s, params object[] args)
|
public static void BotDebug(string s, params object[] args)
|
||||||
@@ -151,7 +154,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
|
|
||||||
random = new XRandom((int)p.PlayerActor.ActorID);
|
random = new XRandom((int)p.PlayerActor.ActorID);
|
||||||
|
|
||||||
resourceTypes = Rules.Info["world"].Traits.WithInterface<ResourceTypeInfo>()
|
resourceTypes = Map.Rules.Actors["world"].Traits.WithInterface<ResourceTypeInfo>()
|
||||||
.Select(t => t.TerrainType).ToArray();
|
.Select(t => t.TerrainType).ToArray();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -185,8 +188,8 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
foreach (var unit in Info.UnitsToBuild)
|
foreach (var unit in Info.UnitsToBuild)
|
||||||
if (buildableThings.Any(b => b.Name == unit.Key))
|
if (buildableThings.Any(b => b.Name == unit.Key))
|
||||||
if (myUnits.Count(a => a == unit.Key) < unit.Value * myUnits.Length)
|
if (myUnits.Count(a => a == unit.Key) < unit.Value * myUnits.Length)
|
||||||
if (HasAdequateAirUnits(Rules.Info[unit.Key]))
|
if (HasAdequateAirUnits(Map.Rules.Actors[unit.Key]))
|
||||||
return Rules.Info[unit.Key];
|
return Map.Rules.Actors[unit.Key];
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@@ -215,7 +218,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
ActorInfo GetBuildingInfoByCommonName(string commonName, Player owner)
|
ActorInfo GetBuildingInfoByCommonName(string commonName, Player owner)
|
||||||
{
|
{
|
||||||
if (commonName == "ConstructionYard")
|
if (commonName == "ConstructionYard")
|
||||||
return Rules.Info.Where(k => Info.BuildingCommonNames[commonName].Contains(k.Key)).Random(random).Value;
|
return Map.Rules.Actors.Where(k => Info.BuildingCommonNames[commonName].Contains(k.Key)).Random(random).Value;
|
||||||
|
|
||||||
return GetInfoByCommonName(Info.BuildingCommonNames, commonName, owner);
|
return GetInfoByCommonName(Info.BuildingCommonNames, commonName, owner);
|
||||||
}
|
}
|
||||||
@@ -230,7 +233,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
if (!names.Any() || !names.ContainsKey(commonName))
|
if (!names.Any() || !names.ContainsKey(commonName))
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
return Rules.Info.Where(k => names[commonName].Contains(k.Key) &&
|
return Map.Rules.Actors.Where(k => names[commonName].Contains(k.Key) &&
|
||||||
k.Value.Traits.Get<BuildableInfo>().Owner.Contains(owner.Country.Race)).Random(random).Value;
|
k.Value.Traits.Get<BuildableInfo>().Owner.Contains(owner.Country.Race)).Random(random).Value;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -314,8 +317,8 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
foreach (var frac in Info.BuildingFractions)
|
foreach (var frac in Info.BuildingFractions)
|
||||||
if (buildableThings.Any(b => b.Name == frac.Key))
|
if (buildableThings.Any(b => b.Name == frac.Key))
|
||||||
if (myBuildings.Count(a => a == frac.Key) < frac.Value * myBuildings.Length && HasAdequateNumber(frac.Key, p) &&
|
if (myBuildings.Count(a => a == frac.Key) < frac.Value * myBuildings.Length && HasAdequateNumber(frac.Key, p) &&
|
||||||
playerPower.ExcessPower >= Rules.Info[frac.Key].Traits.Get<BuildingInfo>().Power)
|
playerPower.ExcessPower >= Map.Rules.Actors[frac.Key].Traits.Get<BuildingInfo>().Power)
|
||||||
return Rules.Info[frac.Key];
|
return Map.Rules.Actors[frac.Key];
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@@ -334,7 +337,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
|
|
||||||
public CPos? ChooseBuildLocation(string actorType, bool distanceToBaseIsImportant, int maxBaseDistance, BuildingType type)
|
public CPos? ChooseBuildLocation(string actorType, bool distanceToBaseIsImportant, int maxBaseDistance, BuildingType type)
|
||||||
{
|
{
|
||||||
var bi = Rules.Info[actorType].Traits.GetOrDefault<BuildingInfo>();
|
var bi = Map.Rules.Actors[actorType].Traits.GetOrDefault<BuildingInfo>();
|
||||||
if (bi == null)
|
if (bi == null)
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
@@ -348,7 +351,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
foreach (var t in tlist)
|
foreach (var t in tlist)
|
||||||
if (world.CanPlaceBuilding(actorType, bi, t, null))
|
if (world.CanPlaceBuilding(actorType, bi, t, null))
|
||||||
if (bi.IsCloseEnoughToBase(world, p, actorType, t))
|
if (bi.IsCloseEnoughToBase(world, p, actorType, t))
|
||||||
if (NoBuildingsUnder(Util.ExpandFootprint(FootprintUtils.Tiles(actorType, bi, t), false)))
|
if (NoBuildingsUnder(Util.ExpandFootprint(FootprintUtils.Tiles(Map.Rules, actorType, bi, t), false)))
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -377,7 +380,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
if (distanceToBaseIsImportant && !bi.IsCloseEnoughToBase(world, p, actorType, t))
|
if (distanceToBaseIsImportant && !bi.IsCloseEnoughToBase(world, p, actorType, t))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (NoBuildingsUnder(Util.ExpandFootprint(FootprintUtils.Tiles(actorType, bi, t), false)))
|
if (NoBuildingsUnder(Util.ExpandFootprint(FootprintUtils.Tiles(Map.Rules, actorType, bi, t), false)))
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -850,7 +853,7 @@ namespace OpenRA.Mods.RA.AI
|
|||||||
if (queue == null)
|
if (queue == null)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (Rules.Info[name] != null)
|
if (Map.Rules.Actors[name] != null)
|
||||||
world.IssueOrder(Order.StartProduction(queue.self, name, 1));
|
world.IssueOrder(Order.StartProduction(queue.self, name, 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -31,7 +31,7 @@ namespace OpenRA.Mods.RA
|
|||||||
public void Killed(Actor self, AttackInfo e)
|
public void Killed(Actor self, AttackInfo e)
|
||||||
{
|
{
|
||||||
var player = (info.NotifyAll) ? self.World.LocalPlayer : self.Owner;
|
var player = (info.NotifyAll) ? self.World.LocalPlayer : self.Owner;
|
||||||
Sound.PlayNotification(player, "Speech", info.Notification, self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, player, "Speech", info.Notification, self.Owner.Country.Race);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -82,7 +82,7 @@ namespace OpenRA.Mods.RA
|
|||||||
Coords = Exts.Lazy(() => self.Trait<IBodyOrientation>());
|
Coords = Exts.Lazy(() => self.Trait<IBodyOrientation>());
|
||||||
limitedAmmo = Exts.Lazy(() => self.TraitOrDefault<LimitedAmmo>());
|
limitedAmmo = Exts.Lazy(() => self.TraitOrDefault<LimitedAmmo>());
|
||||||
|
|
||||||
Weapon = Rules.Weapons[info.Weapon.ToLowerInvariant()];
|
Weapon = self.World.Map.Rules.Weapons[info.Weapon.ToLowerInvariant()];
|
||||||
Burst = Weapon.Burst;
|
Burst = Weapon.Burst;
|
||||||
|
|
||||||
if (info.LocalOffset.Length % 3 != 0)
|
if (info.LocalOffset.Length % 3 != 0)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -44,7 +44,7 @@ namespace OpenRA.Mods.RA
|
|||||||
// Build a list of templates that should be overlayed with bridges
|
// Build a list of templates that should be overlayed with bridges
|
||||||
foreach(var bridge in Info.Bridges)
|
foreach(var bridge in Info.Bridges)
|
||||||
{
|
{
|
||||||
var bi = Rules.Info[bridge].Traits.Get<BridgeInfo>();
|
var bi = w.Map.Rules.Actors[bridge].Traits.Get<BridgeInfo>();
|
||||||
foreach (var template in bi.Templates)
|
foreach (var template in bi.Templates)
|
||||||
BridgeTypes.Add(template.First, Pair.New(bridge, template.Second));
|
BridgeTypes.Add(template.First, Pair.New(bridge, template.Second));
|
||||||
}
|
}
|
||||||
|
|||||||
6
OpenRA.Mods.RA/Buildings/Building.cs
Executable file → Normal file
6
OpenRA.Mods.RA/Buildings/Building.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -65,7 +65,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
return false;
|
return false;
|
||||||
|
|
||||||
var buildingMaxBounds = (CVec)Dimensions;
|
var buildingMaxBounds = (CVec)Dimensions;
|
||||||
var buildingTraits = Rules.Info[buildingName].Traits;
|
var buildingTraits = world.Map.Rules.Actors[buildingName].Traits;
|
||||||
if (buildingTraits.Contains<BibInfo>() && !(buildingTraits.Get<BibInfo>().HasMinibib))
|
if (buildingTraits.Contains<BibInfo>() && !(buildingTraits.Get<BibInfo>().HasMinibib))
|
||||||
buildingMaxBounds += new CVec(0, 1);
|
buildingMaxBounds += new CVec(0, 1);
|
||||||
|
|
||||||
@@ -91,7 +91,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var buildingTiles = FootprintUtils.Tiles(buildingName, this, topLeft).ToList();
|
var buildingTiles = FootprintUtils.Tiles(world.Map.Rules, buildingName, this, topLeft).ToList();
|
||||||
return nearnessCandidates
|
return nearnessCandidates
|
||||||
.Any(a => buildingTiles
|
.Any(a => buildingTiles
|
||||||
.Any(b => Math.Abs(a.X - b.X) <= Adjacent
|
.Any(b => Math.Abs(a.X - b.X) <= Adjacent
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
if (b == null)
|
if (b == null)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
foreach (var u in FootprintUtils.Tiles(a.Info.Name, b.Info, a.Location))
|
foreach (var u in FootprintUtils.Tiles(map.Rules, a.Info.Name, b.Info, a.Location))
|
||||||
if (map.IsInMap(u) && influence[u.X, u.Y] == null)
|
if (map.IsInMap(u) && influence[u.X, u.Y] == null)
|
||||||
influence[u.X, u.Y] = a;
|
influence[u.X, u.Y] = a;
|
||||||
};
|
};
|
||||||
@@ -45,7 +45,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
if (b == null)
|
if (b == null)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
foreach (var u in FootprintUtils.Tiles(a.Info.Name, b.Info, a.Location))
|
foreach (var u in FootprintUtils.Tiles(map.Rules, a.Info.Name, b.Info, a.Location))
|
||||||
if (map.IsInMap(u) && influence[u.X, u.Y] == a)
|
if (map.IsInMap(u) && influence[u.X, u.Y] == a)
|
||||||
influence[u.X, u.Y] = null;
|
influence[u.X, u.Y] = null;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -37,7 +37,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
if (order.OrderString == "PowerDown")
|
if (order.OrderString == "PowerDown")
|
||||||
{
|
{
|
||||||
disabled = !disabled;
|
disabled = !disabled;
|
||||||
Sound.PlayNotification(self.Owner, "Sounds", (disabled ? "EnablePower" : "DisablePower"), self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Sounds", (disabled ? "EnablePower" : "DisablePower"), self.Owner.Country.Race);
|
||||||
PowerManager.UpdateActor(self, disabled ? 0 : normalPower);
|
PowerManager.UpdateActor(self, disabled ? 0 : normalPower);
|
||||||
|
|
||||||
if (disabled)
|
if (disabled)
|
||||||
|
|||||||
8
OpenRA.Mods.RA/Buildings/FootprintUtils.cs
Executable file → Normal file
8
OpenRA.Mods.RA/Buildings/FootprintUtils.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -16,13 +16,13 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
{
|
{
|
||||||
public static class FootprintUtils
|
public static class FootprintUtils
|
||||||
{
|
{
|
||||||
public static IEnumerable<CPos> Tiles(string name, BuildingInfo buildingInfo, CPos topLeft)
|
public static IEnumerable<CPos> Tiles(MapRuleset rules, string name, BuildingInfo buildingInfo, CPos topLeft)
|
||||||
{
|
{
|
||||||
var dim = (CVec)buildingInfo.Dimensions;
|
var dim = (CVec)buildingInfo.Dimensions;
|
||||||
|
|
||||||
var footprint = buildingInfo.Footprint.Where(x => !char.IsWhiteSpace(x));
|
var footprint = buildingInfo.Footprint.Where(x => !char.IsWhiteSpace(x));
|
||||||
|
|
||||||
var buildingTraits = Rules.Info[name].Traits;
|
var buildingTraits = rules.Actors[name].Traits;
|
||||||
if (buildingTraits.Contains<BibInfo>() && !(buildingTraits.Get<BibInfo>().HasMinibib))
|
if (buildingTraits.Contains<BibInfo>() && !(buildingTraits.Get<BibInfo>().HasMinibib))
|
||||||
{
|
{
|
||||||
dim += new CVec(0, 1);
|
dim += new CVec(0, 1);
|
||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
|
|
||||||
public static IEnumerable<CPos> Tiles(Actor a)
|
public static IEnumerable<CPos> Tiles(Actor a)
|
||||||
{
|
{
|
||||||
return Tiles( a.Info.Name, a.Info.Traits.Get<BuildingInfo>(), a.Location );
|
return Tiles(a.World.Map.Rules, a.Info.Name, a.Info.Traits.Get<BuildingInfo>(), a.Location);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static IEnumerable<CPos> UnpathableTiles(string name, BuildingInfo buildingInfo, CPos position)
|
public static IEnumerable<CPos> UnpathableTiles(string name, BuildingInfo buildingInfo, CPos position)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2012 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -108,7 +108,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
if (--nextPowerAdviceTime <= 0)
|
if (--nextPowerAdviceTime <= 0)
|
||||||
{
|
{
|
||||||
if (lowPower)
|
if (lowPower)
|
||||||
Sound.PlayNotification(self.Owner, "Speech", "LowPower", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", "LowPower", self.Owner.Country.Race);
|
||||||
nextPowerAdviceTime = Info.AdviceInterval;
|
nextPowerAdviceTime = Info.AdviceInterval;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -51,7 +51,7 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
Repairer = p;
|
Repairer = p;
|
||||||
Sound.PlayNotification(Repairer, "Speech", "Repairing", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, Repairer, "Speech", "Repairing", self.Owner.Country.Race);
|
||||||
|
|
||||||
self.World.AddFrameEndTask(
|
self.World.AddFrameEndTask(
|
||||||
w => w.Add(new RepairIndicator(self, Info.IndicatorPalettePrefix, p)));
|
w => w.Add(new RepairIndicator(self, Info.IndicatorPalettePrefix, p)));
|
||||||
|
|||||||
6
OpenRA.Mods.RA/Buildings/Util.cs
Executable file → Normal file
6
OpenRA.Mods.RA/Buildings/Util.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -35,14 +35,14 @@ namespace OpenRA.Mods.RA.Buildings
|
|||||||
return true;
|
return true;
|
||||||
|
|
||||||
var res = world.WorldActor.Trait<ResourceLayer>();
|
var res = world.WorldActor.Trait<ResourceLayer>();
|
||||||
return FootprintUtils.Tiles(name, building, topLeft).All(
|
return FootprintUtils.Tiles(world.Map.Rules, name, building, topLeft).All(
|
||||||
t => world.Map.IsInMap(t.X, t.Y) && res.GetResource(t) == null &&
|
t => world.Map.IsInMap(t.X, t.Y) && res.GetResource(t) == null &&
|
||||||
world.IsCellBuildable(t, building, toIgnore));
|
world.IsCellBuildable(t, building, toIgnore));
|
||||||
}
|
}
|
||||||
|
|
||||||
public static IEnumerable<CPos> GetLineBuildCells(World world, CPos location, string name, BuildingInfo bi)
|
public static IEnumerable<CPos> GetLineBuildCells(World world, CPos location, string name, BuildingInfo bi)
|
||||||
{
|
{
|
||||||
var lbi = Rules.Info[name].Traits.Get<LineBuildInfo>();
|
var lbi = world.Map.Rules.Actors[name].Traits.Get<LineBuildInfo>();
|
||||||
var topLeft = location; // 1x1 assumption!
|
var topLeft = location; // 1x1 assumption!
|
||||||
|
|
||||||
if (world.IsCellBuildable(topLeft, bi))
|
if (world.IsCellBuildable(topLeft, bi))
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
var race = info.NewOwnerVoice ? newOwner.Country.Race : oldOwner.Country.Race;
|
var race = info.NewOwnerVoice ? newOwner.Country.Race : oldOwner.Country.Race;
|
||||||
Sound.PlayNotification(captor.World.LocalPlayer, "Speech", info.Notification, race);
|
Sound.PlayNotification(self.World.Map.Rules, captor.World.LocalPlayer, "Speech", info.Notification, race);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -158,7 +158,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
public static void DoExplosion(Actor attacker, string weapontype, WPos pos)
|
public static void DoExplosion(Actor attacker, string weapontype, WPos pos)
|
||||||
{
|
{
|
||||||
var weapon = Rules.Weapons[weapontype.ToLowerInvariant()];
|
var weapon = attacker.World.Map.Rules.Weapons[weapontype.ToLowerInvariant()];
|
||||||
if (weapon.Report != null && weapon.Report.Any())
|
if (weapon.Report != null && weapon.Report.Any())
|
||||||
Sound.Play(weapon.Report.Random(attacker.World.SharedRandom), pos);
|
Sound.Play(weapon.Report.Random(attacker.World.SharedRandom), pos);
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -70,7 +70,7 @@ namespace OpenRA.Mods.RA
|
|||||||
Game.RunAfterDelay(Info.NotificationDelay, () =>
|
Game.RunAfterDelay(Info.NotificationDelay, () =>
|
||||||
{
|
{
|
||||||
if (Game.IsCurrentWorld(self.World))
|
if (Game.IsCurrentWorld(self.World))
|
||||||
Sound.PlayNotification(self.Owner, "Speech", "Lose", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", "Lose", self.Owner.Country.Race);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -81,7 +81,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
Game.Debug("{0} is victorious.".F(self.Owner.PlayerName));
|
Game.Debug("{0} is victorious.".F(self.Owner.PlayerName));
|
||||||
if (self.Owner == self.World.LocalPlayer)
|
if (self.Owner == self.World.LocalPlayer)
|
||||||
Game.RunAfterDelay(Info.NotificationDelay, () => Sound.PlayNotification(self.Owner, "Speech", "Win", self.Owner.Country.Race));
|
Game.RunAfterDelay(Info.NotificationDelay, () => Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", "Win", self.Owner.Country.Race));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -90,7 +90,7 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
var crate = w.CreateActor(false, crateActor, new TypeDictionary { new OwnerInit(w.WorldActor.Owner) });
|
var crate = w.CreateActor(false, crateActor, new TypeDictionary { new OwnerInit(w.WorldActor.Owner) });
|
||||||
var startPos = w.ChooseRandomEdgeCell();
|
var startPos = w.ChooseRandomEdgeCell();
|
||||||
var altitude = Rules.Info[info.DeliveryAircraft].Traits.Get<PlaneInfo>().CruiseAltitude;
|
var altitude = self.World.Map.Rules.Actors[info.DeliveryAircraft].Traits.Get<PlaneInfo>().CruiseAltitude;
|
||||||
var plane = w.CreateActor(info.DeliveryAircraft, new TypeDictionary
|
var plane = w.CreateActor(info.DeliveryAircraft, new TypeDictionary
|
||||||
{
|
{
|
||||||
new CenterPositionInit(startPos.CenterPosition + new WVec(WRange.Zero, WRange.Zero, altitude)),
|
new CenterPositionInit(startPos.CenterPosition + new WVec(WRange.Zero, WRange.Zero, altitude)),
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA.Crates
|
|||||||
|
|
||||||
public bool CanGiveTo(Actor collector)
|
public bool CanGiveTo(Actor collector)
|
||||||
{
|
{
|
||||||
var bi = Rules.Info[Info.Unit].Traits.GetOrDefault<BuildableInfo>();
|
var bi = self.World.Map.Rules.Actors[Info.Unit].Traits.GetOrDefault<BuildableInfo>();
|
||||||
|
|
||||||
// this unit is not buildable by the collector's country, so
|
// this unit is not buildable by the collector's country, so
|
||||||
// don't give them free ones either.
|
// don't give them free ones either.
|
||||||
@@ -68,7 +68,7 @@ namespace OpenRA.Mods.RA.Crates
|
|||||||
|
|
||||||
IEnumerable<CPos> GetSuitableCells(CPos near)
|
IEnumerable<CPos> GetSuitableCells(CPos near)
|
||||||
{
|
{
|
||||||
var mi = Rules.Info[Info.Unit].Traits.Get<MobileInfo>();
|
var mi = self.World.Map.Rules.Actors[Info.Unit].Traits.Get<MobileInfo>();
|
||||||
|
|
||||||
for (var i = -1; i < 2; i++)
|
for (var i = -1; i < 2; i++)
|
||||||
for (var j = -1; j < 2; j++)
|
for (var j = -1; j < 2; j++)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -49,7 +49,7 @@ namespace OpenRA.Mods.RA.Effects
|
|||||||
anim.PlayRepeating("up");
|
anim.PlayRepeating("up");
|
||||||
|
|
||||||
pos = launchPos;
|
pos = launchPos;
|
||||||
var weaponRules = Rules.Weapons[weapon.ToLowerInvariant()];
|
var weaponRules = firedBy.World.Map.Rules.Weapons[weapon.ToLowerInvariant()];
|
||||||
if (weaponRules.Report != null && weaponRules.Report.Any())
|
if (weaponRules.Report != null && weaponRules.Report.Any())
|
||||||
Sound.Play(weaponRules.Report.Random(firedBy.World.SharedRandom), pos);
|
Sound.Play(weaponRules.Report.Random(firedBy.World.SharedRandom), pos);
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -42,7 +42,7 @@ namespace OpenRA.Mods.RA
|
|||||||
dudesValue /= 100;
|
dudesValue /= 100;
|
||||||
|
|
||||||
var eligibleLocations = FootprintUtils.Tiles(self).ToList();
|
var eligibleLocations = FootprintUtils.Tiles(self).ToList();
|
||||||
var actorTypes = info.ActorTypes.Select(a => new { Name = a, Cost = Rules.Info[a].Traits.Get<ValuedInfo>().Cost }).ToArray();
|
var actorTypes = info.ActorTypes.Select(a => new { Name = a, Cost = self.World.Map.Rules.Actors[a].Traits.Get<ValuedInfo>().Cost }).ToArray();
|
||||||
|
|
||||||
while (eligibleLocations.Count > 0 && actorTypes.Any(a => a.Cost <= dudesValue))
|
while (eligibleLocations.Count > 0 && actorTypes.Any(a => a.Cost <= dudesValue))
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -70,7 +70,7 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
Level++;
|
Level++;
|
||||||
|
|
||||||
Sound.PlayNotification(self.Owner, "Sounds", "LevelUp", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Sounds", "LevelUp", self.Owner.Country.Race);
|
||||||
self.World.AddFrameEndTask(w => w.Add(new CrateEffect(self, "levelup", info.ChevronPalette)));
|
self.World.AddFrameEndTask(w => w.Add(new CrateEffect(self, "levelup", info.ChevronPalette)));
|
||||||
if (Level == 1)
|
if (Level == 1)
|
||||||
self.World.AddFrameEndTask(w =>
|
self.World.AddFrameEndTask(w =>
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -11,6 +11,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
using OpenRA;
|
||||||
using OpenRA.Traits;
|
using OpenRA.Traits;
|
||||||
|
|
||||||
namespace OpenRA.Mods.RA
|
namespace OpenRA.Mods.RA
|
||||||
@@ -23,22 +24,22 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
EmitError = emitError;
|
EmitError = emitError;
|
||||||
|
|
||||||
foreach (var actorInfo in Rules.Info)
|
foreach (var actorInfo in map.Rules.Actors)
|
||||||
foreach (var traitInfo in actorInfo.Value.Traits.WithInterface<ITraitInfo>())
|
foreach (var traitInfo in actorInfo.Value.Traits.WithInterface<ITraitInfo>())
|
||||||
CheckTrait(actorInfo.Value, traitInfo);
|
CheckTrait(actorInfo.Value, traitInfo, map);
|
||||||
}
|
}
|
||||||
|
|
||||||
void CheckTrait(ActorInfo actorInfo, ITraitInfo traitInfo)
|
void CheckTrait(ActorInfo actorInfo, ITraitInfo traitInfo, Map map)
|
||||||
{
|
{
|
||||||
var actualType = traitInfo.GetType();
|
var actualType = traitInfo.GetType();
|
||||||
foreach (var field in actualType.GetFields())
|
foreach (var field in actualType.GetFields())
|
||||||
{
|
{
|
||||||
if (field.HasAttribute<ActorReferenceAttribute>())
|
if (field.HasAttribute<ActorReferenceAttribute>())
|
||||||
CheckReference(actorInfo, traitInfo, field, Rules.Info, "actor");
|
CheckReference(actorInfo, traitInfo, field, map.Rules.Actors, "actor");
|
||||||
if (field.HasAttribute<WeaponReferenceAttribute>())
|
if (field.HasAttribute<WeaponReferenceAttribute>())
|
||||||
CheckReference(actorInfo, traitInfo, field, Rules.Weapons, "weapon");
|
CheckReference(actorInfo, traitInfo, field, map.Rules.Weapons, "weapon");
|
||||||
if (field.HasAttribute<VoiceReferenceAttribute>())
|
if (field.HasAttribute<VoiceReferenceAttribute>())
|
||||||
CheckReference(actorInfo, traitInfo, field, Rules.Voices, "voice");
|
CheckReference(actorInfo, traitInfo, field, map.Rules.Voices, "voice");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -57,7 +58,7 @@ namespace OpenRA.Mods.RA
|
|||||||
}
|
}
|
||||||
|
|
||||||
void CheckReference<T>(ActorInfo actorInfo, ITraitInfo traitInfo, FieldInfo fieldInfo,
|
void CheckReference<T>(ActorInfo actorInfo, ITraitInfo traitInfo, FieldInfo fieldInfo,
|
||||||
Dictionary<string, T> dict, string type)
|
IReadOnlyDictionary<string, T> dict, string type)
|
||||||
{
|
{
|
||||||
var values = GetFieldValues(traitInfo, fieldInfo);
|
var values = GetFieldValues(traitInfo, fieldInfo);
|
||||||
foreach (var v in values)
|
foreach (var v in values)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -19,11 +19,11 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
public void Run(Action<string> emitError, Action<string> emitWarning, Map map)
|
public void Run(Action<string> emitError, Action<string> emitWarning, Map map)
|
||||||
{
|
{
|
||||||
var sequences = MiniYaml.MergeLiberal(map.Sequences,
|
var sequences = MiniYaml.MergeLiberal(map.SequenceDefinitions,
|
||||||
Game.modData.Manifest.Sequences.Select(s => MiniYaml.FromFile(s))
|
Game.modData.Manifest.Sequences.Select(s => MiniYaml.FromFile(s))
|
||||||
.Aggregate(MiniYaml.MergeLiberal));
|
.Aggregate(MiniYaml.MergeLiberal));
|
||||||
|
|
||||||
foreach (var actorInfo in Rules.Info)
|
foreach (var actorInfo in map.Rules.Actors)
|
||||||
foreach (var renderInfo in actorInfo.Value.Traits.WithInterface<RenderSimpleInfo>())
|
foreach (var renderInfo in actorInfo.Value.Traits.WithInterface<RenderSimpleInfo>())
|
||||||
{
|
{
|
||||||
var image = renderInfo.Image ?? actorInfo.Value.Name;
|
var image = renderInfo.Image ?? actorInfo.Value.Name;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -18,7 +18,7 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
public void Run(Action<string> emitError, Action<string> emitWarning, Map map)
|
public void Run(Action<string> emitError, Action<string> emitWarning, Map map)
|
||||||
{
|
{
|
||||||
foreach (var actorInfo in Rules.Info.Where(a => !a.Key.StartsWith("^")))
|
foreach (var actorInfo in map.Rules.Actors.Where(a => !a.Key.StartsWith("^")))
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var traits = actorInfo.Value.TraitsInConstructOrder().ToArray();
|
var traits = actorInfo.Value.TraitsInConstructOrder().ToArray();
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -18,13 +18,13 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
public void Run(Action<string> emitError, Action<string> emitWarning, Map map)
|
public void Run(Action<string> emitError, Action<string> emitWarning, Map map)
|
||||||
{
|
{
|
||||||
var providedPrereqs = Rules.Info.Keys.Concat(
|
var providedPrereqs = map.Rules.Actors.Keys.Concat(
|
||||||
Rules.Info.SelectMany(a => a.Value.Traits
|
map.Rules.Actors.SelectMany(a => a.Value.Traits
|
||||||
.WithInterface<ProvidesCustomPrerequisiteInfo>()
|
.WithInterface<ProvidesCustomPrerequisiteInfo>()
|
||||||
.Select(p => p.Prerequisite))).ToArray();
|
.Select(p => p.Prerequisite))).ToArray();
|
||||||
|
|
||||||
// TODO: this check is case insensitive while the real check in-game is not
|
// TODO: this check is case insensitive while the real check in-game is not
|
||||||
foreach (var i in Rules.Info)
|
foreach (var i in map.Rules.Actors)
|
||||||
{
|
{
|
||||||
var bi = i.Value.Traits.GetOrDefault<BuildableInfo>();
|
var bi = i.Value.Traits.GetOrDefault<BuildableInfo>();
|
||||||
if (bi != null)
|
if (bi != null)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -40,7 +40,7 @@ namespace OpenRA.Mods.RA
|
|||||||
this.self = self;
|
this.self = self;
|
||||||
|
|
||||||
var tileset = self.World.TileSet.Id.ToLower();
|
var tileset = self.World.TileSet.Id.ToLower();
|
||||||
tile = SequenceProvider.GetSequence("overlay", "build-valid-{0}".F(tileset)).GetSprite(0);
|
tile = self.World.Map.SequenceProvider.GetSequence("overlay", "build-valid-{0}".F(tileset)).GetSprite(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<IOrderTargeter> Orders
|
public IEnumerable<IOrderTargeter> Orders
|
||||||
@@ -120,8 +120,8 @@ namespace OpenRA.Mods.RA
|
|||||||
minefieldStart = xy;
|
minefieldStart = xy;
|
||||||
|
|
||||||
var tileset = self.World.TileSet.Id.ToLower();
|
var tileset = self.World.TileSet.Id.ToLower();
|
||||||
tileOk = SequenceProvider.GetSequence("overlay", "build-valid-{0}".F(tileset)).GetSprite(0);
|
tileOk = self.World.Map.SequenceProvider.GetSequence("overlay", "build-valid-{0}".F(tileset)).GetSprite(0);
|
||||||
tileBlocked = SequenceProvider.GetSequence("overlay", "build-invalid").GetSprite(0);
|
tileBlocked = self.World.Map.SequenceProvider.GetSequence("overlay", "build-invalid").GetSprite(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -31,10 +31,10 @@ namespace OpenRA.Mods.RA.Orders
|
|||||||
Producer = producer;
|
Producer = producer;
|
||||||
Building = name;
|
Building = name;
|
||||||
var tileset = producer.World.TileSet.Id.ToLower();
|
var tileset = producer.World.TileSet.Id.ToLower();
|
||||||
BuildingInfo = Rules.Info[Building].Traits.Get<BuildingInfo>();
|
BuildingInfo = producer.World.Map.Rules.Actors[Building].Traits.Get<BuildingInfo>();
|
||||||
|
|
||||||
buildOk = SequenceProvider.GetSequence("overlay", "build-valid-{0}".F(tileset)).GetSprite(0);
|
buildOk = producer.World.Map.SequenceProvider.GetSequence("overlay", "build-valid-{0}".F(tileset)).GetSprite(0);
|
||||||
buildBlocked = SequenceProvider.GetSequence("overlay", "build-invalid").GetSprite(0);
|
buildBlocked = producer.World.Map.SequenceProvider.GetSequence("overlay", "build-invalid").GetSprite(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
||||||
@@ -57,11 +57,11 @@ namespace OpenRA.Mods.RA.Orders
|
|||||||
if (!world.CanPlaceBuilding(Building, BuildingInfo, topLeft, null)
|
if (!world.CanPlaceBuilding(Building, BuildingInfo, topLeft, null)
|
||||||
|| !BuildingInfo.IsCloseEnoughToBase(world, Producer.Owner, Building, topLeft))
|
|| !BuildingInfo.IsCloseEnoughToBase(world, Producer.Owner, Building, topLeft))
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(Producer.Owner, "Speech", "BuildingCannotPlaceAudio", Producer.Owner.Country.Race);
|
Sound.PlayNotification(world.Map.Rules, Producer.Owner, "Speech", "BuildingCannotPlaceAudio", Producer.Owner.Country.Race);
|
||||||
yield break;
|
yield break;
|
||||||
}
|
}
|
||||||
|
|
||||||
var isLineBuild = Rules.Info[Building].Traits.Contains<LineBuildInfo>();
|
var isLineBuild = world.Map.Rules.Actors[Building].Traits.Contains<LineBuildInfo>();
|
||||||
yield return new Order(isLineBuild ? "LineBuild" : "PlaceBuilding",
|
yield return new Order(isLineBuild ? "LineBuild" : "PlaceBuilding",
|
||||||
Producer.Owner.PlayerActor, false) { TargetLocation = topLeft, TargetString = Building };
|
Producer.Owner.PlayerActor, false) { TargetLocation = topLeft, TargetString = Building };
|
||||||
}
|
}
|
||||||
@@ -74,14 +74,16 @@ namespace OpenRA.Mods.RA.Orders
|
|||||||
var position = wr.Position(wr.Viewport.ViewToWorldPx(Viewport.LastMousePos)).ToCPos();
|
var position = wr.Position(wr.Viewport.ViewToWorldPx(Viewport.LastMousePos)).ToCPos();
|
||||||
var topLeft = position - FootprintUtils.AdjustForBuildingSize(BuildingInfo);
|
var topLeft = position - FootprintUtils.AdjustForBuildingSize(BuildingInfo);
|
||||||
|
|
||||||
var actorInfo = Rules.Info[Building];
|
var rules = world.Map.Rules;
|
||||||
|
|
||||||
|
var actorInfo = rules.Actors[Building];
|
||||||
foreach (var dec in actorInfo.Traits.WithInterface<IPlaceBuildingDecoration>())
|
foreach (var dec in actorInfo.Traits.WithInterface<IPlaceBuildingDecoration>())
|
||||||
dec.Render(wr, world, actorInfo, position.CenterPosition); /* hack hack */
|
dec.Render(wr, world, actorInfo, position.CenterPosition); /* hack hack */
|
||||||
|
|
||||||
var cells = new Dictionary<CPos, bool>();
|
var cells = new Dictionary<CPos, bool>();
|
||||||
// Linebuild for walls.
|
// Linebuild for walls.
|
||||||
// Assumes a 1x1 footprint; weird things will happen for other footprints
|
// Assumes a 1x1 footprint; weird things will happen for other footprints
|
||||||
if (Rules.Info[Building].Traits.Contains<LineBuildInfo>())
|
if (rules.Actors[Building].Traits.Contains<LineBuildInfo>())
|
||||||
{
|
{
|
||||||
foreach (var t in BuildingUtils.GetLineBuildCells(world, topLeft, Building, BuildingInfo))
|
foreach (var t in BuildingUtils.GetLineBuildCells(world, topLeft, Building, BuildingInfo))
|
||||||
cells.Add(t, BuildingInfo.IsCloseEnoughToBase(world, world.LocalPlayer, Building, t));
|
cells.Add(t, BuildingInfo.IsCloseEnoughToBase(world, world.LocalPlayer, Building, t));
|
||||||
@@ -90,7 +92,7 @@ namespace OpenRA.Mods.RA.Orders
|
|||||||
{
|
{
|
||||||
if (!initialized)
|
if (!initialized)
|
||||||
{
|
{
|
||||||
var rbi = Rules.Info[Building].Traits.GetOrDefault<RenderBuildingInfo>();
|
var rbi = rules.Actors[Building].Traits.GetOrDefault<RenderBuildingInfo>();
|
||||||
if (rbi == null)
|
if (rbi == null)
|
||||||
preview = new IRenderable[0];
|
preview = new IRenderable[0];
|
||||||
else
|
else
|
||||||
@@ -98,7 +100,7 @@ namespace OpenRA.Mods.RA.Orders
|
|||||||
var palette = rbi.Palette ?? (Producer.Owner != null ?
|
var palette = rbi.Palette ?? (Producer.Owner != null ?
|
||||||
rbi.PlayerPalette + Producer.Owner.InternalName : null);
|
rbi.PlayerPalette + Producer.Owner.InternalName : null);
|
||||||
|
|
||||||
preview = rbi.RenderPreview(Rules.Info[Building], wr.Palette(palette));
|
preview = rbi.RenderPreview(rules.Actors[Building], wr.Palette(palette));
|
||||||
}
|
}
|
||||||
|
|
||||||
initialized = true;
|
initialized = true;
|
||||||
@@ -110,7 +112,7 @@ namespace OpenRA.Mods.RA.Orders
|
|||||||
|
|
||||||
var res = world.WorldActor.Trait<ResourceLayer>();
|
var res = world.WorldActor.Trait<ResourceLayer>();
|
||||||
var isCloseEnough = BuildingInfo.IsCloseEnoughToBase(world, world.LocalPlayer, Building, topLeft);
|
var isCloseEnough = BuildingInfo.IsCloseEnoughToBase(world, world.LocalPlayer, Building, topLeft);
|
||||||
foreach (var t in FootprintUtils.Tiles(Building, BuildingInfo, topLeft))
|
foreach (var t in FootprintUtils.Tiles(rules, Building, BuildingInfo, topLeft))
|
||||||
cells.Add(t, isCloseEnough && world.IsCellBuildable(t, BuildingInfo) && res.GetResource(t) == null);
|
cells.Add(t, isCloseEnough && world.IsCellBuildable(t, BuildingInfo) && res.GetResource(t) == null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2012 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -57,7 +57,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
if (self.World.WorldTick - lastAttackTime > info.NotifyInterval * 25)
|
if (self.World.WorldTick - lastAttackTime > info.NotifyInterval * 25)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(self.Owner, "Speech", "BaseAttack", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", "BaseAttack", self.Owner.Country.Race);
|
||||||
|
|
||||||
if (radarPings != null)
|
if (radarPings != null)
|
||||||
radarPings.Add(() => self.Owner == self.World.LocalPlayer, self.CenterPosition, info.RadarPingColor, info.RadarPingDuration);
|
radarPings.Add(() => self.Owner == self.World.LocalPlayer, self.CenterPosition, info.RadarPingColor, info.RadarPingDuration);
|
||||||
|
|||||||
6
OpenRA.Mods.RA/Player/ClassicProductionQueue.cs
Executable file → Normal file
6
OpenRA.Mods.RA/Player/ClassicProductionQueue.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -81,7 +81,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
foreach (var p in producers.Where(p => !p.Actor.IsDisabled()))
|
foreach (var p in producers.Where(p => !p.Actor.IsDisabled()))
|
||||||
{
|
{
|
||||||
if (p.Trait.Produce(p.Actor, Rules.Info[name]))
|
if (p.Trait.Produce(p.Actor, self.World.Map.Rules.Actors[name]))
|
||||||
{
|
{
|
||||||
FinishProduction();
|
FinishProduction();
|
||||||
return true;
|
return true;
|
||||||
@@ -92,7 +92,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
public override int GetBuildTime(String unitString)
|
public override int GetBuildTime(String unitString)
|
||||||
{
|
{
|
||||||
var unit = Rules.Info[unitString];
|
var unit = self.World.Map.Rules.Actors[unitString];
|
||||||
if (unit == null || !unit.Traits.Contains<BuildableInfo>())
|
if (unit == null || !unit.Traits.Contains<BuildableInfo>())
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2012 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -48,7 +48,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
if (self.World.WorldTick - lastAttackTime > info.NotifyInterval * 25)
|
if (self.World.WorldTick - lastAttackTime > info.NotifyInterval * 25)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(self.Owner, "Speech", "HarvesterAttack", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", "HarvesterAttack", self.Owner.Country.Race);
|
||||||
|
|
||||||
if (radarPings != null)
|
if (radarPings != null)
|
||||||
radarPings.Add(() => self.Owner == self.World.LocalPlayer, self.CenterPosition, info.RadarPingColor, info.RadarPingDuration);
|
radarPings.Add(() => self.Owner == self.World.LocalPlayer, self.CenterPosition, info.RadarPingColor, info.RadarPingDuration);
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ namespace OpenRA.Mods.RA
|
|||||||
self.World.Add(playerBeacon);
|
self.World.Add(playerBeacon);
|
||||||
|
|
||||||
if (self.Owner.IsAlliedWith(self.World.RenderPlayer))
|
if (self.Owner.IsAlliedWith(self.World.RenderPlayer))
|
||||||
Sound.PlayNotification(null, info.NotificationType, info.Notification,
|
Sound.PlayNotification(self.World.Map.Rules, null, info.NotificationType, info.Notification,
|
||||||
self.World.RenderPlayer != null ? self.World.RenderPlayer.Country.Race : null);
|
self.World.RenderPlayer != null ? self.World.RenderPlayer.Country.Race : null);
|
||||||
|
|
||||||
if (radarPings != null)
|
if (radarPings != null)
|
||||||
|
|||||||
6
OpenRA.Mods.RA/Player/PlaceBuilding.cs
Executable file → Normal file
6
OpenRA.Mods.RA/Player/PlaceBuilding.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -40,7 +40,7 @@ namespace OpenRA.Mods.RA
|
|||||||
if (queue == null)
|
if (queue == null)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
var unit = Rules.Info[order.TargetString];
|
var unit = self.World.Map.Rules.Actors[order.TargetString];
|
||||||
var buildingInfo = unit.Traits.Get<BuildingInfo>();
|
var buildingInfo = unit.Traits.Get<BuildingInfo>();
|
||||||
|
|
||||||
if (order.OrderString == "LineBuild")
|
if (order.OrderString == "LineBuild")
|
||||||
@@ -92,7 +92,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
if (GetNumBuildables(self.Owner) > prevItems)
|
if (GetNumBuildables(self.Owner) > prevItems)
|
||||||
w.Add(new DelayedAction(10,
|
w.Add(new DelayedAction(10,
|
||||||
() => Sound.PlayNotification(order.Player, "Speech", "NewOptions", order.Player.Country.Race)));
|
() => Sound.PlayNotification(self.World.Map.Rules, order.Player, "Speech", "NewOptions", order.Player.Country.Race)));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
20
OpenRA.Mods.RA/Player/ProductionQueue.cs
Executable file → Normal file
20
OpenRA.Mods.RA/Player/ProductionQueue.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -135,7 +135,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
IEnumerable<ActorInfo> AllBuildables(string category)
|
IEnumerable<ActorInfo> AllBuildables(string category)
|
||||||
{
|
{
|
||||||
return Rules.Info.Values
|
return self.World.Map.Rules.Actors.Values
|
||||||
.Where( x => x.Name[ 0 ] != '^' )
|
.Where( x => x.Name[ 0 ] != '^' )
|
||||||
.Where( x => x.Traits.Contains<BuildableInfo>() )
|
.Where( x => x.Traits.Contains<BuildableInfo>() )
|
||||||
.Where( x => x.Traits.Get<BuildableInfo>().Queue == category );
|
.Where( x => x.Traits.Get<BuildableInfo>().Queue == category );
|
||||||
@@ -149,14 +149,14 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
public void PrerequisitesAvailable(string key)
|
public void PrerequisitesAvailable(string key)
|
||||||
{
|
{
|
||||||
var ps = Produceable[ Rules.Info[key] ];
|
var ps = Produceable[ self.World.Map.Rules.Actors[key] ];
|
||||||
if (!ps.Sticky)
|
if (!ps.Sticky)
|
||||||
ps.Buildable = true;
|
ps.Buildable = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void PrerequisitesUnavailable(string key)
|
public void PrerequisitesUnavailable(string key)
|
||||||
{
|
{
|
||||||
var ps = Produceable[ Rules.Info[key] ];
|
var ps = Produceable[ self.World.Map.Rules.Actors[key] ];
|
||||||
if (!ps.Sticky)
|
if (!ps.Sticky)
|
||||||
ps.Buildable = false;
|
ps.Buildable = false;
|
||||||
}
|
}
|
||||||
@@ -209,7 +209,7 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
case "StartProduction":
|
case "StartProduction":
|
||||||
{
|
{
|
||||||
var unit = Rules.Info[order.TargetString];
|
var unit = self.World.Map.Rules.Actors[order.TargetString];
|
||||||
var bi = unit.Traits.Get<BuildableInfo>();
|
var bi = unit.Traits.Get<BuildableInfo>();
|
||||||
if (bi.Queue != Info.Type)
|
if (bi.Queue != Info.Type)
|
||||||
return; /* Not built by this queue */
|
return; /* Not built by this queue */
|
||||||
@@ -243,15 +243,15 @@ namespace OpenRA.Mods.RA
|
|||||||
var isBuilding = unit.Traits.Contains<BuildingInfo>();
|
var isBuilding = unit.Traits.Contains<BuildingInfo>();
|
||||||
if (isBuilding && !hasPlayedSound)
|
if (isBuilding && !hasPlayedSound)
|
||||||
{
|
{
|
||||||
hasPlayedSound = Sound.PlayNotification(self.Owner, "Speech", Info.ReadyAudio, self.Owner.Country.Race);
|
hasPlayedSound = Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", Info.ReadyAudio, self.Owner.Country.Race);
|
||||||
}
|
}
|
||||||
else if (!isBuilding)
|
else if (!isBuilding)
|
||||||
{
|
{
|
||||||
if (BuildUnit(order.TargetString))
|
if (BuildUnit(order.TargetString))
|
||||||
Sound.PlayNotification(self.Owner, "Speech", Info.ReadyAudio, self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", Info.ReadyAudio, self.Owner.Country.Race);
|
||||||
else if (!hasPlayedSound && time > 0)
|
else if (!hasPlayedSound && time > 0)
|
||||||
{
|
{
|
||||||
hasPlayedSound = Sound.PlayNotification(self.Owner, "Speech", Info.BlockedAudio, self.Owner.Country.Race);
|
hasPlayedSound = Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", Info.BlockedAudio, self.Owner.Country.Race);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
})));
|
})));
|
||||||
@@ -274,7 +274,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
virtual public int GetBuildTime(String unitString)
|
virtual public int GetBuildTime(String unitString)
|
||||||
{
|
{
|
||||||
var unit = Rules.Info[unitString];
|
var unit = self.World.Map.Rules.Actors[unitString];
|
||||||
if (unit == null || ! unit.Traits.Contains<BuildableInfo>())
|
if (unit == null || ! unit.Traits.Contains<BuildableInfo>())
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
@@ -329,7 +329,7 @@ namespace OpenRA.Mods.RA
|
|||||||
}
|
}
|
||||||
|
|
||||||
var sp = self.TraitsImplementing<Production>().FirstOrDefault(p => p.Info.Produces.Contains(Info.Type));
|
var sp = self.TraitsImplementing<Production>().FirstOrDefault(p => p.Info.Produces.Contains(Info.Type));
|
||||||
if (sp != null && !self.IsDisabled() && sp.Produce(self, Rules.Info[name]))
|
if (sp != null && !self.IsDisabled() && sp.Produce(self, self.World.Map.Rules.Actors[name]))
|
||||||
{
|
{
|
||||||
FinishProduction();
|
FinishProduction();
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -77,7 +77,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
isPrimary = true;
|
isPrimary = true;
|
||||||
|
|
||||||
Sound.PlayNotification(self.Owner, "Speech", "PrimaryBuildingSelected", self.Owner.Country.Race);
|
Sound.PlayNotification(self.World.Map.Rules, self.Owner, "Speech", "PrimaryBuildingSelected", self.Owner.Country.Race);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA
|
|||||||
var range = FallbackRange;
|
var range = FallbackRange;
|
||||||
|
|
||||||
if (armaments.Any())
|
if (armaments.Any())
|
||||||
range = armaments.Select(a => Rules.Weapons[a.Weapon.ToLowerInvariant()].Range).Max();
|
range = armaments.Select(a => w.Map.Rules.Weapons[a.Weapon.ToLowerInvariant()].Range).Max();
|
||||||
|
|
||||||
if (range == WRange.Zero)
|
if (range == WRange.Zero)
|
||||||
return;
|
return;
|
||||||
|
|||||||
@@ -67,7 +67,7 @@ namespace OpenRA.Scripting
|
|||||||
public int BuildTime(string type)
|
public int BuildTime(string type)
|
||||||
{
|
{
|
||||||
ActorInfo ai;
|
ActorInfo ai;
|
||||||
if (!Rules.Info.TryGetValue(type, out ai))
|
if (!context.World.Map.Rules.Actors.TryGetValue(type, out ai))
|
||||||
throw new LuaException("Unknown actor type '{0}'".F(type));
|
throw new LuaException("Unknown actor type '{0}'".F(type));
|
||||||
|
|
||||||
return ai.GetBuildTime();
|
return ai.GetBuildTime();
|
||||||
@@ -77,7 +77,7 @@ namespace OpenRA.Scripting
|
|||||||
public int CruiseAltitude(string type)
|
public int CruiseAltitude(string type)
|
||||||
{
|
{
|
||||||
ActorInfo ai;
|
ActorInfo ai;
|
||||||
if (!Rules.Info.TryGetValue(type, out ai))
|
if (!context.World.Map.Rules.Actors.TryGetValue(type, out ai))
|
||||||
throw new LuaException("Unknown actor type '{0}'".F(type));
|
throw new LuaException("Unknown actor type '{0}'".F(type));
|
||||||
|
|
||||||
var pi = ai.Traits.GetOrDefault<PlaneInfo>();
|
var pi = ai.Traits.GetOrDefault<PlaneInfo>();
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -171,10 +171,10 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
public object TraitInfoOrDefault(string actorType, string className)
|
public object TraitInfoOrDefault(string actorType, string className)
|
||||||
{
|
{
|
||||||
var type = Game.modData.ObjectCreator.FindType(className);
|
var type = Game.modData.ObjectCreator.FindType(className);
|
||||||
if (type == null || !Rules.Info.ContainsKey(actorType))
|
if (type == null || !world.Map.Rules.Actors.ContainsKey(actorType))
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
return Rules.Info[actorType].Traits.GetOrDefault(type);
|
return world.Map.Rules.Actors[actorType].Traits.GetOrDefault(type);
|
||||||
}
|
}
|
||||||
|
|
||||||
[LuaGlobal]
|
[LuaGlobal]
|
||||||
@@ -202,13 +202,13 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
[LuaGlobal]
|
[LuaGlobal]
|
||||||
public void PlaySpeechNotification(Player player, string notification)
|
public void PlaySpeechNotification(Player player, string notification)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(player, "Speech", notification, player != null ? player.Country.Race : null);
|
Sound.PlayNotification(world.Map.Rules, player, "Speech", notification, player != null ? player.Country.Race : null);
|
||||||
}
|
}
|
||||||
|
|
||||||
[LuaGlobal]
|
[LuaGlobal]
|
||||||
public void PlaySoundNotification(Player player, string notification)
|
public void PlaySoundNotification(Player player, string notification)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(player, "Sounds", notification, player != null ? player.Country.Race : null);
|
Sound.PlayNotification(world.Map.Rules, player, "Sounds", notification, player != null ? player.Country.Race : null);
|
||||||
}
|
}
|
||||||
|
|
||||||
[LuaGlobal]
|
[LuaGlobal]
|
||||||
@@ -248,7 +248,7 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
[LuaGlobal]
|
[LuaGlobal]
|
||||||
public void PlayRandomMusic()
|
public void PlayRandomMusic()
|
||||||
{
|
{
|
||||||
if (!Rules.InstalledMusic.Any() || !Game.Settings.Sound.MapMusic)
|
if (!Game.Settings.Sound.MapMusic || !world.Map.Rules.InstalledMusic.Any())
|
||||||
return;
|
return;
|
||||||
Game.ConnectionStateChanged += StopMusic;
|
Game.ConnectionStateChanged += StopMusic;
|
||||||
PlayMusic();
|
PlayMusic();
|
||||||
@@ -256,7 +256,7 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
|
|
||||||
void PlayMusic()
|
void PlayMusic()
|
||||||
{
|
{
|
||||||
var track = Rules.InstalledMusic.Random(Game.CosmeticRandom);
|
var track = world.Map.Rules.InstalledMusic.Random(Game.CosmeticRandom);
|
||||||
Sound.PlayMusicThen(track.Value, PlayMusic);
|
Sound.PlayMusicThen(track.Value, PlayMusic);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -385,7 +385,7 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
|
|
||||||
ClassicProductionQueue GetSharedQueueForUnit(Player player, string unit)
|
ClassicProductionQueue GetSharedQueueForUnit(Player player, string unit)
|
||||||
{
|
{
|
||||||
var ri = Rules.Info[unit];
|
var ri = world.Map.Rules.Actors[unit];
|
||||||
|
|
||||||
var bi = ri.Traits.GetOrDefault<BuildableInfo>();
|
var bi = ri.Traits.GetOrDefault<BuildableInfo>();
|
||||||
if (bi == null)
|
if (bi == null)
|
||||||
@@ -406,7 +406,7 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
[LuaGlobal]
|
[LuaGlobal]
|
||||||
public void BuildWithPerFactoryQueue(Actor factory, string unit, double amount)
|
public void BuildWithPerFactoryQueue(Actor factory, string unit, double amount)
|
||||||
{
|
{
|
||||||
var ri = Rules.Info[unit];
|
var ri = world.Map.Rules.Actors[unit];
|
||||||
|
|
||||||
var bi = ri.Traits.GetOrDefault<BuildableInfo>();
|
var bi = ri.Traits.GetOrDefault<BuildableInfo>();
|
||||||
if (bi == null)
|
if (bi == null)
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA.Scripting
|
|||||||
public void Produce(string actorType)
|
public void Produce(string actorType)
|
||||||
{
|
{
|
||||||
ActorInfo actorInfo;
|
ActorInfo actorInfo;
|
||||||
if (!Rules.Info.TryGetValue(actorType, out actorInfo))
|
if (!self.World.Map.Rules.Actors.TryGetValue(actorType, out actorInfo))
|
||||||
throw new LuaException("Unknown actor type '{0}'".F(actorType));
|
throw new LuaException("Unknown actor type '{0}'".F(actorType));
|
||||||
|
|
||||||
self.QueueActivity(new WaitFor(() => p.Produce(self, actorInfo)));
|
self.QueueActivity(new WaitFor(() => p.Produce(self, actorInfo)));
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -76,7 +76,7 @@ namespace OpenRA.Mods.RA
|
|||||||
variantStride = info.Index.Length;
|
variantStride = info.Index.Length;
|
||||||
for (var j = 0; j < info.Variants.Length; j++)
|
for (var j = 0; j < info.Variants.Length; j++)
|
||||||
{
|
{
|
||||||
var seq = SequenceProvider.GetSequence(info.Sequence, info.Variants[j]);
|
var seq = map.SequenceProvider.GetSequence(info.Sequence, info.Variants[j]);
|
||||||
for (var i = 0; i < info.Index.Length; i++)
|
for (var i = 0; i < info.Index.Length; i++)
|
||||||
sprites[j * variantStride + i] = seq.GetSprite(i);
|
sprites[j * variantStride + i] = seq.GetSprite(i);
|
||||||
}
|
}
|
||||||
@@ -95,7 +95,7 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
var ts = Game.modData.Manifest.TileSize;
|
var ts = Game.modData.Manifest.TileSize;
|
||||||
var data = Exts.MakeArray<byte>(ts.Width * ts.Height, _ => (byte)info.ShroudColor);
|
var data = Exts.MakeArray<byte>(ts.Width * ts.Height, _ => (byte)info.ShroudColor);
|
||||||
var s = Game.modData.SheetBuilder.Add(data, ts);
|
var s = map.Rules.TileSets[map.Tileset].Data.SpriteLoader.SheetBuilder.Add(data, ts);
|
||||||
unexploredTile = new Sprite(s.sheet, s.bounds, s.offset, s.channel, info.ShroudBlend);
|
unexploredTile = new Sprite(s.sheet, s.bounds, s.offset, s.channel, info.ShroudBlend);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -30,7 +30,7 @@ namespace OpenRA.Mods.RA
|
|||||||
void SpawnUnitsForPlayer(World w, Player p, CPos sp)
|
void SpawnUnitsForPlayer(World w, Player p, CPos sp)
|
||||||
{
|
{
|
||||||
var spawnClass = p.PlayerReference.StartingUnitsClass ?? w.LobbyInfo.GlobalSettings.StartingUnitsClass;
|
var spawnClass = p.PlayerReference.StartingUnitsClass ?? w.LobbyInfo.GlobalSettings.StartingUnitsClass;
|
||||||
var unitGroup = Rules.Info["world"].Traits.WithInterface<MPStartUnitsInfo>()
|
var unitGroup = w.Map.Rules.Actors["world"].Traits.WithInterface<MPStartUnitsInfo>()
|
||||||
.Where(g => g.Class == spawnClass && g.Races != null && g.Races.Contains(p.Country.Race))
|
.Where(g => g.Class == spawnClass && g.Races != null && g.Races.Contains(p.Country.Race))
|
||||||
.RandomOrDefault(w.SharedRandom);
|
.RandomOrDefault(w.SharedRandom);
|
||||||
|
|
||||||
@@ -57,7 +57,7 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
foreach (var s in unitGroup.SupportActors)
|
foreach (var s in unitGroup.SupportActors)
|
||||||
{
|
{
|
||||||
var mi = Rules.Info[s.ToLowerInvariant()].Traits.Get<MobileInfo>();
|
var mi = w.Map.Rules.Actors[s.ToLowerInvariant()].Traits.Get<MobileInfo>();
|
||||||
var validCells = supportSpawnCells.Where(c => mi.CanEnterCell(w, c));
|
var validCells = supportSpawnCells.Where(c => mi.CanEnterCell(w, c));
|
||||||
if (!validCells.Any())
|
if (!validCells.Any())
|
||||||
throw new InvalidOperationException("No cells available to spawn starting unit {0}".F(s));
|
throw new InvalidOperationException("No cells available to spawn starting unit {0}".F(s));
|
||||||
|
|||||||
@@ -28,9 +28,9 @@ namespace OpenRA.Mods.RA
|
|||||||
this.info = info;
|
this.info = info;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void WorldLoaded(World w, WorldRenderer wr)
|
public void WorldLoaded(World world, WorldRenderer wr)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(null, "Speech", info.Notification, null);
|
Sound.PlayNotification(world.Map.Rules, null, "Speech", info.Notification, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
2
OpenRA.Mods.RA/SupportPowers/AirstrikePower.cs
Executable file → Normal file
2
OpenRA.Mods.RA/SupportPowers/AirstrikePower.cs
Executable file → Normal file
@@ -59,7 +59,7 @@ namespace OpenRA.Mods.RA
|
|||||||
var attackRotation = WRot.FromFacing(attackFacing);
|
var attackRotation = WRot.FromFacing(attackFacing);
|
||||||
var delta = new WVec(0, -1024, 0).Rotate(attackRotation);
|
var delta = new WVec(0, -1024, 0).Rotate(attackRotation);
|
||||||
|
|
||||||
var altitude = Rules.Info[info.UnitType].Traits.Get<PlaneInfo>().CruiseAltitude.Range;
|
var altitude = self.World.Map.Rules.Actors[info.UnitType].Traits.Get<PlaneInfo>().CruiseAltitude.Range;
|
||||||
var target = order.TargetLocation.CenterPosition + new WVec(0, 0, altitude);
|
var target = order.TargetLocation.CenterPosition + new WVec(0, 0, altitude);
|
||||||
var startEdge = target - (self.World.DistanceToMapEdge(target, -delta) + info.Cordon).Range * delta / 1024;
|
var startEdge = target - (self.World.DistanceToMapEdge(target, -delta) + info.Cordon).Range * delta / 1024;
|
||||||
var finishEdge = target + (self.World.DistanceToMapEdge(target, delta) + info.Cordon).Range * delta / 1024;
|
var finishEdge = target + (self.World.DistanceToMapEdge(target, delta) + info.Cordon).Range * delta / 1024;
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ namespace OpenRA.Mods.RA
|
|||||||
public override IOrderGenerator OrderGenerator(string order, SupportPowerManager manager)
|
public override IOrderGenerator OrderGenerator(string order, SupportPowerManager manager)
|
||||||
{
|
{
|
||||||
Sound.PlayToPlayer(manager.self.Owner, Info.SelectTargetSound);
|
Sound.PlayToPlayer(manager.self.Owner, Info.SelectTargetSound);
|
||||||
return new SelectTarget(order, manager, this);
|
return new SelectTarget(self.World, order, manager, this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Activate(Actor self, Order order, SupportPowerManager manager)
|
public override void Activate(Actor self, Order order, SupportPowerManager manager)
|
||||||
@@ -115,20 +115,20 @@ namespace OpenRA.Mods.RA
|
|||||||
readonly SupportPowerManager manager;
|
readonly SupportPowerManager manager;
|
||||||
readonly string order;
|
readonly string order;
|
||||||
|
|
||||||
public SelectTarget(string order, SupportPowerManager manager, ChronoshiftPower power)
|
public SelectTarget(World world, string order, SupportPowerManager manager, ChronoshiftPower power)
|
||||||
{
|
{
|
||||||
this.manager = manager;
|
this.manager = manager;
|
||||||
this.order = order;
|
this.order = order;
|
||||||
this.power = power;
|
this.power = power;
|
||||||
this.range = (power.Info as ChronoshiftPowerInfo).Range;
|
this.range = (power.Info as ChronoshiftPowerInfo).Range;
|
||||||
tile = SequenceProvider.GetSequence("overlay", "target-select").GetSprite(0);
|
tile = world.Map.SequenceProvider.GetSequence("overlay", "target-select").GetSprite(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
||||||
{
|
{
|
||||||
world.CancelInputMode();
|
world.CancelInputMode();
|
||||||
if (mi.Button == MouseButton.Left)
|
if (mi.Button == MouseButton.Left)
|
||||||
world.OrderGenerator = new SelectDestination(order, manager, power, xy);
|
world.OrderGenerator = new SelectDestination(world, order, manager, power, xy);
|
||||||
|
|
||||||
yield break;
|
yield break;
|
||||||
}
|
}
|
||||||
@@ -173,7 +173,7 @@ namespace OpenRA.Mods.RA
|
|||||||
readonly SupportPowerManager manager;
|
readonly SupportPowerManager manager;
|
||||||
readonly string order;
|
readonly string order;
|
||||||
|
|
||||||
public SelectDestination(string order, SupportPowerManager manager, ChronoshiftPower power, CPos sourceLocation)
|
public SelectDestination(World world, string order, SupportPowerManager manager, ChronoshiftPower power, CPos sourceLocation)
|
||||||
{
|
{
|
||||||
this.manager = manager;
|
this.manager = manager;
|
||||||
this.order = order;
|
this.order = order;
|
||||||
@@ -182,9 +182,9 @@ namespace OpenRA.Mods.RA
|
|||||||
this.range = (power.Info as ChronoshiftPowerInfo).Range;
|
this.range = (power.Info as ChronoshiftPowerInfo).Range;
|
||||||
|
|
||||||
var tileset = manager.self.World.TileSet.Id.ToLower();
|
var tileset = manager.self.World.TileSet.Id.ToLower();
|
||||||
validTile = SequenceProvider.GetSequence("overlay", "target-valid-{0}".F(tileset)).GetSprite(0);
|
validTile = world.Map.SequenceProvider.GetSequence("overlay", "target-valid-{0}".F(tileset)).GetSprite(0);
|
||||||
invalidTile = SequenceProvider.GetSequence("overlay", "target-invalid").GetSprite(0);
|
invalidTile = world.Map.SequenceProvider.GetSequence("overlay", "target-invalid").GetSprite(0);
|
||||||
sourceTile = SequenceProvider.GetSequence("overlay", "target-select").GetSprite(0);
|
sourceTile = world.Map.SequenceProvider.GetSequence("overlay", "target-select").GetSprite(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ namespace OpenRA.Mods.RA
|
|||||||
public override IOrderGenerator OrderGenerator(string order, SupportPowerManager manager)
|
public override IOrderGenerator OrderGenerator(string order, SupportPowerManager manager)
|
||||||
{
|
{
|
||||||
Sound.PlayToPlayer(manager.self.Owner, Info.SelectTargetSound);
|
Sound.PlayToPlayer(manager.self.Owner, Info.SelectTargetSound);
|
||||||
return new SelectTarget(order, manager, this);
|
return new SelectTarget(self.World, order, manager, this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Activate(Actor self, Order order, SupportPowerManager manager)
|
public override void Activate(Actor self, Order order, SupportPowerManager manager)
|
||||||
@@ -76,13 +76,13 @@ namespace OpenRA.Mods.RA
|
|||||||
readonly SupportPowerManager manager;
|
readonly SupportPowerManager manager;
|
||||||
readonly string order;
|
readonly string order;
|
||||||
|
|
||||||
public SelectTarget(string order, SupportPowerManager manager, IronCurtainPower power)
|
public SelectTarget(World world, string order, SupportPowerManager manager, IronCurtainPower power)
|
||||||
{
|
{
|
||||||
this.manager = manager;
|
this.manager = manager;
|
||||||
this.order = order;
|
this.order = order;
|
||||||
this.power = power;
|
this.power = power;
|
||||||
this.range = (power.Info as IronCurtainPowerInfo).Range;
|
this.range = (power.Info as IronCurtainPowerInfo).Range;
|
||||||
tile = SequenceProvider.GetSequence("overlay", "target-select").GetSprite(0);
|
tile = world.Map.SequenceProvider.GetSequence("overlay", "target-select").GetSprite(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
public IEnumerable<Order> Order(World world, CPos xy, MouseInput mi)
|
||||||
|
|||||||
4
OpenRA.Mods.RA/SupportPowers/ParatroopersPower.cs
Executable file → Normal file
4
OpenRA.Mods.RA/SupportPowers/ParatroopersPower.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -55,7 +55,7 @@ namespace OpenRA.Mods.RA
|
|||||||
flare.QueueActivity(new RemoveSelf());
|
flare.QueueActivity(new RemoveSelf());
|
||||||
}
|
}
|
||||||
|
|
||||||
var altitude = Rules.Info[info.UnitType].Traits.Get<PlaneInfo>().CruiseAltitude;
|
var altitude = self.World.Map.Rules.Actors[info.UnitType].Traits.Get<PlaneInfo>().CruiseAltitude;
|
||||||
var a = w.CreateActor(info.UnitType, new TypeDictionary
|
var a = w.CreateActor(info.UnitType, new TypeDictionary
|
||||||
{
|
{
|
||||||
new CenterPositionInit(startPos.CenterPosition + new WVec(WRange.Zero, WRange.Zero, altitude)),
|
new CenterPositionInit(startPos.CenterPosition + new WVec(WRange.Zero, WRange.Zero, altitude)),
|
||||||
|
|||||||
4
OpenRA.Mods.RA/SupportPowers/SpyPlanePower.cs
Executable file → Normal file
4
OpenRA.Mods.RA/SupportPowers/SpyPlanePower.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -30,7 +30,7 @@ namespace OpenRA.Mods.RA
|
|||||||
base.Activate(self, order, manager);
|
base.Activate(self, order, manager);
|
||||||
|
|
||||||
var enterCell = self.World.ChooseRandomEdgeCell();
|
var enterCell = self.World.ChooseRandomEdgeCell();
|
||||||
var altitude = Rules.Info["u2"].Traits.Get<PlaneInfo>().CruiseAltitude;
|
var altitude = self.World.Map.Rules.Actors["u2"].Traits.Get<PlaneInfo>().CruiseAltitude;
|
||||||
|
|
||||||
var plane = self.World.CreateActor("u2", new TypeDictionary
|
var plane = self.World.CreateActor("u2", new TypeDictionary
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -79,8 +79,8 @@ namespace OpenRA.Mods.RA
|
|||||||
|
|
||||||
public IEnumerable<IRenderable> GenerateRenderables(WorldRenderer wr)
|
public IEnumerable<IRenderable> GenerateRenderables(WorldRenderer wr)
|
||||||
{
|
{
|
||||||
var bright = SequenceProvider.GetSequence(image, "bright");
|
var bright = wr.world.Map.SequenceProvider.GetSequence(image, "bright");
|
||||||
var dim = SequenceProvider.GetSequence(image, "dim");
|
var dim = wr.world.Map.SequenceProvider.GetSequence(image, "dim");
|
||||||
|
|
||||||
var source = wr.ScreenPosition(pos);
|
var source = wr.ScreenPosition(pos);
|
||||||
var target = wr.ScreenPosition(pos + length);
|
var target = wr.ScreenPosition(pos + length);
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -38,7 +38,7 @@ namespace OpenRA.Mods.RA
|
|||||||
{
|
{
|
||||||
this.self = self;
|
this.self = self;
|
||||||
Info = info;
|
Info = info;
|
||||||
bi = Rules.Info[info.IntoActor].Traits.GetOrDefault<BuildingInfo>();
|
bi = self.World.Map.Rules.Actors[info.IntoActor].Traits.GetOrDefault<BuildingInfo>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public string VoicePhraseForOrder(Actor self, Order order)
|
public string VoicePhraseForOrder(Actor self, Order order)
|
||||||
|
|||||||
32
OpenRA.Mods.RA/Widgets/BuildPaletteWidget.cs
Executable file → Normal file
32
OpenRA.Mods.RA/Widgets/BuildPaletteWidget.cs
Executable file → Normal file
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2012 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -124,11 +124,11 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
|
|
||||||
// Play palette-open sound at the start of the activate anim (open)
|
// Play palette-open sound at the start of the activate anim (open)
|
||||||
if (paletteAnimationFrame == 1 && paletteOpen)
|
if (paletteAnimationFrame == 1 && paletteOpen)
|
||||||
Sound.PlayNotification(null, "Sounds", "BuildPaletteOpen", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "BuildPaletteOpen", null);
|
||||||
|
|
||||||
// Play palette-close sound at the start of the activate anim (close)
|
// Play palette-close sound at the start of the activate anim (close)
|
||||||
if (paletteAnimationFrame == paletteAnimationLength + -1 && !paletteOpen)
|
if (paletteAnimationFrame == paletteAnimationLength + -1 && !paletteOpen)
|
||||||
Sound.PlayNotification(null, "Sounds", "BuildPaletteClose", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "BuildPaletteClose", null);
|
||||||
|
|
||||||
// Animation is complete
|
// Animation is complete
|
||||||
if ((paletteAnimationFrame == 0 && !paletteOpen)
|
if ((paletteAnimationFrame == 0 && !paletteOpen)
|
||||||
@@ -314,7 +314,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
{
|
{
|
||||||
return mi =>
|
return mi =>
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(null, "Sounds", "TabClick", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "TabClick", null);
|
||||||
|
|
||||||
if (name != null)
|
if (name != null)
|
||||||
HandleBuildPalette(world, name, (mi.Button == MouseButton.Left));
|
HandleBuildPalette(world, name, (mi.Button == MouseButton.Left));
|
||||||
@@ -328,7 +328,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
if (mi.Button != MouseButton.Left)
|
if (mi.Button != MouseButton.Left)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
Sound.PlayNotification(null, "Sounds", "TabClick", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "TabClick", null);
|
||||||
var wasOpen = paletteOpen;
|
var wasOpen = paletteOpen;
|
||||||
paletteOpen = CurrentQueue != queue || !wasOpen;
|
paletteOpen = CurrentQueue != queue || !wasOpen;
|
||||||
CurrentQueue = queue;
|
CurrentQueue = queue;
|
||||||
@@ -337,10 +337,10 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
static string Description(string a)
|
static string Description(MapRuleset rules, string a)
|
||||||
{
|
{
|
||||||
ActorInfo ai;
|
ActorInfo ai;
|
||||||
Rules.Info.TryGetValue(a.ToLowerInvariant(), out ai);
|
rules.Actors.TryGetValue(a.ToLowerInvariant(), out ai);
|
||||||
if (ai != null && ai.Traits.Contains<TooltipInfo>())
|
if (ai != null && ai.Traits.Contains<TooltipInfo>())
|
||||||
return ai.Traits.Get<TooltipInfo>().Name;
|
return ai.Traits.Get<TooltipInfo>().Name;
|
||||||
|
|
||||||
@@ -349,7 +349,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
|
|
||||||
void HandleBuildPalette(World world, string item, bool isLmb)
|
void HandleBuildPalette(World world, string item, bool isLmb)
|
||||||
{
|
{
|
||||||
var unit = Rules.Info[item];
|
var unit = world.Map.Rules.Actors[item];
|
||||||
var producing = CurrentQueue.AllQueued().FirstOrDefault(a => a.Item == item);
|
var producing = CurrentQueue.AllQueued().FirstOrDefault(a => a.Item == item);
|
||||||
|
|
||||||
if (isLmb)
|
if (isLmb)
|
||||||
@@ -379,9 +379,9 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
var buildLimit = unit.Traits.Get<BuildableInfo>().BuildLimit;
|
var buildLimit = unit.Traits.Get<BuildableInfo>().BuildLimit;
|
||||||
|
|
||||||
if (!((buildLimit != 0) && (inWorld + queued >= buildLimit)))
|
if (!((buildLimit != 0) && (inWorld + queued >= buildLimit)))
|
||||||
Sound.PlayNotification(world.LocalPlayer, "Speech", CurrentQueue.Info.QueuedAudio, world.LocalPlayer.Country.Race);
|
Sound.PlayNotification(world.Map.Rules, world.LocalPlayer, "Speech", CurrentQueue.Info.QueuedAudio, world.LocalPlayer.Country.Race);
|
||||||
else
|
else
|
||||||
Sound.PlayNotification(world.LocalPlayer, "Speech", CurrentQueue.Info.BlockedAudio, world.LocalPlayer.Country.Race);
|
Sound.PlayNotification(world.Map.Rules, world.LocalPlayer, "Speech", CurrentQueue.Info.BlockedAudio, world.LocalPlayer.Country.Race);
|
||||||
}
|
}
|
||||||
|
|
||||||
StartProduction(world, item);
|
StartProduction(world, item);
|
||||||
@@ -393,14 +393,14 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
// instant cancel of things we havent really started yet, and things that are finished
|
// instant cancel of things we havent really started yet, and things that are finished
|
||||||
if (producing.Paused || producing.Done || producing.TotalCost == producing.RemainingCost)
|
if (producing.Paused || producing.Done || producing.TotalCost == producing.RemainingCost)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(world.LocalPlayer, "Speech", CurrentQueue.Info.CancelledAudio, world.LocalPlayer.Country.Race);
|
Sound.PlayNotification(world.Map.Rules, world.LocalPlayer, "Speech", CurrentQueue.Info.CancelledAudio, world.LocalPlayer.Country.Race);
|
||||||
int numberToCancel = Game.GetModifierKeys().HasModifier(Modifiers.Shift) ? 5 : 1;
|
int numberToCancel = Game.GetModifierKeys().HasModifier(Modifiers.Shift) ? 5 : 1;
|
||||||
|
|
||||||
world.IssueOrder(Order.CancelProduction(CurrentQueue.self, item, numberToCancel));
|
world.IssueOrder(Order.CancelProduction(CurrentQueue.self, item, numberToCancel));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(world.LocalPlayer, "Speech", CurrentQueue.Info.OnHoldAudio, world.LocalPlayer.Country.Race);
|
Sound.PlayNotification(world.Map.Rules, world.LocalPlayer, "Speech", CurrentQueue.Info.OnHoldAudio, world.LocalPlayer.Country.Race);
|
||||||
world.IssueOrder(Order.PauseProduction(CurrentQueue.self, item, true));
|
world.IssueOrder(Order.PauseProduction(CurrentQueue.self, item, true));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -463,7 +463,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
var pl = world.LocalPlayer;
|
var pl = world.LocalPlayer;
|
||||||
var p = pos.ToFloat2() - new float2(297, -3);
|
var p = pos.ToFloat2() - new float2(297, -3);
|
||||||
|
|
||||||
var info = Rules.Info[unit];
|
var info = world.Map.Rules.Actors[unit];
|
||||||
var tooltip = info.Traits.Get<TooltipInfo>();
|
var tooltip = info.Traits.Get<TooltipInfo>();
|
||||||
var buildable = info.Traits.Get<BuildableInfo>();
|
var buildable = info.Traits.Get<BuildableInfo>();
|
||||||
var cost = info.Traits.Get<ValuedInfo>().Cost;
|
var cost = info.Traits.Get<ValuedInfo>().Cost;
|
||||||
@@ -497,7 +497,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
p += new int2(5, 35);
|
p += new int2(5, 35);
|
||||||
if (!canBuildThis)
|
if (!canBuildThis)
|
||||||
{
|
{
|
||||||
var prereqs = buildable.Prerequisites.Select(Description);
|
var prereqs = buildable.Prerequisites.Select(s => Description(world.Map.Rules, s));
|
||||||
if (prereqs.Any())
|
if (prereqs.Any())
|
||||||
{
|
{
|
||||||
Game.Renderer.Fonts["Regular"].DrawText(RequiresText.F(prereqs.JoinWith(", ")), p.ToInt2(), Color.White);
|
Game.Renderer.Fonts["Regular"].DrawText(RequiresText.F(prereqs.JoinWith(", ")), p.ToInt2(), Color.White);
|
||||||
@@ -520,7 +520,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
|
|
||||||
if (toBuild != null)
|
if (toBuild != null)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(null, "Sounds", "TabClick", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "TabClick", null);
|
||||||
HandleBuildPalette(world, toBuild.Name, true);
|
HandleBuildPalette(world, toBuild.Name, true);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -531,7 +531,7 @@ namespace OpenRA.Mods.RA.Widgets
|
|||||||
// NOTE: Always return true here to prevent mouse events from passing through the sidebar and interacting with the world behind it.
|
// NOTE: Always return true here to prevent mouse events from passing through the sidebar and interacting with the world behind it.
|
||||||
bool ChangeTab(bool reverse)
|
bool ChangeTab(bool reverse)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(null, "Sounds", "TabClick", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "TabClick", null);
|
||||||
var queues = VisibleQueues.Concat(VisibleQueues);
|
var queues = VisibleQueues.Concat(VisibleQueues);
|
||||||
if (reverse)
|
if (reverse)
|
||||||
queues = queues.Reverse();
|
queues = queues.Reverse();
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -38,11 +38,15 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
Sprite[] currentSprites;
|
Sprite[] currentSprites;
|
||||||
int currentFrame;
|
int currentFrame;
|
||||||
|
|
||||||
|
readonly World world;
|
||||||
|
|
||||||
static readonly string[] AllowedExtensions = { ".shp", ".r8", "tmp", ".tem", ".des", ".sno", ".int" };
|
static readonly string[] AllowedExtensions = { ".shp", ".r8", "tmp", ".tem", ".des", ".sno", ".int" };
|
||||||
|
|
||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public AssetBrowserLogic(Widget widget, Action onExit, World world)
|
public AssetBrowserLogic(Widget widget, Action onExit, World world)
|
||||||
{
|
{
|
||||||
|
this.world = world;
|
||||||
|
|
||||||
panel = widget;
|
panel = widget;
|
||||||
assetSource = GlobalFileSystem.MountedFolders.First();
|
assetSource = GlobalFileSystem.MountedFolders.First();
|
||||||
|
|
||||||
@@ -192,7 +196,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
return false;
|
return false;
|
||||||
|
|
||||||
currentFilename = filename;
|
currentFilename = filename;
|
||||||
currentSprites = Game.modData.SpriteLoader.LoadAllSprites(filename);
|
currentSprites = world.Map.Rules.TileSets[world.Map.Tileset].Data.SpriteLoader.LoadAllSprites(filename);
|
||||||
currentFrame = 0;
|
currentFrame = 0;
|
||||||
frameSlider.MaximumValue = (float)currentSprites.Length - 1;
|
frameSlider.MaximumValue = (float)currentSprites.Length - 1;
|
||||||
frameSlider.Ticks = currentSprites.Length;
|
frameSlider.Ticks = currentSprites.Length;
|
||||||
|
|||||||
@@ -20,6 +20,8 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
{
|
{
|
||||||
public class IngameChatLogic
|
public class IngameChatLogic
|
||||||
{
|
{
|
||||||
|
readonly World world;
|
||||||
|
|
||||||
readonly ContainerWidget chatOverlay;
|
readonly ContainerWidget chatOverlay;
|
||||||
readonly ChatDisplayWidget chatOverlayDisplay;
|
readonly ChatDisplayWidget chatOverlayDisplay;
|
||||||
|
|
||||||
@@ -35,6 +37,8 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public IngameChatLogic(Widget widget, OrderManager orderManager, World world)
|
public IngameChatLogic(Widget widget, OrderManager orderManager, World world)
|
||||||
{
|
{
|
||||||
|
this.world = world;
|
||||||
|
|
||||||
chatTraits = world.WorldActor.TraitsImplementing<INotifyChat>().ToList();
|
chatTraits = world.WorldActor.TraitsImplementing<INotifyChat>().ToList();
|
||||||
|
|
||||||
var players = world.Players.Where(p => p != world.LocalPlayer && !p.NonCombatant && !p.IsBot);
|
var players = world.Players.Where(p => p != world.LocalPlayer && !p.NonCombatant && !p.IsBot);
|
||||||
@@ -161,7 +165,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
if (scrolledToBottom)
|
if (scrolledToBottom)
|
||||||
chatScrollPanel.ScrollToBottom();
|
chatScrollPanel.ScrollToBottom();
|
||||||
|
|
||||||
Sound.PlayNotification(null, "Sounds", "ChatLine", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "ChatLine", null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2013 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -18,9 +18,9 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
{
|
{
|
||||||
public class IngameChromeLogic
|
public class IngameChromeLogic
|
||||||
{
|
{
|
||||||
Widget gameRoot;
|
readonly Widget gameRoot;
|
||||||
Widget playerRoot;
|
readonly Widget playerRoot;
|
||||||
World world;
|
readonly World world;
|
||||||
|
|
||||||
[ObjectCreator.UseCtor]
|
[ObjectCreator.UseCtor]
|
||||||
public IngameChromeLogic(World world)
|
public IngameChromeLogic(World world)
|
||||||
@@ -149,7 +149,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
.Any(a => a.Actor.Owner == world.LocalPlayer && a.Trait.IsActive);
|
.Any(a => a.Actor.Owner == world.LocalPlayer && a.Trait.IsActive);
|
||||||
|
|
||||||
if (radarActive != cachedRadarActive)
|
if (radarActive != cachedRadarActive)
|
||||||
Sound.PlayNotification(null, "Sounds", (radarActive ? "RadarUp" : "RadarDown"), null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", (radarActive ? "RadarUp" : "RadarDown"), null);
|
||||||
cachedRadarActive = radarActive;
|
cachedRadarActive = radarActive;
|
||||||
|
|
||||||
// Switch to observer mode after win/loss
|
// Switch to observer mode after win/loss
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
widget.Get<ButtonWidget>("MUSIC").OnClick = () =>
|
widget.Get<ButtonWidget>("MUSIC").OnClick = () =>
|
||||||
{
|
{
|
||||||
widget.Visible = false;
|
widget.Visible = false;
|
||||||
Ui.OpenWindow("MUSIC_PANEL", new WidgetArgs { { "onExit", () => { widget.Visible = true; } } });
|
MusicPlayerLogic.OpenWindow(world, () => { widget.Visible = true; });
|
||||||
};
|
};
|
||||||
widget.Get<ButtonWidget>("RESUME").OnClick = () => onExit();
|
widget.Get<ButtonWidget>("RESUME").OnClick = () => onExit();
|
||||||
|
|
||||||
@@ -82,7 +82,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
|
|
||||||
void LeaveGame(World world)
|
void LeaveGame(World world)
|
||||||
{
|
{
|
||||||
Sound.PlayNotification(null, "Speech", "Leave", world.LocalPlayer == null ? null : world.LocalPlayer.Country.Race);
|
Sound.PlayNotification(world.Map.Rules, null, "Speech", "Leave", world.LocalPlayer == null ? null : world.LocalPlayer.Country.Race);
|
||||||
Game.Disconnect();
|
Game.Disconnect();
|
||||||
Ui.CloseWindow();
|
Ui.CloseWindow();
|
||||||
Game.LoadShellMap();
|
Game.LoadShellMap();
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
#region Copyright & License Information
|
#region Copyright & License Information
|
||||||
/*
|
/*
|
||||||
* Copyright 2007-2011 The OpenRA Developers (see AUTHORS)
|
* Copyright 2007-2014 The OpenRA Developers (see AUTHORS)
|
||||||
* This file is part of OpenRA, which is free software. It is made
|
* 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
|
* available to you under the terms of the GNU General Public License
|
||||||
* as published by the Free Software Foundation. For more information,
|
* as published by the Free Software Foundation. For more information,
|
||||||
@@ -29,6 +29,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
readonly Action onExit;
|
readonly Action onExit;
|
||||||
readonly OrderManager orderManager;
|
readonly OrderManager orderManager;
|
||||||
readonly bool skirmishMode;
|
readonly bool skirmishMode;
|
||||||
|
readonly World world;
|
||||||
|
|
||||||
enum PanelType { Players, Options, Kick, ForceStart }
|
enum PanelType { Players, Options, Kick, ForceStart }
|
||||||
PanelType panel = PanelType.Players;
|
PanelType panel = PanelType.Players;
|
||||||
@@ -98,6 +99,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
this.onStart = onStart;
|
this.onStart = onStart;
|
||||||
this.onExit = onExit;
|
this.onExit = onExit;
|
||||||
this.skirmishMode = skirmishMode;
|
this.skirmishMode = skirmishMode;
|
||||||
|
this.world = world;
|
||||||
|
|
||||||
Game.LobbyInfoChanged += UpdateCurrentMap;
|
Game.LobbyInfoChanged += UpdateCurrentMap;
|
||||||
Game.LobbyInfoChanged += UpdatePlayerList;
|
Game.LobbyInfoChanged += UpdatePlayerList;
|
||||||
@@ -132,7 +134,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
colorPreview = lobby.Get<ColorPreviewManagerWidget>("COLOR_MANAGER");
|
colorPreview = lobby.Get<ColorPreviewManagerWidget>("COLOR_MANAGER");
|
||||||
colorPreview.Color = Game.Settings.Player.Color;
|
colorPreview.Color = Game.Settings.Player.Color;
|
||||||
|
|
||||||
countryNames = Rules.Info["world"].Traits.WithInterface<CountryInfo>()
|
countryNames = world.Map.Rules.Actors["world"].Traits.WithInterface<CountryInfo>()
|
||||||
.Where(c => c.Selectable)
|
.Where(c => c.Selectable)
|
||||||
.ToDictionary(a => a.Race, a => a.Name);
|
.ToDictionary(a => a.Race, a => a.Name);
|
||||||
countryNames.Add("random", "Any");
|
countryNames.Add("random", "Any");
|
||||||
@@ -170,7 +172,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
slotsButton.IsDisabled = () => configurationDisabled() || panel != PanelType.Players ||
|
slotsButton.IsDisabled = () => configurationDisabled() || panel != PanelType.Players ||
|
||||||
!orderManager.LobbyInfo.Slots.Values.Any(s => s.AllowBots || !s.LockTeam);
|
!orderManager.LobbyInfo.Slots.Values.Any(s => s.AllowBots || !s.LockTeam);
|
||||||
|
|
||||||
var botNames = Rules.Info["player"].Traits.WithInterface<IBotInfo>().Select(t => t.Name);
|
var botNames = world.Map.Rules.Actors["player"].Traits.WithInterface<IBotInfo>().Select(t => t.Name);
|
||||||
slotsButton.OnMouseDown = _ =>
|
slotsButton.OnMouseDown = _ =>
|
||||||
{
|
{
|
||||||
var options = new Dictionary<string, IEnumerable<DropDownOption>>();
|
var options = new Dictionary<string, IEnumerable<DropDownOption>>();
|
||||||
@@ -375,7 +377,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
};
|
};
|
||||||
|
|
||||||
Func<string, string> className = c => classNames.ContainsKey(c) ? classNames[c] : c;
|
Func<string, string> className = c => classNames.ContainsKey(c) ? classNames[c] : c;
|
||||||
var classes = Rules.Info["world"].Traits.WithInterface<MPStartUnitsInfo>()
|
var classes = world.Map.Rules.Actors["world"].Traits.WithInterface<MPStartUnitsInfo>()
|
||||||
.Select(a => a.Class).Distinct();
|
.Select(a => a.Class).Distinct();
|
||||||
|
|
||||||
startingUnits.IsDisabled = () => Map.Status != MapStatus.Available || !Map.Map.Options.ConfigurableStartingUnits || configurationDisabled();
|
startingUnits.IsDisabled = () => Map.Status != MapStatus.Available || !Map.Map.Options.ConfigurableStartingUnits || configurationDisabled();
|
||||||
@@ -409,7 +411,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
startingCash.GetText = () => Map.Status != MapStatus.Available || Map.Map.Options.StartingCash.HasValue ? "Not Available" : "${0}".F(orderManager.LobbyInfo.GlobalSettings.StartingCash);
|
startingCash.GetText = () => Map.Status != MapStatus.Available || Map.Map.Options.StartingCash.HasValue ? "Not Available" : "${0}".F(orderManager.LobbyInfo.GlobalSettings.StartingCash);
|
||||||
startingCash.OnMouseDown = _ =>
|
startingCash.OnMouseDown = _ =>
|
||||||
{
|
{
|
||||||
var options = Rules.Info["player"].Traits.Get<PlayerResourcesInfo>().SelectableCash.Select(c => new DropDownOption
|
var options = world.Map.Rules.Actors["player"].Traits.Get<PlayerResourcesInfo>().SelectableCash.Select(c => new DropDownOption
|
||||||
{
|
{
|
||||||
Title = "${0}".F(c),
|
Title = "${0}".F(c),
|
||||||
IsSelected = () => orderManager.LobbyInfo.GlobalSettings.StartingCash == c,
|
IsSelected = () => orderManager.LobbyInfo.GlobalSettings.StartingCash == c,
|
||||||
@@ -481,7 +483,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
|
|
||||||
var musicButton = lobby.GetOrNull<ButtonWidget>("MUSIC_BUTTON");
|
var musicButton = lobby.GetOrNull<ButtonWidget>("MUSIC_BUTTON");
|
||||||
if (musicButton != null)
|
if (musicButton != null)
|
||||||
musicButton.OnClick = () => Ui.OpenWindow("MUSIC_PANEL", new WidgetArgs { { "onExit", DoNothing } });
|
musicButton.OnClick = () => MusicPlayerLogic.OpenWindow(world);
|
||||||
|
|
||||||
var settingsButton = lobby.GetOrNull<ButtonWidget>("SETTINGS_BUTTON");
|
var settingsButton = lobby.GetOrNull<ButtonWidget>("SETTINGS_BUTTON");
|
||||||
if (settingsButton != null)
|
if (settingsButton != null)
|
||||||
@@ -499,7 +501,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
Game.LobbyInfoChanged += WidgetUtils.Once(() =>
|
Game.LobbyInfoChanged += WidgetUtils.Once(() =>
|
||||||
{
|
{
|
||||||
var slot = orderManager.LobbyInfo.FirstEmptyBotSlot();
|
var slot = orderManager.LobbyInfo.FirstEmptyBotSlot();
|
||||||
var bot = Rules.Info["player"].Traits.WithInterface<IBotInfo>().Select(t => t.Name).FirstOrDefault();
|
var bot = world.Map.Rules.Actors["player"].Traits.WithInterface<IBotInfo>().Select(t => t.Name).FirstOrDefault();
|
||||||
var botController = orderManager.LobbyInfo.Clients.FirstOrDefault(c => c.IsAdmin);
|
var botController = orderManager.LobbyInfo.Clients.FirstOrDefault(c => c.IsAdmin);
|
||||||
if (slot != null && bot != null)
|
if (slot != null && bot != null)
|
||||||
orderManager.IssueOrder(Order.Command("slot_bot {0} {1} {2}".F(slot, botController.Index, bot)));
|
orderManager.IssueOrder(Order.Command("slot_bot {0} {1} {2}".F(slot, botController.Index, bot)));
|
||||||
@@ -542,7 +544,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
if (scrolledToBottom)
|
if (scrolledToBottom)
|
||||||
chatPanel.ScrollToBottom();
|
chatPanel.ScrollToBottom();
|
||||||
|
|
||||||
Sound.PlayNotification(null, "Sounds", "ChatLine", null);
|
Sound.PlayNotification(world.Map.Rules, null, "Sounds", "ChatLine", null);
|
||||||
}
|
}
|
||||||
|
|
||||||
void UpdateCurrentMap()
|
void UpdateCurrentMap()
|
||||||
@@ -559,7 +561,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
orderManager.IssueOrder(Order.Command("state {0}".F(Session.ClientState.NotReady)));
|
orderManager.IssueOrder(Order.Command("state {0}".F(Session.ClientState.NotReady)));
|
||||||
|
|
||||||
// Restore default starting cash if the last map set it to something invalid
|
// Restore default starting cash if the last map set it to something invalid
|
||||||
var pri = Rules.Info["player"].Traits.Get<PlayerResourcesInfo>();
|
var pri = world.Map.Rules.Actors["player"].Traits.Get<PlayerResourcesInfo>();
|
||||||
if (!Map.Map.Options.StartingCash.HasValue && !pri.SelectableCash.Contains(orderManager.LobbyInfo.GlobalSettings.StartingCash))
|
if (!Map.Map.Options.StartingCash.HasValue && !pri.SelectableCash.Contains(orderManager.LobbyInfo.GlobalSettings.StartingCash))
|
||||||
orderManager.IssueOrder(Order.Command("startingcash {0}".F(pri.DefaultCash)));
|
orderManager.IssueOrder(Order.Command("startingcash {0}".F(pri.DefaultCash)));
|
||||||
}
|
}
|
||||||
@@ -588,7 +590,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
template = emptySlotTemplate.Clone();
|
template = emptySlotTemplate.Clone();
|
||||||
|
|
||||||
if (Game.IsHost)
|
if (Game.IsHost)
|
||||||
LobbyUtils.SetupEditableSlotWidget(template, slot, client, orderManager);
|
LobbyUtils.SetupEditableSlotWidget(template, slot, client, orderManager, world.Map.Rules);
|
||||||
else
|
else
|
||||||
LobbyUtils.SetupSlotWidget(template, slot, client);
|
LobbyUtils.SetupSlotWidget(template, slot, client);
|
||||||
|
|
||||||
@@ -607,7 +609,7 @@ namespace OpenRA.Mods.RA.Widgets.Logic
|
|||||||
LobbyUtils.SetupClientWidget(template, slot, client, orderManager, client.Bot == null);
|
LobbyUtils.SetupClientWidget(template, slot, client, orderManager, client.Bot == null);
|
||||||
|
|
||||||
if (client.Bot != null)
|
if (client.Bot != null)
|
||||||
LobbyUtils.SetupEditableSlotWidget(template, slot, client, orderManager);
|
LobbyUtils.SetupEditableSlotWidget(template, slot, client, orderManager, world.Map.Rules);
|
||||||
else
|
else
|
||||||
LobbyUtils.SetupEditableNameWidget(template, slot, client, orderManager);
|
LobbyUtils.SetupEditableNameWidget(template, slot, client, orderManager);
|
||||||
|
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user