Ejemplo n.º 1
0
class LangPicker(getUiClass(UI_FILE)):

    # Signals
    exitSignal = QtCore.pyqtSignal()

    def __init__(self, *args, setupUi=True, default=None, langs=langs, **kwargs,):
        super(LangPicker, self).__init__(*args, setupUi=False, **kwargs)
        self.default = default
        self.langs = langs
        self.noDefaultText = 'Choose Language...'
        if setupUi:
            self.setupUi()
    
    def setupUi(self):
        super(LangPicker, self).setupUi()
        self._langList = list(self.langs.keys())
        self._langList.sort()
        self.languageComboBox.addItem(self.noDefaultText)
        for lang in self._langList:
            self.languageComboBox.addItem(lang)

    # Slots
    @QtCore.pyqtSlot()
    def acceptedSlot(self, lang):
        self.exitSignal.emit()
Ejemplo n.º 2
0
class ExpendedEdit(getUiClass(EXTENDEDEDIT_FILE)):
    """
    More comfortable translation editor.
    Inner data must contain 'Origin', 'Translation' and 'keep'.

    Signals:
        translationChanged()
        autoTranslateClicked()
    
    Slots:
        setData(data)
        updateTranslation()
        keepOrigin()
        updateData()
    """

    # Signals
    translationChangedSignal = QtCore.pyqtSignal()
    autoTranslateClicked = QtCore.pyqtSignal()

    def __init__(self, *args, **kwargs):
        super(ExpendedEdit, self).__init__(*args, **kwargs)
        self.data = {}

    def setupUi(self):
        super(ExpendedEdit, self).setupUi()
        self.translationChangedSignal = self.translationTextEdit.textChanged
        self.autoTranslateClicked = self.autoTranslateButton.clicked
        self.translationTextEdit.textChanged.connect(self.updateData)
        self.keepOriginButton.clicked.connect(self.keepOrigin)

    # Slots
    @QtCore.pyqtSlot('PyQt_PyObject')
    def setData(self, data):
        self.data = data
        self.originTextEdit.setText(data['Origin'])
        self.translationTextEdit.setText(data['Translation'])

    @QtCore.pyqtSlot()
    def updateTranslation(self, *args, **kwargs):
        # assert self.data, 'Trying to update data while no data has been set.'
        text = self.data['Translation']
        if text != self.translationTextEdit.toPlainText():
            self.translationTextEdit.setText(text)

    @QtCore.pyqtSlot()
    def keepOrigin(self):
        if not self.data:
            return
        self.translationTextEdit.setText(self.data['Origin'])
        self.data['keep'] = True

    @QtCore.pyqtSlot()
    def updateData(self):
        if not self.data:
            return
        text = self.translationTextEdit.toPlainText()
        if text != self.data['Translation']:
            self.data['Translation'] = text
Ejemplo n.º 3
0
class Message(getUiClass(UI_FILE)):
    def __init__(self, *args, message='An error occure', **kwargs):
        super(Message, self).__init__(*args, **kwargs)
        self.message = message

    @property
    def message(self):
        return self._message

    @message.setter
    def message(self, message):
        self._message = message
        self.label.setText(self._message)
        self.adjustSize()
