Exemple #1
0
        /*
         * Updates the internal quadtree to make it identical to the given terrain
         * quadtree. Collects the tasks necessary to create the missing texture
         * tiles, corresponding to newly created quads.
         */
        protected virtual void GetTiles(QuadTree parent, ref QuadTree tree, TerrainQuad quad)
        {
            //if tree not created, create a new tree and check if its tile is needed
            if (tree == null)
            {
                tree          = new QuadTree(parent);
                tree.needTile = NeedTile(quad);
            }

            //If this trees tile is needed get a tile and add its task to the schedular if the task is not already done
            if (tree.needTile && tree.tile == null)
            {
                tree.tile = m_producer.GetTile(quad.GetLevel(), quad.GetTX(), quad.GetTY());

                if (!tree.tile.GetTask().IsDone())
                {
                    //if task not done schedule task
                    m_manager.GetSchedular().Add(tree.tile.GetTask());
                }
            }

            if (!quad.IsLeaf() && m_producer.HasChildren(quad.GetLevel(), quad.GetTX(), quad.GetTY()))
            {
                for (int i = 0; i < 4; ++i)
                {
                    GetTiles(tree, ref tree.children[i], quad.GetChild(i));
                }
            }
        }
        protected virtual void SetScreenUniforms(TerrainNode node, TerrainQuad quad, MaterialPropertyBlock matPropertyBlock)
        {
            double ox = quad.GetOX();
            double oy = quad.GetOY();
            double l  = quad.GetLength();

            Vector3d2 p0 = new Vector3d2(ox, oy, 0.0);
            Vector3d2 p1 = new Vector3d2(ox + l, oy, 0.0);
            Vector3d2 p2 = new Vector3d2(ox, oy + l, 0.0);
            Vector3d2 p3 = new Vector3d2(ox + l, oy + l, 0.0);

            Matrix4x4d corners = new Matrix4x4d(p0.x, p1.x, p2.x, p3.x,
                                                p0.y, p1.y, p2.y, p3.y,
                                                p0.z, p1.z, p2.z, p3.z,
                                                1.0, 1.0, 1.0, 1.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadCorners, (m_localToScreen * corners).ToMatrix4x4());

            Matrix4x4d verticals = new Matrix4x4d(0.0, 0.0, 0.0, 0.0,
                                                  0.0, 0.0, 0.0, 0.0,
                                                  1.0, 1.0, 1.0, 1.0,
                                                  0.0, 0.0, 0.0, 0.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadVerticals, (m_localToScreen * verticals).ToMatrix4x4());
        }
        /*
         * Sets the shader uniforms that are necessary to project on screen the
         * given TerrainQuad. This method can set the uniforms that are specific to
         * the given quad.
         */
        public virtual void SetUniforms(TerrainNode node, TerrainQuad quad, MaterialPropertyBlock matPropertyBlock)
        {
            if (matPropertyBlock == null || node == null || quad == null)
            {
                return;
            }

            double ox         = quad.GetOX();
            double oy         = quad.GetOY();
            double l          = quad.GetLength();
            double distFactor = (double)node.GetDistFactor();
            int    level      = quad.GetLevel();

            matPropertyBlock.AddVector(m_uniforms.offset, new Vector4((float)ox, (float)oy, (float)l, (float)level));

            Vector3d2 camera = node.GetLocalCameraPos();

            matPropertyBlock.AddVector(m_uniforms.camera, new Vector4((float)((camera.x - ox) / l), (float)((camera.y - oy) / l),
                                                                      (float)((camera.z - node.GetView().GetGroundHeight()) / (l * distFactor)),
                                                                      (float)camera.z));

            Vector3d2 c = node.GetLocalCameraPos();

            Matrix3x3d m = m_localToTangent * (new Matrix3x3d(l, 0.0, ox - c.x, 0.0, l, oy - c.y, 0.0, 0.0, 1.0));

            matPropertyBlock.AddMatrix(m_uniforms.tileToTangent, m.ToMatrix4x4());

            SetScreenUniforms(node, quad, matPropertyBlock);
        }
