From 5177768962dd0999bcde8a3e18d0a4ca62345ab5 Mon Sep 17 00:00:00 2001 From: blitzmann Date: Sat, 16 May 2020 14:42:29 -0400 Subject: [PATCH] Start working through the files, adding translation strings --- gui/aboutData.py | 14 ++--- gui/additionsPane.py | 19 +++---- gui/characterEditor.py | 118 +++++++++++++++++------------------------ gui/mainFrame.py | 85 ++++++++++++++++------------- pyfa.py | 6 ++- 5 files changed, 121 insertions(+), 121 deletions(-) diff --git a/gui/aboutData.py b/gui/aboutData.py index a574af246..ef0a5fd7b 100644 --- a/gui/aboutData.py +++ b/gui/aboutData.py @@ -18,6 +18,8 @@ # ============================================================================= import config +import wx +_ = wx.GetTranslation try: versionString = "{0}".format(config.getVersion()) @@ -26,10 +28,10 @@ except NameError: versionString = "0.0" licenses = ( - "pyfa is released under GNU GPLv3 - see included LICENSE file", - "All EVE-Online related materials are property of CCP hf.", - "Silk Icons Set by famfamfam.com - Creative Commons Attribution 2.5 License", - "Fat Cow Icons by fatcow.com - Creative Commons Attribution 3.0 License" + _("pyfa is released under GNU GPLv3 - see included LICENSE file"), + _("All EVE-Online related materials are property of CCP hf."), + _("Silk Icons Set by famfamfam.com - Creative Commons Attribution 2.5 License"), + _("Fat Cow Icons by fatcow.com - Creative Commons Attribution 3.0 License") ) developers = ( "blitzmann \tSable Blitzmann (maintainer)", @@ -44,7 +46,7 @@ credits = ( "Corollax (Aamrr) \tVarious EOS / pyfa improvements", "Dreae (Dreae)\tPyCrest") description = ( - "Pyfa (the Python Fitting Assistant) is an open-source standalone application able to " + _("Pyfa (the Python Fitting Assistant) is an open-source standalone application able to " "create and simulate fittings for EVE-Online SciFi MMORPG with a very high degree of " - "accuracy. Pyfa can run on all platforms where Python and wxWidgets are supported." + "accuracy. Pyfa can run on all platforms where Python and wxWidgets are supported.") ) diff --git a/gui/additionsPane.py b/gui/additionsPane.py index c4d7d3fe9..21b246069 100644 --- a/gui/additionsPane.py +++ b/gui/additionsPane.py @@ -33,6 +33,7 @@ from gui.builtinAdditionPanes.projectedView import ProjectedView from gui.chrome_tabs import ChromeNotebook from gui.toggle_panel import TogglePanel +_ = wx.GetTranslation class AdditionsPane(TogglePanel): @@ -41,7 +42,7 @@ class AdditionsPane(TogglePanel): TogglePanel.__init__(self, parent, force_layout=1) self.mainFrame = mainFrame - self.SetLabel("Additions") + self.SetLabel(_("Additions")) pane = self.GetContentPanel() baseSizer = wx.BoxSizer(wx.HORIZONTAL) @@ -62,28 +63,28 @@ class AdditionsPane(TogglePanel): notesImg = BitmapLoader.getImage("skill_small", "gui") self.drone = DroneView(self.notebook) - self.notebook.AddPage(self.drone, "Drones", image=droneImg, closeable=False) + self.notebook.AddPage(self.drone, _("Drones"), image=droneImg, closeable=False) self.fighter = FighterView(self.notebook) - self.notebook.AddPage(self.fighter, "Fighters", image=fighterImg, closeable=False) + self.notebook.AddPage(self.fighter, _("Fighters"), image=fighterImg, closeable=False) self.cargo = CargoView(self.notebook) - self.notebook.AddPage(self.cargo, "Cargo", image=cargoImg, closeable=False) + self.notebook.AddPage(self.cargo, _("Cargo"), image=cargoImg, closeable=False) self.implant = ImplantView(self.notebook) - self.notebook.AddPage(self.implant, "Implants", image=implantImg, closeable=False) + self.notebook.AddPage(self.implant, _("Implants"), image=implantImg, closeable=False) self.booster = BoosterView(self.notebook) - self.notebook.AddPage(self.booster, "Boosters", image=boosterImg, closeable=False) + self.notebook.AddPage(self.booster, _("Boosters"), image=boosterImg, closeable=False) self.projectedPage = ProjectedView(self.notebook) - self.notebook.AddPage(self.projectedPage, "Projected", image=projectedImg, closeable=False) + self.notebook.AddPage(self.projectedPage, _("Projected"), image=projectedImg, closeable=False) self.gangPage = CommandView(self.notebook) - self.notebook.AddPage(self.gangPage, "Command", image=gangImg, closeable=False) + self.notebook.AddPage(self.gangPage, _("Command"), image=gangImg, closeable=False) self.notes = NotesView(self.notebook) - self.notebook.AddPage(self.notes, "Notes", image=notesImg, closeable=False) + self.notebook.AddPage(self.notes, _("Notes"), image=notesImg, closeable=False) self.mainFrame.Bind(GE.FIT_CHANGED, self.OnFitChanged) self.mainFrame.Bind(GE.FIT_NOTES_CHANGED, self.OnNotesChanged) diff --git a/gui/characterEditor.py b/gui/characterEditor.py index 39f94078d..ae3268539 100644 --- a/gui/characterEditor.py +++ b/gui/characterEditor.py @@ -45,6 +45,7 @@ from service.esi import Esi from service.fit import Fit from service.market import Market +_ = wx.GetTranslation pyfalog = Logger(__name__) @@ -72,43 +73,21 @@ class CharacterTextValidor(BaseValidator): try: if len(text) == 0: - raise ValueError("You must supply a name for the Character!") + raise ValueError(_("You must supply a name for the Character!")) elif text in [x.name for x in sChar.getCharacterList()]: - raise ValueError("Character name already in use, please choose another.") + raise ValueError(_("Character name already in use, please choose another.")) return True except ValueError as e: pyfalog.error(e) - wx.MessageBox("{}".format(e), "Error") + wx.MessageBox("{}".format(e), _("Error")) textCtrl.SetFocus() return False -class PlaceholderTextCtrl(wx.TextCtrl): - def __init__(self, *args, **kwargs): - self.default_text = kwargs.pop("placeholder", "") - kwargs["value"] = self.default_text - wx.TextCtrl.__init__(self, *args, **kwargs) - self.Bind(wx.EVT_SET_FOCUS, self.OnFocus) - self.Bind(wx.EVT_KILL_FOCUS, self.OnKillFocus) - - def OnFocus(self, evt): - if self.GetValue() == self.default_text: - self.SetValue("") - evt.Skip() - - def OnKillFocus(self, evt): - if self.GetValue().strip() == "": - self.SetValue(self.default_text) - evt.Skip() - - def Reset(self): - self.SetValue(self.default_text) - - class CharacterEntityEditor(EntityEditor): def __init__(self, parent): - EntityEditor.__init__(self, parent, "Character") + EntityEditor.__init__(self, parent, _("Character")) self.SetEditorValidator(CharacterTextValidor) def getEntitiesFromContext(self): @@ -155,7 +134,7 @@ class CharacterEditor(AuxiliaryFrame): def __init__(self, parent): super().__init__( - parent, id=wx.ID_ANY, title="Character Editor", resizeable=True, pos=wx.DefaultPosition, + parent, id=wx.ID_ANY, title=_("Character Editor"), resizeable=True, pos=wx.DefaultPosition, size=wx.Size(950, 650) if "wxGTK" in wx.PlatformInfo else wx.Size(850, 600)) i = wx.Icon(BitmapLoader.getBitmap("character_small", "gui")) @@ -178,17 +157,17 @@ class CharacterEditor(AuxiliaryFrame): self.iview = ImplantEditorView(self.viewsNBContainer, self) self.aview = APIView(self.viewsNBContainer) - self.viewsNBContainer.AddPage(self.sview, "Skills") - self.viewsNBContainer.AddPage(self.iview, "Implants") - self.viewsNBContainer.AddPage(self.aview, "EVE SSO") + self.viewsNBContainer.AddPage(self.sview, _("Skills")) + self.viewsNBContainer.AddPage(self.iview, _("Implants")) + self.viewsNBContainer.AddPage(self.aview, _("EVE SSO")) mainSizer.Add(self.viewsNBContainer, 1, wx.EXPAND | wx.ALL, 5) bSizerButtons = wx.BoxSizer(wx.HORIZONTAL) - self.btnSaveChar = wx.Button(self, wx.ID_ANY, "Save") - self.btnSaveAs = wx.Button(self, wx.ID_ANY, "Save As...") - self.btnRevert = wx.Button(self, wx.ID_ANY, "Revert") + self.btnSaveChar = wx.Button(self, wx.ID_SAVE) + self.btnSaveAs = wx.Button(self, wx.ID_SAVEAS) + self.btnRevert = wx.Button(self, wx.ID_REVERT_TO_SAVED) self.btnOK = wx.Button(self, wx.ID_OK) bSizerButtons.Add(self.btnSaveChar, 0, wx.ALL, 5) @@ -299,10 +278,10 @@ class CharacterEditor(AuxiliaryFrame): with TextEntryValidatedDialog( parent, CharacterTextValidor, - "Enter a name for your new Character:", - "Save Character As..." + _("Enter a name for your new Character:"), + _("Save Character As...") ) as dlg: - dlg.SetValue("{} Copy".format(name)) + dlg.SetValue(_("{} Copy").format(name)) dlg.txtctrl.SetInsertionPointEnd() dlg.CenterOnParent() @@ -327,7 +306,7 @@ class SkillTreeView(wx.Panel): self.clonesChoice.SetSelection(i) hSizer.Add(self.clonesChoice, 5, wx.ALL | wx.EXPAND, 5) - self.searchInput = PlaceholderTextCtrl(self, wx.ID_ANY, placeholder="Search...") + self.searchInput = wx.SearchCtrl(self, wx.ID_ANY) hSizer.Add(self.searchInput, 1, wx.ALL | wx.EXPAND, 5) self.searchInput.Bind(wx.EVT_TEXT, self.delaySearch) @@ -343,7 +322,7 @@ class SkillTreeView(wx.Panel): self.clonesChoice.Bind(wx.EVT_CHOICE, self.cloneChanged) self.clonesChoice.SetToolTip( - wx.ToolTip("Setting an Alpha clone does not replace the character's skills, but rather caps them to Alpha levels.")) + wx.ToolTip(_("Setting an Alpha clone does not replace the character's skills, but rather caps them to Alpha levels."))) pmainSizer.Add(hSizer, 0, wx.EXPAND | wx.ALL, 5) @@ -359,8 +338,8 @@ class SkillTreeView(wx.Panel): self.skillBookImageId = self.imageList.Add(wx.Icon(BitmapLoader.getBitmap("skill_small", "gui"))) self.skillBookDirtyImageId = self.imageList.Add(wx.Icon(BitmapLoader.getBitmap("skill_small_red", "gui"))) - tree.AppendColumn("Skill") - tree.AppendColumn("Level", align=wx.ALIGN_CENTER) + tree.AppendColumn(_("Skill")) + tree.AppendColumn(_("Level"), align=wx.ALIGN_CENTER) # tree.SetMainColumn(0) self.root = tree.GetRootItem() @@ -373,7 +352,8 @@ class SkillTreeView(wx.Panel): tree.SetColumnWidth(0, 525) tree.SetColumnWidth(1, 100) - self.btnSecStatus = wx.Button(self, wx.ID_ANY, "Sec Status: {0:.2f}".format(char.secStatus or 0.0)) + self.secStatusLabel = _("Sec Status: {0:.2f}") + self.btnSecStatus = wx.Button(self, wx.ID_ANY, self.secStatusLabel.format(char.secStatus or 0.0)) self.btnSecStatus.Bind(wx.EVT_BUTTON, self.onSecStatus) self.populateSkillTree() @@ -388,8 +368,8 @@ class SkillTreeView(wx.Panel): bSizerButtons.AddStretchSpacer() - importExport = (("Import", wx.ART_FILE_OPEN, "from"), - ("Export", wx.ART_FILE_SAVE_AS, "to")) + importExport = ((_("Import"), wx.ART_FILE_OPEN, _("from")), + (_("Export"), wx.ART_FILE_SAVE_AS, _("to"))) for name, art, direction in importExport: bitmap = wx.ArtProvider.GetBitmap(art, wx.ART_BUTTON) @@ -401,7 +381,7 @@ class SkillTreeView(wx.Panel): btn.Layout() setattr(self, "{}Btn".format(name.lower()), btn) btn.Enable(True) - btn.SetToolTip("%s skills %s clipboard" % (name, direction)) + btn.SetToolTip(_("%s skills %s clipboard") % (name, direction)) bSizerButtons.Add(btn, 0, wx.ALL, 5) btn.Bind(wx.EVT_BUTTON, getattr(self, "{}Skills".format(name.lower()))) @@ -456,9 +436,9 @@ class SkillTreeView(wx.Panel): def importSkills(self, evt): with wx.MessageDialog( - self, ("Importing skills into this character will set the skill levels as pending. To save the skills " - "permanently, please click the Save button at the bottom of the window after importing"), - "Import Skills", wx.OK + self, (_("Importing skills into this character will set the skill levels as pending. To save the skills " + "permanently, please click the Save button at the bottom of the window after importing")), + _("Import Skills"), wx.OK ) as dlg: dlg.ShowModal() @@ -479,7 +459,7 @@ class SkillTreeView(wx.Panel): raise except Exception as e: pyfalog.error(e) - with wx.MessageDialog(self, "There was an error importing skills, please see log file", "Error", wx.ICON_ERROR) as dlg: + with wx.MessageDialog(self, _("There was an error importing skills, please see log file"), _("Error"), wx.ICON_ERROR) as dlg: dlg.ShowModal() finally: @@ -505,10 +485,10 @@ class SkillTreeView(wx.Panel): if dlg.ShowModal() == wx.ID_OK: value = dlg.floatSpin.GetValue() sChar.setSecStatus(char, value) - self.btnSecStatus.SetLabel("Sec Status: {0:.2f}".format(value)) + self.btnSecStatus.SetLabel(self.secStatusLabel.format(value)) def delaySearch(self, evt): - if self.searchInput.GetValue() == "" or self.searchInput.GetValue() == self.searchInput.default_text: + if self.searchInput.GetValue() == "": self.populateSkillTree() else: self.searchTimer.Stop() @@ -520,14 +500,14 @@ class SkillTreeView(wx.Panel): self.populateSkillTree() def charChanged(self, event=None): - self.searchInput.Reset() + self.searchInput.SetValue("") char = self.charEditor.entityEditor.getActiveEntity() for i in range(self.clonesChoice.GetCount()): cloneID = self.clonesChoice.GetClientData(i) if char.alphaCloneID == cloneID: self.clonesChoice.SetSelection(i) - self.btnSecStatus.SetLabel("Sec Status: {0:.2f}".format(char.secStatus or 0.0)) + self.btnSecStatus.SetLabel(self.secStatusLabel.format(char.secStatus or 0.0)) self.populateSkillTree(event) @@ -548,7 +528,7 @@ class SkillTreeView(wx.Panel): iconId = self.skillBookDirtyImageId childId = tree.AppendItem(root, name, iconId, data=('skill', id)) - tree.SetItemText(childId, 1, "Level %d" % int(level) if isinstance(level, float) else level) + tree.SetItemText(childId, 1, _("Level {}d").format(int(level) if isinstance(level, float) else level)) def populateSkillTree(self, event=None): sChar = Character.getInstance() @@ -607,7 +587,7 @@ class SkillTreeView(wx.Panel): childId = tree.AppendItem(root, name, iconId, data=('skill', id)) - tree.SetItemText(childId, 1, "Level %d" % int(level) if isinstance(level, float) else level) + tree.SetItemText(childId, 1, _("Level {}").format(int(level) if isinstance(level, float) else level)) def spawnMenu(self, event): item = event.GetItem() @@ -626,9 +606,9 @@ class SkillTreeView(wx.Panel): char = self.charEditor.entityEditor.getActiveEntity() if char.name not in ("All 0", "All 5"): menu.AppendSeparator() - menu.Append(self.idUnlearned, "Unlearn") + menu.Append(self.idUnlearned, _("Unlearn")) for level in range(6): - menu.Append(self.idLevels[level], "Level %d" % level) + menu.Append(self.idLevels[level], _("Level {}").format(level)) menu.Bind(wx.EVT_MENU, self.changeLevel) self.PopupMenu(menu) @@ -661,7 +641,7 @@ class SkillTreeView(wx.Panel): lvl, dirty = sChar.getSkillLevel(char.ID, skillID) self.skillTreeListCtrl.SetItemText(treeItem, 1, - "Level {}".format(int(lvl)) if not isinstance(lvl, str) else lvl) + _("Level {}").format(int(lvl)) if not isinstance(lvl, str) else lvl) if not dirty: self.skillTreeListCtrl.SetItemImage(treeItem, self.skillBookImageId) @@ -769,8 +749,8 @@ class APIView(wx.Panel): hintSizer = wx.BoxSizer(wx.HORIZONTAL) hintSizer.AddStretchSpacer() self.stDisabledTip = wx.StaticText(self, wx.ID_ANY, - "You cannot link All 0 or All 5 characters to an EVE character.\n" - "Please select another character or make a new one.", style=wx.ALIGN_CENTER) + _("You cannot link All 0 or All 5 characters to an EVE character.") + "\n" + + _("Please select another character or make a new one."), style=wx.ALIGN_CENTER) self.stDisabledTip.Wrap(-1) hintSizer.Add(self.stDisabledTip, 0, wx.TOP | wx.BOTTOM, 10) @@ -783,14 +763,14 @@ class APIView(wx.Panel): fgSizerInput.SetFlexibleDirection(wx.BOTH) fgSizerInput.SetNonFlexibleGrowMode(wx.FLEX_GROWMODE_SPECIFIED) - self.m_staticCharText = wx.StaticText(self, wx.ID_ANY, "Character:", wx.DefaultPosition, wx.DefaultSize, 0) + self.m_staticCharText = wx.StaticText(self, wx.ID_ANY, _("Character:"), wx.DefaultPosition, wx.DefaultSize, 0) self.m_staticCharText.Wrap(-1) fgSizerInput.Add(self.m_staticCharText, 0, wx.ALL | wx.ALIGN_RIGHT | wx.ALIGN_CENTER_VERTICAL, 10) self.charChoice = wx.Choice(self, wx.ID_ANY, style=0) fgSizerInput.Add(self.charChoice, 1, wx.TOP | wx.BOTTOM | wx.EXPAND, 10) - self.fetchButton = wx.Button(self, wx.ID_ANY, "Get Skills", wx.DefaultPosition, wx.DefaultSize, 0) + self.fetchButton = wx.Button(self, wx.ID_ANY, _("Get Skills"), wx.DefaultPosition, wx.DefaultSize, 0) self.fetchButton.Bind(wx.EVT_BUTTON, self.fetchSkills) fgSizerInput.Add(self.fetchButton, 0, wx.ALL | wx.ALIGN_RIGHT | wx.ALIGN_CENTER_VERTICAL, 10) @@ -801,12 +781,12 @@ class APIView(wx.Panel): self.m_staticline1 = wx.StaticLine(self, wx.ID_ANY, wx.DefaultPosition, wx.DefaultSize, wx.LI_HORIZONTAL) pmainSizer.Add(self.m_staticline1, 0, wx.EXPAND | wx.ALL, 10) - self.noCharactersTip = wx.StaticText(self, wx.ID_ANY, "Don't see your EVE character in the list?", style=wx.ALIGN_CENTER) + self.noCharactersTip = wx.StaticText(self, wx.ID_ANY, _("Don't see your EVE character in the list?"), style=wx.ALIGN_CENTER) self.noCharactersTip.Wrap(-1) pmainSizer.Add(self.noCharactersTip, 0, wx.CENTER | wx.TOP | wx.BOTTOM, 0) - self.addButton = wx.Button(self, wx.ID_ANY, "Log In with EVE SSO", wx.DefaultPosition, wx.DefaultSize, 0) + self.addButton = wx.Button(self, wx.ID_ANY, _("Log In with EVE SSO"), wx.DefaultPosition, wx.DefaultSize, 0) self.addButton.Bind(wx.EVT_BUTTON, self.addCharacter) pmainSizer.Add(self.addButton, 0, wx.ALL | wx.ALIGN_CENTER, 10) @@ -867,7 +847,7 @@ class APIView(wx.Panel): self.charChoice.Clear() - noneID = self.charChoice.Append("None", None) + noneID = self.charChoice.Append(_("None"), None) for char in ssoChars: currId = self.charChoice.Append(char.characterName, char.ID) @@ -909,24 +889,24 @@ class APIView(wx.Panel): pyfalog.warn(exc_value) wx.MessageBox( - "Error fetching skill information", - "Error", wx.ICON_ERROR | wx.STAY_ON_TOP) + _("Error fetching skill information"), + _("Error"), wx.ICON_ERROR | wx.STAY_ON_TOP) else: wx.MessageBox( - "Successfully fetched skills", "Success", wx.ICON_INFORMATION | wx.STAY_ON_TOP) + _("Successfully fetched skills"), _("Success"), wx.ICON_INFORMATION | wx.STAY_ON_TOP) class SecStatusDialog(wx.Dialog): def __init__(self, parent, sec): - super().__init__(parent, title="Set Security Status", size=(300, 175), style=wx.DEFAULT_DIALOG_STYLE) + super().__init__(parent, title=_("Set Security Status"), size=(300, 175), style=wx.DEFAULT_DIALOG_STYLE) self.SetSizeHints(wx.DefaultSize, wx.DefaultSize) bSizer1 = wx.BoxSizer(wx.VERTICAL) self.m_staticText1 = wx.StaticText(self, wx.ID_ANY, - "Security Status is used in some CONCORD hull calculations", + _("Security Status is used in some CONCORD hull calculations"), wx.DefaultPosition, wx.DefaultSize, 0) self.m_staticText1.Wrap(-1) bSizer1.Add(self.m_staticText1, 1, wx.ALL | wx.EXPAND, 5) diff --git a/gui/mainFrame.py b/gui/mainFrame.py index 244d1bf18..74ebe22b6 100644 --- a/gui/mainFrame.py +++ b/gui/mainFrame.py @@ -69,6 +69,7 @@ from service.price import Price from service.settings import HTMLExportSettings, SettingsProvider from service.update import Update +_ = wx.GetTranslation pyfalog = Logger(__name__) @@ -182,7 +183,7 @@ class MainFrame(wx.Frame): self.marketBrowser.splitter.SetSashPosition(self.marketHeight) self.shipBrowser = ShipBrowser(self.notebookBrowsers) - self.notebookBrowsers.AddPage(self.shipBrowser, "Fittings", image=shipBrowserImg, closeable=False) + self.notebookBrowsers.AddPage(self.shipBrowser, _("Fittings"), image=shipBrowserImg, closeable=False) self.notebookBrowsers.SetSelection(1) @@ -269,7 +270,7 @@ class MainFrame(wx.Frame): self.fitMultiSwitch.AddPage() return - self.waitDialog = wx.BusyInfo("Loading previous fits...", parent=self) + self.waitDialog = wx.BusyInfo(_("Loading previous fits..."), parent=self) OpenFitsThread(fits, self.closeWaitDialog) def _getDisplayData(self): @@ -412,7 +413,7 @@ class MainFrame(wx.Frame): # except: # matplotlib_version = None # - # info.Description = wordwrap(gui.aboutData.description + "\n\nDevelopers:\n\t" + + # info.Description = wordwrap(gui.aboutData.description + _("\n\nDevelopers:\n\t") + # "\n\t".join(gui.aboutData.developers) + # "\n\nAdditional credits:\n\t" + # "\n\t".join(gui.aboutData.credits) + @@ -462,8 +463,8 @@ class MainFrame(wx.Frame): defaultFile = "%s - %s.xml" % (fit.ship.item.name, fit.name) if fit else None with wx.FileDialog( - self, "Save Fitting As...", - wildcard="EVE XML fitting files (*.xml)|*.xml", + self, _("Save Fitting As..."), + wildcard=_("EVE XML fitting files (*.xml)|*.xml"), style=wx.FD_SAVE, defaultFile=defaultFile ) as dlg: @@ -640,15 +641,15 @@ class MainFrame(wx.Frame): if not fit.ignoreRestrictions: with wx.MessageDialog( - self, "Are you sure you wish to ignore fitting restrictions for the " - "current fit? This could lead to wildly inaccurate results and possible errors.", - "Confirm", wx.YES_NO | wx.ICON_QUESTION + self, _("Are you sure you wish to ignore fitting restrictions for the " + "current fit? This could lead to wildly inaccurate results and possible errors."), + _("Confirm"), wx.YES_NO | wx.ICON_QUESTION ) as dlg: result = dlg.ShowModal() == wx.ID_YES else: with wx.MessageDialog( - self, "Re-enabling fitting restrictions for this fit will also remove any illegal items " - "from the fit. Do you want to continue?", "Confirm", wx.YES_NO | wx.ICON_QUESTION + self, _("Re-enabling fitting restrictions for this fit will also remove any illegal items " + "from the fit. Do you want to continue?"), _("Confirm"), wx.YES_NO | wx.ICON_QUESTION ) as dlg: result = dlg.ShowModal() == wx.ID_YES if result: @@ -666,7 +667,7 @@ class MainFrame(wx.Frame): menu = self.GetMenuBar() sEsi = Esi.getInstance() - menu.SetLabel(menu.ssoLoginId, "Manage Characters") + menu.SetLabel(menu.ssoLoginId, _("Manage Characters")) enable = len(sEsi.getSsoCharacters()) == 0 menu.Enable(menu.eveFittingsId, not enable) menu.Enable(menu.exportToEveId, not enable) @@ -683,7 +684,7 @@ class MainFrame(wx.Frame): wx.PostEvent(self, GE.FitChanged(fitIDs=changedFitIDs)) menu = self.GetMenuBar() menu.SetLabel(menu.toggleOverridesId, - "&Turn Overrides Off" if ModifiedAttributeDict.overrides_enabled else "&Turn Overrides On") + _("&Turn Overrides Off") if ModifiedAttributeDict.overrides_enabled else _("&Turn Overrides On")) def saveChar(self, event): sChr = Character.getInstance() @@ -716,7 +717,7 @@ class MainFrame(wx.Frame): fitItems = {i for i in Fit.fitItemIter(fit, forceFitImplants=True) if i is not fit.ship.item} self.disablerAll = wx.WindowDisabler() - self.waitDialog = wx.BusyInfo("Please Wait...", parent=self) + self.waitDialog = wx.BusyInfo(_("Please Wait..."), parent=self) Price.getInstance().findCheaperReplacements(fitItems, updateFitCb, fetchTimeout=10) def AdditionsTabSelect(self, event): @@ -800,10 +801,12 @@ class MainFrame(wx.Frame): sCharacter = Character.getInstance() with wx.FileDialog( self, - "Export Skills Needed As...", - wildcard=("EVEMon skills training file (*.emp)|*.emp|" - "EVEMon skills training XML file (*.xml)|*.xml|" - "Text skills training file (*.txt)|*.txt"), + _("Export Skills Needed As..."), + wildcard=("|".join([ + _("EVEMon skills training file") + " (*.emp)|*.emp", + _("EVEMon skills training XML file") +" (*.xml)|*.xml", + _("Text skills training file") + " (*.txt)|*.txt" + ])), style=wx.FD_SAVE | wx.FD_OVERWRITE_PROMPT, ) as dlg: if dlg.ShowModal() == wx.ID_OK: @@ -820,22 +823,24 @@ class MainFrame(wx.Frame): if '.' not in os.path.basename(filePath): filePath += ".{0}".format(saveFmt) - self.waitDialog = wx.BusyInfo("Exporting skills needed...", parent=self) + self.waitDialog = wx.BusyInfo(_("Exporting skills needed..."), parent=self) sCharacter.backupSkills(filePath, saveFmt, self.getActiveFit(), self.closeWaitDialog) def fileImportDialog(self, event): """Handles importing single/multiple EVE XML / EFT cfg fit files""" with wx.FileDialog( self, - "Open One Or More Fitting Files", - wildcard=("EVE XML fitting files (*.xml)|*.xml|" - "EFT text fitting files (*.cfg)|*.cfg|" - "All Files (*)|*"), + _("Open One Or More Fitting Files"), + wildcard=("|".join([ + _("EVE XML fitting files") + " (*.xml)|*.xml", + _("EFT text fitting files") + " (*.cfg)|*.cfg", + _("All Files") + "|*" + ])), style=wx.FD_OPEN | wx.FD_FILE_MUST_EXIST | wx.FD_MULTIPLE ) as dlg: if dlg.ShowModal() == wx.ID_OK: self.progressDialog = wx.ProgressDialog( - "Importing fits", + _("Importing fits"), " " * 100, # set some arbitrary spacing to create width in window parent=self, style=wx.PD_CAN_ABORT | wx.PD_SMOOTH | wx.PD_ELAPSED_TIME | wx.PD_APP_MODAL @@ -849,8 +854,8 @@ class MainFrame(wx.Frame): with wx.FileDialog( self, - "Save Backup As...", - wildcard="EVE XML fitting file (*.xml)|*.xml", + _("Save Backup As..."), + wildcard=_("EVE XML fitting file")+" (*.xml)|*.xml", style=wx.FD_SAVE | wx.FD_OVERWRITE_PROMPT, defaultFile=defaultFile, ) as dlg: @@ -863,8 +868,8 @@ class MainFrame(wx.Frame): max_ = sFit.countAllFits() self.progressDialog = wx.ProgressDialog( - "Backup fits", - "Backing up %d fits to: %s" % (max_, filePath), + _("Backup fits"), + _("Backing up {} fits to: {}").format(max_, filePath), maximum=max_, parent=self, style=wx.PD_CAN_ABORT | wx.PD_SMOOTH | wx.PD_ELAPSED_TIME | wx.PD_APP_MODAL @@ -883,16 +888,19 @@ class MainFrame(wx.Frame): if not os.path.isdir(os.path.dirname(path)): with wx.MessageDialog( self, - "Invalid Path\n\nThe following path is invalid or does not exist: \n%s\n\nPlease verify path location pyfa's preferences." % path, - "Error", + _("Invalid Path") + "\n\n" + + _("The following path is invalid or does not exist:") + + f"\n{path}\n\n" + + _("Please verify path location pyfa's preferences."), + _("Error"), wx.OK | wx.ICON_ERROR ) as dlg: if dlg.ShowModal() == wx.ID_OK: return self.progressDialog = wx.ProgressDialog( - "Backup fits", - "Generating HTML file at: %s" % path, + _("Backup fits"), + _("Generating HTML file at: {}").format(path), maximum=max_, parent=self, style=wx.PD_APP_MODAL | wx.PD_ELAPSED_TIME) @@ -934,10 +942,12 @@ class MainFrame(wx.Frame): _message = None if action & IPortUser.ID_ERROR: self.closeProgressDialog() - _message = "Import Error" if action & IPortUser.PROCESS_IMPORT else "Export Error" + _message = _("Import Error") if action & IPortUser.PROCESS_IMPORT else _("Export Error") with wx.MessageDialog( self, - "The following error was generated\n\n%s\n\nBe aware that already processed fits were not saved" % data, + _("The following error was generated") + + f"\n\n{data}\n\n" + + _("Be aware that already processed fits were not saved"), _message, wx.OK | wx.ICON_ERROR ) as dlg: dlg.ShowModal() @@ -996,13 +1006,16 @@ class MainFrame(wx.Frame): """ Imports character XML file from EVE API """ with wx.FileDialog( self, - "Open One Or More Character Files", - wildcard="EVE API XML character files (*.xml)|*.xml|All Files (*)|*", + _("Open One Or More Character Files"), + wildcard="|".join([ + _("EVE API XML character files") + " (*.xml)|*.xml", + _("All Files") + "|*" + ]), style=wx.FD_OPEN | wx.FD_FILE_MUST_EXIST | wx.FD_MULTIPLE ) as dlg: if dlg.ShowModal() == wx.ID_OK: self.supress_left_up = True - self.waitDialog = wx.BusyInfo("Importing Character...", parent=self) + self.waitDialog = wx.BusyInfo(_("Importing Character..."), parent=self) sCharacter = Character.getInstance() sCharacter.importCharacter(dlg.GetPaths(), self.importCharacterCallback) diff --git a/pyfa.py b/pyfa.py index fbee4220b..101c1d6e1 100755 --- a/pyfa.py +++ b/pyfa.py @@ -74,6 +74,8 @@ parser.add_option("-s", "--savepath", action="store", dest="savepath", help="Set parser.add_option("-l", "--logginglevel", action="store", dest="logginglevel", help="Set desired logging level [Critical|Error|Warning|Info|Debug]", default="Error") parser.add_option("-p", "--profile", action="store", dest="profile_path", help="Set location to save profileing.", default=None) +parser.add_option("-i", "--language", action="store", dest="language", help="Set the language for pyfa", default="en_US") + (options, args) = parser.parse_args() @@ -105,6 +107,7 @@ if __name__ == "__main__": config.loggingLevel = config.LOGLEVEL_MAP.get(options.logginglevel.lower(), config.LOGLEVEL_MAP['error']) config.defPaths(options.savepath) config.defLogging() + config.language = options.language with config.logging_setup.threadbound(): @@ -133,13 +136,14 @@ if __name__ == "__main__": os.mkdir(config.savePath) eos.db.saveddata_meta.create_all() + from gui.app import PyfaApp from gui.mainFrame import MainFrame # set title if it wasn't supplied by argument if options.title is None: options.title = "pyfa %s - Python Fitting Assistant" % (config.getVersion()) - pyfa = wx.App(False) + pyfa = PyfaApp(False) mf = MainFrame(options.title) ErrorHandler.SetParent(mf)