i18n with gettext

This commit is contained in:
2022-02-02 19:35:57 +01:00
parent 939c86dbe2
commit 9c28a41904
21 changed files with 686 additions and 437 deletions

View File

@@ -8,24 +8,24 @@ from PySide6.QtWidgets import *
import constants import constants
from label import Label from label import Label
from vbox import VBox from vbox import VBox
from raven.i18n import _
class AboutDialog(QDialog): class AboutDialog(QDialog):
"""Dialog for showing info about RavenLog""" """Dialog for showing info about RavenLog"""
def __init__(self, parent=None): def __init__(self, parent=None):
super(AboutDialog, self).__init__(parent) super(AboutDialog, self).__init__(parent)
self.setWindowTitle(self.tr("About RavenLog")) self.setWindowTitle(_("About RavenLog"))
self.setModal(True) self.setModal(True)
self.layout = QVBoxLayout(self) self.layout = QVBoxLayout(self)
heading_app_name = QLabel(self.tr("RavenLog")) heading_app_name = QLabel(_("RavenLog"))
heading_app_name.setAlignment(Qt.AlignmentFlag.AlignLeft) heading_app_name.setAlignment(Qt.AlignmentFlag.AlignLeft)
heading_app_name.setFont(QFont("default", 25)) heading_app_name.setFont(QFont("default", 25))
heading_app_name.setTextInteractionFlags(Qt.TextInteractionFlag.TextSelectableByMouse) heading_app_name.setTextInteractionFlags(Qt.TextInteractionFlag.TextSelectableByMouse)
version = QLabel(self.tr("Version: {0}".format(self._version()))) version = QLabel(_("Version: {0}".format(self._version())))
version.setAlignment(Qt.AlignmentFlag.AlignLeft) version.setAlignment(Qt.AlignmentFlag.AlignLeft)
app_icon = QLabel() app_icon = QLabel()
@@ -40,8 +40,8 @@ class AboutDialog(QDialog):
self.layout.addWidget(heading) self.layout.addWidget(heading)
tabs = QTabWidget() tabs = QTabWidget()
tabs.addTab(self._about(), self.tr("About")) tabs.addTab(self._about(), _("About"))
tabs.addTab(self._license(), self.tr("License")) tabs.addTab(self._license(), _("License"))
self.layout.addWidget(tabs) self.layout.addWidget(tabs)
@@ -53,7 +53,7 @@ class AboutDialog(QDialog):
def _about(self) -> QWidget: def _about(self) -> QWidget:
result = QWidget() result = QWidget()
result.layout = QVBoxLayout(result) result.layout = QVBoxLayout(result)
label = Label(self.tr(textwrap.dedent(""" label = Label(_(textwrap.dedent("""
Log file viewer<br> Log file viewer<br>
(c) 2022 Open Text Corporation<br> (c) 2022 Open Text Corporation<br>
<a href="https://www.opentext.com/">License: LGPL v3</a>"""))) <a href="https://www.opentext.com/">License: LGPL v3</a>""")))
@@ -68,7 +68,7 @@ class AboutDialog(QDialog):
<li>urllib3 (MIT) - <a href="https://urllib3.readthedocs.io/en/stable/">https://urllib3.readthedocs.io/en/stable/</a></li> <li>urllib3 (MIT) - <a href="https://urllib3.readthedocs.io/en/stable/">https://urllib3.readthedocs.io/en/stable/</a></li>
<li>watchdog 2.16 (Apache 2.0) - <a href="https://github.com/gorakhargosh/watchdog">https://github.com/gorakhargosh/watchdog</a></li> <li>watchdog 2.16 (Apache 2.0) - <a href="https://github.com/gorakhargosh/watchdog">https://github.com/gorakhargosh/watchdog</a></li>
</ul>""".format(pyside=PySide6.__version__, qt=PySide6.QtCore.__version__) </ul>""".format(pyside=PySide6.__version__, qt=PySide6.QtCore.__version__)
label = self.tr(textwrap.dedent(dependencies)) label = _(textwrap.dedent(dependencies))
result = QWidget() result = QWidget()
result.layout = QVBoxLayout(result) result.layout = QVBoxLayout(result)

View File

@@ -25,7 +25,7 @@ from ravenui import RavenUI
from settings import Settings from settings import Settings
from watchdog.observers import Observer from watchdog.observers import Observer
from watchdog.events import FileSystemEventHandler from watchdog.events import FileSystemEventHandler
from raven.i18n import _
class FileObserver(FileSystemEventHandler): class FileObserver(FileSystemEventHandler):
@@ -168,24 +168,24 @@ class InnerBigText(QWidget):
def _open_menu(self, position): def _open_menu(self, position):
menu = QMenu(self) menu = QMenu(self)
copy_clipboard = QAction(QIcon.fromTheme("edit-copy"), self.tr("&Copy to Clipboard"), self, copy_clipboard = QAction(QIcon.fromTheme("edit-copy"), _("&Copy to Clipboard"), self,
triggered=self.copy_selection) triggered=self.copy_selection)
copy_clipboard.setShortcut("CTRL+C") copy_clipboard.setShortcut("CTRL+C")
copy_clipboard.setDisabled(not self._has_selection()) copy_clipboard.setDisabled(not self._has_selection())
menu.addAction(copy_clipboard) menu.addAction(copy_clipboard)
copy_to_file = QAction(QIcon.fromTheme("document-save-as"), self.tr("Copy to &File"), self, copy_to_file = QAction(QIcon.fromTheme("document-save-as"), _("Copy to &File"), self,
triggered=self._copy_selection_to_file) triggered=self._copy_selection_to_file)
copy_to_file.setDisabled(not self._has_selection()) copy_to_file.setDisabled(not self._has_selection())
menu.addAction(copy_to_file) menu.addAction(copy_to_file)
select_all = QAction(QIcon.fromTheme("edit-select-all"), self.tr("Select &All"), self, select_all = QAction(QIcon.fromTheme("edit-select-all"), _("Select &All"), self,
triggered=self._select_all) triggered=self._select_all)
select_all.setShortcut("CTRL+A") select_all.setShortcut("CTRL+A")
menu.addAction(select_all) menu.addAction(select_all)
manage_highlighting = QAction( manage_highlighting = QAction(
self.tr("&Highlighter"), _("&Highlighter"),
self, self,
triggered=lambda: HighlightingDialog(self.model.settings).exec()) triggered=lambda: HighlightingDialog(self.model.settings).exec())
manage_highlighting.setShortcut("CTRL+H") manage_highlighting.setShortcut("CTRL+H")
@@ -329,13 +329,13 @@ class InnerBigText(QWidget):
if end - start > (1024 ** 2) * 5: if end - start > (1024 ** 2) * 5:
you_sure = QMessageBox( you_sure = QMessageBox(
QMessageBox.Icon.Warning, QMessageBox.Icon.Warning,
self.tr("data selection"), _("data selection"),
self.tr( _(
"You have selected <b>{0}</b> of data.").format(bytes_human_readable)) "You have selected <b>{0}</b> of data.").format(bytes_human_readable))
you_sure.setStandardButtons(QMessageBox.StandardButton.Cancel) you_sure.setStandardButtons(QMessageBox.StandardButton.Cancel)
you_sure.addButton(QPushButton(self.tr("Copy {0} to Clipboard").format(bytes_human_readable)), you_sure.addButton(QPushButton(_("Copy {0} to Clipboard").format(bytes_human_readable)),
QMessageBox.ButtonRole.AcceptRole) QMessageBox.ButtonRole.AcceptRole)
you_sure.addButton(QPushButton(self.tr("Write to File")), QMessageBox.ActionRole) you_sure.addButton(QPushButton(_("Write to File")), QMessageBox.ActionRole)
you_sure.setDefaultButton(QMessageBox.StandardButton.Cancel) you_sure.setDefaultButton(QMessageBox.StandardButton.Cancel)
result = you_sure.exec() result = you_sure.exec()
if result == 1: # second custom button has the number 1 if result == 1: # second custom button has the number 1
@@ -355,7 +355,7 @@ class InnerBigText(QWidget):
end = max(self.selection_highlight.start_byte, self.selection_highlight.end_byte) end = max(self.selection_highlight.start_byte, self.selection_highlight.end_byte)
dialog = QFileDialog(self) dialog = QFileDialog(self)
(selected_file, _filter) = dialog.getSaveFileName( (selected_file, _filter) = dialog.getSaveFileName(
caption=self.tr("Save File"), caption=_("Save File"),
dir=os.path.dirname(self.model.get_file()) dir=os.path.dirname(self.model.get_file())
) )
if selected_file: if selected_file:

View File

@@ -2,7 +2,7 @@ import re
from PySide6.QtGui import QColor, QPixmap, QIcon from PySide6.QtGui import QColor, QPixmap, QIcon
from PySide6.QtWidgets import QWidget, QHBoxLayout, QPushButton, QColorDialog, QSizePolicy, QComboBox from PySide6.QtWidgets import QWidget, QHBoxLayout, QPushButton, QColorDialog, QSizePolicy, QComboBox
from raven.i18n import _
class ColorButton(QWidget): class ColorButton(QWidget):
def __init__(self, color: str, parent=None): def __init__(self, color: str, parent=None):
@@ -15,40 +15,40 @@ class ColorButton(QWidget):
colors = { colors = {
# red # red
self.tr('Strawberry Cream'): 'ff8080', _('Strawberry Cream'): 'ff8080',
self.tr('Pale Crimson'): 'e61919', _('Pale Crimson'): 'e61919',
# orange # orange
self.tr('Broken Buttercup'): 'ffd080', _('Broken Buttercup'): 'ffd080',
self.tr('Passion Fruit Sugar'): 'ffa200', _('Passion Fruit Sugar'): 'ffa200',
# yellow # yellow
self.tr('Sunrise Yellow'): 'fff080', _('Sunrise Yellow'): 'fff080',
self.tr('Magical Mustard'): 'ccb400', _('Magical Mustard'): 'ccb400',
# green # green
self.tr('Trendy Green'): 'aaff80', _('Trendy Green'): 'aaff80',
self.tr('Garden Of Sweden'): '44cc00', _('Garden Of Sweden'): '44cc00',
# blue # blue
self.tr('Light Sky Blue'): '80c6ff', _('Light Sky Blue'): '80c6ff',
self.tr('True Blue'): '0073d1', _('True Blue'): '0073d1',
# purple # purple
self.tr('Fairy Topia'): 'ff80f4', _('Fairy Topia'): 'ff80f4',
self.tr('Magenta Bachiego'): 'cc00bb', _('Magenta Bachiego'): 'cc00bb',
# grey # grey
self.tr('Breeze of Mist'): 'eaeaea', _('Breeze of Mist'): 'eaeaea',
self.tr('Light Grey'): 'cccccc', _('Light Grey'): 'cccccc',
self.tr('Grey'): '999999', _('Grey'): '999999',
} }
self.color_drop_down = QComboBox() self.color_drop_down = QComboBox()
self.layout.addWidget(self.color_drop_down) self.layout.addWidget(self.color_drop_down)
self.color_drop_down.currentIndexChanged.connect(self._color_selected) self.color_drop_down.currentIndexChanged.connect(self._color_selected)
self.color_drop_down.addItem(QIcon(self._color_pixmap("ffffffff")), self.tr("transparent"), "None") self.color_drop_down.addItem(QIcon(self._color_pixmap("ffffffff")), _("transparent"), "None")
for color_name in colors.keys(): for color_name in colors.keys():
color_value = colors[color_name] color_value = colors[color_name]
self.color_drop_down.addItem(QIcon(self._color_pixmap(color_value)), color_name, color_value) self.color_drop_down.addItem(QIcon(self._color_pixmap(color_value)), color_name, color_value)
if color == color_name or color == color_value: if color == color_name or color == color_value:
self.color_drop_down.setCurrentIndex(self.color_drop_down.count() - 1) self.color_drop_down.setCurrentIndex(self.color_drop_down.count() - 1)
self.btn_color_picker = QPushButton(QIcon.fromTheme("color-picker"), self.tr("custom")) self.btn_color_picker = QPushButton(QIcon.fromTheme("color-picker"), _("custom"))
self.layout.addWidget(self.btn_color_picker) self.layout.addWidget(self.btn_color_picker)
self.btn_color_picker.pressed.connect(self._update_color) self.btn_color_picker.pressed.connect(self._update_color)
self.btn_color_picker.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed)) self.btn_color_picker.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed))

View File

@@ -1,6 +1,5 @@
import unittest import unittest
def humanbytes(bytes: int) -> str: def humanbytes(bytes: int) -> str:
"""non-localized conversion of bytes to human readable strings""" """non-localized conversion of bytes to human readable strings"""
powers = {0: 'bytes', 1: 'KB', 2: 'MB', 3: 'GB', 4: 'TB', 5: 'PB', 6: 'EB'} powers = {0: 'bytes', 1: 'KB', 2: 'MB', 3: 'GB', 4: 'TB', 5: 'PB', 6: 'EB'}

View File

@@ -11,6 +11,7 @@ from bigtext import BigText
from logFileModel import LogFileModel from logFileModel import LogFileModel
from ravenui import RavenUI from ravenui import RavenUI
from raven.i18n import _
class FilterTask(QRunnable): class FilterTask(QRunnable):
aborted = False aborted = False
@@ -96,15 +97,15 @@ class FilterWidget(QWidget):
self.query_field = QLineEdit() self.query_field = QLineEdit()
self.query_field.textChanged.connect(self.filter_changed) self.query_field.textChanged.connect(self.filter_changed)
self.btn_cancel_search = QPushButton(self.tr("Cancel")) self.btn_cancel_search = QPushButton(_("Cancel"))
self.btn_cancel_search.setVisible(False) self.btn_cancel_search.setVisible(False)
self.btn_cancel_search.pressed.connect(self._cancel_search) self.btn_cancel_search.pressed.connect(self._cancel_search)
self.ignore_case = QCheckBox(self.tr("ignore case")) self.ignore_case = QCheckBox(_("ignore case"))
self.ignore_case.setChecked(True) self.ignore_case.setChecked(True)
self.ignore_case.stateChanged.connect(self.filter_changed) self.ignore_case.stateChanged.connect(self.filter_changed)
self.is_regex = QCheckBox(self.tr("regex")) self.is_regex = QCheckBox(_("regex"))
self.is_regex.setChecked(True) self.is_regex.setChecked(True)
self.is_regex.stateChanged.connect(self.filter_changed) self.is_regex.stateChanged.connect(self.filter_changed)

View File

