コード例 #1
0
class QTimeInputDialog(QDialog):

    def __init__(self, title='', description='', initial=QtCore.QTime(),
                 minValue=QtCore.QTime(), maxValue=QtCore.QTime(),
                 dformat='mm.ss', parent=None):
        super().__init__(parent)

        self.setWindowTitle(title)

        self.setWindowModality(QtCore.Qt.ApplicationModal)
        self.setMaximumSize(300, 110)
        self.setMinimumSize(300, 110)
        self.resize(300, 130)

        self.label = QLabel(description, self)
        self.label.setGeometry(10, 0, 280, 20)
        self.label.setAlignment(QtCore.Qt.AlignCenter)

        self.time = QTimeEdit(self)
        self.time.setDisplayFormat(dformat)
        self.time.setMaximumTime(maxValue)
        self.time.setMinimumTime(minValue)
        self.time.setTime(initial)
        self.time.setGeometry(10, 30, 280, 25)

        self.acceptButton = QPushButton(self)
        self.acceptButton.setGeometry(QtCore.QRect(180, 80, 100, 25))
        self.acceptButton.setText("Ok")

        self.rejectButton = QPushButton(self)
        self.rejectButton.setGeometry(QtCore.QRect(60, 80, 100, 25))
        self.rejectButton.setText("Cancel")

        self.rejectButton.clicked.connect(self.reject)
        self.acceptButton.clicked.connect(self.accept)
    def createEditor(self, parent, option, index):
        editor = QTimeEdit(parent=parent)

        editor.setMinimumTime(datetime.time(hour=8, minute=30, second=30))
        editor.setMaximumTime(datetime.time(hour=23, minute=30, second=30))
        editor.setDisplayFormat("HH:mm:ss")

        # setFrame(): tell whether the line edit draws itself with a frame.
        # If enabled (the default) the line edit draws itself inside a frame, otherwise the line edit draws itself without any frame.
        editor.setFrame(False)

        return editor
    def createEditor(self, parent, option, index):
        editor = QTimeEdit(parent=parent)

        editor.setMinimumTime(datetime.time(hour=8,  minute=30, second=30))
        editor.setMaximumTime(datetime.time(hour=23, minute=30, second=30))
        editor.setDisplayFormat("HH:mm:ss")

        # setFrame(): tell whether the line edit draws itself with a frame.
        # If enabled (the default) the line edit draws itself inside a frame, otherwise the line edit draws itself without any frame.
        editor.setFrame(False)

        return editor
コード例 #4
0
class Window(QWidget):

    def __init__(self):
        super().__init__()

        # Make widgets #################

        self.edit1 = QTimeEdit()
        self.edit2 = QTimeEdit()
        self.edit3 = QTimeEdit()

        self.edit1.setMinimumTime(datetime.time(hour=8, minute=30, second=30))
        self.edit2.setMinimumTime(datetime.time(hour=8, minute=30, second=30))
        self.edit3.setMinimumTime(datetime.time(hour=8, minute=30, second=30))

        self.edit1.setMaximumTime(datetime.time(hour=18, minute=30, second=30))
        self.edit2.setMaximumTime(datetime.time(hour=18, minute=30, second=30))
        self.edit3.setMaximumTime(datetime.time(hour=18, minute=30, second=30))

        self.edit1.setTime(datetime.datetime.now().time())
        self.edit2.setTime(datetime.datetime.now().time())
        self.edit3.setTime(datetime.datetime.now().time())

        # Format: see http://doc.qt.io/qt-5/qdatetime.html#toString-2
        self.edit1.setDisplayFormat("HH:mm")
        self.edit2.setDisplayFormat("HH:mm:ss t")
        self.edit3.setDisplayFormat("h m AP")

        self.btn = QPushButton("Print")

        # Set button slot ##############

        self.btn.clicked.connect(self.printText)

        # Set the layout ###############

        vbox = QVBoxLayout()

        vbox.addWidget(self.edit1)
        vbox.addWidget(self.edit2)
        vbox.addWidget(self.edit3)

        vbox.addWidget(self.btn)

        self.setLayout(vbox)

    def printText(self):
        print(self.edit1.text())
        print(self.edit2.text())
        print(self.edit3.text())
