Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

clear() on framebuffer not working on Intel macs #6428

Closed
1 of 17 tasks
davepagurek opened this issue Sep 20, 2023 · 1 comment · Fixed by #6429
Closed
1 of 17 tasks

clear() on framebuffer not working on Intel macs #6428

davepagurek opened this issue Sep 20, 2023 · 1 comment · Fixed by #6429
Assignees

Comments

@davepagurek
Copy link
Contributor

Most appropriate sub-area of p5.js?

  • Accessibility
  • Color
  • Core/Environment/Rendering
  • Data
  • DOM
  • Events
  • Image
  • IO
  • Math
  • Typography
  • Utilities
  • WebGL
  • Build Process
  • Unit Testing
  • Internalization
  • Friendly Errors
  • Other (specify if possible)

p5.js version

1.7.0

Web browser and version

Chrome 116, Firefox 115

Operating System

MacOS 10.14.6

Steps to reproduce this

Steps:

  1. Turn off antialiasing
  2. Draw something to a framebuffer
  3. Draw the framebuffer to the main canvas
  4. Clear the framebuffer
  5. Draw it to the main canvas again

I expect the second draw to not draw anything, but it seems to draw the old content a second time. When antialiasing is turned on (or with antialiasing off, but on my newer M1 Macbook Pro), it looks like this:
expected

However, on my Intel mac, it looks like this:
broken

Snippet:

Live: https://editor.p5js.org/davepagurek/sketches/O_0u83OcQ

let componentFbo
let img

const components = [
  {
    draw: () => {
      imageMode(CENTER)
      image(img, 0, 0, 100, 100, 0, 0, img.width, img.height, CONTAIN)
    },
    position: [100, 100]
  },
  {
    draw: () => {},
    position: [-100, -100]
  }
]

function preload() {
  img = loadImage('escher.jpg')
}

function setup() {
  createCanvas(400, 400, WEBGL)
  setAttributes({ antialias: false })
  componentFbo = createFramebuffer()
}

function draw() {
  background('#88F')
  for (const component of components) {
    componentFbo.begin()
    clear()
    push()
    component.draw()
    pop()
    componentFbo.end()
    push()
    translate(...component.position)
    imageMode(CENTER)
    image(componentFbo, 0, 0)
    pop()
  }
}
@davepagurek davepagurek self-assigned this Sep 20, 2023
@davepagurek
Copy link
Contributor Author

Well, you're not going to like the fix for this...

If I clear with this (the current p5 clear implementation), it doesn't work:

drawingContext.clearColor(0,0,0,0)
drawingContext.clearDepth(1)
drawingContext.clear(drawingContext.COLOR_BUFFER_BIT|drawingContext.DEPTH_BUFFER_BIT)

If I clear with THIS, where the alpha is not quite 0 but still small enough to round down to 0, it works:

drawingContext.clearColor(0,0,0,1e-10)
drawingContext.clearDepth(1)
drawingContext.clear(drawingContext.COLOR_BUFFER_BIT|drawingContext.DEPTH_BUFFER_BIT)

It looks like the drivers on these Macs check for 0,0,0,0 exactly and special case it with this buggy behavior.

It feels hacky, but it only needs to be applied when (1) a framebuffer is bound, (2) it's not antialiased, and (3) it's not using float colors (so we don't have to worry about the rounding down not happening.) This feels really hacky, but it does work...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant