| @@ -1726,26 +1726,16 @@ const Result Result::fail (const String& errorMessage) noexcept | |||
| return Result (errorMessage.isEmpty() ? "Unknown Error" : errorMessage); | |||
| } | |||
| bool Result::wasOk() const noexcept | |||
| { | |||
| return errorMessage.isEmpty(); | |||
| } | |||
| bool Result::failed() const noexcept | |||
| { | |||
| return errorMessage.isNotEmpty(); | |||
| } | |||
| Result::operator bool() const noexcept | |||
| { | |||
| return errorMessage.isEmpty(); | |||
| } | |||
| const String Result::getErrorMessage() const noexcept | |||
| { | |||
| return errorMessage; | |||
| } | |||
| bool Result::wasOk() const noexcept { return errorMessage.isEmpty(); } | |||
| Result::operator bool() const noexcept { return errorMessage.isEmpty(); } | |||
| bool Result::failed() const noexcept { return errorMessage.isNotEmpty(); } | |||
| bool Result::operator!() const noexcept { return errorMessage.isNotEmpty(); } | |||
| END_JUCE_NAMESPACE | |||
| /*** End of inlined file: juce_Result.cpp ***/ | |||
| @@ -48506,6 +48496,7 @@ void ComboBox::lookAndFeelChanged() | |||
| } | |||
| addAndMakeVisible (label); | |||
| setWantsKeyboardFocus (! label->isEditable()); | |||
| label->addListener (this); | |||
| label->addMouseListener (this, false); | |||
| @@ -76902,6 +76893,14 @@ public: | |||
| while (owner.renderAndSwapBuffers() && ! threadShouldExit()) | |||
| owner.waitAfterSwapping(); | |||
| owner.releaseOpenGLContext(); | |||
| #if JUCE_LINUX | |||
| owner.deleteContext(); | |||
| #else | |||
| owner.makeCurrentContextInactive(); | |||
| #endif | |||
| triggerAsyncUpdate(); | |||
| } | |||
| @@ -76933,17 +76932,13 @@ public: | |||
| void componentPeerChanged() | |||
| { | |||
| const ScopedLock sl (owner->getContextLock()); | |||
| owner->stopRendering(); | |||
| } | |||
| void componentVisibilityChanged() | |||
| { | |||
| if (! owner->isShowing()) | |||
| { | |||
| const ScopedLock sl (owner->getContextLock()); | |||
| owner->stopRendering(); | |||
| } | |||
| } | |||
| private: | |||
| @@ -76955,7 +76950,8 @@ private: | |||
| OpenGLComponent::OpenGLComponent (const OpenGLType type_) | |||
| : type (type_), | |||
| contextToShareListsWith (nullptr), | |||
| needToUpdateViewport (true) | |||
| needToUpdateViewport (true), | |||
| useThread (false) | |||
| { | |||
| setOpaque (true); | |||
| componentWatcher = new OpenGLComponentWatcher (this); | |||
| @@ -76963,7 +76959,8 @@ OpenGLComponent::OpenGLComponent (const OpenGLType type_) | |||
| OpenGLComponent::~OpenGLComponent() | |||
| { | |||
| deleteContext(); | |||
| stopRendering(); | |||
| renderThread = nullptr; | |||
| componentWatcher = nullptr; | |||
| } | |||
| @@ -77079,14 +77076,29 @@ void OpenGLComponent::paint (Graphics&) | |||
| renderThread = new OpenGLComponentRenderThread (*this); | |||
| if (! renderThread->isThreadRunning()) | |||
| { | |||
| renderThread->handleUpdateNowIfNeeded(); // may still be shutting down as well | |||
| #if ! JUCE_LINUX | |||
| // Except for Linux, create the context etc. first | |||
| const ScopedLock sl (contextLock); | |||
| if (makeCurrentContextActive()) // Make active just to create | |||
| makeCurrentContextInactive(); | |||
| #endif | |||
| renderThread->startThread (6); | |||
| } | |||
| // fall-through and update the masking region | |||
| } | |||
| else | |||
| { | |||
| if (renderThread != nullptr && renderThread->isThreadRunning()) | |||
| renderThread->stopThread (5000); | |||
| if (renderThread != nullptr) | |||
| { | |||
| stopRendering(); | |||
| renderThread = nullptr; | |||
| } | |||
| if (! renderAndSwapBuffers()) | |||
| return; | |||
| @@ -77127,26 +77139,19 @@ void OpenGLComponent::waitAfterSwapping() | |||
| Thread::sleep (20); | |||
| } | |||
| bool OpenGLComponent::stopRendering() | |||
| void OpenGLComponent::stopRendering() | |||
| { | |||
| const ScopedLock sl (contextLock); | |||
| if (renderThread != nullptr) | |||
| renderThread->stopThread (5000); | |||
| if (! makeCurrentContextActive()) | |||
| return false; | |||
| releaseOpenGLContext(); // callback to allow for shutdown | |||
| if (renderThread != nullptr && Thread::getCurrentThread() == renderThread) | |||
| if (context != nullptr && makeCurrentContextActive()) | |||
| { | |||
| // make the context inactive - if we're on a thread, this will release the context, | |||
| // so the main thread can take it and do shutdown | |||
| // On Linux, when threaded, context will have already been cleared | |||
| const ScopedLock sl (contextLock); | |||
| makeCurrentContextInactive(); | |||
| releaseOpenGLContext(); | |||
| deleteContext(); | |||
| } | |||
| else if (context != nullptr) | |||
| context->deleteContext(); | |||
| return true; | |||
| } | |||
| void OpenGLComponent::internalRepaint (int x, int y, int w, int h) | |||
| @@ -73,7 +73,7 @@ namespace JuceDummyNamespace {} | |||
| */ | |||
| #define JUCE_MAJOR_VERSION 1 | |||
| #define JUCE_MINOR_VERSION 53 | |||
| #define JUCE_BUILDNUMBER 77 | |||
| #define JUCE_BUILDNUMBER 78 | |||
| /** Current Juce version number. | |||
| @@ -12059,6 +12059,11 @@ public: | |||
| */ | |||
| operator bool() const noexcept; | |||
| /** Returns true if this result indicates a failure. | |||
| This is equivalent to calling failed(). | |||
| */ | |||
| bool operator!() const noexcept; | |||
| /** Returns the error message that was set when this result was created. | |||
| For a successful result, this will be an empty string; | |||
| */ | |||
| @@ -12074,6 +12079,10 @@ private: | |||
| String errorMessage; | |||
| explicit Result (const String& errorMessage) noexcept; | |||
| // These casts are private to prevent people trying to use the Result object in numeric contexts | |||
| operator int() const; | |||
| operator void*() const; | |||
| }; | |||
| #endif // __JUCE_RESULT_JUCEHEADER__ | |||
| @@ -63926,15 +63935,9 @@ public: | |||
| Used when rendering is running on a thread. The default is 20 millseconds, giving | |||
| a nominal frame rate of just under 50 fps. | |||
| */ | |||
| */ | |||
| virtual void waitAfterSwapping(); | |||
| /** Stop Rendering. | |||
| Use to shut down an openGLComponent properly, whether on a thread or not. | |||
| */ | |||
| virtual bool stopRendering(); | |||
| /** This returns a critical section that can be used to lock the current context. | |||
| Because the context that is used by this component can change, e.g. when the | |||
| @@ -63980,6 +63983,7 @@ private: | |||
| OpenGLContext* createContext(); | |||
| void updateContextPosition(); | |||
| void internalRepaint (int x, int y, int w, int h); | |||
| void stopRendering(); | |||
| JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (OpenGLComponent); | |||
| }; | |||
| @@ -67,26 +67,15 @@ const Result Result::fail (const String& errorMessage) noexcept | |||
| return Result (errorMessage.isEmpty() ? "Unknown Error" : errorMessage); | |||
| } | |||
| //============================================================================== | |||
| bool Result::wasOk() const noexcept | |||
| { | |||
| return errorMessage.isEmpty(); | |||
| } | |||
| bool Result::failed() const noexcept | |||
| { | |||
| return errorMessage.isNotEmpty(); | |||
| } | |||
| Result::operator bool() const noexcept | |||
| { | |||
| return errorMessage.isEmpty(); | |||
| } | |||
| const String Result::getErrorMessage() const noexcept | |||
| { | |||
| return errorMessage; | |||
| } | |||
| bool Result::wasOk() const noexcept { return errorMessage.isEmpty(); } | |||
| Result::operator bool() const noexcept { return errorMessage.isEmpty(); } | |||
| bool Result::failed() const noexcept { return errorMessage.isNotEmpty(); } | |||
| bool Result::operator!() const noexcept { return errorMessage.isNotEmpty(); } | |||
| END_JUCE_NAMESPACE | |||
| @@ -85,6 +85,11 @@ public: | |||
| */ | |||
| operator bool() const noexcept; | |||
| /** Returns true if this result indicates a failure. | |||
| This is equivalent to calling failed(). | |||
| */ | |||
| bool operator!() const noexcept; | |||
| /** Returns the error message that was set when this result was created. | |||
| For a successful result, this will be an empty string; | |||
| */ | |||
| @@ -101,6 +106,10 @@ private: | |||
| String errorMessage; | |||
| explicit Result (const String& errorMessage) noexcept; | |||
| // These casts are private to prevent people trying to use the Result object in numeric contexts | |||
| operator int() const; | |||
| operator void*() const; | |||
| }; | |||
| @@ -33,7 +33,7 @@ | |||
| */ | |||
| #define JUCE_MAJOR_VERSION 1 | |||
| #define JUCE_MINOR_VERSION 53 | |||
| #define JUCE_BUILDNUMBER 77 | |||
| #define JUCE_BUILDNUMBER 78 | |||
| /** Current Juce version number. | |||
| @@ -432,6 +432,7 @@ void ComboBox::lookAndFeelChanged() | |||
| } | |||
| addAndMakeVisible (label); | |||
| setWantsKeyboardFocus (! label->isEditable()); | |||
| label->addListener (this); | |||
| label->addMouseListener (this, false); | |||
| @@ -148,6 +148,14 @@ public: | |||
| while (owner.renderAndSwapBuffers() && ! threadShouldExit()) | |||
| owner.waitAfterSwapping(); | |||
| owner.releaseOpenGLContext(); | |||
| #if JUCE_LINUX | |||
| owner.deleteContext(); | |||
| #else | |||
| owner.makeCurrentContextInactive(); | |||
| #endif | |||
| triggerAsyncUpdate(); | |||
| } | |||
| @@ -184,17 +192,13 @@ public: | |||
| void componentPeerChanged() | |||
| { | |||
| const ScopedLock sl (owner->getContextLock()); | |||
| owner->stopRendering(); | |||
| } | |||
| void componentVisibilityChanged() | |||
| { | |||
| if (! owner->isShowing()) | |||
| { | |||
| const ScopedLock sl (owner->getContextLock()); | |||
| owner->stopRendering(); | |||
| } | |||
| } | |||
| //============================================================================== | |||
| @@ -208,7 +212,8 @@ private: | |||
| OpenGLComponent::OpenGLComponent (const OpenGLType type_) | |||
| : type (type_), | |||
| contextToShareListsWith (nullptr), | |||
| needToUpdateViewport (true) | |||
| needToUpdateViewport (true), | |||
| useThread (false) | |||
| { | |||
| setOpaque (true); | |||
| componentWatcher = new OpenGLComponentWatcher (this); | |||
| @@ -216,7 +221,8 @@ OpenGLComponent::OpenGLComponent (const OpenGLType type_) | |||
| OpenGLComponent::~OpenGLComponent() | |||
| { | |||
| deleteContext(); | |||
| stopRendering(); | |||
| renderThread = nullptr; | |||
| componentWatcher = nullptr; | |||
| } | |||
| @@ -332,14 +338,29 @@ void OpenGLComponent::paint (Graphics&) | |||
| renderThread = new OpenGLComponentRenderThread (*this); | |||
| if (! renderThread->isThreadRunning()) | |||
| { | |||
| renderThread->handleUpdateNowIfNeeded(); // may still be shutting down as well | |||
| #if ! JUCE_LINUX | |||
| // Except for Linux, create the context etc. first | |||
| const ScopedLock sl (contextLock); | |||
| if (makeCurrentContextActive()) // Make active just to create | |||
| makeCurrentContextInactive(); | |||
| #endif | |||
| renderThread->startThread (6); | |||
| } | |||
| // fall-through and update the masking region | |||
| } | |||
| else | |||
| { | |||
| if (renderThread != nullptr && renderThread->isThreadRunning()) | |||
| renderThread->stopThread (5000); | |||
| if (renderThread != nullptr) | |||
| { | |||
| stopRendering(); | |||
| renderThread = nullptr; | |||
| } | |||
| if (! renderAndSwapBuffers()) | |||
| return; | |||
| @@ -380,26 +401,19 @@ void OpenGLComponent::waitAfterSwapping() | |||
| Thread::sleep (20); | |||
| } | |||
| bool OpenGLComponent::stopRendering() | |||
| void OpenGLComponent::stopRendering() | |||
| { | |||
| const ScopedLock sl (contextLock); | |||
| if (! makeCurrentContextActive()) | |||
| return false; | |||
| if (renderThread != nullptr) | |||
| renderThread->stopThread (5000); | |||
| releaseOpenGLContext(); // callback to allow for shutdown | |||
| if (renderThread != nullptr && Thread::getCurrentThread() == renderThread) | |||
| if (context != nullptr && makeCurrentContextActive()) | |||
| { | |||
| // make the context inactive - if we're on a thread, this will release the context, | |||
| // so the main thread can take it and do shutdown | |||
| // On Linux, when threaded, context will have already been cleared | |||
| const ScopedLock sl (contextLock); | |||
| makeCurrentContextInactive(); | |||
| releaseOpenGLContext(); | |||
| deleteContext(); | |||
| } | |||
| else if (context != nullptr) | |||
| context->deleteContext(); | |||
| return true; | |||
| } | |||
| void OpenGLComponent::internalRepaint (int x, int y, int w, int h) | |||
| @@ -346,15 +346,9 @@ public: | |||
| Used when rendering is running on a thread. The default is 20 millseconds, giving | |||
| a nominal frame rate of just under 50 fps. | |||
| */ | |||
| */ | |||
| virtual void waitAfterSwapping(); | |||
| /** Stop Rendering. | |||
| Use to shut down an openGLComponent properly, whether on a thread or not. | |||
| */ | |||
| virtual bool stopRendering(); | |||
| /** This returns a critical section that can be used to lock the current context. | |||
| Because the context that is used by this component can change, e.g. when the | |||
| @@ -403,6 +397,7 @@ private: | |||
| OpenGLContext* createContext(); | |||
| void updateContextPosition(); | |||
| void internalRepaint (int x, int y, int w, int h); | |||
| void stopRendering(); | |||
| JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (OpenGLComponent); | |||
| }; | |||