diff --git a/Assets/Scenes/MenuScene.unity b/Assets/Scenes/MenuScene.unity
index df240458b..f172adfb6 100644
--- a/Assets/Scenes/MenuScene.unity
+++ b/Assets/Scenes/MenuScene.unity
@@ -2406,6 +2406,162 @@ CanvasRenderer:
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1876917083}
m_CullTransparentMesh: 1
+--- !u!1 &1886399722
+GameObject:
+ m_ObjectHideFlags: 0
+ m_CorrespondingSourceObject: {fileID: 0}
+ m_PrefabInstance: {fileID: 0}
+ m_PrefabAsset: {fileID: 0}
+ serializedVersion: 6
+ m_Component:
+ - component: {fileID: 1886399723}
+ - component: {fileID: 1886399726}
+ - component: {fileID: 1886399725}
+ - component: {fileID: 1886399724}
+ m_Layer: 5
+ m_Name: Support Text
+ m_TagString: Untagged
+ m_Icon: {fileID: 0}
+ m_NavMeshLayer: 0
+ m_StaticEditorFlags: 0
+ m_IsActive: 1
+--- !u!224 &1886399723
+RectTransform:
+ m_ObjectHideFlags: 0
+ m_CorrespondingSourceObject: {fileID: 0}
+ m_PrefabInstance: {fileID: 0}
+ m_PrefabAsset: {fileID: 0}
+ m_GameObject: {fileID: 1886399722}
+ m_LocalRotation: {x: -0, y: -0, z: -0, w: 1}
+ m_LocalPosition: {x: 0, y: 0, z: 0}
+ m_LocalScale: {x: 1, y: 1, z: 1}
+ m_ConstrainProportionsScale: 0
+ m_Children: []
+ m_Father: {fileID: 2044165073}
+ m_RootOrder: -1
+ m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
+ m_AnchorMin: {x: 1, y: 1}
+ m_AnchorMax: {x: 1, y: 1}
+ m_AnchoredPosition: {x: -7.9999695, y: -30.500004}
+ m_SizeDelta: {x: 125, y: 11}
+ m_Pivot: {x: 0.9999996, y: 1}
+--- !u!114 &1886399724
+MonoBehaviour:
+ m_ObjectHideFlags: 0
+ m_CorrespondingSourceObject: {fileID: 0}
+ m_PrefabInstance: {fileID: 0}
+ m_PrefabAsset: {fileID: 0}
+ m_GameObject: {fileID: 1886399722}
+ m_Enabled: 1
+ m_EditorHideFlags: 0
+ m_Script: {fileID: 11500000, guid: 306cc8c2b49d7114eaa3623786fc2126, type: 3}
+ m_Name:
+ m_EditorClassIdentifier:
+ m_IgnoreLayout: 0
+ m_MinWidth: -1
+ m_MinHeight: -1
+ m_PreferredWidth: 0
+ m_PreferredHeight: -1
+ m_FlexibleWidth: -1
+ m_FlexibleHeight: -1
+ m_LayoutPriority: 1
+--- !u!114 &1886399725
+MonoBehaviour:
+ m_ObjectHideFlags: 0
+ m_CorrespondingSourceObject: {fileID: 0}
+ m_PrefabInstance: {fileID: 0}
+ m_PrefabAsset: {fileID: 0}
+ m_GameObject: {fileID: 1886399722}
+ m_Enabled: 1
+ m_EditorHideFlags: 0
+ m_Script: {fileID: 11500000, guid: f4688fdb7df04437aeb418b961361dc5, type: 3}
+ m_Name:
+ m_EditorClassIdentifier:
+ m_Material: {fileID: 0}
+ m_Color: {r: 1, g: 1, b: 1, a: 1}
+ m_RaycastTarget: 1
+ m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0}
+ m_Maskable: 1
+ m_OnCullStateChanged:
+ m_PersistentCalls:
+ m_Calls: []
+ m_text: Custom
+ m_isRightToLeft: 0
+ m_fontAsset: {fileID: 11400000, guid: 8f586378b4e144a9851e7b34d9b748ee, type: 2}
+ m_sharedMaterial: {fileID: 2100000, guid: 1b9ed95aaf90c334f85001d466686cf6, type: 2}
+ m_fontSharedMaterials: []
+ m_fontMaterial: {fileID: 0}
+ m_fontMaterials: []
+ m_fontColor32:
+ serializedVersion: 2
+ rgba: 4294967295
+ m_fontColor: {r: 1, g: 1, b: 1, a: 1}
+ m_enableVertexGradient: 0
+ m_colorMode: 3
+ m_fontColorGradient:
+ topLeft: {r: 1, g: 1, b: 1, a: 1}
+ topRight: {r: 1, g: 1, b: 1, a: 1}
+ bottomLeft: {r: 1, g: 1, b: 1, a: 1}
+ bottomRight: {r: 1, g: 1, b: 1, a: 1}
+ m_fontColorGradientPreset: {fileID: 0}
+ m_spriteAsset: {fileID: 0}
+ m_tintAllSprites: 0
+ m_StyleSheet: {fileID: 0}
+ m_TextStyleHashCode: -1183493901
+ m_overrideHtmlColors: 0
+ m_faceColor:
+ serializedVersion: 2
+ rgba: 4294967295
+ m_fontSize: 9
+ m_fontSizeBase: 9
+ m_fontWeight: 400
+ m_enableAutoSizing: 0
+ m_fontSizeMin: 18
+ m_fontSizeMax: 72
+ m_fontStyle: 1
+ m_HorizontalAlignment: 4
+ m_VerticalAlignment: 256
+ m_textAlignment: 65535
+ m_characterSpacing: 0
+ m_wordSpacing: 0
+ m_lineSpacing: 0
+ m_lineSpacingMax: 0
+ m_paragraphSpacing: 0
+ m_charWidthMaxAdj: 0
+ m_enableWordWrapping: 0
+ m_wordWrappingRatios: 0.4
+ m_overflowMode: 0
+ m_linkedTextComponent: {fileID: 0}
+ parentLinkedComponent: {fileID: 0}
+ m_enableKerning: 1
+ m_enableExtraPadding: 0
+ checkPaddingRequired: 0
+ m_isRichText: 1
+ m_parseCtrlCharacters: 1
+ m_isOrthographic: 1
+ m_isCullingEnabled: 0
+ m_horizontalMapping: 0
+ m_verticalMapping: 0
+ m_uvLineOffset: 0
+ m_geometrySortingOrder: 0
+ m_IsTextObjectScaleStatic: 0
+ m_VertexBufferAutoSizeReduction: 0
+ m_useMaxVisibleDescender: 1
+ m_pageToDisplay: 1
+ m_margin: {x: 0, y: 0, z: 0, w: 0}
+ m_isUsingLegacyAnimationComponent: 0
+ m_isVolumetricText: 0
+ m_hasFontAssetChanged: 0
+ m_baseMaterial: {fileID: 0}
+ m_maskOffset: {x: 0, y: 0, z: 0, w: 0}
+--- !u!222 &1886399726
+CanvasRenderer:
+ m_ObjectHideFlags: 0
+ m_CorrespondingSourceObject: {fileID: 0}
+ m_PrefabInstance: {fileID: 0}
+ m_PrefabAsset: {fileID: 0}
+ m_GameObject: {fileID: 1886399722}
+ m_CullTransparentMesh: 1
--- !u!1 &1986583190
GameObject:
m_ObjectHideFlags: 0
@@ -2440,11 +2596,11 @@ RectTransform:
m_Father: {fileID: 2044165073}
m_RootOrder: -1
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
- m_AnchorMin: {x: 0, y: 1}
+ m_AnchorMin: {x: 1, y: 1}
m_AnchorMax: {x: 1, y: 1}
- m_AnchoredPosition: {x: 46, y: -12.5}
- m_SizeDelta: {x: -108, y: 24}
- m_Pivot: {x: 0.5, y: 1}
+ m_AnchoredPosition: {x: -7.9999695, y: -12.5}
+ m_SizeDelta: {x: 125, y: 18}
+ m_Pivot: {x: 0.9999996, y: 1}
--- !u!114 &1986583192
MonoBehaviour:
m_ObjectHideFlags: 0
@@ -2595,6 +2751,7 @@ RectTransform:
m_Children:
- {fileID: 1844302445}
- {fileID: 1986583191}
+ - {fileID: 1886399723}
- {fileID: 1330867043}
- {fileID: 80151784}
m_Father: {fileID: 396272154}
@@ -2658,5 +2815,6 @@ MonoBehaviour:
songName: {fileID: 149797927}
artist: {fileID: 1290299072}
lengthText: {fileID: 1986583193}
+ supportText: {fileID: 1886399725}
albumCover: {fileID: 1330867046}
albumCoverAlt: {fileID: 1876917083}
diff --git a/Assets/Script/Data/SongInfo.cs b/Assets/Script/Data/SongInfo.cs
index 00c4efd60..ebfce3293 100644
--- a/Assets/Script/Data/SongInfo.cs
+++ b/Assets/Script/Data/SongInfo.cs
@@ -3,22 +3,19 @@
using YARG.Serialization;
namespace YARG.Data {
- [JsonObject(MemberSerialization.Fields)]
+ [JsonObject(MemberSerialization.OptIn)]
public class SongInfo {
- [JsonIgnore]
public bool fetched;
- [JsonIgnore]
public bool errored;
+ [JsonProperty]
[JsonConverter(typeof(DirectoryInfoConverter))]
public DirectoryInfo folder;
- [field: JsonProperty("bassPedal2xExpertPlus")]
public bool BassPedal2xExpertPlus {
private set;
get;
}
- [field: JsonProperty("live")]
public bool Live {
private set;
get;
@@ -46,10 +43,75 @@ public string SongName {
}
public string SongNameNoParen => SongName.Replace("(", "").Replace(")", "");
- public string artistName;
- public string source;
+ public bool WaveGroup {
+ private set;
+ get;
+ }
+
+ [JsonProperty("artist")]
+ private string _artistName;
+ public string ArtistName {
+ set {
+ const string WAVEGROUP = " (WaveGroup)";
+ WaveGroup = value.EndsWith(WAVEGROUP);
+ if (WaveGroup) {
+ value = value[..^WAVEGROUP.Length];
+ }
+ _artistName = value;
+ }
+ get => _artistName;
+ }
+
+ ///
+ /// Used for JSON. Compresses flags (, etc.) into a small string.
+ ///
+ [JsonProperty("flags")]
+ public string JsonFlags {
+ get {
+ string o = "";
+
+ if (BassPedal2xExpertPlus) {
+ o += "B";
+ }
+ if (Live) {
+ o += "L";
+ }
+ if (WaveGroup) {
+ o += "W";
+ }
+
+ return o;
+ }
+ set {
+ string i = value;
+
+ if (i.StartsWith('B')) {
+ BassPedal2xExpertPlus = true;
+ i = i.Remove(0, 1);
+ } else {
+ BassPedal2xExpertPlus = false;
+ }
+ if (i.StartsWith('L')) {
+ Live = true;
+ i = i.Remove(0, 1);
+ } else {
+ Live = false;
+ }
+ if (i.StartsWith('W')) {
+ WaveGroup = true;
+ // i = i.Remove(0, 1);
+ } else {
+ WaveGroup = false;
+ }
+ }
+ }
+
+ [JsonProperty]
+ public string source;
+ [JsonProperty]
public float? songLength;
+ [JsonProperty]
public float delay;
public SongInfo(DirectoryInfo folder) {
@@ -59,10 +121,10 @@ public SongInfo(DirectoryInfo folder) {
var split = dirName.Split(" - ");
if (split.Length == 2) {
SongName = split[1];
- artistName = split[0];
+ ArtistName = split[0];
} else {
SongName = dirName;
- artistName = "Unknown";
+ ArtistName = "Unknown";
}
}
}
diff --git a/Assets/Script/PlayMode/Play.cs b/Assets/Script/PlayMode/Play.cs
index 56459d5ee..2263dc6bf 100644
--- a/Assets/Script/PlayMode/Play.cs
+++ b/Assets/Script/PlayMode/Play.cs
@@ -106,7 +106,7 @@ private void Update() {
// Audio raising and lowering based on player preformance
UpdateAudio("guitar", "guitar");
- UpdateAudio("bass", "rhythm");
+ UpdateAudio("bass", "bass", "rhythm");
UpdateAudio("keys", "keys");
// Update beats
@@ -128,10 +128,12 @@ private void Update() {
}
}
- private void UpdateAudio(string name, string audioName) {
- // Skip if that audio track doesn't exist
- if (!audioSources.TryGetValue(audioName, out var audioSource)) {
- return;
+ private void UpdateAudio(string name, string audioName, string altAudioName = null) {
+ // Skip if that audio track doesn't exist and alt track doesn't exist
+ if (!audioSources.TryGetValue(audioName, out AudioSource audioSource)) {
+ if (altAudioName == null || !audioSources.TryGetValue(altAudioName, out audioSource)) {
+ return;
+ }
}
int total = PlayerManager.PlayersWithInstrument(name);
diff --git a/Assets/Script/Serialization/MidiParser.cs b/Assets/Script/Serialization/MidiParser.cs
index 5ddc1411f..357d52e82 100644
--- a/Assets/Script/Serialization/MidiParser.cs
+++ b/Assets/Script/Serialization/MidiParser.cs
@@ -443,7 +443,12 @@ private List ParseGenericLyrics(TrackChunk trackChunk, TempoMa
foreach (var trackEvent in trackChunk.Events) {
totalDelta += trackEvent.DeltaTime;
- if (trackEvent is not LyricEvent lyricEvent) {
+ if (trackEvent is not BaseTextEvent lyricEvent) {
+ continue;
+ }
+
+ // Skip if track name
+ if (lyricEvent.Text == "PART VOCALS") {
continue;
}
@@ -452,13 +457,19 @@ private List ParseGenericLyrics(TrackChunk trackChunk, TempoMa
var time = (float) TimeConverter.ConvertTo(totalDelta, tempo).TotalSeconds;
string text = lyricEvent.Text;
+ // Skip if state stats
+ if (text.StartsWith('[') && text.EndsWith(']')) {
+ continue;
+ }
+
// Remove all metadata
for (int i = text.Length - 1; i >= 0; i--) {
- if (!char.IsWhiteSpace(text[i]) &&
+ if (text[i] == '#' || (
+ !char.IsWhiteSpace(text[i]) &&
!char.IsLetter(text[i]) &&
!char.IsNumber(text[i]) &&
text[i] != '\'' &&
- text[i] != '-') {
+ text[i] != '-')) {
text = text.Remove(i, 1);
}
diff --git a/Assets/Script/Serialization/SongIni.cs b/Assets/Script/Serialization/SongIni.cs
index 5d84d6a87..5754a6bd9 100644
--- a/Assets/Script/Serialization/SongIni.cs
+++ b/Assets/Script/Serialization/SongIni.cs
@@ -35,7 +35,7 @@ public static SongInfo CompleteSongInfo(SongInfo song, FileIniDataParser parser)
// Set basic info
song.SongName ??= section["name"];
- song.artistName ??= section["artist"];
+ song.ArtistName ??= section["artist"];
// Get song source
if (section.ContainsKey("icon") && section["icon"] != "0") {
diff --git a/Assets/Script/UI/GameUI.cs b/Assets/Script/UI/GameUI.cs
index 329a3c376..378f59054 100644
--- a/Assets/Script/UI/GameUI.cs
+++ b/Assets/Script/UI/GameUI.cs
@@ -24,7 +24,7 @@ private void Awake() {
}
private void Start() {
- songTitle.text = $"{Play.song.SongName} - {Play.song.artistName}";
+ songTitle.text = $"{Play.song.SongName} - {Play.song.ArtistName}";
}
private void Update() {
diff --git a/Assets/Script/UI/SelectedSongView.cs b/Assets/Script/UI/SelectedSongView.cs
index 1604e9e16..ca4bb9457 100644
--- a/Assets/Script/UI/SelectedSongView.cs
+++ b/Assets/Script/UI/SelectedSongView.cs
@@ -15,6 +15,8 @@ public class SelectedSongView : MonoBehaviour {
private TextMeshProUGUI artist;
[SerializeField]
private TextMeshProUGUI lengthText;
+ [SerializeField]
+ private TextMeshProUGUI supportText;
[Space]
[SerializeField]
@@ -51,7 +53,7 @@ public void UpdateSongView(SongInfo songInfo) {
// Basic info
songName.text = $"{songInfo.SongName}";
- artist.text = $"{songInfo.artistName}";
+ artist.text = $"{songInfo.ArtistName}";
// Song length
if (songInfo.songLength == null) {
@@ -64,6 +66,19 @@ public void UpdateSongView(SongInfo songInfo) {
lengthText.text = $"{minutes}:{seconds:00}";
}
+ // Source
+ supportText.text = songInfo.source switch {
+ "gh1" or "gh1dlc" => "Little Support",
+ "gh2" or "gh2dlc" => "Some Support",
+ "ghm" => "Some Support",
+ "rb1" or "rb1dlc" => "Full Support",
+ "rb2" or "rb2dlc" => "Full Support",
+ "tbrb" or "tbrbdlc" => "Full Support",
+ "rbacdc" => "Full Support",
+ "rb3" or "rb3dlc" => "Full Pro Support",
+ _ => "Unknown Support"
+ };
+
// Album cover
albumCover.texture = null;
albumCover.color = new Color(0f, 0f, 0f, 0.4f);
diff --git a/Assets/Script/UI/SongSelect.cs b/Assets/Script/UI/SongSelect.cs
index 894fdd74f..60136de38 100644
--- a/Assets/Script/UI/SongSelect.cs
+++ b/Assets/Script/UI/SongSelect.cs
@@ -173,7 +173,7 @@ public void UpdateSearch() {
// TODO: fuzzy search
var text = searchField.text.ToLower();
songInfos = SongLibrary.Songs
- .Where(song => song.SongName.ToLower().StartsWith(text) || song.artistName.ToLower().StartsWith(text));
+ .Where(song => song.SongName.ToLower().StartsWith(text) || song.ArtistName.ToLower().StartsWith(text));
}
songs = songInfos
diff --git a/Assets/Script/UI/SongView.cs b/Assets/Script/UI/SongView.cs
index 1289b3e56..f49da5100 100644
--- a/Assets/Script/UI/SongView.cs
+++ b/Assets/Script/UI/SongView.cs
@@ -13,7 +13,7 @@ public class SongView : MonoBehaviour {
public void UpdateSongView(SongInfo songInfo) {
songName.text = $"{songInfo.SongName}";
- artist.text = $"{songInfo.artistName}";
+ artist.text = $"{songInfo.ArtistName}";
if (songInfo.songLength == null) {
lengthText.text = "N/A";