# Depth of Field effect with a shader

**URL:** <https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265>\
**Category:** Processing.py\
**Created:** [May 22, 2018, 5:03pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265 "2018-05-22T17:03:20Z")\
**Posts on this page:** 12\
**Page:** 1

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [May 22, 2018, 5:03pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/1 "2018-05-22T17:03:20Z")

</div>

Hi all,

As some of you may already know I’m trying to make a Depth of Field effect in Python mode.  
I’ve recently stumbled onto [this thread](https://forum.processing.org/two/discussion/6515/working-dof-example-shared) where I could get hold of a Proscene [DOF demo sketch](https://github.com/remixlab/proscene.droid/tree/master/examples/Demos/DOF) based on the following shaders:

**depth.glsl**

```auto
uniform float maxDepth;

void main() {
  float depth = gl_FragCoord.z / gl_FragCoord.w;
  gl_FragColor = vec4(vec3(1.0 - depth/maxDepth), 1.0);
}

```

**dof.glsl**

```auto
uniform sampler2D texture;

varying vec4 vertexture;
varying vec4 vertTexCoord;

uniform sampler2D tDepth;
	    
uniform float maxBlur; // max blur amount
uniform float aperture; // aperture - bigger values for shallower depth of field

uniform float focus;
uniform float aspect;

void main() {
    vec2 vUv = vertTexCoord.st;
				    
    vec2 aspectcorrect = vec2( 1.0, aspect );
		
    vec4 depth1 = texture2D( tDepth, vUv );
    
    float factor = depth1.x - focus;
    
    vec2 dofblur = vec2 ( clamp( factor * aperture, -maxBlur, maxBlur ) );
    
    vec2 dofblur9 = dofblur * 0.9;
    vec2 dofblur7 = dofblur * 0.7;
    vec2 dofblur4 = dofblur * 0.4;
    
    vec4 col = vec4( 0.0 );
    
    col += texture2D( texture, vUv.xy );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, 0.4 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, 0.37 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, 0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, 0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.40, 0.0 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, -0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, -0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, -0.37 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, -0.4 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, 0.37 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, 0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, 0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.4, 0.0 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, -0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, -0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, -0.37 ) * aspectcorrect ) * dofblur );
    
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, 0.37 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, 0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, -0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, -0.37 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, 0.37 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, 0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, -0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, -0.37 ) * aspectcorrect ) * dofblur9 );
    
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, 0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.40, 0.0 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, -0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, -0.4 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, 0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.4, 0.0 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, -0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, 0.4 ) * aspectcorrect ) * dofblur7 );
    
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, 0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.4, 0.0 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, -0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, -0.4 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, 0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.4, 0.0 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, -0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, 0.4 ) * aspectcorrect ) * dofblur4 );
    
    gl_FragColor = col / 41.0;
    gl_FragColor.a = 1.0;
}

```

What I’d like is to be able to use those shaders using the PeasyCam library instead of the Proscene dependency.

In the sketch below I’m testing the shaders on a point cloud but can’t seem to make the DoF effect work.  
I’m pretty sure I have to draw the points into an off-screen graphics buffer but can’t figure out which one and why. I got lost in the process…

Would appreciate your help.

PS: this new forum looks good !

```auto
add_library('peasycam')
liste = []

def setup():
    global depthShader, depthPGraphics, dofPGraphics, dofShader, cam, buf
    size(900, 900, P3D)
        
    cam = PeasyCam(this, 900)
    cam.setMaximumDistance(width)
    
    for e in range(100):
        liste.append(PVector(random(width), random(height), random(width)))
        
    depthShader = loadShader("depth.glsl")
    dofShader = loadShader("dof.glsl")
    
    depthShader.set("maxDepth", cam.getDistance())
    dofShader.set("aspect", width / float(height))
    dofShader.set("maxBlur", 0.016)
    dofShader.set("aperture", 0.02)
    
    dofPGraphics = createGraphics(width, height, P3D)
    depthPGraphics = createGraphics(width, height, P3D)
    dofPGraphics.shader(dofShader)
    depthPGraphics.shader(depthShader)
    
    frameRate(1000)
    
def draw():
    background(255)
    shader(depthShader)

    stroke(0)
    strokeWeight(10)
    for e in liste:
        point(e.x-width/2, e.y-height/2, e.z-height/2)

    dofShader.set("focus", map(mouseX, 0, width, -0.5, 1.5))
    dofShader.set("tDepth", depthPGraphics)    
    filter(dofShader)

```

---

<div class="post-metadata">

**Author:** ![GoToLoop](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/gotoloop/32/86_2.png) [@GoToLoop](https://discourse.processing.org/u/GoToLoop)\
**Post date:** [May 22, 2018, 6:10pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/2 "2018-05-22T18:10:07Z")

</div>

Your old forum topic-related post: 😉

- [https://Forum.Processing.org/two/discussion/27905/converting-java-code-to-python](https://Forum.Processing.org/two/discussion/27905/converting-java-code-to-python)

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [May 26, 2018, 12:07pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/6 "2018-05-26T12:07:35Z")

</div>

I think I’m getting closer…  
I’m drawing the points on the `scene` PGraphics and then passing it through 2 other PGraphics (`canvas` and `buf`). In theory it should work but I’m still stuck with the PeasyCam part at the very end of the script.

If I write:

- `cam.getState().apply(canvas)` I get a DoF effect BUT on a 2D canvas
- `cam.getState().apply(scene)` I get a 3D canvas BUT without a DoF effect

Any help would be really appreciated.

```auto
add_library('peasycam')
liste = []

def setup():
    global depthShader, dofShader, cam, canvas, buf, scene
    size(900, 900, P3D)
        
    cam = PeasyCam(this, 900)
    cam.setMaximumDistance(width)
    
    for e in range(100):
        liste.append(PVector(random(width), random(height), random(width)))
        
    depthShader = loadShader("depth.glsl")
    dofShader = loadShader("dof.glsl")
    
    depthShader.set("maxDepth", cam.getDistance())
    dofShader.set("aspect", width / float(height))
    dofShader.set("maxBlur", 0.015)
    dofShader.set("aperture", 0.02)
    
    canvas = createGraphics(width, height, P3D)
    canvas.shader(depthShader)
    buf = createGraphics(width, height, P3D)
    buf.shader(dofShader)
    
    scene = createGraphics(width, height, P3D)
    
    frameRate(1000)

def draw():
        
    scene.beginDraw()
    scene.background(255)
    scene.stroke(0)
    scene.strokeWeight(10)
    for e in liste:
        scene.point(e.x-width/2, e.y-height/2, e.z-height/2)
    scene.endDraw()

    canvas.beginDraw()
    canvas.image(scene, 0, 0)
    canvas.endDraw()
    
    buf.beginDraw()
    dofShader.set("focus", map(mouseX, 0, width, -0.5, 1.5))
    dofShader.set("tDepth", canvas)
    buf.image(scene, 0, 0)
    buf.endDraw()
    
    cam.beginHUD()
    image(buf, 0, 0)
    cam.endHUD()

    cam.getState().apply(scene)

```

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [May 28, 2018, 4:28pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/7 "2018-05-28T16:28:24Z")

</div>

I’ve been trying to implement the [example sketch](https://github.com/hamoid/P5PostProcessing/tree/master/Dof) provided by @hamoid where the Proscene dependency is no longer needed but I still can’t figure out why the amount of blur stays the same for each and every object drawn in the scene, no matter how far they are from the camera (PeasyCam).

I suspect the `depthShader` not to be correcly working on the `canvas` PGraphics buffer but can’t say for sure.

Basically, what I’m doing here:

- I’m drawing cubes on the `scene` PGraphics buffer.
- Then I draw the same thing on the `canvas` PGraphics buffer where the `depthShader` shader is applied.
- Finally I display the first `scene` through a third graphic buffer named `buf` where the `dofShader` is applied. (the `tDepth` setting of this shader is based on the second canvas)

Once again I would really appreciate any help.

Thank you

```auto
add_library('peasycam')
liste = []

def setup():
    global depthShader, dofShader, cam, canvas, buf, scene, shp
    size(900, 900, P3D)
    
    cam = PeasyCam(this, 900)
    cam.setMaximumDistance(width)
        
    depthShader, dofShader = loadShader("depth.glsl"), loadShader("dof.glsl")
    dofShader.set("aspect", width / float(height))

    
    canvas, buf, scene = createGraphics(width, height, P3D), createGraphics(width, height, P3D), createGraphics(width, height, P3D)
    canvas.smooth(8)
    canvas.shader(depthShader)
    
    for e in range(100): liste.append(PVector(random(width), random(height), random(width))) 
    
    frameRate(1000)
    
    shp = createShape(BOX, 60)
    shp.setStroke(color(120))
        

def draw():
        
    scene.beginDraw()
    scene.background(255)
    for i in range(10):
        scene.pushMatrix()
        scene.translate((i*7763)%width, (i*777)%height, 30*i*sin(i)-500)
        scene.shape(shp)
        scene.popMatrix()
    scene.endDraw()

    canvas.beginDraw()
    canvas.background(255)
    for i in range(10):
        canvas.pushMatrix()
        canvas.translate((i*7763)%width, (i*777)%height, 30*i*sin(i)-500)
        canvas.shape(shp)
        canvas.popMatrix()
    canvas.endDraw()

    depthShader.set("maxDepth", cam.getDistance())

    buf.beginDraw()
    dofShader.set("tDepth", canvas)
    dofShader.set("maxBlur", 0.015)
    dofShader.set("focus", map(mouseX, 0, width, float(-0.5), float(1.5)))
    dofShader.set("aperture", float(0.02))
    buf.shader(dofShader)
    
    buf.image(scene, 0, 0)
    buf.endDraw()

    cam.beginHUD()
    image(buf, 0, 0)
    cam.endHUD()
    #cam.getState().apply(scene)

```

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [May 28, 2018, 11:06pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/8 "2018-05-28T23:06:42Z")

</div>

Depth of Field effect with PeasyCam, **working** 😃 😭 example sketch:

```auto
add_library('peasycam')
liste = []
colors = [[0,189,202], [251,183,0], [255,17,79], [252,128,35], [0,108,254]]

def setup():
    global depthShader, dofShader, cam, canvas, buf, scene, pnt
    size(900, 900, P3D)
    
    cam = PeasyCam(this, 900)
    cam.setMaximumDistance(width)
        
    depthShader, dofShader = loadShader("depth.glsl"), loadShader("dof.glsl")
    depthShader.set("maxDepth", cam.getDistance()*2)
    dofShader.set("aspect", width / float(height))
    dofShader.set("maxBlur", 0.025)
    dofShader.set("aperture", 0.05)
    
    canvas, buf, scene = createGraphics(width, height, P3D), createGraphics(width, height, P3D), createGraphics(width, height, P3D)
    canvas.shader(depthShader) 
    buf.shader(dofShader)
    buf.smooth(8)
    scene.smooth(8)

    for e in range(300): liste.append(PVector(random(width), random(height), random(width))) 

    pnt = createShape(SPHERE, 12)
    pnt.setStroke(False)
    
    frameRate(1000)

def draw():
    scene.beginDraw()
    scene.background(0)
    for i in range(len(liste)):
        scene.pushMatrix()
        scene.translate(liste[i].x-width/2, liste[i].y-width/2, liste[i].z-width/2)
        scene.shape(pnt)
        pnt.setFill(color(colors[i%4][0], colors[i%4][1], colors[i%4][2]))
        scene.popMatrix()
    scene.endDraw()

    canvas.beginDraw()
    canvas.background(0)
    for i in range(len(liste)):
        canvas.pushMatrix()
        canvas.translate(liste[i].x-width/2, liste[i].y-width/2, liste[i].z-width/2)
        canvas.shape(pnt)
        canvas.popMatrix()
    canvas.endDraw()

    buf.beginDraw()
    dofShader.set("tDepth", canvas)
    dofShader.set("focus", map(mouseX, 0, width, .3, 1))
    buf.image(scene, 0, 0)
    buf.endDraw()

    cam.beginHUD()
    image(buf, 0, 0)
    cam.getState().apply(canvas)
    cam.getState().apply(scene)
    cam.endHUD()
    
    cam.rotateY(.002)

```

If someone knows how get a DoF effect with points instead of sphere shapes, please let me know.

---

<div class="post-metadata">

**Author:** ![jeremydouglass](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/jeremydouglass/32/20_2.png) [@jeremydouglass](https://discourse.processing.org/u/jeremydouglass)\
**Post date:** [May 29, 2018, 3:42pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/9 "2018-05-29T15:42:44Z")

</div>

Congratulations! Is that still using the same `depth.glsl` and `dof.glsl` that you posted above, or have they changed?

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [May 29, 2018, 9:09pm UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/10 "2018-05-29T21:09:34Z")

</div>

@jeremydouglass Thank you. Yes, the sketch is using the shaders posted above.

[https://media.giphy.com/media/9VnTlgGU9ROiomuDML/giphy.gif(image larger than 4096KB)](https://media.giphy.com/media/9VnTlgGU9ROiomuDML/giphy.gif)

For clarity let me re-post the whole thing with an updated script.

**sketch.pyde**

```auto
add_library('peasycam')
colors, liste = [[0,189,202], [251,183,0], [255,17,79], [252,128,35], [0,108,254]], []

def setup():
    global depthShader, dofShader, cam, buf1, buf2, buf3, pnt
    size(900, 900, P3D)
    frameRate(1000)

    cam = PeasyCam(this, 900)
    cam.setMaximumDistance(width)
    pnt = createShape(BOX, 30)
    pnt.setStroke(False)
        
    depthShader, dofShader = loadShader("depth.glsl"), loadShader("dof.glsl")
    depthShader.set("maxDepth", cam.getDistance()*2)
    dofShader.set("aspect", width / float(height)), dofShader.set("maxBlur", 0.02), dofShader.set("aperture", 0.06)
    
    buf1, buf2, buf3 = [createGraphics(width, height, P3D) for e in range(3)]
    buf1.smooth(8), buf2.shader(depthShader), buf3.shader(dofShader)

    for e in range(300): liste.append(PVector(random(width), random(height), random(width))) 
    
def drawScene(pg):
    pg.beginDraw()
    pg.background(0)
    for i in range(len(liste)):
        pg.pushMatrix()
        pg.translate(liste[i].x-width/2, liste[i].y-width/2, liste[i].z-width/2)
        pg.shape(pnt)
        pnt.setFill(color(colors[i%5][0], colors[i%5][1], colors[i%5][2]))
        pg.popMatrix()
    pg.endDraw()
    cam.getState().apply(pg)

def draw():
    drawScene(buf1), drawScene(buf2)

    buf3.beginDraw()
    dofShader.set("tDepth", buf2)
    dofShader.set("focus", map(mouseX, 0, width, .3, 1))
    buf3.image(buf1, 0, 0)
    buf3.endDraw()
    
    cam.beginHUD()
    image(buf3, 0, 0)
    cam.endHUD()

```

**depth.glsl**

```auto
uniform float maxDepth;

void main() {
  float depth = gl_FragCoord.z / gl_FragCoord.w;
  gl_FragColor = vec4(vec3(1.0 - depth/maxDepth), 1.0);
}

```

**dof.glsl**

```auto
uniform sampler2D texture;

varying vec4 vertexture;
varying vec4 vertTexCoord;

uniform sampler2D tDepth;
	    
uniform float maxBlur; // max blur amount
uniform float aperture; // aperture - bigger values for shallower depth of field

uniform float focus;
uniform float aspect;

void main() {
    vec2 vUv = vertTexCoord.st;
				    
    vec2 aspectcorrect = vec2( 1.0, aspect );
		
    vec4 depth1 = texture2D( tDepth, vUv );
    
    float factor = depth1.x - focus;
    
    vec2 dofblur = vec2 ( clamp( factor * aperture, -maxBlur, maxBlur ) );
    
    vec2 dofblur9 = dofblur * 0.9;
    vec2 dofblur7 = dofblur * 0.7;
    vec2 dofblur4 = dofblur * 0.4;
    
    vec4 col = vec4( 0.0 );
    
    col += texture2D( texture, vUv.xy );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, 0.4 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, 0.37 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, 0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, 0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.40, 0.0 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, -0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, -0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, -0.37 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, -0.4 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, 0.37 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, 0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, 0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.4, 0.0 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, -0.15 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, -0.29 ) * aspectcorrect ) * dofblur );
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, -0.37 ) * aspectcorrect ) * dofblur );
    
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, 0.37 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, 0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, -0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, -0.37 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.15, 0.37 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.37, 0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.37, -0.15 ) * aspectcorrect ) * dofblur9 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.15, -0.37 ) * aspectcorrect ) * dofblur9 );
    
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, 0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.40, 0.0 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, -0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, -0.4 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, 0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.4, 0.0 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, -0.29 ) * aspectcorrect ) * dofblur7 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, 0.4 ) * aspectcorrect ) * dofblur7 );
    
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, 0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.4, 0.0 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.29, -0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, -0.4 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, 0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.4, 0.0 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( -0.29, -0.29 ) * aspectcorrect ) * dofblur4 );
    col += texture2D( texture, vUv.xy + ( vec2( 0.0, 0.4 ) * aspectcorrect ) * dofblur4 );
    
    gl_FragColor = col / 41.0;
    gl_FragColor.a = 1.0;
}

```

I still have one problem though: I’d like to draw points instead of spheres but when I do so (`createShape(POINT, x, y, z`) the DoF doesn’t work anymore. Why is that ?

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [May 30, 2018, 10:28am UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/11 "2018-05-30T10:28:30Z")

</div>

Sorry to be persistent but I really would like to solve the one remaining issue I mentionned in my previous comments.

**Goal** : I would like to display thousands of points on a 3D canvas where the Depth of Field effect above is applied.

**Problem** : For some reason the sketch I posted works with every primitives except `POINT` and `LINE`. I could certainly replace points by spheres, but as I just mentionned I’m trying to display _thousands_ of points and drawing spheres instead would be too computer-intensive.

More specifically: when drawing points (`pnt = createShape(POINT, 0, 0, 0)` instead of `pnt = createShape(SPHERE, 4)`) on line 11:

- The depth of field doesn’t work anymore (distance from camera not taken into account ?)
- Only pink, yellow and orange points seem to be reacting to the change of focus (when moving the mouse). Dark blue and light blue points stay blurry

 ![](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/1X/f65b232617d8655adda3351128a9f7b6e6d0b168.png)  
 ![](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/1X/3f61f19d0419dbec60b08b933127adefe84611b2.png)

For comparison, the same sketch displaying spheres:

 ![](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/1X/c4a7d4130512fdd8adf80dff0963828fc375a1e7.png)

---

<div class="post-metadata">

**Author:** ![WakeMeAtThree](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/wakemeatthree/32/38_2.png) [@WakeMeAtThree](https://discourse.processing.org/u/WakeMeAtThree)\
**Post date:** [June 2, 2018, 7:38am UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/12 "2018-06-02T07:38:43Z")

</div>

> [@solub](#):
>
> **Problem** : For some reason the sketch I posted works with every primitives except `POINT` and `LINE` . I could certainly replace points by spheres, but as I just mentionned I’m trying to display _thousands_ of points and drawing spheres instead would be too computer-intensive.

`POINT` and `LINE` shaders behave differently than `COLOR` shaders. [Check out the Processing Shaders tutorial](https://processing.org/tutorials/pshader/) on how to do the math for the projection of `POINTS`

> # 10. Point and line shaders
> 
> The point and line shaders are only used by the P3D renderer in order to draw stroke geometry. The reason is that the stroke geometry is always screen-facing in 3D, so it needs a different projection calculation in the vertex stage. In P2D, all the geometry is contained in the same plane, so there is no need of special handling for stroke lines and points (everything is just rendered as triangles with an orthographic projection).

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [June 2, 2018, 11:13am UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/13 "2018-06-02T11:13:35Z")

</div>

Thanks @WakeMeAtThree, just figured this out yesterday. I’ll try to find some time later next week to make that shader work. Maybe I’ll make some changes in the blur computation as well (I find the Gaussian blur softer to the eye).

Btw I like your work on morphing, very cool stuff.

---

<div class="post-metadata">

**Author:** ![solub](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/solub/32/333_2.png) [@solub](https://discourse.processing.org/u/solub)\
**Post date:** [June 5, 2018, 10:40am UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/14 "2018-06-05T10:40:25Z")

</div>

I have tweaked the point shader from the shaders tutorial to take the depth information into acount and implemented it in the script I posted previsoulsy.

At first glance, the sketch seems to work:

 ![](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/1X/7871c88f56db332fe97a33110a3790a0361ecd05.png)

But I’m still having a problem with colors.  
The Depth of Field works with white / reddish / yellowish colors but not with bluish / greenish colors:

 ![](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/1X/0d91ffa787ea5800bfeccde063059f5abfc36931.jpg)

Do you know what could be missing in the following point shaders ?

**pointfrag.glsl**

```auto
#ifdef GL_ES
precision mediump float;
precision mediump int;
#endif

varying vec4 vertColor;
uniform float maxDepth;
 
void main() {

  float depth = gl_FragCoord.z / gl_FragCoord.w;
  gl_FragColor = vec4(vec3(vertColor - depth/maxDepth), 1) ;

}

```

**pointvert.glsl**

```auto
uniform mat4 projection;
uniform mat4 modelview;

attribute vec4 position;
attribute vec4 color;
attribute vec2 offset;

varying vec4 vertColor;
varying vec4 vertTexCoord;

void main() {
  vec4 pos = modelview * position;
  vec4 clip = projection * pos;

  gl_Position = clip + projection * vec4(offset, 0, 0);

  vertColor = color;
}

```

Overall I’m not really satisfied with that DOF shader: I don’t like the halo seen around the primitives and the points tend to pixelate:

 ![](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/1X/85df29ce1c9bae83cbb5ed6e42164e950a05dcb8.jpg)

**Example sketch** (Python mode + PeasyCam library needed)

```auto
add_library('peasycam')

def setup():
    global pointShader, cam, pg, depthShader, dofShader, buf1, buf2, buf3
    size(900, 900, P3D)
    frameRate(1000)
    smooth(8)
    
    cam = PeasyCam(this, 500)
    cam.setMaximumDistance(width)
    perspective(60 * DEG_TO_RAD, width/float(height), 2, 6000)
    
    pointShader = loadShader("pointfrag.glsl", "pointvert.glsl")
    pointShader.set("maxDepth", cam.getDistance()*3)
    
    depthShader, dofShader = loadShader("depth.glsl"), loadShader("dof.glsl")
    dofShader.set("aspect", width / float(height)), dofShader.set("maxBlur", 0.015), dofShader.set("aperture", 0.06)
    
    buf1, buf2, buf3 = [createGraphics(width, height, P3D) for e in range(3)]
    buf2.shader(depthShader), buf3.shader(dofShader)

    pg = createShape()
    pg.beginShape(POINTS)
    pg.strokeWeight(5)
    pg.stroke(255)
    pg.translate(-width/2, -width/2, -width/2)    
    for e in range(5000):
        pg.vertex(random(width), random(width), random(width))
    pg.endShape()
    
def drawScene(buf):
    buf.beginDraw()
    buf.shader(pointShader, POINTS)
    buf.background(0)
    buf.shape(pg,0,0)
    buf.endDraw()
    cam.getState().apply(buf)
    
def draw():
    drawScene(buf1)
    drawScene(buf2)
            
    buf3.beginDraw()
    dofShader.set("tDepth", buf2)
    dofShader.set("focus", map(mouseX, 0, width, .3, 1))
    buf3.image(buf1, 0, 0)
    buf3.endDraw()
    
    cam.beginHUD()
    image(buf3, 0, 0)
    cam.endHUD()
    cam.rotateY(.0002)
    cam.rotateX(.0001)

```

---

<div class="post-metadata">

**Author:** ![micuat](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/micuat/32/19407_2.png) [@micuat](https://discourse.processing.org/u/micuat)\
**Post date:** [November 26, 2018, 9:02am UTC](https://discourse.processing.org/t/depth-of-field-effect-with-a-shader/265/15 "2018-11-26T09:02:16Z")

</div>

I found that adding `minDepth` can make better effect. This case you should keep `focus` parameter to 0.5 and move `minDepth` and `maxDepth` instead.

```auto
varying vec4 vertColor;
uniform float minDepth;
uniform float maxDepth;

void main() {
  float depth = gl_FragCoord.z / gl_FragCoord.w;
  float d = 1.0 - (depth-minDepth)/(maxDepth-minDepth);
  d = max(0.0, min(1.0, d));
  gl_FragColor = vec4(vec3(d), 1.0);
}

```
