Resizing stuttering on OpenGL rendered UI

Hi guys, I’m using an OpenGL renderer to paint my components, but every time a resize happens the components kind of stutter and jump a few times before ending up in the right position (even for simple components like Label and TextButton). This is my code, and a video demonstrating the strange resizing behaviour.


#include "../JuceLibraryCode/JuceHeader.h"
#include "MainComponent.h"

class IntrojucerTestsApplication  : public JUCEApplication
{
public:
    IntrojucerTestsApplication() {}

    const String getApplicationName() override       { return ProjectInfo::projectName; }
    const String getApplicationVersion() override    { return ProjectInfo::versionString; }
    bool moreThanOneInstanceAllowed() override       { return true; }

    void initialise (const String& commandLine) override
    {
        mainWindow = new MainWindow (getApplicationName());
		mainWindow->setResizeLimits(300, 300, 100000, 100000);
		mainWindow->setResizable(true, false);
    }

    void shutdown() override
    {
        mainWindow = nullptr; // (deletes our window)
    }

    void systemRequestedQuit() override
    {
        quit();
    }

    void anotherInstanceStarted (const String& commandLine) override
    {
    }

    class MainWindow    : public DocumentWindow
    {
    public:
        MainWindow (String name)  : DocumentWindow (name,
                                                    Colours::lightgrey,
                                                    DocumentWindow::allButtons)
        {
            setUsingNativeTitleBar (true);
            setContentOwned (new MainContentComponent(), true);
            centreWithSize (getWidth(), getHeight());
            setVisible (true);
        }

        void closeButtonPressed() override
        {
            JUCEApplication::getInstance()->systemRequestedQuit();
        }

    private:
        JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (MainWindow)
    };

private:
    ScopedPointer<MainWindow> mainWindow;
};

START_JUCE_APPLICATION (IntrojucerTestsApplication)

#include "MainComponent.h"

MainContentComponent::MainContentComponent()
{
	label.setColour(Label::ColourIds::textColourId, Colours::white);
	label.setText("Label", juce::NotificationType::dontSendNotification);
	addAndMakeVisible(label);
	button.setButtonText("Button");
	addAndMakeVisible(button);
	setSize(300, 300);

#ifdef USE_GL
    juceContext.attachTo(*this);
#endif
}

MainContentComponent::~MainContentComponent()
{
#ifdef USE_GL
	juceContext.detach();
#endif
}

void MainContentComponent::paint (Graphics& g)
{
    g.fillAll (Colour (0xff001F36));
    g.setFont (Font (16.0f));
    g.setColour (Colours::white);
    g.drawText ("Hello World!", getLocalBounds(), Justification::centred, true);
}

void MainContentComponent::resized()
{
	label.setBounds(0, 0, 150, 50);
	button.setBounds(150, 0, 150, 50);
}

#ifndef MAINCOMPONENT_H_INCLUDED
#define MAINCOMPONENT_H_INCLUDED

//#define USE_GL
#include "../JuceLibraryCode/JuceHeader.h"

class MainContentComponent : public Component
{
public:
    MainContentComponent();
    ~MainContentComponent();

    void paint (Graphics&) override;
    void resized() override;

#ifdef USE_GL
	OpenGLContext juceContext;
#endif

private:
	TextButton button;
	Label label;
    JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (MainContentComponent)
};


#endif

Hmmm I can’t seem to re-produce this (tried on Windows 10 (both in a VM and a real machine) and Sierra). Which windows version is this? Do you have accelerated 3D graphics? Could this be a driver problem? Do you see the same stuttering in other (non-JUCE) OpenGL apps?

Hi thanks for the reply, I have some more information now. On OSX there seems to be no problem, nor on Windows 8 (not sure because I coudn’t test all cases). On Windows 10 version 1607 the problem was visible with desktop scaling turned on (no retina). On another Windows 10 computer with a retina screen (version 1607 aswell), we see the problem without desktop scaling aswell. So I geuss it has something to do with latest Windows 10 desktop scaling. The stutter does however not become bigger when the scaling is turned up. Maybe its a rounding error somewhere?

Hmmm ok I’ll try to re-produce this again with various scaling settings…

OK, I can re-produce this now when scaling is enabled on Windows 10. It’s very difficult to debug as it doesn’t occur if I add breakpoints to the window resize code. What I can see so far is that the window shortly resizes to a larger window size and then immediately re-size again to a smaller size. As the opengl runs on another thread, it will lag behind a bit and render the components with an incorrect view port causing the graphics to be scaled and translated incorrectly. Not sure exactly why the window is resized two times yet though…

Hi Fabian, is there any news on the OpenGL component rendering stutters? /bump

No sorry no news on this yet.

This issue is quite annoying, and is observable in latest JUCE demo from develop.

Has anyone found any workarounds other than using software renderer?

We also still haven’t found a workaround and it ain’t pretty…

Any update on this issue?

@ed95 is currently in the deep end of Windows/OpenGL scaling code which is fixing most of these issues and similar. Still a few nasty bugs to go though so I’m not going to predict when we push this to develop. Sorry.

Hmm, I have same issue with latest Juce ver. On any iOS (my current 14.6). It looks like the OpenGL component changes position smoothly (via animation) and not instantly. I had such an effect when an animation duration of 200 ms was set in CALayer.