Ejemplo n.º 1
0
class ClusterDialog(QDialog):
    
    editClusterName = None
    def __init__(self, lifeline, defaultName, parent = None):
        super(ClusterDialog, self).__init__(parent)

        self.lifeline = lifeline
        layout = QVBoxLayout(self)

        message = QLabel('Enter group name')
        layout.addWidget(message)

        self.editClusterName = QLineEdit(defaultName)
        self.editClusterName.setFixedHeight(30)
        self.editClusterName.setFixedWidth(400)
        self.editClusterName.textChanged.connect(self.validateCluster)
        layout.addWidget(self.editClusterName)

        self.validation_msg = QLabel(' ')
        layout.addWidget(self.validation_msg)

        buttons = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel, QtCore.Qt.Horizontal, self)
        buttons.accepted.connect(self.accept)
        buttons.rejected.connect(self.reject)
        layout.addWidget(buttons)

        self.validateCluster()

    def validateCluster(self):
        cnt = 0
        for l in self.lifeline:
            if self.editClusterName.text() in l.getClassName() and not l.getFlagCluster() and not l.getClusterLifeline():
                cnt += 1

        available_flag = True
        for l in self.lifeline:
            if self.editClusterName.text() in l.getClassName() and l.getFlagCluster():
                available_flag = False
                break

        if available_flag:
            self.validation_msg.setText("group name includes %d life-lines" % (cnt))
        else:
            self.validation_msg.setText("group name is not available")

    def getClusterText(self):
        return self.editClusterName.text()
    
    @staticmethod
    def getClusterName(lifelines, defaultName, parent = None):
        dialog = ClusterDialog(lifelines,defaultName,parent)
        result = dialog.exec_()
        return (result, dialog.getClusterText())

         
Ejemplo n.º 2
0
class ClusterDialog(QDialog):
    
    editClusterName = None
    def __init__(self, lifeline, defaultName, parent = None):
        super(ClusterDialog, self).__init__(parent)

        self.lifeline = lifeline
        layout = QVBoxLayout(self)

        message = QLabel('Enter group name')
        layout.addWidget(message)

        self.editClusterName = QLineEdit(defaultName)
        self.editClusterName.setFixedHeight(30)
        self.editClusterName.setFixedWidth(400)
        self.editClusterName.textChanged.connect(self.validateCluster)
        layout.addWidget(self.editClusterName)

        self.validation_msg = QLabel(' ')
        layout.addWidget(self.validation_msg)

        buttons = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel, QtCore.Qt.Horizontal, self)
        buttons.accepted.connect(self.accept)
        buttons.rejected.connect(self.reject)
        layout.addWidget(buttons)

        self.validateCluster()

    def validateCluster(self):
        cnt = 0
        for l in self.lifeline:
            if self.editClusterName.text() in l.getClassName() and not l.getFlagCluster() and not l.getClusterLifeline():
                cnt += 1

        available_flag = True
        for l in self.lifeline:
            if self.editClusterName.text() in l.getClassName() and l.getFlagCluster():
                available_flag = False
                break

        if available_flag:
            self.validation_msg.setText("group name includes %d life-lines" % (cnt))
        else:
            self.validation_msg.setText("group name is not available")

    def getClusterText(self):
        return self.editClusterName.text()
    
    @staticmethod
    def getClusterName(lifelines, defaultName, parent = None):
        dialog = ClusterDialog(lifelines,defaultName,parent)
        result = dialog.exec_()
        return (result, dialog.getClusterText())
Ejemplo n.º 3
0
class PyCalcUi(QMainWindow):
    """PyCalc's View (GUI)."""

    def __init__(self,
                 win_title: str = 'PyCalc',
                 win_size: Tuple[int, int] = (235, 235),
                 icon_path: Union[Path, str, None] = Path(R'.\coffeebean.ico')
                 ) -> None:
        """View initializer."""
        super().__init__()

        # Set some main window's properties
        self.setWindowTitle(win_title)
        self.setFixedSize(win_size[0], win_size[1])
        if isinstance(icon_path, Path):
            icon_path = str(icon_path.resolve())
        self.setWindowIcon(QIcon(icon_path))

        # Set the central widget
        self._centralWidget = QWidget(self)
        self.setCentralWidget(self._centralWidget)
        self.generalLayout = QVBoxLayout()
        self._centralWidget.setLayout(self.generalLayout)

        # Create the display and the buttons
        self._createDisplay()
        self._createButtons()

    def _createDisplay(self) -> None:
        """Create the display."""
        # Create the display widget
        self.display = QLineEdit()
        # Set some display's properties
        self.display.setFixedHeight(35)
        self.display.setAlignment(Qt.AlignRight)
        self.display.setReadOnly(True)
        # Add the display to the general layout
        self.generalLayout.addWidget(self.display)

    def _createButtons(self) -> None:
        """Create the buttons."""
        self.buttons: Dict[str, QPushButton] = {}
        buttonsLayout = QGridLayout()
        # Button text | position on the QGridLayout
        buttons: Dict[str, Tuple[int, int]] = {'7': (0, 0), '8': (0, 1), '9': (0, 2),
                                               '/': (0, 3),
                                               'C': (0, 4),
                                               '4': (1, 0), '5': (1, 1), '6': (1, 2),
                                               '*': (1, 3),
                                               '(': (1, 4),
                                               '1': (2, 0), '2': (2, 1), '3': (2, 2),
                                               '-': (2, 3),
                                               ')': (2, 4),
                                               '0': (3, 0), '00': (3, 1), '.': (3, 2),
                                               '+': (3, 3),
                                               '=': (3, 4),
                                               }
        # Create the buttons and add them to the grid layout
        for btnText, pos in buttons.items():
            self.buttons[btnText] = QPushButton(btnText)
            self.buttons[btnText].setFixedSize(40, 40)
            buttonsLayout.addWidget(self.buttons[btnText], pos[0], pos[1])
            # Add buttonsLayout to the general layout
            self.generalLayout.addLayout(buttonsLayout)

    def setDisplayText(self, text: str) -> None:
        """Set display's text."""
        self.display.setText(text)
        self.display.setFocus()

    def displayText(self) -> str:
        """Get display's text."""
        return cast(str, self.display.text())

    def clearDisplay(self) -> None:
        """Clear the display."""
        self.setDisplayText('')
Ejemplo n.º 4
0
class ParameterInteger(QWidget):
    def check_int(self, s):
        if s[0] in ("-", "+"):
            return s[1:].isdigit()
        return s.isdigit()

    def clamp(self, value, min_value, max_value):
        if value < min_value:
            return min_value
        elif value > max_value:
            return max_value
        else:
            return value

    def __init__(self,
                 parent=None,
                 value=0,
                 name="",
                 label_text="",
                 min_value=None,
                 max_value=None,
                 label_width=64,
                 height=22,
                 min_visible=0,
                 max_visible=10,
                 change_callback=None):
        QWidget.__init__(self, parent)

        self.VERTICAL_MARGIN = 0
        self.HORIZONTAL_MARGIN = 0

        self.name = name
        self.label_text = label_text
        self.min_value_raw = min_value
        self.max_value_raw = max_value
        self.min_value = min_value if min_value is not None else -sys.maxsize
        self.max_value = max_value if max_value is not None else sys.maxsize
        self.value = self.clamp(value, self.min_value, self.max_value)
        self.min_visible = max(self.min_value, min(min_visible, self.value))
        self.max_visible = min(self.max_value, max(max_visible, self.value))
        self._is_callback_define = False
        if change_callback is not None:
            self._change_callback = change_callback
            self._is_callback_define = True
        self._last_call = None

        self.label = QLabel(label_text)
        self.label.setFixedWidth(label_width)
        self.label.setFixedHeight(height)
        self.value_textbox = QLineEdit()
        self.value_textbox.setFixedWidth(52)
        self.value_textbox.setFixedHeight(height)
        self._update_value_label()
        self.slider = QSlider(Qt.Horizontal)
        self.slider.setFixedHeight(height)
        self._update_visible_interval()
        self.slider.setValue(value)
        layout = QHBoxLayout()
        layout.setContentsMargins(self.HORIZONTAL_MARGIN, self.VERTICAL_MARGIN,
                                  self.HORIZONTAL_MARGIN, self.VERTICAL_MARGIN)
        layout.addWidget(self.label)
        layout.addWidget(self.value_textbox)
        layout.addWidget(self.slider)
        self.setLayout(layout)

        self.slider.valueChanged.connect(self.slider_valueChanged)
        self.value_textbox.returnPressed.connect(self.textbox_enter)
        self.value_textbox.editingFinished.connect(self.textbox_enter)
        self.slider.sliderReleased.connect(self.slider_sliderReleased)

    def _update_visible_interval(self):
        self.slider.setRange(self.min_visible, self.max_visible)

    def _update_value_label(self):
        self.value_textbox.setText(str(self.value))

    def slider_valueChanged(self, value):
        self.value = value
        self._update_value_label()
        self.value_change()

    def slider_sliderReleased(self):
        self.try_change_visible(self.value)
        self.slider.setValue(self.value)

    def try_change_visible(self, new_value):
        delta = self.max_visible - self.min_visible
        # increase visible interval if new value out of the current
        if new_value <= self.min_visible:
            self.min_visible = max(self.min_value, new_value - delta)
        if new_value >= self.max_visible:
            self.max_visible = min(self.max_value, new_value + delta)
        self._update_visible_interval()

    def textbox_enter(self):
        text = self.value_textbox.text()
        # check is this text is integer
        if self.check_int(text):
            new_value = int(text)
            # clamp value
            if new_value < self.min_value:
                new_value = self.min_value
            if new_value > self.max_value:
                new_value = self.max_value
            self.try_change_visible(new_value)
            self.slider.setValue(new_value)
            self._update_value_label()
            self.value_change()
        else:
            self._update_value_label()
        self.value_textbox.clearFocus()

    def value_change(self):
        if self._is_callback_define:
            if self._last_call is None or self._last_call != self.value:
                self._last_call = self.value
                self._change_callback(param_name=self.name,
                                      param_value=self.value)
Ejemplo n.º 5
0
class PyCalcUi(QWidget):
    """PyCalc's View (GUI)."""

    def __init__(self,
                 parent: QWidget = None,
                 ) -> None:
        """View initializer."""
        super().__init__()

        self.setFixedSize(235, 235)

        self.generalLayout = QVBoxLayout()
        self.setLayout(self.generalLayout)
        # Create the display and the buttons
        self._createDisplay()
        self._createButtons()

        # Connect signals and slots
        self._connectSignals()

    def _createDisplay(self) -> None:
        """Create the display."""
        # Create the display widget
        self.display = QLineEdit()
        # Set some display's properties
        self.display.setFixedHeight(35)
        self.display.setAlignment(Qt.AlignRight)
        self.display.setReadOnly(True)
        # Add the display to the general layout
        self.generalLayout.addWidget(self.display)

    def _createButtons(self) -> None:
        """Create the buttons."""
        print("creating button")
        self.buttons: Dict[str, QPushButton] = {}
        buttonsLayout = QGridLayout()
        # Button text | position on the QGridLayout
        buttons: Dict[str, Tuple[int, int]] = {'7': (0, 0), '8': (0, 1), '9': (0, 2),
                                               '/': (0, 3),
                                               'C': (0, 4),
                                               '4': (1, 0), '5': (1, 1), '6': (1, 2),
                                               '*': (1, 3),
                                               '(': (1, 4),
                                               '1': (2, 0), '2': (2, 1), '3': (2, 2),
                                               '-': (2, 3),
                                               ')': (2, 4),
                                               '0': (3, 0), '00': (3, 1), '.': (3, 2),
                                               '+': (3, 3),
                                               '=': (3, 4),
                                               }
        # Create the buttons and add them to the grid layout
        for btnText, pos in buttons.items():
            self.buttons[btnText] = QPushButton(btnText)
            self.buttons[btnText].setFixedSize(40, 40)
            buttonsLayout.addWidget(self.buttons[btnText], pos[0], pos[1])
            # Add buttonsLayout to the general layout
            self.generalLayout.addLayout(buttonsLayout)

    def setDisplayText(self, text: str) -> None:
        """Set display's text."""
        self.display.setText(text)
        self.display.setFocus()

    def displayText(self) -> str:
        """Get display's text."""
        return cast(str, self.display.text())

    def clearDisplay(self) -> None:
        """Clear the display."""
        self.setDisplayText('')

    ERROR_MSG = 'ERROR'

    def _calculateResult(self) -> None:
        """Evaluate expressions."""
        result = self._evaluateExpression(self.displayText())
        self.setDisplayText(result)

    def _buildExpression(self, sub_exp: str) -> None:
        """Build expression."""
        if self.displayText() == self.ERROR_MSG:
            self.clearDisplay()

        expression = self.displayText() + sub_exp
        self.setDisplayText(expression)

    def _connectSignals(self) -> None:
        # Connect signals and slots.
        for btnText, btn in self.buttons.items():
            if btnText not in {'=', 'C'}:
                btn.clicked.connect(partial(self._buildExpression, btnText))

        self.buttons['='].clicked.connect(self._calculateResult)
        self.display.returnPressed.connect(self._calculateResult)
        self.buttons['C'].clicked.connect(self.clearDisplay)


    def _evaluateExpression(self, expression: str) -> str:
        """Evaluate an expression."""
        try:
            result = str(eval(expression, {}, {}))
        except Exception:
            result = PyCalcUi.ERROR_MSG
        finally:
            return result