@@ -8,6 +8,7 @@ from highlight_regex import HighlightRegex
from highlighting import Highlighting from highlighting import Highlighting
from settings import Settings from settings import Settings
from raven.i18n import _
class PayloadItem(QListWidgetItem): class PayloadItem(QListWidgetItem):
def __init__(self, text: str, payload=None): def __init__(self, text: str, payload=None):
@@ -18,7 +19,7 @@ class PayloadItem(QListWidgetItem):
class HighlightingDialog(QDialog): class HighlightingDialog(QDialog):
def __init__(self, settings: Settings): def __init__(self, settings: Settings):
super(HighlightingDialog, self).__init__() super(HighlightingDialog, self).__init__()
self.setWindowTitle(self.tr("Manage Highlighting")) self.setWindowTitle(_("Manage Highlighting"))
self.setModal(True) self.setModal(True)
self._settings = settings self._settings = settings
@@ -30,23 +31,23 @@ class HighlightingDialog(QDialog):
form_grid.addWidget(self.list, row, 0, 1, 2) form_grid.addWidget(self.list, row, 0, 1, 2)
row = row + 1 row = row + 1
self.btn_add = QPushButton(QIcon.fromTheme("list-add"), self.tr("Add")) self.btn_add = QPushButton(QIcon.fromTheme("list-add"), _("Add"))
self.btn_add.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed)) self.btn_add.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed))
self.btn_add.pressed.connect(self._add) self.btn_add.pressed.connect(self._add)
self.btn_update = QPushButton(QIcon.fromTheme("stock_edit"), self.tr("Update")) self.btn_update = QPushButton(QIcon.fromTheme("stock_edit"), _("Update"))
self.btn_update.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed)) self.btn_update.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed))
self.btn_update.pressed.connect(self._update) self.btn_update.pressed.connect(self._update)
self.btn_delete = QPushButton(QIcon.fromTheme("list-remove"), self.tr("Remove")) self.btn_delete = QPushButton(QIcon.fromTheme("list-remove"), _("Remove"))
self.btn_delete.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed)) self.btn_delete.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed))
self.btn_delete.pressed.connect(self._delete) self.btn_delete.pressed.connect(self._delete)
self.btn_move_up = QPushButton(QIcon.fromTheme("go-up"), self.tr("Up")) self.btn_move_up = QPushButton(QIcon.fromTheme("go-up"), _("Up"))
self.btn_move_up.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed)) self.btn_move_up.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed))
self.btn_move_up.pressed.connect(self._move_up) self.btn_move_up.pressed.connect(self._move_up)
self.btn_move_down = QPushButton(QIcon.fromTheme("go-down"), self.tr("Down")) self.btn_move_down = QPushButton(QIcon.fromTheme("go-down"), _("Down"))
self.btn_move_down.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed)) self.btn_move_down.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Fixed, QSizePolicy.Policy.Fixed))
self.btn_move_down.pressed.connect(self._move_down) self.btn_move_down.pressed.connect(self._move_down)
button_box = HBox(self.btn_update, self.btn_add, self.btn_delete, self.btn_move_up, self.btn_move_down) button_box = HBox(self.btn_update, self.btn_add, self.btn_delete, self.btn_move_up, self.btn_move_down)
@@ -54,26 +55,26 @@ class HighlightingDialog(QDialog):
row = row + 1 row = row + 1
self.query = QLineEdit(self) self.query = QLineEdit(self)
form_grid.addWidget(QLabel(self.tr("Query:")), row, 0) form_grid.addWidget(QLabel(_("Query:")), row, 0)
form_grid.addWidget(self.query, row, 1) form_grid.addWidget(self.query, row, 1)
row = row + 1 row = row + 1
self.ignore_case = QCheckBox(self.tr("Ignore Case")) self.ignore_case = QCheckBox(_("Ignore Case"))
self.ignore_case.setChecked(True) self.ignore_case.setChecked(True)
form_grid.addWidget(self.ignore_case, row, 0, 1, 2) form_grid.addWidget(self.ignore_case, row, 0, 1, 2)
row = row + 1 row = row + 1
self.is_regex = QCheckBox(self.tr("Regular Expression")) self.is_regex = QCheckBox(_("Regular Expression"))
self.is_regex.setChecked(True) self.is_regex.setChecked(True)
form_grid.addWidget(self.is_regex, row, 0, 1, 2) form_grid.addWidget(self.is_regex, row, 0, 1, 2)
row = row + 1 row = row + 1
form_grid.addWidget(QLabel(self.tr("Hit Background:")), row, 0) form_grid.addWidget(QLabel(_("Hit Background:")), row, 0)
self.hit_background_color = ColorButton("ccb400") self.hit_background_color = ColorButton("ccb400")
form_grid.addWidget(self.hit_background_color, row, 1) form_grid.addWidget(self.hit_background_color, row, 1)
row = row + 1 row = row + 1
form_grid.addWidget(QLabel(self.tr("Line Background:")), row, 0) form_grid.addWidget(QLabel(_("Line Background:")), row, 0)
self.line_background_color = ColorButton("fff080") self.line_background_color = ColorButton("fff080")
form_grid.addWidget(self.line_background_color, row, 1) form_grid.addWidget(self.line_background_color, row, 1)
@@ -137,10 +138,10 @@ class HighlightingDialog(QDialog):
def _save(self): def _save(self):
if self._is_dirty(): if self._is_dirty():
unsaved = QMessageBox(QMessageBox.Icon.Question, self.tr("unsaved changes"), unsaved = QMessageBox(QMessageBox.Icon.Question, _("unsaved changes"),
self.tr("You have unsaved changes. Continue?")) _("You have unsaved changes. Continue?"))
unsaved.setStandardButtons(QMessageBox.StandardButton.Cancel) unsaved.setStandardButtons(QMessageBox.StandardButton.Cancel)
unsaved.addButton(QPushButton(self.tr("Continue")), QMessageBox.ButtonRole.AcceptRole) unsaved.addButton(QPushButton(_("Continue")), QMessageBox.ButtonRole.AcceptRole)
result = unsaved.exec() result = unsaved.exec()
if result == QMessageBox.StandardButton.Cancel: if result == QMessageBox.StandardButton.Cancel:
return return

Binary file not shown.

View File

