From fe60f6f5dfd66b52bbb8f729f294ee4ae26026e5 Mon Sep 17 00:00:00 2001 From: Flamefire Date: Thu, 7 Aug 2014 19:31:17 +0200 Subject: [PATCH] Simplify Songmenu (only selected and preview numbers) More consistent handling of mouse and keyboard selection of songs --- .../PartyModeChallenge/CPartyModeChallenge.cs | 2 +- .../CPartyModeChallengeMedley.cs | 2 +- .../PartyModeTicTacToe/CPartyModeTicTacToe.cs | 2 +- Vocaluxe/Screens/CScreenSong.cs | 256 +++---- VocaluxeLib/CHelper.cs | 9 + VocaluxeLib/Extensions.cs | 10 + VocaluxeLib/Menu/CMenu.cs | 1 + VocaluxeLib/Menu/CStatic.cs | 39 +- VocaluxeLib/Menu/SongMenu/CSongMenu.cs | 85 +-- VocaluxeLib/Menu/SongMenu/CSongMenuBook.cs | 22 + VocaluxeLib/Menu/SongMenu/CSongMenuDreidel.cs | 29 +- .../Menu/SongMenu/CSongMenuFramework.cs | 299 ++++---- VocaluxeLib/Menu/SongMenu/CSongMenuList.cs | 19 + .../Menu/SongMenu/CSongMenuTileBoard.cs | 672 +++++++----------- VocaluxeLib/Menu/SongMenu/ISongMenu.cs | 34 +- VocaluxeLib/PartyModes/IPartyMode.cs | 2 +- VocaluxeLib/Structs.cs | 9 + 17 files changed, 697 insertions(+), 795 deletions(-) diff --git a/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs b/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs index 46260c81..b0129bec 100644 --- a/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs +++ b/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs @@ -270,7 +270,7 @@ namespace VocaluxeLib.PartyModes.Challenge public override void UpdateGame() { /* - if (CBase.Songs.GetCurrentCategoryIndex() != -1 || _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) + if (CBase.Songs.IsInCategory() || _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) _ScreenSongOptions.Selection.RandomOnly = true; else _ScreenSongOptions.Selection.RandomOnly = false;*/ diff --git a/PartyModes/PartyModeChallengeMedley/CPartyModeChallengeMedley.cs b/PartyModes/PartyModeChallengeMedley/CPartyModeChallengeMedley.cs index b0975714..46f9edda 100644 --- a/PartyModes/PartyModeChallengeMedley/CPartyModeChallengeMedley.cs +++ b/PartyModes/PartyModeChallengeMedley/CPartyModeChallengeMedley.cs @@ -275,7 +275,7 @@ namespace VocaluxeLib.PartyModes.ChallengeMedley public override void UpdateGame() { /* - if (CBase.Songs.GetCurrentCategoryIndex() != -1 || _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) + if (CBase.Songs.IsInCategory() || _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) _ScreenSongOptions.Selection.RandomOnly = true; else _ScreenSongOptions.Selection.RandomOnly = false;*/ diff --git a/PartyModes/PartyModeTicTacToe/CPartyModeTicTacToe.cs b/PartyModes/PartyModeTicTacToe/CPartyModeTicTacToe.cs index c695a1c7..d3f29442 100644 --- a/PartyModes/PartyModeTicTacToe/CPartyModeTicTacToe.cs +++ b/PartyModes/PartyModeTicTacToe/CPartyModeTicTacToe.cs @@ -329,7 +329,7 @@ namespace VocaluxeLib.PartyModes.TicTacToe public override void UpdateGame() { /* - if (CBase.Songs.GetCurrentCategoryIndex() != -1 || _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) + if (CBase.Songs.IsInCategory() || _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) _ScreenSongOptions.Selection.RandomOnly = true; else _ScreenSongOptions.Selection.RandomOnly = false;*/ diff --git a/Vocaluxe/Screens/CScreenSong.cs b/Vocaluxe/Screens/CScreenSong.cs index 996f427c..7dcc1a0c 100644 --- a/Vocaluxe/Screens/CScreenSong.cs +++ b/Vocaluxe/Screens/CScreenSong.cs @@ -23,6 +23,7 @@ using System.Windows.Forms; using Vocaluxe.Base; using VocaluxeLib; using VocaluxeLib.Menu; +using VocaluxeLib.Menu.SongMenu; using VocaluxeLib.PartyModes; using VocaluxeLib.Songs; @@ -70,8 +71,8 @@ namespace Vocaluxe.Screens private const string _StaticSearchBar = "StaticSearchBar"; private const string _StaticOptionsBG = "StaticOptionsBG"; - private const string _SongMenu = "SongMenu"; - private const string _Playlist = "Playlist"; + private const string _SongMenuName = "SongMenu"; + private const string _PlaylistName = "Playlist"; private string _SearchText = String.Empty; private bool _SearchActive; @@ -91,6 +92,9 @@ namespace Vocaluxe.Screens private int _SelectedSongID; private int _SelectedCategoryIndex; + private CSongMenu _SongMenu; + private CPlaylist _Playlist; + public CScreenSong() { _AvailableGameModes = new List(); @@ -133,19 +137,20 @@ namespace Vocaluxe.Screens _ThemeTexts = tlist.ToArray(); _ThemeButtons = blist.ToArray(); _ThemeSelectSlides = new string[] {_SelectSlideOptionsMode, _SelectSlideOptionsPlaylistAdd, _SelectSlideOptionsPlaylistOpen, _SelectSlideOptionsNumMedleySongs}; - _ThemeSongMenus = new string[] {_SongMenu}; - _ThemePlaylists = new string[] {_Playlist}; + _ThemeSongMenus = new string[] {_SongMenuName}; + _ThemePlaylists = new string[] {_PlaylistName}; } public override void LoadTheme(string xmlPath) { base.LoadTheme(xmlPath); + _SongMenu = _SongMenus[_SongMenuName]; + _Playlist = _Playlists[_PlaylistName]; _ToggleSongOptions(ESongOptionsView.None); - _Playlists[_Playlist].Visible = false; - _DragAndDropCover = GetNewStatic(); - _Playlists[_Playlist].Init(); + _Playlist.Init(); + _Playlist.Visible = false; _AvailableGameModes.Clear(); } @@ -158,7 +163,7 @@ namespace Vocaluxe.Screens if (_PlaylistActive) { - _Playlists[_Playlist].HandleInput(keyEvent); + _Playlist.HandleInput(keyEvent); return true; } @@ -176,8 +181,8 @@ namespace Vocaluxe.Screens } else { - _SongMenus[_SongMenu].HandleInput(ref keyEvent, _Sso); - _UpdatePartyModeOptions(); + if (_SongMenu.HandleInput(ref keyEvent, _Sso)) + keyEvent.Handled = true; if (keyEvent.Handled) return true; @@ -210,32 +215,31 @@ namespace Vocaluxe.Screens } } if (_Buttons[_ButtonStart].Selected) - _HandlePartySongSelection(_SongMenus[_SongMenu].GetSelectedSong()); + _HandlePartySongSelection(_SongMenu.GetPreviewSongNr()); } if (CSongs.NumSongsVisible > 0 && !_Sso.Selection.PartyMode) { - if (_SongMenus[_SongMenu].GetSelectedSong() != -1 && !_SongOptionsActive) - { - if (!_Sso.Selection.PartyMode) - _ToggleSongOptions(ESongOptionsView.Song); - } + if (_SongMenu.GetPreviewSongNr() != -1) + _ToggleSongOptions(ESongOptionsView.Song); } break; case Keys.Tab: - if (_Playlists[_Playlist].Visible) + if (_Playlist.Visible) { _PlaylistActive = !_PlaylistActive; - _Playlists[_Playlist].Selected = _PlaylistActive; - _SongMenus[_SongMenu].SetActive(!_PlaylistActive); + _Playlist.Selected = _PlaylistActive; + _SongMenu.Active = !_PlaylistActive; } break; case Keys.Back: - if (_SearchActive && _SearchText != "") - _ApplyNewSearchFilter(_SearchText.Remove(_SearchText.Length - 1)); - - if ((CSongs.Category < 0 || _Sso.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) && !_Sso.Selection.PartyMode && !_SearchActive) + if (_SearchActive) + { + if (_SearchText != "") + _ApplyNewSearchFilter(_SearchText.Remove(_SearchText.Length - 1)); + } + else if ((!CSongs.IsInCategory || _Sso.Sorting.Tabs == EOffOn.TR_CONFIG_OFF) && !_Sso.Selection.PartyMode) CGraphics.FadeTo(EScreens.ScreenMain); break; @@ -276,7 +280,12 @@ namespace Vocaluxe.Screens case Keys.S: if (keyEvent.Mod == EModifier.Ctrl && CSongs.NumSongsVisible > 0 && !_Sso.Selection.PartyMode) - _StartMedleySong(_SongMenus[_SongMenu].GetSelectedSong()); + _StartMedleySong(_SongMenu.GetPreviewSongNr()); + break; + + case Keys.F: + if (keyEvent.Mod == EModifier.Ctrl) + _SearchActive = true; break; case Keys.D1: @@ -322,7 +331,7 @@ namespace Vocaluxe.Screens else if (_Buttons[_ButtonOptionsSing].Selected) { _ToggleSongOptions(ESongOptionsView.None); - _StartSong(_SongMenus[_SongMenu].GetSelectedSong()); + _StartSong(_SongMenu.GetPreviewSongNr()); } else if (_Buttons[_ButtonOptionsPlaylist].Selected) { @@ -332,9 +341,9 @@ namespace Vocaluxe.Screens else if (_Buttons[_ButtonOptionsRandom].Selected) { if (CSongs.IsInCategory) - _SongMenus[_SongMenu].SetSelectedSong(CSongs.GetRandomSong()); + _SongMenu.SetSelectedSong(CSongs.GetRandomSong()); else - _SongMenus[_SongMenu].SetSelectedCategory(CSongs.GetRandomCategory()); + _SongMenu.SetSelectedCategory(CSongs.GetRandomCategory()); } else if (_Buttons[_ButtonOptionsSingAll].Selected) _StartRandomAllSongs(); @@ -397,24 +406,24 @@ namespace Vocaluxe.Screens _OldMousePosX = mouseEvent.X; _OldMousePosY = mouseEvent.Y; - if (_Playlists[_Playlist].Visible && _Playlists[_Playlist].IsMouseOver(mouseEvent)) + if (_Playlist.Visible && _Playlist.IsMouseOver(mouseEvent)) { _PlaylistActive = true; - _Playlists[_Playlist].Selected = _PlaylistActive; - _SongMenus[_SongMenu].SetActive(!_PlaylistActive); + _Playlist.Selected = _PlaylistActive; + _SongMenu.Active = !_PlaylistActive; _ToggleSongOptions(ESongOptionsView.None); } - else if (CHelper.IsInBounds(_SongMenus[_SongMenu].Rect, mouseEvent.X, mouseEvent.Y)) + else if (CHelper.IsInBounds(_SongMenu.Rect, mouseEvent.X, mouseEvent.Y)) { _PlaylistActive = false; - _Playlists[_Playlist].Selected = _PlaylistActive; - _SongMenus[_SongMenu].SetActive(!_PlaylistActive); + _Playlist.Selected = _PlaylistActive; + _SongMenu.Active = !_PlaylistActive; } - if (_Playlists[_Playlist].Visible && _PlaylistActive) + if (_Playlist.Visible && _PlaylistActive) { - if (_Playlists[_Playlist].HandleMouse(mouseEvent)) + if (_Playlist.HandleMouse(mouseEvent)) return true; } @@ -447,16 +456,16 @@ namespace Vocaluxe.Screens if (mouseEvent.LD && !_Sso.Selection.PartyMode) { - if (CSongs.NumSongsVisible > 0 && _SongMenus[_SongMenu].GetActualSelection() != -1 && _SongMenus[_SongMenu].IsMouseOverActualSelection(mouseEvent)) + if (CSongs.NumSongsVisible > 0 && _SongMenu.GetPreviewSongNr() != -1 && _SongMenu.IsMouseOverSelectedSong(mouseEvent)) { _ToggleSongOptions(ESongOptionsView.None); - _StartVisibleSong(_SongMenus[_SongMenu].GetActualSelection()); + _StartVisibleSong(_SongMenu.GetPreviewSongNr()); return true; } } - _SongMenus[_SongMenu].HandleMouse(ref mouseEvent, _Sso); - _UpdatePartyModeOptions(); + if (_SongMenu.HandleMouse(ref mouseEvent, _Sso)) + mouseEvent.Handled = true; if (mouseEvent.Handled) return true; @@ -478,7 +487,7 @@ namespace Vocaluxe.Screens if (_Buttons[_ButtonOptionsSing].Selected) { _ToggleSongOptions(ESongOptionsView.None); - _StartSong(_SongMenus[_SongMenu].GetSelectedSong()); + _StartSong(_SongMenu.GetPreviewSongNr()); return true; } if (_Buttons[_ButtonOptionsPlaylist].Selected) @@ -491,7 +500,7 @@ namespace Vocaluxe.Screens { if (CSongs.IsInCategory) { - _SongMenus[_SongMenu].SetSelectedSong(CSongs.GetRandomSong()); + _SongMenu.SetSelectedSong(CSongs.GetRandomSong()); return true; } } @@ -499,7 +508,7 @@ namespace Vocaluxe.Screens { if (!CSongs.IsInCategory) { - _SongMenus[_SongMenu].SetSelectedCategory(CSongs.GetRandomCategory()); + _SongMenu.SetSelectedCategory(CSongs.GetRandomCategory()); return true; } } @@ -545,7 +554,7 @@ namespace Vocaluxe.Screens { if (_Buttons[_ButtonStart].Selected) { - _HandlePartySongSelection(_SongMenus[_SongMenu].GetSelectedSong()); + _HandlePartySongSelection(_SongMenu.GetPreviewSongNr()); return true; } @@ -563,25 +572,20 @@ namespace Vocaluxe.Screens } } - if (CSongs.NumSongsVisible > 0 && _SongMenus[_SongMenu].GetActualSelection() != -1 && !_Sso.Selection.PartyMode) + if (CSongs.NumSongsVisible > 0 && _SongMenu.GetPreviewSongNr() != -1 && !_Sso.Selection.PartyMode) { - if (_SongMenus[_SongMenu].GetSelectedSong() != -1 && !_SongOptionsActive) - { - _ToggleSongOptions(ESongOptionsView.Song); - return true; - } - _ToggleSongOptions(ESongOptionsView.None); + _ToggleSongOptions(!_SongOptionsActive ? ESongOptionsView.Song : ESongOptionsView.None); return true; } } if (mouseEvent.LBH) { - if (!_DragAndDropActive && _Playlists[_Playlist].Visible && CSongs.NumSongsVisible > 0 && _SongMenus[_SongMenu].GetActualSelection() != -1) + if (!_DragAndDropActive && _Playlist.Visible && CSongs.NumSongsVisible > 0 && _SongMenu.GetSelectedSongNr() != -1) { - _DragAndDropCover = _SongMenus[_SongMenu].GetSelectedSongCover(); + _DragAndDropCover = _SongMenu.GetSelectedSongCover(); _DragAndDropCover.Rect.Z = CSettings.ZNear; - _Playlists[_Playlist].DragAndDropSongID = CSongs.VisibleSongs[_SongMenus[_SongMenu].GetActualSelection()].ID; + _Playlist.DragAndDropSongID = CSongs.VisibleSongs[_SongMenu.GetSelectedSongNr()].ID; _DragAndDropActive = true; return true; } @@ -591,7 +595,7 @@ namespace Vocaluxe.Screens if (!mouseEvent.LBH && _DragAndDropActive) { _DragAndDropActive = false; - _Playlists[_Playlist].DragAndDropSongID = -1; + _Playlist.DragAndDropSongID = -1; return true; } @@ -608,7 +612,7 @@ namespace Vocaluxe.Screens else if (_Sso.Selection.CategoryChangeAllowed) { _ToggleSongOptions(ESongOptionsView.None); - _SongMenus[_SongMenu].EnterCurrentCategory(); + _SongMenu.EnterSelectedCategory(); } } @@ -625,7 +629,7 @@ namespace Vocaluxe.Screens _SearchText = _Sso.Sorting.SearchString; CGame.Reset(); - _SongMenus[_SongMenu].OnShow(); + _SongMenu.OnShow(); if (_Sso.Selection.PartyMode) _PlaylistActive = false; @@ -633,14 +637,14 @@ namespace Vocaluxe.Screens if (_Sso.Selection.PartyMode) _ToggleSongOptions(ESongOptionsView.None); - _SongMenus[_SongMenu].SetActive(!_PlaylistActive); - _SongMenus[_SongMenu].SetSmallView(_Playlists[_Playlist].Visible); + _SongMenu.Active = !_PlaylistActive; + _SongMenu.SmallView = _Playlist.Visible; - if (_Playlists[_Playlist].ActivePlaylistID != -1) - _Playlists[_Playlist].LoadPlaylist(_Playlists[_Playlist].ActivePlaylistID); + if (_Playlist.ActivePlaylistID != -1) + _Playlist.LoadPlaylist(_Playlist.ActivePlaylistID); _DragAndDropActive = false; - _Playlists[_Playlist].DragAndDropSongID = -1; + _Playlist.DragAndDropSongID = -1; UpdateGame(); if (CSongs.IsInCategory) @@ -649,23 +653,30 @@ namespace Vocaluxe.Screens public override bool UpdateGame() { - if (_SongMenus[_SongMenu].IsSmallView()) - CheckPlaylist(); + if (_PlaylistActive) + _CheckPlaylist(); _Texts[_TextCategory].Text = CSongs.GetCurrentCategoryName(); - if (CSongs.Category > -1 || CConfig.Tabs == EOffOn.TR_CONFIG_OFF) + if (CSongs.IsInCategory || CConfig.Tabs == EOffOn.TR_CONFIG_OFF) CBackgroundMusic.Disabled = true; else CBackgroundMusic.Disabled = false; - int song = _SongMenus[_SongMenu].GetActualSelection(); - if ((CSongs.IsInCategory || CConfig.Tabs == EOffOn.TR_CONFIG_OFF) && song >= 0 && song < CSongs.VisibleSongs.Count) - _Texts[_TextSelection].Text = CSongs.VisibleSongs[song].Artist + " - " + CSongs.VisibleSongs[song].Title; - else if (!CSongs.IsInCategory && song >= 0 && song < CSongs.Categories.Count) - _Texts[_TextSelection].Text = CSongs.Categories[song].Name; + string selectionText = ""; + if (CSongs.IsInCategory) + { + int song = _SongMenu.GetSelectedSongNr(); + if (song >= 0 && song < CSongs.VisibleSongs.Count) + selectionText = CSongs.VisibleSongs[song].Artist + " - " + CSongs.VisibleSongs[song].Title; + } else - _Texts[_TextSelection].Text = String.Empty; + { + int cat = _SongMenu.GetSelectedCategory(); + if (!CSongs.IsInCategory && cat >= 0 && cat < CSongs.Categories.Count) + _Texts[_TextSelection].Text = CSongs.Categories[cat].Name; + } + _Texts[_TextSelection].Text = selectionText; _Texts[_TextSearchBar].Text = _SearchText; if (_SearchActive) @@ -703,12 +714,12 @@ namespace Vocaluxe.Screens base.OnClose(); CBackgroundMusic.Disabled = false; CSound.SetGlobalVolume(CConfig.BackgroundMusicVolume); - _SongMenus[_SongMenu].OnHide(); + _SongMenu.OnHide(); } private void _HandlePartySongSelection(int songNr) { - if ((CSongs.Category >= 0) && (songNr >= 0)) + if (CSongs.IsInCategory && (songNr >= 0)) { CSong song = CSongs.VisibleSongs[songNr]; if (song != null) @@ -730,12 +741,12 @@ namespace Vocaluxe.Screens _SelectNextRandomSong(); if (_Sso.Selection.SongIndex != -1) - _SongMenus[_SongMenu].SetSelectedSong(_Sso.Selection.SongIndex); + _SongMenu.SetSelectedSong(_Sso.Selection.SongIndex); } - if (_SelectedSongID != _SongMenus[_SongMenu].GetSelectedSong() && CSongs.Category > -1) + if (_SelectedSongID != _SongMenu.GetPreviewSongNr() && CSongs.IsInCategory) { - _SelectedSongID = _SongMenus[_SongMenu].GetSelectedSong(); + _SelectedSongID = _SongMenu.GetPreviewSongNr(); CParty.OnSongChange(_SelectedSongID, ref _Sso); } @@ -752,14 +763,13 @@ namespace Vocaluxe.Screens _ToggleSongOptions(ESongOptionsView.None); } - _SongMenus[_SongMenu].Update(_Sso); + _SongMenu.Update(_Sso); if (_Sso.Selection.RandomOnly && _Sso.Selection.NumJokers != null) { _Buttons[_ButtonStart].Visible = true; - if (!_SongMenus[_SongMenu].IsSmallView()) - _SongMenus[_SongMenu].SetSmallView(true); + _SongMenu.SmallView = true; for (int i = 0; i < CSettings.MaxNumPlayer; i++) { @@ -791,8 +801,8 @@ namespace Vocaluxe.Screens } else { - if (_Sso.Selection.PartyMode && _SongMenus[_SongMenu].IsSmallView()) - _SongMenus[_SongMenu].SetSmallView(false); + if (_Sso.Selection.PartyMode) + _SongMenu.SmallView = false; for (int i = 0; i < CSettings.MaxNumPlayer; i++) { @@ -806,7 +816,7 @@ namespace Vocaluxe.Screens private void _StartSong(int songNr) { - if ((CSongs.Category >= 0) && (songNr >= 0)) + if (CSongs.IsInCategory && (songNr >= 0)) { EGameMode gm; if (_AvailableGameModes.Count >= _SelectSlides[_SelectSlideOptionsMode].Selection) @@ -824,7 +834,7 @@ namespace Vocaluxe.Screens private void _StartVisibleSong(int songNr) { - if (CSongs.Category >= 0 && songNr >= 0 && CSongs.NumSongsVisible > songNr) + if (CSongs.IsInCategory && songNr >= 0 && CSongs.NumSongsVisible > songNr) { EGameMode gm = CSongs.VisibleSongs[songNr].IsDuet ? EGameMode.TR_GAMEMODE_DUET : EGameMode.TR_GAMEMODE_NORMAL; @@ -838,7 +848,7 @@ namespace Vocaluxe.Screens private void _StartMedleySong(int songNr) { - if ((CSongs.Category >= 0) && (songNr >= 0)) + if (CSongs.IsInCategory && (songNr >= 0)) { if (!CSongs.VisibleSongs[songNr].IsGameModeAvailable(EGameMode.TR_GAMEMODE_MEDLEY)) return; @@ -964,7 +974,7 @@ namespace Vocaluxe.Screens if (CSongs.IsInCategory) { _ToggleSongOptions(ESongOptionsView.None); - _SongMenus[_SongMenu].SetSelectedSong(CSongs.GetRandomSong()); + _SongMenu.SetSelectedSong(CSongs.GetRandomSong()); return true; } return false; @@ -975,7 +985,7 @@ namespace Vocaluxe.Screens if (!CSongs.IsInCategory) { _ToggleSongOptions(ESongOptionsView.None); - _SongMenus[_SongMenu].SetSelectedCategory(CSongs.GetRandomCategory()); + _SongMenu.SetSelectedCategory(CSongs.GetRandomCategory()); return true; } return false; @@ -999,7 +1009,7 @@ namespace Vocaluxe.Screens private void _JumpTo(char letter) { int start = 0; - int curSelected = _SongMenus[_SongMenu].GetActualSelection(); + int curSelected = CSongs.IsInCategory ? _SongMenu.GetSelectedSongNr() : _SongMenu.GetSelectedCategory(); bool firstLevel = CConfig.Tabs == EOffOn.TR_CONFIG_OFF && CSongs.IsInCategory; bool secondSort = CConfig.Tabs == EOffOn.TR_CONFIG_ON && (CConfig.SongSorting == ESongSorting.TR_CONFIG_ARTIST || @@ -1042,7 +1052,7 @@ namespace Vocaluxe.Screens break; } if (visibleID > -1) - _SongMenus[_SongMenu].SetSelectedSong(visibleID); + _SongMenu.SetSelectedSong(visibleID); } else if (secondSort && CSongs.IsInCategory) { @@ -1066,7 +1076,7 @@ namespace Vocaluxe.Screens break; } if (visibleID > -1) - _SongMenus[_SongMenu].SetSelectedSong(visibleID); + _SongMenu.SetSelectedSong(visibleID); } else if (!CSongs.IsInCategory) { @@ -1076,7 +1086,7 @@ namespace Vocaluxe.Screens start = curSelected + 1; int visibleID = _FindIndex(categories, start, element => element.Name.StartsWith(letter.ToString(), StringComparison.OrdinalIgnoreCase)); if (visibleID > -1) - _SongMenus[_SongMenu].SetSelectedCategory(visibleID); + _SongMenu.SetSelectedCategory(visibleID); } } @@ -1088,9 +1098,9 @@ namespace Vocaluxe.Screens bool refresh = false; _SearchText = newFilterString; - int songIndex = _SongMenus[_SongMenu].GetSelectedSong(); + int songIndex = _SongMenu.GetSelectedSongNr(); int songID = -1; - if (songIndex != -1 && CSongs.NumSongsVisible > 0 && CSongs.NumSongsVisible > songIndex) + if (songIndex != -1) songID = CSongs.VisibleSongs[songIndex].ID; if (newFilterString == "" && _Sso.Sorting.Tabs == EOffOn.TR_CONFIG_ON) @@ -1107,13 +1117,13 @@ namespace Vocaluxe.Screens CSongs.Sort(_Sso.Sorting.SongSorting, _Sso.Sorting.Tabs, _Sso.Sorting.IgnoreArticles, newFilterString, _Sso.Sorting.DuetOptions); - if (songID == -1 || CSongs.NumSongsVisible == 0 || CSongs.NumSongsVisible <= songIndex || CSongs.GetVisibleSongByIndex(songIndex).ID != songID) + if (songID == -1 || CSongs.NumSongsVisible <= songIndex || CSongs.GetVisibleSongByIndex(songIndex).ID != songID) refresh = true; if (refresh) - _SongMenus[_SongMenu].OnHide(); + _SongMenu.OnHide(); - _SongMenus[_SongMenu].OnShow(); + _SongMenu.OnShow(); } private void _ToggleSongOptions(ESongOptionsView view) @@ -1163,7 +1173,7 @@ namespace Vocaluxe.Screens private void _CheckAndAddGameMode(EGameMode gameMode) { - if (CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].IsGameModeAvailable(gameMode)) + if (CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].IsGameModeAvailable(gameMode)) { _SelectSlides[_SelectSlideOptionsMode].AddValue(Enum.GetName(typeof(EGameMode), gameMode)); _AvailableGameModes.Add(gameMode); @@ -1243,9 +1253,9 @@ namespace Vocaluxe.Screens } #region Playlist Actions - public void CheckPlaylist() + private void _CheckPlaylist() { - if (_Playlists[_Playlist].ActivePlaylistID == -1 && _PlaylistActive) + if (_Playlist.ActivePlaylistID == -1 && _PlaylistActive) _ClosePlaylist(); } @@ -1253,21 +1263,21 @@ namespace Vocaluxe.Screens { if (CPlaylists.Playlists.Length > playlistID && playlistID >= 0) { - _Playlists[_Playlist].LoadPlaylist(playlistID); - _SongMenus[_SongMenu].SetSmallView(true); - _Playlists[_Playlist].Visible = true; + _Playlist.LoadPlaylist(playlistID); + _SongMenu.SmallView = true; + _Playlist.Visible = true; } } private void _ClosePlaylist() { - if (_Playlists[_Playlist].Visible || _PlaylistActive) + if (_Playlist.Visible || _PlaylistActive) { - _SongMenus[_SongMenu].SetSmallView(false); + _SongMenu.SmallView = false; _PlaylistActive = false; - _Playlists[_Playlist].Selected = _PlaylistActive; - _SongMenus[_SongMenu].SetActive(!_PlaylistActive); - _Playlists[_Playlist].ClosePlaylist(); + _Playlist.Selected = _PlaylistActive; + _SongMenu.Active = !_PlaylistActive; + _Playlist.ClosePlaylist(); } } @@ -1283,14 +1293,14 @@ namespace Vocaluxe.Screens private void _OpenAndAddPlaylistAction() { //Open an existing playlist and add song - if (_Playlists[_Playlist].ActivePlaylistID != (_SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection - 1) && + if (_Playlist.ActivePlaylistID != (_SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection - 1) && (_SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection - 1) != -1) { //Check selected game-mode EGameMode gm; if (_AvailableGameModes.Count >= _SelectSlides[_SelectSlideOptionsMode].Selection) gm = _AvailableGameModes[_SelectSlides[_SelectSlideOptionsMode].Selection]; - else if (CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].IsDuet) + else if (CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].IsDuet) gm = EGameMode.TR_GAMEMODE_DUET; else gm = EGameMode.TR_GAMEMODE_NORMAL; @@ -1298,15 +1308,15 @@ namespace Vocaluxe.Screens //Check if Playlist really exists if (_SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection - 1 >= 0) { - _Playlists[_Playlist].ActivePlaylistID = _SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection - 1; + _Playlist.ActivePlaylistID = _SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection - 1; //Add song to playlist - CPlaylists.Playlists[_Playlists[_Playlist].ActivePlaylistID].AddSong(CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].ID, gm); + CPlaylists.Playlists[_Playlist.ActivePlaylistID].AddSong(CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].ID, gm); //Open playlist - _OpenPlaylist(_Playlists[_Playlist].ActivePlaylistID); + _OpenPlaylist(_Playlist.ActivePlaylistID); - _Playlists[_Playlist].ScrollToBottom(); + _Playlist.ScrollToBottom(); } } //Create a new playlist and add song @@ -1316,23 +1326,23 @@ namespace Vocaluxe.Screens EGameMode gm; if (_AvailableGameModes.Count >= _SelectSlides[_SelectSlideOptionsMode].Selection) gm = _AvailableGameModes[_SelectSlides[_SelectSlideOptionsMode].Selection]; - else if (CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].IsDuet) + else if (CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].IsDuet) gm = EGameMode.TR_GAMEMODE_DUET; else gm = EGameMode.TR_GAMEMODE_NORMAL; //Create new playlist - _Playlists[_Playlist].ActivePlaylistID = CPlaylists.NewPlaylist(); + _Playlist.ActivePlaylistID = CPlaylists.NewPlaylist(); //Add song to playlist - CPlaylists.Playlists[_Playlists[_Playlist].ActivePlaylistID].AddSong(CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].ID, gm); + CPlaylists.Playlists[_Playlist.ActivePlaylistID].AddSong(CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].ID, gm); //Open playlist - _OpenPlaylist(_Playlists[_Playlist].ActivePlaylistID); + _OpenPlaylist(_Playlist.ActivePlaylistID); //Add new playlist to select-slide - _SelectSlides[_SelectSlideOptionsPlaylistAdd].AddValue(CPlaylists.Playlists[_Playlists[_Playlist].ActivePlaylistID].PlaylistName); - _SelectSlides[_SelectSlideOptionsPlaylistOpen].AddValue(CPlaylists.Playlists[_Playlists[_Playlist].ActivePlaylistID].PlaylistName); + _SelectSlides[_SelectSlideOptionsPlaylistAdd].AddValue(CPlaylists.Playlists[_Playlist.ActivePlaylistID].PlaylistName); + _SelectSlides[_SelectSlideOptionsPlaylistOpen].AddValue(CPlaylists.Playlists[_Playlist.ActivePlaylistID].PlaylistName); } //Add song to loaded playlist else @@ -1341,20 +1351,20 @@ namespace Vocaluxe.Screens EGameMode gm; if (_AvailableGameModes.Count >= _SelectSlides[_SelectSlideOptionsMode].Selection) gm = _AvailableGameModes[_SelectSlides[_SelectSlideOptionsMode].Selection]; - else if (CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].IsDuet) + else if (CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].IsDuet) gm = EGameMode.TR_GAMEMODE_DUET; else gm = EGameMode.TR_GAMEMODE_NORMAL; - CPlaylists.Playlists[_Playlists[_Playlist].ActivePlaylistID].AddSong(CSongs.VisibleSongs[_SongMenus[_SongMenu].GetSelectedSong()].ID, gm); - _Playlists[_Playlist].UpdatePlaylist(); - _Playlists[_Playlist].ScrollToBottom(); + CPlaylists.Playlists[_Playlist.ActivePlaylistID].AddSong(CSongs.VisibleSongs[_SongMenu.GetPreviewSongNr()].ID, gm); + _Playlist.UpdatePlaylist(); + _Playlist.ScrollToBottom(); } } private void _SetSelectSlidePlaylistToCurrentPlaylist() { - if (_Playlists[_Playlist].ActivePlaylistID > -1) - _SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection = _Playlists[_Playlist].ActivePlaylistID + 1; + if (_Playlist.ActivePlaylistID > -1) + _SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection = _Playlist.ActivePlaylistID + 1; else _SelectSlides[_SelectSlideOptionsPlaylistAdd].Selection = 0; } diff --git a/VocaluxeLib/CHelper.cs b/VocaluxeLib/CHelper.cs index 9d37b818..01183730 100644 --- a/VocaluxeLib/CHelper.cs +++ b/VocaluxeLib/CHelper.cs @@ -114,6 +114,15 @@ namespace VocaluxeLib return Int32.TryParse(value, out result) ? result : 0; } + public static void SetRect(SRectF bounds, out SRectF rect, float rectAspect, EAspect aspect) + { + var bounds2 = new RectangleF(bounds.X, bounds.Y, bounds.W, bounds.H); + RectangleF rect2; + SetRect(bounds2, out rect2, rectAspect, aspect); + + rect = new SRectF(rect2.X, rect2.Y, rect2.Width, rect2.Height, bounds.Z); + } + public static void SetRect(RectangleF bounds, out RectangleF rect, float rectAspect, EAspect aspect) { float boundsW = bounds.Width; diff --git a/VocaluxeLib/Extensions.cs b/VocaluxeLib/Extensions.cs index 4cc4fe2e..f04d5f40 100644 --- a/VocaluxeLib/Extensions.cs +++ b/VocaluxeLib/Extensions.cs @@ -124,5 +124,15 @@ namespace VocaluxeLib { return value.ToString("F", NumberFormatInfo.InvariantInfo); } + + public static SRectF Scale(this SRectF rect, float scale) + { + return new SRectF( + rect.X - rect.W * (scale - 1f), + rect.Y - rect.H * (scale - 1f), + rect.W + 2 * rect.W * (scale - 1f), + rect.H + 2 * rect.H * (scale - 1f), + rect.Z); + } } } \ No newline at end of file diff --git a/VocaluxeLib/Menu/CMenu.cs b/VocaluxeLib/Menu/CMenu.cs index af2e5443..01fcb9ab 100644 --- a/VocaluxeLib/Menu/CMenu.cs +++ b/VocaluxeLib/Menu/CMenu.cs @@ -339,6 +339,7 @@ namespace VocaluxeLib.Menu foreach (CNameSelection ns in _NameSelections) ns.UnloadTextures(); + foreach (CPlaylist pls in _Playlists) pls.UnloadTextures(); diff --git a/VocaluxeLib/Menu/CStatic.cs b/VocaluxeLib/Menu/CStatic.cs index 24b9b56c..327dfc14 100644 --- a/VocaluxeLib/Menu/CStatic.cs +++ b/VocaluxeLib/Menu/CStatic.cs @@ -188,43 +188,20 @@ namespace VocaluxeLib.Menu public void Draw(bool forceDraw = false) { - Draw(1f, Rect.Z, Aspect, forceDraw); + Draw(Aspect, 1f, 0f, forceDraw); } - public void Draw(EAspect aspect) - { - Draw(1f, Rect.Z, aspect); - } - - public void Draw(float scale, EAspect aspect) - { - Draw(scale, Rect.Z, aspect); - } - - public void Draw(float scale, float z, EAspect aspect, bool forceDraw = false) + public void Draw(EAspect aspect, float scale = 1f, float zModify = 0f, bool forceDraw = false) { CTexture texture = Texture ?? new CTexture((int)Rect.W, (int)Rect.H); - var bounds = new SRectF( - Rect.X - Rect.W * (scale - 1f), - Rect.Y - Rect.H * (scale - 1f), - Rect.W + 2 * Rect.W * (scale - 1f), - Rect.H + 2 * Rect.H * (scale - 1f), - z); - - SRectF rect = bounds; - + SRectF bounds = Rect.Scale(scale); + SRectF rect; if (aspect != EAspect.Stretch) - { - var bounds2 = new RectangleF(bounds.X, bounds.Y, bounds.W, bounds.H); - RectangleF rect2; - CHelper.SetRect(bounds2, out rect2, texture.OrigAspect, aspect); - - rect.X = rect2.X; - rect.Y = rect2.Y; - rect.W = rect2.Width; - rect.H = rect2.Height; - } + CHelper.SetRect(bounds, out rect, texture.OrigAspect, aspect); + else + rect = bounds; + rect.Z = Rect.Z + zModify; var color = new SColorF(Color.R, Color.G, Color.B, Color.A * Alpha); if (Visible || forceDraw || (CBase.Settings.GetProgramState() == EProgramState.EditTheme)) diff --git a/VocaluxeLib/Menu/SongMenu/CSongMenu.cs b/VocaluxeLib/Menu/SongMenu/CSongMenu.cs index 84e729b6..74bac712 100644 --- a/VocaluxeLib/Menu/SongMenu/CSongMenu.cs +++ b/VocaluxeLib/Menu/SongMenu/CSongMenu.cs @@ -33,16 +33,29 @@ namespace VocaluxeLib.Menu.SongMenu _CreateSongMenu(); } + #region ISongMenu public bool Selected { - get { return _SongMenu.IsSelected(); } - set { _SongMenu.SetSelected(value); } + get { return _SongMenu.Selected; } + set { _SongMenu.Selected = value; } } public bool Visible { - get { return _SongMenu.IsVisible(); } - set { _SongMenu.SetVisible(value); } + get { return _SongMenu.Visible; } + set { _SongMenu.Visible = value; } + } + + public bool Active + { + get { return _SongMenu.Active; } + set { _SongMenu.Active = value; } + } + + public bool SmallView + { + get { return _SongMenu.SmallView; } + set { _SongMenu.SmallView = value; } } public SRectF Rect @@ -50,7 +63,6 @@ namespace VocaluxeLib.Menu.SongMenu get { return _SongMenu.Rect; } } - #region ISongMenu public void Update(SScreenSongOptions songOptions) { _SongMenu.Update(songOptions); @@ -66,14 +78,14 @@ namespace VocaluxeLib.Menu.SongMenu _SongMenu.OnHide(); } - public void HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions songOptions) + public bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options) { - _SongMenu.HandleInput(ref keyEvent, songOptions); + return _SongMenu.HandleInput(ref keyEvent, options); } - public void HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) + public bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) { - _SongMenu.HandleMouse(ref mouseEvent, songOptions); + return _SongMenu.HandleMouse(ref mouseEvent, songOptions); } public void Draw() @@ -81,24 +93,19 @@ namespace VocaluxeLib.Menu.SongMenu _SongMenu.Draw(); } - public bool IsActive() + public bool IsMouseOverSelectedSong(SMouseEvent mEvent) { - return _SongMenu.IsActive(); + return _SongMenu.IsMouseOverSelectedSong(mEvent); } - public void SetActive(bool active) + public int GetPreviewSongNr() { - _SongMenu.SetActive(active); + return _SongMenu.GetPreviewSongNr(); } - public bool IsMouseOverActualSelection(SMouseEvent mEvent) + public int GetSelectedSongNr() { - return _SongMenu.IsMouseOverActualSelection(mEvent); - } - - public int GetSelectedSong() - { - return _SongMenu.GetSelectedSong(); + return _SongMenu.GetSelectedSongNr(); } public CStatic GetSelectedSongCover() @@ -121,44 +128,14 @@ namespace VocaluxeLib.Menu.SongMenu _SongMenu.SetSelectedCategory(categoryNr); } - public bool EnterCurrentCategory() + public bool EnterSelectedCategory() { - return _SongMenu.EnterCurrentCategory(); + return _SongMenu.EnterSelectedCategory(); } - public int GetActualSelection() + public int GetPreviewSong() { - return _SongMenu.GetActualSelection(); - } - - public bool IsSelected() - { - return _SongMenu.IsSelected(); - } - - public void SetSelected(bool selected) - { - _SongMenu.SetSelected(selected); - } - - public bool IsVisible() - { - return _SongMenu.IsVisible(); - } - - public void SetVisible(bool visible) - { - _SongMenu.SetVisible(visible); - } - - public bool IsSmallView() - { - return _SongMenu.IsSmallView(); - } - - public void SetSmallView(bool smallView) - { - _SongMenu.SetSmallView(smallView); + return _SongMenu.GetPreviewSong(); } #endregion ISongMenu diff --git a/VocaluxeLib/Menu/SongMenu/CSongMenuBook.cs b/VocaluxeLib/Menu/SongMenu/CSongMenuBook.cs index f1a372fa..a7b0510c 100644 --- a/VocaluxeLib/Menu/SongMenu/CSongMenuBook.cs +++ b/VocaluxeLib/Menu/SongMenu/CSongMenuBook.cs @@ -15,11 +15,33 @@ // along with Vocaluxe. If not, see . #endregion +using VocaluxeLib.PartyModes; + namespace VocaluxeLib.Menu.SongMenu { class CSongMenuBook : CSongMenuFramework { public CSongMenuBook(int partyModeID) : base(partyModeID) {} + + public override float SelectedTileZoomFactor + { + get { return 1.2f; } + } + + public override bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options) + { + return false; + } + + public override bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) + { + return false; + } + + public override CStatic GetSelectedSongCover() + { + return null; + } } } \ No newline at end of file diff --git a/VocaluxeLib/Menu/SongMenu/CSongMenuDreidel.cs b/VocaluxeLib/Menu/SongMenu/CSongMenuDreidel.cs index 14a668ed..318b053b 100644 --- a/VocaluxeLib/Menu/SongMenu/CSongMenuDreidel.cs +++ b/VocaluxeLib/Menu/SongMenu/CSongMenuDreidel.cs @@ -15,6 +15,8 @@ // along with Vocaluxe. If not, see . #endregion +using VocaluxeLib.PartyModes; + namespace VocaluxeLib.Menu.SongMenu { class CSongMenuDreidel : CSongMenuFramework @@ -30,13 +32,6 @@ namespace VocaluxeLib.Menu.SongMenu private CText _Artist; private CText _Title; private CText _SongLength; - - private int _actualSelection = -1; - - public override int GetActualSelection() - { - return _actualSelection; - } */ public CSongMenuDreidel(int partyModeID) @@ -59,5 +54,25 @@ namespace VocaluxeLib.Menu.SongMenu } // ReSharper restore RedundantOverridenMember + + public override float SelectedTileZoomFactor + { + get { return 1.2f; } + } + + public override bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options) + { + return false; + } + + public override bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) + { + return false; + } + + public override CStatic GetSelectedSongCover() + { + return null; + } } } \ No newline at end of file diff --git a/VocaluxeLib/Menu/SongMenu/CSongMenuFramework.cs b/VocaluxeLib/Menu/SongMenu/CSongMenuFramework.cs index e7f260f9..55f65a0d 100644 --- a/VocaluxeLib/Menu/SongMenu/CSongMenuFramework.cs +++ b/VocaluxeLib/Menu/SongMenu/CSongMenuFramework.cs @@ -16,7 +16,7 @@ #endregion using System; -using System.Collections.Generic; +using System.Diagnostics; using System.IO; using System.Xml; using VocaluxeLib.Draw; @@ -98,81 +98,70 @@ namespace VocaluxeLib.Menu.SongMenu protected SThemeSongMenu _Theme; private bool _ThemeLoaded; - private CFading _VideoFading; - private readonly List _Streams = new List(); - protected CTexture _Vidtex; - protected bool _Initialized; - protected int _LastKnownNumSongs; - protected int _LastKnownCategory = -1; - protected SColorF _Color; - - protected bool _Active; - - protected float _MaxVolume = 100f; - - //the real selected song for singing - protected int _Locked { get; set; } - - protected int _PreviewIdInternal = -1; - protected virtual int _PreviewId + private int _PreviewNrInternal = -1; + protected virtual int _PreviewNr { - get { return _PreviewIdInternal; } + get { return _PreviewNrInternal; } set { - //Do this first, otherwhise song will restart - _PlaySong(value); - _PreviewIdInternal = value; + if (_PreviewNrInternal == value) + return; + if (CBase.Songs.IsInCategory()) + { + if (value >= CBase.Songs.GetNumSongsVisible()) + value = -1; + _PlaySong(value); + } + else if (value >= CBase.Songs.GetNumCategories()) + value = -1; + + _PreviewNrInternal = value; } } protected int _PreviewSongStream { get; private set; } protected int _PreviewVideoStream { get; private set; } + private CFading _VideoFading; + protected CTexture _Vidtex; + + private SColorF _ColorInternal; + protected SColorF _Color + { + get { return _ColorInternal; } + } + + public int GetPreviewSong() + { + return _PreviewNr; + } public SRectF Rect { get; protected set; } - - public SColorF Color - { - get { return _Color; } - } - - public virtual int GetActualSelection() - { - return -1; - } - + public bool Active { get; set; } private bool _Selected; - private bool _Visible = true; - - public bool IsSelected() + public bool Selected { - return _Selected; - } - - public void SetSelected(bool selected) - { - _Selected = selected; - SetActive(selected); - } - - public bool IsVisible() - { - return _Visible; - } - - public void SetVisible(bool visible) - { - _Visible = visible; + get { return _Selected; } + set + { + _Selected = value; + Active = value; + } } + public bool Visible { get; set; } + public virtual bool SmallView { get; set; } + public abstract float SelectedTileZoomFactor { get; } + // This is the nr of the current selection (song or category) + protected virtual int _SelectionNr { get; set; } protected CSongMenuFramework(int partyModeID) { + Visible = true; _PartyModeID = partyModeID; _PreviewVideoStream = -1; _PreviewSongStream = -1; - _Locked = -1; _Theme = new SThemeSongMenu { SongMenuTileBoard = @@ -190,6 +179,7 @@ namespace VocaluxeLib.Menu.SongMenu }; } + #region Theme public string GetThemeName() { return _Theme.Name; @@ -208,13 +198,13 @@ namespace VocaluxeLib.Menu.SongMenu _ThemeLoaded &= xmlReader.GetValue(item + "/MedleyTagIcon", out _Theme.MedleyTagIcon, String.Empty); if (xmlReader.GetValue(item + "/Color", out _Theme.ColorName, String.Empty)) - _ThemeLoaded &= CBase.Theme.GetColor(_Theme.ColorName, skinIndex, out _Color); + _ThemeLoaded &= CBase.Theme.GetColor(_Theme.ColorName, skinIndex, out _ColorInternal); else { - _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/R", ref _Color.R); - _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/G", ref _Color.G); - _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/B", ref _Color.B); - _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/A", ref _Color.A); + _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/R", ref _ColorInternal.R); + _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/G", ref _ColorInternal.G); + _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/B", ref _ColorInternal.B); + _ThemeLoaded &= xmlReader.TryGetFloatValue(item + "/A", ref _ColorInternal.A); } #region SongMenuTileBoard @@ -352,25 +342,20 @@ namespace VocaluxeLib.Menu.SongMenu } return false; } + #endregion Theme public virtual void Init() { - _Reset(); + _ResetPreview(); _Initialized = true; } - public void UpdateRect(SRectF rect) - { - Rect = rect; - Init(); - } - public virtual void Update(SScreenSongOptions songOptions) { if (!_Initialized) return; - if (_Streams.Count <= 0 || _PreviewVideoStream == -1) + if (_PreviewSongStream == -1 || _PreviewVideoStream == -1) return; if (CBase.Video.IsFinished(_PreviewVideoStream) || CBase.Sound.IsFinished(_PreviewSongStream)) @@ -398,69 +383,72 @@ namespace VocaluxeLib.Menu.SongMenu } } - public virtual void OnShow() - { - _PreviewSongStream = -1; - _Vidtex = null; - } + public virtual void OnShow() {} public virtual void OnHide() { - _Reset(); + _ResetPreview(); } - public virtual void HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions songOptions) {} + public abstract bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options); - public virtual void HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) {} + public abstract bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions); public virtual void Draw() { - if (!_Initialized || !_Visible) + if (!_Initialized || !Visible) return; if (_PreviewVideoStream != -1) CBase.Drawing.DrawTexture(_Vidtex, new SRectF(0, 0, 1280, 720, 0)); } - public virtual bool IsActive() + public bool IsMouseOverSelectedSong(SMouseEvent mEvent) { - return _Active; + CStatic selCov = GetSelectedSongCover(); + return selCov != null && CHelper.IsInBounds(selCov.Rect.Scale(SelectedTileZoomFactor), mEvent); } - public virtual void SetActive(bool active) - { - _Active = active; - } - - public virtual bool IsMouseOverActualSelection(SMouseEvent mEvent) - { - return false; - } - - public virtual int GetSelectedSong() + public int GetPreviewSongNr() { + if (CBase.Songs.IsInCategory()) + return _PreviewNr; return -1; } - public virtual CStatic GetSelectedSongCover() - { - return new CStatic(_PartyModeID); - } - - public virtual int GetSelectedCategory() + public int GetSelectedSongNr() { + if (CBase.Songs.IsInCategory()) + return _SelectionNr; return -1; } - public virtual void SetSelectedSong(int visibleSongNr) {} + public abstract CStatic GetSelectedSongCover(); - public virtual void SetSelectedCategory(int categoryNr) {} - - public virtual void SetSmallView(bool smallView) {} - - public virtual bool IsSmallView() + public int GetSelectedCategory() { - return false; + if (!CBase.Songs.IsInCategory()) + return _SelectionNr; + return -1; + } + + public void SetSelectedSong(int visibleSongNr) + { + Debug.Assert(CBase.Songs.IsInCategory()); + if (visibleSongNr >= 0 && visibleSongNr < CBase.Songs.GetNumSongsVisible()) + _SelectionNr = visibleSongNr; + else + _SelectionNr = -1; + _PreviewNr = _SelectionNr; + } + + public void SetSelectedCategory(int categoryNr) + { + Debug.Assert(!CBase.Songs.IsInCategory()); + if (categoryNr >= 0 && categoryNr < CBase.Songs.GetNumCategories()) + _SelectionNr = categoryNr; + else + _SelectionNr = -1; } public virtual void UnloadTextures() {} @@ -470,7 +458,7 @@ namespace VocaluxeLib.Menu.SongMenu Init(); if (!String.IsNullOrEmpty(_Theme.ColorName)) - _Color = CBase.Theme.GetColor(_Theme.ColorName, _PartyModeID); + _ColorInternal = CBase.Theme.GetColor(_Theme.ColorName, _PartyModeID); } public void ReloadTextures() @@ -479,29 +467,29 @@ namespace VocaluxeLib.Menu.SongMenu LoadTextures(); } - public bool EnterCurrentCategory() + public bool EnterSelectedCategory() { if (!_Initialized) return false; - if (CBase.Songs.IsInCategory() || _PreviewId < 0 || _PreviewId >= CBase.Songs.GetNumCategories()) + if (CBase.Songs.IsInCategory() || GetSelectedCategory() < 0 || GetSelectedCategory() >= CBase.Songs.GetNumCategories()) return false; - _EnterCategory(_PreviewId); + _EnterCategory(GetSelectedCategory()); return true; } - protected virtual void _EnterCategory(int category) + protected virtual void _EnterCategory(int categoryNr) { if (!_Initialized) return; - if (category >= CBase.Songs.GetNumCategories()) + if (categoryNr >= CBase.Songs.GetNumCategories()) return; - _Reset(); - CBase.Songs.SetCategory(category); + _ResetPreview(); + CBase.Songs.SetCategory(categoryNr); } - protected virtual void _ShowCategories() + protected virtual void _LeaveCategory() { if (!_Initialized) return; @@ -509,60 +497,51 @@ namespace VocaluxeLib.Menu.SongMenu if (!CBase.Songs.IsInCategory()) return; - _Reset(); + _ResetPreview(); CBase.Songs.SetCategory(-1); } - protected void _PlaySong(int nr) + private void _PlaySong(int nr) { - if (CBase.Songs.IsInCategory() && (_PreviewId != nr || _Streams.Count == 0)) + _ResetPreview(); + + CSong song = CBase.Songs.GetVisibleSong(nr); + if (song == null) + return; + + //TODO: Using prescan here causes Vocaluxe to hang a bit on loading the song but we need the length below + _PreviewSongStream = CBase.Sound.Load(Path.Combine(song.Folder, song.MP3FileName), true, true); + + float startposition = song.Preview.StartTime; + float length = CBase.Sound.GetLength(_PreviewSongStream); + + if (song.Preview.Source == EDataSource.None) + startposition = length / 4f; + else if (startposition > length - 5f) + startposition = Math.Max(0f, Math.Min(length / 4f, length - 5f)); + + CBase.Sound.SetPosition(_PreviewSongStream, startposition); + CBase.Sound.Play(_PreviewSongStream); + CBase.Sound.SetStreamVolume(_PreviewSongStream, 0f); + CBase.Sound.Fade(_PreviewSongStream, 100f, 3f); + + if (song.VideoFileName != "" && CBase.Config.GetVideoPreview() == EOffOn.TR_CONFIG_ON) { - _Reset(); - - CSong song = CBase.Songs.GetVisibleSong(nr); - if (song == null) + _PreviewVideoStream = CBase.Video.Load(Path.Combine(song.Folder, song.VideoFileName)); + if (_PreviewVideoStream == -1) return; - - //TODO: Using prescan here causes Vocaluxe to hang a bit on loading the song but we need the length below - int stream = CBase.Sound.Load(Path.Combine(song.Folder, song.MP3FileName), true, true); - - float startposition = song.Preview.StartTime; - float length = CBase.Sound.GetLength(stream); - - if (song.Preview.Source == EDataSource.None) - startposition = length / 4f; - else if (startposition > length - 5f) - startposition = Math.Max(0f, Math.Min(length / 4f, length - 5f)); - - if (startposition >= 0.5f) - startposition -= 0.5f; - - CBase.Sound.SetPosition(stream, startposition); - CBase.Sound.Play(stream); - CBase.Sound.SetStreamVolume(stream, 0f); - CBase.Sound.Fade(stream, 100f, 3f); - _Streams.Add(stream); - _PreviewSongStream = stream; - - _PreviewIdInternal = nr; - - if (song.VideoFileName != "" && CBase.Config.GetVideoPreview() == EOffOn.TR_CONFIG_ON) - { - _PreviewVideoStream = CBase.Video.Load(Path.Combine(song.Folder, song.VideoFileName)); - if (_PreviewVideoStream == -1) - return; - CBase.Video.SetLoop(_PreviewVideoStream); - CBase.Video.Skip(_PreviewVideoStream, startposition, song.VideoGap); - _VideoFading = new CFading(0f, 1f, 3f); - } + CBase.Video.SetLoop(_PreviewVideoStream); + CBase.Video.Skip(_PreviewVideoStream, startposition, song.VideoGap); + _VideoFading = new CFading(0f, 1f, 3f); } } - protected void _Reset() + protected void _ResetPreview() { - foreach (int stream in _Streams) - CBase.Sound.FadeAndClose(stream, 0f, 0.75f); - _Streams.Clear(); + if (_PreviewSongStream >= 0) + CBase.Sound.FadeAndClose(_PreviewSongStream, 0f, 0.75f); + + _PreviewSongStream = -1; CBase.Video.Close(_PreviewVideoStream); _PreviewVideoStream = -1; @@ -571,12 +550,18 @@ namespace VocaluxeLib.Menu.SongMenu } #region ThemeEdit + private void _UpdateRect(SRectF rect) + { + Rect = rect; + Init(); + } + public void MoveElement(int stepX, int stepY) { SRectF rect = Rect; rect.X += stepX; rect.Y += stepY; - UpdateRect(rect); + _UpdateRect(rect); } public void ResizeElement(int stepW, int stepH) @@ -591,7 +576,7 @@ namespace VocaluxeLib.Menu.SongMenu if (rect.H < 100) rect.H = 100; - UpdateRect(rect); + _UpdateRect(rect); } #endregion ThemeEdit } diff --git a/VocaluxeLib/Menu/SongMenu/CSongMenuList.cs b/VocaluxeLib/Menu/SongMenu/CSongMenuList.cs index 655fa404..9c5b7a6e 100644 --- a/VocaluxeLib/Menu/SongMenu/CSongMenuList.cs +++ b/VocaluxeLib/Menu/SongMenu/CSongMenuList.cs @@ -15,11 +15,30 @@ // along with Vocaluxe. If not, see . #endregion +using VocaluxeLib.PartyModes; + namespace VocaluxeLib.Menu.SongMenu { class CSongMenuList : CSongMenuFramework { public CSongMenuList(int partyModeID) : base(partyModeID) {} + + public override float SelectedTileZoomFactor + { + get { return 1.2f; } + } + + public override bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options) + { + return false; + } + + public override bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) { return false; } + + public override CStatic GetSelectedSongCover() + { + return null; + } } } \ No newline at end of file diff --git a/VocaluxeLib/Menu/SongMenu/CSongMenuTileBoard.cs b/VocaluxeLib/Menu/SongMenu/CSongMenuTileBoard.cs index 1fef5094..9fd47088 100644 --- a/VocaluxeLib/Menu/SongMenu/CSongMenuTileBoard.cs +++ b/VocaluxeLib/Menu/SongMenu/CSongMenuTileBoard.cs @@ -37,8 +37,8 @@ namespace VocaluxeLib.Menu.SongMenu private CStatic _MedleyCalcIcon; private CStatic _MedleyTagIcon; - private CTexture _CoverBigTexture; - private CTexture _CoverTexture; + private CTexture _CoverBigBGTexture; + private CTexture _CoverBGTexture; private CText _Artist; private CText _Title; @@ -53,63 +53,68 @@ namespace VocaluxeLib.Menu.SongMenu private int _TileW; private int _TileH; - private int _Offset = -1; - private int _ActualSelection = -1; - - private bool _SmallView; + // Offset is the song or categoryNr of the tile in the left upper corner + private int _Offset; private float _Length = -1f; + private int _LastKnownNumSongs; + private int _LastKnownCategory = -1; + + public override float SelectedTileZoomFactor + { + get { return 1.2f; } + } + + protected override int _SelectionNr + { + set + { + int max = CBase.Songs.IsInCategory() ? CBase.Songs.GetNumSongsVisible() : CBase.Songs.GetNumCategories(); + base._SelectionNr = value.Clamp(-1, max - 1); + //Update list in case we scrolled + _UpdateList(); + + foreach (CStatic tile in _Tiles) + tile.Selected = false; + int tileNr = _SelectionNr - _Offset; + if (tileNr >= 0 && tileNr < _Tiles.Count) + _Tiles[tileNr].Selected = true; + } + } + + public override bool SmallView + { + set + { + if (SmallView == value) + return; + base.SmallView = value; + _InitTiles(); + _UpdateList(true); + } + } public CSongMenuTileBoard(int partyModeID) : base(partyModeID) {} - protected override int _PreviewId + protected override int _PreviewNr { set { - if (value == base._PreviewId) + if (value == base._PreviewNr) return; - base._PreviewId = value; + base._PreviewNr = value; _UpdatePreview(); } } - public override int GetActualSelection() - { - return _ActualSelection; - } - public override void Init() { base.Init(); - Rect = _Theme.SongMenuTileBoard.TileRect; - - _NumW = _Theme.SongMenuTileBoard.NumW; - _NumH = _Theme.SongMenuTileBoard.NumH; _SpaceW = _Theme.SongMenuTileBoard.SpaceW; _SpaceH = _Theme.SongMenuTileBoard.SpaceH; - _TileW = (int)((_Theme.SongMenuTileBoard.TileRect.W - _SpaceW * (_NumW - 1)) / _NumW); - _TileH = (int)((_Theme.SongMenuTileBoard.TileRect.H - _SpaceH * (_NumH - 1)) / _NumH); - - _CoverTexture = CBase.Theme.GetSkinTexture(_Theme.CoverBackgroundName, _PartyModeID); - _CoverBigTexture = CBase.Theme.GetSkinTexture(_Theme.CoverBigBackgroundName, _PartyModeID); - - _Tiles = new List(); - for (int i = 0; i < _NumH; i++) - { - for (int j = 0; j < _NumW; j++) - { - var rect = new SRectF(_Theme.SongMenuTileBoard.TileRect.X + j * (_TileW + _SpaceW), - _Theme.SongMenuTileBoard.TileRect.Y + i * (_TileH + _SpaceH), _TileW, _TileH, Rect.Z); - var tile = new CStatic(_PartyModeID, _CoverTexture, Color, rect); - _Tiles.Add(tile); - } - } - - _ScrollRect = new SRectF(0, 0, CBase.Settings.GetRenderW(), CBase.Settings.GetRenderH(), _Theme.SongMenuTileBoard.TileRect.Z); - _CoverBig = _Theme.SongMenuTileBoard.StaticCoverBig; _TextBG = _Theme.SongMenuTileBoard.StaticTextBG; _DuetIcon = _Theme.SongMenuTileBoard.StaticDuetIcon; @@ -121,8 +126,42 @@ namespace VocaluxeLib.Menu.SongMenu _Title = _Theme.SongMenuTileBoard.TextTitle; _SongLength = _Theme.SongMenuTileBoard.TextSongLength; - _PreviewId = -1; - _Offset = 0; + _PreviewNr = -1; + _InitTiles(); + } + + private void _InitTiles() + { + if (SmallView) + { + _NumH = _Theme.SongMenuTileBoard.NumHsmall; + _NumW = _Theme.SongMenuTileBoard.NumWsmall; + Rect = _Theme.SongMenuTileBoard.TileRectSmall; + } + else + { + _NumH = _Theme.SongMenuTileBoard.NumH; + _NumW = _Theme.SongMenuTileBoard.NumW; + Rect = _Theme.SongMenuTileBoard.TileRect; + } + + _TileW = (int)((Rect.W - _SpaceW * (_NumW - 1)) / _NumW); + _TileH = (int)((Rect.H - _SpaceH * (_NumH - 1)) / _NumH); + + _CoverBGTexture = CBase.Theme.GetSkinTexture(_Theme.CoverBackgroundName, _PartyModeID); + _CoverBigBGTexture = CBase.Theme.GetSkinTexture(_Theme.CoverBigBackgroundName, _PartyModeID); + + _Tiles = new List(); + for (int i = 0; i < _NumH; i++) + { + for (int j = 0; j < _NumW; j++) + { + var rect = new SRectF(Rect.X + j * (_TileW + _SpaceW), Rect.Y + i * (_TileH + _SpaceH), _TileW, _TileH, Rect.Z); + var tile = new CStatic(_PartyModeID, _CoverBGTexture, _Color, rect); + _Tiles.Add(tile); + } + } + _ScrollRect = new SRectF(0, 0, CBase.Settings.GetRenderW(), CBase.Settings.GetRenderH(), Rect.Z); } public override void Update(SScreenSongOptions songOptions) @@ -130,21 +169,16 @@ namespace VocaluxeLib.Menu.SongMenu base.Update(songOptions); if (songOptions.Selection.RandomOnly) - { - _Locked = _PreviewId; - _ActualSelection = _PreviewId; - for (int i = 0; i < _Tiles.Count; i++) - _Tiles[i].Selected = _Locked == i + _Offset; - } + _PreviewNr = _SelectionNr; if (_Length < 0 && CBase.Songs.IsInCategory() && CBase.Sound.GetLength(_PreviewSongStream) > 0) - _UpdateLength(CBase.Songs.GetVisibleSong(_PreviewId)); + _UpdateLength(CBase.Songs.GetVisibleSong(_PreviewNr)); } private void _UpdatePreview() { //First hide everything so we just have to set what we actually want - _CoverBig.Texture = _CoverBigTexture; + _CoverBig.Texture = _CoverBigBGTexture; _Artist.Text = String.Empty; _Title.Text = String.Empty; _SongLength.Text = String.Empty; @@ -155,12 +189,12 @@ namespace VocaluxeLib.Menu.SongMenu _Length = -1f; //Check if nothing is selected (for preview) - if (_PreviewId < 0) + if (_PreviewNr < 0) return; if (CBase.Songs.IsInCategory()) { - CSong song = CBase.Songs.GetVisibleSong(_PreviewId); + CSong song = CBase.Songs.GetVisibleSong(_PreviewNr); //Check if we have a valid song (song still visible, index >=0 etc is checked by framework) if (song == null) { @@ -185,7 +219,7 @@ namespace VocaluxeLib.Menu.SongMenu } else { - CCategory category = CBase.Songs.GetCategory(_PreviewId); + CCategory category = CBase.Songs.GetCategory(_PreviewNr); //Check if we have a valid category if (category == null) return; @@ -223,250 +257,203 @@ namespace VocaluxeLib.Menu.SongMenu { if (CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_OFF && CBase.Songs.GetNumCategories() > 0 && !CBase.Songs.IsInCategory()) _EnterCategory(0); - _ActualSelection = -1; - _Locked = -1; - _UpdateList(0, true); - //AfterCategoryChange(); - SetSelectedSong(_PreviewId); - _AfterCategoryChange(); - - if (_PreviewId < 0) + else { - _PreviewId = 0; - _Locked = 0; - } - - if (CBase.Songs.GetNumSongsVisible() == 0 && CBase.Songs.GetSearchFilter() != "") - { - _PreviewId = -1; - _Locked = -1; - } - } - - public override void HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions songOptions) - { - base.HandleInput(ref keyEvent, songOptions); - - if (!keyEvent.KeyPressed) - { - if (!(keyEvent.Key == Keys.Left || keyEvent.Key == Keys.Right || keyEvent.Key == Keys.Up || keyEvent.Key == Keys.Down || - keyEvent.Key == Keys.Escape || keyEvent.Key == Keys.Back || keyEvent.Key == Keys.Enter || - keyEvent.Key == Keys.PageDown || keyEvent.Key == Keys.PageUp)) - return; - - bool sel = _Tiles.Any(tile => tile.Selected); - - if ((_Locked == -1 || !sel) && - (keyEvent.Key != Keys.Escape && keyEvent.Key != Keys.Back && keyEvent.Key != Keys.PageUp && keyEvent.Key != Keys.PageDown)) + if (CBase.Songs.IsInCategory()) { - if (_PreviewId > -1) - _Locked = _PreviewId; + if (_SelectionNr < 0) + SetSelectedSong(0); else - { - _Locked = 0; - _ActualSelection = 0; - _PreviewId = 0; - _UpdateList(0, true); - } + SetSelectedSong(_SelectionNr); } else { - switch (keyEvent.Key) - { - case Keys.Enter: - if (!CBase.Songs.IsInCategory()) - { - _EnterCategory(_PreviewId); - keyEvent.Handled = true; - } - else if (_ActualSelection > -1 && _PreviewId >= 0) - _Locked = _ActualSelection; - break; - - case Keys.Escape: - case Keys.Back: - if (CBase.Songs.IsInCategory() && CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && songOptions.Selection.CategoryChangeAllowed) - { - _ShowCategories(); - keyEvent.Handled = true; - } - //else if (CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_OFF) - //{ - // CGraphics.FadeTo(EScreens.ScreenMain); - //} - break; - - case Keys.PageUp: - if (CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && songOptions.Selection.CategoryChangeAllowed) - _PrevCategory(); - break; - - case Keys.PageDown: - if (CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && songOptions.Selection.CategoryChangeAllowed) - _NextCategory(); - break; - - case Keys.Left: - if (_Locked > 0 && (!songOptions.Selection.RandomOnly || songOptions.Selection.CategoryChangeAllowed && !CBase.Songs.IsInCategory())) - { - _Locked--; - _UpdateList(); - } - break; - - case Keys.Right: - if (!CBase.Songs.IsInCategory() && songOptions.Selection.CategoryChangeAllowed) - { - if (_Locked < CBase.Songs.GetNumCategories() - 1) - { - _Locked++; - _UpdateList(); - } - } - else - { - if (CBase.Songs.IsInCategory() && _Locked < CBase.Songs.GetNumSongsVisible() - 1 && !songOptions.Selection.RandomOnly) - { - _Locked++; - _UpdateList(); - } - } - break; - - case Keys.Up: - if (keyEvent.ModShift && CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && songOptions.Selection.CategoryChangeAllowed) - { - _PrevCategory(); - break; - } - - if (_Locked > _NumW - 1 && - (!songOptions.Selection.RandomOnly || songOptions.Selection.CategoryChangeAllowed && !CBase.Songs.IsInCategory())) - { - _Locked -= _NumW; - _UpdateList(); - } - break; - - case Keys.Down: - if (keyEvent.ModShift && CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && songOptions.Selection.CategoryChangeAllowed) - { - _NextCategory(); - break; - } - - if (!CBase.Songs.IsInCategory() && songOptions.Selection.CategoryChangeAllowed) - { - if (_Locked < CBase.Songs.GetNumCategories() - _NumW) - { - _Locked += _NumW; - _UpdateList(); - } - } - else if (_Locked < CBase.Songs.GetNumSongsVisible() - _NumW && !songOptions.Selection.RandomOnly) - { - _Locked += _NumW; - _UpdateList(); - } - break; - } - } - - if (!keyEvent.Handled) - { - _ActualSelection = _Locked; - _PreviewId = _Locked; - - for (int i = 0; i < _Tiles.Count; i++) - _Tiles[i].Selected = _Locked == i + _Offset; + if (_SelectionNr < 0) + SetSelectedCategory(0); + else + SetSelectedCategory(_SelectionNr); } } + _PreviewNr = _SelectionNr; + _AfterCategoryChange(); } - public override void HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) + public override bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options) { - base.HandleMouse(ref mouseEvent, songOptions); + if (keyEvent.KeyPressed) + return false; - int i = 0; - bool sel = false; - int lastselection = _ActualSelection; + bool moveAllowed = !options.Selection.RandomOnly || (options.Selection.CategoryChangeAllowed && !CBase.Songs.IsInCategory()); + bool catChangePossible = CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && options.Selection.CategoryChangeAllowed; - if (!songOptions.Selection.RandomOnly || (!CBase.Songs.IsInCategory() && songOptions.Selection.CategoryChangeAllowed)) + //If nothing selected set a reasonable default value + if (keyEvent.IsArrowKey() && moveAllowed && _SelectionNr < 0) + _SelectionNr = (_PreviewNr < 0) ? _Offset : _PreviewNr; + + switch (keyEvent.Key) { - foreach (CStatic tile in _Tiles) - { - if (tile.Texture != _CoverTexture && CHelper.IsInBounds(tile.Rect, mouseEvent) && !sel) + case Keys.Enter: + if (CBase.Songs.IsInCategory()) { - if (mouseEvent.LB || !CBase.Songs.IsInCategory()) + if (_SelectionNr >= 0 && _PreviewNr != _SelectionNr) { - if (_PreviewId == i + _Offset) - _Locked = _PreviewId; - else - { - _PreviewId = i + _Offset; - _Locked = -1; - } + _PreviewNr = _SelectionNr; + keyEvent.Handled = true; } - tile.Selected = true; - _ActualSelection = i + _Offset; - sel = true; } else - tile.Selected = false; - i++; - } - } - else - sel = true; + { + _EnterCategory(_PreviewNr); + keyEvent.Handled = true; + } + break; - if (mouseEvent.Sender == ESender.WiiMote && _ActualSelection != lastselection && _ActualSelection != -1) - CBase.Controller.SetRumble(0.050f); + case Keys.Escape: + case Keys.Back: + if (CBase.Songs.IsInCategory() && catChangePossible) + { + _LeaveCategory(); + keyEvent.Handled = true; + } + break; - if (!sel) - _ActualSelection = -1; + case Keys.PageUp: + if (catChangePossible) + { + _PrevCategory(); + keyEvent.Handled = true; + } + break; - if (mouseEvent.RB && (CBase.Songs.GetNumCategories() > 0) && CBase.Songs.IsInCategory() && CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && - songOptions.Selection.CategoryChangeAllowed) - { - _ShowCategories(); - mouseEvent.Handled = true; - return; + case Keys.PageDown: + if (catChangePossible) + { + _NextCategory(); + keyEvent.Handled = true; + } + break; + + case Keys.Left: + //Check for >0 so we do not allow selection of nothing (-1) + if (_SelectionNr > 0 && moveAllowed) + { + _SelectionNr--; + keyEvent.Handled = true; + } + break; + + case Keys.Right: + if (moveAllowed) + { + _SelectionNr++; + keyEvent.Handled = true; + } + break; + + case Keys.Up: + if (keyEvent.ModShift) + { + if (catChangePossible) + { + _PrevCategory(); + keyEvent.Handled = true; + } + } + else if (_SelectionNr >= _NumW && moveAllowed) + { + _SelectionNr -= _NumW; + keyEvent.Handled = true; + } + break; + + case Keys.Down: + if (keyEvent.ModShift) + { + if (catChangePossible) + { + _NextCategory(); + keyEvent.Handled = true; + } + } + else if (moveAllowed) + { + _SelectionNr += _NumW; + keyEvent.Handled = true; + } + break; } - if (mouseEvent.RB && CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_OFF && !songOptions.Selection.PartyMode) - CBase.Graphics.FadeTo(EScreens.ScreenMain); - else if (_PreviewId != -1 && mouseEvent.LB && CBase.Songs.GetCurrentCategoryIndex() != -1 && !songOptions.Selection.PartyMode) - { - if (CHelper.IsInBounds(_CoverBig.Rect, mouseEvent) || CHelper.IsInBounds(_TextBG.Rect, mouseEvent)) - _Locked = _PreviewId; - } - else if (mouseEvent.LB && (!CBase.Songs.IsInCategory())) + if (!CBase.Songs.IsInCategory()) + _PreviewNr = _SelectionNr; + return keyEvent.Handled; + } + + public override bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions) + { + if (!songOptions.Selection.RandomOnly || (!CBase.Songs.IsInCategory() && songOptions.Selection.CategoryChangeAllowed)) { + if (mouseEvent.Wheel != 0 && CHelper.IsInBounds(_ScrollRect, mouseEvent)) + _UpdateList(_Offset + _NumW * mouseEvent.Wheel); + + int lastSelection = _SelectionNr; + int i = 0; foreach (CStatic tile in _Tiles) { - if (tile.Texture != _CoverTexture && CHelper.IsInBounds(tile.Rect, mouseEvent)) + if (tile.Texture != _CoverBGTexture && CHelper.IsInBounds(tile.Rect, mouseEvent)) { - _EnterCategory(_PreviewId); - mouseEvent.Handled = true; - return; + _SelectionNr = i + _Offset; + if (!CBase.Songs.IsInCategory()) + _PreviewNr = i + _Offset; + break; } + i++; } + if (mouseEvent.Sender == ESender.WiiMote && _SelectionNr != lastSelection && _SelectionNr != -1) + CBase.Controller.SetRumble(0.050f); } - if (mouseEvent.Wheel != 0 && CHelper.IsInBounds(_ScrollRect, mouseEvent) && - (!songOptions.Selection.RandomOnly || !CBase.Songs.IsInCategory() && songOptions.Selection.CategoryChangeAllowed)) - _UpdateList(_Offset + _NumW * mouseEvent.Wheel); + + if (mouseEvent.RB) + { + if (CBase.Songs.IsInCategory() && CBase.Songs.GetNumCategories() > 0 && CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_ON && + songOptions.Selection.CategoryChangeAllowed) + { + _LeaveCategory(); + return true; + } + if (CBase.Songs.GetTabs() == EOffOn.TR_CONFIG_OFF && !songOptions.Selection.PartyMode) + { + CBase.Graphics.FadeTo(EScreens.ScreenMain); + return true; + } + } + else if (mouseEvent.LB) + { + if (_SelectionNr >= 0) + { + if (CBase.Songs.IsInCategory()) + { + if (_PreviewNr == _SelectionNr) + return false; + _PreviewNr = _SelectionNr; + } + else + EnterSelectedCategory(); + return true; + } + } + return false; } public override void Draw() { foreach (CStatic tile in _Tiles) { - if (tile.Selected && _Active) - tile.Draw(1.2f, tile.Rect.Z - 0.1f, EAspect.Crop); + if (tile.Selected && Active) + tile.Draw(EAspect.Crop, SelectedTileZoomFactor, -0.1f); else { - EAspect aspect = (tile.Texture != _CoverTexture) ? EAspect.Crop : EAspect.Stretch; - tile.Draw(1f, tile.Rect.Z, aspect); + EAspect aspect = (tile.Texture != _CoverBGTexture) ? EAspect.Crop : EAspect.Stretch; + tile.Draw(aspect); } } @@ -475,7 +462,7 @@ namespace VocaluxeLib.Menu.SongMenu if (_Vidtex != null && _PreviewVideoStream != -1) { if (_Vidtex.Color.A < 1) - _CoverBig.Draw(1f, EAspect.Crop); + _CoverBig.Draw(EAspect.Crop); var bounds = new RectangleF(_CoverBig.Rect.X, _CoverBig.Rect.Y, _CoverBig.Rect.W, _CoverBig.Rect.H); RectangleF rect; CHelper.SetRect(bounds, out rect, _Vidtex.OrigAspect, EAspect.Crop); @@ -486,7 +473,7 @@ namespace VocaluxeLib.Menu.SongMenu CBase.Drawing.DrawTextureReflection(_Vidtex, vidRect, _Vidtex.Color, vidRectBounds, _CoverBig.ReflectionSpace, _CoverBig.ReflectionHeight); } else - _CoverBig.Draw(1f, EAspect.Crop); + _CoverBig.Draw(EAspect.Crop); _Artist.Draw(); @@ -498,104 +485,32 @@ namespace VocaluxeLib.Menu.SongMenu _MedleyTagIcon.Draw(); } - public override int GetSelectedSong() - { - return _Locked; - } - - public override bool IsMouseOverActualSelection(SMouseEvent mEvent) - { - CStatic selCov = GetSelectedSongCover(); - if (selCov.Texture == null) - return false; - var rect = new SRectF(selCov.Rect.X - selCov.Rect.W * 0.2f, selCov.Rect.Y - selCov.Rect.H * 0.2f, selCov.Rect.W * 1.2f, selCov.Rect.H * 1.2f, selCov.Rect.Z); - return CHelper.IsInBounds(rect, mEvent); - } - public override CStatic GetSelectedSongCover() { - foreach (CStatic tile in _Tiles) - { - if (tile.Selected) - return new CStatic(tile); - } - return new CStatic(_PartyModeID); + return _Tiles.FirstOrDefault(tile => tile.Selected); } - private void _SetSelectedTile(int itemNr) + protected override void _EnterCategory(int categoryNr) { - bool sel = _Tiles.Any(tile => tile.Selected); + base._EnterCategory(categoryNr); - if (_Locked == -1 || !sel) - { - if (_PreviewId > -1) - _Locked = _PreviewId; - else - { - _Locked = 0; - _ActualSelection = 0; - _PreviewId = 0; - _UpdateList(0, true); - } - } - - foreach (CStatic tile in _Tiles) - tile.Selected = false; - - _PreviewId = itemNr; - _Locked = itemNr; - - _UpdateList(true); - - _PreviewId = _Locked; - _ActualSelection = _Locked; - - if (_Locked - _Offset >= 0) - _Tiles[_Locked - _Offset].Selected = true; - } - - public override void SetSelectedSong(int visibleSongNr) - { - _PlaySong(visibleSongNr); - base.SetSelectedSong(visibleSongNr); - - if (visibleSongNr >= 0 && visibleSongNr < CBase.Songs.GetNumSongsVisible()) - _SetSelectedTile(visibleSongNr); - } - - public override void SetSelectedCategory(int categoryNr) - { - base.SetSelectedCategory(categoryNr); - - if (categoryNr >= 0 && categoryNr < CBase.Songs.GetNumCategories()) - _SetSelectedTile(categoryNr); - } - - protected override void _EnterCategory(int cat) - { - base._EnterCategory(cat); - - _PreviewId = 0; - _Locked = -1; - _ActualSelection = 0; + _PreviewNr = 0; + SetSelectedSong(0); _AfterCategoryChange(); - _Locked = 0; } - protected override void _ShowCategories() + protected override void _LeaveCategory() { - base._ShowCategories(); + base._LeaveCategory(); - _PreviewId = 0; - _Locked = -1; - _ActualSelection = 0; + _PreviewNr = 0; + SetSelectedCategory(0); _AfterCategoryChange(); - _Locked = 0; } private void _NextCategory() { - if (CBase.Songs.GetCurrentCategoryIndex() > -1) + if (CBase.Songs.IsInCategory()) { CBase.Songs.NextCategory(); _EnterCategory(CBase.Songs.GetCurrentCategoryIndex()); @@ -604,7 +519,7 @@ namespace VocaluxeLib.Menu.SongMenu private void _PrevCategory() { - if (CBase.Songs.GetCurrentCategoryIndex() > -1) + if (CBase.Songs.IsInCategory()) { CBase.Songs.PrevCategory(); _EnterCategory(CBase.Songs.GetCurrentCategoryIndex()); @@ -613,24 +528,30 @@ namespace VocaluxeLib.Menu.SongMenu private void _AfterCategoryChange() { - foreach (CStatic tile in _Tiles) - tile.Selected = false; - - if (_ActualSelection >= 0 && _ActualSelection < _Tiles.Count) - _Tiles[_ActualSelection].Selected = true; - if ((_LastKnownNumSongs == CBase.Songs.GetNumSongsVisible()) && (_LastKnownCategory == CBase.Songs.GetCurrentCategoryIndex())) return; _LastKnownCategory = CBase.Songs.GetCurrentCategoryIndex(); _LastKnownNumSongs = CBase.Songs.GetNumSongsVisible(); - _UpdateList(0, true); CBase.Songs.UpdateRandomSongList(); + _UpdateList(true); + } + + private int _GetOffsetForPosition(int index, int rowNum = 0) + { + return (index / _NumW) * _NumW - (_NumW * rowNum.Clamp(0, _NumH - 1)); } private void _UpdateList(bool force = false) { - _UpdateList((_Locked / _NumW) * _NumW - (_NumW * (_NumH - 2)), force); + int offset; + if (_SelectionNr < _Offset && _SelectionNr >= 0) + offset = _GetOffsetForPosition(_SelectionNr); + else if (_SelectionNr >= _Offset + _NumW * _NumH) + offset = _GetOffsetForPosition(_SelectionNr, _NumH); + else + offset = _Offset; + _UpdateList(offset, force); } private void _UpdateList(int offset, bool force = false) @@ -638,11 +559,7 @@ namespace VocaluxeLib.Menu.SongMenu bool isInCategory = CBase.Songs.IsInCategory(); int itemCount = isInCategory ? CBase.Songs.GetNumSongsVisible() : CBase.Songs.GetNumCategories(); - if (offset >= (itemCount / _NumW) * _NumW - (_NumW * (_NumH - 1))) - offset = (itemCount / _NumW) * _NumW - (_NumW * (_NumH - 1)); - - if (offset < 0) - offset = 0; + offset = offset.Clamp(0, _GetOffsetForPosition(itemCount, _NumH - 1)); if (offset == _Offset && !force) return; @@ -656,58 +573,13 @@ namespace VocaluxeLib.Menu.SongMenu } else { - _Tiles[i].Texture = _CoverTexture; + _Tiles[i].Texture = _CoverBGTexture; _Tiles[i].Color = _Color; } } _Offset = offset; } - public override void SetSmallView(bool smallView) - { - base.SetSmallView(smallView); - - _SmallView = smallView; - - if (_SmallView) - { - _NumH = _Theme.SongMenuTileBoard.NumHsmall; - _NumW = _Theme.SongMenuTileBoard.NumWsmall; - Rect = _Theme.SongMenuTileBoard.TileRectSmall; - } - else - { - _NumH = _Theme.SongMenuTileBoard.NumH; - _NumW = _Theme.SongMenuTileBoard.NumW; - Rect = _Theme.SongMenuTileBoard.TileRect; - } - - _TileW = (int)((Rect.W - _SpaceW * (_NumW - 1)) / _NumW); - _TileH = (int)((Rect.H - _SpaceH * (_NumH - 1)) / _NumH); - - _CoverTexture = CBase.Theme.GetSkinTexture(_Theme.CoverBackgroundName, _PartyModeID); - _CoverBigTexture = CBase.Theme.GetSkinTexture(_Theme.CoverBigBackgroundName, _PartyModeID); - - _Tiles = new List(); - for (int i = 0; i < _NumH; i++) - { - for (int j = 0; j < _NumW; j++) - { - var rect = new SRectF(Rect.X + j * (_TileW + _SpaceW), Rect.Y + i * (_TileH + _SpaceH), _TileW, _TileH, Rect.Z); - var tile = new CStatic(_PartyModeID, _CoverTexture, Color, rect); - _Tiles.Add(tile); - } - } - - _ScrollRect = new SRectF(0, 0, CBase.Settings.GetRenderW(), CBase.Settings.GetRenderH(), Rect.Z); - _UpdateList(true); - } - - public override bool IsSmallView() - { - return _SmallView; - } - public override void LoadTextures() { base.LoadTextures(); diff --git a/VocaluxeLib/Menu/SongMenu/ISongMenu.cs b/VocaluxeLib/Menu/SongMenu/ISongMenu.cs index e1ea8998..fbd9a116 100644 --- a/VocaluxeLib/Menu/SongMenu/ISongMenu.cs +++ b/VocaluxeLib/Menu/SongMenu/ISongMenu.cs @@ -25,34 +25,30 @@ namespace VocaluxeLib.Menu.SongMenu void OnShow(); void OnHide(); - void HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions songOptions); - void HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions); + bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options); + bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions); void Draw(); - int GetSelectedSong(); + // The selected song is the song, where the mouse is hovering over + // The number is refering to the index in the visible songs array + int GetPreviewSongNr(); + int GetSelectedSongNr(); CStatic GetSelectedSongCover(); void SetSelectedSong(int visibleSongNr); + bool IsMouseOverSelectedSong(SMouseEvent mEvent); - bool IsActive(); - void SetActive(bool active); - - bool IsMouseOverActualSelection(SMouseEvent mEvent); - + // Same for categories int GetSelectedCategory(); void SetSelectedCategory(int categoryNr); - int GetActualSelection(); + bool EnterSelectedCategory(); - bool EnterCurrentCategory(); - - bool IsSelected(); - void SetSelected(bool selected); - - bool IsVisible(); - void SetVisible(bool visible); - - bool IsSmallView(); - void SetSmallView(bool smallView); + // The song that is currently playing (set e.g. by clicking on a song) + int GetPreviewSong(); SRectF Rect { get; } + bool Active { get; set; } + bool Selected { get; set; } + bool Visible { get; set; } + bool SmallView { get; set; } } } \ No newline at end of file diff --git a/VocaluxeLib/PartyModes/IPartyMode.cs b/VocaluxeLib/PartyModes/IPartyMode.cs index d71e8135..71c30c9a 100644 --- a/VocaluxeLib/PartyModes/IPartyMode.cs +++ b/VocaluxeLib/PartyModes/IPartyMode.cs @@ -44,7 +44,7 @@ namespace VocaluxeLib.PartyModes public struct SSelectionOptions { /// - /// If != -1, the SongMenu should set the song selection on the provided song index (visible index) if possible + /// If != -1, the SongMenu should set the song selection to the provided song index (visible index) if possible /// public int SongIndex; diff --git a/VocaluxeLib/Structs.cs b/VocaluxeLib/Structs.cs index 13ee20ca..d0c73628 100644 --- a/VocaluxeLib/Structs.cs +++ b/VocaluxeLib/Structs.cs @@ -132,6 +132,15 @@ namespace VocaluxeLib if (ctrl) Mod |= EModifier.Ctrl; } + + /// + /// Returns true if this is about an arrow key (left, right, up down) + /// + /// True if Key is an arrow key + public bool IsArrowKey() + { + return Key == Keys.Left || Key == Keys.Right || Key == Keys.Up || Key == Keys.Down; + } } public struct SMouseEvent