reduceClipRegion and fillRectList results in broken drawing on macOS

If I use the combination of bool Graphics::reduceClipRegion (const Path& path, const AffineTransform& transform) and void Graphics::fillRectList (const RectangleList<float>& rectangles) const then on macOS the fillRectList scribbles over a part of the image that has already been drawn.

It should look like this:

But it looks like this:

If I set setBufferedToImage ( true ); then it draws correctly, if I set it to false then I get the drawing glitch. It also draws correctly if I use reduceClipRegion with a rect.

This is on macOS Ventura 13.2.1. You may need to resize the window to see the glitch, often it paints correctly the first time.

Code: juce_bugs/Gradient/Source at master · FigBug/juce_bugs · GitHub

To be honest, I have no idea what’s going wrong here. My best guess is that this is a bug in macOS; I tried out the same project on macOS 10.13, 10.14, 12, and 13. It worked on 10.13 with no changes, but was broken on the other platforms. It also worked if I manually disabled layer backed views, so this might be a bug in the layer-backed-drawing.

After experimenting a bit, the attached patch seems to resolve the issue, at least in the example project. Would you mind trying it out and seeing whether it works for you?

gradients.patch (13.0 KB)

That makes everything go crazy:

That’s odd, I’m not sure why that’s happening, although I did spot some SVGs in the DemoRunner that weren’t rendering correctly with the patch above. That issue seems to be fixed by this patch. Could you try this out too?

gradients.patch (9.1 KB)

1 Like

That seems to have fixed it

2 Likes

The previous fix was merged to develop here:

Unfortunately, this change had some unintended consequences - on an M1 machine running macOS 13.4, the borders of dialog windows in the Projucer were not always rendered correctly.

That new issue seems to be fixed by this change:

1 Like

Just FYI.

I believe we found a bug that has the same underlying problem and is fixed in develop now.

We had some code that had ColourGradients with zero areas (x1=x2 and y1=y2), it worked fine, and when we updated intel computers to macOS 13.4, it pained all the area with the initial gradient color.

Code to reproduce would be in a paint method:

    // ======= code that fails ==========
    auto bounds = getBounds();
    
    auto gradientColour = juce::Colours::blue;
    auto transparent = gradientColour.withAlpha(0.0f);

    auto gradientHeight = 0.0f; //  gradientHeight > 0 works well
    
    auto gradient = juce::ColourGradient(gradientColour, 0.0f, bounds.getY(),
                                         transparent,    0.0f, bounds.getY() + gradientHeight,
                                         false);
        
    g.setGradientFill(gradient);
    g.fillRect(bounds);
    
    // ==================================

If we use a non-zero area gradient, works perfectly.
If we use a zero area gradient, in previous macOS versions works perfectly.
If we use a zero area gradient, in macOS 13.4 with JUCE 7.0.5 it doesn’t work (paints all the area with gradientColour)
If we use a zero area greadient, in macOS 13.4 with JUCE develop branch, works perfectly.

Hope it helps.

Have a nice day!

Sorry to open this as it seems the fix has a regression?

Ever since this commit it makes some drawing worsen.
Here is an example:

Good:
image

Bad:
image

To reproduce, here is a simple SVG you can load up into Projucer preview.
(I’ve add a black rect to make the regression easier to see).

<svg id="juce_bug" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 10.7 28 13">
  <defs>
    <linearGradient id="linear-gradient" x1="0.362" y1="0.532" x2="0.677" y2="0.531" gradientUnits="objectBoundingBox">
      <stop offset="0" stop-color="#fff"/>
      <stop offset="1" stop-color="gray" stop-opacity="0"/>
    </linearGradient>
  </defs>
  <rect id="Rectangle_2443" data-name="Rectangle 2443" y="10.7" width="28" height="13" fill="black"/>
  <path id="Path_4696" data-name="Path 4696" d="M240.334-90.312a5.98,5.98,0,0,1-4.236,1.751,6,6,0,0,1-6-6,6,6,0,0,1,6-6,5.979,5.979,0,0,1,4.2,1.72c.054.053,1.051,1.125,1.051,1.125h0a2.989,2.989,0,0,0,2.1.86h-.023a3,3,0,0,0,2.471-1.3l.554-.651a5.98,5.98,0,0,1,4.236-1.752,6,6,0,0,1,6,6,6,6,0,0,1-6,6,5.978,5.978,0,0,1-4.2-1.719c-.054-.054-1.051-1.125-1.051-1.125h0a2.985,2.985,0,0,0-2.1-.86h.023a2.994,2.994,0,0,0-2.471,1.3Z" transform="translate(-229.317 111.781)" stroke="#fff" stroke-miterlimit="10" stroke-width="0.5" fill="url(#linear-gradient)"/>
  <text id="R" transform="translate(16.5 12.455)" fill="#ff3131" font-size="7" font-family="Lato-Medium, Lato" font-weight="500" letter-spacing="0.01em"><tspan x="2.37" y="7">R</tspan></text>
  <text id="L" transform="translate(1.451 12.455)" fill="#1d1d1d" font-size="7" font-family="Lato-Medium, Lato" font-weight="500" letter-spacing="0.01em"><tspan x="2.774" y="7">L</tspan></text>
</svg>

3 Likes

I have noticed the regression too, it’s very apparent and annoying. Unfortunately it is still present in the 7.0.6 release:

3 Likes

We’ve reverted the original fix. Drawing should now appear the same as it did in early 7.0.5.

Having tested on Sonoma beta 5, the black rectangle glitch that was previously present has been fixed, so I’m pretty sure this is a macOS bug that is now fixed. Give that it’s a bug, there’s not much we can do to work around it in a robust way. Any attempt on our side will be guesswork, so it’s better for us to just implement things according to the docs.

If you’re seeing the black rectangle glitch when running on Ventura or earlier, there are a few things you can try:

  • Disable async drawing by passing the windowRequiresSynchronousCoreGraphicsRendering flag when creating windows.
  • Modify your drawing routine. It may be possible to avoid the black rectangles by reording graphics calls, or by adding extra redundant fillAll calls which are then overwritten later on.
4 Likes