天天看点

unity3d lod

//以下是简单lod的核心脚本,主要是功能就是通过距离来判断哪些东西隐藏 哪些东西显示


// *********************************************************************
// Speed LOD manager, set for 5 LOD
// (c) Nikko /Unity3dx.com
// All Rights reserved
// http://unity3dx.com
//*********************************************************************
// How to use: this script needs to be attached to the LOD prefab.

//@script ExecuteInEditMode

 private enum _Nikko_LOD_LEVEL { LOD0, LOD1, LOD2, LOD3, LOD4,LOD5}
 public var nlod:int;
    public var lodMesh0 : GameObject;
    public var lodMesh1 : GameObject;
    public var lodMesh2 : GameObject;       
 public var lodMesh3 : GameObject;   
 public var lodMesh4 : GameObject;   
 public var mycam : Camera;   
 public var delaycounter:int;
 public var distancehide:float;

    public var distanceLOD1 : float;
    public var distanceLOD2 : float;       
 public var distanceLOD3 : float;  
 public var distanceLOD4 : float;    
 
    private var currentLOD : _Nikko_LOD_LEVEL= _Nikko_LOD_LEVEL.LOD4; 
 private var counter:int;

 function getLODNbr()
 {
  return nlod;
 }
 function setLODNbr(v:int)
 {
  nlod=v;
 }
 function getComponentName()
 {
  return "Nikko_LODManager5";
 }