Ejemplo n.º 6
0
class NewWindow(QMainWindow):
    def __init__(self):
        super(NewWindow, self).__init__()
        # def setupUi(self, NewWindow):

        self.latlong = "0"
        self.textEdit = QTextEdit()
        self.mainWidget = QWidget()

        self.mainLayout = QVBoxLayout()
        font0 = QFont("Arial", 12)
        font0.setBold(True)
        font01 = QFont("Arial", 12)
        font02 = QFont("Arial", 12)
        self.text1 = QLabel("<b>Domyślne Współrzędne:</b><br/>"
                            "Szerokość: 51° 06' 00''<br/>"
                            "Długość: 17° 01' 00''<br/>"
                            "(Współrzędne geograficzne Wrocławia)")
        self.solarpanelcordinates = QLabel('WSPÓŁRZĘDNE PANELU SŁONECZNEGO: ')
        self.solarpanelcordinates.setFont(font0)
        # self.solarpanelcordinates.setFrameStyle(QFrame.Box | QFrame.Sunken)
        # self.solarpanelcordinates.setMidLineWidth(6)
        self.text1.setFont(font01)
        self.text1.setFrameStyle(QFrame.Box | QFrame.Raised)
        self.text1.setMidLineWidth(6)
        self.result4 = QLabel('')
        self.result4.setFont(font02)
        self.result4.setMidLineWidth(3)
        self.result5 = QLabel('')
        self.result5.setFont(font02)
        self.result6 = QLabel('')
        self.result6.setFont(font02)
        self.result7 = QLabel('')
        self.result7.setFont(font02)
        self.result8 = QLabel('')
        self.result8.setFont(font02)
        self.result9 = QLabel('')
        self.result9.setFont(font02)
        self.mainLayout.addWidget(self.text1)
        self.mainLayout.addWidget(self.solarpanelcordinates)
        self.mainLayout.addWidget(self.result4)
        self.mainLayout.addWidget(self.result5)
        self.mainLayout.addWidget(self.result6)
        self.mainLayout.addWidget(self.result7)
        self.mainLayout.addWidget(self.result8)
        self.mainLayout.addWidget(self.result9)
        self.mainWidget.setLayout(self.mainLayout)
        self.setCentralWidget(self.mainWidget)

        #self.createActions()
        #self.createMenus()
        #self.createToolBars()
        #self.createStatusBar()
        self.createDockWindows()
        self.setWindowTitle("Nowe Okno")
        self.rad = 0
        self.o = 0
        self.timer = QTimer()
        self.timer.timeout.connect(self.dLocation)
        self.timerIsUp = False
        self.timer2 = QTimer()
        self.timer2.timeout.connect(self.update)
        self.timer2.start(1000)
        #self.newLetter()
        self.s = ephem.Sun()
        self.o = ephem.Observer()

    def createStatusBar(self):
        self.statusBar().showMessage("Gotowy")

    def dLocation(self):
        self.s = ephem.Sun()
        self.s.compute(epoch=ephem.now())
        if self.dateandtimeEdit.text():
            self.o.date = self.dateandtimeEdit.text()
        else:
            self.o.date = ephem.now()  # 00:22:07 EDT 06:22:07 UT+1
        self.s.compute(self.o)
        hour_angle = self.o.sidereal_time() - self.s.ra
        t = ephem.hours(hour_angle +
                        ephem.hours('12:00')).norm  # .norm for 0..24
        self.rad = str(ephem.hours(hour_angle + ephem.hours('12:00')).norm)
        # self.result.setText("R.A.: " + str(self.s.a_ra) + "                DEC.: " + str(self.s.a_dec))
        # self.result2.setText("HOUR ANGLE: " + str(self.rad) + " SIDERAL TIME: " + str(self.o.sidereal_time()))
        # self.result3.setText("SUN Altitude: " + str(self.s.alt) + "       SUN Azimuth: " + str(self.s.az))
        self.result4.setText("R.A.: " + str(self.s.a_ra))
        self.result5.setText("DEC.: " + str(self.s.a_dec))
        self.result6.setText("HOUR ANGLE: " + str(self.rad))
        self.result7.setText("SIDERAL TIME: " + str(self.o.sidereal_time()))
        self.result8.setText("SUN Altitude: " + str(self.s.alt))
        self.result9.setText("SUN Azimuth: " + str(self.s.az))

    def createDockWindows(self):
        dock = QDockWidget("Współrzędne Geograficzne Panelu: ", self)
        s = ephem.Sun()
        s.compute(epoch=ephem.now())
        dock.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
        self.multiWidget3 = QWidget()
        font5 = QFont("Arial", 12)
        font6 = QFont("Arial", 17)
        self.vLayout3 = QGridLayout()
        self.result = QLabel(self.latlong)
        self.latitude = QLabel('Szerokość')
        self.longitude = QLabel('Długość')
        self.dateandtime = QLabel('Data i Czas')
        self.solarpanelcor = QLabel('WSPÓŁRZĘDNE PANELU SŁONECZNEGO: ')
        self.latitudeEdit = QLineEdit()
        self.latitudeEdit.setFixedHeight(28)
        self.latitudeEdit.setFixedWidth(386)
        self.latitudeEdit.setStatusTip(
            "Wprowadzona szerokość powinna być w stopniach dziesiętnych (np.: 51.100000)"
        )
        self.longitudeEdit = QLineEdit()
        self.longitudeEdit.setFixedHeight(28)
        self.longitudeEdit.setFixedWidth(386)
        self.longitudeEdit.setStatusTip(
            "Wprowadzona długość powinna być w stopniach dziesiętnych (np.: 17.03333)"
        )
        self.dateandtimeEdit = QLineEdit()
        self.dateandtimeEdit.setFixedHeight(28)
        self.dateandtimeEdit.setFixedWidth(386)
        self.dateandtimeEdit.setStatusTip(
            "Wprowadzona data powinna być w formacie: rok/mies/dzień<spacja>godz:min:sek (np.: 2022/12/4 8:12:7)"
        )
        self.button = QPushButton('Wylicz współrzędne / Przerwij liczenie',
                                  self)
        self.button.clicked.connect(self.handleButton3)
        self.latitude.setFont(font5)
        self.longitude.setFont(font5)
        self.dateandtime.setFont(font5)
        self.button.setFont(font6)
        self.button.setStatusTip("Rozpoczyna Obliczenia")
        self.vLayout3.addWidget(self.latitude)
        self.vLayout3.addWidget(self.latitudeEdit)
        self.vLayout3.addWidget(self.longitude)
        self.vLayout3.addWidget(self.longitudeEdit)
        self.vLayout3.addWidget(self.dateandtime)
        self.vLayout3.addWidget(self.dateandtimeEdit)
        self.vLayout3.addWidget(self.button)
        self.multiWidget3.setLayout(self.vLayout3)
        dock.setWidget(self.multiWidget3)
        self.addDockWidget(Qt.RightDockWidgetArea, dock)
        # self.viewMenu.addAction(dock.toggleViewAction())

    def handleButton3(self):
        self.button.setStatusTip("Przerywa liczenie")
        if self.timerIsUp == False:
            if self.latitudeEdit.text() and self.longitudeEdit.text():
                self.o.lat = self.latitudeEdit.text()
                self.o.lon = self.longitudeEdit.text()
            else:
                self.o.lon, self.o.lat = '17.03333', '51.100000'  # Współrzędne Wrocławia
            self.timer.start(1000)
            self.timerIsUp = True
        else:
            self.timer.stop()
            self.timerIsUp = False
            self.button.setStatusTip("Rozpoczyna Obliczenia")
Ejemplo n.º 7
0
class NewWindow2(QMainWindow):
    def __init__(self):
        super(NewWindow2, self).__init__()

        self.latlong = "0"
        self.textEdit = QTextEdit()
        self.mainWidget = QWidget()
        self.mainLayout = QVBoxLayout()
        font0 = QFont("Arial", 12)
        font0.setBold(True)
        font01 = QFont("Arial", 12)
        font02 = QFont("Arial", 12)
        self.text1 = QLabel("<b>Domyślne Współrzędne:</b><br/>"
                            "Szerokość: 51° 06' 00''<br/>"
                            "Długość: 17° 01' 00''<br/>"
                            "(Współrzędne geograficzne Wrocławia)")
        self.solarpanelcordinates = QLabel('WSPÓŁRZĘDNE PANELU SŁONECZNEGO: ')
        self.solarpanelcordinates.setFont(font0)
        # self.solarpanelcordinates.setFrameStyle(QFrame.Box | QFrame.Sunken)
        # self.solarpanelcordinates.setMidLineWidth(6)
        #self.text1.setAlignment(QtCore.Qt.AlignRight | QtCore.Qt.AlignVCenter)
        self.text1.setAlignment(Qt.AlignHCenter | Qt.AlignVCenter)
        self.text1.setFont(font01)
        self.text1.setFrameStyle(QFrame.Box | QFrame.Raised)
        self.text1.setMidLineWidth(6)
        self.result4 = QLabel('')
        self.result4.setFont(font02)
        self.result4.setMidLineWidth(3)
        self.result5 = QLabel('')
        self.result5.setFont(font02)
        self.result6 = QLabel('')
        self.result6.setFont(font02)
        self.result7 = QLabel('')
        self.result7.setFont(font02)
        self.result8 = QLabel('')
        self.result8.setFont(font02)
        self.result9 = QLabel('')
        self.result9.setFont(font02)
        self.mainLayout.addWidget(self.text1)
        self.mainLayout.addWidget(self.solarpanelcordinates)
        self.mainLayout.addWidget(self.result4)
        self.mainLayout.addWidget(self.result5)
        self.mainLayout.addWidget(self.result6)
        self.mainLayout.addWidget(self.result7)
        self.mainLayout.addWidget(self.result8)
        self.mainLayout.addWidget(self.result9)
        self.mainWidget.setLayout(self.mainLayout)
        self.setCentralWidget(self.mainWidget)

        self.createActions()
        self.createMenus()
        #self.createToolBars()
        self.createStatusBar()
        self.createDockWindows()
        self.setWindowTitle("Nowe Okno")
        self.rad = 0
        self.o = 0
        self.timer = QTimer()
        self.timer.timeout.connect(self.dLocation)
        self.timerIsUp = False
        self.timer2 = QTimer()
        self.timer2.timeout.connect(self.update)
        self.timer2.start(1000)
        self.newLetter()
        self.s = ephem.Sun()
        self.o = ephem.Observer()
        # zmienna = []
        # i=0
        # with open('Breslau.txt', 'r') as f:
        #     for line in f:
        #         zmienna.append(line)
        #         i=i+1
        #     print(zmienna)
        #     f = self.nameEdit.text()
        #     f = self.latitudeEdit.text()
        #     f = self.longitudeEdit.text()
        #     f = self.dateandtimeEdit.text()
        #     print(self.nameEdit.text())
        #     print(self.latitudeEdit.text())
        #     print(self.longitudeEdit.text())
        #     print(self.dateandtimeEdit.text())

# class MainWindow(QMainWindow):
#     def __init__(self):
#         super(MainWindow, self).__init__()
#
#         self.latlong = "0"
#         self.textEdit = QTextEdit()
#         self.setCentralWidget(self.textEdit)
#         self.createActions()
#         self.createMenus()
#         #self.createToolBars()
#         self.createStatusBar()
#         self.createDockWindows()
#         self.setWindowTitle("Panel Słoneczny")
#         self.rad = 0
#         self.o = 0
#         self.timer = QTimer()
#         self.timer.timeout.connect(self.dLocation)
#         self.timerIsUp = False
#         self.timer2 = QTimer()
#         self.timer2.timeout.connect(self.update)
#         self.timer2.start(1000)
#         self.newLetter()
#         self.s = ephem.Sun()
#         self.o = ephem.Observer()

    def newWindow(self):
        self.newWin = NewWindow()
        self.newWin.show()

    def newWindow2(self):
        self.newWin2 = NewWindow2()
        self.newWin2.show()

    def newLetter(self):

        self.textEdit.clear()
        self.text2 = QLabel("<b>Domyślne Współrzędne:</b><br/>"
                            "Szerokość: 51° 06' 00''<br/>"
                            "Długość: 17° 01' 00''<br/>"
                            "(Współrzędne geograficzne Wrocławia)")

        cursor = self.textEdit.textCursor()
        cursor.movePosition(QTextCursor.Start)
        topFrame = cursor.currentFrame()
        topFrameFormat = topFrame.frameFormat()
        topFrameFormat.setPadding(16)
        topFrame.setFrameFormat(topFrameFormat)
        textFormat = QTextCharFormat()
        boldFormat = QTextCharFormat()
        boldFormat.setFontWeight(QFont.Bold)
        italicFormat = QTextCharFormat()
        italicFormat.setFontItalic(True)

        tableFormat = QTextTableFormat()
        tableFormat.setBorder(1)
        tableFormat.setCellPadding(16)
        tableFormat.setAlignment(Qt.AlignRight)
        cursor.insertTable(1, 1, tableFormat)
        cursor.insertText("Domyślne Współrzędne: ", boldFormat)
        self.text2.setText(self.nameEdit.text())
        cursor.insertText
        #self.text1.setText(self.nameEdit.text())
        cursor.insertBlock()
        cursor.insertBlock()
        cursor.insertText("Szerokość: 51° 06' 00''", textFormat)
        cursor.insertBlock()
        cursor.insertBlock()
        cursor.insertText("Długość: 17° 01' 00''")
        cursor.insertBlock()
        cursor.insertBlock()
        cursor.insertText("(Współrzędne geograficzne Wrocławia)")
        cursor.setPosition(topFrame.lastPosition())
