Esempio n. 1
0
        protected override void Initialise()
        {
            Resource.EnableResourceTracking();

            //draw targets usually need a camera.
            Xen.Ex.Camera.FirstPersonControlledCamera3D camera = new Xen.Ex.Camera.FirstPersonControlledCamera3D(this.UpdateManager, Vector3.Zero, false);

            //don't allow the camera to move too fast
            camera.MovementSensitivity *= 0.1f;
            camera.LookAt(new Vector3(0, 3, 0), new Vector3(1, 5, 10), new Vector3(0, 1, 0));

            //create the draw target.
            drawToScreen = new DrawTargetScreen(this, camera);
            drawToScreen.ClearBuffer.ClearColour = new Color(45, 50, 60);


            //create the fire and smoke particle system
            this.fireParticleSystem  = new ParticleSystem(this.UpdateManager);
            this.smokeParticleSystem = new ParticleSystem(this.UpdateManager);

            //IMPORTANT
            //The following flags are FALSE by default.
            //For looping effects, such as the fire and smoke, it's highly
            //recommended to enable this flag. Otherwise, while the effect
            //is offscreen, the particle system will continue to process.
            this.fireParticleSystem.PauseUpdatingWhileCulled  = true;
            this.smokeParticleSystem.PauseUpdatingWhileCulled = true;


            this.drawSorted   = new Xen.Ex.Scene.DepthDrawSorter(Xen.Ex.Scene.DepthSortMode.BackToFront);
            this.drawUnsorted = new DrawList();

            Xen.Ex.Graphics.Display.ParticleDrawer3D fireDrawer  = new Xen.Ex.Graphics.Display.VelocityBillboardParticles3D(this.fireParticleSystem, true);
            Xen.Ex.Graphics.Display.ParticleDrawer3D smokeDrawer = new Xen.Ex.Graphics.Display.BillboardParticles3D(this.smokeParticleSystem);

            for (int i = 0; i < 10; i++)
            {
                Vector3 position = new Vector3((float)Math.Cos(i * Math.PI / 5.0) * 6.0f, 0, (float)Math.Sin(i * Math.PI / 5.0) * 6.0f);

                CullableParticleWrapper fireEffect, smokeEffect;

                fireEffect  = new CullableParticleWrapper(fireDrawer, position, new Vector3(0, 2, 0), 4);
                smokeEffect = new CullableParticleWrapper(smokeDrawer, position, new Vector3(0, 6, 0), 5);

                this.drawSorted.Add(fireEffect);
                this.drawSorted.Add(smokeEffect);

                this.drawUnsorted.Add(fireEffect);
                this.drawUnsorted.Add(smokeEffect);

                GroundLightDisk light = new GroundLightDisk(position);
                this.drawSorted.Add(light);
                this.drawUnsorted.Add(light);
            }


            //setup the burst effect
            this.burstParticleSystem = new ParticleSystem(this.UpdateManager);

            //for this case, PauseUpdatingWhileCulled is not set to true.
            //The particle emitting is culled when offscreen. If set to true,
            //Any particles left offscreen could 'pause', when they naturally
            //wouldn't be emitted anyway.
            //(The particle system will use very few resources when it has no
            //active particles)

            this.burstSources = new BurstSource[20];
            Random rand = new Random();

            for (int i = 0; i < this.burstSources.Length; i++)
            {
                //create the bursts out in the distance
                Vector3 position = new Vector3((float)i * 5.0f - this.burstSources.Length * 2.5f, 0, -20);
                float   radius   = 10;             // with a decent radius

                //give them a random starting time
                this.burstSources[i] = new BurstSource(position, radius, (float)rand.NextDouble() * 2);

                this.drawSorted.Add(this.burstSources[i]);
                this.drawUnsorted.Add(this.burstSources[i]);
            }

            //the bursts need to be drawn as a group..
            ParticleDrawer3D burstDrawer = new Xen.Ex.Graphics.Display.VelocityBillboardParticles3D(this.burstParticleSystem, false, 0.5f);

            this.drawSorted.Add(burstDrawer);
            this.drawUnsorted.Add(burstDrawer);

            //Use all the burst sources to cull the drawer (may not be ideal if there were many sources...)
            //Use the particle drawer CullProxy to do it
            burstDrawer.CullProxy = new BurstCullProxy(this.burstSources);



            //add a ground plane to show the horizon
            drawToScreen.Add(new Tutorial_22.DarkGroundPlane(new Vector4(0.125f, 0.15f, 0.135f, 1)));

            //add the sorted and unsorted lists
            drawToScreen.Add(drawSorted);
            drawToScreen.Add(drawUnsorted);


            //finally, create a CullTestVisualizer, which will visually show the cull tests performed
            cullTestVisualizer = new Xen.Ex.Scene.CullTestVisualizer(this.drawToScreen.Camera);

            //the visualizer is added as a draw modifier
            this.drawToScreen.AddModifier(cullTestVisualizer);

            //add help text
            this.text = new TextElement();
            this.text.VerticalAlignment = VerticalAlignment.Bottom;
            this.text.Position          = new Vector2(50, 100);
            drawToScreen.Add(this.text);

            //add draw stats
            stats = new Xen.Ex.Graphics2D.Statistics.DrawStatisticsDisplay(this.UpdateManager);
            drawToScreen.Add(stats);
        }
		protected override void Initialise()
		{
			//draw targets usually need a camera.
			var camera = new Xen.Camera.FirstPersonControlledCamera3D(this.UpdateManager, Vector3.Zero, false);

			//don't allow the camera to move too fast
			camera.MovementSensitivity *= 0.1f;
			camera.LookAt(new Vector3(0,3,0), new Vector3(1, 5, 10), new Vector3(0, 1, 0));
			
			//create the draw target.
			drawToScreen = new DrawTargetScreen(camera);
			drawToScreen.ClearBuffer.ClearColour = new Color(45,50,60);

			
			//create the fire and smoke particle system
			this.fireParticleSystem = new ParticleSystem(this.UpdateManager);
			this.smokeParticleSystem = new ParticleSystem(this.UpdateManager);

			//IMPORTANT
			//The following flags are FALSE by default.
			//For looping effects, such as the fire and smoke, it's highly
			//recommended to enable this flag. Otherwise, while the effect
			//is offscreen, the particle system will continue to process.
			this.fireParticleSystem.PauseUpdatingWhileCulled = true;
			this.smokeParticleSystem.PauseUpdatingWhileCulled = true;


			this.drawSorted = new Xen.Ex.Scene.DepthDrawSorter(Xen.Ex.Scene.DepthSortMode.BackToFront);
			this.drawUnsorted = new DrawList();

			var fireDrawer = new Xen.Ex.Graphics.Display.VelocityBillboardParticles3D(this.fireParticleSystem, true);
			var smokeDrawer = new Xen.Ex.Graphics.Display.BillboardParticles3D(this.smokeParticleSystem);

			for (int i = 0; i < 10; i++)
			{
				Vector3 position = new Vector3((float)Math.Cos(i * Math.PI / 5.0) * 6.0f, 0, (float)Math.Sin(i * Math.PI / 5.0) * 6.0f);
				
				CullableParticleWrapper fireEffect, smokeEffect;

				fireEffect = new CullableParticleWrapper(fireDrawer, position, new Vector3(0, 2, 0), 4);
				smokeEffect = new CullableParticleWrapper(smokeDrawer, position, new Vector3(0, 6, 0), 5);

				this.drawSorted.Add(fireEffect);
				this.drawSorted.Add(smokeEffect);

				this.drawUnsorted.Add(fireEffect);
				this.drawUnsorted.Add(smokeEffect);

				var light = new GroundLightDisk(position);
				this.drawSorted.Add(light);
				this.drawUnsorted.Add(light);
			}


			//setup the burst effect
			this.burstParticleSystem = new ParticleSystem(this.UpdateManager);

			//for this case, PauseUpdatingWhileCulled is not set to true.
			//The particle emitting is culled when offscreen. If set to true,
			//Any particles left offscreen could 'pause', when they naturally
			//wouldn't be emitted anyway.
			//(The particle system will use very few resources when it has no
			//active particles)

			this.burstSources = new BurstSource[20];
			Random rand = new Random();

			for (int i = 0; i < this.burstSources.Length; i++)
			{
				//create the bursts out in the distance
				Vector3 position = new Vector3((float)i * 5.0f - this.burstSources.Length * 2.5f, 0, -20); 
				float radius = 10; // with a decent radius

				//give them a random starting time
				this.burstSources[i] = new BurstSource(position, radius, (float)rand.NextDouble() * 2);

				this.drawSorted.Add(this.burstSources[i]);
				this.drawUnsorted.Add(this.burstSources[i]);
			}

			//the bursts need to be drawn as a group..
			var burstDrawer = new Xen.Ex.Graphics.Display.VelocityBillboardParticles3D(this.burstParticleSystem,false,0.5f);

			this.drawSorted.Add(burstDrawer);
			this.drawUnsorted.Add(burstDrawer);

			//Use all the burst sources to cull the drawer (may not be ideal if there were many sources...)
			//Use the particle drawer CullProxy to do it
			burstDrawer.CullProxy = new BurstCullProxy(this.burstSources);
			


			//add a ground plane to show the horizon
			drawToScreen.Add(new Tutorial_22.DarkGroundPlane(new Vector4(0.125f,0.15f,0.135f,1)));

			//add the sorted and unsorted lists
			drawToScreen.Add(drawSorted);
			drawToScreen.Add(drawUnsorted);


			//finally, create a CullTestVisualizer, which will visually show the cull tests performed
			cullTestVisualizer = new Xen.Ex.Scene.CullTestVisualizer();

			//the visualizer is added as a draw modifier
			this.drawToScreen.AddModifier(cullTestVisualizer);

			//add help text
			this.text = new TextElement();
			this.text.VerticalAlignment = VerticalAlignment.Bottom;
			this.text.Position = new Vector2(50, 100);
			drawToScreen.Add(this.text);

			//add draw stats
			stats = new Xen.Ex.Graphics2D.Statistics.DrawStatisticsDisplay(this.UpdateManager);
			drawToScreen.Add(stats);
		}
		protected override void Initialise()
		{
			//create the camera
			Xen.Camera.FirstPersonControlledCamera3D camera = 
				new Xen.Camera.FirstPersonControlledCamera3D(this.UpdateManager,Vector3.Zero);
			camera.Projection.FarClip *= 10;

			this.camera = camera;


			//create the draw target.
			drawToScreen = new DrawTargetScreen(camera);

			//25,000 instances
			const int instanceCount = 25000;
			const float areaRadius = 500;

			//setup the two draw lists
			this.staticDrawList = new ToggleDrawList();
			this.dynamicDrawList = new ToggleDrawList();

			//geometry that will be drawn
			var geometry = new Xen.Ex.Geometry.Sphere(Vector3.One, 2, true, false, false);

			//create the mesh instance drawer, (but add it to the screen later)
			var meshDrawer = new DynamicInstancedMeshGeometry(instanceCount, geometry);
			var staticMeshDrawer = new StaticInstancedMeshGeometry(instanceCount, geometry);

			//the dynamicly culled instances are added to a StaticBinaryTreePartition, which 
			//sorts the items into a binary tree, for more efficient culling.
			//This class assumes it's children do not move (ie they are static)

			var sceneTree = new Xen.Ex.Scene.StaticBinaryTreePartition();

			//add it to the dynamic list
			dynamicDrawList.Children.Add(sceneTree);



			//create the instances
			Random random = new Random();

			for (int i = 0; i < instanceCount; i++)
			{
				//create a random position in a sphere
				Vector3 position = new Vector3(	(float)(random.NextDouble()-.5),
												(float)(random.NextDouble()-.5),
												(float)(random.NextDouble()-.5));
				position.Normalize();
				position *= (float)Math.Sqrt(random.NextDouble()) * areaRadius;


				//create the instance
				var instance = new DynamicMeshInstance(meshDrawer, position);

				//add the instance to the StaticBinaryTreePartition
				sceneTree.Add(instance);


				//add the details of this instance to the static drawer
				staticMeshDrawer.AddStaticInstance(Matrix.CreateTranslation(position), 1);
			}

			//now add the drawer (instances will be drawn by the StaticBinaryPartition, before the drawer)
			dynamicDrawList.Children.Add(meshDrawer);

			//now add the static mesh drawer
			staticDrawList.Children.Add(staticMeshDrawer);

			//finally, add them both to the screen
			this.drawToScreen.Add(dynamicDrawList);
			this.drawToScreen.Add(staticDrawList);

			//Note that if the StaticBinaryTreePartition was not used, then 
			//in each frame, every single instance would perform a CullTest to the screen
			//CullTests, despite their simplicity can be very costly in large numbers.
			//The StaticBinaryTreePartition will usually perform a maximum number of CullTests
			//that is approximately ~30% the number of children. (in this case, ~8000 tests)
			//At it's best, when it's entirely off or on screen, it will perform only 1 or 2 CullTests.
			
			//The number of cull tests performed will be displayed in debug builds of this tutorial:

			//add some statusText to display on screen to show the stats
			statusText = new TextElement();
			statusText.Position = new Vector2(50, -50);
			drawToScreen.Add(statusText);

			//add the cull test visualiser
			this.cullVis = new Xen.Ex.Scene.CullTestVisualizer();
			drawToScreen.AddModifier(cullVis);
		}