def createCalendar(self): vbox = QVBoxLayout() calendar = QCalendarWidget() calendar.setGridVisible( True) #can be removed only makes the calendar squares visible vbox.addWidget(calendar) self.setLayout(vbox)
def riqikuangxuanxiang(self, zujian: QLineEdit, show_action: QAction, rili: QCalendarWidget, def_qj, showDate): # zujian.setInputMask("0000-00-00") #格式限制 # for i in range(4): # name = zujian.objectName() + str(i) # # locals()['v' + str(i)] = i # print(name) # self.show_action = zujian.objectName() # self.rili = jiemian.objectName() # print(self.show_action) # print(self.rili) # zj = zujian.objectName() # jm = jiemian.objectName() # self.show_action = locals() #为了生成多个变量 # self.rili = locals() # self.show_action[zj] = QAction(self) #创建控件 show_action.setIcon(QIcon('ICO/png/1234864.png')) #设置控件图标 zujian.addAction(show_action, QLineEdit.TrailingPosition) #控件放置位置 show_action.triggered.connect(def_qj) # 信号和槽连接 # self.rili[jm] = QCalendarWidget(jiemian) rili.selectedDate() # 获取选中日期,默认当前系统时间 rili.setGridVisible(True) # 是否显示日期之间的网格 rili.setGeometry(zujian.x(), zujian.y() + zujian.height() + 62, 280, 200) #日历控件位置 rili.setFocusPolicy(Qt.ClickFocus) rili.hide() # 隐藏日期控件 # date = self.rili.selectedDate()#获取选中日期,默认当前系统时间 rili.clicked[QDate].connect( showDate) #clicked[参数],即定义showDate是传入的参数类型设置
class DateDialog(QDialog): def __init__(self, parent=None, title=""): super(DateDialog, self).__init__(parent) layout = QGridLayout(self) self.setStyleSheet("") self.calendar = QCalendarWidget(self) self.calendar.setStyleSheet("") self.setWindowTitle(title) buttons = QWidget(self) buttons_layout = QGridLayout(buttons) self.enter_button = QPushButton("Enter", self) self.enter_button.clicked.connect(self.enter) self._not_canceled = False self.cancel_button = QPushButton("Cancel", self) self.cancel_button.clicked.connect(self.close) buttons_layout.addWidget(self.enter_button, 0, 0) buttons_layout.addWidget(self.cancel_button, 0, 1) layout.addWidget(self.calendar) layout.addWidget(buttons) self._date = "" def enter(self): self._not_canceled = True self._date = self.calendar.selectedDate().toString("MM/dd/yyyy") self.close() def getDate(self): return self._date def notCanceled(self): return self._not_canceled
def create_new_show(self): w = QDialog() w.setWindowTitle("Create New Show") w.setLayout(QFormLayout()) show_name = QLineEdit("New Show") w.layout().addRow(QLabel("New Show Title:"), show_name) prod_days = QSpinBox() w.layout().addRow(QLabel("Days of production:"), prod_days) calendar_input = QCalendarWidget() w.layout().addRow(QLabel("Start date:")) w.layout().addRow(calendar_input) if self.shows: # If a show has already been created. previous_show = self.shows[-1] prod_days.setValue(previous_show.prod_days) accept = QPushButton("Create") accept.clicked.connect(w.accept) reject = QPushButton("Cancel") reject.clicked.connect(w.reject) w.layout().addRow(accept, reject) if w.exec_() == QDialog.Accepted: print("New show name:", show_name.text(), "Days of pre-production", prod_days.value()) selected_date = calendar_input.selectedDate() start_date = datetime.date(selected_date.year(), selected_date.month(), selected_date.day()) self.shows.append( Show(show_name.text(), prod_days.value(), start_date))
def __init__(self): super().__init__() self.calendar = QCalendarWidget() self.setWindowTitle("Pyside2 Calendar") self.setGeometry(300, 200, 500, 400) self.create_calender() self.show()
def createCalendar(self): vbox = QVBoxLayout() self.calendar = QCalendarWidget() self.calendar.setGridVisible(True) vbox.addWidget(self.calendar) # Met le calendirer dans le layout self.setLayout(vbox) #Associe le layout à la fenêtre
def __init__(self, widget, parent=None): super(MainWindow, self).__init__(parent) # Set window title self.setWindowTitle("CoBolt") self.setCentralWidget(widget) # Initiat menu self.menu = self.menuBar() self.file_menu = self.menu.addMenu("File") # Set exit exit_action = QAction("Exit", self) exit_action.setShortcut(QKeySequence.Quit) exit_action.triggered.connect(self.close) self.file_menu.addAction(exit_action) # Status bar self.status = self.statusBar() self.status.showMessage("Hei, dette er CoBolt!") # Window dimensions geometry = qApp.desktop().availableGeometry(self) #self.setFixedSize(geometry.width() * 0.8, geometry.height() * 0.7) self.resize(geometry.width() * 0.8, geometry.height() * 0.7) # Create widgets self.edit = QLineEdit("Write my name here") self.button = QPushButton("Show Greetings") self.button2 = QPushButton("Clear") self.calender = QCalendarWidget() # Create layout and add widgets # layout = QVBoxLayout() layout.addWidget(self.edit) #layout.addWidget(self.button2) # layout2 = QVBoxLayout() layout2.addWidget(self.button) layout2.addWidget(self.button2) layout2.insertStretch(1) layout2.insertStretch(2) # # layout3 = QHBoxLayout() layout3.addLayout(layout) layout3.addLayout(layout2) # Set dialog layout self.setLayout(layout3) # Add button signal to greetings slot self.button.clicked.connect(self.greetings) self.button2.clicked.connect(self.cleartext)
def __init__(self, user: User): super().__init__() logging.debug("MainWindow creation") self.ui = Ui_MainWindow(self) self.retranslate_ui() self.set_offer_ui_enabled(False) self.font_database = QFontDatabase() self.font_database.addApplicationFont(':/font-regular') self.font_database.addApplicationFont(':/font-medium') self.font_database.addApplicationFont(':/font-bold') self.offer_font = self.font_database.font('Montserrat', 'Regular', 7) logging.info(f"Loaded font for offer print: {self.offer_font.family()} {self.offer_font.styleName()}") self.offer = None self.user = user self.calendar = QCalendarWidget() self.ui.action_new.triggered.connect(self.new_offer) self.ui.action_open.triggered.connect(self.load_offer) self.ui.action_save.triggered.connect(self.save_offer) self.ui.action_new_number.triggered.connect(self.new_offer_symbol) self.ui.action_exit.triggered.connect(self.exit) self.ui.action_print.triggered.connect(self.print_preview) self.ui.action_PDF.triggered.connect(self.print_pdf) self.ui.action_create_merchandise.triggered.connect(self.create_merchandise) self.ui.action_create_customer.triggered.connect(self.create_customer) self.ui.action_about.triggered.connect(self.about) self.ui.action_about_Qt.triggered.connect(self.about_qt) self.ui.push_button_add_merchandise.clicked.connect(self.select_merchandise) self.ui.push_button_remove_row.clicked.connect(self.remove_row) self.ui.push_button_discount.clicked.connect(self.set_discount) self.ui.push_button_discount_group.clicked.connect(self.set_discount_group) self.ui.command_link_button_customer.clicked.connect(self.select_customer) self.ui.check_box_query_date.stateChanged.connect(self.inquiry_date_toggled) self.ui.line_edit_query_date.textChanged.connect(self.inquiry_date_text_changed) self.ui.push_button_query_date.clicked.connect(self.inquiry_date_button_clicked) self.ui.check_box_query_number.stateChanged.connect(self.inquiry_number_toggled) self.ui.line_edit_query_number.textChanged.connect(self.inquiry_number_changed) self.ui.command_link_button_delivery.clicked.connect(self.select_delivery_terms) self.ui.command_link_button_offer.clicked.connect(self.select_offer_terms) self.ui.command_link_button_billing.clicked.connect(self.select_billing_terms) self.ui.command_link_button_delivery_date.clicked.connect(self.select_delivery_date_terms) self.ui.plain_text_edit_remarks.textChanged.connect(self.update_remarks) # must be connected at the end or will break tests self.calendar.clicked.connect(self.inquiry_date_changed)
def riqikuangxuanxiang(self, zujian: QLineEdit): # show_signal = pyqtSignal() # 点击下拉框发送信号 # zujian.curDateTime.toString('yyyy/MM/dd') self.show_action = QAction(self) self.show_action.setIcon(QIcon('ICO/png/1234864.png')) zujian.addAction(self.show_action, QLineEdit.TrailingPosition) self.show_action.triggered.connect(self.openCalendar) # 信号和槽连接 self.rili = QCalendarWidget(self) self.rili.setGridVisible(True) # 是否显示日期之间的网格 self.rili.setGeometry(zujian.x(), 140, 280, 200) #日历控件位置 self.rili.hide() # 隐藏日期控件 # date = self.rili.selectedDate()#获取选中日期,默认当前系统时间 self.rili.clicked[QDate].connect( self.showDate) #clicked[参数],即定义showDate是传入的参数类型设置
class Window(QWidget): def __init__(self): super().__init__() self.calendar = QCalendarWidget() self.setWindowTitle("Pyside2 Calendar") self.setGeometry(300, 200, 500, 400) self.create_calender() self.show() def create_calender(self): vbox = QVBoxLayout() self.calendar.setGridVisible(True) vbox.addWidget(self.calendar) self.setLayout(vbox)
def createCalendar(self): vbox = QVBoxLayout() self._calendar = QCalendarWidget() self._calendar.setGridVisible(True) self._calendar.setFirstDayOfWeek(Qt.Monday) vbox.addWidget(self._calendar) self.setLayout(vbox) self._buttonBox = QtWidgets.QDialogButtonBox(self) self._buttonBox.setOrientation(QtCore.Qt.Horizontal) self._buttonBox.setStandardButtons(QtWidgets.QDialogButtonBox.Ok | QtWidgets.QDialogButtonBox.Cancel) self._buttonBox.layout().setDirection(QBoxLayout.RightToLeft) self._buttonBox.button(QtWidgets.QDialogButtonBox.Ok).clicked.connect( self._onOk) self._buttonBox.button( QtWidgets.QDialogButtonBox.Cancel).clicked.connect(self._onCancel) vbox.addWidget(self._buttonBox)
def initUI(self): vbox = QVBoxLayout(self) cal = QCalendarWidget(self) cal.setGridVisible(True) cal.clicked[QDate].connect(self.showDate) vbox.addWidget(cal) date = cal.selectedDate() self.lbl = QLabel(self) self.lbl.setText(date.toString()) vbox.addWidget(self.lbl) self.setLayout(vbox) self.setGeometry(300, 300, 350, 300) self.setWindowTitle('Calendar控件') self.show()
def createCalendar(self): vbox = QVBoxLayout( ) #vbox stands for vertical box, where the QVBox layout sets the attributes for the object self.calendar = QCalendarWidget() # self.calendar.setGridVisible(True) vbox.addWidget(self.calendar) self.setLayout(vbox)
def __init__(self, parent=None): from ..ui.time_series_fixed_resolution_editor import Ui_TimeSeriesFixedResolutionEditor super().__init__(parent) start = datetime(year=2000, month=1, day=1) resolution = [duration_to_relativedelta("1 hour")] values = 2 * [0.0] initial_value = TimeSeriesFixedResolution(start, resolution, values, False, False) self._model = TimeSeriesModelFixedResolution(initial_value) self._model.dataChanged.connect(self._update_plot) self._model.modelReset.connect(self._update_plot) self._model.rowsInserted.connect(self._update_plot) self._model.rowsRemoved.connect(self._update_plot) self._ui = Ui_TimeSeriesFixedResolutionEditor() self._ui.setupUi(self) self._plot_widget = PlotWidget() self._ui.splitter.insertWidget(1, self._plot_widget) self._ui.start_time_edit.setText(str(initial_value.start)) self._ui.start_time_edit.editingFinished.connect( self._start_time_changed) self._ui.calendar_button.clicked.connect(self._show_calendar) self._ui.resolution_edit.setText( _resolution_to_text(initial_value.resolution)) self._ui.resolution_edit.editingFinished.connect( self._resolution_changed) self._time_series_table = TimeSeriesFixedResolutionTableView( self._ui.splitter) self._ui.left_layout.addWidget(self._time_series_table) self._time_series_table.setModel(self._model) self._time_series_table.setContextMenuPolicy(Qt.CustomContextMenu) self._time_series_table.customContextMenuRequested.connect( self._show_table_context_menu) self._ui.ignore_year_check_box.setChecked( self._model.value.ignore_year) self._ui.ignore_year_check_box.toggled.connect( self._model.set_ignore_year) self._ui.repeat_check_box.setChecked(self._model.value.repeat) self._ui.repeat_check_box.toggled.connect(self._model.set_repeat) self._calendar = QCalendarWidget(self) self._calendar.setMinimumDate(QDate(100, 1, 1)) self._calendar.setWindowFlags(Qt.Popup) self._calendar.activated.connect(self._select_date) self._update_plot()
def __init__(self, parent=None, title=""): super(DateDialog, self).__init__(parent) layout = QGridLayout(self) self.setStyleSheet("") self.calendar = QCalendarWidget(self) self.calendar.setStyleSheet("") self.setWindowTitle(title) buttons = QWidget(self) buttons_layout = QGridLayout(buttons) self.enter_button = QPushButton("Enter", self) self.enter_button.clicked.connect(self.enter) self._not_canceled = False self.cancel_button = QPushButton("Cancel", self) self.cancel_button.clicked.connect(self.close) buttons_layout.addWidget(self.enter_button, 0, 0) buttons_layout.addWidget(self.cancel_button, 0, 1) layout.addWidget(self.calendar) layout.addWidget(buttons) self._date = ""
def get_date(self, is_start): w = QDialog() w.setLayout(QFormLayout()) calendar_input = QCalendarWidget() w.layout().addRow(calendar_input) accept_button = QPushButton("Accept") accept_button.clicked.connect(w.accept) cancel_button = QPushButton("Cancel") cancel_button.clicked.connect(w.reject) w.layout().addRow(accept_button, cancel_button) if w.exec() == QDialog.Accepted: selected_date = calendar_input.selectedDate() new_date = datetime.date(selected_date.year(), selected_date.month(), selected_date.day()) print("New date is", new_date) if is_start: self.start_date = new_date self.start_button.setText(str(new_date)) if self.end_date: print("Number of days is", self.end_date - self.start_date) self.calendar_view.setColumnCount( (self.end_date - self.start_date).days) date_labels = [ str(date) for date in date_iterator( self.start_date, self.end_date) ] self.calendar_view.setHorizontalHeaderLabels(date_labels) else: self.end_date = new_date self.end_button.setText(str(new_date)) if self.start_date: print("Number of days is", (self.end_date - self.start_date).days) self.calendar_view.setColumnCount( (self.end_date - self.start_date).days) date_labels = [ str(date) for date in date_iterator( self.start_date, self.end_date) ] self.calendar_view.setHorizontalHeaderLabels(date_labels)
def initUI(self): cal=QCalendarWidget(self) cal.setGridVisible(True) cal.setFixedWidth(400) vbox=QVBoxLayout() vbox.addWidget(cal) self.setLayout(vbox)
class Window(QWidget): def __init__(self): super().__init__() self.setWindowTitle("Pyside2 Calendar") # Configure le titre de la fenêtre self.setGeometry(300, 300, 500, 400) # Configure la taille de la fenêtre self.setIcon() self.createCalendar() def setIcon(self): appIcon = QIcon("icon.png") self.setWindowIcon(appIcon) def createCalendar(self): vbox = QVBoxLayout() self.calendar = QCalendarWidget() self.calendar.setGridVisible(True) vbox.addWidget(self.calendar) # Met le calendirer dans le layout self.setLayout(vbox) #Associe le layout à la fenêtre
def handle_dateSelectButton(self): # method to handle the okay button when it is pressed def handle_okayButton(): # get date from calendar widget and create a string out of it q_date = calendar.selectedDate() if q_date.day() < 10: day = str(0) + str(q_date.day()) else: day = str(q_date.day()) if q_date.month() < 10: month = str(0) + str(q_date.month()) else: month = str(q_date.month()) year = str(q_date.year()) date = day + '/' + month + '/' + year self.dateDisplay.setText(date) popup.accept() # method to handle the cancel button when it is pressed def handle_cancelButton(): popup.reject() # initialise the dialog popup = QDialog() popup.setWindowTitle('Select Date') # create the widgets and connect them to functions calendar = QCalendarWidget() okayButton = QPushButton('Okay') okayButton.clicked.connect(handle_okayButton) cancelButton = QPushButton('Cancel') cancelButton.clicked.connect(handle_cancelButton) # initialise the layout manager layout = QVBoxLayout() # add the widgets to the layout manager layout.addWidget(calendar) layout.addWidget(cancelButton) layout.addWidget(okayButton) popup.setLayout(layout) # set the dialog as modal so that the user cannot interact with the main window when the dialog is open popup.setModal(True) popup.show() popup.exec_()
def __init__(self, parent=None): super(DatePicker, self).__init__(parent) self.button = QPushButton(self) icon = QIcon("logo.svg") self.button.setIcon(icon) self.setFixedSize(32, 32) self.button.setFixedSize(32, 32) self.button.setIconSize(QSize(22, 22)) self.__margin__ = 5 self.dialog = QDialog() self.dialog.setWindowFlags(Qt.Window | Qt.FramelessWindowHint | Qt.Popup) self.dialog.setFixedSize(480, 240) self.dialog.setLayout(QHBoxLayout()) self.calender = QCalendarWidget(self) self.dialog.layout().addWidget(self.calender) self.dialog.layout().setContentsMargins(0, 0, 0, 0) self.dialog.layout().setSpacing(0) self.button.clicked.connect(self.showCalender) self.calender.selectionChanged.connect(self.__onSelectionChanged__)
def create_date_picker(self, index): tmp_time = self.uniqueDates[index] time_QFormat = tmp_time.split("-") # date is parsed and converted to int to comply with required format of QDate date_picker = QDateTimeEdit( QDate(int(time_QFormat[0]), int(time_QFormat[1]), int(time_QFormat[2])), self) date_picker.setDisplayFormat("yyyy.MM.dd") date_picker.setCalendarPopup(True) date_picker.setCalendarWidget(QCalendarWidget()) date_picker.resize(date_picker.width() + 20, date_picker.height()) return date_picker
def initUI(self): cal = QCalendarWidget(self) cal.setGridVisible(True) cal.move(20, 20) cal.clicked[QDate].connect(self.showDate) self.lbl = QLabel(self) date = cal.selectedDate() self.lbl.setText(date.toString()) self.lbl.move(130, 260) self.setGeometry(300, 300, 350, 300) self.setWindowTitle('QProgressBar') self.show()
class CalendarDialog(QDialog): def __init__(self, parent): QDialog.__init__(self, parent) self.setModal(True) self.setWindowTitle("Datum auswählen") self._calendar: QCalendarWidget = None self._buttonBox: QtWidgets.QDialogButtonBox = None self._callback = None self.createCalendar() def setCallback(self, cbfnc): self._callback = cbfnc def setMinimumDate(self, y: int, m: int, d: int): self._calendar.setMinimumDate(QDate(y, m, d)) def setMaximumDate(self, y: int, m: int, d: int): self._calendar.setMaximumDate(QDate(y, m, d)) def createCalendar(self): vbox = QVBoxLayout() self._calendar = QCalendarWidget() self._calendar.setGridVisible(True) self._calendar.setFirstDayOfWeek(Qt.Monday) vbox.addWidget(self._calendar) self.setLayout(vbox) self._buttonBox = QtWidgets.QDialogButtonBox(self) self._buttonBox.setOrientation(QtCore.Qt.Horizontal) self._buttonBox.setStandardButtons(QtWidgets.QDialogButtonBox.Ok | QtWidgets.QDialogButtonBox.Cancel) self._buttonBox.layout().setDirection(QBoxLayout.RightToLeft) self._buttonBox.button(QtWidgets.QDialogButtonBox.Ok).clicked.connect( self._onOk) self._buttonBox.button( QtWidgets.QDialogButtonBox.Cancel).clicked.connect(self._onCancel) vbox.addWidget(self._buttonBox) def setSelectedDate(self, date: QDate): self._calendar.setSelectedDate(date) def _onOk(self): date: QDate = self._calendar.selectedDate() self.hide() if self._callback: self._callback(date) def _onCancel(self): self.hide()
def makeDueDateLayout(self): dueDateLayout = QVBoxLayout() rowLayout = QHBoxLayout() dateLabel = QLabel('Due Date:') dateLabel.setStyleSheet('QLabel { color: #cccccc; };') rowLayout.addWidget(dateLabel) dateLineEdit = QLineEdit() dateLineEdit.setStyleSheet(''' QLineEdit { background-color: #2a2a2a; color: #cccccc; }; ''') if self.dueDate > 0: dateLineEdit.setText(toLocalTime(self.dueDate)) else: dateLineEdit.setText('None') self.dateLineEdit = dateLineEdit calWidget = QCalendarWidget() calWidget.setStyleSheet(''' QCalendarWidget QWidget { background-color: #2a2a2a; alternate-background-color: #303030; color: #cccccc; } QCalendarWidget QToolButton { background-color: #2a2a2a; alternate-background-color: #303030; color: #cccccc; } QCalendarWidget QAbstractItemView { background-color: #2a2a2a; alternate-background-color: #303030; color: #cccccc; } ''') calWidget.setVerticalHeaderFormat(QCalendarWidget.NoVerticalHeader) calWidget.clicked.connect(self.onCalendarClick) rowLayout.addWidget(dateLineEdit) dueDateLayout.addLayout(rowLayout) dueDateLayout.addWidget(calWidget) return dueDateLayout
class Window(QWidget): go_list = [] unit = None def __init__(self): super(Window, self).__init__() self.createCalendarBox() self.setup_database_dialog() self.database_utilities() self.ready_plots() layout = QGridLayout() layout.addWidget(self.db_dialog_groupbox, 0, 0) layout.addWidget(self.previewGroupBox, 0, 1) layout.addWidget(self.db_util_groupbox, 1, 0) layout.addWidget(self.ready_plt_groupbox, 1, 1) layout.setSizeConstraint(QLayout.SetFixedSize) self.setLayout(layout) self.previewLayout.setRowMinimumHeight(0, self.calendar.sizeHint().height()) self.previewLayout.setColumnMinimumWidth(0, self.calendar.sizeHint().width()) self.setWindowTitle("Data Visualization Application") def createCalendarBox(self): self.previewGroupBox = QGroupBox("Custom Plot") # db_entry_layout self.db_entry_layout = QHBoxLayout() self.db_entry_field = QLineEdit("tasos.db") self.db_entry_label = QLabel("Set Sensor") self.db_entry_set_button = QPushButton("Set") # Create available db QComboBox self.avail_db_combo = QComboBox() self.avail_db_combo.addItems(self.available_db_combo()) self.avail_db_combo_reload = QPushButton("Reload") # Create QHBoxLayout for avail_db_combo self.avail_db_combo_layout = QHBoxLayout() # Adds widgets to db_entry_ayout QHBoxLayout self.db_entry_layout.addWidget(self.db_entry_label) self.db_entry_layout.addWidget(self.avail_db_combo) self.db_entry_layout.addWidget(self.avail_db_combo_reload) self.db_entry_layout.addWidget(self.db_entry_set_button) self.db_entry_set_button.clicked.connect(self.set_db_entry_button_script) # Calendar Widget self.calendar = QCalendarWidget() self.calendar.setGridVisible(True) # Create main layout self.previewLayout = QGridLayout() # Creating sub layouts and adding their widgets self.cal_options = QGridLayout() self.chart_label = QLabel("&Chart") self.calendar_chart_field = QComboBox() self.calendar_chart_field.addItem("Lines") self.calendar_chart_field.addItem("Lines and Markers") self.calendar_chart_field.addItem("Scatter") self.calendar_chart_field.addItem("Bars") self.chart_label.setBuddy(self.calendar_chart_field) # Mode Layout self.h_mode_layout = QHBoxLayout() self.h_mode_layout.addWidget(self.chart_label) self.h_mode_layout.addWidget(self.calendar_chart_field) self.from_to_dates_layout = QVBoxLayout() # From Layout self.from_date_layout = QHBoxLayout() self.from_date_label = QLabel("From") self.from_date = QDateEdit() self.update_from_date = QPushButton("Set Date") self.from_date.setDisplayFormat('MMM d yyyy') self.from_date.setDate(self.calendar.selectedDate()) self.update_from_date.clicked.connect(self.from_selectedDateChanged) # Adds widgets to from_date_layout QHBoxLayout self.from_date_layout.addWidget(self.from_date) self.from_date_layout.addWidget(self.update_from_date) # To layout self.to_date_layout = QHBoxLayout() self.to_date_label = QLabel("To") self.to_date = QDateEdit() self.update_to_date = QPushButton("Set Date") self.to_date.setDisplayFormat('MMM d yyyy') self.to_date.setDate(self.calendar.selectedDate()) self.update_to_date.clicked.connect(self.to_selectedDateChanged) # Multiple graphic objects layout self.multi_go_label = QLabel("Plot multiple graph objects") self.multi_go_layout = QHBoxLayout() self.multi_go_add_button = QPushButton("Add Graph Object") self.multi_go_clear_button = QPushButton("Clear Graph Objects") self.multi_go_plot_button = QPushButton("Plot Graph Objects") # Adds widges to multi_go_layout self.multi_go_layout.addWidget(self.multi_go_add_button) self.multi_go_layout.addWidget(self.multi_go_clear_button) # Adds widgets to to_date_layout QHBoxLayout self.to_date_layout.addWidget(self.to_date) self.to_date_layout.addWidget(self.update_to_date) # Add widgets and QHBoxLayout to our QVBoxLayout self.from_to_dates_layout.addWidget(self.from_date_label) self.from_to_dates_layout.addLayout(self.from_date_layout) self.from_to_dates_layout.addWidget(self.to_date_label) self.from_to_dates_layout.addLayout(self.to_date_layout) self.custom_plot_button = QPushButton("Custom Plot") # self.available_db_combo() # self.cal_options.addLayout(self.avail_db_combo_layout, 0, 0) self.cal_options.addLayout(self.db_entry_layout, 0, 0) self.cal_options.addLayout(self.h_mode_layout, 1, 0) self.cal_options.addLayout(self.from_to_dates_layout, 2, 0) self.cal_options.addWidget(self.custom_plot_button, 3, 0) self.multi_qvbox_layout = QVBoxLayout() self.multi_qvbox_layout.addWidget(self.multi_go_label) self.multi_qvbox_layout.addLayout(self.multi_go_layout) self.multi_qvbox_layout.addWidget(self.multi_go_plot_button) self.avail_db_combo_reload.clicked.connect(self.reload_db_combo) self.custom_plot_button.clicked.connect(self.custom_plot_script) # Connect multi_go buttons self.multi_go_add_button.clicked.connect(self.add_go_script) self.multi_go_clear_button.clicked.connect(self.clear_go_script) self.multi_go_plot_button.clicked.connect(self.multi_go_plot_script) # Create QVBoxLayout that contains a QHBoxLayout with min,max,avg,count,sum self.stats_label = QLabel("Get Stats from The Selected Sensor and Dates") self.max = QPushButton("Get Max") self.min = QPushButton("Get Min") self.avg = QPushButton("Get Average") self.count = QPushButton("Get Count Of Measurements") self.sum = QPushButton("Get Total Sum") self.avg_to_max = QPushButton("Get Count Between Avg-Max") self.stats_first_qhbox_layout = QHBoxLayout() self.stats_first_qhbox_layout.addWidget(self.min) self.stats_first_qhbox_layout.addWidget(self.max) self.stats_first_qhbox_layout.addWidget(self.avg) self.stats_second_qhbox_layout = QHBoxLayout() self.stats_second_qhbox_layout.addWidget(self.count) self.stats_second_qhbox_layout.addWidget(self.sum) self.stats_second_qhbox_layout.addWidget(self.avg_to_max) self.stats_qvbox_layout = QVBoxLayout() self.stats_qvbox_layout.addWidget(self.stats_label) self.stats_qvbox_layout.addLayout(self.stats_first_qhbox_layout) self.stats_qvbox_layout.addLayout(self.stats_second_qhbox_layout) # Connect stats buttons when clicked self.min.clicked.connect(self.get_min_script) self.max.clicked.connect(self.get_max_script) self.avg.clicked.connect(self.get_avg_script) self.count.clicked.connect(self.get_count_script) self.sum.clicked.connect(self.get_sum_script) self.avg_to_max.clicked.connect(self.get_avg_to_max_count_script) # Add widgets and sub layout to main layout self.previewLayout.addWidget(self.calendar, 0, 0, Qt.AlignTop) # , Qt.AlignCenter self.previewLayout.addLayout(self.cal_options, 0, 1) self.previewLayout.addLayout(self.stats_qvbox_layout, 1, 0) self.previewLayout.addLayout(self.multi_qvbox_layout, 1, 1) self.previewGroupBox.setLayout(self.previewLayout) def get_avg_to_max_count_script(self): avgToMax_from_date = str(self.from_date.date().toPython()) avgToMax_to_date = str(self.to_date.date().toPython()) avgToMax_error = "Something went wrong while retrieving the percentage" avgToMax_db = self.avail_db_combo.currentText() + ".db" avgToMax_extr = Extractor(avgToMax_db) try: total_count = avgToMax_extr.get_count(avgToMax_from_date, avgToMax_to_date) avgToMax_avg = avgToMax_extr.get_avg(avgToMax_from_date, avgToMax_to_date) avgToMax_max = avgToMax_extr.get_max(avgToMax_from_date, avgToMax_to_date) atm_avg = avgToMax_avg[0][0] atm_max = avgToMax_max[0][0] avgToMax_count = avgToMax_extr.get_avg_to_max_count( str(atm_avg), str(atm_max), avgToMax_from_date, avgToMax_to_date) avgToMax_percentage = (avgToMax_count[0][0]/total_count[0][0]) print(avgToMax_count[0][0], total_count[0][0]) avgToMax_success = True except Exception as ex: avgToMax_success = False avgToMax_error = ex avgToMax_msg = QMessageBox() if avgToMax_success: avgToMax_msg.setIcon(QMessageBox.Information) avgToMax_msg.setText( "Percentage of values between average and max for the selected sensor and dates") avgToMax_msg.setInformativeText( "Avg to Max percentage: {0} %".format(avgToMax_percentage*100)) avgToMax_msg.setWindowTitle("Avg to Max percentage") copy_avgToMax_to_clip = avgToMax_msg.addButton( self.tr("Copy to clipboard"), QMessageBox.AcceptRole) avgToMax_msg.setStandardButtons(QMessageBox.Close) avgToMax_msg.setDefaultButton(copy_avgToMax_to_clip) else: avgToMax_msg.setIcon(QMessageBox.Critical) avgToMax_msg.setText("Getting Avg to Max Percentage Failed!") avgToMax_msg.setInformativeText( "Getting Avg to Max percentage from {0} failed!".format(self.avail_db_combo.currentText())) avgToMax_msg.setWindowTitle("ERROR!") avgToMax_msg.setDetailedText("ERROR:\n {0}".format(avgToMax_error)) avgToMax_msg.setStandardButtons(QMessageBox.Abort) avgToMax_retval = avgToMax_msg.exec_() copy_avgToMax_to_clip.clicked.connect(self.copy_to_clipboard(avgToMax_percentage)) avgToMax_msg.show() def get_sum_script(self): sum_from_date = str(self.from_date.date().toPython()) sum_to_date = str(self.to_date.date().toPython()) sum_error = "Something went wrong while retrieving sum" sum_db = self.avail_db_combo.currentText() + ".db" sum_extr = Extractor(sum_db) try: sum_stat = sum_extr.get_sum(sum_from_date, sum_to_date) sum_success = True except Exception as ex: sum_success = False sum_error = ex sum_msg = QMessageBox() if sum_success: sum_msg.setIcon(QMessageBox.Information) sum_msg.setText("Sum value for the selected sensor and dates") sum_msg.setInformativeText( "Sum value: {0}".format(sum_stat[0][0])) sum_msg.setWindowTitle("sum Value") copy_sum_to_clip = sum_msg.addButton( self.tr("Copy to clipboard"), QMessageBox.AcceptRole) sum_msg.setStandardButtons(QMessageBox.Close) sum_msg.setDefaultButton(copy_sum_to_clip) else: sum_msg.setIcon(QMessageBox.Critical) sum_msg.setText("Getting Sum Value Failed!") sum_msg.setInformativeText( "Getting sum value from {0} failed!".format(self.avail_db_combo.currentText())) sum_msg.setWindowTitle("ERROR!") sum_msg.setDetailedText("ERROR:\n {0}".format(sum_error)) sum_msg.setStandardButtons(QMessageBox.Abort) sum_retval = sum_msg.exec_() copy_sum_to_clip.clicked.connect(self.copy_to_clipboard(sum_stat[0][0])) sum_msg.show() def get_count_script(self): count_from_date = str(self.from_date.date().toPython()) count_to_date = str(self.to_date.date().toPython()) count_error = "Something went wrong while retrieving count" count_db = self.avail_db_combo.currentText() + ".db" count_extr = Extractor(count_db) try: count_stat = count_extr.get_count(count_from_date, count_to_date) count_success = True except Exception as ex: count_success = False count_error = ex count_msg = QMessageBox() if count_success: count_msg.setIcon(QMessageBox.Information) count_msg.setText("Count value for the selected sensor and dates") count_msg.setInformativeText( "count value: {0}".format(count_stat[0][0])) count_msg.setWindowTitle("Count Value") copy_count_to_clip = count_msg.addButton( self.tr("Copy to clipboard"), QMessageBox.AcceptRole) count_msg.setStandardButtons(QMessageBox.Close) count_msg.setDefaultButton(copy_count_to_clip) else: count_msg.setIcon(QMessageBox.Critical) count_msg.setText("Getting Count Value Failed!") count_msg.setInformativeText( "Getting count value from {0} failed!".format(self.avail_db_combo.currentText())) count_msg.setWindowTitle("ERROR!") count_msg.setDetailedText("ERROR:\n {0}".format(count_error)) count_msg.setStandardButtons(QMessageBox.Abort) count_retval = count_msg.exec_() copy_count_to_clip.clicked.connect(self.copy_to_clipboard(count_stat[0][0])) count_msg.show() def get_avg_script(self): avg_from_date = str(self.from_date.date().toPython()) avg_to_date = str(self.to_date.date().toPython()) avg_error = "Something went wrong while retrieving avg" avg_db = self.avail_db_combo.currentText() + ".db" avg_extr = Extractor(avg_db) try: avg_stat = avg_extr.get_avg(avg_from_date, avg_to_date) avg_success = True except Exception as ex: avg_success = False avg_error = ex avg_msg = QMessageBox() if avg_success: avg_msg.setIcon(QMessageBox.Information) avg_msg.setText("Avg value for the selected sensor and dates") avg_msg.setInformativeText( "Avg value: {0}".format(avg_stat[0][0])) avg_msg.setWindowTitle("Avg Value") copy_avg_to_clip = avg_msg.addButton( self.tr("Copy to clipboard"), QMessageBox.AcceptRole) avg_msg.setStandardButtons(QMessageBox.Close) avg_msg.setDefaultButton(copy_avg_to_clip) else: avg_msg.setIcon(QMessageBox.Critical) avg_msg.setText("Getting Avg Value Failed!") avg_msg.setInformativeText( "Getting avg value from {0} failed!".format(self.avail_db_combo.currentText())) avg_msg.setWindowTitle("ERROR!") avg_msg.setDetailedText("ERROR:\n {0}".format(avg_error)) avg_msg.setStandardButtons(QMessageBox.Abort) avg_retval = avg_msg.exec_() copy_avg_to_clip.clicked.connect(self.copy_to_clipboard(avg_stat[0][0])) avg_msg.show() def get_max_script(self): max_from_date = str(self.from_date.date().toPython()) max_to_date = str(self.to_date.date().toPython()) max_error = "Something went wrong while retrieving max" max_db = self.avail_db_combo.currentText() + ".db" max_extr = Extractor(max_db) try: max_stat = max_extr.get_max(max_from_date, max_to_date) max_success = True except Exception as ex: max_success = False max_error = ex max_msg = QMessageBox() if max_success: max_msg.setIcon(QMessageBox.Information) max_msg.setText("Max value for the selected sensor and dates") max_msg.setInformativeText( "Max value: {0}".format(max_stat[0][0])) max_msg.setWindowTitle("Max Value") copy_max_to_clip = max_msg.addButton( self.tr("Copy to clipboard"), QMessageBox.AcceptRole) max_msg.setStandardButtons(QMessageBox.Close) max_msg.setDefaultButton(copy_max_to_clip) else: max_msg.setIcon(QMessageBox.Critical) max_msg.setText("Getting Max Value Failed!") max_msg.setInformativeText( "Getting max value from {0} failed!".format(self.avail_db_combo.currentText())) max_msg.setWindowTitle("ERROR!") max_msg.setDetailedText("ERROR:\n {0}".format(max_error)) max_msg.setStandardButtons(QMessageBox.Abort) max_retval = max_msg.exec_() copy_max_to_clip.clicked.connect(self.copy_to_clipboard(max_stat[0][0])) max_msg.show() def get_min_script(self): min_from_date = str(self.from_date.date().toPython()) min_to_date = str(self.to_date.date().toPython()) min_error = "Something went wrong while retrieving min" min_db = self.avail_db_combo.currentText() + ".db" min_extr = Extractor(min_db) try: min_stat = min_extr.get_min(min_from_date, min_to_date) min_success = True except Exception as ex: min_success = False min_error = ex min_msg = QMessageBox() if min_success: min_msg.setIcon(QMessageBox.Information) min_msg.setText("Min value for the selected sensor and dates") min_msg.setInformativeText( "Min value: {0}".format(min_stat[0][0])) min_msg.setWindowTitle("Min Value") copy_min_to_clip = min_msg.addButton( self.tr("Copy to clipboard"), QMessageBox.AcceptRole) min_msg.setStandardButtons(QMessageBox.Close) min_msg.setDefaultButton(copy_min_to_clip) else: min_msg.setIcon(QMessageBox.Critical) min_msg.setText("Getting Min Value Failed!") min_msg.setInformativeText( "Getting min value from {0} failed!".format(self.avail_db_combo.currentText())) min_msg.setWindowTitle("ERROR!") min_msg.setDetailedText("ERROR:\n {0}".format(min_error)) min_msg.setStandardButtons(QMessageBox.Abort) min_retval = min_msg.exec_() copy_min_to_clip.clicked.connect(self.copy_to_clipboard(min_stat[0][0])) min_msg.show() def copy_to_clipboard(self, var): pyperclip.copy(var) def add_go_script(self): current_index_chart = self.calendar_chart_field.currentIndex() if current_index_chart == 0: chart_mode = "lines" elif current_index_chart == 1: chart_mode = "lines+markers" elif current_index_chart == 2: chart_mode = "markers" elif current_index_chart == 3: chart_mode = "Bars" else: cm_error = "Something went wrong" print(cm_error) multi_go_db = self.avail_db_combo.currentText() + ".db" multi_go_extr = Extractor(multi_go_db) multi_go_plt = Plotter() multi_go_lists = [] # converts Qdate object to python date object go_from_date = str(self.from_date.date().toPython()) go_to_date = str(self.to_date.date().toPython()) multi_go_lists = multi_go_extr.custom_select(go_from_date, go_to_date) if chart_mode == "lines" or chart_mode == "lines+markers" or chart_mode == "markers": go_data = multi_go_plt.go_scatter( chart_mode, multi_go_lists[0], multi_go_lists[1], multi_go_db) Window.go_list.append(go_data) if Window.unit is None: Window.unit = multi_go_lists[2][0] elif chart_mode == "Bars": go_data = multi_go_plt.go_bar( chart_mode, multi_go_lists[0], multi_go_lists[1], multi_go_db) Window.go_list.append(go_data) if Window.unit is None: Window.unit = multi_go_lists[2][0] else: print("Something went wrong") def clear_go_script(self): Window.go_list.clear() Window.unit = None def multi_go_plot_script(self): multi_go_plt = Plotter() current_index_chart = self.calendar_chart_field.currentIndex() if current_index_chart == 0: chart_mode = "lines" elif current_index_chart == 1: chart_mode = "lines+markers" elif current_index_chart == 2: chart_mode = "markers" elif current_index_chart == 3: chart_mode = "Bars" else: cm_error = "Something went wrong" print(cm_error) if chart_mode == "lines" or chart_mode == "lines+markers" or chart_mode == "markers": multi_go_plt.go_plot("Multiple Graphs", "TIME", Window.unit, Window.go_list) elif chart_mode == "Bars": multi_go_plt.go_bar_plot("Multiple Graphs", "TIME", Window.unit, Window.go_list) else: print("Something went wrong") Window.go_list.clear() Window.unit = None def custom_plot_script(self): current_index_chart = self.calendar_chart_field.currentIndex() if current_index_chart == 0: chart_mode = "lines" elif current_index_chart == 1: chart_mode = "lines+markers" elif current_index_chart == 2: chart_mode = "markers" elif current_index_chart == 3: chart_mode = "Bars" else: cm_error = "Something went wrong" print(cm_error) custom_db = self.avail_db_combo.currentText() + ".db" custom_extr = Extractor(custom_db) custom_plt = Plotter() custom_plot_lists = [] custom_plot_title = custom_db[:-3] # converts Qdate object to python date object custom_from_date = str(self.from_date.date().toPython()) custom_to_date = str(self.to_date.date().toPython()) custom_plot_lists = custom_extr.custom_select(custom_from_date, custom_to_date) if chart_mode == "lines" or chart_mode == "lines+markers" or chart_mode == "markers": custom_plt.scatter_plot( chart_mode, custom_plot_lists[0], custom_plot_lists[1], custom_plot_title, "TIME", custom_plot_lists[2][0]) elif chart_mode == "Bars": custom_plt.bar_plot(custom_plot_lists[0], custom_plot_lists[1], custom_plot_title, "TIME", custom_plot_lists[2][0]) else: print("Something went wrong") def setup_database_dialog(self): # Create Groupbox self.db_dialog_groupbox = QGroupBox("Sensor Declaration and Data Import") # Create widgets self.db_label = QLabel("Provide a name for the sensor") self.path_label = QLabel("Provide path to search for .xml files") self.db_field = QLineEdit("") self.path_field = QLineEdit(str(os.path.dirname(os.path.realpath(__file__)))) self.button = QPushButton("Get started") # Create layout and add widgets self.db_dialog_layout = QVBoxLayout() self.db_dialog_layout.addWidget(self.db_label) self.db_dialog_layout.addWidget(self.db_field) self.db_dialog_layout.addWidget(self.path_label) self.db_dialog_layout.addWidget(self.path_field) self.db_dialog_layout.addWidget(self.button) # Set dialog layout self.db_dialog_groupbox.setLayout(self.db_dialog_layout) self.db_field.textChanged.connect(self.db_field_changed) self.button.clicked.connect(self.run_script) def run_script(self): error = "Error parsing files or path" db = self.db_field.text() + ".db" db_interaction = DatabaseInteraction(db) # returns object of class DatabaseInteraction path = self.path_field.text() xml_importer = XMLImporter(db_interaction.name, path) try: success = xml_importer.import_xml() except Exception as ex: success = False error = ex msg = QMessageBox() if success: msg.setIcon(QMessageBox.Information) msg.setText("Sensor declaration successful") msg.setInformativeText("The sensor: {0} has been created.".format(self.db_field.text())) msg.setWindowTitle("Sensor declared!") msg.setDetailedText("The details are as follows:\nSensor name: {0} \nPath of .xml " "files: {1}".format(self.db_field.text(), path)) msg.setStandardButtons(QMessageBox.Ok) else: msg.setIcon(QMessageBox.Critical) msg.setText("Sensor declaration failed!") msg.setInformativeText( "Declaration of the sensor: {0} failed!".format(self.db_field.text())) msg.setWindowTitle("Sensor declaration failed!") msg.setDetailedText("ERROR:\n {0}".format(error)) msg.setStandardButtons(QMessageBox.Abort) retval = msg.exec_() msg.show() def database_utilities(self): # Create Groupbox self.db_util_groupbox = QGroupBox("Utilities") # Create Widgets self.db_update_label = QLabel("Select the Sensor you wish to update") self.path_label = QLabel("Xml File Path") self.update_path_field = QLineEdit(str(os.path.dirname(os.path.realpath(__file__)))) self.update_button = QPushButton("Update") self.update_title = QLabel("Update Sensor") # self.db_clear_field = QLineEdit("example.db") self.db_clear_label = QLabel("Select Sensor") self.clear_button = QPushButton("Remove") self.clear_title = QLabel("Remove a sensor") # Create available db QComboBox for update self.update_avail_db_combo = QComboBox() self.update_avail_db_combo.addItems(self.available_db_combo()) self.update_avail_db_combo_reload = QPushButton("Reload") # Create available db QComboBox for clear table self.clear_avail_db_combo = QComboBox() self.clear_avail_db_combo.addItems(self.available_db_combo()) self.clear_avail_db_combo_reload = QPushButton("Reload") # Add Widgets self.db_util_db_update = QHBoxLayout() self.db_util_db_update.addWidget(self.db_update_label) self.db_util_db_update.addWidget(self.update_avail_db_combo) self.db_util_db_update.addWidget(self.update_avail_db_combo_reload) self.db_util_path = QHBoxLayout() self.db_util_path.addWidget(self.path_label) self.db_util_path.addWidget(self.update_path_field) self.db_util_clear = QHBoxLayout() self.db_util_clear.addWidget(self.db_clear_label) self.db_util_clear.addWidget(self.clear_avail_db_combo) self.db_util_clear.addWidget(self.clear_avail_db_combo_reload) self.db_util_vbox_layout = QVBoxLayout() self.db_util_vbox_layout.addWidget(self.update_title) self.db_util_vbox_layout.addLayout(self.db_util_db_update) self.db_util_vbox_layout.addLayout(self.db_util_path) self.db_util_vbox_layout.addWidget(self.update_button) self.db_util_vbox_layout.addWidget(self.clear_title) self.db_util_vbox_layout.addLayout(self.db_util_clear) self.db_util_vbox_layout.addWidget(self.clear_button) # Set dialog layout self.db_util_groupbox.setLayout(self.db_util_vbox_layout) self.update_button.clicked.connect(self.update_script) self.clear_button.clicked.connect(self.clear_table_script) self.update_avail_db_combo_reload.clicked.connect(self.reload_db_combo) self.clear_avail_db_combo_reload.clicked.connect(self.reload_db_combo) def update_script(self): db = self.update_avail_db_combo.currentText() + ".db" database_interaction = DatabaseInteraction(db) path = self.update_path_field.text() xml_importer = XMLImporter(database_interaction.name, path) update_error = "Something went wrong during update" try: success = xml_importer.import_xml() except Exception as ex: success = False update_error = ex update_msg = QMessageBox() if success: update_msg.setIcon(QMessageBox.Information) update_msg.setText("Sensor update successful") update_msg.setInformativeText("The sensor: {0} has been updated.".format(db[:-3])) update_msg.setWindowTitle("Sensor updated!") update_msg.setDetailedText("The details are as follows:\Sensor name: {0} \nPath of .xml " "files: {1}".format(db[:-3], path)) update_msg.setStandardButtons(QMessageBox.Ok) else: update_msg.setIcon(QMessageBox.Critical) update_msg.setText("Sensor update failed!") update_msg.setInformativeText("Update of the sensor: {0} failed!".format(db[:-3])) update_msg.setWindowTitle("Sensor update failed!") update_msg.setDetailedText("ERROR:\n {0}".format(update_error)) update_msg.setStandardButtons(QMessageBox.Abort) update_retval = update_msg.exec_() update_msg.show() def ready_plots(self): # Create Groupbox self.ready_plt_groupbox = QGroupBox("Ready-to-use plots") # Create Widgets self.choose_db_label = QLabel( "Provide the database that contains the data you wish to plot") self.choose_db_field = QLineEdit("") self.chart_label = QLabel("Chart") self.chart_field = QComboBox() self.chart_field.addItem("Lines") self.chart_field.addItem("Lines and Markers") self.chart_field.addItem("Scatter") self.chart_field.addItem("Bars") self.plot_mode_label = QLabel("Choose what time period to plot") self.plot_mode_field = QComboBox() self.plot_mode_field.addItem("Daily") self.plot_mode_field.addItem("Weekly") self.plot_mode_field.addItem("Monthly") self.plot_mode_field.addItem("Yearly") self.plot_button = QPushButton("Plot") # Create available db QComboBox for ready-plots self.ready_plot_avail_db_combo = QComboBox() self.ready_plot_avail_db_combo.addItems(self.available_db_combo()) self.ready_plot_avail_db_combo_reload = QPushButton("Reload") # Add QComboBox and QPushButton to a QHBoxLayout self.ready_plot_qhbox_layout = QHBoxLayout() self.ready_plot_qhbox_layout.addWidget(self.ready_plot_avail_db_combo) self.ready_plot_qhbox_layout.addWidget(self.ready_plot_avail_db_combo_reload) # Add Widgets self.plot_vbox_layout = QVBoxLayout() self.plot_vbox_layout.addWidget(self.choose_db_label) self.plot_vbox_layout.addLayout(self.ready_plot_qhbox_layout) self.plot_vbox_layout.addWidget(self.chart_label) self.plot_vbox_layout.addWidget(self.chart_field) self.plot_vbox_layout.addWidget(self.plot_mode_label) self.plot_vbox_layout.addWidget(self.plot_mode_field) self.plot_vbox_layout.addWidget(self.plot_button) # Set layout to groupbox self.ready_plt_groupbox.setLayout(self.plot_vbox_layout) self.plot_button.clicked.connect(self.ready_plot_script) self.ready_plot_avail_db_combo_reload.clicked.connect(self.reload_db_combo) def db_field_changed(self): self.db_field.setText(self.db_field.text()) def db_clear_field_changed(self): self.db_clear_field.setText(self.db_clear_field.text()) def db_update_field_changed(self): self.db_update_field.setText(self.db_update_field.text()) def from_selectedDateChanged(self): self.from_date.setDate(self.calendar.selectedDate()) def to_selectedDateChanged(self): self.to_date.setDate(self.calendar.selectedDate()) def clear_table_script(self): clear_error = "Something went wrong during clearing sensor" db = self.clear_avail_db_combo.currentText() + ".db" try: # db_int.clear_table() os.remove(db) clear_success = True except Exception as ex: clear_success = False clear_error = ex clear_msg = QMessageBox() if clear_success: clear_msg.setIcon(QMessageBox.Information) clear_msg.setText("Sensor has been removed") clear_msg.setInformativeText( "The {0} sensor have been removed.".format(db[:-3])) clear_msg.setWindowTitle("Sensor has been removed!") clear_msg.setStandardButtons(QMessageBox.Ok) else: clear_msg.setIcon(QMessageBox.Critical) clear_msg.setText("Removing sensor has failed!") clear_msg.setInformativeText("Removing the sensor: {0} has failed!".format(db[:-3])) clear_msg.setWindowTitle("Removing this sensor has failed!") clear_msg.setDetailedText("ERROR:\n {0}".format(clear_error)) clear_msg.setStandardButtons(QMessageBox.Abort) clear_retval = clear_msg.exec_() clear_msg.show() def set_db_entry_button_script(self): db_name_fixed = self.avail_db_combo.currentText() + ".db" self.db = DatabaseInteraction(db_name_fixed) extr = Extractor(self.db.name) # Create datetime objects of the first and last strings of date self.datetime_first = datetime.strptime(extr.select_first_row()[ 0][0], "%Y-%m-%dT%H:%M:%S.%fZ") self.datetime_last = datetime.strptime(extr.select_last_row()[ 0][0], "%Y-%m-%dT%H:%M:%S.%fZ") self.first_row = QDate.fromString(str(self.datetime_first.date()), "yyyy-MM-dd") self.last_row = QDate.fromString(str(self.datetime_last.date()), "yyyy-MM-dd") self.calendar.setMinimumDate(self.first_row) self.calendar.setMaximumDate(self.last_row) self.first_row = QDate.fromString(str(self.datetime_first.date()), "yyyy-MM-dd") self.last_row = QDate.fromString(str(self.datetime_last.date()), "yyyy-MM-dd") self.calendar.setMinimumDate(self.first_row) self.calendar.setMaximumDate(self.last_row) def reload_db_combo(self): self.avail_db_combo.clear() self.avail_db_combo.addItems(self.available_db_combo()) self.clear_avail_db_combo.clear() self.clear_avail_db_combo.addItems(self.available_db_combo()) self.update_avail_db_combo.clear() self.update_avail_db_combo.addItems(self.available_db_combo()) self.ready_plot_avail_db_combo.clear() self.ready_plot_avail_db_combo.addItems(self.available_db_combo()) def available_db_combo(self): db_files = [] db_list_model = QStringListModel() for subdir, dirs, files in os.walk(os.path.dirname(os.path.realpath(__file__))): for file in files: filepath = subdir + os.path.sep + file if filepath.endswith(".db"): if filepath not in db_files: db_files.append(file[:-3]) db_list_model.setStringList(db_files) return db_list_model.stringList() def ready_plot_script(self): db = self.ready_plot_avail_db_combo.currentText() + ".db" extr = Extractor(db) plt = Plotter() ready_plot_title = db[:-3] if self.chart_field.currentIndex() == 0: chart_mode = "lines" elif self.chart_field.currentIndex() == 1: chart_mode = "lines+markers" elif self.chart_field.currentIndex() == 2: chart_mode = "markers" elif self.chart_field.currentIndex() == 3: chart_mode = "Bars" else: print("Something went wrong") if self.plot_mode_field.currentIndex() == 0: plot_mode = "daily_select" elif self.plot_mode_field.currentIndex() == 1: plot_mode = "weekly_select" elif self.plot_mode_field.currentIndex() == 2: plot_mode = "monthly_select" elif self.plot_mode_field.currentIndex() == 3: plot_mode = "yearly_select" else: print("Something went wrong") plot_lists = [] # Extract from the database the data for x-y axis and the unit plot_lists = extr.extract(plot_mode) if chart_mode == "lines" or chart_mode == "lines+markers" or chart_mode == "markers": plt.scatter_plot(chart_mode, plot_lists[0], plot_lists[1], ready_plot_title, "TIME", plot_lists[2][0]) elif chart_mode == "Bars": plt.bar_plot(plot_lists[0], plot_lists[1], ready_plot_title, "TIME", plot_lists[2][0]) else: print("Something went wrong")
def createCalendarBox(self): self.previewGroupBox = QGroupBox("Custom Plot") # db_entry_layout self.db_entry_layout = QHBoxLayout() self.db_entry_field = QLineEdit("tasos.db") self.db_entry_label = QLabel("Set Sensor") self.db_entry_set_button = QPushButton("Set") # Create available db QComboBox self.avail_db_combo = QComboBox() self.avail_db_combo.addItems(self.available_db_combo()) self.avail_db_combo_reload = QPushButton("Reload") # Create QHBoxLayout for avail_db_combo self.avail_db_combo_layout = QHBoxLayout() # Adds widgets to db_entry_ayout QHBoxLayout self.db_entry_layout.addWidget(self.db_entry_label) self.db_entry_layout.addWidget(self.avail_db_combo) self.db_entry_layout.addWidget(self.avail_db_combo_reload) self.db_entry_layout.addWidget(self.db_entry_set_button) self.db_entry_set_button.clicked.connect(self.set_db_entry_button_script) # Calendar Widget self.calendar = QCalendarWidget() self.calendar.setGridVisible(True) # Create main layout self.previewLayout = QGridLayout() # Creating sub layouts and adding their widgets self.cal_options = QGridLayout() self.chart_label = QLabel("&Chart") self.calendar_chart_field = QComboBox() self.calendar_chart_field.addItem("Lines") self.calendar_chart_field.addItem("Lines and Markers") self.calendar_chart_field.addItem("Scatter") self.calendar_chart_field.addItem("Bars") self.chart_label.setBuddy(self.calendar_chart_field) # Mode Layout self.h_mode_layout = QHBoxLayout() self.h_mode_layout.addWidget(self.chart_label) self.h_mode_layout.addWidget(self.calendar_chart_field) self.from_to_dates_layout = QVBoxLayout() # From Layout self.from_date_layout = QHBoxLayout() self.from_date_label = QLabel("From") self.from_date = QDateEdit() self.update_from_date = QPushButton("Set Date") self.from_date.setDisplayFormat('MMM d yyyy') self.from_date.setDate(self.calendar.selectedDate()) self.update_from_date.clicked.connect(self.from_selectedDateChanged) # Adds widgets to from_date_layout QHBoxLayout self.from_date_layout.addWidget(self.from_date) self.from_date_layout.addWidget(self.update_from_date) # To layout self.to_date_layout = QHBoxLayout() self.to_date_label = QLabel("To") self.to_date = QDateEdit() self.update_to_date = QPushButton("Set Date") self.to_date.setDisplayFormat('MMM d yyyy') self.to_date.setDate(self.calendar.selectedDate()) self.update_to_date.clicked.connect(self.to_selectedDateChanged) # Multiple graphic objects layout self.multi_go_label = QLabel("Plot multiple graph objects") self.multi_go_layout = QHBoxLayout() self.multi_go_add_button = QPushButton("Add Graph Object") self.multi_go_clear_button = QPushButton("Clear Graph Objects") self.multi_go_plot_button = QPushButton("Plot Graph Objects") # Adds widges to multi_go_layout self.multi_go_layout.addWidget(self.multi_go_add_button) self.multi_go_layout.addWidget(self.multi_go_clear_button) # Adds widgets to to_date_layout QHBoxLayout self.to_date_layout.addWidget(self.to_date) self.to_date_layout.addWidget(self.update_to_date) # Add widgets and QHBoxLayout to our QVBoxLayout self.from_to_dates_layout.addWidget(self.from_date_label) self.from_to_dates_layout.addLayout(self.from_date_layout) self.from_to_dates_layout.addWidget(self.to_date_label) self.from_to_dates_layout.addLayout(self.to_date_layout) self.custom_plot_button = QPushButton("Custom Plot") # self.available_db_combo() # self.cal_options.addLayout(self.avail_db_combo_layout, 0, 0) self.cal_options.addLayout(self.db_entry_layout, 0, 0) self.cal_options.addLayout(self.h_mode_layout, 1, 0) self.cal_options.addLayout(self.from_to_dates_layout, 2, 0) self.cal_options.addWidget(self.custom_plot_button, 3, 0) self.multi_qvbox_layout = QVBoxLayout() self.multi_qvbox_layout.addWidget(self.multi_go_label) self.multi_qvbox_layout.addLayout(self.multi_go_layout) self.multi_qvbox_layout.addWidget(self.multi_go_plot_button) self.avail_db_combo_reload.clicked.connect(self.reload_db_combo) self.custom_plot_button.clicked.connect(self.custom_plot_script) # Connect multi_go buttons self.multi_go_add_button.clicked.connect(self.add_go_script) self.multi_go_clear_button.clicked.connect(self.clear_go_script) self.multi_go_plot_button.clicked.connect(self.multi_go_plot_script) # Create QVBoxLayout that contains a QHBoxLayout with min,max,avg,count,sum self.stats_label = QLabel("Get Stats from The Selected Sensor and Dates") self.max = QPushButton("Get Max") self.min = QPushButton("Get Min") self.avg = QPushButton("Get Average") self.count = QPushButton("Get Count Of Measurements") self.sum = QPushButton("Get Total Sum") self.avg_to_max = QPushButton("Get Count Between Avg-Max") self.stats_first_qhbox_layout = QHBoxLayout() self.stats_first_qhbox_layout.addWidget(self.min) self.stats_first_qhbox_layout.addWidget(self.max) self.stats_first_qhbox_layout.addWidget(self.avg) self.stats_second_qhbox_layout = QHBoxLayout() self.stats_second_qhbox_layout.addWidget(self.count) self.stats_second_qhbox_layout.addWidget(self.sum) self.stats_second_qhbox_layout.addWidget(self.avg_to_max) self.stats_qvbox_layout = QVBoxLayout() self.stats_qvbox_layout.addWidget(self.stats_label) self.stats_qvbox_layout.addLayout(self.stats_first_qhbox_layout) self.stats_qvbox_layout.addLayout(self.stats_second_qhbox_layout) # Connect stats buttons when clicked self.min.clicked.connect(self.get_min_script) self.max.clicked.connect(self.get_max_script) self.avg.clicked.connect(self.get_avg_script) self.count.clicked.connect(self.get_count_script) self.sum.clicked.connect(self.get_sum_script) self.avg_to_max.clicked.connect(self.get_avg_to_max_count_script) # Add widgets and sub layout to main layout self.previewLayout.addWidget(self.calendar, 0, 0, Qt.AlignTop) # , Qt.AlignCenter self.previewLayout.addLayout(self.cal_options, 0, 1) self.previewLayout.addLayout(self.stats_qvbox_layout, 1, 0) self.previewLayout.addLayout(self.multi_qvbox_layout, 1, 1) self.previewGroupBox.setLayout(self.previewLayout)
class zhujiemian(QMainWindow): def __init__(self, parent=None): super().__init__(parent) # 调用父类构造函数,创建窗体 self.ui = Ui_MainWindow() # 创建UI对象 self.ui.setupUi(self) # 构造UI界面 self.setWindowTitle(bt) # 设置窗体标题 # open = QAction(QIcon('ICO/240.png'), '240', self) # self.addAction(open) # 设置窗口LOGO # self.setStyleSheet("MainWindow{border-image:url(./python.jpg);}") # # 设置窗口背景图片 self.tab = {} # 空字典 global L db = self.connect_db() # 获取游标 self.cur = db.cursor(pymysql.cursors.DictCursor) # 使用字典类型输出 # 根据” ID 字段“排序,倒叙输出 人员信息 表中的数据。备注:asc是表示升序,desc表示降序。limit 1表示输出一条记录 sql_renyuan = "select * FROM 人员信息 WHERE 工号 = %s order by ID desc limit 1" rows = self.cur.execute(sql_renyuan, L[len(L) - 1]) rows = self.cur.fetchone() qiye = QLabel(bt) # 设置窗体标题 qiye.setMinimumWidth(150) gonghao = QLabel("工号:%s" % L[len(L) - 1]) gonghao.setMinimumWidth(120) xingming = QLabel("姓名:%s" % rows['姓名']) xingming.setMinimumWidth(120) bumen = QLabel("部门:%s" % rows['部门']) bumen.setMinimumWidth(120) zhiwei = QLabel("职位:%s" % rows['职位']) zhiwei.setMinimumWidth(120) self.ui.statusBar.addWidget(qiye) # 加到状态栏 self.ui.statusBar.addWidget(gonghao) self.ui.statusBar.addWidget(xingming) self.ui.statusBar.addWidget(bumen) self.ui.statusBar.addWidget(zhiwei) cur = db.cursor(pymysql.cursors.DictCursor) # 1.控件的上面的小tab变成透明 # 2.选项卡部件:窗格{ 边框:1px纯灰;顶部:-1px;背景:透明;} # 3.突出选中的部分(改变颜色) # 4.设置QTabBar删除按钮图标和位置 # 4.设置QTabBar删除按钮图标(点击前) # 4.设置QTabBar删除按钮图标(点击时) str = "QTabBar::tab{background-color:rbg(255,255,255,0);}" + \ "QTabWidget:pane{border: 0.5px solid grey; top: -1px;background: transparent;}" + \ "QTabBar::tab:selected{color:blue;background-color:rbg(255,255,255);} " + \ "QTabBar::close-button{image: url(ICO/240.png);subcontrol-postion:left}" + \ "QTabBar::close-button:hover{image:url(ICO/301.png);subcontrol-postion:left}" + \ "QTabBar::close-button:pressed{image:url(ICO/302.png);subcontrol-postion:left}" self.ui.ZhuCaiDan.setStyleSheet(str) self.ui.ZhuCaiDan.setCurrentIndex(0) # 显示第一个选项卡 self.ui.ZhuCaiDan.setTabsClosable(True) # 所有选项加上关闭按钮 self.ui.ZhuCaiDan.tabBar().setTabButton(0, QTabBar.RightSide, None) # 第一项去掉关闭按钮 # self.ui.ZhuCaiDan.tabBar().setTabButton(1, QTabBar.RightSide, None) # # 第二项去掉关闭按钮 u = self.ui.ZhuCaiDan.count() # 获取选项卡数量 # 删除多余选项卡 while u > 0: self.ui.ZhuCaiDan.removeTab(u) u = u - 1 self.ui.ZhuCaiDan.tabCloseRequested.connect( self.close_tab) # ZhuCaiDan(页)关闭函数 self.riqikuangxuanxiang(self.ui.ryxx_Q_riqi) self.riqikuangxuanxiang(self.ui.ryxx_J_riqi) # 窗体居中设置 def center(self): deskSize = QDesktopWidget().screenGeometry() # 获取桌面窗体参数 windowSize = self.geometry() # 获取窗体本身参数 self.move((deskSize.width() - windowSize.width()) / 2, (deskSize.height() - windowSize.height()) / 2) # 居中设置 # ZhuCaiDan(页)关闭函数; def close_tab(self, index): # currentTab = self.ui.ZhuCaiDan.currentWidget() currentTab = self.ui.ZhuCaiDan.widget(index) # 获取选项卡的值 del self.tab[currentTab.objectName()] # 获取选项卡命名(objectName),删除对应数组 self.ui.ZhuCaiDan.removeTab(index) # 隐藏选项卡 # 添加指定选项卡,显示按钮 @Slot(bool) def on_actFont_ranyuanchaxun_triggered(self, clicked): # self.ui.actFont_ranyuanchaxun.triggered.connect(self.add_tab_renyuanxinxi) # # 新增选项卡(标题等同) self.tab['renyuanxinxi'] = [ "部门", "组别", "职位", "工号", "姓名", "性别", "联系电话", "入职日期", "出生日期", "身份证号码", "地址", "待遇", "调薪日期", "离职日期", "备注" ] self.add_tab(self.ui.renyuanxinxi, '人员信息', self.tab['renyuanxinxi'], self.ui.ryxx_tableWidget) # 添加tableWidgetn内容,查询按钮 @Slot() def on_ryxx_chaxun_clicked(self): # self.ui.ryxx_chaxun.clicked.connect(self.chaxun_ryxx) # 查询按钮 text = "select * FROM 人员信息;" self.chaxun(self.ui.ryxx_tableWidget, text, self.tab['renyuanxinxi']) # 退出按钮 @Slot() def on_ryxx_tuichu_clicked(self): index = self.ui.ZhuCaiDan.currentIndex() # 获取当前选项卡的值 self.ui.ZhuCaiDan.removeTab(index) # 隐藏选项卡 @Slot(bool) def on_actFont_xiangmuxinxi_triggered(self, clicked): # self.ui.actFont_xiangmuxinxi.triggered.connect(self.add_tab_xiangmuxingxi) # # 新增选项卡 self.tab['xiangmuxinxi'] = [ "内部编号", "客户编号", "模具等级", "业务担当", "项目担当", "设计担当", "钳工担当", "钳工组别", "下单日期", "首样日期", "预验日期", "复验日期", "终验日期", "要求移模日期", "实际移模日期", "出货判定", "备注" ] self.add_tab(self.ui.xiangmuxinxi, '项目信息', self.tab['xiangmuxinxi'], self.ui.xmxx_tableWidget) @Slot() def on_xmxx_chaxun_clicked(self): text = "select * FROM 项目信息;" self.chaxun(self.ui.xmxx_tableWidget, text, self.tab['xiangmuxinxi']) @Slot() def on_xmxx_tuichu_clicked(self): index = self.ui.ZhuCaiDan.currentIndex() # 获取当前选项卡的值 self.ui.ZhuCaiDan.removeTab(index) # 隐藏选项卡 # 添加选项卡通用函数 def add_tab(self, tab: QWidget, biao_ti: str, biao_tou: list, tableWidgetX: QTableWidgetItem): # self.add_tab(self.ui.xiangmuxinxi, '项目信息', headerText, self.ui.tableWidget_xm) while self.ui.ZhuCaiDan.indexOf(tab) < 0: self.ui.ZhuCaiDan.addTab(tab, biao_ti) # 添加选项卡tab,以及标题biao_ti tableWidgetX.setColumnCount(len(biao_tou)) # 设置列数 tableWidgetX.setRowCount(0) # 设置数据区行数 tableWidgetX.setHorizontalHeaderLabels(biao_tou) # 设置列命名biao_tou tableWidgetX.setAlternatingRowColors(True) # 交替行颜色 selMode = QAbstractItemView.SelectRows tableWidgetX.setSelectionBehavior(selMode) # 选择行为:行选择 # selMode = QAbstractItemView.SelectItems # self.ui.ryxx_tableWidget.setSelectionBehavior(selMode) # ##选择行为:单元格选择 w = self.ui.ZhuCaiDan.indexOf(tab) self.ui.ZhuCaiDan.setCurrentIndex(w) tableWidgetX.setSortingEnabled(False) # 设置排序关闭 # 添加tableWidget内容通用函数 def chaxun(self, tableWidgetX: QTableWidgetItem, text: str, headerText: list): tableWidgetX.setSortingEnabled(False) # 设置排序关闭 tableWidgetX.clearContents() # 清空表格内容 tableWidgetX.setRowCount(0) # 设置数据区行数 rows = self.cur.execute(text) for i in range(rows): item = self.cur.fetchone() # 获取一组数组 row = tableWidgetX.rowCount() # 获得QTableWidget表格控件的行数 tableWidgetX.insertRow(row) # 插入行 for j in range(len(headerText)): if item[headerText[j]] is not None: items = QTableWidgetItem(item[headerText[j]]) tableWidgetX.setItem(i, j, items) else: pass tableWidgetX.resizeRowsToContents() # 自动行高 # tableWidgetX.resizeColumnsToContents() # 自动列宽 #设置表格头的伸缩模式,也就是让表格铺满整个QTableWidget控件 self.ui.ryxx_tableWidget.horizontalHeader().setSectionResizeMode( QHeaderView.Stretch) str="QHeaderView::up-arrow { subcontrol-position: center right; padding-right: 1px;" \ "image: url(ICO/ico/247.ico);}" + \ "QHeaderView::down-arrow { subcontrol-position: center right; padding-right: 1px;" \ "image: url(ICO/ico/248.ico);}" tableWidgetX.horizontalHeader().setStyleSheet( str) #修改排序图标的展现方式(修改图标、位置) # tableWidgetX.setSortIndicatorShown(bool show) # connect(tableWidgetX.horizontalHeader(), SIGNAL(sectionClicked(int)), # tableWidgetX, SLOT(sortByColumn(int))) # 连接信号与槽 # tableWidgetX.horizontalHeader().setSortIndicator(0, AscendingOrder) # tableWidgetX.horizontalHeader().setClickable(true) tableWidgetX.horizontalHeader().setSortIndicatorShown(True) # 显示排序图标 tableWidgetX.setSortingEnabled(True) # 设置排序已启用 # tableWidgetX.sortItems(2,Qt.DescendingOrder) # Qt.AscEndingOrder升序,Qt.DescendingOrder降序 # 数据库连接 def connect_db(self): try: file = open('my.ini', 'r') global L while True: d = file.readline() if not d: file.close() # 关闭文件 break cc = d.split('=')[1].strip() L.append(cc) # # 建立数据库连接 db = pymysql.connect( host=L[0], # 'localhost', # "192.168.202.1""127.0.0.1" port=int(L[1]), # 3306 user=L[2], # 'root' password=L[3], # '080420' db=L[4], # 'mysql' charset=str(L[5])) # 字体设置"utf8" return db except IOError: QMessageBox.about(self, '提示信息', '服务器链接失败') # 窗口关闭提示 def closeEvent(self, event): result = QMessageBox.question(self, '关闭提示框', '确定要退出吗?', QMessageBox.Yes | QMessageBox.No, QMessageBox.NoButton) if (result == QMessageBox.Yes): event.accept() else: event.ignore() # QLineEdit日期显示 def riqikuangxuanxiang(self, zujian: QLineEdit): # show_signal = pyqtSignal() # 点击下拉框发送信号 # zujian.curDateTime.toString('yyyy/MM/dd') self.show_action = QAction(self) self.show_action.setIcon(QIcon('ICO/png/1234864.png')) zujian.addAction(self.show_action, QLineEdit.TrailingPosition) self.show_action.triggered.connect(self.openCalendar) # 信号和槽连接 self.rili = QCalendarWidget(self) self.rili.setGridVisible(True) # 是否显示日期之间的网格 self.rili.setGeometry(zujian.x(), 140, 280, 200) #日历控件位置 self.rili.hide() # 隐藏日期控件 # date = self.rili.selectedDate()#获取选中日期,默认当前系统时间 self.rili.clicked[QDate].connect( self.showDate) #clicked[参数],即定义showDate是传入的参数类型设置 # self.show_action.triggered.connect(self.showDate(date,zujian)) # if self.rili.clicked[QDate].connect() = True: # zujian.setText(date.toString("yyyy/MM/dd")) # self.rili.close() # 关闭日期控件 def showDate(self, date): self.ui.ryxx_J_riqi.setText(date.toString("yyyy/MM/dd")) self.rili.close() #关闭日期控件 def openCalendar(self): self.rili.show() #显示日期控件
def setup(self): for label, value in self.data: if label is None and value is None: # Separator: (None, None) separator = QFrame() separator.setFrameShape(QFrame.HLine) separator.setFrameShadow(QFrame.Sunken) self.formlayout.addRow(separator) self.widgets.append(None) continue if label is None: if isinstance(value, (list, tuple)): field = PushLayout(value, self) self.formlayout.addRow(field) else: img_fmt = tuple(['.'+str(bytes(ext).decode()) for ext in QImageReader.supportedImageFormats()]) if value.endswith(img_fmt): # Image pixmap = QPixmap(value) lab = QLabel() lab.setPixmap(pixmap) self.formlayout.addRow(lab) else: # Comment self.formlayout.addRow(QLabel(value)) self.widgets.append(None) continue if tuple_to_qfont(value) is not None: field = FontLayout(value, self) elif text_to_qcolor(value).isValid(): field = ColorLayout(QColor(value), self) elif is_text_string(value): if value in ['file', 'dir'] or value.startswith('file:'): field = FileLayout(value, self) elif value == 'slider' or value.startswith('slider:') \ or value.startswith('slider@'): field = SliderLayout(value, self) elif value == 'password': field = QLineEdit(self) field.setEchoMode(QLineEdit.Password) elif value in ['calendar', 'calendarM'] \ or value.startswith(('calendar:', 'calendarM:')) \ or value.startswith(('calendar@', 'calendarM@')): index = value.find('@') if index != -1: value, date = value[:index], value[index+1:] else: date = False field = QCalendarWidget(self) field.setVerticalHeaderFormat(field.NoVerticalHeader) parsed = value.split(':') if parsed[-1] == '': field.setGridVisible(True) parsed.pop(-1) if parsed[0] == 'calendarM': field.setFirstDayOfWeek(Qt.Monday) if len(parsed) == 2: field.setMaximumDate(datetime.date(*eval(parsed[1]))) elif len(parsed) == 3: field.setMinimumDate(datetime.date(*eval(parsed[1]))) field.setMaximumDate(datetime.date(*eval(parsed[2]))) if date: field.setSelectedDate(datetime.date(*eval(date))) elif '\n' in value: if value == '\n': value = '' for linesep in (os.linesep, '\n'): if linesep in value: value = value.replace(linesep, "\u2029") # paragraph separator field = QTextEdit(value, self) else: field = QLineEdit(value, self) elif isinstance(value, (list, tuple)) and is_text_string(value[0])\ and (value[0].startswith('0v') or value[0].startswith('0h') or value[0].startswith('1v') or value[0].startswith('1h')): if value[0][2:]: binary = value[0][2:] else: binary = value[0][0] * len(value[1:]) if value[0][1] == 'v': field = CheckVLayout(value[1:], binary, self) elif value[0][1] == 'h': field = CheckHLayout(value[1:], binary, self) elif isinstance(value, (list, tuple)): save_value = value value = list(value) # always needed to protect self.data selindex = value.pop(0) if isinstance(selindex, int): selindex = selindex - 1 if isinstance(value[0], (list, tuple)): keys = [ key for key, _val in value ] value = [ val for _key, val in value ] else: keys = value if selindex in value: selindex = value.index(selindex) elif selindex in keys: selindex = keys.index(selindex) elif not isinstance(selindex, int): print(f"Warning: '{selindex}' index is invalid (label: {label}, value: {value})" ,file=sys.stderr) selindex = -1 if isinstance(save_value, list): field = QComboBox(self) field.addItems(value) field.setCurrentIndex(selindex) elif isinstance(save_value, tuple): field = RadioLayout(value, selindex, self) elif isinstance(value, bool): field = QCheckBox(self) field.setChecked(value) elif isinstance(value, float): field = QLineEdit(QLocale().toString(value), self) field.setValidator(QDoubleValidator(field)) dialog = self.get_dialog() dialog.register_float_field(field) if SIGNAL is None: field.textChanged.connect(dialog.float_valid) else: self.connect(field, SIGNAL('textChanged(QString)'), dialog.float_valid) elif isinstance(value, int): field = QSpinBox(self) field.setRange(-1e9, 1e9) field.setValue(value) elif isinstance(value, datetime.datetime): field = QDateTimeEdit(self) field.setDateTime(value) elif isinstance(value, datetime.date): field = QDateEdit(self) field.setDate(value) elif isinstance(value, datetime.time): field = QTimeEdit(self) field.setTime(value) else: field = QLineEdit(repr(value), self) # Eventually catching the 'countfield' feature and processing it if label.startswith('n '): label = label[2:] if isinstance(field, QLineEdit) and is_text_string(value) or isinstance(field, QComboBox): field = CountLayout(field) else: print(f"Warning: '{label}' doesn't support 'nfield' feature", file=sys.stderr) # Eventually extracting tooltip from label and processing it index = label.find('::') if index != -1: label, tooltip = label[:index], label[index+2:] field.setToolTip(tooltip) # Eventually catching the 'required' feature and processing it if label.endswith(' *'): label = label[:-1] + '<font color="red">*</font>' if isinstance(field, (QLineEdit, QTextEdit, QComboBox, FileLayout, RadioLayout)): dialog = self.get_dialog() dialog.register_required_field(field) else: print(f"Warning: '{type(field)}' doesn't support 'required' feature", file=sys.stderr) if isinstance(field, QLineEdit): if SIGNAL is None: field.textChanged.connect(dialog.required_valid) else: self.connect(field, SIGNAL('textChanged(QString)'),dialog.required_valid) elif isinstance(field, QTextEdit): if SIGNAL is None: field.textChanged.connect(dialog.required_valid) else: self.connect(field, SIGNAL('textChanged()'),dialog.required_valid) elif isinstance(field, QComboBox): if SIGNAL is None: field.currentIndexChanged.connect(dialog.required_valid) else: self.connect(field,SIGNAL('currentIndexChanged(QString)'),dialog.required_valid) elif isinstance(field, FileLayout): if SIGNAL is None: field.lineedit.textChanged.connect(dialog.required_valid) else: self.connect(field.lineedit,SIGNAL('textChanged(QString)'),dialog.required_valid) elif isinstance(field, RadioLayout): if SIGNAL is None: field.group.buttonClicked.connect(dialog.required_valid) else: self.connect(field.group, SIGNAL('buttonClicked(int)'),dialog.required_valid) # Eventually setting the widget_color if self.widget_color: style = "background-color:" + self.widget_color + ";" field.setStyleSheet(style) if self.type == 'form': self.formlayout.addRow(label, field) elif self.type == 'questions': self.formlayout.addRow(QLabel(label)) self.formlayout.addRow(field) self.widgets.append(field)
class MainWindow(QMainWindow): def __init__(self, user: User): super().__init__() logging.debug("MainWindow creation") self.ui = Ui_MainWindow(self) self.retranslate_ui() self.set_offer_ui_enabled(False) self.font_database = QFontDatabase() self.font_database.addApplicationFont(':/font-regular') self.font_database.addApplicationFont(':/font-medium') self.font_database.addApplicationFont(':/font-bold') self.offer_font = self.font_database.font('Montserrat', 'Regular', 7) logging.info(f"Loaded font for offer print: {self.offer_font.family()} {self.offer_font.styleName()}") self.offer = None self.user = user self.calendar = QCalendarWidget() self.ui.action_new.triggered.connect(self.new_offer) self.ui.action_open.triggered.connect(self.load_offer) self.ui.action_save.triggered.connect(self.save_offer) self.ui.action_new_number.triggered.connect(self.new_offer_symbol) self.ui.action_exit.triggered.connect(self.exit) self.ui.action_print.triggered.connect(self.print_preview) self.ui.action_PDF.triggered.connect(self.print_pdf) self.ui.action_create_merchandise.triggered.connect(self.create_merchandise) self.ui.action_create_customer.triggered.connect(self.create_customer) self.ui.action_about.triggered.connect(self.about) self.ui.action_about_Qt.triggered.connect(self.about_qt) self.ui.push_button_add_merchandise.clicked.connect(self.select_merchandise) self.ui.push_button_remove_row.clicked.connect(self.remove_row) self.ui.push_button_discount.clicked.connect(self.set_discount) self.ui.push_button_discount_group.clicked.connect(self.set_discount_group) self.ui.command_link_button_customer.clicked.connect(self.select_customer) self.ui.check_box_query_date.stateChanged.connect(self.inquiry_date_toggled) self.ui.line_edit_query_date.textChanged.connect(self.inquiry_date_text_changed) self.ui.push_button_query_date.clicked.connect(self.inquiry_date_button_clicked) self.ui.check_box_query_number.stateChanged.connect(self.inquiry_number_toggled) self.ui.line_edit_query_number.textChanged.connect(self.inquiry_number_changed) self.ui.command_link_button_delivery.clicked.connect(self.select_delivery_terms) self.ui.command_link_button_offer.clicked.connect(self.select_offer_terms) self.ui.command_link_button_billing.clicked.connect(self.select_billing_terms) self.ui.command_link_button_delivery_date.clicked.connect(self.select_delivery_date_terms) self.ui.plain_text_edit_remarks.textChanged.connect(self.update_remarks) # must be connected at the end or will break tests self.calendar.clicked.connect(self.inquiry_date_changed) def retranslate_ui(self) -> None: self.ui.menu_offer.setTitle(self.tr("Offer")) self.ui.menu_export.setTitle(self.tr("Export")) self.ui.menu_database.setTitle(self.tr("Database")) self.ui.menu_help.setTitle(self.tr("Help")) self.ui.action_new.setText(self.tr("New")) self.ui.action_open.setText(self.tr("Open")) self.ui.action_save.setText(self.tr("Save")) self.ui.action_exit.setText(self.tr("Exit")) self.ui.action_PDF.setText(self.tr("PDF")) self.ui.action_print.setText(self.tr("Print preview")) self.ui.action_create_merchandise.setText(self.tr("Create merchandise")) self.ui.action_create_customer.setText(self.tr("Create customer")) self.ui.action_about.setText(self.tr("About")) self.ui.action_about_Qt.setText(self.tr("About Qt")) self.ui.action_new_number.setText(self.tr("Set new offer symbol")) self.ui.push_button_add_merchandise.setText(self.tr("Add merchandise")) self.ui.push_button_discount.setText(self.tr("Set Discount")) self.ui.push_button_discount_group.setText(self.tr("Set Discount for group")) self.ui.push_button_remove_row.setText(self.tr("Remove row")) self.ui.tabWidget.setTabText(self.ui.tabWidget.indexOf(self.ui.tab), self.tr("Offer table")) self.ui.tabWidget.setTabText(self.ui.tabWidget.indexOf(self.ui.tab_2), self.tr("Other information")) self.ui.command_link_button_customer.setText(self.tr("Choose customer")) self.ui.grup_box_query.setTitle(self.tr("Inquiry")) self.ui.check_box_query_date.setText(self.tr("Inquiry date:")) self.ui.push_button_query_date.setText("") self.ui.check_box_query_number.setText(self.tr("Inquiry number:")) self.ui.groupBox.setTitle(self.tr("Other information")) self.ui.command_link_button_delivery.setText(self.tr("Shipment terms")) self.ui.command_link_button_delivery_date.setText(self.tr("Delivery date")) self.ui.command_link_button_billing.setText(self.tr("Billing terms")) self.ui.command_link_button_offer.setText(self.tr("Offer terms")) self.ui.command_link_button_remarks.setText(self.tr("Remarks")) self.ui.group_box_columns.setTitle(self.tr("Columns to be printed")) self.ui.check_box_no_column.setText(self.tr("No.")) self.ui.check_box_code_column.setText(self.tr("Code")) self.ui.check_box_details_column.setText(self.tr("Specification")) self.ui.check_box_list_price_column.setText(self.tr("List Price")) self.ui.check_box_discount_column.setText(self.tr("Discount")) self.ui.check_box_price_column.setText(self.tr("Price")) self.ui.check_box_quantity_column.setText(self.tr("Quantity")) self.ui.check_box_total_column.setText(self.tr("Total")) def set_offer_ui_enabled(self, enable: bool) -> None: # menus self.ui.menu_export.setEnabled(enable) self.ui.action_save.setEnabled(enable) self.ui.action_new_number.setEnabled(enable) # tabs self.ui.tab.setEnabled(enable) self.ui.tab_2.setEnabled(enable) def update_inquiry_text(self) -> None: self.ui.plain_text_edit_query.setPlainText(self.offer.inquiry_text) @Slot() def new_offer(self) -> None: self.offer = Offer.create_empty(self.user, self) self.set_offer_ui_enabled(True) self.setWindowTitle(f"pyOffer - {self.offer.symbol}") self.ui.tableView.setModel(self.offer.merchandise_list) self.update_inquiry_text() @Slot() def new_offer_symbol(self) -> None: self.offer.new_symbol() self.setWindowTitle(f"pyOffer - {self.offer.symbol}") @Slot() def select_customer(self) -> None: dialog = CustomerSelectionDialog.make(self) if dialog.exec_() == QDialog.Accepted and dialog.chosen_customer: self.ui.plain_text_edit_customer.setPlainText(dialog.chosen_customer.description) self.offer.customer = dialog.chosen_customer @Slot() def update_remarks(self) -> None: self.offer.remarks = self.ui.plain_text_edit_remarks.toPlainText() @Slot() def select_delivery_terms(self) -> None: term_type = TermType.delivery dialog = TermsChooserDialog.make(term_type, self) if dialog.exec_() == QDialog.Accepted and dialog.chosen_item: self.ui.plain_text_edit_delivery.setPlainText(dialog.chosen_item.long_desc) self.offer.terms[term_type] = dialog.chosen_item @Slot() def select_offer_terms(self) -> None: term_type = TermType.offer dialog = TermsChooserDialog.make(term_type, self) if dialog.exec_() == QDialog.Accepted and dialog.chosen_item: self.ui.plain_text_edit_offer.setPlainText(dialog.chosen_item.long_desc) self.offer.terms[term_type] = dialog.chosen_item @Slot() def select_billing_terms(self) -> None: term_type = TermType.billing dialog = TermsChooserDialog.make(term_type, self) if dialog.exec_() == QDialog.Accepted and dialog.chosen_item: self.ui.plain_text_edit_billing.setPlainText(dialog.chosen_item.long_desc) self.offer.terms[term_type] = dialog.chosen_item @Slot() def select_delivery_date_terms(self) -> None: term_type = TermType.delivery_date dialog = TermsChooserDialog.make(term_type, self) if dialog.exec_() == QDialog.Accepted and dialog.chosen_item: self.ui.plain_text_edit_delivery_date.setPlainText(dialog.chosen_item.long_desc) self.offer.terms[term_type] = dialog.chosen_item @Slot() def select_merchandise(self) -> None: dialog = MerchandiseSelectionDialog.make(self) dialog.exec_() for item in dialog.selected.values(): self.offer.merchandise_list.change_item_count(item) @Slot() def remove_row(self) -> None: index = self.ui.tableView.currentIndex() if index.row() < self.offer.merchandise_list.rowCount(): self.offer.merchandise_list.removeRow(index.row()) @Slot() def set_discount(self) -> None: dialog = DiscountDialog(self) dialog.line_edit_expression.textChanged.connect(self.offer.merchandise_list.select_items) self.offer.merchandise_list.select_items("") if dialog.exec_() == QDialog.Accepted: self.offer.merchandise_list.apply_discount(dialog.discount_value) else: self.offer.merchandise_list.select_items(None) @Slot() def set_discount_group(self) -> None: dialog = DiscountGroupDialog(self.offer.merchandise_list.get_discount_groups(), self) dialog.selectionChanged.connect(self.offer.merchandise_list.select_items) if dialog.exec_() == QDialog.Accepted: self.offer.merchandise_list.apply_discount(dialog.discount_value) else: self.offer.merchandise_list.select_items(None) @Slot() def inquiry_date_button_clicked(self) -> None: self.ui.check_box_query_date.setChecked(Qt.Checked) self.calendar.show() @Slot(QDate) def inquiry_date_changed(self, d: QDate) -> None: self.ui.line_edit_query_date.setText(f"{d.toPython():%d.%m.%Y}") self.calendar.close() @Slot(int) def inquiry_date_toggled(self, state: int) -> None: enabled = state == Qt.Checked self.ui.line_edit_query_date.setEnabled(enabled) if enabled: self.ui.line_edit_query_date.setText(f"{date.today():%d.%m.%Y}") else: self.ui.line_edit_query_date.clear() @Slot(str) def inquiry_date_text_changed(self, text: str) -> None: self.offer.inquiry_date = text self.update_inquiry_text() @Slot(int) def inquiry_number_toggled(self, state: int) -> None: enabled = state == Qt.Checked self.ui.line_edit_query_number.setEnabled(enabled) if not enabled: self.ui.line_edit_query_number.clear() @Slot(str) def inquiry_number_changed(self, text: str) -> None: self.offer.inquiry_number = text self.update_inquiry_text() @Slot() def load_offer(self) -> None: pass @Slot() def save_offer(self) -> None: pass @Slot() def exit(self) -> None: """Forward to QMainWindow.close, but keep here for sake of tests""" super().close() @Slot(QPrinter) def print(self, printer: QPrinter) -> None: print_options = PrintOptions( print_no=self.ui.check_box_no_column.isChecked(), print_code=self.ui.check_box_code_column.isChecked(), print_description=self.ui.check_box_details_column.isChecked(), print_list_price=self.ui.check_box_list_price_column.isChecked(), print_discount=self.ui.check_box_discount_column.isChecked(), print_price=self.ui.check_box_price_column.isChecked(), print_quantity=self.ui.check_box_quantity_column.isChecked(), print_total=self.ui.check_box_total_column.isChecked() ) margin = 5 printer.setPageSize(QPrinter.A4) printer.setPageMargins(margin, margin, margin, margin, QPrinter.Millimeter) printer.setResolution(96) doc = QTextDocument() doc.setUseDesignMetrics(True) doc.setDefaultFont(self.offer_font) doc.setHtml(self.offer.printout(print_options)) doc.setPageSize(printer.pageRect().size()) doc.print_(printer) @Slot() def print_preview(self) -> None: printer = QPrinter() printer.setOutputFormat(QPrinter.NativeFormat) dialog = QPrintPreviewDialog(printer, self) dialog.setWindowFlags(Qt.Window) dialog.paintRequested.connect(self.print) dialog.showMaximized() dialog.exec_() @Slot() def print_pdf(self) -> None: file_name = QFileDialog.getSaveFileName(self, self.tr("Save to .pdf"), filter=self.tr("Portable Document Format (*.pdf)"))[0] if not file_name: return printer = QPrinter() printer.setOutputFormat(QPrinter.PdfFormat) printer.setOutputFileName(file_name) self.print(printer) @Slot() def create_merchandise(self) -> None: dialog = CreateMerchandiseDialog.make(self) dialog.show() @Slot() def create_customer(self) -> None: dialog = CreateCustomerDialog.make(self) dialog.show() @Slot() def about(self) -> None: QMessageBox.information(self, self.tr("About pyOffer"), self.tr("pyOffer version {}\nAll rights reserved (c) Kamil Strzempowicz".format(version))) @Slot() def about_qt(self) -> None: """Forward to QApplication.aboutQt, but keep here for sake of tests""" QApplication.aboutQt()
class CalendarDialog(QDialog): def __init__(self, parent): QDialog.__init__(self, parent) self.setModal(True) self.setTitle("Datum auswählen") self._calendar: QCalendarWidget = None self._buchungsjahrChangedCallback = None self._buttonBox: QtWidgets.QDialogButtonBox = None self._callback = None self.createCalendar() def setTitle(self, title: str) -> None: self.setWindowTitle(title) def setCallback(self, cbfnc): self._callback = cbfnc def setMinimumDate(self, y: int, m: int, d: int): self._calendar.setMinimumDate(QDate(y, m, d)) def setMaximumDate(self, y: int, m: int, d: int): self._calendar.setMaximumDate(QDate(y, m, d)) def createCalendar(self): vbox = QVBoxLayout() self._calendar = QCalendarWidget() self._calendar.setGridVisible(True) self._calendar.setFirstDayOfWeek(Qt.Monday) vbox.addWidget(self._calendar) self.setLayout(vbox) self._buttonBox = QtWidgets.QDialogButtonBox(self) self._buttonBox.setOrientation(QtCore.Qt.Horizontal) self._buttonBox.setStandardButtons(QtWidgets.QDialogButtonBox.Ok | QtWidgets.QDialogButtonBox.Cancel) self._buttonBox.layout().setDirection(QBoxLayout.RightToLeft) self._buttonBox.button(QtWidgets.QDialogButtonBox.Ok).clicked.connect( self._onOk) self._buttonBox.button( QtWidgets.QDialogButtonBox.Cancel).clicked.connect(self._onCancel) vbox.addWidget(self._buttonBox) def setSelectedDate(self, date: QDate): self._calendar.setSelectedDate(date) def setSelectedDateFromString(self, datestring: str): """ datestring needs to be given as "yyyy-mm-dd" or "dd.mm.yyyy" day and month may be given one-digit. :param datestring: :return: """ parts = datestring.split("-") if len(parts) == 0: parts = datestring.split(".") else: # yyyy-mm-dd dt = QDate(int(parts[0]), int(parts[1]), int(parts[2])) self.setSelectedDate(dt) if len(parts) == 0: raise Exception( "CalendarDialog.setSelectedDateFromString: wrong date format '%s'" % (datestring)) else: # dd.mm.yyyy dt = QDate(int(parts[2]), int(parts[1]), int(parts[0])) self.setSelectedDate(dt) def _onOk(self): date: QDate = self._calendar.selectedDate() self.hide() if self._callback: self._callback(date) def _onCancel(self): self.hide()