#region license // This file is part of Vocaluxe. // // Vocaluxe is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, or // (at your option) any later version. // // Vocaluxe is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with Vocaluxe. If not, see . #endregion using System.Diagnostics; using System.Xml.Serialization; using VocaluxeLib.PartyModes; namespace VocaluxeLib.Menu.SongMenu { [XmlType("SongMenu")] public struct SThemeSongMenu { [XmlAttribute(AttributeName = "Name")] public string Name; public string CoverBackground; public string CoverBigBackground; public string DuetIcon; public string RapIcon; public string VideoIcon; public string MedleyCalcIcon; public string MedleyTagIcon; public string InstrumentalIcon; public string VocalsIcon; public SThemeColor Color; //public SThemeSongMenuBook songMenuBook; //public SThemeSongMenuDreidel songMenuDreidel; public SThemeSongMenuList SongMenuList; public SThemeSongMenuTileBoard SongMenuTileBoard; } public struct SThemeSongMenuList { /// /// Number of visible songs in list /// public int ListLength; /// /// Space between tiles horizontal /// public float SpaceW; /// /// Space between tiles vertical /// public float SpaceH; public SRectF TileRect; public SRectF TileRectSmall; public SThemeText TextArtist; public SThemeText TextTitle; public SThemeText TextSongLength; public SThemeText TextSongYear; public SThemeStatic StaticCoverBig; public SThemeStatic StaticTextBG; public SThemeStatic StaticDuetIcon; public SThemeStatic StaticRapIcon; public SThemeStatic StaticInstrumentalIcon; public SThemeStatic StaticVocalsIcon; public SThemeStatic StaticVideoIcon; public SThemeStatic StaticMedleyCalcIcon; public SThemeStatic StaticMedleyTagIcon; } public struct SThemeSongMenuTileBoard { /// /// Number of tiles horizontal /// public int NumW; /// /// Number of tiles vertical /// public int NumH; /// /// Number of tiles horizontal in small-modus /// public int NumWsmall; /// /// Number of tiles vertical in small-modus /// public int NumHsmall; /// /// Space between tiles horizontal /// public float SpaceW; /// /// Space between tiles vertical /// public float SpaceH; public SRectF TileRect; public SRectF TileRectSmall; public SThemeText TextArtist; public SThemeText TextTitle; public SThemeText TextSongLength; public SThemeText TextSongYear; public SThemeStatic StaticCoverBig; public SThemeStatic StaticTextBG; public SThemeStatic StaticDuetIcon; public SThemeStatic StaticRapIcon; public SThemeStatic StaticInstrumentalIcon; public SThemeStatic StaticVocalsIcon; public SThemeStatic StaticVideoIcon; public SThemeStatic StaticMedleyCalcIcon; public SThemeStatic StaticMedleyTagIcon; } public abstract class CSongMenuFramework : CMenuElementBase, ISongMenu { protected readonly int _PartyModeId; protected SThemeSongMenu _Theme; public bool ThemeLoaded { get; private set; } public bool Selectable { get { return Visible; } } protected bool _Initialized; private int _PreviewNrInternal = -1; protected virtual int _PreviewNr { get { return _PreviewNrInternal; } set { 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; CBase.BackgroundMusic.SetPlayingPreview(false); } _PreviewNrInternal = value; } } protected int _AutoplayDelayinMs = CBase.Config.GetAutoplayPreviewDelay(); protected System.Timers.Timer _AutoplayTimer = new System.Timers.Timer(); protected volatile bool _AutoplayPending = false; private SColorF _ColorInternal; protected SColorF _Color { get { return _ColorInternal; } } public int GetPreviewSong() { return _PreviewNr; } 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; } protected CSongMenuFramework(SThemeSongMenu theme, int partyModeId) { Visible = true; _PartyModeId = partyModeId; _Theme = theme; ThemeLoaded = true; } #region Theme public string GetThemeName() { return _Theme.Name; } public virtual object GetTheme() { return _Theme; } #endregion Theme public virtual void Init() { _ResetPreview(false); _InitializeAutoplayTimer(); _Initialized = true; } public virtual void Update(SScreenSongOptions songOptions) { if (_AutoplayPending) { _AutoplayPending = false; _PreviewSelectedSong(); } } public abstract void OnShow(); public virtual void OnHide() { _AutoplayTimer.Stop(); _AutoplayPending = false; var check = CBase.Graphics.GetNextScreenType(); if (CBase.Graphics.GetNextScreenType() == EScreen.Sing) { _ResetPreview(false); } else if ((CBase.Graphics.GetNextScreenType() != EScreen.Names && CBase.Graphics.GetNextScreenType() != EScreen.Highscore) || CBase.Config.GetBackgroundMusicStatus() == EBackgroundMusicOffOn.TR_CONFIG_OFF) { _ResetPreview(); } } public abstract bool HandleInput(ref SKeyEvent keyEvent, SScreenSongOptions options); public abstract bool HandleMouse(ref SMouseEvent mouseEvent, SScreenSongOptions songOptions); public virtual void Draw() { if (!_Initialized || !Visible) { return; } if (CBase.BackgroundMusic.IsPlaying()) { CBase.Drawing.DrawTexture(CBase.BackgroundMusic.GetVideoTexture(), new SRectF(0, 0, 1920, 1080, 0)); } } public virtual bool IsMouseOverSelectedSong(SMouseEvent mEvent) { var selCov = GetSelectedSongCover(); return selCov != null && CHelper.IsInBounds(selCov.Rect.Scale(SelectedTileZoomFactor), mEvent); } public int GetPreviewSongNr() { if (CBase.Songs.IsInCategory()) { return _PreviewNr; } return -1; } public int GetSelectedSongNr() { if (CBase.Songs.IsInCategory()) { return _SelectionNr; } return -1; } public abstract CStatic GetSelectedSongCover(); public int GetSelectedCategory() { 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; } _PreviewNr = _SelectionNr; } public void LeaveSelectedCategory() { if (!CBase.Songs.IsInCategory()) { return; } var oldCategory = CBase.Songs.GetCurrentCategoryIndex(); _LeaveCategory(); if (oldCategory >= 0 && oldCategory < CBase.Songs.GetNumCategories()) { SetSelectedCategory(oldCategory); } else if (CBase.Songs.GetNumCategories() > 0) { SetSelectedCategory(0); } } public virtual void UnloadSkin() { } public virtual void LoadSkin() { Init(); _Theme.Color.Get(_PartyModeId, out _ColorInternal); } public void ReloadSkin() { UnloadSkin(); LoadSkin(); } public bool EnterSelectedCategory() { if (!_Initialized) { return false; } if (CBase.Songs.IsInCategory() || GetSelectedCategory() < 0 || GetSelectedCategory() >= CBase.Songs.GetNumCategories()) { return false; } _EnterCategory(GetSelectedCategory()); return true; } protected virtual void _EnterCategory(int categoryNr) { _AutoplayTimer.Stop(); _AutoplayPending = false; if (!_Initialized) { return; } if (categoryNr >= CBase.Songs.GetNumCategories()) { return; } _ResetPreview(false); CBase.Songs.SetCategory(categoryNr); } protected virtual void _LeaveCategory() { _AutoplayTimer.Stop(); _AutoplayPending = false; if (!_Initialized) { return; } if (!CBase.Songs.IsInCategory()) { return; } _ResetPreview(); CBase.Songs.SetCategory(-1); } private void _PlaySong(int nr) { _PreviewNrInternal = -1; var song = CBase.Songs.GetVisibleSong(nr); if (song == null) { return; } CBase.BackgroundMusic.LoadPreview(song, song.Preview.StartTime); } protected void _ResetPreview(bool playBGagain = true) { _AutoplayTimer.Stop(); _AutoplayPending = false; if (_PreviewNrInternal == -1) { return; } CBase.BackgroundMusic.StopPreview(); CBase.Sound.SetGlobalVolume(CBase.Config.GetMusicVolume(EMusicType.Background)); if (playBGagain) { CBase.BackgroundMusic.Play(); } //Make sure we don't have a preview here otherwise a change won't be recognized //(e.g. leave a category with one song and set preview to 0 --> previewOld=previewNew=0 --> No change --> Old data shown //Use internal nr because this function gets called from withing setPreviewNr _PreviewNrInternal = -1; } protected void _PreviewSelectedSong() { _PreviewNr = _SelectionNr; } protected void _InitializeAutoplayTimer() { _AutoplayTimer.Stop(); _AutoplayPending = false; _AutoplayTimer.Interval = _AutoplayDelayinMs; _AutoplayTimer.AutoReset = false; _AutoplayTimer.Elapsed -= _OnAutoplayTimerElapsed; _AutoplayTimer.Elapsed += _OnAutoplayTimerElapsed; } private void _OnAutoplayTimerElapsed(object sender, System.Timers.ElapsedEventArgs e) { _AutoplayPending = true; } protected void _AutoplayPreviewIfEnabled() { if (CBase.Config.GetAutoplayPreviews() == EOffOn.TR_CONFIG_ON) { _PlayPreviewAfterDelay(); } } protected void _PlayPreviewAfterDelay() { _AutoplayPending = false; _AutoplayTimer.Stop(); _AutoplayTimer.Start(); } #region ThemeEdit public void MoveElement(int stepX, int stepY) { X += stepX; Y += stepY; Init(); } public void ResizeElement(int stepW, int stepH) { W += stepW; if (W < 100) { W = 100; } H += stepH; if (H < 100) { H = 100; } Init(); } #endregion ThemeEdit } }