True Displacement True or False

Hello!

There’s some discussion around about true Displacement so i wanted to share what i found out about it!

So, i was able to achieve clean true displacement on a UV Sphere with the following code:


displacement Displacer(
    output float Fact = 0
    ){
    P += (distance(Ng,P,I*0.1)*0.1)*noise("perlin",1.5*cos(P))*100;
    return;
}

Wow does this works?

1 - (distance(Ng,P,I*0.1)*0.1) - It fixes the area of the transformation so it doesn’t show the individual subdivided polygons that broke the whole thing up! Note that there is a side effect the entire mesh will move a little in space but i think that is a lesser evil.

  1. noise(“perlin”,1.5cos§)*100 - This is truly where the magic happens. You HAVE to put P in the mix for the displacement to work if you use P you can do anything thats the only rule. If you use N you’ll slice your mesh and if you mix N with P you can get some sliced but interesting (and broken) results!

I’ve illustrated this same code with some screens bellow:


The UV Sphere and the displaced UV Sphere,


The same with a Cube mesh.

I used a subdivion modifier on both to a power of 3.

I hope i helped a bit!

Also if you want, you can apply a texture but i’m still working on it since it’s a bit displaced!


If you turn Dicing to 0.01 you will get a cleaner result!


displacement ODisp(
    float DisplaceTexture = 1,
    output float D = 0
){
    D = D + 0.0001;
    P += (distance(Ng,P,I*0.1)*0.1)*P*DisplaceTexture;
    return;
}

I’m also able to add an image texture to displace but i’m still working on some placement details:


displacement Displacer(
    output float Fact = 0
    ){
    color IM = texture("alienpipes.jpg",P[0]*0.9+P[2]*u*0.9,P[1]*0.9+P[2]*v*0.9,"swrap","periodic","twrap","mirror","interp","cubic");
    P += (distance(Ng,P,I*0.1)*0.1)*P*(IM[0]-IM[1]-IM[2])*0.3;
    return;
}

So, that’s really all i know about the true displacement thingy!

interesting, but it is still not working consistently: At some point I do get displacement (but not with the release version just with the daily built) but as soon as I toggle the object to/from edit mode the displacement is gone and no matter what I do I can’t get it back …

Also, recompiling the shader does not have any effect (unless done directly after reloading the .blend) and a shader with input parameters isn’t reevaluated when those parameters change …

stlll needs some work I guess :slight_smile:

AH! Yes, there’s a trick to it, you have to rechoose true displacement again from the menu for it to apply any change (Or to get in and out rendered view). Also i’ve tested it with some few different blender releases and had no major issues. I’ve noticed that sometimes displacement gets ignored in some versions if you don’t assign a value to your output variable ( D = D + 0.0001;).

After some work i’m getting near into place a 2D texture for true displacement:


displacement ODisp(
    output float D = 0
){
    D = D + 0.0001;
    vector Loc;
    getattribute("object:location",Loc);
    int Res[2];
    gettextureinfo("circuit.jpg","resolution",Res);
    float Pz = distance(P[2]*0.3,P[2]*0.3/Res[1]);
    float Px = distance(P[0]*0.3,P[0]*0.3/Res[0]);
    float Py = distance(P[1]*0.3,P[1]*0.3/Res[1]);
    float DispText = texture("circuit.jpg",distance(Px,Pz),distance(Py,Pz),"blur",0.025,"wrap","mirror");
    P += (distance(Ng,P,I*0.1)*0.1)*P*(DispText);
    return;
}