How does P2D make lines look so smooth and how can this be replicated in the default renderer?

When I set the renderer to P2D, the lines seem to be a lot more smooth compared to the regular JAVA2D renderer. Is there a reason for this and can it be done with other renderers?


Same code, but the quality for the P2D is significantly higher

void setup() {
  size(800, 800); 
  smooth(8);
   textSize(60);
}

PShape l;

float f(float x) {
  return 200*sin((x+3*frameCount/2000)/23f);
}

void draw() {
  
  background(0);
  translate(width/2,height/2);
  l = createShape();

  l.beginShape(LINES);
  l.stroke(0,255,0);
  l.strokeWeight(5.5);
  for (float i = -500; i < 500; i+=0.2) {
    l.vertex(i, f(i));
  }

  l.endShape();
  shape(l);

}

I’ve noticed this problem with the JAVA2D renderer particularly when there’s overlapping line segments.

To get a much smoother result, increment the curve samples (i) by 1 rather than 0.2 so it does not produce tightly packed/overlapping segments.

void draw() {

  background(0);
  translate(width/2, height/2);
  l = createShape();

  l.beginShape();
  l.stroke(0, 255, 0);
  l.noFill();
  l.strokeWeight(5.5);
  for (float i = -500; i < 500; i+=1) {
    l.vertex(i, f(i));
  }

  l.endShape();
  shape(l);
}

…or use the JavaFX renderer FX2D (which is faster too).

3 Likes

To which? Be careful in measurement of FX2D - it uses asynchronous rendering.

1 Like

Thank you for replying. Would it be possible to use hint(DISABLE_ASYNC_SAVEFRAME) to force it to be synchronous?

That hint isn’t controlling this - it’s to do with saving images. There’s no way to control it, it’s just how JavaFX itself works. With P2D and P3D the thread that calls draw() is the thread writing to the screen. In JavaFX, the animation thread buffers instructions that get rendered later by a hidden rendering thread. If the rendering thread can’t keep up, it will throw stuff away.

See eg. jfx/GraphicsContext.java at master · openjdk/jfx · GitHub and jfx/GraphicsContext.java at master · openjdk/jfx · GitHub

EDIT - Discourse really isn’t helpful when you link to two different lines on GitHub! :smile: