13#include "core/Utils_p.h"
14#include "core/View_p.h"
15#include "ViewWrapper_p.h"
16#include "core/layouting/Item_p.h"
17#include "core/ScopedValueRollback_p.h"
18#include "qtquick/Window_p.h"
22#include <QtQuick/private/qquickitem_p.h>
23#include <qpa/qplatformwindow.h>
24#include <QtGui/private/qhighdpiscaling_p.h>
25#include <QGuiApplication>
39class MouseEventRedirector :
public QObject
43 explicit MouseEventRedirector(QQuickItem *eventSource,
View *eventTarget)
45 , m_eventSource(eventSource)
46 , m_eventTarget(eventTarget)
51 auto oldRedirector = s_mouseEventRedirectors.take(eventSource);
53 eventSource->removeEventFilter(oldRedirector);
54 oldRedirector->deleteLater();
57 s_mouseEventRedirectors.insert(eventSource,
this);
60 static MouseEventRedirector *redirectorForSource(
QObject *eventSource)
62 return s_mouseEventRedirectors.value(eventSource);
65 ~MouseEventRedirector()
override;
71 m_eventTarget->onHoverEvent(
72 hev, m_eventSource->mapToGlobal(Qt5Qt6Compat::eventPos(hev)).toPoint());
87 m_eventTarget->setProperty(
"cursorPosition", m_eventSource->property(
"cursorPosition"));
89 qGuiApp->sendEvent(m_eventTarget, me);
101 QQuickItem *
const m_eventSource;
108MouseEventRedirector::~MouseEventRedirector()
110 s_mouseEventRedirectors.
remove(m_eventSource);
130 , View_qt(controller, type, this)
131 , m_windowFlags(flags)
139 connect(
this, &QQuickItem::widthChanged,
this, [
this] {
146 connect(
this, &QQuickItem::heightChanged,
this, [
this] {
153 qGuiApp->installEventFilter(
this);
154 _setSize({ 800, 800 });
165 QQmlComponent component(engine, filename);
166 QObject *obj = component.create(context);
168 qWarning() << Q_FUNC_INFO << component.errorString();
172 return qobject_cast<QQuickItem *>(obj);
177 if (
auto existingRedirector = MouseEventRedirector::redirectorForSource(source)) {
178 if (existingRedirector->m_eventTarget ==
this) {
187void View::sendVisibleChangeEvent()
202void View::itemChange(QQuickItem::ItemChange change,
const QQuickItem::ItemChangeData &data)
204 QQuickItem::itemChange(change, data);
207 if (change == QQuickItem::ItemVisibleHasChanged)
208 sendVisibleChangeEvent();
211void View::updateNormalGeometry()
219 if (
const QPlatformWindow *pw =
window->handle()) {
220 normalGeometry = QHighDpi::fromNativePixels(pw->normalGeometry(), pw->window());
235 if (
QWindow *w = QQuickItem::window()) {
236 w->setPosition(
x,
y);
251 return QQuickItem::event(ev);
256 if (qobject_cast<QWindow *>(watched)) {
257 if (m_mouseTrackingEnabled) {
258 switch (ev->
type()) {
263 qGuiApp->sendEvent(
this, ev);
274 updateNormalGeometry();
280 return QQuickItem::eventFilter(watched, ev);
285 if (
auto viewqtquick = qobject_cast<View *>(item)) {
287 viewqtquick->Core::View::d->closeRequested.emit(&ev);
290 viewqtquick->setVisible(
false);
306 QQuickItem::QQUICKITEMgeometryChanged(newGeometry, oldGeometry);
310 if (newGeometry.
size() != oldGeometry.
size()) {
312 qGuiApp->sendEvent(
this, &ev);
317 qGuiApp->sendEvent(
this, &ev);
325 if (
QWindow *w = QQuickItem::window()) {
335 auto priv = QQuickItemPrivate::get(
this);
336 return priv->explicitVisible;
342 if (
QWindow *w = QQuickItem::window()) {
343 if (
is && !w->isVisible()) {
345 }
else if (!
is && w->isVisible()) {
351 QQuickItem::setVisible(
is);
353#if QT_VERSION >= QT_VERSION_CHECK(6, 5, 0)
355 if (
is && !parentItem() && !QQuickItem::isVisible()) {
356 sendVisibleChangeEvent();
363 auto priv = QQuickItemPrivate::get(
this);
364 return !priv->explicitVisible;
373void View::_setSize(
QSize newSize)
380 if (
window->size() != newSize) {
383 window->setGeometry(windowGeo);
388 QQuickItem::setSize(newSize);
394 return window->rootView();
396 auto thisNonConst =
const_cast<View *
>(
this);
403 qWarning() << Q_FUNC_INFO <<
"Invalid item";
407 QQuickItem *parentItem = item->parentItem();
409 qWarning() << Q_FUNC_INFO <<
"Invalid parentItem for" << item;
415 qWarning() << Q_FUNC_INFO <<
"Invalid anchors for" << item;
425 m_widgetAttributes |= attr;
427 m_widgetAttributes &= ~attr;
432 return m_widgetAttributes & attr;
446 return m_windowFlags;
451 const QSize min = property(
"kddockwidgets_min_size").toSize();
452 return min.
expandedTo(Core::Item::hardcodedMinimumSize);
457 const QSize max = property(
"kddockwidgets_max_size").toSize();
458 return max.
isEmpty() ? Core::Item::hardcodedMaximumSize
459 : max.
boundedTo(Core::Item::hardcodedMaximumSize);
465 if (
QWindow *w = QQuickItem::window()) {
466 return w->geometry();
470 return QRect(
QPointF(QQuickItem::x(), QQuickItem::y()).toPoint(), QQuickItem::size().toSize());
475 return m_normalGeometry;
480 m_normalGeometry = geo;
486 setProperty(
"kddockwidgets_max_size", sz);
494 QQuickItem::setWidth(w);
499 QQuickItem::setHeight(h);
535 ScopedValueRollback guard(m_inSetParent,
true);
536 QQuickItem::setParent(parentItem);
537 QQuickItem::setParentItem(parentItem);
554 if (
QWindow *w = item->window()) {
556 w->requestActivate();
567 if (
QWindow *w = QQuickItem::window())
568 w->requestActivate();
574 if (
QWindow *w = QQuickItem::window())
576 }
else if (
auto p = QQuickItem::parentItem()) {
578 const auto siblings = p->childItems();
579 QQuickItem *last = siblings.last();
587 QQuickItem *parent = item->parentItem();
591 if (
auto *w = qobject_cast<QQuickWindow *>(item->window())) {
592 if (parent == w->contentItem() || item == w->contentItem())
594 if (
auto *qv = qobject_cast<QQuickView *>(item->window())) {
595 if (parent == qv->rootObject() || item == qv->rootObject())
610 return qobject_cast<QQuickView *>(QQuickItem::window());
615 return QQuickItem::mapToGlobal(localPt).toPoint();
620 return QQuickItem::mapFromGlobal(globalPt).toPoint();
629 return parentItem->mapFromGlobal(QQuickItem::mapToGlobal(
pos)).toPoint();
634 if (
QWindow *w = QQuickItem::window())
640 if (
QWindow *w = QQuickItem::window())
646 if (
QWindow *w = QQuickItem::window())
652 if (
QWindow *w = QQuickItem::window())
653 return w->isActive();
660 if (
QWindow *w = QQuickItem::window())
666 if (
QWindow *w = QQuickItem::window())
672 if (
QWindow *w = QQuickItem::window())
678 if (
QWindow *w = QQuickItem::window())
686 if (
QWindow *w = QQuickItem::window())
694 if (
QWindow *w = QQuickItem::window()) {
695 auto windowqtquick =
new QtQuick::Window(w);
696 return std::shared_ptr<Core::Window>(windowqtquick);
704 auto child = QQuickItem::childAt(p.
x(), p.
y());
711 auto p = item->parentItem();
712 if (QQuickWindow *
window = item->window()) {
713 if (p ==
window->contentItem()) {
725 return ViewWrapper::create(item);
735 return ViewWrapper::create(
this);
740 QQuickItem::grabMouse();
745 QQuickItem::ungrabMouse();
755 QQuickItem::setFocus(
true, reason);
756 forceActiveFocus(reason);
761 return QQuickItem::hasActiveFocus();
766 return m_focusPolicy;
771 m_focusPolicy = policy;
776 return QQuickItem::objectName();
782 setProperty(
"kddockwidgets_min_size", sz);
790 if (QQuickWindow *w = QQuickItem::window()) {
791 const QImage image = w->grabWindow();
793 const QPoint pos = mapToScene({ 0, 0 }).toPoint();
801 QQuickItem::setCursor(shape);
806 m_mouseTrackingEnabled = enable;
812 const auto childItems = QQuickItem::childItems();
813 result.
reserve(childItems.size());
814 for (QQuickItem *child : childItems) {
824 m_oldWindowState =
window->windowState();
833 if (filename.
startsWith(QStringLiteral(
"qrc:/")))
834 return filename.
right(filename.
size() - 3);
843 QQmlEngine *engine =
nullptr;
844 while (p && !engine) {
845 engine = qmlEngine(p);
853 qWarning() << Q_FUNC_INFO <<
"No engine found";
858 qWarning() << Q_FUNC_INFO <<
"File not found" << filename;
862 QQmlComponent component(engine, filename);
863 auto qquickitem = qobject_cast<QQuickItem *>(component.create(ctx));
865 qWarning() << Q_FUNC_INFO << component.errorString();
869 qquickitem->setParentItem(parent);
870 qquickitem->QObject::setParent(parent);
882 qWarning() << Q_FUNC_INFO
883 <<
"Base class called, please implement in your derived class if needed";
890 if (
auto ctx = qmlContext(item))
892 item = item->parentItem();
bool isAccepted() const const
QEvent::Type type() const const
bool exists() const const
int remove(const Key &key)
qreal devicePixelRatio() const const
void installEventFilter(QObject *filterObj)
QVariant property(const char *name) const const
void setParent(QObject *parent)
bool setProperty(const char *name, const QVariant &value)
void drawImage(const QRectF &target, const QImage &image, const QRectF &source, Qt::ImageConversionFlags flags)
QRect window() const const
bool isValid() const const
void setSize(const QSize &size)
QSizeF size() const const
QPointF topLeft() const const
QSize boundedTo(const QSize &otherSize) const const
QSize expandedTo(const QSize &otherSize) const const
bool isEmpty() const const
QString right(int n) const const
bool startsWith(const QString &s, Qt::CaseSensitivity cs) const const
static bool flagsAreTopLevelFlags(Qt::WindowFlags flags)
static QQuickItem * actualParentItem(QQuickItem *candidateParentItem, Qt::WindowFlags flags)
QVariant fromValue(const T &value)
bool isValid() const const
bool toBool() const const