Exemple #4
0
        void OnPostRender()
        {
            if (!on)
            {
                return;
            }

            for (int i = 0; i < terrainNode.Length; i++)
            {
                if (!terrainNode[i].activeInHierarchy)
                {
                    continue;
                }

                if (node[i] == null)
                {
                    continue;
                }

                TerrainQuad root = node[i].GetRoot();

                if (root == null)
                {
                    continue;
                }

                root.DrawQuadOutline(Camera.main.camera, lineMaterial, col[i % 6]);
            }
        }
Exemple #5
0
        /*
         * Updates the internal quadtree to make it identical to the given terrain
         * quadtree. This method releases the texture tiles corresponding to
         * deleted quads.
         */
        protected virtual void PutTiles(QuadTree tree, TerrainQuad quad)
        {
            if (tree == null)
            {
                return;
            }

            //Check if this tile is needed, if not put tile.
            tree.needTile = NeedTile(quad);

            if (!tree.needTile && tree.tile != null)
            {
                m_producer.PutTile(tree.tile);
                tree.tile = null;
            }

            //If this qiad is a leaf then all children of the tree are not needed
            if (quad.IsLeaf())
            {
                if (!tree.IsLeaf())
                {
                    tree.RecursiveDeleteChildren(this);
                }
            }
            else if (m_producer.HasChildren(quad.GetLevel(), quad.GetTX(), quad.GetTY()))
            {
                for (int i = 0; i < 4; ++i)
                {
                    PutTiles(tree.children[i], quad.GetChild(i));
                }
            }
        }
