Move map configuration to rules.

This commit is contained in:
Paul Chote
2016-02-29 22:34:20 +00:00
parent 5b2bf5b284
commit d4f8fe1666
17 changed files with 102 additions and 76 deletions

View File

@@ -56,19 +56,6 @@ namespace OpenRA
} }
} }
public class MapOptions
{
public string TechLevel;
public string[] Difficulties = { };
public bool? ShortGame;
public void UpdateServerSettings(Session.Global settings)
{
if (ShortGame.HasValue)
settings.ShortGame = ShortGame.Value;
}
}
public class MapVideos public class MapVideos
{ {
public string BackgroundInfo; public string BackgroundInfo;
@@ -122,18 +109,6 @@ namespace OpenRA
return SubCellOffsets[(int)subCell]; return SubCellOffsets[(int)subCell];
} }
[FieldLoader.LoadUsing("LoadOptions")] public MapOptions Options;
static object LoadOptions(MiniYaml y)
{
var options = new MapOptions();
var nodesDict = y.ToDictionary();
if (nodesDict.ContainsKey("Options"))
FieldLoader.Load(options, nodesDict["Options"]);
return options;
}
[FieldLoader.LoadUsing("LoadVideos")] public MapVideos Videos; [FieldLoader.LoadUsing("LoadVideos")] public MapVideos Videos;
static object LoadVideos(MiniYaml y) static object LoadVideos(MiniYaml y)
@@ -253,7 +228,6 @@ namespace OpenRA
MapSize = new int2(size); MapSize = new int2(size);
Tileset = tileset.Id; Tileset = tileset.Id;
Videos = new MapVideos(); Videos = new MapVideos();
Options = new MapOptions();
MapResources = Exts.Lazy(() => new CellLayer<ResourceTile>(Grid.Type, size)); MapResources = Exts.Lazy(() => new CellLayer<ResourceTile>(Grid.Type, size));
@@ -495,9 +469,6 @@ namespace OpenRA
} }
root.Add(new MiniYamlNode("Videos", FieldSaver.SaveDifferences(Videos, new MapVideos()))); root.Add(new MiniYamlNode("Videos", FieldSaver.SaveDifferences(Videos, new MapVideos())));
root.Add(new MiniYamlNode("Options", FieldSaver.SaveDifferences(Options, new MapOptions())));
root.Add(new MiniYamlNode("Players", null, PlayerDefinitions)); root.Add(new MiniYamlNode("Players", null, PlayerDefinitions));
root.Add(new MiniYamlNode("Actors", null, ActorDefinitions)); root.Add(new MiniYamlNode("Actors", null, ActorDefinitions));

View File

@@ -190,7 +190,7 @@ namespace OpenRA.Network
public bool Fog = true; public bool Fog = true;
public bool AllyBuildRadius = true; public bool AllyBuildRadius = true;
public int StartingCash = 5000; public int StartingCash = 5000;
public string TechLevel = "none"; public string TechLevel;
public string StartingUnitsClass; public string StartingUnitsClass;
public string GameSpeedType = "default"; public string GameSpeedType = "default";
public bool ShortGame = true; public bool ShortGame = true;

View File

@@ -734,6 +734,7 @@
<Compile Include="UtilityCommands\ResizeMapCommand.cs" /> <Compile Include="UtilityCommands\ResizeMapCommand.cs" />
<Compile Include="Traits\World\MapCreeps.cs" /> <Compile Include="Traits\World\MapCreeps.cs" />
<Compile Include="Traits\World\MapBuildRadius.cs" /> <Compile Include="Traits\World\MapBuildRadius.cs" />
<Compile Include="Traits\World\MapOptions.cs" />
</ItemGroup> </ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" /> <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<PropertyGroup> <PropertyGroup>

View File

@@ -348,7 +348,6 @@ namespace OpenRA.Mods.Common.Server
var oldSlots = server.LobbyInfo.Slots.Keys.ToArray(); var oldSlots = server.LobbyInfo.Slots.Keys.ToArray();
LoadMap(server); LoadMap(server);
SetDefaultDifficulty(server);
// Reset client states // Reset client states
foreach (var c in server.LobbyInfo.Clients) foreach (var c in server.LobbyInfo.Clients)
@@ -587,19 +586,23 @@ namespace OpenRA.Mods.Common.Server
{ "difficulty", { "difficulty",
s => s =>
{ {
if (!server.Map.Options.Difficulties.Any())
return true;
if (!client.IsAdmin) if (!client.IsAdmin)
{ {
server.SendOrderTo(conn, "Message", "Only the host can set that option."); server.SendOrderTo(conn, "Message", "Only the host can set that option.");
return true; return true;
} }
if (s != null && !server.Map.Options.Difficulties.Contains(s)) var mapOptions = server.Map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>();
if (mapOptions.DifficultyLocked || !mapOptions.Difficulties.Any())
{
server.SendOrderTo(conn, "Message", "Map has disabled difficulty configuration.");
return true;
}
if (s != null && !mapOptions.Difficulties.Contains(s))
{ {
server.SendOrderTo(conn, "Message", "Invalid difficulty selected: {0}".F(s)); server.SendOrderTo(conn, "Message", "Invalid difficulty selected: {0}".F(s));
server.SendOrderTo(conn, "Message", "Supported values: {0}".F(server.Map.Options.Difficulties.JoinWith(", "))); server.SendOrderTo(conn, "Message", "Supported values: {0}".F(mapOptions.Difficulties.JoinWith(", ")));
return true; return true;
} }
@@ -683,7 +686,8 @@ namespace OpenRA.Mods.Common.Server
return true; return true;
} }
if (server.Map.Options.TechLevel != null) var mapOptions = server.Map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>();
if (mapOptions.TechLevelLocked)
{ {
server.SendOrderTo(conn, "Message", "Map has disabled Tech configuration."); server.SendOrderTo(conn, "Message", "Map has disabled Tech configuration.");
return true; return true;
@@ -939,7 +943,8 @@ namespace OpenRA.Mods.Common.Server
return true; return true;
} }
if (server.Map.Options.ShortGame.HasValue) var mapOptions = server.Map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>();
if (mapOptions.ShortGameLocked)
{ {
server.SendOrderTo(conn, "Message", "Map has disabled short game configuration."); server.SendOrderTo(conn, "Message", "Map has disabled short game configuration.");
return true; return true;
@@ -990,7 +995,6 @@ namespace OpenRA.Mods.Common.Server
public void ServerStarted(S server) public void ServerStarted(S server)
{ {
LoadMap(server); LoadMap(server);
SetDefaultDifficulty(server);
} }
static Session.Slot MakeSlotFromPlayerReference(PlayerReference pr) static Session.Slot MakeSlotFromPlayerReference(PlayerReference pr)
@@ -1039,19 +1043,10 @@ namespace OpenRA.Mods.Common.Server
var mapBuildRadius = server.Map.Rules.Actors["world"].TraitInfoOrDefault<MapBuildRadiusInfo>(); var mapBuildRadius = server.Map.Rules.Actors["world"].TraitInfoOrDefault<MapBuildRadiusInfo>();
gs.AllyBuildRadius = mapBuildRadius != null && mapBuildRadius.AllyBuildRadiusEnabled; gs.AllyBuildRadius = mapBuildRadius != null && mapBuildRadius.AllyBuildRadiusEnabled;
server.Map.Options.UpdateServerSettings(server.LobbyInfo.GlobalSettings); var mapOptions = server.Map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>();
} gs.ShortGame = mapOptions.ShortGameEnabled;
gs.TechLevel = mapOptions.TechLevel;
static void SetDefaultDifficulty(S server) gs.Difficulty = mapOptions.Difficulty ?? mapOptions.Difficulties.FirstOrDefault();
{
if (!server.Map.Options.Difficulties.Any())
{
server.LobbyInfo.GlobalSettings.Difficulty = null;
return;
}
if (!server.Map.Options.Difficulties.Contains(server.LobbyInfo.GlobalSettings.Difficulty))
server.LobbyInfo.GlobalSettings.Difficulty = server.Map.Options.Difficulties.First();
} }
static HSLColor SanitizePlayerColor(S server, HSLColor askedColor, int playerIndex, Connection connectionToEcho = null) static HSLColor SanitizePlayerColor(S server, HSLColor askedColor, int playerIndex, Connection connectionToEcho = null)

View File

@@ -40,8 +40,7 @@ namespace OpenRA.Mods.Common.Traits
public ProvidesTechPrerequisite(ProvidesTechPrerequisiteInfo info, ActorInitializer init) public ProvidesTechPrerequisite(ProvidesTechPrerequisiteInfo info, ActorInitializer init)
{ {
this.info = info; this.info = info;
var tech = init.World.Map.Options.TechLevel ?? init.World.LobbyInfo.GlobalSettings.TechLevel; enabled = info.Name == init.World.LobbyInfo.GlobalSettings.TechLevel;
enabled = info.Name == tech;
} }
} }
} }

View File

@@ -0,0 +1,43 @@
#region Copyright & License Information
/*
* Copyright 2007-2016 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, either version 3 of
* the License, or (at your option) any later version. For more
* information, see COPYING.
*/
#endregion
using System.Collections.Generic;
using OpenRA.Traits;
namespace OpenRA.Mods.Common.Traits
{
[Desc("Controls the map difficulty, tech level, and short game lobby options.")]
public class MapOptionsInfo : TraitInfo<MapOptions>
{
[Desc("Default value of the short game checkbox in the lobby.")]
public readonly bool ShortGameEnabled = true;
[Desc("Prevent the short game enabled state from being changed in the lobby.")]
public readonly bool ShortGameLocked = false;
[Desc("Default tech level.")]
public readonly string TechLevel = "Unrestricted";
[Desc("Prevent the tech level from being changed in the lobby.")]
public readonly bool TechLevelLocked = false;
[Desc("Difficulty levels supported by the map.")]
public readonly string[] Difficulties = { };
[Desc("Default difficulty level.")]
public readonly string Difficulty = null;
[Desc("Prevent the difficulty from being changed in the lobby.")]
public readonly bool DifficultyLocked = false;
}
public class MapOptions { }
}

View File

@@ -406,8 +406,11 @@ namespace OpenRA.Mods.Common.Widgets.Logic
var shortGame = optionsBin.GetOrNull<CheckboxWidget>("SHORTGAME_CHECKBOX"); var shortGame = optionsBin.GetOrNull<CheckboxWidget>("SHORTGAME_CHECKBOX");
if (shortGame != null) if (shortGame != null)
{ {
var shortGameLocked = new CachedTransform<Map, bool>(
map => map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>().ShortGameLocked);
shortGame.IsChecked = () => orderManager.LobbyInfo.GlobalSettings.ShortGame; shortGame.IsChecked = () => orderManager.LobbyInfo.GlobalSettings.ShortGame;
shortGame.IsDisabled = () => configurationDisabled() || Map.Options.ShortGame.HasValue; shortGame.IsDisabled = () => configurationDisabled() || shortGameLocked.Update(Map);
shortGame.OnClick = () => orderManager.IssueOrder(Order.Command( shortGame.OnClick = () => orderManager.IssueOrder(Order.Command(
"shortgame {0}".F(!orderManager.LobbyInfo.GlobalSettings.ShortGame))); "shortgame {0}".F(!orderManager.LobbyInfo.GlobalSettings.ShortGame)));
} }
@@ -415,12 +418,15 @@ namespace OpenRA.Mods.Common.Widgets.Logic
var difficulty = optionsBin.GetOrNull<DropDownButtonWidget>("DIFFICULTY_DROPDOWNBUTTON"); var difficulty = optionsBin.GetOrNull<DropDownButtonWidget>("DIFFICULTY_DROPDOWNBUTTON");
if (difficulty != null) if (difficulty != null)
{ {
difficulty.IsVisible = () => Map != null && Map.Options.Difficulties.Any(); var mapOptions = new CachedTransform<Map, MapOptionsInfo>(
difficulty.IsDisabled = configurationDisabled; map => map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>());
difficulty.IsVisible = () => Map != null && mapOptions.Update(Map).Difficulties.Any();
difficulty.IsDisabled = () => configurationDisabled() || mapOptions.Update(Map).DifficultyLocked;
difficulty.GetText = () => orderManager.LobbyInfo.GlobalSettings.Difficulty; difficulty.GetText = () => orderManager.LobbyInfo.GlobalSettings.Difficulty;
difficulty.OnMouseDown = _ => difficulty.OnMouseDown = _ =>
{ {
var options = Map.Options.Difficulties.Select(d => new DropDownOption var options = mapOptions.Update(Map).Difficulties.Select(d => new DropDownOption
{ {
Title = d, Title = d,
IsSelected = () => orderManager.LobbyInfo.GlobalSettings.Difficulty == d, IsSelected = () => orderManager.LobbyInfo.GlobalSettings.Difficulty == d,
@@ -514,19 +520,23 @@ namespace OpenRA.Mods.Common.Widgets.Logic
var techLevel = optionsBin.GetOrNull<DropDownButtonWidget>("TECHLEVEL_DROPDOWNBUTTON"); var techLevel = optionsBin.GetOrNull<DropDownButtonWidget>("TECHLEVEL_DROPDOWNBUTTON");
if (techLevel != null) if (techLevel != null)
{ {
var techTraits = modRules.Actors["player"].TraitInfos<ProvidesTechPrerequisiteInfo>().ToList(); var mapOptions = new CachedTransform<Map, MapOptionsInfo>(
techLevel.IsVisible = () => techTraits.Count > 0; map => map.Rules.Actors["world"].TraitInfo<MapOptionsInfo>());
var techLevels = new CachedTransform<Map, List<ProvidesTechPrerequisiteInfo>>(
map => map.Rules.Actors["player"].TraitInfos<ProvidesTechPrerequisiteInfo>().ToList());
techLevel.IsVisible = () => Map != null && techLevels.Update(Map).Any();
var techLevelDescription = optionsBin.GetOrNull<LabelWidget>("TECHLEVEL_DESC"); var techLevelDescription = optionsBin.GetOrNull<LabelWidget>("TECHLEVEL_DESC");
if (techLevelDescription != null) if (techLevelDescription != null)
techLevelDescription.IsVisible = () => techTraits.Count > 0; techLevelDescription.IsVisible = techLevel.IsVisible;
techLevel.IsDisabled = () => configurationDisabled() || Map.Options.TechLevel != null || techTraits.Count <= 1; techLevel.IsDisabled = () => configurationDisabled() || mapOptions.Update(Map).TechLevelLocked;
techLevel.GetText = () => MapPreview.Status != MapStatus.Available || techLevel.GetText = () => MapPreview.Status != MapStatus.Available ||
Map == null || Map.Options.TechLevel != null ? "Not Available" : "{0}".F(orderManager.LobbyInfo.GlobalSettings.TechLevel); Map == null || mapOptions.Update(Map).TechLevelLocked ? "Not Available" : "{0}".F(orderManager.LobbyInfo.GlobalSettings.TechLevel);
techLevel.OnMouseDown = _ => techLevel.OnMouseDown = _ =>
{ {
var options = techTraits.Select(c => new DropDownOption var options = techLevels.Update(Map).Select(c => new DropDownOption
{ {
Title = "{0}".F(c.Name), Title = "{0}".F(c.Name),
IsSelected = () => orderManager.LobbyInfo.GlobalSettings.TechLevel == c.Name, IsSelected = () => orderManager.LobbyInfo.GlobalSettings.TechLevel == c.Name,

View File

@@ -15,6 +15,7 @@ using System.IO;
using System.Linq; using System.Linq;
using System.Threading; using System.Threading;
using OpenRA.Graphics; using OpenRA.Graphics;
using OpenRA.Mods.Common.Traits;
using OpenRA.Network; using OpenRA.Network;
using OpenRA.Primitives; using OpenRA.Primitives;
using OpenRA.Widgets; using OpenRA.Widgets;
@@ -177,7 +178,18 @@ namespace OpenRA.Mods.Common.Widgets.Logic
selectedMapPreview = preview; selectedMapPreview = preview;
// Cache the rules on a background thread to avoid jank // Cache the rules on a background thread to avoid jank
new Thread(() => selectedMap.PreloadRules()).Start(); var difficultyDisabled = true;
var difficulties = new string[0];
new Thread(() =>
{
selectedMap.PreloadRules();
var mapOptions = selectedMap.Rules.Actors["world"].TraitInfo<MapOptionsInfo>();
difficulty = mapOptions.Difficulty ?? mapOptions.Difficulties.FirstOrDefault();
difficulties = mapOptions.Difficulties;
difficultyDisabled = mapOptions.DifficultyLocked || mapOptions.Difficulties.Length <= 1;
}).Start();
var briefingVideo = selectedMap.Videos.Briefing; var briefingVideo = selectedMap.Videos.Briefing;
var briefingVideoVisible = briefingVideo != null; var briefingVideoVisible = briefingVideo != null;
@@ -204,13 +216,11 @@ namespace OpenRA.Mods.Common.Widgets.Logic
if (difficultyButton != null) if (difficultyButton != null)
{ {
difficultyButton.IsDisabled = () => !selectedMap.Options.Difficulties.Any(); difficultyButton.IsDisabled = () => difficultyDisabled;
difficulty = selectedMap.Options.Difficulties.FirstOrDefault();
difficultyButton.GetText = () => difficulty ?? "Normal"; difficultyButton.GetText = () => difficulty ?? "Normal";
difficultyButton.OnMouseDown = _ => difficultyButton.OnMouseDown = _ =>
{ {
var options = selectedMap.Options.Difficulties.Select(d => new DropDownOption var options = difficulties.Select(d => new DropDownOption
{ {
Title = d, Title = d,
IsSelected = () => difficulty == d, IsSelected = () => difficulty == d,

View File

@@ -236,7 +236,6 @@ namespace OpenRA.Mods.TS.UtilityCommands
map.MapTiles = Exts.Lazy(() => new CellLayer<TerrainTile>(map.Grid.Type, size)); map.MapTiles = Exts.Lazy(() => new CellLayer<TerrainTile>(map.Grid.Type, size));
map.MapHeight = Exts.Lazy(() => new CellLayer<byte>(map.Grid.Type, size)); map.MapHeight = Exts.Lazy(() => new CellLayer<byte>(map.Grid.Type, size));
map.Options = new MapOptions();
map.RequiresMod = modData.Manifest.Mod.Id; map.RequiresMod = modData.Manifest.Mod.Id;
return map; return map;

View File

@@ -163,7 +163,6 @@ ServerTraits:
LobbySettingsNotification LobbySettingsNotification
LobbyDefaults: LobbyDefaults:
TechLevel: Unrestricted
ChromeMetrics: ChromeMetrics:
common|metrics.yaml common|metrics.yaml

View File

@@ -75,6 +75,7 @@ World:
MapCreeps: MapCreeps:
SpawnMapActors: SpawnMapActors:
MapBuildRadius: MapBuildRadius:
MapOptions:
MPStartLocations: MPStartLocations:
CreateMPPlayers: CreateMPPlayers:
MPStartUnits@mcvonly: MPStartUnits@mcvonly:

View File

@@ -156,8 +156,6 @@ ServerTraits:
LobbySettingsNotification LobbySettingsNotification
LobbyDefaults: LobbyDefaults:
StartingUnitsClass: none
TechLevel: Unrestricted
ChromeMetrics: ChromeMetrics:
common|metrics.yaml common|metrics.yaml

View File

@@ -90,6 +90,7 @@ World:
MapCreeps: MapCreeps:
SpawnMapActors: SpawnMapActors:
MapBuildRadius: MapBuildRadius:
MapOptions:
CreateMPPlayers: CreateMPPlayers:
MPStartLocations: MPStartLocations:
MPStartUnits@mcv: MPStartUnits@mcv:

View File

@@ -166,8 +166,6 @@ ServerTraits:
LobbySettingsNotification LobbySettingsNotification
LobbyDefaults: LobbyDefaults:
StartingUnitsClass: none
TechLevel: Unrestricted
ChromeMetrics: ChromeMetrics:
common|metrics.yaml common|metrics.yaml

View File

@@ -121,6 +121,7 @@ World:
WarheadDebugOverlay: WarheadDebugOverlay:
SpawnMapActors: SpawnMapActors:
MapBuildRadius: MapBuildRadius:
MapOptions:
CreateMPPlayers: CreateMPPlayers:
MPStartUnits@mcvonly: MPStartUnits@mcvonly:
Class: none Class: none

View File

@@ -215,7 +215,6 @@ ServerTraits:
LobbySettingsNotification LobbySettingsNotification
LobbyDefaults: LobbyDefaults:
StartingUnitsClass: none
ChromeMetrics: ChromeMetrics:
common|metrics.yaml common|metrics.yaml

View File

@@ -99,6 +99,7 @@ World:
WarheadDebugOverlay: WarheadDebugOverlay:
SpawnMapActors: SpawnMapActors:
MapBuildRadius: MapBuildRadius:
MapOptions:
CreateMPPlayers: CreateMPPlayers:
MPStartUnits@MCV: MPStartUnits@MCV:
Class: none Class: none