Qt
Internal/Contributor docs for the Qt SDK. <b>Note:</b> These are NOT official API docs; those are found <a href='https://doc.qt.io/'>here</a>.
Loading...
Searching...
No Matches
qeglfscursor.cpp
Go to the documentation of this file.
1// Copyright (C) 2016 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4#include "qeglfscursor_p.h"
6#include "qeglfsscreen_p.h"
7#include "qeglfscontext_p.h"
8
9#include <qpa/qwindowsysteminterface.h>
10#include <QtGui/QOpenGLContext>
11#include <QtGui/QOpenGLFunctions>
12#include <QtCore/QFile>
13#include <QtCore/QJsonDocument>
14#include <QtCore/QJsonArray>
15#include <QtCore/QJsonObject>
16
17#include <QtGui/private/qguiapplication_p.h>
18#include <QtOpenGL/private/qopenglvertexarrayobject_p.h>
19
20#ifndef GL_VERTEX_ARRAY_BINDING
21#define GL_VERTEX_ARRAY_BINDING 0x85B5
22#endif
23
25
26using namespace Qt::StringLiterals;
27
28QEglFSCursor::QEglFSCursor(QPlatformScreen *screen)
29 : m_visible(true),
30 m_screen(static_cast<QEglFSScreen *>(screen)),
31 m_activeScreen(nullptr),
32 m_deviceListener(nullptr),
33 m_updateRequested(false)
34{
35 QByteArray hideCursorVal = qgetenv("QT_QPA_EGLFS_HIDECURSOR");
36 if (!hideCursorVal.isEmpty())
37 m_visible = hideCursorVal.toInt() == 0;
38 if (!m_visible)
39 return;
40
41 int rotation = qEnvironmentVariableIntValue("QT_QPA_EGLFS_ROTATION");
42 if (rotation)
43 m_rotationMatrix.rotate(rotation, 0, 0, 1);
44
45 // Try to load the cursor atlas. If this fails, m_visible is set to false and
46 // paintOnScreen() and setCurrentCursor() become no-ops.
47 initCursorAtlas();
48
49 // initialize the cursor
50#ifndef QT_NO_CURSOR
52 setCurrentCursor(&cursor);
53#endif
54
55 m_deviceListener = new QEglFSCursorDeviceListener(this);
58 updateMouseStatus();
59}
60
61QEglFSCursor::~QEglFSCursor()
62{
63 resetResources();
64 delete m_deviceListener;
65}
66
67void QEglFSCursor::updateMouseStatus()
68{
69 m_visible = m_deviceListener->hasMouse();
70}
71
76
82
83void QEglFSCursor::resetResources()
84{
85 m_cursor.customCursorPending = !m_cursor.customCursorImage.isNull();
86}
87
88void QEglFSCursor::createShaderPrograms()
89{
90 static const char *textureVertexProgram =
91 "attribute highp vec2 vertexCoordEntry;\n"
92 "attribute highp vec2 textureCoordEntry;\n"
93 "varying highp vec2 textureCoord;\n"
94 "uniform highp mat4 mat;\n"
95 "void main() {\n"
96 " textureCoord = textureCoordEntry;\n"
97 " gl_Position = mat * vec4(vertexCoordEntry, 1.0, 1.0);\n"
98 "}\n";
99
100 static const char *textureFragmentProgram =
101 "uniform sampler2D texture;\n"
102 "varying highp vec2 textureCoord;\n"
103 "void main() {\n"
104 " gl_FragColor = texture2D(texture, textureCoord).bgra;\n"
105 "}\n";
106
107 QEglFSCursorData &gfx = static_cast<QEglFSContext*>(QOpenGLContext::currentContext()->handle())->cursorData;
108 gfx.program.reset(new QOpenGLShaderProgram);
109 gfx.program->addCacheableShaderFromSourceCode(QOpenGLShader::Vertex, textureVertexProgram);
110 gfx.program->addCacheableShaderFromSourceCode(QOpenGLShader::Fragment, textureFragmentProgram);
111 gfx.program->bindAttributeLocation("vertexCoordEntry", 0);
112 gfx.program->bindAttributeLocation("textureCoordEntry", 1);
113 gfx.program->link();
114
115 gfx.textureEntry = gfx.program->uniformLocation("texture");
116 gfx.matEntry = gfx.program->uniformLocation("mat");
117}
118
119void QEglFSCursor::createCursorTexture(uint *texture, const QImage &image)
120{
123 if (!*texture)
124 f->glGenTextures(1, texture);
125 f->glBindTexture(GL_TEXTURE_2D, *texture);
126 f->glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
127 f->glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
128 f->glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
129 f->glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
130
131 f->glTexImage2D(GL_TEXTURE_2D, 0 /* level */, GL_RGBA, image.width(), image.height(), 0 /* border */,
132 GL_RGBA, GL_UNSIGNED_BYTE, image.constBits());
133}
134
135void QEglFSCursor::initCursorAtlas()
136{
137 static QByteArray json = qgetenv("QT_QPA_EGLFS_CURSOR");
138 if (json.isEmpty())
139 json = ":/cursor.json";
140
142 if (!file.open(QFile::ReadOnly)) {
143 m_visible = false;
144 return;
145 }
146
148 QJsonObject object = doc.object();
149
150 QString atlas = object.value("image"_L1).toString();
151 Q_ASSERT(!atlas.isEmpty());
152
153 const int cursorsPerRow = object.value("cursorsPerRow"_L1).toDouble();
154 Q_ASSERT(cursorsPerRow);
155 m_cursorAtlas.cursorsPerRow = cursorsPerRow;
156
157 const QJsonArray hotSpots = object.value("hotSpots"_L1).toArray();
158 Q_ASSERT(hotSpots.count() == Qt::LastCursor + 1);
159 for (int i = 0; i < hotSpots.count(); i++) {
160 QPoint hotSpot(hotSpots[i].toArray()[0].toDouble(), hotSpots[i].toArray()[1].toDouble());
161 m_cursorAtlas.hotSpots << hotSpot;
162 }
163
165 m_cursorAtlas.cursorWidth = image.width() / m_cursorAtlas.cursorsPerRow;
166 m_cursorAtlas.cursorHeight = image.height() / ((Qt::LastCursor + cursorsPerRow) / cursorsPerRow);
167 m_cursorAtlas.width = image.width();
168 m_cursorAtlas.height = image.height();
169 m_cursorAtlas.image = image;
170}
171
172#ifndef QT_NO_CURSOR
173void QEglFSCursor::changeCursor(QCursor *cursor, QWindow *window)
174{
176 const QRect oldCursorRect = cursorRect();
177 if (setCurrentCursor(cursor))
178 update(oldCursorRect | cursorRect(), false);
179}
180
181bool QEglFSCursor::setCurrentCursor(QCursor *cursor)
182{
183 if (!m_visible)
184 return false;
185
186 const Qt::CursorShape newShape = cursor ? cursor->shape() : Qt::ArrowCursor;
187 if (m_cursor.shape == newShape && newShape != Qt::BitmapCursor)
188 return false;
189
190 if (m_cursor.shape == Qt::BitmapCursor) {
191 m_cursor.customCursorImage = QImage();
192 m_cursor.customCursorPending = false;
193 }
194 m_cursor.shape = newShape;
195 if (newShape != Qt::BitmapCursor) { // standard cursor
196 const float ws = (float)m_cursorAtlas.cursorWidth / m_cursorAtlas.width,
197 hs = (float)m_cursorAtlas.cursorHeight / m_cursorAtlas.height;
198 m_cursor.textureRect = QRectF(ws * (m_cursor.shape % m_cursorAtlas.cursorsPerRow),
199 hs * (m_cursor.shape / m_cursorAtlas.cursorsPerRow),
200 ws, hs);
201 m_cursor.hotSpot = m_cursorAtlas.hotSpots[m_cursor.shape];
202 m_cursor.useCustomCursor = false;
203 m_cursor.size = QSize(m_cursorAtlas.cursorWidth, m_cursorAtlas.cursorHeight);
204 } else {
206 m_cursor.textureRect = QRectF(0, 0, 1, 1);
207 m_cursor.hotSpot = cursor->hotSpot();
208 m_cursor.useCustomCursor = false; // will get updated in the next render()
209 m_cursor.size = image.size();
210 m_cursor.customCursorImage = image;
211 m_cursor.customCursorPending = true;
212 m_cursor.customCursorKey = m_cursor.customCursorImage.cacheKey();
213 }
214
215 return true;
216}
217#endif
218
220{
221public:
222 CursorUpdateEvent(const QPoint &pos, const QRect &rect, bool allScreens)
223 : QEvent(QEvent::Type(QEvent::User + 1)),
224 m_pos(pos),
225 m_rect(rect),
226 m_allScreens(allScreens)
227 { }
228 QPoint pos() const { return m_pos; }
229 QRegion rect() const { return m_rect; }
230 bool allScreens() const { return m_allScreens; }
231
232private:
233 QPoint m_pos;
234 QRect m_rect;
235 bool m_allScreens;
236};
237
238bool QEglFSCursor::event(QEvent *e)
239{
240 if (e->type() == QEvent::User + 1) {
241 CursorUpdateEvent *ev = static_cast<CursorUpdateEvent *>(e);
242 m_updateRequested = false;
243 if (!ev->allScreens()) {
244 QWindow *w = m_screen->topLevelAt(ev->pos()); // works for the entire virtual desktop, no need to loop
245 if (w) {
248 }
249 } else {
250 for (QWindow *w : qGuiApp->topLevelWindows())
251 QWindowSystemInterface::handleExposeEvent(w, w->geometry());
253 }
254 return true;
255 }
256 return QPlatformCursor::event(e);
257}
258
259void QEglFSCursor::update(const QRect &rect, bool allScreens)
260{
261 if (!m_updateRequested) {
262 // Must not flush the window system events directly from here since we are likely to
263 // be a called directly from QGuiApplication's processMouseEvents. Flushing events
264 // could cause reentering by dispatching more queued mouse events.
265 m_updateRequested = true;
266 QCoreApplication::postEvent(this, new CursorUpdateEvent(m_cursor.pos, rect, allScreens));
267 }
268}
269
270QRect QEglFSCursor::cursorRect() const
271{
272 return QRect(m_cursor.pos - m_cursor.hotSpot, m_cursor.size);
273}
274
275QPoint QEglFSCursor::pos() const
276{
277 return m_cursor.pos;
278}
279
280void QEglFSCursor::setPos(const QPoint &pos)
281{
283 const QRect oldCursorRect = cursorRect();
284 m_cursor.pos = pos;
285 update(oldCursorRect | cursorRect(), false);
286 for (QPlatformScreen *screen : m_screen->virtualSiblings())
287 static_cast<QEglFSScreen *>(screen)->handleCursorMove(m_cursor.pos);
288}
289
290void QEglFSCursor::pointerEvent(const QMouseEvent &event)
291{
292 if (event.type() != QEvent::MouseMove)
293 return;
294 const QRect oldCursorRect = cursorRect();
295 m_cursor.pos = event.globalPosition().toPoint();
296 update(oldCursorRect | cursorRect(), false);
297 for (QPlatformScreen *screen : m_screen->virtualSiblings())
298 static_cast<QEglFSScreen *>(screen)->handleCursorMove(m_cursor.pos);
299}
300
301void QEglFSCursor::paintOnScreen()
302{
303 if (!m_visible)
304 return;
305
306 // cr must be a QRectF, otherwise cr.right() and bottom() would be off by
307 // one in the calculations below.
308 QRectF cr = cursorRect(); // hotspot included
309
310 // Support virtual desktop too. Backends with multi-screen support (e.g. all
311 // variants of KMS/DRM) will enable this by default. In this case all
312 // screens are siblings of each other. When not enabled, the sibling list
313 // only contains m_screen itself.
314 for (QPlatformScreen *screen : m_screen->virtualSiblings()) {
315 if (screen->geometry().contains(cr.topLeft().toPoint() + m_cursor.hotSpot))
316 {
318 const QSize screenSize = screen->geometry().size();
319 const GLfloat x1 = 2 * (cr.left() / GLfloat(screenSize.width())) - 1;
320 const GLfloat x2 = 2 * (cr.right() / GLfloat(screenSize.width())) - 1;
321 const GLfloat y1 = 1 - (cr.top() / GLfloat(screenSize.height())) * 2;
322 const GLfloat y2 = 1 - (cr.bottom() / GLfloat(screenSize.height())) * 2;
324
325 draw(r);
326
327 if (screen != m_activeScreen) {
328 m_activeScreen = screen;
329 // Do not want a leftover cursor on the screen the cursor just left.
330 update(cursorRect(), true);
331 }
332
333 break;
334 }
335 }
336}
337
338// In order to prevent breaking code doing custom OpenGL rendering while
339// expecting the state in the context unchanged, save and restore all the state
340// we touch. The exception is Qt Quick where the scenegraph is known to be able
341// to deal with the changes we make.
343{
345 f = func;
347
348 static bool windowsChecked = false;
349 static bool shouldSave = true;
350 if (!windowsChecked) {
351 windowsChecked = true;
353 if (!windows.isEmpty() && windows[0]->inherits("QQuickWindow"))
354 shouldSave = false;
355 }
356 saved = shouldSave;
357 if (!shouldSave)
358 return;
359
360 f->glGetIntegerv(GL_CURRENT_PROGRAM, &program);
361 f->glGetIntegerv(GL_TEXTURE_BINDING_2D, &texture);
362 f->glGetIntegerv(GL_ACTIVE_TEXTURE, &activeTexture);
363 f->glGetIntegerv(GL_FRONT_FACE, &frontFace);
364 cull = f->glIsEnabled(GL_CULL_FACE);
365 depthTest = f->glIsEnabled(GL_DEPTH_TEST);
366 blend = f->glIsEnabled(GL_BLEND);
367 f->glGetIntegerv(GL_BLEND_SRC_RGB, blendFunc);
368 f->glGetIntegerv(GL_BLEND_SRC_ALPHA, blendFunc + 1);
369 f->glGetIntegerv(GL_BLEND_DST_RGB, blendFunc + 2);
370 f->glGetIntegerv(GL_BLEND_DST_ALPHA, blendFunc + 3);
371 scissor = f->glIsEnabled(GL_SCISSOR_TEST);
372 stencil = f->glIsEnabled(GL_STENCIL_TEST);
373 f->glGetIntegerv(GL_ARRAY_BUFFER_BINDING, &arrayBuf);
374 if (vaoHelper->isValid())
375 f->glGetIntegerv(GL_VERTEX_ARRAY_BINDING, &vao);
376 else
377 vao = 0;
378 for (int i = 0; i < 2; ++i) {
379 f->glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_ENABLED, &va[i].enabled);
380 f->glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_SIZE, &va[i].size);
381 f->glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_TYPE, &va[i].type);
382 f->glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_NORMALIZED, &va[i].normalized);
383 f->glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_STRIDE, &va[i].stride);
384 f->glGetVertexAttribiv(i, GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING, &va[i].buffer);
385 f->glGetVertexAttribPointerv(i, GL_VERTEX_ATTRIB_ARRAY_POINTER, &va[i].pointer);
386 }
387 }
389 if (saved) {
390 f->glUseProgram(program);
391 f->glBindTexture(GL_TEXTURE_2D, texture);
392 f->glActiveTexture(activeTexture);
393 f->glFrontFace(frontFace);
394 if (cull)
395 f->glEnable(GL_CULL_FACE);
396 if (depthTest)
397 f->glEnable(GL_DEPTH_TEST);
398 if (!blend)
399 f->glDisable(GL_BLEND);
400 f->glBlendFuncSeparate(blendFunc[0], blendFunc[1], blendFunc[2], blendFunc[3]);
401 if (scissor)
402 f->glEnable(GL_SCISSOR_TEST);
403 if (stencil)
404 f->glEnable(GL_STENCIL_TEST);
405 f->glBindBuffer(GL_ARRAY_BUFFER, arrayBuf);
406 if (vaoHelper->isValid())
407 vaoHelper->glBindVertexArray(vao);
408 for (int i = 0; i < 2; ++i) {
409 if (va[i].enabled)
410 f->glEnableVertexAttribArray(i);
411 else
412 f->glDisableVertexAttribArray(i);
413 f->glBindBuffer(GL_ARRAY_BUFFER, va[i].buffer);
414 f->glVertexAttribPointer(i, va[i].size, va[i].type, va[i].normalized, va[i].stride, va[i].pointer);
415 }
416 }
417 }
420 bool saved;
425 bool cull;
427 bool blend;
428 GLint blendFunc[4];
433 struct { GLint enabled, type, size, normalized, stride, buffer; GLvoid *pointer; } va[2];
434};
435
436void QEglFSCursor::draw(const QRectF &r)
437{
440 StateSaver stateSaver(f);
441
442 QEglFSCursorData &gfx = static_cast<QEglFSContext*>(QOpenGLContext::currentContext()->handle())->cursorData;
443 if (!gfx.program) {
444 createShaderPrograms();
445
446 if (!gfx.atlasTexture) {
447 createCursorTexture(&gfx.atlasTexture, m_cursorAtlas.image);
448
449 if (m_cursor.shape != Qt::BitmapCursor)
450 m_cursor.useCustomCursor = false;
451 }
452 }
453
454 if (m_cursor.shape == Qt::BitmapCursor && (m_cursor.customCursorPending || m_cursor.customCursorKey != gfx.customCursorKey)) {
455 // upload the custom cursor
456 createCursorTexture(&gfx.customCursorTexture, m_cursor.customCursorImage);
457 m_cursor.useCustomCursor = true;
458 m_cursor.customCursorPending = false;
459 gfx.customCursorKey = m_cursor.customCursorKey;
460 }
461
462 GLuint cursorTexture = !m_cursor.useCustomCursor ? gfx.atlasTexture : gfx.customCursorTexture;
463 Q_ASSERT(cursorTexture);
464
465 gfx.program->bind();
466
467 const GLfloat x1 = r.left();
468 const GLfloat x2 = r.right();
469 const GLfloat y1 = r.top();
470 const GLfloat y2 = r.bottom();
471 const GLfloat cursorCoordinates[] = {
472 x1, y2,
473 x2, y2,
474 x1, y1,
475 x2, y1
476 };
477
478 const GLfloat s1 = m_cursor.textureRect.left();
479 const GLfloat s2 = m_cursor.textureRect.right();
480 const GLfloat t1 = m_cursor.textureRect.top();
481 const GLfloat t2 = m_cursor.textureRect.bottom();
482 const GLfloat textureCoordinates[] = {
483 s1, t2,
484 s2, t2,
485 s1, t1,
486 s2, t1
487 };
488
489 f->glActiveTexture(GL_TEXTURE0);
490 f->glBindTexture(GL_TEXTURE_2D, cursorTexture);
491
492 if (stateSaver.vaoHelper->isValid())
493 stateSaver.vaoHelper->glBindVertexArray(0);
494
495 f->glBindBuffer(GL_ARRAY_BUFFER, 0);
496
497 gfx.program->enableAttributeArray(0);
498 gfx.program->enableAttributeArray(1);
499 gfx.program->setAttributeArray(0, cursorCoordinates, 2);
500 gfx.program->setAttributeArray(1, textureCoordinates, 2);
501
502 gfx.program->setUniformValue(gfx.textureEntry, 0);
503 gfx.program->setUniformValue(gfx.matEntry, m_rotationMatrix);
504
505 f->glDisable(GL_CULL_FACE);
506 f->glFrontFace(GL_CCW);
507 f->glEnable(GL_BLEND);
508 f->glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
509 f->glDisable(GL_DEPTH_TEST); // disable depth testing to make sure cursor is always on top
510 f->glDisable(GL_SCISSOR_TEST);
511 f->glDisable(GL_STENCIL_TEST);
512
513 f->glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
514
515 gfx.program->disableAttributeArray(0);
516 gfx.program->disableAttributeArray(1);
517 gfx.program->release();
518}
519
521
522#include "moc_qeglfscursor_p.cpp"
CursorUpdateEvent(const QPoint &pos, const QRect &rect, bool allScreens)
QPoint pos() const
QRegion rect() const
bool allScreens() const
\inmodule QtCore
Definition qbytearray.h:57
bool isEmpty() const noexcept
Returns true if the byte array has size 0; otherwise returns false.
Definition qbytearray.h:107
static void postEvent(QObject *receiver, QEvent *event, int priority=Qt::NormalEventPriority)
The QCursor class provides a mouse cursor with an arbitrary shape.
Definition qcursor.h:45
QPixmap pixmap() const
Returns the cursor pixmap.
Definition qcursor.cpp:584
Qt::CursorShape shape() const
Returns the cursor shape identifier.
Definition qcursor.cpp:498
QPoint hotSpot() const
Returns the cursor hot spot, or (0, 0) if it is one of the standard cursors.
Definition qcursor.cpp:595
void onDeviceListChanged(QInputDeviceManager::DeviceType type)
@ ExcludeUserInputEvents
Definition qeventloop.h:27
\inmodule QtCore
Definition qcoreevent.h:45
@ MouseMove
Definition qcoreevent.h:63
Type type() const
Returns the event type.
Definition qcoreevent.h:304
\inmodule QtCore
Definition qfile.h:93
QFILE_MAYBE_NODISCARD bool open(OpenMode flags) override
Opens the file using OpenMode mode, returning true if successful; otherwise false.
Definition qfile.cpp:904
static QInputDeviceManager * inputDeviceManager()
static QWindowList allWindows()
Returns a list of all the windows in the application.
QByteArray readAll()
Reads all remaining data from the device, and returns it as a byte array.
\inmodule QtGui
Definition qimage.h:37
@ Format_ARGB32_Premultiplied
Definition qimage.h:48
QImage convertToFormat(Format f, Qt::ImageConversionFlags flags=Qt::AutoColor) const &
Definition qimage.h:125
void deviceListChanged(QInputDeviceManager::DeviceType type)
\inmodule QtCore\reentrant
Definition qjsonarray.h:18
qsizetype count() const
Same as size().
Definition qjsonarray.h:42
\inmodule QtCore\reentrant
QJsonObject object() const
Returns the QJsonObject contained in the document.
static QJsonDocument fromJson(const QByteArray &json, QJsonParseError *error=nullptr)
Parses json as a UTF-8 encoded JSON document, and creates a QJsonDocument from it.
\inmodule QtCore\reentrant
Definition qjsonobject.h:20
bool isEmpty() const noexcept
Definition qlist.h:401
\inmodule QtGui
Definition qevent.h:196
virtual bool event(QEvent *event)
This virtual function receives events to an object and should return true if the event e was recogniz...
Definition qobject.cpp:1389
static QOpenGLContext * currentContext()
Returns the last context which called makeCurrent in the current thread, or \nullptr,...
The QOpenGLFunctions class provides cross-platform access to the OpenGL ES 2.0 API.
The QOpenGLShaderProgram class allows OpenGL shader programs to be linked and used.
static Q_OPENGL_EXPORT QOpenGLVertexArrayObjectHelper * vertexArrayObjectHelperForContext(QOpenGLContext *context)
QImage toImage() const
Converts the pixmap to a QImage.
Definition qpixmap.cpp:408
The QPlatformScreen class provides an abstraction for visual displays.
\inmodule QtCore\reentrant
Definition qpoint.h:217
\inmodule QtCore\reentrant
Definition qpoint.h:25
\inmodule QtCore\reentrant
Definition qrect.h:484
constexpr qreal bottom() const noexcept
Returns the y-coordinate of the rectangle's bottom edge.
Definition qrect.h:500
constexpr qreal left() const noexcept
Returns the x-coordinate of the rectangle's left edge.
Definition qrect.h:497
constexpr QPointF topLeft() const noexcept
Returns the position of the rectangle's top-left corner.
Definition qrect.h:511
constexpr void translate(qreal dx, qreal dy) noexcept
Moves the rectangle dx along the x-axis and dy along the y-axis, relative to the current position.
Definition qrect.h:738
constexpr qreal top() const noexcept
Returns the y-coordinate of the rectangle's top edge.
Definition qrect.h:498
constexpr qreal right() const noexcept
Returns the x-coordinate of the rectangle's right edge.
Definition qrect.h:499
\inmodule QtCore\reentrant
Definition qrect.h:30
constexpr QPoint topLeft() const noexcept
Returns the position of the rectangle's top-left corner.
Definition qrect.h:221
bool contains(const QRect &r, bool proper=false) const noexcept
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition qrect.cpp:855
constexpr QSize size() const noexcept
Returns the size of the rectangle.
Definition qrect.h:242
The QRegion class specifies a clip region for a painter.
Definition qregion.h:27
QRect geometry
the screen's geometry in pixels
Definition qscreen.h:45
\inmodule QtCore
Definition qsize.h:25
constexpr int height() const noexcept
Returns the height.
Definition qsize.h:133
constexpr int width() const noexcept
Returns the width.
Definition qsize.h:130
\macro QT_RESTRICTED_CAST_FROM_ASCII
Definition qstring.h:129
static QString fromUtf8(QByteArrayView utf8)
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition qstring.cpp:6018
The QWindowSystemInterface provides an event queue for the QPA platform.
static bool flushWindowSystemEvents(QEventLoop::ProcessEventsFlags flags=QEventLoop::AllEvents)
Make Qt Gui process all events on the event queue immediately.
static bool handleExposeEvent(QWindow *window, const QRegion &region)
\inmodule QtGui
Definition qwindow.h:63
QCursor cursor
rect
[4]
Combined button and popup list for selecting options.
CursorShape
@ BitmapCursor
@ LastCursor
@ ArrowCursor
QTextStream & ws(QTextStream &stream)
Calls \l {QTextStream::}{skipWhiteSpace()} on stream and returns stream.
Definition image.cpp:4
#define qGuiApp
@ User
typedef GLint(GL_APIENTRYP PFNGLGETPROGRAMRESOURCELOCATIONINDEXEXTPROC)(GLuint program
typedef GLfloat(GL_APIENTRYP PFNGLGETPATHLENGTHNVPROC)(GLuint path
GLfloat GLfloat GLfloat w
[0]
GLuint GLfloat GLfloat GLfloat GLfloat y1
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLboolean r
[2]
GLuint GLfloat GLfloat GLfloat x1
GLuint GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat s1
GLenum GLenum GLsizei const GLuint GLboolean enabled
GLfloat GLfloat f
GLuint GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat t1
[4]
const void GLsizei GLsizei stride
GLenum GLuint buffer
GLenum type
GLenum GLuint texture
GLuint program
struct _cl_event * event
#define GL_TEXTURE0
Definition qopenglext.h:129
GLenum func
Definition qopenglext.h:663
#define GL_BLEND_DST_ALPHA
Definition qopenglext.h:325
#define GL_VERTEX_ATTRIB_ARRAY_SIZE
Definition qopenglext.h:578
#define GL_CURRENT_PROGRAM
Definition qopenglext.h:649
#define GL_VERTEX_ATTRIB_ARRAY_NORMALIZED
Definition qopenglext.h:607
GLfixed GLfixed GLfixed y2
#define GL_VERTEX_ATTRIB_ARRAY_POINTER
Definition qopenglext.h:583
#define GL_VERTEX_ATTRIB_ARRAY_ENABLED
Definition qopenglext.h:577
#define GL_ARRAY_BUFFER_BINDING
Definition qopenglext.h:489
#define GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING
Definition qopenglext.h:491
#define GL_ACTIVE_TEXTURE
Definition qopenglext.h:161
#define GL_ARRAY_BUFFER
Definition qopenglext.h:487
#define GL_VERTEX_ATTRIB_ARRAY_TYPE
Definition qopenglext.h:580
GLfixed GLfixed x2
GLsizei const void * pointer
Definition qopenglext.h:384
GLint GLenum GLboolean normalized
Definition qopenglext.h:752
#define GL_BLEND_DST_RGB
Definition qopenglext.h:323
GLint GLfloat GLint stencil
#define GL_VERTEX_ATTRIB_ARRAY_STRIDE
Definition qopenglext.h:579
#define GL_CLAMP_TO_EDGE
Definition qopenglext.h:100
#define GL_BLEND_SRC_RGB
Definition qopenglext.h:324
#define GL_BLEND_SRC_ALPHA
Definition qopenglext.h:326
#define GL_VERTEX_ARRAY_BINDING
#define Q_ASSERT(cond)
Definition qrandom.cpp:47
#define GLuint
#define GL_UNSIGNED_BYTE
#define GL_RGBA
#define s2
#define s1
#define t2
#define t1
QScreen * screen
[1]
Definition main.cpp:29
Q_CORE_EXPORT QByteArray qgetenv(const char *varName)
Q_CORE_EXPORT int qEnvironmentVariableIntValue(const char *varName, bool *ok=nullptr) noexcept
#define Q_UNUSED(x)
unsigned int uint
Definition qtypes.h:34
static double toDouble(Value v)
#define enabled
QFile file
[0]
connect(quitButton, &QPushButton::clicked, &app, &QCoreApplication::quit, Qt::QueuedConnection)
QObject::connect nullptr
myFilter draw(painter, QPoint(0, 0), originalPixmap)
aWidget window() -> setWindowTitle("New Window Title")
[2]
StateSaver(QOpenGLFunctions *func)
QOpenGLFunctions * f
QOpenGLVertexArrayObjectHelper * vaoHelper
GLint activeTexture
Definition moc.h:23