Exemple #6
0
        /*
         * Returns true if a tile is needed for the given terrain quad.
         */
        protected virtual bool NeedTile(TerrainQuad quad)
        {
            bool needTile = m_storeLeaf;

            //if the quad is not a leaf and producer has children
            //and if have been asked not to store parent then dont need tile
            if (!m_storeParent && !quad.IsLeaf() && m_producer.HasChildren(quad.GetLevel(), quad.GetTX(), quad.GetTY()))
            {
                needTile = false;
            }

            //Check if any of the filters have determined that this tile is not needed
            foreach (TileFilter filter in m_tileFilters)
            {
                if (filter.DiscardTile(quad))
                {
                    needTile = false;
                    break;
                }
            }

            //if this quad is not visilbe and have not been asked to store invisilbe quads dont need tile
            if (!m_storeInvisible && !quad.IsVisible())
            {
                needTile = false;
            }

            return(needTile);
        }
        //Creates the four subquads of this quad.
        void Subdivide()
        {
            float hl = (float)m_length / 2.0f;

            m_children[0] = new TerrainQuad(m_owner, this, 2 * m_tx, 2 * m_ty, m_ox, m_oy, hl, m_zmin, m_zmax);
            m_children[1] = new TerrainQuad(m_owner, this, 2 * m_tx + 1, 2 * m_ty, m_ox + hl, m_oy, hl, m_zmin, m_zmax);
            m_children[2] = new TerrainQuad(m_owner, this, 2 * m_tx, 2 * m_ty + 1, m_ox, m_oy + hl, hl, m_zmin, m_zmax);
            m_children[3] = new TerrainQuad(m_owner, this, 2 * m_tx + 1, 2 * m_ty + 1, m_ox + hl, m_oy + hl, hl, m_zmin, m_zmax);
        }
 /*
  * Creates a new TerrainQuad.
  *
  * param owner the TerrainNode to which the terrain quadtree belongs.
  * param parent the parent quad of this quad.
  * param tx the logical x coordinate of this quad.
  * param ty the logical y coordinate of this quad.
  * param ox the physical x coordinate of the lower left corner of this quad.
  * param oy the physical y coordinate of the lower left corner of this quad.
  * param l the physical size of this quad.
  * param zmin the minimum %terrain elevation inside this quad.
  * param zmax the maximum %terrain elevation inside this quad.
  */
 public TerrainQuad(TerrainNode owner, TerrainQuad parent, int tx, int ty, double ox, double oy, double length, float zmin, float zmax)
 {
     m_owner    = owner;
     m_parent   = parent;
     m_level    = (m_parent == null) ? 0 : m_parent.GetLevel() + 1;
     m_tx       = tx;
     m_ty       = ty;
     m_ox       = ox;
     m_oy       = oy;
     m_zmax     = zmax;
     m_zmin     = zmin;
     m_length   = length;
     m_localBox = new Box3d(m_ox, m_ox + m_length, m_oy, m_oy + m_length, m_zmin, m_zmax);
 }
        /*
         * Override the default TileSampler NeedTile to retrive the tile
         * that is below the camera as well as its default behaviour
         */
        protected override bool NeedTile(TerrainQuad quad)
        {
            Vector3d2 c  = quad.GetOwner().GetLocalCameraPos();
            int       l  = quad.GetLevel();
            double    ox = quad.GetOX();
            double    oy = quad.GetOY();

            if (c.x >= ox && c.x < ox + l && c.y >= oy && c.y < oy + l)
            {
                return(true);
            }

            return(base.NeedTile(quad));
        }
        protected override void SetScreenUniforms(TerrainNode node, TerrainQuad quad, MaterialPropertyBlock matPropertyBlock)
        {
            double ox = quad.GetOX();
            double oy = quad.GetOY();
            double l  = quad.GetLength();

            Vector3d2 p0 = new Vector3d2(ox, oy, R);
            Vector3d2 p1 = new Vector3d2(ox + l, oy, R);
            Vector3d2 p2 = new Vector3d2(ox, oy + l, R);
            Vector3d2 p3 = new Vector3d2(ox + l, oy + l, R);
            Vector3d2 pc = (p0 + p3) * 0.5;

            double    l0 = 0.0, l1 = 0.0, l2 = 0.0, l3 = 0.0;
            Vector3d2 v0 = p0.Normalized(ref l0);
            Vector3d2 v1 = p1.Normalized(ref l1);
            Vector3d2 v2 = p2.Normalized(ref l2);
            Vector3d2 v3 = p3.Normalized(ref l3);

            Matrix4x4d deformedCorners = new Matrix4x4d(v0.x * R, v1.x * R, v2.x * R, v3.x * R,
                                                        v0.y * R, v1.y * R, v2.y * R, v3.y * R,
                                                        v0.z * R, v1.z * R, v2.z * R, v3.z * R,
                                                        1.0, 1.0, 1.0, 1.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadCorners, (m_localToScreen * deformedCorners).ToMatrix4x4());

            Matrix4x4d deformedVerticals = new Matrix4x4d(v0.x, v1.x, v2.x, v3.x,
                                                          v0.y, v1.y, v2.y, v3.y,
                                                          v0.z, v1.z, v2.z, v3.z,
                                                          0.0, 0.0, 0.0, 0.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadVerticals, (m_localToScreen * deformedVerticals).ToMatrix4x4());
            matPropertyBlock.AddVector(m_uniforms.screenQuadCornerNorms, new Vector4((float)l0, (float)l1, (float)l2, (float)l3));

            Vector3d2 uz = pc.Normalized();
            Vector3d2 ux = (new Vector3d2(0, 1, 0)).Cross(uz).Normalized();
            Vector3d2 uy = uz.Cross(ux);

            Matrix4x4d ltow = node.GetLocalToWorld();

            Matrix3x3d tangentFrameToWorld = new Matrix3x3d(ltow.m[0, 0], ltow.m[0, 1], ltow.m[0, 2],
                                                            ltow.m[1, 0], ltow.m[1, 1], ltow.m[1, 2],
                                                            ltow.m[2, 0], ltow.m[2, 1], ltow.m[2, 2]);

            Matrix3x3d m = new Matrix3x3d(ux.x, uy.x, uz.x,
                                          ux.y, uy.y, uz.y,
                                          ux.z, uy.z, uz.z);

            matPropertyBlock.AddMatrix(m_uniforms.tangentFrameToWorld, (tangentFrameToWorld * m).ToMatrix4x4());
        }
        protected override void GetTiles(QuadTree parent, ref QuadTree tree, TerrainQuad quad)
        {
            if (tree == null)
            {
                tree          = new QuadTreeZ(parent, quad);
                tree.needTile = NeedTile(quad);
            }

            QuadTreeZ t = tree as QuadTreeZ;

            //If tile needs elevation data read back add to container
            if (t.tile != null && t.tile.GetTask().IsDone() && !t.readBack && m_maxReadBacksPerFrame > 0)
            {
                if (!m_needReadBack.ContainsKey(t.tile.GetId()))
                {
                    t.readBack = true;
                    m_needReadBack.Add(t.tile.GetId(), t);
                }
            }

            base.GetTiles(parent, ref tree, quad);

            //Check if this quad is below the camera. If so store a reference to it.
            if (m_cameraQuad == null && t.tile != null && t.tile.GetTask().IsDone())
            {
                Vector3d2 c = quad.GetOwner().GetLocalCameraPos();

                double l  = quad.GetLength();
                double ox = quad.GetOX();
                double oy = quad.GetOY();

                if (c.x >= ox && c.x < ox + l && c.y >= oy && c.y < oy + l)
                {
                    m_cameraQuadCoords = new Vector2((float)((c.x - ox) / l), (float)((c.y - oy) / l));
                    m_cameraQuad       = t;
                }
            }
        }
