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

LOD - change to billboard at a distance - billboard generation

Discussion in 'Scripting' started by andyz, Nov 26, 2010.

  1. andyz

    andyz

    Joined:
    Jan 5, 2010
    Posts:
    2,251
    I would like to be able to replace objects with a billboard when they get a certain distance away - somewhat like the terrain trees.
    Are there any scripts lying around to handle this and also to generate a billboard(s) for a model (perhaps at runtime using render-to-texture)?

    (Of course would be nice to have a sophisticated LOD system built into Unity too to handle LOD mesh swaps and billboarding for any obejct).
     
  2. Nikolay116

    Nikolay116

    Joined:
    Mar 21, 2010
    Posts:
    421
    I am also curious, but i guess you gotta use render to texture
     
  3. tomnullpointer

    tomnullpointer

    Joined:
    Sep 20, 2010
    Posts:
    142
    It depends on the construction of the actual model. Simple and symmetrical models (trees etc) are usually just produced as billboards in the same art production process. It would be much more efficient to just screenshot the model in your 3d modeling app and make a quick billboard version (speedtree etc does this for you).

    Some games will render the whole of distant models into a full 360 skybox to give you a greater sense of depth that way.

    As for how to switch the models, The simplest way would be to give each tree gameobject a script that checks its distance from camera and uses a threshold to decide when to mute/unmute the attached 3d model/billboard. Of course this wouldnt be very efficient as youd be running potentially hundreds of tests. It might be better to do some quadtree like chunk testing (groups of objects all tested in 1 go)

    The terrain examples in the unity demo use dynamic billboard switching for trees etc. Its more difficult for larger non-symmetric models as the viewing angle can make much more difference. (people are ok with rotating tree billboards, not so much with rotating walls etc)
     
  4. andyz

    andyz

    Joined:
    Jan 5, 2010
    Posts:
    2,251
    Well I wrote a script to generate a billboard of an object - works in any version of Unity - could be useful to others
    (tis .js)

    PHP:
    /*
    Make a billboard out of an object in the scene
    The camera will auto-place to get the best view of the object so no need for camera adjustment

    To use - place an object in an empty scene with just camera and any lighting you want.
    Add this script to your scene camera and link to the object you want to render.
    Press play and you will get a snapshot of the object (looking down the +Z-axis at it) saved out to billboard.png in your project folder
    Any pixels colored the same as the camera background color will be transparent
    */

    var objectToRender GameObject;
    var 
    imageWidth int 128;
    var 
    imageHeight int 128;

    function 
    Start()
    {
        if (!
    objectToRender) return;

        
    //grab the main camera and mess with it for rendering the object - make sure orthographic
        
    var cam Camera Camera.main;
        
    cam.orthographic true;
        
        
    //render to screen rect area equal to out image size
        
    var rw float imageWidthrw /= Screen.width;
        var 
    rh float imageHeightrh /= Screen.height;
        
    cam.rect Rect(0,0,rw,rh);
        
        
    //grab size of object to render - place/size camera to fit
        
    var bb Bounds objectToRender.GetComponent(Renderer).bounds;
        
            
    //place camera looking at centre of object - and backwards down the z-axis from it
        
    cam.transform.position bb.center;
        
    cam.transform.position.= -1.0 + (bb.min.2.0);
            
    //make clip planes fairly optimal and enclose whole mesh
        
    cam.nearClipPlane 0.5;
        
    cam.farClipPlane = -cam.transform.position.10.0 bb.max.z;
            
    //set camera size to just cover entire mesh
        
    cam.orthographicSize 1.01 Mathf.Max( (bb.max.bb.min.y)/2.0, (bb.max.bb.min.x)/2.0);
        
    cam.transform.position.+= cam.orthographicSize 0.05;

        
    //render
        
    yield new WaitForEndOfFrame();
        
        var 
    tex = new Texture2DimageWidthimageHeightTextureFormat.ARGB32false );
        
    // Read screen contents into the texture
        
    tex.ReadPixelsRect(00imageWidthimageHeight), 0);
        
    tex.Apply();

        
    //turn all pixels == background-color to transparent
        
    var bCol Color cam.backgroundColor;
        var 
    alpha bCol;
        
    alpha.0.0;
        for(var 
    int 0imageHeighty++)
        {
            for(var 
    int 0imageWidthx++)
            {
                var 
    Color tex.GetPixel(x,y);
                if (
    c.== bCol.r)
                    
    tex.SetPixel(x,y,alpha);
            }
        }
        
    tex.Apply();

        
    // Encode texture into PNG
        
    var bytes tex.EncodeToPNG();
        
    Destroytex );
        
    System.IO.File.WriteAllBytes(Application.dataPath "/../billboard.png"bytes);
    }
     
    jason-fisher likes this.
  5. marcatore

    marcatore

    Joined:
    May 22, 2015
    Posts:
    160
    @andyz
    I'm new with Unity and I've found just your script to render a billboard of an object and I think it's really useful.
    Trying it I've discovered that when you set the image resolution over 512x512 , the script seems to freeze Unity.
    Could you confirm? If yes, is there any reason for this?

    Thanks in advance for your reply and for you script.