mirror of
https://github.com/juce-framework/JUCE.git
synced 2026-01-15 00:24:19 +00:00
Direct2D: Fix flickery resizing when using an internal resizer
Resizing using window manager functionality (e.g. clicking and dragging in the non-client area) will send WM_SIZING to the window, which in turn will enable continuous repainting in the D2D renderer until the resize operation ends. Continuous repainting is required in order for the window to display correctly during the resize. Without continuous repainting, some frames may not be completely painted, and may display with black areas, producing a flickery effect. When a resize is controlled entirely by the client, e.g. using the corner resizer in the AudioPluginDemo standalone, WM_SIZING is never posted. Instead, we assume that if the window has captured the cursor during a setBounds call then it is probably resizing. We enable continuous repainting in this case, and stop repainting once the window releases the mouse. An alternative appropach would be to add some kind of start/stop resize API to ComponentPeer. I'm currently reluctant to do that because the ComponentPeer API is already so large.
This commit is contained in:
parent
adc63cecb1
commit
659de5842f
3 changed files with 30 additions and 1 deletions
|
|
@ -406,6 +406,11 @@ public:
|
|||
resizing = x;
|
||||
}
|
||||
|
||||
bool getResizing() const
|
||||
{
|
||||
return resizing;
|
||||
}
|
||||
|
||||
void setSize (Rectangle<int> size)
|
||||
{
|
||||
if (size == frameSize || size.isEmpty())
|
||||
|
|
@ -692,6 +697,11 @@ void Direct2DHwndContext::setResizing (bool x)
|
|||
pimpl->setResizing (x);
|
||||
}
|
||||
|
||||
bool Direct2DHwndContext::getResizing() const
|
||||
{
|
||||
return pimpl->getResizing();
|
||||
}
|
||||
|
||||
void Direct2DHwndContext::setSize (int width, int height)
|
||||
{
|
||||
pimpl->setSize ({ width, height });
|
||||
|
|
|
|||
|
|
@ -46,6 +46,7 @@ public:
|
|||
void setWindowAlpha (float alpha);
|
||||
|
||||
void setResizing (bool);
|
||||
bool getResizing() const;
|
||||
void setSize (int width, int height);
|
||||
void updateSize();
|
||||
|
||||
|
|
|
|||
|
|
@ -1457,6 +1457,7 @@ struct RenderContext
|
|||
virtual void performAnyPendingRepaintsNow() = 0;
|
||||
virtual void onVBlank() = 0;
|
||||
virtual void setResizing (bool) = 0;
|
||||
virtual bool getResizing() const = 0;
|
||||
virtual void handleNcCalcSize (WPARAM wParam, LPARAM lParam) = 0;
|
||||
virtual void handleShowWindow() = 0;
|
||||
|
||||
|
|
@ -1641,6 +1642,13 @@ public:
|
|||
if (inHandlePositionChanged)
|
||||
return;
|
||||
|
||||
// This is more of a guess than a certainty, but if we've captured the mouse and we're also
|
||||
// updating the bounds, there's a good chance we're in a client-initiated resize.
|
||||
// The resizing flag will be unset by WM_CAPTURECHANGED.
|
||||
if (GetCapture() == hwnd)
|
||||
if (renderContext != nullptr)
|
||||
renderContext->setResizing (true);
|
||||
|
||||
const ScopedValueSetter<bool> scope (shouldIgnoreModalDismiss, true);
|
||||
|
||||
fullScreen = isNowFullScreen;
|
||||
|
|
@ -2811,6 +2819,9 @@ private:
|
|||
constrainerIsResizing = false;
|
||||
}
|
||||
|
||||
if (renderContext != nullptr && renderContext->getResizing())
|
||||
renderContext->setResizing (false);
|
||||
|
||||
if (isDragging)
|
||||
doMouseUp (getCurrentMousePos(), (WPARAM) 0);
|
||||
}
|
||||
|
|
@ -4609,7 +4620,8 @@ public:
|
|||
|
||||
void onVBlank() override {}
|
||||
|
||||
void setResizing (bool) override {}
|
||||
void setResizing (bool x) override { resizing = x; }
|
||||
bool getResizing() const override { return resizing; }
|
||||
void handleNcCalcSize (WPARAM, LPARAM) override {}
|
||||
void handleShowWindow() override {}
|
||||
|
||||
|
|
@ -4780,6 +4792,7 @@ private:
|
|||
TemporaryImage offscreenImageGenerator;
|
||||
RectangleList<int> deferredRepaints;
|
||||
uint8 layeredWindowAlpha = 255;
|
||||
bool resizing = false;
|
||||
};
|
||||
|
||||
class D2DContext : public RenderContext
|
||||
|
|
@ -4870,6 +4883,11 @@ public:
|
|||
direct2DContext->setResizing (x);
|
||||
}
|
||||
|
||||
bool getResizing() const override
|
||||
{
|
||||
return direct2DContext->getResizing();
|
||||
}
|
||||
|
||||
void handleNcCalcSize (WPARAM, LPARAM lParam) override
|
||||
{
|
||||
JUCE_TRACE_LOG_D2D_RESIZE (WM_NCCALCSIZE);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue