Screen Space Displacement Mapping (No Tesselation) - Progress

This was not my issue, so I can’t speak for the user that posted it. I had assumed that user that posted that comment had contacted you. But if not I was just wanting to be sure all would be okay.

Little over my deadline but hopefully by tomorrow it should be out, so here is another video of current state. Really excited to play with this myself). specs: win10 1920x1080 gtx970

6 Likes

Amazing work!

Do you think that combining this tech with terrain height map texture streaming (via Granite or Amplify Texture), it is possible to do insane terrain view distances?

1 Like

@Elecman , Thanks! For sure, all you need is your mesh and a shader that has the look you want (or use included), as long as that shader draw can draw to the 4 MRT’s on the mapping layer of the mapping camera and the rest is taken care of. So your meshes are not draw main camera directly.

Meshes you do not want to use displacement can just be like normal, but I am not sure how one would mix shadows on different layers. but non displaced meshes can be draw in the meshes layer too, just set shader displacement to 0.0. I will make sure I Identify what would need to happen when moding your own shaders.

1 Like

If anyone is interested in a playable demo you can grab it here…

http://oddityinteractive.com/unity/oi/demo/SSDM_Demo.zip

it is very basic demo - the hallway is all instancing and the balls are instancing but the main square with the dragons is not instancing. I could not currently get pointlights to work well with instancing so until I figure that out only directional lights for instances. The standard meshes receive direction and up to 4 point lights. there is no AA or post effects in this demo.

I will be uploading package and project tonight so will post when available.

First release will not have VR as will have to be in a later release due to some issues I will have to work around and I will discuss here and video as I progress (of course will be free updates over the life of product).

Hope you find it interesting.

2 Likes

Just Launched, so if want to try this I added link at first post!

Thanks for the interest!

Will it soon arrive at the asset store?

@ChezDoodles , no, I am self publishing as this something I want to learn about. Same service and free upgrades as they happen. Thanks for the interest!

Just did some tests to see how deep I could go with a single quad and height map and seems about 1m. This is an extreme test, as edges are pure 90 degree angles so specularity would be incorrect there but the results still took me by surprise and good with around 10m viewing range at 1920x1080. I think this weekend I might have a shot at building some sci-fi assets to include as a free addon with this and try my hand at a much better demo which is more than just functional. Nice to feel inspired to model again as it has been a while and I am sure there is more to discover with this method. I am intrigued anyway)).

Edit: oh and thanks for the first few sales!

Hello,
Congratulations on the release :slight_smile:
I had quite a few questions:) I hope you can answer.

-Does you shaders support Precomputed GI (Enlighten)?
-Do they have self-shadowing? Can you add Directional lightmap rotation to your demo?
-Can we use Deferred with Linear color space with your shader?
-Do they support transparency?
-Do you have plans to add material layering (two sets of materials painted on a surface)?
-Any tests made with Post Processing Stack V2?
-Which platforms are supported?

Thanks

1 Like

@gurayg , Hi and thanks very much!

- I will have to look into this first one, but currently I do not believe this will utilize this feature. I do not see it to be a problem to add to the shader but light maps and such have not been included to contribute to this first release. I will look into adding this, but the displacement mesh happens runtime and will not contribute to the map.
**-**Yes, receiving shadowing(can be turned off) and casting (but not from the displaced mesh). Only directional light shadows are received. Yes, I will add rotation of the lighting to the demo and upload tomorrow, I had not thought about that).
- Yes, you can set the main camera to deferred, only the displacement camera needs forward base and Yes to linear color (seemed fine selecting and using from player settings)…
**-**Yes, material layering is a shader I want to do next, because I want to blend dynamic textures with the original height-maps, such as water ripple effects and FFT ocean type things etc…
**-**I did a test with post processing from the Asset Store but not V2 yet, however it will be same results I believe. Because the final mesh is generated with DrawProcedural only screen space effects will work with the mesh so FXAA, Bloom, Color correction Depth blur etc… will be ok, but SSAO I found did not work but I read that is because DP meshes do not contribute to the scene depth effect.
**-**Right now The only limit is Shader Model 5.0 (compute shader) support and systems supporting floating point RenderTextures (ARGBFloat) - so I guess mobile would be out with that texture format.

Hope that helped answer most of your questions and thanks for the interest!

2 Likes

@gurayg , “Can you add Directional lightmap rotation to your demo?” all done and uploaded. Thanks for the suggestion and hoping to have a better demo soon).

1 Like

@winning now do you suppose your method could be a very ideal solution if this worked with Vector Displacement mapping? I’m thinking this could be how Vector Displacement finally becomes the successor of height map displacement, evolve the gaming industry… ideally convert photo scanned assets to vector displacement and then use a shader like yours hopefully not increasing the rendering cost.
I’m also very interested in seeing this work with Megasplat if it would increase performance.

Edit: I think this method might be ideal for oceans or rivers as well if the textures can be scrolled .
I don’t know if its possible or ideal but maybe a transition of Vector images/small vector video clips (maybe mp4 format) to create waves or earth opening up, mudslides, avalanches etc. AAh just dreaming about the possibilities.

3 Likes

Damn. This thread might just be the greatest thread in real-time graphics for some time. Are the height-maps converted to position buffers implicitly by your method?

1 Like

