1
0
mirror of https://github.com/cookiengineer/audacity synced 2025-06-16 16:10:06 +02:00

Remove TranslatedInternalString, use ComponentInterfaceSymbol

This commit is contained in:
Paul Licameli 2019-12-15 10:58:19 -05:00
parent e875adaa6f
commit 54e2bbd8ff
19 changed files with 79 additions and 116 deletions

View File

@ -78,9 +78,9 @@ public:
// Two-argument version distinguishes internal from translatable string
// such as when the first squeezes spaces out
ComponentInterfaceSymbol( const wxString &internal,
ComponentInterfaceSymbol( const Identifier &internal,
const TranslatableString &msgid )
: mInternal{ internal }
: mInternal{ internal.GET() }
// Do not permit non-empty msgid with empty internal
, mMsgid{ internal.empty() ? TranslatableString{} : msgid }
{}
@ -88,6 +88,8 @@ public:
const wxString &Internal() const { return mInternal; }
const TranslatableString &Msgid() const { return mMsgid; }
const wxString Translation() const { return mMsgid.Translation(); }
const wxString StrippedTranslation() const
{ return TranslatableString{mMsgid}.Strip().Translation(); }
bool empty() const { return mInternal.empty(); }

View File

@ -1754,9 +1754,9 @@ void AdornedRulerPanel::DrawBothOverlays()
void AdornedRulerPanel::UpdateButtonStates()
{
auto common = [this]
(AButton &button, const CommandID &commandName, const wxString &label) {
TranslatedInternalString command{ commandName, label };
auto common = [this](
AButton &button, const CommandID &commandName, const TranslatableString &label) {
ComponentInterfaceSymbol command{ commandName, label };
ToolBar::SetButtonToolTip( *mProject, button, &command, 1u );
button.SetLabel(button.GetToolTipText());
@ -1777,8 +1777,8 @@ void AdornedRulerPanel::UpdateButtonStates()
(gAudioIO->IsCapturing() ? 2 : 0) + (state ? 0 : 1));
// Bug 1584: Toltip now shows what clicking will do.
const auto label = state
? _("Click to unpin")
: _("Click to pin");
? XO("Click to unpin")
: XO("Click to pin");
common(*pinButton, wxT("PinnedHead"), label);
}
}

View File

@ -143,7 +143,7 @@ void MacroCommandDialog::PopulateCommandList()
long ii = 0;
for ( const auto &entry : mCatalog )
// insert the user-facing string
mChoices->InsertItem( ii++, entry.name.Translated() );
mChoices->InsertItem( ii++, entry.name.StrippedTranslation() );
}
void MacroCommandDialog::ValidateChoices()
@ -188,11 +188,12 @@ void MacroCommandDialog::OnItemSelected(wxListEvent &event)
mEditParams->Enable(!ID.empty());
mUsePreset->Enable(em.HasPresets(ID));
if ( command.name.Translated() == mCommand->GetValue() )
auto value = command.name.StrippedTranslation();
if ( value == mCommand->GetValue() )
// This uses the assumption of uniqueness of translated names!
return;
mCommand->SetValue(command.name.Translated());
mCommand->SetValue(value);
mInternalCommandName = command.name.Internal();
wxString params = MacroCommands::GetCurrentParamsFor(mInternalCommandName);
@ -244,11 +245,11 @@ void MacroCommandDialog::SetCommandAndParams(const CommandID &Command, const wxS
// in default of any better friendly name
mCommand->SetValue( Command.GET() );
else {
mCommand->SetValue( iter->name.Translated() );
mCommand->SetValue( iter->name.StrippedTranslation() );
// using GET to expose a CommandID to the user!
// Macro command details are one place that we do expose Identifier
// to (more sophisticated) users
mDetails->SetValue( iter->name.Internal().GET() + "\r\n" + iter->category );
mDetails->SetValue( iter->name.Internal() + "\r\n" + iter->category );
mChoices->SetItemState(iter - mCatalog.begin(),
wxLIST_STATE_SELECTED, wxLIST_STATE_SELECTED);

View File

@ -294,7 +294,7 @@ MacroCommandsCatalog::MacroCommandsCatalog( const AudacityProject *project )
Entries commands;
for( const auto &command : SpecialCommands )
commands.push_back( {
{ command.second, command.first.Translation() },
{ command.second, command.first },
_("Special Command")
} );
@ -309,7 +309,7 @@ MacroCommandsCatalog::MacroCommandsCatalog( const AudacityProject *project )
auto command = em.GetCommandIdentifier(plug->GetID());
if (!command.empty())
commands.push_back( {
{ command, plug->GetSymbol().Translation() },
{ command, plug->GetSymbol().Msgid() },
plug->GetPluginType() == PluginTypeEffect ?
_("Effect") : _("Menu Command (With Parameters)")
} );
@ -365,7 +365,7 @@ MacroCommandsCatalog::MacroCommandsCatalog( const AudacityProject *project )
{
{
mNames[i], // Internal name.
label.Translation() // User readable name
label // User readable name
},
_("Menu Command (No Parameters)")
}
@ -379,23 +379,26 @@ MacroCommandsCatalog::MacroCommandsCatalog( const AudacityProject *project )
// keeping specials before effects and menu items, and lastly commands.
auto less =
[](const Entry &a, const Entry &b)
{ return a.name.Translated() < b.name.Translated(); };
{ return a.name.StrippedTranslation() <
b.name.StrippedTranslation(); };
std::stable_sort(commands.begin(), commands.end(), less);
// Now uniquify by friendly name
auto equal =
[](const Entry &a, const Entry &b)
{ return a.name.Translated() == b.name.Translated(); };
{ return a.name.StrippedTranslation() ==
b.name.StrippedTranslation(); };
std::unique_copy(
commands.begin(), commands.end(), std::back_inserter(mCommands), equal);
}
// binary search
auto MacroCommandsCatalog::ByFriendlyName( const wxString &friendlyName ) const
auto MacroCommandsCatalog::ByFriendlyName( const TranslatableString &friendlyName ) const
-> Entries::const_iterator
{
const auto less = [](const Entry &entryA, const Entry &entryB)
{ return entryA.name.Translated() < entryB.name.Translated(); };
{ return entryA.name.StrippedTranslation() <
entryB.name.StrippedTranslation(); };
auto range = std::equal_range(
begin(), end(), Entry{ { {}, friendlyName }, {} }, less
);
@ -943,7 +946,7 @@ bool MacroCommands::ApplyMacro(
// uh oh, using GET to expose an internal name to the user!
// in default of any better friendly name
command.GET()
: iter->name.Translated();
: iter->name.StrippedTranslation();
if (!ApplyCommandInBatchMode(friendly, command, mParamsMacro[i]) || mAbort)
break;
}

View File

@ -16,6 +16,7 @@
#include "export/Export.h"
#include "commands/CommandFlag.h"
#include "audacity/ComponentInterface.h" // for ComponentInterfaceSymbol
class wxArrayString;
class Effect;
@ -28,7 +29,7 @@ class MacroCommandsCatalog {
public:
// A triple of user-visible name, internal string identifier and type/help string.
struct Entry {
TranslatedInternalString name;
ComponentInterfaceSymbol name;
wxString category;
};
using Entries = std::vector<Entry>;
@ -36,7 +37,7 @@ public:
MacroCommandsCatalog( const AudacityProject *project );
// binary search
Entries::const_iterator ByFriendlyName( const wxString &friendlyName ) const;
Entries::const_iterator ByFriendlyName( const TranslatableString &friendlyName ) const;
// linear search
Entries::const_iterator ByCommandId( const CommandID &commandId ) const;

View File

@ -745,7 +745,7 @@ void MacrosWindow::AddItem(const CommandID &Action, const wxString &Params)
{
auto entry = mCatalog.ByCommandId(Action);
auto friendlyName = entry != mCatalog.end()
? entry->name.Translated()
? entry->name.StrippedTranslation()
:
// uh oh, using GET to expose an internal name to the user!
// in default of any better friendly name

View File

@ -163,43 +163,4 @@ class ComponentInterfaceSymbol;
wxArrayStringEx LocalizedStrings(
const EnumValueSymbol strings[], size_t nStrings);
// This object pairs an internal string, maybe empty, with a translated string.
// Any internal string may be written to configuration or other files and,
// for compatibility, should not vary between Audacity versions.
// The translated string may be shown to users and may vary with locale, and
// Audacity version if it is decided to use a different user-visible message.
// Sometimes the translated string is derived from a msgid identical
// to the internal string. The translated string is not meant to persist.
class TranslatedInternalString
{
public:
using ID = CommandID;
TranslatedInternalString() = default;
// One-argument constructor from a msgid
explicit TranslatedInternalString( const wxString &internal )
: mInternal{ internal }, mTranslated{ GetCustomTranslation( internal ) }
{}
// Two-argument version, when translated does not derive from internal
TranslatedInternalString( const ID &internal,
const wxString &translated )
: mInternal{ internal }, mTranslated{ translated }
{}
const ID &Internal() const { return mInternal; }
const wxString Translated() const
{
wxString Temp = mTranslated;
Temp.Replace( "&","" );
return Temp;
}
private:
ID mInternal;
wxString mTranslated;
};
#endif

View File

@ -64,7 +64,7 @@ bool BatchEvalCommand::Apply(const CommandContext & context)
auto iter = catalog.ByCommandId(cmdName);
const wxString &friendly = (iter == catalog.end())
? cmdName // Expose internal name to user, in default of a better one!
: iter->name.Translated();
: iter->name.StrippedTranslation();
// Create a Batch that will have just one command in it...
MacroCommands Batch;

View File

@ -963,8 +963,8 @@ void CommandManager::SetKeyFromIndex(int i, const NormalizedKeyString &key)
entry->key = key;
}
wxString CommandManager::DescribeCommandsAndShortcuts
(const TranslatedInternalString commands[], size_t nCommands) const
TranslatableString CommandManager::DescribeCommandsAndShortcuts(
const ComponentInterfaceSymbol commands[], size_t nCommands) const
{
wxString mark;
// This depends on the language setting and may change in-session after
@ -974,7 +974,7 @@ wxString CommandManager::DescribeCommandsAndShortcuts
mark = wxT("\u200f");
static const wxString &separatorFormat = wxT("%s / %s");
wxString result;
TranslatableString result;
for (size_t ii = 0; ii < nCommands; ++ii) {
const auto &pair = commands[ii];
// If RTL, then the control character forces right-to-left sequencing of
@ -982,7 +982,11 @@ wxString CommandManager::DescribeCommandsAndShortcuts
// left, consistently with accelerators in menus (assuming matching
// operating system prefernces for language), even if the command name
// was missing from the translation file and defaulted to the English.
auto piece = wxString::Format(wxT("%s%s"), mark, pair.Translated());
// Note: not putting this and other short format strings in the
// translation catalogs
auto piece = TranslatableString{wxT("%s%s")}
.Format( mark, TranslatableString{pair.Msgid()}.Strip() );
auto name = pair.Internal();
if (!name.empty()) {
@ -1000,14 +1004,14 @@ wxString CommandManager::DescribeCommandsAndShortcuts
#endif
// The mark makes correctly placed parentheses for RTL, even
// in the case that the piece is untranslated.
piece = wxString::Format(format, piece, mark, keyString);
piece = TranslatableString{format}.Format( piece, mark, keyString );
}
}
if (result.empty())
result = piece;
else
result = wxString::Format(separatorFormat, result, piece);
result = TranslatableString{ separatorFormat }.Format( result, piece );
}
return result;
}

View File

@ -34,7 +34,6 @@ class wxMenuBar;
class wxArrayString;
class wxMenu;
class wxMenuBar;
class TranslatedInternalString;
using CommandParameter = CommandID;
struct MenuBarListEntry
@ -288,11 +287,11 @@ class AUDACITY_DLL_API CommandManager final
///
/// Formatting summaries that include shortcut keys
///
wxString DescribeCommandsAndShortcuts
TranslatableString DescribeCommandsAndShortcuts
(
// If a shortcut key is defined for the command, then it is appended,
// parenthesized, after the translated name.
const TranslatedInternalString commands[], size_t nCommands) const;
const ComponentInterfaceSymbol commands[], size_t nCommands) const;
// Sorted list of the shortcut keys to be exluded from the standard defaults
static const std::vector<NormalizedKeyString> &ExcludedList();

View File

@ -268,15 +268,15 @@ void ControlToolBar::RegenerateTooltips()
name = wxT("CursProjectStart");
break;
}
std::vector<TranslatedInternalString> commands(
1u, { name, pCtrl->GetLabel() } );
std::vector<ComponentInterfaceSymbol> commands(
1u, { name, TranslatableString{ pCtrl->GetLabel() } } );
// Some have a second
switch (iWinID)
{
case ID_PLAY_BUTTON:
// With shift
commands.push_back( { wxT("PlayLooped"), _("Loop Play") } );
commands.push_back( { wxT("PlayLooped"), XO("Loop Play") } );
break;
case ID_RECORD_BUTTON:
// With shift
@ -286,8 +286,8 @@ void ControlToolBar::RegenerateTooltips()
commands.push_back( {
wxT("Record2ndChoice"),
!bPreferNewTrack
? _("Record New Track")
: _("Append Record")
? XO("Record New Track")
: XO("Append Record")
} );
}
break;
@ -298,12 +298,12 @@ void ControlToolBar::RegenerateTooltips()
case ID_FF_BUTTON:
// With shift
commands.push_back( {
wxT("SelEnd"), _("Select to End") } );
wxT("SelEnd"), XO("Select to End") } );
break;
case ID_REW_BUTTON:
// With shift
commands.push_back( {
wxT("SelStart"), _("Select to Start") } );
wxT("SelStart"), XO("Select to Start") } );
break;
}
ToolBar::SetButtonToolTip(

View File

@ -277,8 +277,8 @@ void EditToolBar::ForAllButtons(int Action)
for (const auto &entry : EditToolbarButtonList) {
#if wxUSE_TOOLTIPS
if( Action & ETBActTooltips ){
TranslatedInternalString command{
entry.commandName, entry.untranslatedLabel.Translation() };
ComponentInterfaceSymbol command{
entry.commandName, entry.untranslatedLabel };
ToolBar::SetButtonToolTip( mProject,
*mButtons[entry.tool], &command, 1u );
}

View File

@ -149,10 +149,10 @@ void ScrubbingToolBar::RegenerateTooltips()
void ScrubbingToolBar::DoRegenerateTooltips( bool force )
{
#if wxUSE_TOOLTIPS
auto fn = [&]
(AButton &button, const wxString &label, const CommandID &cmd)
auto fn = [&](
AButton &button, const TranslatableString &label, const CommandID &cmd)
{
TranslatedInternalString command{ cmd, label };
ComponentInterfaceSymbol command{ cmd, label };
ToolBar::SetButtonToolTip( mProject, button, &command, 1u );
};
@ -163,7 +163,7 @@ void ScrubbingToolBar::DoRegenerateTooltips( bool force )
const auto scrubButton = mButtons[STBScrubID];
const auto seekButton = mButtons[STBSeekID];
wxString label;
TranslatableString label;
bool scrubs = scrubber.Scrubs();
if (force || mLastScrub != scrubs) {
label = (
@ -172,8 +172,8 @@ void ScrubbingToolBar::DoRegenerateTooltips( bool force )
"Scrubbing" is variable-speed playback, ...
"Seeking" is normal speed playback but with skips
*/
? _("Stop Scrubbing")
: _("Start Scrubbing")
? XO("Stop Scrubbing")
: XO("Start Scrubbing")
);
fn(*scrubButton, label, wxT("Scrub"));
}
@ -187,8 +187,8 @@ void ScrubbingToolBar::DoRegenerateTooltips( bool force )
"Scrubbing" is variable-speed playback, ...
"Seeking" is normal speed playback but with skips
*/
? _("Stop Seeking")
: _("Start Seeking")
? XO("Stop Seeking")
: XO("Start Seeking")
);
fn(*seekButton, label, wxT("Seek"));
}
@ -198,8 +198,8 @@ void ScrubbingToolBar::DoRegenerateTooltips( bool force )
if (force || mLastRuler != showingRuler) {
label = (
showingRuler
? _("Hide Scrub Ruler")
: _("Show Scrub Ruler")
? XO("Hide Scrub Ruler")
: XO("Show Scrub Ruler")
);
fn(*mButtons[STBRulerID], label, wxT("ToggleScrubRuler"));
}

View File

@ -860,16 +860,16 @@ void ToolBar::MakeAlternateImages(AButton &button, int idx,
void ToolBar::SetButtonToolTip
(AudacityProject &theProject,
AButton &button, const TranslatedInternalString commands[], size_t nCommands)
AButton &button, const ComponentInterfaceSymbol commands[], size_t nCommands)
{
wxString result;
TranslatableString result;
const auto project = &theProject;
const auto commandManager =
project ? &CommandManager::Get( *project ) : nullptr;
if (commandManager)
result =
commandManager->DescribeCommandsAndShortcuts(commands, nCommands);
button.SetToolTip( TranslatableString{ result } );
button.SetToolTip( result );
}
//

View File

@ -172,7 +172,7 @@ public:
(AudacityProject &project, AButton &button,
// If a shortcut key is defined for the command, then it is appended,
// parenthesized, after the translated name.
const TranslatedInternalString commands[], size_t nCommands);
const ComponentInterfaceSymbol commands[], size_t nCommands);
static void MakeButtonBackgroundsSmall();
static void MakeButtonBackgroundsLarge();

