From ba31b3d7ba22b498807845ff14668afa450de7be Mon Sep 17 00:00:00 2001
From: Luke Campagnola <>
Date: Tue, 28 May 2013 18:47:33 -0400
Subject: [PATCH] Legends can be dragged by user

---
 .../graphicsItems/GraphicsWidgetAnchor.py     | 45 +++++++++++++++++++
 pyqtgraph/graphicsItems/LegendItem.py         | 12 +++--
 2 files changed, 54 insertions(+), 3 deletions(-)

diff --git a/pyqtgraph/graphicsItems/GraphicsWidgetAnchor.py b/pyqtgraph/graphicsItems/GraphicsWidgetAnchor.py
index 3174e6e0..251bc0c8 100644
--- a/pyqtgraph/graphicsItems/GraphicsWidgetAnchor.py
+++ b/pyqtgraph/graphicsItems/GraphicsWidgetAnchor.py
@@ -47,7 +47,52 @@ class GraphicsWidgetAnchor(object):
         self.__parentAnchor = parentPos
         self.__offset = offset
         self.__geometryChanged()
+    
+
+    def autoAnchor(self, pos, relative=True):
+        """
+        Set the position of this item relative to its parent by automatically 
+        choosing appropriate anchor settings.
+        
+        If relative is True, one corner of the item will be anchored to 
+        the appropriate location on the parent with no offset. The anchored
+        corner will be whichever is closest to the parent's boundary.
+        
+        If relative is False, one corner of the item will be anchored to the same
+        corner of the parent, with an absolute offset to achieve the correct
+        position. 
+        """
+        pos = Point(pos)
+        br = self.mapRectToParent(self.boundingRect()).translated(pos - self.pos())
+        pbr = self.parentItem().boundingRect()
+        anchorPos = [0,0]
+        parentPos = Point()
+        itemPos = Point()
+        if abs(br.left() - pbr.left()) < abs(br.right() - pbr.right()):
+            anchorPos[0] = 0
+            parentPos[0] = pbr.left()
+            itemPos[0] = br.left()
+        else:
+            anchorPos[0] = 1
+            parentPos[0] = pbr.right()
+            itemPos[0] = br.right()
+
+        if abs(br.top() - pbr.top()) < abs(br.bottom() - pbr.bottom()):
+            anchorPos[1] = 0
+            parentPos[1] = pbr.top()
+            itemPos[1] = br.top()
+        else:
+            anchorPos[1] = 1
+            parentPos[1] = pbr.bottom()
+            itemPos[1] = br.bottom()
         
+        if relative:
+            relPos = [(itemPos[0]-pbr.left()) / pbr.width(), (itemPos[1]-pbr.top()) / pbr.height()]
+            self.anchor(anchorPos, relPos)
+        else:
+            offset = itemPos - parentPos
+            self.anchor(anchorPos, anchorPos, offset)
+    
     def __geometryChanged(self):
         if self.__parent is None:
             return
diff --git a/pyqtgraph/graphicsItems/LegendItem.py b/pyqtgraph/graphicsItems/LegendItem.py
index a2fc0e04..6c42fb4c 100644
--- a/pyqtgraph/graphicsItems/LegendItem.py
+++ b/pyqtgraph/graphicsItems/LegendItem.py
@@ -101,7 +101,6 @@ class LegendItem(GraphicsWidget, GraphicsWidgetAnchor):
                 label.close()
                 self.updateSize()                       # redraq box
 
-        
     def updateSize(self):
         if self.size is not None:
             return
@@ -115,15 +114,22 @@ class LegendItem(GraphicsWidget, GraphicsWidgetAnchor):
             #print(width, height)
         #print width, height
         self.setGeometry(0, 0, width+25, height)
-        
+    
     def boundingRect(self):
         return QtCore.QRectF(0, 0, self.width(), self.height())
-        
+    
     def paint(self, p, *args):
         p.setPen(fn.mkPen(255,255,255,100))
         p.setBrush(fn.mkBrush(100,100,100,50))
         p.drawRect(self.boundingRect())
+
+    def hoverEvent(self, ev):
+        ev.acceptDrags(QtCore.Qt.LeftButton)
         
+    def mouseDragEvent(self, ev):
+        if ev.button() == QtCore.Qt.LeftButton:
+            dpos = ev.pos() - ev.lastPos()
+            self.autoAnchor(self.pos() + dpos)
         
 class ItemSample(GraphicsWidget):
     def __init__(self, item):
-- 
GitLab