Beispiel #1
0
 public void Dispose()
 {
     DefaultBlendState?.Dispose();
     AlphaBlendState?.Dispose();
     AlphaDarkenState?.Dispose();
     Checkers?.Dispose();
 }
Beispiel #2
0
 public void Dispose()
 {
     DefaultBlendState?.Dispose();
     AlphaBlendState?.Dispose();
     AlphaDarkenState?.Dispose();
     LinearSampler?.Dispose();
     PointSampler?.Dispose();
     Checkers?.Dispose();
 }
		/// <summary>
		/// draws the particles on a GPU system
		/// </summary>
		protected override void DrawGpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Texture2D positionTex, Texture2D velocityRotation, Texture2D colourTex, Texture2D userValues, bool usesUserValuesPositionBuffer)
		{
			Vector2 targetSize = state.DrawTarget.Size;

			state.RenderState.Push();
			state.RenderState.CurrentBlendState = blendMode;
			state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

			//get the shared vertice
			VelocityLineParticles2DElement.GenerateLinesVertices(state, ref vertices);

			int count = (int)particleCount;

			DrawVelocityParticles_LinesGpuTex shaderNoColour = null;
			DrawVelocityParticlesColour_LinesGpuTex shaderColour = null;
			//user variants
			DrawVelocityParticles_LinesGpuTex_UserOffset shaderNoColour_UO = null;
			DrawVelocityParticlesColour_LinesGpuTex_UserOffset shaderColour_UO = null;

			float resolutionXF = (float)positionTex.Width;
			float resolutionYF = (float)positionTex.Height;

			Vector2 invTextureSize;

			Vector2 velScale = new Vector2(velocityScale, 0);
			if (this.useRotationToScaleVelocityEffect)
				velScale = new Vector2(0, velocityScale);
			invTextureSize = new Vector2(1.0f / resolutionXF, 1.0f / resolutionYF);


			IShader shader;
			if (!usesUserValuesPositionBuffer)
			{
				if (colourTex != null)
				{
					shader = shaderColour = state.GetShader<DrawVelocityParticlesColour_LinesGpuTex>();

					shaderColour.PositionTexture = positionTex;
					shaderColour.ColourTexture = colourTex;
					shaderColour.VelocityTexture = velocityRotation;

					shaderColour.SetVelocityScale(ref velScale);
				}
				else
				{
					shader = shaderNoColour = state.GetShader<DrawVelocityParticles_LinesGpuTex>();

					shaderNoColour.PositionTexture = positionTex;
					shaderNoColour.VelocityTexture = velocityRotation;

					shaderNoColour.SetVelocityScale(ref velScale);
				}
			}
			else
			{
				if (colourTex != null)
				{
					shader = shaderColour_UO = state.GetShader<DrawVelocityParticlesColour_LinesGpuTex_UserOffset>();

					shaderColour_UO.PositionTexture = positionTex;
					shaderColour_UO.ColourTexture = colourTex;
					shaderColour_UO.VelocityTexture = velocityRotation;

					shaderColour_UO.SetVelocityScale(ref velScale);
				}
				else
				{
					shader = shaderNoColour_UO = state.GetShader<DrawVelocityParticles_LinesGpuTex_UserOffset>();

					shaderNoColour_UO.PositionTexture = positionTex;
					shaderNoColour_UO.VelocityTexture = velocityRotation;

					shaderNoColour_UO.SetVelocityScale(ref velScale);
				}
			}


			int drawn = 0;
			while (count > 0)
			{
				int drawCount = Math.Min(count, vertices.Count / 4);

				if (!usesUserValuesPositionBuffer)
				{
					if (colourTex != null)
						shaderColour.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
					else
						shaderNoColour.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
				}
				else
				{
					if (colourTex != null)
						shaderColour_UO.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
					else
						shaderNoColour_UO.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
				}

				//bind
				using (state.Shader.Push(shader))
				{
					//draw!
					vertices.Draw(state, null, PrimitiveType.LineList, drawCount, 0, 0);
				}

				count -= drawCount;
				drawn += drawCount;
			}


			state.RenderState.Pop();
		}
		/// <summary>
		/// draws the particles from a CPU system
		/// </summary>
		protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
		{
			Vector2 targetSize = state.DrawTarget.Size;

			state.RenderState.Push();
			state.RenderState.CurrentBlendState = blendMode;
			state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

			VelocityLineParticles2DElement.GenerateLinesVertices(state, ref this.vertices);


			int count = (int)particleCount;



			DrawVelocityParticles_LinesCpu shaderNoColour = null;
			DrawVelocityParticlesColour_LinesCpu shaderColour = null;

			if (colourData != null)
				shaderColour = state.GetShader<DrawVelocityParticlesColour_LinesCpu>();
			else
				shaderNoColour = state.GetShader<DrawVelocityParticles_LinesCpu>();

			Vector2 velScale = new Vector2(velocityScale, 0);
			if (this.useRotationToScaleVelocityEffect)
				velScale = new Vector2(0, velocityScale);

			int drawn = 0;
			while (count > 0)
			{
				int drawCount;

				drawCount = Math.Min(count, 80);
				uint drawCountU = (uint)drawCount;
				uint drawnU = (uint)drawn;

				if (colourData != null)
				{
					shaderColour.SetPositionData(positionSize, drawnU, 0, drawCountU);
					shaderColour.SetVelocityData(velocityRotation, drawnU, 0, drawCountU);
					shaderColour.SetColourData(colourData, drawnU, 0, drawCountU);

					shaderColour.SetVelocityScale(ref velScale);

					state.Shader.Push(shaderColour);
				}
				else
				{
					shaderNoColour.SetPositionData(positionSize, drawnU, 0, drawCountU);
					shaderNoColour.SetVelocityData(velocityRotation, drawnU, 0, drawCountU);

					shaderNoColour.SetVelocityScale(ref velScale);

					state.Shader.Push(shaderNoColour);
				}

				vertices.Draw(state, null, PrimitiveType.LineList, drawCount, 0, 0);

				state.Shader.Pop();

				count -= drawCount;
				drawn += drawCount;
			}


			state.RenderState.Pop();
		}