View File

@ -153,8 +153,8 @@ void ToolsToolBar::RegenerateTooltips()
};
for (const auto &entry : table) {
TranslatedInternalString command{
entry.commandName, entry.untranslatedLabel.Translation() };
ComponentInterfaceSymbol command{
entry.commandName, entry.untranslatedLabel };
ToolBar::SetButtonToolTip( mProject,
*mTool[entry.tool], &command, 1u );
}

View File

@ -346,9 +346,9 @@ void TranscriptionToolBar::RegenerateTooltips()
};
for (const auto &entry : table) {
TranslatedInternalString commands[] = {
{ entry.commandName, entry.untranslatedLabel.Translation() },
{ entry.commandName2, entry.untranslatedLabel2.Translation() },
ComponentInterfaceSymbol commands[] = {
{ entry.commandName, entry.untranslatedLabel },
{ entry.commandName2, entry.untranslatedLabel2 },
};
ToolBar::SetButtonToolTip( mProject,
*mButtons[entry.tool], commands, 2u );

View File

@ -51,10 +51,8 @@ TranslatableString MuteButtonHandle::Tip(const wxMouseState &) const
return name;
auto &commandManager = CommandManager::Get( *project );
TranslatedInternalString command{ wxT("TrackMute"), name.Translation() };
return TranslatableString{
commandManager.DescribeCommandsAndShortcuts(&command, 1u)
};
ComponentInterfaceSymbol command{ wxT("TrackMute"), name };
return commandManager.DescribeCommandsAndShortcuts(&command, 1u);
}
UIHandlePtr MuteButtonHandle::HitTest
@ -109,10 +107,8 @@ TranslatableString SoloButtonHandle::Tip(const wxMouseState &) const
return name;
auto &commandManager = CommandManager::Get( *project );
TranslatedInternalString command{ wxT("TrackSolo"), name.Translation() };
return TranslatableString{
commandManager.DescribeCommandsAndShortcuts( &command, 1u )
};
ComponentInterfaceSymbol command{ wxT("TrackSolo"), name };
return commandManager.DescribeCommandsAndShortcuts( &command, 1u );
}
UIHandlePtr SoloButtonHandle::HitTest

View File

@ -180,10 +180,8 @@ TranslatableString CloseButtonHandle::Tip(const wxMouseState &) const
return name;
auto &commandManager = CommandManager::Get( *project );
TranslatedInternalString command{ wxT("TrackClose"), name.Translation() };
return TranslatableString{
commandManager.DescribeCommandsAndShortcuts( &command, 1u )
};
ComponentInterfaceSymbol command{ wxT("TrackClose"), name };
return commandManager.DescribeCommandsAndShortcuts( &command, 1u );
}
UIHandlePtr CloseButtonHandle::HitTest
@ -242,10 +240,8 @@ TranslatableString MenuButtonHandle::Tip(const wxMouseState &) const
return name;
auto &commandManager = CommandManager::Get( *project );
TranslatedInternalString command{ wxT("TrackMenu"), name.Translation() };
return TranslatableString{
commandManager.DescribeCommandsAndShortcuts( &command, 1u )
};
ComponentInterfaceSymbol command{ wxT("TrackMenu"), name };
return commandManager.DescribeCommandsAndShortcuts( &command, 1u );
}
UIHandlePtr MenuButtonHandle::HitTest