def createBottomView(self): rememberPsdBtn = QRadioButton() rememberPsdBtn.setText('记住密码') rememberPsdBtn.hide() autoLoginBtn = QRadioButton() autoLoginBtn.setText('自动登录') autoLoginBtn.hide() gourp = QButtonGroup(rememberPsdBtn) gourp.addButton(rememberPsdBtn) gourp.addButton(autoLoginBtn) gourp.setExclusive(False) forgetPsdBtn = QPushButton() forgetPsdBtn.setText('忘记密码') forgetPsdBtn.clicked.connect(lambda: self.btnAction(forgetPsdBtn)) forgetPsdBtn.hide() registeredBtn = QPushButton() registeredBtn.setText('注册账号') registeredBtn.hide() self.bottomLayout.addWidget(rememberPsdBtn, 1, 1) self.bottomLayout.addWidget(forgetPsdBtn, 1, 2) self.bottomLayout.addWidget(autoLoginBtn, 2, 1) self.bottomLayout.addWidget(registeredBtn, 2, 2)
def initUI(self): self.widgetLayout = QHBoxLayout(self) self.playerGroup = QGroupBox(self) self.widgetLayout.addWidget(self.playerGroup) self.playerButtonGroup = QButtonGroup(self) self.playerGroupLayout = QGridLayout(self.playerGroup) b = QRadioButton("", self.playerGroup) # self.playerGroupLayout.addWidget(b) self.playerButtonGroup.addButton(b, 0) self.playerButtons = [b] b.hide() for i, player in enumerate(self.engine.getListPlayers(), 1): b = QRadioButton( '{}. {}'.format(i, player), self.playerGroup) if len(self.engine.getListPlayers()) > 2: self.playerGroupLayout.addWidget(b, (i-1) % 2, (i-1)/2) else: self.playerGroupLayout.addWidget(b, 0, (i-1) % 2) self.playerButtonGroup.addButton(b, i) self.playerButtons.append(b) self.kindGroup = QGroupBox(self) self.widgetLayout.addWidget(self.kindGroup) self.kindButtonGroup = QButtonGroup(self) self.kindGroupLayout = QGridLayout(self.kindGroup) b = QRadioButton("", self.kindGroup) # self.kindGroupLayout.addWidget(b) self.kindButtonGroup.addButton(b, 0) self.kindButtons = [b] b.hide() self.scoreSpinBox = ScoreSpinBox(self) self.scoreSpinBox.setAlignment(QtCore.Qt.AlignCenter) self.scoreSpinBox.setMaximumWidth(60) self.scoreSpinBox.setRange(0, 300) for i, kind in enumerate(self.engine.getEntryKinds(), 1): lbl = i18n("CarcassonneInputWidget", kind) b = QRadioButton('{}. {}'.format(i, lbl), self.kindGroup) self.kindGroupLayout.addWidget(b, (i-1) % 2, (i-1)/2) self.kindButtonGroup.addButton(b, i) b.clicked.connect(self.scoreSpinBox.setFocus) self.kindButtons.append(b) self.kindButtons[3].toggled.connect(self.setCloisterPoints) self.kindButtons[5].toggled.connect(self.setGoodsPoints) self.kindButtons[6].toggled.connect(self.setFairPoints) self.scoreGroup = QGroupBox(self) self.widgetLayout.addWidget(self.scoreGroup) self.scoreGroupLayout = QHBoxLayout(self.scoreGroup) self.scoreGroupLayout.addWidget(self.scoreSpinBox) self.reset() self.retranslateUI()
class TableTabBarV2(QWidget): """ We tried to use QTabBar as the base class, we found that QTabBar's UI is hard to customize. """ show_songs_needed = pyqtSignal() show_artists_needed = pyqtSignal() show_albums_needed = pyqtSignal() show_desc_needed = pyqtSignal() show_contributed_albums_needed = pyqtSignal() def __init__(self, parent=None): super().__init__(parent=parent) self.songs_btn = QRadioButton('歌曲', self) self.albums_btn = QRadioButton('专辑', self) self.desc_btn = QRadioButton('简介', self) self.contributed_btn = QRadioButton('参与作品', self) self._layout = QHBoxLayout(self) self.songs_btn.clicked.connect(self.show_songs_needed.emit) self.albums_btn.clicked.connect(self.show_albums_needed.emit) self.desc_btn.clicked.connect(self.show_desc_needed.emit) self.contributed_btn.clicked.connect( self.show_contributed_albums_needed.emit) self.check_default() self._setup_ui() def check_default(self): self.songs_btn.setChecked(True) def artist_mode(self): self.songs_btn.show() self.albums_btn.show() self.desc_btn.show() self.contributed_btn.show() def album_mode(self): self.albums_btn.hide() self.contributed_btn.hide() self.songs_btn.show() self.desc_btn.show() def _setup_ui(self): self._layout.setSpacing(0) self._layout.setContentsMargins(0, 0, 0, 0) self._layout.addWidget(self.desc_btn) self._layout.addWidget(self.songs_btn) self._layout.addWidget(self.albums_btn) self._layout.addWidget(self.contributed_btn)
def updatePlayerOrder(self): trash = QWidget() trash.setLayout(self.playerGroupLayout) self.playerButtonGroup = QButtonGroup(self) self.playerGroupLayout = QGridLayout(self.playerGroup) b = QRadioButton("", self.playerGroup) self.playerButtonGroup.addButton(b, 0) self.playerButtons = [b] b.hide() for i, player in enumerate(self.engine.getListPlayers(), 1): b = QRadioButton( '{}. {}'.format(i, player), self.playerGroup) if len(self.engine.getListPlayers()) > 2: self.playerGroupLayout.addWidget(b, (i-1) % 2, (i-1)/2) else: self.playerGroupLayout.addWidget(b, 0, (i-1) % 2) self.playerButtonGroup.addButton(b, i) self.playerButtons.append(b) self.reset()
class Window(QWidget): """创建窗口类""" def __init__(self): self.answers = {} super(Window, self).__init__() # self.initWindow() # # def initWindow(self): """初始化窗口设置""" # 设置图标 self.setWindowIcon(QIcon('data/qst.png')) # 设置窗口大小 self.resize(450, 350) # 获取屏幕中心点 screen_point = QDesktopWidget().availableGeometry().center() # 设置到中心 self.frameGeometry().moveCenter(screen_point) # 两个按钮,水平布局 self.h_box = QHBoxLayout() self.h_box.addStretch(1) # 伸缩因子,按钮置右 self.pre_button = QPushButton('上一题') self.next_button = QPushButton('下一题') self.commit_button = QPushButton('确认提交') self.pre_button.setMaximumWidth(120) self.next_button.setMaximumWidth(120) self.commit_button.setMaximumWidth(120) # 按钮点击关联方法 self.pre_button.clicked.connect(self.pre_question) self.next_button.clicked.connect(self.next_question) self.commit_button.clicked.connect(self.commit) # 按钮设置为不可用 self.pre_button.setEnabled(False) self.next_button.setEnabled(False) self.commit_button.setEnabled(False) self.h_box.addWidget(self.pre_button, alignment=Qt.AlignBottom) self.h_box.addWidget(self.next_button, alignment=Qt.AlignBottom) self.h_box.addWidget(self.commit_button, alignment=Qt.AlignBottom) # 垂直布局 self.v_box = QVBoxLayout() # 标签显示消息 self.content_label = QLabel() # 自动换行设置 # self.content_label.setWordWrap(True) self.content_label.setText('点击开始加载资源') # 设置标签大小 # 进度条 self.process_bar = QProgressBar() # 设置控件的大小,在布局Layout内resize方法已经不能使用,设置最大、最小、最高的参数来调整 # process_bar.setMinimumSize(100, 25) # 定时器激活进度条 self.timer = QBasicTimer() self.step = 0 # 按钮 self.start_btn = QPushButton('加载资源') self.start_btn.setMaximumSize(120, 25) # 按钮点击关联的方法 self.start_btn.clicked.connect(self.start_downloader) # 答案按钮组与答案按钮 self.ans_btn_group = QButtonGroup() # 关联方法 self.ans_btn_group.buttonClicked.connect(self.saved_answer) self.btn_a = QRadioButton() self.btn_b = QRadioButton() self.btn_c = QRadioButton() self.btn_d = QRadioButton() # 添加到组中,并设置ID self.ans_btn_group.addButton(self.btn_a, id=1) self.ans_btn_group.addButton(self.btn_b, id=2) self.ans_btn_group.addButton(self.btn_c, id=3) self.ans_btn_group.addButton(self.btn_d, id=4) # 答案按钮布局 v_ans_box = QVBoxLayout() v_ans_box.addWidget(self.btn_a, alignment=Qt.AlignLeft) v_ans_box.addWidget(self.btn_b, alignment=Qt.AlignLeft) v_ans_box.addWidget(self.btn_c, alignment=Qt.AlignLeft) v_ans_box.addWidget(self.btn_d, alignment=Qt.AlignLeft) # 设置按钮之间的距离 v_ans_box.setSpacing(10) # 与外布局之间的距离,左,上,右,下 v_ans_box.setContentsMargins(QMargins(100, 0, 0, 0)) # 设置隐藏 self.btn_a.hide() self.btn_b.hide() self.btn_c.hide() self.btn_d.hide() # 布局添加标签、进度条和按钮 self.v_box.addWidget(self.content_label, alignment=Qt.AlignCenter) self.v_box.addWidget(self.process_bar) self.v_box.addWidget(self.start_btn, alignment=Qt.AlignCenter) # 设置控件距离 self.v_box.setSpacing(5) # 将水平布局加入垂直布局 self.v_box.addLayout(v_ans_box) self.v_box.addLayout(self.h_box) # 窗口展示布局 self.setLayout(self.v_box) # 窗口标题 self.setWindowTitle('测测你是谁?') self.show() def timerEvent(self, *args, **kwargs): """重写时间处理""" if self.step >= 100: self.timer.stop() self.content_label.setText('资源加载完成!') self.start_btn.setText('开始测试') return self.step += 5 self.process_bar.setValue(self.step) def start_downloader(self): """开始加载资源""" if self.timer.isActive(): self.timer.stop() self.start_btn.setText('继续加载') else: if self.step >= 100: # 加载完成再次点击可进入测试 self.enter_test() else: self.timer.start(20, self) self.start_btn.setText('暂停') def enter_test(self): print('开始测试') # 进入测试界面发生改变 # 上下题按钮设置为可用 self.pre_button.setEnabled(True) self.next_button.setEnabled(True) # 去掉进度条和'开始测试'按钮 self.v_box.removeWidget(self.process_bar) self.v_box.removeWidget(self.start_btn) sip.delete(self.process_bar) sip.delete(self.start_btn) # QLabel显示信息变为题目信息 question_dict = QUESTIONS.get('1') # 设置内容 self.set_content(question_dict) # 显示选项按钮 self.btn_a.show() self.btn_b.show() self.btn_c.show() self.btn_d.show() def set_content(self, qd): if isinstance(qd, dict): question = qd.get('Q', 'No Question!') answer_a = qd.get('A', 'No Answer A') answer_b = qd.get('B', 'No Answer B') answer_c = qd.get('C', 'No Answer C') answer_d = qd.get('D', 'No Answer D') self.content_label.setText(question) # 答案按钮的添加内容并可见 self.btn_a.setText(answer_a) self.btn_b.setText(answer_b) self.btn_c.setText(answer_c) self.btn_d.setText(answer_d) else: print("the params 'qd' of function set_content must be class dict") def match_sequence(self): q = self.content_label.text() result = re.match('\d', q) if result: sequence = result.group() else: sequence = 0 return int(sequence) def pre_question(self): # 获取当前是第几条题目 sequence = self.match_sequence() if 1 < sequence <= len(QUESTIONS): # 开启一题按钮 self.next_button.setEnabled(True) # 获取上一题内容 question_dict = QUESTIONS.get(str(sequence - 1)) # 设置内容到标签和按钮 self.set_content(question_dict) else: # 将上一题按钮设置不可用 self.pre_button.setEnabled(False) def next_question(self): # 获取当前是第几条题目 sequence = self.match_sequence() if 1 <= int(sequence) < len(QUESTIONS): # 开启上一题按钮 self.pre_button.setEnabled(True) # 获取下一题内容 question_dict = QUESTIONS.get(str(sequence + 1)) # 设置内容 self.set_content(question_dict) else: # 将下题按钮设置为不可用 self.next_button.setEnabled(False) # 提交按钮可用 self.commit_button.setEnabled(True) def commit(self): lock, key = self.checked_answer() if lock: print('提交成功') else: print('第{}题还没做!'.format(key)) def checked_answer(self): for key in QUESTIONS: if not self.answers.get(key): return False, key return True, 1 # def clear_checked(self): # """清除按钮选中状态""" # if self.btn_a.isChecked(): # self.btn_a.setChecked(True) # # if self.btn_b.isChecked(): # # self.btn_b.setChecked(True) # if self.btn_c.isChecked(): # # self.btn_c.setChecked(True) # if self.btn_d.isChecked(): # # self.btn_d.setChecked(True) def saved_answer(self): if self.ans_btn_group.checkedId() == 1: print('您选择了A') # 获取当前题号 sequence = str(self.match_sequence()) self.answers[sequence] = 'A' elif self.ans_btn_group.checkedId() == 2: print('您选择了B') sequence = str(self.match_sequence()) self.answers[sequence] = 'B' elif self.ans_btn_group.checkedId() == 3: print('您选择了C') sequence = str(self.match_sequence()) self.answers[sequence] = 'C' else: print('您选择了D') sequence = str(self.match_sequence()) self.answers[sequence] = 'D'
class SongsTableToolbar(QWidget): _desc_btn_checked_text = '折叠' _desc_btn_unchecked_text = '展开描述' play_all_needed = pyqtSignal() show_songs_needed = pyqtSignal() show_albums_needed = pyqtSignal() # show_videos_needed = pyqtSignal() # album filters filter_albums_mini_needed = pyqtSignal() filter_albums_contributed_needed = pyqtSignal() filter_albums_live_needed = pyqtSignal() filter_albums_all_needed = pyqtSignal() toggle_desc_needed = pyqtSignal() def __init__(self, parent=None): super().__init__(parent) self.play_all_btn = QPushButton('播放全部', self) self.show_songs_btn = QPushButton('歌曲', parent=self) self.show_albums_btn = QPushButton('专辑', parent=self) # self.show_videos_btn = QPushButton(parent=self) self.desc_btn = QPushButton(self._desc_btn_unchecked_text, self) self.play_all_btn.clicked.connect(self.play_all_needed.emit) self.show_songs_btn.clicked.connect(self.show_songs_needed.emit) self.show_albums_btn.clicked.connect(self.show_albums_needed.emit) # self.show_videos_btn.clicked.connect(self.show_videos_needed.emit) self.desc_btn.clicked.connect(self.on_desc_btn_toggled) # album filters self.filter_albums_all_btn = QRadioButton('所有', parent=self) self.filter_albums_mini_btn = QRadioButton('单曲与EP', parent=self) self.filter_albums_contributed_btn = QRadioButton('参与作品', parent=self) self.filter_albums_live_btn = QRadioButton('现场', parent=self) self.filter_albums_all_btn.clicked.connect( self.filter_albums_all_needed.emit) self.filter_albums_mini_btn.clicked.connect( self.filter_albums_mini_needed.emit) self.filter_albums_contributed_btn.clicked.connect( self.filter_albums_contributed_needed.emit) self.filter_albums_live_btn.clicked.connect( self.filter_albums_live_needed.emit) self.show_songs_btn.hide() self.show_albums_btn.hide() self.desc_btn.hide() self.filter_albums_mini_btn.hide() self.filter_albums_contributed_btn.hide() self.filter_albums_all_btn.hide() self.filter_albums_live_btn.hide() self._setup_ui() def before_change_mode(self): """filter all filter buttons""" self.filter_albums_mini_btn.hide() self.filter_albums_contributed_btn.hide() self.filter_albums_all_btn.hide() self.filter_albums_live_btn.hide() def artist_mode(self): self.before_change_mode() self.play_all_btn.show() self.show_songs_btn.show() self.show_albums_btn.show() def albums_mode(self): self.before_change_mode() self.play_all_btn.hide() self.show_albums_btn.show() self.filter_albums_mini_btn.show() self.filter_albums_contributed_btn.show() self.filter_albums_all_btn.show() self.filter_albums_live_btn.show() def songs_mode(self): self.before_change_mode() self.play_all_btn.show() def pure_songs_mode(self): """playlist/collections mode""" self.before_change_mode() self.show_albums_btn.hide() self.show_songs_btn.hide() self.play_all_btn.show() def enter_state_playall_start(self): self.play_all_btn.setEnabled(False) # currently, this is called only when feeluown is fetching songs, # so when we enter state_playall_start, we set play all btn text # to this. self.play_all_btn.setText('正在获取全部歌曲...') def enter_state_playall_end(self): self.play_all_btn.setText('正在获取全部歌曲...done') self.play_all_btn.setEnabled(True) self.play_all_btn.setText('播放全部') def _setup_ui(self): self._layout = QHBoxLayout(self) self._layout.setContentsMargins(0, 0, 0, 0) self._layout.setSpacing(0) self._layout.addWidget(self.play_all_btn) self._layout.addSpacing(5) self._layout.addWidget(self.show_songs_btn) self._layout.addSpacing(5) self._layout.addWidget(self.show_albums_btn) self._layout.addStretch(1) self._layout.addWidget(self.filter_albums_all_btn) self._layout.addWidget(self.filter_albums_mini_btn) self._layout.addWidget(self.filter_albums_live_btn) self._layout.addWidget(self.filter_albums_contributed_btn) self._layout.addStretch(1) self._layout.addWidget(self.desc_btn) self._layout.addStretch(1) def on_desc_btn_toggled(self, checked): if checked: self.play_all_btn.hide() self.desc_btn.setText(self._desc_btn_checked_text) else: self.play_all_btn.show() self.desc_btn.setText(self._desc_btn_unchecked_text) self.toggle_desc_needed.emit()
class NutrientStatPlotter(QMainWindow): def __init__(self): super().__init__() self.setWindowIcon(QIcon(':/assets/icon.svg')) self.central_widget = QWidget() self.setCentralWidget(self.central_widget) self.header_key = { 'NOx': 'NOx', 'Phosphate': 'PHOSPHATE', 'Silicate': 'SILICATE', 'Ammonia': 'AMMONIA', 'Nitrite': 'NITRITE', 'Salinity': 'Salinity (PSU)', 'Oxygen': 'Oxygen (uM)' } self.init_ui() self.reagent_colour = '#000000' self.reaglines = [] self.legend_label = '' self.rad_sel = 'none' self.setStyleSheet(''' QLabel { font: 14px; } QPushButton { font: 14px; } QComboBox { font: 14px; } QListWidget { font: 14px; } QTableWidget { font: 14px; } QCheckBox { font: 14px; } QRadioButton { font: 14px; } ''') def init_ui(self): self.setFont(QFont('Segoe UI')) grid_layout = QGridLayout() grid_layout.setSpacing(10) self.setGeometry(0, 0, 950, 500) qtRect = self.frameGeometry() centrePoint = QDesktopWidget().availableGeometry().center() qtRect.moveCenter(centrePoint) self.move(qtRect.topLeft()) self.setWindowTitle('Hydro Nut Base/Gain Plotter') folder_label = QLabel( 'Find folder that contains a voyages worth \nof nutrient .SLK files: ' ) self.folder_path = QLineEdit('') folder_browse = QPushButton('Browse...') folder_browse.clicked.connect(self.locate_folder) linesep1 = QFrame() linesep1.setFrameShape(QFrame.HLine) linesep1.setFrameShadow(QFrame.Sunken) nutrient_label = QLabel('Select Nutrient to view: ') self.select_nutrient = QComboBox() self.select_nutrient.addItems( ['NOx', 'Phosphate', 'Silicate', 'Ammonia', 'Nitrite']) self.select_nutrient.currentTextChanged.connect(self.populate_radios) self.draw_base = QCheckBox('Draw Baseline Offset') self.draw_gain = QCheckBox('Draw Gain') plot_by_label = QLabel('Plot Data By: ') self.plot_by_option = QComboBox() self.plot_by_option.addItems(['Analysis', 'Date']) draw = QPushButton('View Data') draw.clicked.connect(self.draw_data) linesep2 = QFrame() linesep2.setFrameShape(QFrame.HLine) linesep2.setFrameShadow(QFrame.Sunken) plot_drawing_label = QLabel('Draw Line for Fresh Reagent') self.nox_colour = QRadioButton('NEDD Colour') self.nox_colour.toggled.connect( lambda: self.radio_selected(self.nox_colour)) self.nox_buffer = QRadioButton('Amm Chl Buffer') self.nox_buffer.toggled.connect( lambda: self.radio_selected(self.nox_buffer)) self.nox_column = QRadioButton('Cadmium Column') self.nox_column.toggled.connect( lambda: self.radio_selected(self.nox_column)) self.nitrite_colour = QRadioButton('NEDD Colour') self.nitrite_colour.toggled.connect( lambda: self.radio_selected(self.nitrite_colour)) self.phosphate_colour = QRadioButton('Phos Molybdate Colour') self.phosphate_colour.toggled.connect( lambda: self.radio_selected(self.phosphate_colour)) self.phoshphate_acid = QRadioButton('Ascorbic Acid') self.phoshphate_acid.toggled.connect( lambda: self.radio_selected(self.phoshphate_acid)) self.silicate_colour = QRadioButton('Sil Molybdate Colour') self.silicate_colour.toggled.connect( lambda: self.radio_selected(self.silicate_colour)) self.silicate_acid = QRadioButton('Tartaric Acid') self.silicate_acid.toggled.connect( lambda: self.radio_selected(self.silicate_acid)) self.silicate_reductant = QRadioButton('Stannous Chloride') self.silicate_reductant.toggled.connect( lambda: self.radio_selected(self.silicate_reductant)) self.ammonia_reagent = QRadioButton('OPA') self.ammonia_reagent.toggled.connect( lambda: self.radio_selected(self.ammonia_reagent)) self.erase = QPushButton('Undo') self.erase.clicked.connect(self.undo_plot) self.copy = QPushButton('Copy') self.copy.clicked.connect(self.copy_plot) self.figure = plt.figure() self.figure.set_tight_layout(tight=True) self.canvas = FigureCanvas(self.figure) self.canvas.setParent(self) self.toolbar = NavigationToolbar(self.canvas, self) grid_layout.addWidget(folder_label, 0, 0, 1, 3) grid_layout.addWidget(self.folder_path, 1, 0, 1, 3) grid_layout.addWidget(folder_browse, 2, 2, 1, 1) grid_layout.addWidget(linesep1, 3, 0, 1, 3) grid_layout.addWidget(nutrient_label, 4, 0, 1, 3) grid_layout.addWidget(self.select_nutrient, 4, 2) grid_layout.addWidget(self.draw_base, 6, 0, 1, 1) grid_layout.addWidget(self.draw_gain, 7, 0, 1, 1) grid_layout.addWidget(plot_by_label, 5, 0, 1, 3) grid_layout.addWidget(self.plot_by_option, 5, 2, 1, 1) grid_layout.addWidget(draw, 8, 0, 1, 3) grid_layout.addWidget(linesep2, 9, 0, 1, 3) grid_layout.addWidget(plot_drawing_label, 10, 0, 1, 3) grid_layout.addWidget(self.nox_colour, 11, 0, 1, 2) grid_layout.addWidget(self.nox_buffer, 12, 0, 1, 2) grid_layout.addWidget(self.nox_column, 13, 0, 1, 2) grid_layout.addWidget(self.nitrite_colour, 11, 0, 1, 2) grid_layout.addWidget(self.phosphate_colour, 11, 0, 1, 2) grid_layout.addWidget(self.phoshphate_acid, 12, 0, 1, 2) grid_layout.addWidget(self.silicate_colour, 11, 0, 1, 2) grid_layout.addWidget(self.silicate_acid, 12, 0, 1, 2) grid_layout.addWidget(self.silicate_reductant, 13, 0, 1, 2) grid_layout.addWidget(self.ammonia_reagent, 11, 0, 1, 2) grid_layout.addWidget(self.erase, 14, 0) grid_layout.addWidget(self.copy, 14, 2) grid_layout.addWidget(self.canvas, 0, 3, 14, 7) grid_layout.addWidget(self.toolbar, 14, 3) self.mainplot = self.figure.add_subplot(111) self.mainplot.set_facecolor('#f9f9f9') self.second = self.mainplot.twinx() self.centralWidget().setLayout(grid_layout) self.populate_radios() self.show() clicker = self.figure.canvas.mpl_connect("button_press_event", self.on_click) def undo_plot(self): try: self.mainplot.lines.pop(-1) self.reaglines.pop(-1) self.canvas.draw() except Exception: print(traceback.print_exc()) def copy_plot(self): buffer = io.BytesIO() self.figure.savefig(buffer, dpi=300) QApplication.clipboard().setImage(QImage.fromData(buffer.getvalue())) def draw_reagent_line(self, x): if self.rad_sel != 'none': current_ledge = self.mainplot.get_legend().texts current_labs = [] for item in current_ledge: current_labs.append(item.get_text()) if self.legend_label in current_labs: self.legend_label = '' bot, top = self.mainplot.get_ylim() self.reaglines.append( self.mainplot.plot([x + self.x_offset, x + self.x_offset], [-10000, 10000], color=self.reagent_colour, ls=self.line_styl, lw=1, label=self.legend_label)) self.mainplot.set_ylim(bot, top) self.mainplot.legend() self.canvas.draw() def populate_radios(self): nut = self.select_nutrient.currentText() if nut == 'NOx': self.nox_colour.show() self.nox_buffer.show() self.nox_column.show() self.phoshphate_acid.hide() self.phosphate_colour.hide() self.silicate_acid.hide() self.silicate_colour.hide() self.silicate_reductant.hide() self.ammonia_reagent.hide() self.nitrite_colour.hide() if nut == 'Phosphate': self.nox_colour.hide() self.nox_buffer.hide() self.nox_column.hide() self.phoshphate_acid.show() self.phosphate_colour.show() self.silicate_acid.hide() self.silicate_colour.hide() self.silicate_reductant.hide() self.ammonia_reagent.hide() self.nitrite_colour.hide() if nut == 'Silicate': self.nox_colour.hide() self.nox_buffer.hide() self.nox_column.hide() self.phoshphate_acid.hide() self.phosphate_colour.hide() self.silicate_acid.show() self.silicate_colour.show() self.silicate_reductant.show() self.ammonia_reagent.hide() self.nitrite_colour.hide() if nut == 'Ammonia': self.nox_colour.hide() self.nox_buffer.hide() self.nox_column.hide() self.phoshphate_acid.hide() self.phosphate_colour.hide() self.silicate_acid.hide() self.silicate_colour.hide() self.silicate_reductant.hide() self.ammonia_reagent.show() self.nitrite_colour.hide() if nut == 'Nitrite': self.nox_colour.hide() self.nox_buffer.hide() self.nox_column.hide() self.phoshphate_acid.hide() self.phosphate_colour.hide() self.silicate_acid.hide() self.silicate_colour.hide() self.silicate_reductant.hide() self.ammonia_reagent.hide() self.nitrite_colour.show() def radio_selected(self, but): if but.text() == 'NEDD Colour': self.rad_sel = 'NEDD' self.reagent_colour = '#1664b7' self.line_styl = '--' self.x_offset = -0.1 self.legend_label = 'NEDD Colour' if but.text() == 'Amm Chl Buffer': self.rad_sel = 'AmmChl' self.reagent_colour = '#52adce' self.line_styl = '-.' self.x_offset = 0.1 self.legend_label = 'AmmChl Buffer' if but.text() == 'Cadmium Column': self.rad_sel = 'Cd Col' self.reagent_colour = '#3e536d' self.line_styl = ':' self.x_offset = 0.001 self.legend_label = 'Cadmium Column' if but.text() == 'Phos Molybdate Colour': self.rad_sel = 'Molyb' self.reagent_colour = '#af2f21' self.line_styl = '--' self.x_offset = -0.1 self.legend_label = 'Molybdate Colour' if but.text() == 'Ascorbic Acid': self.rad_sel = 'AA' self.reagent_colour = '#f79999' self.line_styl = '-.' self.x_offset = 0.1 self.legend_label = 'Ascorbic Acid' if but.text() == 'Sil Molybdate Colour': self.rad_sel = 'Molyb' self.reagent_colour = '#056b1d' self.line_styl = '--' self.x_offset = -0.2 self.legend_label = 'Molybdate Colour' if but.text() == 'Tartaric Acid': self.reagent_colour = '#4bb769' self.rad_sel = 'Tart' self.line_styl = '-.' self.x_offset = 0.2 self.legend_label = 'Tartaric Acid' if but.text() == 'Stannous Chloride': self.reagent_colour = '#25893c' self.rad_sel = 'SnCl' self.line_styl = ':' self.x_offset = -0.02 self.legend_label = 'Stannous Chloride' if but.text() == 'OPA': self.reagent_colour = '#d8d145' self.rad_sel = 'OPA' self.line_styl = '--' self.x_offset = 0 self.legend_label = 'OPA' def draw_data(self): try: nutrient = self.header_key[self.select_nutrient.currentText()] folder_path = self.folder_path.text() plot_by = self.plot_by_option.currentText() draw_base = self.draw_base.isChecked() draw_gain = self.draw_gain.isChecked() count = 0 runs = [] base = [] gain = [] dates = [] times = [] filesindirec = os.listdir(folder_path) for file in filesindirec: print(file) if file[-4:] == '.SLK': filearray = self.read_slk(folder_path + '/' + file) nutx, nuty = self.getindex(filearray, '"' + nutrient + '"') if nutx != 'no': basex, basey = self.getindex(filearray, '"Base"') base.append(int(filearray[basex][nuty])) gainx, gainy = self.getindex(filearray, '"Gain"') gain.append(filearray[gainx][nuty]) findx, findy = self.getindex(filearray, '"TIME"') times.append(filearray[findx][findy + 1][1:-1]) findx, findy = self.getindex(filearray, '"DATE"') dates.append(filearray[findx][findy + 1][1:-1]) count = count + 1 runs.append(count) self.mainplot.cla() self.second.cla() if self.plot_by_option.currentText() == 'Analysis': xaxis = runs xlabel = 'Analysis' else: tdstampformat = '%d/%m/%Y %H:%M:%S %p' tdstampconverts = [] for i, x in enumerate(times): tdstamp = dates[i] + ' ' + x tdstampconverts.append( time.mktime(time.strptime(tdstamp, tdstampformat))) xaxis = tdstampconverts xlabel = 'Date' plotTimeFormat = '%d/%m/%y' xticks = self.linspace(min(xaxis), max(xaxis), 7) xlabels = [ time.strftime(plotTimeFormat, time.gmtime(x)) for x in xticks ] if draw_base == True: self.mainplot.plot(xaxis, base, marker='o', ms=6, lw=1, color='#bec2c4', mec='#999999', label='Baseline Offset') self.mainplot.grid(alpha=0.2) self.mainplot.set_ylabel('Baseline Offset', fontsize=12) if max(base) < 0: self.mainplot.invert_yaxis() if draw_gain == True: if draw_base == True: self.second.plot(xaxis, gain, marker='s', mfc='#a8a8a8', ms=6, lw=1, color='#bec2c4', label='Gain', mec='none', alpha=0.6) self.second.set_ylabel('Gain', fontsize=12) else: self.mainplot.plot(xaxis, gain, marker='o', mfc='#a8a8a8', ms=7, lw=1, color='#bec2c4', label='Gain', mec='none') self.mainplot.grid(alpha=0.2) self.second.set_yticks([]) self.second.set_yticklabels([]) self.mainplot.set_ylabel('Gain', fontsize=12) if draw_gain == False: self.second.set_yticks([]) self.second.set_yticklabels([]) self.mainplot.set_title(str(self.select_nutrient.currentText()), fontsize=15) self.mainplot.set_xlabel(xlabel, fontsize=12) if self.plot_by_option.currentText() == 'Date': plt.xticks(xticks, xlabels) self.mainplot.legend() self.canvas.draw() except Exception: print(traceback.print_exc()) def linspace(self, start, stop, n): if n == 1: yield stop return h = (stop - start) / (n - 1) for i in range(n): yield start + h * i def on_click(self, event): if event.button == 1 and event.inaxes: xcoord = int(event.xdata) self.draw_reagent_line(xcoord) def locate_folder(self): path = QFileDialog.Options() files = QFileDialog.getExistingDirectory( self, "Select Folder containing NC files") if os.path.exists(files): self.folder_path.setText(files) def read_slk(self, file): with open(file) as fileread: read = csv.reader(fileread, delimiter=';') readlist = list(read) datasection = [] # Now the .SLK will be parsed, this is messy because there are different 'versions' of the # .slk as there isn't a defined standard.. # THe .slk is essentially a spreadshet and it will be broken up into an array for x in readlist: if x[0] == 'C' or x[0] == 'F': datasection.append(x) # Get size of spreadsheet to make array to hold data if x[0] == 'B': if x[1][0] == 'X': w = int(x[1][1:]) if x[2][0] == 'X': w = int(x[2][1:]) if x[2][0] == 'Y': h = int(x[2][1:]) if x[1][0] == 'Y': h = int(x[1][1:]) dataarray = [['' for i in range(w)] for j in range(h)] row = 0 col = 0 for x in datasection: try: if x[1][0] == 'Y': row = int(x[1][1:]) - 1 if len(x) > 2: if x[2][0] == 'X': col = int(x[2][1:]) - 1 if x[1][0] == 'X': col = int(x[1][1:]) - 1 if x[0][0] == 'F': if len(x) == 4: if x[3][0] == 'M': fake = 0 else: col = int(x[3][1:]) - 1 else: if x[1][0] != 'W': col = int(x[3][1:]) - 1 dataarray[row][col] = x[-1][1:] except Exception as e: print(x) # print('len: ' + str(len(x))) return dataarray def getindex(self, arr, item): for i, x in enumerate(arr): for j, y in enumerate(x): if y == item: return i, j return 'no', 'no'
class _FwdGeomGroupbox(_StateAwareGroupbox): """Groupbox to setup spacing and montage""" default_montage = 'standard_1005' default_spacing = 'oct6' def __init__(self, default_subj, title='Select montage and spacing', parent=None): super().__init__(title=title, parent=parent) # -------- setup paths and fetch montages -------- # self._get_builtin_montages() self._default_forwards_path = op.join(COGNIGRAPH_DATA, 'forwards', default_subj) self.get_available_forwards(self._default_forwards_path) # self._is_montages_combo_connected = False # to spacings combo # ------------------------------------------------ # # -------- setup comboboxes -------- # self._montages_combo = _ResettableComboBox() self._montages_combo.currentTextChanged.connect( self._on_montage_combo_changed) montages_combo_label = QLabel('Select montage:') montages_combo_label.setBuddy(self._montages_combo) montages_combo_layout = QHBoxLayout() montages_combo_layout.addWidget(montages_combo_label) montages_combo_layout.addWidget(self._montages_combo) self._montages_combo_widget = QWidget() self._montages_combo_widget.setLayout(montages_combo_layout) self._spacings_combo = _ResettableComboBox() self._spacings_combo.currentTextChanged.connect( self._on_spacings_combo_changed) spacings_label = QLabel('Select spacing:') spacings_label.setBuddy(self._spacings_combo) spacings_combo_layout = QHBoxLayout() spacings_combo_layout.addWidget(spacings_label) spacings_combo_layout.addWidget(self._spacings_combo) self._spacings_combo_widget = QWidget() self._spacings_combo_widget.setLayout(spacings_combo_layout) self._forwards_combo = _ResettableComboBox() forwards_label = QLabel('Select forward operator:') forwards_label.setBuddy(self._spacings_combo) forwards_combo_layout = QVBoxLayout() forwards_combo_layout.addWidget(forwards_label) forwards_combo_layout.addWidget(self._forwards_combo) self._forwards_combo_widget = QWidget() self._forwards_combo_widget.setLayout(forwards_combo_layout) # ---------------------------------- # self._use_default_montage_radio = QRadioButton('&Use default') self._import_montage_radio = QRadioButton('&Import montage') self._use_default_montage_radio.setChecked(True) self._use_default_montage_radio.toggled.connect( self._on_import_montage_radio_toggled) self._import_montage_radio.toggled.connect( self._on_import_montage_radio_toggled) self._select_montage_dialog = _FileSelectorWidget( dialog_caption='Select montage model', path='', file_filter='*.txt *.elc *.csd *.elp *.htps' ' *.sfp *.loc *.locs *.eloc *.bvef') self._select_montage_dialog.path_ledit.textChanged.connect( self._on_montage_path_changed) self._select_montage_dialog.setDisabled(True) # initialize combos with available forwards self.is_use_available = True # -------- setup layout -------- # default_fwd_layout = QVBoxLayout() default_fwd_layout.addWidget(self._use_default_montage_radio) default_fwd_layout.addWidget(self._montages_combo_widget) default_fwd_layout.addWidget(self._import_montage_radio) default_fwd_layout.addWidget(self._select_montage_dialog) default_fwd_layout.addWidget(self._spacings_combo_widget) default_fwd_layout.addWidget(self._forwards_combo_widget) self.default_fwd_widget = QWidget() self.default_fwd_widget.setLayout(default_fwd_layout) self.default_fwd_widget.setSizePolicy(QSizePolicy.Minimum, QSizePolicy.Fixed) default_fwd_setup_layout = QVBoxLayout() default_fwd_setup_layout.addWidget(self.default_fwd_widget) self.setLayout(default_fwd_setup_layout) # ------------------------------ # def _get_builtin_montages(self): montages_desc_path = op.join(COGNIGRAPH_DATA, 'montages_desc.json') with open(montages_desc_path, 'r') as f: description = json.load(f) self.montages_desc = description['montages'] self.spacings_desc = description['spacings'] self.builtin_montage_names = sorted( mne.channels.get_builtin_montages()) def get_available_forwards(self, folder): p = folder self._available_montages = sorted( [i for i in os.listdir(p) if op.isdir(op.join(p, i))]) self._available_forwards = {} for a in self._available_montages: spacings = os.listdir(op.join(p, a)) self._available_forwards[a] = {} for s in spacings: forwards = [ f for f in os.listdir(op.join(p, a, s)) if f.endswith('fwd.fif') ] self._available_forwards[a][s] = forwards def _set_hints(self): """Set popup description messages to comboboxes""" block_signals = QSignalBlocker(self._montages_combo) # noqa for i, key in enumerate(self._montages_combo.getItems()): try: self._montages_combo.setItemData(i, self.montages_desc[key], Qt.ToolTipRole) except KeyError: pass for i, key in enumerate(self._spacings_combo.getItems()): try: self._spacings_combo.setItemData(i, self.spacings_desc[key], Qt.ToolTipRole) except KeyError: pass def _set_combos_to_builtin(self): """Used when we switch to compute forward mode""" block_signals = QSignalBlocker(self._montages_combo) # noqa self._montages_combo.setItems(self.builtin_montage_names) self.montage = self.default_montage self._spacings_combo.setItems( [k for k in self.spacings_desc if k != 'imported']) self.spacing = self.default_spacing # uses spacing setter self._forwards_combo_widget.hide() self._set_hints() self._use_default_montage_radio.show() self._import_montage_radio.show() self._select_montage_dialog.show() def _set_combos_to_available(self): """Default option: load forward from cognigraph folders structure""" self._set_montages_combo_to_available() self._forwards_combo_widget.show() self._set_hints() self._use_default_montage_radio.hide() self._import_montage_radio.hide() self._select_montage_dialog.hide() def _set_montages_combo_to_available(self): block_signals = QSignalBlocker(self._montages_combo) # noqa self._montages_combo.setItems(self._available_montages) self.montage = self.default_montage self._set_spacings_combo_to_available() def _set_spacings_combo_to_available(self): montage = self.montage self._spacings_combo.setItems(self._available_forwards[montage].keys()) self.spacing = self.default_spacing self._set_forwards_combo_to_available() def _set_forwards_combo_to_available(self): self._forwards_combo.setItems( self._available_forwards[self.montage][self.spacing]) def _on_montage_combo_changed(self): """ If using available forwards, fetch all available spacings and forwards for selected montage; set self.montage """ if self.is_use_available: self._set_spacings_combo_to_available() if self._forwards_combo.currentText(): self.is_valid = True else: self.is_valid = False def _on_spacings_combo_changed(self): if self.is_use_available: self._set_forwards_combo_to_available() def _on_import_montage_radio_toggled(self): if self._use_default_montage_radio.isChecked(): self._select_montage_dialog.setDisabled(True) self._montages_combo_widget.setDisabled(False) if self._forwards_combo.currentText(): self.is_valid = True else: self.is_valid = False else: self._select_montage_dialog.setDisabled(False) self._montages_combo_widget.setDisabled(True) if self._select_montage_dialog.path_ledit.text(): self.is_valid = True else: self.is_valid = False self._select_montage_dialog.browse_button.setFocus() def _on_montage_path_changed(self): if self._select_montage_dialog.path_ledit.text(): self.is_valid = True @property def montage(self): montage = None if self._use_default_montage_radio.isChecked(): montage = self._montages_combo.currentText() else: montage = self._select_montage_dialog.path_ledit.text() return montage @montage.setter def montage(self, value): if self._use_default_montage_radio.isChecked(): self._montages_combo.setCurrentText(value) else: self._select_montage_dialog.path_ledit.setText(value) @property def spacing(self): return self._spacings_combo.currentText() @spacing.setter def spacing(self, value): self._spacings_combo.setCurrentText(value) @property def fwd_name(self): return self._forwards_combo.currentText() @fwd_name.setter def fwd_name(self, value): self._forwards_combo.setCurrentText(value) @property def is_use_available(self): return self._is_use_available @is_use_available.setter def is_use_available(self, value): self._is_use_available = value if value: self._set_combos_to_available() else: self._set_combos_to_builtin()
class MultplayerTournamentItem(): def __init__(self, y_pos, x_pos, startCheck: int): tb_x_pos = x_pos cb_x_pos = x_pos + 300 cb_x_step = 75 self.textbox = QLineEdit() self.textbox.move(tb_x_pos, y_pos) self.textbox.resize(280, 40) font1 = self.textbox.font() font1.setPointSize(20) self.textbox.setFont(font1) self.buttonGroup = QButtonGroup() self.radiobutton1 = QRadioButton("Gray") self.radiobutton2 = QRadioButton("Red") self.radiobutton3 = QRadioButton("Yellow") self.radiobutton4 = QRadioButton("Green") font = QFont() font.setStyleHint(QFont.Helvetica) font.setPointSize(13) font.setBold(True) self.radiobutton1.setFont(font) self.radiobutton2.setFont(font) self.radiobutton3.setFont(font) self.radiobutton4.setFont(font) self.buttonGroup.addButton(self.radiobutton1) self.buttonGroup.addButton(self.radiobutton2) self.buttonGroup.addButton(self.radiobutton3) self.buttonGroup.addButton(self.radiobutton4) self.buttonGroup.setId(self.radiobutton1, 1) self.buttonGroup.setId(self.radiobutton2, 2) self.buttonGroup.setId(self.radiobutton3, 3) self.buttonGroup.setId(self.radiobutton4, 4) if startCheck is 1: self.radiobutton1.setChecked(True) elif startCheck is 2: self.radiobutton2.setChecked(True) elif startCheck is 3: self.radiobutton3.setChecked(True) else: self.radiobutton4.setChecked(True) y_plus = 7 self.radiobutton1.move(cb_x_pos, y_pos + y_plus) self.radiobutton2.move(cb_x_pos + cb_x_step, y_pos + y_plus) self.radiobutton3.move(cb_x_pos + cb_x_step * 2, y_pos + y_plus) self.radiobutton4.move(cb_x_pos + cb_x_step * 3, y_pos + y_plus) def hideAllWidgets(self): self.textbox.hide() self.radiobutton1.hide() self.radiobutton2.hide() self.radiobutton3.hide() self.radiobutton4.hide() def showAllWidgets(self): self.textbox.show()
class MyTableWidget(QWidget): def __init__(self, parent): super(QWidget, self).__init__(parent) self.train_path = "D:/test/train" self.val_path = "D:/test/val" self.test_path = "" self.new_path_model = "Model_1_85aug.h5" self.list_ale, self.list_epi, self.list_tot = [], [], [] self.epoch = 100 self.model = 'drop' self.batch_dim = 100 self.monte = 5 self.train_js, self.val_js, self.test_js = "new_train_js.txt", "new_val_js.txt", "" self.path_work = "D:/test" self.path_tiles_train, self.path_tiles_val, self.path_tiles_test = '', '', '' self.selected_th, self.path_save_clean = '', '' self.flag, self.aug = 0, 0 self.layout = QVBoxLayout(self) self.threadPool = QThreadPool() # Initialize tab screen self.tabs = QTabWidget() self.tab1 = QWidget() self.tab2 = QWidget() self.tab3 = QWidget() self.tab4 = QWidget() self.tab5 = QWidget() # Add tabs self.tabs.addTab(self.tab1, "Get Tiles") self.tabs.addTab(self.tab2, "Training") self.tabs.addTab(self.tab3, "Uncertainty analysis") self.tabs.addTab(self.tab4, "Data cleaning") self.t5 = TestTab(parent=self) self.tabs.addTab(self.t5, "Testing") # Create first tab self.tab1.layout = QVBoxLayout(self) self.tab2.layout = QVBoxLayout(self) self.tab3.layout = QVBoxLayout(self) self.tab4.layout = QVBoxLayout(self) # Elements section 1 self.first = QLabel( "First things first, select a place where put all data sets:") self.first_button = QPushButton("Select folder") self.first_button.clicked.connect(self.first_selection) newfont = QFont("Helvetica", 15, QFont.Bold) self.title_train = QLabel('TRAINING SET') self.title_train.setFont(newfont) self.title_val = QLabel('VALIDATION SET') self.title_val.setFont(newfont) self.title_test = QLabel('TEST SET') self.title_test.setFont(newfont) self.start = QPushButton("Start") self.start.clicked.connect(self.start_tiles) self.description_t = QLabel("Press here to select the train folder: ") self.description_v = QLabel( "Press here to select the validation folder: ") self.description_test = QLabel( "Press here to select the test folder: ") self.folder_train = QPushButton("Select folder") self.folder_train.clicked.connect(self.select_folder_train) self.folder_val = QPushButton("Select folder") self.folder_val.clicked.connect(self.select_folder_val) self.folder_test = QPushButton("Select folder") self.folder_test.clicked.connect(self.select_folder_test) self.prog1 = QProgressBar(self) self.prog2 = QProgressBar(self) self.prog3 = QProgressBar(self) self.prog1_v = QProgressBar(self) self.prog2_v = QProgressBar(self) self.prog3_v = QProgressBar(self) self.prog1_test = QProgressBar(self) self.prog2_test = QProgressBar(self) self.prog3_test = QProgressBar(self) # train self.list_ac = QListWidget(self) self.list_ad = QListWidget(self) self.list_h = QListWidget(self) # validation self.list_ac_v = QListWidget(self) self.list_ad_v = QListWidget(self) self.list_h_v = QListWidget(self) # test # validation self.list_ac_test = QListWidget(self) self.list_ad_test = QListWidget(self) self.list_h_test = QListWidget(self) self.first_layout = QHBoxLayout(self) self.first_layout.addWidget(self.first) self.first_layout.addWidget(self.first_button) self.h_train = QHBoxLayout(self) self.h_train.addWidget(self.description_t) self.h_train.addWidget(self.folder_train) self.h_val = QHBoxLayout(self) self.h_val.addWidget(self.description_v) self.h_val.addWidget(self.folder_val) self.h_test = QHBoxLayout(self) self.h_test.addWidget(self.description_test) self.h_test.addWidget(self.folder_test) self.list_t = QHBoxLayout(self) self.list_t.addWidget(self.list_ac) self.list_t.addWidget(self.list_ad) self.list_t.addWidget(self.list_h) self.list_v = QHBoxLayout(self) self.list_v.addWidget(self.list_ac_v) self.list_v.addWidget(self.list_ad_v) self.list_v.addWidget(self.list_h_v) self.list_test = QHBoxLayout(self) self.list_test.addWidget(self.list_ac_test) self.list_test.addWidget(self.list_ad_test) self.list_test.addWidget(self.list_h_test) self.pr = QHBoxLayout(self) self.pr.addWidget(self.prog1) self.pr.addWidget(self.prog2) self.pr.addWidget(self.prog3) self.pr_v = QHBoxLayout(self) self.pr_v.addWidget(self.prog1_v) self.pr_v.addWidget(self.prog2_v) self.pr_v.addWidget(self.prog3_v) self.pr_test = QHBoxLayout(self) self.pr_test.addWidget(self.prog1_test) self.pr_test.addWidget(self.prog2_test) self.pr_test.addWidget(self.prog3_test) # tab1 self.tab1.layout.addLayout(self.first_layout) self.tab1.layout.addWidget(QHLine()) self.tab1.layout.addWidget(self.title_train) self.tab1.layout.addLayout(self.h_train) self.tab1.layout.addLayout(self.list_t) self.tab1.layout.addLayout(self.pr) self.tab1.layout.addWidget(QHLine()) self.tab1.layout.addWidget(self.title_val) self.tab1.layout.addLayout(self.h_val) self.tab1.layout.addLayout(self.list_v) self.tab1.layout.addLayout(self.pr_v) self.tab1.layout.addWidget(QHLine()) self.tab1.layout.addWidget(self.title_test) self.tab1.layout.addLayout(self.h_test) self.tab1.layout.addLayout(self.list_test) self.tab1.layout.addLayout(self.pr_test) self.tab1.layout.addWidget(QHLine()) self.tab1.layout.addWidget(self.start) self.tab1.setLayout(self.tab1.layout) # Elements section 2 self.progrestrain = QProgressBar(self) self.text = QLineEdit(self) self.text_batch = QLineEdit(self) self.start_train = QPushButton("Start") self.start_train.clicked.connect(self.train) self.state_train = QLabel("Press start to train the model.") self.state_train.setMargin(10) self.state_train.setFixedWidth(900) self.state_train.setFixedHeight(1500) self.state_train.setAlignment(Qt.AlignTop) self.scrolltr = QScrollArea() self.scrolltr.setAlignment(Qt.AlignTop) self.scrolltr.setWidget(self.state_train) self.description_tr = QLabel('Insert numer of epochs: ') self.description_batch = QLabel('Insert dimension of batch: ') self.description_batch2 = QLabel('Default value: 100') self.description_model = QLabel( 'Select one of the 2 available models:') self.description_tr2 = QLabel('Default epochs: 100') self.kl = QRadioButton('Kl divergence') self.kl.toggled.connect(self.load_kl) self.drop = QRadioButton('Drop-Out') self.drop.setChecked(True) self.drop.toggled.connect(self.load_drop) self.ok_text = QPushButton('Ok') self.ok_text.clicked.connect(self.ok_epochs) self.ok_batc = QPushButton('Ok') self.ok_batc.clicked.connect(self.ok_batch) self.set_epochs = QHBoxLayout(self) self.set_epochs.addWidget(self.description_tr) self.set_epochs.addWidget(self.text) self.set_epochs.addWidget(self.ok_text) self.set_epochs.addWidget(self.description_tr2) self.set_batch_size = QHBoxLayout(self) self.set_batch_size.addWidget(self.description_batch) self.set_batch_size.addWidget(self.text_batch) self.set_batch_size.addWidget(self.ok_batc) self.set_batch_size.addWidget(self.description_batch2) self.set_model = QHBoxLayout(self) self.set_model.addWidget(self.description_model) self.set_model.addWidget(self.kl) self.set_model.addWidget(self.drop) self.description_optional = QLabel( 'Optional, select two folder where can retrive ' 'the training end validation tiles:') self.retrive_train = QPushButton('Train') self.retrive_train.clicked.connect(self.ret_train) self.retrive_test = QPushButton('Val') self.retrive_test.clicked.connect(self.ret_test) self.new_folder = QHBoxLayout(self) self.new_folder.addWidget(self.retrive_train) self.new_folder.addWidget(self.retrive_test) self.new_folder.addStretch(1) self.data_aug = QCheckBox('Data Agumentation') self.data_aug.stateChanged.connect(self.agumentation) # tab2 self.tab2.layout.addLayout(self.set_model) self.tab2.layout.addLayout(self.set_epochs) self.tab2.layout.addLayout(self.set_batch_size) self.tab2.layout.addWidget(self.data_aug) self.tab2.layout.addWidget(QHLine()) self.tab2.layout.addWidget(self.description_optional) self.tab2.layout.addLayout(self.new_folder) self.tab2.layout.addWidget(QHLine()) self.tab2.layout.addWidget(self.start_train) self.tab2.layout.addWidget(self.scrolltr) self.tab2.layout.addWidget(self.progrestrain) self.tab2.setLayout(self.tab2.layout) # Elements section 3 self.description_clas = QLabel( 'The purpose of this step is to obtain the values of uncertainty values' ) self.description_monte = QLabel('Write here Monte Carlo samples:') self.title_train_cl = QLabel('TRAINING SET') self.title_val_cl = QLabel('VALIDATION SET') self.title_test_cl = QLabel('TEST SET') self.title_train_cl.setFont(newfont) self.title_val_cl.setFont(newfont) self.title_test_cl.setFont(newfont) self.description_monte2 = QLabel('Default value: {}'.format( self.monte)) self.text_monte = QLineEdit() self.prog_monte = QProgressBar() self.ok_monte = QPushButton('Ok') self.ok_monte.clicked.connect(self.ok_m) self.start_classify_train = QPushButton('Start') self.start_classify_train.clicked.connect(self.cl_train) self.start_classify_val = QPushButton('Start') self.start_classify_val.clicked.connect(self.cl_val) self.start_classify_test = QPushButton('Start') self.start_classify_test.clicked.connect(self.cl_test) self.HMonte = QHBoxLayout(self) self.HMonte.addWidget(self.description_monte) self.HMonte.addWidget(self.text_monte) self.HMonte.addWidget(self.ok_monte) self.HMonte.addWidget(self.description_monte2) # tab 3 self.tab3.layout.addWidget(self.description_clas, alignment=Qt.AlignTop) self.tab3.layout.addWidget(QHLine()) self.tab3.layout.addLayout(self.HMonte) self.tab3.layout.addWidget(self.title_train_cl) self.tab3.layout.addWidget(self.start_classify_train) self.tab3.layout.addWidget(QHLine()) self.tab3.layout.addWidget(self.title_val_cl) self.tab3.layout.addWidget(self.start_classify_val) self.tab3.layout.addWidget(QHLine()) self.tab3.layout.addWidget(self.title_test_cl) self.tab3.layout.addWidget(self.start_classify_test) self.tab3.layout.addStretch(1) self.tab3.layout.addWidget(self.prog_monte) self.tab3.setLayout(self.tab3.layout) # Elements 4 self.hist_ale = MplCanvas('Aleatoric uncertainty', self, width=5, height=4, dpi=100) self.hist_epi = MplCanvas('Epistemic uncertainty', self, width=5, height=4, dpi=100) self.hist_tot = MplCanvas('Total uncertainty', self, width=5, height=4, dpi=100) self.hist_removed = QPushButton( 'Show number of tiles that i will remove for class') self.hist_removed.hide() self.hist_removed.clicked.connect(self.show_class_removed) self.description_total_before = QLabel() self.description_total_before.hide() self.description_total_after = QLabel() self.description_total_after.hide() self.description_select_data = QLabel('Select which dataset analyze:') self.description_types = QLabel( 'Select one of the two modes, Auto the software will find the correct ' 'threshold to divide the images between certain and uncertain; in Manual ' 'you have to write the desired value in the text box.') self.description_folder = QLabel( 'Folder where the dataset cleaned will be created:') self.folder_cl_data = QPushButton('Select a emplty folder') self.folder_cl_data.clicked.connect(self.conclusion_folder) self.auto = QRadioButton('Auto') self.auto.setEnabled(False) self.control = QRadioButton('Control') self.control.hide() self.auto.toggled.connect(self.update_auto) self.manual = QRadioButton('Manual') self.manual.setEnabled(False) self.manual.toggled.connect(self.update_man) self.mode_group = QButtonGroup() self.mode_group.addButton(self.auto) self.mode_group.addButton(self.manual) self.mode_group.addButton(self.control) self.prog_copy = QProgressBar() self.dataset_train = QRadioButton('Training set') self.dataset_train.toggled.connect(self.clean_train) self.dataset_val = QRadioButton('Validation set') self.dataset_val.toggled.connect(self.clean_val) self.dataset_group = QButtonGroup() self.dataset_group.addButton(self.dataset_train) self.dataset_group.addButton(self.dataset_val) self.manual_value = QLineEdit() self.manual_value.hide() self.start_clean = QPushButton('Start analysis with manual threshold') self.start_clean.clicked.connect(self.push_manual) self.start_clean.hide() self.create_new_dataset = QPushButton('Create new data set') self.create_new_dataset.clicked.connect(self.conclusion_cleaning) self.create_new_dataset.setEnabled(False) self.mode = QHBoxLayout() self.mode.addWidget(self.auto, alignment=Qt.AlignCenter) self.mode.addWidget(self.manual, alignment=Qt.AlignCenter) self.mode.addWidget(self.manual_value) self.mode.addWidget(self.start_clean) self.mode.addStretch(1) self.hist_v = QVBoxLayout() self.hist_v.addWidget(self.hist_ale) self.hist_v.addWidget(self.hist_epi) self.hist_o = QHBoxLayout() self.hist_o.addWidget(self.hist_tot) self.hist_o.addLayout(self.hist_v) self.folder_cl = QHBoxLayout() self.folder_cl.addWidget(self.description_folder) self.folder_cl.addWidget(self.folder_cl_data) self.number = QVBoxLayout() self.number.addWidget(self.description_total_before) self.number.addWidget(self.description_total_after) self.h_number = QHBoxLayout() self.h_number.addLayout(self.number) self.h_number.addWidget(self.hist_removed) self.h_select_dataset = QHBoxLayout() self.h_select_dataset.addWidget(self.description_select_data) self.h_select_dataset.addWidget(self.dataset_train) self.h_select_dataset.addWidget(self.dataset_val) self.otsu_th = QRadioButton('Otsu threshold') self.otsu_th.setEnabled(False) self.otsu_th.toggled.connect(self.sel_otsu) self.new_th = QRadioButton('New threshold') self.new_th.setEnabled(False) self.new_th.toggled.connect(self.sel_new) self.manul_th = QRadioButton('Manual threshold') self.manul_th.setEnabled(False) self.manul_th.toggled.connect(self.sel_manual) self.group_th = QButtonGroup() self.group_th.addButton(self.otsu_th) self.group_th.addButton(self.new_th) self.group_th.addButton(self.manul_th) self.h_selection_th = QHBoxLayout() self.h_selection_th.addWidget(self.otsu_th) self.h_selection_th.addWidget(self.new_th) self.h_selection_th.addWidget(self.manul_th) self.h_selection_th.addStretch(1) # tab 4 self.tab4.layout.addLayout(self.h_select_dataset) self.tab4.layout.addWidget(QHLine()) self.tab4.layout.addLayout(self.hist_o) self.tab4.layout.addLayout(self.h_number) self.tab4.layout.addWidget(QHLine()) self.tab4.layout.addWidget(self.description_types) self.tab4.layout.addLayout(self.mode) self.tab4.layout.addWidget(QHLine()) self.tab4.layout.addLayout(self.folder_cl) self.tab4.layout.addLayout(self.h_selection_th) self.tab4.layout.addWidget(self.create_new_dataset) self.tab4.layout.addStretch(1) self.tab4.layout.addWidget(self.prog_copy) self.tab4.setLayout(self.tab4.layout) # Add tabs to widget self.layout.addWidget(self.tabs) self.setLayout(self.layout) start_time = time.asctime(time.localtime(time.time())) self.log_epoch = "Start {}".format(start_time) def sel_otsu(self): self.selected_th = 'otsu' def sel_new(self): self.selected_th = 'new' def sel_manual(self): self.selected_th = 'manual' def agumentation(self, state): if Qt.Checked == state: self.aug = 1 else: self.aug = 0 def show_class_removed(self): self.obj_clean.removed_class() def ret_test(self): fl = QFileDialog.getExistingDirectory(self, "Select Directory") if fl != '': self.path_tiles_val = fl else: pass def ret_train(self): fl = QFileDialog.getExistingDirectory(self, "Select Directory") if fl != '': self.path_tiles_train = fl else: pass def conclusion_cleaning(self): if not os.path.exists(os.path.join(self.path_save_clean, 'AC')): os.mkdir(os.path.join(self.path_save_clean, 'AC')) os.mkdir(os.path.join(self.path_save_clean, 'H')) os.mkdir(os.path.join(self.path_save_clean, 'AD')) work_copy = WorkerLong(self.obj_clean.clean_js, self.selected_th, self.path_save_clean) work_copy.signals.result.connect(self.print_output) work_copy.signals.progress.connect(self.progress_fn) work_copy.signals.progress.connect(self.prog_copy.setValue) work_copy.signals.finished.connect(self.thread_complete) self.threadPool.start(work_copy) def conclusion_folder(self): save_fl = QFileDialog.getExistingDirectory(self, "Select Directory") if save_fl != '': self.path_save_clean = save_fl self.create_new_dataset.setEnabled(True) else: pass def first_selection(self): fl = QFileDialog.getExistingDirectory(self, "Select Directory") if fl != '': self.path_work = fl self.path_tiles_train = os.path.join(fl, 'train') self.path_tiles_val = os.path.join(fl, 'val') self.path_tiles_test = os.path.join(fl, 'test') else: pass def ok_m(self): tex = self.text_monte.text() if tex.isdecimal() and int(tex) > 0: self.description_monte2.setText( 'Monte Carlo samples: {}'.format(tex)) self.monte = tex else: pass def ok_batch(self): tex = self.text_batch.text() if tex.isdecimal() and int(tex) > 0: self.description_batch2.setText('Batch dimension: {}'.format(tex)) self.batch_dim = tex else: pass def draw_hist(self, path_js, name): self.obj_clean = Th(path_js, name) self.list_ale, self.list_epi, self.list_tot = self.obj_clean.create_list( ) lim = max(self.list_tot) n_bin = round((len(self.list_tot)) / 100) self.hist_tot.axes.clear() self.hist_tot.axes.set_xlim(0, lim) self.hist_tot.axes.set_title('Total uncertainty') self.hist_tot.axes.hist(self.list_tot, bins=n_bin, color='#FFA420') self.hist_tot.draw() self.hist_ale.axes.clear() self.hist_ale.axes.set_xlim(0, lim) self.hist_ale.axes.set_title('Aleatoric uncertainty') self.hist_ale.axes.hist(self.list_ale, bins=n_bin, color='#FFA420') self.hist_ale.draw() self.hist_epi.axes.clear() self.hist_epi.axes.set_xlim(0, lim) self.hist_epi.axes.set_title('Epistemic uncertainty') self.hist_epi.axes.hist(self.list_epi, bins=n_bin, color='#FFA420') self.hist_epi.draw() def unlock_an(self): self.auto.setEnabled(True) self.manual.setEnabled(True) self.auto.setChecked(False) self.manual.setChecked(False) self.control.setChecked(True) self.control.setChecked(True) def clean_train(self): self.unlock_an() self.draw_hist(self.train_js, 'train') self.description_total_before.setText( 'Total number of tiles before cleaning: {}'.format( len(self.list_tot))) self.description_total_before.show() self.description_total_after.hide() self.hist_removed.hide() def clean_val(self): self.unlock_an() self.draw_hist(self.val_js, 'val') self.description_total_before.setText( 'Total number of tiles before cleaning: {}'.format( len(self.list_tot))) self.description_total_before.show() self.description_total_after.hide() self.hist_removed.hide() def load_kl(self): self.model = 'kl' def load_drop(self): self.model = 'drop' def update_auto(self): self.obj_clean.otsu() self.newth, self.thfin, number_new_dataset1, number_new_dataset = self.obj_clean.th_managment( ) self.description_total_after.setText( 'Total number of tiles after cleaning: \n' 'Otsu Threshold: {:10}\n' 'New Threshold: {:10}'.format(number_new_dataset, number_new_dataset1)) self.description_total_after.show() self.hist_removed.show() self.hist_tot.axes.axvline(x=self.newth, ls='--', color='k', label='New Threshold') self.hist_tot.axes.axvline(x=self.thfin, color='red', label='Otsu Threshold') self.hist_tot.axes.axvline(x=-3, ls='--', color='y', label='Manual Threshold') if self.flag == 0: self.hist_tot.axes.legend(prop={'size': 10}) self.flag = 1 else: pass self.hist_tot.draw() if self.auto.isChecked(): self.manual_value.hide() self.start_clean.hide() self.th_update() def th_update(self): self.otsu_th.setEnabled(True) self.new_th.setEnabled(True) self.manul_th.setEnabled(True) def update_man(self): if self.manual.isChecked(): self.manual_value.show() self.start_clean.show() def select_folder_train(self): self.train_path = QFileDialog.getExistingDirectory( self, "Select Directory") if self.train_path != '': cl = os.listdir(self.train_path) try: for i in cl: nfiles = os.listdir(os.path.join(self.train_path, i)) if i == 'AC' or i == 'ac': self.list_ac.addItems(nfiles) elif i == 'AD' or i == 'ad': self.list_ad.addItems(nfiles) elif i == 'H' or i == 'h': self.list_h.addItems(nfiles) else: pass print(self.train_path) except: pass else: pass def select_folder_test(self): self.test_path = QFileDialog.getExistingDirectory( self, "Select Directory") if self.test_path != '': cl = os.listdir(self.test_path) try: for i in cl: nfiles = os.listdir(os.path.join(self.test_path, i)) if i == 'AC' or i == 'ac': self.list_ac_test.addItems(nfiles) elif i == 'AD' or i == 'ad': self.list_ad_test.addItems(nfiles) elif i == 'H' or i == 'h': self.list_h_test.addItems(nfiles) else: pass print(self.test_path) except: pass else: pass def select_folder_val(self): self.val_path = QFileDialog.getExistingDirectory( self, "Select Directory") if self.val_path != '': cl = os.listdir(self.val_path) try: for i in cl: nfiles = os.listdir(os.path.join(self.val_path, i)) if i == 'AC' or i == 'ac': self.list_ac_v.addItems(nfiles) elif i == 'AD' or i == 'ad': self.list_ad_v.addItems(nfiles) elif i == 'H' or i == 'h': self.list_h_v.addItems(nfiles) else: pass print(self.val_path) except: pass else: pass def push_manual(self): tex = float(self.manual_value.text()) self.th_update() if 1 > tex > 0.1: print('dentro id') self.selected_th = tex self.obj_clean.otsu() print('TEXT--------', tex) self.man, self.thfin, number_new_dataset1, number_new_dataset = self.obj_clean.th_managment( self.selected_th) self.description_total_after.setText( 'Total number of tiles after cleaning: \n' 'Otsu Threshold: {:10}\n' 'Manual Threshold: {:10}'.format(number_new_dataset, number_new_dataset1)) self.description_total_after.show() self.hist_removed.show() self.hist_tot.axes.axvline(x=self.man, ls='--', color='y', label='Manual Threshold') self.hist_tot.draw() def progress_fn(self, n): print("%d%% done" % n) def print_output(self, s): self.state_train.setText(str(s)) print(s) def thread_complete(self): print("THREAD COMPLETE!") def thread_train_complete(self): self.state_train.setText( 'Training completed! The history is saved in the work folder.') print("THREAD COMPLETE!") def th_tiles(self, pr, path, name): cl = os.listdir(self.path) for y, k in enumerate(cl, 0): save_folder = os.path.join(self.path_work, name, k) f_p = os.path.join(path, k) print(save_folder) if os.path.exists(save_folder): pass else: os.makedirs(save_folder) st_tile = StartAnalysis(tile_size=256, lev_sec=0) print('inizio il threading \n', f_p, save_folder) name_th = str(k) + name name_th = WorkerLong(st_tile.list_files, f_p, save_folder) name_th.signals.result.connect(self.print_output) name_th.signals.progress.connect(self.progress_fn) name_th.signals.progress.connect(pr[y].setValue) name_th.signals.finished.connect(self.thread_complete) self.threadPool.start(name_th) def start_tiles(self): pr = [[self.prog1, self.prog2, self.prog3], [self.prog1_v, self.prog2_v, self.prog3_v], [self.prog1_test, self.prog2_test, self.prog3_test]] ph = [self.train_path, self.val_path, self.test_path] dataset = ['train', 'val', 'test'] for t, i in enumerate(dataset): print(pr[t], ph[t], i) self.th_tiles(pr[t], ph[t], name=i) def ok_epochs(self): text_value = self.text.text() if text_value.isdecimal() and int(text_value) > 0: self.description_tr2.setText( 'Limit epochs: {}'.format(text_value)) self.epoch = text_value else: pass def train(self): self.state_train.setText( 'The training is starting, in few second other information will be showed...' ) t_stamp = time.strftime("%Y_%m%d_%H%M%S") if self.model == 'drop': self.new_path_model = os.path.join(self.path_work, 'ModelDrop-' + t_stamp + '.h5') print(self.train_path) obj_model = ModelDropOut(n_model=self.new_path_model, epochs=self.epoch, path_train=self.path_tiles_train, path_val=self.path_tiles_val, b_dim=int(self.batch_dim), aug=self.aug) else: self.new_path_model = os.path.join(self.path_work, 'ModelKl-' + t_stamp + '.h5') obj_model = ModelKl(n_model=self.new_path_model, epochs=self.epoch, path_train=self.path_tiles_train, path_val=self.path_tiles_val, b_dim=int(self.batch_dim), aug=self.aug) k = WorkerLong(obj_model.start_train) k.signals.result.connect(self.print_output) k.signals.progress.connect(self.progrestrain.setValue) k.signals.result1.connect(self.tr_view) k.signals.finished.connect(self.thread_train_complete) self.threadPool.start(k) def cl_train(self): self.start_an(self.path_tiles_train) self.train_js = os.path.join( self.path_tiles_train, 'dictionary_monte_' + str(self.monte) + '_js.txt') self.t5.traincm.setEnabled(True) self.t5.get_paths(train=self.train_js) def cl_test(self): self.start_an(self.path_tiles_test) self.test_js = os.path.join( self.path_tiles_test, 'dictionary_monte_' + str(self.monte) + '_js.txt') self.t5.testcm.setEnabled(True) self.t5.get_paths(test=self.test_js) def cl_val(self): self.start_an(self.path_tiles_val) self.val_js = os.path.join( self.path_tiles_val, 'dictionary_monte_' + str(self.monte) + '_js.txt') self.t5.valcm.setEnabled(True) self.t5.get_paths(val=self.val_js) def start_an(self, data): cls = Classification(data, ty='datacleaning') worker_cl = WorkerLong(cls.classify, 'datacleaning', int(self.monte), self.new_path_model) worker_cl.signals.result.connect(self.print_output) worker_cl.signals.progress.connect(self.progress_fn) worker_cl.signals.progress.connect(self.prog_monte.setValue) worker_cl.signals.finished.connect(self.thread_complete) self.threadPool.start(worker_cl) def tr_view(self, val): if 'Epoch' in str(val): self.log_epoch = self.log_epoch + '\n' + str(val) self.state_train.setText(str(self.log_epoch)) print('trova la parola epoca EMETTE:', self.log_epoch) else: show_b = self.log_epoch + '\n' + str(val) self.state_train.setText(str(show_b))
class Phase10InputWidget(GameInputWidget): def __init__(self, engine, parent=None): super(Phase10InputWidget, self).__init__(engine, parent) self.initUI() def initUI(self): self.winnerButtonGroup = QButtonGroup() self.nobodyWinnerRadioButton = QRadioButton(self) self.nobodyWinnerRadioButton.hide() self.nobodyWinnerRadioButton.setChecked(True) self.winnerButtonGroup.addButton(self.nobodyWinnerRadioButton) players = self.engine.getListPlayers() if len(players) >= 4: players_grid = True self.widgetLayout = QGridLayout(self) else: players_grid = False self.widgetLayout = QVBoxLayout(self) # self.widgetLayout.addStretch() for np, player in enumerate(players): self.playerInputList[player] = Phase10PlayerWidget( player, self.engine, self.winnerButtonGroup, self) self.playerInputList[player].roundWinnerSet.connect( self.changedWinner) if players_grid: self.widgetLayout.addWidget( self.playerInputList[player], np/2, np % 2) else: self.widgetLayout.addWidget(self.playerInputList[player]) # if not players_grid: self.widgetLayout.addStretch() def retranslateUI(self): for piw in self.playerInputList.values(): piw.retranslateUI() def switchPhasesInOrder(self, in_order): for player in self.engine.getListPlayers(): self.playerInputList[player].switchPhasesInOrder(in_order) def hasPlayerCleared(self, player): return self.playerInputList[player].isRoundCleared() def getPlayerAimedPhase(self, player): return self.playerInputList[player].getRoundPhase() def updatePanel(self): self.nobodyWinnerRadioButton.setChecked(True) for player in self.engine.getListPlayers(): score = self.engine.getScoreFromPlayer(player) completed = self.engine.getCompletedPhasesFromPlayer(player) remaining = self.engine.getRemainingPhasesFromPlayer(player) self.playerInputList[player].updateDisplay( score, completed, remaining) def unsetDealer( self): self.playerInputList[self.engine.getDealer()].unsetDealer() def setDealer( self): self.playerInputList[self.engine.getDealer()].setDealer() def setWinner(self): winner = self.engine.getWinner() if winner in self.engine.getListPlayers(): self.playerInputList[winner].setWinner() for pi in self.playerInputList.values(): pi.finish() def getWinner(self): for player, piw in self.playerInputList.items(): if piw.isRoundWinner(): return player return None def updatePlayerOrder(self): # QWidget().setLayout(self.layout()) trash = QWidget() trash.setLayout(self.layout()) players = self.engine.getListPlayers() if len(players) >= 4: players_grid = True self.widgetLayout = QGridLayout(self) else: players_grid = False self.widgetLayout = QVBoxLayout(self) for i, player in enumerate(self.engine.getListPlayers()): trash.layout().removeWidget(self.playerInputList[player]) if players_grid: self.widgetLayout.addWidget( self.playerInputList[player], i/2, i % 2) else: self.widgetLayout.addWidget(self.playerInputList[player]) self.playerInputList[player].setColour(PlayerColours[i])
class ShowMedicalRecordWidget(QWidget): def __init__(self): super().__init__() self.record_id = None self.user_id = None self.initUI() def initUI(self): self.grid = QGridLayout() self.grid.setSpacing(1) # 外层网格 self.gridinformation = QGridLayout() self.gridinformation.setSpacing(10) # 病人基本信息网格,行距1个字距 self.title = QLabel(' 电子病历', self) self.title.setFont(QFont("Microsoft YaHei", 18, QFont.Bold)) self.gridinformation.addWidget(self.title, 0, 0) string = ' 姓名: ' self.name = QLabel(string, self) self.name.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.name, 1, 0) string = '工作单位: ' self.company = QLabel(string, self) self.company.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.company, 1, 1) string = ' 性别: ' self.gender = QLabel(string, self) self.gender.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.gender, 2, 0) string = '住 址: ' self.address = QLabel(string, self) self.address.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.address, 2, 1) string = ' 年龄: ' self.age = QLabel(string, self) self.age.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.age, 3, 0) string = '科 室: ' self.department = QLabel(string, self) self.department.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.department, 3, 1) string = ' 民族: ' self.nation = QLabel(string, self) self.nation.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.nation, 4, 0) string = '日 期: ' self.date = QLabel(string, self) self.date.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation.addWidget(self.date, 4, 1) self.gridinformation2 = QGridLayout() self.gridinformation2.setSpacing(1) string = '症 状: ' self.symptom = QLabel(string, self) self.symptom.setWordWrap(True) self.symptom.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation2.addWidget(self.symptom, 0, 0, 2, 2) string = '病情结论: ' self.conclusion = QLabel(string, self) self.conclusion.setWordWrap(True) self.conclusion.setFont(QFont("Microsoft YaHei", 11)) self.gridinformation2.addWidget(self.conclusion, 1, 0, 2, 2) self.editButton = QPushButton('编辑') self.editButton.setFixedSize(60, 30) self.gridinformation2.addWidget(self.editButton, 4, 0) self.setGeometry(0, 0, 570, 650) self.setFixedSize(610, 650) self.center() self.setWindowTitle('电子病历') self.gridsign = QGridLayout() self.gridsign.setSpacing(1) self.signframe = QFrame(self) self.signframe.setFrameShape(QFrame.StyledPanel) self.signframe.move(20, 420) self.signframe.resize(575, 190) def load_ui_not_signed(self): if not hasattr(self, 'signprompt'): string = ' 是否电子签名,若进行电子签名,病历便不能修改' self.signprompt = QLabel(string, self) self.signprompt.setFont(QFont("Microsoft YaHei", 11)) self.gridsign.addWidget(self.signprompt, 0, 0) self.yes = QRadioButton('是', self) self.yes.setFocusPolicy(Qt.NoFocus) self.yes.toggle() self.no = QRadioButton('否', self) self.no.setFocusPolicy(Qt.NoFocus) self.no.toggle() self.gridsign.addWidget(self.yes, 1, 1) self.gridsign.addWidget(self.no, 1, 2) self.gridbutton = QGridLayout() self.gridbutton.setSpacing(1) self.okButton = QPushButton('提交') self.okButton.setFixedSize(60, 30) self.gridbutton.addWidget(self.okButton, 0, 2) self.okButton.clicked.connect(self.on_sign_button_clicked) self.grid.addLayout(self.gridbutton, 3, 0) self.grid.addLayout(self.gridinformation, 0, 0) self.grid.addLayout(self.gridinformation2, 1, 0) self.grid.addLayout(self.gridsign, 2, 0) self.setLayout(self.grid) else: self.signprompt.show() self.yes.show() self.no.show() self.okButton.show() if hasattr(self, 'Sign'): self.Sign.hide() def load_ui_signed(self, name): if not hasattr(self, 'Sign'): self.Sign = QLabel(' 电子签名:' + name, self) self.Sign.setFont(QFont("Microsoft YaHei", 14, QFont.Bold)) self.gridsign.addWidget(self.Sign, 2, 0) self.gridblank = QGridLayout() self.gridblank.setSpacing(1) self.blank = QLabel('') self.blank.setFixedSize(60, 30) self.gridblank.addWidget(self.blank, 0, 2) self.grid.addLayout(self.gridblank, 3, 0) self.grid.addLayout(self.gridinformation, 0, 0) self.grid.addLayout(self.gridinformation2, 1, 0) self.grid.addLayout(self.gridsign, 2, 0) self.setLayout(self.grid) else: self.Sign.setText(' 电子签名:' + name) self.Sign.show() if hasattr(self, 'signprompt'): self.signprompt.hide() self.yes.hide() self.no.hide() self.okButton.hide() def center(self): qr = self.frameGeometry() cp = QDesktopWidget().availableGeometry().center() qr.moveCenter(cp) self.move(qr.topLeft()) def load_data(self, name): self.data = RecordService().get_record_data(name) def refresh_data(self, user_id): if self.data is None: return False self.record_id = self.data.get('id') self.user_id = user_id self.name.setText(' 姓名: ' + self.data.get('name')) self.company.setText('工作单位: ' + self.data.get('company')) self.gender.setText(' 性别: ' + self.data.get('gender')) self.age.setText(' 年龄: ' + self.data.get('age')) self.address.setText('住 址: ' + self.data.get('address')) self.department.setText('科 室: ' + self.data.get('department')) self.nation.setText(' 民族: ' + self.data.get('nation')) self.date.setText('日 期: ' + self.data.get('date')) self.symptom.setText('症 状: ' + self.data.get('symptom')) self.conclusion.setText('病情结论: ' + self.data.get('conclusion')) if self.data.get('sign') is None: self.load_ui_not_signed() else: self.load_ui_signed(self.data.get('sign')) return True def on_sign_button_clicked(self): if self.yes.isChecked(): ret, message = SignService().sign(self.user_id, self.record_id) QMessageBox.information(self, "警告", message, QMessageBox.Yes) if ret: self.hide() else: QMessageBox.information(self, "警告", '提交了,然而并没有什么卵用', QMessageBox.Yes)
class MainWindow(QWidget): """ This class contain the GUI and the functions for the Main window \n and uses all the other classes.""" def __init__(self): super(MainWindow, self).__init__() """Overall layout of the main window.""" self.setWindowTitle('Plot segmentation') self.resize(self.sizeHint()) ## initialization self.field_image = None self.displaySize = 400 self.threshold = 0.20 self.noise = 200 self.pix4D = None self.rawImgFold = None ## definition self.text_intro = QLabel('LOAD FIELD IMAGE') self.text_intro.setAlignment(Qt.AlignCenter) self.text_screenSize = QLabel('Select your screen resolution:') self.text_screenSize2 = QLabel('(If the size is not in the list, please choose a smaller size.)') self.comboBox_screenSize = QComboBox() self.comboBox_screenSize.addItem('1024 x 640 pixels') self.comboBox_screenSize.addItem('1280 x 800 pixels') self.comboBox_screenSize.addItem('1440 x 900 pixels') self.comboBox_screenSize.addItem('1680 x 1050 pixels') self.comboBox_screenSize.addItem('2048 x 1152 pixels') self.comboBox_screenSize.addItem('2560 x 1140 pixels') self.comboBox_screenSize.addItem('3200 x 1800 pixels') self.text_fieldImage = QLabel('Choose the field image: ') self.button_fieldImage = QPushButton('Choose') self.text_image = QLabel('Image chosen:') self.text_imagePath = QLabel(str(self.field_image)) self.button_drawField = QPushButton('Draw field shape') self.button_getBinary = QPushButton('Convert to binary') self.check_binary = QCheckBox('Check this if the chosen image is already a binary') self.text_threshold = QLabel('ExG threshold to create binary:') self.text_threshold2 = QLabel('0.20 usually works. Set to 1.00 for automatic.') self.spinbox_threshold = QDoubleSpinBox() self.spinbox_threshold.setRange(0.00, 1.00) self.spinbox_threshold.setSingleStep(0.05) self.spinbox_threshold.setValue(0.20) self.text_noise = QLabel('Minimum feature size for noise removal (px):') self.spinbox_noise = QSpinBox() self.spinbox_noise.setRange(1, 10000) self.spinbox_noise.setValue(200) self.text_plot = QLabel('PLOT PARAMETERS') self.text_plot.setAlignment(Qt.AlignCenter) self.text_nbOfRowPerPlot = QLabel('Number of plant rows per plot:') self.spinbox_nbOfRowPerPlot = QSpinBox() self.spinbox_nbOfRowPerPlot.setRange(1, 100) self.spinbox_nbOfRowPerPlot.setSingleStep(1) self.spinbox_nbOfRowPerPlot.setValue(1) self.text_nbOfColumnPerPlot = QLabel('Number of ranges per plot:') self.spinbox_nbOfColumnPerPlot = QSpinBox() self.spinbox_nbOfColumnPerPlot.setRange(1, 100) self.spinbox_nbOfColumnPerPlot.setSingleStep(1) self.spinbox_nbOfColumnPerPlot.setValue(1) self.text_plotArrangment = QLabel('Global orientation of the ranges:') self.radio_horizontal = QRadioButton('Horizontal\t\t\t') self.radio_horizontal.setChecked(True) self.radio_vertical = QRadioButton('Vertical') self.radio_vertical.setChecked(False) self.button_apply = QPushButton('Identify plots') self.text_intro_revCal = QLabel('CALCULATE PLOT COORDINATES IN RAW IMAGES') self.text_intro_revCal.setAlignment(Qt.AlignCenter) self.text_pix4D = QLabel('Pix4D project folder:') self.button_pix4D = QPushButton('Choose') self.text_rawImgFold = QLabel('Raw images folder:') self.button_rawImgFold = QPushButton('Choose') self.button_apply_revCal = QPushButton('Apply') ## connections self.button_fieldImage.clicked.connect(self.fieldImage_clicked) self.button_drawField.clicked.connect(self.drawField_clicked) self.comboBox_screenSize.activated.connect(self.ScreenSizeFunction) self.button_getBinary.clicked.connect(self.getBinary_clicked) self.button_apply.clicked.connect(self.application) self.button_pix4D.clicked.connect(self.button_pix4D_clicked) self.button_rawImgFold.clicked.connect(self.button_rawImgFold_clicked) self.button_apply_revCal.clicked.connect(self.button_apply_revCal_clicked) ## options self.text_screenSize.hide() self.text_screenSize2.hide() self.comboBox_screenSize.hide() self.check_binary.hide() self.text_threshold.hide() self.text_threshold2.hide() self.spinbox_threshold.hide() self.text_noise.hide() self.spinbox_noise.hide() self.button_drawField.hide() self.text_imagePath.hide() self.text_image.hide() self.text_plot.hide() self.button_getBinary.hide() self.text_nbOfColumnPerPlot.hide() self.spinbox_nbOfColumnPerPlot.hide() self.text_nbOfRowPerPlot.hide() self.spinbox_nbOfRowPerPlot.hide() self.button_apply.hide() self.text_plotArrangment.hide() self.radio_horizontal.hide() self.radio_vertical.hide() self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() ## layout self.layout = QGridLayout() self.layout.addWidget(self.text_intro, 1, 0, 1, -1) self.layout.addWidget(self.text_fieldImage, 2, 0) self.layout.addWidget(self.button_fieldImage, 2, 1, 1, -1) self.layout.addWidget(self.text_image, 3, 0) self.layout.addWidget(self.text_imagePath, 3, 1, 1, -1) self.layout.addWidget(self.check_binary, 4, 1, 1, -1) self.layout.addWidget(self.text_noise, 5, 0) self.layout.addWidget(self.spinbox_noise, 5, 1) self.layout.addWidget(self.text_screenSize, 6, 0) self.layout.addWidget(self.comboBox_screenSize, 6, 1) self.layout.addWidget(self.text_screenSize2, 6, 2, 1, 3) self.layout.addWidget(self.button_drawField, 7, 0, 1, -1) self.layout.addWidget(self.text_threshold, 8, 0) self.layout.addWidget(self.spinbox_threshold, 8, 1) self.layout.addWidget(self.text_threshold2, 8, 2, 1, -1) self.layout.addWidget(self.button_getBinary, 9, 0, 1, -1) self.layout.addWidget(self.text_plot,10, 0, 1, -1) self.layout.addWidget(self.text_nbOfRowPerPlot, 11, 0) self.layout.addWidget(self.spinbox_nbOfRowPerPlot, 11, 1, 1, -1) self.layout.addWidget(self.text_nbOfColumnPerPlot, 12, 0) self.layout.addWidget(self.spinbox_nbOfColumnPerPlot, 12, 1, 1, -1) self.layout.addWidget(self.text_plotArrangment, 13, 0) self.layout.addWidget(self.radio_horizontal, 13, 1) self.layout.addWidget(self.radio_vertical, 13, 2) self.layout.addWidget(self.button_apply, 14, 0, 1, -1) self.layout.addWidget(self.text_intro_revCal, 15, 0, 1, -1) self.layout.addWidget(self.text_pix4D, 16, 0) self.layout.addWidget(self.button_pix4D, 16, 1, 1, -1) self.layout.addWidget(self.text_rawImgFold, 17, 0) self.layout.addWidget(self.button_rawImgFold, 17, 1, 1, -1) self.layout.addWidget(self.button_apply_revCal, 18, 0, 1, -1) self.setLayout(self.layout) self.show() def ScreenSizeFunction(self): """ This function is part of the class 'MainWindow'. \n It is linked to the change of the combo box self.comboBox_screenSize \n It decides the maximum size for the display of pictures depending on the inputted size of the screen """ if self.comboBox_screenSize.currentText() == '1024 x 640 pixels': self.displaySize = 600 if self.comboBox_screenSize.currentText() == '1280 x 800 pixels': self.displaySize = 800 if self.comboBox_screenSize.currentText() == '1440 x 900 pixels': self.displaySize = 900 if self.comboBox_screenSize.currentText() == '1680 x 1050 pixels': self.displaySize = 1000 if self.comboBox_screenSize.currentText() == '2048 x 1152 pixels': self.displaySize = 1100 if self.comboBox_screenSize.currentText() == '2560 x 1140 pixels': self.displaySize = 1100 if self.comboBox_screenSize.currentText() == '3200 x 1800 pixels': self.displaySize = 1700 def fieldImage_clicked(self): """ This function is part of the class 'MainWindow' \n It is connected to the button button_fieldImage and allows the user to chose the image of the whole field on which all the program is based""" self.field_image, _ = QFileDialog.getOpenFileName(self, "Select the field image", "",".tif or .tiff or .jpg or .jpeg or .png (*.tif *.tiff *.TIF *.TIFF *.jpg *.jpeg *.JPG *.JPEG *.PNG *.png)", options=QFileDialog.DontUseNativeDialog) self.field_image = Path(self.field_image) self.text_imagePath.setText(str(self.field_image)) if self.field_image.is_file(): self.check_binary.show() self.text_noise.show() self.spinbox_noise.show() self.text_imagePath.show() self.text_image.show() self.text_screenSize.show() self.text_screenSize2.show() self.comboBox_screenSize.show() self.button_drawField.show() else: self.check_binary.hide() self.text_noise.hide() self.spinbox_noise.hide() self.text_imagePath.hide() self.text_image.hide() self.text_screenSize.hide() self.text_screenSize2.hide() self.comboBox_screenSize.hide() self.button_drawField.hide() self.coord = [] self.text_threshold.hide() self.text_threshold2.hide() self.spinbox_threshold.hide() self.button_getBinary.hide() self.text_plot.hide() self.text_nbOfRowPerPlot.hide() self.spinbox_nbOfRowPerPlot.hide() self.text_nbOfColumnPerPlot.hide() self.spinbox_nbOfColumnPerPlot.hide() self.button_apply.hide() self.text_plotArrangment.hide() self.radio_horizontal.hide() self.radio_vertical.hide() self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() def drawField_clicked(self): """This function is part of the class 'MainWindow' \n It is connected to the button button_drawField and opens the beforehand chosen image of fieldImage_clicked into a new window so the user can select the field points as they wish. The image is then binarized using ExGreen calculation and cropped to avoid useless data storage""" # instructions QMessageBox.about(self, 'Information', "A drawing window will appear. \nTo (Q)uit without saving, press Q.\nTo (R)estart, press R. \nWhen you are (D)one, press D. \n\nPlease mark the corners of the field. \nNo need to close the polygon.") # initialization self.coord = [] self.YN_binary = self.check_binary.isChecked() self.img = cv2.imread(str(self.field_image)) img_name = self.field_image.stem WindowsName = 'Mark the corners of the field. (Q)uit (R)estart (D)one' # make a repository self.main_folder = self.field_image.parent / str('Micro_plots_' + img_name) if self.main_folder.is_dir(): rmtree(self.main_folder, ignore_errors = True) try: self.main_folder.mkdir() except PermissionError: QMessageBox.about(self, 'Information', "Previous results for this image already existed and have been erased.") self.main_folder.mkdir() except FileExistsError: QMessageBox.about(self, 'Information', "Results for this image already exist. Please delete or rename it and try again.") return # resize the image according to the screen size if len(self.img[:, 0]) >= len(self.img[0,:]) : #if the picture's height is bigger than its width self.H = self.displaySize coeff = self.H/len(self.img[:, 0]) self.W = int(coeff*len(self.img[0, :])) else: # if width is bigger than height self.W = self.displaySize coeff = self.W/len(self.img[0, :]) self.H = int(coeff*len(self.img[:, 0])) self.img = cv2.resize(self.img, (self.W, self.H)) # if binary is [0,1], map 1's to 255 if np.amax(self.img) == 1 : self.img [self.img == 1] = 255 # display the picture in a new window cv2.namedWindow(WindowsName) cv2.setMouseCallback(WindowsName, self.draw_point, param = None) # events while drawing (infinite loop) while (1): # show the image window cv2.imshow(WindowsName, self.img) key = cv2.waitKey(20) & 0xFF # to restart the drawing if key == ord('r') or key == ord('R'): # reload the original image (without any points on it) self.img = cv2.imread(str(self.field_image)) self.img = cv2.resize(self.img, (self.W, self.H)) cv2.namedWindow(WindowsName, cv2.WINDOW_NORMAL) # define the name of the window again cv2.setMouseCallback(WindowsName, self.draw_point, param = None) # call the function self.coord = [] # do not save any coordinates # to exit and stop the drawing mode if key == ord('q') or key == ord('Q'): self.coord = [] # no pixels are saved QMessageBox.about(self, 'Information', "No corners were selected.") # close the window cv2.destroyAllWindows() cv2.waitKey(1) self.text_threshold.hide() self.text_threshold2.hide() self.spinbox_threshold.hide() self.button_getBinary.hide() self.text_plot.hide() self.text_nbOfRowPerPlot.hide() self.spinbox_nbOfRowPerPlot.hide() self.text_nbOfColumnPerPlot.hide() self.spinbox_nbOfColumnPerPlot.hide() self.button_apply.hide() self.text_plotArrangment.hide() self.radio_horizontal.hide() self.radio_vertical.hide() self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() return # to finish the drawing and save the points drawn if key == ord('d') or key == ord('D'): # field must be at least rectangular if len(self.coord) < 3: QMessageBox.about(self, 'Information', "Please select at least 3 points. \nIf you want to escape, press 'e' key.") else: ## when done, saving the images and producing exG + binary images # close the drawing with the last magenta line cv2.line(self.img, self.coord[-1], self.coord[0], (255, 0, 255), 1) cv2.imshow(WindowsName, self.img) QMessageBox.about(self, 'Information', "Selected points are: \n" + str(self.coord) + '\n\nThe image will be processed. \nPress OK and wait a few seconds.') # save the coordinate image cv2.imwrite(str(self.main_folder / 'Field_points.jpg'), self.img) cv2.destroyWindow(WindowsName) self.img = get_drawn_image(self.field_image, self.coord, coeff) if self.YN_binary: # get rid of the useless black pixels coords = np.argwhere(self.img) y0, x0 = coords.min(axis = 0) y1, x1 = coords.max(axis = 0) + 1 self.img = self.img[y0:y1, x0:x1] # apply the noise removal B = (self.img != 0) self.img_binary = morphology.remove_small_objects(B, min_size = int(self.noise))*255 # save binary image cv2.imwrite(str(self.main_folder / 'Binary_image.tiff'), self.img_binary) # save the value of cutted black parts for the end of the program (shp files) self.y_offset, self.x_offset = y0, x0 self.text_plot.show() self.text_nbOfRowPerPlot.show() self.spinbox_nbOfRowPerPlot.show() self.text_nbOfColumnPerPlot.show() self.spinbox_nbOfColumnPerPlot.show() self.button_apply.show() self.text_plotArrangment.show() self.radio_horizontal.show() self.radio_vertical.show() self.text_threshold.hide() self.text_threshold2.hide() self.spinbox_threshold.hide() self.button_getBinary.hide() else: self.text_threshold.show() self.text_threshold2.show() self.spinbox_threshold.show() self.button_getBinary.show() self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() return def getBinary_clicked(self): """This function is part of the class 'MainWindow' \n It is connected to the button button_getBinary and opens the beforehand chosen image of fieldImage_clicked into a new window so the user can select the field points as they wish. The image is then binarized using ExGreen calculation and cropped to avoid useless data storage""" self.threshold = self.spinbox_threshold.value() self.noise = self.spinbox_noise.value() # get coordinates of the first non-black pixels coords = np.argwhere(self.img) try: y0, x0, z = coords.min(axis = 0) y1, x1, z = coords.max(axis = 0) + 1 # generate a binary image self.img_exG, self.img_binary = get_binary(self.img, self.noise, self.threshold) # cut all images according to avoid useless black pixels self.img = self.img[y0:y1, x0:x1] self.img_exG = self.img_exG[y0:y1, x0:x1] self.img_binary = self.img_binary[y0:y1, x0:x1] # save outputs cv2.imwrite(str(self.main_folder / 'ExcessGreen.tiff'), self.img_exG) cv2.imwrite(str(self.main_folder / 'Field_area.tiff'), self.img) # show binary and ask to accept/reject QMessageBox.about(self, 'Information', "The binary will be displayed. \nTo (A)ccept it, press A.\nTo (R)etry with a different threshold, press R.") while (1): # show the image window self.img_binary_show = cv2.resize(self.img_binary, (self.W, self.H)) cv2.imshow('Binary. (A)ccept (R)etry', self.img_binary_show) key = cv2.waitKey(20) & 0xFF # to retry with different values if key == ord('r') or key == ord('R'): cv2.destroyAllWindows() self.text_plot.hide() self.text_nbOfRowPerPlot.hide() self.spinbox_nbOfRowPerPlot.hide() self.text_nbOfColumnPerPlot.hide() self.spinbox_nbOfColumnPerPlot.hide() self.button_apply.hide() self.text_plotArrangment.hide() self.radio_horizontal.hide() self.radio_vertical.hide() self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() return if key == ord('a') or key == ord('A'): cv2.destroyAllWindows() break except ValueError: QMessageBox.about(self, 'Information', "It seems that your image is already a binary. It will be treated as a binary for the rest of the program.") self.YN_binary == True y0, x0 = coords.min(axis = 0) y1, x1 = coords.max(axis = 0) + 1 self.img = self.img[y0:y1, x0:x1] # apply the noise removal B = (self.img != 0) self.img_binary = morphology.remove_small_objects(B, min_size = int(self.noise))*255 # save the value of cutted black parts for the end of the program (shp files) self.y_offset, self.x_offset = y0, x0 # displays buttons useful for next steps self.text_plot.show() self.text_nbOfRowPerPlot.show() self.spinbox_nbOfRowPerPlot.show() self.text_nbOfColumnPerPlot.show() self.spinbox_nbOfColumnPerPlot.show() self.button_apply.show() self.text_plotArrangment.show() self.radio_horizontal.show() self.radio_vertical.show() self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() def draw_point (self, event, x, y, flags, param): """ This function is part of the class 'MainWindow' and is used in the function 'drawField_clicked'. It draws a red circle everytime the right button of the mouse is clicked down. If there is more than one point, a magenta line will link the two latest points clicked. Inputs : 5 event : mouth clicked down x : position on the x-axis y : position on the y-axis (going down) flags : param : None [could pass a specific color if needed] """ if event == cv2.EVENT_LBUTTONDOWN: #when the button is pushed, the first pixel is recorded and a circle is drawn on the picture self.coord.append((int(x), int(y))) cv2.circle(self.img, (x,y), 6, (0, 0, 255), -1) #draw the circle if len(self.coord) > 1: cv2.line(self.img, self.coord[-2], self.coord[-1], (255, 0, 255), 1) def application(self): """ This function is part of the class 'MainWindow'. It is linked to the button 'button_apply' and starts the image processing (i.e. clustering, cropping, *.shp files, reverse calculation) """ if self.radio_horizontal.isChecked() == False and self.radio_vertical.isChecked() == False: QMessageBox.about(self, 'Information', "Please indicate if the ranges are more vertically or horizontally oriented. \nIf no particular orientation stands out, choose any.") else: img_raster = rasterio.open(self.field_image) aff = img_raster.transform self.crs = img_raster.crs if type(self.crs) == type(None): aff = 0 img_raster.close() nbRow = self.spinbox_nbOfRowPerPlot.value() nbColumn = self.spinbox_nbOfColumnPerPlot.value() if self.radio_horizontal.isChecked() == True: orientation = 'H' elif self.radio_vertical.isChecked() == True: orientation = 'V' # inform the user the program is finished output = MPE(self.img_binary, self.main_folder, self.img, self.YN_binary, nbRow, nbColumn, orientation, self.noise, self.field_image, aff, self.y_offset, self.x_offset) if output == '1': QMessageBox.about(self, 'Information', 'Sorry, no range has been detected. Please change the input parameters and retry.') self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() if output == '2': QMessageBox.about(self, 'Information', 'Sorry, no row has been detected. Please change the input parameters and retry.') self.text_intro_revCal.hide() self.text_pix4D.hide() self.button_pix4D.hide() self.text_rawImgFold.hide() self.button_rawImgFold.hide() self.button_apply_revCal.hide() elif output == 'OK' : QMessageBox.about(self, 'Information', '''Micro-plot extraction finished!''') # if the original image is georeferenced if type(self.crs) != type(None): # unlock inputs for reverse calculation self.text_intro_revCal.show() self.text_pix4D.show() self.button_pix4D.show() self.text_rawImgFold.show() self.button_rawImgFold.show() self.button_apply_revCal.show() else : QMessageBox.about(self, 'Information', 'The original image is not georeferenced. Thus, reverse calculation cannot be performed.') # make sure everything is unchecked/back to the original value self.spinbox_nbOfRowPerPlot.setValue(1) self.spinbox_nbOfColumnPerPlot.setValue(1) self.radio_horizontal.setChecked(True) self.radio_vertical.setChecked(False) def button_pix4D_clicked(self): self.pix4D = QFileDialog.getExistingDirectory(self, "Select the pix4D project folder") self.pix4D = Path(self.pix4D) def button_rawImgFold_clicked(self): self.rawImgFold = QFileDialog.getExistingDirectory(self, "Select the raw images folder") self.rawImgFold = Path(self.rawImgFold) def button_apply_revCal_clicked(self): if self.pix4D is None or self.rawImgFold is None: QMessageBox.about(self, 'Error', 'There are missing parameters. Please make sure you provided all the inputs.') else : revCal_csv = ReverseCalculation(self.main_folder, self.pix4D, self.rawImgFold) QMessageBox.about(self, 'Information', 'Reverse calculation finished! Output: ' + str(revCal_csv)) self.pix4D = None self.rawImgFold = None
class TCP_UDP(COMM): ''' call sequence: onInit onWidget onUiInitDone isConnected send getConfig ''' id = "tcp_udp" name = "TCP UDP" showSwitchSignal = pyqtSignal(ConnectionStatus) updateTargetSignal = pyqtSignal(str) updateClientsSignal = pyqtSignal(bool, tuple) def onInit(self, config): self.conn = None self.config = config default = { "protocol": "tcp", "mode": "client", "target": ["127.0.0.1:2345", ["127.0.0.1:2345"]], "port": 2345, "auto_reconnect": False, "auto_reconnect_interval": 1.0 } for k in default: if not k in self.config: self.config[k] = default[k] self.widgetConfMap = { "protocol": None, "mode": None, "target": None, "port": None, "auto_reconnect": None, "auto_reconnect_interval": None } self.isOpened = False self.busy = False self.status = ConnectionStatus.CLOSED self.widget = None self.serverModeClientsConns = { # "127.0.0.1:76534": conn } self.serverModeSelectedClient = None # None means all clients, or ip:port string def disconnect(self): if self.isConnected(): self.openCloseSerial() def onDel(self): if self.isConnected(): self.openCloseSerial() def __del__(self): try: self.status = ConnectionStatus.CLOSED if not self.conn is None: self.conn.close() self.conn = None except Exception: pass time.sleep( 0.05 ) # wait for child threads, not wait also ok, cause child threads are daemon def getConfig(self): ''' get config, dict type ''' return self.config def onUiInitDone(self): for key in self.config: self.setSerialConfig(key, self.widgetConfMap[key], self.config[key]) def onWidget(self): serialSetting = QWidget() self.serialSettingsLayout = QGridLayout() protocolLabel = QLabel(_("Protocol")) self.modeLabel = QLabel(_("Mode")) self.targetLabel = QLabel(_("Target")) self.targetCombobox = ComboBox() self.targetCombobox.setEditable(True) self.portLabel = QLabel(_("Port")) self.portLabel.hide() self.porttEdit = QLineEdit() protocolWidget = QWidget() modeWidget = QWidget() layoutProtocol = QHBoxLayout() layoutMode = QHBoxLayout() protocolWidget.setLayout(layoutProtocol) modeWidget.setLayout(layoutMode) self.protoclTcpRadioBtn = QRadioButton("TCP") self.protoclUdpRadioBtn = QRadioButton("UDP") self.protoclTcpRadioBtn.setChecked(True) layoutProtocol.addWidget(self.protoclTcpRadioBtn) layoutProtocol.addWidget(self.protoclUdpRadioBtn) self.modeClientRadioBtn = QRadioButton("Client") self.modeServerRadioBtn = QRadioButton("Server") self.modeClientRadioBtn.setChecked(True) layoutMode.addWidget(self.modeClientRadioBtn) layoutMode.addWidget(self.modeServerRadioBtn) self.clientsCombobox = ComboBox() self.clientsCombobox.addItem("0 | " + _("All clients")) self.disconnetClientBtn = QPushButton(_("Disconnect")) self.autoReconnetLable = QLabel(_("Auto reconnect")) self.autoReconnect = QCheckBox() self.autoReconnectIntervalEdit = QLineEdit("1.0") self.serialOpenCloseButton = QPushButton(_("OPEN")) self.serialSettingsLayout.addWidget(protocolLabel, 0, 0) self.serialSettingsLayout.addWidget(protocolWidget, 0, 1, 1, 2) self.serialSettingsLayout.addWidget(self.modeLabel, 1, 0) self.serialSettingsLayout.addWidget(modeWidget, 1, 1, 1, 2) self.serialSettingsLayout.addWidget(self.targetLabel, 2, 0) self.serialSettingsLayout.addWidget(self.targetCombobox, 2, 1, 1, 2) self.serialSettingsLayout.addWidget(self.portLabel, 3, 0) self.serialSettingsLayout.addWidget(self.porttEdit, 3, 1, 1, 2) self.serialSettingsLayout.addWidget(self.clientsCombobox, 4, 0, 1, 2) self.serialSettingsLayout.addWidget(self.disconnetClientBtn, 4, 2, 1, 1) self.serialSettingsLayout.addWidget(self.autoReconnetLable, 5, 0, 1, 1) self.serialSettingsLayout.addWidget(self.autoReconnect, 5, 1, 1, 1) self.serialSettingsLayout.addWidget(self.autoReconnectIntervalEdit, 5, 2, 1, 1) self.serialSettingsLayout.addWidget(self.serialOpenCloseButton, 6, 0, 1, 3) serialSetting.setLayout(self.serialSettingsLayout) self.widgetConfMap["protocol"] = self.protoclTcpRadioBtn self.widgetConfMap["mode"] = self.modeClientRadioBtn self.widgetConfMap["target"] = self.targetCombobox self.widgetConfMap["port"] = self.porttEdit self.widgetConfMap["auto_reconnect"] = self.autoReconnect self.widgetConfMap[ "auto_reconnect_interval"] = self.autoReconnectIntervalEdit self.initEvet() self.widget = serialSetting return serialSetting def initEvet(self): self.serialOpenCloseButton.clicked.connect(self.openCloseSerial) self.porttEdit.textChanged.connect(self.onPortChanged) self.showSwitchSignal.connect(self.showSwitch) self.updateTargetSignal.connect(self.updateTarget) self.updateClientsSignal.connect(self.updateClients) self.protoclTcpRadioBtn.clicked.connect( lambda: self.changeProtocol("tcp")) self.protoclUdpRadioBtn.clicked.connect( lambda: self.changeProtocol("udp")) self.modeServerRadioBtn.clicked.connect( lambda: self.changeMode("server")) self.modeClientRadioBtn.clicked.connect( lambda: self.changeMode("client")) self.clientsCombobox.currentIndexChanged.connect( self.serverModeClientChanged) self.disconnetClientBtn.clicked.connect( self.serverModeDisconnectClient) self.autoReconnect.stateChanged.connect( lambda x: self.setVar("auto_reconnect", value=x)) self.autoReconnectIntervalEdit.textChanged.connect( lambda: self.setVar("auto_reconnect_interval")) self.targetCombobox.currentTextChanged.connect(self.onTargetChanged) def changeProtocol(self, protocol, init=False): if init or protocol != self.config["protocol"]: if self.isConnected(): self.openCloseSerial() if protocol == "tcp": self.modeClientRadioBtn.show() self.modeServerRadioBtn.show() self.modeLabel.show() self.changeMode(self.config["mode"], init=True) else: self.targetCombobox.show() self.targetLabel.show() self.porttEdit.show() self.portLabel.show() self.clientsCombobox.hide() self.disconnetClientBtn.hide() self.autoReconnect.hide() self.autoReconnectIntervalEdit.hide() self.autoReconnetLable.hide() self.modeClientRadioBtn.hide() self.modeServerRadioBtn.hide() self.modeLabel.hide() self.widget.adjustSize() self.config["protocol"] = protocol def changeMode(self, mode, init=False): if init or mode != self.config["mode"]: if self.isConnected(): self.openCloseSerial() if mode == "server": self.targetCombobox.hide() self.targetLabel.hide() self.porttEdit.show() self.portLabel.show() self.clientsCombobox.show() self.disconnetClientBtn.show() self.autoReconnect.hide() self.autoReconnectIntervalEdit.hide() self.autoReconnetLable.hide() else: self.targetCombobox.show() self.targetLabel.show() self.porttEdit.hide() self.portLabel.hide() self.clientsCombobox.hide() self.disconnetClientBtn.hide() self.autoReconnect.show() self.autoReconnectIntervalEdit.show() self.autoReconnetLable.show() self.widget.adjustSize() self.config["mode"] = mode def onTargetChanged(self): text = self.targetCombobox.currentText() self.config["target"][0] = text def updateTarget(self, new): idx = self.targetCombobox.findText(new) if idx < 0: self.targetCombobox.addItem(new) self.config["target"][1].append(new) self.targetCombobox.setEditText(new) self.config["target"][0] = new def updateClients(self, add: bool, addr: tuple): host, port = addr if add: self.clientsCombobox.addItem(f'{host}:{port}') else: idx = self.clientsCombobox.findText(f'{host}:{port}') if idx > 0: self.clientsCombobox.removeItem(idx) self.clientsCombobox.setItemText( 0, "{} | ".format(self.clientsCombobox.count() - 1) + _("All clients")) def serverModeClientChanged(self): if self.clientsCombobox.currentIndex() == 0: self.serverModeSelectedClient = None else: self.serverModeSelectedClient = self.clientsCombobox.currentText() def serverModeDisconnectClient(self): if not self.serverModeSelectedClient: for addr, conn in self.serverModeClientsConns.items(): try: conn.close() except Exception: pass else: conn = self.serverModeClientsConns[self.serverModeSelectedClient] try: conn.close() except Exception: pass def onPortChanged(self): text = self.porttEdit.text() while 1: try: port = int(text) break except Exception: text = text[:-1] self.porttEdit.setText(text) def onSerialConfigChanged(self, conf_type, obj, value_type, caller=""): pass def setSerialConfig(self, conf_type, obj, value): if conf_type == "protocol": if value == "tcp": obj.setChecked(True) else: obj.setChecked(False) elif conf_type == "mode": if value == "client": obj.setChecked(True) self.changeMode("client", init=True) else: obj.setChecked(False) self.modeServerRadioBtn.setChecked(True) self.changeMode("server", init=True) elif conf_type == "target": for i, target in enumerate(self.config["target"][1]): self.targetCombobox.addItem(target) self.targetCombobox.setCurrentText(self.config["target"][0]) elif conf_type == "port": obj.setText(str(value)) elif conf_type == "auto_reconnect": obj.setChecked(value) elif conf_type == "auto_reconnect_interval": obj.setText("%.3f" % (value)) def setVar(self, key, value=None): if key == "auto_reconnect": self.config[key] = value elif key == "auto_reconnect_interval": text = self.autoReconnectIntervalEdit.text() try: interval = float(text) self.config[key] = interval except Exception: text = "".join(re.findall('[\d\.]*', text)) self.autoReconnectIntervalEdit.setText(text) def openCloseSerial(self): if self.busy: return self.busy = True if self.serialOpenCloseButton.text() == _("OPEN"): self.isOpened = False else: self.isOpened = True t = threading.Thread(target=self.openCloseSerialProcess) t.setDaemon(True) t.start() def openCloseSerialProcess(self): if self.isOpened: print("-- disconnect") try: # set status first to prevent auto reconnect self.status = ConnectionStatus.CLOSED if not self.conn is None: time.sleep(0.1) # wait receive thread exit try: self.conn.close() except Exception: pass self.conn = None for k, conn in self.serverModeClientsConns.items(): try: conn.close() except Exception: pass except Exception as e: print(e) pass self.onConnectionStatus.emit(self.status, "") self.showSwitchSignal.emit(self.status) else: try: if self.config["protocol"] == "tcp": if self.config["mode"] == "client": print("-- connect") target = self.checkTarget(self.config["target"][0]) if not target: raise Exception( _("Target error") + ": " + self.config["target"][0]) print("-- connect", target) self.onConnectionStatus.emit( ConnectionStatus.CONNECTING, "") self.conn = socket.socket() self.conn.connect(target) self.status = ConnectionStatus.CONNECTED print("-- connect success") self.receiveProcess = threading.Thread( target=self.receiveDataProcess, args=(self.conn, )) self.receiveProcess.setDaemon(True) self.receiveProcess.start() else: print("-- server mode, wait client connect") self.conn = socket.socket() self.conn.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) self.conn.bind(("0.0.0.0", self.config["port"])) self.conn.listen(100) self.status = ConnectionStatus.CONNECTED self.waitClentsProcess = threading.Thread( target=self.waitClientsProcess) self.waitClentsProcess.setDaemon(True) self.waitClentsProcess.start() else: print("-- UPD protocol") self.conn = socket.socket(type=socket.SOCK_DGRAM) self.conn.bind(("0.0.0.0", self.config["port"])) self.status = ConnectionStatus.CONNECTED self.receiveProcess = threading.Thread( target=self.receiveDataProcess, args=(self.conn, )) self.receiveProcess.setDaemon(True) self.receiveProcess.start() self.onConnectionStatus.emit(self.status, "") self.showSwitchSignal.emit(self.status) except Exception as e: print("----", e) try: self.conn.close() self.conn = None except Exception: pass msg = _("Connect Failed") + "\n" + str(e) self.hintSignal.emit("error", _("Error"), msg) self.status = ConnectionStatus.CLOSED self.onConnectionStatus.emit(self.status, msg) self.showSwitchSignal.emit(self.status) self.busy = False def checkTarget(self, target): if not target: return None host = target port = 80 target = target.replace(":", ":") if target.endswith(":"): target = target[:-1] _host = re.match('http(.*)://(.*)', target) if _host: s, target = _host.groups() host = target _host = re.match('(.*):(\d*)', target) if _host: host, port = _host.groups() port = int(port) if host.endswith("/"): host = host[:-1] target = (host, port) target_str = f'{host}:{port}' self.updateTargetSignal.emit(target_str) return target # @pyqtSlot(ConnectionStatus) def showSwitch(self, status): if status == ConnectionStatus.CLOSED: self.serialOpenCloseButton.setText(_("OPEN")) self.serialOpenCloseButton.setProperty("class", "") elif status == ConnectionStatus.CONNECTED: self.serialOpenCloseButton.setText(_("CLOSE")) self.serialOpenCloseButton.setProperty("class", "") else: self.serialOpenCloseButton.setText(_("CLOSE")) self.serialOpenCloseButton.setProperty("class", "warning") self.updateStyle(self.serialOpenCloseButton) def updateStyle(self, widget): self.widget.style().unpolish(widget) self.widget.style().polish(widget) self.widget.update() def waitClientsProcess(self): while self.status != ConnectionStatus.CLOSED: print("-- wait for client connect") try: conn, addr = self.conn.accept() except Exception as e: if self.status != ConnectionStatus.CLOSED: print("-- accept connection fail:", str(e)) continue print("-- client connected, ip:", addr) addr_str = f'{addr[0]}:{addr[1]}' self.updateClientsSignal.emit(True, addr) self.onConnectionStatus.emit( ConnectionStatus.CONNECTED, _("Client connected:") + " " + addr_str) self.serverModeClientsConns[addr_str] = conn t = threading.Thread(target=self.receiveDataProcess, args=(conn, addr)) t.setDaemon(True) t.start() print("-- wait connection thread exit") def receiveDataProcess(self, conn, remote_addr: tuple = None): waitingReconnect = False buffer = b'' t = 0 conn.settimeout(0.1) protocolIsTcp = self.config["protocol"] == "tcp" modeIsServer = self.config["mode"] == "server" remoteStr = "" if remote_addr: remoteStr = f'{remote_addr[0]}:{remote_addr[1]}' while self.status != ConnectionStatus.CLOSED: if waitingReconnect: try: target = self.checkTarget(self.config["target"][0]) if not target: raise Exception( _("Target error") + ": " + self.config["target"][0]) self.onConnectionStatus.emit(ConnectionStatus.CONNECTING, "") conn = socket.socket() conn.connect(target) conn.settimeout(0.1) self.conn = conn print("-- reconnect") waitingReconnect = False self.onConnectionStatus.emit(ConnectionStatus.CONNECTED, _("Reconnected")) self.showSwitchSignal.emit(ConnectionStatus.CONNECTED) continue except Exception as e: pass time.sleep(self.config["auto_reconnect_interval"]) continue try: # length = max(1, self.conn.in_waiting) flush = True try: if protocolIsTcp: data = conn.recv(4096) # ignore not selected target's msg if modeIsServer and self.serverModeSelectedClient and ( remoteStr != self.serverModeSelectedClient): data = None else: data, target = conn.recvfrom(4096) if data == b'': # closed by peer(peer send FIN, now we can close this connection) if buffer: self.onReceived(buffer) raise Exception(_("Closed by peer")) except socket.timeout: data = None if data: if len(data) > 4096: flush = False t = time.time() # if length == 1 and not buffer: # just start receive # buffer += data # continue buffer += data if flush or ( buffer and (time.time() - t > 0.001)): # no new data in 0.1ms try: self.onReceived(buffer) except Exception as e: print("-- error in onReceived callback:", e) buffer = b'' except Exception as e: print("-- recv error:", e, type(e)) if modeIsServer or not self.config["auto_reconnect"]: over = False if protocolIsTcp and modeIsServer: self.onConnectionStatus.emit( ConnectionStatus.CLOSED, _("Connection") + f' {remote_addr[0]}:{remote_addr[1]} ' + _("closed!")) over = True else: self.status = ConnectionStatus.CLOSED self.onConnectionStatus.emit( self.status, _("Connection closed!") + " " + str(e)) self.showSwitchSignal.emit(self.status) try: conn.close() except Exception: pass if over: break elif (self.status != ConnectionStatus.CLOSED): # close as fast as we can to release port try: conn.close() except Exception: pass waitingReconnect = True self.onConnectionStatus.emit(ConnectionStatus.LOSE, _("Connection lose!")) self.showSwitchSignal.emit(ConnectionStatus.LOSE) time.sleep(self.config["auto_reconnect_interval"]) # server mode remove client if self.config["mode"] == "server": remote_str = f'{remote_addr[0]}:{remote_addr[1]}' print(f"-- client {remote_str} disconnect") self.updateClientsSignal.emit(False, remote_addr) if remote_str == self.serverModeSelectedClient: self.serverModeSelectedClient = None self.serverModeClientsConns.pop(remote_str) print("-- receiveDataProcess exit") def send(self, data: bytes): if self.conn: if self.config["protocol"] == "tcp": if self.config["mode"] == "client": self.conn.sendall(data) else: if not self.serverModeSelectedClient: for addr, conn in self.serverModeClientsConns.items(): conn.sendall(data) else: self.serverModeClientsConns[ self.serverModeSelectedClient].sendall(data) else: target = self.checkTarget(self.config["target"][0]) if not target: self.hintSignal.emit( "error", _("Target error"), _("Target error") + ": " + self.config["target"]) self.conn.sendto(data, target) def isConnected(self): return self.status == ConnectionStatus.CONNECTED
class _FwdGeomGroupbox(_StateAwareGroupbox): """ Groupbox to setup spacing and montage and select forward from disk. If in choosing from available forwards mode, combobox values in spacing and montage correspond to folders in COGNIGRAPH_DATA. Availabled forwards are fetched from these folers. If in computing forward mode, montage combobox values come from mne-python get_builtin_montages function while spacing combobox values are preset to be from ['oct5', 'ico5', 'oct6', 'ico6'], which are octahedron and icosahedron tesselations of a sphere with number corresponding to the number of tesselation steps. """ default_montage = "standard_1005" default_spacing = "oct6" def __init__( self, default_subj, title="Select montage and spacing", parent=None, data_chnames=None, ): _StateAwareGroupbox.__init__(self, title=title, parent=parent) self._data_chnames = data_chnames self._anat_folder = None # self.is_valid = True # self.setToolTip('I`m here to help') # -------- setup paths and fetch montages -------- # self._get_builtin_montages() self._default_forwards_path = op.join(COGNIGRAPH_DATA, "forwards", default_subj) self.get_available_forwards(self._default_forwards_path) # self._is_montages_combo_connected = False # to spacings combo # ------------------------------------------------ # # -------- setup comboboxes -------- # self._montages_combo = _ResettableComboBox() self._montages_combo.currentTextChanged.connect( self._on_montage_combo_changed) # self._montages_combo.currentIndexChanged.connect(self._check_if_valid) montages_combo_label = QLabel("Select montage:") montages_combo_label.setBuddy(self._montages_combo) montages_combo_layout = QHBoxLayout() montages_combo_layout.addWidget(montages_combo_label) montages_combo_layout.addWidget(self._montages_combo) self._montages_combo_widget = QWidget() self._montages_combo_widget.setLayout(montages_combo_layout) self._spacings_combo = _ResettableComboBox() self._spacings_combo.currentTextChanged.connect( self._on_spacings_combo_changed) spacings_label = QLabel("Select spacing:") spacings_label.setBuddy(self._spacings_combo) spacings_combo_layout = QHBoxLayout() spacings_combo_layout.addWidget(spacings_label) spacings_combo_layout.addWidget(self._spacings_combo) self._spacings_combo_widget = QWidget() self._spacings_combo_widget.setLayout(spacings_combo_layout) self._forwards_combo = _ResettableComboBox() forwards_label = QLabel("Select forward operator:") forwards_label.setBuddy(self._spacings_combo) forwards_combo_layout = QVBoxLayout() forwards_combo_layout.addWidget(forwards_label) forwards_combo_layout.addWidget(self._forwards_combo) self._forwards_combo_widget = QWidget() self._forwards_combo_widget.setLayout(forwards_combo_layout) # ---------------------------------- # self._use_default_montage_radio = QRadioButton("&Use default") self._import_montage_radio = QRadioButton("&Import montage") self._use_default_montage_radio.setChecked(True) self._use_default_montage_radio.toggled.connect( self._on_import_montage_radio_toggled) self._import_montage_radio.toggled.connect( self._on_import_montage_radio_toggled) self._select_montage_dialog = _FileSelectorWidget( dialog_caption="Select montage model", path="", file_filter="*.txt *.elc *.csd *.elp *.htps" " *.sfp *.loc *.locs *.eloc *.bvef", ) self._select_montage_dialog.path_ledit.textChanged.connect( self._on_montage_path_changed) # self._select_montage_dialog.path_ledit.textChanged.connect( # self._check_if_valid # ) self._select_montage_dialog.setDisabled(True) self._custom_montage_widget = _CustomMontageWidget() self._custom_montage_widget.button.clicked.connect( self._on_edit_montage_button_clicked) self._custom_montage_widget.checkbox.stateChanged.connect( self._on_custom_montage_checkbox_toggled) # self._custom_montage_widget.lineedit.textChanged.connect( # self._check_if_valid # ) # initialize combos with available forwards self.is_use_available = True # -------- setup layout -------- # default_fwd_layout = QVBoxLayout() default_fwd_layout.addWidget(self._use_default_montage_radio) default_fwd_layout.addWidget(self._montages_combo_widget) default_fwd_layout.addWidget(self._import_montage_radio) default_fwd_layout.addWidget(self._select_montage_dialog) default_fwd_layout.addWidget(self._custom_montage_widget) default_fwd_layout.addWidget(self._spacings_combo_widget) default_fwd_layout.addWidget(self._forwards_combo_widget) self.default_fwd_widget = QWidget() self.default_fwd_widget.setLayout(default_fwd_layout) self.default_fwd_widget.setSizePolicy(QSizePolicy.Minimum, QSizePolicy.Fixed) default_fwd_setup_layout = QVBoxLayout() default_fwd_setup_layout.addWidget(self.default_fwd_widget) self.setLayout(default_fwd_setup_layout) # ------------------------------ # # self._check_if_valid() def _get_builtin_montages(self): # called when choosing forward from available files on disk montages_desc_path = op.join(COGNIGRAPH_DATA, "montages_desc.json") with open(montages_desc_path, "r", encoding="utf8") as f: description = json.load(f) self.montages_desc = description["montages"] self.spacings_desc = description["spacings"] self.builtin_montage_names = sorted( mne.channels.get_builtin_montages()) def get_available_forwards(self, folder): """Fetch forwards from COGNIGRAPH_DATA folders structure""" self._anat_folder = folder p = folder if op.isdir(p): self._available_montages = sorted( [i for i in os.listdir(p) if op.isdir(op.join(p, i))]) else: self._available_montages = [] self._available_forwards = {} for a in self._available_montages: spacings = os.listdir(op.join(p, a)) self._available_forwards[a] = {} for s in spacings: forwards = [ f for f in os.listdir(op.join(p, a, s)) if f.endswith("fwd.fif") ] self._available_forwards[a][s] = forwards def _set_hints(self): """Set popup description messages to comboboxes""" block_signals = QSignalBlocker(self._montages_combo) # noqa for i, key in enumerate(self._montages_combo.getItems()): try: self._montages_combo.setItemData(i, self.montages_desc[key], Qt.ToolTipRole) except KeyError: pass for i, key in enumerate(self._spacings_combo.getItems()): try: self._spacings_combo.setItemData(i, self.spacings_desc[key], Qt.ToolTipRole) except KeyError: pass def _set_combos_to_builtin(self): """Used when we switch to compute forward mode""" block_signals = QSignalBlocker(self._montages_combo) # noqa self._montages_combo.setItems(self.builtin_montage_names) self.montage = self.default_montage self._spacings_combo.setItems( [k for k in self.spacings_desc if k != "imported"]) self.spacing = self.default_spacing # uses spacing setter self._forwards_combo_widget.hide() self._set_hints() self._use_default_montage_radio.show() self._import_montage_radio.show() self._select_montage_dialog.show() self._custom_montage_widget.show() def _set_combos_to_available(self): """Default option: load forward from cognigraph folders structure""" self._set_montages_combo_to_available() self._forwards_combo_widget.show() self._set_hints() self._use_default_montage_radio.hide() self._import_montage_radio.hide() self._select_montage_dialog.hide() self._custom_montage_widget.hide() def _set_montages_combo_to_available(self): block_signals = QSignalBlocker(self._montages_combo) # noqa self._montages_combo.setItems(self._available_montages) self.montage = self.default_montage self._set_spacings_combo_to_available() def _set_spacings_combo_to_available(self): montage = self.montage if self._available_forwards: self._spacings_combo.setItems( self._available_forwards[montage].keys()) self.spacing = self.default_spacing self._set_forwards_combo_to_available() def _set_forwards_combo_to_available(self): if self._available_forwards: self._forwards_combo.setItems( self._available_forwards[self.montage][self.spacing]) def _on_montage_combo_changed(self): """ If using available forwards, fetch all available spacings and forwards for selected montage; set self.montage """ if self.is_use_available: self._set_spacings_combo_to_available() # if self._forwards_combo.currentText(): # self.is_valid = True # else: # self.is_valid = False if self._custom_montage_widget.checkbox.isChecked(): self._custom_montage_widget.lineedit.setText( self._montages_combo.currentText()) QTimer.singleShot(0, self._check_if_valid) def _on_spacings_combo_changed(self): if self.is_use_available: self._set_forwards_combo_to_available() QTimer.singleShot(0, self._check_if_valid) def _on_import_montage_radio_toggled(self): if self._use_default_montage_radio.isChecked(): self._select_montage_dialog.setDisabled(True) self._montages_combo_widget.setDisabled(False) else: # 'compute forward' case self._select_montage_dialog.setDisabled(False) self._montages_combo_widget.setDisabled(True) self._select_montage_dialog.browse_button.setFocus() QTimer.singleShot(0, self._check_if_valid) def _on_montage_path_changed(self): # if self._select_montage_dialog.path_ledit.text(): # self.is_valid = True if self._custom_montage_widget.checkbox.isChecked(): self._custom_montage_widget.lineedit.setText( self._select_montage_dialog.path_ledit.text()) QTimer.singleShot(0, self._check_if_valid) def _check_if_valid(self): is_montage_valid = self._check_montage() if self.is_use_available and not self.fwd_name: is_forward_ok = False else: is_forward_ok = True self.is_valid = is_montage_valid and is_forward_ok if not is_montage_valid: self.parent()._dialog_buttons.button( QDialogButtonBox.Ok).setToolTip( "Data and forward channel names dont match." " Please edit montage or select another forward.") elif not is_forward_ok: self.parent()._dialog_buttons.button( QDialogButtonBox.Ok).setToolTip("Forward model is missing.") else: self.parent()._dialog_buttons.button( QDialogButtonBox.Ok).setToolTip("") def _check_montage(self): montage_name = self.montage if montage_name != "imported": try: montage = mne.channels.read_montage(montage_name) except ValueError: montage_path = op.join(MONTAGES_DIR, montage_name) + ".elc" try: montage = mne.channels.read_montage(montage_path) except Exception: return False ch_names_forward = montage.ch_names else: fwd_path = op.join(self._anat_folder, self.montage, self.spacing, self.fwd_name) fwd = mne.read_forward_solution(fwd_path) ch_names_forward = fwd["info"]["ch_names"] data_chnames_upper = [d.upper() for d in self._data_chnames] ch_names_intersect = [ n for n in ch_names_forward if n.upper() in data_chnames_upper ] if len(ch_names_intersect) > 0.2 * len(self._data_chnames): return True else: return False @property def montage(self): montage = None if not self._custom_montage_widget.checkbox.isChecked(): if self._use_default_montage_radio.isChecked(): montage = self._montages_combo.currentText() else: montage = self._select_montage_dialog.path_ledit.text() else: montage = self._custom_montage_widget.lineedit.text() return montage @montage.setter def montage(self, value): if not self._custom_montage_widget.checkbox.isChecked(): if self._use_default_montage_radio.isChecked(): self._montages_combo.setCurrentText(value) else: self._select_montage_dialog.path_ledit.setText(value) else: self._custom_montage_widget.lineedit.setText(value) @property def spacing(self): return self._spacings_combo.currentText() @spacing.setter def spacing(self, value): self._spacings_combo.setCurrentText(value) @property def fwd_name(self): return self._forwards_combo.currentText() @fwd_name.setter def fwd_name(self, value): self._forwards_combo.setCurrentText(value) @property def is_use_available(self): return self._is_use_available @is_use_available.setter def is_use_available(self, value): self._is_use_available = value self._use_default_montage_radio.setChecked(True) if value: self._set_combos_to_available() else: # forward computation case self._set_combos_to_builtin() def _on_edit_montage_button_clicked(self): m = mne.channels.read_montage(self.montage) montage_editor = MontageEditor(self._data_chnames, m, self) montage_editor.exec() if montage_editor.result(): self.montage = montage_editor.montage_path QTimer.singleShot(0, self._check_if_valid) def _on_custom_montage_checkbox_toggled(self, state): if state: if self._use_default_montage_radio.isChecked(): montage = self._montages_combo.currentText() else: montage = self._select_montage_dialog.path_ledit.text() self._custom_montage_widget.lineedit.setText(montage)
class mainApp(QWidget): eventStarted = pyqtSignal(eventManager.eventManager) def __init__(self): super().__init__() self.initUI() self.manager = ButtonReleaseManager() self.manager.released.connect(self.show_position) self.manager.loopStop.connect(self.loopStop) self.eventThread = eventManager.eventThread(parent=self) self.eventManager = eventManager.eventManager(self.eventThread) self.pinList = deque() def initUI(self): mainLayout = QGridLayout() # 제일 위 currentCoTextLabel = QLabel('현재 좌표: ', self) self.currentCoLabel = QLabel('', self) self.currentCoLabel.setStyleSheet("border :1px solid grey;") # fixCoTextLabel = QLabel('클릭 좌표: ', self) # self.fixCoLabel = QLabel('', self) # self.fixCoLabel.setStyleSheet("border :1px solid grey;") headerGroup = QButtonGroup(self) pinRadio = QRadioButton('PIN 입력') cashRadio = QRadioButton('기프트 구입') headerGroup.addButton(pinRadio) headerGroup.addButton(cashRadio) pinRadio.setChecked(True) # 중간 inputTypeTextLabel = QLabel('동작 구분: ', self) self.inputTypeCombobox = QComboBox(self) self.inputTypeCombobox.addItem('클릭') self.inputTypeCombobox.addItem('드래그') self.inputTypeCombobox.addItem('마우스이동') self.inputTypeCombobox.addItem('텍스트') self.inputTypeCombobox.addItem('핀입력') self.inputTypeCombobox.addItem('핫키') self.inputTypeCombobox.addItem('브라우저') self.inputTypeCombobox.addItem('컬쳐결과확인') self.inputTypeCombobox.addItem('해피결과확인') self.inputTypeCombobox.activated[str].connect(self.onActivated) self.startCoTextLabel = QLabel('시작 좌표', self) self.startCoText = QLineEdit(self) self.endCoTextLabel = QLabel('종료 좌표', self) self.endCoText = QLineEdit(self) self.typoTextLabel = QLabel('텍스트', self) self.typoText = QLineEdit(self) self.browserLabel = QLabel('URL', self) self.browserText = QLineEdit(self) hotkeyGroup = QButtonGroup(self) self.copyRadio = QRadioButton('복사') self.pasteRadio = QRadioButton('붙여넣기') self.closeRadio = QRadioButton('창닫기') hotkeyGroup.addButton(self.copyRadio) hotkeyGroup.addButton(self.pasteRadio) hotkeyGroup.addButton(self.closeRadio) delayTextLabel = QLabel('지연 시간', self) self.delayText = QLineEdit(self) actionTypeTextLabel = QLabel('동작 횟수', self) self.actionTypeCombobox = QComboBox(self) self.actionTypeCombobox.addItem('한번만') self.actionTypeCombobox.addItem('반복') self.addButton = QPushButton(self) self.addButton.setText('추가') self.addButton.clicked.connect(self.eventAdd) self.startButton = QPushButton(self) self.startButton.setText('시작') self.startButton.clicked.connect(self.macroStart) self.typoTextLabel.hide() self.typoText.hide() self.browserLabel.hide() self.browserText.hide() self.copyRadio.hide() self.pasteRadio.hide() self.closeRadio.hide() self.endCoText.setEnabled(False) self.copyRadio.setChecked(True) # 아래 # self.pinLabel = QLabel() # self.pinLabel.setStyleSheet("border :1px solid grey;") self.pinLabelScrollArea = QScrollArea() self.pinLabelScrollArea.setWidgetResizable(True) self.pinScrollWidget = QWidget(self) pinScrollLayout = QVBoxLayout(self) self.pinScrollWidget.setLayout(pinScrollLayout) self.pinLabelScrollArea.setWidget(self.pinScrollWidget) self.eventLabelScrollArea = QScrollArea() self.eventLabelScrollArea.setWidgetResizable(True) self.scrollWidget = QWidget(self) # scrollLayout = QVBoxLayout(self) scrollLayout = QGridLayout(self) self.scrollWidget.setLayout(scrollLayout) # self.eventLabel = QLabel() self.eventLabelScrollArea.setWidget(self.scrollWidget) # 그리드에 쌓기 mainLayout.addWidget(currentCoTextLabel, 0, 0) mainLayout.addWidget(self.currentCoLabel, 0, 1, 1, 3) # mainLayout.addWidget(fixCoTextLabel, 0, 4) # mainLayout.addWidget(self.fixCoLabel, 0, 5, 1, 3) mainLayout.addWidget(pinRadio, 0, 10) mainLayout.addWidget(cashRadio, 0, 11, 1, 2) mainLayout.addWidget(inputTypeTextLabel, 1, 0) mainLayout.addWidget(self.inputTypeCombobox, 1, 1) mainLayout.addWidget(self.startCoTextLabel, 1, 2) mainLayout.addWidget(self.startCoText, 1, 3) mainLayout.addWidget(self.endCoTextLabel, 1, 4) mainLayout.addWidget(self.endCoText, 1, 5) mainLayout.addWidget(self.typoTextLabel, 1, 2) mainLayout.addWidget(self.typoText, 1, 3, 1, 3) mainLayout.addWidget(self.browserLabel, 1, 2) mainLayout.addWidget(self.browserText, 1, 3, 1, 3) mainLayout.addWidget(self.copyRadio, 1, 2) mainLayout.addWidget(self.pasteRadio, 1, 3) mainLayout.addWidget(self.closeRadio, 1, 4) mainLayout.addWidget(delayTextLabel, 1, 6) mainLayout.addWidget(self.delayText, 1, 7) mainLayout.addWidget(actionTypeTextLabel, 1, 8) mainLayout.addWidget(self.actionTypeCombobox, 1, 9) mainLayout.addWidget(self.addButton, 1, 10) mainLayout.addWidget(self.startButton, 1, 11) mainLayout.addWidget(self.pinLabelScrollArea, 2, 0, 1, 10) mainLayout.addWidget(self.eventLabelScrollArea, 3, 0, 1, 10) # mouseTrackThread = threading.Thread(target=self.mouseTrack, args=()) # mouseTrackThread.daemon = True # mouseTrackThread.start() self.setLayout(mainLayout) self.setWindowTitle('Sample Macro') self.setFixedSize(1280, 768) qtRectangle = self.frameGeometry() centerPoint = QDesktopWidget().availableGeometry().center() qtRectangle.moveCenter(centerPoint) self.move(qtRectangle.topLeft()) self.show() def mouseTrack(self): while 1: x, y = pyautogui.position() self.currentCoLabel.setText('x={0}, y={1}'.format(x, y)) def keyPressEvent(self, e): if e.key() == Qt.Key_Escape: if self.eventThread.isRun: self.eventThread.isRun = False print('loop end') else: with open("eventScenario.json", "w") as json_file: json.dump(self.eventManager.eventScenarioJson, json_file, indent=4) print('app end') self.close() def onActivated(self, text): self.startCoTextLabel.hide() self.startCoText.hide() self.endCoTextLabel.hide() self.endCoText.hide() self.typoTextLabel.hide() self.typoText.hide() self.browserLabel.hide() self.browserText.hide() self.copyRadio.hide() self.pasteRadio.hide() self.closeRadio.hide() self.startCoText.setText('') self.typoText.setText('') self.browserText.setText('') self.endCoText.setText('') self.delayText.setText('') if text == '클릭' or text == '마우스이동': self.startCoTextLabel.show() self.startCoText.show() self.endCoTextLabel.show() self.endCoText.show() self.endCoText.setEnabled(False) elif text == '드래그': self.startCoTextLabel.show() self.startCoText.show() self.endCoTextLabel.show() self.endCoText.show() self.endCoText.setEnabled(True) elif text == '텍스트': self.typoTextLabel.show() self.typoText.show() elif text == '핫키': self.copyRadio.show() self.pasteRadio.show() self.closeRadio.show() self.copyRadio.setChecked(True) elif text == '브라우저': self.browserLabel.show() self.browserText.show() def eventAdd(self): # print('add click') eventType = self.inputTypeCombobox.currentText() startXy = self.startCoText.text() endXy = self.endCoText.text() typoText = self.typoText.text() url = self.browserText.text() hotkey = '' if eventType == '핫키': if self.copyRadio.isChecked(): hotkey = 'copy' elif self.pasteRadio.isChecked(): hotkey = 'paste' else: hotkey = 'close' delay = self.delayText.text() actionType = self.actionTypeCombobox.currentIndex() self.clearEventLayout() newSeq = sequence.sequence(startXy, eventType, endXy, typoText, url, hotkey, delay, actionType, self.pinList) self.eventManager.addEvent(newSeq, actionType) self.buildEventLayout() # print(json.dumps(self.eventManager)) def jsonEventAdd(self, jsonData): # print('add click') eventList = jsonData['eventList'] repeatEventList = jsonData['repeatEventList'] for eventSeq in eventList: eventType = eventSeq['eventType'] startXy = eventSeq['startXy'] endXy = eventSeq['endXy'] typoText = eventSeq['text'] url = eventSeq['url'] hotkey = eventSeq['command'] delay = eventSeq['delayTime'] actionType = eventSeq['actionType'] newSeq = sequence.sequence(startXy, eventType, endXy, typoText, url, hotkey, delay, actionType, self.pinList) self.eventManager.addEvent(newSeq, actionType) for eventSeq in repeatEventList: eventType = eventSeq['eventType'] startXy = eventSeq['startXy'] endXy = eventSeq['endXy'] typoText = eventSeq['text'] url = eventSeq['url'] hotkey = eventSeq['command'] delay = eventSeq['delayTime'] actionType = eventSeq['actionType'] newSeq = sequence.sequence(startXy, eventType, endXy, typoText, url, hotkey, delay, actionType, self.pinList) self.eventManager.addEvent(newSeq, actionType) def clearEventLayout(self): while self.scrollWidget.layout().count(): item = self.scrollWidget.layout().takeAt(0) widget = item.widget() widget.deleteLater() def buildEventLayout(self): for idx, eventSeq in enumerate(self.eventManager.eventList): seqString = '동작구분={0}, 시작좌표={1}, 끝좌표={2}, 텍스트={3}, 주소={7}, 단축키={4}, 지연시간={5}, 반복구분={6}\n'.format( eventSeq.eventType, eventSeq.startXy, eventSeq.endXy, eventSeq.text, eventSeq.command, eventSeq.delayTime, eventSeq.actionType, eventSeq._url) eventLabel = QLabel(seqString) # eventEditButton = QPushButton() # eventEditButton.setText('수정') eventDeleteButton = QPushButton() eventDeleteButton.setText('삭제') # eventEditButton.clicked.connect(lambda checked, _idx = idx : self.eventEdit(_idx, eventSeq.actionType)) eventDeleteButton.clicked.connect( lambda checked, _idx=idx: self.eventDelete( _idx, eventSeq.actionType)) self.scrollWidget.layout().addWidget(eventLabel, idx, 0) # self.scrollWidget.layout().addWidget(eventEditButton, idx, 1) self.scrollWidget.layout().addWidget(eventDeleteButton, idx, 2) for idx, repeatEventSeq in enumerate(self.eventManager.repeatEventList, len(self.eventManager.eventList)): seqString = '동작구분={0}, 시작좌표={1}, 끝좌표={2}, 텍스트={3}, 주소={7}단축키={4}, 지연시간={5}, 반복구분={6}\n'.format( repeatEventSeq.eventType, repeatEventSeq.startXy, repeatEventSeq.endXy, repeatEventSeq.text, repeatEventSeq.command, repeatEventSeq.delayTime, repeatEventSeq.actionType, repeatEventSeq._url) eventLabel = QLabel(seqString) # eventEditButton = QPushButton() # eventEditButton.setText('수정') eventDeleteButton = QPushButton() eventDeleteButton.setText('삭제') # eventEditButton.clicked.connect(lambda checked, _idx = idx - len(self.eventManager.eventList) : self.eventEdit(_idx, repeatEventSeq.actionType)) eventDeleteButton.clicked.connect( lambda checked, _idx=idx - len(self.eventManager.eventList): self.eventDelete(_idx, repeatEventSeq.actionType)) self.scrollWidget.layout().addWidget(eventLabel, idx, 0) # self.scrollWidget.layout().addWidget(eventEditButton, idx, 1) self.scrollWidget.layout().addWidget(eventDeleteButton, idx, 2) def macroStart(self): # print('start click') self.eventManager.executeEvent() # def on_click(self, x, y, button, pressed): # if pressed == True: # print(x,y) def eventEdit(self, _index, actionType): print('actionType:{0} index:{1} edit click'.format(actionType, _index)) def eventDelete(self, _index, actionType): # print('actionType:{0} index:{1} delete click'.format(actionType, _index)) if actionType == 0: del self.eventManager.eventList[_index] del self.eventManager.eventScenarioJson['eventList'][_index] elif actionType == 1: del self.eventManager.repeatEventList[_index] del self.eventManager.eventScenarioJson['repeatEventList'][_index] self.clearEventLayout() self.buildEventLayout() @pyqtSlot() def show_position(self): x, y = pyautogui.position() coordText = '{0}, {1}'.format(x, y) win32clipboard.OpenClipboard() win32clipboard.EmptyClipboard() win32clipboard.SetClipboardText(coordText, win32clipboard.CF_TEXT) win32clipboard.CloseClipboard() self.currentCoLabel.setText(coordText) @pyqtSlot() def loopStop(self): self.eventManager.isRun = False self.eventThread.isRun = False print('crtl+d: loop stop') def pinLoad(self, _data): pinData = _data['pinData'] count = 0 # for i in range(2) : for pinString in pinData: self.pinList.append(pinString) pinText = '{0}: {1}'.format(count, pinString) pinLabel = QLabel(pinText) self.pinScrollWidget.layout().addWidget(pinLabel) count += 1
class Window(QWidget): def __init__(self): super().__init__() self.title = "OS Project Group 10" self.top = 100 self.left = 100 self.width = 400 self.height = 300 self.setWindowTitle(self.title) self.setGeometry(self.left, self.top, self.width, self.height) self.hbox = QHBoxLayout() self.initBox() self.setLayout(self.hbox) self.show() def initBox(self): self.groupbox = QGroupBox("Type of scheduler") self.groupbox.setFont(QtGui.QFont("sanserif", 15)) self.hbox.addWidget(self.groupbox) self.vbox = QVBoxLayout() self.FCFS = QRadioButton("FCFS") self.vbox.addWidget(self.FCFS) self.SJF = QRadioButton("SJF") self.vbox.addWidget(self.SJF) self.RR = QRadioButton("RR") self.vbox.addWidget(self.RR) self.pri = QRadioButton("Priority") self.vbox.addWidget(self.pri) self.button = QPushButton("Next", self) self.button.clicked.connect(self.next) self.vbox.addWidget(self.button) self.groupbox.setLayout(self.vbox) self.i = 0 def next(self): self.SJF.hide() self.FCFS.hide() self.RR.hide() self.pri.hide() self.pree = QCheckBox('Preemptive') self.nonpree = QCheckBox('Non-Preemptive') if self.SJF.isChecked(): self.label = QLabel("SJF") self.label.setFont(QtGui.QFont("sanserif", 20)) self.vbox.addWidget(self.label) self.vbox.addWidget(self.pree) self.vbox.addWidget(self.nonpree) elif self.FCFS.isChecked(): self.label = QLabel("FCFS") self.label.setFont(QtGui.QFont("sanserif", 20)) self.vbox.addWidget(self.label) elif self.RR.isChecked(): self.label = QLabel("RR") self.label.setFont(QtGui.QFont("sanserif", 20)) self.vbox.addWidget(self.label) elif self.pri.isChecked(): self.label = QLabel("Priority") self.label.setFont(QtGui.QFont("sanserif", 20)) self.vbox.addWidget(self.label) self.vbox.addWidget(self.pree) self.vbox.addWidget(self.nonpree) if self.i == 0: self.button.hide() self.labelProcess = QLabel("Number of process") self.processBox = QSpinBox(self) self.vbox.addWidget(self.labelProcess) self.vbox.addWidget(self.processBox) self.button = QPushButton("Next", self) self.button.clicked.connect(self.nextPressed) self.vbox.addWidget(self.button) self.i = 5 def nextPressed(self): self.processBox.hide() i = self.processBox.text() self.labelProcess.setText("Number of process = " + i) i = int(i, 10) self.tList = list() self.lList = list() self.timeShots = list() self.timeInserted = list() self.pirority = list() self.groupbox2 = QGroupBox("Process's info") self.groupbox2.setFont(QtGui.QFont("sanserif", 15)) self.vbox2 = QVBoxLayout() if self.nonpree.isChecked(): self.pree.hide() self.nonpree.hide() self.label = QLabel("Type : " + self.nonpree.text()) self.label.setFont(QtGui.QFont("sanserif", 15)) self.vbox2.addWidget(self.label) elif self.pree.isChecked(): self.pree.hide() self.nonpree.hide() self.label = QLabel("Type : " + self.pree.text()) self.label.setFont(QtGui.QFont("sanserif", 15)) self.vbox2.addWidget(self.label) for j in range(i): self.label = QLabel("P" + str(j + 1)) self.lList.append(self.label) self.label.setFont(QtGui.QFont("sanserif", 15)) self.vbox2.addWidget(self.label) self.label = QLabel("Burst Time") self.timeShots.append(self.label) self.label.setFont(QtGui.QFont("sanserif", 13)) self.textbox = QSpinBox(self) self.tList.append(self.textbox) self.vbox2.addWidget(self.label) self.vbox2.addWidget(self.textbox) if not (self.pri.isChecked() and self.nonpree.isChecked()): self.label = QLabel("Arrival Time:") self.timeShots.append(self.label) self.label.setFont(QtGui.QFont("sanserif", 13)) self.vbox2.addWidget(self.label) self.textbox = QSpinBox(self) self.timeInserted.append(self.textbox) self.vbox2.addWidget(self.textbox) if self.pri.isChecked(): self.label = QLabel( "Priority (low number is higher in priority)") self.timeShots.append(self.label) self.label.setFont(QtGui.QFont("sanserif", 13)) self.textbox = QSpinBox(self) self.pirority.append(self.textbox) self.vbox2.addWidget(self.label) self.vbox2.addWidget(self.textbox) if self.RR.isChecked() or (self.pri.isChecked() and self.nonpree.isChecked()): self.label = QLabel("Time Quantum:") self.label.setFont(QtGui.QFont("sanserif", 15)) self.timeShots.append(self.label) self.vbox2.addWidget(self.label) self.textbox = QSpinBox(self) self.tList.append(self.textbox) self.vbox2.addWidget(self.textbox) self.button.hide() self.button = QPushButton("Draw", self) self.button.clicked.connect(self.Draw) self.vbox2.addWidget(self.button) self.groupbox2.setLayout(self.vbox2) self.scroll = QScrollArea() self.scroll.setWidget(self.groupbox2) self.scroll.setWidgetResizable(True) self.scroll.setFixedWidth(600) self.hbox.addWidget(self.scroll) def Draw(self): df = list() self.button.hide() self.button = QPushButton("Restart", self) self.button.clicked.connect(self.restart) self.vbox.addWidget(self.button) numberList = list() nameList = list() processList = list() inserted = list() pirority = list() for i in self.timeShots: i.hide() for i in self.lList: i.hide() nameList.append(i.text()) for i in self.tList: i.hide() numberList.append(i.value()) for i in self.timeInserted: i.hide() inserted.append(i.value()) for i in self.pirority: i.hide() pirority.append(i.value()) if self.SJF.isChecked() and self.nonpree.isChecked(): for i in range(len(numberList)): process = { 'name': nameList[i], 'Tburst': numberList[i], 'TimeInserted': inserted[i], 'waiting': 0 } processList.append(process) SortedArrival = sorted(processList, key=itemgetter('TimeInserted'), reverse=False) SortedProcess = sorted(processList, key=itemgetter('Tburst'), reverse=False) timeinserted = 0 for p in SortedProcess: timeinserted = timeinserted + p['TimeInserted'] if timeinserted == 0: start = 0 waiting = 0 for i in SortedProcess: df.append( dict(Task=i['name'], Start=start, Finish=i['Tburst'] + start)) waiting = waiting + (start) start = i['Tburst'] + start self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedProcess)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) plot(fig) else: sum = 1 min = 100 index = 0 start = SortedArrival[0]['TimeInserted'] time = SortedArrival[0]['TimeInserted'] while sum > 0: for i in range(len(SortedArrival)): print("in the for loop") if i == index: df.append( dict(Task=SortedArrival[i]['name'], Start=start, Finish=start + SortedArrival[i]['Tburst'])) SortedArrival[i][ 'waiting'] = start - SortedArrival[i][ 'TimeInserted'] time = start + SortedArrival[i]['Tburst'] start = time SortedArrival[i]['Tburst'] = 0 min = 100 for p in range(len(SortedArrival)): if SortedArrival[p][ 'TimeInserted'] <= time and SortedArrival[ p]['Tburst'] < min and SortedArrival[ p]['Tburst'] > 0: index = p min = SortedArrival[p]['Tburst'] sum = 0 for p in SortedArrival: sum = sum + p['Tburst'] waiting = 0 for p in SortedArrival: waiting = waiting + p['waiting'] self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedArrival)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) plot(fig) elif self.SJF.isChecked() and self.pree.isChecked(): for i in range(len(numberList)): process = { 'name': nameList[i], 'Tburst': numberList[i], 'TimeInserted': inserted[i], 'waiting': 0, 'finished': inserted[i] } processList.append(process) SortedArrival = sorted(processList, key=itemgetter('TimeInserted'), reverse=False) SortedBurst = sorted(processList, key=itemgetter('Tburst'), reverse=False) sum = 1 start = SortedArrival[0]['TimeInserted'] k = 0 time = SortedArrival[0]['TimeInserted'] min = 100 while sum > 0: for i in range(len(SortedArrival)): if SortedArrival[i][ 'TimeInserted'] <= time and SortedArrival[i][ 'Tburst'] < min and SortedArrival[i][ 'Tburst'] > 0: if time > SortedArrival[0]['TimeInserted']: df.append( dict(Task=SortedArrival[index]['name'], Start=start, Finish=time)) SortedArrival[index]['finished'] = time start = time SortedArrival[index][ 'Tburst'] = SortedArrival[index]['Tburst'] - k k = 0 index = i SortedArrival[index][ 'waiting'] = SortedArrival[index]['waiting'] + ( time - SortedArrival[index]['finished']) min = SortedArrival[index]['Tburst'] time = time + 1 k = k + 1 else: SortedArrival[index][ 'Tburst'] = SortedArrival[index]['Tburst'] - 1 if SortedArrival[index]['Tburst'] == 0: df.append( dict(Task=SortedArrival[index]['name'], Start=start, Finish=time)) start = time k = 0 min = 100 found = 0 for j in range(len(SortedArrival)): if SortedArrival[j][ 'TimeInserted'] <= time and SortedArrival[ j]['Tburst'] < min and SortedArrival[ j]['Tburst'] > 0: min = SortedArrival[j]['Tburst'] index = j found = 1 if found == 1: SortedArrival[index][ 'waiting'] = SortedArrival[index][ 'waiting'] + ( time - SortedArrival[index]['finished']) else: min = SortedArrival[index]['Tburst'] time = time + 1 k = k + 1 if SortedArrival[i][ 'TimeInserted'] <= time and SortedArrival[i][ 'Tburst'] < min and SortedArrival[i][ 'Tburst'] > 0: df.append( dict(Task=SortedArrival[index]['name'], Start=start, Finish=time)) SortedArrival[index]['finished'] = time start = time SortedArrival[index]['Tburst'] = SortedArrival[ index]['Tburst'] - k + 1 k = 0 index = i SortedArrival[index]['waiting'] = SortedArrival[ index]['waiting'] + ( time - SortedArrival[index]['finished']) min = SortedArrival[index]['Tburst'] time = time + 1 k = k + 1 sum = 0 for p in SortedArrival: sum = sum + p['Tburst'] waiting = 0 for p in SortedArrival: waiting = waiting + p['waiting'] self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedArrival)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) plot(fig) elif self.FCFS.isChecked(): for i in range(len(numberList)): process = { 'name': nameList[i], 'Tburst': numberList[i], 'TimeInserted': inserted[i] } processList.append(process) SortedProcess = sorted(processList, key=itemgetter('TimeInserted'), reverse=False) i = 0 waiting = 0 start = SortedProcess[0]['TimeInserted'] for i in SortedProcess: if start < i['TimeInserted']: start = i['TimeInserted'] df.append( dict(Task=i['name'], Start=start, Finish=i['Tburst'] + start)) waiting = waiting + (start - i['TimeInserted']) start = i['Tburst'] + start self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedProcess)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) plot(fig) elif self.RR.isChecked(): queue = list() timeSlice = numberList[-1] processList = list() sum = 1 for i in range(len(numberList) - 1): process = { 'name': nameList[i], 'Tburst': numberList[i], 'TimeInserted': inserted[i], 'waiting': 0, 'finished': inserted[i] } processList.append(process) SortedProcess = sorted(processList, key=itemgetter('TimeInserted'), reverse=False) time = SortedProcess[0]['TimeInserted'] start = SortedProcess[0]['TimeInserted'] queue.append(SortedProcess[0]) i = 0 while (sum > 0): if len(queue) > 0: if queue[0]['TimeInserted'] <= time: if queue[0]['Tburst'] > timeSlice: df.append( dict(Task=queue[0]['name'], Start=time, Finish=timeSlice + time)) if time != queue[0]['finished']: queue[0]['waiting'] = queue[0]['waiting'] + ( time - queue[0]['finished']) elif queue[0]['name'] == SortedProcess[0]['name']: queue[0]['waiting'] = queue[0]['waiting'] + ( time - queue[0]['finished']) queue[0]['finished'] = timeSlice + time queue[0]['Tburst'] = queue[0]['Tburst'] - timeSlice z = queue[0] time = timeSlice + time # queue.pop(0) for j in SortedProcess: if j['name'] == z['name']: j['Tburst'] = z['Tburst'] j['finished'] = z['finished'] j['waiting'] = z['waiting'] for j in SortedProcess: found = 0 for p in queue: if j['name'] == p['name']: found = 1 break if found == 1: continue else: if j['Tburst'] > 0 and j[ 'TimeInserted'] <= time: queue.append(j) queue.pop(0) queue.append(z) else: df.append( dict(Task=queue[0]['name'], Start=time, Finish=queue[0]['Tburst'] + time)) if time != queue[0]['finished']: queue[0]['waiting'] = queue[0]['waiting'] + ( time - queue[0]['finished']) elif queue[0]['name'] == SortedProcess[0]['name']: queue[0]['waiting'] = queue[0]['waiting'] + ( time - queue[0]['finished']) time = queue[0]['Tburst'] + time queue[0]['Tburst'] = 0 z = queue[0] queue.pop(0) for j in SortedProcess: if j['name'] == z['name']: j['Tburst'] = 0 j['finished'] = z['finished'] j['waiting'] = z['waiting'] for j in SortedProcess: found = 0 for p in queue: if j['name'] == p['name']: found = 1 break if found == 1: continue else: if j['Tburst'] > 0 and j[ 'TimeInserted'] <= time: queue.append(j) else: time = time + 1 for j in SortedProcess: found = 0 for p in queue: if j['name'] == p['name']: found = 1 break if found == 1: continue else: if j['Tburst'] > 0 and j['TimeInserted'] <= time: queue.append(j) print(queue) sum = 0 for k in SortedProcess: sum = sum + k['Tburst'] print(sum) waiting = 0 for i in SortedProcess: waiting = waiting + i['waiting'] self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedProcess)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) plot(fig) elif self.pri.isChecked() and self.nonpree.isChecked(): timeSlice = numberList[-1] print(timeSlice) for i in range(len(numberList) - 1): process = { 'name': nameList[i], 'Tburst': numberList[i], 'TimeInserted': 0, 'pri': pirority[i], 'flag': 0, 'waiting': 0, 'finished': 0 } processList.append(process) SortedProcess = sorted(processList, key=itemgetter('pri'), reverse=False) duplicateList = list() i = 0 while i < len(SortedProcess): pairList = list() if SortedProcess[i]['flag'] == 0: pairList.append(SortedProcess[i]) SortedProcess[i]['flag'] = 1 for j in range(i + 1, len(SortedProcess)): if (SortedProcess[j]['pri'] == SortedProcess[i]['pri'] ) and SortedProcess[j]['flag'] == 0: pairList.append(SortedProcess[j]) SortedProcess[j]['flag'] = 1 else: continue duplicateList.append(pairList) i = i + 1 else: i = i + 1 start = 0 waiting = 0 for m in duplicateList: if len(m) == 1: df.append( dict(Task=m[0]['name'], Start=start, Finish=m[0]['Tburst'] + start)) waiting = waiting + (start - m[0]['TimeInserted']) start = m[0]['Tburst'] + start else: sum = 0 for j in m: sum = sum + j['Tburst'] i = 0 while (sum > 0): for i in range(len(m)): if m[i]['Tburst'] > 0: if m[i]['Tburst'] > timeSlice: df.append( dict(Task=m[i]['name'], Start=start, Finish=timeSlice + start)) if start != m[i]['finished']: m[i]['waiting'] = m[i]['waiting'] + ( start - m[i]['finished']) m[i]['finished'] = timeSlice + start m[i]['TimeInserted'] = timeSlice + start start = timeSlice + start m[i]['Tburst'] = m[i]['Tburst'] - timeSlice else: df.append( dict(Task=m[i]['name'], Start=start, Finish=m[i]['Tburst'] + start)) if start != m[i]['finished']: m[i]['waiting'] = m[i]['waiting'] + ( start - m[i]['finished']) m[i]['finished'] = timeSlice + start m[i]['TimeInserted'] = m[i][ 'Tburst'] + start start = m[i]['Tburst'] + start m[i]['Tburst'] = m[i]['Tburst'] - timeSlice sum = 0 for k in range(len(m)): sum = sum + m[k]['Tburst'] for k in range(len(m)): waiting = waiting + m[k]['waiting'] self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedProcess)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) # plot(fig) elif self.pri.isChecked() and self.pree.isChecked(): for i in range(len(numberList)): process = { 'name': nameList[i], 'Tburst': numberList[i], 'TimeInserted': inserted[i], 'waiting': 0, 'pri': pirority[i], 'finished': inserted[i] } processList.append(process) SortedArrival = sorted(processList, key=itemgetter('TimeInserted'), reverse=False) sum = 1 start = SortedArrival[0]['TimeInserted'] k = 0 time = SortedArrival[0]['TimeInserted'] min = 100 while sum > 0: for i in range(len(SortedArrival)): if SortedArrival[i][ 'TimeInserted'] <= time and SortedArrival[i][ 'pri'] < min and SortedArrival[i]['Tburst'] > 0: if time > SortedArrival[0]['TimeInserted']: df.append( dict(Task=SortedArrival[index]['name'], Start=start, Finish=time)) SortedArrival[index]['finished'] = time start = time SortedArrival[index][ 'Tburst'] = SortedArrival[index]['Tburst'] - k k = 0 index = i SortedArrival[index][ 'waiting'] = SortedArrival[index]['waiting'] + ( time - SortedArrival[index]['finished']) min = SortedArrival[index]['pri'] time = time + 1 k = k + 1 else: SortedArrival[index][ 'Tburst'] = SortedArrival[index]['Tburst'] - 1 if SortedArrival[index]['Tburst'] == 0: df.append( dict(Task=SortedArrival[index]['name'], Start=start, Finish=time)) start = time k = 0 min = 100 found = 0 for j in range(len(SortedArrival)): if SortedArrival[j][ 'TimeInserted'] <= time and SortedArrival[ j]['pri'] < min and SortedArrival[ j]['Tburst'] > 0: min = SortedArrival[j]['pri'] index = j found = 1 if found == 1: SortedArrival[index][ 'waiting'] = SortedArrival[index][ 'waiting'] + ( time - SortedArrival[index]['finished']) else: min = SortedArrival[index]['pri'] time = time + 1 k = k + 1 if SortedArrival[i][ 'TimeInserted'] <= time and SortedArrival[i][ 'pri'] < min and SortedArrival[i][ 'Tburst'] > 0: df.append( dict(Task=SortedArrival[index]['name'], Start=start, Finish=time)) SortedArrival[index]['finished'] = time start = time SortedArrival[index]['Tburst'] = SortedArrival[ index]['Tburst'] - k + 1 k = 0 index = i SortedArrival[index]['waiting'] = SortedArrival[ index]['waiting'] + ( time - SortedArrival[index]['finished']) min = SortedArrival[index]['pri'] time = time + 1 k = k + 1 sum = 0 for p in SortedArrival: sum = sum + p['Tburst'] waiting = 0 for p in SortedArrival: waiting = waiting + p['waiting'] print(p['waiting']) self.labelTime = QLabel("Average waiting time : " + str(waiting / len(SortedArrival)) + " ms") self.vbox.addWidget(self.labelTime) fig = ff.create_gantt(df, show_colorbar=True, group_tasks=True, showgrid_x=True, showgrid_y=True) fig['layout']['xaxis'].update({'type': None}) plot(fig) def restart(self): self.button.hide() self.labelTime.hide() self.groupbox.hide() self.scroll.hide() self.initBox()