diff --git a/Output/PartyModes/Challenge.xml b/Output/PartyModes/Challenge.xml
index 964a589e..49873a96 100644
--- a/Output/PartyModes/Challenge.xml
+++ b/Output/PartyModes/Challenge.xml
@@ -15,5 +15,6 @@
CPartyScreenChallengeMain
CPartyScreenChallengeConfig
CPartyScreenChallengeNames
+ CPartyScreenChallengeSongs
diff --git a/Output/PartyModes/Challenge/Themes/Default/Screens/PartyScreenChallengeSongs.xml b/Output/PartyModes/Challenge/Themes/Default/Screens/PartyScreenChallengeSongs.xml
new file mode 100644
index 00000000..3c26cfcd
--- /dev/null
+++ b/Output/PartyModes/Challenge/Themes/Default/Screens/PartyScreenChallengeSongs.xml
@@ -0,0 +1,407 @@
+
+
+
+ PartyScreenChallengeSongs
+ 1
+
+
+
+ Video
+
+
+ BG_Default
+
+
+
+
+
+
+
+
+ 0
+ 40
+ 1280
+ 45
+ 1
+
+
+
+
+
+ 640
+ 50
+ 0
+ 27
+ 0
+
+
+ Center
+ Center
+
+ Outline
+ TR_SCREENCONFIG_TITLE
+
+
+ 75
+ 105
+ 0
+ 27
+ 0
+
+
+ Left
+ Center
+
+ Outline
+ TR_SCREENCONFIG_SONGSOURCE
+
+
+ 75
+ 290
+ 0
+ 27
+ 0
+
+
+ Left
+ Center
+
+ Outline
+ TR_SCREENCONFIG_GAMEMODE
+
+
+
+
+
+
+
+
+
+
+
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+ SelectSlide
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+
+ 500
+ 100
+ 700
+ 50
+ 0
+
+
+ 505
+ 105
+ 40
+ 40
+ 0
+
+
+ 1155
+ 105
+ 40
+ 40
+ 0
+
+
+
+
+
+
+
+ 27
+ 50
+ 0
+ 205.33
+ Outline
+ Bold
+ 3
+
+
+
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+ SelectSlide
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+
+ 500
+ 160
+ 700
+ 50
+ 0
+
+
+ 505
+ 165
+ 40
+ 40
+ 0
+
+
+ 1155
+ 165
+ 40
+ 40
+ 0
+
+
+
+
+
+
+
+ 27
+ 50
+ 0
+ 600
+ Outline
+ Bold
+ 3
+
+
+
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+ SelectSlide
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+
+ 500
+ 160
+ 700
+ 50
+ 0
+
+
+ 505
+ 165
+ 40
+ 40
+ 0
+
+
+ 1155
+ 165
+ 40
+ 40
+ 0
+
+
+
+
+
+
+
+ 27
+ 50
+ 0
+ 600
+ Outline
+ Bold
+ 3
+
+
+
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+ SelectSlide
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+
+ 500
+ 220
+ 700
+ 50
+ 0
+
+
+ 505
+ 225
+ 40
+ 40
+ 0
+
+
+ 1155
+ 225
+ 40
+ 40
+ 0
+
+
+
+
+
+
+
+ 27
+ 50
+ 0
+ 600
+ Outline
+ Bold
+ 1
+
+
+
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+ SelectSlide
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+
+ 500
+ 290
+ 700
+ 50
+ 0
+
+
+ 505
+ 295
+ 40
+ 40
+ 0
+
+
+ 1155
+ 295
+ 40
+ 40
+ 0
+
+
+
+
+
+
+
+ 27
+ 50
+ 0
+ 205.33
+ Outline
+ Bold
+ 2
+
+
+
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+ SelectSlide
+ SelectSlideArrowLeft
+ SelectSlideArrowRight
+
+ 500
+ 360
+ 700
+ 50
+ 0
+
+
+ 505
+ 365
+ 40
+ 40
+ 0
+
+
+ 1155
+ 365
+ 40
+ 40
+ 0
+
+
+
+
+
+
+
+ 27
+ 50
+ 0
+ 205.33
+ Outline
+ Bold
+ 5
+
+
+
+
+
+
+
+
+
diff --git a/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs b/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs
index ee39a94b..4ffb9805 100644
--- a/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs
+++ b/PartyModes/PartyModeChallenge/CPartyModeChallenge.cs
@@ -17,8 +17,11 @@
using System;
using System.Collections.Generic;
+using System.Collections.ObjectModel;
+using System.Linq;
using System.Runtime.InteropServices;
using VocaluxeLib.Menu;
+using VocaluxeLib.Songs;
[assembly: ComVisible(false)]
@@ -103,9 +106,11 @@ namespace VocaluxeLib.PartyModes.Challenge
private enum EStage
{
Config,
+ Songs,
Names,
Main,
- Singing
+ Singing,
+ MedleySinging
}
public struct SData
@@ -118,6 +123,14 @@ namespace VocaluxeLib.PartyModes.Challenge
public int[] Jokers;
public List ProfileIDs;
+ public ESongSource SongSource;
+ public ESongSorting Sorting;
+ public int CategoryIndex;
+ public int PlaylistID;
+
+ public EGameMode GameMode;
+ public int NumMedleySongs;
+
public CChallengeRounds Rounds;
public List ResultTable;
public int[,] Results;
@@ -125,6 +138,7 @@ namespace VocaluxeLib.PartyModes.Challenge
public int CurrentRoundNr;
public int[] CatSongIndices;
+ public List Songs;
}
private struct SStats
@@ -151,7 +165,25 @@ namespace VocaluxeLib.PartyModes.Challenge
_ScreenSongOptions.Sorting.DuetOptions = EDuetOptions.NoDuets;
_ScreenSongOptions.Sorting.FilterPlaylistID = -1;
- GameData = new SData {NumPlayer = 4, NumPlayerAtOnce = 2, NumRounds = 12, NumJokers = 5, RefillJokers = true, CurrentRoundNr = 1, ProfileIDs = new List(), CatSongIndices = null, Results = null};
+ GameData = new SData
+ {
+ NumPlayer = 4,
+ NumPlayerAtOnce = 2,
+ NumRounds = 12,
+ NumJokers = 5,
+ RefillJokers = true,
+ CurrentRoundNr = 1,
+ ProfileIDs = new List(),
+ Sorting = CBase.Config.GetSongSorting(),
+ SongSource = ESongSource.TR_ALLSONGS,
+ PlaylistID = 0,
+ CategoryIndex = 0,
+ GameMode = EGameMode.TR_GAMEMODE_NORMAL,
+ NumMedleySongs = 5,
+ CatSongIndices = null,
+ Results = null,
+ Songs = new List()
+ };
}
public override void SetDefaults()
@@ -194,12 +226,16 @@ namespace VocaluxeLib.PartyModes.Challenge
{
case EStage.Config:
return _Screens["CPartyScreenChallengeConfig"];
+ case EStage.Songs:
+ return _Screens["CPartyScreenChallengeSongs"];
case EStage.Names:
return _Screens["CPartyScreenChallengeNames"];
case EStage.Main:
return _Screens["CPartyScreenChallengeMain"];
case EStage.Singing:
return CBase.Graphics.GetScreen(EScreen.Song);
+ case EStage.MedleySinging:
+ return CBase.Graphics.GetScreen(EScreen.Sing);
default:
throw new ArgumentException("Invalid stage: " + _Stage);
}
@@ -215,6 +251,9 @@ namespace VocaluxeLib.PartyModes.Challenge
switch (_Stage)
{
case EStage.Config:
+ _Stage = EStage.Songs;
+ break;
+ case EStage.Songs:
_Stage = EStage.Names;
break;
case EStage.Names:
@@ -226,9 +265,13 @@ namespace VocaluxeLib.PartyModes.Challenge
GameData.Jokers = null;
break;
case EStage.Main:
- _Stage = EStage.Singing;
+ if (GameData.GameMode == EGameMode.TR_GAMEMODE_MEDLEY)
+ _Stage = EStage.MedleySinging;
+ else
+ _Stage = EStage.Singing;
_StartNextRound();
break;
+ case EStage.MedleySinging:
case EStage.Singing:
_Stage = EStage.Main;
_UpdateScores();
@@ -246,9 +289,12 @@ namespace VocaluxeLib.PartyModes.Challenge
case EStage.Config:
CBase.Graphics.FadeTo(EScreen.Party);
return;
- case EStage.Names:
+ case EStage.Songs:
_Stage = EStage.Config;
break;
+ case EStage.Names:
+ _Stage = EStage.Songs;
+ break;
case EStage.Main:
_Stage = EStage.Names;
break;
@@ -265,8 +311,38 @@ namespace VocaluxeLib.PartyModes.Challenge
public override SScreenSongOptions GetScreenSongOptions()
{
- _ScreenSongOptions.Sorting.SongSorting = CBase.Config.GetSongSorting();
- _ScreenSongOptions.Sorting.Tabs = CBase.Config.GetTabs();
+ switch(GameData.SongSource)
+ {
+ case ESongSource.TR_ALLSONGS:
+ _ScreenSongOptions.Sorting.SongSorting = CBase.Config.GetSongSorting();
+ _ScreenSongOptions.Sorting.Tabs = CBase.Config.GetTabs();
+ _ScreenSongOptions.Sorting.FilterPlaylistID = -1;
+
+ _ScreenSongOptions.Selection.CategoryChangeAllowed = true;
+ break;
+
+ case ESongSource.TR_CATEGORY:
+ _ScreenSongOptions.Sorting.SongSorting = GameData.Sorting;
+ _ScreenSongOptions.Sorting.Tabs = EOffOn.TR_CONFIG_ON;
+ _ScreenSongOptions.Sorting.FilterPlaylistID = -1;
+
+ if (GameData.CatSongIndices == null)
+ _CreateCatSongIndices();
+
+ _ScreenSongOptions.Selection.SongIndex = GameData.CatSongIndices[GameData.CategoryIndex];
+
+ _ScreenSongOptions.Selection.CategoryChangeAllowed = false;
+ break;
+
+ case ESongSource.TR_PLAYLIST:
+ _ScreenSongOptions.Sorting.SongSorting = CBase.Config.GetSongSorting();
+ _ScreenSongOptions.Sorting.Tabs = EOffOn.TR_CONFIG_OFF;
+ _ScreenSongOptions.Sorting.FilterPlaylistID = GameData.PlaylistID;
+
+ _ScreenSongOptions.Selection.CategoryChangeAllowed = false;
+ break;
+ }
+
_ScreenSongOptions.Sorting.IgnoreArticles = CBase.Config.GetIgnoreArticles();
return _ScreenSongOptions;
@@ -343,30 +419,7 @@ namespace VocaluxeLib.PartyModes.Challenge
public override void SongSelected(int songID)
{
- const EGameMode gm = EGameMode.TR_GAMEMODE_NORMAL;
-
- CBase.Game.Reset();
- CBase.Game.ClearSongs();
- CBase.Game.AddSong(songID, gm);
- CBase.Game.SetNumPlayer(GameData.NumPlayerAtOnce);
-
- SPlayer[] players = CBase.Game.GetPlayers();
- if (players == null)
- return;
-
- if (players.Length < GameData.NumPlayerAtOnce)
- return;
-
- CRound c = GameData.Rounds[GameData.CurrentRoundNr - 1];
-
- for (int i = 0; i < GameData.NumPlayerAtOnce; i++)
- {
- //try to fill with the right data
- if (c != null)
- players[i].ProfileID = GameData.ProfileIDs[c.Players[i]];
- else
- players[i].ProfileID = -1;
- }
+ _PrepareGame(new int[] { songID });
CBase.Graphics.FadeTo(EScreen.Sing);
}
@@ -380,11 +433,63 @@ namespace VocaluxeLib.PartyModes.Challenge
private void _StartNextRound()
{
- _ScreenSongOptions.Selection.RandomOnly = _ScreenSongOptions.Sorting.Tabs != EOffOn.TR_CONFIG_ON;
- _ScreenSongOptions.Selection.CategoryChangeAllowed = _ScreenSongOptions.Sorting.Tabs == EOffOn.TR_CONFIG_ON;
- _SetNumJokers();
- _SetTeamNames();
- GameData.CatSongIndices = null;
+ if (GameData.GameMode == EGameMode.TR_GAMEMODE_MEDLEY)
+ {
+ int[] songIDs = new int[GameData.NumMedleySongs];
+ for (int i = 0; i < GameData.NumMedleySongs; i++)
+ {
+ if (GameData.Songs.Count == 0)
+ _UpdateSongList();
+
+ songIDs[i] = GameData.Songs[0];
+ GameData.Songs.RemoveAt(0);
+ }
+
+ _PrepareGame(songIDs);
+ }
+ else
+ {
+ _ScreenSongOptions.Selection.RandomOnly = _ScreenSongOptions.Sorting.Tabs != EOffOn.TR_CONFIG_ON;
+ _ScreenSongOptions.Selection.CategoryChangeAllowed = false;
+ _SetNumJokers();
+ _SetTeamNames();
+ GameData.CatSongIndices = null;
+ }
+ }
+
+ private bool _PrepareGame(int[] songIDs)
+ {
+ CBase.Game.Reset();
+ CBase.Game.ClearSongs();
+
+ #region PlayerNames
+ CBase.Game.SetNumPlayer(GameData.NumPlayerAtOnce);
+ SPlayer[] players = CBase.Game.GetPlayers();
+ if (players == null)
+ return false;
+
+ if (players.Length < GameData.NumPlayerAtOnce)
+ return false;
+
+ CRound c = GameData.Rounds[GameData.CurrentRoundNr - 1];
+
+ for (int i = 0; i < GameData.NumPlayerAtOnce; i++)
+ {
+ //try to fill with the right data
+ if (c != null)
+ players[i].ProfileID = GameData.ProfileIDs[c.Players[i]];
+ else
+ players[i].ProfileID = -1;
+ }
+ #endregion PlayerNames
+
+ #region SongQueue
+ for (int i = 0; i < songIDs.Length; i++)
+ CBase.Game.AddSong(songIDs[i], GameData.GameMode);
+ #endregion SongQueue
+
+ return true;
+
}
private void _SetNumJokers()
@@ -429,6 +534,38 @@ namespace VocaluxeLib.PartyModes.Challenge
_ScreenSongOptions.Selection.TeamNames[i] = CBase.Profiles.GetPlayerName(GameData.ProfileIDs[c.Players[i]]);
}
+ private void _UpdateSongList()
+ {
+ if (GameData.Songs.Count > 0)
+ return;
+
+ switch (GameData.SongSource)
+ {
+ case ESongSource.TR_PLAYLIST:
+ for (int i = 0; i < CBase.Playlist.GetSongCount(GameData.PlaylistID); i++)
+ {
+ int id = CBase.Playlist.GetSong(GameData.PlaylistID, i).SongID;
+ if (CBase.Songs.GetSongByID(id).AvailableGameModes.Contains(EGameMode.TR_GAMEMODE_MEDLEY))
+ GameData.Songs.Add(id);
+ }
+ break;
+
+ case ESongSource.TR_ALLSONGS:
+ ReadOnlyCollection avSongs = CBase.Songs.GetSongs();
+ GameData.Songs.AddRange(avSongs.Where(song => song.AvailableGameModes.Contains(EGameMode.TR_GAMEMODE_MEDLEY)).Select(song => song.ID));
+ break;
+
+ case ESongSource.TR_CATEGORY:
+ CBase.Songs.SetCategory(GameData.CategoryIndex);
+ avSongs = CBase.Songs.GetVisibleSongs();
+ GameData.Songs.AddRange(avSongs.Where(song => song.AvailableGameModes.Contains(EGameMode.TR_GAMEMODE_MEDLEY)).Select(song => song.ID));
+
+ CBase.Songs.SetCategory(-1);
+ break;
+ }
+ GameData.Songs.Shuffle();
+ }
+
private void _UpdateScores()
{
if (GameData.ResultTable.Count == 0)
diff --git a/PartyModes/PartyModeChallenge/CPartyScreenChallengeSongs.cs b/PartyModes/PartyModeChallenge/CPartyScreenChallengeSongs.cs
new file mode 100644
index 00000000..931a1791
--- /dev/null
+++ b/PartyModes/PartyModeChallenge/CPartyScreenChallengeSongs.cs
@@ -0,0 +1,63 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using VocaluxeLib.Menu;
+
+namespace VocaluxeLib.PartyModes.Challenge
+{
+ class CPartyScreenChallengeSongs : CMenuPartySongSelection
+ {
+ protected override int _ScreenVersion
+ {
+ get { return 1; }
+ }
+
+ private new CPartyModeChallenge _PartyMode;
+
+ public override void Init()
+ {
+ base.Init();
+ _PartyMode = (CPartyModeChallenge)base._PartyMode;
+ }
+
+ public override void OnShow()
+ {
+ Source = _PartyMode.GameData.SongSource;
+ Sorting = _PartyMode.GameData.Sorting;
+ Category = _PartyMode.GameData.CategoryIndex;
+ Playlist = _PartyMode.GameData.PlaylistID;
+ SongMode = _PartyMode.GameData.GameMode;
+ NumMedleySongs = _PartyMode.GameData.NumMedleySongs;
+
+ base.OnShow();
+ }
+
+ public override void Back()
+ {
+ _SaveConfig();
+ _PartyMode.Back();
+ }
+
+ public override void Next()
+ {
+ _SaveConfig();
+ _PartyMode.Next();
+ }
+
+ public override bool UpdateGame()
+ {
+ return true;
+ }
+
+ private void _SaveConfig()
+ {
+ _PartyMode.GameData.SongSource = Source;
+ _PartyMode.GameData.Sorting = Sorting;
+ _PartyMode.GameData.CategoryIndex = Category;
+ _PartyMode.GameData.PlaylistID = Playlist;
+ _PartyMode.GameData.GameMode = SongMode;
+ _PartyMode.GameData.NumMedleySongs = NumMedleySongs;
+ }
+ }
+}
diff --git a/PartyModes/PartyModeChallenge/PartyModeChallenge.csproj b/PartyModes/PartyModeChallenge/PartyModeChallenge.csproj
index 1d0a49a9..c2ecf5b3 100644
--- a/PartyModes/PartyModeChallenge/PartyModeChallenge.csproj
+++ b/PartyModes/PartyModeChallenge/PartyModeChallenge.csproj
@@ -71,6 +71,7 @@
+
@@ -109,4 +110,4 @@ rm -f "$(SolutionDir)Output\PartyModes\$(TargetName)\Code\GlobalSuppressions.cs"
-->
-
+
\ No newline at end of file
diff --git a/Vocaluxe/Screens/CScreenSong.cs b/Vocaluxe/Screens/CScreenSong.cs
index 0e7d9dfe..6d2d8be6 100644
--- a/Vocaluxe/Screens/CScreenSong.cs
+++ b/Vocaluxe/Screens/CScreenSong.cs
@@ -644,6 +644,11 @@ namespace Vocaluxe.Screens
_Sso = CParty.GetSongSelectionOptions();
CSongs.Sort(_Sso.Sorting.SongSorting, _Sso.Sorting.Tabs, _Sso.Sorting.IgnoreArticles, _Sso.Sorting.SearchString, _Sso.Sorting.DuetOptions, _Sso.Sorting.FilterPlaylistID);
+ if (_Sso.Selection.CategoryIndex != CBase.Songs.GetCurrentCategoryIndex())
+ {
+ _SelectedCategoryIndex = _Sso.Selection.CategoryIndex;
+ _SongMenu.EnterSelectedCategory();
+ }
_SearchActive = _Sso.Sorting.SearchActive;
_SearchText = _Sso.Sorting.SearchString;
diff --git a/VocaluxeLib/PartyModes/IPartyMode.cs b/VocaluxeLib/PartyModes/IPartyMode.cs
index d78f0047..a4bad99e 100644
--- a/VocaluxeLib/PartyModes/IPartyMode.cs
+++ b/VocaluxeLib/PartyModes/IPartyMode.cs
@@ -48,6 +48,11 @@ namespace VocaluxeLib.PartyModes
///
public int SongIndex;
+ ///
+ /// If != -1, the SongMenu should enter show category based on provided category index if possible
+ ///
+ public int CategoryIndex;
+
///
/// If true, the SongMenu should perform the select random song method
///