Exemple #12
0
 //Creates the four subquads of this quad.
 void Subdivide()
 {
     float hl = (float) m_length / 2.0f;
     m_children[0] = new TerrainQuad(m_owner, this, 2 * m_tx, 2 * m_ty, m_ox, m_oy, hl, m_zmin, m_zmax);
     m_children[1] = new TerrainQuad(m_owner, this, 2 * m_tx + 1, 2 * m_ty, m_ox + hl, m_oy, hl, m_zmin, m_zmax);
     m_children[2] = new TerrainQuad(m_owner, this, 2 * m_tx, 2 * m_ty + 1, m_ox, m_oy + hl, hl, m_zmin, m_zmax);
     m_children[3] = new TerrainQuad(m_owner, this, 2 * m_tx + 1, 2 * m_ty + 1, m_ox + hl, m_oy + hl, hl, m_zmin, m_zmax);
 }
Exemple #13
0
 /**
 * Creates a new TerrainQuad.
 *
 * param owner the TerrainNode to which the terrain quadtree belongs.
 * param parent the parent quad of this quad.
 * param tx the logical x coordinate of this quad.
 * param ty the logical y coordinate of this quad.
 * param ox the physical x coordinate of the lower left corner of this quad.
 * param oy the physical y coordinate of the lower left corner of this quad.
 * param l the physical size of this quad.
 * param zmin the minimum %terrain elevation inside this quad.
 * param zmax the maximum %terrain elevation inside this quad.
 */
 public TerrainQuad(TerrainNode owner, TerrainQuad parent, int tx, int ty, double ox, double oy, double length, float zmin, float zmax)
 {
     m_owner = owner;
     m_parent = parent;
     m_level = (m_parent == null) ? 0 : m_parent.GetLevel() + 1;
     m_tx = tx;
     m_ty = ty;
     m_ox = ox;
     m_oy = oy;
     m_zmax = zmax;
     m_zmin = zmin;
     m_length = length;
     m_localBox = new Box3d(m_ox, m_ox + m_length, m_oy, m_oy + m_length, m_zmin, m_zmax);
 }