// Library to access internal values of the LOD manager.
 function setLOD(l:int)
 {
  switch (l)
  {
   case _Nikko_LOD_LEVEL.LOD0:
    lodMesh0.SetActiveRecursively(true);
    lodMesh1.SetActiveRecursively(false);
    lodMesh2.SetActiveRecursively(false);    
    if (nlod>3) lodMesh3.SetActiveRecursively(false);
    if (nlod>4) lodMesh4.SetActiveRecursively(false);    
   break;
   case _Nikko_LOD_LEVEL.LOD1:
    lodMesh0.SetActiveRecursively(false);
    lodMesh1.SetActiveRecursively(true);
    lodMesh2.SetActiveRecursively(false);    
    if (nlod>3) lodMesh3.SetActiveRecursively(false);
    if (nlod>4) lodMesh4.SetActiveRecursively(false);    
   break;
   case _Nikko_LOD_LEVEL.LOD2:
    lodMesh0.SetActiveRecursively(false);
    lodMesh1.SetActiveRecursively(false);
    lodMesh2.SetActiveRecursively(true);    
    if (nlod>3) lodMesh3.SetActiveRecursively(false);
    if (nlod>4) lodMesh4.SetActiveRecursively(false);    
   break;
   case _Nikko_LOD_LEVEL.LOD3:
    lodMesh0.SetActiveRecursively(false);
    lodMesh1.SetActiveRecursively(false);
    lodMesh2.SetActiveRecursively(false);    
    if (nlod>3) lodMesh3.SetActiveRecursively(true);
    if (nlod>4) lodMesh4.SetActiveRecursively(false);    
   break;
   case _Nikko_LOD_LEVEL.LOD4:
    lodMesh0.SetActiveRecursively(false);
    lodMesh1.SetActiveRecursively(false);
    lodMesh2.SetActiveRecursively(false);    
    if (nlod>3) lodMesh3.SetActiveRecursively(false);
    if (nlod>4) lodMesh4.SetActiveRecursively(true);    
   break;     
   case _Nikko_LOD_LEVEL.LOD5:
    lodMesh0.SetActiveRecursively(false);
    lodMesh1.SetActiveRecursively(false);
    lodMesh2.SetActiveRecursively(false);    
    if (nlod>3) lodMesh3.SetActiveRecursively(false);    
    if (nlod>4) lodMesh4.SetActiveRecursively(false);
   break;   
   default:
    lodMesh0.SetActiveRecursively(false);
    lodMesh1.SetActiveRecursively(false);
    lodMesh2.SetActiveRecursively(false);    
    if (nlod>3) lodMesh3.SetActiveRecursively(false);
    if (nlod>4) lodMesh4.SetActiveRecursively(false);
  }
 }
 
  // Library to access internal values of the LOD manager.
 function setDistanceLOD(lod:int,dist:float)
 {
  switch (lod)
  {
   case _Nikko_LOD_LEVEL.LOD0:
    distanceLOD0=dist;
   break;
   case _Nikko_LOD_LEVEL.LOD1:
    distanceLOD1=dist;
   break;
   case _Nikko_LOD_LEVEL.LOD2:
    distanceLOD2=dist;
   break;
   case _Nikko_LOD_LEVEL.LOD3:
    distanceLOD3=dist;
   break;   
   case _Nikko_LOD_LEVEL.LOD4:
    distanceLOD4=dist;
   break;
   default:
   Debug.LogError("SetDistanceLOD: Wrong LOD value");return;
    
  }
 }
 
 // Change the time when this LOD script will execute.
 function SetCounter(c:int)
 {
  counter=c;
 }
 
 
    function Start()
    {
  // spread the autoupdate within the range of the delay counter variable so that each LOD check itself every x number of frames.
  counter=Random.Range(1, delaycounter);
  // check if some object are too far, if yes, disable them
  var distanceFromObject : float = Vector3.Distance(transform.position, mycam.transform.position);
  if (distanceFromObject  > distancehide) 
  {
    switch (nlod) // each LOD (3,4,5) has to be done separately
    {
    case 3:
     currentLOD = _Nikko_LOD_LEVEL.LOD3;
     lodMesh0.SetActiveRecursively(false);
     lodMesh1.SetActiveRecursively(false);
     lodMesh2.SetActiveRecursively(false);    
    break;
    case 4:
     currentLOD = _Nikko_LOD_LEVEL.LOD4;
     lodMesh0.SetActiveRecursively(false);
     lodMesh1.SetActiveRecursively(false);
     lodMesh2.SetActiveRecursively(false);    
     lodMesh3.SetActiveRecursively(false);    
    break;   
    case 5:
     currentLOD = _Nikko_LOD_LEVEL.LOD5;
     lodMesh0.SetActiveRecursively(false);
     lodMesh1.SetActiveRecursively(false);
     lodMesh2.SetActiveRecursively(false);    
     lodMesh3.SetActiveRecursively(false);    
     lodMesh4.SetActiveRecursively(false);
    break;
   }
  }    
    }
 
    function LateUpdate() 
 {  
  
  /*if (currentLOD == _Nikko_LOD_LEVEL.LOD0)
  {
   // we are on the closest LOD
   // place here your real time effect, for your closest objects, like wind, movements, animations.
  }
  */ 
  counter=counter-1;
  // check that we are at the time we need to check ourself and maybe change our LOD
  if (counter<0)
  {
   counter=delaycounter;
   // quick method to calculate the distance with the camera.
   var distanceFromObject : float = Vector3.Distance(transform.position, mycam.transform.position);
  
   switch (nlod) // each LOD (3,4,5) has to be done separately
   {
   
        //************************   LOD 3 *************************
    case 3:
     // LOD0 is set here
     if (distanceFromObject < distanceLOD1 && currentLOD != _Nikko_LOD_LEVEL.LOD0)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD0;
      lodMesh0.SetActiveRecursively(true);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false);     
      return;

      
     }
     // LOD 1 is set here
     else if (distanceFromObject >= distanceLOD1 && distanceFromObject < distanceLOD2 && currentLOD != _Nikko_LOD_LEVEL.LOD1)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD1;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(true);
      lodMesh2.SetActiveRecursively(false);
      return;

     }
     // LOD 2 is set here.
     else if (distanceFromObject >= distanceLOD2 && distanceFromObject  < distancehide && currentLOD != _Nikko_LOD_LEVEL.LOD2)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD2;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(true);   
      return;
     }    
     else if (distanceFromObject  > distancehide && currentLOD != _Nikko_LOD_LEVEL.LOD5)
     {
      // again if we are here, this object has gone too far: disable it!
      currentLOD = _Nikko_LOD_LEVEL.LOD3;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1. (false);
      lodMesh2.SetActiveRecursively(false);   
      return;
     }
    break;
      //************************   LOD 4 *************************
    case 4:
     // LOD0 is set here
     if (distanceFromObject < distanceLOD1 && currentLOD != _Nikko_LOD_LEVEL.LOD0)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD0;
      lodMesh0.SetActiveRecursively(true);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false);    
      lodMesh3.SetActiveRecursively(false);  
      return;

      
     }
     // LOD 1 is set here
     else if (distanceFromObject >= distanceLOD1 && distanceFromObject < distanceLOD2 && currentLOD != _Nikko_LOD_LEVEL.LOD1)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD1;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(true);
      lodMesh2.SetActiveRecursively(false);
      lodMesh3.SetActiveRecursively(false); 
      return;

     }
     // LOD 2 is set here.
     else if (distanceFromObject >= distanceLOD2 && distanceFromObject  < distanceLOD3 && currentLOD != _Nikko_LOD_LEVEL.LOD2)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD2;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(true);  
      lodMesh3.SetActiveRecursively(false);  
      return;
     }   
     // LOD 3 is set here.
     else if (distanceFromObject >= distanceLOD3 && distanceFromObject  < distancehide && currentLOD != _Nikko_LOD_LEVEL.LOD3)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD3;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false);  
      lodMesh3.SetActiveRecursively(true);
  
      return;
     }   
     else if (distanceFromObject  > distancehide && currentLOD != _Nikko_LOD_LEVEL.LOD5)
     {
      // again if we are here, this object has gone too far: disable it!
      currentLOD = _Nikko_LOD_LEVEL.LOD4;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false); 
      lodMesh3.SetActiveRecursively(false);    
      return;
     }
    break;
   
    //************************   LOD 5 *************************
    case 5:
     // LOD0 is set here
     if (distanceFromObject < distanceLOD1 && currentLOD != _Nikko_LOD_LEVEL.LOD0)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD0;
      lodMesh0.SetActiveRecursively(true);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false);    
      lodMesh3.SetActiveRecursively(false);
      lodMesh4.SetActiveRecursively(false);   
      return;

      
     }
     // LOD 1 is set here
     else if (distanceFromObject >= distanceLOD1 && distanceFromObject < distanceLOD2 && currentLOD != _Nikko_LOD_LEVEL.LOD1)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD1;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(true);
      lodMesh2.SetActiveRecursively(false);
      lodMesh3.SetActiveRecursively(false); 
      lodMesh4.SetActiveRecursively(false);   
      return;

     }
     // LOD 2 is set here.
     else if (distanceFromObject >= distanceLOD2 && distanceFromObject  < distanceLOD3 && currentLOD != _Nikko_LOD_LEVEL.LOD2)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD2;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(true);  
      lodMesh3.SetActiveRecursively(false);
      lodMesh4.SetActiveRecursively(false);   
      return;
     }   
     // LOD 3 is set here.
     else if (distanceFromObject >= distanceLOD3 && distanceFromObject  < distanceLOD4 && currentLOD != _Nikko_LOD_LEVEL.LOD3)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD3;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false);  
      lodMesh3.SetActiveRecursively(true);
      lodMesh4.SetActiveRecursively(false);   
      return;
     }   
     // LOD 4 is set here.
     else if (distanceFromObject >= distanceLOD4 && distanceFromObject  < distancehide && currentLOD != _Nikko_LOD_LEVEL.LOD4)
     {
      currentLOD = _Nikko_LOD_LEVEL.LOD4;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false);  
      lodMesh3.SetActiveRecursively(true);
      lodMesh4.SetActiveRecursively(false);   
      return;
     }
     else if (distanceFromObject  > distancehide && currentLOD != _Nikko_LOD_LEVEL.LOD5)
     {
      // again if we are here, this object has gone too far: disable it!
      currentLOD = _Nikko_LOD_LEVEL.LOD5;
      lodMesh0.SetActiveRecursively(false);
      lodMesh1.SetActiveRecursively(false);
      lodMesh2.SetActiveRecursively(false); 
      lodMesh3.SetActiveRecursively(false);  
      lodMesh4.SetActiveRecursively(false);   
      return;
     }
    break;
   
   }
  
  }   
 

 }