Example #1
0
        /// <summary>
        /// Load the object provided
        /// </summary>
        /// <param name="go">Terrain to load</param>
        public void LoadGameObject(GameObject go)
        {
            //Check not null
            if (go == null)
            {
                Debug.LogError("Must supply a valid game object! GameObject load aborted.");
                return;
            }

            //Clear out the old
            Reset();

            //Load up the new
            m_featureName = go.name;

            //Duplicate the object
            GameObject workingGo = GameObject.Instantiate(go);

            workingGo.transform.position      = transform.position;
            workingGo.transform.localRotation = Quaternion.identity;
            workingGo.transform.localScale    = Vector3.one;

            //Delete any old colliders
            Collider[] colliders = workingGo.GetComponentsInChildren <Collider>();
            foreach (Collider c in colliders)
            {
                DestroyImmediate(c);
            }

            //Now add mesh colliders to all active game objects for the most accurate possible scanning
            Transform[] transforms = workingGo.GetComponentsInChildren <Transform>();
            foreach (Transform child in transforms)
            {
                if (child.gameObject.activeSelf)
                {
                    child.gameObject.AddComponent <MeshCollider>();
                }
            }

            //Calculate bounds
            m_scanBounds.center = workingGo.transform.position;
            m_scanBounds.size   = Vector3.zero;
            foreach (MeshCollider c in workingGo.GetComponentsInChildren <MeshCollider>())
            {
                m_scanBounds.Encapsulate(c.bounds);
            }

            //Update scan array details - dont need to allocate mem until we scan
            m_scanWidth  = (int)(Mathf.Ceil(m_scanBounds.size.x * (1f / m_scanResolution)));
            m_scanHeight = (int)(Mathf.Ceil(m_scanBounds.size.y * (1f / m_scanResolution)));
            m_scanDepth  = (int)(Mathf.Ceil(m_scanBounds.size.z * (1f / m_scanResolution)));

            //Now scan the object
            m_scanMap = new HeightMap(m_scanWidth, m_scanDepth);
            Vector3 scanMin = m_scanBounds.min;
            Vector3 scanPos = scanMin;

            scanPos.y = m_scanBounds.max.y;
            RaycastHit scanHit;

            //Perform the scan - only need to store hits as float arrays inherently zero
            for (int x = 0; x < m_scanWidth; x++)
            {
                scanPos.x = scanMin.x + (m_scanResolution * (float)x);
                for (int z = 0; z < m_scanDepth; z++)
                {
                    scanPos.z = scanMin.z + (m_scanResolution * (float)z);
                    if (Physics.Raycast(scanPos, Vector3.down, out scanHit, m_scanBounds.size.y))
                    {
                        m_scanMap[x, z] = 1f - (scanHit.distance / m_scanBounds.size.y);
                    }
                }
            }

            //Now delete the scanned clone
            DestroyImmediate(workingGo);

            //Nad make sure we had some data
            if (m_scanMap.HasData() == false)
            {
                Debug.LogError("Unable to scan GameObject. GameObject load aborted.");
                return;
            }

            m_scanBounds = new Bounds(transform.position, new Vector3(m_scanWidth * m_scanResolution, m_scanWidth * m_scanResolution * 0.4f, m_scanDepth * m_scanResolution));
            m_baseLevel  = m_scanMap.GetBaseLevel();

            MeshFilter mf = GetComponent <MeshFilter>();

            if (mf == null)
            {
                mf           = gameObject.AddComponent <MeshFilter>();
                mf.hideFlags = HideFlags.HideInInspector;
            }
            MeshRenderer mr = GetComponent <MeshRenderer>();

            if (mr == null)
            {
                mr           = gameObject.AddComponent <MeshRenderer>();
                mr.hideFlags = HideFlags.HideInInspector;
            }
            mf.mesh = Gaia.GaiaUtils.CreateMesh(m_scanMap.Heights(), m_scanBounds.size);
            if (m_previewMaterial != null)
            {
                m_previewMaterial.hideFlags = HideFlags.HideInInspector;
                mr.sharedMaterial           = m_previewMaterial;
            }
        }