Exemple #14
0
        protected virtual void SetScreenUniforms(TerrainNode node, TerrainQuad quad, MaterialPropertyBlock matPropertyBlock)
        {
            double ox = quad.GetOX();
            double oy = quad.GetOY();
            double l = quad.GetLength();

            Vector3d2 p0 = new Vector3d2(ox, oy, 0.0);
            Vector3d2 p1 = new Vector3d2(ox + l, oy, 0.0);
            Vector3d2 p2 = new Vector3d2(ox, oy + l, 0.0);
            Vector3d2 p3 = new Vector3d2(ox + l, oy + l, 0.0);

            Matrix4x4d corners = new Matrix4x4d(p0.x, p1.x, p2.x, p3.x,
                                                p0.y, p1.y, p2.y, p3.y,
                                                p0.z, p1.z, p2.z, p3.z,
                                                1.0, 1.0, 1.0, 1.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadCorners, (m_localToScreen * corners).ToMatrix4x4());

            Matrix4x4d verticals = new Matrix4x4d(	0.0, 0.0, 0.0, 0.0,
                                                  0.0, 0.0, 0.0, 0.0,
                                                  1.0, 1.0, 1.0, 1.0,
                                                  0.0, 0.0, 0.0, 0.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadVerticals, (m_localToScreen * verticals).ToMatrix4x4());
        }
Exemple #15
0
        /**
        * Sets the shader uniforms that are necessary to project on screen the
        * given TerrainQuad. This method can set the uniforms that are specific to
        * the given quad.
        */
        public virtual void SetUniforms(TerrainNode node, TerrainQuad quad, MaterialPropertyBlock matPropertyBlock)
        {
            if(matPropertyBlock == null || node == null || quad == null) return;

            double ox = quad.GetOX();
            double oy = quad.GetOY();
            double l = quad.GetLength();
            double distFactor = (double)node.GetDistFactor();
            int level = quad.GetLevel();

            matPropertyBlock.AddVector(m_uniforms.offset, new Vector4((float)ox, (float)oy, (float)l, (float)level));

            Vector3d2 camera = node.GetLocalCameraPos();

            matPropertyBlock.AddVector(m_uniforms.camera, new Vector4(	(float)((camera.x - ox) / l), (float)((camera.y - oy) / l),
                                                                      (float)((camera.z - node.GetView().GetGroundHeight()) / (l * distFactor)),
                                                                      (float)camera.z));

            Vector3d2 c = node.GetLocalCameraPos();

            Matrix3x3d m = m_localToTangent * (new Matrix3x3d(l, 0.0, ox - c.x, 0.0, l, oy - c.y, 0.0, 0.0, 1.0));

            matPropertyBlock.AddMatrix(m_uniforms.tileToTangent, m.ToMatrix4x4());

            SetScreenUniforms(node, quad, matPropertyBlock);
        }
 public QuadTreeZ(QuadTree parent, TerrainQuad quad)
     : base(parent)
 {
     this.quad = quad;
     readBack  = false;
 }
