From 2371eb43446ad348020829616978e43df555137f Mon Sep 17 00:00:00 2001 From: Flamefire Date: Thu, 16 Oct 2014 19:00:41 +0200 Subject: [PATCH] Refactor theme system --- .../Challenge/Themes/Default/Blue.xml | 14 +-- .../ChallengeMedley/Themes/Default/Blue.xml | 14 +-- .../TicTacToe/Themes/Default/Blue.xml | 14 +-- Output/Themes/Ambient/Screens/ScreenMain.xml | 4 +- Output/Themes/Ambient/Screens/ScreenSing.xml | 8 +- Output/Themes/Ambient/Skin Blue.xml | 14 +-- Output/Themes/Ambient/Skin Green.xml | 14 +-- Output/Themes/Ambient/Skin Red.xml | 14 +-- Output/Themes/Ambient/Skin Yellow.xml | 14 +-- Vocaluxe/Base/ThemeSystem/CBaseSkin.cs | 42 +++++++ Vocaluxe/Base/ThemeSystem/CBaseTheme.cs | 64 ++++++++++ Vocaluxe/Base/ThemeSystem/CPartySkin.cs | 48 +++++++ Vocaluxe/Base/ThemeSystem/CPartyTheme.cs | 69 +++++++++++ Vocaluxe/Base/ThemeSystem/CSkin.cs | 117 ++++-------------- Vocaluxe/Base/ThemeSystem/CTheme.cs | 78 +++--------- Vocaluxe/Base/ThemeSystem/CThemes.cs | 99 +++++++-------- Vocaluxe/Vocaluxe.csproj | 4 + 17 files changed, 365 insertions(+), 266 deletions(-) create mode 100644 Vocaluxe/Base/ThemeSystem/CBaseSkin.cs create mode 100644 Vocaluxe/Base/ThemeSystem/CBaseTheme.cs create mode 100644 Vocaluxe/Base/ThemeSystem/CPartySkin.cs create mode 100644 Vocaluxe/Base/ThemeSystem/CPartyTheme.cs diff --git a/Output/PartyModes/Challenge/Themes/Default/Blue.xml b/Output/PartyModes/Challenge/Themes/Default/Blue.xml index 8cbfea81..a3650a59 100644 --- a/Output/PartyModes/Challenge/Themes/Default/Blue.xml +++ b/Output/PartyModes/Challenge/Themes/Default/Blue.xml @@ -1,13 +1,13 @@  - 3 + 4 Blue brunzel 0 1 - + 0,000 0,000 @@ -182,18 +182,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 0,000 0,000 0,000 1,000 - + 1,000 1,000 @@ -206,7 +206,7 @@ 1,000 0,000 - + [Blue]BG_Default.png Menu.png diff --git a/Output/PartyModes/ChallengeMedley/Themes/Default/Blue.xml b/Output/PartyModes/ChallengeMedley/Themes/Default/Blue.xml index 8cbfea81..a3650a59 100644 --- a/Output/PartyModes/ChallengeMedley/Themes/Default/Blue.xml +++ b/Output/PartyModes/ChallengeMedley/Themes/Default/Blue.xml @@ -1,13 +1,13 @@  - 3 + 4 Blue brunzel 0 1 - + 0,000 0,000 @@ -182,18 +182,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 0,000 0,000 0,000 1,000 - + 1,000 1,000 @@ -206,7 +206,7 @@ 1,000 0,000 - + [Blue]BG_Default.png Menu.png diff --git a/Output/PartyModes/TicTacToe/Themes/Default/Blue.xml b/Output/PartyModes/TicTacToe/Themes/Default/Blue.xml index 8cbfea81..a3650a59 100644 --- a/Output/PartyModes/TicTacToe/Themes/Default/Blue.xml +++ b/Output/PartyModes/TicTacToe/Themes/Default/Blue.xml @@ -1,13 +1,13 @@  - 3 + 4 Blue brunzel 0 1 - + 0,000 0,000 @@ -182,18 +182,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 0,000 0,000 0,000 1,000 - + 1,000 1,000 @@ -206,7 +206,7 @@ 1,000 0,000 - + [Blue]BG_Default.png Menu.png diff --git a/Output/Themes/Ambient/Screens/ScreenMain.xml b/Output/Themes/Ambient/Screens/ScreenMain.xml index f1701971..fba26420 100644 --- a/Output/Themes/Ambient/Screens/ScreenMain.xml +++ b/Output/Themes/Ambient/Screens/ScreenMain.xml @@ -53,10 +53,10 @@ 15 0 - TextWhite + White - TextWhite + White Left Center diff --git a/Output/Themes/Ambient/Screens/ScreenSing.xml b/Output/Themes/Ambient/Screens/ScreenSing.xml index 16099416..fd2c0365 100644 --- a/Output/Themes/Ambient/Screens/ScreenSing.xml +++ b/Output/Themes/Ambient/Screens/ScreenSing.xml @@ -910,10 +910,10 @@ 27 880 - TextBlack + Black - TextBlack + Black Center Center @@ -929,10 +929,10 @@ 20 0 - TextWhite + White - TextWhite + White Right Center diff --git a/Output/Themes/Ambient/Skin Blue.xml b/Output/Themes/Ambient/Skin Blue.xml index 261baee1..4bfe3d4b 100644 --- a/Output/Themes/Ambient/Skin Blue.xml +++ b/Output/Themes/Ambient/Skin Blue.xml @@ -1,6 +1,6 @@  - 3 + 4 Blue bohning @@ -44,8 +44,6 @@ 0,500 1,000 - - 0,000 0,000 @@ -220,18 +218,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 1,000 1,000 1,000 1,000 - + 1,000 1,000 @@ -280,7 +278,7 @@ 1,000 0,850 - + [Blue]BG_Default.png [Blue]BG_Options.png diff --git a/Output/Themes/Ambient/Skin Green.xml b/Output/Themes/Ambient/Skin Green.xml index 7535b7e8..2844dca7 100644 --- a/Output/Themes/Ambient/Skin Green.xml +++ b/Output/Themes/Ambient/Skin Green.xml @@ -1,6 +1,6 @@  - 3 + 4 Green bohning @@ -44,8 +44,6 @@ 0,500 1,000 - - 0,000 0,000 @@ -214,18 +212,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 1,000 1,000 1,000 1,000 - + 1,000 1,000 @@ -274,7 +272,7 @@ 0,811 0,811 - + [Green]BG_Default.png [Green]BG_Options.png diff --git a/Output/Themes/Ambient/Skin Red.xml b/Output/Themes/Ambient/Skin Red.xml index 42db93cb..3da09c58 100644 --- a/Output/Themes/Ambient/Skin Red.xml +++ b/Output/Themes/Ambient/Skin Red.xml @@ -1,6 +1,6 @@  - 3 + 4 Red bohning @@ -44,8 +44,6 @@ 0,500 1,000 - - 0,000 0,000 @@ -214,18 +212,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 1,000 1,000 1,000 1,000 - + 1,000 1,000 @@ -274,7 +272,7 @@ 0,800 0,850 - + [Red]BG_Default.png [Red]BG_Options.png diff --git a/Output/Themes/Ambient/Skin Yellow.xml b/Output/Themes/Ambient/Skin Yellow.xml index 739b3bab..bd305808 100644 --- a/Output/Themes/Ambient/Skin Yellow.xml +++ b/Output/Themes/Ambient/Skin Yellow.xml @@ -1,6 +1,6 @@  - 3 + 4 Yellow bohning @@ -44,8 +44,6 @@ 0,500 1,000 - - 0,000 0,000 @@ -214,18 +212,18 @@ 0,000 1,000 - + 0,000 0,000 0,000 1,000 - - + + 1,000 1,000 1,000 1,000 - + 1,000 1,000 @@ -274,7 +272,7 @@ 0,800 0,850 - + [Yellow]BG_Default.png [Yellow]BG_Options.png diff --git a/Vocaluxe/Base/ThemeSystem/CBaseSkin.cs b/Vocaluxe/Base/ThemeSystem/CBaseSkin.cs new file mode 100644 index 00000000..aab19f28 --- /dev/null +++ b/Vocaluxe/Base/ThemeSystem/CBaseSkin.cs @@ -0,0 +1,42 @@ +using System; +using System.Collections.Generic; + +namespace Vocaluxe.Base.ThemeSystem +{ + class CBaseSkin : CSkin + { + public CBaseSkin(string folder, string file, CTheme parent) : base(folder, file, parent) {} + + public override bool Load() + { + if (!base.Load()) + return false; + + if (!_CheckRequiredElements()) + { + _IsLoaded = false; + return false; + } + + return true; + } + + private bool _CheckRequiredElements() + { + List missingTextures = _RequiredTextures.FindAll(name => !_Textures.ContainsKey(name)); + List missingVideos = _RequiredVideos.FindAll(name => !_Videos.ContainsKey(name)); + List missingColors = _RequiredColors.FindAll(name => !_Colors.ContainsKey(name)); + if (missingTextures.Count + missingVideos.Count + missingColors.Count == 0) + return true; + string msg = "The skin \"" + this + "\" is missing the following elements: "; + if (missingTextures.Count > 0) + msg += Environment.NewLine + "Textures: " + String.Join(", ", missingTextures); + if (missingVideos.Count > 0) + msg += Environment.NewLine + "Videos: " + String.Join(", ", missingVideos); + if (missingColors.Count > 0) + msg += Environment.NewLine + "Colors: " + String.Join(", ", missingColors); + CLog.LogError(msg); + return false; + } + } +} \ No newline at end of file diff --git a/Vocaluxe/Base/ThemeSystem/CBaseTheme.cs b/Vocaluxe/Base/ThemeSystem/CBaseTheme.cs new file mode 100644 index 00000000..3589d702 --- /dev/null +++ b/Vocaluxe/Base/ThemeSystem/CBaseTheme.cs @@ -0,0 +1,64 @@ +using System.IO; +using System.Linq; +using Vocaluxe.Base.Fonts; +using VocaluxeLib.Xml; + +namespace Vocaluxe.Base.ThemeSystem +{ + class CBaseTheme : CTheme + { + public SThemeCursor CursorTheme; + + public CBaseTheme(string filePath) : base(filePath, -1) {} + + protected override CSkin _GetNewSkin(string path, string file) + { + return new CBaseSkin(path, file, this); + } + + public override void Unload() + { + base.Unload(); + CFonts.UnloadThemeFonts(Name); + } + + protected override bool _Load(CXMLReader xmlReader) + { + return _LoadCursor(xmlReader) && + CFonts.LoadThemeFonts(Name, Path.Combine(_Folder, Name, CSettings.FolderNameThemeFonts), xmlReader); + } + + private bool _LoadCursor(CXMLReader xmlReader) + { + bool ok = xmlReader.GetValue("//root/Cursor/Skin", out CursorTheme.SkinName); + + ok &= xmlReader.TryGetFloatValue("//root/Cursor/W", ref CursorTheme.W); + ok &= xmlReader.TryGetFloatValue("//root/Cursor/H", ref CursorTheme.H); + + if (!xmlReader.GetValue("//root/Cursor/Color/Name", out CursorTheme.Color.Name)) + ok &= xmlReader.Read("//root/Cursor/Color/Color", out CursorTheme.Color.Color); + + return ok; + } + + protected override bool _LoadSkin() + { + CSkin skin; + if (!_Skins.TryGetValue(CConfig.Skin, out skin)) + skin = _Skins.Values.FirstOrDefault(); + while (skin != null) + { + if (skin.Load()) + break; + skin.Unload(); + CLog.LogError("Failed to load skin " + skin + "! Removing...", true); + _Skins.Remove(skin.Name); + skin = _Skins.Values.FirstOrDefault(); + } + if (skin == null) + return false; + CurrentSkin = skin; + return true; + } + } +} \ No newline at end of file diff --git a/Vocaluxe/Base/ThemeSystem/CPartySkin.cs b/Vocaluxe/Base/ThemeSystem/CPartySkin.cs new file mode 100644 index 00000000..9133c048 --- /dev/null +++ b/Vocaluxe/Base/ThemeSystem/CPartySkin.cs @@ -0,0 +1,48 @@ +using VocaluxeLib; +using VocaluxeLib.Draw; + +namespace Vocaluxe.Base.ThemeSystem +{ + class CPartySkin : CSkin + { + private CSkin _BaseSkin; + + public CPartySkin(string folder, string file, CTheme parent) : base(folder, file, parent) {} + + public override bool Load() + { + _BaseSkin = CThemes.CurrentThemes[-1].CurrentSkin; + if (!base.Load()) + return false; + for (int i = 1; i <= CSettings.MaxNumPlayer; i++) + { + if (!_Colors.ContainsKey("Player" + i)) + continue; + CLog.LogDebug("Party themes cannot contain player colors. They will be ignored!"); + break; + } + return true; + } + + public override bool GetColor(string name, out SColorF color) + { + if (_Parent.Name == "Default" && !_RequiredColors.Contains(name)) + CLog.LogDebug("Non-Default color: " + name); + return base.GetColor(name, out color) || _BaseSkin.GetColor(name, out color); + } + + public override CVideoStream GetVideo(string name, bool loop) + { + if (_Parent.Name == "Default" && !_RequiredVideos.Contains(name)) + CLog.LogDebug("Non-Default color: " + name); + return base.GetVideo(name, loop) ?? _BaseSkin.GetVideo(name, loop); + } + + public override CTextureRef GetTexture(string name) + { + if (_Parent.Name == "Default" && !_RequiredTextures.Contains(name)) + CLog.LogDebug("Non-Default color: " + name); + return base.GetTexture(name) ?? _BaseSkin.GetTexture(name); + } + } +} \ No newline at end of file diff --git a/Vocaluxe/Base/ThemeSystem/CPartyTheme.cs b/Vocaluxe/Base/ThemeSystem/CPartyTheme.cs new file mode 100644 index 00000000..45705469 --- /dev/null +++ b/Vocaluxe/Base/ThemeSystem/CPartyTheme.cs @@ -0,0 +1,69 @@ +using System; +using System.IO; +using System.Linq; +using Vocaluxe.Base.Fonts; +using VocaluxeLib.Xml; + +namespace Vocaluxe.Base.ThemeSystem +{ + class CPartyTheme : CTheme + { + public CPartyTheme(string filePath, int partyModeID) : base(filePath, partyModeID) {} + + public override void Unload() + { + base.Unload(); + CFonts.UnloadPartyModeFonts(PartyModeID); + } + + protected override CSkin _GetNewSkin(string path, string file) + { + return new CPartySkin(path, file, this); + } + + protected override bool _Load(CXMLReader xmlReader) + { + return CFonts.LoadPartyModeFonts(PartyModeID, Path.Combine(_Folder, "..", CSettings.FolderNamePartyModeFonts), xmlReader); + } + + private CSkin _GetSkinToLoad(int fallbackNum) + { + CSkin skin; + switch (fallbackNum) + { + case 0: + _Skins.TryGetValue(CConfig.Skin, out skin); + break; + case 1: + _Skins.TryGetValue(CSettings.DefaultName, out skin); + break; + case 2: + skin = _Skins.Values.FirstOrDefault(); + break; + default: + throw new ArgumentException(); + } + return skin; + } + + protected override bool _LoadSkin() + { + CSkin skin = null; + for (int i = 0; i < 3; i++) + { + skin = _GetSkinToLoad(i); + if (skin == null) + continue; + if (skin.Load()) + break; + skin.Unload(); + CLog.LogError("Failed to load skin " + skin + "! Removing...", true); + _Skins.Remove(skin.Name); + } + if (skin == null) + return false; + CurrentSkin = skin; + return true; + } + } +} \ No newline at end of file diff --git a/Vocaluxe/Base/ThemeSystem/CSkin.cs b/Vocaluxe/Base/ThemeSystem/CSkin.cs index 9494d742..53e43840 100644 --- a/Vocaluxe/Base/ThemeSystem/CSkin.cs +++ b/Vocaluxe/Base/ThemeSystem/CSkin.cs @@ -14,16 +14,16 @@ namespace Vocaluxe.Base.ThemeSystem public CVideoStream VideoStream; } - class CSkin + abstract class CSkin { - private const int _SkinSystemVersion = 3; - private static readonly List _RequiredTextures = new List(); - private static readonly List _RequiredVideos = new List(); - private static readonly List _RequiredColors = new List(); + private const int _SkinSystemVersion = 4; + protected static readonly List _RequiredTextures = new List(); + protected static readonly List _RequiredVideos = new List(); + protected static readonly List _RequiredColors = new List(); private readonly string _Folder; private readonly string _FileName; - private readonly CTheme _Parent; + protected readonly CTheme _Parent; private SInfo _Info; public String Name @@ -31,13 +31,11 @@ namespace Vocaluxe.Base.ThemeSystem get { return _Info.Name; } } - private readonly Dictionary _Textures = new Dictionary(); - private readonly Dictionary _Videos = new Dictionary(); + protected readonly Dictionary _Textures = new Dictionary(); + protected readonly Dictionary _Videos = new Dictionary(); + protected readonly Dictionary _Colors = new Dictionary(); - private readonly Dictionary _ColorSchemes = new Dictionary(); - private SColorF[] _PlayerColors; - - private bool _IsLoaded; + protected bool _IsLoaded; public static bool InitRequiredElements() { @@ -48,6 +46,12 @@ namespace Vocaluxe.Base.ThemeSystem bool ok = xmlReader.Read("//root/Textures", _RequiredTextures); ok &= xmlReader.Read("//root/Videos", _RequiredVideos); ok &= xmlReader.Read("//root/Colors", _RequiredColors); + for (int i = 1; i <= CSettings.MaxNumPlayer; i++) + { + string name = "Player" + i; + if (!_RequiredColors.Contains(name)) + _RequiredColors.Add(name); + } return ok; } @@ -58,7 +62,7 @@ namespace Vocaluxe.Base.ThemeSystem _RequiredColors.Clear(); } - public CSkin(string folder, string file, CTheme parent) + protected CSkin(string folder, string file, CTheme parent) { _Folder = folder; _FileName = file; @@ -70,7 +74,6 @@ namespace Vocaluxe.Base.ThemeSystem return _Parent.Name + ":" + Name; } - #region Load public bool Init() { CXMLReader xmlReader = CXMLReader.OpenFile(Path.Combine(_Folder, _FileName)); @@ -91,7 +94,7 @@ namespace Vocaluxe.Base.ThemeSystem return true; } - public bool Load() + public virtual bool Load() { if (_IsLoaded) return true; @@ -129,38 +132,13 @@ namespace Vocaluxe.Base.ThemeSystem _Videos.Add(name, sk); } - // load colors if (!_LoadColors(xmlReader)) return false; - if (!_CheckRequiredElements()) - return false; - _IsLoaded = true; return true; } - private bool _CheckRequiredElements() - { - if (_Parent.PartyModeID >= 0) - return true; - List missingTextures = _RequiredTextures.FindAll(name => !_Textures.ContainsKey(name)); - List missingVideos = _RequiredVideos.FindAll(name => !_Videos.ContainsKey(name)); - SColorF dummyColor; - List missingColors = _RequiredColors.FindAll(name => !GetColor(name, out dummyColor)); - if (missingTextures.Count + missingVideos.Count + missingColors.Count == 0) - return true; - string msg = "The skin \"" + this + "\" is missing the following elements: "; - if (missingTextures.Count > 0) - msg += Environment.NewLine + "Textures: " + string.Join(", ", missingTextures); - if (missingVideos.Count > 0) - msg += Environment.NewLine + "Videos: " + string.Join(", ", missingVideos); - if (missingColors.Count > 0) - msg += Environment.NewLine + "Colors: " + string.Join(", ", missingColors); - CLog.LogError(msg); - return false; - } - public void Unload() { foreach (CTextureRef tex in _Textures.Values) @@ -171,73 +149,30 @@ namespace Vocaluxe.Base.ThemeSystem _Textures.Clear(); _Videos.Clear(); - _PlayerColors = null; - _ColorSchemes.Clear(); + _Colors.Clear(); _IsLoaded = false; } private bool _LoadColors(CXMLReader xmlReader) { - if (_Parent.PartyModeID == -1) - { - _PlayerColors = new SColorF[CSettings.MaxNumPlayer]; - - for (int i = 0; i < CSettings.MaxNumPlayer; i++) - { - SColorF color; - if (!xmlReader.Read("//root/Colors/Player" + (i + 1), out color)) - return false; - _PlayerColors[i] = color; - } - } - - List names = xmlReader.GetNames("//root/ColorSchemes/*"); + List names = xmlReader.GetNames("//root/Colors/*"); foreach (string str in names) { SColorF color; - if (!xmlReader.Read("//root/ColorSchemes/" + str, out color)) + if (!xmlReader.Read("//root/Colors/" + str, out color)) return false; - _ColorSchemes.Add(str, color); + _Colors.Add(str, color); } return true; } - #endregion Load - public bool GetColor(string colorName, out SColorF color) + public virtual bool GetColor(string colorName, out SColorF color) { - if (_Parent.Name == "Default" && !_RequiredColors.Contains(colorName)) - CLog.LogDebug("Non-Default color: " + colorName); - return _ColorSchemes.TryGetValue(colorName, out color) || _GetPlayerColor(colorName, out color); + return _Colors.TryGetValue(colorName, out color); } - private bool _GetPlayerColor(string playerNrString, out SColorF color) - { - color = new SColorF(); - if (playerNrString == null) - return false; - if (playerNrString.StartsWith("Player")) - playerNrString = playerNrString.Substring(6); - int playerNr; - if (!int.TryParse(playerNrString, out playerNr)) - return false; - - return GetPlayerColor(playerNr, out color); - } - - public bool GetPlayerColor(int playerNr, out SColorF color) - { - if (_PlayerColors != null && playerNr >= 1 && playerNr <= _PlayerColors.Length) - { - color = _PlayerColors[playerNr - 1]; - return true; - } - - color = new SColorF(); - return false; - } - - public CVideoStream GetVideo(string videoName, bool loop = true) + public virtual CVideoStream GetVideo(string videoName, bool loop) { Debug.Assert(_Parent.Name != "Default" || _RequiredVideos.Contains(videoName)); CVideoSkinElement sk; @@ -253,7 +188,7 @@ namespace Vocaluxe.Base.ThemeSystem return null; } - public CTextureRef GetTexture(string name) + public virtual CTextureRef GetTexture(string name) { Debug.Assert(_Parent.Name != "Default" || _RequiredTextures.Contains(name)); CTextureRef texture; diff --git a/Vocaluxe/Base/ThemeSystem/CTheme.cs b/Vocaluxe/Base/ThemeSystem/CTheme.cs index eedb2b85..808a0524 100644 --- a/Vocaluxe/Base/ThemeSystem/CTheme.cs +++ b/Vocaluxe/Base/ThemeSystem/CTheme.cs @@ -3,7 +3,6 @@ using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Linq; -using Vocaluxe.Base.Fonts; using VocaluxeLib; using VocaluxeLib.Xml; @@ -19,7 +18,7 @@ namespace Vocaluxe.Base.ThemeSystem public SThemeColor Color; } - class CTheme + abstract class CTheme { // Version number for theme files. Increment it, if you've changed something on the theme files! private const int _ThemeSystemVersion = 5; @@ -35,18 +34,18 @@ namespace Vocaluxe.Base.ThemeSystem get { return _Skins.Keys.ToArray(); } } - private readonly string _Folder; - private readonly string _FileName; public readonly int PartyModeID; - public SThemeCursor CursorTheme; - public CSkin CurrentSkin { get; private set; } + protected readonly string _Folder; + private readonly string _FileName; - private readonly Dictionary _Skins = new Dictionary(); + public CSkin CurrentSkin { get; protected set; } + + protected readonly Dictionary _Skins = new Dictionary(); private bool _IsLoaded; - public CTheme(string filePath, int partyModeID) + protected CTheme(string filePath, int partyModeID) { _Folder = Path.GetDirectoryName(filePath); _FileName = Path.GetFileName(filePath); @@ -83,7 +82,7 @@ namespace Vocaluxe.Base.ThemeSystem ok = false; foreach (string file in files) { - CSkin skin = new CSkin(path, file, this); + CSkin skin = _GetNewSkin(path, file); if (skin.Init()) { _Skins.Add(skin.Name, skin); @@ -93,6 +92,10 @@ namespace Vocaluxe.Base.ThemeSystem return ok; } + protected abstract CSkin _GetNewSkin(string path, string file); + protected abstract bool _Load(CXMLReader xmlReader); + protected abstract bool _LoadSkin(); + public bool Load() { if (_IsLoaded) @@ -103,70 +106,19 @@ namespace Vocaluxe.Base.ThemeSystem if (!_LoadSkin()) return false; - bool ok; - if (PartyModeID == -1) - { - ok = _LoadCursor(xmlReader); - ok &= CFonts.LoadThemeFonts(Name, Path.Combine(_Folder, Name, CSettings.FolderNameThemeFonts), xmlReader); - } - else - ok = CFonts.LoadPartyModeFonts(PartyModeID, Path.Combine(_Folder, "..", CSettings.FolderNamePartyModeFonts), xmlReader); + bool ok = _Load(xmlReader); + _IsLoaded = ok; return ok; } - private bool _LoadSkin() - { - CSkin skin; - if (!_Skins.TryGetValue(CConfig.Skin, out skin)) - { - if (PartyModeID < 0) - skin = _Skins.Values.FirstOrDefault(); - else if (Name == CSettings.DefaultName) - { - if (!_Skins.TryGetValue(CSettings.DefaultName, out skin)) - skin = _Skins.Values.FirstOrDefault(); - } - } - while (skin != null) - { - if (skin.Load()) - break; - skin.Unload(); - CLog.LogError("Failed to load skin " + skin + "! Removing...", true); - _Skins.Remove(skin.Name); - skin = (PartyModeID == -1 || Name == CSettings.DefaultName) ? _Skins.Values.FirstOrDefault() : null; - } - if (skin == null) - return false; - CurrentSkin = skin; - return true; - } - - private bool _LoadCursor(CXMLReader xmlReader) - { - bool ok = xmlReader.GetValue("//root/Cursor/Skin", out CursorTheme.SkinName); - - ok &= xmlReader.TryGetFloatValue("//root/Cursor/W", ref CursorTheme.W); - ok &= xmlReader.TryGetFloatValue("//root/Cursor/H", ref CursorTheme.H); - - if (!xmlReader.GetValue("//root/Cursor/Color/Name", out CursorTheme.Color.Name)) - ok &= xmlReader.Read("//root/Cursor/Color/Color", out CursorTheme.Color.Color); - - return ok; - } - - public void Unload() + public virtual void Unload() { if (CurrentSkin != null) { CurrentSkin.Unload(); CurrentSkin = null; } - if (PartyModeID == -1) - CFonts.UnloadThemeFonts(Name); - else - CFonts.UnloadPartyModeFonts(PartyModeID); _IsLoaded = false; } diff --git a/Vocaluxe/Base/ThemeSystem/CThemes.cs b/Vocaluxe/Base/ThemeSystem/CThemes.cs index 14b8c76e..1190c85e 100644 --- a/Vocaluxe/Base/ThemeSystem/CThemes.cs +++ b/Vocaluxe/Base/ThemeSystem/CThemes.cs @@ -30,12 +30,12 @@ namespace Vocaluxe.Base.ThemeSystem private static readonly List _Themes = new List(); public static string[] ThemeNames { - get { return _Themes.Where(th => th.PartyModeID == -1).Select(th => th.Name).ToArray(); } + get { return _Themes.Select(th => th.Name).ToArray(); } } public static string[] SkinNames { - get { return _GetTheme(-1).SkinNames; } + get { return CurrentThemes[-1].SkinNames; } } public static bool Init() @@ -43,6 +43,11 @@ namespace Vocaluxe.Base.ThemeSystem return CSkin.InitRequiredElements() && ReadThemesFromFolder(Path.Combine(CSettings.ProgramFolder, CSettings.FolderNameThemes), -1); } + /// + /// Currently loaded themes. Only for internal use methods of this static class for getting values from the themes. + /// + public static readonly Dictionary CurrentThemes = new Dictionary(); + public static void Close() { Unload(); @@ -52,8 +57,9 @@ namespace Vocaluxe.Base.ThemeSystem public static void Unload() { - foreach (CTheme theme in _Themes) + foreach (CBaseTheme theme in _Themes) theme.Unload(); + CurrentThemes.Clear(); } /// @@ -63,7 +69,7 @@ namespace Vocaluxe.Base.ThemeSystem /// public static void Load() { - CTheme theme = _GetTheme(-1) ?? _Themes.FirstOrDefault(th => th.PartyModeID == -1); + CTheme theme = _Themes.FirstOrDefault(th => th is CBaseTheme && th.Name == CConfig.Theme) ?? _Themes.FirstOrDefault(th => th is CBaseTheme); while (theme != null) { if (theme.Load()) @@ -71,8 +77,9 @@ namespace Vocaluxe.Base.ThemeSystem theme.Unload(); CLog.LogError("Failed to load theme " + theme + "! Removing...", true); _Themes.Remove(theme); - theme = _Themes.FirstOrDefault(th => th.PartyModeID == -1); + theme = _Themes.FirstOrDefault(th => th is CBaseTheme); } + CurrentThemes.Add(-1, theme); if (theme == null) CLog.LogError("No themes found! Cannot continue!", true, true); else @@ -87,20 +94,27 @@ namespace Vocaluxe.Base.ThemeSystem public static bool LoadPartymodeTheme(int partyModeID) { - CTheme theme = _GetTheme(partyModeID); - if (theme.Load()) - return true; - theme.Unload(); - if (theme.Name != CSettings.DefaultName) + Debug.Assert(partyModeID >= 0); + CTheme theme = _Themes.FirstOrDefault(th => th.PartyModeID == partyModeID && th.Name == CConfig.Theme); + if (theme != null) { + if (theme.Load()) + { + CurrentThemes.Add(partyModeID, theme); + return true; + } + theme.Unload(); CLog.LogError("Failed to load theme " + theme + " for partymode! Removing...", true); _Themes.Remove(theme); - theme = _GetTheme(partyModeID); - if (theme.Load()) - return true; + } + theme = _Themes.First(th => th.PartyModeID == partyModeID && th.Name == CSettings.DefaultName); + if (theme.Load()) + { + CurrentThemes.Add(partyModeID, theme); + return true; } CLog.LogError("Failed to load default theme for partymode! Unloading partymode!", true); - foreach (CTheme th in _Themes.Where(th => th.PartyModeID == partyModeID)) + foreach (CPartyTheme th in _Themes.Where(th => th.PartyModeID == partyModeID)) th.Unload(); _Themes.RemoveAll(th => th.PartyModeID == partyModeID); return false; @@ -114,7 +128,8 @@ namespace Vocaluxe.Base.ThemeSystem public static void ReloadSkin() { - _GetTheme(-1).ReloadSkin(); + foreach (CTheme theme in CurrentThemes.Values) + theme.ReloadSkin(); } public static bool ReadThemesFromFolder(string path, int partyModeID) @@ -124,7 +139,11 @@ namespace Vocaluxe.Base.ThemeSystem List newThemes = new List(); foreach (string file in files) { - CTheme theme = new CTheme(file, partyModeID); + CTheme theme; + if (partyModeID < 0) + theme = new CBaseTheme(file); + else + theme = new CPartyTheme(file, partyModeID); if (theme.Init()) newThemes.Add(theme); } @@ -143,72 +162,46 @@ namespace Vocaluxe.Base.ThemeSystem return true; } - private static CTheme _GetTheme(int partyModeID) - { - foreach (CTheme theme in _Themes) - { - if (theme.PartyModeID == partyModeID && theme.Name == CConfig.Theme) - return theme; - } - if (partyModeID >= 0) - { - foreach (CTheme theme in _Themes) - { - if (theme.PartyModeID == partyModeID && theme.Name == CSettings.DefaultName) - return theme; - } - Debug.Assert(false, "Partymode misses default theme, this should be checked during partymode loading!"); - } - return null; - } - public static string GetThemeScreensPath(int partyModeID) { - return _GetTheme(partyModeID).GetScreenPath(); + return CurrentThemes[partyModeID].GetScreenPath(); } - private static void _LogMissingElement(CTheme theme, string elType, string elName) + private static void _LogMissingElement(int partyModeID, string elType, string elName) { - CLog.LogError("Skin " + theme.CurrentSkin + " is missing the " + elType + " \"" + elName + "\"! Expect visual problems!"); + CLog.LogError("Skin " + CurrentThemes[partyModeID].CurrentSkin + " is missing the " + elType + " \"" + elName + "\"! Expect visual problems!"); } public static CTextureRef GetSkinTexture(string textureName, int partyModeID) { if (String.IsNullOrEmpty(textureName)) return null; - CTheme theme = _GetTheme(partyModeID); - CTextureRef texture = theme.CurrentSkin.GetTexture(textureName); - if (texture == null && partyModeID >= 0) - texture = _GetTheme(-1).CurrentSkin.GetTexture(textureName); + CTextureRef texture = CurrentThemes[partyModeID].CurrentSkin.GetTexture(textureName); if (texture == null) - _LogMissingElement(theme, "texture", textureName); + _LogMissingElement(partyModeID, "texture", textureName); return texture; } public static CVideoStream GetSkinVideo(string videoName, int partyModeID, bool loop = true) { Debug.Assert(!String.IsNullOrEmpty(videoName)); - CTheme theme = _GetTheme(partyModeID); - CVideoStream video = theme.CurrentSkin.GetVideo(videoName, loop); - if (video == null && partyModeID >= 0) - video = _GetTheme(-1).CurrentSkin.GetVideo(videoName, loop); + CVideoStream video = CurrentThemes[partyModeID].CurrentSkin.GetVideo(videoName, loop); if (video == null) - _LogMissingElement(theme, "video", videoName); + _LogMissingElement(partyModeID, "video", videoName); return video; } public static SThemeCursor GetCursorTheme() { - return _GetTheme(-1).CursorTheme; + return ((CBaseTheme)CurrentThemes[-1]).CursorTheme; } public static bool GetColor(string colorName, int partyModeID, out SColorF color) { Debug.Assert(!String.IsNullOrEmpty(colorName)); - CTheme theme = _GetTheme(partyModeID); - if (!theme.CurrentSkin.GetColor(colorName, out color) && (partyModeID == -1 || !_GetTheme(-1).CurrentSkin.GetColor(colorName, out color))) + if (!CurrentThemes[partyModeID].CurrentSkin.GetColor(colorName, out color)) { - _LogMissingElement(theme, "color", colorName); + _LogMissingElement(partyModeID, "color", colorName); return false; } return true; @@ -217,7 +210,7 @@ namespace Vocaluxe.Base.ThemeSystem public static SColorF GetPlayerColor(int playerNr) { SColorF color; - if (!_GetTheme(-1).CurrentSkin.GetPlayerColor(playerNr, out color)) + if (!GetColor("Player" + playerNr, -1, out color)) CLog.LogError("Invalid color requested: Color for player " + playerNr + ". Expect visual problems!", true); return color; } diff --git a/Vocaluxe/Vocaluxe.csproj b/Vocaluxe/Vocaluxe.csproj index db195a8d..3bb3e2f5 100644 --- a/Vocaluxe/Vocaluxe.csproj +++ b/Vocaluxe/Vocaluxe.csproj @@ -219,6 +219,10 @@ + + + +