Fixed docking of floating widgets for MacOS

This commit is contained in:
Uwe Kindler 2020-06-09 20:29:19 +02:00
parent 788c357cc0
commit fdf169ce9a
2 changed files with 108 additions and 0 deletions

View File

@ -978,6 +978,109 @@ void CFloatingDockContainer::finishDragging()
d->titleMouseReleaseEvent();
}
#ifdef Q_OS_MACOS
//============================================================================
bool CFloatingDockContainer::event(QEvent *e)
{
switch (d->DraggingState)
{
case DraggingInactive:
{
// Normally we would check here, if the left mouse button is pressed.
// But from QT version 5.12.2 on the mouse events from
// QEvent::NonClientAreaMouseButtonPress return the wrong mouse button
// The event always returns Qt::RightButton even if the left button
// is clicked.
// It is really great to work around the whole NonClientMouseArea
// bugs
#if (QT_VERSION >= QT_VERSION_CHECK(5, 12, 2))
if (e->type() == QEvent::NonClientAreaMouseButtonPress /*&& QGuiApplication::mouseButtons().testFlag(Qt::LeftButton)*/)
#else
if (e->type() == QEvent::NonClientAreaMouseButtonPress && QGuiApplication::mouseButtons().testFlag(Qt::LeftButton))
#endif
{
ADS_PRINT("FloatingWidget::event Event::NonClientAreaMouseButtonPress" << e->type());
d->DragStartPos = pos();
d->setState(DraggingMousePressed);
}
}
break;
case DraggingMousePressed:
switch (e->type())
{
case QEvent::NonClientAreaMouseButtonDblClick:
ADS_PRINT("FloatingWidget::event QEvent::NonClientAreaMouseButtonDblClick");
d->setState(DraggingInactive);
break;
case QEvent::Resize:
// If the first event after the mouse press is a resize event, then
// the user resizes the window instead of dragging it around.
// But there is one exception. If the window is maximized,
// then dragging the window via title bar will cause the widget to
// leave the maximized state. This in turn will trigger a resize event.
// To know, if the resize event was triggered by user via moving a
// corner of the window frame or if it was caused by a windows state
// change, we check, if we are not in maximized state.
if (!isMaximized())
{
d->setState(DraggingInactive);
}
break;
default:
break;
}
break;
case DraggingFloatingWidget:
if (e->type() == QEvent::NonClientAreaMouseButtonRelease)
{
ADS_PRINT("FloatingWidget::event QEvent::NonClientAreaMouseButtonRelease");
d->titleMouseReleaseEvent();
}
break;
default:
break;
}
#if (ADS_DEBUG_LEVEL > 0)
qDebug() << QTime::currentTime() << "CFloatingDockContainer::event " << e->type();
#endif
return QWidget::event(e);
}
//============================================================================
void CFloatingDockContainer::moveEvent(QMoveEvent *event)
{
QWidget::moveEvent(event);
switch (d->DraggingState)
{
case DraggingMousePressed:
d->setState(DraggingFloatingWidget);
d->updateDropOverlays(QCursor::pos());
break;
case DraggingFloatingWidget:
d->updateDropOverlays(QCursor::pos());
// In OSX when hiding the DockAreaOverlay the application would set
// the main window as the active window for some reason. This fixes
// that by resetting the active window to the floating widget after
// updating the overlays.
QApplication::setActiveWindow(this);
break;
default:
break;
}
}
#endif
} // namespace ads
//---------------------------------------------------------------------------

View File

@ -181,6 +181,11 @@ protected: // reimplements QWidget
virtual void hideEvent(QHideEvent *event) override;
virtual void showEvent(QShowEvent *event) override;
#ifdef Q_OS_MACOS
virtual bool event(QEvent *e) override;
virtual void moveEvent(QMoveEvent *event) override;
#endif
#ifdef Q_OS_WIN
/**
* Native event filter for handling WM_MOVING messages on Windows