コード例 #5
0
class Window(QWidget):
    def __init__(self):
        super().__init__()

        # Make widgets #################

        self.edit1 = QTimeEdit()
        self.edit2 = QTimeEdit()
        self.edit3 = QTimeEdit()

        self.edit1.setMinimumTime(datetime.time(hour=8, minute=30, second=30))
        self.edit2.setMinimumTime(datetime.time(hour=8, minute=30, second=30))
        self.edit3.setMinimumTime(datetime.time(hour=8, minute=30, second=30))

        self.edit1.setMaximumTime(datetime.time(hour=18, minute=30, second=30))
        self.edit2.setMaximumTime(datetime.time(hour=18, minute=30, second=30))
        self.edit3.setMaximumTime(datetime.time(hour=18, minute=30, second=30))

        self.edit1.setTime(datetime.datetime.now().time())
        self.edit2.setTime(datetime.datetime.now().time())
        self.edit3.setTime(datetime.datetime.now().time())

        # Format: see http://doc.qt.io/qt-5/qdatetime.html#toString-2
        self.edit1.setDisplayFormat("HH:mm")
        self.edit2.setDisplayFormat("HH:mm:ss t")
        self.edit3.setDisplayFormat("h m AP")

        self.btn = QPushButton("Print")

        # Set button slot ##############

        self.btn.clicked.connect(self.printText)

        # Set the layout ###############

        vbox = QVBoxLayout()

        vbox.addWidget(self.edit1)
        vbox.addWidget(self.edit2)
        vbox.addWidget(self.edit3)

        vbox.addWidget(self.btn)

        self.setLayout(vbox)

    def printText(self):
        print(self.edit1.text())
        print(self.edit2.text())
        print(self.edit3.text())
コード例 #6
0
class VCTimeCounter(QWidget):
    timeChanged = pyqtSignal(QTime)

    def __init__(self, parent=None):
        super(VCTimeCounter, self).__init__(parent)
        self.parent = parent
        self.timeedit = QTimeEdit(QTime(0, 0))
        self.timeedit.setObjectName('timeCounter')
        self.timeedit.setStyle(QStyleFactory.create('Fusion'))
        self.timeedit.setFrame(False)
        self.timeedit.setDisplayFormat('hh:mm:ss.zzz')
        self.timeedit.timeChanged.connect(self.timeChangeHandler)
        separator = QLabel('/')
        separator.setObjectName('timeSeparator')
        self.duration = QLabel('00:00:00.000')
        self.duration.setObjectName('timeDuration')
        layout = QHBoxLayout()
        layout.setContentsMargins(0, 0, 0, 0)
        layout.setSpacing(5)
        layout.addWidget(self.timeedit)
        layout.addWidget(separator)
        layout.addWidget(self.duration)
        self.setLayout(layout)

    def setRange(self, minval: str, maxval: str) -> None:
        self.timeedit.setTimeRange(QTime.fromString(minval, 'hh:mm:ss.zzz'),
                                   QTime.fromString(maxval, 'hh:mm:ss.zzz'))

    def setMinimum(self, val: str = None) -> None:
        if val is None:
            self.timeedit.setMinimumTime(QTime(0, 0))
        else:
            self.timeedit.setMinimumTime(QTime.fromString(val, 'hh:mm:ss.zzz'))

    def setMaximum(self, val: str) -> None:
        self.timeedit.setMaximumTime(QTime.fromString(val, 'hh:mm:ss.zzz'))

    def setTime(self, time: str) -> None:
        self.timeedit.setTime(QTime.fromString(time, 'hh:mm:ss.zzz'))

    def setDuration(self, time: str) -> None:
        self.duration.setText(time)
        self.setMaximum(time)

    def clearFocus(self) -> None:
        self.timeedit.clearFocus()

    def hasFocus(self) -> bool:
        if self.timeedit.hasFocus():
            return True
        return super(VCTimeCounter, self).hasFocus()

    def reset(self) -> None:
        self.timeedit.setTime(QTime(0, 0))
        self.setDuration('00:00:00.000')

    def setReadOnly(self, readonly: bool) -> None:
        self.timeedit.setReadOnly(readonly)
        if readonly:
            self.timeedit.setButtonSymbols(QAbstractSpinBox.NoButtons)
        else:
            self.timeedit.setButtonSymbols(QAbstractSpinBox.UpDownArrows)

    @pyqtSlot(QTime)
    def timeChangeHandler(self, newtime: QTime) -> None:
        if self.timeedit.hasFocus():
            self.timeChanged.emit(newtime)
