Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

[RELEASED] Super Fast Soft Shadows

Discussion in 'Works In Progress - Archive' started by Andy-Korth, Jun 5, 2015.

  1. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Super Fast Soft Shadows is live on the asset store!
    https://www.assetstore.unity3d.com/en/#!/content/38682





    We're the authors of Chipmunk2D physics engine and Cocos2D-SpriteBuilder maintainers. We recently rewrote the Cocos2D renderer and added lighting effects, and now we're back to writing Unity plugins!

    Super Fast Soft Shadows uses a unique shader based algorithm: Shadow projection occurs inside the vertex shader, not on the CPU. This allows us to achieve:
    * Speed on mobile platforms
    * High number of colored lights and shadowed objects
    * Flexibility in light size and softness of shadows

    Shadow mask generation occurs in a single pass - it doesn't use expensive image filters or pixel shaders to soften the shadows. This means it runs great on mobile!


    Physically realistic penumbra, umbra, and antumbra rendering is based on configurable light sizes. This produces accurate rendering when the light source is larger than the objects casting the shadows.

    Great for atmospheric effects:


    Here's the store page: https://www.assetstore.unity3d.com/en/#!/content/38682
     
    Last edited: Dec 21, 2016
    Mauri, RavenOfCode, Farelle and 4 others like this.
  2. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    Here's a good example of the sort of nice soft penumbras you can get:


    It can produce nice, accurate penumbras, and even antumbras when the light source is bigger than the object casting the shadow. This is because we are calculating the actual occlusion percentages when casting the shadows instead of applying some sort of blur or other image based effect. Blurs are incredibly bandwidth intensive, and this is especially a problem on mobile. Even though the occlusion we calculate is per pixel, it's a pretty short fragment shader and most of the math is done in the vertex shader. You are really just paying for the fillrate to blend the visible parts of the shadow masks and lights.
     
    khaled24 likes this.
  3. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    We put together a demo of how it might be used in a forest to add some ambience to something like a top down game:



    The light has an animated color, allowing it to flicker as it moves, creating a torch-like effect.
     
    pcg, Rodolfo-Rubens, Ony and 5 others like this.
  4. larku

    larku

    Joined:
    Mar 14, 2013
    Posts:
    1,422
    WOW looks fantastic.

    I could really use this for a mobile project that's nearing completion..

    Any chance of beta testing this?

    I'm currently using my own faked shadows but they don't look as good as this and my implementation is a little expensive (performance wise).
     
  5. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Sure! We'll send you one at the end of the day. We've got some editor scripts for editing shadow shapes (in case you want different shadow casting shapes from your colliders). They might be a little rough, but they should be pretty good by the end of the day. Thanks!
     
    Last edited: Jun 8, 2015
  6. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Hey Larku,
    Check your PMs, I sent you a beta copy. Thanks for testing!



    Here's a picture of using a custom cookie- this one is a spotlight texture we included.
     
  7. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    Hierarchical culling is working pretty good now. You can get a lot of lights and shadow casters on the screen without slowing to a crawl:
     
    Manny Calavera likes this.
  8. imaginaryhuman

    imaginaryhuman

    Joined:
    Mar 21, 2010
    Posts:
    5,834
    cool. curious how this works under the hood?
     
  9. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    It's sort of like the popular 2D hard shadow mask algorithm. You outline your objects with a polyline. Each segment of the polyline gets projected and extruded into a quad. Each edge of the segment gets projected from a different position to accommodate for the size of the light. Then for each vertex, it calculates the amount of occlusion for either edge of the segment. The fragment shader just has to mix the occlusion values together, add some smoothstep, and do some clipping. What took the longest to figure out about is that you really can't take many shortcuts. If you do, the shadows cast from two adjacent segments won't interpolate exactly and you'll get a hole in their shadow instead of blending together seamlessly.

    Then it's just rinse and repeat for each light. Generate the shadow mask, then multiply each light's cookie by the mask and add it to the lightmap buffer.
     
  10. imaginaryhuman

    imaginaryhuman

    Joined:
    Mar 21, 2010
    Posts:
    5,834
    So it is generating a bunch of extruded mesh data for all solid objects every frame?
     
  11. hippocoder

    hippocoder

    Digital Ape

    Joined:
    Apr 11, 2010
    Posts:
    29,723
    I imagine it already has the meshes and merely uses a vertex shader to extrude them in similar manner as if you were performing stencil buffered shadows.
     
  12. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    @hippocoder More or less yes. The vertex shader does most of the work, the CPU is just needs to batch the mesh data so it doesn't make a separate draw call for each shadow caster. It caches what it can.
     
    AlanMattano likes this.
  13. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Here's another demo where we've got a mouse-look flashlight in a platformer like game:

    Some of the effects are pretty subtle, and don't show up very well in the youtube video, but we also have a layer of dust over the scene that adds some depth and variety to the foggy light. The character also has a jetpack that receives lighting effects.

     
  14. Manny Calavera

    Manny Calavera

    Joined:
    Oct 19, 2011
    Posts:
    205
    I'm salivating.. :)
     
  15. Darkays

    Darkays

    Joined:
    Mar 31, 2013
    Posts:
    176
    Wow! This looks gorgeous! I could see myself using this in our current project.

    Can you still create some version of hard edged shadows with this? Or is this exclusively physically based soft edges?

    Awesome job so far guys!
     
  16. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    Yes. If you set the light's radius to 0 then it will cast hard shadows. One of the advantages to doing things in a physically realistic way is that it usually "just works" the way you'd expect. Since the per-pixel cost isn't a lot higher than hard shadows, it doesn't waste a lot of fillrate either.
     
  17. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144


    Shadow geometry can be calculated automatically from 2D polygon colliders, but you can also tweak the geometry by hand or add your own from scratch. Here's the shadow geometry editor, in action.

    The dust effect shows up better in the image than in the video :D
     
  18. TheValar

    TheValar

    Joined:
    Nov 12, 2012
    Posts:
    760
    This looks awesome!
     
  19. IndieAner3d

    IndieAner3d

    Joined:
    Oct 20, 2014
    Posts:
    77
    Broken Image... Oo
    Can´t see... oO
    Re-up plz... ^o^
     
  20. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Hm, it's working for me, but here's an Imgur link in case that helps: http://i.imgur.com/2hlMPCW.png
     
  21. IndieAner3d

    IndieAner3d

    Joined:
    Oct 20, 2014
    Posts:
    77
    Niceee ^^
    THX

    Looks really good OO
    Very good for dark projects/scenes
    to bring some deep atmosphere in it... ;---)
    Limbo and Co.
    lol ^o^

    P.s. On Mobile, they some limitation...
    Like OpenGl 2/3 only...
    Also with RenderMode...
    Single or Multithreaded...
     
    Last edited: Jun 17, 2015
  22. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Yeah! Thanks! I'm excited to see what some real artists do with it. All our examples have been pretty dark, but you can also turn crank up the global dynamic range in order to create bloom-like effects or really oversaturated images like this:


    (imgur: http://imgur.com/jnb8LYr )

    I think with the right magic touch, this could be a cool stylistic effect!
     
    IndieAner3d likes this.
  23. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    Not a problem. Our idea was built around the limitations of mobile from the beginning. It doesn't use any new shader features, it doesn't use a lot of memory bandwidth (just blending), there's not a lot of overdraw, etc. The asteroids scene from the first post was able to run on an iPad 2 or an original Nexus 7 with 6 onscreen lights at a time and still run at Unity's 30 fps cap. (I never actually tried disabling the cap or trying more lights, we should do some real performance testing I guess.)
     
    IndieAner3d likes this.
  24. Mr-Stein

    Mr-Stein

    Joined:
    Dec 4, 2013
    Posts:
    169
    Hi @Andy.Korth, your shadow system look awesome! can you send me a copy of the beta? how much will cost when you release en assets store?

    Regards,
     
  25. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    We are wrapping everything up and getting ready to submit it to the store this afternoon. Stay tuned!
     
  26. Manny Calavera

    Manny Calavera

    Joined:
    Oct 19, 2011
    Posts:
    205
    Please, can you share a video or at least a screenshot of the forest demo running with the Profiler window open?
     
  27. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    The asset is in review, we're just waiting to hear back from Unity now!

    @Manny Calavera:
    Sure, here's a screenshot of the profiler in the forest scene:


    So it's running at just under 1000 FPS on my Macbook here. The shadow drawing part specifically is the selected 0.28 ms part, plus another 0.02 ms OnPostRender call. The profiler is reporting 6 draw calls for the entire scene, it has batched all the different trees.

    Anything else you want to see?
     
    Manny Calavera likes this.
  28. Manny Calavera

    Manny Calavera

    Joined:
    Oct 19, 2011
    Posts:
    205
    That looks good! Where's the 124 bytes coming from?
     
  29. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    That's mostly from creating a lambda method used for the culling of shadows and lights. You can pass null instead, and skip the allocation, but culling is far more beneficial than 124 bytes ;)
     
  30. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    New video! This one shows everything altogether. We did submit to the asset store on Friday, and are just waiting for approval now.

     
    IndieAner3d likes this.
  31. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    Still waiting to be accepted... It's been two weeks now. :-\
     
    Manny Calavera likes this.
  32. Darkays

    Darkays

    Joined:
    Mar 31, 2013
    Posts:
    176
    Man, sorry to hear that... Hopefully it will pass. I'm not sure on how long these things take (I haven't put anything up there before) but if you don't hear anything by the end of the week I would definitely contact them by then.

    Good luck, can't wait to mess around in my projects.
     
  33. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
  34. castor76

    castor76

    Joined:
    Dec 5, 2011
    Posts:
    2,517
    Hi.

    We are already using another solution for our 2D lighting, but always interested with alternative method to see if things can improve.

    I have few questions if you don't mind.

    1. We have our own custom rendering pipe line that requires for us to obtain the texture for shadow part of the lighting and actual lightmap part. Is this possible? Also we need to do separate rendering for the vision and actual lighting using the same system, so we would need to render them separately.

    2. Our game is top down game that is aligned on XZ plane. Meaning camera is looking down on Y global axis. Does this package work with such axis system?

    3. For shadow casting polygon issue, I don't mind defining them manually, but we already use the 3D collider that is generated by 2Dtoolkit. And then we generate a shadow masking objects from the polygon mesh data of the 3D collider. I don't think this can be used directly with this package, but can you explain a bit more about the shadow casting geometry stuff? If all it is to create a geometry for a say,.. shadow rendering camera to use , it may be possible to just use the existing ones that we have.

    4. Also because we use 2Dtoolkit sprites , it maybe possible to obtain the necessary data straight from the 2Dtoolkit sprite's data. Because 2Dtoolkit also just "draws" the polygon collider as 2D way (no depth when drawing them) but then it creates 3D collider from that data. So "the array of the points" may be available already. Reason why this is good idea too is that usually those polygon colliders are used for the physics , (say a wall) so it should be natural thing to cast shadow anyway.

    Thanks for your time. If things do look promising , then it would be great if we can test it to see if it can fit into our existing rendering pipeline.
     
  35. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    1) Sort of, definitely if you modify the code slightly. It generates a render texture with the lightmap in it at the beginning of the frame, then accesses it through a shader global. You could trivially modify it to keep the texture reference around longer.

    2) Hmm. That's a problem actually. It would be possible to swap the axes with a bit of work, but some of the math does make the assumption that it's operating on the x/y plane.

    3/4) The polygon objects can be set up in code easily enough. You could just copy the data over in a Start() method. Since they store some culling information they can't be easily replaced in the code though.
     
  36. castor76

    castor76

    Joined:
    Dec 5, 2011
    Posts:
    2,517
    Humm...

    Seems like the biggest issue may be to work with different system of axis. I think it may be worth while for you to support the XZ plane since the "top down" games would generally use the XZ plane due to the Unity Navigation system not supporting the XY plane. What part of the system does assume that it is XY plane? shadow casting polygon generation?
    If that is all it is then it may be ok for us since we plan to supply the shadow casting geometry ourselves. But if shaders assume that everything is based on XY plane, this could be bigger problem.
     
  37. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    I'm skimming through our code to see what would need changes. Some of the shadow casting is assuming 2D polygons colliders, but as mentioned by Scott, it's pretty easy to replace that code. (and generate shadow geometry some other way). So the poly generation is not a huge worry.

    The culling operates a lot of Rects, that would be complicated to change, but maybe you can avoid that change and treat the rects as an arbitrary axis without code changes. - You would need to be sure the the camera viewing rect and object positions and extends go into the system in your new plane rather than the default.

    The shaders have some swizzling down to float2s, but mostly you'll just need to change the whateverFloat3.xy to whateverFloat3.xz, for example. We were definitely focusing on making this easy for people using the stock unity 2d stuff, but nothing will prevent these changes. I believe you can't change the axis with Unity's 2D stuff, right? Interesting that Unity's own NavMesh stuff doesn't work in XY. I've never used it, I always got the feeling that it was a piece of middleware that was dropped in for a specific client who was making a very specific game.

    The editor scripts are clamped to the XY plane, but it sounds like you might not care about that since you can disable it and you already have plans for generating shadow geometry from the other information you have set up on your sprites.

    Hope that helps.
     
  38. castor76

    castor76

    Joined:
    Dec 5, 2011
    Posts:
    2,517
    Yeah, Unity's default navigation doesn't work with their 2D solution and they don't have any plan to make it to work in the future. (I have asked this so many times during Unity summit and so on)

    Also Unity's 2D doesn't work with XZ plane neither. It's pretty mis-matching pieces of tools in my opinion.

    I got this feeling that this asset has potential. And it would be interesting to investigate the difference in between using our current solution and yours. This is the asset I am using :

    https://www.assetstore.unity3d.com/...ymjGfBAJirOflSXKk1xoC4x3w_wcB#!/content/20461

    And while you wouldn't be able to give us your opinion about the comparison unless you have used the asset, I wonder if you can let me know what you think the possible differences are. I could not investigate the shader for the asset I am using because it doesn't include any sources for it, but it seems like it is doing some kind of marching technique.. it has count for number of iterations and so on..

    If you are interested, you should investigate above solution because it is pretty much only similar competition to your asset.
     
  39. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    It looks like we both support soft shadows, having separate shadow casting geometry, and colored lights. Theirs seems to require Unity Pro and ours doesn't (although that might just be because they uploaded with an older version of Unity).

    Our light casting uses cookies, so it's a bit more flexible. They seem to have point lights, spot lights, and directional lights. You can look at their screenshots and notice how the spotlights work- they definitely come out of a single very small point. Technically, we don't support directional lights, but a large square cookie seems to do pretty well for our purposes. I'm pretty sure their light is cast from a single point, so you probably only get a penumbra- you won't get the full umbra/penumbra/antumbra.

    Our lights have a actual physical radius, so we have physically accurate soft shadows, which is especially noticeable when the light source is large. Like in real light, the softness of shadows is based on the size of the light. It looks like their product has a softness slider.. Things get softer as the shadow gets longer, but it looks like the shadows have the same softness at the point where they start. Hard to tell, I'm looking at the green screenshot in particular for that. Softness is probably a global setting.
     
  40. castor76

    castor76

    Joined:
    Dec 5, 2011
    Posts:
    2,517
    I can tell you that their solution also supports cookies , but from your description , I think the biggest difference may be yours having a actual physical radius.

    I am kinda on the edge here, it is hard to decide to give a go with your solution , not because the price for the asset, but time it may take to make it work in XZ plane. I might just try it over the weekend but any help to try and make it work for the XZ plane would be really nice. ( For example, modified shaders..)

    I know I may be asking a bit too much for my specific case, but I think there would be a lot more developers like me who uses 2dtoolkit for sprites and then use XZ plane for top down game.

    I have not seen a single solution that can work on XZ plane well, at least based on GPU solution.
     
  41. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    A new version has been submitted to the store featuring some fixes to full screen shader effects and some improvements focusing Unity 5.

    Next in progress we are planning some light-probe-like behaviors. Stay tuned!
     
    garrido86 likes this.
  42. garrido86

    garrido86

    Joined:
    Dec 17, 2013
    Posts:
    233
    Nice, looking forward this!
     
  43. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Important fix for DirectX platforms!

    To fix DirectX rendering of Super Fast Soft Shadows, please apply the following fix:

    In SFRender.cs, at the end of the RenderLightMapMethod (around line 230), replace the code with this code:

    Code (CSharp):
    1.  
    2.             var textureMatrix = (clippedProjection*modelView).inverse;
    3.              
    4. #if !UNITY_EDITOR_OSX && ( UNITY_EDITOR_WIN || UNITY_STANDALONE_WIN || UNITY_XBOX360 || UNITY_XBOXONE || UNITY_WP8 || UNITY_WSA || UNITY_WINRT )
    5.             // Viewport and texture coordinats are flipped on DirectX.
    6.             // Need to flip the projection going in, then flip the texture coordinates coming out.
    7.             var flip = Matrix4x4.Scale(new Vector3(1.0f, -1.0f, 1.0f));
    8.             textureMatrix = flip*textureMatrix*flip;
    9. #endif
    10.  
    11.             // Composite the light.
    12.             // Draw a fullscreen quad with the light's texture on it.
    13.             // The vertex shader doesn't use any transforms at all.
    14.             // Abuse the projection matrix since there isn't really a better way to pass the texture's transform.
    15.             GL.LoadProjectionMatrix(textureMatrix);
    16.             Graphics.DrawTexture(LIGHT_RECT, light._cookieTexture, SRC_RECT, 0, 0, 0, 0, color, this.lightMaterial);
    17.         }
    18.  
    19.         if(shadows) _culledPolygons.Clear();
    The extra #ifdef will ensure viewport and texture coordinates get flipped properly to account for the reversed Y axis on DirectX platforms.

    Thanks to everyone in the community for your support and help finding and fixing this issue! This fix has been submitted for version 1.2 in the asset store, but it will be a few days before it goes out- it's currently in review.
     
  44. Andy-Korth

    Andy-Korth

    Joined:
    Jun 7, 2013
    Posts:
    144
    Hi everyone,
    The previously mentioned version 1.2 is now available in the asset store. Thanks!

    Next in-progress is some sort of light sampling options- targeted for people who are looking for sprites that can move over shadowed terrain without casting shadows and take on the light profile at their feet.
     
  45. arkhament

    arkhament

    Joined:
    Jan 24, 2015
    Posts:
    114
    Hi @Andy.Korth, with SFSS I can made or reproduce Scenes/Levels shiny like this?:


    Regards,
     
  46. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    On request, we've been adding sampled lighting so that you can light a sprite using the amount of light at it's base. You can set it up to sample the light at a specific point or along a line. Stay tuned!

    For example:
     
  47. Mr-Stein

    Mr-Stein

    Joined:
    Dec 4, 2013
    Posts:
    169
    Hi @Andy.Korth and @slembcke2 I'm looking for a solution like looking @arkhament.
    It is possible to make that kind of effect as the lights in the Guacamelee! game?
     
  48. slembcke2

    slembcke2

    Joined:
    Jun 26, 2013
    Posts:
    270
    So Pablo is the name of the user that requested the extra light sampling features. He sent me a work in progress shot and said I could share it. Looks awesome so far!
     
    bluescrn likes this.
  49. bluescrn

    bluescrn

    Joined:
    Feb 25, 2013
    Posts:
    642
    Hi,

    Are there any known issues with culling of shadowcasters?

    I'm experimenting with SFSS and in my test scene, a shadowcaster seems to be prematurely culled when I move the camera to the right:

    culling_issue.png

    It's just a simple test scene - 3 lights, 2 SFPolygons. The SFPolygon on the large block of tiles appears to stop casting shadows when the origin position of its GameObject goes off the left, top, or bottom of the screen (but not if it goes off the right, strangely) - the object is set up like this:

    sfpolygon.png

    (It's just a quick test set up manually in the editor - I'm not adding SFPolygons to my tilemap in script yet)

    edit: Looks like this is actually only happening in editor mode, and is working correctly when the game is running?

    edit 2: Debugging a little, it looks like SFPolygon::_UpdateBounds is only called when the verts are edited, or on Start(). And the bounds aren't serialised - so if you reload an existing scene, the bounds aren't set correctly? (unless you move a vertex, then it updates and starts working)

    Also... has anyone tried to get this working with a perspective camera? I've switched to ortho for now, but I was intending to use perspective just as one way of handling parallax layers (all lights/shadowcasters at z=0, though)
     
    Last edited: Sep 13, 2015
  50. condition6d5489

    condition6d5489

    Joined:
    Jul 17, 2014
    Posts:
    11
    Hi,

    This asset looks amazing! My only question is: Can I use the 2d light sources in custom shaders or do I have to use the shaders that come with this project? I see that your shaders are prefixed with SF, is that ShaderForge? I'm currently using 3D lights, ShaderForge and SpriteLamp to do my lighting. However, a fully 2D solution would be ideal. Do you support/use ShaderForge? Please say yes. Please!