Ejemplo n.º 4
0
class PickLanguageDialog(getUiClass(UI_FILE)):

    # Signals
    acceptedSignal = QtCore.pyqtSignal('PyQt_PyObject', arguments=['ReturnDict'])
    rejectedSignal = QtCore.pyqtSignal('PyQt_PyObject', arguments=['ReturnDictNoLang'])

    def __init__(self, *args, langs=langs, setupUi=True, default="Hebrew", existLangs={}, onExist=CREATE, **kwargs):
        super(PickLanguageDialog, self).__init__( *args, setupUi=False, **kwargs)
        self.default = default
        self._langs = dict()
        self.langs = langs
        self.noDefaultText = 'Choose Language...'
        self.onExist = onExist
        self.langExist = False
        self.existLangs = existLangs
        if setupUi:
            self.setupUi()
    
    # Methodes
    def setupUi(self):
        super(PickLanguageDialog, self).setupUi()
        # self.langExistGroupBox.setVisible(False)
        self.buttonBox.button(QtWidgets.QDialogButtonBox.Ok).setAutoDefault(True)
        self.buttonBox.button(QtWidgets.QDialogButtonBox.Cancel).setAutoDefault(True)

        # Setup combo box
        if not self.default:
            self.langComboBox.addItem(self.noDefaultText)
        for lang in self._langList:
            self.langComboBox.addItem(lang)
        defaultIdx = self._langList.index(self.default) if self.default else 0
        self.langComboBox.setCurrentIndex(defaultIdx)

        # Setup on Exists
        if self.onExist == EDIT:
            self.editExistTranslation.setChecked(True)
        elif self.onExist == CREATE:
            self.createNewTranslation.setChecked(True)

        self.adjustSize()
    
    def _checkLangExists(self, lang):
        self.langExist = lang in self.existLangs
        if self.langExist:
            self.langExistGroupBox.show()
        else:
            self.langExistGroupBox.hide()

        self.adjustSize()

    # Properties
    @QtCore.pyqtProperty(dict)
    def langs(self):
      return  self._langs
    
    @langs.setter
    def langs(self, langs):
        self._langs = langs
        self._langList = list(self._langs.keys())
        self._langList.sort()
    
    # Slots
    @QtCore.pyqtSlot(str)
    def onLangPick(self, lang):
        if lang in self._langList:
            self.buttonBox.button(QtWidgets.QDialogButtonBox.Ok).setEnabled(True)
            self.buttonBox.button(QtWidgets.QDialogButtonBox.Ok).setDefault(True)
            self.buttonBox.button(QtWidgets.QDialogButtonBox.Cancel).setDefault(False)
        else:
            self.buttonBox.button(QtWidgets.QDialogButtonBox.Ok).setEnabled(False)
            self.buttonBox.button(QtWidgets.QDialogButtonBox.Cancel).setDefault(True)
        self._checkLangExists(lang)
    
    @QtCore.pyqtSlot()
    def acceptedSlot(self):
        ret = {
            'Lang': self.langComboBox.currentText(),
            'Exists': self.langExist,
            'onExists': CREATE if self.createNewTranslation.isChecked() else EDIT
        }
        self.acceptedSignal.emit(ret)
    
    @QtCore.pyqtSlot()
    def rejectedSlot(self):
        ret = {
            'Lang': '',
        }
        self.rejectedSignal.emit(ret)
Ejemplo n.º 5
0
class MainWindow(getUiClass(UI_FILE)):
    """
    Description for MainWindow.
    """
    def __init__(self, *args, **kwargs):
        super(MainWindow, self).__init__(*args, **kwargs)
        self.threadpool = t

    def setupUi(self):
        super(MainWindow, self).setupUi()
        self.projectsTree.itemClicked.connect(self.tabs.addTranslator)
        self.openEditors.itemClicked.connect(self.tabs.focus)
        self.tabs.translatorAdded.connect(self.openEditors.addTranslator)
        self.tabs.translatorClosed.connect(self.openEditors.removeTranslator)
        self.tabs.focused.connect(self.openEditors.focus)
        self.tabs.focused.connect(self.projectsTree.focus)
        self.action_Open_ROM.triggered.connect(self.menuOpenROM)
        self.action_Open_APK.triggered.connect(self.menuOpenAPK)
        self.action_Open_XML.triggered.connect(self.menuOpenXML)
        self.actionSave.triggered.connect(self.tabs.save)
        self.actionBuild.triggered.connect(self.tabs.build)

        # Shortcut
        self.shortcutSave = QtWidgets.QShortcut(QtGui.QKeySequence('Ctrl+S'),
                                                self)
        self.shortcutSaveAs = QtWidgets.QShortcut(QtGui.QKeySequence('Ctrl+S'),
                                                  self)
        self.shortcutOpenAPK = QtWidgets.QShortcut(
            QtGui.QKeySequence('Ctrl+O'), self)
        # self.shortcut = QtWidgets.QShortcut(QtGui.QKeySequence('Ctrl+'), self)
        # self.shortcut = QtWidgets.QShortcut(QtGui.QKeySequence('Ctrl+'), self)
        # self.shortcut = QtWidgets.QShortcut(QtGui.QKeySequence('Ctrl+'), self)
        self.shortcutSave.activated.connect(self.tabs.save)
        # self.shortcutSaveAs.activated.connect(self.)
        self.shortcutOpenAPK.activated.connect(self.menuOpenAPK)

    def menuOpenROM(self):
        romDir = QtWidgets.QFileDialog.getExistingDirectory(
            None,
            'Select Rom Directory',
        )
        self.open(romDir) if romDir else None

    def menuOpenAPK(self):
        apkDir = QtWidgets.QFileDialog.getOpenFileName(
            None, 'Open APK File', filter='APK file (*.apk)')[0]
        print(apkDir)
        self.open(apkDir) if apkDir else None

    def menuOpenXML(self):
        xmlPath = QtWidgets.QFileDialog.getOpenFileName(
            None, 'Open XML File', filter='XML file (*.xml)')[0]
        self.open(xmlPath) if xmlPath else None

    def open(self, path):
        treeItem = ProjectTreeItem(Translator(path=path), children=True)
        self.projectsTree.addTopLevelItem(treeItem)
        if isFileOfType(path, 'xml'):
            self.projectsTree.itemActivated.emit(treeItem, 0)

    # Events
    def startDrag(self):
        print('start drag')

    def dragEnterEvent(self, e):
        for url in e.mimeData().urls():
            if url.scheme() == 'file':
                path = os.path.normpath(url.path()[1:])
                if isFileOfType(path, 'xml') or isFileOfType(
                        path, 'apk') or os.path.isdir(path):
                    e.accept()
                    return
        e.ignore()

    def dropEvent(self, e):
        for url in e.mimeData().urls():
            path = os.path.normpath(url.path()[1:])
            if isFileOfType(path, 'xml') or isFileOfType(
                    path, 'apk') or os.path.isdir(path):
                self.open(path)
Ejemplo n.º 6
0
class TranslateView(getUiClass(UI_FILE)):

    transaltionErrorSignal = QtCore.pyqtSignal('PyQt_PyObject',
                                               arguments=['Exception'])
    translationCanceledSignal = QtCore.pyqtSignal()
    dataUpdated = QtCore.pyqtSignal()
    rowUpdated = QtCore.pyqtSignal(int, arguments=['Exception'])

    def __init__(self, *args, setupUi=False, parent=None, **kwargs):
        self._uiSet = False
        super(TranslateView, self).__init__(*args, setupUi=setupUi, **kwargs)
        self._langPicker = None
        self.langPickRet = {}
        self.activeRow = None
        self._data = []
        self._stopTransThread = [False]
        self.dataUpdated.connect(self.refreshTable)
        print('parent Name:', parent.name) if parent else None
        self.dataUpdated.connect(parent.childDataUpdated) if parent else None

    def setupUi(self):
        if self._uiSet:
            return
        super(TranslateView, self).setupUi()
        self.tg = None
        self.translationTable.setData(['Name', 'Origin', 'Translation'],
                                      list(self.data))
        self.transaltionErrorSignal.connect(self.transaltionErrorSlot)
        self.translationTable.rowClickedSignal.connect(self.setActiveRow)
        self.translationTable.rowChangedSignal.connect(self.updateExpendedEdit)
        self.expendedEdit.translationChangedSignal.connect(
            self.updateActiveRow)
        self.expendedEdit.autoTranslateClicked.connect(self.translateActiveRow)
        self.translationCanceledSignal.connect(self.closeTg)

        if self.activeRow != None:
            self.translationTable.selectRow(self.activeRow)
            self.setActiveRow(self.activeRow)
        self._uiSet = True

    def focused(self, translator, *args, **kwargs):
        if translator is not self:
            return
        self.refreshTable()

    @QtCore.pyqtSlot(int)
    def updateExpendedEdit(self, row):
        self.expendedEdit.updateTranslation(
        ) if row == self.activeRow else None

    @QtCore.pyqtSlot()
    def updateActiveRow(self):
        print(self.activeRow)
        self.translationTable.updateRow(
            self.activeRow) if self.activeRow != None else None

    @QtCore.pyqtSlot(int)
    def setActiveRow(self, row):
        if self._uiSet and self.data:
            self.expendedEdit.setData(list(self.translationTable.data)[row])
            self.expendedEditBorder.setTitle(
                self.translationTable.data[row]['Name'])
        self.activeRow = row

    def refreshTable(self):
        if self._uiSet:
            self.translationTable.refresh()
            # self.translationTable.setData(['Name', 'Origin', 'Translation'], list(self.data))

    def childDataUpdated(self):
        print('childDataUpdated, ', self.name)
        self.dataUpdated.emit()

    def getChildren(self):
        """
        Should be implemented in the logic part.
        """
        return []

    def _translate(self, data):
        """
        Should be implemented in the logic part (this is the ui part)
        """
        pass
        return [i * 2 for i in data]

    def pickLang(self, *args, **kwargs):
        if not self._langPicker:
            self._langPicker = PickLanguageDialog(*args, **kwargs)
            self._langPicker.acceptedSignal.connect(self.pickLangSlot)
            self._langPicker.rejectedSignal.connect(self.pickLangSlot)
        else:
            self._langPicker.__init__(*args, **kwargs)
        self._langPicker.exec()

    @QtCore.pyqtSlot('PyQt_PyObject')
    def pickLangSlot(self, ret):
        self.langPickRet = ret
        self.newLang = ret['Lang']

    def isTransThreadStopped(self):
        return self._stopTransThread[-1]

    # Slots
    @QtCore.pyqtSlot()
    def stopTransThread(self, *args, **kwargs):
        if self.isTransThreadStopped():
            return
        self._stopTransThread.append(True)
        self.translationCanceledSignal.emit()

    def closeTg(self):
        self.tg.close()

    # @QtCore.pyqtSlot(int, int)
    def startTranslateData(self, data):
        if not self.tg:
            self.tg = TranslatingDialog()
            self.tg.rejected.connect(self.stopTransThread)
        thread = Worker(target=self.translateData,
                        tar_args=(data, self.isTransThreadStopped),
                        callBackEmptySignal=self.translationCanceledSignal,
                        callback=self.stopTransThread)
        self._stopTransThread = [False]
        self.threadpool.start(thread)
        self.tg.exec()

    @QtCore.pyqtSlot('PyQt_PyObject')
    def transaltionErrorSlot(self, exception):
        m = Message(message=f'An error occure while translating: {exception}')
        m.exec()

    @QtCore.pyqtSlot()
    def translateAllSlot(self):
        self.startTranslateData(self.data)

    def translateActiveRow(self):
        self.startTranslateData([self.expendedEdit.data
                                 ]) if self.activeRow != None else None

    def translateData(self, data, stopFlagGetter, from_='Origin'):
        for i in data:
            translated = self._translate(i[from_])
            if stopFlagGetter():
                return
            if type(translated) != str:
                self.transaltionErrorSignal.emit(translated)
                return
            i['Translation'] = translated
            self.translationTable.rowChangedSignal.emit(
                self.translationTable.data.index(i))

    # properties
    @property
    def data(self):
        if self.getChildren():
            for child in self.getChildren():
                for i in child.data:
                    yield i
        else:
            for i in self._data:
                yield i

    @data.setter
    def data(self, data):
        self._data = data
        self.dataUpdated.emit()

    @QtCore.pyqtSlot()
    def save(self):
        pass
        self.saveData()

    def saveData(self):
        """
        Should be implemented in the logic part (this is the ui part)
        """
        pass

    def getNewXMLPath(self, recommandedPath):
        d = QtWidgets.QFileDialog(None, 'Save To XML', recommandedPath,
                                  'XML file (*.xml)')
        d.setAcceptMode(QtWidgets.QFileDialog.AcceptSave)
        d.setDefaultSuffix('xml')
        d.exec()
        xmlpath = d.selectedFiles()[0]
        return xmlpath

    def getNewAPKPath(self, recommandedPath):
        d = QtWidgets.QFileDialog(None, 'Save To APK', recommandedPath,
                                  'XML file (*.apk)')
        d.setAcceptMode(QtWidgets.QFileDialog.AcceptSave)
        d.setDefaultSuffix('apk')
        d.exec()
        apkPath = d.selectedFiles()[0]
        return apkPath

    def buildError(self, srcPath, dstPath):
        m = Message(
            message=
            f'Could not build: {srcPath} into {dstPath}.\nYou may want to look in the logs.'
        )
        m.exec()