#         cursor.insertText(QDate.currentDate().toString("Dziś jest: d MMMM yyyy:"),
#                 textFormat)
#         cursor.insertText(QTime.currentTime().toString("  hh:mm:ss"), textFormat)
# #        cursor.insertText(QTimer.timer("  hh:mm:ss", 1000), textFormat)
#         cursor.insertBlock()
#         cursor.insertBlock()
#         cursor.insertText("Wrocław: ", textFormat)
#         cursor.insertText("17.03 deg; 51.10 deg", textFormat)
#         cursor.insertText(",", textFormat)
#         for i in range(3):
#             cursor.insertBlock()
#         cursor.insertText("Text", textFormat)

    def dLocation(self):
        self.s = ephem.Sun()
        self.s.compute(epoch=ephem.now())
        if self.nameEdit.text():
            self.text1.setText(self.nameEdit.text())
            font03 = QFont("Arial", 16)
            font03.setBold(True)
            self.text1.setFont(font03)
            if not self.dateandtimeEdit.text():
                self.o.date = ephem.now()  # 00:22:07 EDT 06:22:07 UT+1
        else:
            if self.dateandtimeEdit.text():
                self.o.date = self.dateandtimeEdit.text()
                self.text1.setText("<b>Obliczenia dla:</b><br/> " +
                                   self.dateandtimeEdit.text())
                font03 = QFont("Arial", 16)
                font03.setBold(True)
                self.text1.setFont(font03)
            else:
                self.o.date = ephem.now()  # 00:22:07 EDT 06:22:07 UT+1
        #self.o.date = ephem.now()  # 00:22:07 EDT 06:22:07 UT+1
        self.s.compute(self.o)
        hour_angle = self.o.sidereal_time() - self.s.ra
        t = ephem.hours(hour_angle +
                        ephem.hours('12:00')).norm  # .norm for 0..24
        self.rad = str(ephem.hours(hour_angle + ephem.hours('12:00')).norm)
        # self.result.setText("R.A.: " + str(self.s.a_ra) + "                DEC.: " + str(self.s.a_dec))
        # self.result2.setText("HOUR ANGLE: " + str(self.rad) + " SIDERAL TIME: " + str(self.o.sidereal_time()))
        # self.result3.setText("SUN Altitude: " + str(self.s.alt) + "       SUN Azimuth: " + str(self.s.az))
        self.result4.setText("R.A.: " + str(self.s.a_ra))
        self.result5.setText("DEC.: " + str(self.s.a_dec))
        self.result6.setText("HOUR ANGLE: " + str(self.rad))
        self.result7.setText("SIDERAL TIME: " + str(self.o.sidereal_time()))
        self.result8.setText("SUN Altitude: " + str(self.s.alt))
        self.result9.setText("SUN Azimuth: " + str(self.s.az))

    def update(self):
        time = QTime.currentTime()
        self.clock.setText(QTime.currentTime().toString("hh:mm:ss"))

    def about(self):
        QMessageBox.about(
            self, "O Programie",
            "<p align=justify>Program <b><i>''Panel Słoneczny''</b></i> pozwala na wyliczenie współrzędnych Słońca, "
            "na podstawie których należy ustawić Panel. Domyślnie program startuje dla "
            "szerokości i&nbsp;długości geograficznej Wrocławia z obecną dla użytkownika datą i godziną. "
            "Użytkownik może podać swoją szerokość i długość geograficzną oraz swój czas i datę wpisując "
            "w odpowiednie pola swoje dane. W polach Szerokość i Długość należy podać w stopniach dziesiętnych "
            "W polu ''Data i Czas'' własne dane należy wpisywać zgodnie ze schematem: "
            "rok/mies/dzień godz:min:sek (np.: 2019/02/04 14:02:03). Pisanie zer przed godzinami, minutami i sekundami "
            "dla liczb poniżej dziesięciu nie jest wymagane (2019/02/04 14:02:03 = 2019/2/4 14:2:3)<p/>"
        )

    def about2(self):
        QMessageBox.about(
            self, "Symbole i skróty",
            "<p align=justify><b><i>Rektascensja (R.A.)</b></i> – (Right Ascension; wznoszenie proste) jest kątem dwuściennym "
            "pomiędzy płaszczyzną koła godzinnego przechodzącego przez punkt Barana, a&nbsp;płaszczyzną koła godzinnego "
            "danego ciała niebieskiego). <br/>"
            "<b><i>Deklinacja (DEC.)</b></i> - kąt zawarty między płaszczyzną równika niebieskiego,"
            "a prostą łączącą punkt na sferze niebieskiej, a środkiem sfery niebieskiej. "
            "Deklinacja zmienia się w zakresie od 90° (biegun północny) przez 0° (równik niebieski) do -90° (biegun południowy).<br/> "
            "<b><i>Kąt Godzinny (HOUR ANGLE)</b></i> - kąt dwuścienny zawarty pomiędzy płaszczyzną lokalnego południka "
            "i płaszczyzną koła godzinnego danego obiektu. Kąt godzinny odmierza się w kierunku zgodnym "
            "z dziennym ruchem sfery niebieskiej, a przyjmuje on wartości (0h,24h) lub (0°,360°) "
            "Kąt godzinny zależy od miejsca obserwacji (ulokowania panela) i od lokalnego czasu.<br/> "
            "<b><i>Czas Gwiazdowy (SIDERAL TIME)</b></i> - czyli kąt godzinny punktu Barana. ( Jeden z&nbsp;dwóch punktów "
            "przecięcia się ekliptyki z równikiem niebieskim. Moment przejścia Słońca przez punkt Barana "
            "oznacza początek astronomicznej wiosny na półkuli północnej. Dlatego nazywany jest także punktem "
            "równonocy wiosennej.)<br/> "
            "<b><i>Wysokość Słońca (nad horyzontem; SUN Altitude)</b></i> - na daną chwilę wyliczona wysokość Słońca, "
            "jeżeli jest ujemna to znaczy, że słońce jest pod horyzontem.<br/> "
            "<b><i>Azymut Słońca (SUN Azimuth)</b></i> - kąt dwuścienny, w programie liczy się w kierunku na wschód "
            "(stojąc twarzą do północy w prawo; w Astronomii jest tak samo, tzn. w prawo, ale zaczyna od południka)."
            "Azymut geograficzny i astronomiczny różni się o 180°.<p/> ")

    def createActions(self):
        # self.newLetterAct = QAction(QIcon.fromTheme('document-new', QIcon(':/images/new.png')), "&New Letter",
        #         self, shortcut=QKeySequence.New,
        #         statusTip="Create a new form letter", triggered=self.newLetter())

        self.newWindowAct = QAction(QIcon.fromTheme('document-new',
                                                    QIcon(':/images/new.png')),
                                    "&Nowe Okno",
                                    self,
                                    shortcut=QKeySequence.New,
                                    statusTip="Create a new form letter",
                                    triggered=self.newWindow2)
        self.saveAct = QAction(QIcon.fromTheme('document-save',
                                               QIcon(':/images/save.png')),
                               "&Zapisz",
                               self,
                               shortcut=QKeySequence.Save,
                               statusTip="Zapisz obecne współrzędne",
                               triggered=self.save)
        self.loadAct = QAction(QtGui.QIcon(':/images/open.png'),
                               "&Wczytaj",
                               self,
                               shortcut=QtGui.QKeySequence.Open,
                               statusTip="Wczytaj współrzędne z pliku",
                               triggered=self.load)
        self.aboutAct = QAction("&O Programie",
                                self,
                                statusTip="Pokazuje pomoc dla programu",
                                triggered=self.about)
        self.aboutAct2 = QAction(
            "&Symbole i skróty",
            self,
            statusTip=
            "Pokazuje objaśnienia używanych w programie skrótów i symboli",
            triggered=self.about2)
        self.quitAct = QAction("&Zamknij",
                               self,
                               shortcut="Ctrl+Q",
                               statusTip="Zamyka aplikację",
                               triggered=self.close)
        self.DefaultAct = QAction(
            QIcon.fromTheme('document-default', QIcon(':/images/def.png')),
            "&Rozpocznij dla domyślnej lokacji",
            self,
            statusTip="Rozpoczyna obliczenia dla domyślnej lokacji (Wrocław)",
            triggered=self.handleButton2)

    def createToolBars(self):
        self.fileToolBar = self.addToolBar("File")
        self.fileToolBar.addAction(self.newLetterAct)

    def createMenus(self):
        self.fileMenu = self.menuBar().addMenu("&Plik")
        self.fileMenu.addAction(self.newWindowAct)
        self.fileMenu.addAction(self.saveAct)
        self.fileMenu.addAction(self.loadAct)
        self.fileMenu.addAction(self.DefaultAct)
        self.fileMenu.addSeparator()
        self.fileMenu.addAction(self.quitAct)
        self.fileMenu.addSeparator()
        self.editMenu = self.menuBar().addMenu("&Edycja")
        self.viewMenu = self.menuBar().addMenu("&Widok")
        self.menuBar().addSeparator()
        self.helpMenu = self.menuBar().addMenu("&Pomoc")
        self.helpMenu.addAction(self.aboutAct)
        self.helpMenu.addAction(self.aboutAct2)

    def createStatusBar(self):
        self.statusBar().showMessage("Gotowy", 3000)

    def saving(self):
        cursor = self.textEdit.textCursor()
        self.nameEdit.text()
        cursor.insertBlock()
        self.latitudeEdit.text()
        cursor.insertBlock()
        self.longitudeEdit.text()
        cursor.insertBlock()
        self.dateandtimeEdit.text()

    def save(self):
        filename, _ = QFileDialog.getSaveFileName(self, "Zapisywanie jako",
                                                  '.',
                                                  "Dokumenty textowe(*.txt)")
        if not filename:
            return

        file = QFile(filename)
        if not file.open(QFile.WriteOnly | QFile.Text):
            QMessageBox.warning(
                self, "Panel Słoneczny", "nie mógł zapisać pliku %s:\n%s." %
                (filename, file.errorString()))
            return

        out = QTextStream(file)
        #QApplication.setOverrideCursor(Qt.WaitCursor)
        #out << self.textEdit.toPlainText()
        out << self.nameEdit.text() + "\n" + self.latitudeEdit.text(
        ) + "\n" + self.longitudeEdit.text(
        ) + "\n" + self.dateandtimeEdit.text()
        #out << "self.text1.setText("+self.nameEdit.text()+")"
        #QApplication.restoreOverrideCursor()

        self.statusBar().showMessage("Zapisano w '%s'" % filename, 2000)

    def load(self):
        filename, _ = QFileDialog.getOpenFileName(self)

        if not filename:
            return

        file = QFile(filename)
        if not file.open(QFile.ReadOnly | QFile.Text):
            QMessageBox.warning(
                self, "Panel Słoneczny", "nie mógł wczytać pliku %s:\n%s." %
                (filename, file.errorString()))
            return

        inf = QTextStream(file)
        #QApplication.setOverrideCursor(QtCore.Qt.WaitCursor)
        self.textEdit.setPlainText(inf.readAll())
        #with open(file, 'r') as input:
        with open('Breslau.txt', 'r') as f:
            # f = self.nameEdit.text()
            # f = self.latitudeEdit.text()
            # f = self.longitudeEdit.text()
            # f = self.dateandtimeEdit.text()
            # print(self.nameEdit.text())
            # print(self.latitudeEdit.text())
            # print(self.longitudeEdit.text())
            # print(self.dateandtimeEdit.text())
            # for line in f:
            #      print (line, end='')
            f_name = f.readline()
            #f_name = self.nameEdit.text()
            self.text1.setText(f_name)
            f_lat = f.readline()
            f_lat = self.latitudeEdit.text()
            f_lon = f.readline()
            f_lon = self.longitudeEdit.text()
            f_dnt = f.readline()
            f_dnt = self.dateandtimeEdit.text()

            # for line in f:
            #     if 'name' in line:
            #         self.text1.setText(line)
            #if 'lat' in line:

        #self.text1.setText(self.textEdit.setPlainText(inf.readAll()))
        #self.text1.setText(self.nameEdit.text())

        #QApplication.restoreOverrideCursor()

        #self.setCurrentFile(filename)

        self.statusBar().showMessage("Wczytano plik", 2000)

    def createDockWindows(self):
        # dock = QDockWidget('n', self)
        # dock.setFeatures(dock.NoDockWidgetFeatures)
        # dock.DockWidgetMovable = False
        # dock.setAllowedAreas(Qt.TopDockWidgetArea)
        # self.addDockWidget(Qt.TopDockWidgetArea, dock)

        dock = QDockWidget("Program", self)
        dock.setFeatures(dock.NoDockWidgetFeatures)
        dock.DockWidgetMovable = False
        dock.setAllowedAreas(Qt.LeftDockWidgetArea)
        self.multiWidget = QWidget()
        font1 = QFont("Courier New", 10)
        self.title = QLabel("SOLAR PANEL Program")
        font2 = QFont("Courier New", 10)
        font2.setBold(True)
        self.author = QLabel("Tomasz Dróżdż")
        self.author.setFont(font2)
        self.other = QLabel("Politechnika Wrocławska")
        self.other2 = QLabel("Automatyka i Robotyka")
        self.vLayout = QVBoxLayout()
        self.vLayout.addWidget(self.title)
        self.vLayout.addWidget(self.author)
        self.vLayout.addWidget(self.other)
        self.vLayout.addWidget(self.other2)
        self.multiWidget.setLayout(self.vLayout)
        dock.setWidget(self.multiWidget)
        self.addDockWidget(Qt.LeftDockWidgetArea, dock)

        dock = QDockWidget("Zegar", self)
        dock.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
        self.multiWidget2 = QWidget()
        font3 = QFont("Arial", 13)
        font4 = QFont("Arial", 20)
        self.date = QLabel(QDate.currentDate().toString("d MMMM yyyy:  "))
        self.clock = QLabel(QTime.currentTime().toString("hh:mm:ss"))
        self.date.setFont(font3)
        self.clock.setFont(font4)
        font4.setBold(True)
        self.vLayout2 = QVBoxLayout()
        self.vLayout2.addWidget(self.date)
        self.vLayout2.addWidget(self.clock)
        self.multiWidget2.setLayout(self.vLayout2)
        dock.setWidget(self.multiWidget2)
        self.addDockWidget(Qt.LeftDockWidgetArea, dock)
        self.viewMenu.addAction(dock.toggleViewAction())

        dock = QDockWidget("Współrzędne Geograficzne Panelu: ", self)
        s = ephem.Sun()
        s.compute(epoch=ephem.now())
        dock.setAllowedAreas(Qt.LeftDockWidgetArea | Qt.RightDockWidgetArea)
        self.multiWidget3 = QWidget()
        font5 = QFont("Arial", 12)
        font6 = QFont("Arial", 17)
        self.vLayout3 = QGridLayout()
        self.result = QLabel(self.latlong)
        self.name = QLabel('Nazwa')
        self.latitude = QLabel('Szerokość')
        self.longitude = QLabel('Długość')
        self.dateandtime = QLabel('Data i Czas')
        # self.result = QLabel('')
        # self.result2 = QLabel('')
        # self.result3 = QLabel('')
        self.solarpanelcor = QLabel('WSPÓŁRZĘDNE PANELU SŁONECZNEGO: ')
        self.nameEdit = QLineEdit()
        self.nameEdit.setFixedHeight(28)
        self.nameEdit.setFixedWidth(386)
        self.nameEdit.setStatusTip(
            "Wprowadź nazwę dla konfiguracji współrzędnych i czasu")
        self.latitudeEdit = QLineEdit()
        self.latitudeEdit.setFixedHeight(28)
        self.latitudeEdit.setFixedWidth(386)
        self.latitudeEdit.setStatusTip(
            "Wprowadzona szerokość powinna być w stopniach dziesiętnych (np.: 51.100000)"
        )
        self.longitudeEdit = QLineEdit()
        self.longitudeEdit.setFixedHeight(28)
        self.longitudeEdit.setFixedWidth(386)
        self.longitudeEdit.setStatusTip(
            "Wprowadzona długość powinna być w stopniach dziesiętnych (np.: 17.03333)"
        )
        self.dateandtimeEdit = QLineEdit()
        self.dateandtimeEdit.setFixedHeight(28)
        self.dateandtimeEdit.setFixedWidth(386)
        self.dateandtimeEdit.setStatusTip(
            "Wprowadzona data powinna być w formacie: rok/mies/dzień<spacja>godz:min:sek (np.: 2022/12/4 8:12:7)"
        )
        self.button = QPushButton('Wylicz współrzędne / Przerwij liczenie',
                                  self)
        self.button.clicked.connect(self.handleButton4)
        self.name.setFont(font5)
        self.latitude.setFont(font5)
        self.longitude.setFont(font5)
        self.dateandtime.setFont(font5)
        self.button.setFont(font6)
        self.button.setStatusTip("Rozpoczyna Obliczenia")
        # self.button.addAction(self.buttonAct)
        # self.solarpanelcor.setFont(font5)
        # self.result.setFont(font6)
        # self.result2.setFont(font6)
        # self.result3.setFont(font6)
        self.vLayout3.addWidget(self.name)
        self.vLayout3.addWidget(self.nameEdit)
        self.vLayout3.addWidget(self.latitude)
        self.vLayout3.addWidget(self.latitudeEdit)
        self.vLayout3.addWidget(self.longitude)
        self.vLayout3.addWidget(self.longitudeEdit)
        self.vLayout3.addWidget(self.dateandtime)
        self.vLayout3.addWidget(self.dateandtimeEdit)
        self.vLayout3.addWidget(self.button)
        # self.vLayout3.addWidget(self.solarpanelcor)
        # self.vLayout3.addWidget(self.result)
        # self.vLayout3.addWidget(self.result2)
        # self.vLayout3.addWidget(self.result3)
        self.multiWidget3.setLayout(self.vLayout3)
        dock.setWidget(self.multiWidget3)
        self.addDockWidget(Qt.RightDockWidgetArea, dock)
        self.viewMenu.addAction(dock.toggleViewAction())

    def handleButton2(self):
        self.button.setStatusTip("Przerywa liczenie")
        if self.timerIsUp == False:
            self.o.lon, self.o.lat = '17.03333', '51.100000'  # Współrzędne Wrocławia
            self.text1.setText("Wrocław")
            font03 = QFont("Arial", 16)
            font03.setBold(True)
            self.text1.setFont(font03)
            self.timer.start(1000)
            self.timerIsUp = True
        else:
            self.timer.stop()
            self.timerIsUp = False
            self.button.setStatusTip("Rozpoczyna Obliczenia")

    # def handleButton2(self):
    #     print(self.nameEdit.text())
    #     print(self.latitudeEdit.text())
    #     print(self.longitudeEdit.text())
    #     print(self.dateandtimeEdit.text())

    def handleButton3(self):
        self.button.setStatusTip("Przerywa liczenie")
        if self.timerIsUp == False:
            if self.latitudeEdit.text() and self.longitudeEdit.text():
                self.o.lat = self.latitudeEdit.text()
                self.o.lon = self.longitudeEdit.text()
            if self.nameEdit.text():
                self.text1.setText(self.nameEdit.text())
                font03 = QFont("Arial", 16)
                font03.setBold(True)
                self.text1.setFont(font03)
            else:
                self.text1.setText("Wrocław")
                font03 = QFont("Arial", 16)
                font03.setBold(True)
                self.text1.setFont(font03)
                self.o.lon, self.o.lat = '17.03333', '51.100000'  # Współrzędne Wrocławia
            self.timer.start(1000)
            self.timerIsUp = True
        else:
            self.timer.stop()
            self.timerIsUp = False
            self.button.setStatusTip("Rozpoczyna Obliczenia")

    def handleButton4(self):
        self.button.setStatusTip("Przerywa liczenie")
        if self.timerIsUp == False:
            #zastąpic wlasna logika
            # if self.latitudeEdit.text() and self.longitudeEdit.text():
            #     self.o.lat = self.latitudeEdit.text()
            #     self.o.lon = self.longitudeEdit.text()
            if self.nameEdit.text():
                self.text1.setText(self.nameEdit.text())
                font03 = QFont("Arial", 16)
                font03.setBold(True)
                self.text1.setFont(font03)
            else:
                if self.latitudeEdit.text() and self.longitudeEdit.text():
                    self.o.lat = self.latitudeEdit.text()
                    self.o.lon = self.longitudeEdit.text()
                    self.text1.setText("<b>Obliczenia dla:</b><br/> " +
                                       "Szerokość: " +
                                       self.latitudeEdit.text() + "°" + "  " +
                                       "Długość: " +
                                       self.longitudeEdit.text() + "°")
                    font03 = QFont("Arial", 16)
                    #font03.setBold(True)
                    self.text1.setFont(font03)
                else:
                    self.text1.setText("Wrocław")
                    font03 = QFont("Arial", 16)
                    font03.setBold(True)
                    self.text1.setFont(font03)
                    self.o.lon, self.o.lat = '17.03333', '51.100000'  # Współrzędne Wrocławia
            self.timer.start(1000)
            self.timerIsUp = True
        else:
            self.timer.stop()
            self.timerIsUp = False
            self.button.setStatusTip("Rozpoczyna Obliczenia")