コード例 #7
0
class WindowEmployeeUpdate(QDialog):
    def __init__(self):
        super(WindowEmployeeUpdate, self).__init__()

        self.setWindowTitle("Update Employee Details")
        self.set_layout()

    def set_layout(self):
        #Set up basic Stuff here
        vbox = QVBoxLayout()
        group1 = QGroupBox("Employee Update")
        form1 = QFormLayout()
        group1.setLayout(form1)
        #Set Nane
        self.namelabel = QLabel("Name")
        self.nameLineEdit = QLineEdit("")
        self.nameLineEdit.setEnabled(False)
        form1.setWidget(0, QFormLayout.LabelRole, self.namelabel)
        form1.setWidget(0, QFormLayout.FieldRole, self.nameLineEdit)

        #Set Date Label
        self.datelabel = QLabel("Date Started")
        self.dateLineEdit = QDateEdit()
        self.dateLineEdit.setDate(QDate(2021, 1, 1))
        self.dateLineEdit.setCalendarPopup(True)
        form1.setWidget(1, QFormLayout.LabelRole, self.datelabel)
        form1.setWidget(1, QFormLayout.FieldRole, self.dateLineEdit)

        # set Time Started
        self.timestartlabel = QLabel("Time Started")
        self.updatestartLineEdit = QTimeEdit()
        # Set time constrain
        self.updatestartLineEdit.timeChanged.connect(self.connect_start_end)
        #Add to form Widget
        form1.setWidget(2, QFormLayout.LabelRole, self.timestartlabel)
        form1.setWidget(2, QFormLayout.FieldRole, self.updatestartLineEdit)
        # set Time Ended
        self.timeendedlabel = QLabel("Time Ended")
        self.updateendeLineEdit = QTimeEdit()
        # connect min time of endtime as starttime
        self.updateendeLineEdit.timeChanged.connect(
            self.connect_min_time)  #you can use lambda function to get 1 line
        # Add to form Widget
        form1.setWidget(3, QFormLayout.LabelRole, self.timeendedlabel)
        form1.setWidget(3, QFormLayout.FieldRole, self.updateendeLineEdit)

        ##ADD BUTTON
        self.updatebtn = QPushButton("Update Employee")
        self.updatebtn.clicked.connect(self.saved_messagebox)

        ## ADD ITEMS TO LAYOUT
        vbox.addWidget(group1)
        vbox.addWidget(self.updatebtn, 0, Qt.AlignHCenter)
        self.setLayout(vbox)

    def connect_start_end(self):
        self.updateendeLineEdit.setTime(self.updatestartLineEdit.time())

    def connect_min_time(self):
        self.updateendeLineEdit.setMinimumTime(self.updateendeLineEdit.time())

    def saved_messagebox(self):
        if self.nameLineEdit.text() != "":
            QMessageBox.information(self, "Information",
                                    "Details Updated Successfully")
            self.accept()
        elif self.nameLineEdit.text() == "":
            QMessageBox.warning(self, "Warning", "All Boxes Must be Filled")
コード例 #8
0
class WindowEmployeeAdd(QDialog):
    def __init__(self):
        super(WindowEmployeeAdd, self).__init__()

        self.setWindowTitle("Add Employee")
        self.set_layout()

    def set_layout(self):
        # Set up basic Stuff here
        vbox = QVBoxLayout()
        group1 = QGroupBox("Employee")
        form1 = QFormLayout()
        group1.setLayout(form1)

        self.namelabel = QLabel("Name")
        self.nameLineEdit = QLineEdit("")
        self.nameLineEdit.setPlaceholderText("Enter Employee Name")
        form1.setWidget(0, QFormLayout.LabelRole, self.namelabel)
        form1.setWidget(0, QFormLayout.FieldRole, self.nameLineEdit)

        datelabel = QLabel("Date Started")
        self.dateLineEdit = QDateEdit()
        self.dateLineEdit.setDate(QDate(2021, 1, 1))
        self.dateLineEdit.setCalendarPopup(True)
        form1.setWidget(1, QFormLayout.LabelRole, datelabel)
        form1.setWidget(1, QFormLayout.FieldRole, self.dateLineEdit)

        self.timestartlabel = QLabel("Time Started")
        self.timestartLineEdit = QTimeEdit()
        self.timestartLineEdit.setTime(QTime(7, 0, 0))
        # Set time constrain
        self.timestartLineEdit.timeChanged.connect(self.connect_start_end)
        form1.setWidget(2, QFormLayout.LabelRole, self.timestartlabel)
        form1.setWidget(2, QFormLayout.FieldRole, self.timestartLineEdit)

        timeendedlabel = QLabel("Time Ended")
        self.timeendeLineEdit = QTimeEdit()
        self.timeendeLineEdit.setTime(QTime(self.timestartLineEdit.time()))
        # connect min time of endtime as starttime
        self.timeendeLineEdit.timeChanged.connect(
            self.set_min_time)  # you can use lambda function to get 1 line
        form1.setWidget(3, QFormLayout.LabelRole, timeendedlabel)
        form1.setWidget(3, QFormLayout.FieldRole, self.timeendeLineEdit)

        ##Group 2 (Employer)
        group2 = QGroupBox("Employer")
        form2 = QFormLayout()
        group2.setLayout(form2)
        # Add items to form
        amountlabel = QLabel("Amount Paid Per Hour")
        self.amountLine = QLineEdit("$5.00")
        self.amountLine.setEnabled(False)

        form2.setWidget(0, QFormLayout.LabelRole, amountlabel)
        form2.setWidget(0, QFormLayout.FieldRole, self.amountLine)

        ##ADD BUTTON
        self.addbtn = QPushButton("Add Emmployee")
        self.addbtn.clicked.connect(self.saved_messagebox)

        ## ADD ITEMS TO LAYOUT
        vbox.addWidget(group1)
        vbox.addWidget(group2)
        vbox.addWidget(self.addbtn, 0, Qt.AlignHCenter)
        self.setLayout(vbox)

    def connect_start_end(self):
        self.timeendeLineEdit.setTime(self.timestartLineEdit.time())

    def set_min_time(self):
        self.timeendeLineEdit.setMinimumTime(self.timestartLineEdit.time())

    def saved_messagebox(self):
        if self.nameLineEdit.text() != "":
            QMessageBox.information(self, "Information",
                                    "Details Saved Successfully")
            self.accept()
        elif self.nameLineEdit.text() == "":
            QMessageBox.warning(self, "Warning", "All Boxes Must be Filled")
