eric6/Project/ProjectTranslationsBrowser.py

changeset 7907
7991ea245c20
parent 7836
2f0d208b8137
child 7911
4621c9082a43
equal deleted inserted replaced
7906:0af028b93cb3 7907:7991ea245c20
99 self.tsprocBackMenuActions = [] 99 self.tsprocBackMenuActions = []
100 self.qmprocBackMenuActions = [] 100 self.qmprocBackMenuActions = []
101 101
102 self.menu = QMenu(self) 102 self.menu = QMenu(self)
103 if self.project.getProjectType() in [ 103 if self.project.getProjectType() in [
104 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 104 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
105 "PySide2", "PySide2C"
105 ]: 106 ]:
106 act = self.menu.addAction( 107 act = self.menu.addAction(
107 self.tr('Generate translation'), self.__generateSelected) 108 self.tr('Generate translation'), self.__generateSelected)
108 self.tsMenuActions.append(act) 109 self.tsMenuActions.append(act)
109 self.tsprocMenuActions.append(act) 110 self.tsprocMenuActions.append(act)
226 self.menu.addSeparator() 227 self.menu.addSeparator()
227 self.menu.addAction(self.tr('Configure...'), self._configure) 228 self.menu.addAction(self.tr('Configure...'), self._configure)
228 229
229 self.backMenu = QMenu(self) 230 self.backMenu = QMenu(self)
230 if self.project.getProjectType() in [ 231 if self.project.getProjectType() in [
231 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 232 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
233 "PySide2", "PySide2C"
232 ]: 234 ]:
233 act = self.backMenu.addAction( 235 act = self.backMenu.addAction(
234 self.tr('Generate all translations'), 236 self.tr('Generate all translations'),
235 self.__generateAll) 237 self.__generateAll)
236 self.tsprocBackMenuActions.append(act) 238 self.tsprocBackMenuActions.append(act)
287 self.backMenu.setEnabled(False) 289 self.backMenu.setEnabled(False)
288 290
289 # create the menu for multiple selected files 291 # create the menu for multiple selected files
290 self.multiMenu = QMenu(self) 292 self.multiMenu = QMenu(self)
291 if self.project.getProjectType() in [ 293 if self.project.getProjectType() in [
292 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 294 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
295 "PySide2", "PySide2C"
293 ]: 296 ]:
294 act = self.multiMenu.addAction( 297 act = self.multiMenu.addAction(
295 self.tr('Generate translations'), 298 self.tr('Generate translations'),
296 self.__generateSelected) 299 self.__generateSelected)
297 self.tsMultiMenuActions.append(act) 300 self.tsMultiMenuActions.append(act)
371 self.multiMenu.addSeparator() 374 self.multiMenu.addSeparator()
372 self.multiMenu.addAction(self.tr('Configure...'), self._configure) 375 self.multiMenu.addAction(self.tr('Configure...'), self._configure)
373 376
374 self.dirMenu = QMenu(self) 377 self.dirMenu = QMenu(self)
375 if self.project.getProjectType() in [ 378 if self.project.getProjectType() in [
376 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 379 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
380 "PySide2", "PySide2C"
377 ]: 381 ]:
378 act = self.dirMenu.addAction( 382 act = self.dirMenu.addAction(
379 self.tr('Generate all translations'), 383 self.tr('Generate all translations'),
380 self.__generateAll) 384 self.__generateAll)
381 self.tsprocDirMenuActions.append(act) 385 self.tsprocDirMenuActions.append(act)
489 def __showContextMenu(self): 493 def __showContextMenu(self):
490 """ 494 """
491 Private slot called by the menu aboutToShow signal. 495 Private slot called by the menu aboutToShow signal.
492 """ 496 """
493 if self.project.getProjectType() in [ 497 if self.project.getProjectType() in [
494 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 498 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
499 "PySide2", "PySide2C"
495 ]: 500 ]:
496 tsFiles = 0 501 tsFiles = 0
497 qmFiles = 0 502 qmFiles = 0
498 itmList = self.getSelectedItems() 503 itmList = self.getSelectedItems()
499 for itm in itmList[:]: 504 for itm in itmList[:]:
533 def __showContextMenuMulti(self): 538 def __showContextMenuMulti(self):
534 """ 539 """
535 Private slot called by the multiMenu aboutToShow signal. 540 Private slot called by the multiMenu aboutToShow signal.
536 """ 541 """
537 if self.project.getProjectType() in [ 542 if self.project.getProjectType() in [
538 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 543 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
544 "PySide2", "PySide2C"
539 ]: 545 ]:
540 tsFiles = 0 546 tsFiles = 0
541 qmFiles = 0 547 qmFiles = 0
542 itmList = self.getSelectedItems() 548 itmList = self.getSelectedItems()
543 for itm in itmList[:]: 549 for itm in itmList[:]:
575 def __showContextMenuDir(self): 581 def __showContextMenuDir(self):
576 """ 582 """
577 Private slot called by the dirMenu aboutToShow signal. 583 Private slot called by the dirMenu aboutToShow signal.
578 """ 584 """
579 if self.project.getProjectType() in [ 585 if self.project.getProjectType() in [
580 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 586 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
587 "PySide2", "PySide2C"
581 ]: 588 ]:
582 if self.pylupdateProcRunning: 589 if self.pylupdateProcRunning:
583 for act in self.tsprocDirMenuActions: 590 for act in self.tsprocDirMenuActions:
584 act.setEnabled(False) 591 act.setEnabled(False)
585 if self.lreleaseProcRunning: 592 if self.lreleaseProcRunning:
595 def __showContextMenuBack(self): 602 def __showContextMenuBack(self):
596 """ 603 """
597 Private slot called by the backMenu aboutToShow signal. 604 Private slot called by the backMenu aboutToShow signal.
598 """ 605 """
599 if self.project.getProjectType() in [ 606 if self.project.getProjectType() in [
600 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 607 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
608 "PySide2", "PySide2C"
601 ]: 609 ]:
602 if self.pylupdateProcRunning: 610 if self.pylupdateProcRunning:
603 for act in self.tsprocBackMenuActions: 611 for act in self.tsprocBackMenuActions:
604 act.setEnabled(False) 612 act.setEnabled(False)
605 if self.lreleaseProcRunning: 613 if self.lreleaseProcRunning:
953 "The generation of the translation files (*.ts) has" 961 "The generation of the translation files (*.ts) has"
954 " failed.{0}").format(info)) 962 " failed.{0}").format(info))
955 963
956 for index in range(len(self.__pylupdateProcesses)): 964 for index in range(len(self.__pylupdateProcesses)):
957 if proc == self.__pylupdateProcesses[index][0]: 965 if proc == self.__pylupdateProcesses[index][0]:
958 try: 966 tmpProjectFile = self.__pylupdateProcesses[index][1]
959 self.__tmpProjects.remove( 967 if tmpProjectFile:
960 self.__pylupdateProcesses[index][1]) 968 try:
961 os.remove(self.__pylupdateProcesses[index][1]) 969 self.__tmpProjects.remove(tmpProjectFile)
962 except OSError: 970 os.remove(tmpProjectFile)
963 pass 971 except OSError:
972 pass
964 del self.__pylupdateProcesses[index] 973 del self.__pylupdateProcesses[index]
965 break 974 break
975
966 if not self.__pylupdateProcesses: 976 if not self.__pylupdateProcesses:
967 # all done 977 # all done
968 self.pylupdateProcRunning = False 978 self.pylupdateProcRunning = False
969 979
970 def __generateTSFile(self, noobsolete=False, generateAll=True): 980 def __generateTSFile(self, noobsolete=False, generateAll=True):
1006 li = [self.project.getRelativePath(lang.fileName()) 1016 li = [self.project.getRelativePath(lang.fileName())
1007 for lang in langs] 1017 for lang in langs]
1008 self.hooks["generateSelectedWithObsolete"](li) 1018 self.hooks["generateSelectedWithObsolete"](li)
1009 return 1019 return
1010 1020
1011 # generate a minimal temporary projectfile suitable for pylupdate 1021 # generate a minimal temporary project file suitable for pylupdate
1012 self.__tmpProjects = [] 1022 self.__tmpProjects = []
1013 if self.project.getProjectLanguage() in [ 1023 if self.project.getProjectLanguage() in [
1014 "Python", "Python3" 1024 "Python", "Python3"
1015 ]: 1025 ]:
1016 ok = self.__writeTempProjectFile(langs, [".py"]) 1026 if self.project.getProjectType() not in ["PyQt6", "PyQt6C"]:
1017 else: 1027 ok = self.__writeTempProjectFile(langs, [".py"])
1018 ok = False 1028 if not ok:
1019 if not ok: 1029 return
1030 else:
1020 return 1031 return
1021 1032
1022 if self.project.getProjectType() in ["PyQt5", "PyQt5C"]: 1033 if self.project.getProjectType() in ["PyQt5", "PyQt5C"]:
1023 self.pylupdate = Utilities.generatePyQtToolPath('pylupdate5') 1034 self.pylupdate = Utilities.generatePyQtToolPath('pylupdate5')
1035 elif self.project.getProjectType() in ["PyQt6", "PyQt6C"]:
1036 self.pylupdate = Utilities.generatePyQtToolPath('pylupdate6')
1024 elif self.project.getProjectType() in ["E6Plugin"]: 1037 elif self.project.getProjectType() in ["E6Plugin"]:
1025 self.pylupdate = Utilities.generatePyQtToolPath('pylupdate5') 1038 self.pylupdate = Utilities.generatePyQtToolPath('pylupdate5')
1026 elif self.project.getProjectType() in ["PySide2", "PySide2C"]: 1039 elif self.project.getProjectType() in ["PySide2", "PySide2C"]:
1027 self.pylupdate = Utilities.generatePySideToolPath( 1040 self.pylupdate = Utilities.generatePySideToolPath(
1028 'pyside2-lupdate') 1041 'pyside2-lupdate')
1029 else: 1042 else:
1030 return 1043 return
1031 1044
1032 self.__pylupdateProcesses = [] 1045 self.__pylupdateProcesses = []
1033 for tempProjectFile in self.__tmpProjects[:]: 1046 if self.project.getProjectType() in ["PyQt6", "PyQt6C"]:
1034 proc = QProcess() 1047 if langs:
1035 args = [] 1048 langs = [self.project.getRelativePath(lang.fileName())
1036 1049 for lang in langs if lang.fileName().endswith('.ts')]
1037 if noobsolete:
1038 args.append('-noobsolete')
1039
1040 args.append('-verbose')
1041 path, filename = os.path.split(tempProjectFile)
1042 args.append(filename)
1043 proc.setWorkingDirectory(os.path.join(self.project.ppath, path))
1044 proc.finished.connect(
1045 lambda c, s: self.__generateTSFileDone(c, s, proc))
1046 proc.readyReadStandardOutput.connect(
1047 lambda: self.__readStdoutLupdate(proc))
1048 proc.readyReadStandardError.connect(
1049 lambda: self.__readStderrLupdate(proc))
1050
1051 proc.start(self.pylupdate, args)
1052 procStarted = proc.waitForStarted()
1053 if procStarted:
1054 self.pylupdateProcRunning = True
1055 self.__pylupdateProcesses.append((proc, tempProjectFile))
1056 else: 1050 else:
1057 E5MessageBox.critical( 1051 try:
1052 pattern = self.project.pdata["TRANSLATIONPATTERN"].replace(
1053 "%language%", "*")
1054 langs = [
1055 lang for lang in self.project.pdata["TRANSLATIONS"]
1056 if fnmatch.fnmatch(lang, pattern)
1057 ]
1058 except IndexError:
1059 langs = []
1060 if not langs:
1061 E5MessageBox.warning(
1058 self, 1062 self,
1059 self.tr('Process Generation Error'), 1063 self.tr("Write temporary project file"),
1060 self.tr( 1064 self.tr("""No translation files (*.ts) selected."""))
1061 'Could not start {0}.<br>' 1065 return
1062 'Ensure that it is in the search path.' 1066 for lang in langs:
1063 ).format(self.pylupdate)) 1067 proc = QProcess()
1064 # cleanup 1068 args = []
1065 try: 1069
1066 self.__tmpProjects.remove(tempProjectFile) 1070 if noobsolete:
1067 os.remove(tempProjectFile) 1071 args.append('--no-obsolete')
1068 except OSError: 1072
1069 pass 1073 args += ["--ts", lang]
1074 args.append(".")
1075
1076 proc.setWorkingDirectory(self.project.ppath)
1077 proc.finished.connect(
1078 lambda c, s: self.__generateTSFileDone(c, s, proc))
1079 proc.readyReadStandardOutput.connect(
1080 lambda: self.__readStdoutLupdate(proc))
1081 proc.readyReadStandardError.connect(
1082 lambda: self.__readStderrLupdate(proc))
1083
1084 proc.start(self.pylupdate, args)
1085 procStarted = proc.waitForStarted()
1086 if procStarted:
1087 self.pylupdateProcRunning = True
1088 self.__pylupdateProcesses.append((proc, ""))
1089 else:
1090 E5MessageBox.critical(
1091 self,
1092 self.tr('Process Generation Error'),
1093 self.tr(
1094 'Could not start {0}.<br>'
1095 'Ensure that it is in the search path.'
1096 ).format(self.pylupdate))
1097 else:
1098 for tempProjectFile in self.__tmpProjects[:]:
1099 proc = QProcess()
1100 args = []
1101
1102 if noobsolete:
1103 args.append('-noobsolete')
1104
1105 args.append('-verbose')
1106 path, filename = os.path.split(tempProjectFile)
1107 args.append(filename)
1108 proc.setWorkingDirectory(
1109 os.path.join(self.project.ppath, path))
1110 proc.finished.connect(
1111 lambda c, s: self.__generateTSFileDone(c, s, proc))
1112 proc.readyReadStandardOutput.connect(
1113 lambda: self.__readStdoutLupdate(proc))
1114 proc.readyReadStandardError.connect(
1115 lambda: self.__readStderrLupdate(proc))
1116
1117 proc.start(self.pylupdate, args)
1118 procStarted = proc.waitForStarted()
1119 if procStarted:
1120 self.pylupdateProcRunning = True
1121 self.__pylupdateProcesses.append((proc, tempProjectFile))
1122 else:
1123 E5MessageBox.critical(
1124 self,
1125 self.tr('Process Generation Error'),
1126 self.tr(
1127 'Could not start {0}.<br>'
1128 'Ensure that it is in the search path.'
1129 ).format(self.pylupdate))
1130 # cleanup
1131 try:
1132 self.__tmpProjects.remove(tempProjectFile)
1133 os.remove(tempProjectFile)
1134 except OSError:
1135 pass
1070 1136
1071 def __generateAll(self): 1137 def __generateAll(self):
1072 """ 1138 """
1073 Private method to generate all translation files (.ts) for Qt Linguist. 1139 Private method to generate all translation files (.ts) for Qt Linguist.
1074 1140
1180 for lang in langs] 1246 for lang in langs]
1181 self.hooks["releaseSelected"](li) 1247 self.hooks["releaseSelected"](li)
1182 return 1248 return
1183 1249
1184 if self.project.getProjectType() in [ 1250 if self.project.getProjectType() in [
1185 "PyQt5", "PyQt5C", "E6Plugin", "PySide2", "PySide2C" 1251 "PyQt5", "PyQt5C", "PyQt6", "PyQt6C", "E6Plugin",
1252 "PySide2", "PySide2C"
1186 ]: 1253 ]:
1187 lrelease = os.path.join( 1254 lrelease = os.path.join(
1188 Utilities.getQtBinariesPath(), 1255 Utilities.getQtBinariesPath(),
1189 Utilities.generateQtToolName("lrelease")) 1256 Utilities.generateQtToolName("lrelease"))
1190 else: 1257 else:

eric ide

mercurial