6 """ |
6 """ |
7 Module implementing a class used to display the resources part of the project. |
7 Module implementing a class used to display the resources part of the project. |
8 """ |
8 """ |
9 |
9 |
10 import os |
10 import os |
|
11 import contextlib |
11 |
12 |
12 from PyQt5.QtCore import QThread, QFileInfo, pyqtSignal, QProcess |
13 from PyQt5.QtCore import QThread, QFileInfo, pyqtSignal, QProcess |
13 from PyQt5.QtWidgets import QDialog, QApplication, QMenu |
14 from PyQt5.QtWidgets import QDialog, QApplication, QMenu |
14 |
15 |
15 from E5Gui.E5Application import e5App |
16 from E5Gui.E5Application import e5App |
325 @param coord the position of the mouse pointer (QPoint) |
326 @param coord the position of the mouse pointer (QPoint) |
326 """ |
327 """ |
327 if not self.project.isOpen(): |
328 if not self.project.isOpen(): |
328 return |
329 return |
329 |
330 |
330 try: |
331 with contextlib.suppress(Exception): |
331 categories = self.getSelectedItemsCountCategorized( |
332 categories = self.getSelectedItemsCountCategorized( |
332 [ProjectBrowserFileItem, ProjectBrowserSimpleDirectoryItem]) |
333 [ProjectBrowserFileItem, ProjectBrowserSimpleDirectoryItem]) |
333 cnt = categories["sum"] |
334 cnt = categories["sum"] |
334 if cnt <= 1: |
335 if cnt <= 1: |
335 index = self.indexAt(coord) |
336 index = self.indexAt(coord) |
355 self.dirMenu.popup(self.mapToGlobal(coord)) |
356 self.dirMenu.popup(self.mapToGlobal(coord)) |
356 else: |
357 else: |
357 self.backMenu.popup(self.mapToGlobal(coord)) |
358 self.backMenu.popup(self.mapToGlobal(coord)) |
358 else: |
359 else: |
359 self.backMenu.popup(self.mapToGlobal(coord)) |
360 self.backMenu.popup(self.mapToGlobal(coord)) |
360 except Exception: # secok |
|
361 pass |
|
362 |
361 |
363 def __showContextMenu(self): |
362 def __showContextMenu(self): |
364 """ |
363 """ |
365 Private slot called by the menu aboutToShow signal. |
364 Private slot called by the menu aboutToShow signal. |
366 """ |
365 """ |
493 if not res: |
492 if not res: |
494 # user selected to not overwrite |
493 # user selected to not overwrite |
495 return |
494 return |
496 |
495 |
497 try: |
496 try: |
498 if self.project.useSystemEol(): |
497 newline = (None if self.project.useSystemEol() |
499 newline = None |
498 else self.project.getEolString()) |
500 else: |
|
501 newline = self.project.getEolString() |
|
502 with open(fname, 'w', encoding="utf-8", |
499 with open(fname, 'w', encoding="utf-8", |
503 newline=newline) as rcfile: |
500 newline=newline) as rcfile: |
504 rcfile.write('<!DOCTYPE RCC>\n') |
501 rcfile.write('<!DOCTYPE RCC>\n') |
505 rcfile.write('<RCC version="1.0">\n') |
502 rcfile.write('<RCC version="1.0">\n') |
506 rcfile.write('<qresource>\n') |
503 rcfile.write('<qresource>\n') |
600 exitCode == 0 and |
597 exitCode == 0 and |
601 self.buf |
598 self.buf |
602 ): |
599 ): |
603 ofn = os.path.join(self.project.ppath, self.compiledFile) |
600 ofn = os.path.join(self.project.ppath, self.compiledFile) |
604 try: |
601 try: |
605 if self.project.useSystemEol(): |
602 newline = (None if self.project.useSystemEol() |
606 newline = None |
603 else self.project.getEolString()) |
607 else: |
|
608 newline = self.project.getEolString() |
|
609 with open(ofn, "w", encoding="utf-8", newline=newline) as f: |
604 with open(ofn, "w", encoding="utf-8", newline=newline) as f: |
610 for line in self.buf.splitlines(): |
605 for line in self.buf.splitlines(): |
611 f.write(line + "\n") |
606 f.write(line + "\n") |
612 if self.compiledFile not in self.project.pdata["SOURCES"]: |
607 if self.compiledFile not in self.project.pdata["SOURCES"]: |
613 self.project.appendFile(ofn) |
608 self.project.appendFile(ofn) |
628 ui.showNotification( |
623 ui.showNotification( |
629 UI.PixmapCache.getPixmap("resourcesCompiler48"), |
624 UI.PixmapCache.getPixmap("resourcesCompiler48"), |
630 self.tr("Resource Compilation"), |
625 self.tr("Resource Compilation"), |
631 self.tr( |
626 self.tr( |
632 "The compilation of the resource file failed."), |
627 "The compilation of the resource file failed."), |
633 kind=NotificationTypes.Critical, |
628 kind=NotificationTypes.CRITICAL, |
634 timeout=0) |
629 timeout=0) |
635 self.compileProc = None |
630 self.compileProc = None |
636 |
631 |
637 def __compileQRC(self, fn, noDialog=False, progress=None): |
632 def __compileQRC(self, fn, noDialog=False, progress=None): |
638 """ |
633 """ |
646 self.compileProc = QProcess() |
641 self.compileProc = QProcess() |
647 args = [] |
642 args = [] |
648 self.buf = "" |
643 self.buf = "" |
649 |
644 |
650 if self.project.getProjectLanguage() == "Python3": |
645 if self.project.getProjectLanguage() == "Python3": |
651 if self.project.getProjectType() in ["PyQt5", "PyQt5C"]: |
646 if self.project.getProjectType() in ["PyQt5", "PyQt5C", |
652 self.rccCompiler = Utilities.generatePyQtToolPath('pyrcc5') |
647 "E6Plugin"]: |
653 elif self.project.getProjectType() in ["E6Plugin"]: |
|
654 self.rccCompiler = Utilities.generatePyQtToolPath('pyrcc5') |
648 self.rccCompiler = Utilities.generatePyQtToolPath('pyrcc5') |
655 elif self.project.getProjectType() in ["PySide2", "PySide2C"]: |
649 elif self.project.getProjectType() in ["PySide2", "PySide2C"]: |
656 self.rccCompiler = Utilities.generatePySideToolPath( |
650 self.rccCompiler = Utilities.generatePySideToolPath( |
657 'pyside2-rcc', variant=2) |
651 'pyside2-rcc', variant=2) |
658 elif self.project.getProjectType() in ["PySide6", "PySide6C"]: |
652 elif self.project.getProjectType() in ["PySide6", "PySide6C"]: |
748 self.tr("Abort"), 0, numResources, |
742 self.tr("Abort"), 0, numResources, |
749 self.tr("%v/%m Resources"), self) |
743 self.tr("%v/%m Resources"), self) |
750 progress.setModal(True) |
744 progress.setModal(True) |
751 progress.setMinimumDuration(0) |
745 progress.setMinimumDuration(0) |
752 progress.setWindowTitle(self.tr("Resources")) |
746 progress.setWindowTitle(self.tr("Resources")) |
753 i = 0 |
|
754 |
747 |
755 for fn in self.project.pdata["RESOURCES"]: |
748 for prog, fn in enumerate(self.project.pdata["RESOURCES"]): |
756 progress.setValue(i) |
749 progress.setValue(prog) |
757 if progress.wasCanceled(): |
750 if progress.wasCanceled(): |
758 break |
751 break |
759 proc = self.__compileQRC(fn, True, progress) |
752 proc = self.__compileQRC(fn, True, progress) |
760 if proc is not None: |
753 if proc is not None: |
761 while proc.state() == QProcess.ProcessState.Running: |
754 while proc.state() == QProcess.ProcessState.Running: |
762 QApplication.processEvents() |
755 QApplication.processEvents() |
763 QThread.msleep(300) |
756 QThread.msleep(300) |
764 QApplication.processEvents() |
757 QApplication.processEvents() |
765 else: |
758 else: |
766 break |
759 break |
767 i += 1 |
|
768 |
|
769 progress.setValue(numResources) |
760 progress.setValue(numResources) |
770 |
761 |
771 def __compileSelectedResources(self): |
762 def __compileSelectedResources(self): |
772 """ |
763 """ |
773 Private method to compile selected resources to source files. |
764 Private method to compile selected resources to source files. |
785 self.tr("Abort"), 0, numResources, |
776 self.tr("Abort"), 0, numResources, |
786 self.tr("%v/%m Resources"), self) |
777 self.tr("%v/%m Resources"), self) |
787 progress.setModal(True) |
778 progress.setModal(True) |
788 progress.setMinimumDuration(0) |
779 progress.setMinimumDuration(0) |
789 progress.setWindowTitle(self.tr("Resources")) |
780 progress.setWindowTitle(self.tr("Resources")) |
790 i = 0 |
|
791 |
781 |
792 for fn in files: |
782 for prog, fn in enumerate(files): |
793 progress.setValue(i) |
783 progress.setValue(prog) |
794 if progress.wasCanceled(): |
784 if progress.wasCanceled(): |
795 break |
785 break |
796 if not fn.endswith('.ui.h'): |
786 if not fn.endswith('.ui.h'): |
797 proc = self.__compileQRC(fn, True, progress) |
787 proc = self.__compileQRC(fn, True, progress) |
798 if proc is not None: |
788 if proc is not None: |
800 QApplication.processEvents() |
790 QApplication.processEvents() |
801 QThread.msleep(300) |
791 QThread.msleep(300) |
802 QApplication.processEvents() |
792 QApplication.processEvents() |
803 else: |
793 else: |
804 break |
794 break |
805 i += 1 |
|
806 |
|
807 progress.setValue(numResources) |
795 progress.setValue(numResources) |
808 |
796 |
809 def __checkResourcesNewer(self, filename, mtime): |
797 def __checkResourcesNewer(self, filename, mtime): |
810 """ |
798 """ |
811 Private method to check, if any file referenced in a resource |
799 Private method to check, if any file referenced in a resource |
857 progress = E5ProgressDialog( |
845 progress = E5ProgressDialog( |
858 self.tr("Determining changed resources..."), |
846 self.tr("Determining changed resources..."), |
859 self.tr("Abort"), 0, 100, self.tr("%v/%m Resources")) |
847 self.tr("Abort"), 0, 100, self.tr("%v/%m Resources")) |
860 progress.setMinimumDuration(0) |
848 progress.setMinimumDuration(0) |
861 progress.setWindowTitle(self.tr("Resources")) |
849 progress.setWindowTitle(self.tr("Resources")) |
862 i = 0 |
|
863 |
850 |
864 # get list of changed resources |
851 # get list of changed resources |
865 changedResources = [] |
852 changedResources = [] |
866 progress.setMaximum(len(self.project.pdata["RESOURCES"])) |
853 progress.setMaximum(len(self.project.pdata["RESOURCES"])) |
867 for fn in self.project.pdata["RESOURCES"]: |
854 for prog, fn in enumerate(self.project.pdata["RESOURCES"]): |
868 progress.setValue(i) |
855 progress.setValue(prog) |
869 QApplication.processEvents() |
856 QApplication.processEvents() |
870 ifn = os.path.join(self.project.ppath, fn) |
857 ifn = os.path.join(self.project.ppath, fn) |
871 if self.project.getProjectLanguage() == "Python3": |
858 if self.project.getProjectLanguage() == "Python3": |
872 dirname, filename = os.path.split(os.path.splitext(ifn)[0]) |
859 dirname, filename = os.path.split(os.path.splitext(ifn)[0]) |
873 ofn = os.path.join( |
860 ofn = os.path.join( |
878 dirname, self.RCFilenameFormatRuby.format(filename)) |
865 dirname, self.RCFilenameFormatRuby.format(filename)) |
879 else: |
866 else: |
880 return |
867 return |
881 if ( |
868 if ( |
882 not os.path.exists(ofn) or |
869 not os.path.exists(ofn) or |
883 os.stat(ifn).st_mtime > os.stat(ofn).st_mtime |
870 os.stat(ifn).st_mtime > os.stat(ofn).st_mtime or |
|
871 self.__checkResourcesNewer(ifn, os.stat(ofn).st_mtime) |
884 ): |
872 ): |
885 changedResources.append(fn) |
873 changedResources.append(fn) |
886 elif self.__checkResourcesNewer(ifn, os.stat(ofn).st_mtime): |
874 progress.setValue(len(self.project.pdata["RESOURCES"])) |
887 changedResources.append(fn) |
|
888 i += 1 |
|
889 progress.setValue(i) |
|
890 QApplication.processEvents() |
875 QApplication.processEvents() |
891 |
876 |
892 if changedResources: |
877 if changedResources: |
893 progress.setLabelText( |
878 progress.setLabelText( |
894 self.tr("Compiling changed resources...")) |
879 self.tr("Compiling changed resources...")) |
895 progress.setMaximum(len(changedResources)) |
880 progress.setMaximum(len(changedResources)) |
896 i = 0 |
881 progress.setValue(0) |
897 progress.setValue(i) |
|
898 QApplication.processEvents() |
882 QApplication.processEvents() |
899 for fn in changedResources: |
883 for prog, fn in enumerate(changedResources): |
900 progress.setValue(i) |
884 progress.setValue(prog) |
901 if progress.wasCanceled(): |
885 if progress.wasCanceled(): |
902 break |
886 break |
903 proc = self.__compileQRC(fn, True, progress) |
887 proc = self.__compileQRC(fn, True, progress) |
904 if proc is not None: |
888 if proc is not None: |
905 while proc.state() == QProcess.ProcessState.Running: |
889 while proc.state() == QProcess.ProcessState.Running: |
906 QApplication.processEvents() |
890 QApplication.processEvents() |
907 QThread.msleep(300) |
891 QThread.msleep(300) |
908 QApplication.processEvents() |
892 QApplication.processEvents() |
909 else: |
893 else: |
910 break |
894 break |
911 i += 1 |
|
912 progress.setValue(len(changedResources)) |
895 progress.setValue(len(changedResources)) |
913 QApplication.processEvents() |
896 QApplication.processEvents() |
914 |
897 |
915 def handlePreferencesChanged(self): |
898 def handlePreferencesChanged(self): |
916 """ |
899 """ |