2010-12-15 81 views
30

我有一個包含多個子項的QWidget。最終目標是能夠從一個小部件拖放到另一個小部件,並在小部件之間移動。我有一個信號被觸發到我的父控件的控制器,並可以確定何時拖動正確開始和結束。我目前的問題是確定鼠標是否在鼠標上方的目標部件上方。Qt - 確定絕對小部件和光標位置

當我在文檔中看到underMouse時,我很興奮,但它在拖放事件過程中不起作用(當我測試時,它似乎返回不正確的值)。如果失敗了,我的目標是找到包含目標小部件的矩形,並查找它是否包含鼠標上的鼠標座標。我不能簡單地使用contentsRect,因爲它返回相對於它被調用的窗口小部件的位置。我認爲mapToGlobal會給我絕對的屏幕像素值,但它仍然失敗。我試圖在父窗口小部件的窗口上調用mapTo,但是這似乎也失敗了。

下面是顯示我用各種方法得到的各種QRects和QPoints的代碼。也許有一個簡單的錯誤,所以我已經提供了所有這些。

QRect relativeWidgetRect = targetWidget->contentsRect(); 
QRect *absoluteWidgetRect = new QRect(QWidget::mapToGlobal(relativeWidgetRect.topLeft()), QWidget::mapToGlobal(relativeWidgetRect.bottomRight())); 
QRect *widgetRect = new QRect(mapTo(window(), relativeWidgetRect.topLeft()), mapTo(window(), relativeWidgetRect.bottomRight())); 
QPoint relativeMousePos = QCursor::pos(); 
QPoint absoluteMousePos = QWidget::mapToGlobal(relativeMousePos); 
QPoint widgetMousePos = mapTo(window(), relativeMousePos); 

mapToParent不會爲我的目的工作,因爲目標小部件實際上是由頂級父母的孩子父。

更新這是最終解決問題的代碼。在我的頂級窗口部件(這是祖先的源和目標部件都),我添加了這個:

QRect widgetRect = targetWidget->Geometry(); 
QPoint mousePos = targetWidget->mapFromGlobal(QCursor::pos()); 
if(widgetRect.contains(mousePos)) 
{ 
// Logic 
} 

回答

32

如上所述,在這種特殊情況下,您應該使用targetWidget->geometry()而不是contentsRect()

接下來我想知道您發佈的代碼屬於哪個類別。應該從您的座標相對於的QWidget調用方法QWidget::mapToGlobal()。如果我給你的權利,它看起來應該是這樣的:

QRect widgetRect = targetWidget->geometry(); 
widgetRect.moveTopLeft(targetWidget->parentWidget()->mapToGlobal(widgetRect.topLeft())); 

然後注意QCursor::pos()已經返回全局的屏幕座標,因此沒有必要映射任何東西在這裏:

if (widgetRect.contains(QCursor::pos())) { 
    /* swap widgets */ 
}

編輯:也許這是甚至最好不要映射RECT全球,但全球光標位置到窗口小部件圖:如果鼠標位置在widge內

if (targetWidget->rect().contains(targetWidget->mapFromGlobal(QCursor::pos()))) { 
    /* do stuff */ 
}
+1

啊哈,謝謝!我用最終解決了我的問題的代碼更新了我的問題。 – 2010-12-15 19:26:40

2

也許你正在尋找的QWidget geometry()frameGeometry()。有關更多詳細信息,請參閱here

0

這PyQt的方法將返回true T的矩形 - 包括案件如鼠標是通過組合視圖小部件

def underMouse(self): 
    pos = QtGui.QCursor.pos() 
    rect = self.rect() 
    leftTop  = self.mapToGlobal(QtCore.QPoint(rect.left(),rect.top())) 
    rightBottom = self.mapToGlobal(QtCore.QPoint(rect.right(),rect.bottom())) 
    globalRect = QtCore.QRect(leftTop.x(), leftTop.y(), rightBottom.x(), rightBottom.y()) 
    return globalRect.contains(self.mapToGlobal(pos))