256 lines
7.6 KiB
C#
256 lines
7.6 KiB
C#
|
using System;
|
||
|
using System.Collections.Generic;
|
||
|
using System.Linq;
|
||
|
using UnityEditor;
|
||
|
|
||
|
namespace I2.Loc
|
||
|
{
|
||
|
public partial class LanguageSourceData
|
||
|
{
|
||
|
#region Language
|
||
|
|
||
|
public void UpdateDictionary(bool force = false)
|
||
|
{
|
||
|
if (!force && mDictionary != null && mDictionary.Count == mTerms.Count)
|
||
|
return;
|
||
|
|
||
|
StringComparer comparer = CaseInsensitiveTerms ? StringComparer.OrdinalIgnoreCase : StringComparer.Ordinal;
|
||
|
if (mDictionary.Comparer != comparer)
|
||
|
mDictionary = new Dictionary<string, TermData>(comparer);
|
||
|
else
|
||
|
mDictionary.Clear();
|
||
|
|
||
|
for (int i = 0, imax = mTerms.Count; i < imax; ++i)
|
||
|
{
|
||
|
var termData = mTerms[i];
|
||
|
ValidateFullTerm(ref termData.Term);
|
||
|
|
||
|
mDictionary[termData.Term]= mTerms[i];
|
||
|
mTerms[i].Validate();
|
||
|
}
|
||
|
|
||
|
if (I2Utils.IsPlaying())
|
||
|
{
|
||
|
SaveLanguages(true);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
public string GetTranslation (string term, string overrideLanguage = null, string overrideSpecialization = null, bool skipDisabled = false, bool allowCategoryMistmatch = false)
|
||
|
{
|
||
|
string Translation;
|
||
|
if (TryGetTranslation(term, out Translation, overrideLanguage:overrideLanguage, overrideSpecialization:overrideSpecialization, skipDisabled:skipDisabled, allowCategoryMistmatch:allowCategoryMistmatch))
|
||
|
return Translation;
|
||
|
|
||
|
return string.Empty;
|
||
|
}
|
||
|
|
||
|
public bool TryGetTranslation (string term, out string Translation, string overrideLanguage=null, string overrideSpecialization=null, bool skipDisabled=false, bool allowCategoryMistmatch=false)
|
||
|
{
|
||
|
int Index = GetLanguageIndex( overrideLanguage==null ? LocalizationManager.CurrentLanguage : overrideLanguage, SkipDisabled: false );
|
||
|
|
||
|
if (Index>=0 && (!skipDisabled || mLanguages[Index].IsEnabled()))
|
||
|
{
|
||
|
TermData data = GetTermData(term, allowCategoryMistmatch:allowCategoryMistmatch);
|
||
|
if (data!=null)
|
||
|
{
|
||
|
Translation = data.GetTranslation(Index, overrideSpecialization, editMode:true);
|
||
|
|
||
|
// "---" is a code to define that the translation is meant to be empty
|
||
|
if (Translation == "---")
|
||
|
{
|
||
|
Translation = string.Empty;
|
||
|
return true;
|
||
|
}
|
||
|
|
||
|
if (!string.IsNullOrEmpty(Translation))
|
||
|
{
|
||
|
// has a valid translation
|
||
|
return true;
|
||
|
}
|
||
|
|
||
|
Translation = null;
|
||
|
}
|
||
|
|
||
|
if (OnMissingTranslation == MissingTranslationAction.ShowWarning)
|
||
|
{
|
||
|
Translation = $"<!-Missing Translation [{term}]-!>";
|
||
|
return true;
|
||
|
}
|
||
|
|
||
|
if (OnMissingTranslation == MissingTranslationAction.Fallback && data!=null)
|
||
|
{
|
||
|
return TryGetFallbackTranslation(data, out Translation, Index, overrideSpecialization, skipDisabled);
|
||
|
}
|
||
|
|
||
|
if (OnMissingTranslation == MissingTranslationAction.Empty)
|
||
|
{
|
||
|
Translation = string.Empty;
|
||
|
return true;
|
||
|
}
|
||
|
|
||
|
if (OnMissingTranslation == MissingTranslationAction.ShowTerm)
|
||
|
{
|
||
|
Translation = term;
|
||
|
return true;
|
||
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
Translation = null;
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
bool TryGetFallbackTranslation(TermData termData, out string Translation, int langIndex, string overrideSpecialization = null, bool skipDisabled = false)
|
||
|
{
|
||
|
// Find base Language Code
|
||
|
string baseLanguage = mLanguages[langIndex].Code;
|
||
|
if (!string.IsNullOrEmpty(baseLanguage))
|
||
|
{
|
||
|
if (baseLanguage.Contains('-'))
|
||
|
{
|
||
|
baseLanguage = baseLanguage.Substring(0, baseLanguage.IndexOf('-'));
|
||
|
}
|
||
|
|
||
|
// Try finding in any of the Region of the base language
|
||
|
for (int i = 0; i < mLanguages.Count; ++i)
|
||
|
{
|
||
|
if (i != langIndex &&
|
||
|
mLanguages[i].Code.StartsWith(baseLanguage, StringComparison.Ordinal) &&
|
||
|
(!skipDisabled || mLanguages[i].IsEnabled()) )
|
||
|
{
|
||
|
Translation = termData.GetTranslation(i, overrideSpecialization, editMode: true);
|
||
|
if (!string.IsNullOrEmpty(Translation))
|
||
|
return true;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
|
||
|
// Otherwise, Try finding the first active language with a valid translation
|
||
|
for (int i = 0; i < mLanguages.Count; ++i)
|
||
|
{
|
||
|
if (i!=langIndex &&
|
||
|
(!skipDisabled || mLanguages[i].IsEnabled()) &&
|
||
|
(baseLanguage==null || !mLanguages[i].Code.StartsWith(baseLanguage, StringComparison.Ordinal)))
|
||
|
{
|
||
|
Translation = termData.GetTranslation(i, overrideSpecialization, editMode: true);
|
||
|
if (!string.IsNullOrEmpty(Translation))
|
||
|
return true;
|
||
|
}
|
||
|
}
|
||
|
Translation = null;
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
public TermData AddTerm( string term )
|
||
|
{
|
||
|
return AddTerm (term, eTermType.Text);
|
||
|
}
|
||
|
|
||
|
public TermData GetTermData( string term, bool allowCategoryMistmatch = false)
|
||
|
{
|
||
|
if (string.IsNullOrEmpty(term))
|
||
|
return null;
|
||
|
|
||
|
if (mDictionary.Count==0)// != mTerms.Count)
|
||
|
UpdateDictionary();
|
||
|
|
||
|
TermData data;
|
||
|
if (mDictionary.TryGetValue(term, out data))
|
||
|
return data;
|
||
|
|
||
|
TermData d = null;
|
||
|
if (allowCategoryMistmatch)
|
||
|
{
|
||
|
var keyPart = GetKeyFromFullTerm (term);
|
||
|
foreach (var kvp in mDictionary)
|
||
|
if (kvp.Value.IsTerm (keyPart, true))
|
||
|
{
|
||
|
if (d == null)
|
||
|
d = kvp.Value;
|
||
|
else
|
||
|
return null;
|
||
|
}
|
||
|
}
|
||
|
return d;
|
||
|
}
|
||
|
|
||
|
public bool ContainsTerm(string term)
|
||
|
{
|
||
|
return GetTermData(term)!=null;
|
||
|
}
|
||
|
|
||
|
public List<string> GetTermsList ( string Category = null )
|
||
|
{
|
||
|
if (mDictionary.Count != mTerms.Count)
|
||
|
UpdateDictionary();
|
||
|
if (string.IsNullOrEmpty( Category ))
|
||
|
return new List<string>( mDictionary.Keys );
|
||
|
var terms = new List<string>();
|
||
|
for (int i=0; i<mTerms.Count; ++i)
|
||
|
{
|
||
|
var term = mTerms[i];
|
||
|
if (GetCategoryFromFullTerm( term.Term ) == Category)
|
||
|
terms.Add( term.Term );
|
||
|
}
|
||
|
return terms;
|
||
|
}
|
||
|
|
||
|
public TermData AddTerm( string NewTerm, eTermType termType, bool SaveSource = true )
|
||
|
{
|
||
|
ValidateFullTerm( ref NewTerm );
|
||
|
NewTerm = NewTerm.Trim ();
|
||
|
|
||
|
if (mLanguages.Count == 0)
|
||
|
AddLanguage ("English", "en");
|
||
|
|
||
|
// Don't duplicate Terms
|
||
|
TermData data = GetTermData(NewTerm);
|
||
|
if (data==null)
|
||
|
{
|
||
|
data = new TermData();
|
||
|
data.Term = NewTerm;
|
||
|
data.TermType = termType;
|
||
|
data.Languages = new string[ mLanguages.Count ];
|
||
|
data.Flags = new byte[ mLanguages.Count ];
|
||
|
mTerms.Add (data);
|
||
|
mDictionary.Add ( NewTerm, data);
|
||
|
#if UNITY_EDITOR
|
||
|
if (SaveSource)
|
||
|
{
|
||
|
Editor_SetDirty();
|
||
|
AssetDatabase.SaveAssets();
|
||
|
}
|
||
|
#endif
|
||
|
}
|
||
|
|
||
|
return data;
|
||
|
}
|
||
|
|
||
|
public void RemoveTerm( string term )
|
||
|
{
|
||
|
for (int i=0, imax=mTerms.Count; i<imax; ++i)
|
||
|
if (mTerms[i].Term==term)
|
||
|
{
|
||
|
mTerms.RemoveAt(i);
|
||
|
mDictionary.Remove(term);
|
||
|
return;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
public static void ValidateFullTerm( ref string Term )
|
||
|
{
|
||
|
Term = Term.Replace('\\', '/');
|
||
|
Term = Term.Trim();
|
||
|
if (Term.StartsWith(EmptyCategory, StringComparison.Ordinal))
|
||
|
{
|
||
|
if (Term.Length>EmptyCategory.Length && Term[EmptyCategory.Length]=='/')
|
||
|
Term = Term.Substring(EmptyCategory.Length+1);
|
||
|
}
|
||
|
Term = I2Utils.GetValidTermName(Term, true);
|
||
|
}
|
||
|
|
||
|
|
||
|
#endregion
|
||
|
}
|
||
|
}
|