Skip to content
Permalink
Browse files

Add support for using custom fonts for lyrics. (#342)

  • Loading branch information
iminashi authored and cozy1 committed Oct 24, 2019
1 parent fdb737d commit dc9ace6fe3d68aaf7070505c9daafd7c163d9d35
@@ -120,7 +120,5 @@ __pycache__/
*.egg
*.userprefs

/.vs/RocksmithCustomSongCreator/v15/Server/sqlite3
/.vs/RocksmithCustomSongCreator/v15/sqlite3

.vs/
*.vshost.exe
@@ -19,6 +19,7 @@
using RocksmithToolkitLib.XML;
using RocksmithToolkitLib.XmlRepository;
using System.Drawing;
using System.Xml;

// do most work with the arrangment as memory variable

@@ -341,6 +342,21 @@ public void LoadArrangementData(string xmlFilePath)
Arrangement.MasterId = masterId;
}

private static ArrangementType DetectArrangementType(string filename)
{
using (XmlReader reader = XmlReader.Create(filename))
{
reader.MoveToContent();
if (reader.LocalName == "vocals")
return ArrangementType.Vocal;
if (reader.LocalName == "showlights")
return ArrangementType.ShowLight;

// Return guitar for everything else
return ArrangementType.Guitar;
}
}

public bool AddXmlArrangement(string xmlFilePath)
{
// only use this method when adding new arrangements
@@ -353,18 +369,33 @@ public bool AddXmlArrangement(string xmlFilePath)
SongXml = new SongXML { File = xmlFilePath }
};

var arrType = DetectArrangementType(xmlFilePath);

// SETUP FIELDS
if (xmlFilePath.ToLower().EndsWith("vocals.xml") || xmlFilePath.ToLower().EndsWith("vocals_rs2.xml"))
if (arrType == ArrangementType.Vocal)
{
cmbArrangementType.SelectedItem = ArrangementType.Vocal;
Arrangement.ArrangementType = ArrangementType.Vocal;

if (xmlFilePath.ToLower().EndsWith("_jvocals.xml") || xmlFilePath.ToLower().EndsWith("jvocals_rs2.xml"))
// Attempt to auto-detect Japanese vocals from filename
if (xmlFilePath.IndexOf("jvocal", StringComparison.OrdinalIgnoreCase) >= 0
|| xmlFilePath.IndexOf("jlyric", StringComparison.OrdinalIgnoreCase) >= 0)
{
cmbArrangementName.SelectedItem = ArrangementName.JVocals;

// Try to find a custom font texture with the filename lyrics.dds
string fontTexture = Path.Combine(Path.GetDirectoryName(xmlFilePath), "lyrics.dds");
if (File.Exists(fontTexture))
{
Arrangement.LyricArt = fontTexture;
}
}
else
{
cmbArrangementName.SelectedItem = ArrangementName.Vocals;
}
}
else if (xmlFilePath.ToLower().EndsWith("_showlights.xml"))
else if (arrType == ArrangementType.ShowLight)
{
cmbArrangementType.SelectedItem = ArrangementType.ShowLight;
Arrangement.ArrangementType = ArrangementType.ShowLight;
@@ -559,31 +590,18 @@ private void EditShowlights()

private void EditVocals()
{
if (Arrangement.CustomFont)
MessageBox.Show("NOTICE: Expert Toolkit Users Only ..." + Environment.NewLine + Environment.NewLine +
"A custom lyrics font is already" + Environment.NewLine +
"defined for this arrangement.", DLCPackageCreator.MESSAGEBOX_CAPTION, MessageBoxButtons.OK, MessageBoxIcon.Warning);

using (var form = new VocalsForm(Arrangement.FontSng, _parentControl.LyricArtPath, Arrangement.CustomFont, Arrangement.SongXml.File))
using (var form = new VocalsForm(Arrangement.LyricArt, Arrangement.SongXml.File))
{
if (DialogResult.OK != form.ShowDialog())
return;

Arrangement.FontSng = form.SngPath; // this is always null/empty
_parentControl.LyricArtPath = form.ArtPath;
Arrangement.CustomFont = form.IsCustom;
Arrangement.LyricArt = File.Exists(form.ArtPath) ? form.ArtPath : null;

if (!String.IsNullOrEmpty(form.VocalsPath))
{
XmlPath = form.VocalsPath;
Arrangement.SongXml.File = form.VocalsPath;
if (XmlPath.ToLower().EndsWith("_jvocals.xml"))
cmbArrangementName.SelectedItem = ArrangementName.JVocals;
else
cmbArrangementName.SelectedItem = ArrangementName.Vocals;
}


}
}

@@ -250,8 +250,6 @@ public string CurrentOFDPackageFilter
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)] // perma fix to prevent creating a property value in designer
public bool JavaBool { get; set; }
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)] // perma fix to prevent creating a property value in designer
public string LyricArtPath { get; set; }
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)] // perma fix to prevent creating a property value in designer
public string ToolkitVers { get; set; }
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)] // perma fix to prevent creating a property value in designer
public string PackageAuthor { get; set; }
@@ -591,10 +589,10 @@ public string SaveTemplateFile(string templateDir = "", bool validate = true)
continue;
arr.SongXml.File = arr.SongXml.File.RelativeTo(BasePath);
arr.SongFile.File = "";
if (!String.IsNullOrEmpty(arr.FontSng))
arr.FontSng = arr.FontSng.RelativeTo(BasePath);
if (!String.IsNullOrEmpty(arr.LyricArt))
arr.LyricArt = arr.LyricArt.RelativeTo(BasePath);
}