@@ -0,0 +1,279 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR ORGANIZATION
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
msgid ""
msgstr ""
"Project-Id-Version: RavenLog\n"
"POT-Creation-Date: 2022-02-01 20:07+0100\n"
"PO-Revision-Date: 2022-02-01 20:17+0100\n"
"Last-Translator: \n"
"Language-Team: \n"
"Language: de\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Generated-By: pygettext.py 1.5\n"
"X-Generator: Poedit 2.3\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
#: aboutdialog.py:19
msgid "About RavenLog"
msgstr "Über RavenLog"
#: aboutdialog.py:24 raven/mainwindow.py:44 ravenui.py:20
msgid "RavenLog"
msgstr "RavenLog"
#: aboutdialog.py:44
msgid "About"
msgstr "Über RavenLog"
#: aboutdialog.py:45
msgid "License"
msgstr "Lizenz"
#: bigtext.py:172
msgid "&Copy to Clipboard"
msgstr "In Zwischenablage &Kopieren"
#: bigtext.py:178
msgid "Copy to &File"
msgstr "In &Datei Kopieren"
#: bigtext.py:183
msgid "Select &All"
msgstr "&Alles Selektieren"
#: bigtext.py:189 raven/mainwindow.py:121
msgid "&Highlighter"
msgstr "&Hervorhebungen"
#: bigtext.py:333
msgid "data selection"
msgstr "selektion"
#: bigtext.py:334
msgid "You have selected <b>{0}</b> of data."
msgstr "Du hast <b>{0}</b> selektiert."
#: bigtext.py:337
msgid "Copy {0} to Clipboard"
msgstr "Kopiere {0} in die Zwischenablage"
#: bigtext.py:339
msgid "Write to File"
msgstr "Schreibe in Datei"
#: bigtext.py:359
msgid "Save File"
msgstr "Speichere Datei"
#: colorbutton.py:19
msgid "Strawberry Cream"
msgstr "Strawberry Cream"
#: colorbutton.py:20
msgid "Pale Crimson"
msgstr "Pale Crimson"
#: colorbutton.py:22
msgid "Broken Buttercup"
msgstr "Pale Crimson"
#: colorbutton.py:23
msgid "Passion Fruit Sugar"
msgstr "Passion Fruit Sugar"
#: colorbutton.py:25
msgid "Sunrise Yellow"
msgstr ""
#: colorbutton.py:26
msgid "Magical Mustard"
msgstr ""
#: colorbutton.py:28
msgid "Trendy Green"
msgstr ""
#: colorbutton.py:29
msgid "Garden Of Sweden"
msgstr ""
#: colorbutton.py:31
msgid "Light Sky Blue"
msgstr ""
#: colorbutton.py:32
msgid "True Blue"
msgstr ""
#: colorbutton.py:34
msgid "Fairy Topia"
msgstr ""
#: colorbutton.py:35
msgid "Magenta Bachiego"
msgstr ""
#: colorbutton.py:37
msgid "Breeze of Mist"
msgstr ""
#: colorbutton.py:38
msgid "Light Grey"
msgstr "Helles Grau"
#: colorbutton.py:39
msgid "Grey"
msgstr "Grau"
#: colorbutton.py:45
msgid "transparent"
msgstr "Transparent"
#: colorbutton.py:52
msgid "custom"
msgstr "individuell"
#: filterwidget.py:101
msgid "Cancel"
msgstr "Abbrechen"
#: filterwidget.py:105
msgid "ignore case"
msgstr "Groß-/Kleinschreibung ignorieren"
#: filterwidget.py:109
msgid "regex"
msgstr "RegExp"
#: highlightingdialog.py:23
msgid "Manage Highlighting"
msgstr "Hervorhebungen Verwalten"
#: highlightingdialog.py:35
msgid "Add"
msgstr "Hinzufügen"
#: highlightingdialog.py:39
msgid "Update"
msgstr "Aktualisieren"
#: highlightingdialog.py:43
msgid "Remove"
msgstr "Entfernen"
#: highlightingdialog.py:47
msgid "Up"
msgstr "Hoch"
#: highlightingdialog.py:51
msgid "Down"
msgstr "Runter"
#: highlightingdialog.py:59
msgid "Query:"
msgstr "Suche:"
#: highlightingdialog.py:63
msgid "Ignore Case"
msgstr "Groß-/Kleinschreibung ignorieren"
#: highlightingdialog.py:68
msgid "Regular Expression"
msgstr "Regulärer Ausdruck"
#: highlightingdialog.py:73
msgid "Hit Background:"
msgstr "Trefferhintergrund:"
#: highlightingdialog.py:78
msgid "Line Background:"
msgstr "Zeilenhintergrund:"
#: highlightingdialog.py:142
msgid "unsaved changes"
msgstr "nicht gespeicherte Änderungen"
#: highlightingdialog.py:143
msgid "You have unsaved changes. Continue?"
msgstr "Du hast nicht gespeicherte Änderungen. Weiter?"
#: highlightingdialog.py:145
msgid "Continue"
msgstr "Weiter"
#: raven/mainwindow.py:52 raven/plugins/openfileplugin.py:31
msgid "Open &Recent"
msgstr "Zu&letzt geöffnete Dateien"
#: raven/mainwindow.py:71
#: venv310/lib/python3.10/site-packages/PySide6/examples/widgets/gettext/main.py:57
msgid "&File"
msgstr "&Datei"
#: raven/mainwindow.py:72
msgid "&Settings"
msgstr "&Einstellungen"
#: raven/mainwindow.py:73
msgid "&Window"
msgstr "&Fenster"
#: raven/mainwindow.py:74
msgid "&Help"
msgstr "&Hilfe"
#: raven/mainwindow.py:129
msgid "Highlight &Searches"
msgstr "&Suchtreffer Hervorheben"
#: raven/mainwindow.py:138
msgid "Open Tab on Save As File"
msgstr "Öffne neues Tab wenn Selektion als neue Datei gespeichert wird"
#: raven/plugins/logfileplugin.py:26
msgid "File not found"
msgstr "Datei nicht gefunden"
#: raven/plugins/logfileplugin.py:27
msgid "'{0}' is not a file or cannot be opened"
msgstr "'{0}' ist keine Datei oder kann nicht geöffnet werden"
#: raven/plugins/notesplugin.py:26
msgid "Add &Notes"
msgstr "&Notizen Hinzufügen"
#: raven/plugins/notesplugin.py:34
msgid "Notes {0}"
msgstr "Notizen {0}"
#: raven/plugins/openfileplugin.py:26
msgid "&Open..."
msgstr "&Öffnen..."
#: raven/plugins/openfileplugin.py:47
msgid "Open File"
msgstr "Öffne Datei"
#: raven/plugins/ravenlogplugin.py:46
msgid "&About"
msgstr "&Über RavenLog"
#: raven/plugins/ravenlogplugin.py:54
msgid "E&xit"
msgstr "&Beenden"
#: ravenui.py:18
msgid "{0} - RavenLog"
msgstr "{0} - RavenLog"
#: venv310/lib/python3.10/site-packages/PySide6/examples/widgets/gettext/main.py:58
msgid "Quit"
msgstr "Beenden"
#: venv310/lib/python3.10/site-packages/PySide6/examples/widgets/gettext/main.py:59
msgid "CTRL+Q"
msgstr "STRG+Q"

280
locales/messages.pot Normal file
View File