Exemple #17
0
        /*
         * Returns true if a texture tile must be produced for the given quad.
         */

        public abstract bool DiscardTile(TerrainQuad q);
		/*
		* Override the default TileSampler NeedTile to retrive the tile 
		* that is below the camera as well as its default behaviour
	 	*/
		protected override bool NeedTile(TerrainQuad quad)
		{
			Vector3d2 c = quad.GetOwner().GetLocalCameraPos();
			int l = quad.GetLevel();
			double ox = quad.GetOX();
			double oy = quad.GetOY();
			
			if (c.x >= ox && c.x < ox + l && c.y >= oy && c.y < oy + l) {
				return true;
			}
			
			return base.NeedTile(quad);
		}
		protected override void GetTiles(QuadTree parent, ref QuadTree tree, TerrainQuad quad)
		{
			if (tree == null) 
			{
				tree = new QuadTreeZ(parent, quad);
				tree.needTile = NeedTile(quad);
			}
			
			QuadTreeZ t = tree as QuadTreeZ;
			
			//If tile needs elevation data read back add to container
			if(t.tile != null && t.tile.GetTask().IsDone() && !t.readBack && m_maxReadBacksPerFrame > 0)
			{
				if(!m_needReadBack.ContainsKey(t.tile.GetId()))
				{
					t.readBack = true;
					m_needReadBack.Add(t.tile.GetId(), t);
				}
			}
			
			base.GetTiles(parent, ref tree, quad);
			
			//Check if this quad is below the camera. If so store a reference to it.
			if (m_cameraQuad == null && t.tile != null && t.tile.GetTask().IsDone()) 
			{
				Vector3d2 c = quad.GetOwner().GetLocalCameraPos();
				
				double l = quad.GetLength();
				double ox = quad.GetOX();
				double oy = quad.GetOY();
				
				if (c.x >= ox && c.x < ox + l && c.y >= oy && c.y < oy + l) 
				{
					m_cameraQuadCoords = new Vector2((float)((c.x - ox) / l), (float)((c.y - oy) / l));
					m_cameraQuad = t;
				}
			}
		}
			public QuadTreeZ(QuadTree parent, TerrainQuad quad) 
				: base(parent) 
			{
				this.quad = quad;
				readBack = false;
			}
        protected override void SetScreenUniforms(TerrainNode node, TerrainQuad quad, MaterialPropertyBlock matPropertyBlock)
        {
            double ox = quad.GetOX();
            double oy = quad.GetOY();
            double l = quad.GetLength();

            Vector3d2 p0 = new Vector3d2(ox, oy, R);
            Vector3d2 p1 = new Vector3d2(ox + l, oy, R);
            Vector3d2 p2 = new Vector3d2(ox, oy + l, R);
            Vector3d2 p3 = new Vector3d2(ox + l, oy + l, R);
            Vector3d2 pc = (p0 + p3) * 0.5;

            double l0 = 0.0, l1 = 0.0, l2 = 0.0, l3 = 0.0;
            Vector3d2 v0 = p0.Normalized(ref l0);
            Vector3d2 v1 = p1.Normalized(ref l1);
            Vector3d2 v2 = p2.Normalized(ref l2);
            Vector3d2 v3 = p3.Normalized(ref l3);

            Matrix4x4d deformedCorners = new Matrix4x4d(v0.x * R, v1.x * R, v2.x * R, v3.x * R,
                                                        v0.y * R, v1.y * R, v2.y * R, v3.y * R,
                                                        v0.z * R, v1.z * R, v2.z * R, v3.z * R,
                                                        1.0, 1.0, 1.0, 1.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadCorners, (m_localToScreen * deformedCorners).ToMatrix4x4());

            Matrix4x4d deformedVerticals = new Matrix4x4d(	v0.x, v1.x, v2.x, v3.x,
                                                          v0.y, v1.y, v2.y, v3.y,
                                                          v0.z, v1.z, v2.z, v3.z,
                                                          0.0, 0.0, 0.0, 0.0);

            matPropertyBlock.AddMatrix(m_uniforms.screenQuadVerticals, (m_localToScreen * deformedVerticals).ToMatrix4x4());
            matPropertyBlock.AddVector(m_uniforms.screenQuadCornerNorms, new Vector4((float)l0, (float)l1, (float)l2, (float)l3));

            Vector3d2 uz = pc.Normalized();
            Vector3d2 ux = (new Vector3d2(0,1,0)).Cross(uz).Normalized();
            Vector3d2 uy = uz.Cross(ux);

            Matrix4x4d ltow = node.GetLocalToWorld();

            Matrix3x3d tangentFrameToWorld = new Matrix3x3d(ltow.m[0,0], ltow.m[0,1], ltow.m[0,2],
                                                            ltow.m[1,0], ltow.m[1,1], ltow.m[1,2],
                                                            ltow.m[2,0], ltow.m[2,1], ltow.m[2,2]);

            Matrix3x3d m = new Matrix3x3d(	ux.x, uy.x, uz.x,
                                          ux.y, uy.y, uz.y,
                                          ux.z, uy.z, uz.z);

            matPropertyBlock.AddMatrix(m_uniforms.tangentFrameToWorld, (tangentFrameToWorld * m).ToMatrix4x4());
        }
Exemple #22
0
		/*
         * Returns true if a texture tile must be produced for the given quad.
         */
	
		public abstract bool DiscardTile(TerrainQuad q);