try
{
using (var stm = XmlWriter.Create(templatePath, new XmlWriterSettings { CheckCharacters = true, Indent = true }))
@@ -612,8 +610,8 @@ public string SaveTemplateFile(string templateDir = "", bool validate = true)
arr.SongXml.File = arr.SongXml.File.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arr.SongFile.File))
arr.SongFile.File = arr.SongFile.File.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arr.FontSng))
arr.FontSng = arr.FontSng.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arr.LyricArt))
arr.LyricArt = arr.LyricArt.AbsoluteTo(BasePath);
}

if (!String.IsNullOrEmpty(packageData.LyricArtPath))
@@ -627,8 +625,8 @@ public string SaveTemplateFile(string templateDir = "", bool validate = true)
arr.SongXml.File = arr.SongXml.File.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arr.SongFile.File))
arr.SongFile.File = arr.SongFile.File.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arr.FontSng))
arr.FontSng = arr.FontSng.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arr.LyricArt))
arr.LyricArt = arr.LyricArt.AbsoluteTo(BasePath);
}

if (!String.IsNullOrEmpty(packageData.LyricArtPath))
@@ -949,10 +947,6 @@ public void FillPackageCreatorForm(DLCPackageData info, string filesBaseDir)
info.ArtFiles = null; // force ArtFiles array to be generated from the AlbumArtPath
}

// Lyric art
if (!String.IsNullOrEmpty(info.LyricArtPath))
LyricArtPath = info.LyricArtPath.AbsoluteTo(BasePath);

// Audio file
if (!String.IsNullOrEmpty(info.OggPath))
AudioPath = info.OggPath.AbsoluteTo(BasePath);
@@ -970,8 +964,8 @@ public void FillPackageCreatorForm(DLCPackageData info, string filesBaseDir)
{
arrangement.SongXml.File = arrangement.SongXml.File.AbsoluteTo(BasePath);

if (!String.IsNullOrEmpty(arrangement.FontSng))
arrangement.FontSng = arrangement.FontSng.AbsoluteTo(BasePath);
if (!String.IsNullOrEmpty(arrangement.LyricArt))
arrangement.LyricArt = arrangement.LyricArt.AbsoluteTo(BasePath);

arrangement.ClearCache();

@@ -1329,7 +1323,7 @@ private DLCPackageData GetPackageData(bool validate, out string errorMsg)
},

AlbumArtPath = AlbumArtPath,
LyricArtPath = LyricArtPath,
LyricArtPath = arrangements.Find(arr => arr.HasCustomFont)?.LyricArt,

This comment has been minimized.

Copy link
@cozy1

cozy1 Oct 24, 2019

Contributor

FixMe: Syntax is not compatible with .Net4.0.

This comment has been minimized.

Copy link
@iminashi

iminashi Oct 25, 2019

Author Contributor

In that case a temporary variable needs to be used:
var laArr = arrangements.Find(arr => arr.HasCustomFont);
...
LyricArtPath = laArr != null ? laArr.LyricArt : string.Empty,

OggPath = AudioPath,
OggPreviewPath = audioPreviewPath,
OggQuality = numAudioQuality.Value,
@@ -1886,16 +1880,21 @@ public DLCPackageData PackageGenerate()
if (packageData.GameVersion == GameVersion.RS2012)
continue;

// only validate lyrics that do not use a custom font (RS2014 ONLY)
if (!arr.CustomFont)
// Only validate lyrics that do not use a custom font (RS2014 ONLY)
if (!arr.HasCustomFont)
{
var oldXml = GeneralExtension.CopyToTempFile(arr.SongXml.File);
using (var outputStream = new FileStream(arr.SongXml.File, FileMode.Create, FileAccess.ReadWrite))
var vocals = Vocals.LoadFromFile(arr.SongXml.File);
foreach(var voc in vocals.Vocal)
{
var vocals2014 = RocksmithToolkitLib.Sng2014HSL.Sng2014FileWriter.ReadVocals(oldXml);
// validate lyrics
var xmlContent = new Vocals(vocals2014, true);
xmlContent.Serialize(outputStream);
if(voc.Lyric.Length != voc.Lyric.GetValidLyric().Length)
{
var errMsg = Path.GetFileName(arr.SongXml.File) +
"\n\nThis lyrics file contains characters not included in the game's default font."
+"\nYou will have to use a custom font for them to show up in the game.";
BetterDialog2.ShowDialog(errMsg, "Custom Font Needed", null, null, "Ok", Bitmap.FromHicon(SystemIcons.Warning.Handle), "Warning", 150, 150);

break;
}
}
}

0 comments on commit dc9ace6

Please sign in to comment.
You can’t perform that action at this time.