コード例 #9
0
class VideoWindow(QWidget):
    def __init__(self, vidPath):
        super().__init__()
        self.fullPath = vidPath
        self.startTime = 0
        self.endTime = 0
        self.init_ui()

    def init_ui(self):
        layout = QVBoxLayout()
        self.setLayout(layout)
        self.setWindowTitle(self.fullPath)

        self.mediaPlayer = QMediaPlayer(None, QMediaPlayer.VideoSurface)

        self.videoWidget = QVideoWidget()

        self.playButton = QPushButton()
        self.playButton.setEnabled(True)
        self.playButton.setIcon(self.style().standardIcon(QStyle.SP_MediaPlay))
        self.playButton.setFixedWidth(100)
        self.playButton.setFixedHeight(50)
        self.playButton.clicked.connect(self.play)

        self.trimButton = QPushButton("Trim")
        self.trimButton.setFixedWidth(150)
        self.trimButton.setFixedHeight(50)
        self.trimButton.clicked.connect(self.trimVid)

        self.positionSlider = QSlider(QtCore.Qt.Horizontal)
        self.positionSlider.setRange(0, 0)
        self.positionSlider.sliderMoved.connect(self.setPosition)

        self.rangeSlider = qrangeslider.QRangeSlider()
        self.rangeSlider.setRange(0, 0)
        self.rangeSlider.endValueChanged.connect(self.adjustForEnd)
        self.rangeSlider.startValueChanged.connect(self.adjustForStart)
        self.rangeSlider.setFixedHeight(15)

        self.startTimeInput = QTimeEdit()
        self.endTimeInput = QTimeEdit()
        self.startTimeInput.setDisplayFormat('hh:mm:ss.zzz')
        self.endTimeInput.setDisplayFormat('hh:mm:ss.zzz')

        self.startTimeInput.timeChanged.connect(self.startInputChanged)
        self.endTimeInput.timeChanged.connect(self.endInputChanged)

        self.mediaPlayer.setMedia(
            QMediaContent(QtCore.QUrl.fromLocalFile(self.fullPath)))

        layout.addWidget(self.videoWidget)
        self.mediaPlayer.setVideoOutput(self.videoWidget)
        self.mediaPlayer.setNotifyInterval(10)
        self.mediaPlayer.stateChanged.connect(self.mediaStateChanged)
        self.mediaPlayer.positionChanged.connect(self.positionChanged)
        self.mediaPlayer.durationChanged.connect(self.durationChanged)

        controlLayout = QVBoxLayout()
        controlLayout.setContentsMargins(0, 0, 0, 0)
        controlLayout.addWidget(self.rangeSlider)
        controlLayout.addWidget(self.positionSlider)

        timeInputLayout = QHBoxLayout()
        timeInputLayout.addWidget(self.playButton)
        timeInputLayout.addWidget(self.startTimeInput)
        timeInputLayout.addWidget(self.endTimeInput)
        timeInputLayout.addWidget(self.trimButton)

        controlLayout.addLayout(timeInputLayout)

        layout.addLayout(controlLayout)

        self.mediaPlayer.play()

        self.resize(1024, 700)

        self.show()

    def closeEvent(self, event):
        self.mediaPlayer.stop()
        self.videoWidget.setParent(None)
        self.mediaPlayer.setParent(None)
        self.mediaPlayer.deleteLater()
        self.videoWidget.deleteLater()

    def trimVid(self):
        self.trimButton.setEnabled(False)
        outName = mytools.getAvailableName(self.fullPath, 'Trim')
        print(outName)
        trimStartTime = self.startTimeInput.time().toString('hh:mm:ss.zzz')
        trimEndTime = self.endTimeInput.time().toString('hh:mm:ss.zzz')
        try:
            ff = FFmpeg(inputs={self.fullPath: None},
                        outputs={
                            outName: [
                                '-ss',
                                trimStartTime,
                                '-to',
                                trimEndTime,
                                '-c:v',
                                'copy',
                                '-c:a',
                                'copy',
                            ]
                        })
            ff.run()
        except Exception as e:
            msg = QMessageBox()
            msg.setWindowTitle("Trim Failed")
            msg.setText(str(e))
            msg.setIcon(QMessageBox.Critical)

            showMsg = msg.exec_()
        self.trimButton.setEnabled(True)

    def play(self):
        if self.mediaPlayer.state() == QMediaPlayer.PlayingState:
            self.mediaPlayer.pause()
        else:
            self.mediaPlayer.play()

    def mediaStateChanged(self, state):
        if self.mediaPlayer.state() == QMediaPlayer.PlayingState:
            self.playButton.setIcon(self.style().standardIcon(
                QStyle.SP_MediaPause))
        else:
            self.playButton.setIcon(self.style().standardIcon(
                QStyle.SP_MediaPlay))

    def positionChanged(self, position):
        self.positionSlider.setValue(position)
        if position > self.endTime:
            self.mediaPlayer.setPosition(self.startTime)

    def adjustForStart(self, startPos):
        self.startTime = startPos
        self.mediaPlayer.setPosition(startPos)

        self.startTimeInput.setTime(QtCore.QTime(0, 0).addMSecs(startPos))
        self.endTimeInput.setMinimumTime(QtCore.QTime(0, 0).addMSecs(startPos))

    def adjustForEnd(self, endPos):
        self.endTime = endPos
        if self.positionSlider.value() > endPos:
            self.mediaPlayer.setPosition(endPos)

        self.endTimeInput.setTime(QtCore.QTime(0, 0).addMSecs(endPos))
        self.startTimeInput.setMaximumTime(QtCore.QTime(0, 0).addMSecs(endPos))

    def startInputChanged(self, inputTime):
        self.rangeSlider.setStart(QtCore.QTime(0, 0, 0, 0).msecsTo(inputTime))

    def endInputChanged(self, inputTime):
        self.rangeSlider.setEnd(QtCore.QTime(0, 0, 0, 0).msecsTo(inputTime))

    def durationChanged(self, duration):
        self.positionSlider.setRange(0, duration)
        self.rangeSlider.setMax(duration)
        self.rangeSlider.setEnd(duration)

        self.startTimeInput.setMinimumTime(QtCore.QTime(0, 0))
        self.endTimeInput.setMinimumTime(QtCore.QTime(0, 0))
        self.endTimeInput.setTime(QtCore.QTime(0, 0).addMSecs(duration))
        self.startTimeInput.setMaximumTime(
            QtCore.QTime(0, 0).addMSecs(duration))
        self.endTimeInput.setMaximumTime(QtCore.QTime(0, 0).addMSecs(duration))

    def setPosition(self, position):
        self.mediaPlayer.setPosition(position)
