1
0
Fork 0
mirror of https://github.com/juce-framework/JUCE.git synced 2026-01-10 23:44:24 +00:00

Fix correct repainting of OpenGLContexts if a non-compositing window manager is used on linux

This commit is contained in:
hogliux 2015-07-08 17:09:59 +01:00
parent a4526eae3f
commit effdc661ca
2 changed files with 78 additions and 4 deletions

View file

@ -2320,6 +2320,10 @@ public:
XEvent nextEvent;
ScopedXLock xlock;
// if we have opengl contexts then just repaint them all
// regardless if this is really necessary
repaintOpenGLContexts ();
if (exposeEvent.window != windowH)
{
Window child;
@ -2509,6 +2513,28 @@ public:
return currentScaleFactor;
}
//===============================================================================
void addOpenGLRepaintListener (Component* dummy)
{
if (dummy != nullptr)
glRepaintListeners.addIfNotAlreadyThere (dummy);
}
void removeOpenGLRepaintListener (Component* dummy)
{
if (dummy != nullptr)
glRepaintListeners.removeAllInstancesOf (dummy);
}
void repaintOpenGLContexts()
{
for (int i = 0; i < glRepaintListeners.size(); ++i)
{
if (Component* c = glRepaintListeners [i])
c->handleCommandMessage (0);
}
}
//==============================================================================
bool dontRepaint;
@ -2668,6 +2694,7 @@ private:
BorderSize<int> windowBorder;
bool isAlwaysOnTop;
double currentScaleFactor;
Array<Component*> glRepaintListeners;
enum { KeyPressEventType = 2 };
struct MotifWmHints
@ -4124,6 +4151,18 @@ Rectangle<int> juce_LinuxScaledToPhysicalBounds(ComponentPeer* peer, const Recta
return retval;
}
void juce_LinuxAddRepaintListener (ComponentPeer* peer, Component* dummy)
{
if (LinuxComponentPeer* linuxPeer = dynamic_cast<LinuxComponentPeer*> (peer))
linuxPeer->addOpenGLRepaintListener (dummy);
}
void juce_LinuxRemoveRepaintListener (ComponentPeer* peer, Component* dummy)
{
if (LinuxComponentPeer* linuxPeer = dynamic_cast<LinuxComponentPeer*> (peer))
linuxPeer->removeOpenGLRepaintListener (dummy);
}
//==============================================================================
#if JUCE_MODAL_LOOPS_PERMITTED
void JUCE_CALLTYPE NativeMessageBox::showMessageBox (AlertWindow::AlertIconType iconType,

View file

@ -28,11 +28,31 @@ extern XContext windowHandleXContext;
//==============================================================================
// Defined juce_linux_Windowing.cpp
Rectangle<int> juce_LinuxScaledToPhysicalBounds(ComponentPeer* peer, const Rectangle<int>& bounds);
Rectangle<int> juce_LinuxScaledToPhysicalBounds (ComponentPeer* peer, const Rectangle<int>& bounds);
void juce_LinuxAddRepaintListener (ComponentPeer* peer, Component* dummy);
void juce_LinuxRemoveRepaintListener (ComponentPeer* peer, Component* dummy);
//==============================================================================
class OpenGLContext::NativeContext
{
private:
class DummyComponent : public Component
{
public:
DummyComponent (OpenGLContext::NativeContext& nativeParentContext)
: native (nativeParentContext)
{
}
void handleCommandMessage (int commandId) override
{
if (commandId == 0)
native.triggerRepaint();
}
private:
OpenGLContext::NativeContext& native;
};
public:
NativeContext (Component& comp,
const OpenGLPixelFormat& cPixelFormat,
@ -40,7 +60,7 @@ public:
bool /*useMultisampling*/,
OpenGLVersion)
: component (comp), renderContext (0), embeddedWindow (0), swapFrames (0), bestVisual (0),
contextToShareWith (shareContext)
contextToShareWith (shareContext), context (nullptr), dummy (*this)
{
ScopedXLock xlock;
XSync (display, False);
@ -96,10 +116,14 @@ public:
XFreeColormap (display, colourMap);
XSync (display, False);
juce_LinuxAddRepaintListener (peer, &dummy);
}
~NativeContext()
{
juce_LinuxRemoveRepaintListener (component.getPeer(), &dummy);
if (embeddedWindow != 0)
{
ScopedXLock xlock;
@ -111,15 +135,17 @@ public:
XFree (bestVisual);
}
void initialiseOnRenderThread (OpenGLContext& context)
void initialiseOnRenderThread (OpenGLContext& c)
{
ScopedXLock xlock;
renderContext = glXCreateContext (display, bestVisual, (GLXContext) contextToShareWith, GL_TRUE);
context.makeActive();
c.makeActive();
context = &c;
}
void shutdownOnRenderThread()
{
context = nullptr;
deactivateCurrentContext();
glXDestroyContext (display, renderContext);
renderContext = nullptr;
@ -183,6 +209,12 @@ public:
void* getRawContext() const noexcept { return renderContext; }
GLuint getFrameBufferID() const noexcept { return 0; }
void triggerRepaint()
{
if (context != nullptr)
context->triggerRepaint();
}
struct Locker { Locker (NativeContext&) {} };
private:
@ -195,6 +227,9 @@ private:
XVisualInfo* bestVisual;
void* contextToShareWith;
OpenGLContext* context;
DummyComponent dummy;
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (NativeContext)
};