123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106 |
- #!/usr/bin/python
- # -*- coding: utf-8 -*-
- from PyQt4.QtGui import *
- from PyQt4.QtCore import *
- # FIXME:
- # - Add support for highlighting vertices.
- class Shape(object):
- P_SQUARE, P_ROUND = range(2)
- ## The following class variables influence the drawing
- ## of _all_ shape objects.
- line_color = QColor(0, 255, 0, 128)
- fill_color = QColor(255, 0, 0, 128)
- select_color = QColor(255, 255, 255)
- point_type = P_SQUARE
- point_size = 8
- scale = 1.0
- def __init__(self, label=None, line_color=None):
- self.label = label
- self.points = []
- self.fill = False
- self.selected = False
- if line_color is not None:
- # Override the class line_color attribute
- # with an object attribute. Currently this
- # is used for drawing the pending line a different color.
- self.line_color = line_color
- def addPoint(self, point):
- self.points.append(point)
- def popPoint(self):
- if self.points:
- return self.points.pop()
- return None
- def isClosed(self):
- return len(self.points) > 1 and self[0] == self[-1]
- # TODO:
- # The paths could be stored and elements added directly to them.
- def paint(self, painter):
- if self.points:
- pen = QPen(self.select_color if self.selected else self.line_color)
- # Try using integer sizes for smoother drawing(?)
- pen.setWidth(max(1, int(round(2.0 / self.scale))))
- painter.setPen(pen)
- line_path = QPainterPath()
- vrtx_path = QPainterPath()
- line_path.moveTo(QPointF(self.points[0]))
- self.drawVertex(vrtx_path, self.points[0])
- for p in self.points[1:]:
- line_path.lineTo(QPointF(p))
- # Skip last element, otherwise its vertex is not filled.
- if p != self.points[0]:
- self.drawVertex(vrtx_path, p)
- painter.drawPath(line_path)
- painter.fillPath(vrtx_path, self.line_color)
- if self.fill:
- painter.fillPath(line_path, self.fill_color)
- def drawVertex(self, path, point):
- d = self.point_size / self.scale
- if self.point_type == self.P_SQUARE:
- path.addRect(point.x() - d/2, point.y() - d/2, d, d)
- else:
- path.addEllipse(point, d/2.0, d/2.0)
- def containsPoint(self, point):
- return self.makePath().contains(point)
- def makePath(self):
- path = QPainterPath(self.points[0])
- for p in self.points[1:]:
- path.lineTo(p)
- return path
- def boundingRect(self):
- return self.makePath().boundingRect()
- def moveBy(self, offset):
- self.points = [p + offset for p in self.points]
- def copy(self):
- shape = Shape("Copy of %s" % self.label )
- shape.points= [p for p in self.points]
- shape.fill = self.fill
- shape.selected = self.selected
- return shape
- def __len__(self):
- return len(self.points)
- def __getitem__(self, key):
- return self.points[key]
- def __setitem__(self, key, value):
- self.points[key] = value
|