class Calculator(QMainWindow):
    def __init__(self):
        super(Calculator, self).__init__()
        self.setWindowTitle("Calculator")
        self.setWindowIcon(QIcon('arti.PNG'))
        self.setFont(QFont('Roboto', 12))
        palette = QPalette()
        palette.setColor(palette.Window, QColor('#000000'))
        palette.setColor(palette.WindowText, QColor('#FFFFFF'))
        self.setPalette(palette)
        self.setGeometry(300, 300, 300, 300)
        self.generalLayout = QVBoxLayout()
        self._centralWidget = QWidget(self)
        self.setCentralWidget(self._centralWidget)
        self._centralWidget.setLayout(self.generalLayout)
        self._createDisplay()
        self._createButtons()

    def _createDisplay(self):
        self.display = QLineEdit()
        self.display.setFixedHeight(45)
        self.display.setAlignment(Qt.AlignRight)
        self.display.setReadOnly(True)
        self.generalLayout.addWidget(self.display)

    def _createButtons(self):
        self.buttons = {}
        buttons_layout = QGridLayout()
        buttons = {
            "7": (0, 0),
            "8": (0, 1),
            "9": (0, 2),
            "/": (0, 3),
            "C": (0, 4),
            "4": (1, 0),
            "5": (1, 1),
            "6": (1, 2),
            "*": (1, 3),
            "(": (1, 4),
            "1": (2, 0),
            "2": (2, 1),
            "3": (2, 2),
            "-": (2, 3),
            ")": (2, 4),
            "0": (3, 0),
            "00": (3, 1),
            ".": (3, 2),
            "+": (3, 3),
            "=": (3, 4),
        }
        for btnText, pos in buttons.items():
            self.buttons[btnText] = QPushButton(btnText)
            self.buttons[btnText].setFixedSize(40, 40)
            buttons_layout.addWidget(self.buttons[btnText], pos[0], pos[1])
        self.generalLayout.addLayout(buttons_layout)

    def setDisplayText(self, text):
        self.display.setText(text)
        self.display.setFocus()

    def displayText(self):
        return self.display.text()

    def clearDisplay(self):
        self.setDisplayText("")
Ejemplo n.º 9
0
class Window(QWidget):
    def __init__(self, parent=None):
        super().__init__(parent)
        self.setFont(QFont("Berlin Sans FB", 10))
        self.setWindowTitle("File ENC")
        self.setFixedSize(500, 220)

        self.btn_src = QPushButton("browse")
        self.btn_dst = QPushButton("browse")
        self.btn_enc = QPushButton("Encrypt")
        self.btn_dec = QPushButton("Decrypt")
        self.btn_src.setFixedSize(60, WIDGET_HEIGHT)
        self.btn_dst.setFixedSize(60, WIDGET_HEIGHT)
        self.btn_src.clicked.connect(self.open_file_dialog)
        self.btn_dst.clicked.connect(self.open_dir_dialog)
        self.btn_enc.clicked.connect(self.encrypt_file)
        self.btn_dec.clicked.connect(self.decrypt_file)

        self.LE_file_path = QLineEdit()
        self.LE_file_path.setPlaceholderText("Source File Path...")
        self.LE_file_path.setFixedHeight(WIDGET_HEIGHT)
        self.LE_file_path.setReadOnly(True)

        self.LE_dir_path = QLineEdit()
        self.LE_dir_path.setPlaceholderText("Destination Path...")
        self.LE_dir_path.setFixedHeight(WIDGET_HEIGHT)
        self.LE_dir_path.setReadOnly(True)

        self.LE_key = QLineEdit()
        self.LE_key.setPlaceholderText("Enter the Cipher Key...")
        self.LE_key.setFixedHeight(WIDGET_HEIGHT)

        layout = QGridLayout()
        layout.setRowMinimumHeight(0, 30)
        layout.addWidget(self.btn_src, 0, 1)
        layout.addWidget(self.btn_dst, 1, 1)
        layout.addWidget(self.btn_enc, 3, 0, 1, 2, alignment=Qt.AlignHCenter)
        layout.addWidget(self.btn_dec, 4, 0, 1, 2, alignment=Qt.AlignHCenter)
        layout.addWidget(self.LE_file_path, 0, 0)
        layout.addWidget(self.LE_dir_path, 1, 0)
        layout.addWidget(self.LE_key, 2, 0, 1, 2)
        layout.setHorizontalSpacing(10)
        layout.setHorizontalSpacing(0)
        print(layout.rowStretch(0))
        self.setLayout(layout)
        self.show()

    def open_file_dialog(self):
        fname = QFileDialog.getOpenFileName(self, "Select File")
        self.LE_file_path.setText(fname[0])

    def open_dir_dialog(self):
        file = QFileDialog.getExistingDirectory(self, "Select Directory")
        self.LE_dir_path.setText(file)

    def encrypt_file(self):
        cipher = Fernet(self.LE_key.text())
        with open(self.LE_file_path.text(), 'rb') as f:
            data = f.read()
        with open(
                f"{self.LE_dir_path.text()}\\enc_{os.path.basename(self.LE_file_path.text())}",
                'wb') as f:
            f.write(cipher.encrypt(data))

    def decrypt_file(self):
        cipher = Fernet(self.LE_key.text())
        with open(self.LE_file_path.text(), 'rb') as f:
            data = f.read()
        with open(
                f"{self.LE_dir_path.text()}\\dec_{os.path.basename(self.LE_file_path.text())}",
                'wb') as f:
            f.write(cipher.decrypt(data))
Ejemplo n.º 10
0
class WidgetConfig(QWidget):
    def __init__(self):
        super(WidgetConfig, self).__init__()

        HEIGHT = 30

        grid1 = QGridLayout()

        # 使用默认摄像头复选框
        self.check_camera = QCheckBox('Use default camera')
        self.check_camera.setChecked(gb.get_config('use_camera', True))
        self.check_camera.stateChanged.connect(self.slot_check_camera)
        grid1.addWidget(self.check_camera, 0, 0, 1, 4)

        # 选择视频文件
        label_video = QLabel('Source')
        self.line_video = QLineEdit()
        self.line_video.setText(gb.get_config('video', ''))
        self.line_video.setFixedHeight(HEIGHT)
        self.line_video.setEnabled(False)
        self.line_video.editingFinished.connect(
            lambda: gb.record_config({'video': self.line_video.text()}))

        self.btn_video = QPushButton('...')
        self.btn_video.setFixedWidth(40)
        self.btn_video.setFixedHeight(HEIGHT)
        self.btn_video.setEnabled(False)
        self.btn_video.clicked.connect(self.choose_video_file)
        self.slot_check_camera()

        grid1.addWidget(label_video, 1, 0)
        grid1.addWidget(self.line_video, 1, 1, 1, 2)
        grid1.addWidget(self.btn_video, 1, 3)

        # 视频录制
        self.check_record = QCheckBox('Record video')
        self.check_record.setChecked(gb.get_config('record', True))
        self.check_record.stateChanged.connect(lambda: gb.record_config(
            {'record': self.check_record.isChecked()}))
        grid1.addWidget(self.check_record, 2, 0, 1, 4)

        # Settings
        self.btn_settings = QPushButton('Settings')
        grid1.addWidget(self.btn_settings, 3, 0, 1, 4)

        box = QGroupBox()
        box.setLayout(grid1)

        vbox = QVBoxLayout()
        vbox.setContentsMargins(0, 0, 0, 0)
        vbox.addWidget(box)

        self.setLayout(vbox)

    def slot_check_camera(self):
        check = self.check_camera.isChecked()
        gb.record_config({'use_camera': check})  # 保存配置
        if check:
            self.line_video.setEnabled(False)
            self.btn_video.setEnabled(False)
        else:
            self.line_video.setEnabled(True)
            self.btn_video.setEnabled(True)

    def choose_video_file(self):
        """从系统中选择视频文件"""
        file = QFileDialog.getOpenFileName(self, "Video Files", "./",
                                           "Video Files (*)")
        if file[0] != '':
            self.line_video.setText(file[0])
            gb.record_config({'video': file[0]})
Ejemplo n.º 11
0
class PyCalcUi(QMainWindow):
    """PyCalc's View (GUI)."""
    def __init__(self):
        """View initializer."""
        super().__init__()
        # Set some main window's properties
        self.setWindowTitle('PyCalc')
        self.setFixedSize(235, 235)
        # Set the central widget and the general layout
        self.generalLayout = QVBoxLayout()
        self._centralWidget = QWidget(self)
        self.setCentralWidget(self._centralWidget)
        self._centralWidget.setLayout(self.generalLayout)
        # Create the display and the buttons
        self._createDisplay()
        self._createButtons()

    def _createDisplay(self):
        """Create the display."""
        # Create the display widget
        self.display = QLineEdit()
        # Set some display's properties
        self.display.setFixedHeight(35)
        self.display.setAlignment(Qt.AlignRight)
        self.display.setReadOnly(True)
        # Add the display to the general layout
        self.generalLayout.addWidget(self.display)

    def _createButtons(self):
        """Create the buttons."""
        self.buttons = {}
        buttonsLayout = QGridLayout()
        # Button text | position on the QGridLayout
        buttons = {
            '7': (0, 0),
            '8': (0, 1),
            '9': (0, 2),
            '/': (0, 3),
            'C': (0, 4),
            '4': (1, 0),
            '5': (1, 1),
            '6': (1, 2),
            '*': (1, 3),
            '(': (1, 4),
            '1': (2, 0),
            '2': (2, 1),
            '3': (2, 2),
            '-': (2, 3),
            ')': (2, 4),
            '0': (3, 0),
            '00': (3, 1),
            '.': (3, 2),
            '+': (3, 3),
            '=': (3, 4),
        }
        # Create the buttons and add them to the grid layout
        for btnText, pos in buttons.items():
            self.buttons[btnText] = QPushButton(btnText)
            self.buttons[btnText].setFixedSize(40, 40)
            buttonsLayout.addWidget(self.buttons[btnText], pos[0], pos[1])
        # Add buttonsLayout to the general layout
        self.generalLayout.addLayout(buttonsLayout)

    def setDisplayText(self, text):
        """Set display's text."""
        self.display.setText(text)
        self.display.setFocus()

    def displayText(self):
        """Get display's text."""
        return self.display.text()

    def clearDisplay(self):
        """Clear the display."""
        self.setDisplayText('')
Ejemplo n.º 12
0
class TrackEditor(Observation, QWidget, metaclass=FinalMeta):
    def __init__(self,
                 subject,
                 powermode=False,
                 allowEditBackend=False,
                 confirmUpdate=True):
        Observation.__init__(self, subject)
        QWidget.__init__(self)

        self._template = None
        self.deleted = False
        self.shouldSave = False
        self.powermode = powermode
        self.allowEditBackend = allowEditBackend
        self.confirmUpdate = confirmUpdate
        self.descriptionMaxLen = 1000
        self._code = ""

        layout = QVBoxLayout()
        layout.setAlignment(Qt.AlignTop)
        layout.setSpacing(0)
        layout.setContentsMargins(0, 0, 0, 0)
        self.setLayout(layout)

        if self.allowEditBackend:
            self._initForm()
        self._initCodeEditor()

        self.setFixedSize(630, 600)
        self.setAttribute(Qt.WA_StyledBackground)
        self.setStyleSheet(Theme.templateEditor.style)

        self.setContextMenuPolicy(Qt.NoContextMenu)
        self.setWindowModality(Qt.ApplicationModal)

        self.setWindowFlags(Qt.Tool | Qt.WindowTitleHint
                            | Qt.CustomizeWindowHint | Qt.WindowCloseButtonHint
                            | Qt.WindowMaximizeButtonHint)
        self.setWindowFlag(Qt.WindowMinimizeButtonHint, False)

        self.codeView.closeShortcut.setEnabled(False)

        QShortcut(QKeySequence(self.tr("Ctrl+w")), self, self.close)

    def _initForm(self):

        layout = QFormLayout()
        self.runCommand = QLineEdit(self, maxLength=200)
        self.runCommand.setStyleSheet(Theme.templateEditor.inputStyle)
        self.runCommand.setFont(Theme.templateEditor.inputCodeFont)
        self.runCommand.setFixedHeight(Theme.templateEditor.inputHeight)

        if self.powermode:
            self.backendName = QLineEdit(self, maxLength=20)
            self.backendName.setStyleSheet(Theme.templateEditor.inputStyle)
            self.backendName.setFont(Theme.templateEditor.inputFont)
            self.backendName.setFixedHeight(Theme.templateEditor.inputHeight)

            self.editorMode = QComboBox()
            [self.editorMode.addItem(mode) for mode in self._availableModes()]
            self.editorMode.currentIndexChanged.connect(
                self.onEditorModeChanged)

            self.inputRegex = QLineEdit(self, maxLength=100)
            self.inputRegex.setToolTip("regex")
            self.inputRegex.setStyleSheet(Theme.templateEditor.inputStyle)
            self.inputRegex.setFont(Theme.templateEditor.inputCodeFont)
            self.inputRegex.setFixedHeight(Theme.templateEditor.inputHeight)

            self.inputReplace = QLineEdit(self, maxLength=100)
            self.inputReplace.setToolTip("substitution string")
            self.inputReplace.setStyleSheet(Theme.templateEditor.inputStyle)
            self.inputReplace.setFont(Theme.templateEditor.inputCodeFont)
            self.inputReplace.setFixedHeight(Theme.templateEditor.inputHeight)

            self.outputRegex = QLineEdit(self, maxLength=100)
            self.outputRegex.setToolTip("regex")
            self.outputRegex.setStyleSheet(Theme.templateEditor.inputStyle)
            self.outputRegex.setFont(Theme.templateEditor.inputCodeFont)
            self.outputRegex.setFixedHeight(Theme.templateEditor.inputHeight)

            self.outputReplace = QLineEdit(self, maxLength=100)
            self.outputReplace.setToolTip("substitution string")
            self.outputReplace.setStyleSheet(Theme.templateEditor.inputStyle)
            self.outputReplace.setFont(Theme.templateEditor.inputCodeFont)
            self.outputReplace.setFixedHeight(Theme.templateEditor.inputHeight)

            self.description = QPlainTextEdit(self, minimumHeight=80)
            self.description.setStyleSheet(
                Theme.templateEditor.descriptionStyle)
            self.description.setFont(Theme.templateEditor.descriptionFont)

        layout.addRow(self.tr("Run Command:"), self.runCommand)

        if self.powermode:
            layout.addRow(self.tr("Backend Name:"), self.backendName)
            layout.addRow(self.tr("Editor Mode:"), self.editorMode)

            inputMiddlewareLayout = QHBoxLayout()
            inputMiddlewareLayout.addWidget(self.inputRegex)
            inputMiddlewareLayout.addWidget(self.inputReplace)
            layout.addRow(self.tr("Input Middleware:"), inputMiddlewareLayout)

            outputMiddlewareLayout = QHBoxLayout()
            outputMiddlewareLayout.addWidget(self.outputRegex)
            outputMiddlewareLayout.addWidget(self.outputReplace)
            layout.addRow(self.tr("Output Middleware:"),
                          outputMiddlewareLayout)

            layout.addRow(self.tr("Description:"), self.description)

        layout.setSpacing(10)
        layout.setContentsMargins(10, 10, 10, 10)
        self.layout().addLayout(layout)

    def _initCodeEditor(self):
        self.codeView = CodeView(self.subject, viewTip=False)
        self.layout().addWidget(QLabel("Setup Code:", margin=10))
        self.layout().addWidget(self.codeView)
        self.codeView.setDelegate(self)

    def _availableModes(self):
        return acePropertyNames("mode-", ".js", False)

    def onEditorModeChanged(self, e):
        mode = self.editorMode.itemText(e)
        self.codeView.setMode(mode)

        if self._template is not None:
            self._template.editor_mode = mode

    def onSave(self):
        self.shouldSave = True

        if self.allowEditBackend:
            self._template.run_command = self.runCommand.text().strip()

        if self.powermode and self.allowEditBackend:
            self._template.backend_name = self.backendName.text().strip()

            self._template.editor_mode = self.editorMode.currentText()

            self._template.backend_middleware.input.regex = \
                self.inputRegex.text()
            self._template.backend_middleware.input.substitution = \
                self.inputReplace.text()

            self._template.backend_middleware.output.regex = \
                self.outputRegex.text()
            self._template.backend_middleware.output.substitution = \
                self.outputReplace.text()

            self._template.description = self.description.toPlainText(
            )[:self.descriptionMaxLen]

        self._template.setup_code = self._code

    def setTemplate(self, delegate):
        self._template = delegate
        self.codeView.setDelegate(self)
        self.deserialize()

    def setCode(self, code, notify):
        if self._template is None:
            return

        self._code = code

        if self.shouldSave:
            self._template.setup_code = code
            self.onTemplateUpdate()

    def onTemplateUpdate(self):
        pass

    def code(self):
        if self._template is None:
            return ""

        return self._template.setup_code

    def codeWindowTitle(self):
        return "Track Template Editor"

    def deserialize(self):
        if self._template is None:
            return

        if self.allowEditBackend:
            self.runCommand.setText(self._template.run_command.strip())

        if self.powermode and self.allowEditBackend:
            self.backendName.setText(self._template.backend_name.strip())
            self.editorMode.setCurrentText(self._template.editor_mode)
            self.inputRegex.setText(
                self._template.backend_middleware.input.regex)
            self.inputReplace.setText(
                self._template.backend_middleware.input.substitution)
            self.outputRegex.setText(
                self._template.backend_middleware.output.regex)
            self.outputReplace.setText(
                self._template.backend_middleware.output.substitution)
            self.description.document().setPlainText(
                self._template.description)
        else:
            self.codeView.setMode(self._template.editor_mode)
        self._code = self._template.setup_code

        self.setWindowTitle("Track Template Editor")

    def delete(self):
        self.deleted = True
        self.codeView.delete()
        self.unregister()
        self.setParent(None)
        self.deleteLater()

    def template(self):
        return self._template

    def showEvent(self, event):
        self.shouldSave = False
        self.codeView.show()
        super().showEvent(event)

    def closeEvent(self, event):
        if self._template is not None and not self.deleted:
            if self.confirmUpdate:
                question = "Do you want to save changes in " +\
                        f"{self._template.backend_name} template?"
                confirmation = ConfirmationDialog("Update Track Template",
                                                  question)

                if confirmation.exec_() == ConfirmationDialog.Yes:
                    self.onSave()
            else:
                self.onSave()

        self.codeView.close()
        super().closeEvent(event)
Ejemplo n.º 13
0
class SettingsDialog(QDialog):
    def __init__(self):
        super(SettingsDialog, self).__init__()
        self.setWindowTitle('Settings')
        self.setWindowIcon(QIcon('img/yologo.png'))
        self.setWindowFlags(Qt.WindowCloseButtonHint)
        self.setMinimumWidth(600)

        HEIGHT = 30

        grid = QGridLayout()

        # 选择权重文件
        label_weights = QLabel('Weights')
        self.line_weights = QLineEdit()
        self.line_weights.setFixedHeight(HEIGHT)

        self.btn_weights = QPushButton('...')
        self.btn_weights.setFixedWidth(40)
        self.btn_weights.setFixedHeight(HEIGHT)
        self.btn_weights.clicked.connect(self.choose_weights_file)

        grid.addWidget(label_weights, 2, 0)
        grid.addWidget(self.line_weights, 2, 1, 1, 2)
        grid.addWidget(self.btn_weights, 2, 3)

        # 是否使用GPU
        label_device = QLabel('CUDA device')
        self.line_device = QLineEdit('cpu')
        self.line_device.setToolTip('cuda device, i.e. 0 or 0,1,2,3 or cpu')
        self.line_device.setPlaceholderText('cpu or 0 or 0,1,2,3')
        self.line_device.setFixedHeight(HEIGHT)

        grid.addWidget(label_device, 3, 0)
        grid.addWidget(self.line_device, 3, 1, 1, 3)

        # 设置图像大小
        label_size = QLabel('Img Size')
        self.combo_size = QComboBox()
        self.combo_size.setToolTip('inference size (pixels)')
        self.combo_size.setFixedHeight(HEIGHT)
        self.combo_size.setStyleSheet(
            'QAbstractItemView::item {height: 40px;}')
        self.combo_size.setView(QListView())
        self.combo_size.addItem('320', 320)
        self.combo_size.addItem('384', 384)
        self.combo_size.addItem('448', 448)
        self.combo_size.addItem('512', 512)
        self.combo_size.addItem('576', 576)
        self.combo_size.addItem('640', 640)

        grid.addWidget(label_size, 4, 0)
        grid.addWidget(self.combo_size, 4, 1, 1, 3)

        # 设置置信度阈值
        label_conf = QLabel('Confidence')
        self.spin_conf = QDoubleSpinBox()
        self.spin_conf.setToolTip('confidence threshold')
        self.spin_conf.setFixedHeight(HEIGHT)
        self.spin_conf.setDecimals(1)
        self.spin_conf.setRange(0.1, 0.9)
        self.spin_conf.setSingleStep(0.1)

        grid.addWidget(label_conf, 5, 0)
        grid.addWidget(self.spin_conf, 5, 1, 1, 3)

        # 设置IOU阈值
        label_iou = QLabel('IOU')
        self.spin_iou = QDoubleSpinBox()
        self.spin_iou.setToolTip('NMS IoU threshold')
        self.spin_iou.setFixedHeight(HEIGHT)
        self.spin_iou.setDecimals(1)
        self.spin_iou.setRange(0.1, 0.9)
        self.spin_iou.setSingleStep(0.1)

        grid.addWidget(label_iou, 6, 0)
        grid.addWidget(self.spin_iou, 6, 1, 1, 3)

        # maximum detections per image
        label_max_det = QLabel('maximum detections')
        self.spin_max_det = QDoubleSpinBox()
        self.spin_max_det.setToolTip('Maximum detections per image')
        self.spin_max_det.setFixedHeight(HEIGHT)
        self.spin_max_det.setDecimals(0)
        self.spin_max_det.setRange(10, 1000)
        self.spin_max_det.setSingleStep(10)

        grid.addWidget(label_max_det, 7, 0)
        grid.addWidget(self.spin_max_det, 7, 1, 1, 3)

        # class-agnostic NMS
        self.check_agnostic = QCheckBox('Agnostic')
        self.check_agnostic.setToolTip('class-agnostic NMS')

        # augmented inference
        self.check_augment = QCheckBox('Augment')
        self.check_augment.setToolTip('augmented inference')

        # half
        self.check_half = QCheckBox('Half')
        self.check_half.setToolTip('use FP16 half-precision inference')

        grid.addWidget(self.check_agnostic, 8, 0)
        grid.addWidget(self.check_augment, 8, 1)
        grid.addWidget(self.check_half, 8, 2)

        # use OpenCV DNN for ONNX inference
        self.check_dnn = QCheckBox('DNN')
        self.check_dnn.setToolTip('Use OpenCV DNN for ONNX inference')

        grid.addWidget(self.check_dnn, 9, 0)

        box = QGroupBox()
        box.setLayout(grid)

        hbox = QHBoxLayout()
        self.btn_cancel = QPushButton('Cancel')
        self.btn_cancel.clicked.connect(self.restore)
        self.btn_ok = QPushButton('Ok')
        self.btn_ok.clicked.connect(self.save_settings)
        hbox.addStretch()
        hbox.addWidget(self.btn_cancel)
        hbox.addWidget(self.btn_ok)

        vbox = QVBoxLayout()
        vbox.addWidget(box)
        vbox.addLayout(hbox)

        self.setLayout(vbox)

        self.load_settings()

    def choose_weights_file(self):
        """从系统中选择权重文件"""
        weights_path = '.'
        weights = gb.get_config('weights', '')
        if os.path.exists(weights):
            weights_path = os.path.dirname(weights)
        file = QFileDialog.getOpenFileName(
            self, "Pre-trained YOLOv5 Weights", weights_path,
            "Weights Files (*.pt);;All Files (*)")
        if file[0] != '':
            self.line_weights.setText(file[0])

    def load_settings(self):
        self.line_weights.setText(gb.get_config('weights', ''))
        self.line_device.setText(gb.get_config('device', 'cpu'))
        self.combo_size.setCurrentText(gb.get_config('img_size', '640'))
        self.spin_conf.setValue(gb.get_config('conf_thresh', 0.5))
        self.spin_iou.setValue(gb.get_config('iou_thresh', 0.5))
        self.spin_max_det.setValue(gb.get_config('max_det', 50))
        self.check_agnostic.setChecked(gb.get_config('agnostic', True))
        self.check_augment.setChecked(gb.get_config('augment', True))
        self.check_half.setChecked(gb.get_config('half', True))
        self.check_dnn.setChecked(gb.get_config('dnn', False))

    def save_settings(self):
        """更新配置"""
        config = {
            'weights': self.line_weights.text(),
            'device': self.line_device.text(),
            'img_size': self.combo_size.currentText(),
            'conf_thresh': round(self.spin_conf.value(), 1),
            'iou_thresh': round(self.spin_iou.value(), 1),
            'max_det': int(self.spin_max_det.value()),
            'agnostic': self.check_agnostic.isChecked(),
            'augment': self.check_augment.isChecked(),
            'half': self.check_half.isChecked(),
            'dnn': self.check_dnn.isChecked()
        }
        gb.record_config(config)
        self.accept()

    def restore(self):
        """恢复原配置"""
        self.load_settings()
        self.reject()

    def closeEvent(self, event):
        self.restore()
Ejemplo n.º 14
0
class SignUpForm(QDialog):
    def __init__(self, parent=None):
        super(SignUpForm, self).__init__(parent)

        self.checkedPass = 0

        self.setWindowTitle("Backend Discord-GUI")
        self.changeStyle('fusion')

        palette = QPalette()
        palette.setColor(QPalette.Window, QColor(53, 53, 53))
        palette.setColor(QPalette.WindowText, Qt.white)
        palette.setColor(QPalette.Text, Qt.white)
        palette.setColor(QPalette.Button, QColor(60, 60, 60))
        palette.setColor(QPalette.ButtonText, Qt.white)
        palette.setColor(QPalette.Base, QColor(40, 40, 40))
        palette.setColor(QPalette.ToolTipBase, QColor(60, 60, 60))
        palette.setColor(QPalette.ToolTipText, Qt.white)
        palette.setColor(QPalette.PlaceholderText, QColor(100, 60, 60))
        palette.setColor(QPalette.BrightText, Qt.white)
        palette.setColor(QPalette.Highlight, QColor(106, 13, 173))
        palette.setColor(QPalette.HighlightedText, Qt.white)

        mainLayout = QVBoxLayout()
        hMainLayout = QHBoxLayout()
        passwordLayout = QHBoxLayout()

        entryBG = QPalette()
        gradient = QGradient()
        gradient.setColorAt(0.0, QColor(30, 30, 30))
        gradient.setColorAt(0.4, QColor(30, 30, 30))
        gradient.setColorAt(1.0, QColor(70, 70, 70))
        gradient.setSpread(QGradient.RepeatSpread)
        entryBG.setBrush(QPalette.Button, QBrush(gradient))

        self.name = QLineEdit(self)
        self.name.setFixedHeight(24)
        self.name.setToolTip("Max 64 Characters")
        self.name.setStyleSheet(
            "QToolTip { border: 0px; border-radius: 3px; }")
        self.name.setPalette(entryBG)
        self.QNameLabel = QLabel("Full Name")
        self.QNameLabel.setFont(QFont("Copperplate", 12))
        self.name.setMaxLength(64)

        self.email = QLineEdit(self)
        self.email.setFixedHeight(24)
        self.email.setToolTip(
            "Max 128 Characters, Example - [email protected]")
        self.email.setStyleSheet(
            "QToolTip { border: 0px; border-radius: 3px }")
        self.email.setPalette(entryBG)
        self.QEmailLabel = QLabel("Email")
        self.QEmailLabel.setFont(QFont("Copperplate", 12))
        self.email.setMaxLength(128)

        self.username = QLineEdit(self)
        self.username.setFixedHeight(24)
        self.username.setToolTip("Max 16 Characters")
        self.username.setStyleSheet(
            "QToolTip { border: 0px; border-radius: 3px }")
        self.username.setPalette(entryBG)
        self.QUserLabel = QLabel("Username")
        self.QUserLabel.setFont(QFont("Copperplate", 12))
        self.username.setMaxLength(16)

        self.password = QLineEdit(self)
        self.password.setFixedHeight(24)
        self.password.setToolTip(
            "Max 32 Characters, Must Include = Uppercase Letter,\nNumber and Special Character"
        )
        self.password.setStyleSheet(
            "QToolTip { border: 0px; border-radius: 3px }")
        self.password.setPalette(entryBG)
        self.QPasswordLabel = QLabel("Password ")
        self.password.setMaxLength(32)
        self.QPasswordLabel.setFont(QFont("Copperplate", 12))
        self.showhideButton = QPushButton("Show")
        self.showhideButton.setCheckable(True)
        self.showhideButton.setChecked(False)
        self.showhideButton.clicked.connect(lambda: self.show_hide())
        self.password.setEchoMode(QLineEdit.Password)
        passwordLayout.addWidget(self.QPasswordLabel)
        passwordLayout.addWidget(self.password)
        passwordLayout.addWidget(self.showhideButton)

        self.btn_SignUp = QPushButton("Sign Up")
        self.btn_SignUp.clicked.connect(lambda: self.signUpWindow())

        shortcut = QShortcut(QKeySequence("Return"), self.btn_SignUp)
        shortcut.activated.connect(lambda: self.signUpWindow())
        shortcut.setEnabled(True)

        self.btn_cancel = QPushButton("Cancel")
        self.btn_cancel.clicked.connect(lambda: self.cancel())

        layout = QFormLayout()
        layout.addRow(self.QNameLabel, self.name)
        layout.addRow(self.QEmailLabel, self.email)
        layout.addRow(self.QUserLabel, self.username)
        layout.addRow(passwordLayout)
        layout.addRow(self.btn_SignUp)
        layout.addRow(self.btn_cancel)

        Label = QLabel("Sign Up To The\nBackend Discord-GUI Development")
        Label.setFont(QFont("Copperplate", 15, QFont.Bold))
        Label.setAlignment(Qt.AlignCenter)

        mainLayout.addSpacing(40)
        mainLayout.addWidget(Label)
        mainLayout.addLayout(layout)
        mainLayout.addSpacing(60)

        hMainLayout.addSpacing(115)
        hMainLayout.addLayout(mainLayout)
        hMainLayout.addSpacing(115)
        self.setLayout(hMainLayout)

        QApplication.setPalette(palette)

    def keyPressEvent(self, e):
        if e.key() == Qt.Key_Escape:
            pass

    def check_passwordCheck(self):
        if self.checkedPass <= 0:
            msg = QMessageBox()
            msg.setIcon(QMessageBox.Information)

            msg.setText("Check Password?")
            msg.setInformativeText(
                "Are you sure you want to Sign Up, you haven't checked your password. Do you want to proceed?"
            )
            msg.setWindowTitle("Check Password?")
            msg.setDetailedText(
                "We monitor basic actions you make, this is part of our policy. This MessageBox "
                +
                "was generated because we detected you did not check your password before clicking "
                +
                "the sign up button. We recommend this just incase you forget your password.\n\n"
                +
                "We believe in the best for our customers, so we try to minimise simple errors, "
                +
                "like this, to serve customers quicker when there is a higher priority support request."
            )
            msg.setStandardButtons(QMessageBox.No | QMessageBox.Yes)
            msg.buttonClicked.connect(self.signUp)

            retval = msg.exec_()
        else:
            self.signUp(proceed=True)

    def signUpWindow(self):
        namePassed, emailPassed, usernamePassed, passwordPassed = False, False, False, False
        errors = []
        if len(self.name.text()) <= 1:
            self.name.setStyleSheet(
                "QLineEdit { border: 1px solid red; border-radius: 3px; } QToolTip { border: 0px }"
            )
            errors.append("Name: Too Short")
        else:
            self.name.setStyleSheet(
                "QLineEdit { border: 0px; border-radius: 3px; } QToolTip { border: 0px }"
            )
            namePassed = True

        if re.match(r"(^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$)",
                    self.email.text()):
            self.email.setStyleSheet(
                "QLineEdit { border: 0px; border-radius: 3px; } QToolTip { border: 0px }"
            )
            emailPassed = True
        else:
            self.email.setStyleSheet(
                "QLineEdit { border: 1px solid red; border-radius: 3px; } QToolTip { border: 0px }"
            )
            errors.append("Email: This is not a valid Email")

        if len(self.username.text()) <= 2:
            self.username.setStyleSheet(
                "QLineEdit { border: 1px solid red; border-radius: 3px; } QToolTip { border: 0px }"
            )
            errors.append("Username: Too Short")
        else:
            if re.match(r"([a-zA-Z0-9_]+$)", self.username.text()):
                self.username.setStyleSheet(
                    "QLineEdit { border: 0px; border-radius: 3px; } QToolTip { border: 0px }"
                )
                usernamePassed = True
            else:
                self.username.setStyleSheet(
                    "QLineEdit { border: 1px solid red; border-radius: 3px; } QToolTip { border: 0px }"
                )
                errors.append(
                    "Username: Can only have, a-z (A-Z), 0-9 and '_'")

        if len(self.password.text()) <= 7:
            self.password.setStyleSheet(
                "QLineEdit { border: 1px solid red; border-radius: 3px; } QToolTip { border: 0px }"
            )
            errors.append("Password: Too Short")
        else:
            if re.match(
                    r'^.*(?=.{8,10})(?=.*[a-zA-Z])(?=.*?[A-Z])(?=.*\d)[a-zA-Z0-9!@£$%^&*()_+={}?:~\[\]]+$',
                    self.password.text()):
                self.password.setStyleSheet(
                    "QLineEdit { border: 0px; border-radius: 3px; } QToolTip { border: 0px }"
                )
                passwordPassed = True
            else:
                self.password.setStyleSheet(
                    "QLineEdit { border: 1px solid red; border-radius: 3px; } QToolTip { border: 0px }"
                )
                errors.append(
                    "Password: Needs to have, Capital Letter, Number, Special Character"
                )

        if namePassed and emailPassed and usernamePassed and passwordPassed:
            self.check_passwordCheck()
        else:
            if len(errors) > 2:
                string = "; ".join(errors[:2])
                overall_string = str("Errors: " + string +
                                     " +{} more".format(len(errors) - 2))
            else:
                string = "; ".join(errors)
                overall_string = str("Errors: " + string)
            window.setStatusBar(overall_string, True)

    def signUp(self, i=None, proceed=False):
        if i != None:
            if i.text() == "&Yes":
                signUp = True
                QApplication.quit()
            else:
                pass
        signUp = proceed
        if signUp == True:
            print("Signed Up")
            QApplication.quit()

    def show_hide(self):
        if self.showhideButton.isChecked():
            self.checkedPass += 1
            self.password.setEchoMode(QLineEdit.Normal)
            self.showhideButton.setText("Hide")
        else:
            self.password.setEchoMode(QLineEdit.Password)
            self.showhideButton.setText("Show")

    def changeStyle(self, styleName):
        QApplication.setStyle(QStyleFactory.create(styleName))

    def cancel(self):
        window.openLogIn()
