• Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
5
Question by GlitchEnzo2 · Dec 02, 2010 at 10:46 PM · gpudisplacementvertexshaderisvisiblefrustrumculling

Disable Frustum Culling?

Is there a way to disable frustum culling on specific objects? Or perhaps disable it entirely?

I'm displacing the vertices in my mesh in a vertex shader. They are displaced to the extent that the original mesh (on the CPU side) is out of the view frustum, whereas the displaced vertices (on the GPU side) ARE in the view frustum. This causes the mesh to suddenly stop rendering and disappear, which is obviously not the desired behavior.

I tried solving this by overriding the OnBecameInvisible() method and forcing the renderer to be enabled, but that did nothing. (I had thought that the frustum culling disabled the renderer, but that is not the case.)

I wish the isVisible field on the renderer was able to be set. I feel that would solve this issue. Any other ideas?

Update: I thought about forcing the bounds on the renderer to be the same size as the maximum displacement, but the bounds property is read-only too.

I then tried having a second camera in the scene that is static and moved back enough to always have the displaced mesh in view, but that didn't work either. Apparently each camera does it's own frustum culling, which makes sense.

Comment
Add comment
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

10 Replies

· Add your reply
  • Sort: 
avatar image
2

Answer by Andy-Korth · Feb 04, 2016 at 11:00 PM

A perhaps better approach for new versions of Unity (5.x and later) is to use the new preculling callback. It works with SpriteRenderers, whereas most of the above solutions do not.

     private Camera thisCamera;
     public void Start(){
         thisCamera = GetComponent<Camera> ();
     }
 
 
     public void PreRenderAdjustFOV(Camera cam){
 
         if (cam == thisCamera) {
             Debug.Log ("MyPreRender: " + cam.gameObject.name);
             cam.fieldOfView = 60;
         }
     }
 
     // callback to be called before any culling
     public void PreCullAdjustFOV(Camera cam)
     {
         if (cam == thisCamera) {
             Debug.Log ("PreCull: " + cam.gameObject.name);
             cam.fieldOfView = 70;
 
             //These are needed for the FOV change to take effect.
             cam.ResetWorldToCameraMatrix();
             cam.ResetProjectionMatrix();
         }
     }
     public void OnEnable()
     {
         // register the callback when enabling object
         Camera.onPreCull += PreCullAdjustFOV;
         Camera.onPreRender += PreRenderAdjustFOV;
     }
     public void OnDisable()
     {
         // remove the callback when disabling object
         Camera.onPreCull -= PreCullAdjustFOV;
         Camera.onPreRender -= PreRenderAdjustFOV;
     }

This allows a small increase in the FOV for culling, and turns it back to the proper field of view when it's time to render. You get the benefits of the frustum culling with an adjustable "extra space" for the geometry of your vertex shader.

Comment
Add comment · Show 1 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image soulburner · Mar 01, 2017 at 12:20 PM 0
Share

I'm trying to implement this solution for my orthographic camera (changing not FOV, but ortho size) and that fixes the culling issue, but breaks the light. It seems that light range calculation is somehow related to the camera ortho size.

avatar image
1

Answer by GlitchEnzo2 · Dec 04, 2010 at 10:10 PM

I've come up with a partial solution. It's not perfect, but it's a lot better than it used to be.

In my camera script, at the end of the LateUpdate() method, I added this:

camera.fieldOfView = 60;
Shader.SetGlobalMatrix("viewMatrix", camera.worldToCameraMatrix);
Shader.SetGlobalMatrix("projMatrix", camera.projectionMatrix);
camera.fieldOfView = 179;

As you can see, it sets the field of view to the standard 60 degrees, sets the shader View and Projection matrices, and then forces the field of view to 179 degrees (the maximum). So, from the shader's point of view, the camera is normal, but in Unity's point of view, the frustum is widened out to the extreme. This means that when Unity does the culling and determines which objects to render, a lot more objects pass the test.

Of course, this means that you have to change your shaders to use your own matrix variables instead of the Unity built-in variables, but that's not too bad:

o.pos = mul(_Object2World, v.vertex);
o.pos = mul(viewMatrix, o.pos);
o.pos = mul(projMatrix, o.pos);

As I said, it's not perfect and some of the displaced meshes still are clipped, but it's only about 1% of the time now as opposed to about 90% of the time before.

Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image
0

Answer by KingSharaman · Mar 10, 2012 at 12:53 AM

Use RecalculateBounds() after you assign the mesh to a MeshFilter component. So for example in C#:

GetComponent().mesh = aMeshObject; aMeshObject.RecalculateBounds();

This way it will recalculate renderer bounds.

Comment
Add comment · Show 4 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image Dylan Gundlach · Aug 09, 2014 at 06:22 PM 0
Share

I don't know why you got so many down votes. I was having this render culling problem with a function in an editor script I created(see below), and adding "mesh.RecalculateBounds()" worked fine. Thanks mate.

private void shift$$anonymous$$esh(){ $$anonymous$$esh mesh = target.GetComponent<$$anonymous$$eshFilter>().shared$$anonymous$$esh; Vector3[] vertices = mesh.vertices; // for(int i = 0; i < vertices.Length; i++){ vertices[i] += shift; } mesh.vertices = vertices; mesh.RecalculateBounds(); }

avatar image PappyA · May 01, 2015 at 11:30 PM 1
Share

I think the reason is because the question pertains to manipulating vertex position in the vertex shader, which happens after the CPU is done with the object. As far as the CPU is concerned the vertices have never moved, thus mesh.RecalculateBounds() doesn't do anything.

avatar image Velo222 · Oct 11, 2015 at 11:40 PM 0
Share

Using the "RecalculateBounds()" command fixed my problem as well. Thank you. Whether or not this is in the scope of the original question, I don't think it should have negative votes, but.....technicalities I guess. It helped me.

avatar image $$anonymous$$ · Nov 09, 2015 at 05:59 PM 0
Share

This suggestion fixed my problem as well. I had an issues with the Vuforia SD$$anonymous$$ and turns out Vuforia does not call RecalculateBounds() after creating it's camera texture background. Been searching for a why to fix this for better part of the day and your suggestion fixed it. Thanks. Gave an up vote to show my gratitude.

avatar image
0

Answer by Seizure · Apr 23, 2013 at 08:10 PM

myTerrain.basemapDistance = 5000; //Allows terrain textures to be shown at a greater distance. myTerrain.detailObjectDistance = 5000; //Allows grass and similiar to be shown at greater distance.

Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image
0
Wiki

Answer by image28 · Nov 26, 2014 at 10:21 PM

I did it without code by using a second camera with a far far clip plane distance, and placed the object on a separate layer and told the camera to only render that layer, then adjusted the depth of the camera and the clear flags to depth only...

Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
  • ‹
  • 1
  • 2

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Welcome to Unity Answers

If you’re new to Unity Answers, please check our User Guide to help you navigate through our website and refer to our FAQ for more information.

Before posting, make sure to check out our Knowledge Base for commonly asked Unity questions.

Check our Moderator Guidelines if you’re a new moderator and want to work together in an effort to improve Unity Answers and support our users.

Follow this Question

Answers Answers and Comments

18 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

Modify water displacement 0 Answers

Character animation smooth on old GPU, strobing on new GPU 0 Answers

GPU warm up 1 Answer

How creating Multiple Scenes affects CPU and GPU Memory (windows PC build) ? 0 Answers

Removing trig functions from mobile shaders 0 Answers


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges