class GameWidget(QGraphicsView): def __init__(self, parent=None): super(GameWidget, self).__init__(parent) self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.m = 150 self.n = 150 self.scene = QGraphicsScene(self) self.setScene(self.scene) self.scene.setSceneRect(0, 0, self.width(), self.height()) self.setAlignment(Qt.AlignLeft | Qt.AlignTop) self.universe = engine.Universe(self.n, self.m) print(Qt.red) self.timer = QTimer(self) self.timer.timeout.connect(self.step) def load(self, item): self.universe.file_input(item) def drawUniverse(self): width = self.width() height = self.height() cellWidth = width / self.universe.n cellHeight = height / self.universe.m x = 0 y = 0 for this_list in self.universe.map: y = 0 for elem in this_list: color = Qt.gray if elem == 1: color = Qt.green self.scene.addRect(x, y, cellWidth, cellHeight, brush=color) y += cellHeight x += cellWidth def step(self): self.scene.clear() self.universe.step() self.drawUniverse() self.scene.update() def run(self): self.timer.start() def stop(self): self.timer.stop()
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.dibujar.clicked.connect(self.dibujar) self.ui.limpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) def wheelEvent(self, event): print(event.delta()) if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def dibujar(self): print('dibujar') pen = QPen() pen.setWidth(2) for i in range(0, 100): r = randint(0, 255) g = randint(0, 255) b = randint(0, 255) color = QColor(r, g, b) pen.setColor(color) x_origen = randint(0, 500) y_origen = randint(0, 500) x_destin = randint(0, 500) y_destin = randint(0, 500) self.scene.addEllipse(x_origen, y_origen, 6, 6, pen) self.scene.addEllipse(x_destin, y_destin, 6, 6, pen) self.scene.addLine(x_origen + 3, y_origen + 3, x_destin + 3, y_destin + 3, pen) @Slot() def limpiar(self): print('limpiar') self.scene.clear() self.ui.graphicsView.setTransform(QTransform())
class CaptchaDialogue(QDialog): def __init__(self, *args, **kwargs): super(CaptchaDialogue, self).__init__(*args, **kwargs) self.ui = ui.CaptchaDialogue() self.ui.setupUi(self) self.captcha_generator = ImageCaptcha() self.scene = QGraphicsScene() self.ui.captcha_view.setScene(self.scene) self.text = None self.ui.buttons.accepted.connect(self.accept) self.ui.buttons.rejected.connect(self.reject) def open(self): self.generate_captcha() super().open() def done(self, result: QDialog.DialogCode): if result == QDialog.Accepted and self.ui.captcha_input.text( ) != self.text: self.ui.input_label.setText("Incorrect CAPTCHA given. Try again:") self.ui.input_label.setStyleSheet("color: red") self.generate_captcha() else: self.ui.input_label.setText( "Enter the characters displayed above:") self.ui.input_label.setStyleSheet("") self.ui.captcha_input.clear() super().done(result) def generate_captcha(self): self.text = self._generate_text() image_bytes = self.captcha_generator.generate(self.text).getvalue() image = QByteArray(image_bytes) pixmap = QPixmap() pixmap.loadFromData(image, "png") self.scene.clear() self.scene.addPixmap(pixmap) @staticmethod def _generate_text() -> str: """Return a string of random characters to be used for CAPTCHA generation.""" sample = random.sample(CHARACTERS, 6) return "".join(sample)
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.dibujar.clicked.connect(self.dibujar) self.ui.limpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def dibujar(self): pen = QPen() pen.setWidth(2) for i in range(200): r = randint(0, 255) g = randint(0, 255) b = randint(0, 255) color = QColor(r, g, b) pen.setColor(color) origen_x = randint(0, 500) origen_y = randint(0, 500) destino_x = randint(0, 500) destino_y = randint(0, 500) self.scene.addEllipse(origen_x, origen_y, 3, 3, pen) self.scene.addEllipse(destino_x, destino_y, 3, 3, pen) self.scene.addLine(origen_x+3, origen_y+3, destino_x, destino_y, pen) @Slot() def limpiar(self): self.scene.clear()
class ImageViewer(QWidget): def __init__(self, parent): super().__init__() self.parent = parent self.scene = QGraphicsScene() self.view = QGraphicsView(self.scene) layout = QVBoxLayout() layout.addWidget(self.view) self.img_width = None self.img_height = None self.setLayout(layout) def load_image(self, image_arr): self.clear() image_path = QImage(image_arr, image_arr.shape[1], image_arr.shape[0], QImage.Format_RGB888) pixmap = QPixmap(image_path) self.scene.addPixmap(pixmap) self.img_width = pixmap.width() self.img_height = pixmap.height() self.scale_self() self.scene.update() def scale_self(self): if self.img_width is not None: self.view.fitInView(QRectF(0, 0, self.img_width, self.img_height), Qt.KeepAspectRatio) self.view.scale(self.img_width / self.scene.width(), self.img_height / self.scene.height()) def clear(self): self.scene.clear()
class TimeLineLabelView(QGraphicsView): def __init__(self, parent=None): super(TimeLineLabelView, self).__init__(parent) self.x = 0 self.y = 0 self.m_originX = 0 self.m_originY = 0 self.label_height = 10 self.frame_width = 10 self.time_line_length = 10 self.label_width = 80 self.zoom_factor = 0.0001 self._min_scale_factor = 0.01 self.scale_factor = 1.0 self.time_lines = dict() self.setInteractive(True) self.setDragMode(drag_mode) self.setSceneRect(0, 0, self.time_line_length, self.label_height) self.labels = [] self.setTransformationAnchor( transform_anchor ) # needs to be set to 0 to allow view transform changes https://bugreports.qt.io/browse/QTBUG- self.frame_indicator = None self.edit_start_frame_indicator = None self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff) def create_frame_indicator(self): size = QSizeF() height = 100 size.setHeight(height) size.setWidth(self.label_height) self.frame_indicator = FrameIndicator(size, self.frame_width, self.label_width, 0) self._label_scene.addItem(self.frame_indicator) self.edit_start_frame_indicator = FrameIndicator( size, self.frame_width, self.label_width, 0, blue) self._label_scene.addItem(self.edit_start_frame_indicator) def initScene(self): brush = QBrush() color = QColor() color.setGreen(255) color.setAlpha(255) brush.setColor(color) self._label_scene = QGraphicsScene() self._label_scene.setBackgroundBrush(grey) #self._label_scene.setForegroundBrush(color) self.setScene(self._label_scene) def clearScene(self): self.labels = [] self.time_lines = dict() self._label_scene.clear() def setTimeLineParameters(self, time_line_length, label_height): self.label_height = label_height self.time_line_length = self.frame_width * time_line_length def addLabel(self, l, indices, color): y = len(self.labels) * self.label_height pos = QPointF(0, y) label = l timeline = TimeLine(label, indices, pos, self.time_line_length, self.label_height, self.label_width, self.frame_width, color) self._label_scene.addItem(timeline) self.time_lines[label] = timeline self.labels.append(l) self.setSceneRect(0, 0, self.time_line_length, self.label_height * len(self.labels)) def mousePressEvent(self, event): if event.button() == Qt.LeftButton: self.m_originX = event.x() self.m_originY = event.y() def mouseMoveEvent(self, event): if event.buttons() and Qt.LeftButton: deltaX = event.x() - self.m_originX deltaY = event.y() - self.m_originY #self.translate(deltaX, deltaY) self.x += deltaX self.y += deltaY self.updateTransform() self.m_originX = event.x() self.m_originY = event.y() def wheelEvent(self, event): self.scale_factor += event.angleDelta().y() * self.zoom_factor self.scale_factor = max(self._min_scale_factor, self.scale_factor) self.updateTransform() def setFrame(self, idx): self.x = self.scale_factor * -idx * self.frame_width + self.label_width #transform = Qt.QTransform() #transform.translate(-deltaX, 0) #self.setTransform(transform) self.updateTransform() if self.frame_indicator is not None: self.frame_indicator.setFrame(idx) def set_edit_start_frame(self, idx): if self.edit_start_frame_indicator is not None: self.edit_start_frame_indicator.setFrame(idx) def updateTransform(self): if self.x > 0: self.x = 0 self.resetTransform() m = QTransform() m.translate(self.x, self.y) m.scale(self.scale_factor, 1.0) self.setTransform(m)
class Widget(QWidget): def __init__(self): QWidget.__init__(self) #Paths self.folderPath = "../Crop_Reports/Bengal Crop Reports PNG/" self.index = 0 self.page_index = 0 self.crop_report = "" self.pixmap = QPixmap() self.data = pd.read_csv("../Crop_Reports/Manual Check Crop Reports/crop_reports_verified.csv") #choices self.choices = listdir(self.folderPath) self.scene = QGraphicsScene() self.image = QGraphicsView(self.scene) self.image.show() self.submitButton = QPushButton("Submit") self.dateText = QLineEdit("") self.middle = QVBoxLayout() self.middle.setMargin(10) self.middle.addWidget(self.image) self.middle.addWidget(self.dateText) self.middle.addWidget(self.submitButton) # QWidget Layout self.layout = QHBoxLayout() self.layout.addLayout(self.middle) # Set the layout to the QWidget self.setLayout(self.layout) # Here we connect widgets to functions self.submitButton.clicked.connect(self.submit) # Here we add functions @Slot() def submit(self): self.index = self.index+1 self.scene.clear() temp_path = self.choices[self.index] self.crop_report_pages = os.listdir(temp_path) self.pixmap = QPixmap(temp_path) self.scene.addPixmap(self.pixmap) @Slot() def nextPage(self): self.page_index = self.page_index + 1
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.administra = Administrador() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.AgFinal_pushButton.clicked.connect(self.click_capturar) self.ui.AgInicio_pushButton.clicked.connect(self.click_capturar_Inicio) self.ui.Mostrar_pushButton.clicked.connect(self.click_mostrar) self.ui.actionAbrir.triggered.connect(self.actio_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.actio_guardar_archivo) self.ui.actionPor_ID.triggered.connect(self.Ordenar_ID) self.ui.actionPor_Distancia.triggered.connect(self.Ordenar_Distancia) self.ui.actionPor_Velocidad.triggered.connect(self.Ordenar_Velocida) self.ui.Mostrar_Tabla_PushButton.clicked.connect(self.mostrar_tabla) self.ui.Buscar_Tabla_PushButton.clicked.connect(self.buscar_id) self.ui.Dibujar_dibujo_pushButton.clicked.connect(self.Dibujar_part) self.ui.Limpiar_dibujo_pushButton.clicked.connect(self.Limpiar_part) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) self.sceneG = QGraphicsScene() self.ui.Grafo_graphicsView.setScene(self.sceneG) self.ui.Grafo_L_pushButton.clicked.connect(self.Limpiar_Grafo) self.ui.Grafo_M_pushButton.clicked.connect(self.Mostrar_Grafo) self.ui.Busqueda_pushButton.clicked.connect(self.Buscar_Grafo) @Slot() def Buscar_Grafo(self): self.ui.Busquedas_plainTextEdit.clear() grafo = dict() for particula in self.administra: o_x = str(particula.origen_x).upper() o_y = str(particula.origen_y).upper() d_x = str(particula.destino_x).upper() d_y = str(particula.destino_y).upper() origen = o_x, o_y destino = d_x, d_y if origen in grafo: grafo[origen].append(destino) else: grafo[origen] = [destino] if destino in grafo: grafo[destino].append(origen) else: grafo[destino] = [origen] UbicX = self.ui.Busqueda_x_spinBox.value() UbicY = self.ui.Busqued_y_spinBox.value() Ubicacion_X = str(UbicX).upper() Ubicacion_Y = str(UbicY).upper() Ubicacion = Ubicacion_X, Ubicacion_Y if Ubicacion in grafo: adyacencia = Ubicacion visitados = [] pila = deque() recorrido = [] visitados.append(adyacencia) pila.append(adyacencia) while len(pila) != 0: vertice = pila[-1] recorrido.append(vertice) pila.pop() for ady in grafo[vertice]: if ady not in visitados: visitados.append(ady) pila.append(ady) self.ui.Busquedas_plainTextEdit.insertPlainText('Profundidad\n') for parte in recorrido: self.ui.Busquedas_plainTextEdit.insertPlainText(str(parte)) self.ui.Busquedas_plainTextEdit.insertPlainText('\n') self.ui.Busquedas_plainTextEdit.insertPlainText('\n\n') adyacencia2 = Ubicacion visitados2 = [] cola = deque() recorrido2 = [] visitados2.append(adyacencia2) cola.append(adyacencia2) while len(cola) != 0: vertice2 = cola[0] recorrido2.append(vertice2) cola.popleft() for ady2 in grafo[vertice2]: if ady2 not in visitados2: visitados2.append(ady2) cola.append(ady2) self.ui.Busquedas_plainTextEdit.insertPlainText('Amplitud\n') for parte in recorrido2: self.ui.Busquedas_plainTextEdit.insertPlainText(str(parte)) self.ui.Busquedas_plainTextEdit.insertPlainText('\n') else: QMessageBox.critical(self, "Error", "Esta ubicacion no se encuentra en el grafo") @Slot() def Mostrar_Grafo(self): grafo = dict() for particula in self.administra: o_x = str(particula.origen_x).upper() o_y = str(particula.origen_y).upper() d_x = str(particula.destino_x).upper() d_y = str(particula.destino_y).upper() peso = int(particula.distancia) origen = o_x, o_y destino = d_x, d_y arista_o_d = (destino, peso) arista_d_o = (origen, peso) if origen in grafo: grafo[origen].append(arista_o_d) else: grafo[origen] = [arista_o_d] if destino in grafo: grafo[destino].append(arista_d_o) else: grafo[destino] = [arista_d_o] strn = pformat(grafo, width=40, indent=1) for particula in self.administra: pen = QPen() pen.setWidth(2) color = QColor(particula.red, particula.green, particula.blue) pen.setColor(color) self.sceneG.addEllipse(particula.origen_x, particula.origen_y, 3, 3, pen) self.sceneG.addEllipse(particula.destino_x, particula.destino_y, 3, 3, pen) self.sceneG.addLine(particula.origen_x + 3, particula.origen_y + 3, particula.destino_x, particula.destino_y, pen) self.ui.Grafo_plainTextEdit.clear() self.ui.Grafo_plainTextEdit.insertPlainText(strn) @Slot() def Limpiar_Grafo(self): self.sceneG.clear() self.ui.Grafo_plainTextEdit.clear() @Slot() def Dibujar_part(self): for particula in self.administra: pen = QPen() pen.setWidth(2) color = QColor(particula.red, particula.green, particula.blue) pen.setColor(color) self.scene.addEllipse(particula.origen_x, particula.origen_y, 3, 3, pen) self.scene.addEllipse(particula.destino_x, particula.destino_y, 3, 3, pen) self.scene.addLine(particula.origen_x + 3, particula.origen_y + 3, particula.destino_x, particula.destino_y, pen) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) if event.delta() > 0: self.ui.Grafo_graphicsView.scale(1.2, 1.2) else: self.ui.Grafo_graphicsView.scale(0.8, 0.8) @Slot() def Limpiar_part(self): self.scene.clear() @Slot() def buscar_id(self): identificador = self.ui.Buscar_Tabla_lineEdit.text() Encontrado = False for particula in self.administra: if identificador == str(particula.ide): self.ui.Tabla.clear() self.ui.Tabla.setRowCount(1) ide_widget = QTableWidgetItem(str(particula.ide)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) distancia_widget = QTableWidgetItem(str(particula.distancia)) red_widget = QTableWidgetItem(str(particula.red)) green_widget = QTableWidgetItem(str(particula.green)) blue_widget = QTableWidgetItem(str(particula.blue)) self.ui.Tabla.setItem(0, 0, ide_widget) self.ui.Tabla.setItem(0, 1, origen_x_widget) self.ui.Tabla.setItem(0, 2, origen_y_widget) self.ui.Tabla.setItem(0, 3, destino_x_widget) self.ui.Tabla.setItem(0, 4, destino_y_widget) self.ui.Tabla.setItem(0, 5, velocidad_widget) self.ui.Tabla.setItem(0, 6, distancia_widget) self.ui.Tabla.setItem(0, 7, red_widget) self.ui.Tabla.setItem(0, 8, green_widget) self.ui.Tabla.setItem(0, 9, blue_widget) Encontrado = True return if not Encontrado: QMessageBox.warning( self, "Atencion", "La particula con identificador " + identificador + " no fue encontrada") @Slot() def mostrar_tabla(self): self.ui.Tabla.setColumnCount(10) headers = [ "ID", "Origen_X", "Origen_Y", "Destino_X", "Destino_Y", "Velocidad", "Distancia", "Red", "Green", "Blue" ] self.ui.Tabla.setHorizontalHeaderLabels(headers) self.ui.Tabla.setRowCount(len(self.administra)) row = 0 for particula in self.administra: ide_widget = QTableWidgetItem(str(particula.ide)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) distancia_widget = QTableWidgetItem(str(particula.distancia)) red_widget = QTableWidgetItem(str(particula.red)) green_widget = QTableWidgetItem(str(particula.green)) blue_widget = QTableWidgetItem(str(particula.blue)) self.ui.Tabla.setItem(row, 0, ide_widget) self.ui.Tabla.setItem(row, 1, origen_x_widget) self.ui.Tabla.setItem(row, 2, origen_y_widget) self.ui.Tabla.setItem(row, 3, destino_x_widget) self.ui.Tabla.setItem(row, 4, destino_y_widget) self.ui.Tabla.setItem(row, 5, velocidad_widget) self.ui.Tabla.setItem(row, 6, distancia_widget) self.ui.Tabla.setItem(row, 7, red_widget) self.ui.Tabla.setItem(row, 8, green_widget) self.ui.Tabla.setItem(row, 9, blue_widget) row += 1 @Slot() def actio_abrir_archivo(self): ubicacion = QFileDialog.getOpenFileName(self, 'Abrir Archivo', '.', 'JSON (*.json)')[0] if self.administra.abrir(ubicacion): QMessageBox.information(self, "Exito", "Se abrio el archivo " + ubicacion) else: QMessageBox.critical(self, "Error", "Error al abrir el archivo " + ubicacion) @Slot() def actio_guardar_archivo(self): ubicacion = QFileDialog.getSaveFileName(self, 'Guardar Archivo', '.', 'JSON (*.json)')[0] print(ubicacion) if self.administra.guardar(ubicacion): QMessageBox.information(self, "Exito", "Se pudo crear el archivo " + ubicacion) else: QMessageBox.critical(self, "Error", "No se pud crear el archivo " + ubicacion) @Slot() def Ordenar_ID(self): self.administra.ordenar() @Slot() def Ordenar_Distancia(self): self.administra.ordenar_distancia() @Slot() def Ordenar_Velocida(self): self.administra.ordenar_velocidad() @Slot() def click_mostrar(self): self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText(str(self.administra)) @Slot() def click_capturar(self): Ide = self.ui.ID_spinBox.value() OrigenX = self.ui.OrigenX_spinBox.value() OrigenY = self.ui.OrigenY_spinBox.value() DestinoX = self.ui.DestinoX_spinBox.value() DestinoY = self.ui.DestinoY_spinBox.value() Velocidad = self.ui.Velocidad_spinBox.value() Red = self.ui.ColorRed_spinBox.value() Green = self.ui.ColorGreen_spinBox.value() Blue = self.ui.ColorBlue_spinBox.value() particula = Particula(Ide, OrigenX, OrigenY, DestinoX, DestinoY, Velocidad, Red, Green, Blue) self.administra.agregar_final(particula) @Slot() def click_capturar_Inicio(self): Ide = self.ui.ID_spinBox.value() OrigenX = self.ui.OrigenX_spinBox.value() OrigenY = self.ui.OrigenY_spinBox.value() DestinoX = self.ui.DestinoX_spinBox.value() DestinoY = self.ui.DestinoY_spinBox.value() Velocidad = self.ui.Velocidad_spinBox.value() Red = self.ui.ColorRed_spinBox.value() Green = self.ui.ColorGreen_spinBox.value() Blue = self.ui.ColorBlue_spinBox.value() particula = Particula(Ide, OrigenX, OrigenY, DestinoX, DestinoY, Velocidad, Red, Green, Blue) self.administra.agregar_inicio(particula)
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.AlmacenP = AlmacenDeParticulas() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.AgregarFinal.clicked.connect(self.click_agregar) self.ui.AgregarInicio.clicked.connect(self.click_agregarInicio) self.ui.Mostrar.clicked.connect(self.click_mostrar) self.ui.actionAbrir.triggered.connect(self.action_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.action_guardar_archivo) self.ui.Mostrar_Tabla_Boton.clicked.connect(self.mostrar_tabla) self.ui.Buscar_Boton.clicked.connect(self.buscar_id) self.ui.Dibujar.clicked.connect(self.dibujar) self.ui.Limpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) self.ui.OrdId.clicked.connect(self.ordId) self.ui.OrdDistancia.clicked.connect(self.ordDistancia) self.ui.OrdVelocidad.clicked.connect(self.ordVelocidad) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) self.Scene = QGraphicsScene() self.ui.GrafoF_graphicsView.setScene(self.Scene) self.ui.Mostrar_pushButton.clicked.connect(self.MostrarGrafo) self.ui.Limpiar_pushButton.clicked.connect(self.limpiarGrafo) self.ui.Recorrer.clicked.connect(self.Profundidad_Amplitud) @Slot() def Profundidad_Amplitud(self): self.ui.Recorrido_plainTextEdit.clear() grafo = dict() for Particulas in self.AlmacenP: OX = str(Particulas.OrigenX).upper() OY = str(Particulas.OrigenY).upper() DX = str(Particulas.DestinoX).upper() DY = str(Particulas.DestinoY).upper() Origen = OX, OY Destino = DX, DY if Origen in grafo: grafo[Origen].append(Destino) else: grafo[Origen] = [Destino] if Destino in grafo: grafo[Destino].append(Origen) else: grafo[Destino] = [Origen] UbicX = self.ui.BusquedaX_spinBox.value() UbicY = self.ui.BusquedaY_spinBox.value() UbicacionX = str(UbicX).upper() UbicacionY = str(UbicY).upper() Ubicacion = UbicacionX, UbicacionY if Ubicacion in grafo: adyacencia = Ubicacion visitados = [] pila = deque() recorrido = [] visitados.append(adyacencia) pila.append(adyacencia) while len(pila) != 0: vertice = pila[-1] recorrido.append(vertice) pila.pop() for ady in grafo[vertice]: if ady not in visitados: visitados.append(ady) pila.append(ady) self.ui.Recorrido_plainTextEdit.insertPlainText('Profundidad\n') for parte in recorrido: self.ui.Recorrido_plainTextEdit.insertPlainText(str(parte)) self.ui.Recorrido_plainTextEdit.insertPlainText('\n') self.ui.Recorrido_plainTextEdit.insertPlainText('\n\n') adyacencia2 = Ubicacion visitados2 = [] cola = deque() recorrido2 = [] visitados2.append(adyacencia2) cola.append(adyacencia2) while len(cola) != 0: vertice2 = cola[0] recorrido2.append(vertice2) cola.popleft() for ady2 in grafo[vertice2]: if ady2 not in visitados2: visitados2.append(ady2) cola.append(ady2) self.ui.Recorrido_plainTextEdit.insertPlainText('Amplitud\n') for parte in recorrido2: self.ui.Recorrido_plainTextEdit.insertPlainText(str(parte)) self.ui.Recorrido_plainTextEdit.insertPlainText('\n') else: QMessageBox.critical(self, "Error", "Esta ubicacion no se encuentra en el grafo") @Slot() def MostrarGrafo(self): grafo = dict() for Particulas in self.AlmacenP: OX = str(Particulas.OrigenX).upper() OY = str(Particulas.OrigenY).upper() DX = str(Particulas.DestinoX).upper() DY = str(Particulas.DestinoY).upper() DI = int(Particulas.Distancia) Origen = OX, OY Destino = DX, DY AristaOD = (DX, DY, DI) AristaDO = (OX, OY, DI) if Origen in grafo: grafo[Origen].append(AristaOD) else: grafo[Origen] = [AristaOD] if Destino in grafo: grafo[Destino].append(AristaDO) else: grafo[Destino] = [AristaDO] strn = pformat(grafo, width=40, indent=1) pprint(grafo, width=40) for Particulas in self.AlmacenP: pen = QPen() pen.setWidth(2) color = QColor(Particulas.Red, Particulas.Green, Particulas.Blue) pen.setColor(color) self.Scene.addEllipse(Particulas.OrigenX, Particulas.OrigenY, 3, 3, pen) self.Scene.addEllipse(Particulas.DestinoX, Particulas.DestinoY, 3, 3, pen) self.Scene.addLine(Particulas.OrigenX + 3, Particulas.OrigenY + 3, Particulas.DestinoX, Particulas.DestinoY, pen) self.ui.Grafo_plainTextEdit.clear() self.ui.Grafo_plainTextEdit.insertPlainText(strn) @Slot() def limpiarGrafo(self): self.Scene.clear() self.ui.Grafo_plainTextEdit.clear() # def sort_by_Distancia(self.__lista): # return self.__particulas.Distancia @Slot() def ordId(self): self.AlmacenP.ordenar() @Slot() def ordDistancia(self): self.AlmacenP.ordenarD() @Slot() def ordVelocidad(self): self.AlmacenP.ordenarV() @Slot() def dibujar(self): pen = QPen() pen.setWidth(3) for Particulas in self.AlmacenP: r = float(Particulas.Red) g = float(Particulas.Green) b = float(Particulas.Blue) # origen_x = randint(0, 500) # origen_y = randint(0, 500) # destino_x = randint(0, 500) # destino_y = randint(0, 500) color = QColor(r, g, b) pen.setColor(color) self.scene.addEllipse(float(Particulas.OrigenX), float(Particulas.OrigenY), 3, 3, pen) self.scene.addEllipse(float(Particulas.DestinoX), float(Particulas.DestinoY), 3, 3, pen) self.scene.addLine( float(Particulas.OrigenX) + 3, float(Particulas.OrigenY) + 3, float(Particulas.DestinoX), float(Particulas.DestinoY), pen) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) if event.delta() > 0: self.ui.GrafoF_graphicsView.scale(1.2, 1.2) else: self.ui.GrafoF_graphicsView.scale(0.8, 0.8) @Slot() def limpiar(self): self.scene.clear() @Slot() def buscar_id(self): Id = self.ui.Buscar.text() encontrado = False for Particulas in self.AlmacenP: if Id == str(Particulas.Id): self.ui.tableWidget.clear() self.ui.tableWidget.setRowCount(1) Id_widget = QTableWidgetItem(str(Particulas.Id)) OrigenX_widget = QTableWidgetItem(str(Particulas.OrigenX)) OrigenY_widget = QTableWidgetItem(str(Particulas.OrigenY)) DestinoX_widget = QTableWidgetItem(str(Particulas.DestinoX)) DestinoY_widget = QTableWidgetItem(str(Particulas.DestinoY)) Velocidad_widget = QTableWidgetItem(str(Particulas.Velocidad)) Red_widget = QTableWidgetItem(str(Particulas.Red)) Green_widget = QTableWidgetItem(str(Particulas.Green)) Blue_widget = QTableWidgetItem(str(Particulas.Blue)) Distancia_widget = QTableWidgetItem(str(Particulas.Distancia)) self.ui.tableWidget.setItem(0, 0, Id_widget) self.ui.tableWidget.setItem(0, 1, OrigenX_widget) self.ui.tableWidget.setItem(0, 2, OrigenY_widget) self.ui.tableWidget.setItem(0, 3, DestinoX_widget) self.ui.tableWidget.setItem(0, 4, DestinoY_widget) self.ui.tableWidget.setItem(0, 5, Velocidad_widget) self.ui.tableWidget.setItem(0, 6, Red_widget) self.ui.tableWidget.setItem(0, 7, Green_widget) self.ui.tableWidget.setItem(0, 8, Blue_widget) self.ui.tableWidget.setItem(0, 9, Distancia_widget) encontrado = True return if not encontrado: QMessageBox.warning( self, 'Atencion', f'La particula con el Id "{Id}" no fue encontrado') @Slot() def mostrar_tabla(self): #print('mostrar_tabla') self.ui.tableWidget.setColumnCount(10) headers = [ "Id", "OrigenX", "OrigenY", "DestinoX", "DestinoY", "Velocidad", "Red", "Green", "Blue", "Distancia" ] self.ui.tableWidget.setHorizontalHeaderLabels(headers) self.ui.tableWidget.setRowCount(len(self.AlmacenP)) row = 0 for Particulas in self.AlmacenP: Id_widget = QTableWidgetItem(str(Particulas.Id)) OrigenX_widget = QTableWidgetItem(str(Particulas.OrigenX)) OrigenY_widget = QTableWidgetItem(str(Particulas.OrigenY)) DestinoX_widget = QTableWidgetItem(str(Particulas.DestinoX)) DestinoY_widget = QTableWidgetItem(str(Particulas.DestinoY)) Velocidad_widget = QTableWidgetItem(str(Particulas.Velocidad)) Red_widget = QTableWidgetItem(str(Particulas.Red)) Green_widget = QTableWidgetItem(str(Particulas.Green)) Blue_widget = QTableWidgetItem(str(Particulas.Blue)) Distancia_widget = QTableWidgetItem(str(Particulas.Distancia)) self.ui.tableWidget.setItem(row, 0, Id_widget) self.ui.tableWidget.setItem(row, 1, OrigenX_widget) self.ui.tableWidget.setItem(row, 2, OrigenY_widget) self.ui.tableWidget.setItem(row, 3, DestinoX_widget) self.ui.tableWidget.setItem(row, 4, DestinoY_widget) self.ui.tableWidget.setItem(row, 5, Velocidad_widget) self.ui.tableWidget.setItem(row, 6, Red_widget) self.ui.tableWidget.setItem(row, 7, Green_widget) self.ui.tableWidget.setItem(row, 8, Blue_widget) self.ui.tableWidget.setItem(row, 9, Distancia_widget) row += 1 @Slot() def action_abrir_archivo(self): #print('abrir_archivo') ubication = QFileDialog.getOpenFileName(self, 'Abrir Archivo', '.', 'JSON (*.json)')[0] if self.AlmacenP.abrir(ubication): QMessageBox.information(self, "Exito", "Se abrio el archivo " + ubication) else: QMessageBox.critical(self, "Error", "Eror al abrir el archivo" + ubication) @Slot() def action_guardar_archivo(self): #print('Guardar_archivo') ubication = QFileDialog.getSaveFileName(self, 'Guardar Archivo', '.', 'JSON (*.json)')[0] print(ubication) if self.AlmacenP.guardar(ubication): QMessageBox.information(self, "Exito", "Se pudo crear el archivo" + ubication) else: QMessageBox.critical(self, "Error", "No se pudo crear el archivo" + ubication) @Slot() def click_mostrar(self): #self.AlmacenP.mostrar() self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText(str(self.AlmacenP)) @Slot() def click_agregar(self): Id = self.ui.Id_spinBox.value() OrigenX = self.ui.OrigenX_spinBox.value() OrigenY = self.ui.OrigenY_spinBox.value() DestinoX = self.ui.DestinoX_spinBox.value() DestinoY = self.ui.DestinoY_spinBox.value() Velocidad = self.ui.Velocidad_spinBox.value() Red = self.ui.Red_spinBox.value() Green = self.ui.Green_spinBox.value() Blue = self.ui.Blue_spinBox.value() Distancia = self.ui.Distancia_spinBox.value() Particulas = Particula(Id, OrigenX, OrigenY, DestinoX, DestinoY, Velocidad, Red, Green, Blue) self.AlmacenP.agregar_final(Particulas) # print(Id, OrigenX, OrigenY, DestinoX, DestinoY, Velocidad, Red, Green, Blue) # self.ui.plainTextEdit.insertPlainText(str(Id) + str(OrigenX) + str(OrigenY) + str(DestinoX) + str(DestinoY) + str(Velocidad) + str(Red) + str(Green) + str(Blue)) @Slot() def click_agregarInicio(self): Id = self.ui.Id_spinBox.value() OrigenX = self.ui.OrigenX_spinBox.value() OrigenY = self.ui.OrigenY_spinBox.value() DestinoX = self.ui.DestinoX_spinBox.value() DestinoY = self.ui.DestinoY_spinBox.value() Velocidad = self.ui.Velocidad_spinBox.value() Red = self.ui.Red_spinBox.value() Green = self.ui.Green_spinBox.value() Blue = self.ui.Blue_spinBox.value() Distancia = self.ui.Distancia_spinBox.value() Particulas = Particula(Id, OrigenX, OrigenY, DestinoX, DestinoY, Velocidad, Red, Green, Blue) self.AlmacenP.agregar_inicio(Particulas)
class RawImageEditor(SubWindow): def __init__(self, name='RawImageEditor', parent=None): super().__init__(name, parent, Ui_ImageEditor(), need_processBar=True) self.scene = QGraphicsScene() self.imageview = ImageView(self.scene, parent) self.img_params = RawImageParams() self.img_params = self.load_params(RawImageParams()) self.img_pipeline = IspPipeline(self.img_params, process_bar=self.progress_bar) self.img = self.img_pipeline.get_image(0) self.point_data = 0 self.scale_ratio = 100 self.histShow = None self.show_img = None self.select_awb = False # 由于graphicsView被自定义了,需要重新定义一下UI,gridlayout还需要重新加一下widget self.ui.graphicsView.addWidget(self.imageview, 0, 1, 3, 1) self.imageview.sigDragEvent.connect(self.__init_img) self.imageview.sigMouseMovePoint.connect(self.show_point_rgb) self.imageview.sigWheelEvent.connect(self.update_wheel_ratio) # 回调函数初始化 self.ui.pipeline.doubleClicked.connect(self.update_img_index) self.ui.pipeline_ok.clicked.connect(self.update_pipeline) self.ui.open_image.clicked.connect(self.open_image) self.ui.analysis_img.clicked.connect(self.openHistView) self.ui.select_from_raw.clicked.connect(self.select_awb_from_raw) self.imageview.rubberBandChanged.connect(self.update_awb_from_raw) self.ui.save_image.clicked.connect(self.save_now_image) self.ui.reload.clicked.connect(self.img_pipeline.reload_isp) # ISP 处理线程回调 self.img_pipeline.ispProcthread.doneCB.connect(self.update_img) self.img_pipeline.ispProcthread.processRateCB.connect( self.update_process_bar) self.img_pipeline.ispProcthread.costTimeCB.connect( self.update_time_bar) def update_img(self): """ func: ISP 处理完成后的显示回调函数 """ self.displayImage(self.img_pipeline.get_image(-1)) def update_process_bar(self, value): """ func: ISP 处理进度回调 """ self.progress_bar.setValue(value) def update_time_bar(self, value): """ func:ISP 处理时长回调 """ self.time_bar.setText(value) def show(self): """ func: 显示初始化 """ super().show() self.img_params.set_img_params_ui(self.ui) if (self.img_params.filename != "" and self.img_params.get_width() != 0 and self.img_params.get_height() != 0 and self.img_params.get_bit_depth() != 0): if (self.img_pipeline.pipeline_reset() == True): self.img = self.img_pipeline.get_image(0) for i in range(1, self.ui.pipeline.count()): self.ui.pipeline.item(i).setCheckState(Qt.Unchecked) self.img.load_image_with_params(self.img_params) self.img.set_bayer_pattern(self.img_params.get_pattern()) self.rect = [0, 0, self.img_params.width, self.img_params.height] if (self.img.get_raw_data() is not None): self.displayImage(self.img) def displayImage(self, img): """ 显示图像 输入需要是RawImageInfo """ self.scene.clear() self.img = img self.show_img = img.get_showimage() if (self.show_img is not None): showimg = QImage(self.show_img, self.show_img.shape[1], self.show_img.shape[0], QImage.Format_BGR888) self.scene.addPixmap(QPixmap(showimg)) self.ui.photo_title.setTitle(img.get_name()) def select_awb_from_raw(self): """ func: 进入raw图选择模式,修改鼠标类型 """ self.imageview.setDragMode(QGraphicsView.RubberBandDrag) self.select_awb = True def update_awb_from_raw(self, viewportRect, fromScenePoint, toScenePoint): """ func: 鼠标选中事件的回调:执行AWB的选择区域或者图像分析的选择区域 """ if (toScenePoint.x() == 0 and toScenePoint.y() == 0 and self.rect[2] > self.rect[0] and self.rect[3] > self.rect[1]): if (self.select_awb == True): self.imageview.setDragMode(QGraphicsView.ScrollHandDrag) self.select_awb = False awb_ratio = self.img.get_raw_img_rect(self.rect) if (awb_ratio is not None): self.img_params.set_awb_ratio(awb_ratio) awb_gain = self.img_params.get_awb_gain() self.ui.awb_r.setValue(awb_gain[0]) self.ui.awb_g.setValue(awb_gain[1]) self.ui.awb_b.setValue(awb_gain[2]) else: critical("请在raw图上进行选择") else: if (self.histView is not None): self.histView.update_rect_data(self.show_img, self.rect) else: self.rect = [ int(fromScenePoint.x()), int(fromScenePoint.y()), int(toScenePoint.x()), int(toScenePoint.y()) ] def update_pipeline(self): """ func: 运行ISP pipeline """ self.img_params.get_img_params(self.ui) self.img_pipeline.pipeline_clear() for i in range(self.ui.pipeline.count()): if (self.ui.pipeline.item(i).checkState() == Qt.Checked): self.img_pipeline.add_pipeline_node( self.ui.pipeline.item(i).data(0)) self.img_pipeline.run_pipeline() def update_img_index(self, item): """ func: 更新当前画面的序号 """ if (self.ui.pipeline.item(item.row()).checkState() == Qt.Checked): index = self.img_pipeline.get_pipeline_node_index(item.data()) + 1 self.displayImage(self.img_pipeline.get_image(index)) def open_image(self): """ func: 打开图片的回调函数 """ if (self.img_params.filename != ''): now_path = os.path.dirname(self.img_params.filename) else: now_path = './' self.img_params.get_img_params(self.ui) imagepath = QFileDialog.getOpenFileName(None, '打开RAW图', now_path, "raw (*.raw)") self.__init_img(imagepath[0]) def __init_img(self, filename): width = self.img_params.get_width() height = self.img_params.get_height() bit_depth = self.img_params.get_bit_depth() if (filename != "" and width != 0 and height != 0 and bit_depth != 0): if (self.img_pipeline.pipeline_reset() == True): self.img = self.img_pipeline.get_image(0) for i in range(1, self.ui.pipeline.count()): self.ui.pipeline.item(i).setCheckState(Qt.Unchecked) self.img.load_image(filename, height, width, bit_depth) self.img.set_bayer_pattern(self.img_params.get_pattern()) self.img_params.filename = filename self.rect = [0, 0, self.img_params.width, self.img_params.height] if (self.img.get_raw_data() is not None): self.displayImage(self.img) else: critical("打开图片失败,图片格式错误") else: critical("打开图片失败,图片格式错误") def save_now_image(self): """ func: 保存图片的回调 """ if (self.img.get_raw_data() is not None): imagepath = QFileDialog.getSaveFileName(None, '保存图片', './', "Images (*.jpg)") if (imagepath[0] != ""): self.img.save_image(imagepath[0]) def show_point_rgb(self, point): """ func: 鼠标移动的回调 """ self.x = int(point.x()) self.y = int(point.y()) if (self.img.get_raw_data() is not None): point_data = self.img.get_img_point(self.x, self.y) if (point_data is not None): self.point_data = point_data self.set_img_info_show() def update_wheel_ratio(self, ratio): """ func: 鼠标滚轮的回调 """ if (self.img.get_raw_data() is not None): self.scale_ratio = int(ratio * 100) self.set_img_info_show() def set_img_info_show(self): """ func: 显示像素点的值以及缩放比例 """ if (self.point_data.size == 1): self.info_bar.setText("x:{},y:{} : {}: 亮度:{} 缩放比例:{}%".format( self.x, self.y, self.img.get_img_point_pattern(self.y, self.x).upper(), self.point_data, self.scale_ratio)) elif (self.point_data.size == 3): if (self.img.get_color_space() == 'RGB'): self.info_bar.setText( "x:{},y:{} : R:{} G:{} B:{} 缩放比例:{}%".format( self.x, self.y, self.point_data[2], self.point_data[1], self.point_data[0], self.scale_ratio)) else: self.info_bar.setText( "x:{},y:{} : Y:{} Cr:{} Cb:{} 缩放比例:{}%".format( self.x, self.y, self.point_data[0], self.point_data[1], self.point_data[2], self.scale_ratio)) def openHistView(self): self.histView = HistView(self.imageview) rect = [0, 0, self.show_img.shape[1], self.show_img.shape[0]] self.histView.update_rect_data(self.show_img, rect) self.histView.show()
class CanvasGraphicsView(QGraphicsView): onSelection = Signal(PickNode) requestEditMode = Signal(bool) def __init__(self, parent=None): super(CanvasGraphicsView, self).__init__(parent) self.setFocusPolicy(Qt.StrongFocus) # Scene properties self.setAcceptDrops(True) self.setMouseTracking(True) self.setRenderHint(QPainter.Antialiasing) self.setTransformationAnchor(QGraphicsView.AnchorUnderMouse) self.setResizeAnchor(QGraphicsView.AnchorUnderMouse) self.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.setBackgroundBrush(QBrush(QColor(51, 51, 51))) self.setFrameShape(QFrame.NoFrame) self.setDragMode(QGraphicsView.RubberBandDrag) self.ViewportUpdateMode(QGraphicsView.BoundingRectViewportUpdate) self.init() def init(self): self.piiPath = str() self._model = {'background': str()} self._isPanning = False self._isZooming = False self._mousePressed = False self._scene = QGraphicsScene() self._scene.selectionChanged.connect(self.update_node_settings) self._backgroundNode = QGraphicsPixmapItem() self._scene.addItem(self._backgroundNode) self._orderSelected = list() self._lastPos = QPoint(0, 0) self.editMode = False self._namespace = str() self._dragMulti = list() self._defaultColor = QColor(255, 255, 255) self._defaultTextColor = QColor(0, 0, 0) self._defaultTextSize = 20 self._defaultText = "New Node" self.workHight = 2160 self.workWidth = 4096 self.setScene(self._scene) self.setContextMenuPolicy(Qt.CustomContextMenu) self.setBackgroundImage(str()) def update_node_settings(self): if self._orderSelected: node = self._orderSelected[-1] self._defaultText = node.toPlainText() self._defaultColor = node.Background self._defaultTextColor = node.defaultTextColor() self._defaultTextSize = node.font().pointSize() def update_maya_selection(self): ''' Update Maya Scene base on active selection. ''' clearSelection() selection = list() for each in self._orderSelected: selection += each.Items if selection: selectObjects(selection) def setBackgroundImage(self, path=str()): ''' Set background image Parameters ---------- path: (str) Path to background image. ''' self._model['background'] = path self.setStatusTip(self._model['background']) pixmap = QPixmap(self._model['background']) self._backgroundNode.setPixmap(pixmap) def getBackgroundImage(self): ''' Get background image ''' return self._model['background'] BackgroundImage = property(getBackgroundImage, setBackgroundImage) def actionMenu(self, QPos): ''' Show action menu. Parameters ---------- QPos: (list) list of x and y location. ''' self.mainMenu = QMenu() add_action = self.mainMenu.addAction('Add A Button') add_action.setEnabled(self.editMode) add_action.triggered.connect(self.add_node) addMany_action = self.mainMenu.addAction('Add Many Buttons') addMany_action.setEnabled(self.editMode) addMany_action.triggered.connect(self.add_multiple_nodes) activeNode = self.mouse_on_node() if activeNode: update_action = self.mainMenu.addAction('Update Button') update_action.setEnabled(self.editMode) update_action.triggered.connect( lambda: self.update_node(activeNode)) delete_action = self.mainMenu.addAction('Delete Button') delete_action.setEnabled(self.editMode) delete_action.setShortcut('Backspace') delete_action.triggered.connect(self.removeSelected) self.mainMenu.addSeparator() # search for selected ButtonNode btnStatus = [ isinstance(n, ButtonNode) for n in self._scene.selectedItems() ] if True in btnStatus: # first ButtonNode activeNode = self._scene.selectedItems()[btnStatus.index(True)] command_action = self.mainMenu.addAction('Edit Command Button...') command_action.setEnabled(self.editMode) command_action.triggered.connect( lambda: self.update_ButtonNode(activeNode)) else: command_action = self.mainMenu.addAction('add Command Button...') command_action.setEnabled(self.editMode) command_action.triggered.connect(self.add_commands) self.mainMenu.addSeparator() reset_action = self.mainMenu.addAction('Reset View') reset_action.setShortcut('H') reset_action.triggered.connect(self.reset_view) frame_action = self.mainMenu.addAction('Frame View') frame_action.setShortcut('F') frame_action.triggered.connect(self.frame_view) self.mainMenu.addSeparator() alignGrp = QMenu('Align') self.mainMenu.addMenu(alignGrp) hac_action = alignGrp.addAction('Horizontal Align Center') hac_action.setIcon(QIconSVG('h_align-01')) hac_action.setEnabled(self.editMode) hac_action.triggered.connect(self.align_horizontal) vac_action = alignGrp.addAction('Vertical Align Center') vac_action.setIcon(QIconSVG('v_align-01')) vac_action.setEnabled(self.editMode) vac_action.triggered.connect(self.align_vertical) hd_action = alignGrp.addAction('Horizontal Distribute') hd_action.setIcon(QIconSVG('h_d_align-01')) hd_action.setEnabled(self.editMode) hd_action.triggered.connect(self.align_horizontal_distribute) vd_action = alignGrp.addAction('Vertical Distribute') vd_action.setIcon(QIconSVG('v_d_align-01')) vd_action.setEnabled(self.editMode) vd_action.triggered.connect(self.align_vertical_distribute) alignGrp.addSeparator() ins_action = alignGrp.addAction('Increase Size') ins_action.setShortcut('+') ins_action.setEnabled(self.editMode) ins_action.triggered.connect(self.increase_size) dis_action = alignGrp.addAction('Decrease Size') dis_action.setShortcut('-') dis_action.setEnabled(self.editMode) dis_action.triggered.connect(self.decrease_size) self.mainMenu.addSeparator() edit_mode = self.mainMenu.addAction('Edit Mode') edit_mode.setCheckable(True) edit_mode.setChecked(self.editMode) edit_mode.triggered.connect( lambda: self.request_edit(not self.editMode)) pos = self.mapToGlobal(QPoint(0, 0)) self.mainMenu.move(pos + QPos) self.mainMenu.show() def mouse_on_node(self): globPosition = self.mapFromGlobal(QCursor.pos()) scenePosition = self.mapToScene(globPosition) for node in self._scene.items(): if isinstance(node, PickNode): if node.mapRectToScene( node.boundingRect()).contains(scenePosition): return node return None def update_node(self, node=PickNode): ''' Update the Node selection base on selection in maya. ''' mayaScene = getActiveItems() # for each in self._scene.selectedItems(): node.Items = mayaScene def update_ButtonNode(self, node=ButtonNode): ''' Update the ButtonNode commands. Parameters ---------- node: (ButtonNode) ButtonNode Node. ''' self.newCommand = CommandDialog(text=node.toPlainText(), cmd=node.Command, cmdType=node.CommandsType) if self.newCommand.exec_() == QDialog.Accepted: data = self.newCommand.Raw node.setPlainText(data[PIIButton.TEXT]) node.Command = data[PIIButton.COMMAND] node.CommandsType = data[PIIButton.COMMANDTYPE] def add_commands(self): ''' Create a new ButtonNode with Commands. ''' globPosition = self.mapFromGlobal(QCursor.pos()) scenePosition = self.mapToScene(globPosition) self.newCommand = CommandDialog() if self.newCommand.exec_() == QDialog.Accepted: data = self.newCommand.Raw self.create_button(position=scenePosition, text=data[PIIButton.TEXT], size=self._defaultTextSize, textColor=self._defaultTextColor, bgColor=self._defaultColor, cmd=data[PIIButton.COMMAND], cmdType=data[PIIButton.COMMANDTYPE]) def align_horizontal(self): ''' Align the selection to center horizontally. ''' selected = self._scene.selectedItems() if len(selected) > 1: minValue = selected[0].y() maxValue = selected[0].y() whole = None for each in selected: y = each.y() value = y + each.boundingRect().height() # finding lowest value minValue = y if y < minValue else minValue minValue = value if value < minValue else minValue # finding highest value maxValue = y if y > maxValue else maxValue maxValue = value if value > maxValue else maxValue total = maxValue - minValue if total != 0: middle = (maxValue + minValue) / 2 for each in selected: center = each.shape().boundingRect().center() start_y = each.y() offset = start_y + center.y() - middle each.setY(each.y() - offset) def align_vertical(self): ''' Align the selection to center vertically. ''' selected = self._scene.selectedItems() if len(selected) > 1: # sort it based on x position + width selected = sorted(selected, key=lambda x: x.x() + x.boundingRect().width()) leftNode = selected[0] rightNode = selected[-1] # total length of x axis total = rightNode.boundingRect().width() + rightNode.x( ) - leftNode.x() if total != 0: middle = (total / 2) + leftNode.x() for each in selected: center = each.shape().boundingRect().center() start_x = each.x() offset = start_x + center.x() - middle each.setX(each.x() - offset) def align_horizontal_distribute(self): ''' Disturbute the selected nodes evenly between first node on the left and last node on the right horizontally. ''' selected = self._scene.selectedItems() if len(selected) > 2: # sort it based on x position + width selected = sorted(selected, key=lambda x: x.x() + x.boundingRect().width()) startItem = selected.pop(0) endItem = selected.pop(-1) # total length of items itemsLength = int() for each in selected: itemsLength += each.boundingRect().width() startPoint = startItem.x() + startItem.boundingRect().width() total = endItem.x() - startPoint section_num = len(selected) + 1 extraSpace = total - itemsLength # nicly divide if extraSpace > 0: gap = extraSpace / section_num nextPlace = startPoint for each in selected: newLoc = nextPlace + gap nextPlace += gap + each.boundingRect().width() each.setX(newLoc) else: total = endItem.x() - startPoint gap = total / section_num nextPlace = startPoint for each in selected: nextPlace += gap each.setX(nextPlace) else: errorMes("PUPPETMASTER-INFO: Select more than 2 nodes.") def align_vertical_distribute(self): ''' Disturbute the selected nodes evenly between first node on the top and last node on the bottom vertically. ''' selected = self._scene.selectedItems() if len(selected) > 2: # sort it based on y position + width selected = sorted( selected, key=lambda node: node.y() + node.boundingRect().height()) startItem = selected.pop(0) endItem = selected.pop(-1) # total length of items itemsLength = int() for each in selected: itemsLength += each.boundingRect().height() startPoint = startItem.y() + startItem.boundingRect().height() total = endItem.y() - startPoint section_num = len(selected) + 1 extraSpace = total - itemsLength # nicly divide if extraSpace > 0: gap = extraSpace / section_num nextPlace = startPoint for each in selected: newLoc = nextPlace + gap nextPlace += gap + each.boundingRect().height() each.setY(newLoc) else: total = endItem.y() - startPoint gap = total / section_num nextPlace = startPoint for each in selected: nextPlace += gap each.setY(nextPlace) else: errorMes("PUPPETMASTER-INFO: Select more than 2 nodes.") def reset_view(self): ''' Fit all the items to the view. ''' items = self._scene.items() if items: rects = [ item.mapToScene(item.boundingRect()).boundingRect() for item in items ] rect = self.min_bounding_rect(rects) self._scene.setSceneRect(rect) self.fitInView(rect, Qt.KeepAspectRatio) def frame_view(self): ''' Fit selected items to the view. ''' items = self._scene.selectedItems() if items: rects = [ item.mapToScene(item.boundingRect()).boundingRect() for item in items ] rect = self.min_bounding_rect(rects) self.fitInView(rect, Qt.KeepAspectRatio) def fit_contents(self): ''' Update the scene boundery. ''' items = self._scene.items() if items: rects = [ item.mapToScene(item.boundingRect()).boundingRect() for item in items ] rect = self.min_bounding_rect(rects) self._scene.setSceneRect(rect) def request_edit(self, value=bool): self.requestEditMode.emit(value) def min_bounding_rect(self, rectList=list()): ''' Get the minimum boundry based on objects in the scene. Parameters ---------- rectList: (list) List of QRectF (boundry of objects) Return ------ out: (QRectF) Get the minimum boundry ''' minX = rectList[0].left() minY = rectList[0].top() maxX = rectList[0].right() maxY = rectList[0].bottom() for k in range(1, len(rectList)): minX = min(minX, rectList[k].left()) minY = min(minY, rectList[k].top()) maxX = max(maxX, rectList[k].right()) maxY = max(maxY, rectList[k].bottom()) return QRectF(minX, minY, maxX - minX, maxY - minY) def increase_size(self): ''' Increase the size of selected items by 1 unit. ''' selected = self._scene.selectedItems() for each in selected: font = each.font() fontSize = font.pointSize() if fontSize < 99: fontSize += 1 font.setPointSize(fontSize) each.setFont(font) def decrease_size(self): ''' Decrease the size of selected items by 1 unit. ''' selected = self._scene.selectedItems() for each in selected: font = each.font() fontSize = font.pointSize() if fontSize > 1: fontSize -= 1 font.setPointSize(fontSize) each.setFont(font) def is_texture(self, path=str): ''' Check if the texture path is valid. Return ------ out: (bool) True if texture is valide, otherwise False. ''' if path.lower().endswith(IMAGE_FORMATS): return True return False def _QMimeDataToFile(self, data=QMimeData): ''' Get all the filepath from drag file. Parameters ---------- data: (QMimeData) QMimeData of dragged file. ''' files = list() if data.hasUrls: for each in data.urls(): files.append(each.toLocalFile()) return files def _is_dragValid(self, event): ''' Check for draged file validation ''' dragedItems = self._QMimeDataToFile(event.mimeData()) if dragedItems: first_path = dragedItems[0] if self.is_texture(first_path) and self.editMode: return True return False def dragEnterEvent(self, event): event.accept() if self._is_dragValid(event) else event.ignore() def dragMoveEvent(self, event): event.accept() if self._is_dragValid(event) else event.ignore() def dropEvent(self, event): dragedItems = self._QMimeDataToFile(event.mimeData()) if dragedItems: first_path = dragedItems[0] if self.is_texture(first_path): self.setBackgroundImage(path=first_path) event.accept() else: event.ignore() def mousePressEvent(self, event): self._lastPos = event.pos() self._lastScenePos = self.mapToScene(event.pos()) if self._dragMulti: for each in self._dragMulti: each.setSelected(True) self._dragMulti = list() if event.button() == Qt.MiddleButton: self._isPanning = True self.setCursor(QPixmap(iconSVG('nav-pan-02'))) self._dragPos = event.pos() event.accept() elif event.button() == Qt.RightButton: if event.modifiers() == Qt.AltModifier: self._isZooming = True self.setCursor(QPixmap(iconSVG('nav-zoom-02'))) self._dragPos = event.pos() self._dragPos2 = self.mapToScene(event.pos()) else: self.actionMenu(event.pos()) event.accept() else: super(CanvasGraphicsView, self).mousePressEvent(event) def mouseMoveEvent(self, event): if self._dragMulti and len(self._dragMulti) > 1: start = self._lastScenePos end = self.mapToScene(event.pos()) total = len(self._dragMulti) - 1 xLength = start.x() - end.x() yLength = start.y() - end.y() xStep = 0 if xLength == 0 else -(xLength / total) yStep = 0 if yLength == 0 else -(yLength / total) num = 0 for each in self._dragMulti: position = QPointF(start.x() + (num * xStep), start.y() + (num * yStep)) each.setPos(position) num += 1 if self._isPanning: newPos = event.pos() diff = newPos - self._dragPos self._dragPos = newPos self.horizontalScrollBar().setValue( self.horizontalScrollBar().value() - diff.x()) self.verticalScrollBar().setValue( self.verticalScrollBar().value() - diff.y()) event.accept() elif self._isZooming: newPos = event.pos() diff = newPos - self._dragPos self._dragPos = newPos factor = 1.000 if diff.x() < 0: factor = 0.98 else: factor = 1.02 self.scale(factor, factor) event.accept() else: if event.modifiers() == Qt.ShiftModifier: diff = event.pos() - self._lastPos x = event.x() if abs(diff.x()) > abs( diff.y()) else self._lastPos.x() y = event.y() if abs(diff.y()) > abs( diff.x()) else self._lastPos.y() event = QMouseEvent(QEvent.MouseMove, QPoint(x, y), self.mapToGlobal(QPoint(x, y)), Qt.LeftButton, Qt.LeftButton, Qt.NoModifier) super(CanvasGraphicsView, self).mouseMoveEvent(event) def mouseReleaseEvent(self, event): self._isPanning = False self._isZooming = False self.setCursor(Qt.ArrowCursor) super(CanvasGraphicsView, self).mouseReleaseEvent(event) self.fit_contents() self.update_maya_selection() def keyPressEvent(self, event): if event.key() == Qt.Key_Backspace or event.key() == Qt.Key_Delete: if self.editMode: self.removeSelected() elif event.key() == Qt.Key_Plus: if self.editMode: self.increase_size() elif event.key() == Qt.Key_Minus: if self.editMode: self.decrease_size() elif event.key() == Qt.Key_H: self.reset_view() elif event.key() == Qt.Key_F: self.frame_view() else: super(CanvasGraphicsView, self).keyPressEvent(event) def removeSelected(self): ''' Remove selected Items. ''' for each in self._scene.selectedItems(): self._scene.removeItem(each) self.remove_stack(each) def wheelEvent(self, event): factor = 1.05 if event.delta() < 0: # factor = .2 / factor factor = 0.95 self.scale(factor, factor) self.update() def add_node(self): ''' Add a new PickNode to the scene. ''' # Cursor Position on Scene globPosition = self.mapFromGlobal(QCursor.pos()) scenePosition = self.mapToScene(globPosition) self.create_node(text=self._defaultText, size=self._defaultTextSize, textColor=self._defaultTextColor, bgColor=self._defaultColor, position=scenePosition, items=getActiveItems(), shape=PickShape.SQUARE) def add_multiple_nodes(self): ''' Add group of PickNode bellow each other to the scene. ''' # Cursor Position on Scene globPosition = self.mapFromGlobal(QCursor.pos()) scenePosition = self.mapToScene(globPosition) self._dragMulti = list() for each in getActiveItems(): node = self.create_node(text=self._defaultText, size=self._defaultTextSize, textColor=self._defaultTextColor, bgColor=self._defaultColor, position=scenePosition, items=[each], shape=PickShape.SQUARE) self._dragMulti.append(node) # scenePosition = QPointF(scenePosition.x(), node.y() + node.boundingRect().height() + 5) def create_node(self, position=list, text=str, size=int, textColor=QColor, bgColor=QColor, items=list, shape=PickShape.SQUARE): ''' Create a new PickNode. Parameters ---------- position: (list) List of x and y location. text: (str) Name of the text. size: (int) Size of the text. textColor: (QColor) Color of the text. bgColor: (QColor) Background Color of the node. items: (list) List of selected Maya object. Return ------ out: (PickNode) Reference of created Node. ''' textNode = PickNode() font = QFont("SansSerif", size) font.setStyleHint(QFont.Helvetica) textNode.setFont(font) textNode.setDefaultTextColor(textColor) textNode.setFlag(QGraphicsItem.ItemIsMovable, self.editMode) textNode.setFlag(QGraphicsItem.ItemIsSelectable) # textNode.setFlag(QGraphicsItem.ItemIsFocusable, self.editMode) textNode.Background = bgColor textNode.Items = items textNode.Shape = shape textNode.onSelected.connect(lambda: self.onSelection.emit(textNode)) textNode.onAddToStack.connect(lambda: self.add_stack(textNode)) textNode.onRemoveFromStack.connect(lambda: self.remove_stack(textNode)) textNode.setPos(position) textNode.setPlainText(text) self._scene.addItem(textNode) return textNode def create_button(self, position=list, text=str, size=int, textColor=QColor, bgColor=QColor, cmd=str, cmdType=str): ''' Create a new ButtonNode. Parameters ---------- position: (list) List of x and y location. text: (str) Name of the text. size: (int) Size of the text. textColor: (QColor) Color of the text. bgColor: (QColor) Background Color of the node. cmd: (str) Command to run when it's pressed. cmdType: (str) Type of command.("python"/"mel") ''' btnNode = ButtonNode() font = QFont("SansSerif", size) font.setStyleHint(QFont.Helvetica) btnNode.setFont(font) btnNode.setDefaultTextColor(textColor) btnNode.setFlag(QGraphicsItem.ItemIsMovable, self.editMode) btnNode.setFlag(QGraphicsItem.ItemIsSelectable) btnNode.Background = bgColor btnNode.CommandsType = cmdType btnNode.Command = cmd # btnNode.onSelected.connect(lambda: self.onSelection.emit(textNode)) btnNode.onSelected.connect(lambda: self.onSelection.emit(btnNode)) btnNode.onClicked.connect(self.scriptJob) btnNode.setPos(position) btnNode.setPlainText(text) self._scene.addItem(btnNode) def scriptJob(self, cmdType=str, cmd=str): ''' Run a command. Parameters ---------- cmd: (str) Command to run. cmdType: (str) Type of command.("python"/"mel") ''' if not self.editMode: if cmdType == CommandType.PYTHON: runPython(cmd) elif cmdType == CommandType.MEL: runMel(cmd) def add_stack(self, node=PickNode): ''' Add a node selection in right order into the stack. Parameters ---------- node: (PickNode) Selected node. ''' self._orderSelected.append(node) def remove_stack(self, node=PickNode): ''' Remove a node from the stack. Parameters ---------- node: (PickNode) Selected node. ''' if node in self._orderSelected: index = self._orderSelected.index(node) self._orderSelected.pop(index) def get_edit(self): return self.editMode def set_edit(self, value=bool): self.editMode = value for each in self._scene.items(): if type(each) == PickNode: each.setFlag(QGraphicsItem.ItemIsMovable, self.editMode) elif type(each) == ButtonNode: each.setFlag(QGraphicsItem.ItemIsMovable, self.editMode) Edit = property(get_edit, set_edit) def get_path(self): return self.piiPath def set_path(self, path=str): self.piiPath = path Path = property(get_path, set_path) def get_raw(self): ''' Get the scene information. (can be be save in .pii) Return ------ out: (dict) Dictionary of scene date to be save in .pii file. ''' image_data = str() pixmap = self._backgroundNode.pixmap() # Extract Image Data if not pixmap.isNull(): buffer = QBuffer() buffer.open(QIODevice.WriteOnly) pixmap.save(buffer, "PNG") # Image Data image_data = bytes(buffer.data().toBase64()).decode('ascii') nodeList = [] for each in self._scene.items(): if type(each) == PickNode: textColor = each.defaultTextColor() bgColor = each.Background item = { PIIPick.TYPE: PIINode.PICK, PIIPick.TEXT: each.toPlainText(), PIIPick.SIZE: each.font().pointSize(), PIIPick.POSITION: (each.pos().x(), each.pos().y()), PIIPick.COLOR: (textColor.red(), textColor.green(), textColor.blue()), PIIPick.BACKGROUND: (bgColor.red(), bgColor.green(), bgColor.blue()), PIIPick.SELECTION: each.Items, PIIPick.SHAPE: each.Shape } nodeList.append(item) elif type(each) == ButtonNode: textColor = each.defaultTextColor() bgColor = each.Background item = { PIIButton.TYPE: PIINode.BUTTON, PIIButton.TEXT: each.toPlainText(), PIIButton.SIZE: each.font().pointSize(), PIIButton.POSITION: (each.pos().x(), each.pos().y()), PIIButton.COLOR: (textColor.red(), textColor.green(), textColor.blue()), PIIButton.BACKGROUND: (bgColor.red(), bgColor.green(), bgColor.blue()), PIIButton.COMMAND: each.Command, PIIButton.COMMANDTYPE: each.CommandsType } nodeList.append(item) rawData = { PII.VERSION: "1.0.0", PII.BACKGROUND: image_data, PII.NODES: nodeList } return rawData def set_raw(self, data=dict): ''' set the scene information. (information from .pii) Parameters ---------- data: (dict) Dictionary of date from .pii file. ''' if data: if data[PII.VERSION] == "1.0.0": self.load_1_0_0(data) Raw = property(get_raw, set_raw) def get_namespace(self): ''' Get namespace of all PickNode. Return ------ out: (list) List of namespaces. ''' namespaceList = [] for each in self._scene.items(): if type(each) == PickNode: valueList = each.Items for sObj in valueList: if ":" in sObj: group = sObj.split(":")[:-1] for index in range(len(group)): namespaceList.append(":".join(group[:index + 1])) return list(set(namespaceList)) def set_namespace(self, data=dict): ''' Set namespace of all PickNode. Parameters ---------- data: (dict) Dictionary of namespace with value of new namespace. ''' for each in self._scene.items(): if type(each) == PickNode: valueList = each.Items newValue = list() for sObj in valueList: if ":" in sObj: # namesapce nameS = ":".join(sObj.split(":")[:-1]) # object name object_name = sObj.split(":")[-1] keys = data.keys() keys.sort(reverse=True) for key in keys: if key in nameS: nameS = nameS.replace(key, data[key], 1) # making sure doesn't start with ':' nameS = nameS[1:] if nameS.startswith(":") else nameS # add the object to namespace nameS = ":".join([nameS, object_name ]) if nameS else object_name newValue.append(nameS) else: newValue.append(sObj) each.Items = newValue Namespace = property(get_namespace, set_namespace) def get_NSHistory(self): return self._namespace def set_NSHistory(self, name=str): self._namespace = name NamespaceHistory = property(get_NSHistory, set_NSHistory) def get_highlight(self): return def set_highlight(self, data=list): if data: for each in self._scene.items(): # QApplication.processEvents() if type(each) == PickNode: for item in data: if item in each.Items: each.Highlight = True break else: each.Highlight = False else: for each in self._scene.items(): if type(each) == PickNode: each.Highlight = False Highlight = property(get_highlight, set_highlight) def clear_scene(self): ''' Clear the scene. ''' self._orderSelected = list() self._scene.clear() self._backgroundNode = QGraphicsPixmapItem() self._scene.addItem(self._backgroundNode) self.reset_view() def is_changed(self): ''' Check for the scene changes. ''' if self._backgroundNode.pixmap(): return True elif len(self._scene.items()) > 1: return True return False def load_1_0_0(self, data=dict): ''' Load v1.0.0 of .pii version file. Parameters ---------- data: (dict) Dictionary of date from .pii file. ''' if data[PII.BACKGROUND]: # Import Image Data newPix = QPixmap() newPix.loadFromData( QByteArray.fromBase64(data[PII.BACKGROUND].encode('ascii')), "PNG") self._backgroundNode.setPixmap(newPix) for each in data[PII.NODES]: if each["type"] == PIINode.PICK: self.create_node(text=each[PIIPick.TEXT], size=each[PIIPick.SIZE], textColor=QColor(*each[PIIPick.COLOR]), bgColor=QColor(*each[PIIPick.BACKGROUND]), position=QPointF(*each[PIIPick.POSITION]), items=each[PIIPick.SELECTION], shape=each[PIIPick.SHAPE]) elif each["type"] == PIINode.BUTTON: self.create_button(position=QPointF(*each[PIIButton.POSITION]), text=each[PIIButton.TEXT], size=each[PIIButton.SIZE], textColor=QColor(*each[PIIButton.COLOR]), bgColor=QColor(*each[PIIButton.BACKGROUND]), cmd=each[PIIButton.COMMAND], cmdType=each[PIIButton.COMMANDTYPE]) def set_nodes_bg_color(self, color=QColor): ''' Set background color of selected nodes. Parameters ---------- color: (QColor) QColor value. ''' self._defaultColor = color for each in self._scene.selectedItems(): each.Background = color self.update() def set_nodes_font_color(self, color=QColor): ''' Set font color of selected nodes. Parameters ---------- color: (QColor) QColor value. ''' self._defaultTextColor = color for each in self._scene.selectedItems(): each.setDefaultTextColor(color) def set_nodes_font_size(self, size=int): ''' Set font size of selected nodes. Parameters ---------- size: (int) font size. ''' self._defaultTextSize = size for each in self._scene.selectedItems(): font = each.font() font.setPointSize(size) each.setFont(font) def set_nodes_text(self, text=str): ''' Set text for selected nodes. Parameters ---------- text: (str) text for the node. ''' self._defaultText = text for each in self._scene.selectedItems(): each.setPlainText(text) def set_nodes_shape(self, shape=str): ''' Set shape for selected nodes. Parameters ---------- shape: (str) name for the shape. ''' for each in self._scene.selectedItems(): if isinstance(each, PickNode): each.Shape = shape
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.particulas = Particula_libreria() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.agregar_inicio_pushButton.clicked.connect( self.click_agregar_inicio) self.ui.agregar_final_pushButton.clicked.connect( self.click_agregar_final) self.ui.mostrar_pushButton.clicked.connect(self.click_mostrar) self.ui.actionAbrir.triggered.connect(self.action_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.action_guardar_archivo) self.ui.mostar_tabla_pushButton_2.clicked.connect(self.mostrar_tabla) self.ui.buscar_pushButton.clicked.connect(self.buscar_particula) self.ui.dibujar.clicked.connect(self.dibujar) self.ui.limpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) self.ui.actionPor_id.triggered.connect(self.ordenar_id) self.ui.actionPor_distancia.triggered.connect(self.ordenar_distancia) self.ui.actionPor_velocidad.triggered.connect(self.ordenar_velocidad) self.ui.actionMostrar_diccionario.triggered.connect( self.mostrar_diccionario) self.ui.actionBusqueda_de_Profundidad.triggered.connect(self.recorrido) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def recorrido(self): self.particulas.bye_peso() self.ui.salida.clear() origenes = (self.ui.origen_x_spinBox.value(), self.ui.origen_y_spinBox.value()) recorrido = self.particulas.mostrar_recorrido(origenes) print("Profundidad") self.ui.salida.insertPlainText("Profundidad" + '\n') for i in recorrido: self.ui.salida.insertPlainText(str(i) + '\n') print(i) recorrido_2 = self.particulas.mostrar_recorrido_2(origenes) print("\nAmplitud") self.ui.salida.insertPlainText('\n' "Amplitud" + '\n') for i in recorrido_2: self.ui.salida.insertPlainText(str(i) + '\n') print(i) @Slot() def mostrar_diccionario(self): self.ui.salida.clear() self.ui.salida.insertPlainText(self.particulas.mostrar_diccionario()) QMessageBox.information(self, "Exito", "Se imprimio el diccionario ") @Slot() def ordenar_id(self): self.ui.tabla.clear() self.ui.tabla.clear() headers = [ "Id", "Origen_x", "Origen_y", "Destino_x", "Destino_y", "Velocidad", "Red", "Green", "Blue", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.particulas)) particulas = [] for particula in self.particulas: particulas.append(particula) particulas.sort(key=lambda particula: particula.Id, reverse=False) row = 0 for particula in particulas: id_widget = QTableWidgetItem(str(particula.Id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(row, 0, id_widget) self.ui.tabla.setItem(row, 1, origen_x_widget) self.ui.tabla.setItem(row, 2, origen_y_widget) self.ui.tabla.setItem(row, 3, destino_x_widget) self.ui.tabla.setItem(row, 4, destino_y_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, rojo_widget) self.ui.tabla.setItem(row, 7, verde_widget) self.ui.tabla.setItem(row, 8, azul_widget) self.ui.tabla.setItem(row, 9, distancia_widget) row += 1 for particula in particulas: self.ui.salida.insertPlainText(str(particula)) @Slot() def ordenar_distancia(self): self.ui.tabla.clear() self.ui.tabla.clear() headers = [ "Id", "Origen_x", "Origen_y", "Destino_x", "Destino_y", "Velocidad", "Red", "Green", "Blue", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.particulas)) particulas = [] for particula in self.particulas: particulas.append(particula) particulas.sort(key=lambda particula: particula.distancia, reverse=True) row = 0 for particula in particulas: id_widget = QTableWidgetItem(str(particula.Id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(row, 0, id_widget) self.ui.tabla.setItem(row, 1, origen_x_widget) self.ui.tabla.setItem(row, 2, origen_y_widget) self.ui.tabla.setItem(row, 3, destino_x_widget) self.ui.tabla.setItem(row, 4, destino_y_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, rojo_widget) self.ui.tabla.setItem(row, 7, verde_widget) self.ui.tabla.setItem(row, 8, azul_widget) self.ui.tabla.setItem(row, 9, distancia_widget) row += 1 for particula in particulas: self.ui.salida.insertPlainText(str(particula)) @Slot() def ordenar_velocidad(self): self.ui.tabla.clear() self.ui.tabla.clear() headers = [ "Id", "Origen_x", "Origen_y", "Destino_x", "Destino_y", "Velocidad", "Red", "Green", "Blue", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.particulas)) particulas = [] for particula in self.particulas: particulas.append(particula) particulas.sort(key=lambda particula: particula.velocidad, reverse=False) row = 0 for particula in particulas: id_widget = QTableWidgetItem(str(particula.Id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(row, 0, id_widget) self.ui.tabla.setItem(row, 1, origen_x_widget) self.ui.tabla.setItem(row, 2, origen_y_widget) self.ui.tabla.setItem(row, 3, destino_x_widget) self.ui.tabla.setItem(row, 4, destino_y_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, rojo_widget) self.ui.tabla.setItem(row, 7, verde_widget) self.ui.tabla.setItem(row, 8, azul_widget) self.ui.tabla.setItem(row, 9, distancia_widget) row += 1 for particula in particulas: self.ui.salida.insertPlainText(str(particula)) @Slot() def dibujar(self): pen = QPen() pen.setWidth(2) for particula in self.particulas: r = particula.rojo g = particula.verde b = particula.azul color = QColor(r, g, b) pen.setColor(color) self.scene.addEllipse(particula.origen_x, particula.origen_y, 4, 4, pen) self.scene.addEllipse(particula.destino_x, particula.destino_y, 4, 4, pen) self.scene.addLine(particula.origen_x, particula.origen_y, particula.destino_x, particula.destino_y, pen) @Slot() def limpiar(self): self.scene.clear() @Slot() def buscar_particula(self): ID = self.ui.buscar_lineEdit.text() encontrado = False for particula in self.particulas: if ID == particula.Id: self.ui.tabla.clear() self.ui.tabla.setRowCount(1) id_widget = QTableWidgetItem(str(particula.Id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(0, 0, id_widget) self.ui.tabla.setItem(0, 1, origen_x_widget) self.ui.tabla.setItem(0, 2, origen_y_widget) self.ui.tabla.setItem(0, 3, destino_x_widget) self.ui.tabla.setItem(0, 4, destino_y_widget) self.ui.tabla.setItem(0, 5, velocidad_widget) self.ui.tabla.setItem(0, 6, rojo_widget) self.ui.tabla.setItem(0, 7, verde_widget) self.ui.tabla.setItem(0, 8, azul_widget) self.ui.tabla.setItem(0, 9, distancia_widget) encontrado = True return if not encontrado: QMessageBox.warning( self, "Atención", f'La particula con Id "{ID}" no fue encontrada') @Slot() def mostrar_tabla(self): self.ui.tabla.setColumnCount(10) headers = [ "Id", "origen_x", "origen_y", "destino_x", "destino_y", "velocidad", "rojo", "verde", "azul", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.particulas)) row = 0 for particula in self.particulas: id_widget = QTableWidgetItem(str(particula.Id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(row, 0, id_widget) self.ui.tabla.setItem(row, 1, origen_x_widget) self.ui.tabla.setItem(row, 2, origen_y_widget) self.ui.tabla.setItem(row, 3, destino_x_widget) self.ui.tabla.setItem(row, 4, destino_y_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, rojo_widget) self.ui.tabla.setItem(row, 7, verde_widget) self.ui.tabla.setItem(row, 8, azul_widget) self.ui.tabla.setItem(row, 9, distancia_widget) row += 1 @Slot() def action_abrir_archivo(self): ubicacion = QFileDialog.getOpenFileName(self, 'Abrir achivo', '.', 'JSON (*.json)')[0] if self.particulas.abrir(ubicacion): QMessageBox.information(self, "Exito", "Se abrió el archivo" + ubicacion) else: QMessageBox.critical(self, "Error", "Error al abrir el archivo " + ubicacion) @Slot() def action_guardar_archivo(self): ubicacion = QFileDialog.getSaveFileName(self, 'Guardar Archivo', '.', 'JSON (*.json)')[0] print(ubicacion) if self.particulas.guardar(ubicacion): QMessageBox.information(self, "Éxito", "Se pudo crear el archivo" + ubicacion) else: QMessageBox.critical(self, "Error", "No se pudo crear el archivo" + ubicacion) @Slot() def click_mostrar(self): self.ui.salida.clear() self.ui.salida.insertPlainText(str(self.particulas)) @Slot() def click_agregar_inicio(self): id = self.ui.id_lineEdit.text() origen_x = self.ui.origen_x_spinBox.value() origen_y = self.ui.origen_y_spinBox.value() destino_x = self.ui.destino_x_spinBox.value() destino_y = self.ui.destino_y_spinBox.value() velocidad = self.ui.velocidad_spinBox.value() red = self.ui.red_spinBox.value() green = self.ui.green_spinBox.value() blue = self.ui.blue_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, red, green, blue) self.particulas.agregar_inicio(particula) @Slot() def click_agregar_final(self): id = self.ui.id_lineEdit.text() origen_x = self.ui.origen_x_spinBox.value() origen_y = self.ui.origen_y_spinBox.value() destino_x = self.ui.destino_x_spinBox.value() destino_y = self.ui.destino_y_spinBox.value() velocidad = self.ui.velocidad_spinBox.value() red = self.ui.red_spinBox.value() green = self.ui.green_spinBox.value() blue = self.ui.blue_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, red, green, blue) self.particulas.agregar_final(particula)
class Widget(QWidget): def __init__(self): QWidget.__init__(self) #Paths self.folderPath = "../Crop_Reports/Bengal Crop Reports PNG/" self.pixmap = QPixmap() #Creates Combobox Choice options self.choices = listdir(self.folderPath) #Creating widgets #Left self.choiceCombo = QComboBox() self.choiceCombo.addItems(self.choices) self.insertionsLabel = QLabel("Insertions") self.insertions = QLineEdit("2") self.substitutionsLabel = QLabel("Substitutions") self.substitutions = QLineEdit("2") self.deletionsLabel = QLabel("Deletions") self.deletions = QLineEdit("2") self.errorsLabel = QLabel("Errors") self.errors = QLineEdit("2") self.searchTextOutputLabel = QLabel("Search Results") self.searchTextOutput = QTextEdit() self.searchTextOutput.setReadOnly(True) self.searchStringLabel = QLabel("Search for a word") self.searchString = QLineEdit() self.searchStringButton = QPushButton("Search") #middle self.nextImage = QPushButton("Next Image") self.previousImage = QPushButton("Previous Image") self.scene = QGraphicsScene() self.image = QGraphicsView(self.scene) self.image.show() self.zoomIn = QPushButton("Zoom In") self.zoomOut = QPushButton("Zoom Out") self.left = QVBoxLayout() self.left.setMargin(10) self.left.addWidget(self.choiceCombo) self.left.addWidget(self.insertionsLabel) self.left.addWidget(self.insertions) self.left.addWidget(self.substitutionsLabel) self.left.addWidget(self.substitutions) self.left.addWidget(self.deletionsLabel) self.left.addWidget(self.deletions) self.left.addWidget(self.errorsLabel) self.left.addWidget(self.errors) self.left.addWidget(self.searchTextOutputLabel) self.left.addWidget(self.searchTextOutput) self.left.addWidget(self.searchStringLabel) self.left.addWidget(self.searchString) self.left.addWidget(self.searchStringButton) self.middle = QVBoxLayout() self.middle.setMargin(10) self.middle.addWidget(self.image) self.middle.addWidget(self.nextImage) self.middle.addWidget(self.previousImage) self.middle.addWidget(self.zoomIn) self.middle.addWidget(self.zoomOut) # QWidget Layout self.layout = QHBoxLayout() self.layout.addLayout(self.left) self.layout.addLayout(self.middle) # Set the layout to the QWidget self.setLayout(self.layout) # Here we connect widgets to functions self.searchStringButton.clicked.connect(self.search_data) self.nextImage.clicked.connect(self.next_image) self.previousImage.clicked.connect(self.previous_image) self.zoomIn.clicked.connect(self.zoom_in) self.zoomOut.clicked.connect(self.zoom_out) # Here we add functions @Slot() def search_data(self): mydata = self.data results = (mydata[mydata["word"] == self.searchString.text()]) output = [ "(" + word + ", " + img + ") " for word, img in zip(results["word"], results["shortName"]) ] print(output) #resets search index to 0 self.searchIndex = 0 self.searchOutput = results print(self.searchOutput) self.searchTextOutput.setText(str(output)) @Slot() def next_image(self): self.searchIndex += 1 if self.searchIndex > len(self.searchOutput) - 1: self.searchIndex = 0 @Slot() def previous_image(self): self.searchIndex -= 1 if self.searchIndex < 0: self.searchIndex = len(self.searchOutput) - 1 @Slot() def zoom_in(self): self.scene.clear() self.pixmap = self.pixmap.scaled(self.pixmap.size().width() * 1.25, self.pixmap.size().height() * 1.25, Qt.KeepAspectRatio) self.scene.addPixmap(self.pixmap) @Slot() def zoom_out(self): self.scene.clear() self.pixmap = self.pixmap.scaled(self.pixmap.size().width() * 0.8, self.pixmap.size().height() * 0.8, Qt.KeepAspectRatio) self.scene.addPixmap(self.pixmap) @Slot() def post_image(self): print("filler")
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.organizador = Organizador() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.scene = QGraphicsScene() self.ui.graficos.setScene(self.scene) self.ui.agregar_inicio_button.clicked.connect(self.agregar_ini) self.ui.agregar_final_button.clicked.connect(self.agregar_fin) self.ui.mostrar_button.clicked.connect(self.mostrar) self.ui.buscar_button.clicked.connect(self.buscar) self.ui.mostrar_tabla_button.clicked.connect(self.mostrar_tabla) self.ui.dibujar_button.clicked.connect(self.dibujar) self.ui.limpiar_button.clicked.connect(self.limpiar) self.ui.generar_button.clicked.connect(self.generar) self.ui.actionAbrir.triggered.connect(self.abrir_archivo) self.ui.actionGuardar.triggered.connect(self.guardar_archivo) self.ui.actionGrafo.triggered.connect(self.generar_grafo) self.ui.actionRecorrido.triggered.connect(self.recorrido) self.ui.id_checkbox.stateChanged.connect(self.ordenar_id) self.ui.velocidad_checkbox.stateChanged.connect(self.ordenar_vel) self.ui.distancia_checkbox.stateChanged.connect(self.ordenar_dis) def recorrido(self): self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText("Recorrido en Profundidad: \n") self.ui.plainTextEdit.insertPlainText( self.organizador.profundidad(self.ui.origen_X.value(), self.ui.origen_y.value())) self.ui.plainTextEdit.insertPlainText("\n\nRecorrido en Amplitud: \n") self.ui.plainTextEdit.insertPlainText( self.organizador.amplitud(self.ui.origen_X.value(), self.ui.origen_y.value())) def generar_grafo(self): self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText( "Grafo (Lista de Adyacencia): \n") self.ui.plainTextEdit.insertPlainText(self.organizador.grafo()) def wheelEvent(self, event): if event.delta() > 0: self.ui.graficos.scale(1.1, 1.1) else: self.ui.graficos.scale(0.9, 0.9) @Slot() def ordenar_id(self): if self.ui.id_checkbox.isChecked(): self.ui.velocidad_checkbox.setChecked(False) self.ui.distancia_checkbox.setChecked(False) self.organizador.orden(False, "id") @Slot() def ordenar_dis(self): if self.ui.distancia_checkbox.isChecked(): self.ui.velocidad_checkbox.setChecked(False) self.ui.id_checkbox.setChecked(False) self.organizador.orden(True, "dis") @Slot() def ordenar_vel(self): if self.ui.velocidad_checkbox.isChecked(): self.ui.distancia_checkbox.setChecked(False) self.ui.id_checkbox.setChecked(False) self.organizador.orden(False, "vel") @Slot() def dibujar(self): pen = QPen() brush = QBrush() pen.setWidth(3) for i in self.organizador: color = QColor(i.red, i.green, i.blue) brush.setStyle(Qt.SolidPattern) brush.setColor(color) pen.setColor(color) self.scene.addEllipse(i.or_x, i.or_y, 7, 7, pen, brush) self.scene.addEllipse(i.de_x, i.de_y, 7, 7, pen, brush) self.scene.addLine((i.or_x) + 3.5, (i.or_y) + 3.5, (i.de_x) + 3.5, (i.de_y) + 3.5, pen) for keys in self.organizador.grafo_dic: text = QGraphicsTextItem(str(keys)) text.setFlag(QGraphicsItem.ItemIsMovable) text.setFont(QFont("TimesNewRoman", 12, QFont.ExtraBold)) self.scene.addItem(text) text.setPos(keys[0], keys[1]) @Slot() def limpiar(self): self.scene.clear() @Slot() def generar(self): self.ui.id.setValue((randint(0, 9) * 10000) + (randint(0, 9) * 1000) + (randint(0, 9) * 100) + (randint(0, 9) * 10) + randint(0, 9)) self.ui.origen_X.setValue(randint(0, 500)) self.ui.origen_y.setValue(randint(0, 500)) self.ui.destino_x.setValue(randint(0, 500)) self.ui.destino_y.setValue(randint(0, 500)) self.ui.vel.setValue(randint(0, 200)) self.ui.red.setValue(randint(0, 255)) self.ui.green.setValue(randint(0, 255)) self.ui.blue.setValue(randint(0, 225)) @Slot() def buscar(self): key = int(self.ui.buscar_line_edit.text()) find = False for particula in self.organizador: if key == particula.id: self.ui.tabla.setColumnCount(10) labels = [ 'ID', 'Origen en X', 'Origen en Y', 'Destino en X', 'Destino en Y', 'Velocidad', 'Distancia', 'Red', 'Green', 'Blue' ] self.ui.tabla.setHorizontalHeaderLabels(labels) self.ui.tabla.setRowCount(1) self.ui.tabla.setItem(0, 0, QTableWidgetItem(str(particula.id))) self.ui.tabla.setItem(0, 1, QTableWidgetItem(str(particula.or_x))) self.ui.tabla.setItem(0, 2, QTableWidgetItem(str(particula.or_y))) self.ui.tabla.setItem(0, 3, QTableWidgetItem(str(particula.de_x))) self.ui.tabla.setItem(0, 4, QTableWidgetItem(str(particula.de_y))) self.ui.tabla.setItem(0, 5, QTableWidgetItem(str(particula.vel))) self.ui.tabla.setItem(0, 6, QTableWidgetItem(str(particula.dis))) self.ui.tabla.setItem(0, 7, QTableWidgetItem(str(particula.red))) self.ui.tabla.setItem(0, 8, QTableWidgetItem(str(particula.green))) self.ui.tabla.setItem(0, 9, QTableWidgetItem(str(particula.blue))) find = True return if find == False: QMessageBox.warning(self, "Atención", f"La partícula '{key}' no fue encontrada") @Slot() def mostrar_tabla(self): self.ui.tabla.setColumnCount(10) labels = [ 'ID', 'Origen en X', 'Origen en Y', 'Destino en X', 'Destino en Y', 'Velocidad', 'Distancia', 'Red', 'Green', 'Blue' ] self.ui.tabla.setHorizontalHeaderLabels(labels) self.ui.tabla.setRowCount(len(self.organizador)) fila = 0 for particula in self.organizador: self.ui.tabla.setItem(fila, 0, QTableWidgetItem(str(particula.id))) self.ui.tabla.setItem(fila, 1, QTableWidgetItem(str(particula.or_x))) self.ui.tabla.setItem(fila, 2, QTableWidgetItem(str(particula.or_y))) self.ui.tabla.setItem(fila, 3, QTableWidgetItem(str(particula.de_x))) self.ui.tabla.setItem(fila, 4, QTableWidgetItem(str(particula.de_y))) self.ui.tabla.setItem(fila, 5, QTableWidgetItem(str(particula.vel))) self.ui.tabla.setItem(fila, 6, QTableWidgetItem(str(particula.dis))) self.ui.tabla.setItem(fila, 7, QTableWidgetItem(str(particula.red))) self.ui.tabla.setItem(fila, 8, QTableWidgetItem(str(particula.green))) self.ui.tabla.setItem(fila, 9, QTableWidgetItem(str(particula.blue))) fila += 1 @Slot() def abrir_archivo(self): ubicacion = QFileDialog.getOpenFileName( self, "Abrir", ".", "JSON (*.json)", )[0] if self.organizador.abrir(ubicacion): QMessageBox.information( self, "Operación Exitosa", "El archivo se abrió con éxito desde la direccion: \n" + ubicacion) self.organizador.borrar_grafo() else: QMessageBox.critical(self, "Error!", "El archivo no se logró abrir") @Slot() def guardar_archivo(self): ubicacion = QFileDialog.getSaveFileName(self, 'Guadar', '.', 'JSON (*.json)')[0] if self.organizador.guardar(ubicacion): QMessageBox.information( self, "Operación Exitosa", "El archivo se guardó con éxito en la direccion: \n" + ubicacion) else: QMessageBox.critical(self, "Error!", "El archivo no se logró guardar") @Slot() def agregar_ini(self): Id = self.ui.id.value() or_x = self.ui.origen_X.value() or_y = self.ui.origen_y.value() ds_x = self.ui.destino_x.value() ds_y = self.ui.destino_y.value() vel = self.ui.vel.value() red = self.ui.red.value() grn = self.ui.green.value() blu = self.ui.blue.value() part = Particula(Id, or_x, or_y, ds_x, ds_y, vel, red, grn, blu) self.organizador.agregar_inicio(part) @Slot() def agregar_fin(self): Id = self.ui.id.value() or_x = self.ui.origen_X.value() or_y = self.ui.origen_y.value() ds_x = self.ui.destino_x.value() ds_y = self.ui.destino_y.value() vel = self.ui.vel.value() red = self.ui.red.value() grn = self.ui.green.value() blu = self.ui.blue.value() part = Particula(Id, or_x, or_y, ds_x, ds_y, vel, red, grn, blu) self.organizador.agregar_final(part) def mostrar(self): self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText(str(self.organizador))
class MainWindow(QMainWindow, Ui_MainWindow): def __init__(self, parent=None): super().__init__(parent) self.setupUi(self) # Kinematics Graphics Setup self.pen = QPen(Qt.black, 3, Qt.DashDotLine, Qt.RoundCap, Qt.RoundJoin) self.graphicsScene = QGraphicsScene() self.graphicsView.setScene(self.graphicsScene) self.graphicsView.setAlignment(Qt.AlignBottom | Qt.AlignLeft) self.graphicsView.show() # Other Widget Initializations self.verticalSlider.setSliderPosition(angles[0]) self.verticalSlider_2.setSliderPosition(angles[1]) self.verticalSlider_3.setSliderPosition(angles[2]) self.textEdit.setPlainText(str(round(lengths[0], PRECISION))) self.textEdit_2.setPlainText(str(round(lengths[1], PRECISION))) self.textEdit_3.setPlainText(str(round(lengths[2], PRECISION))) self.label.setText(str(angles[0])) self.label_2.setText(str(angles[1])) self.label_3.setText(str(angles[2])) self.connect() self.draw_2d() def connect(self): self.verticalSlider.valueChanged[int].connect(self.angle1) self.verticalSlider_2.valueChanged[int].connect(self.angle2) self.verticalSlider_3.valueChanged[int].connect(self.angle3) self.textEdit.textChanged.connect(self.length1) self.textEdit_2.textChanged.connect(self.length2) self.textEdit_3.textChanged.connect(self.length3) def draw_2d(self): self.graphicsScene.clear() point, line = [], [] point.append((0, 0)) for i in range(1, 4): point.append( (point[i - 1][0] + (lengths[i - 1] * math.cos(np.deg2rad(-sum(angles[:i])))), point[i - 1][1] + (lengths[i - 1] * math.sin(np.deg2rad(-sum(angles[:i])))))) line.append( QGraphicsLineItem(point[i - 1][0], point[i - 1][1], point[i][0], point[i][1])) self.graphicsScene.addItem(line[i - 1]) self.label_5.setText("[" + str(round(point[3][0], PRECISION)) + ", " + str(round(-point[3][1], PRECISION)) + "]") @Slot() def angle1(self, value): angles[0] = value self.label.setText(str(value)) self.draw_2d() @Slot() def angle2(self, value): angles[1] = value self.label_2.setText(str(value)) self.draw_2d() @Slot() def angle3(self, value): angles[2] = value self.label_3.setText(str(value)) self.draw_2d() @Slot() def length1(self): lengths[0] = float(self.textEdit.toPlainText()) self.draw_2d() @Slot() def length2(self): lengths[1] = float(self.textEdit_2.toPlainText()) self.draw_2d() @Slot() def length3(self): lengths[2] = float(self.textEdit_3.toPlainText()) self.draw_2d()
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.administrador = Administrador() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.agregar_final_pushButton.clicked.connect(self.click_agregar) self.ui.agregar_inicio_pushButton.clicked.connect( self.click_agregar_inicio) self.ui.mostrar_pushButton.clicked.connect(self.click_mostrar) self.ui.actionAbrir.triggered.connect(self.action_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.action_guardar_archivo) self.ui.mostrar_tabla_pushButton.clicked.connect(self.mostrar_tabla) self.ui.buscar_pushButton.clicked.connect(self.buscar_id) self.ui.dibujar.clicked.connect(self.dibujar) self.ui.limpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def dibujar(self): pen = QPen() pen.setWidth(2) for particula in self.administrador: r = particula.red g = particula.green b = particula.blue color = QColor(r, g, b) pen.setColor(color) self.scene.addEllipse(particula.origen_x, particula.origen_y, 3, 3, pen) self.scene.addEllipse(particula.destino_x, particula.destino_y, 3, 3, pen) self.scene.addLine(particula.origen_x + 3, particula.origen_y + 3, particula.destino_x, particula.destino_y, pen) @Slot() def limpiar(self): self.scene.clear() @Slot() def buscar_id(self): id = self.ui.buscar_lineEdit.text() encontrado = False for particula in self.administrador: if id == particula.id: self.ui.tabla.clear() self.ui.tabla.setRowCount(1) id_widget = QTableWidgetItem(particula.id) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(particula.velocidad) red_widget = QTableWidgetItem(str(particula.red)) green_widget = QTableWidgetItem(str(particula.green)) blue_widget = QTableWidgetItem(str(particula.blue)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(0, 0, id_widget) self.ui.tabla.setItem(0, 1, origen_x_widget) self.ui.tabla.setItem(0, 2, origen_y_widget) self.ui.tabla.setItem(0, 3, destino_x_widget) self.ui.tabla.setItem(0, 4, destino_y_widget) self.ui.tabla.setItem(0, 5, velocidad_widget) self.ui.tabla.setItem(0, 6, red_widget) self.ui.tabla.setItem(0, 7, green_widget) self.ui.tabla.setItem(0, 8, blue_widget) self.ui.tabla.setItem(0, 9, distancia_widget) encontrado = True return if not encontrado: QMessageBox.warning( self, "Atención", f'La particula con el id "{id}" no fue encontrada') @Slot() def mostrar_tabla(self): self.ui.tabla.setColumnCount(10) headers = [ "Id", "Origen_x", "Origen_y", "Destino_x", "Destino_y", "Velocidad", "Red", "Green", "Blue", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.administrador)) row = 0 for particula in self.administrador: id_widget = QTableWidgetItem(particula.id) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(particula.velocidad) red_widget = QTableWidgetItem(str(particula.red)) green_widget = QTableWidgetItem(str(particula.green)) blue_widget = QTableWidgetItem(str(particula.blue)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(row, 0, id_widget) self.ui.tabla.setItem(row, 1, origen_x_widget) self.ui.tabla.setItem(row, 2, origen_y_widget) self.ui.tabla.setItem(row, 3, destino_x_widget) self.ui.tabla.setItem(row, 4, destino_y_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, red_widget) self.ui.tabla.setItem(row, 7, green_widget) self.ui.tabla.setItem(row, 8, blue_widget) self.ui.tabla.setItem(row, 9, distancia_widget) row += 1 @Slot() def action_abrir_archivo(self): ubicacion = QFileDialog.getOpenFileName(self, 'Abrir Archivo', '.', 'JSON (*.json)')[0] if self.administrador.abrir(ubicacion): QMessageBox.information(self, "Éxito", "Se abrió el archivo" + ubicacion) else: QMessageBox.critical(self, "Error", "Error al abrir el archivo" + ubicacion) @Slot() def action_guardar_archivo(self): ubicacion = QFileDialog.getSaveFileName(self, 'Guardar Archivo', '.', 'JSON (*.json)')[0] print(ubicacion) if self.administrador.guardar(ubicacion): QMessageBox.information(self, "Éxito", "Se pudo crear el archivo" + ubicacion) else: QMessageBox.critical(self, "Error", "No se pudo crear el archivo") @Slot() def click_mostrar(self): #self.administrador.mostrar() self.ui.salida.clear() self.ui.salida.insertPlainText(str(self.administrador)) @Slot() def click_agregar(self): id = self.ui.id_lineEdit.text() origen_x = self.ui.origen_x_spinBox.value() origen_y = self.ui.origen_y_spinBox.value() destino_x = self.ui.destino_x_spinBox.value() destino_y = self.ui.destino_y_spinBox.value() velocidad = self.ui.velocidad_lineEdit.text() red = self.ui.red_spinBox.value() green = self.ui.green_spinBox.value() blue = self.ui.blue_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, red, green, blue) self.administrador.agregar_final(particula) #print (id, origen_x, origen_y, destino_x, destino_y, velocidad, red, green, blue) #self.ui.salida.insertPlainText (id + str(origen_x) + str(origen_y) + str(destino_x) + str(destino_y) + #velocidad + str(red) + str(green) + str(blue)) @Slot() def click_agregar_inicio(self): id = self.ui.id_lineEdit.text() origen_x = self.ui.origen_x_spinBox.value() origen_y = self.ui.origen_y_spinBox.value() destino_x = self.ui.destino_x_spinBox.value() destino_y = self.ui.destino_y_spinBox.value() velocidad = self.ui.velocidad_lineEdit.text() red = self.ui.red_spinBox.value() green = self.ui.green_spinBox.value() blue = self.ui.blue_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, red, green, blue) self.administrador.agregar_inicio(particula)
class DisplayWidget(QStackedWidget): imageClicked = Signal(int, QEvent) def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.max_columns = None # Set when presenter starts # Max cols for multimages self.cached_images = {} # Cache read of image from disk self.start() def emitter(self, index, event): self.imageClicked.emit(index, event) def start(self): # Layout for single images self.single_image = QWidget() self.single_image_layout = QGridLayout() self.single_image_view = QGraphicsView() self.single_image_scene = QGraphicsScene() self.single_image_view.setScene(self.single_image_scene) self.single_image_layout.addWidget(self.single_image_view) self.single_image.setLayout(self.single_image_layout) # Layout for multiple images self.multiple_image = QWidget() self.multiple_image_view_layout = QVBoxLayout() self.multiple_image_layout = QGraphicsGridLayout() self.multiple_image_view = QGraphicsView() self.multiple_image_scene = QGraphicsScene() self.multiple_image_view.setScene(self.multiple_image_scene) self.panel = QGraphicsWidget() self.multiple_image_scene.addItem(self.panel) self.multiple_image_view_layout.addWidget(self.multiple_image_view) self.panel.setLayout(self.multiple_image_layout) self.multiple_image.setLayout(self.multiple_image_view_layout) self.addWidget(self.single_image) self.addWidget(self.multiple_image) def setMaxColumns(self, max_cols): self.max_columns = max_cols def images_load(self, images): """ Take list of images and display in main window """ num = len(images) if num == 0: return width = self.width() maxcol = self.max_columns if num < maxcol: maxcol = num colwidth = width / maxcol # Set proper widget for display of multiple or single images if num > 1: self.setCurrentWidget(self.multiple_image) # Clear the layout while self.multiple_image_layout.count(): self.multiple_image_layout.removeAt(0) # Clear the scene for child in self.panel.childItems(): child.setParent(None) else: self.setCurrentWidget(self.single_image) self.single_image_scene.clear() self.single_image_scene.setSceneRect( self.single_image_scene.itemsBoundingRect()) # Display images or image row = 0 col = -1 for index, image in images.items(): col += 1 if col >= maxcol: col = 0 row += 1 # Used any cached reads if index not in self.cached_images.keys(): image_reader = QImageReader() image_reader.setDecideFormatFromContent(True) image_reader.setFileName(image.getFilename()) self.cached_images[index] = image_reader.read() cached_image = self.cached_images[index] pixmap = QPixmap(cached_image) if num > 1: pixmap = pixmap.scaledToWidth(colwidth - 20) rec = MultiImageWidget(pixmap, basename(image.getFilename()), index) rec.imageClicked.connect(self.emitter) self.multiple_image_layout.addItem(rec, row, col) else: self.single_image_scene.addPixmap(pixmap) adjusted = self.multiple_image_scene.itemsBoundingRect() adjusted.adjust(0, 0, 0, 8 * row) self.multiple_image_scene.setSceneRect(adjusted)
class Widget(QWidget): def __init__(self): QWidget.__init__(self) self.x1 = "" self.x3 = "" self.y1 = "" self.y3 = "" self.scene = QGraphicsScene() self.image = QGraphicsView(self.scene) self.image.show() self.submitButton = QPushButton("Submit") self.undoButton = QPushButton("Undo") self.nextReport = QPushButton("Next Report") self.districtText = QLineEdit("") self.prevPageButton = QPushButton("Previous Page") self.nextPageButton = QPushButton("Next Page") self.middle = QVBoxLayout() self.left = QHBoxLayout() self.middle.setMargin(10) self.middle.addWidget(self.image) self.middle.addLayout(self.left) self.bottom = QHBoxLayout() self.left.addWidget(self.prevPageButton) self.left.addWidget(self.nextPageButton) self.middle.addWidget(self.districtText) self.bottom.addWidget(self.nextReport) self.bottom.addWidget(self.undoButton) self.bottom.addWidget(self.submitButton) self.middle.addLayout(self.bottom) # QWidget Layout self.layout = QHBoxLayout() self.layout.addLayout(self.middle) # Set the layout to the QWidget self.setLayout(self.layout) # second # self.data_path = "../Crop_Reports/Manual Check Crop Reports/crop_reports_verified.csv" # self.data = pd.read_csv(self.data_path) self.dir_path = "../Crop_Reports/Bengal Crop Reports PNG/" # connect functions self.nextReport.clicked.connect(self.ignore) self.submitButton.clicked.connect(self.submit) self.undoButton.clicked.connect(self.undo) self.nextPageButton.clicked.connect(self.nextImage) self.prevPageButton.clicked.connect(self.prevImage) self.crop_index = 0 self.page_index = 0 self.zoom = .125 self.out_folder = "../Crop_Reports/Bengal Crop Reports OCR Bounds/" self.finished = os.listdir(self.out_folder) self.data = pd.read_csv( "../Crop_Reports/Manual Check Crop Reports/crop_reports_verified_cleaned_is_good.csv" ) self.data.Date = pd.to_datetime(self.data.Date) self.data = self.data[(self.data.Date > start_date) & (self.data.Date < end_date)] self.columns = ["District", "x1", "y1", "x3", "y3", "Date", "Raw_Text"] self.bound_data = pd.DataFrame(columns=self.columns) self.bound_data_text = "" self.ocr_data_list = list() data = self.data for string in self.finished: string = string.split(".")[0] data = data[data.Path != string] self.reports = list(data.Path) self.dates = list(data.Date) print(u"Data index:", data.index) self.remain_string = "remaining folders " + str(len(self.reports)) self.remainingLabel = QLabel(self.remain_string) self.left.addWidget(self.remainingLabel) temp_path = os.path.join(self.dir_path, self.reports[self.crop_index]) self.report = os.listdir(temp_path) self.postImage() # Sets up drawing capabilities: self.image.setMouseTracking(True) self.image.viewport().installEventFilter(self) self.start = None self.end = None # error here, disregarded bc why not? :) def eventFilter(self, source, event): if event.type( ) == QtCore.QEvent.MouseButtonPress and source is self.image.viewport( ): if self.start is None: self.start = event.pos() elif self.end is None: self.end = event.pos() self.draw_bounding_box() else: print("ERROR!") #print(event.pos()) #print(self.image.mapToScene(event.pos())) @Slot() def submit(self): self.postImage() ["District", "x1", "y1", "x3", "y3", "Date", "Raw_Text"] row = { 'District': self.districtText.text(), 'x1': self.x1, 'y1': self.y1, 'x3': self.x3, 'y3': self.y3, 'Date': self.date, 'Raw_Text': self.bound_data_text } self.bound_data = self.bound_data.append(row, ignore_index=True) print(self.bound_data) self.districtText.setText("") @Slot() def undo(self): print(self.bound_data) self.bound_data.drop(self.bound_data.tail(1).index, inplace=True) print(self.bound_data) @Slot() def ignore(self): self.remain_string = "remaining folders " + str( len(self.reports) - self.crop_index - 1) self.remainingLabel.setText(self.remain_string) path = self.out_folder + self.reports[self.crop_index] + ".csv" print(u"out path:", path) self.bound_data.to_csv(path, index=False) self.bound_data = pd.DataFrame(columns=self.columns) self.crop_index = self.crop_index + 1 self.page_index = 0 self.postImage() @Slot() def nextImage(self): if ((len(self.report) - 1) > self.page_index): self.page_index = self.page_index + 1 else: self.page_index = 0 self.postImage() @Slot() def prevImage(self): if (1 > self.page_index): self.page_index = len(self.report) - 1 else: self.page_index = self.page_index - 1 self.postImage() def postImage(self): self.date = self.dates[self.crop_index] print(u"Date:", self.date) print(self.dates) temp_path = os.path.join(self.dir_path, self.reports[self.crop_index]) report = os.listdir(temp_path) dt.sort_nicely(report) self.report = report self.ocr_data_list = dt.report_to_data(self.reports[self.crop_index]) if (len(self.report) > 0): self.page = self.report[self.page_index] self.page_df = self.ocr_data_list[self.page_index] temp_path = os.path.join(self.dir_path, self.reports[self.crop_index], self.page) self.scene.clear() self.pixmap = QPixmap(temp_path) # adjusts zoom self.pixmap = self.pixmap.scaled( self.pixmap.size().width() * self.zoom, self.pixmap.size().height() * self.zoom, Qt.KeepAspectRatio) self.scene.addPixmap(self.pixmap) # def draw_bounding_box(self, x1, y1, x3, y3): # # start = self.image.mapToScene(x1,y1) # end = self.image.mapToScene(x3,y3) # len_x = end.x()-start.x() # len_y = end.y()-start.y() # rectItem = QGraphicsRectItem(start.x(), start.y(), len_x, len_y) # self.scene.addItem(rectItem) def draw_bounding_box(self): #self.item = QGraphicsPixmapItem(QPixmap(self.df["image"].iloc[self.index])) #self.scene.addItem(self.item) start = self.image.mapToScene(self.start) end = self.image.mapToScene(self.end) self.startSceneLoc = start self.endSceneLoc = end df = self.page_df scale = (1 / self.zoom) self.x1 = start.x() * scale #self.x3 = end.x()*scale #Fixed x length self.x3 = self.x1 + 250 * scale self.y1 = start.y() * scale self.y3 = end.y() * scale df = df[(df.x1 > self.x1) & (df.x3 < self.x3) & (df.y1 > self.y1) & (df.y3 < self.y3)] print(u"x1:", self.x1, u" x3:", self.x3, u" y1:", self.y1, u" y3:", self.y3, u" Scale:", scale) print(u"Current image:", self.report[self.page_index], u" Current df image:", df.image.unique()) print(df.word) self.bound_data_text = " ".join(df.word.to_list()) diff_x = (self.x1 - self.x3) * self.zoom diff_y = (self.y1 - self.y3) * self.zoom rectItem = QGraphicsRectItem(start.x(), start.y(), -diff_x, -diff_y) self.scene.addItem(rectItem) self.start = None self.end = None # def write_to_csv(self): # new_row = {'ocr_report_path': self.reports[self.crop_index], 'date': self.districtText.text()} # self.data = self.data.append(new_row, ignore_index=True) # self.data.to_csv(self.data_path, index=False) def keyPressEvent(self, event): if event.key() == Qt.Key_Return: self.submit()
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.particula = Particula() self.organizador = Organizador() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.abInicio.clicked.connect(self.click_agregar_inicio) self.ui.abFinal.clicked.connect(self.click_agregar_final) self.ui.abMostrar.clicked.connect(self.click_mostrar) self.ui.actionGuardar_.triggered.connect(self.guardar) self.ui.actionAbrir_.triggered.connect(self.abrir) self.ui.abMostrarParticulas.clicked.connect( self.mostrarParticulasTodas) self.ui.abBuscar.clicked.connect(self.buscarParticulaId) self.ui.abLimpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def click_mostrar(self): if (not self.ui.rBId.isChecked() and not self.ui.rBDistancia.isChecked() and not self.ui.rBVelocidad.isChecked()): QMessageBox.about(self, "Advertencia", "Seleccione alguna de las siguientes opciones.") self.click_mostrar_grafico() lista = [] if (self.ui.rBId.isChecked()): lista = sorted(self.organizador.organizador, key=lambda particula: particula.Id, reverse=False) elif (self.ui.rBDistancia.isChecked()): lista = sorted(self.organizador.organizador, key=lambda particula: particula.distancia, reverse=True) elif (self.ui.rBVelocidad.isChecked()): lista = sorted(self.organizador.organizador, key=lambda particula: particula.velocidad, reverse=False) #self.click_mostrar_ordenacion(lista) self.click_mostrar_grafo() @Slot() def click_mostrar_grafico(self): pen = QPen() pen.setWidth(2) for item in self.organizador.organizador: pen.setColor(item.color()) origen_x = item.Xi() origen_y = item.Yi() destino_x = item.Xf() destino_y = item.Yf() self.scene.addEllipse(origen_x, origen_y, 3, 3, pen) self.scene.addEllipse(destino_x, destino_y, 3, 3, pen) self.scene.addLine(origen_x + 3, origen_y + 3, destino_x, destino_y, pen) @Slot() def click_mostrar_ordenacion(self, lista): cadenas = "" self.ui.plainTextEdit.clear() for particula in lista: cadenas += str(particula) + "\n" self.ui.plainTextEdit.insertPlainText(cadenas) @Slot() def click_mostrar_grafo(self): grafo = dict() for particula in self.organizador.organizador: grafo[particula.origenInicial()] = [] grafo[particula.destinoFinal()] = [] for particula in self.organizador.organizador: grafo[particula.origenInicial()].append( (particula.destinoFinal(), particula.distancia)) grafo[particula.destinoFinal()].append( (particula.origenInicial(), particula.distancia)) str = pformat(grafo, width=40, indent=1) self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText(str) print(str) @Slot() def click_agregar_inicio(self): id = self.ui.id.value() origen_x = self.ui.origenX.value() origen_y = self.ui.origenY.value() destino_x = self.ui.destinoX.value() destino_y = self.ui.destinoY.value() velocidad = self.ui.velocidad.value() rojo = self.ui.rojo.value() verde = self.ui.verde.value() azul = self.ui.azul.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, rojo, verde, azul) self.organizador.agregar_inicio(particula) @Slot() def click_agregar_final(self): id = self.ui.id.value() origen_x = self.ui.origenX.value() origen_y = self.ui.origenY.value() destino_x = self.ui.destinoX.value() destino_y = self.ui.destinoY.value() velocidad = self.ui.velocidad.value() rojo = self.ui.rojo.value() verde = self.ui.verde.value() azul = self.ui.azul.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, rojo, verde, azul) self.organizador.agregar_final(particula) @Slot() def guardar(self): ubicacion = QFileDialog.getSaveFileName(self, 'Guardar', '.', 'JSON (*.json)') with open(ubicacion[0], 'w') as archivo: json.dump(self.organizador.guardar(), archivo, indent=4) @Slot() def abrir(self): ubicacion = QFileDialog.getOpenFileName(self, 'Abrir', '.', 'JSON (*.json)') with open(ubicacion[0], 'r') as archivo: self.organizador.get(json.load(archivo)) @Slot() def buscarParticulaId(self): id = self.ui.lineaBuscar.text() encontrado = False for item in self.organizador.organizador: if id == item.getId(): self.ui.tableWidget.clear() self.ui.tableWidget.setRowCount(1) headers = [ "Id", "Origen", "Destino", "Velocidad", "Color", "Distancia" ] self.ui.tableWidget.setHorizontalHeaderLabels(headers) id = QTableWidgetItem(item.getId()) origen = QTableWidgetItem(item.getOrigen()) destino = QTableWidgetItem(item.getDestino()) velocidad = QTableWidgetItem(item.getVelocidad()) color = QTableWidgetItem(item.getColor()) distancia = QTableWidgetItem(item.getDistancia()) self.ui.tableWidget.setItem(0, 0, id) self.ui.tableWidget.setItem(0, 1, origen) self.ui.tableWidget.setItem(0, 2, destino) self.ui.tableWidget.setItem(0, 3, velocidad) self.ui.tableWidget.setItem(0, 4, color) self.ui.tableWidget.setItem(0, 5, distancia) encontrado = True return if not encontrado: QMessageBox.warning( self, "Atención", f'La partícula con identificador "{id}" no fue encontrada') @Slot() def mostrarParticulasTodas(self): row = 0 self.ui.tableWidget.clear() self.ui.tableWidget.setRowCount(len(self.organizador.organizador)) headers = [ "Id", "Origen", "Destino", "Velocidad", "Color", "Distancia" ] self.ui.tableWidget.setHorizontalHeaderLabels(headers) for item in self.organizador.organizador: id = QTableWidgetItem(item.getId()) origen = QTableWidgetItem(item.getOrigen()) destino = QTableWidgetItem(item.getDestino()) velocidad = QTableWidgetItem(item.getVelocidad()) color = QTableWidgetItem(item.getColor()) distancia = QTableWidgetItem(item.getDistancia()) self.ui.tableWidget.setItem(row, 0, id) self.ui.tableWidget.setItem(row, 1, origen) self.ui.tableWidget.setItem(row, 2, destino) self.ui.tableWidget.setItem(row, 3, velocidad) self.ui.tableWidget.setItem(row, 4, color) self.ui.tableWidget.setItem(row, 5, distancia) row += 1 @Slot() def limpiar(self): self.scene.clear() self.ui.plainTextEdit.clear()
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.particulas = AdminParticula() #instancia en la clase MainWindow self.ui = Ui_MainWindow() #crear un objeto de una vista del designer self.ui.setupUi(self) #Las configuraciones que se hacen se incrustan en el objeto self.ui.agregar_inicio_pushButton.clicked.connect(self.click_agregar_inicio) #Decirle que cuando le de click se conecte a la función self.ui.agregar_final_pushButton.clicked.connect(self.click_agregar_final) self.ui.mostrar_pushButton.clicked.connect(self.mostrar) #Conectar el evento del boton a la función #Conectar eventos al presionar respectivos botones abrir y guardar #Triggered -> Disparó self.ui.actionAbrir.triggered.connect(self.action_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.action_guardar_archivo) #Conexión a botones tabla self.ui.mostrar_tabla_pushButton.clicked.connect(self.action_mostrar_tabla) self.ui.buscar_pushButton.clicked.connect(self.action_buscar_id) #Conexión a botones dibujar self.ui.draw_pushButton.clicked.connect(self.action_dibujar) self.ui.clear_pushButton.clicked.connect(self.action_limpiar) #Crear Escena self.scene = QGraphicsScene() #Crear escena self.ui.graphicsView.setScene(self.scene) #Insertar scene #Button sort Plane and Edit self.ui.sort_plane_pushButton.clicked.connect(self.action_sort_plane) #Button Busquedas en profundidad y en anchura self.ui.busqueda_grafo_pushButton.clicked.connect(self.action_busqueda_grafo) #Busqueda en grafo profundidad y anchura @Slot() def action_busqueda_grafo(self): grafo = self.particulas.get_grafo() listAux = list(grafo.keys()) arista_x = self.ui.nodo_x_spinBox.value() arista_y = self.ui.nodo_y_spinBox.value() profundidad = False if arista_x == 0 and arista_y == 0: if self.ui.tipo_busqueda_comboBox.currentText() == "Profundidad": recorrido_grafo = busqueda_profundidad(grafo, listAux[0]) profundidad = True elif self.ui.tipo_busqueda_comboBox.currentText() == "Anchura": recorrido_grafo = busqueda_amplitud(grafo, listAux[0]) else: return -1 else: origen = (arista_x, arista_y) if self.ui.tipo_busqueda_comboBox.currentText() == "Profundidad": recorrido_grafo = busqueda_profundidad(grafo, origen) profundidad = True elif self.ui.tipo_busqueda_comboBox.currentText() == "Anchura": recorrido_grafo = busqueda_amplitud(grafo, origen) else: return -1 self.ui.mostrar_grafo_plainTextEdit.clear() if profundidad: self.ui.mostrar_grafo_plainTextEdit.insertPlainText("Profundidad: \n") else: self.ui.mostrar_grafo_plainTextEdit.insertPlainText("Anchura: \n") for i in recorrido_grafo: self.ui.mostrar_grafo_plainTextEdit.insertPlainText(str(i)) self.ui.mostrar_grafo_plainTextEdit.insertPlainText("\n") #self.ui.mostrar_grafo_plainTextEdit.insertPlainText(pformat(recorrido_grafo, width=20)) #print(recorrido_grafo) #Odenamientos sort() @Slot() def action_sort_plane(self): if self.ui.desicion_plane_comboBox.currentText() == "Id (ascendente)": self.particulas.sort_id() elif self.ui.desicion_plane_comboBox.currentText() == "Distancia (descendente)": self.particulas.sort_distancia() elif self.ui.desicion_plane_comboBox.currentText() == "Velocidad (ascendente)": self.particulas.sort_velocidad() else: return -1 if len(self.particulas) > 0: QMessageBox.information( self, "Éxito", "Se ordeno con éxito" ) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def action_dibujar(self): if len(self.particulas) > 0: pen = QPen() #Definir una pluma pen.setWidth(2) #Tamaño en pixelex del ancho de la pluma #Ingresar el color for particula in self.particulas: color = QColor(particula.red, particula.green, particula.blue) pen.setColor(color) self.scene.addEllipse(particula.origen_x, particula.origen_y, 3, 3, pen) #Dibujar un elipse -> (0, 0, 3, 3) ->posX, posY, radio, radio self.scene.addEllipse(particula.destino_x, particula.destino_y, 3, 3, pen) self.scene.addLine(particula.origen_x, particula.origen_y, particula.destino_x, particula.destino_y, pen) #Agregar linea entre los dos elipses else: QMessageBox.warning( self, "Atención", 'No hay partículas registradas' ) @Slot() def action_limpiar(self): self.scene.clear() #Reestablecer la escala al predeterminado self.ui.graphicsView.setTransform(QTransform()) @Slot() def action_buscar_id(self): busca_id = self.ui.buscar_lineEdit.text() #Obtener el texto del lineEdit if(len(busca_id) > 0): busca_id = int(busca_id) encontrado = False for particula in self.particulas: if busca_id == particula.id: self.ui.table.clear() #Limpiar tabla self.table_add_column() self.ui.table.setRowCount(1) self.table_widget(0, particula) encontrado = True return if not encontrado: QMessageBox.warning( self, "Atención", f'La partícula con el id "{busca_id}" no fue encontrada' ) @Slot() def action_mostrar_tabla(self): self.table_add_column() self.ui.table.setRowCount(len(self.particulas)) #Agregar filas a la tabla row = 0 #Contador de filas for particula in self.particulas: self.table_widget(row, particula) row += 1 def table_widget(self, row, particula:Particula): #construcción de Widgets id_widget = QTableWidgetItem(str(particula.id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) red_widget = QTableWidgetItem(str(particula.red)) green_widget = QTableWidgetItem(str(particula.green)) blue_widget = QTableWidgetItem(str(particula.blue)) distancia_widget = QTableWidgetItem(str(particula.distancia)) #Ingresar información en la tabla self.ui.table.setItem(row, 0, id_widget) self.ui.table.setItem(row, 1, origen_x_widget) self.ui.table.setItem(row, 2, origen_y_widget) self.ui.table.setItem(row, 3, destino_x_widget) self.ui.table.setItem(row, 4, destino_y_widget) self.ui.table.setItem(row, 5, velocidad_widget) self.ui.table.setItem(row, 6, red_widget) self.ui.table.setItem(row, 7, green_widget) self.ui.table.setItem(row, 8, blue_widget) self.ui.table.setItem(row, 9, distancia_widget) def table_add_column(self): self.ui.table.setColumnCount(10) #Generar columnas en la tabla #Nombre de los headers en una lista headers = ["Id", "Origen x", "Origen y", "Destino x", "Destino y", "Velocidad", "Red", "Green", "Blue", "Distancia"] self.ui.table.setHorizontalHeaderLabels(headers) #Ingresar el nombre de las columnas @Slot() def action_abrir_archivo(self): #print("Abrir archivo") ubicacion = QFileDialog.getOpenFileName( #Regresa ubicación del archivo modo de apertura self, 'Abrir Archivo', '.', #Decirle desde la carpeta que se esta trabajando 'JSON (*.json)' )[0] if self.particulas.abrir(ubicacion): self.particulas.mandar_particulas_grafo() QMessageBox.information( self, "Éxito", "Se abrió el archivo " + ubicacion ) else: QMessageBox.critical( self, "Error", "Error al abrir el archivo " + ubicacion ) @Slot() def action_guardar_archivo(self): #print('Guardar Archivo') ubicacion = QFileDialog.getSaveFileName( #Método para regresar la ubicación self, 'Guardar Archivo', '.', 'JSON (*.json)' )[0] #pirmera posición de la tupla #print(ubicacion) if self.particulas.guardar(ubicacion): #invocar método de AdminParticula() QMessageBox.information( self, "Éxito", "Se pudo crear el archivo " + ubicacion ) else: QMessageBox.critical( self, "Error", "No se pudo crear el archivo " + ubicacion ) def limpiar(self): self.ui.id_spinBox.setValue(0) self.ui.origenx_spinBox.setValue(0) self.ui.origeny_spinBox.setValue(0) self.ui.destinox_spinBox.setValue(0) self.ui.destinoy_spinBox.setValue(0) self.ui.velocidad_spinBox.setValue(0) self.ui.red_spinBox.setValue(0) self.ui.green_spinBox.setValue(0) self.ui.blue_spinBox.setValue(0) def entrada_datos(self): id = self.ui.id_spinBox.value() origen_x = self.ui.origenx_spinBox.value() origen_y = self.ui.origeny_spinBox.value() destino_x = self.ui.destinox_spinBox.value() destino_y = self.ui.destinoy_spinBox.value() velocidad = self.ui.velocidad_spinBox.value() red = self.ui.red_spinBox.value() green = self.ui.green_spinBox.value() blue = self.ui.blue_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, red, green, blue) return particula @Slot() #Decirle que la siguiente función detectara eventos click def click_agregar_inicio(self): self.particulas.agregar_inicio(self.entrada_datos()) self.limpiar() @Slot() def click_agregar_final(self): self.particulas.agregar_final(self.entrada_datos()) self.limpiar() @Slot() def mostrar(self): self.ui.salida.clear() self.ui.salida.insertPlainText(str(self.particulas)) self.ui.salida_plainTextEdit.clear() self.ui.salida_plainTextEdit.insertPlainText(self.particulas.mostrar_grafo()) print("Grafo: ", self.particulas.mostrar_grafo())
class ScreenshotView(QGraphicsView): def __init__(self, parent, screen, parm, gradient_edit, ramp_sketch): super(ScreenshotView, self).__init__(parent) self.scene = QGraphicsScene(parent) self.setScene(self.scene) self.parm = parm # type: hou.Parm self.screen = screen geometry = screen.geometry() if sys.platform == "darwin": self.screen_pixmap = screen.grabWindow(0, geometry.x(), geometry.y(), geometry.width(), geometry.height()) else: self.screen_pixmap = screen.grabWindow(0) self.screen_image = self.screen_pixmap.toImage() # type: QImage self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOff) self.setFrameStyle(QFrame.NoFrame) self.scene.clear() self.setGeometry(screen.geometry()) self.setSceneRect(0, 0, self.screen_pixmap.width(), self.screen_pixmap.height()) self.scene.addPixmap(self.screen_pixmap) self.setMouseTracking(True) self.color_info = ColorInformation() self.scene.addItem(self.color_info) self.gradient_edit = gradient_edit self.ramp_sketch = ramp_sketch self.path = QPainterPath() self.draw_path = False self.path_item = QGraphicsPathItem() if not self.ramp_sketch: self.path_item.setPen(QPen(QColor(0, 200, 100, 200), 2)) else: self.path_item.setPen(QPen(QColor(200, 200, 50, 255), 4)) self.scene.addItem(self.path_item) self.colors = [] # type: list[QColor] self.positions = [] # type: list[QPoint] self.picked_color = QColor() self.disable_gamma_correction = False if self.underMouse(): self.color_info.show() else: self.color_info.hide() self.is_macos = sys.platform == "darwin" # TODO: ??? if self.is_macos: self.color_info.show() if self.ramp_sketch: self.color_info.hide() def update_info(self, pos): image_pos = pos * self.screen.devicePixelRatio() if self.screen_image.rect().contains(image_pos): self.color_info.color = QColor( self.screen_image.pixel(image_pos.x(), image_pos.y())) self.color_info.setPos(pos) self.color_info.pos = pos def write_ramp_sketch(self): if len(self.positions) < 2: return positions = np.array([(float(p.x()), float(-p.y())) for p in self.positions]) min_point = positions.min(axis=0) max_point = positions.max(axis=0) ramp_range = max_point - min_point if not np.any((ramp_range == 0.0)): norm_positions = (positions - min_point) / ramp_range geo_points = [] geo_points.append( hou.Vector3(norm_positions[0][0], norm_positions[0][1], 0.0)) left = 0.0 for pt in norm_positions[1:-1]: if pt[0] >= left: left = pt[0] geo_points.append(hou.Vector3(pt[0], pt[1], 0.0)) geo_points.append( hou.Vector3(norm_positions[-1][0], norm_positions[-1][1], 0.0)) ramp_geo = hou.Geometry() # type: hou.Geometry ramp_points = ramp_geo.createPoints(geo_points) ramp_geo.createPolygons((ramp_points, ), False) resample_verb = hou.sopNodeTypeCategory().nodeVerb( "resample") # type: hou.SopVerb resample_verb.setParms({"length": 0.04}) resample_verb.execute(ramp_geo, [ramp_geo]) facet_verb = hou.sopNodeTypeCategory().nodeVerb( "facet") # type: hou.SopVerb facet_verb.setParms({"inline": 1, "inlinedist": 0.003}) facet_verb.execute(ramp_geo, [ramp_geo]) ramp_poly = ramp_geo.prim(0) ramp_points = ramp_poly.points() ramp_basis = hou.rampBasis.BSpline if self.disable_gamma_correction else hou.rampBasis.Linear basis = [] keys = [] values = [] for point in ramp_points: # type: hou.Point basis.append(ramp_basis) pos = point.position() keys.append(pos.x()) values.append(pos.y()) ramp = hou.Ramp(basis, keys, values) self.parm.set(ramp) self.parm.pressButton() def write_color_ramp(self): if len(self.colors) < 2: return color_points = [] vlast_color = hou.Vector3(hou.qt.fromQColor(self.colors[0])[0].rgb()) last_color_index = 0 color_points.append((vlast_color, 0)) # remove same keys in a row for index, color in enumerate(self.colors[1:]): color_index = index + 1 vcolor = hou.Vector3(hou.qt.fromQColor(color)[0].rgb()) dist = vcolor.distanceTo(vlast_color) if dist > TOLERANCE: # if color_index - last_color_index > 1 and dist > SHARP_PRECISION: # color_points.append((hou.Vector3(vlast_color), color_index - 1)) color_points.append((hou.Vector3(vcolor), color_index)) vlast_color = vcolor last_color_index = color_index if color_points[-1][1] < (len(self.colors) - 1): color_points.append( (hou.Vector3(hou.qt.fromQColor(self.colors[-1])[0].rgb()), len(self.colors) - 1)) # Create a polyline representing ramp and remove inline points with Facet SOP points = [color_point[0] for color_point in color_points] pos = [color_point[1] for color_point in color_points] ramp_geo = hou.Geometry() pos_attrib = ramp_geo.addAttrib(hou.attribType.Point, "ramp_pos", 0.0, create_local_variable=False) ramp_points = ramp_geo.createPoints(points) fnum_points = float(len(self.colors) - 1) for ptnum, point in enumerate(ramp_points): # type: (int, hou.Point) point.setAttribValue(pos_attrib, float(pos[ptnum]) / fnum_points) ramp_poly = ramp_geo.createPolygons((ramp_points, ), False)[0] # type: hou.Face facet_verb = hou.sopNodeTypeCategory().nodeVerb( "facet") # type: hou.SopVerb facet_verb.setParms({"inline": 1, "inlinedist": 0.02}) facet_verb.execute(ramp_geo, [ramp_geo]) ramp_poly = ramp_geo.prim(0) ramp_points = ramp_poly.points() linear = hou.rampBasis.Linear basis = [] keys = [] values = [] pos_attrib = ramp_geo.findPointAttrib("ramp_pos") for point in ramp_points: # type: hou.Point basis.append(linear) keys.append(point.attribValue(pos_attrib)) values.append(tuple(point.position())) if not self.disable_gamma_correction: values = [np.power(v, 2.2) for v in values] ramp = hou.Ramp(basis, keys, values) self.parm.set(ramp) self.parm.pressButton() def enterEvent(self, event): if not self.ramp_sketch: self.color_info.show() def leaveEvent(self, event): self.color_info.hide() def mouseMoveEvent(self, event): pos = event.pos() #* self.screen.devicePixelRatio() self.update_info(pos) # TODO: ??? if self.is_macos and not self.ramp_sketch: self.color_info.show() if self.draw_path: path = self.path_item.path() path.lineTo(pos) self.path_item.setPath(path) self.colors.append(self.color_info.color) self.positions.append(pos) return QGraphicsView.mouseMoveEvent(self, event) def mousePressEvent(self, event): modifiers = QApplication.keyboardModifiers() if modifiers & Qt.ShiftModifier: self.disable_gamma_correction = True if self.gradient_edit or self.ramp_sketch: self.draw_path = True self.path.moveTo(event.pos()) self.path_item.setPath(self.path) else: self.picked_color = self.color_info.color def mouseReleaseEvent(self, event): if self.gradient_edit and self.draw_path: self.write_color_ramp() elif self.ramp_sketch and self.draw_path: self.write_ramp_sketch() elif not self.gradient_edit: out_color = hou.qt.fromQColor(self.picked_color)[0].rgb() if not self.disable_gamma_correction: out_color = np.power(out_color, 2.2) if isinstance(self.parm, hou.ParmTuple) and len(self.parm) == 4: alpha = self.parm[3].eval() out_color = np.append(out_color, alpha) self.parm.set(out_color) if self.parent() is not None: self.parent().mouseReleaseEvent(event)
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.adm_part = Adm_part() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.agregar_final_pushButton.clicked.connect(self.click_agregar) self.ui.agregar_inicio_pushButton.clicked.connect( self.click_agregar_inicio) self.ui.mostrar_pushButton.clicked.connect(self.click_mostrar) self.ui.actionAbrir.triggered.connect(self.action_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.action_guardar_archivo) self.ui.mostrar_tabla_pushButton.clicked.connect(self.mostrar_tabla) self.ui.buscar_pushButton.clicked.connect(self.buscar_id) self.ui.dibujar.clicked.connect(self.dibujar) self.ui.limpiar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def dibujar(self): pen = QPen() pen.setWidth(2) for particula in self.adm_part: r = int(particula.rojo) g = int(particula.verde) b = int(particula.azul) color = QColor(r, g, b) pen.setColor(color) origen_x = int(particula.origen_x) origen_y = int(particula.origen_y) destino_x = int(particula.destino_x) destino_y = int(particula.destino_y) self.scene.addEllipse(origen_x, origen_y, 3, 3, pen) self.scene.addEllipse(destino_x, destino_y, 3, 3, pen) self.scene.addLine(origen_x + 3, origen_y + 3, destino_x, destino_y, pen) @Slot() def limpiar(self): self.scene.clear() @Slot() def buscar_id(self): id = self.ui.buscar_spinBox.value() encontrado = False for particula in self.adm_part: if id == particula.id: self.ui.tabla.clear() self.ui.tabla.setRowCount(1) id_widget = QTableWidgetItem(str(particula.id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(0, 0, id_widget) self.ui.tabla.setItem(0, 1, origen_x_widget) self.ui.tabla.setItem(0, 2, origen_y_widget) self.ui.tabla.setItem(0, 3, destino_x_widget) self.ui.tabla.setItem(0, 4, destino_y_widget) self.ui.tabla.setItem(0, 5, velocidad_widget) self.ui.tabla.setItem(0, 6, rojo_widget) self.ui.tabla.setItem(0, 7, verde_widget) self.ui.tabla.setItem(0, 8, azul_widget) self.ui.tabla.setItem(0, 9, distancia_widget) encontrado = True return if not encontrado: QMessageBox.warning( self, "Atención", f'La particula con el ID "{id}" no fue encontrada') @Slot() def mostrar_tabla(self): self.ui.tabla.setColumnCount(10) headers = [ "ID", "Origen en x", "Origen en y", "Destino en x", "Destino en y", "Velocidad", "Rojo", "Verde", "Azul", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.adm_part)) row = 0 for particula in self.adm_part: id_widget = QTableWidgetItem(str(particula.id)) origen_x_widget = QTableWidgetItem(str(particula.origen_x)) origen_y_widget = QTableWidgetItem(str(particula.origen_y)) destino_x_widget = QTableWidgetItem(str(particula.destino_x)) destino_y_widget = QTableWidgetItem(str(particula.destino_y)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) rojo_widget = QTableWidgetItem(str(particula.rojo)) verde_widget = QTableWidgetItem(str(particula.verde)) azul_widget = QTableWidgetItem(str(particula.azul)) distancia_widget = QTableWidgetItem(str(particula.distancia)) self.ui.tabla.setItem(row, 0, id_widget) self.ui.tabla.setItem(row, 1, origen_x_widget) self.ui.tabla.setItem(row, 2, origen_y_widget) self.ui.tabla.setItem(row, 3, destino_x_widget) self.ui.tabla.setItem(row, 4, destino_y_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, rojo_widget) self.ui.tabla.setItem(row, 7, verde_widget) self.ui.tabla.setItem(row, 8, azul_widget) self.ui.tabla.setItem(row, 9, distancia_widget) row += 1 @Slot() def action_abrir_archivo(self): #print('abrir_archivo') ubicacion = QFileDialog.getOpenFileName(self, 'Abrir archivo', '.', 'JSON(*.json)')[0] if self.adm_part.abrir(ubicacion): QMessageBox.information(self, "Exito", "Se abrió el archivo " + ubicacion) else: QMessageBox.critical(self, "Error", "No se pudo abrir el archivo " + ubicacion) @Slot() def action_guardar_archivo(self): #print('guardar_archivo') ubicacion = QFileDialog.getSaveFileName(self, 'Guardar Archivo', '.', 'JSON (*.json)')[0] print(ubicacion) if self.adm_part.guardar(ubicacion): QMessageBox.information(self, "Exito", "Se pudo crear el archivo " + ubicacion) else: QMessageBox.critical(self, "Error", "No se pudo crear el archivo " + ubicacion) @Slot() def click_mostrar(self): #self.adm_part.mostrar() self.ui.plainTextEdit.clear() self.ui.plainTextEdit.insertPlainText(str(self.adm_part)) @Slot() def click_agregar(self): id = self.ui.id_spinBox.value() origen_x = self.ui.origen_x_spinBox.value() origen_y = self.ui.origen_y_spinBox.value() destino_x = self.ui.destino_x_spinBox.value() destino_y = self.ui.destino_y_spinBox.value() velocidad = self.ui.velocidad_spinBox.value() rojo = self.ui.rojo_spinBox.value() azul = self.ui.azul_spinBox.value() verde = self.ui.verde_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, rojo, verde, azul) self.adm_part.agregar_final(particula) #print(id,origen_x,origen_y,destino_x,destino_y,rojo,azul,verde) #self.ui.plainTextEdit.insertPlainText(id + origen_x + origen_y + #destino_x + destino_y + rojo + azul + verde) @Slot() def click_agregar_inicio(self): id = self.ui.id_spinBox.value() origen_x = self.ui.origen_x_spinBox.value() origen_y = self.ui.origen_y_spinBox.value() destino_x = self.ui.destino_x_spinBox.value() destino_y = self.ui.destino_y_spinBox.value() velocidad = self.ui.velocidad_spinBox.value() rojo = self.ui.rojo_spinBox.value() azul = self.ui.azul_spinBox.value() verde = self.ui.verde_spinBox.value() particula = Particula(id, origen_x, origen_y, destino_x, destino_y, velocidad, rojo, verde, azul) self.adm_part.agregar_inicio(particula)
class Widget(QWidget): def __init__(self): QWidget.__init__(self) self.scene = QGraphicsScene() self.image = QGraphicsView(self.scene) self.image.show() self.submitButton = QPushButton("Submit") self.dateText = QLineEdit("") self.prevPageButton = QPushButton("Previous Page") self.nextPageButton = QPushButton("Next Page") self.middle = QVBoxLayout() self.left = QHBoxLayout() self.middle.setMargin(10) self.middle.addWidget(self.image) self.middle.addLayout(self.left) self.left.addWidget(self.prevPageButton) self.left.addWidget(self.nextPageButton) self.middle.addWidget(self.dateText) self.middle.addWidget(self.submitButton) # QWidget Layout self.layout = QHBoxLayout() self.layout.addLayout(self.middle) # Set the layout to the QWidget self.setLayout(self.layout) #second self.data_path = "../Crop_Reports/Manual Check Crop Reports/crop_reports_verified.csv" self.data = pd.read_csv(self.data_path) self.dir_path = "../Crop_Reports/Bengal Crop Reports PNG/" #connect functions self.submitButton.clicked.connect(self.submit) self.nextPageButton.clicked.connect(self.nextImage) self.prevPageButton.clicked.connect(self.prevImage) self.crop_index = 0 self.page_index = 0 self.zoom = .2 self.reports = os.listdir(self.dir_path) reports_already_done = set(self.data.ocr_report_path) lst = self.reports for finished in reports_already_done: lst.remove(finished) self.reports = lst remain_string = "remaining folders " + str(len(self.reports)) self.remainingLabel = QLabel(remain_string) self.left.addWidget(self.remainingLabel) temp_path = os.path.join(self.dir_path, self.reports[self.crop_index]) self.report = os.listdir(temp_path) if (len(self.report) > 0): self.page = self.report[self.page_index] temp_path = os.path.join(self.dir_path, self.reports[self.crop_index], self.page) print(temp_path) self.pixmap = QPixmap(temp_path) self.scene.clear() self.pixmap = QPixmap(temp_path) #adjusts zoom self.pixmap = self.pixmap.scaled( self.pixmap.size().width() * self.zoom, self.pixmap.size().height() * self.zoom, Qt.KeepAspectRatio) self.scene.addPixmap(self.pixmap) #key bindings def key_press(event): key = event.char print(key, 'is pressed') @Slot() def submit(self): self.write_to_csv() self.page_index = 0 self.crop_index = self.crop_index + 1 self.postImage() self.dateText.setText("") remain_string = "remaining folders " + str( len(self.reports) - self.crop_index) self.remainingLabel.setText(remain_string) @Slot() def nextImage(self): if ((len(self.report) - 1) > self.page_index): self.page_index = self.page_index + 1 else: self.page_index = 0 self.postImage() @Slot() def prevImage(self): if (1 > self.page_index): self.page_index = len(self.report) - 1 else: self.page_index = self.page_index - 1 self.postImage() def postImage(self): temp_path = os.path.join(self.dir_path, self.reports[self.crop_index]) self.report = os.listdir(temp_path) if (len(self.report) > 0): print(self.page_index) self.page = self.report[self.page_index] temp_path = os.path.join(self.dir_path, self.reports[self.crop_index], self.page) print(temp_path) self.scene.clear() self.pixmap = QPixmap(temp_path) #adjusts zoom self.pixmap = self.pixmap.scaled( self.pixmap.size().width() * self.zoom, self.pixmap.size().height() * self.zoom, Qt.KeepAspectRatio) self.scene.addPixmap(self.pixmap) def write_to_csv(self): new_row = { 'ocr_report_path': self.reports[self.crop_index], 'date': self.dateText.text() } self.data = self.data.append(new_row, ignore_index=True) self.data.to_csv(self.data_path, index=False) def keyPressEvent(self, event): if event.key() == Qt.Key_Return: self.submit()
class MainWindow(QMainWindow): def __init__(self): super().__init__() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui = Ui_MainWindow() self.ui.setupUi(self) self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador = Capturador() self.ui.pushButton.clicked.connect(self.click) self.ui.pushButton_2.clicked.connect(self.mostrar) self.ui.actionGuardar.triggered.connect(self.guardar) self.ui.actionAbrir_2.triggered.connect(self.abrir) self.ui.pushButton_3.clicked.connect(self.ordenar_velocidad) self.ui.pushButton_4.clicked.connect(self.ordenar_distancia) @Slot() def ordenar_velocidad(self): self.scene.clear() self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador.ordenar_velocidad() y = 0 for particula in self.capturador.lista: self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addLine(0, y, particula.distancia, y, self.pen) y = y + 2 @Slot() def ordenar_distancia(self): self.scene.clear() self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador.ordenar_distancia() y = 0 for particula in self.capturador.lista: self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addLine(0, y, particula.distancia, y, self.pen) y = y + 2 @Slot() def guardar(self): self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) file = QFileDialog.getSaveFileName(self, 'Guardar archivo...', '.', 'JSON (*.json)') print(file) self.capturador.guardar(file[0], self.pen, self.scene) @Slot() def abrir(self): file = QFileDialog.getOpenFileName(self, 'Abrir archivo', '.', 'JSON (*.json)') self.capturador.recuperar(file[0]) @Slot() def mostrar(self): self.scene.clear() self.scene.addLine(0, 0, 499, 0, self.pen) y = 0 for particula in self.capturador.lista: self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addLine(0, y, particula.distancia, y, self.pen) y = y + 2 #for particula in self.capturador.lista: # self.ui.plainTextEdit.insertPlainText(str(particula)) # self.pen.setColor(QColor(particula.red, particula.green, particula.blue)) # self.scene.addEllipse(particula.origenX, particula.origenY, 5, 5, self.pen, QBrush(QColor(particula.red, 10,particula.green, particula.blue))) #self.scene.addLine(particula.origenX, particula.origenY, particula.destinoX, particula.destinoY, self.pen) #self.paqueteria.mostrar() @Slot() def click(self): id = self.ui.lineEdit.text() origenX = self.ui.lineEdit_2.text() origenY = self.ui.lineEdit_6.text() destinoX = self.ui.lineEdit_3.text() destinoY = self.ui.lineEdit_7.text() velocidad = self.ui.lineEdit_4.text() red = self.ui.lineEdit_5.text() green = self.ui.lineEdit_8.text() blue = self.ui.lineEdit_9.text() print(id, origenX, origenY, destinoX, destinoY, velocidad, red, green, blue) partiula = Particula() partiula.id = id partiula.origenX = int(origenX) partiula.origenY = int(origenY) partiula.destinoX = int(destinoX) partiula.destinoY = int(destinoY) partiula.distancia = math.sqrt( pow((int(destinoX) - int(origenX)), 2) + pow((int(destinoY) - int(origenY)), 2)) partiula.red = int(red) partiula.green = int(green) partiula.blue = int(blue) partiula.velocidad = int(velocidad) self.capturador.agregar(partiula) msg = QMessageBox.information( self, 'Exito', 'Se agrego paquete con exito' ) #Ventana de mensaje de la libreria QMessageBox self.ui.lineEdit.clear() #Limpiar campos self.ui.lineEdit_2.clear() self.ui.lineEdit_3.clear() self.ui.lineEdit_4.clear() self.ui.lineEdit_5.clear() self.ui.lineEdit_6.clear() self.ui.lineEdit_7.clear() self.ui.lineEdit_8.clear() self.ui.lineEdit_9.clear()
class Widget(QWidget): def __init__(self): QWidget.__init__(self) self.index_districts = index_districts self.x1 = "" self.x3 = "" self.y1 = "" self.y3 = "" self.scene = QGraphicsScene() self.image = QGraphicsView(self.scene) self.image.show() self.submitButton = QPushButton("Submit") self.undoButton = QPushButton("Undo") self.nextReport = QPushButton("Next Report") self.badButton = QPushButton("BAD") self.goodButton = QPushButton("Good") self.noDataButton = QPushButton("No Data") self.districtText = QLineEdit("") self.cattleLabel = QLineEdit("Cattle:") self.top = QHBoxLayout() self.top.addWidget(self.cattleLabel) self.prevPageButton = QPushButton("Previous Page") self.nextPageButton = QPushButton("Next Page") self.middle = QVBoxLayout() self.left = QHBoxLayout() self.middle.setMargin(10) self.middle.addWidget(self.image) self.middle.addLayout(self.top) self.middle.addLayout(self.left) self.bottom = QHBoxLayout() self.left.addWidget(self.prevPageButton) self.left.addWidget(self.nextPageButton) self.middle.addWidget(self.districtText) self.bottom.addWidget(self.badButton) self.bottom.addWidget(self.noDataButton) self.bottom.addWidget(self.goodButton) self.bottom.addWidget(self.nextReport) self.bottom.addWidget(self.undoButton) self.bottom.addWidget(self.submitButton) self.middle.addLayout(self.bottom) # QWidget Layout self.layout = QHBoxLayout() self.layout.addLayout(self.middle) # Set the layout to the QWidget self.setLayout(self.layout) # second # self.data_path = "../Crop_Reports/Manual Check Crop Reports/crop_reports_verified.csv" # self.data = pd.read_csv(self.data_path) self.dir_path = "../Crop_Reports/Bengal Crop Reports PNG/" # connect functions self.nextReport.clicked.connect(self.ignore) self.submitButton.clicked.connect(self.submit) self.undoButton.clicked.connect(self.undo) self.nextPageButton.clicked.connect(self.nextImage) self.prevPageButton.clicked.connect(self.prevImage) self.crop_index = 0 self.page_index = 0 self.zoom = .2 self.out_folder = "../Crop_Reports/Bengal Famine Data/" self.finished = os.listdir(self.out_folder) self.data = pd.read_csv("../Crop_Reports/Manual Check Crop Reports/crop_reports_verified_cleaned_is_good.csv") self.data.Date = pd.to_datetime(self.data.Date) self.data = self.data[(self.data.Date > start_date) & (self.data.Date < end_date)] self.columns = ["District","Date","famine_code"] self.bound_data = pd.DataFrame(columns = self.columns) self.bound_data_text = "" self.ocr_data_list = list() data = self.data for string in self.finished: string = string.split(".")[0] data = data[data.Path != string] self.reports = list(data.Path) self.dates = list(data.Date) print(u"Data index:",data.index) self.remain_string = "remaining folders " + str(len(self.reports)) self.remainingLabel = QLabel(self.remain_string) self.left.addWidget(self.remainingLabel) temp_path = os.path.join(self.dir_path, self.reports[self.crop_index]) self.report = os.listdir(temp_path) #self.forceLastImage() self.postImage() # Sets up drawing capabilities: self.image.setMouseTracking(True) self.image.viewport().installEventFilter(self) self.start = None self.end = None #something #self.draw_boxes() # error here, disregarded bc why not? :) def eventFilter(self, source, event): if event.type() == QtCore.QEvent.MouseButtonRelease and source is self.image.viewport(): if event.button() == Qt.RightButton: self.nextImage() if event.button() == Qt.MidButton: self.ignore() if event.button() == Qt.LeftButton: self.draw_bounding_box() #print(event.pos()) #print(self.image.mapToScene(event.pos())) @Slot() def submit(self, famine_code): self.postImage() ["District", "x1", "y1", "x3", "y3", "Date", "Raw_Text"] row = {'District':self.districtText.text(),'Date':self.date,'famine_code': famine_code} self.bound_data = self.bound_data.append(row, ignore_index= True) print(self.bound_data) self.districtText.setText("") cattle_label_text = "Length: " + str(len(self.bound_data.famine_code)) + ". " + str(list(self.bound_data.famine_code)) self.cattleLabel.setText(cattle_label_text) @Slot() def undo(self): print(self.bound_data) self.bound_data.drop(self.bound_data.tail(1).index, inplace=True) cattle_label_text = "Length: " + str(len(self.bound_data.famine_code)) + ". " + str(list(self.bound_data.famine_code)) self.cattleLabel.setText(cattle_label_text) print(self.bound_data) @Slot() def ignore(self): self.remain_string = "remaining folders " + str(len(self.reports)-self.crop_index-1) self.remainingLabel.setText(self.remain_string) path = self.out_folder + self.reports[self.crop_index] + ".csv" print(u"out path:",path) self.bound_data.District = self.index_districts self.bound_data.to_csv(path, index= False) self.bound_data = pd.DataFrame(columns = self.columns) self.crop_index = self.crop_index + 1 self.page_index = 0 self.postImage() #self.forceLastImage() self.postImage() @Slot() def nextImage(self): if ((len(self.report) - 1) > self.page_index): self.page_index = self.page_index + 1 else: self.page_index = 0 self.postImage() @Slot() def forceLastImage(self): self.page_index = (len(self.report) - 1) @Slot() def prevImage(self): if (1 > self.page_index): self.page_index = len(self.report) - 1 else: self.page_index = self.page_index - 1 self.postImage() def postImage(self): self.date = self.dates[self.crop_index] print(u"Date:",self.date) print(self.dates) temp_path = os.path.join(self.dir_path, self.reports[self.crop_index]) report = os.listdir(temp_path) dt.sort_nicely(report) self.report = report self.ocr_data_list = dt.report_to_data(self.reports[self.crop_index]) if (len(self.report) > 0): self.page = self.report[self.page_index] self.page_df = self.ocr_data_list[self.page_index] temp_path = os.path.join(self.dir_path, self.reports[self.crop_index], self.page) self.scene.clear() self.pixmap = QPixmap(temp_path) # adjusts zoom self.pixmap = self.pixmap.scaled(self.pixmap.size().width() * self.zoom, self.pixmap.size().height() * self.zoom, Qt.KeepAspectRatio) self.scene.addPixmap(self.pixmap) self.draw_bounding_box() # def draw_bounding_box(self, x1, y1, x3, y3): # # start = self.image.mapToScene(x1,y1) # end = self.image.mapToScene(x3,y3) # len_x = end.x()-start.x() # len_y = end.y()-start.y() # rectItem = QGraphicsRectItem(start.x(), start.y(), len_x, len_y) # self.scene.addItem(rectItem) def draw_bounding_box(self): df = self.page_df scale = self.zoom no_df = df[df.word=="redroverr2"] tle_df = df[df.word.str.contains("suf", na = False)] catt_df = df[df.word.str.contains("insuf", na=False)] rinder_df = df[df.word.str.contains("ind1111er", na=False)] for index, row in no_df.iterrows(): print(row) x1 = row.x1*scale y1 = row.y1*scale x3= row.x3*scale y3 = row.y3*scale diff_x = x3-x1 diff_y = y3-y1 rectItem = QGraphicsRectItem(x1,y1,diff_x,diff_y) rectItem.setBrush(QBrush(Qt.green)) #rectItem = QGraphicsRectItem(0, 0, 100, 100) self.scene.addItem(rectItem) for index, row in tle_df.iterrows(): print(row) x1 = row.x1 * scale y1 = row.y1 * scale x3 = row.x3 * scale y3 = row.y3 * scale diff_x = x3 - x1 diff_y = y3 - y1 rectItem = QGraphicsRectItem(x1, y1, diff_x, diff_y) rectItem.setBrush(QBrush(Qt.green)) # rectItem = QGraphicsRectItem(0, 0, 100, 100) self.scene.addItem(rectItem) for index, row in rinder_df.iterrows(): print(row) x1 = row.x1 * scale y1 = row.y1 * scale x3 = row.x3 * scale y3 = row.y3 * scale diff_x = x3 - x1 diff_y = y3 - y1 rectItem = QGraphicsRectItem(x1, y1, diff_x, diff_y) rectItem.setBrush(QBrush(Qt.red)) # rectItem = QGraphicsRectItem(0, 0, 100, 100) self.scene.addItem(rectItem) for index, row in catt_df.iterrows(): print(row) x1 = row.x1 * scale y1 = row.y1 * scale x3 = row.x3 * scale y3 = row.y3 * scale diff_x = x3 - x1 diff_y = y3 - y1 rectItem = QGraphicsRectItem(x1, y1, diff_x, diff_y) rectItem.setBrush(QBrush(Qt.red)) # rectItem = QGraphicsRectItem(0, 0, 100, 100) self.scene.addItem(rectItem) # divider_x = (max(df.x3)-min(df.x1))/2 # week_df = df[df.word.str.contains("icient", na=False)] # for index, row in week_df.iterrows(): # week_anchor = row # # x1 = week_anchor.x1 * scale # y1 = week_anchor.y1 * scale # x3 = week_anchor.x3 * scale # y3 = week_anchor.y3 * scale # diff_x = x3 - x1 # diff_y = y3 - y1 # rectItem = QGraphicsRectItem(x1, y1, diff_x, diff_y) # rectItem.setBrush(QBrush(Qt.blue)) # self.scene.addItem(rectItem) # right_df = df[df.x1 > divider_x] # right_df = right_df[right_df.y1 > week_anchor.y3] # for index, row in right_df.iterrows(): # x1 = row.x1 * scale # y1 = row.y1 * scale # x3 = row.x3 * scale # y3 = row.y3 * scale # diff_x = x3 - x1 # diff_y = y3 - y1 # # rectItem = QGraphicsRectItem(x1, y1, diff_x, diff_y) # rectItem.setBrush(QBrush(Qt.red)) # # self.scene.addItem(rectItem) # for district in self.index_districts: # print(district) # row = df[df.word.str.contains(district, na=False)] # # if (len(row.word) != 0): # x1 = row.x1 * scale # y1 = row.y1 * scale # x3 = row.x3 * scale # y3 = row.y3 * scale # diff_x = x3 - x1 # diff_y = y3 - y1 # # rectItem = QGraphicsRectItem(x1, y1, diff_x, diff_y) # rectItem.setBrush(QBrush(Qt.red)) # # self.scene.addItem(rectItem) # def write_to_csv(self): # new_row = {'ocr_report_path': self.reports[self.crop_index], 'date': self.districtText.text()} # self.data = self.data.append(new_row, ignore_index=True) # self.data.to_csv(self.data_path, index=False) # reformat first half of year 1910 before 10/6 def keyPressEvent(self, event): if event.key() == Qt.Key_A: #disease self.submit("bad") if event.key() == Qt.Key_W: # no mention self.submit("NR") if event.key() == Qt.Key_D: ##not bad self.submit("not_bad")
class MainWindow(QMainWindow): def __init__(self): super(MainWindow, self).__init__() self.particulas = Particulas() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.agregar_final_pushButton.clicked.connect(self.click_agregar) self.ui.agregar_inicio_pushButton.clicked.connect( self.click_agregar_inicio) self.ui.mostrar_pushButton.clicked.connect(self.click_mostrar) self.ui.actionAbrir.triggered.connect(self.click_abrir_archivo) self.ui.actionGuardar.triggered.connect(self.click_guardar_archivo) self.ui.mostrar_tabla_pushButton.clicked.connect(self.mostrar_tabla) self.ui.buscar_pushButton.clicked.connect(self.buscar_id) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) self.ui.dibujar_pushButton.clicked.connect(self.dibujar) self.ui.limpiar_pushButton.clicked.connect(self.limpiar) self.ui.ordenar_id_pushButton.clicked.connect(self.ordenar_id) self.ui.ordenar_distancia_pushButton.clicked.connect( self.ordenar_distancia) self.ui.ordenar_velocidad_pushButton.clicked.connect( self.ordenar_velocidad) self.ui.actionGrafo.triggered.connect(self.mostrar_grafos) self.ui.action_busqueda.triggered.connect(self.busqueda) @Slot() def busqueda(self): self.particulas.peso() self.ui.salida.clear() origenes = (int(self.ui.origenx_lineEdit.text()), int(self.ui.origeny_lineEdit.text())) recorrido = self.particulas.recorrido_profundidad(origenes) print("Profundidad") self.ui.salida.insertPlainText("Profundidad" + '\n') for i in recorrido: self.ui.salida.insertPlainText(str(i) + '\n') print(i) recorrido_2 = self.particulas.recorrido_amplitud(origenes) print("\nAmplitud") self.ui.salida.insertPlainText('\n' "Amplitud" + '\n') for i in recorrido_2: self.ui.salida.insertPlainText(str(i) + '\n') print(i) def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def mostrar_grafos(self): self.ui.salida.clear() self.ui.salida.insertPlainText(self.particulas.mostrar_diccionario()) @Slot() def ordenar_id(self): self.particulas.ordenarid() @Slot() def ordenar_distancia(self): self.particulas.ordenardistancia() @Slot() def ordenar_velocidad(self): self.particulas.ordenarvelocidad() @Slot() def dibujar(self): for particula in self.particulas: pen = QPen() pen.setWidth(1) c_red = particula.red c_green = particula.green c_blue = particula.blue color = QColor(c_red, c_green, c_blue) pen.setColor(color) c_origenx = particula.origenx c_origeny = particula.origeny c_destinox = particula.destinox c_destinoy = particula.destinoy self.scene.addEllipse(c_origenx, c_origeny, .8, .8, pen) self.scene.addEllipse(c_destinox, c_destinoy, .8, .8, pen) self.scene.addLine(c_origenx, c_origeny, c_destinox, c_destinoy, pen) @Slot() def limpiar(self): self.scene.clear() @Slot() def buscar_id(self): ident = self.ui.buscar_lineEdit.text() encontrado = False for particula in self.particulas: if ident == str(particula.identificacion): self.ui.tabla.clear() self.ui.tabla.setRowCount(1) identificacion_widget = QTableWidgetItem( str(particula.identificacion)) origenx_widget = QTableWidgetItem(str(particula.origenx)) origeny_widget = QTableWidgetItem(str(particula.origeny)) destinox_widget = QTableWidgetItem(str(particula.destinox)) destinoy_widget = QTableWidgetItem(str(particula.destinoy)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) red_widget = QTableWidgetItem(str(particula.red)) blue_widget = QTableWidgetItem(str(particula.blue)) green_widget = QTableWidgetItem(str(particula.green)) d_widget = QTableWidgetItem(str(particula.d)) self.ui.tabla.setItem(0, 0, identificacion_widget) self.ui.tabla.setItem(0, 1, origenx_widget) self.ui.tabla.setItem(0, 2, origeny_widget) self.ui.tabla.setItem(0, 3, destinox_widget) self.ui.tabla.setItem(0, 4, destinoy_widget) self.ui.tabla.setItem(0, 5, velocidad_widget) self.ui.tabla.setItem(0, 6, red_widget) self.ui.tabla.setItem(0, 7, blue_widget) self.ui.tabla.setItem(0, 8, green_widget) self.ui.tabla.setItem(0, 9, d_widget) encontrado = True return if not encontrado: QMessageBox.warning( self, "Atención", f'La particula con el id"{ident}"no fue encontrada') @Slot() def mostrar_tabla(self): self.ui.tabla.setColumnCount(10) headers = [ "ID", "Origen en x", "Origen en y", "Destino en x", "Destino en y", "Velocidad", "Red", "Blue", "Green", "Distancia" ] self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.particulas)) row = 0 for particula in self.particulas: identificacion_widget = QTableWidgetItem( str(particula.identificacion)) origenx_widget = QTableWidgetItem(str(particula.origenx)) origeny_widget = QTableWidgetItem(str(particula.origeny)) destinox_widget = QTableWidgetItem(str(particula.destinox)) destinoy_widget = QTableWidgetItem(str(particula.destinoy)) velocidad_widget = QTableWidgetItem(str(particula.velocidad)) red_widget = QTableWidgetItem(str(particula.red)) blue_widget = QTableWidgetItem(str(particula.blue)) green_widget = QTableWidgetItem(str(particula.green)) d_widget = QTableWidgetItem(str(particula.d)) self.ui.tabla.setItem(row, 0, identificacion_widget) self.ui.tabla.setItem(row, 1, origenx_widget) self.ui.tabla.setItem(row, 2, origeny_widget) self.ui.tabla.setItem(row, 3, destinox_widget) self.ui.tabla.setItem(row, 4, destinoy_widget) self.ui.tabla.setItem(row, 5, velocidad_widget) self.ui.tabla.setItem(row, 6, red_widget) self.ui.tabla.setItem(row, 7, blue_widget) self.ui.tabla.setItem(row, 8, green_widget) self.ui.tabla.setItem(row, 9, d_widget) row += 1 @Slot() def click_abrir_archivo(self): ubicacion = QFileDialog.getOpenFileName(self, 'Abrir Archivo', '.', 'JSON (*.json)')[0] if self.particulas.abrir(ubicacion): QMessageBox.information(self, "Éxito", "Se abrió el archivo" + ubicacion) else: QMessageBox.critical(self, "Error", "Error al abrir el archivo" + ubicacion) @Slot() def click_guardar_archivo(self): ubicacion = QFileDialog.getSaveFileName(self, 'Guadar Archivo', '.', 'JSON(*.json)')[0] print(ubicacion) if self.particulas.guardar(ubicacion): QMessageBox.information(self, "Éxito", "Se pudo crear el archivo" + ubicacion) else: QMessageBox.critical(self, "Error", "No se pudo crear el archivo" + ubicacion) @Slot() def click_mostrar(self): self.ui.salida.clear() self.ui.salida.insertPlainText(str(self.particulas)) @Slot() def click_agregar(self): identificacion = int(self.ui.id_lineEdit.text()) origenx = int(self.ui.origenx_lineEdit.text()) origeny = int(self.ui.origeny_lineEdit.text()) destinox = int(self.ui.destinox_lineEdit.text()) destinoy = int(self.ui.destinoy_lineEdit.text()) velocidad = int(self.ui.velocidad_lineEdit.text()) red = int(self.ui.red_lineEdit.text()) green = int(self.ui.green_lineEdit.text()) blue = int(self.ui.blue_lineEdit.text()) particula = Particula(identificacion, origenx, origeny, destinox, destinoy, velocidad, red, green, blue) self.particulas.agregar_final(particula) @Slot() def click_agregar_inicio(self): identificacion = int(self.ui.id_lineEdit.text()) origenx = int(self.ui.origenx_lineEdit.text()) origeny = int(self.ui.origeny_lineEdit.text()) destinox = int(self.ui.destinox_lineEdit.text()) destinoy = int(self.ui.destinoy_lineEdit.text()) velocidad = int(self.ui.velocidad_lineEdit.text()) red = int(self.ui.red_lineEdit.text()) green = int(self.ui.green_lineEdit.text()) blue = int(self.ui.blue_lineEdit.text()) particula = Particula(identificacion, origenx, origeny, destinox, destinoy, velocidad, red, green, blue) self.particulas.agregar_inicio(particula)
class MainWindow(QMainWindow): def __init__(self): super().__init__() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui = Ui_MainWindow() self.ui.setupUi(self) self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.lista = [] self.listaMenor = [] self.capturador = Capturador() self.ui.pushButton.clicked.connect(self.click) self.ui.pushButton_2.clicked.connect(self.mostrar) self.ui.actionGuardar.triggered.connect(self.guardar) self.ui.actionAbrir_2.triggered.connect(self.abrir) self.ui.actionMostar.triggered.connect(self.mostarParticulasPuntos) self.ui.actionPuntos_Cercanos.triggered.connect(self.puntos_cercanos) self.ui.pushButton_3.clicked.connect(self.ordenar_velocidad) self.ui.pushButton_4.clicked.connect(self.ordenar_distancia) @Slot() def puntos_cercanos(self): for i in range(len(self.lista) - 1): particulaMenor = self.lista[i + 1] for j in range(len(self.lista) - 1): particula2 = self.lista[j] if (j == 0): auxDistancia = math.sqrt( pow((int(particula2['x']) - int(particulaMenor['x'])), 2) + pow((int(particula2['y']) - int(particulaMenor['y'])), 2)) aux = {'origen': particulaMenor, 'destino': particula2} if ((math.sqrt( pow((int(particula2['x']) - int(particulaMenor['x'])), 2) + pow((int(particula2['y']) - int(particulaMenor['y'])), 2)) < auxDistancia) and (particulaMenor != particula2)): auxDistancia = math.sqrt( pow((int(particula2['x']) - int(particulaMenor['x'])), 2) + pow((int(particula2['y']) - int(particulaMenor['y'])), 2)) aux = {'origen': particulaMenor, 'destino': particula2} self.listaMenor.append(aux) self.dibujar() @Slot() def mostarParticulasPuntos(self): self.scene.clear() self.scene = QGraphicsScene() # self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador.ordenar_velocidad() for particula in self.capturador.lista: self.lista.append({ 'x': particula.origenX, 'y': particula.origenY, 'color': { 'red': particula.red, 'green': particula.green, 'blue': particula.blue } }) self.lista.append({ 'x': particula.destinoX, 'y': particula.destinoY, 'color': { 'red': particula.red, 'green': particula.green, 'blue': particula.blue } }) self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addEllipse( particula.origenX, particula.origenY, 5, 5, self.pen, QBrush( QColor(particula.red, 10, particula.green, particula.blue))) @Slot() def ordenar_velocidad(self): self.scene.clear() self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador.ordenar_velocidad() y = 0 for particula in self.capturador.lista: self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addLine(0, y, particula.distancia, y, self.pen) y = y + 2 def dibujar(self): self.scene.clear() self.scene = QGraphicsScene() # self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador.ordenar_distancia() for new in self.listaMenor: self.scene.addEllipse( new['origen']['x'], new['origen']['y'], 5, 5, self.pen, QBrush( QColor(new['origen']['color']['red'], 10, new['origen']['color']['green'], new['origen']['color']['blue']))) self.pen.setColor( QColor(new['origen']['color']['red'], new['origen']['color']['green'], new['origen']['color']['blue'])) self.scene.addLine(new['origen']['x'], new['origen']['y'], new['destino']['x'], new['destino']['y'], self.pen) @Slot() def ordenar_distancia(self): self.scene.clear() self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) self.capturador.ordenar_distancia() y = 0 for particula in self.capturador.lista: self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addLine(0, y, particula.distancia, y, self.pen) y = y + 2 @Slot() def guardar(self): self.scene = QGraphicsScene() #self.scene.setSceneRect(0,500) self.ui.graphicsView.setScene(self.scene) self.pen = QPen() self.pen.setColor(QColor(0, 0, 0)) self.pen.setWidth(1) file = QFileDialog.getSaveFileName(self, 'Guardar archivo...', '.', 'JSON (*.json)') print(file) self.capturador.guardar(file[0], self.pen, self.scene) @Slot() def abrir(self): file = QFileDialog.getOpenFileName(self, 'Abrir archivo', '.', 'JSON (*.json)') self.capturador.recuperar(file[0]) @Slot() def mostrar(self): self.scene.clear() self.scene.addLine(0, 0, 499, 0, self.pen) y = 0 for particula in self.capturador.lista: self.ui.plainTextEdit.insertPlainText(str(particula)) self.pen.setColor( QColor(particula.red, particula.green, particula.blue)) self.scene.addLine(0, y, particula.distancia, y, self.pen) y = y + 2 #for particula in self.capturador.lista: # self.ui.plainTextEdit.insertPlainText(str(particula)) # self.pen.setColor(QColor(particula.red, particula.green, particula.blue)) # self.scene.addEllipse(particula.origenX, particula.origenY, 5, 5, self.pen, QBrush(QColor(particula.red, 10,particula.green, particula.blue))) #self.scene.addLine(particula.origenX, particula.origenY, particula.destinoX, particula.destinoY, self.pen) #self.paqueteria.mostrar() @Slot() def click(self): id = self.ui.lineEdit.text() origenX = self.ui.lineEdit_2.text() origenY = self.ui.lineEdit_6.text() destinoX = self.ui.lineEdit_3.text() destinoY = self.ui.lineEdit_7.text() velocidad = self.ui.lineEdit_4.text() red = self.ui.lineEdit_5.text() green = self.ui.lineEdit_8.text() blue = self.ui.lineEdit_9.text() print(id, origenX, origenY, destinoX, destinoY, velocidad, red, green, blue) partiula = Particula() partiula.id = id partiula.origenX = int(origenX) partiula.origenY = int(origenY) partiula.destinoX = int(destinoX) partiula.destinoY = int(destinoY) partiula.distancia = math.sqrt( pow((int(destinoX) - int(origenX)), 2) + pow((int(destinoY) - int(origenY)), 2)) partiula.red = int(red) partiula.green = int(green) partiula.blue = int(blue) partiula.velocidad = int(velocidad) self.capturador.agregar(partiula) msg = QMessageBox.information( self, 'Exito', 'Se agrego paquete con exito' ) #Ventana de mensaje de la libreria QMessageBox self.ui.lineEdit.clear() #Limpiar campos self.ui.lineEdit_2.clear() self.ui.lineEdit_3.clear() self.ui.lineEdit_4.clear() self.ui.lineEdit_5.clear() self.ui.lineEdit_6.clear() self.ui.lineEdit_7.clear() self.ui.lineEdit_8.clear() self.ui.lineEdit_9.clear()
class QPOIViewer(QWidget): """ POI Viewer QWidget """ TAG_SPACING = 50 LEGEND_X = -50 LEGEND_Y = 0 LEGEND_WIDTH = 10 TRACE_FUNC_X = 0 TRACE_FUNC_Y = 0 TRACE_FUNC_WIDTH = 50 TRACE_FUNC_MINHEIGHT = 1000 TAB_HEADER_SIZE = 40 MAX_WINDOW_SIZE = 500 MARK_X = LEGEND_X MARK_WIDTH = TRACE_FUNC_X - LEGEND_X + TRACE_FUNC_WIDTH MARK_HEIGHT = 1 POIID_COLUMN = 0 CRASH_COLUMN = 1 CATEGORY_COLUMN = 2 DIAGNOSE_COLUMN = 3 COLUMN_FIELD = ['id', 'bbl', 'category', 'diagnose'] def __init__(self, workspace, parent=None, diagnose_handler=None): super().__init__(parent=parent) self.workspace = workspace self._diagnose_handler = diagnose_handler self.mark = None self.legend = None self.legend_height = 0 self.legend_img = None self.trace_func_unit_height = 0 self.trace_func = None self.trace_id = None self.tabView = None self.traceView = None self.traceScene = None self.POITraceTab = None self.multiPOITab : QWidget = None self.multiPOIList : QTableWidget = None self.mark = None self.curr_position = 0 self._use_precise_position = False self._selected_traces = [] self._selected_poi = None self._init_widgets() self.selected_ins.am_subscribe(self._subscribe_select_ins) self.poi_trace.am_subscribe(self._subscribe_set_trace) self.multi_poi.am_subscribe(self._subscribe_add_poi) self.multiPOIList.cellDoubleClicked.connect(self._on_cell_double_click) self.multiPOIList.itemChanged.connect(self._on_diagnose_change) # # Forwarding properties # @property def disasm_view(self): """ Get the current disassembly view (if there is one), or create a new one as needed. """ view = self.workspace.view_manager.current_view_in_category("disassembly") if view is None: view = self.workspace._get_or_create_disassembly_view() return view @property def poi_trace(self): return self.workspace.instance.poi_trace @property def multi_poi(self): return self.workspace.instance.multi_poi @property def selected_ins(self): return self.disasm_view.infodock.selected_insns def _init_widgets(self): _l.debug("QPOI Viewer Initiating") self.tabView = QTabWidget() # QGraphicsView() self.tabView.setContentsMargins(0, 0, 0, 0) # # POI trace Tab # self.POITraceTab = QWidget() self.POITraceTab.setContentsMargins(0, 0, 0, 0) singleLayout = QVBoxLayout() singleLayout.setSpacing(0) singleLayout.setContentsMargins(0, 0, 0, 0) self.traceView = QGraphicsView() self.traceScene = QGraphicsScene() self.traceView.setScene(self.traceScene) singleLayout.addWidget(self.traceView) self.POITraceTab.setLayout(singleLayout) # # multiPOI Tab # self.multiPOITab = QMultiPOITab(self) # self.multiPOITab = QWidget() multiLayout = QVBoxLayout() multiLayout.setSpacing(0) multiLayout.setContentsMargins(0, 0, 0, 0) self.multiPOIList = QTableWidget(0, 4) # row, col self.multiPOIList.setHorizontalHeaderItem(0, QTableWidgetItem("ID")) self.multiPOIList.setHorizontalHeaderItem(1, QTableWidgetItem("Crash Point")) self.multiPOIList.setHorizontalHeaderItem(2, QTableWidgetItem("Tag")) self.multiPOIList.setHorizontalHeaderItem(3, QTableWidgetItem("Diagnose")) self.multiPOIList.horizontalHeader().setStretchLastSection(True) self.multiPOIList.horizontalHeader().setSectionResizeMode(QHeaderView.ResizeToContents) self.multiPOIList.setSelectionBehavior(QAbstractItemView.SelectRows) multiLayout.addWidget(self.multiPOIList) self.multiPOITab.setLayout(multiLayout) self.tabView.addTab(self.multiPOITab, "POI List") self.tabView.addTab(self.POITraceTab, "POI Trace") self.POI_TRACE = 1 self.MULTI_POI = 0 layout = QVBoxLayout() layout.addWidget(self.tabView) layout.setContentsMargins(0, 0, 0, 0) self.setLayout(layout) self.show() def _reset(self): self.traceScene.clear() #clear items self.mark = None self.legend = None self.legend_height = 0 self.trace_func = QGraphicsItemGroup() self.trace_id = QGraphicsItemGroup() self.traceScene.addItem(self.trace_func) self.hide() # # Event # def _on_cell_double_click(self, row, _): _l.debug("row %d is double clicked", row) first_cell = self.multiPOIList.item(row, 0) if first_cell is None: return poi_id = first_cell.text() poi = self.multi_poi.am_obj.get_poi_by_id(poi_id) if poi is None: return # sanity checks if not isinstance(poi, dict): return if 'output' not in poi or not isinstance(poi['output'], dict): return if 'bbl_history' not in poi['output']: return trace = poi['output']['bbl_history'] if self._selected_poi != poi_id and trace is not None: # render the trace self.poi_trace.am_obj = TraceStatistics(self.workspace, trace, trace_id=poi_id) # show the trace statistic in POI trace self.poi_trace.am_event() # show covered basic blocks and functions self.multi_poi.am_obj.reload_heatmap(poi_id) # redraw function view view = self.workspace.view_manager.first_view_in_category('functions') if view is not None: view.refresh() # redraw disassembly view view = self.workspace.view_manager.first_view_in_category('disassembly') if view is not None: view.redraw_current_graph() if trace is not None: # switch to POI trace tab self.tabView.setCurrentIndex(self.POI_TRACE) self._selected_poi = poi_id second_cell = self.multiPOIList.item(row, 1) crash_addr = None if second_cell is not None: try: crash_addr = int(second_cell.text(), 16) except ValueError: pass if crash_addr is not None: # show the crashing address view = self.workspace.view_manager.first_view_in_category('disassembly') if view is not None: crash_func = self._get_func_from_addr(crash_addr) if crash_func is not None: self.workspace.on_function_selected(crash_func) self.selected_ins.clear() self.selected_ins.update([crash_addr]) self.selected_ins.am_event() view.current_graph.show_instruction(crash_addr) def _on_diagnose_change(self, item: QTableWidgetItem): column = item.column() row = item.row() poi_id = self.multiPOIList.item(row, self.POIID_COLUMN).text() content = item.text() original_content = self.multi_poi.am_obj.get_content_by_id_column(poi_id, column) _l.debug('updaing %s, content: %s, original: %s', poi_id, content, original_content) if not self._is_identical(content, original_content): updated_poi = self.multi_poi.update_poi(poi_id, column, content) self._diagnose_handler.submit_updated_poi(poi_id, updated_poi) def _subscribe_add_poi(self): _l.debug('add a poi to multi poi list') if self.multi_poi.am_none: self.multi_poi.am_obj = MultiPOI(self.workspace) poi_ids = self.multi_poi.am_obj.get_all_poi_ids() self.multiPOIList.clearContents() self._populate_poi_table(self.multiPOIList, poi_ids) self.show() def _subscribe_set_trace(self): _l.debug('on set trace in poi trace viewer') self._reset() if self.poi_trace.am_none: return _l.debug('minheight: %d, count: %d', self.TRACE_FUNC_MINHEIGHT, self.poi_trace.count) if self.poi_trace.count <= 0: _l.warning("No valid addresses found in trace to show. Check base address offsets?") self.poi_trace.am_obj = None self.poi_trace.am_event() return if self.TRACE_FUNC_MINHEIGHT < self.poi_trace.count * 15: self.trace_func_unit_height = 15 show_func_tag = True else: self.trace_func_unit_height = self.TRACE_FUNC_MINHEIGHT / self.poi_trace.count show_func_tag = True self.legend_height = int(self.poi_trace.count * self.trace_func_unit_height) self._show_trace_func(show_func_tag) self._show_legend() self._set_mark_color() self._refresh_multi_list() # boundingSize = self.traceScene.itemsBoundingRect().width() # windowSize = boundingSize # if boundingSize > self.MAX_WINDOW_SIZE: # windowSize = self.MAX_WINDOW_SIZE # self.traceScene.setSceneRect(self.traceScene.itemsBoundingRect()) #resize # if windowSize > self.width(): # self.setMinimumWidth(windowSize) self.show() def _subscribe_select_ins(self, **kwargs): # pylint: disable=unused-argument if self.poi_trace.am_none: return if self.mark is not None: for i in self.mark.childItems(): self.mark.removeFromGroup(i) self.traceScene.removeItem(i) self.traceScene.removeItem(self.mark) self.mark = QGraphicsItemGroup() self.traceScene.addItem(self.mark) if self.selected_ins: addr = next(iter(self.selected_ins)) positions = self.poi_trace.get_positions(addr) if positions: #if addr is in list of positions # handle case where insn was selected from disas view if not self._use_precise_position: self.curr_position = positions[0] - self.poi_trace.count for p in positions: color = self._get_mark_color(p, self.poi_trace.count) y = self._get_mark_y(p) if p == self.poi_trace.count + self.curr_position: #add thicker line for 'current' mark self.mark.addToGroup(self.traceScene.addRect(self.MARK_X, y, self.MARK_WIDTH, self.MARK_HEIGHT*4, QPen(QColor('black')), QBrush(color))) else: self.mark.addToGroup(self.traceScene.addRect(self.MARK_X, y, self.MARK_WIDTH, self.MARK_HEIGHT, QPen(color), QBrush(color))) self.traceScene.update() #force redraw of the traceScene self.scroll_to_position(self.curr_position) def _get_func_from_addr(self, addr): if self.workspace.instance.cfg.am_none: return None bbl = self.workspace.instance.cfg.get_any_node(addr, anyaddr=True) function_addr = bbl.function_address return self.workspace.instance.project.kb.functions.get(function_addr) def _populate_poi_table(self, view, poi_ids): view.clearContents() view.setRowCount(len(poi_ids)) row = 0 #start after label row for poi_id in poi_ids: poi = self.multi_poi.am_obj.get_poi_by_id(poi_id) _l.debug('populating poi: %s', poi) category = poi['category'] output = poi['output'] crash_addr = output['bbl'] if crash_addr is not None: crash = hex(crash_addr) else: crash = None diagnose = output.get('diagnose') _l.debug('poi_ids: %s', poi_ids) _l.debug('current poi id: %s', poi_id) self._set_item(view, row, self.POIID_COLUMN, poi_id, editable=False) self._set_item(view, row, self.CRASH_COLUMN, crash, editable=True) self._set_item(view, row, self.CATEGORY_COLUMN, category, editable=True) self._set_item(view, row, self.DIAGNOSE_COLUMN, diagnose, editable=True) row += 1 _l.debug('poi_ids: %s', poi_ids) @staticmethod def _set_item(view, row, column, text, editable=True): if not text: text = "" item = QTableWidgetItem(text) if not editable: item.setFlags(item.flags() ^ Qt.ItemIsEditable) view.setItem(row, column, item) def _refresh_multi_list(self): multiPOI = self.multi_poi.am_obj trace_ids = multiPOI.get_all_poi_ids() self.multiPOIList.clearContents() self._populate_poi_table(self.multiPOIList, trace_ids) if self._selected_traces and self.multiPOIList.rowCount() > 0: self.multiPOIList.item(0, 0).setSelected(True) self.multiPOIList.item(0, 1).setSelected(True) else: for row in range(self.multiPOIList.rowCount()): item = self.multiPOIList.item(row, 0) inputItem = self.multiPOIList.item(row, 1) if item.text() in self._selected_traces: item.setSelected(True) inputItem.setSelected(True) self.multi_poi.am_event() def _on_tab_change(self): multiPOI = self.multi_poi.am_obj if self.tabView.currentIndex() == self.MULTI_POI: multiPOI.is_active_tab = True self._refresh_multi_list() elif self.tabView.currentIndex() == self.POI_TRACE: multiPOI = self.multi_poi.am_obj multiPOI.is_active_tab = False # self._show_trace_ids() def scroll_to_position(self, position): relative_pos = self.poi_trace.count + position y_offset = self._get_mark_y(relative_pos) scrollValue = 0 if y_offset > 0.5 * self.traceView.size().height(): scrollValue = y_offset - 0.5 * self.traceView.size().height() scrollValue = min(scrollValue, self.traceView.verticalScrollBar().maximum()) self.traceView.verticalScrollBar().setValue(scrollValue) self._use_precise_position = False def jump_next_insn(self): # for some reason indexing is done backwards if self.curr_position + self.poi_trace.count < self.poi_trace.count - 1: self.curr_position += 1 self._use_precise_position = True bbl_addr = self.poi_trace.get_bbl_from_position(self.curr_position) func = self.poi_trace.get_func_from_position(self.curr_position) self._jump_bbl(func, bbl_addr) def jump_prev_insn(self): if self.curr_position + self.poi_trace.count > 0: self.curr_position -= 1 self._use_precise_position = True bbl_addr = self.poi_trace.get_bbl_from_position(self.curr_position) func = self.poi_trace.get_func_from_position(self.curr_position) self._jump_bbl(func, bbl_addr) def mousePressEvent(self, event): button = event.button() pos = self._to_logical_pos(event.pos()) if button == Qt.LeftButton and self.tabView.currentIndex() == self.POI_TRACE and self._at_legend(pos): func = self._get_func_from_y(pos.y()) bbl_addr = self._get_bbl_from_y(pos.y()) self._use_precise_position = True self.curr_position = self._get_position(pos.y()) self._jump_bbl(func, bbl_addr) def _jump_bbl(self, func, bbl_addr): disasm_view = self.disasm_view if disasm_view is not None: all_insn_addrs = self.workspace.instance.project.factory.block(bbl_addr).instruction_addrs # TODO: replace this with am_events perhaps? self.workspace.on_function_selected(func) self.selected_ins.clear() self.selected_ins.update(all_insn_addrs) self.selected_ins.am_event() # TODO: this ought to happen automatically as a result of the am_event disasm_view.current_graph.show_instruction(bbl_addr) def _get_mark_color(self, i, total): relative_gradient_pos = i * 1000 // total return self.legend_img.pixelColor(self.LEGEND_WIDTH // 2, relative_gradient_pos) def _get_mark_y(self, i): return self.TRACE_FUNC_Y + self.trace_func_unit_height * i def _show_trace_func(self, show_func_tag=True): x = self.TRACE_FUNC_X y = self.TRACE_FUNC_Y prev_name = None for position in self.poi_trace.trace_func: func_name = position.func_name color = self.poi_trace.get_func_color(func_name) self.trace_func.addToGroup(self.traceScene.addRect(x, y, self.TRACE_FUNC_WIDTH, self.trace_func_unit_height, QPen(color), QBrush(color))) if show_func_tag is True and func_name != prev_name: tag = self.traceScene.addText(func_name, QFont("Source Code Pro", 7)) tag.setPos(x + self.TRACE_FUNC_WIDTH + self.TAG_SPACING, y - tag.boundingRect().height() // 2) self.trace_func.addToGroup(tag) anchor = self.traceScene.addLine( self.TRACE_FUNC_X + self.TRACE_FUNC_WIDTH, y, x + self.TRACE_FUNC_WIDTH + self.TAG_SPACING, y) self.trace_func.addToGroup(anchor) prev_name = func_name y += self.trace_func_unit_height @staticmethod def _make_legend_gradient(x1, y1, x2, y2): gradient = QLinearGradient(x1, y1, x2, y2) gradient.setColorAt(0.0, Qt.red) gradient.setColorAt(0.4, Qt.yellow) gradient.setColorAt(0.6, Qt.green) gradient.setColorAt(0.8, Qt.blue) gradient.setColorAt(1.0, Qt.darkBlue) return gradient def _show_legend(self): pen = QPen(Qt.transparent) gradient = self._make_legend_gradient(self.LEGEND_X, self.LEGEND_Y, self.LEGEND_X, self.LEGEND_Y + self.legend_height) brush = QBrush(gradient) self.legend = self.traceScene.addRect(self.LEGEND_X, self.LEGEND_Y, self.LEGEND_WIDTH, self.legend_height, pen, brush) reference_gradient = self._make_legend_gradient(0, 0, self.LEGEND_WIDTH, 1000) base_img = QImage(self.LEGEND_WIDTH, 1000, QImage.Format.Format_ARGB32) p = QPainter(base_img) p.fillRect(base_img.rect(),reference_gradient) self.legend_img = base_img #reference shade def _set_mark_color(self): _l.debug('trace count: %d', self.poi_trace.count) for p in range(self.poi_trace.count): color = self._get_mark_color(p, self.poi_trace.count) self.poi_trace.set_mark_color(p, color) def _at_legend(self, pos): x = pos.x() y = pos.y() return self.TRACE_FUNC_X + self.LEGEND_X < x < self.traceView.width() and \ self.TRACE_FUNC_Y < y < self.TRACE_FUNC_Y + self.legend_height def _to_logical_pos(self, pos): x_offset = self.traceView.horizontalScrollBar().value() y_offset = self.traceView.verticalScrollBar().value() return QPoint(pos.x() + x_offset, pos.y() + y_offset) def _get_position(self, y): y_relative = y - self.legend_height - self.TAB_HEADER_SIZE return int(y_relative // self.trace_func_unit_height) def _get_bbl_from_y(self, y): position = self._get_position(y) return self.poi_trace.get_bbl_from_position(position) def _get_func_from_y(self, y): position = self._get_position(y) func = self.poi_trace.get_func_from_position(position) return func # # Context Menu # def menu_add_empty_poi(self): _l.debug('adding a new empty poi item') if self._diagnose_handler.get_image_id() is None: QMessageBox.warning(self.workspace.main_window, "No CHESS target available", "No angr project is loaded, or you did not associate the current project with a CHESS " "target. Please load a binary and associate it with a CHESS target before creating " "POIs.") return poi_id = str(uuid4()) if self.multi_poi.am_none: self.multi_poi.am_obj = MultiPOI(self.workspace) empty_poi = deepcopy(EMPTY_POI) self.multi_poi.add_poi(poi_id, empty_poi) self.multi_poi.am_event() self._diagnose_handler.submit_updated_poi(poi_id, empty_poi) def menu_remove_poi(self): items = self.multiPOIList.selectedItems() row = items.pop().row() poi_id = self.multiPOIList.item(row, 0).text() _l.debug('removing ID %s', poi_id) self.multi_poi.remove_poi(poi_id) self.multi_poi.am_event() @staticmethod def _is_identical(content, original_content): if content == original_content: return True if content == '' and original_content is None: return True try: if int(content, 16) == int(original_content): return True except (TypeError, ValueError): return False return False
class MainWindow(QMainWindow): def __init__(self): super(MainWindow,self).__init__() self.cern = CERN() self.ui = Ui_MainWindow() self.ui.setupUi(self) self.ui.agregar_inicio_button.clicked.connect(self.agregar_inicio) self.ui.agregar_final_button.clicked.connect(self.agregar_fin) self.ui.mostrar_button.clicked.connect(self.mostrar_plano) self.ui.grafo_button.clicked.connect(self.mostrar_grafo) self.ui.salida.setReadOnly(True) self.grafo = False self.ui.actionAbrir.triggered.connect(self.abrir_archivo) self.ui.actionGuardar.triggered.connect(self.guardar_archivo) self.ui.action_grafo.triggered.connect(self.mostrar_grafo) self.ui.action_lista.triggered.connect(self.mostrar_plano) self.ui.action_recorridos.triggered.connect(self.mostrar_recorridos) self.ui.action_prim.triggered.connect(self.dibujar_prim) self.ui.action_kruskal.triggered.connect(self.dibujar_kruskal) self.ui.action_dijkstra.triggered.connect(self.dibujar_dijkstra) self.ui.mostrar_tabla_pushButton.clicked.connect(self.mostrar_tabla) self.ui.buscar_pushButton.clicked.connect(self.buscar_id) self.ui.dibujar.clicked.connect(self.dibujar) self.ui.borrar.clicked.connect(self.limpiar) self.scene = QGraphicsScene() self.ui.graphicsView.setScene(self.scene) self.ui.plainTextSort.currentIndexChanged.connect(self.sort_plain) self.ui.tableSort.currentIndexChanged.connect(self.sort_plain) @Slot() def dibujar_dijkstra(self): self.mostrar() if not self.grafo or len(self.cern) == 0: QMessageBox.critical( self, "No se pudo leer", "Convierta a grafo no vacío antes" ) else: origen_x = int(self.ui.origin_x.text()) origen_y = int(self.ui.origin_y.text()) origen = (origen_x, origen_y) destino_x = int(self.ui.destination_x.text()) destino_y = int(self.ui.destination_y.text()) destino = (destino_x, destino_y) grafo = self.cern.to_dict() if origen not in grafo or destino not in grafo: QMessageBox.information( self, "Origen o destino inválidos", "Escriba un origen y destino válidos en los campos" ) return distancias, camino = self.cern.dijkstra(origen) print('') formated = pformat(distancias, width=40, indent=1) print(formated) print('') formated = pformat(camino, width=40, indent=1) print(formated) if camino[origen] not in grafo or camino[destino] not in grafo: QMessageBox.critical( self, "Sin camino", "No se encontró el camino" ) return self.ui.tabWidget.setCurrentIndex(2) self.scene.clear() pen = QPen() pen.setColor(QColor(105, 207, 193)) dimension = 5 pen.setWidth(dimension) siguiente = destino while siguiente != origen: actual = camino[siguiente] self.scene.addLine(actual[0]+3, actual[1]+3, siguiente[0], siguiente[1], pen) self.scene.addEllipse(actual[0], actual[1], dimension, dimension, pen) self.scene.addEllipse(siguiente[0], siguiente[1], dimension, dimension, pen) siguiente = camino[siguiente] @Slot() def dibujar_kruskal(self): self.mostrar() if not self.grafo or len(self.cern) == 0: QMessageBox.critical( self, "No se pudo leer", "Convierta a grafo no vacío antes" ) else: arbol = self.cern.kruskal() print("Arbol de expansion minima: ") print(arbol) self.ui.tabWidget.setCurrentIndex(2) pen = QPen() pen.setDashPattern([1,3]) color = QColor(255,255,255) pen.setColor(color) pen.setWidth(4) for arista in arbol: origen = arista[1] destino = arista[2] self.scene.addLine(origen[0]+3, origen[1]+3, destino[0], destino[1], pen) @Slot() def dibujar_prim(self): self.mostrar() if not self.grafo or len(self.cern) == 0: QMessageBox.critical( self, "No se pudo leer", "Convierta a grafo no vacío antes" ) else: origen_x = int(self.ui.origin_x.text()) origen_y = int(self.ui.origin_y.text()) origen = (origen_x, origen_y) if origen not in self.cern.to_dict(): QMessageBox.information( self, "Sin origen válido", "Se usará el primer elemento en el grafo como origen" ) origen = next(iter(self.cern.to_dict())) arbol = self.cern.prim(origen) print(arbol) self.ui.tabWidget.setCurrentIndex(2) pen = QPen() pen.setDashPattern([1,3]) color = QColor(255,255,255) pen.setColor(color) pen.setWidth(4) for arista in arbol: origen = arista[1] destino = arista[2] self.scene.addLine(origen[0]+3, origen[1]+3, destino[0], destino[1], pen) @Slot() def mostrar_recorridos(self): self.mostrar() if not self.grafo or len(self.cern) == 0: QMessageBox.critical( self, "No se pudo leer", "Convierta a grafo no vacío antes" ) else: origen_x = int(self.ui.origin_x.text()) origen_y = int(self.ui.origin_y.text()) origen = (origen_x, origen_y) if origen not in self.cern.to_dict(): QMessageBox.information( self, "Sin origen válido", "Se usará el primer elemento en el grafo como origen" ) origen = next(iter(self.cern.to_dict())) anchura = self.cern.recorrido_anchura(origen) profundidad = self.cern.recorrido_profundidad(origen) print(f"Origen = {str(origen)}") print("Recorrido en anchura:") print(anchura) self.ui.salida.insertPlainText('\n\nRecorrido en anchura:\n') self.ui.salida.insertPlainText(anchura) print("Recorrido en profundidad:") print(profundidad) self.ui.salida.insertPlainText('\nRecorrido en profundidad:\n') self.ui.salida.insertPlainText(profundidad) self.ui.salida.ensureCursorVisible() @Slot() def sort_plain(self,index): self.ui.plainTextSort.setCurrentIndex(index) self.ui.tableSort.setCurrentIndex(index) self.mostrar() def wheelEvent(self, event): if event.delta() > 0: self.ui.graphicsView.scale(1.2, 1.2) else: self.ui.graphicsView.scale(0.8, 0.8) @Slot() def dibujar(self): self.scene.clear() if len(self.cern) > 0: pen = QPen() # maxValue = max( [p.velocidad for p in self.cern] ) for particula in self.cern: color = QColor(int(particula.red), int(particula.green), int(particula.blue)) pen.setColor(color) # dimension = round(6 - 3 * particula.velocidad / (maxValue+0.1)) dimension = 5 pen.setWidth(dimension) self.scene.addLine(particula.origen_x+3, particula.origen_y+3, particula.destino_x, particula.destino_y, pen) self.scene.addEllipse(particula.origen_x, particula.origen_y, dimension, dimension, pen) self.scene.addEllipse(particula.destino_x, particula.destino_y, dimension, dimension, pen) @Slot() def limpiar(self): self.scene.clear() @Slot() def mostrar_tabla(self): headers = ['Id','Origen','Destino','Velocidad','Color','Distancia'] self.ui.tabla.setColumnCount(len(headers)) self.ui.tabla.setHorizontalHeaderLabels(headers) self.ui.tabla.setRowCount(len(self.cern)) for index, part in enumerate(self.cern): id_widget = QTableWidgetItem(str(part.id)) origen_widget = QTableWidgetItem(f"({part.origen_x},{part.origen_y})") destino_widget = QTableWidgetItem(f"({part.destino_x},{part.destino_y})") velocidad_widget = QTableWidgetItem(str(part.velocidad)) color_widget = QTableWidgetItem(f"rgb({part.red},{part.green},{part.blue})") distancia_widget = QTableWidgetItem(f"{part.distancia:.4f}") self.ui.tabla.setItem(index,0,id_widget) self.ui.tabla.setItem(index,1,origen_widget) self.ui.tabla.setItem(index,2,destino_widget) self.ui.tabla.setItem(index,3,velocidad_widget) self.ui.tabla.setItem(index,4,color_widget) self.ui.tabla.setItem(index,5,distancia_widget) @Slot() def buscar_id(self): id = self.ui.buscar_lineEdit.text().strip() for part in self.cern: current_id = str(part.id) if current_id == id: self.ui.tabla.clearContents() self.ui.tabla.setRowCount(1) id_widget = QTableWidgetItem(str(part.id)) origen_widget = QTableWidgetItem(f"({part.origen_x},{part.origen_y})") destino_widget = QTableWidgetItem(f"({part.destino_x},{part.destino_y})") velocidad_widget = QTableWidgetItem(str(part.velocidad)) color_widget = QTableWidgetItem(f"rgb({part.red},{part.green},{part.blue})") distancia_widget = QTableWidgetItem(f"{part.distancia:.4f}") self.ui.tabla.setItem(0, 0, id_widget) self.ui.tabla.setItem(0, 1, origen_widget) self.ui.tabla.setItem(0, 2, destino_widget) self.ui.tabla.setItem(0, 3, velocidad_widget) self.ui.tabla.setItem(0, 4, color_widget) self.ui.tabla.setItem(0, 5, distancia_widget) return QMessageBox.warning( self, 'Atención', f"La particula con id {id} no pudo ser encontrada" ) self.ui.buscar_lineEdit.clear() @Slot() def abrir_archivo(self): ubicacion = QFileDialog.getOpenFileName( self, 'Abrir archivo', './examples', 'JSON (*.json)' )[0] if self.cern.abrir(ubicacion): QMessageBox.information( self, "Éxito", "Se abrió el archivo " + ubicacion ) self.mostrar() else: QMessageBox.critical( self, "Error", "Error al abrir el archivo " + ubicacion ) @Slot() def guardar_archivo(self): ubicacion = QFileDialog.getSaveFileName( self, 'Abrir archivo', './examples', 'JSON (*.json)' )[0] print("Archivo: " + ubicacion) if self.cern.guardar(ubicacion): QMessageBox.information( self, "Éxito", "Se guardó en el archivo " + ubicacion ) else: QMessageBox.critical( self, "Error", "Error al guardar el archivo " + ubicacion ) @Slot() def agregar_inicio(self): self.cern.agregar_inicio(self.get_particula()) self.mostrar() @Slot() def agregar_fin(self): self.cern.agregar_final(self.get_particula()) self.mostrar() @Slot() def mostrar_grafo(self): self.grafo = True self.mostrar() @Slot() def mostrar_plano(self): self.grafo = False self.mostrar() @Slot() def mostrar(self): self.ui.salida.clear() index = self.ui.tableSort.currentIndex() if index == 0: self.cern.sort_by_id() elif index == 1: self.cern.sort_by_distancia() elif index == 2: self.cern.sort_by_velocidad() if self.grafo: grafo = self.cern.to_dict() formated = pformat(grafo, width=40, indent=1) print(formated) self.ui.salida.insertPlainText(formated) else: self.ui.salida.insertPlainText(str(self.cern)) self.mostrar_tabla() self.dibujar() def get_particula(self): id = int(self.ui.id.text()) orig_x = int(self.ui.origin_x.text()) orig_y = int(self.ui.origin_y.text()) dest_x = int(self.ui.destination_x.text()) dest_y = int(self.ui.destination_y.text()) velocidad = int(self.ui.velocity.text()) color_r = int(self.ui.color_r.text()) color_g = int(self.ui.color_g.text()) color_b = int(self.ui.color_b.text()) return Particula(id,orig_x,orig_y,dest_x,dest_y,velocidad,color_r,color_g,color_b)
class VideoCompareView(object): def __init__(self, parent=None): self.widget = QWidget() self.setting_widget = Ui_video_pre_settings() self.setting_widget.setupUi(self.widget) self.scene = QGraphicsScene() self.imageview = ImageView(self.scene, self.widget) self.setting_widget.videoview.addWidget(self.imageview) parent.addWidget(self.widget) # init params self.video_valid = False self.process_speed = 33 self.skip_frames = 0 self.processing_video = False self.video_timer = QTimer() self.video_timer.timeout.connect(self.open_frame) # init func self.setting_widget.openvideo.clicked.connect(self.open_video) self.setting_widget.open_rtsp.clicked.connect(self.open_rtsp) self.setting_widget.skipframe.valueChanged.connect(self.set_skip_frame) self.imageview.sigDragEvent.connect(self.open_video_path) def set_skip_frame(self, value): # self.skip_frames = self.setting_widget.skipframe.value() self.skip_frames = value self.vertify_video() def open_video(self): videopath = QFileDialog.getOpenFileName(None, '打开文件', './', 'video files(*.mp4)') if (videopath[0] != ''): self.open_video_path(videopath[0]) def open_video_path(self, string): self.setting_widget.path.setText(string) self.vertify_video() # self.set_ui_enable(True) def open_rtsp(self): self.rtsp_config_window = QDialog() self.rtsp_config_ui = Ui_RtspConfigView() self.rtsp_config_ui.setupUi(self.rtsp_config_window) self.rtsp_config_window.show() self.rtsp_config_ui.buttonBox.clicked.connect(self.rtsp_config) def rtsp_config(self): username = self.rtsp_config_ui.username.text() password = self.rtsp_config_ui.password.text() ip = self.rtsp_config_ui.ip.text() port = self.rtsp_config_ui.port.text() # 移动设备需要通过adb映射端口 if (self.rtsp_config_ui.isphoto.isChecked() == True): command = "forward tcp:" + port + ' ' + "tcp:" + port os.system("adb " + command) os.system("kdb " + command) rtsp_path = "rtsp://" + username + ":" + password + "@" + ip + ":" + port self.open_video_path(rtsp_path) def vertify_video(self): # 输出参数初始化 # self.frame_count = 0 self.vidcap = cv2.VideoCapture(self.setting_widget.path.text()) # 片头调过多少帧 self.vidcap.set(cv2.CAP_PROP_POS_FRAMES, self.skip_frames) success, frame = self.vidcap.read() if success: self.display(frame) self.video_valid = True else: self.critical_window_show('视频打不开') self.video_valid = False return def display(self, img): self.scene.clear() self.scene.addPixmap( QPixmap( QImage(img, img.shape[1], img.shape[0], QImage.Format_BGR888))) def open_frame(self): success, frame = self.vidcap.read() if success: # self.frame_count += 1 self.display(frame) else: self.video_timer.stop() self.processing_video = False self.video_valid = False def set_speed(self, value): speed = value * 33 if (self.processing_video == True and int(speed) != self.process_speed): self.process_speed = int(speed) self.stop_video() self.start_video() def start_video(self): if (self.video_valid == True): self.processing_video = True # 增加定时器,每100ms进行一帧的处理 self.video_timer.start(self.process_speed) def stop_video(self): self.processing_video = False self.video_timer.stop() def restart_video(self): self.stop_video() self.vertify_video() self.start_video() def critical_window_show(self, str): reply = QMessageBox.critical(self.widget, '警告', str, QMessageBox.Yes, QMessageBox.Yes) return