Fix AddAvailableCatalog() API

Knowing msgIdLanguage is necessary for correct evaluation of preferred
languages order; without it, it would be possible to load undesirable
translation file.

See 2af36e9560 for details.
This commit is contained in:
Václav Slavík 2024-02-10 11:46:13 +01:00
parent 2af36e9560
commit 1030147aff
3 changed files with 35 additions and 19 deletions

View file

@ -160,7 +160,7 @@ public:
// add catalog for the given domain returning true if it could be found by
// wxTranslationsLoader
bool AddAvailableCatalog(const wxString& domain);
bool AddAvailableCatalog(const wxString& domain, wxLanguage msgIdLanguage = wxLANGUAGE_ENGLISH_US);
// add standard wxWidgets catalog ("wxstd")
bool AddStdCatalog();
@ -193,6 +193,15 @@ public:
static const wxString& GetUntranslatedString(const wxString& str);
private:
enum class Translations
{
NotNeeded = -1,
NotFound = 0,
Found = 1
};
Translations DoAddCatalog(const wxString& domain, wxLanguage msgIdLanguage);
// perform loading of the catalog via m_loader
bool LoadCatalog(const wxString& domain, const wxString& lang);

View file

@ -158,6 +158,16 @@ public:
All loaded catalogs will be used for message lookup by GetString() for
the current locale.
@param domain
The catalog domain to add.
@param msgIdLanguage
Specifies the language of "msgid" strings in source code
(i.e. arguments to GetString(), wxGetTranslation() and the _() macro).
It is used if AddCatalog() cannot find any catalog for current language:
if the language is same as source code language, then strings from source
code are used instead.
@return
@true if catalog was successfully loaded, @false otherwise, usually
because it wasn't found. Note that unlike AddCatalog() this
@ -167,9 +177,10 @@ public:
selected or system-default languages, but is not necessarily an
error if no translations are needed in the first place.
@since 3.3.0
@since 3.2.5
*/
bool AddAvailableCatalog(const wxString& domain);
bool AddAvailableCatalog(const wxString& domain,
wxLanguage msgIdLanguage = wxLANGUAGE_ENGLISH_US);
/**
Add a catalog for use with the current locale or fall back to the

View file

@ -1315,22 +1315,18 @@ bool wxTranslations::AddStdCatalog()
return AddCatalog(domain);
}
bool wxTranslations::AddAvailableCatalog(const wxString& domain)
bool wxTranslations::AddAvailableCatalog(const wxString& domain, wxLanguage msgIdLanguage)
{
const wxString domain_lang = GetBestAvailableTranslation(domain);
if ( domain_lang.empty() )
{
wxLogTrace(TRACE_I18N,
wxS("no suitable translation for domain '%s' found"),
domain);
return false;
}
return LoadCatalog(domain, domain_lang);
return DoAddCatalog(domain, msgIdLanguage) == Translations::Found;
}
bool wxTranslations::AddCatalog(const wxString& domain,
wxLanguage msgIdLanguage)
bool wxTranslations::AddCatalog(const wxString& domain, wxLanguage msgIdLanguage)
{
return DoAddCatalog(domain, msgIdLanguage) != Translations::NotFound;
}
wxTranslations::Translations wxTranslations::DoAddCatalog(const wxString& domain,
wxLanguage msgIdLanguage)
{
const wxString msgIdLang = wxUILocale::GetLanguageCanonicalName(msgIdLanguage);
const wxString domain_lang = GetBestTranslation(domain, msgIdLang);
@ -1339,7 +1335,7 @@ bool wxTranslations::AddCatalog(const wxString& domain,
wxLogTrace(TRACE_I18N,
wxS("no suitable translation for domain '%s' found"),
domain);
return false;
return Translations::NotFound;
}
if ( LoadCatalog(domain, domain_lang) )
@ -1347,7 +1343,7 @@ bool wxTranslations::AddCatalog(const wxString& domain,
wxLogTrace(TRACE_I18N,
wxS("adding '%s' translation for domain '%s' (msgid language '%s')"),
domain_lang, domain, msgIdLang);
return true;
return Translations::Found;
}
// LoadCatalog() failed, but GetBestTranslation() returned non-empty language.
@ -1355,7 +1351,7 @@ bool wxTranslations::AddCatalog(const wxString& domain,
wxLogTrace(TRACE_I18N,
wxS("not using translations for domain '%s' with msgid language '%s'"),
domain, msgIdLang);
return true;
return Translations::NotNeeded;
}