summaryrefslogtreecommitdiff
path: root/Graphics.py
diff options
context:
space:
mode:
Diffstat (limited to 'Graphics.py')
-rw-r--r--Graphics.py374
1 files changed, 374 insertions, 0 deletions
diff --git a/Graphics.py b/Graphics.py
new file mode 100644
index 0000000..4d0a5ea
--- /dev/null
+++ b/Graphics.py
@@ -0,0 +1,374 @@
+from functools import partial
+from collections import defaultdict
+import sys
+import numpy as np
+from OMChem.Flowsheet import Flowsheet
+from OMChem.MatStm import MatStm
+from OMChem.Mixer import Mixer
+from OMChem.Heater import Heater
+from OMChem.Splitter import Splitter
+from OMChem.ShortcutColumn import ShortcutColumn
+
+import pandas as pd
+from PyQt5.QtCore import *
+from PyQt5.QtWidgets import *
+from PyQt5.QtGui import QTextDocument ,QTextCursor ,QTextCharFormat ,QFont ,QPixmap
+from PyQt5.uic import loadUiType
+from PyQt5.QtCore import Qt
+from PyQt5.QtWidgets import QGraphicsProxyWidget, QGraphicsObject, QGraphicsEllipseItem ,QGraphicsPixmapItem,QApplication, QGraphicsView, QGraphicsScene, QHBoxLayout, QWidget, QLabel
+from PyQt5.QtGui import QBrush ,QTransform ,QMouseEvent
+import PyQt5.QtGui as QtGui
+import PyQt5.QtCore as QtCore
+import PyQt5.QtWidgets as QtWidgets
+from component_selector import *
+from dockWidget import dockWidget
+from resDockWidget import resdockWidget
+from helper import helperFunc
+import datetime
+from container import Container
+
+class Graphics(QDialog):
+
+ def __init__(self):
+ QDialog.__init__(self)
+ self.scene = QGraphicsScene()
+ self.scene.setItemIndexMethod(QGraphicsScene.BspTreeIndex)
+
+ def getScene(self):
+ return self.scene
+
+ '''def getContainer(self, textBrowser):
+ return Container(textBrowser)
+
+ def getComponentSelector(self):
+ return componentSelector(self)'''
+
+ def createNodeItem(self, conntype, container):
+ return NodeItem(conntype, container)
+
+class NodeLine(QtWidgets.QGraphicsPathItem):
+ def __init__(self, pointA, pointB , socket):
+ super(NodeLine, self).__init__()
+ self._pointA = pointA
+ self._pointB = pointB
+ self.socket = socket
+ self._source = None
+ self._target = None
+ self.setZValue(-1)
+ self.setBrush(QtGui.QColor(0,0,255,255))
+ self.pen = QtGui.QPen()
+
+ self.pen.setStyle(QtCore.Qt.SolidLine)
+ self.pen.setWidth(1)
+ self.pen.setColor(QtGui.QColor(0,0,255,255))
+ self.setPen(self.pen)
+
+ def updatePath(self):
+ path = QtGui.QPainterPath()
+ path.moveTo(self.pointA)
+ midptx = 0.5*(self.pointA.x() + self.pointB.x())
+
+
+ ctrl1_1 = QtCore.QPointF(self.pointA.x(), self.pointA.y())
+ ctrl2_1 = QtCore.QPointF(self.pointA.x(), self.pointA.y())
+ pt1 = QtCore.QPointF(midptx , self.pointA.y())
+ path.cubicTo(ctrl1_1, ctrl2_1, pt1)
+
+ path.moveTo(pt1)
+
+ ctrl1_2 = QtCore.QPointF(midptx, self.pointB.y())
+ ctrl2_2 = QtCore.QPointF(midptx, self.pointB.y())
+ pt2 = QtCore.QPointF(midptx , self.pointB.y())
+ path.cubicTo(ctrl1_2, ctrl2_2, pt2)
+ path.moveTo(pt2)
+
+ ctrl1_3 = QtCore.QPointF(midptx, self.pointB.y())
+ ctrl2_3 = QtCore.QPointF(midptx, self.pointB.y())
+ path.cubicTo(ctrl1_3, ctrl2_3, self.pointB)
+ self.setPath(path)
+
+ def paint(self, painter, option, widget):
+ painter.setPen(self.pen)
+ painter.drawPath(self.path())
+
+ @property
+ def pointA(self):
+ #print('a')
+ return self._pointA
+
+ @pointA.setter
+ def pointA(self, point):
+ #print('seta')
+ self._pointA = point
+ self.updatePath()
+
+ @property
+ def pointB(self):
+ #print('b')
+ return self._pointB
+
+ @pointB.setter
+ def pointB(self, point):
+ #print('set b')
+ self._pointB = point
+ self.updatePath()
+
+ @property
+ def source(self):
+ #print('source')
+ return self._source
+
+ @source.setter
+ def source(self, widget):
+ #print('set source')
+ self._source = widget
+
+ @property
+ def target(self):
+ #print('target')
+ return self._target
+
+ @target.setter
+ def target(self, widget):
+ #print('set target')
+ self._target = widget
+
+ def __delete__(self,instance):
+ del self._source
+ del self._target
+ del self._pointA
+ del self._pointB
+
+class NodeSocket(QtWidgets.QGraphicsItem):
+ def __init__(self, rect, parent, socketType,container):
+ super(NodeSocket, self).__init__(parent)
+ self.rect = rect
+ self.type = socketType
+ self.parent=parent
+ self.container=container
+ self.newLine=None
+ self.otherLine=None
+
+ # Brush.
+ self.brush = QtGui.QBrush()
+ self.brush.setStyle(QtCore.Qt.SolidPattern)
+ self.brush.setColor(QtGui.QColor(180,20,90,255))
+ # Pen.
+ self.pen = QtGui.QPen()
+ self.pen.setStyle(QtCore.Qt.SolidLine)
+ self.pen.setWidth(1)
+ self.pen.setColor(QtGui.QColor(20,20,20,255))
+
+ # Lines.
+ self.outLines = []
+ self.inLines = []
+
+ def shape(self):
+ path = QtGui.QPainterPath()
+ path.addEllipse(self.boundingRect())
+ return path
+
+ def boundingRect(self):
+ return QtCore.QRectF(self.rect)
+
+ def paint(self, painter, option, widget):
+ painter.setBrush(self.brush)
+ painter.setPen(self.pen)
+ painter.drawEllipse(self.rect)
+
+ def mousePressEvent(self, event):
+ if self.type == 'op':
+ rect = self.boundingRect()
+ pointA = QtCore.QPointF(rect.x() + rect.width()/2, rect.y() + rect.height()/2)
+ pointA = self.mapToScene(pointA)
+ pointB = self.mapToScene(event.pos())
+ self.newLine = NodeLine(pointA, pointB ,'op')
+ self.outLines.append(self.newLine)
+ self.scene().addItem(self.newLine)
+ elif self.type == 'in':
+ rect = self.boundingRect()
+ pointA = self.mapToScene(event.pos())
+ pointB = QtCore.QPointF(rect.x() + rect.width()/2, rect.y() + rect.height()/2)
+ pointB = self.mapToScene(pointB)
+ self.newLine = NodeLine(pointA, pointB, 'in')
+ self.inLines.append(self.newLine)
+ self.scene().addItem(self.newLine)
+ else:
+ super(NodeSocket, self).mousePressEvent(event)
+
+ def mouseMoveEvent(self, event):
+ if self.type == 'op':
+ pointB = self.mapToScene(event.pos())
+ self.newLine.pointB = pointB
+ if self.otherLine:
+ self.otherLine.pointB=pointB
+
+ elif self.type == 'in':
+ pointA = self.mapToScene(event.pos())
+ self.newLine.pointA = pointA
+ if self.otherLine:
+ self.otherLine.pointA=pointA
+ else:
+ super(NodeSocket, self).mouseMoveEvent(event)
+
+ def mouseReleaseEvent(self, event):
+ item = self.scene().itemAt(event.scenePos().toPoint(),QtGui.QTransform())
+ item.otherLine=self.newLine
+ if (self.type == 'op') and (item.type == 'in'):
+ self.newLine.source = self
+ self.newLine.target = item
+ item.inLines.append(self.newLine)
+ self.newLine.pointB = item.getCenter()
+ self.container.updateConn(self.newLine.source.parent.obj,self.newLine.target.parent.obj)
+ elif (self.type =='in') and (item.type == 'op'):
+ self.newLine.source = item
+ self.newLine.target = self
+ item.outLines.append(self.newLine)
+ self.newLine.pointA = item.getCenter()
+ self.container.updateConn(self.newLine.source.parent.obj,self.newLine.target.parent.obj)
+ else:
+ self.scene().removeItem(self.newLine)
+ if(self.newLine in self.inLines):
+ self.inLines.remove(self.newLine)
+ if(self.newLine in self.outLines):
+ self.outLines.remove(self.newLine)
+ del self.newLine
+ super(NodeSocket, self).mouseReleaseEvent(event)
+
+ def getCenter(self):
+ rect = self.boundingRect()
+ center = QtCore.QPointF(rect.x() + rect.width()/2, rect.y() + rect.height()/2)
+ center = self.mapToScene(center)
+ return center
+
+class NodeItem(QtWidgets.QGraphicsItem):
+ def __init__(self,comptype,container):
+ l = ['Mixer','Splitter']
+ super(NodeItem, self).__init__()
+ self.type = comptype
+
+ # for creating unit operation objects without helper function
+ if (self.type == 'MatStm'):
+ self.obj = MatStm(CompNames=compound_selected)
+ elif (self.type == 'ShortCol'): # the only class that class name and type does not match
+ self.obj = ShortcutColumn()
+ else:
+ self.obj = eval(self.type)()
+
+
+ #self.obj = myhelperFunc(self.type)
+ self.name = self.obj.getname()
+ self.pos = None
+ self.setToolTip(self.name)
+ self.nin = self.obj.no_of_input
+ self.nop = self.obj.no_of_output
+
+ self.container=container
+ self.container.addUnitOp(self.obj)
+ if(self.type not in l):
+ self.mainwindow= findMainWindow(self)
+ self.dockWidget=dockWidget(self.name,self.type,self.obj)
+ self.mainwindow.addDockWidget(Qt.LeftDockWidgetArea, self.dockWidget)
+ self.dockWidget.hide()
+
+ self.pic=QtGui.QPixmap("icons/"+self.type+".png")
+ self.rect = QtCore.QRect(0,0,self.pic.width(),self.pic.height())
+ self.text = QGraphicsTextItem(self)
+ f = QFont()
+ f.setPointSize(8)
+ self.text.setFont(f)
+ self.text.setDefaultTextColor(QtGui.QColor(73,36,73,255))
+ self.text.setParentItem(self)
+ self.text.setPos(-2.5, self.rect.height()-15)
+ self.text.setPlainText(self.name)
+
+ self.setFlag(QtWidgets.QGraphicsPixmapItem.ItemIsMovable)
+ self.setFlag(QtWidgets.QGraphicsPixmapItem.ItemIsSelectable)
+ self.initUi()
+
+ # Brush
+ self.brush = QtGui.QBrush()
+ self.brush.setStyle(QtCore.Qt.SolidPattern)
+ self.brush.setColor(QtGui.QColor(80,0,90,255))
+ # Pen.
+ self.pen = QtGui.QPen()
+ self.pen.setStyle(QtCore.Qt.SolidLine)
+ self.pen.setWidth(1)
+ self.pen.setColor(QtGui.QColor(20,20,20,255))
+
+ self.selPen = QtGui.QPen()
+ self.selPen.setStyle(QtCore.Qt.SolidLine)
+ self.selPen.setWidth(2)
+ self.selPen.setColor(QtGui.QColor(222,192,222))
+
+ def initUi(self):
+ self.Input , self.Output = self.initializeSockets(self.type)
+
+ def shape(self):
+ path = QtGui.QPainterPath()
+ path.addRect(self.boundingRect())
+ return path
+
+ def boundingRect(self):
+ return QtCore.QRectF(self.rect)
+
+ def paint(self, painter, option, widget):
+ if self.isSelected():
+ painter.setPen(self.selPen)
+ painter.drawRect(QtCore.QRectF(self.rect))
+ else:
+ painter.setPen(self.pen)
+ painter.drawPixmap(self.rect,self.pic)
+
+ def initializeSockets(self,type):
+ if(self.type=="Flash" or self.type=="CompSep"):
+ Input = [NodeSocket(QtCore.QRect(-2.5+5.5,(self.rect.height()*x/(self.nin+1))-8,4,4), self, 'in',self.container) for x in range(1,self.nin+1) ]
+ Output = [NodeSocket(QtCore.QRect(self.rect.width()-7.5,(self.rect.height()*x*0.90/(self.nop+1))-4,4,4), self, 'op',self.container) for x in range(1,self.nop+1)]
+ return Input,Output
+ elif(self.type=="AdiaComp" or self.type=="AdiaExp" or self.type =="Mixer" or self.type =="Splitter" or self.type =="Valve" ):
+ Input = [NodeSocket(QtCore.QRect(-3.5,(self.rect.height()*x/(self.nin+1))-6,4,4), self, 'in',self.container) for x in range(1,self.nin+1) ]
+ Output = [NodeSocket(QtCore.QRect(self.rect.width()-2.5,(self.rect.height()*x/(self.nop+1))-6,4,4), self, 'op',self.container) for x in range(1,self.nop+1)]
+ return Input,Output
+ elif(self.type=="Cooler" or self.type=="Heater"):
+ Input = [NodeSocket(QtCore.QRect(3.5,(self.rect.height()*x/(self.nin+1))-4,4,4), self, 'in',self.container) for x in range(1,self.nin+1) ]
+ Output = [NodeSocket(QtCore.QRect(self.rect.width()-8.0,(self.rect.height()*x/(self.nop+1))-4,4,4), self, 'op',self.container) for x in range(1,self.nop+1)]
+ return Input,Output
+ elif(self.type=="Pump"):
+ Input = [NodeSocket(QtCore.QRect(-2.5,(self.rect.height()*x/(self.nin+1))-10,4,4), self, 'in',self.container) for x in range(1,self.nin+1) ]
+ Output = [NodeSocket(QtCore.QRect(self.rect.width()-2.5,-2.5,4,4), self, 'op',self.container) for x in range(1,self.nop+1)]
+ return Input,Output
+ elif(self.type=="DistCol" or self.type=="ShortCol"):
+ Input = [NodeSocket(QtCore.QRect(-2.5,(self.rect.height()*x/(self.nin+1))-12,5,5), self, 'in',self.container) for x in range(1,self.nin+1) ]
+ Output = [NodeSocket(QtCore.QRect(self.rect.width()-5.5,(self.rect.height()*1.44*x/(self.nop+1))-67,5,5), self, 'op',self.container) for x in range(1,self.nop+1)]
+ return Input,Output
+ elif(self.type=="MatStm"):
+ Input = [NodeSocket(QtCore.QRect(-2.5,(self.rect.height()*x/(self.nin+1))-1,4,4), self, 'in',self.container) for x in range(1,self.nin+1) ]
+ Output = [NodeSocket(QtCore.QRect(self.rect.width()-2.5,(self.rect.height()*x/(self.nin+1))-1,4,4), self, 'op',self.container) for x in range(1,self.nop+1)]
+ return Input,Output
+
+ def mouseMoveEvent(self, event):
+ #print(event.scenePos())
+ super(NodeItem, self).mouseMoveEvent(event)
+ for output in self.Output:
+ for line in output.outLines:
+ line.pointA = line.source.getCenter()
+ line.pointB = line.target.getCenter()
+ for input in self.Input:
+ for line in input.inLines:
+ line.pointA = line.source.getCenter()
+ line.pointB = line.target.getCenter()
+ self.pos = event.scenePos()
+
+ def mouseDoubleClickEvent(self, event):
+ self.setPos(event.scenePos().x()-250,event.scenePos().y())
+ self.dockWidget.show()
+
+def findMainWindow(self):
+ '''
+ Global function to find the (open) QMainWindow in application
+ '''
+ app = QApplication.instance()
+ for widget in app.topLevelWidgets():
+ if isinstance(widget, QMainWindow):
+ return widget
+ return None