/// <summary> /// Allocates global buffers. /// </summary> private void OnCapacityCountChange() { // Allocate global buffers bool allocateGlobalBuffer = false; if (globalBuffer == null) { allocateGlobalBuffer = true; } else if (globalBuffer.ElementCount != CapacityCount) { // Reallocate global buffer if capacity changed allocateGlobalBuffer = true; // Release previous buffer globalBuffer.Release(); sortBuffer.Release(); } // Allocate new buffers if (allocateGlobalBuffer) { if (CapacityCount > 0) { globalBuffer = Buffer.Structured.New(graphicsDeviceService.GraphicsDevice, CapacityCount, StructureSize, true); globalBuffer.Name = "ParticleGlobalBuffer"; sortBuffer = Buffer.Structured.New(graphicsDeviceService.GraphicsDevice, CapacityCount, sizeof(int) * 2, true); sortBuffer.Name = "ParticleSortBuffer"; } } }
public void DisposeBuffers() { if (AppendBuffer != null) { AppendBuffer.Release(); AppendBuffer = null; } if (ConsumeBuffer != null) { ConsumeBuffer.Release(); ConsumeBuffer = null; } }
/// <summary> /// Creates an Entity that contains our dynamic Vertex and Index buffers. /// This Entity will be rendered by the model renderer. /// </summary> /// <param name="verticesCount"></param> /// <param name="indicesCount"></param> private void CreateTerrainModelEntity(int verticesCount, int indicesCount) { // Compute sizes var vertexDeclaration = VertexNormalTexture.VertexDeclaration; var vertexBufferSize = verticesCount * vertexDeclaration.CalculateSize(); var indexBufferSize = indicesCount * sizeof(int); // Create Vertex and Index buffers terrainVertexBuffer = Buffer.Vertex.New(GraphicsDevice, vertexBufferSize, GraphicsResourceUsage.Dynamic); terrainIndexBuffer = Buffer.New(GraphicsDevice, indexBufferSize, BufferFlags.IndexBuffer, GraphicsResourceUsage.Dynamic); // Prepare mesh and entity var meshDraw = new MeshDraw { PrimitiveType = PrimitiveType.TriangleStrip, VertexBuffers = new[] { new VertexBufferBinding(terrainVertexBuffer, vertexDeclaration, verticesCount) }, IndexBuffer = new IndexBufferBinding(terrainIndexBuffer, true, indicesCount), }; // var effect1 = EffectSystem.LoadEffect("SimpleTerrainEffectMain").WaitForResult(); // var effect2 = EffectSystem.LoadEffect("VertexTextureTerrain"); var effectMaterial = LoadAsset <Material>("mt_rock"); Texture tex0 = (Texture)effectMaterial.Parameters[MaterialKeys.DiffuseMap]; // rock Texture tex1 = (Texture)effectMaterial.Parameters[DiffuseMap1]; // grass Texture tex2 = (Texture)effectMaterial.Parameters[DiffuseMap2]; // water effectMaterial.Parameters.Add(VertexTextureTerrainKeys.MeshTexture0, tex1); effectMaterial.Parameters.Add(VertexTextureTerrainKeys.MeshTexture1, tex0); effectMaterial.Parameters.Add(VertexTextureTerrainKeys.MeshTexture2, tex2); effectMaterial.Parameters.Add(MaterialKeys.DiffuseMap, tex1); //terrainMesh = new Mesh { Draw = meshDraw /*, Material = LoadAsset<Material>("TerrainMaterial")*/ }; terrainMesh = new Mesh { Draw = meshDraw, MaterialIndex = 0 }; //terrainEntity = new Entity { { ModelComponent.Key, new ModelComponent { Model = new Model { terrainMesh } } } }; //TerrainEntity.Add<ModelComponent>( ModelComponent.Key, new ModelComponent { Model = new Model { terrainMesh } } ); TerrainEntity.Add <ModelComponent>(ModelComponent.Key, new ModelComponent { Model = new Model { terrainMesh, effectMaterial } }); }
public ParameterConstantBuffer(GraphicsDevice device, string constantBufferName, ShaderConstantBufferDescription constantBufferDesc) { ConstantBufferDesc = constantBufferDesc; constantBufferDatas = new ConstantBufferData[GraphicsDevice.ThreadCount]; dataStreams = new DataPointer[GraphicsDevice.ThreadCount]; for (uint i = 0; i < GraphicsDevice.ThreadCount; ++i) { constantBufferDatas[i] = new ConstantBufferData(constantBufferDesc); dataStreams[i] = new DataPointer(constantBufferDatas[i].Data, constantBufferDesc.Size); } Buffer = SiliconStudio.Paradox.Graphics.Buffer.New(device, constantBufferDatas[0].Desc.Size, BufferFlags.ConstantBuffer, UsingMap ? GraphicsResourceUsage.Dynamic : GraphicsResourceUsage.Default); // We want to clear flags // TODO: Should be later replaced with either an internal field on GraphicsResourceBase, or a reset counter somewhere? Buffer.Reload = Reload; }
/// <summary> /// Allocates the buffers. /// </summary> public void AllocateBuffers(GraphicsDevice graphicsDevice) { DisposeBuffers(); AppendBuffer = Buffer.StructuredAppend.New(graphicsDevice, UserState.Count, StructureSize); ConsumeBuffer = Buffer.StructuredAppend.New(graphicsDevice, UserState.Count, StructureSize); }
protected override void DrawCore(RenderContext context) { var inputTexture = RadianceMap; if (inputTexture == null) { return; } // Gets and checks the input texture if (inputTexture.Dimension != TextureDimension.TextureCube) { throw new NotSupportedException("Only texture cube are currently supported as input of 'LambertianPrefilteringSH' effect."); } const int FirstPassBlockSize = 4; const int FirstPassSumsCount = FirstPassBlockSize * FirstPassBlockSize; var faceCount = inputTexture.Dimension == TextureDimension.TextureCube ? 6 : 1; var inputSize = new Int2(inputTexture.Width, inputTexture.Height); // (Note: for cube maps width = height) var coefficientsCount = harmonicalOrder * harmonicalOrder; var sumsToPerfomRemaining = inputSize.X * inputSize.Y * faceCount / FirstPassSumsCount; var partialSumBuffer = NewScopedTypedBuffer(coefficientsCount * sumsToPerfomRemaining, PixelFormat.R32G32B32A32_Float, true); // Project the radiance on the SH basis and sum up the results along the 4x4 blocks firstPassEffect.ThreadNumbers = new Int3(FirstPassBlockSize, FirstPassBlockSize, 1); firstPassEffect.ThreadGroupCounts = new Int3(inputSize.X / FirstPassBlockSize, inputSize.Y / FirstPassBlockSize, faceCount); firstPassEffect.Parameters.Set(LambertianPrefilteringSHParameters.BlockSize, FirstPassBlockSize); firstPassEffect.Parameters.Set(SphericalHarmonicsParameters.HarmonicsOrder, harmonicalOrder); firstPassEffect.Parameters.Set(LambertianPrefilteringSHPass1Keys.RadianceMap, inputTexture); firstPassEffect.Parameters.Set(LambertianPrefilteringSHPass1Keys.OutputBuffer, partialSumBuffer); firstPassEffect.Draw(context); // Recursively applies the pass2 (sums the coefficients together) as long as needed. Swap input/output buffer at each iteration. var secondPassInputBuffer = partialSumBuffer; Buffer secondPassOutputBuffer = null; while (sumsToPerfomRemaining % 2 == 0) { // we are limited in the number of summing threads by the group-shared memory size. // determine the number of threads to use and update the number of sums remaining afterward. var sumsCount = 1; while (sumsCount < (1 << 10) && sumsToPerfomRemaining % 2 == 0) // shader can perform only an 2^x number of sums. { sumsCount <<= 1; sumsToPerfomRemaining >>= 1; } // determine the numbers of groups (limited to 65535 groups by dimensions) var groupCountX = 1; var groupCountY = sumsToPerfomRemaining; while (groupCountX >= short.MaxValue) { groupCountX <<= 1; groupCountY >>= 1; } // create the output buffer if not existing yet if (secondPassOutputBuffer == null) { secondPassOutputBuffer = NewScopedTypedBuffer(coefficientsCount * sumsToPerfomRemaining, PixelFormat.R32G32B32A32_Float, true); } // draw pass 2 secondPassEffect.ThreadNumbers = new Int3(sumsCount, 1, 1); secondPassEffect.ThreadGroupCounts = new Int3(groupCountX, groupCountY, coefficientsCount); secondPassEffect.Parameters.Set(LambertianPrefilteringSHParameters.BlockSize, sumsCount); secondPassEffect.Parameters.Set(SphericalHarmonicsParameters.HarmonicsOrder, harmonicalOrder); secondPassEffect.Parameters.Set(LambertianPrefilteringSHPass2Keys.InputBuffer, secondPassInputBuffer); secondPassEffect.Parameters.Set(LambertianPrefilteringSHPass2Keys.OutputBuffer, secondPassOutputBuffer); secondPassEffect.Draw(context); // swap second pass input/output buffers. var swapTemp = secondPassOutputBuffer; secondPassOutputBuffer = secondPassInputBuffer; secondPassInputBuffer = swapTemp; } // create and initialize result SH prefilteredLambertianSH = new SphericalHarmonics(HarmonicOrder); // Get the data out of the final buffer var sizeResult = coefficientsCount * sumsToPerfomRemaining * PixelFormat.R32G32B32A32_Float.SizeInBytes(); var stagedBuffer = NewScopedBuffer(new BufferDescription(sizeResult, BufferFlags.None, GraphicsResourceUsage.Staging)); GraphicsDevice.CopyRegion(secondPassInputBuffer, 0, new ResourceRegion(0, 0, 0, sizeResult, 1, 1), stagedBuffer, 0); var finalsValues = stagedBuffer.GetData <Vector4>(); // performs last possible additions, normalize the result and store it in the SH for (var c = 0; c < coefficientsCount; c++) { var coeff = Vector4.Zero; for (var f = 0; f < sumsToPerfomRemaining; ++f) { coeff += finalsValues[coefficientsCount * f + c]; } prefilteredLambertianSH.Coefficients[c] = 4 * MathUtil.Pi / coeff.W * new Color3(coeff.X, coeff.Y, coeff.Z); } }
private static byte[] GetDataSafe(this Buffer buffer) { var data = buffer.GetSerializationData(); return(data != null ? data.Content : buffer.GetData <byte>()); }
public void Generate(IServiceRegistry services, Model model) { if (services == null) { throw new ArgumentNullException("services"); } if (model == null) { throw new ArgumentNullException("model"); } var graphicsDevice = services.GetSafeServiceAs <IGraphicsDeviceService>().GraphicsDevice; var data = this.CreatePrimitiveMeshData(); if (data.Vertices.Length == 0) { throw new InvalidOperationException("Invalid GeometricPrimitive [{0}]. Expecting non-zero Vertices array"); } var boundingBox = BoundingBox.Empty; for (int i = 0; i < data.Vertices.Length; i++) { BoundingBox.Merge(ref boundingBox, ref data.Vertices[i].Position, out boundingBox); } BoundingSphere boundingSphere; unsafe { fixed(void *verticesPtr = data.Vertices) BoundingSphere.FromPoints((IntPtr)verticesPtr, 0, data.Vertices.Length, VertexPositionNormalTexture.Size, out boundingSphere); } var originalLayout = data.Vertices[0].GetLayout(); // Generate Tangent/BiNormal vectors var resultWithTangentBiNormal = VertexHelper.GenerateTangentBinormal(originalLayout, data.Vertices, data.Indices); // Generate Multitexcoords var result = VertexHelper.GenerateMultiTextureCoordinates(resultWithTangentBiNormal); var meshDraw = new MeshDraw(); var layout = result.Layout; var vertexBuffer = result.VertexBuffer; var indices = data.Indices; if (indices.Length < 0xFFFF) { var indicesShort = new ushort[indices.Length]; for (int i = 0; i < indicesShort.Length; i++) { indicesShort[i] = (ushort)indices[i]; } meshDraw.IndexBuffer = new IndexBufferBinding(Buffer.Index.New(graphicsDevice, indicesShort).RecreateWith(indicesShort), false, indices.Length); } else { if (graphicsDevice.Features.Profile <= GraphicsProfile.Level_9_3) { throw new InvalidOperationException("Cannot generate more than 65535 indices on feature level HW <= 9.3"); } meshDraw.IndexBuffer = new IndexBufferBinding(Buffer.Index.New(graphicsDevice, indices).RecreateWith(indices), true, indices.Length); } meshDraw.VertexBuffers = new[] { new VertexBufferBinding(Buffer.New(graphicsDevice, vertexBuffer, BufferFlags.VertexBuffer).RecreateWith(vertexBuffer), layout, data.Vertices.Length) }; meshDraw.DrawCount = indices.Length; meshDraw.PrimitiveType = PrimitiveType.TriangleList; var mesh = new Mesh { Draw = meshDraw, BoundingBox = boundingBox, BoundingSphere = boundingSphere }; model.BoundingBox = boundingBox; model.BoundingSphere = boundingSphere; model.Add(mesh); if (MaterialInstance != null && MaterialInstance.Material != null) { model.Materials.Add(MaterialInstance); } }
/// <summary> /// Copies the current count of structured elements from a structured buffer to an <see cref="IIndirectBuffer"/>. /// </summary> /// <param name="sourceBuffer">The structured buffer</param> /// <param name="destBuffer">The indirect buffer</param> /// <param name="offsetToDest">Offset into the indirect buffer to write arguments to</param> public void CopyCount(Buffer sourceBuffer, Buffer destBuffer, int offsetToDest) { throw new NotImplementedException(); }
/// <summary> /// Sets a constant buffer to the shader pipeline. /// </summary> /// <param name="stage">The shader stage.</param> /// <param name="slot">The binding slot.</param> /// <param name="buffer">The constant buffer to set.</param> public void SetConstantBuffer(ShaderStage stage, int slot, Buffer buffer) { throw new NotImplementedException(); }
/// <summary> /// Execute a compute shader from a thread group using arguments stored in the <see cref="IIndirectBuffer"/>. /// </summary> /// <param name="indirectBuffer">Buffer storing arguments of the standard dispatch method (threadCountX/Y/Z).</param> /// <param name="offsetInBytes">Offset to start to read the arguments from the indirect buffer.</param> public void Dispatch(Buffer indirectBuffer, int offsetInBytes) { throw new NotImplementedException(); }
/// <summary> /// Clears a structured buffer /// </summary> /// <param name="buffer">The structured buffer.</param> /// <param name="value">Set this value for the whole buffer.</param> public void Clear(Buffer buffer, int value) { throw new NotImplementedException(); }