Browse Source

Bit of modernisation in OpenGLContext

tags/2021-05-28
jules 7 years ago
parent
commit
12f9f33e91
2 changed files with 75 additions and 89 deletions
  1. +61
    -75
      modules/juce_opengl/opengl/juce_OpenGLContext.cpp
  2. +14
    -14
      modules/juce_opengl/opengl/juce_OpenGLContext.h

+ 61
- 75
modules/juce_opengl/opengl/juce_OpenGLContext.cpp View File

@@ -74,18 +74,7 @@ public:
CachedImage (OpenGLContext& c, Component& comp, CachedImage (OpenGLContext& c, Component& comp,
const OpenGLPixelFormat& pixFormat, void* contextToShare) const OpenGLPixelFormat& pixFormat, void* contextToShare)
: ThreadPoolJob ("OpenGL Rendering"), : ThreadPoolJob ("OpenGL Rendering"),
context (c), component (comp),
scale (1.0),
#if JUCE_OPENGL3
vertexArrayObject (0),
#endif
#if JUCE_OPENGL_ES
shadersAvailable (true),
#else
shadersAvailable (false),
#endif
hasInitialised (false),
needsUpdate (1), lastMMLockReleaseTime (0)
context (c), component (comp)
{ {
nativeContext = new NativeContext (component, pixFormat, contextToShare, nativeContext = new NativeContext (component, pixFormat, contextToShare,
c.useMultisampling, c.versionRequired); c.useMultisampling, c.versionRequired);
@@ -180,8 +169,8 @@ public:
//============================================================================== //==============================================================================
bool ensureFrameBufferSize() bool ensureFrameBufferSize()
{ {
const int fbW = cachedImageFrameBuffer.getWidth();
const int fbH = cachedImageFrameBuffer.getHeight();
auto fbW = cachedImageFrameBuffer.getWidth();
auto fbH = cachedImageFrameBuffer.getHeight();
if (fbW != viewportArea.getWidth() || fbH != viewportArea.getHeight() || ! cachedImageFrameBuffer.isValid()) if (fbW != viewportArea.getWidth() || fbH != viewportArea.getHeight() || ! cachedImageFrameBuffer.isValid())
{ {
@@ -200,9 +189,9 @@ public:
glClearColor (0, 0, 0, 0); glClearColor (0, 0, 0, 0);
glEnable (GL_SCISSOR_TEST); glEnable (GL_SCISSOR_TEST);
const GLuint previousFrameBufferTarget = OpenGLFrameBuffer::getCurrentFrameBufferTarget();
auto previousFrameBufferTarget = OpenGLFrameBuffer::getCurrentFrameBufferTarget();
cachedImageFrameBuffer.makeCurrentRenderingTarget(); cachedImageFrameBuffer.makeCurrentRenderingTarget();
const int imageH = cachedImageFrameBuffer.getHeight();
auto imageH = cachedImageFrameBuffer.getHeight();
for (auto& r : list) for (auto& r : list)
{ {
@@ -280,16 +269,16 @@ public:
void updateViewportSize (bool canTriggerUpdate) void updateViewportSize (bool canTriggerUpdate)
{ {
if (ComponentPeer* peer = component.getPeer())
if (auto* peer = component.getPeer())
{ {
lastScreenBounds = component.getTopLevelComponent()->getScreenBounds(); lastScreenBounds = component.getTopLevelComponent()->getScreenBounds();
const double newScale = Desktop::getInstance().getDisplays()
.getDisplayContaining (lastScreenBounds.getCentre()).scale;
auto newScale = Desktop::getInstance().getDisplays()
.getDisplayContaining (lastScreenBounds.getCentre()).scale;
Rectangle<int> newArea (peer->getComponent().getLocalArea (&component, component.getLocalBounds())
.withZeroOrigin()
* newScale);
auto newArea = peer->getComponent().getLocalArea (&component, component.getLocalBounds())
.withZeroOrigin()
* newScale;
if (scale != newScale || viewportArea != newArea) if (scale != newScale || viewportArea != newArea)
{ {
@@ -312,7 +301,7 @@ public:
void checkViewportBounds() void checkViewportBounds()
{ {
const Rectangle<int> screenBounds (component.getTopLevelComponent()->getScreenBounds());
auto screenBounds = component.getTopLevelComponent()->getScreenBounds();
if (lastScreenBounds != screenBounds) if (lastScreenBounds != screenBounds)
updateViewportSize (true); updateViewportSize (true);
@@ -524,7 +513,7 @@ public:
} }
//============================================================================== //==============================================================================
struct MessageLockWorker : MessageManagerLock::BailOutChecker
struct MessageLockWorker : public MessageManagerLock::BailOutChecker
{ {
MessageLockWorker (CachedImage& cachedImageRequestingLock) MessageLockWorker (CachedImage& cachedImageRequestingLock)
: owner (cachedImageRequestingLock) : owner (cachedImageRequestingLock)
@@ -534,11 +523,11 @@ public:
bool shouldAbortAcquiringLock() override { return owner.doWorkWhileWaitingForLock (false); } bool shouldAbortAcquiringLock() override { return owner.doWorkWhileWaitingForLock (false); }
CachedImage& owner; CachedImage& owner;
JUCE_DECLARE_NON_COPYABLE(MessageLockWorker)
JUCE_DECLARE_NON_COPYABLE (MessageLockWorker)
}; };
//============================================================================== //==============================================================================
struct BlockingWorker : OpenGLContext::AsyncWorker
struct BlockingWorker : public OpenGLContext::AsyncWorker
{ {
BlockingWorker (OpenGLContext::AsyncWorker::Ptr && workerToUse) BlockingWorker (OpenGLContext::AsyncWorker::Ptr && workerToUse)
: originalWorker (static_cast<OpenGLContext::AsyncWorker::Ptr&&> (workerToUse)) : originalWorker (static_cast<OpenGLContext::AsyncWorker::Ptr&&> (workerToUse))
@@ -552,7 +541,7 @@ public:
finishedSignal.signal(); finishedSignal.signal();
} }
void block() { finishedSignal.wait(); }
void block() noexcept { finishedSignal.wait(); }
OpenGLContext::AsyncWorker::Ptr originalWorker; OpenGLContext::AsyncWorker::Ptr originalWorker;
WaitableEvent finishedSignal; WaitableEvent finishedSignal;
@@ -599,7 +588,9 @@ public:
blocker->block(); blocker->block();
} }
else else
{
jassertfalse; // you called execute AFTER you detached your openglcontext jassertfalse; // you called execute AFTER you detached your openglcontext
}
} }
//============================================================================== //==============================================================================
@@ -610,7 +601,7 @@ public:
//============================================================================== //==============================================================================
// used to push no work on to the gl thread to easily block // used to push no work on to the gl thread to easily block
struct DoNothingWorker : OpenGLContext::AsyncWorker
struct DoNothingWorker : public OpenGLContext::AsyncWorker
{ {
DoNothingWorker() {} DoNothingWorker() {}
void operator() (OpenGLContext&) override {} void operator() (OpenGLContext&) override {}
@@ -625,18 +616,23 @@ public:
OpenGLFrameBuffer cachedImageFrameBuffer; OpenGLFrameBuffer cachedImageFrameBuffer;
RectangleList<int> validArea; RectangleList<int> validArea;
Rectangle<int> viewportArea, lastScreenBounds; Rectangle<int> viewportArea, lastScreenBounds;
double scale;
double scale = 1.0;
#if JUCE_OPENGL3 #if JUCE_OPENGL3
GLuint vertexArrayObject;
GLuint vertexArrayObject = 0;
#endif #endif
StringArray associatedObjectNames; StringArray associatedObjectNames;
ReferenceCountedArray<ReferenceCountedObject> associatedObjects; ReferenceCountedArray<ReferenceCountedObject> associatedObjects;
WaitableEvent canPaintNowFlag, finishedPaintingFlag, repaintEvent; WaitableEvent canPaintNowFlag, finishedPaintingFlag, repaintEvent;
bool shadersAvailable, hasInitialised;
Atomic<int> needsUpdate, destroying;
uint32 lastMMLockReleaseTime;
#if JUCE_OPENGL_ES
bool shadersAvailable = true;
#else
bool shadersAvailable = false;
#endif
bool hasInitialised = false;
Atomic<int> needsUpdate { 1 }, destroying;
uint32 lastMMLockReleaseTime = 0;
ScopedPointer<ThreadPool> renderThread; ScopedPointer<ThreadPool> renderThread;
ReferenceCountedArray<OpenGLContext::AsyncWorker, CriticalSection> workQueue; ReferenceCountedArray<OpenGLContext::AsyncWorker, CriticalSection> workQueue;
@@ -667,17 +663,15 @@ public:
void detach() void detach()
{ {
Component& comp = *getComponent();
auto& comp = *getComponent();
stop(); stop();
comp.setCachedComponentImage (nullptr); comp.setCachedComponentImage (nullptr);
context.nativeContext = nullptr; context.nativeContext = nullptr;
} }
void componentMovedOrResized (bool /*wasMoved*/, bool /*wasResized*/) override void componentMovedOrResized (bool /*wasMoved*/, bool /*wasResized*/) override
{ {
Component& comp = *getComponent();
auto& comp = *getComponent();
if (isAttached (comp) != canBeAttached (comp)) if (isAttached (comp) != canBeAttached (comp))
componentVisibilityChanged(); componentVisibilityChanged();
@@ -685,10 +679,10 @@ public:
if (comp.getWidth() > 0 && comp.getHeight() > 0 if (comp.getWidth() > 0 && comp.getHeight() > 0
&& context.nativeContext != nullptr) && context.nativeContext != nullptr)
{ {
if (CachedImage* const c = CachedImage::get (comp))
if (auto* c = CachedImage::get (comp))
c->handleResize(); c->handleResize();
if (ComponentPeer* peer = comp.getTopLevelComponent()->getPeer())
if (auto* peer = comp.getTopLevelComponent()->getPeer())
context.nativeContext->updateWindowPosition (peer->getAreaCoveredBy (comp)); context.nativeContext->updateWindowPosition (peer->getAreaCoveredBy (comp));
} }
} }
@@ -701,7 +695,7 @@ public:
void componentVisibilityChanged() override void componentVisibilityChanged() override
{ {
Component& comp = *getComponent();
auto& comp = *getComponent();
if (canBeAttached (comp)) if (canBeAttached (comp))
{ {
@@ -730,7 +724,7 @@ public:
void update() void update()
{ {
Component& comp = *getComponent();
auto& comp = *getComponent();
if (canBeAttached (comp)) if (canBeAttached (comp))
start(); start();
@@ -751,7 +745,7 @@ private:
if (! c.isVisible()) if (! c.isVisible())
return false; return false;
if (Component* p = c.getParentComponent())
if (auto* p = c.getParentComponent())
return isShowingOrMinimised (*p); return isShowingOrMinimised (*p);
return c.getPeer() != nullptr; return c.getPeer() != nullptr;
@@ -764,10 +758,10 @@ private:
void attach() void attach()
{ {
Component& comp = *getComponent();
CachedImage* const newCachedImage = new CachedImage (context, comp,
context.openGLPixelFormat,
context.contextToShareWith);
auto& comp = *getComponent();
auto* newCachedImage = new CachedImage (context, comp,
context.openGLPixelFormat,
context.contextToShareWith);
comp.setCachedComponentImage (newCachedImage); comp.setCachedComponentImage (newCachedImage);
start(); start();
@@ -777,21 +771,21 @@ private:
{ {
stopTimer(); stopTimer();
Component& comp = *getComponent();
auto& comp = *getComponent();
#if JUCE_MAC #if JUCE_MAC
[[(NSView*) comp.getWindowHandle() window] disableScreenUpdatesUntilFlush]; [[(NSView*) comp.getWindowHandle() window] disableScreenUpdatesUntilFlush];
#endif #endif
if (CachedImage* const oldCachedImage = CachedImage::get (comp))
if (auto* oldCachedImage = CachedImage::get (comp))
oldCachedImage->stop(); // (must stop this before detaching it from the component) oldCachedImage->stop(); // (must stop this before detaching it from the component)
} }
void start() void start()
{ {
Component& comp = *getComponent();
auto& comp = *getComponent();
if (CachedImage* const cachedImage = CachedImage::get (comp))
if (auto* cachedImage = CachedImage::get (comp))
{ {
cachedImage->start(); // (must wait until this is attached before starting its thread) cachedImage->start(); // (must wait until this is attached before starting its thread)
cachedImage->updateViewportSize (true); cachedImage->updateViewportSize (true);
@@ -802,21 +796,13 @@ private:
void timerCallback() override void timerCallback() override
{ {
if (CachedImage* const cachedImage = CachedImage::get (*getComponent()))
if (auto* cachedImage = CachedImage::get (*getComponent()))
cachedImage->checkViewportBounds(); cachedImage->checkViewportBounds();
} }
}; };
//============================================================================== //==============================================================================
OpenGLContext::OpenGLContext() OpenGLContext::OpenGLContext()
: nativeContext (nullptr), renderer (nullptr),
currentRenderScale (1.0), contextToShareWith (nullptr),
versionRequired (OpenGLContext::defaultGLVersion),
imageCacheMaxSize (8 * 1024 * 1024),
renderComponents (true),
useMultisampling (false),
continuousRepaint (false),
overrideCanAttach (false)
{ {
} }
@@ -894,7 +880,7 @@ void OpenGLContext::attachTo (Component& component)
void OpenGLContext::detach() void OpenGLContext::detach()
{ {
if (Attachment* a = attachment)
if (auto* a = attachment.get())
{ {
a->detach(); // must detach before nulling our pointer a->detach(); // must detach before nulling our pointer
attachment = nullptr; attachment = nullptr;
@@ -915,7 +901,7 @@ Component* OpenGLContext::getTargetComponent() const noexcept
OpenGLContext* OpenGLContext::getContextAttachedTo (Component& c) noexcept OpenGLContext* OpenGLContext::getContextAttachedTo (Component& c) noexcept
{ {
if (CachedImage* const ci = CachedImage::get (c))
if (auto* ci = CachedImage::get (c))
return &(ci->context); return &(ci->context);
return nullptr; return nullptr;
@@ -930,7 +916,7 @@ OpenGLContext* OpenGLContext::getCurrentContext()
bool OpenGLContext::makeActive() const noexcept bool OpenGLContext::makeActive() const noexcept
{ {
OpenGLContext*& current = currentThreadActiveContext.get();
auto& current = currentThreadActiveContext.get();
if (nativeContext != nullptr && nativeContext->makeActive()) if (nativeContext != nullptr && nativeContext->makeActive())
{ {
@@ -955,7 +941,7 @@ void OpenGLContext::deactivateCurrentContext()
void OpenGLContext::triggerRepaint() void OpenGLContext::triggerRepaint()
{ {
if (CachedImage* const cachedImage = getCachedImage())
if (auto* cachedImage = getCachedImage())
cachedImage->triggerRepaint(); cachedImage->triggerRepaint();
} }
@@ -987,7 +973,7 @@ void* OpenGLContext::getRawContext() const noexcept
OpenGLContext::CachedImage* OpenGLContext::getCachedImage() const noexcept OpenGLContext::CachedImage* OpenGLContext::getCachedImage() const noexcept
{ {
if (Component* const comp = getTargetComponent())
if (auto* comp = getTargetComponent())
return CachedImage::get (*comp); return CachedImage::get (*comp);
return nullptr; return nullptr;
@@ -995,7 +981,7 @@ OpenGLContext::CachedImage* OpenGLContext::getCachedImage() const noexcept
bool OpenGLContext::areShadersAvailable() const bool OpenGLContext::areShadersAvailable() const
{ {
CachedImage* const c = getCachedImage();
auto* c = getCachedImage();
return c != nullptr && c->shadersAvailable; return c != nullptr && c->shadersAvailable;
} }
@@ -1003,7 +989,7 @@ ReferenceCountedObject* OpenGLContext::getAssociatedObject (const char* name) co
{ {
jassert (name != nullptr); jassert (name != nullptr);
CachedImage* const c = getCachedImage();
auto* c = getCachedImage();
// This method must only be called from an openGL rendering callback. // This method must only be called from an openGL rendering callback.
jassert (c != nullptr && nativeContext != nullptr); jassert (c != nullptr && nativeContext != nullptr);
@@ -1017,7 +1003,7 @@ void OpenGLContext::setAssociatedObject (const char* name, ReferenceCountedObjec
{ {
jassert (name != nullptr); jassert (name != nullptr);
if (CachedImage* const c = getCachedImage())
if (auto* c = getCachedImage())
{ {
// This method must only be called from an openGL rendering callback. // This method must only be called from an openGL rendering callback.
jassert (nativeContext != nullptr); jassert (nativeContext != nullptr);
@@ -1050,7 +1036,7 @@ size_t OpenGLContext::getImageCacheSize() const noexcept { return ima
void OpenGLContext::execute (OpenGLContext::AsyncWorker::Ptr workerToUse, bool shouldBlock) void OpenGLContext::execute (OpenGLContext::AsyncWorker::Ptr workerToUse, bool shouldBlock)
{ {
if (CachedImage* const c = getCachedImage())
if (auto* c = getCachedImage())
c->execute (static_cast<OpenGLContext::AsyncWorker::Ptr&&> (workerToUse), shouldBlock); c->execute (static_cast<OpenGLContext::AsyncWorker::Ptr&&> (workerToUse), shouldBlock);
else else
jassertfalse; // You must have attached the context to a component jassertfalse; // You must have attached the context to a component
@@ -1062,7 +1048,7 @@ void OpenGLContext::overrideCanBeAttached (bool newCanAttach)
{ {
overrideCanAttach = newCanAttach; overrideCanAttach = newCanAttach;
if (Attachment* a = attachment)
if (auto* a = attachment.get())
a->update(); a->update();
} }
} }
@@ -1185,13 +1171,13 @@ void OpenGLContext::copyTexture (const Rectangle<int>& targetClipArea,
Params params; Params params;
}; };
const GLshort left = (GLshort) targetClipArea.getX();
const GLshort top = (GLshort) targetClipArea.getY();
const GLshort right = (GLshort) targetClipArea.getRight();
const GLshort bottom = (GLshort) targetClipArea.getBottom();
auto left = (GLshort) targetClipArea.getX();
auto top = (GLshort) targetClipArea.getY();
auto right = (GLshort) targetClipArea.getRight();
auto bottom = (GLshort) targetClipArea.getBottom();
const GLshort vertices[] = { left, bottom, right, bottom, left, top, right, top }; const GLshort vertices[] = { left, bottom, right, bottom, left, top, right, top };
const OverlayShaderProgram& program = OverlayShaderProgram::select (*this);
auto& program = OverlayShaderProgram::select (*this);
program.params.set ((float) contextWidth, (float) contextHeight, anchorPosAndTextureSize.toFloat(), flippedVertically); program.params.set ((float) contextWidth, (float) contextHeight, anchorPosAndTextureSize.toFloat(), flippedVertically);
GLuint vertexBuffer = 0; GLuint vertexBuffer = 0;
@@ -1199,7 +1185,7 @@ void OpenGLContext::copyTexture (const Rectangle<int>& targetClipArea,
extensions.glBindBuffer (GL_ARRAY_BUFFER, vertexBuffer); extensions.glBindBuffer (GL_ARRAY_BUFFER, vertexBuffer);
extensions.glBufferData (GL_ARRAY_BUFFER, sizeof (vertices), vertices, GL_STATIC_DRAW); extensions.glBufferData (GL_ARRAY_BUFFER, sizeof (vertices), vertices, GL_STATIC_DRAW);
const GLuint index = (GLuint) program.params.positionAttribute.attributeID;
auto index = (GLuint) program.params.positionAttribute.attributeID;
extensions.glVertexAttribPointer (index, 2, GL_SHORT, GL_FALSE, 4, 0); extensions.glVertexAttribPointer (index, 2, GL_SHORT, GL_FALSE, 4, 0);
extensions.glEnableVertexAttribArray (index); extensions.glEnableVertexAttribArray (index);
JUCE_CHECK_OPENGL_ERROR JUCE_CHECK_OPENGL_ERROR


+ 14
- 14
modules/juce_opengl/opengl/juce_OpenGLContext.h View File

@@ -300,30 +300,30 @@ public:
private: private:
class CachedImage; class CachedImage;
class Attachment; class Attachment;
NativeContext* nativeContext;
OpenGLRenderer* renderer;
double currentRenderScale;
NativeContext* nativeContext = nullptr;
OpenGLRenderer* renderer = nullptr;
double currentRenderScale = 1.0;
ScopedPointer<Attachment> attachment; ScopedPointer<Attachment> attachment;
OpenGLPixelFormat openGLPixelFormat; OpenGLPixelFormat openGLPixelFormat;
void* contextToShareWith;
OpenGLVersion versionRequired;
size_t imageCacheMaxSize;
bool renderComponents, useMultisampling, continuousRepaint, overrideCanAttach;
void* contextToShareWith = nullptr;
OpenGLVersion versionRequired = defaultGLVersion;
size_t imageCacheMaxSize = 8 * 1024 * 1024;
bool renderComponents = true, useMultisampling = false, continuousRepaint = false, overrideCanAttach = false;
//============================================================================== //==============================================================================
struct AsyncWorker : ReferenceCountedObject
struct AsyncWorker : public ReferenceCountedObject
{ {
typedef ReferenceCountedObjectPtr<AsyncWorker> Ptr; typedef ReferenceCountedObjectPtr<AsyncWorker> Ptr;
virtual void operator() (OpenGLContext&) = 0; virtual void operator() (OpenGLContext&) = 0;
virtual ~AsyncWorker() {} virtual ~AsyncWorker() {}
}; };
template <typename T>
struct AsyncWorkerFunctor : AsyncWorker
template <typename FunctionType>
struct AsyncWorkerFunctor : public AsyncWorker
{ {
AsyncWorkerFunctor (T functorToUse) : functor (functorToUse) {}
AsyncWorkerFunctor (FunctionType functorToUse) : functor (functorToUse) {}
void operator() (OpenGLContext& callerContext) override { functor (callerContext); } void operator() (OpenGLContext& callerContext) override { functor (callerContext); }
T functor;
FunctionType functor;
JUCE_DECLARE_NON_COPYABLE (AsyncWorkerFunctor) JUCE_DECLARE_NON_COPYABLE (AsyncWorkerFunctor)
}; };
@@ -341,8 +341,8 @@ private:
//============================================================================== //==============================================================================
#ifndef DOXYGEN #ifndef DOXYGEN
template <typename T>
void OpenGLContext::executeOnGLThread (T&& f, bool shouldBlock) { execute (new AsyncWorkerFunctor<T> (f), shouldBlock); }
template <typename FunctionType>
void OpenGLContext::executeOnGLThread (FunctionType&& f, bool shouldBlock) { execute (new AsyncWorkerFunctor<FunctionType> (f), shouldBlock); }
#endif #endif
} // namespace juce } // namespace juce

Loading…
Cancel
Save