コード例 #10
0
class QFrameSelect(QWidget):
    frameSelectionChanged = pyqtSignal(int, QTime)

    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        layout = QVBoxLayout()
        self.setLayout(layout)

        self.slider = Slider(self)
        self.slider.setOrientation(Qt.Horizontal)
        self.slider.valueChanged.connect(self._handleSliderChange)
        self.slider.setTickInterval(1)

        layout.addWidget(self.slider)

        hlayout = QHBoxLayout()
        layout.addLayout(hlayout)

        self.leftLabel = QLabel(self)

        self.spinBox = QSpinBox(self)
        self.spinBox.valueChanged.connect(self._handleSpinboxChange)

        self.currentTime = QTimeEdit(self)
        self.currentTime.setDisplayFormat("H:mm:ss.zzz")
        self.currentTime.timeChanged.connect(self._handleTimeEditChange)
        self.currentTime.editingFinished.connect(self._handleTimeEditFinished)

        self.rightLabel = QLabel(self)

        hlayout.addWidget(self.leftLabel)
        hlayout.addStretch()
        hlayout.addWidget(QLabel("Frame index:", self))
        hlayout.addWidget(self.spinBox)
        hlayout.addWidget(QLabel("Timestamp:", self))
        hlayout.addWidget(self.currentTime)
        hlayout.addStretch()
        hlayout.addWidget(self.rightLabel)

        self.setPtsTimeArray(None)

    def setValue(self, n):
        self.slider.setValue(n)

    def setMinimum(self, n=0):
        self.slider.setMinimum(n)
        self.spinBox.setMinimum(n)

        ms = int(self.pts_time[n] * 1000 + 0.5)
        s, ms = divmod(ms, 1000)
        m, s = divmod(s, 60)
        h, m = divmod(m, 60)

        self.currentTime.setMinimumTime(QTime(h, m, s, ms))
        self.leftLabel.setText(f"{n} ({h}:{m:02d}:{s:02d}.{ms:03d})")

    def setMaximum(self, n=None):
        if n is None:
            n = len(self.pts_time) - 1

        self.slider.setMaximum(n)
        self.spinBox.setMaximum(n)

        ms = int(self.pts_time[n] * 1000 + 0.5)
        s, ms = divmod(ms, 1000)
        m, s = divmod(s, 60)
        h, m = divmod(m, 60)

        self.currentTime.setMaximumTime(QTime(h, m, s, ms))
        self.rightLabel.setText(f"{n} ({h}:{m:02d}:{s:02d}.{ms:03d})")

    def setStartEndVisible(self, value):
        self.leftLabel.setHidden(not bool(value))
        self.rightLabel.setHidden(not bool(value))

    def setPtsTimeArray(self, pts_time=None):
        self.pts_time = pts_time

        if pts_time is not None:
            N = len(pts_time)
            self.setMinimum(0)
            self.setMaximum(N - 1)

            self.slider.setValue(0)
            self.slider.setSnapValues(None)

            self.slider.setDisabled(False)
            self.spinBox.setDisabled(False)
            self.currentTime.setDisabled(False)

        else:
            self.slider.setMinimum(0)
            self.slider.setMaximum(0)
            self.slider.setSnapValues(None)
            self.slider.setDisabled(True)
            self.spinBox.setDisabled(True)
            self.currentTime.setDisabled(True)

    def _handleSliderChange(self, n):
        self.spinBox.blockSignals(True)
        self.spinBox.setValue(n)
        self.spinBox.blockSignals(False)

        pts_time = self.pts_time[n]
        ms = int(pts_time * 1000 + 0.5)
        s, ms = divmod(ms, 1000)
        m, s = divmod(s, 60)
        h, m = divmod(m, 60)

        self.currentTime.blockSignals(True)
        self.currentTime.setTime(QTime(h, m, s, ms))
        self.currentTime.blockSignals(False)

        self.frameSelectionChanged.emit(n, QTime(h, m, s, ms))

    def _handleSpinboxChange(self, n):
        self.slider.blockSignals(True)
        self.slider.setValue(n)
        self.slider.blockSignals(False)

        pts_time = self.pts_time[n]
        ms = int(pts_time * 1000 + 0.5)
        s, ms = divmod(ms, 1000)
        m, s = divmod(s, 60)
        h, m = divmod(m, 60)

        self.currentTime.blockSignals(True)
        self.currentTime.setTime(QTime(h, m, s, ms))
        self.currentTime.blockSignals(False)

        self.frameSelectionChanged.emit(n, QTime(h, m, s, ms))

    def _handleTimeEditChange(self, t):
        pts = t.msecsSinceStartOfDay() / 1000

        try:
            n = search(self.pts_time, pts + 0.0005, dir="-")

        except IndexError:
            n = 0

        if n != self.slider.value():
            self.slider.blockSignals(True)
            self.slider.setValue(n)
            self.slider.blockSignals(False)

            self.spinBox.blockSignals(True)
            self.spinBox.setValue(n)
            self.spinBox.blockSignals(False)

            pts_time = self.pts_time[n]
            ms = int(pts_time * 1000 + 0.5)
            s, ms = divmod(ms, 1000)
            m, s = divmod(s, 60)
            h, m = divmod(m, 60)

            self.frameSelectionChanged.emit(n, QTime(h, m, s, ms))

    def _handleTimeEditFinished(self):
        t = self.currentTime.time()
        pts = t.msecsSinceStartOfDay() / 1000
        n = search(self.pts_time, pts + 0.0005, dir="-")
        pts_time = self.pts_time[n]

        ms = int(pts_time * 1000 + 0.5)
        s, ms = divmod(ms, 1000)
        m, s = divmod(s, 60)
        h, m = divmod(m, 60)
        T = QTime(h, m, s, ms)

        if t != T:
            self.currentTime.setTime(T)