Beispiel #5
0
 /// <summary>
 /// This method is only present on Windows builds
 /// </summary>
 /// <param name="blendMode"></param><param name="colour"></param><param name="count"></param><param name="particleType"></param>
 /// <param name="positionSize"></param><param name="state"></param><param name="userValues"></param><param name="velocityRotation"></param>
 protected abstract void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint count, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colour, Vector4[] userValues);
Beispiel #6
0
 /// <summary>
 /// <para>Method to override to draw 3D particles</para>
 /// <para>Note: When 'usesUserValuesPositionBuffer' is true, the values 'user1, user2 and user3' (yzw in the UserTexture) store a position offset for the particle</para></summary>
 /// <param name="state"></param><param name="particleType"></param><param name="count"></param><param name="blendMode"></param>
 /// <param name="positionSize"></param><param name="velocityRotation"></param><param name="colour"></param><param name="userValues"></param><param name="usesUserValuesPositionBuffer"></param>
 protected abstract void DrawGpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint count, AlphaBlendState blendMode, Texture2D positionSize, Texture2D velocityRotation, Texture2D colour, Texture2D userValues, bool usesUserValuesPositionBuffer);
Beispiel #7
0
        /// <summary>
        /// implements the method to draw cpu particles
        /// </summary>
        protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
        {
            //this is a bit more complex, but mostly the same as the GPU draw method
            Vector2 targetSize = state.DrawTarget.Size;

            state.PushRenderState();
            state.RenderState.AlphaBlend = blendMode;
            state.RenderState.DepthColourCull.DepthWriteEnabled = false;

            Texture2D displayTexture = particleType.Texture ?? Xen.Ex.Material.WhiteTexture.GetTexture(state);

            GenerateBillboardVertices(state, ref this.vertices, ref this.indices);


            int count = (int)particleCount;

            DrawBillboardParticles_BillboardCpu       shaderNoColour = null;
            DrawBillboardParticlesColour_BillboardCpu shaderColour   = null;

            if (positionBuffer == null)
            {
                positionBuffer = GetPositionBuffer(state, positionBuffer);
            }

            if (colourData != null)
            {
                shaderColour = state.GetShader <DrawBillboardParticlesColour_BillboardCpu>();
            }
            else
            {
                shaderNoColour = state.GetShader <DrawBillboardParticles_BillboardCpu>();
            }

            int drawn = 0;

            while (count > 0)
            {
                int drawCount;

                drawCount = Math.Min(count, 120);

                //the only major difference from the GPU drawer is here
                for (int i = 0; i < drawCount; i++)
                {
                    //copy position xy and w (size), and velocity.w (rotation)
                    positionBuffer[i]   = positionSize[drawn + i];
                    positionBuffer[i].Z = velocityRotation[drawn + i].W;
                }

                if (colourData != null)
                {
                    shaderColour.PositionData.SetArray(positionBuffer, 0);
                    shaderColour.ColourData.SetArray(colourData, drawn);

                    shaderColour.DisplayTexture = displayTexture;

                    shaderColour.Bind(state);
                }
                else
                {
                    shaderNoColour.PositionData.SetArray(positionBuffer, 0);

                    shaderNoColour.DisplayTexture = displayTexture;

                    shaderNoColour.Bind(state);
                }

                vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

                count -= drawCount;
                drawn += drawCount;
            }


            state.PopRenderState();
        }
        //draws on CPU particle systems
        /// <summary>
        /// draws the particles from a CPU system
        /// </summary>
        protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
        {
            //this is very similar to the billboard drawer (see it for reference)
            Vector2 targetSize = state.DrawTarget.Size;

            state.PushRenderState();
            state.RenderState.AlphaBlend = blendMode;
            state.RenderState.DepthColourCull.DepthWriteEnabled = false;

            Texture2D displayTexture = particleType.Texture ?? Xen.Ex.Material.WhiteTexture.GetTexture(state);

            BillboardParticles2DElement.GenerateBillboardVertices(state, ref this.vertices, ref this.indices);


            int count = (int)particleCount;



            DrawVelocityParticles_BillboardCpu       shaderNoColour = null;
            DrawVelocityParticlesColour_BillboardCpu shaderColour   = null;


            if (colourData != null)
            {
                shaderColour = state.GetShader <DrawVelocityParticlesColour_BillboardCpu>();
            }
            else
            {
                shaderNoColour = state.GetShader <DrawVelocityParticles_BillboardCpu>();
            }

            Vector2 velScale = new Vector2(velocityScale, 0);

            if (this.useRotationToScaleVelocityEffect)
            {
                velScale = new Vector2(0, velocityScale);
            }

            int drawn = 0;

            while (count > 0)
            {
                int drawCount;

                drawCount = Math.Min(count, 80);

                if (colourData != null)
                {
                    shaderColour.PositionData.SetArray(positionSize, drawn);
                    shaderColour.VelocityData.SetArray(velocityRotation, drawn);
                    shaderColour.ColourData.SetArray(colourData, drawn);

                    shaderColour.DisplayTexture = displayTexture;
                    shaderColour.SetVelocityScale(ref velScale);

                    shaderColour.Bind(state);
                }
                else
                {
                    shaderNoColour.PositionData.SetArray(positionSize, drawn);
                    shaderNoColour.VelocityData.SetArray(velocityRotation, drawn);

                    shaderNoColour.DisplayTexture = displayTexture;
                    shaderNoColour.SetVelocityScale(ref velScale);

                    shaderNoColour.Bind(state);
                }

                vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

                count -= drawCount;
                drawn += drawCount;
            }


            state.PopRenderState();
        }
		/// <summary>
		/// implements the method to draw cpu particles
		/// </summary>
		protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
		{
			//this is a bit more complex, but mostly the same as the GPU draw method
			Vector2 targetSize = state.DrawTarget.Size;

			state.RenderState.Push();
			state.RenderState.CurrentBlendState = blendMode;
			state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

			Texture2D displayTexture = particleType.Texture ?? state.Properties.WhiteTexture;

			GenerateBillboardVertices(state, ref this.vertices, ref this.indices);


			int count = (int)particleCount;

			DrawBillboardParticles_BillboardCpu shaderNoColour = null;
			DrawBillboardParticlesColour_BillboardCpu shaderColour = null;

			if (positionBuffer == null)
			{
				positionBuffer = GetPositionBuffer(state, positionBuffer);
			}

			if (colourData != null)
				shaderColour = state.GetShader<DrawBillboardParticlesColour_BillboardCpu>();
			else
				shaderNoColour = state.GetShader<DrawBillboardParticles_BillboardCpu>();
		
			int drawn = 0;
			while (count > 0)
			{
				int drawCount;

				drawCount = Math.Min(count, 120);
				uint drawCountU = (uint)drawCount;
				uint drawnU = (uint)drawn;

				//the only major difference from the GPU drawer is here
				for (int i = 0; i < drawCount; i++)
				{
					//copy position xy and w (size), and velocity.w (rotation)
					positionBuffer[i] = positionSize[drawn + i];
					positionBuffer[i].Z = velocityRotation[drawn + i].W;
				}

				if (colourData != null)
				{
					shaderColour.SetPositionData(positionBuffer, 0, 0, drawCountU);
					shaderColour.SetColourData(colourData, drawnU, 0, drawCountU);

					shaderColour.DisplayTexture = displayTexture;

					state.Shader.Push(shaderColour);
				}
				else
				{
					shaderNoColour.SetPositionData(positionBuffer, 0, 0, drawCountU);

					shaderNoColour.DisplayTexture = displayTexture;

					state.Shader.Push(shaderNoColour);
				}

				vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

				state.Shader.Pop();

				count -= drawCount;
				drawn += drawCount;
			}


			state.RenderState.Pop();
		}
		/// <summary>
		/// draws the particles on a GPU system
		/// </summary>
		protected override void DrawGpuParticles(DrawState state, Xen.Ex.Graphics.Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Texture2D positionTex, Texture2D velocityRotation, Texture2D colourTex, Texture2D userValues, bool usesUserValuesPositionBuffer)
		{
			//this is very similar to the billboard drawer (see it for reference)

			using (state.RenderState.Push())
			{
				state.RenderState.CurrentBlendState = blendMode;
				state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

				Texture2D displayTexture = particleType.Texture;

				//get the shared vertice
				BillboardParticles2DElement.GenerateBillboardVertices(state, ref vertices, ref indices);

				int count = (int)particleCount;

				DrawVelocityParticles_GpuTex shaderNoColour = null;
				DrawVelocityParticlesColour_GpuTex shaderColour = null;
				//user variants
				DrawVelocityParticles_GpuTex_UserOffset shaderNoColour_UO = null;
				DrawVelocityParticlesColour_GpuTex_UserOffset shaderColour_UO = null;

				float resolutionXF = (float)positionTex.Width;
				float resolutionYF = (float)positionTex.Height;

				Vector2 invTextureSize;

				Vector2 velScale = new Vector2(velocityScale, 0);
				if (this.useRotationToScaleVelocityEffect)
					velScale = new Vector2(0, velocityScale);
				invTextureSize = new Vector2(1.0f / resolutionXF, 1.0f / resolutionYF);


				IShader shader;

				if (!usesUserValuesPositionBuffer)
				{
					if (colourTex != null)
					{
						shader = shaderColour = state.GetShader<DrawVelocityParticlesColour_GpuTex>();

						shaderColour.PositionTexture = positionTex;
						shaderColour.ColourTexture = colourTex;
						shaderColour.VelocityTexture = velocityRotation;
						shaderColour.DisplayTexture = displayTexture;

						shaderColour.SetVelocityScale(ref velScale);
					}
					else
					{
						shader = shaderNoColour = state.GetShader<DrawVelocityParticles_GpuTex>();

						shaderNoColour.PositionTexture = positionTex;
						shaderNoColour.VelocityTexture = velocityRotation;
						shaderNoColour.DisplayTexture = displayTexture;

						shaderNoColour.SetVelocityScale(ref velScale);
					}
				}
				else
				{
					if (colourTex != null)
					{
						shader = shaderColour_UO = state.GetShader<DrawVelocityParticlesColour_GpuTex_UserOffset>();

						shaderColour_UO.PositionTexture = positionTex;
						shaderColour_UO.ColourTexture = colourTex;
						shaderColour_UO.VelocityTexture = velocityRotation;
						shaderColour_UO.UserTexture = userValues;
						shaderColour_UO.DisplayTexture = displayTexture;

						shaderColour_UO.SetVelocityScale(ref velScale);
					}
					else
					{
						shader = shaderNoColour_UO = state.GetShader<DrawVelocityParticles_GpuTex_UserOffset>();

						shaderNoColour_UO.PositionTexture = positionTex;
						shaderNoColour_UO.VelocityTexture = velocityRotation;
						shaderNoColour_UO.UserTexture = userValues;
						shaderNoColour_UO.DisplayTexture = displayTexture;

						shaderNoColour_UO.SetVelocityScale(ref velScale);
					}
				}


				int drawn = 0;
				while (count > 0)
				{
					int drawCount = Math.Min(count, vertices.Count / 4);

					if (!usesUserValuesPositionBuffer)
					{
						if (colourTex != null)
							shaderColour.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
						else
							shaderNoColour.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
					}
					else
					{
						if (colourTex != null)
							shaderColour_UO.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
						else
							shaderNoColour_UO.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
					}

					//bind
					using (state.Shader.Push(shader))
						vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

					count -= drawCount;
					drawn += drawCount;
				}


			}
		}
		//draws on CPU particle systems
		/// <summary>
		/// draws the particles from a CPU system
		/// </summary>
		protected override void DrawCpuParticles(DrawState state, Xen.Ex.Graphics.Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
		{
			//this is very similar to the billboard drawer (see it for reference)
			Vector2 targetSize = state.DrawTarget.Size;

			using (state.RenderState.Push())
			{
				state.RenderState.CurrentBlendState = blendMode;
				state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

				Texture2D displayTexture = particleType.Texture;

				BillboardParticles2DElement.GenerateBillboardVertices(state, ref this.vertices, ref this.indices);


				int count = (int)particleCount;



				DrawVelocityParticles_BillboardCpu shaderNoColour = null;
				DrawVelocityParticlesColour_BillboardCpu shaderColour = null;


				Vector2 velScale = new Vector2(velocityScale, 0);
				if (this.useRotationToScaleVelocityEffect)
					velScale = new Vector2(0, velocityScale);

				if (colourData != null)
				{
					shaderColour = state.GetShader<DrawVelocityParticlesColour_BillboardCpu>();

					shaderColour.DisplayTexture = displayTexture;
					shaderColour.SetVelocityScale(ref velScale);
				}
				else
				{
					shaderNoColour = state.GetShader<DrawVelocityParticles_BillboardCpu>();

					shaderNoColour.DisplayTexture = displayTexture;
					shaderNoColour.SetVelocityScale(ref velScale);
				}

				int drawn = 0;
				while (count > 0)
				{
					int drawCount;

					drawCount = Math.Min(count, 80);
					IShader shader = null;

					if (colourData != null)
					{
						shaderColour.SetPositionData(positionSize, (uint)drawn, 0, (uint)drawCount);
						shaderColour.SetVelocityData(velocityRotation, (uint)drawn, 0, (uint)drawCount);
						shaderColour.SetColourData(colourData, (uint)drawn, 0, (uint)drawCount);

						shader = shaderColour;
					}
					else
					{
						shaderNoColour.SetPositionData(positionSize, (uint)drawn, 0, (uint)drawCount);
						shaderNoColour.SetVelocityData(velocityRotation, (uint)drawn, 0, (uint)drawCount);

						shader = shaderNoColour;
					}

					using (state + shader)
						vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

					count -= drawCount;
					drawn += drawCount;
				}
			}
		}
		/// <summary>
		///Note: When 'usesUserValuesPositionBuffer' is true, the values 'user1, user2 and user3' (yzw in the UserTexture) store a position offset for the particle 
		/// </summary>
		protected abstract void DrawGpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint count, AlphaBlendState blendMode, Texture2D positionSize, Texture2D velocityRotation, Texture2D colour, Texture2D userValues, bool usesUserValuesPositionBuffer);
		/// <summary>
		/// This method is only present on Windows builds
		/// </summary>
		/// <param name="blendMode"></param><param name="colour"></param><param name="count"></param><param name="particleType"></param>
		/// <param name="positionSize"></param><param name="state"></param><param name="userValues"></param><param name="velocityRotation"></param>
		protected abstract void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint count, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colour, Vector4[] userValues);
		/// <summary>
		/// <para>implements the method to draw cpu particles</para>
		/// </summary>
		protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
		{
			//this is a bit more complex, but mostly the same as the GPU draw method
			Vector2 targetSize = state.DrawTarget.Size;

			state.RenderState.Push();
			state.RenderState.CurrentBlendState = blendMode;
			state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

			Texture2D displayTexture = particleType.Texture ?? state.Properties.WhiteTexture;

			BillboardParticles2DElement.GenerateBillboardVertices(state, ref this.vertices, ref this.indices);

			Matrix cameraMatrix;
			state.Camera.GetCameraMatrix(out cameraMatrix);

			Vector3 worldSpaceYAxis = new Vector3(cameraMatrix.M21, cameraMatrix.M22, cameraMatrix.M23);


			int count = (int)particleCount;

			DrawBillboardParticles_BillboardCpu3D shaderNoColour = null;
			DrawBillboardParticlesColour_BillboardCpu3D shaderColour = null;

			if (colourData != null)
			{
				shaderColour = state.GetShader<DrawBillboardParticlesColour_BillboardCpu3D>();
				shaderColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
			}
			else
			{
				shaderNoColour = state.GetShader<DrawBillboardParticles_BillboardCpu3D>();
				shaderNoColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
			}

			int drawn = 0;
			while (count > 0)
			{
				int drawCount;

				drawCount = Math.Min(count, 75);
				uint drawCountU = (uint)drawCount;
				uint drawnU = (uint)drawn;

				if (colourData != null)
				{
					shaderColour.SetPositionData(positionSize, drawnU, 0, drawCountU);
					shaderColour.SetVelocityData(velocityRotation, drawnU, 0, drawCountU);
					shaderColour.SetColourData(colourData, drawnU,0,drawCountU);

					shaderColour.DisplayTexture = displayTexture;

					state.Shader.Push(shaderColour);
				}
				else
				{
					shaderNoColour.SetPositionData(positionSize, drawnU, 0, drawCountU);
					shaderNoColour.SetVelocityData(velocityRotation, drawnU, 0, drawCountU);

					shaderNoColour.DisplayTexture = displayTexture;

					state.Shader.Push(shaderNoColour);
				}

				vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

				state.Shader.Pop();

				count -= drawCount;
				drawn += drawCount;
			}


			state.RenderState.Pop();
		}
        /// <summary>
        /// implements the method to draw cpu processed particles
        /// </summary>
        protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
        {
            //this is a bit more complex, but mostly the same as the GPU draw method
            Vector2 targetSize = state.DrawTarget.Size;

            state.PushRenderState();
            state.RenderState.AlphaBlend = blendMode;
            state.RenderState.DepthColourCull.DepthWriteEnabled = false;

            Texture2D displayTexture = particleType.Texture ?? Xen.Ex.Material.WhiteTexture.GetTexture(state);

            BillboardParticles2DElement.GenerateBillboardVertices(state, ref this.vertices, ref this.indices);

            Matrix cameraMatrix;

            state.Camera.GetCameraMatrix(out cameraMatrix);

            Vector3 worldSpaceYAxis = new Vector3(cameraMatrix.M21, cameraMatrix.M22, cameraMatrix.M23);


            Vector2 velScale = new Vector2(velocityScale, 0);

            if (this.useRotationToScaleVelocityEffect)
            {
                velScale = new Vector2(0, velocityScale);
            }



            int count = (int)particleCount;

            DrawVelocityBillboardParticles_BillboardCpu3D       shaderNoColour = null;
            DrawVelocityBillboardParticlesColour_BillboardCpu3D shaderColour   = null;

            if (colourData != null)
            {
                shaderColour = state.GetShader <DrawVelocityBillboardParticlesColour_BillboardCpu3D>();
                shaderColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
                shaderColour.SetVelocityScale(ref velScale);
            }
            else
            {
                shaderNoColour = state.GetShader <DrawVelocityBillboardParticles_BillboardCpu3D>();
                shaderNoColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
                shaderNoColour.SetVelocityScale(ref velScale);
            }

            int drawn = 0;

            while (count > 0)
            {
                int drawCount;

                drawCount = Math.Min(count, 75);

                if (colourData != null)
                {
                    shaderColour.PositionData.SetArray(positionSize, drawn);
                    shaderColour.VelocityData.SetArray(velocityRotation, drawn);
                    shaderColour.ColourData.SetArray(colourData, drawn);

                    shaderColour.DisplayTexture = displayTexture;

                    shaderColour.Bind(state);
                }
                else
                {
                    shaderNoColour.PositionData.SetArray(positionSize, drawn);
                    shaderNoColour.VelocityData.SetArray(velocityRotation, drawn);

                    shaderNoColour.DisplayTexture = displayTexture;

                    shaderNoColour.Bind(state);
                }

                vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

                count -= drawCount;
                drawn += drawCount;
            }


            state.PopRenderState();
        }
		/// <summary>
		/// <para>implements the method to draw gpu particles</para>
		/// <para>Note: When 'usesUserValuesPositionBuffer' is true, the values 'user1, user2 and user3' (yzw in the UserTexture) store a position offset for the particle</para></summary>
		protected override void DrawGpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Texture2D positionTex, Texture2D velocityRotation, Texture2D colourTex, Texture2D userValues, bool usesUserValuesPositionBuffer)
		{
			Vector2 targetSize = state.DrawTarget.Size;

			state.RenderState.Push();
			state.RenderState.CurrentBlendState = blendMode;
			state.RenderState.CurrentDepthState.DepthWriteEnabled = false;

			//get the display texture, or a white texture if none exists
			Texture2D displayTexture = particleType.Texture ?? state.Properties.WhiteTexture;

			//get / create the shared vertices and indices for drawing billboard particles
			BillboardParticles2DElement.GenerateBillboardVertices(state, ref vertices, ref indices);

			int count = (int)particleCount;

			//instances of the two possible shaders
			DrawBillboardParticles_GpuTex3D shaderNoColour = null;
			DrawBillboardParticlesColour_GpuTex3D shaderColour = null;
			//user offset variants
			DrawBillboardParticles_GpuTex3D_UserOffset shaderNoColour_UO = null;
			DrawBillboardParticlesColour_GpuTex3D_UserOffset shaderColour_UO = null;

			float resolutionXF = (float)positionTex.Width;
			float resolutionYF = (float)positionTex.Height;

			Vector2 invTextureSize = new Vector2(1.0f / resolutionXF, 1.0f / resolutionYF);

			Matrix cameraMatrix;
			state.Camera.GetCameraMatrix(out cameraMatrix);

			Vector3 worldSpaceYAxis = new Vector3(cameraMatrix.M21, cameraMatrix.M22, cameraMatrix.M23);

			IShader shader;

			if (!usesUserValuesPositionBuffer)
			{
				if (colourTex != null) // does this particle system use colours?
				{
					//get the shader
					shaderColour = state.GetShader<DrawBillboardParticlesColour_GpuTex3D>();

					//set the samplers
					shaderColour.PositionTexture = positionTex;
					shaderColour.ColourTexture = colourTex;
					shaderColour.VelocityTexture = velocityRotation;
					shaderColour.DisplayTexture = displayTexture;

					shaderColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
					shader = shaderColour;
				}
				else
				{
					shaderNoColour = state.GetShader<DrawBillboardParticles_GpuTex3D>();

					shaderNoColour.PositionTexture = positionTex;
					shaderNoColour.VelocityTexture = velocityRotation;
					shaderNoColour.DisplayTexture = displayTexture;

					shaderNoColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
					shader = shaderNoColour;
				}
			}
			else
			{
				if (colourTex != null) // does this particle system use colours?
				{
					//get the shader
					shaderColour_UO = state.GetShader<DrawBillboardParticlesColour_GpuTex3D_UserOffset>();

					//set the samplers
					shaderColour_UO.PositionTexture = positionTex;
					shaderColour_UO.ColourTexture = colourTex;
					shaderColour_UO.VelocityTexture = velocityRotation;
					shaderColour_UO.UserTexture = userValues;
					shaderColour_UO.DisplayTexture = displayTexture;

					shaderColour_UO.SetWorldSpaceYAxis(ref worldSpaceYAxis);
					shader = shaderColour_UO;
				}
				else
				{
					shaderNoColour_UO = state.GetShader<DrawBillboardParticles_GpuTex3D_UserOffset>();

					shaderNoColour_UO.PositionTexture = positionTex;
					shaderNoColour_UO.VelocityTexture = velocityRotation;
					shaderNoColour_UO.UserTexture = userValues;
					shaderNoColour_UO.DisplayTexture = displayTexture;

					shaderNoColour_UO.SetWorldSpaceYAxis(ref worldSpaceYAxis);
					shader = shaderNoColour_UO;
				}
			}


			int drawn = 0;
			while (count > 0)
			{
				//draw upto vertices.Count / 4 (4 vertices per quad)
				int drawCount = Math.Min(count, vertices.Count / 4);

				//set the inverse texture size, and the start offset value, then bind the shader
				if (!usesUserValuesPositionBuffer)
				{
					if (colourTex != null)
						shaderColour.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
					else
						shaderNoColour.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
				}
				else
				{
					if (colourTex != null)
						shaderColour_UO.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
					else
						shaderNoColour_UO.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
				}

				//bind!
				using (state.Shader.Push(shader))
				{
					//draw!
					vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);
				}

				count -= drawCount;
				drawn += drawCount;
			}

			//and done.
			state.RenderState.Pop();
		}
        /// <summary>
        /// implements the method to draw gpu particles
        /// </summary>
        protected override void DrawGpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Texture2D positionTex, Texture2D velocityRotation, Texture2D colourTex, Texture2D userValues, bool usesUserValuesPositionBuffer)
        {
            Vector2 targetSize = state.DrawTarget.Size;

            state.PushRenderState();
            state.RenderState.AlphaBlend = blendMode;
            state.RenderState.DepthColourCull.DepthWriteEnabled = false;

            //get the display texture, or a white texture if none exists
            Texture2D displayTexture = particleType.Texture ?? Xen.Ex.Material.WhiteTexture.GetTexture(state);

            //get / create the shared vertices and indices for drawing billboard particles
            BillboardParticles2DElement.GenerateBillboardVertices(state, ref vertices, ref indices);

            int count = (int)particleCount;

            //instances of the two possible shaders
            DrawVelocityBillboardParticles_GpuTex3D       shaderNoColour = null;
            DrawVelocityBillboardParticlesColour_GpuTex3D shaderColour   = null;
            //user variantes
            DrawVelocityBillboardParticles_GpuTex3D_UserOffset       shaderNoColour_UO = null;
            DrawVelocityBillboardParticlesColour_GpuTex3D_UserOffset shaderColour_UO   = null;

            float resolutionXF = (float)positionTex.Width;
            float resolutionYF = (float)positionTex.Height;

            Vector2 invTextureSize = new Vector2(1.0f / resolutionXF, 1.0f / resolutionYF);

            Matrix cameraMatrix;

            state.Camera.GetCameraMatrix(out cameraMatrix);

            Vector3 worldSpaceYAxis = new Vector3(cameraMatrix.M21, cameraMatrix.M22, cameraMatrix.M23);


            Vector2 velScale = new Vector2(velocityScale, 0);

            if (this.useRotationToScaleVelocityEffect)
            {
                velScale = new Vector2(0, velocityScale);
            }

            IShader shader;

            if (!usesUserValuesPositionBuffer)
            {
                if (colourTex != null)                 // does this particle system use colours?
                {
                    //get the shader
                    shaderColour = state.GetShader <DrawVelocityBillboardParticlesColour_GpuTex3D>();

                    //set the samplers
                    shaderColour.PositionTexture = positionTex;
                    shaderColour.ColourTexture   = colourTex;
                    shaderColour.VelocityTexture = velocityRotation;
                    shaderColour.DisplayTexture  = displayTexture;

                    shaderColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
                    shaderColour.SetVelocityScale(ref velScale);
                    shader = shaderColour;
                }
                else
                {
                    shaderNoColour = state.GetShader <DrawVelocityBillboardParticles_GpuTex3D>();

                    shaderNoColour.PositionTexture = positionTex;
                    shaderNoColour.VelocityTexture = velocityRotation;
                    shaderNoColour.DisplayTexture  = displayTexture;

                    shaderNoColour.SetWorldSpaceYAxis(ref worldSpaceYAxis);
                    shaderNoColour.SetVelocityScale(ref velScale);
                    shader = shaderNoColour;
                }
            }
            else
            {
                if (colourTex != null)                 // does this particle system use colours?
                {
                    //get the shader
                    shaderColour_UO = state.GetShader <DrawVelocityBillboardParticlesColour_GpuTex3D_UserOffset>();

                    //set the samplers
                    shaderColour_UO.PositionTexture = positionTex;
                    shaderColour_UO.ColourTexture   = colourTex;
                    shaderColour_UO.VelocityTexture = velocityRotation;
                    shaderColour_UO.UserTexture     = userValues;
                    shaderColour_UO.DisplayTexture  = displayTexture;

                    shaderColour_UO.SetWorldSpaceYAxis(ref worldSpaceYAxis);
                    shaderColour_UO.SetVelocityScale(ref velScale);
                    shader = shaderColour_UO;
                }
                else
                {
                    shaderNoColour_UO = state.GetShader <DrawVelocityBillboardParticles_GpuTex3D_UserOffset>();

                    shaderNoColour_UO.PositionTexture = positionTex;
                    shaderNoColour_UO.VelocityTexture = velocityRotation;
                    shaderNoColour_UO.UserTexture     = userValues;
                    shaderNoColour_UO.DisplayTexture  = displayTexture;

                    shaderNoColour_UO.SetWorldSpaceYAxis(ref worldSpaceYAxis);
                    shaderNoColour_UO.SetVelocityScale(ref velScale);
                    shader = shaderNoColour_UO;
                }
            }


            int drawn = 0;

            while (count > 0)
            {
                //draw upto vertices.Count / 4 (4 vertices per quad)
                int drawCount = Math.Min(count, vertices.Count / 4);

                //set the inverse texture size, and the start offset value, then bind the shader
                if (!usesUserValuesPositionBuffer)
                {
                    if (colourTex != null)
                    {
                        shaderColour.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                    else
                    {
                        shaderNoColour.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                }
                else
                {
                    if (colourTex != null)
                    {
                        shaderColour_UO.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                    else
                    {
                        shaderNoColour_UO.InvTextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                }

                //bind
                shader.Bind(state);

                //draw!
                vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

                count -= drawCount;
                drawn += drawCount;
            }

            //and done.
            state.PopRenderState();
        }
Beispiel #18
0
        /// <summary>
        /// draws the particles on a GPU system
        /// </summary>
        protected override void DrawGpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Texture2D positionTex, Texture2D velocityRotation, Texture2D colourTex, Texture2D userValues, bool usesUserValuesPositionBuffer)
        {
            //this is very similar to the billboard drawer (see it for reference)
            Vector2 targetSize = state.DrawTarget.Size;

            state.PushRenderState();
            state.RenderState.AlphaBlend = blendMode;
            state.RenderState.DepthColourCull.DepthWriteEnabled = false;

            Texture2D displayTexture = particleType.Texture ?? Xen.Ex.Material.WhiteTexture.GetTexture(state);

            //get the shared vertice
            BillboardParticles2DElement.GenerateBillboardVertices(state, ref vertices, ref indices);

            int count = (int)particleCount;

            DrawVelocityParticles_GpuTex       shaderNoColour = null;
            DrawVelocityParticlesColour_GpuTex shaderColour   = null;
            //user variants
            DrawVelocityParticles_GpuTex_UserOffset       shaderNoColour_UO = null;
            DrawVelocityParticlesColour_GpuTex_UserOffset shaderColour_UO   = null;

            float resolutionXF = (float)positionTex.Width;
            float resolutionYF = (float)positionTex.Height;

            Vector2 invTextureSize;

            Vector2 velScale = new Vector2(velocityScale, 0);

            if (this.useRotationToScaleVelocityEffect)
            {
                velScale = new Vector2(0, velocityScale);
            }
            invTextureSize = new Vector2(1.0f / resolutionXF, 1.0f / resolutionYF);


            IShader shader;

            if (!usesUserValuesPositionBuffer)
            {
                if (colourTex != null)
                {
                    shader = shaderColour = state.GetShader <DrawVelocityParticlesColour_GpuTex>();

                    shaderColour.PositionTexture = positionTex;
                    shaderColour.ColourTexture   = colourTex;
                    shaderColour.VelocityTexture = velocityRotation;
                    shaderColour.DisplayTexture  = displayTexture;

                    shaderColour.SetVelocityScale(ref velScale);
                }
                else
                {
                    shader = shaderNoColour = state.GetShader <DrawVelocityParticles_GpuTex>();

                    shaderNoColour.PositionTexture = positionTex;
                    shaderNoColour.VelocityTexture = velocityRotation;
                    shaderNoColour.DisplayTexture  = displayTexture;

                    shaderNoColour.SetVelocityScale(ref velScale);
                }
            }
            else
            {
                if (colourTex != null)
                {
                    shader = shaderColour_UO = state.GetShader <DrawVelocityParticlesColour_GpuTex_UserOffset>();

                    shaderColour_UO.PositionTexture = positionTex;
                    shaderColour_UO.ColourTexture   = colourTex;
                    shaderColour_UO.VelocityTexture = velocityRotation;
                    shaderColour_UO.UserTexture     = userValues;
                    shaderColour_UO.DisplayTexture  = displayTexture;

                    shaderColour_UO.SetVelocityScale(ref velScale);
                }
                else
                {
                    shader = shaderNoColour_UO = state.GetShader <DrawVelocityParticles_GpuTex_UserOffset>();

                    shaderNoColour_UO.PositionTexture = positionTex;
                    shaderNoColour_UO.VelocityTexture = velocityRotation;
                    shaderNoColour_UO.UserTexture     = userValues;
                    shaderNoColour_UO.DisplayTexture  = displayTexture;

                    shaderNoColour_UO.SetVelocityScale(ref velScale);
                }
            }


            int drawn = 0;

            while (count > 0)
            {
                int drawCount = Math.Min(count, vertices.Count / 4);

                if (!usesUserValuesPositionBuffer)
                {
                    if (colourTex != null)
                    {
                        shaderColour.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                    else
                    {
                        shaderNoColour.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                }
                else
                {
                    if (colourTex != null)
                    {
                        shaderColour_UO.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                    else
                    {
                        shaderNoColour_UO.TextureSizeOffset = new Vector3(invTextureSize, (float)drawn);
                    }
                }

                //bind
                shader.Bind(state);

                vertices.Draw(state, indices, PrimitiveType.TriangleList, drawCount * 2, 0, 0);

                count -= drawCount;
                drawn += drawCount;
            }


            state.PopRenderState();
        }
Beispiel #19
0
        /// <summary>
        /// draws the particles from a CPU system
        /// </summary>
        protected override void DrawCpuParticles(DrawState state, Content.ParticleSystemTypeData particleType, uint particleCount, AlphaBlendState blendMode, Vector4[] positionSize, Vector4[] velocityRotation, Vector4[] colourData, Vector4[] userValues)
        {
            Vector2 targetSize = state.DrawTarget.Size;

            state.PushRenderState();
            state.RenderState.AlphaBlend = blendMode;
            state.RenderState.DepthColourCull.DepthWriteEnabled = false;

            VelocityLineParticles2DElement.GenerateLinesVertices(state, ref this.vertices);


            int count = (int)particleCount;



            DrawVelocityParticles_LinesCpu       shaderNoColour = null;
            DrawVelocityParticlesColour_LinesCpu shaderColour   = null;

            if (colourData != null)
            {
                shaderColour = state.GetShader <DrawVelocityParticlesColour_LinesCpu>();
            }
            else
            {
                shaderNoColour = state.GetShader <DrawVelocityParticles_LinesCpu>();
            }

            Vector2 velScale = new Vector2(velocityScale, 0);

            if (this.useRotationToScaleVelocityEffect)
            {
                velScale = new Vector2(0, velocityScale);
            }

            int drawn = 0;

            while (count > 0)
            {
                int drawCount;

                drawCount = Math.Min(count, 80);

                if (colourData != null)
                {
                    shaderColour.PositionData.SetArray(positionSize, drawn);
                    shaderColour.VelocityData.SetArray(velocityRotation, drawn);
                    shaderColour.ColourData.SetArray(colourData, drawn);

                    shaderColour.SetVelocityScale(ref velScale);

                    shaderColour.Bind(state);
                }
                else
                {
                    shaderNoColour.PositionData.SetArray(positionSize, drawn);
                    shaderNoColour.VelocityData.SetArray(velocityRotation, drawn);

                    shaderNoColour.SetVelocityScale(ref velScale);

                    shaderNoColour.Bind(state);
                }

                vertices.Draw(state, null, PrimitiveType.LineList, drawCount, 0, 0);

                count -= drawCount;
                drawn += drawCount;
            }


            state.PopRenderState();
        }