Changeset View
Changeset View
Standalone View
Standalone View
plugins/platforms/x11/standalone/glxbackend.cpp
Show First 20 Lines • Show All 107 Lines • ▼ Show 20 Line(s) | 106 | GlxBackend::GlxBackend(Display *display) | |||
---|---|---|---|---|---|
108 | , m_overlayWindow(kwinApp()->platform()->createOverlayWindow()) | 108 | , m_overlayWindow(kwinApp()->platform()->createOverlayWindow()) | ||
109 | , window(None) | 109 | , window(None) | ||
110 | , fbconfig(nullptr) | 110 | , fbconfig(nullptr) | ||
111 | , glxWindow(None) | 111 | , glxWindow(None) | ||
112 | , ctx(nullptr) | 112 | , ctx(nullptr) | ||
113 | , m_bufferAge(0) | 113 | , m_bufferAge(0) | ||
114 | , m_x11Display(display) | 114 | , m_x11Display(display) | ||
115 | { | 115 | { | ||
116 | // Ensures calls to glXSwapBuffers will always block until the next | | |||
117 | // retrace when using the proprietary NVIDIA driver. This must be | | |||
118 | // set before libGL.so is loaded. | | |||
119 | setenv("__GL_MaxFramesAllowed", "1", true); | | |||
120 | | ||||
121 | // Force initialization of GLX integration in the Qt's xcb backend | 116 | // Force initialization of GLX integration in the Qt's xcb backend | ||
122 | // to make it call XESetWireToEvent callbacks, which is required | 117 | // to make it call XESetWireToEvent callbacks, which is required | ||
123 | // by Mesa when using DRI2. | 118 | // by Mesa when using DRI2. | ||
124 | QOpenGLContext::supportsThreadedOpenGL(); | 119 | QOpenGLContext::supportsThreadedOpenGL(); | ||
125 | } | 120 | } | ||
126 | 121 | | |||
127 | GlxBackend::~GlxBackend() | 122 | GlxBackend::~GlxBackend() | ||
128 | { | 123 | { | ||
▲ Show 20 Lines • Show All 92 Lines • ▼ Show 20 Line(s) | 165 | { | |||
221 | 216 | | |||
222 | if (hasExtension(QByteArrayLiteral("GLX_EXT_buffer_age"))) { | 217 | if (hasExtension(QByteArrayLiteral("GLX_EXT_buffer_age"))) { | ||
223 | const QByteArray useBufferAge = qgetenv("KWIN_USE_BUFFER_AGE"); | 218 | const QByteArray useBufferAge = qgetenv("KWIN_USE_BUFFER_AGE"); | ||
224 | 219 | | |||
225 | if (useBufferAge != "0") | 220 | if (useBufferAge != "0") | ||
226 | setSupportsBufferAge(true); | 221 | setSupportsBufferAge(true); | ||
227 | } | 222 | } | ||
228 | 223 | | |||
229 | setBlocksForRetrace(true); | | |||
230 | | ||||
231 | if (m_haveEXTSwapControl) { | 224 | if (m_haveEXTSwapControl) { | ||
232 | glXSwapIntervalEXT(display(), glxWindow, 1); | 225 | glXSwapIntervalEXT(display(), glxWindow, 1); | ||
233 | } else if (m_haveMESASwapControl) { | 226 | } else if (m_haveMESASwapControl) { | ||
234 | glXSwapIntervalMESA(1); | 227 | glXSwapIntervalMESA(1); | ||
235 | } else { | 228 | } else { | ||
236 | qCWarning(KWIN_X11STANDALONE) << "NO VSYNC! glSwapInterval is not supported"; | 229 | qCWarning(KWIN_X11STANDALONE) << "NO VSYNC! glSwapInterval is not supported"; | ||
237 | } | 230 | } | ||
238 | 231 | | |||
▲ Show 20 Lines • Show All 458 Lines • ▼ Show 20 Line(s) | |||||
697 | { | 690 | { | ||
698 | return new GlxTexture(texture, this); | 691 | return new GlxTexture(texture, this); | ||
699 | } | 692 | } | ||
700 | 693 | | |||
701 | QRegion GlxBackend::prepareRenderingFrame() | 694 | QRegion GlxBackend::prepareRenderingFrame() | ||
702 | { | 695 | { | ||
703 | QRegion repaint; | 696 | QRegion repaint; | ||
704 | 697 | | |||
705 | present(); | | |||
706 | | ||||
707 | if (supportsBufferAge()) | 698 | if (supportsBufferAge()) | ||
708 | repaint = accumulatedDamageHistory(m_bufferAge); | 699 | repaint = accumulatedDamageHistory(m_bufferAge); | ||
709 | 700 | | |||
710 | startRenderTimer(); | 701 | startRenderTimer(); | ||
711 | glXWaitX(); | | |||
712 | 702 | | |||
713 | return repaint; | 703 | return repaint; | ||
714 | } | 704 | } | ||
715 | 705 | | |||
716 | void GlxBackend::endRenderingFrame(const QRegion &renderedRegion, const QRegion &damagedRegion) | 706 | void GlxBackend::endRenderingFrame(const QRegion &renderedRegion, const QRegion &damagedRegion) | ||
717 | { | 707 | { | ||
718 | if (damagedRegion.isEmpty()) { | 708 | if (damagedRegion.isEmpty()) { | ||
719 | setLastDamage(QRegion()); | 709 | setLastDamage(QRegion()); | ||
720 | 710 | | |||
721 | // If the damaged region of a window is fully occluded, the only | 711 | // If the damaged region of a window is fully occluded, the only | ||
722 | // rendering done, if any, will have been to repair a reused back | 712 | // rendering done, if any, will have been to repair a reused back | ||
723 | // buffer, making it identical to the front buffer. | 713 | // buffer, making it identical to the front buffer. | ||
724 | // | 714 | // | ||
725 | // In this case we won't post the back buffer. Instead we'll just | 715 | // In this case we won't post the back buffer. Instead we'll just | ||
726 | // set the buffer age to 1, so the repaired regions won't be | 716 | // set the buffer age to 1, so the repaired regions won't be | ||
727 | // rendered again in the next frame. | 717 | // rendered again in the next frame. | ||
728 | if (!renderedRegion.isEmpty()) | 718 | if (!renderedRegion.isEmpty()) | ||
729 | glFlush(); | 719 | glFlush(); | ||
730 | 720 | | |||
731 | m_bufferAge = 1; | 721 | m_bufferAge = 1; | ||
732 | return; | 722 | return; | ||
733 | } | 723 | } | ||
734 | 724 | | |||
735 | setLastDamage(renderedRegion); | 725 | setLastDamage(renderedRegion); | ||
736 | | ||||
737 | if (!blocksForRetrace()) { | | |||
738 | // This also sets lastDamage to empty which prevents the frame from | | |||
739 | // being posted again when prepareRenderingFrame() is called. | | |||
740 | present(); | 726 | present(); | ||
741 | } else { | | |||
742 | // Make sure that the GPU begins processing the command stream | | |||
743 | // now and not the next time prepareRenderingFrame() is called. | | |||
744 | glFlush(); | | |||
745 | } | | |||
746 | 727 | | |||
747 | if (overlayWindow()->window()) // show the window only after the first pass, | 728 | if (overlayWindow()->window()) // show the window only after the first pass, | ||
748 | overlayWindow()->show(); // since that pass may take long | 729 | overlayWindow()->show(); // since that pass may take long | ||
749 | 730 | | |||
750 | // Save the damaged region to history | 731 | // Save the damaged region to history | ||
751 | if (supportsBufferAge()) | 732 | if (supportsBufferAge()) | ||
752 | addToDamageHistory(damagedRegion); | 733 | addToDamageHistory(damagedRegion); | ||
753 | } | 734 | } | ||
▲ Show 20 Lines • Show All 114 Lines • Show Last 20 Lines |