コード例 #11
0
class SettingsWindow(QMainWindow):
    def __init__(self, screens):
        super().__init__()

        self._init_ui()

        self.addButton.clicked.connect(self.on_add)
        self.deleteButton.clicked.connect(self.on_delete)
        self.upButton.clicked.connect(self.on_up)
        self.downButton.clicked.connect(self.on_down)
        self.startButton.clicked.connect(self.on_start)
        self.saveButton.clicked.connect(self.on_save)
        self.loadButton.clicked.connect(self.on_load)

        self.gradientWindowController = GradientWindowController(screens)

        self._load_settings()

    def _create_color_tab(self):
        self.colorWidget = QWidget()
        self.colorWidget.setAutoFillBackground(True)

        self.colorsLayout = QHBoxLayout()

        self.colorTable = QTableWidget()
        self.colorTable.setRowCount(0)
        self.colorTable.setColumnCount(1)
        self.colorTable.verticalHeader().hide()
        self.colorTable.horizontalHeader().hide()
        self.colorTable.setMaximumWidth(40)
        self.colorTable.setColumnWidth(20, 30)

        self.colorButtonsLayout = QVBoxLayout()
        self.addButton = QPushButton('Добавить')
        self.upButton = QPushButton('Вверх')
        self.downButton = QPushButton('Вниз')
        self.deleteButton = QPushButton('Удалить')
        self.colorButtonsLayout.addWidget(self.addButton)
        self.colorButtonsLayout.addWidget(self.upButton)
        self.colorButtonsLayout.addWidget(self.downButton)
        self.colorButtonsLayout.addWidget(self.deleteButton)
        self.colorButtonsLayout.addStretch()

        self.colorsLayout.addWidget(self.colorTable)
        self.colorsLayout.addStretch()
        self.colorsLayout.addLayout(self.colorButtonsLayout)
        self.colorWidget.setLayout(self.colorsLayout)

        return self.colorWidget

    def _create_intervals_tab(self):
        self.intervalsWidget = QWidget()
        self.intervalsWidget.setAutoFillBackground(True)

        self.intervalsLayout = QVBoxLayout()
        self.delayInput = QTimeEdit()
        self.delayInput.setDisplayFormat('hh:mm:ss')
        self.delayInput.setMinimumTime(QTime(0, 0, 1))
        self.repeatInput = QTimeEdit()
        self.repeatInput.setDisplayFormat('hh:mm:ss')
        self.repeatInput.setMinimumTime(QTime(0, 0, 1))
        self.intervalsLayout.addWidget(QLabel('Первый цвет'))
        self.intervalsLayout.addWidget(self.delayInput)
        self.intervalsLayout.addWidget(QLabel('Интервал'))
        self.intervalsLayout.addWidget(self.repeatInput)
        self.intervalsLayout.addStretch()

        self.intervalsWidget.setLayout(self.intervalsLayout)

        return self.intervalsWidget

    def _init_ui(self):
        self.central = QWidget()

        self.centralLayout = QVBoxLayout()

        self.tabWidget = QTabWidget()
        self.tabWidget.addTab(self._create_color_tab(), 'Цвета')
        self.tabWidget.addTab(self._create_intervals_tab(), 'Интервалы')

        self.centralLayout.addWidget(self.tabWidget)

        self.errorLabel = QLabel()

        self.centralLayout.addWidget(self.errorLabel)

        self.settingsButtonsLayout = QHBoxLayout()
        self.saveButton = QPushButton('Сохранить')
        self.loadButton = QPushButton('Загрузить')
        self.startButton = QPushButton('Запустить')
        self.settingsButtonsLayout.addWidget(self.saveButton)
        self.settingsButtonsLayout.addWidget(self.loadButton)
        self.settingsButtonsLayout.addWidget(self.startButton)

        self.centralLayout.addLayout(self.settingsButtonsLayout)

        self.central.setLayout(self.centralLayout)

        self.setCentralWidget(self.central)

    @pyqtSlot()
    def on_add(self):
        color = QColorDialog.getColor()
        item = QTableWidgetItem()
        item.setBackground(color)

        table: QTableWidget = self.colorTable
        table.insertRow(table.rowCount())
        table.setItem(table.rowCount() - 1, 0, item)

    @pyqtSlot()
    def on_delete(self):
        table: QTableWidget = self.colorTable
        selected = table.selectedIndexes()
        rows = [index.row() for index in selected]
        for row in rows:
            table.removeRow(row)

    @staticmethod
    def _swap_items(table: QTableWidget, row1, col1, row2, col2):
        item1 = table.takeItem(row1, col1)
        item2 = table.takeItem(row2, col2)
        table.setItem(row1, col1, item2)
        table.setItem(row2, col2, item1)

    @pyqtSlot()
    def on_up(self):
        table: QTableWidget = self.colorTable

        selected = table.selectedIndexes()
        if selected:
            rows = [index.row() for index in selected]

            prev_row = 0
            for row in sorted(rows):
                if row > prev_row:
                    SettingsWindow._swap_items(table, row, 0, row - 1, 0)
                else:
                    prev_row += 1

            table.clearSelection()
            table.setRangeSelected(
                QTableWidgetSelectionRange(min(rows) - 1, 0,
                                           max(rows) - 1, 0), True)

    @pyqtSlot()
    def on_down(self):
        table: QTableWidget = self.colorTable

        selected = table.selectedIndexes()
        if selected:
            rows = [index.row() for index in selected]

            next_row = table.rowCount() - 1
            for row in sorted(rows, reverse=True):
                if row < next_row:
                    SettingsWindow._swap_items(table, row, 0, row + 1, 0)
                else:
                    next_row -= 1

            table.clearSelection()
            table.setRangeSelected(
                QTableWidgetSelectionRange(min(rows) + 1, 0,
                                           max(rows) + 1, 0), True)

    @pyqtSlot()
    def on_start(self):
        table: QTableWidget = self.colorTable

        items = [table.item(row, 0) for row in range(table.rowCount())]
        colors = [item.background().color() for item in items]

        if not colors:
            self.errorLabel.setText('цвета добавь')
            return

        if len(colors) < 2:
            self.errorLabel.setText('давай побольше цветов')
            return

        if self.errorLabel.text():
            self.errorLabel.setText('молодец')

        delay = QTime(0, 0).secsTo(self.delayInput.time())
        repeat_interval = QTime(0, 0).secsTo(self.repeatInput.time())

        self.gradientWindowController.set_colors(colors)
        self.gradientWindowController.set_timers(delay, repeat_interval)
        self.gradientWindowController.run()

    @pyqtSlot()
    def on_save(self):
        table: QTableWidget = self.colorTable

        settings = dict()

        items = [table.item(row, 0) for row in range(table.rowCount())]
        colors = [item.background().color() for item in items]
        rgb_colors = [color.getRgb() for color in colors]

        settings['colors'] = rgb_colors
        settings['delay'] = QTime(0, 0).secsTo(self.delayInput.time())
        settings['repeat_interval'] = QTime(0,
                                            0).secsTo(self.repeatInput.time())

        filename = QFileDialog.getSaveFileName(directory='settings.json')[0]
        if filename:
            with open(filename, 'w') as f:
                json.dump(settings, f)

            self.errorLabel.setText(f'настройки сохранены в {filename}')

    def _load_settings(self, filename='settings.json'):
        try:
            with open(filename) as f:
                settings = json.load(f)

                table: QTableWidget = self.colorTable
                table.setRowCount(0)

                for rgb_color in settings['colors']:
                    color = QColor.fromRgb(*rgb_color)

                    item = QTableWidgetItem()
                    item.setBackground(color)

                    table.insertRow(table.rowCount())
                    table.setItem(table.rowCount() - 1, 0, item)

                self.delayInput.setTime(QTime(0, 0).addSecs(settings['delay']))
                self.repeatInput.setTime(
                    QTime(0, 0).addSecs(settings['repeat_interval']))
            self.errorLabel.setText(f'настройки загружены из {filename}')

        except FileNotFoundError:
            pass
        except json.JSONDecodeError or KeyError or TypeError:
            self.errorLabel.setText(f'в {filename} ошибка')

    @pyqtSlot()
    def on_load(self):
        filename = QFileDialog.getOpenFileName()[0]
        if filename:
            self._load_settings(filename)