mirror of
https://github.com/wassname/sloth.git
synced 2026-07-23 13:10:07 +08:00
move inserters to sceneitems
This commit is contained in:
+1
-130
@@ -1,140 +1,11 @@
|
||||
from PyQt4.QtGui import *
|
||||
from PyQt4.QtCore import *
|
||||
from sceneitems import *
|
||||
from annotationmodel import ImageRole
|
||||
from annotationmodel import TypeRole, ImageRole
|
||||
import math
|
||||
import okapy
|
||||
from okapy.guiqt.utilities import toQImage
|
||||
|
||||
class ItemInserter:
|
||||
def __init__(self, scene, mode=None):
|
||||
self.scene_ = scene
|
||||
self.mode_ = mode
|
||||
|
||||
def setScene(self, scene):
|
||||
self.scene_ = scene
|
||||
def scene(self):
|
||||
return self.scene_
|
||||
|
||||
def setMode(self, mode):
|
||||
self.mode_ = mode
|
||||
def mode(self):
|
||||
return self.mode
|
||||
|
||||
def mousePressEvent(self, event, index):
|
||||
event.accept()
|
||||
|
||||
def mouseReleaseEvent(self, event, index):
|
||||
event.accept()
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
event.accept()
|
||||
|
||||
def keyPressEvent(self, event, index):
|
||||
event.ignore()
|
||||
|
||||
class PointItemInserter(ItemInserter):
|
||||
def mousePressEvent(self, event, index):
|
||||
pos = event.scenePos()
|
||||
ann = {'type': 'point',
|
||||
'x': event.pos().x(), 'y': event.pos().y()}
|
||||
index.model().addAnnotation(index, ann)
|
||||
event.accept()
|
||||
|
||||
class RectItemInserter(ItemInserter):
|
||||
def __init__(self, scene, mode=None):
|
||||
ItemInserter.__init__(self, scene, mode)
|
||||
self.current_item_ = None
|
||||
self.init_pos_ = None
|
||||
|
||||
def mousePressEvent(self, event, index):
|
||||
pos = event.scenePos()
|
||||
item = QGraphicsRectItem(QRectF(pos.x(), pos.y(), 0, 0))
|
||||
item.setPen(Qt.red)
|
||||
self.current_item_ = item
|
||||
self.init_pos_ = pos
|
||||
self.scene().addItem(item)
|
||||
event.accept()
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
assert self.init_pos_ is not None
|
||||
rect = QRectF(self.init_pos_, event.scenePos()).normalized()
|
||||
self.current_item_.setRect(rect)
|
||||
|
||||
event.accept()
|
||||
|
||||
def mouseReleaseEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
if self.current_item_.rect().width() > 1 and \
|
||||
self.current_item_.rect().height() > 1:
|
||||
rect = self.current_item_.rect()
|
||||
ann = {'type': 'rect',
|
||||
'x': rect.x(), 'y': rect.y(),
|
||||
'width': rect.width(), 'height': rect.height()}
|
||||
index.model().addAnnotation(index, ann)
|
||||
self.scene().removeItem(self.current_item_)
|
||||
self.current_item_ = None
|
||||
self.init_pos_ = None
|
||||
|
||||
event.accept()
|
||||
|
||||
class FixedRatioRectItemInserter(RectItemInserter):
|
||||
def __init__(self, scene, mode=None):
|
||||
RectItemInserter.__init__(self, scene, mode)
|
||||
self.ratio_ = 1
|
||||
if mode is not None:
|
||||
self.ratio_ = float(mode.get('_ratio', 1))
|
||||
|
||||
def setMode(self, mode):
|
||||
if mode is not None:
|
||||
self.ratio_ = float(mode.get('_ratio', 1))
|
||||
RectItemInserter.setMode(self, mode)
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
new_geometry = QRectF(self.current_item_.rect().topLeft(), event.scenePos())
|
||||
dx = new_geometry.width()
|
||||
dy = new_geometry.height()
|
||||
d = math.sqrt(dx*dx + dy*dy)
|
||||
r = self.ratio_
|
||||
k = math.sqrt(r*r+1)
|
||||
h = d/k
|
||||
w = d*r/k
|
||||
new_geometry.setWidth(w)
|
||||
new_geometry.setHeight(h)
|
||||
self.current_item_.setRect(new_geometry.normalized())
|
||||
|
||||
event.accept()
|
||||
|
||||
class PolygonItemInserter(ItemInserter):
|
||||
def __init__(self, scene, mode=None):
|
||||
ItemInserter.__init__(self, scene, mode)
|
||||
self.current_item_ = None
|
||||
|
||||
def mousePressEvent(self, event, index):
|
||||
pos = event.scenePos()
|
||||
if self.current_item_ is None:
|
||||
item = QGraphicsPolygonItem(QPolygonF([pos]))
|
||||
self.current_item_ = item
|
||||
self.scene().addItem(item)
|
||||
else:
|
||||
polygon = self.current_item_.polygon()
|
||||
polygon.append(pos)
|
||||
self.current_item_.setPolygon(polygon)
|
||||
|
||||
event.accept()
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
pos = event.scenePos()
|
||||
polygon = self.current_item_.polygon()
|
||||
assert polygon.size() > 0
|
||||
polygon[-1] = pos
|
||||
self.current_item_.setPolygon(polygon)
|
||||
|
||||
event.accept()
|
||||
|
||||
class AnnotationScene(QGraphicsScene):
|
||||
|
||||
# TODO signal itemadded
|
||||
|
||||
@@ -218,6 +218,179 @@ class AnnotationGraphicsPointItem(AnnotationGraphicsItem):
|
||||
self.data_ = self.index().data(DataRole).toPyObject()
|
||||
self.updatePoint()
|
||||
|
||||
class ItemInserter:
|
||||
def __init__(self, scene, mode=None):
|
||||
self.scene_ = scene
|
||||
self.mode_ = mode
|
||||
|
||||
def setScene(self, scene):
|
||||
self.scene_ = scene
|
||||
def scene(self):
|
||||
return self.scene_
|
||||
|
||||
def setMode(self, mode):
|
||||
self.mode_ = mode
|
||||
def mode(self):
|
||||
return self.mode
|
||||
|
||||
def mousePressEvent(self, event, index):
|
||||
event.accept()
|
||||
|
||||
def mouseReleaseEvent(self, event, index):
|
||||
event.accept()
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
event.accept()
|
||||
|
||||
def keyPressEvent(self, event, index):
|
||||
event.ignore()
|
||||
|
||||
class PointItemInserter(ItemInserter):
|
||||
def mousePressEvent(self, event, index):
|
||||
pos = event.scenePos()
|
||||
ann = {'type': 'point',
|
||||
'x': event.pos().x(), 'y': event.pos().y()}
|
||||
index.model().addAnnotation(index, ann)
|
||||
event.accept()
|
||||
|
||||
class RectItemInserter(ItemInserter):
|
||||
def __init__(self, scene, mode=None):
|
||||
ItemInserter.__init__(self, scene, mode)
|
||||
self.current_item_ = None
|
||||
self.init_pos_ = None
|
||||
|
||||
def mousePressEvent(self, event, index):
|
||||
pos = event.scenePos()
|
||||
item = QGraphicsRectItem(QRectF(pos.x(), pos.y(), 0, 0))
|
||||
item.setPen(Qt.red)
|
||||
self.current_item_ = item
|
||||
self.init_pos_ = pos
|
||||
self.scene().addItem(item)
|
||||
event.accept()
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
assert self.init_pos_ is not None
|
||||
rect = QRectF(self.init_pos_, event.scenePos()).normalized()
|
||||
self.current_item_.setRect(rect)
|
||||
|
||||
event.accept()
|
||||
|
||||
def mouseReleaseEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
if self.current_item_.rect().width() > 1 and \
|
||||
self.current_item_.rect().height() > 1:
|
||||
rect = self.current_item_.rect()
|
||||
ann = {'type': 'rect',
|
||||
'x': rect.x(), 'y': rect.y(),
|
||||
'width': rect.width(), 'height': rect.height()}
|
||||
index.model().addAnnotation(index, ann)
|
||||
self.scene().removeItem(self.current_item_)
|
||||
self.current_item_ = None
|
||||
self.init_pos_ = None
|
||||
|
||||
event.accept()
|
||||
|
||||
class FixedRatioRectItemInserter(RectItemInserter):
|
||||
def __init__(self, scene, mode=None):
|
||||
RectItemInserter.__init__(self, scene, mode)
|
||||
self.ratio_ = 1
|
||||
if mode is not None:
|
||||
self.ratio_ = float(mode.get('_ratio', 1))
|
||||
|
||||
def setMode(self, mode):
|
||||
if mode is not None:
|
||||
self.ratio_ = float(mode.get('_ratio', 1))
|
||||
RectItemInserter.setMode(self, mode)
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
new_geometry = QRectF(self.current_item_.rect().topLeft(), event.scenePos())
|
||||
dx = new_geometry.width()
|
||||
dy = new_geometry.height()
|
||||
d = math.sqrt(dx*dx + dy*dy)
|
||||
r = self.ratio_
|
||||
k = math.sqrt(r*r+1)
|
||||
h = d/k
|
||||
w = d*r/k
|
||||
new_geometry.setWidth(w)
|
||||
new_geometry.setHeight(h)
|
||||
self.current_item_.setRect(new_geometry.normalized())
|
||||
|
||||
event.accept()
|
||||
|
||||
class PolygonItemInserter(ItemInserter):
|
||||
def __init__(self, scene, mode=None):
|
||||
ItemInserter.__init__(self, scene, mode)
|
||||
self.current_item_ = None
|
||||
|
||||
def mousePressEvent(self, event, index):
|
||||
pos = event.scenePos()
|
||||
if self.current_item_ is None:
|
||||
item = QGraphicsPolygonItem(QPolygonF([pos]))
|
||||
self.current_item_ = item
|
||||
self.scene().addItem(item)
|
||||
else:
|
||||
polygon = self.current_item_.polygon()
|
||||
polygon.append(pos)
|
||||
self.current_item_.setPolygon(polygon)
|
||||
|
||||
event.accept()
|
||||
|
||||
def mouseMoveEvent(self, event, index):
|
||||
if self.current_item_ is not None:
|
||||
pos = event.scenePos()
|
||||
polygon = self.current_item_.polygon()
|
||||
assert polygon.size() > 0
|
||||
polygon[-1] = pos
|
||||
self.current_item_.setPolygon(polygon)
|
||||
|
||||
event.accept()
|
||||
|
||||
class AnnotationGraphicsItemFactory:
|
||||
def __init__(self):
|
||||
self.items_ = {}
|
||||
self.inserters_ = {}
|
||||
|
||||
def register(self, _type, item, inserter, replace=False):
|
||||
_type = _type.lower()
|
||||
|
||||
if _type in self.items_ and not replace:
|
||||
raise Exception("Type %s already has an item: %s" % \
|
||||
(_type, str(self.items_[_type])))
|
||||
else:
|
||||
self.items_[_type] = item
|
||||
|
||||
if _type in self.inserters_ and not replace:
|
||||
raise Exception("Type %s already has an inserter: %s" % \
|
||||
(_type, str(self.inserters_[_type])))
|
||||
else:
|
||||
self.inserters_[_type] = inserter
|
||||
|
||||
def clear(self, _type=None):
|
||||
if _type is None:
|
||||
self.items_ = {}
|
||||
self.inserters_ = {}
|
||||
else:
|
||||
_type = _type.lower()
|
||||
if _type in self.items_:
|
||||
del self.items_[_type]
|
||||
if _type in self.inserters_:
|
||||
del self.inserters_[_type]
|
||||
|
||||
def createItem(self, _type, *args, **kwargs):
|
||||
_type = _type.lower()
|
||||
|
||||
if _type not in self.items_:
|
||||
return None
|
||||
return self.items_[_type](*args, **kwargs)
|
||||
|
||||
def createItemInserter(self, _type, *args, **kwargs):
|
||||
_type = _type.lower()
|
||||
|
||||
if _type not in self.inserters_:
|
||||
return None
|
||||
return self.inserters_[_type](*args, **kwargs)
|
||||
|
||||
# register common item types
|
||||
AnnotationGraphicsItem.addItemType('rect', AnnotationGraphicsRectItem)
|
||||
|
||||
Reference in New Issue
Block a user