@Ascensi , I did a test with Vector DIsplacement but with this method the problem is that you only have screen space pixels as your real-estate. I could see performing this on a lower level per mesh basis might have interesting results, but in this method it is a pixel to pixel for everything rendered on screen so works best with some base geometry and displaceing that. But I think it would be a very cool area to research further. as for other products working with this, as long as possible to draw the mesh on it’s own layer (the displacement layer camera) and the shader outputs to the needed data to the 4 render targets all would be good. I was toying with the idea of doing my own custom megatexture utilizing buffers and memory mapped files (with unity terrain), however finding an easy way to describe the usage might not be so easy. but can be done of course and I will probably add that in an experimental version down the track.

@R0man , glad you are interested like I am). basically the low-poly meshes that are used for displacement are on a seperate layer with own camera (forward base). it outputs mesh pixel position,color+lighting,normal and height + other data if needed to 4 RT’s. these MRT’s are sent to a compute shader where a fullscreen worth of trangles (two triangles per 4 pixels) are pushed to the original low poly pixel position in world space and then displaced along their normals. this full screen mesh is sent to DrawProcedural and from there is back in the normal rendering pipeline. From my instancing tests this leaves around 2 million triangles for low poly meshes on a gtx970. It has really gotten my creative juices flowing as I can really see a lot of potential and interesting effects to create as I have time and hope others will benefit from this too.

1 Like

@winning11123

Some thoughts:

I’m surprised your not doing this with the GBuffer data instead of a custom forward pass? You can write a height value into the extra channel, reconstruct your world position from the depth buffer, and insert your post processing after the GBuffer is resolved, allowing to to work on the data before lighting happens. This also means no extra camera is needed. You could then write the results back into the GBuffer so they can be lit afterwards, which would allow the lighting to affect the displacement, as if my understanding is correct from your description, right now lighting happens on the low resolution mesh, correct?

Another thought is to do your displacement entirely in the pixel shader rather than constructing triangles at all. At 2 triangles per 4 pixels, you are deep into microtriangle territory, which cuts fill rate considerably due to the way GPUs process pixel blocks. If you are creating perfectly aligned 2x2 pixel quads, then the GPU will shade 4 pixels for each pixel on the screen and throw the others away, because you are always on an edge. So this has a huge fill rate hit (which still might be faster than turning on tessellation in some cases). In the end, the technique is moving existing pixels around on the screen to appear displaced, so it’s really just a distortion effect, right? You could also tap through the height field in this pass to add directional shadows on the small details…

4 Likes

@jbooth_1 , well I may be wrong, but from my understanding the gbuffer would draw the original low poly geometry I would assume and this is not desired for final composition with itself and other objects or non displaced objects, just the position data is wanted and a way to gather the rest of the data. Yes, the lighting is done in the same pass with the normal maps and does not really benefit from being done elsewhere as it just lighting the normals and as displaced looks correct.

Although it sounds like micro territory,the triangles become world space as the vertex are moved to the pixel world positions so actually quite large space between when looking from that perspective. the layout of the triangles is that of a screen “structure” but not actually bound to screen pixels. as each is lined with the render target buffers to extract it’s true 3d world position, like a point cloud except with skin.it is also a constant cost set by the resolution.

It is displacement mapping, so if that is classed as distortion then yes) if there is a vertex for every pixel on the screen in 3d world space and that is moved you could call it s distortion - but not like a post process distortion effect. but yes, screen space shadows for self shadowing would be a cool option for sure!

Having not looked at your technique I’m spitballing a bit, but bare with me if your up for it. The unused channel in the gbuffer is cleared to 0, so no displacement would happen unless objects wrote into that channel. Since the gbuffer draws before forward objects, you’d have access to positions (from depth), albedo, specular terms, and normals, and height in the extra channel from all opaque objects. You’d then run your post process (before forward rendered objects and lighting is applied), and distort everything to the expected positions, avoiding the separate rendering camera/pass. You right though- if your authoring normals correctly then they would still be correct for the displaced geometry regardless of technique used.

Yes, so to some degree the microtriangles may be distorted to be larger or smaller. I’d imagine making them larger just reduces the quality of the effect quickly, too.

I was thinking you could tap through the height field, essentially a simpler version of POM, once to figure out where to grab the current pixel from (instead of the triangles), and once for the shadow. Depending on where the bottleneck is this may or may not be faster than the triangle grid - but same code would give you shadows, and other effects are possible like AO… interesting possibilities if the various artifacts are acceptable.

1 Like

That is cool, I am always interested in new approaches an improvements and always great to get others perspective. Although I think as you describe is an option that may work. But there may be some things that could interfere…The thing is though the original colors and depth would be drawn to the gbuffer (if someone was just using the single camera for all scene), which may work for pixels moving out the object, but not inward once the depth is compared with original scene as the insertion of the final DrawProcedural mesh has to be done after the initial pass and another reason to need the extra camera. This is because there is no way to exclude a DrawProcedural meshes from any camera (or control where they are drawn) except calling after previous camera has finished drawing from what I can gather. So that I think would be main primary reason now I think about it more aside from depth overdraw. Also I think another factor is I have no way to control if Unity could change anything in future and all gbuffer slots could be filled or adding complexity to the whole setup. So I agree it seems like the obvious choice and there is nothing to stop a user modding it to use it that way, but for simplicity I think current method is best and maybe only way without going lower level.

well it is all perspective, visually it will always look like pixels right next to eachother but yes the smaller the resolution or lack of details in textures (compression) will reduce quality absolutely.

yes very cool ideas for sure and I am very interested to explore this.

So Guys @jbooth_1 @winning11123 at this time do you foresee Megasplat compatibility and if yes how long might this take to implement or would users simply need to integrate with Megasplat’s custom shader option? I’m not a coder so I dread the thought not being able to integrate.

Almost forgot… would raycast rendering work with this?