Ejemplo n.º 7
0
import os
import threading

from PyQt5 import QtCore, QtGui, QtWidgets
from Ui.UiLoader import getUiClass
from Ui.PickLanguageDialog import PickLanguageDialog
from Ui.Message import Message

from appctx import ApplicationContext

# TranslatingDialog = getUiClass(path.abspath(path.join(path.dirname(__file__), 'TranslatingDialog.ui')))
TranslatingDialog = getUiClass(
    ApplicationContext.get_resource(os.path.join('ui',
                                                 'TranslatingDialog.ui')))
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
#                                                                                             #
# Important!  pyqt5 versions 5.12.0 to 5.13.0 when using Python 3.7.x has a bag. Be carefull  #
#             and don't use them.                                                             #
#                                                                                             #
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #

# UI_FILE = path.abspath(path.join(path.dirname(__file__), 'TranslateView.ui'))
# EXTENDEDEDIT_FILE = path.abspath(path.join(path.dirname(__file__), 'extendedEdit.ui'))
UI_FILE = ApplicationContext.get_resource(
    os.path.join('ui', 'TranslateView.ui'))
EXTENDEDEDIT_FILE = ApplicationContext.get_resource(
    os.path.join('ui', 'extendedEdit.ui'))


class CustomTableWidget(QtWidgets.QTableWidget):