@@ -0,0 +1,280 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR ORGANIZATION
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"POT-Creation-Date: 2022-02-01 20:07+0100\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Generated-By: pygettext.py 1.5\n"
#: ./aboutdialog.py:19
msgid "About RavenLog"
msgstr ""
#: ./aboutdialog.py:24 ./raven/mainwindow.py:44 ./ravenui.py:20
msgid "RavenLog"
msgstr ""
#: ./aboutdialog.py:44
msgid "About"
msgstr ""
#: ./aboutdialog.py:45
msgid "License"
msgstr ""
#: ./bigtext.py:172
msgid "&Copy to Clipboard"
msgstr ""
#: ./bigtext.py:178
msgid "Copy to &File"
msgstr ""
#: ./bigtext.py:183
msgid "Select &All"
msgstr ""
#: ./bigtext.py:189 ./raven/mainwindow.py:121
msgid "&Highlighter"
msgstr ""
#: ./bigtext.py:333
msgid "data selection"
msgstr ""
#: ./bigtext.py:334
msgid "You have selected <b>{0}</b> of data."
msgstr ""
#: ./bigtext.py:337
msgid "Copy {0} to Clipboard"
msgstr ""
#: ./bigtext.py:339
msgid "Write to File"
msgstr ""
#: ./bigtext.py:359
msgid "Save File"
msgstr ""
#: ./colorbutton.py:19
msgid "Strawberry Cream"
msgstr ""
#: ./colorbutton.py:20
msgid "Pale Crimson"
msgstr ""
#: ./colorbutton.py:22
msgid "Broken Buttercup"
msgstr ""
#: ./colorbutton.py:23
msgid "Passion Fruit Sugar"
msgstr ""
#: ./colorbutton.py:25
msgid "Sunrise Yellow"
msgstr ""
#: ./colorbutton.py:26
msgid "Magical Mustard"
msgstr ""
#: ./colorbutton.py:28
msgid "Trendy Green"
msgstr ""
#: ./colorbutton.py:29
msgid "Garden Of Sweden"
msgstr ""
#: ./colorbutton.py:31
msgid "Light Sky Blue"
msgstr ""
#: ./colorbutton.py:32
msgid "True Blue"
msgstr ""
#: ./colorbutton.py:34
msgid "Fairy Topia"
msgstr ""
#: ./colorbutton.py:35
msgid "Magenta Bachiego"
msgstr ""
#: ./colorbutton.py:37
msgid "Breeze of Mist"
msgstr ""
#: ./colorbutton.py:38
msgid "Light Grey"
msgstr ""
#: ./colorbutton.py:39
msgid "Grey"
msgstr ""
#: ./colorbutton.py:45
msgid "transparent"
msgstr ""
#: ./colorbutton.py:52
msgid "custom"
msgstr ""
#: ./filterwidget.py:101
msgid "Cancel"
msgstr ""
#: ./filterwidget.py:105
msgid "ignore case"
msgstr ""
#: ./filterwidget.py:109
msgid "regex"
msgstr ""
#: ./highlightingdialog.py:23
msgid "Manage Highlighting"
msgstr ""
#: ./highlightingdialog.py:35
msgid "Add"
msgstr ""
#: ./highlightingdialog.py:39
msgid "Update"
msgstr ""
#: ./highlightingdialog.py:43
msgid "Remove"
msgstr ""
#: ./highlightingdialog.py:47
msgid "Up"
msgstr ""
#: ./highlightingdialog.py:51
msgid "Down"
msgstr ""
#: ./highlightingdialog.py:59
msgid "Query:"
msgstr ""
#: ./highlightingdialog.py:63
msgid "Ignore Case"
msgstr ""
#: ./highlightingdialog.py:68
msgid "Regular Expression"
msgstr ""
#: ./highlightingdialog.py:73
msgid "Hit Background:"
msgstr ""
#: ./highlightingdialog.py:78
msgid "Line Background:"
msgstr ""
#: ./highlightingdialog.py:142
msgid "unsaved changes"
msgstr ""
#: ./highlightingdialog.py:143
msgid "You have unsaved changes. Continue?"
msgstr ""
#: ./highlightingdialog.py:145
msgid "Continue"
msgstr ""
#: ./raven/mainwindow.py:52 ./raven/plugins/openfileplugin.py:31
msgid "Open &Recent"
msgstr ""
#: ./raven/mainwindow.py:71
#: ./venv310/lib/python3.10/site-packages/PySide6/examples/widgets/gettext/main.py:57
msgid "&File"
msgstr ""
#: ./raven/mainwindow.py:72
msgid "&Settings"
msgstr ""
#: ./raven/mainwindow.py:73
msgid "&Window"
msgstr ""
#: ./raven/mainwindow.py:74
msgid "&Help"
msgstr ""
#: ./raven/mainwindow.py:129
msgid "Highlight &Searches"
msgstr ""
#: ./raven/mainwindow.py:138
msgid "Open Tab on Save As File"
msgstr ""
#: ./raven/plugins/logfileplugin.py:26
msgid "File not found"
msgstr ""
#: ./raven/plugins/logfileplugin.py:27
msgid "'{0}' is not a file or cannot be opened"
msgstr ""
#: ./raven/plugins/notesplugin.py:26
msgid "Add &Notes"
msgstr ""
#: ./raven/plugins/notesplugin.py:34
msgid "Notes {0}"
msgstr ""
#: ./raven/plugins/openfileplugin.py:26
msgid "&Open..."
msgstr ""
#: ./raven/plugins/openfileplugin.py:47
msgid "Open File"
msgstr ""
#: ./raven/plugins/ravenlogplugin.py:46
msgid "&About"
msgstr ""
#: ./raven/plugins/ravenlogplugin.py:54
msgid "E&xit"
msgstr ""
#: ./ravenui.py:18
msgid "{0} - RavenLog"
msgstr ""
#:
#: ./venv310/lib/python3.10/site-packages/PySide6/examples/widgets/gettext/main.py:58
msgid "Quit"
msgstr ""
#:
#: ./venv310/lib/python3.10/site-packages/PySide6/examples/widgets/gettext/main.py:59
msgid "CTRL+Q"
msgstr ""

31
main.py
View File

@@ -2,6 +2,7 @@ import logging
import os import os
import signal import signal
import ctypes import ctypes
from pathlib import Path
from PySide6 import QtCore from PySide6 import QtCore
from PySide6.QtWidgets import QApplication from PySide6.QtWidgets import QApplication
@@ -13,9 +14,14 @@ import constants
from raven.pluginregistry import PluginRegistry from raven.pluginregistry import PluginRegistry
from ravenui import RavenUI from ravenui import RavenUI
import gettext
gettext.install('ravenlog', 'locale')
logging.basicConfig(level=logging.INFO) logging.basicConfig(level=logging.INFO)
log = logging.getLogger("main") log = logging.getLogger("main")
def stop_signal(signum, _stackframe): def stop_signal(signum, _stackframe):
""" Handle terminate signal """ """ Handle terminate signal """
try: try:
@@ -37,20 +43,21 @@ if __name__ == "__main__":
myappid = 'opentext.ravenlog' # arbitrary string myappid = 'opentext.ravenlog' # arbitrary string
ctypes.windll.shell32.SetCurrentProcessExplicitAppUserModelID(myappid) ctypes.windll.shell32.SetCurrentProcessExplicitAppUserModelID(myappid)
# translator = QTranslator()
# if translator.load(QLocale("de"), "messages_de.ts"):
# app.installTranslator(translator)
locale = os.environ['LANG'] if os.environ['LANG'] else "en" locale = os.environ['LANG'] if os.environ['LANG'] else "en"
path = QLibraryInfo.location(QLibraryInfo.TranslationsPath) src_dir = Path(__file__).resolve().parent
translator = QTranslator(app) try:
if translator.load(QLocale(locale), 'qtbase', '_', path): translation = gettext.translation('messages', localedir=src_dir / 'locales', languages=[locale])
app.installTranslator(translator) if translation:
translator = QTranslator(app) translation.install()
path = './translations' _ = translation.gettext
if translator.load(QLocale(locale), 'messages', '_', path): ngettext = translation.ngettext
app.installTranslator(translator) except FileNotFoundError:
pass
if not _:
_ = gettext.gettext
ngettext = gettext.ngettext
print('No translation found')
# workaround to make signals work in QT apps. # workaround to make signals work in QT apps.
# They do not work out of the box, because the main thread # They do not work out of the box, because the main thread

View File

@@ -1,326 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE TS>
<TS version="2.1" language="de_DE">
<context>
<name>AboutDialog</name>
<message>
<location filename="aboutdialog.py" line="18"/>
<source>About RavenLog</source>
<translation>Über RavenLog</translation>
</message>
<message>
<location filename="aboutdialog.py" line="23"/>
<source>RavenLog</source>
<translation>RavenLog</translation>
</message>
<message>
<location filename="aboutdialog.py" line="28"/>
<source>Version: {0}</source>
<translation>Version: {0}</translation>
</message>
<message>
<location filename="aboutdialog.py" line="43"/>
<source>About</source>
<translation>Über RavenLog</translation>
</message>
<message>
<location filename="aboutdialog.py" line="44"/>
<source>License</source>
<translation>Lizenz</translation>
</message>
</context>
<context>
<name>ColorButton</name>
<message>
<location filename="colorbutton.py" line="18"/>
<source>Strawberry Cream</source>
<translation>Strawberry Cream</translation>
</message>
<message>
<location filename="colorbutton.py" line="19"/>
<source>Pale Crimson</source>
<translation>Pale Crimson</translation>
</message>
<message>
<location filename="colorbutton.py" line="21"/>
<source>Broken Buttercup</source>
<translation>Broken Buttercup</translation>
</message>
<message>
<location filename="colorbutton.py" line="22"/>
<source>Passion Fruit Sugar</source>
<translation>Passion Fruit Sugar</translation>
</message>
<message>
<location filename="colorbutton.py" line="24"/>
<source>Sunrise Yellow</source>
<translation>Sunrise Yellow</translation>
</message>
<message>
<location filename="colorbutton.py" line="25"/>
<source>Magical Mustard</source>
<translation>Magical Mustard</translation>
</message>
<message>
<location filename="colorbutton.py" line="27"/>
<source>Trendy Green</source>
<translation>Trendy Green</translation>
</message>
<message>
<location filename="colorbutton.py" line="28"/>
<source>Garden Of Sweden</source>
<translation>Garden Of Sweden</translation>
</message>
<message>
<location filename="colorbutton.py" line="30"/>
<source>Light Sky Blue</source>
<translation>Light Sky Blue</translation>
</message>
<message>
<location filename="colorbutton.py" line="31"/>
<source>True Blue</source>
<translation>True Blue</translation>
</message>
<message>
<location filename="colorbutton.py" line="33"/>
<source>Fairy Topia</source>
<translation>Fairy Topia</translation>
</message>
<message>
<location filename="colorbutton.py" line="34"/>
<source>Magenta Bachiego</source>
<translation>Magenta Bachiego</translation>
</message>
<message>
<location filename="colorbutton.py" line="36"/>
<source>Breeze of Mist</source>
<translation>Breeze of Mist</translation>
</message>
<message>
<location filename="colorbutton.py" line="37"/>
<source>Light Grey</source>
<translation>Light Grey</translation>
</message>
<message>
<location filename="colorbutton.py" line="38"/>
<source>Grey</source>
<translation>Grey</translation>
</message>
<message>
<location filename="colorbutton.py" line="44"/>
<source>transparent</source>
<translation>Transparent</translation>
</message>
<message>
<location filename="colorbutton.py" line="51"/>
<source>custom</source>
<translation>Individuell</translation>
</message>
</context>
<context>
<name>FilterWidget</name>
<message>
<location filename="filterwidget.py" line="99"/>
<source>Cancel</source>
<translation>Abbrechen</translation>
</message>
<message>
<location filename="filterwidget.py" line="103"/>
<source>ignore case</source>
<translation>Groß-/Kleinschreibung</translation>
</message>
<message>
<location filename="filterwidget.py" line="107"/>
<source>regex</source>
<translation>RegExp</translation>
</message>
</context>
<context>
<name>HighlightingDialog</name>
<message>
<location filename="highlightingdialog.py" line="21"/>
<source>Manage Highlighting</source>
<translation>Hervorhebungen Verwalten</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="33"/>
<source>Add</source>
<translation>Hinzufügen</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="37"/>
<source>Update</source>
<translation>Aktualisieren</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="41"/>
<source>Remove</source>
<translation>Entfernen</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="45"/>
<source>Up</source>
<translation>Hoch</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="49"/>
<source>Down</source>
<translation>Runter</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="57"/>
<source>Query:</source>
<translation>Suche</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="61"/>
<source>Ignore Case</source>
<translation>Groß-/Kleinschreibung</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="66"/>
<source>Regular Expression</source>
<translation>Regulärer Ausdruck</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="71"/>
<source>Hit Background:</source>
<translation>Hintergrund Treffer</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="76"/>
<source>Line Background:</source>
<translation>Hintergrund Zeile</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="140"/>
<source>unsaved changes</source>
<translation>nicht gespeicherte Änderungen</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="141"/>
<source>You have unsaved changes. Continue?</source>
<translation>Du hast Änderungen die noch nicht gespeichert sind. Weiter?</translation>
</message>
<message>
<location filename="highlightingdialog.py" line="143"/>
<source>Continue</source>
<translation>Weiter</translation>
</message>
</context>
<context>
<name>InnerBigText</name>
<message>
<location filename="bigtext.py" line="171"/>
<source>&amp;Copy to Clipboard</source>
<translation>&amp;Kopiere in die Zwischenablage</translation>
</message>
<message>
<location filename="bigtext.py" line="177"/>
<source>Copy to &amp;File</source>
<translation>Speichere als &amp;Datei</translation>
</message>
<message>
<location filename="bigtext.py" line="182"/>
<source>Select &amp;All</source>
<translation>&amp;Alles Selektieren</translation>
</message>
<message>
<location filename="bigtext.py" line="188"/>
<source>&amp;Highlighter</source>
<translation>&amp;Hervorhebungen</translation>
</message>
<message>
<location filename="bigtext.py" line="332"/>
<source>data selection</source>
<translation>Selektion</translation>
</message>
<message>
<location filename="bigtext.py" line="334"/>
<source>You have selected &lt;b&gt;{0}&lt;/b&gt; of data.</source>
<translation>Du hast &lt;b&gt;{0}&lt;/b&gt; selektiert.</translation>
</message>
<message>
<location filename="bigtext.py" line="336"/>
<source>Copy {0} to Clipboard</source>
<translation>{0} in Zwischenablage kopieren</translation>
</message>
<message>
<location filename="bigtext.py" line="337"/>
<source>Write to File</source>
<translation>In Datei speichern</translation>
</message>
<message>
<location filename="bigtext.py" line="357"/>
<source>Save File</source>
<translation>Datei Speichern</translation>
</message>
</context>
<context>
<name>MainWindow</name>
<message>
<location filename="raven/mainwindow.py" line="40"/>
<source>RavenLog</source>
<translation>RavenLog</translation>
</message>
<message>
<location filename="raven/mainwindow.py" line="48"/>
<source>Open &amp;Recent</source>
<translation>Zu&amp;letzt geöffnete Dateien</translation>
</message>
<message>
<location filename="raven/mainwindow.py" line="67"/>
<source>&amp;File</source>
<translation>&amp;Datei</translation>
</message>
<message>
<location filename="raven/mainwindow.py" line="68"/>
<source>&amp;Settings</source>
<translation>&amp;Einstellungen</translation>
</message>
<message>
<location filename="raven/mainwindow.py" line="69"/>
<source>&amp;Window</source>
<translation>&amp;Fenster</translation>
</message>
<message>
<location filename="raven/mainwindow.py" line="70"/>
<source>&amp;Help</source>
<translation>&amp;Hilfe</translation>
</message>
</context>
<context>
<name>NotesPlugin</name>
<message>
<location filename="raven/plugins/notesplugin.py" line="29"/>
<source>Add &amp;Notes</source>
<translation>Notizen Hinzufügen</translation>
</message>
<message>
<location filename="raven/plugins/notesplugin.py" line="37"/>
<source>Notes %d</source>
<translation>Notizen %d</translation>
</message>
</context>
<context>
<name>OpenFilePlugin</name>
<message>
<location filename="raven/plugins/openfileplugin.py" line="48"/>
<source>Open File</source>
<translation>Datei öffnen</translation>
</message>
</context>
<context>
<name>RavenLogPlugin</name>
<message>
<location filename="raven/plugins/ravenlogplugin.py" line="45"/>
<source>&amp;About</source>
<translation>&amp;Über RavenLog</translation>
</message>
<message>
<location filename="raven/plugins/ravenlogplugin.py" line="53"/>
<source>E&amp;xit</source>
<translation>Be&amp;enden</translation>
</message>
</context>
</TS>

20
raven/i18n.py Normal file
View File

@@ -0,0 +1,20 @@
import gettext
import os
from pathlib import Path
locale = os.environ['LANG'] if os.environ['LANG'] else "en"
_ = False
src_dir = Path(__file__).resolve().parent.parent
try:
translation = gettext.translation('messages', localedir=src_dir / 'locales', languages=[locale])
if translation:
translation.install()
_ = translation.gettext
ngettext = translation.ngettext
except FileNotFoundError:
pass
if not _:
_ = gettext.gettext
ngettext = gettext.ngettext
print('No translation found')

View File

@@ -18,6 +18,8 @@ from tabs import Tabs
from urlutils import url_is_file from urlutils import url_is_file
from functools import reduce from functools import reduce
from raven.i18n import _
MAX_LINE_LENGTH = 4096 MAX_LINE_LENGTH = 4096
logging.basicConfig(level=logging.INFO) logging.basicConfig(level=logging.INFO)
@@ -35,9 +37,7 @@ class MainWindow(QMainWindow):
self.settings = SettingsStore.load() self.settings = SettingsStore.load()
PluginRegistry.execute("set_settings", self.settings) PluginRegistry.execute("set_settings", self.settings)
self.setWindowTitle(_("RavenLog"))
self.setWindowTitle(self.tr("RavenLog"))
self._restore_window() self._restore_window()
self.setDockNestingEnabled(True) self.setDockNestingEnabled(True)
@@ -45,7 +45,7 @@ class MainWindow(QMainWindow):
self.tabs = Tabs(self.settings) self.tabs = Tabs(self.settings)
self._menu_recent_files = QMenu(self.tr("Open &Recent"), self) self._menu_recent_files = QMenu(_("Open &Recent"), self)
self.setCentralWidget(self.tabs) self.setCentralWidget(self.tabs)
self.status_bar = QStatusBar(self) self.status_bar = QStatusBar(self)
self.setStatusBar(self.status_bar) self.setStatusBar(self.status_bar)
@@ -64,10 +64,10 @@ class MainWindow(QMainWindow):
menu_contributions = sort_menu_contributions(menu_contributions) menu_contributions = sort_menu_contributions(menu_contributions)
known_menus = [ known_menus = [
("file", self.tr("&File")), ("file", _("&File")),
("settings", self.tr("&Settings")), ("settings", _("&Settings")),
("window", self.tr("&Window")), ("window", _("&Window")),
("help", self.tr("&Help")) ("help", _("&Help"))
] ]
for (menu_id, menu_label) in known_menus: for (menu_id, menu_label) in known_menus:
@@ -98,7 +98,7 @@ class MainWindow(QMainWindow):
qmenu.addAction(action) qmenu.addAction(action)
def _raction_to_qaction(self, raction: RAction, qmenu: QMenu) -> QAction: def _raction_to_qaction(self, raction: RAction, qmenu: QMenu) -> QAction:
action = QAction(self.tr(raction.label), qmenu) action = QAction(_(raction.label), qmenu)
if raction.icon_from_theme: if raction.icon_from_theme:
action.setIcon(QIcon.fromTheme(raction.icon_from_theme)) action.setIcon(QIcon.fromTheme(raction.icon_from_theme))
if raction.icon_file: if raction.icon_file:
@@ -114,7 +114,7 @@ class MainWindow(QMainWindow):
def _action_highlighter(self): def _action_highlighter(self):
manage = RAction( manage = RAction(
"&Highlighter", _("&Highlighter"),
action=lambda: HighlightingDialog(self.settings).exec(), action=lambda: HighlightingDialog(self.settings).exec(),
shortcut='Ctrl+H' shortcut='Ctrl+H'
) )
@@ -122,7 +122,7 @@ class MainWindow(QMainWindow):
def _action_highlight_search_terms(self): def _action_highlight_search_terms(self):
highlight_search_terms = RAction( highlight_search_terms = RAction(
"Highlight &Searches", _("Highlight &Searches"),
action=lambda checked: self.settings.set_session("general", "highlight_search_term", action=lambda checked: self.settings.set_session("general", "highlight_search_term",
str(checked)) or self.update() str(checked)) or self.update()
) )
@@ -131,7 +131,7 @@ class MainWindow(QMainWindow):
return highlight_search_terms return highlight_search_terms
def _action_new_tab(self): def _action_new_tab(self):
new_tab = RAction("Open Tab on Save As File") new_tab = RAction(_("Open Tab on Save As File"))
new_tab.set_checkable(True) new_tab.set_checkable(True)
new_tab.set_checked(self.settings.session.getboolean("general", "open_tab_on_save_as_file")) new_tab.set_checked(self.settings.session.getboolean("general", "open_tab_on_save_as_file"))
new_tab.set_action( new_tab.set_action(

View File

@@ -61,7 +61,7 @@ class PluginRegistry():
if len(sig.parameters) != len(args): if len(sig.parameters) != len(args):
raise RuntimeError("method %s.%s has wrong number of arguments. expected %s but was %s " % ( raise RuntimeError("method %s.%s has wrong number of arguments. expected %s but was %s " % (
plugin, function_name, len(args), len(sig.parameters))) plugin, function_name, len(args), len(sig.parameters)))
print("calling %s with args %s" % (fun, args)) # print("calling %s with args %s" % (fun, args))
if len(args) == 0: if len(args) == 0:
return_value = fun() return_value = fun()
elif len(args) == 1: elif len(args) == 1:

View File

@@ -9,23 +9,20 @@ from raven.pluginbase import PluginBase
from raven.plugins.ravenlog.Tab import Tab from raven.plugins.ravenlog.Tab import Tab
from settings import Settings from settings import Settings
from raven.i18n import _
class LogFilePlugin(PluginBase): class LogFilePlugin(PluginBase):
def __init__(self): def __init__(self):
super(LogFilePlugin, self).__init__() super(LogFilePlugin, self).__init__()
self.settings = None self.settings = None
self.tr = None
def set_settings(self, settings: Settings): def set_settings(self, settings: Settings):
self.settings = settings self.settings = settings
def set_translator(self, tr: Callable[[str], str]):
self.tr = tr
def create_tab(self, file: str) -> Optional[Tab]: def create_tab(self, file: str) -> Optional[Tab]:
if not os.path.isfile(file): if not os.path.isfile(file):
message = QMessageBox(QMessageBox.Icon.Warning, "File not found", message = QMessageBox(QMessageBox.Icon.Warning, _("File not found"),
"'%s' is not a file or cannot be opened" % file) _("'{0}' is not a file or cannot be opened").format(file))
message.exec() message.exec()
return None return None

View File

@@ -7,26 +7,22 @@ from raven.pluginregistry import PluginRegistry
from raven.plugins.domain.menucontribution import MenuContribution from raven.plugins.domain.menucontribution import MenuContribution
from raven.plugins.domain.raction import RAction from raven.plugins.domain.raction import RAction
from raven.plugins.notes.noteswidget import NotesWidget from raven.plugins.notes.noteswidget import NotesWidget
from raven.i18n import _
class NotesPlugin(PluginBase): class NotesPlugin(PluginBase):
def __init__(self): def __init__(self):
super(NotesPlugin, self).__init__() super(NotesPlugin, self).__init__()
self.settings = None self.settings = None
self.tr = None
self.tab_counter = 0 self.tab_counter = 0
def set_translator(self, tr: Callable[[str], str]):
self.tr = tr
def get_menu_contributions(self) -> [MenuContribution]: def get_menu_contributions(self) -> [MenuContribution]:
return [ return [
MenuContribution("window", action=self._add_notes_tab_action(), action_id="add notes tab", after="<last>"), MenuContribution("window", action=self._add_notes_tab_action(), action_id="add notes tab", after="<last>"),
] ]
def _add_notes_tab_action(self) -> RAction: def _add_notes_tab_action(self) -> RAction:
open_file = RAction(self.tr("Add &Notes"), self._add_notes_tab, shortcut='Ctrl+Shift+N', open_file = RAction(_("Add &Notes"), self._add_notes_tab, shortcut='Ctrl+Shift+N',
icon_from_theme="filenew") icon_from_theme="filenew")
return open_file return open_file
@@ -34,5 +30,5 @@ class NotesPlugin(PluginBase):
self.tab_counter = self.tab_counter + 1 self.tab_counter = self.tab_counter + 1
notes = NotesWidget( notes = NotesWidget(
"notes_tab_%d" % self.tab_counter, "notes_tab_%d" % self.tab_counter,
self.tr("Notes %d") % self.tab_counter) _("Notes {0}").format(self.tab_counter))
PluginRegistry.execute_single("add_dock", Qt.DockWidgetArea.RightDockWidgetArea, notes) PluginRegistry.execute_single("add_dock", Qt.DockWidgetArea.RightDockWidgetArea, notes)

View File

@@ -12,26 +12,23 @@ from raven.plugins.domain.raction import RAction
from raven.plugins.domain.rmenu import RMenu from raven.plugins.domain.rmenu import RMenu
from settings import Settings from settings import Settings
from raven.i18n import _
class OpenFilePlugin(PluginBase): class OpenFilePlugin(PluginBase):
def __init__(self): def __init__(self):
super(OpenFilePlugin, self).__init__() super(OpenFilePlugin, self).__init__()
self.settings = None self.settings = None
self.tr = None
def set_settings(self, settings: Settings): def set_settings(self, settings: Settings):
self.settings = settings self.settings = settings
def set_translator(self, tr: Callable[[str], str]):
self.tr = tr
def _action_open_file(self) -> RAction: def _action_open_file(self) -> RAction:
open_file = RAction(self.tr("&Open..."), self._open_file_dialog, shortcut='Ctrl+O', open_file = RAction(_("&Open..."), self._open_file_dialog, shortcut='Ctrl+O',
icon_from_theme="document-open") icon_from_theme="document-open")
return open_file return open_file
def _sub_menu_recent_files(self) -> RMenu: def _sub_menu_recent_files(self) -> RMenu:
self._menu_recent_files = RMenu(self.tr("Open &Recent"), icon_from_theme="document-open-recent") self._menu_recent_files = RMenu(_("Open &Recent"), icon_from_theme="document-open-recent")
self._update_recent_files_menu() self._update_recent_files_menu()
return self._menu_recent_files return self._menu_recent_files
@@ -47,7 +44,7 @@ class OpenFilePlugin(PluginBase):
dialog = QFileDialog() dialog = QFileDialog()
(selected_file, _filter) = dialog.getOpenFileName( (selected_file, _filter) = dialog.getOpenFileName(
caption=self.tr("Open File"), caption=_("Open File"),
dir=directory dir=directory
) )
# directory=directory # directory=directory

View File

@@ -11,17 +11,13 @@ from raven.pluginbase import PluginBase
from raven.plugins.domain.menucontribution import MenuContribution from raven.plugins.domain.menucontribution import MenuContribution
from raven.plugins.domain.raction import RAction from raven.plugins.domain.raction import RAction
from raven.plugins.ravenlog.Tab import Tab from raven.plugins.ravenlog.Tab import Tab
from raven.i18n import _
class RavenLogPlugin(PluginBase): class RavenLogPlugin(PluginBase):
def __init__(self): def __init__(self):
super(RavenLogPlugin, self).__init__() super(RavenLogPlugin, self).__init__()
self.tr = None
self.main_window = None self.main_window = None
def set_translator(self, tr: Callable[[str], str]):
self.tr = tr
def create_main_window(self): def create_main_window(self):
if not self.main_window: if not self.main_window:
self.main_window = MainWindow() self.main_window = MainWindow()
@@ -46,7 +42,7 @@ class RavenLogPlugin(PluginBase):
def _action_about(self) -> RAction: def _action_about(self) -> RAction:
about_action = RAction( about_action = RAction(
self.tr("&About"), _("&About"),
action=lambda: AboutDialog().exec(), action=lambda: AboutDialog().exec(),
icon_file=constants.raven_icon icon_file=constants.raven_icon
) )
@@ -54,6 +50,6 @@ class RavenLogPlugin(PluginBase):
def _action_close(self) -> RAction: def _action_close(self) -> RAction:
icon = "close" if sys.platform == 'win32' or sys.platform == 'cygwin' else "exit" icon = "close" if sys.platform == 'win32' or sys.platform == 'cygwin' else "exit"
close_action = RAction(self.tr("E&xit"), action=lambda: self.main_window.destruct(), shortcut='Ctrl+X', close_action = RAction(_("E&xit"), action=lambda: self.main_window.destruct(), shortcut='Ctrl+X',
icon_from_theme=icon) icon_from_theme=icon)
return close_action return close_action

View File

@@ -1,3 +1,6 @@
from raven.i18n import _
class RavenUI(): class RavenUI():
# no type hint because of circular dependencies # no type hint because of circular dependencies
window = None window = None
@@ -11,9 +14,9 @@ class RavenUI():
if not RavenUI.window: if not RavenUI.window:
return return
if len(title) > 0: if len(title) > 0:
RavenUI.window.setWindowTitle("%s - RavenLog" % title) RavenUI.window.setWindowTitle(_("{0} - RavenLog").format(title))
else: else:
RavenUI.window.setWindowTitle("RavenLog") RavenUI.window.setWindowTitle(_("RavenLog"))
@staticmethod @staticmethod
def update_status_bar(text: str): def update_status_bar(text: str):

View File

@@ -1,7 +1,6 @@
#!/bin/bash #!/bin/bash
echo "extract text from source files" echo "extract text from source files"
pyside6-lupdate *.py raven/*.py raven/plugins/*.py -recursive -ts messages_de.ts find . -iname "*.py" | xargs /home/andi/bin/Python-3.10.0/Tools/i18n/pygettext.py -o locales/messages.pot
echo "write translation to qm file" echo "edit with poedit"
pyside6-lrelease messages_de.ts -qm translations/messages_de.qm

Binary file not shown.