Ejemplo n.º 15
0
class WidgetConfig(QGroupBox):
    def __init__(self):
        super(WidgetConfig, self).__init__()

        HEIGHT = 40

        grid = QGridLayout()

        # 使用默认摄像头复选框
        self.check_camera = QCheckBox('Use default camera')
        self.check_camera.setChecked(False)
        self.check_camera.stateChanged.connect(self.slot_check_camera)

        grid.addWidget(self.check_camera, 0, 0, 1, 3)  # 一行三列

        # 选择视频文件
        label_video = QLabel('Detect File')
        self.line_video = QLineEdit()
        if 'video' in GLOBAL.config:
            self.line_video.setText(GLOBAL.config['video'])
        self.line_video.setFixedHeight(HEIGHT)
        self.line_video.setEnabled(False)
        self.line_video.editingFinished.connect(
            lambda: GLOBAL.record_config({'video': self.line_video.text()}))

        self.btn_video = QPushButton('Choose')
        self.btn_video.setFixedHeight(HEIGHT)
        self.btn_video.setEnabled(False)
        self.btn_video.clicked.connect(self.choose_video_file)

        self.slot_check_camera()

        grid.addWidget(label_video, 1, 0)
        grid.addWidget(self.line_video, 1, 1)
        grid.addWidget(self.btn_video, 1, 2)

        # 选择权重文件
        label_weights = QLabel('Weights File')
        self.line_weights = QLineEdit()
        if 'weights' in GLOBAL.config:
            self.line_weights.setText(GLOBAL.config['weights'])
        self.line_weights.setFixedHeight(HEIGHT)
        self.line_weights.editingFinished.connect(lambda: GLOBAL.record_config(
            {'weights': self.line_weights.text()}))

        self.btn_weights = QPushButton('Choose')
        self.btn_weights.setFixedHeight(HEIGHT)
        self.btn_weights.clicked.connect(self.choose_weights_file)

        grid.addWidget(label_weights, 2, 0)
        grid.addWidget(self.line_weights, 2, 1)
        grid.addWidget(self.btn_weights, 2, 2)

        # 是否使用GPU
        label_device = QLabel('CUDA device')
        self.line_device = QLineEdit('gpu')
        if 'device' in GLOBAL.config:
            self.line_device.setText(GLOBAL.config['device'])
        else:
            self.line_device.setText('cpu')
        self.line_device.setPlaceholderText('cpu or 0 or 0,1,2,3')
        self.line_device.setFixedHeight(HEIGHT)
        self.line_device.editingFinished.connect(
            lambda: GLOBAL.record_config({'device': self.line_device.text()}))

        grid.addWidget(label_device, 3, 0)
        grid.addWidget(self.line_device, 3, 1, 1, 2)

        # 设置图像大小
        label_size = QLabel('Img Size')
        self.combo_size = QComboBox()
        self.combo_size.setFixedHeight(HEIGHT)
        self.combo_size.setStyleSheet(
            'QAbstractItemView::item {height: 40px;}')
        self.combo_size.setView(QListView())
        self.combo_size.addItem('320', 320)
        self.combo_size.addItem('416', 416)
        self.combo_size.addItem('480', 480)
        self.combo_size.addItem('544', 544)
        self.combo_size.addItem('640', 640)
        self.combo_size.setCurrentIndex(2)
        self.combo_size.currentIndexChanged.connect(
            lambda: GLOBAL.record_config(
                {'img_size': self.combo_size.currentData()}))

        grid.addWidget(label_size, 4, 0)
        grid.addWidget(self.combo_size, 4, 1, 1, 2)

        #choose net camera
        label_stream = QLabel('NetVedioStream')
        self.combo_stream = QComboBox()
        self.combo_stream.setFixedHeight(HEIGHT)
        self.combo_stream.setStyleSheet(
            'QAbstractItemView::item {height: 40px;}')
        self.combo_stream.setView(QListView())
        self.combo_stream.addItem('rtsp://*****:*****@192.168.0.65/',
                                  'rtsp://*****:*****@192.168.0.65/')
        self.combo_stream.addItem('rtsp://*****:*****@192.168.0.66/',
                                  'rtsp://*****:*****@192.168.0.66/')
        self.combo_stream.addItem('rtsp://*****:*****@192.168.0.67/',
                                  'rtsp://*****:*****@192.168.0.67/')
        self.combo_stream.addItem('rtsp://*****:*****@192.168.0.68/',
                                  'rtsp://*****:*****@192.168.0.68/')
        self.combo_stream.addItem('rtsp://*****:*****@192.168.0.65/',
                                  'rtsp://*****:*****@192.168.0.65/')
        self.combo_stream.setCurrentIndex(0)
        self.combo_stream.currentIndexChanged.connect(
            lambda: GLOBAL.record_config(
                {'netstreamvedio': self.combo_stream.currentData()}))

        grid.addWidget(label_stream, 5, 0)
        grid.addWidget(self.combo_stream, 5, 1, 1, 2)

        # 设置置信度阈值
        label_conf = QLabel('Confidence')
        self.spin_conf = QDoubleSpinBox()
        self.spin_conf.setFixedHeight(HEIGHT)
        self.spin_conf.setDecimals(1)
        self.spin_conf.setRange(0.1, 0.9)
        self.spin_conf.setSingleStep(0.1)
        if 'conf_thresh' in GLOBAL.config:
            self.spin_conf.setValue(GLOBAL.config['conf_thresh'])
        else:
            self.spin_conf.setValue(0.4)  # 默认值
            GLOBAL.record_config({'conf_thresh': 0.4})
        self.spin_conf.valueChanged.connect(lambda: GLOBAL.record_config(
            {'conf_thresh': round(self.spin_conf.value(), 1)}))

        grid.addWidget(label_conf, 6, 0)
        grid.addWidget(self.spin_conf, 6, 1, 1, 2)

        # 设置IOU阈值
        label_iou = QLabel('IOU')
        self.spin_iou = QDoubleSpinBox()
        self.spin_iou.setFixedHeight(HEIGHT)
        self.spin_iou.setDecimals(1)
        self.spin_iou.setRange(0.1, 0.9)
        self.spin_iou.setSingleStep(0.1)
        if 'iou_thresh' in GLOBAL.config:
            self.spin_iou.setValue(GLOBAL.config['iou_thresh'])
        else:
            self.spin_iou.setValue(0.5)  # 默认值
            GLOBAL.record_config({'iou_thresh': 0.5})
        self.spin_iou.valueChanged.connect(lambda: GLOBAL.record_config(
            {'iou_thresh': round(self.spin_iou.value(), 1)}))

        grid.addWidget(label_iou, 7, 0)
        grid.addWidget(self.spin_iou, 7, 1, 1, 2)

        # class-agnostic NMS
        self.check_agnostic = QCheckBox('Agnostic')
        if 'agnostic' in GLOBAL.config:
            self.check_agnostic.setChecked(GLOBAL.config['agnostic'])
        else:
            self.check_agnostic.setChecked(True)
        self.check_agnostic.stateChanged.connect(lambda: GLOBAL.record_config(
            {'agnostic': self.check_agnostic.isChecked()}))

        grid.addWidget(self.check_agnostic, 8, 0, 1, 3)  # 一行三列

        # augmented inference
        self.check_augment = QCheckBox('Augment')
        if 'augment' in GLOBAL.config:
            self.check_augment.setChecked(GLOBAL.config['augment'])
        else:
            self.check_augment.setChecked(True)
        self.check_augment.stateChanged.connect(lambda: GLOBAL.record_config(
            {'augment': self.check_augment.isChecked()}))

        grid.addWidget(self.check_augment, 9, 0, 1, 3)  # 一行三列

        self.setLayout(grid)  # 设置布局

    def slot_check_camera(self):
        check = self.check_camera.isChecked()
        GLOBAL.record_config({'use_camera': check})  # 保存配置
        if check:
            self.line_video.setEnabled(False)
            self.btn_video.setEnabled(False)
        else:
            self.line_video.setEnabled(True)
            self.btn_video.setEnabled(True)

    def choose_weights_file(self):
        """从系统中选择权重文件"""
        file = QFileDialog.getOpenFileName(
            self, "Pre-trained YOLOv5 Weights", "./",
            "Weights Files (*.pt);;All Files (*)")
        if file[0] != '':
            self.line_weights.setText(file[0])
            GLOBAL.record_config({'weights': file[0]})

    def choose_video_file(self):
        """从系统中选择视频文件"""
        file = QFileDialog.getOpenFileName(self, "Video Files", "./",
                                           "Video Files (*)")
        if file[0] != '':
            self.line_video.setText(file[0])
            GLOBAL.record_config({'video': file[0]})

    def save_config(self):
        """保存当前的配置到配置文件"""
        config = {
            'use_camera': self.check_camera.isChecked(),
            'video': self.line_video.text(),
            'weights': self.line_weights.text(),
            'device': self.line_device.text(),
            'img_size': self.combo_size.currentData(),
            'conf_thresh': round(self.spin_conf.value(), 1),
            'iou_thresh': round(self.spin_iou.value(), 1),
            'agnostic': self.check_agnostic.isChecked(),
            'augment': self.check_augment.isChecked(),
            'netstreamvedio': self.combo_stream.currentData()
        }
        GLOBAL.record_config(config)
