Avoid burning cpu in qwindow-compositor with glx and nvidia
[profile/ivi/qtwayland.git] / src / compositor / compositor_api / waylandsurfacenode.cpp
1 #include "waylandsurfacenode.h"
2 #include "waylandsurfaceitem.h"
3
4 #include <QtCore/QMutexLocker>
5 #include <QtQuick/QSGTexture>
6 #include <QtQuick/QSGSimpleTextureNode>
7 #include <QtQuick/QSGFlatColorMaterial>
8
9 WaylandSurfaceNode::WaylandSurfaceNode(WaylandSurfaceItem *item)
10     : m_item(item)
11     , m_textureUpdated(false)
12     , m_useTextureAlpha(false)
13     , m_geometry(QSGGeometry::defaultAttributes_TexturedPoint2D(), 4)
14 {
15     m_textureMaterial = WaylandSurfaceTextureMaterial::createMaterial();
16     m_opaqueTextureMaterial = WaylandSurfaceTextureOpaqueMaterial::createMaterial();
17
18     m_currentMaterial = m_opaqueTextureMaterial;
19
20     setGeometry(&m_geometry);
21     setMaterial(m_currentMaterial);
22
23     if (m_item)
24         m_item->m_node = this;
25     setFlag(UsePreprocess,true);
26 }
27
28
29 WaylandSurfaceNode::~WaylandSurfaceNode()
30 {
31     QMutexLocker locker(WaylandSurfaceItem::mutex);
32     if (m_item)
33         m_item->m_node = 0;
34     delete m_textureMaterial;
35     delete m_opaqueTextureMaterial;
36 }
37
38 void WaylandSurfaceNode::preprocess()
39 {
40     QMutexLocker locker(WaylandSurfaceItem::mutex);
41
42     //Update if the item is dirty and we haven't done an updateTexture for this frame
43     if (m_item && m_item->m_damaged && !m_textureUpdated) {
44         m_item->updateTexture();
45         updateTexture();
46     }
47     //Reset value for next frame: we have not done updatePaintNode yet
48     m_textureUpdated = false;
49 }
50
51 void WaylandSurfaceNode::updateTexture()
52 {
53     Q_ASSERT(m_item && m_item->textureProvider());
54
55     //If m_item->useTextureAlpha has changed to true use m_texureMaterial
56     //otherwise use m_opaqueTextureMaterial.
57     if (m_item->useTextureAlpha() != m_useTextureAlpha) {
58         m_useTextureAlpha = m_item->useTextureAlpha();
59         if (m_useTextureAlpha) {
60             m_currentMaterial = m_textureMaterial;
61         } else {
62             m_currentMaterial = m_opaqueTextureMaterial;
63         }
64         setMaterial(m_currentMaterial);
65     }
66
67     QSGTexture *texture = m_item->textureProvider()->texture();
68     setTexture(texture);
69 }
70
71 void WaylandSurfaceNode::setRect(const QRectF &rect)
72 {
73     if (m_rect == rect)
74         return;
75     m_rect = rect;
76
77     if (texture()) {
78         QSize ts = texture()->textureSize();
79         QRectF sourceRect(0, 0, ts.width(), ts.height());
80         QSGGeometry::updateTexturedRectGeometry(&m_geometry, m_rect, texture()->convertToNormalizedSourceRect(sourceRect));
81     }
82 }
83
84 void WaylandSurfaceNode::setTexture(QSGTexture *texture)
85 {
86     if (m_currentMaterial->state()->texture() == texture)
87         return;
88     m_currentMaterial->state()->setTexture(texture);
89
90     QSize ts = texture->textureSize();
91     QRectF sourceRect(0, 0, ts.width(), ts.height());
92     QSGGeometry::updateTexturedRectGeometry(&m_geometry, m_rect, texture->convertToNormalizedSourceRect(sourceRect));
93     markDirty(DirtyMaterial);
94 }
95
96 QSGTexture *WaylandSurfaceNode::texture() const
97 {
98     return m_currentMaterial->state()->texture();
99 }
100
101 void WaylandSurfaceNode::setItem(WaylandSurfaceItem *item)
102 {
103     m_item = item;
104 }