diff --git a/examples/qml-compositor/main.cpp b/examples/qml-compositor/main.cpp index 530fee8bf227f26307d6768960c4c60fc99f2adc..8a016f3960e4f36e45b56ff31676231480ef9bf8 100644 --- a/examples/qml-compositor/main.cpp +++ b/examples/qml-compositor/main.cpp @@ -101,6 +101,11 @@ private slots: } protected: + void resizeEvent(QResizeEvent *) + { + WaylandCompositor::setOutputGeometry(QRect(0, 0, width(), height())); + } + void surfaceCreated(WaylandSurface *surface) { WaylandSurfaceItem *item = new WaylandSurfaceItem(surface, rootObject()); item->setTouchEventsEnabled(true); diff --git a/examples/qml-compositor/qml/QmlCompositor/WindowContainer.qml b/examples/qml-compositor/qml/QmlCompositor/WindowContainer.qml index ed1dad54f40d79198bf49ce16b99db0f6ea40b91..ae70e3b87213a4f028a9eee6b08bc664a8392644 100644 --- a/examples/qml-compositor/qml/QmlCompositor/WindowContainer.qml +++ b/examples/qml-compositor/qml/QmlCompositor/WindowContainer.qml @@ -86,7 +86,10 @@ Item { } } - transform: Scale { id: scaleTransform; origin.x: container.width / 2; origin.y: container.height / 2; xScale: 1; yScale: 1 } + transform: [ + Rotation { origin.x: container.width / 2; origin.y: container.height / 2; angle: (child && child.surface ? child.surface.windowRotation : 0) }, + Scale { id: scaleTransform; origin.x: container.width / 2; origin.y: container.height / 2; xScale: 1; yScale: 1 } + ] SequentialAnimation { id: destroyAnimation diff --git a/src/compositor/compositor_api/waylandcompositor.cpp b/src/compositor/compositor_api/waylandcompositor.cpp index b1388cbee22804d9d5111abc48db88aba3410188..9196a574188ad21a9c887fe76c559016b9c7a7c9 100644 --- a/src/compositor/compositor_api/waylandcompositor.cpp +++ b/src/compositor/compositor_api/waylandcompositor.cpp @@ -157,6 +157,11 @@ void WaylandCompositor::setOutputGeometry(const QRect &geometry) m_compositor->setOutputGeometry(geometry); } +QRect WaylandCompositor::outputGeometry() const +{ + return m_compositor->outputGeometry(); +} + WaylandInputDevice *WaylandCompositor::defaultInputDevice() const { return m_compositor->defaultInputDevice()->handle(); diff --git a/src/compositor/compositor_api/waylandcompositor.h b/src/compositor/compositor_api/waylandcompositor.h index 3cc255a8bd9760d5a012b6377038e53682c8ffc8..220726590d7b1c5548a77fbd25bf3e2be2862bc7 100644 --- a/src/compositor/compositor_api/waylandcompositor.h +++ b/src/compositor/compositor_api/waylandcompositor.h @@ -82,7 +82,9 @@ public: const char *socketName() const; void setScreenOrientation(Qt::ScreenOrientation orientation); + void setOutputGeometry(const QRect &outputGeometry); + QRect outputGeometry() const; WaylandInputDevice *defaultInputDevice() const; diff --git a/src/compositor/compositor_api/waylandsurface.cpp b/src/compositor/compositor_api/waylandsurface.cpp index e9be748cddc50e40baa83ef0d6520fcef63a3f0b..7effff050eb6cccdfea8376a670328a33096a158 100644 --- a/src/compositor/compositor_api/waylandsurface.cpp +++ b/src/compositor/compositor_api/waylandsurface.cpp @@ -47,8 +47,12 @@ #include "wayland_wrapper/wlsubsurface.h" #include "wayland_wrapper/wlcompositor.h" +#include "waylandcompositor.h" #include "waylandwindowmanagerintegration.h" +#include <QtGui/QGuiApplication> +#include <QtGui/QScreen> + #ifdef QT_COMPOSITOR_QUICK #include "waylandsurfaceitem.h" #endif @@ -80,7 +84,7 @@ public: WaylandSurface::WaylandSurface(Wayland::Surface *surface) : QObject(*new WaylandSurfacePrivate(surface)) { - + connect(this, SIGNAL(windowOrientationChanged()), this, SIGNAL(windowRotationChanged())); } WaylandSurface *WaylandSurface::parentSurface() const @@ -159,7 +163,23 @@ Qt::ScreenOrientation WaylandSurface::windowOrientation() const return d->surface->extendedSurface()->windowOrientation(); } +/*! + \property windowRotation + + Convenience property to get the rotation required to map the surface to the screen + based on its windowOrientation. + */ +int WaylandSurface::windowRotation() const +{ + QRect geometry = compositor()->outputGeometry(); + Qt::ScreenOrientation compositorOrientation = geometry.width() >= geometry.height() ? Qt::LandscapeOrientation : Qt::PortraitOrientation; + Qt::ScreenOrientation wOrientation = windowOrientation(); + if (wOrientation == Qt::PrimaryOrientation) + return 0; + + return QGuiApplication::primaryScreen()->angleBetween(wOrientation, compositorOrientation); +} WaylandSurface::WindowFlags WaylandSurface::windowFlags() const { diff --git a/src/compositor/compositor_api/waylandsurface.h b/src/compositor/compositor_api/waylandsurface.h index 8349066118b54e1db79c2ded60e547040c9e9c8c..40b87017e0d0e425e1a671a2b8eceffe800f1fea 100644 --- a/src/compositor/compositor_api/waylandsurface.h +++ b/src/compositor/compositor_api/waylandsurface.h @@ -73,6 +73,9 @@ class Q_COMPOSITOR_EXPORT WaylandSurface : public QObject Q_PROPERTY(QSize size READ size WRITE setSize NOTIFY sizeChanged) Q_PROPERTY(QPointF pos READ pos WRITE setPos NOTIFY posChanged) Q_PROPERTY(WaylandSurface::WindowFlags windowFlags READ windowFlags NOTIFY windowFlagsChanged) + Q_PROPERTY(Qt::ScreenOrientation windowOrientation READ windowOrientation NOTIFY windowOrientationChanged) + Q_PROPERTY(Qt::ScreenOrientation contentOrientation READ contentOrientation NOTIFY contentOrientationChanged) + Q_PROPERTY(int windowRotation READ windowRotation NOTIFY windowRotationChanged) Q_ENUMS(WindowFlag) Q_FLAGS(WindowFlag WindowFlags) @@ -107,6 +110,7 @@ public: Qt::ScreenOrientation contentOrientation() const; Qt::ScreenOrientation windowOrientation() const; + int windowRotation() const; WindowFlags windowFlags() const; @@ -147,6 +151,9 @@ signals: void posChanged(); void windowPropertyChanged(const QString &name, const QVariant &value); void windowFlagsChanged(WindowFlags flags); + void windowOrientationChanged(); + void contentOrientationChanged(); + void windowRotationChanged(); friend class Wayland::Surface; friend class Wayland::SurfacePrivate; diff --git a/src/compositor/compositor_api/waylandsurfaceitem.cpp b/src/compositor/compositor_api/waylandsurfaceitem.cpp index a080f836fadb59741d9753b971cfe9a44de34211..9418b4297251ff64f66f3e7fb25993751788dc06 100644 --- a/src/compositor/compositor_api/waylandsurfaceitem.cpp +++ b/src/compositor/compositor_api/waylandsurfaceitem.cpp @@ -47,6 +47,8 @@ #include "wlextendedsurface.h" #include <QtGui/QKeyEvent> +#include <QtGui/QGuiApplication> +#include <QtGui/QScreen> #include <QtQuick/QSGSimpleTextureNode> #include <QtQuick/QSGSimpleRectNode> @@ -130,7 +132,11 @@ WaylandSurfaceItem::~WaylandSurfaceItem() void WaylandSurfaceItem::setSurface(WaylandSurface *surface) { + if (surface == m_surface) + return; + init(surface); + emit surfaceChanged(); } bool WaylandSurfaceItem::isYInverted() const diff --git a/src/compositor/compositor_api/waylandsurfaceitem.h b/src/compositor/compositor_api/waylandsurfaceitem.h index 73697ae22811d9394d043186b51071b8b6c21a79..0114f127c6500a4568a004a8b85e1be77fab4b1c 100644 --- a/src/compositor/compositor_api/waylandsurfaceitem.h +++ b/src/compositor/compositor_api/waylandsurfaceitem.h @@ -56,7 +56,7 @@ Q_DECLARE_METATYPE(WaylandSurface*) class Q_COMPOSITOR_EXPORT WaylandSurfaceItem : public QQuickItem { Q_OBJECT - Q_PROPERTY(WaylandSurface* surface READ surface WRITE setSurface) + Q_PROPERTY(WaylandSurface* surface READ surface WRITE setSurface NOTIFY surfaceChanged) Q_PROPERTY(bool paintEnabled READ paintEnabled WRITE setPaintEnabled) Q_PROPERTY(bool useTextureAlpha READ useTextureAlpha WRITE setUseTextureAlpha NOTIFY useTextureAlphaChanged) Q_PROPERTY(bool clientRenderingEnabled READ clientRenderingEnabled WRITE setClientRenderingEnabled NOTIFY clientRenderingEnabledChanged) @@ -114,6 +114,7 @@ signals: void clientRenderingEnabledChanged(); void touchEventsEnabledChanged(); void yInvertedChanged(); + void surfaceChanged(); protected: QSGNode *updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *); diff --git a/src/compositor/wayland_wrapper/wlcompositor.cpp b/src/compositor/wayland_wrapper/wlcompositor.cpp index 545d14e3dba016f0ac353fe9ca810e3f35e1dc7a..27378f19fd3c2b9038804bd79dd5718397d8a98a 100644 --- a/src/compositor/wayland_wrapper/wlcompositor.cpp +++ b/src/compositor/wayland_wrapper/wlcompositor.cpp @@ -360,6 +360,11 @@ void Compositor::setOutputGeometry(const QRect &geometry) m_output_global.setGeometry(geometry); } +QRect Compositor::outputGeometry() const +{ + return m_output_global.geometry(); +} + InputDevice* Compositor::defaultInputDevice() { return m_default_input_device; diff --git a/src/compositor/wayland_wrapper/wlcompositor.h b/src/compositor/wayland_wrapper/wlcompositor.h index 03cd1db558c771549181e2ed445783f5731c4b5b..b2d4ef6e711d38640797699db87bb2f8f66f8de4 100644 --- a/src/compositor/wayland_wrapper/wlcompositor.h +++ b/src/compositor/wayland_wrapper/wlcompositor.h @@ -117,6 +117,7 @@ public: void setScreenOrientation(Qt::ScreenOrientation orientation); Qt::ScreenOrientation screenOrientation() const; void setOutputGeometry(const QRect &geometry); + QRect outputGeometry() const; void enableTouchExtension(); TouchExtensionGlobal *touchExtension() { return m_touchExtension; } diff --git a/src/compositor/wayland_wrapper/wlextendedsurface.cpp b/src/compositor/wayland_wrapper/wlextendedsurface.cpp index c5bde25801a8e07e8f1860044204cb330b227f54..e4dd6bf4510986e64c38c0c94ec7e4135fbee06f 100644 --- a/src/compositor/wayland_wrapper/wlextendedsurface.cpp +++ b/src/compositor/wayland_wrapper/wlextendedsurface.cpp @@ -154,7 +154,11 @@ void ExtendedSurface::set_window_orientation(struct wl_client *client, { Q_UNUSED(client); ExtendedSurface *extended_surface = static_cast<ExtendedSurface *>(extended_surface_resource->data); + + Qt::ScreenOrientation oldOrientation = extended_surface->m_windowOrientation; extended_surface->m_windowOrientation = screenOrientationFromWaylandOrientation(orientation); + if (extended_surface->m_windowOrientation != oldOrientation) + emit extended_surface->m_surface->waylandSurface()->windowOrientationChanged(); } void ExtendedSurface::set_content_orientation(struct wl_client *client, @@ -163,7 +167,11 @@ void ExtendedSurface::set_content_orientation(struct wl_client *client, { Q_UNUSED(client); ExtendedSurface *extended_surface = static_cast<ExtendedSurface *>(extended_surface_resource->data); + + Qt::ScreenOrientation oldOrientation = extended_surface->m_contentOrientation; extended_surface->m_contentOrientation = screenOrientationFromWaylandOrientation(orientation); + if (extended_surface->m_windowOrientation != oldOrientation) + emit extended_surface->m_surface->waylandSurface()->contentOrientationChanged(); } void ExtendedSurface::setWindowFlags(WaylandSurface::WindowFlags flags) diff --git a/src/compositor/wayland_wrapper/wloutput.h b/src/compositor/wayland_wrapper/wloutput.h index f678547a254702d4be6af9b4d4ea21bc753c71d2..b637d2d3f15cb27294573ec9df0407852ba12997 100644 --- a/src/compositor/wayland_wrapper/wloutput.h +++ b/src/compositor/wayland_wrapper/wloutput.h @@ -57,6 +57,7 @@ public: OutputGlobal(); void setGeometry(const QRect &geometry); + QRect geometry() const { return m_geometry; } int x() const { return m_geometry.x(); } int y() const { return m_geometry.y(); }