Ejemplo n.º 16
0
class MainWindow(QMainWindow):
    def __init__(self, application, *args, **kwargs):
        super(MainWindow, self).__init__(*args, **kwargs)

        self.printer_thread = WorkerThread()
        self.printer_thread.message.connect(self.standardOutputWritten)
        self.printer_thread.start()

        self.app = application
        self.app.setStyle("Fusion")

        self.__set_interface()
        self.__set_layouts()
        self.__set_stylesheet()
        self.__set_connections()
        self.__set_params()

    def closeEvent(self, event):
        self.printer_thread.stop()

    def __set_interface(self):
        self.button_width = 0.35
        self.button_height = 0.05

        self.setWindowTitle("GSI-RADS")
        self.__getScreenDimensions()

        self.setGeometry(self.left, self.top, self.width, self.height)
        self.setMaximumWidth(self.width)
        #self.setMaximumHeight(self.height)
        self.setMinimumWidth(self.width)
        self.setMinimumHeight(self.height)
        self.move(self.width / 2, self.height / 2)

        self.menu_bar = QMenuBar(self)
        self.menu_bar.setNativeMenuBar(
            False
        )  # https://stackoverflow.com/questions/25261760/menubar-not-showing-for-simple-qmainwindow-code-qt-creator-mac-os
        self.file_menu = self.menu_bar.addMenu('File')
        self.import_dicom_action = QAction(
            QIcon(
                os.path.join(os.path.dirname(os.path.realpath(__file__)),
                             'images/database-icon.png')), 'Import DICOM',
            self)
        self.import_dicom_action.setShortcut('Ctrl+D')
        self.file_menu.addAction(self.import_dicom_action)
        self.quit_action = QAction('Quit', self)
        self.quit_action.setShortcut("Ctrl+Q")
        self.file_menu.addAction(self.quit_action)

        self.settings_menu = self.menu_bar.addMenu('Settings')
        self.settings_seg_menu = self.settings_menu.addMenu("Segmentation...")
        self.settings_seg_preproc_menu = self.settings_seg_menu.addMenu(
            "Preprocessing...")
        self.settings_seg_preproc_menu_p1_action = QAction(
            "Brain-masking off (P1)", checkable=True)
        self.settings_seg_preproc_menu_p2_action = QAction(
            "Brain-masking on (P2)", checkable=True)
        self.settings_seg_preproc_menu_p2_action.setChecked(True)
        self.settings_seg_preproc_menu.addAction(
            self.settings_seg_preproc_menu_p1_action)
        self.settings_seg_preproc_menu.addAction(
            self.settings_seg_preproc_menu_p2_action)

        self.help_menu = self.menu_bar.addMenu('Help')
        self.readme_action = QAction(
            QIcon(
                os.path.join(os.path.dirname(os.path.realpath(__file__)),
                             'images/readme-icon.jpeg')), 'Tutorial', self)
        self.readme_action.setShortcut("Ctrl+R")
        self.help_menu.addAction(self.readme_action)
        self.about_action = QAction(
            QIcon(
                os.path.join(os.path.dirname(os.path.realpath(__file__)),
                             'images/about-icon.png')), 'About', self)
        self.about_action.setShortcut("Ctrl+A")
        self.help_menu.addAction(self.about_action)
        self.help_action = QAction(
            QIcon.fromTheme("help-faq"), "Help", self
        )  # Default icons can be found here: https://specifications.freedesktop.org/icon-naming-spec/icon-naming-spec-latest.html#guidelines
        self.help_action.setShortcut("Ctrl+J")
        self.help_menu.addAction(self.help_action)

        self.input_image_lineedit = QLineEdit()
        self.input_image_lineedit.setFixedWidth(self.width *
                                                (0.93 - self.button_width / 2))
        self.input_image_lineedit.setFixedHeight(self.height *
                                                 self.button_height)
        self.input_image_lineedit.setReadOnly(True)
        self.input_image_pushbutton = QPushButton('Input MRI')
        self.input_image_pushbutton.setFixedWidth(self.height *
                                                  self.button_width)
        self.input_image_pushbutton.setFixedHeight(self.height *
                                                   self.button_height)

        self.input_segmentation_lineedit = QLineEdit()
        self.input_segmentation_lineedit.setReadOnly(True)
        self.input_segmentation_lineedit.setFixedWidth(
            self.width * (0.93 - self.button_width / 2))
        self.input_segmentation_lineedit.setFixedHeight(self.height *
                                                        self.button_height)
        self.input_segmentation_pushbutton = QPushButton('Input segmentation')
        self.input_segmentation_pushbutton.setFixedWidth(self.height *
                                                         self.button_width)
        self.input_segmentation_pushbutton.setFixedHeight(self.height *
                                                          self.button_height)

        self.output_folder_lineedit = QLineEdit()
        self.output_folder_lineedit.setReadOnly(True)
        self.output_folder_lineedit.setFixedWidth(
            self.width * (0.93 - self.button_width / 2))
        self.output_folder_lineedit.setFixedHeight(self.height *
                                                   self.button_height)
        self.output_folder_pushbutton = QPushButton('Output destination')
        self.output_folder_pushbutton.setFixedWidth(self.height *
                                                    self.button_width)
        self.output_folder_pushbutton.setFixedHeight(self.height *
                                                     self.button_height)

        self.run_button = QPushButton('Run diagnosis')
        self.run_button.setFixedWidth(self.height * self.button_width)
        self.run_button.setFixedHeight(self.height * self.button_height)

        self.main_display_tabwidget = QTabWidget()

        self.tutorial_textedit = QPlainTextEdit()
        self.tutorial_textedit.setReadOnly(True)
        self.tutorial_textedit.setFixedWidth(self.width * 0.97)
        self.tutorial_textedit.setPlainText(
            "HOW TO USE THE SOFTWARE: \n"
            "  1) Click 'Input MRI...' to select from your file explorer the MRI scan to process (unique file).\n"
            "  1*) Alternatively, Click File > Import DICOM... if you wish to process an MRI scan as a DICOM sequence.\n"
            "  2) Click 'Output destination' to choose a directory where to save the results \n"
            "  3) (OPTIONAL) Click 'Input segmentation' to choose a tumor segmentation mask file, if nothing is provided the internal model with generate the segmentation automatically \n"
            "  4) Click 'Run diagnosis' to perform the analysis. The human-readable version will be displayed in the interface.\n"
            " \n"
            "NOTE: \n"
            "The output folder is populated automatically with the following: \n"
            "  * The diagnosis results in human-readable text (report.txt) and Excel-ready format (report.csv).\n"
            "  * The automatic segmentation masks of the brain and the tumor in the original patient space (input_brain_mask.nii.gz and input_tumor_mask.nii.gz).\n"
            "  * The input volume and tumor segmentation mask in MNI space in the sub-directory named \'registration\'.\n"
        )
        self.main_display_tabwidget.addTab(self.tutorial_textedit, 'Tutorial')
        self.prompt_lineedit = QPlainTextEdit()
        self.prompt_lineedit.setReadOnly(True)
        self.prompt_lineedit.setFixedWidth(self.width * 0.97)
        self.main_display_tabwidget.addTab(self.prompt_lineedit, 'Logging')
        self.results_textedit = QPlainTextEdit()
        self.results_textedit.setReadOnly(True)
        self.results_textedit.setFixedWidth(self.width * 0.97)
        self.main_display_tabwidget.addTab(self.results_textedit, 'Results')

        self.sintef_logo_label = QLabel()
        self.sintef_logo_label.setPixmap(
            QPixmap(
                os.path.join(os.path.dirname(os.path.realpath(__file__)),
                             'images/sintef-logo.png')))
        self.sintef_logo_label.setFixedWidth(0.95 * (self.width / 3))
        self.sintef_logo_label.setFixedHeight(
            1 * (self.height * self.button_height))
        self.sintef_logo_label.setScaledContents(True)
        self.stolavs_logo_label = QLabel()
        self.stolavs_logo_label.setPixmap(
            QPixmap(
                os.path.join(os.path.dirname(os.path.realpath(__file__)),
                             'images/stolavs-logo.png')))
        self.stolavs_logo_label.setFixedWidth(0.95 * (self.width / 3))
        self.stolavs_logo_label.setFixedHeight(
            1 * (self.height * self.button_height))
        self.stolavs_logo_label.setScaledContents(True)
        self.amsterdam_logo_label = QLabel()
        self.amsterdam_logo_label.setPixmap(
            QPixmap(
                os.path.join(os.path.dirname(os.path.realpath(__file__)),
                             'images/amsterdam-logo.png')))
        self.amsterdam_logo_label.setFixedWidth(0.95 * (self.width / 3))
        self.amsterdam_logo_label.setFixedHeight(
            1 * (self.height * self.button_height))
        self.amsterdam_logo_label.setScaledContents(True)

    def __set_layouts(self):
        self.input_volume_hbox = QHBoxLayout()
        self.input_volume_hbox.addStretch(1)
        self.input_volume_hbox.addWidget(self.input_image_lineedit)
        self.input_volume_hbox.addWidget(self.input_image_pushbutton)
        self.input_volume_hbox.addStretch(1)

        self.input_seg_hbox = QHBoxLayout()
        self.input_seg_hbox.addStretch(1)
        self.input_seg_hbox.addWidget(self.input_segmentation_lineedit)
        self.input_seg_hbox.addWidget(self.input_segmentation_pushbutton)
        self.input_seg_hbox.addStretch(1)

        self.output_dir_hbox = QHBoxLayout()
        self.output_dir_hbox.addStretch(1)
        self.output_dir_hbox.addWidget(self.output_folder_lineedit)
        self.output_dir_hbox.addWidget(self.output_folder_pushbutton)
        self.output_dir_hbox.addStretch(1)

        self.run_action_hbox = QHBoxLayout()
        self.run_action_hbox.addStretch(1)
        self.run_action_hbox.addWidget(self.run_button)
        self.run_action_hbox.addStretch(1)

        self.dump_area_hbox = QHBoxLayout()
        self.dump_area_hbox.addStretch(1)
        self.dump_area_hbox.addWidget(self.main_display_tabwidget)
        self.dump_area_hbox.addStretch(1)

        self.logos_hbox = QHBoxLayout()
        self.logos_hbox.addStretch(1)
        self.logos_hbox.addWidget(self.sintef_logo_label)
        self.logos_hbox.addWidget(self.stolavs_logo_label)
        self.logos_hbox.addWidget(self.amsterdam_logo_label)
        self.logos_hbox.addStretch(1)

        self.main_vbox = QVBoxLayout()
        self.main_vbox.addWidget(self.menu_bar)
        #self.main_vbox.addStretch(1)
        self.main_vbox.addLayout(self.input_volume_hbox)
        self.main_vbox.addLayout(self.output_dir_hbox)
        self.main_vbox.addLayout(self.input_seg_hbox)
        self.main_vbox.addLayout(self.run_action_hbox)
        #self.main_vbox.addStretch(1)
        self.main_vbox.addLayout(self.dump_area_hbox)
        self.main_vbox.addLayout(self.logos_hbox)
        #self.main_vbox.addStretch(1)

        self.central_label = QLabel()
        self.central_label.setLayout(self.main_vbox)
        self.setCentralWidget(self.central_label)

    def __set_stylesheet(self):
        self.central_label.setStyleSheet(
            'QLabel{background-color: qlineargradient(spread:pad, x1:0.5, y1:1, x2:0.5, y2:0, stop:0 rgba(207, 209, 207, 255), stop:1 rgba(230, 229, 230, 255));}'
        )
        self.menu_bar.setStyleSheet(get_stylesheet('QMenuBar'))
        self.input_image_lineedit.setStyleSheet(get_stylesheet('QLineEdit'))
        self.input_image_pushbutton.setStyleSheet(
            get_stylesheet('QPushButton'))
        self.input_segmentation_lineedit.setStyleSheet(
            get_stylesheet('QLineEdit'))
        self.input_segmentation_pushbutton.setStyleSheet(
            get_stylesheet('QPushButton'))
        self.output_folder_lineedit.setStyleSheet(get_stylesheet('QLineEdit'))
        self.output_folder_pushbutton.setStyleSheet(
            get_stylesheet('QPushButton'))

        self.results_textedit.setStyleSheet(get_stylesheet('QTextEdit'))
        self.prompt_lineedit.setStyleSheet(get_stylesheet('QTextEdit'))

        self.run_button.setStyleSheet(get_stylesheet('QPushButton'))

    def __set_connections(self):
        self.run_button.clicked.connect(self.diagnose_main_wrapper)
        self.input_image_pushbutton.clicked.connect(
            self.run_select_input_image)
        self.input_segmentation_pushbutton.clicked.connect(
            self.run_select_input_segmentation)
        self.output_folder_pushbutton.clicked.connect(
            self.run_select_output_folder)

        self.readme_action.triggered.connect(self.readme_action_triggered)
        self.about_action.triggered.connect(self.about_action_triggered)
        self.quit_action.triggered.connect(self.quit_action_triggered)
        self.import_dicom_action.triggered.connect(
            self.import_dicom_action_triggered)
        self.help_action.triggered.connect(self.help_action_triggered)
        self.settings_seg_preproc_menu_p1_action.triggered.connect(
            self.settings_seg_preproc_menu_p1_action_triggered)
        self.settings_seg_preproc_menu_p2_action.triggered.connect(
            self.settings_seg_preproc_menu_p2_action_triggered)

    def __set_params(self):
        self.input_image_filepath = ''
        self.input_annotation_filepath = ''
        self.output_folderpath = ''

    def __getScreenDimensions(self):
        screen = self.app.primaryScreen()
        size = screen.size()

        self.left = size.width() / 2
        self.top = size.height() / 2
        self.width = 0.4 * size.width()
        self.height = 0.4 * size.height()

    def readme_action_triggered(self):
        popup = QMessageBox()
        popup.setWindowTitle('Tutorial')
        popup.setText(
            "HOW TO USE THE SOFTWARE: \n"
            "  1) Click 'Input MRI...' to select from your file explorer the MRI scan to process (unique file).\n"
            "  1*) Alternatively, Click File > Import DICOM... if you wish to process an MRI scan as a DICOM sequence.\n"
            "  2) Click 'Output destination' to choose a directory where to save the results \n"
            "  3) (OPTIONAL) Click 'Input segmentation' to choose a tumor segmentation mask file, if nothing is provided the internal model with generate the segmentation automatically \n"
            "  4) Click 'Run diagnosis' to perform the analysis. The human-readable version will be displayed in the interface.\n"
            " \n"
            "NOTE: \n"
            "The output folder is populated automatically with the following: \n"
            "  * The diagnosis results in human-readable text (report.txt) and Excel-ready format (report.csv).\n"
            "  * The automatic segmentation masks of the brain and the tumor in the original patient space (input_brain_mask.nii.gz and input_tumor_mask.nii.gz).\n"
            "  * The input volume and tumor segmentation mask in MNI space in the sub-directory named \'registration\'.\n"
        )
        popup.exec_()

    def about_action_triggered(self):
        popup = QMessageBox()
        popup.setWindowTitle('About')
        popup.setText(
            'Software developed as part of a collaboration between: \n'
            '  * Departement of Health Research, SINTEF\n'
            '  * St. Olavs hospital, Trondheim University Hospital\n'
            '  * Amsterdam University Medical Center\n\n'
            'Contact: David Bouget, Andre Pedersen\n\n'
            'For questions about the software, please visit:\n'
            'https://github.com/SINTEFMedtek/GSI-RADS\n'
            'For questions about the methodological aspect, please refer to the original publication:\n'
            'https://www.mdpi.com/2072-6694/13/12/2854/review_report')
        popup.exec_()

    def quit_action_triggered(self):
        self.printer_thread.stop()
        sys.exit()

    def diagnose_main_wrapper(self):
        self.run_diagnosis_thread = threading.Thread(target=self.run_diagnosis)
        self.run_diagnosis_thread.daemon = True  # using daemon thread the thread is killed gracefully if program is abruptly closed
        self.run_diagnosis_thread.start()

    def run_diagnosis(self):
        if not os.path.exists(self.input_image_filepath) or not os.path.exists(
                self.output_folderpath):
            self.standardOutputWritten(
                'Process could not be started - The 1st and 2nd above-fields must be filled in.\n'
            )
            return

        self.run_button.setEnabled(False)
        self.prompt_lineedit.clear()
        self.main_display_tabwidget.setCurrentIndex(1)
        QApplication.processEvents(
        )  # to immidiently update GUI after button is clicked
        self.seg_preprocessing_scheme = 'P1' if self.settings_seg_preproc_menu_p1_action.isChecked(
        ) else 'P2'

        try:
            start_time = time.time()
            print('Initialize - Begin (Step 0/6)')
            from diagnosis.main import diagnose_main
            print('Initialize - End (Step 0/6)')
            print('Step runtime: {} seconds.'.format(
                np.round(time.time() - start_time, 3)) + "\n")
            diagnose_main(
                input_volume_filename=self.input_image_filepath,
                input_segmentation_filename=self.input_annotation_filepath,
                output_folder=self.output_folderpath,
                preprocessing_scheme=self.seg_preprocessing_scheme)
        except Exception as e:
            print('{}'.format(traceback.format_exc()))
            self.run_button.setEnabled(True)
            self.standardOutputWritten(
                'Process could not be completed - Issue arose.\n')
            QApplication.processEvents()
            return

        self.run_button.setEnabled(True)
        results_filepath = os.path.join(
            ResourcesConfiguration.getInstance().output_folder, 'report.txt')
        self.results_textedit.setPlainText(open(results_filepath, 'r').read())
        self.main_display_tabwidget.setCurrentIndex(2)

    def run_select_input_image(self):
        input_image_filedialog = QFileDialog()
        self.input_image_filepath = input_image_filedialog.getOpenFileName(
            self, 'Select input T1 MRI', '~',
            "Image files (*.nii *.nii.gz *.nrrd *.mha *.mhd)")[0]
        self.input_image_lineedit.setText(self.input_image_filepath)

    def run_select_input_segmentation(self):
        filedialog = QFileDialog()
        self.input_annotation_filepath = filedialog.getOpenFileName(
            self, 'Select input segmentation file', '~',
            "Image files (*.nii *.nii.gz)")[0]
        self.input_segmentation_lineedit.setText(
            self.input_annotation_filepath)

    def import_dicom_action_triggered(self):
        filedialog = QFileDialog()
        filedialog.setFileMode(QFileDialog.DirectoryOnly)
        self.input_image_filepath = filedialog.getExistingDirectory(
            self, 'Select DICOM folder', '~')
        self.input_image_lineedit.setText(self.input_image_filepath)

    def run_select_output_folder(self):
        filedialog = QFileDialog()
        filedialog.setFileMode(QFileDialog.DirectoryOnly)
        self.output_folderpath = filedialog.getExistingDirectory(
            self, 'Select output folder', '~')
        self.output_folder_lineedit.setText(self.output_folderpath)

    def standardOutputWritten(self, text):
        self.prompt_lineedit.moveCursor(QTextCursor.End)
        self.prompt_lineedit.insertPlainText(text)

        QApplication.processEvents()

    def help_action_triggered(self):
        # opens browser with specified url, directs user to Issues section of GitHub repo
        QDesktopServices.openUrl(
            QUrl("https://github.com/SINTEFMedtek/GSI-RADS/issues"))

    def settings_seg_preproc_menu_p1_action_triggered(self, status):
        if status:
            self.settings_seg_preproc_menu_p2_action.setChecked(False)
        else:
            self.settings_seg_preproc_menu_p2_action.setChecked(True)

    def settings_seg_preproc_menu_p2_action_triggered(self, status):
        if status:
            self.settings_seg_preproc_menu_p1_action.setChecked(False)
        else:
            self.settings_seg_preproc_menu_p1_action.setChecked(True)
Ejemplo n.º 17
0
class PyCalcUi(QMainWindow):
    """PyCalc's View (GUI)."""
    def __init__(self):
        """View initializer."""
        super().__init__()
        # Set some main window's properties
        self.setWindowTitle("PyCalc")
        self.setFixedSize(235, 235)
        # Set the central widget and the general layout
        self.generalLayout = QVBoxLayout()
        self._centralWidget = QWidget(self)
        self.setCentralWidget(self._centralWidget)
        self._centralWidget.setLayout(self.generalLayout)
        # Create the display and the buttons
        self._createDisplay()
        self._createButtons()
        self.show()

    def _createDisplay(self):
        """Create the display."""
        # Create the display widget
        self.display = QLineEdit()
        # Set some display's properties
        self.display.setFixedHeight(35)
        self.display.setAlignment(Qt.AlignRight)
        self.display.setReadOnly(True)
        # Add the display to the general layout
        self.generalLayout.addWidget(self.display)

    def _createButtons(self):
        """Create the buttons."""
        self.buttons = {}
        buttonsLayout = QGridLayout()
        # Button text | position on the QGridLayout
        buttons = {
            "7": (0, 0),
            "8": (0, 1),
            "9": (0, 2),
            "/": (0, 3),
            "C": (0, 4),
            "4": (1, 0),
            "5": (1, 1),
            "6": (1, 2),
            "*": (1, 3),
            "(": (1, 4),
            "1": (2, 0),
            "2": (2, 1),
            "3": (2, 2),
            "-": (2, 3),
            ")": (2, 4),
            "0": (3, 0),
            "00": (3, 1),
            ".": (3, 2),
            "+": (3, 3),
            "=": (3, 4),
        }
        # Create the buttons and add them to the grid layout
        for btnText, pos in buttons.items():
            self.buttons[btnText] = QPushButton(btnText)
            self.buttons[btnText].setFixedSize(40, 40)
            buttonsLayout.addWidget(self.buttons[btnText], pos[0], pos[1])
        # Add buttonsLayout to the general layout
        self.generalLayout.addLayout(buttonsLayout)

    def setDisplayText(self, text):
        """Set display's text."""
        self.display.setText(text)
        self.display.setFocus()

    def displayText(self):
        """Get display's text."""
        return self.display.text()

    def clearDisplay(self):
        """Clear the display."""
        self.setDisplayText("")