[WIN][JUCE7] Desktop components created outside of a screen area will not get repainted


JUCE 7 has introduced the consolidation of repaint calls on Windows to synchronize them with the screen refresh (Git commit 05a42424f980).

The associated monitor for a HWND is determined with MonitorFromWindow(hwnd, MONITOR_DEFAULTTONULL). The monitor for a component which is added to the desktop with a position outside of any screen will therefore be NULL and will not get attached to a VSyncThread immediately. When the component is moved, a call to handlePositionChanged() will appear after a WM_WINDOWPOSCHANGED was received and will update the associated monitor.This works well in most standard situations.

However, hosted plugin editors in JUCE are embedded into several layers of native windows. Additionally, in our use case we have further surrounding native desktop windows to allow scrolling of hosted plugin editors.

Those child windows will never receive a WM_WINDOWPOSCHANGED because their position relative to the parent does not change. Therefore, they will never get attached to a VSyncThread even if they are moved into a screen area and will never get repainted.

For a quick fix I would propose to change the behaviour of MonitorFromWindow() from MONITOR_DEFAULTTONULL to one of the other options: MONITOR_DEFAULTTONEAREST, MONITOR_DEFAULTTOPRIMARY.

But I am still unsure if the overall approach works correctly for nested native windows in general and if it might be a better fix to make sure all child windows get re-attached to a VSyncThread when their parent component’s monitor has changed. For example move a hosted plugin in the AudioPluginHost Demo between two screens on Windows and you can see in the debugger that the associated monitor will never get updated.


I can see that when using the AudioPluginHost, an embedded window will still receive a WM_NCPAINT message. So adding a VSync registration there seems to solve this issue, at least for the AudioPluginHost.

I don’t know how robust that is though, and what happens with more exotic windowing situations. Can you check if the attached patch solves the problem in your case?

vblank.patch (794 Bytes)

Thanks for the quick reply and the patch. Yes, that solves the problem for JUCE 7 plugins in our host application :slight_smile:

@attila Would you consider this as a fix which could be added to JUCE?

A fix is now out on develop.

However, the provided patch wasn’t sufficient for keeping track of the current monitor, so a more heavy weight, timer based solution was posted.

Awesome, thanks! :slight_smile: