public static Color ToSharpTextColor(this RgbaFloat color) { return(new Color(color.R, color.G, color.B, color.A)); }
public static void ClearColor(RgbaFloat color) => VxContext.Instance.ClearColor = color;
public void Add(RenderCommandType type, ulong stage, ulong surface, ulong camera, ulong texture0, ulong texture1, ulong spareId0, ulong spareId1, RgbaFloat colour) { if (type == RenderCommandType.GpuToCpuSurfaceCopy) { if (CallbackQueueSize > 0) { var copyStageContainedAlready = false; for (var n = 0; n < CallbackQueueSize; n++) { if (_surfaceCopyStageCallbackPool[n] == stage) { copyStageContainedAlready = true; } } if (copyStageContainedAlready) { throw new Yak2DException(string.Concat("Gpu to Cpu Surface Copy Stage (id: ", stage, " , is already queued. You should only queue specific queue once per render as a stage only contains a single data storage array that would be overwritten a second time")); } } if (CallbackQueueSize >= _surfaceCopyStageCallbackPool.Length) { _surfaceCopyStageCallbackPool = Utility.ArrayFunctions.DoubleArraySizeAndKeepContents <ulong>(_surfaceCopyStageCallbackPool); } _surfaceCopyStageCallbackPool[CallbackQueueSize] = stage; CallbackQueueSize++; } if (CommandQueueSize >= _pool.Length) { _pool = Utility.ArrayFunctions.DoubleArraySizeAndKeepContents <RenderCommandQueueItem>(_pool); } _pool[CommandQueueSize].Type = type; _pool[CommandQueueSize].Stage = stage; _pool[CommandQueueSize].Surface = surface; _pool[CommandQueueSize].Camera = camera; _pool[CommandQueueSize].Texture0 = texture0; _pool[CommandQueueSize].Texture1 = texture1; _pool[CommandQueueSize].SpareId0 = spareId0; _pool[CommandQueueSize].SpareId1 = spareId1; _pool[CommandQueueSize].Colour = colour; CommandQueueSize++; }
public unsafe void Points_WithTexture_UpdateUnrelated(bool useTextureView) { // This is a regression test for the case where a user modifies an unrelated texture // at a time after a ResourceSet containing a texture has been bound. The OpenGL // backend was caching texture state improperly, resulting in wrong textures being sampled. Texture target = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.RenderTarget)); Texture staging = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Staging)); Framebuffer framebuffer = RF.CreateFramebuffer(new FramebufferDescription(null, target)); DeviceBuffer orthoBuffer = RF.CreateBuffer(new BufferDescription(64, BufferUsage.UniformBuffer)); Matrix4x4 orthoMatrix = Matrix4x4.CreateOrthographicOffCenter( 0, framebuffer.Width, framebuffer.Height, 0, -1, 1); GD.UpdateBuffer(orthoBuffer, 0, ref orthoMatrix); Texture sampledTexture = RF.CreateTexture( TextureDescription.Texture2D(1, 1, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Sampled)); RgbaFloat white = RgbaFloat.White; GD.UpdateTexture(sampledTexture, (IntPtr)(&white), (uint)Unsafe.SizeOf <RgbaFloat>(), 0, 0, 0, 1, 1, 1, 0, 0); Texture shouldntBeSampledTexture = RF.CreateTexture( TextureDescription.Texture2D(1, 1, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Sampled)); ShaderSetDescription shaderSet = new ShaderSetDescription( new VertexLayoutDescription[] { new VertexLayoutDescription( new VertexElementDescription("Position", VertexElementSemantic.TextureCoordinate, VertexElementFormat.Float2)) }, TestShaders.LoadVertexFragment(RF, "TexturedPoints")); ResourceLayout layout = RF.CreateResourceLayout(new ResourceLayoutDescription( new ResourceLayoutElementDescription("Ortho", ResourceKind.UniformBuffer, ShaderStages.Vertex), new ResourceLayoutElementDescription("Tex", ResourceKind.TextureReadOnly, ShaderStages.Fragment), new ResourceLayoutElementDescription("Smp", ResourceKind.Sampler, ShaderStages.Fragment))); ResourceSet set; if (useTextureView) { TextureView view = RF.CreateTextureView(sampledTexture); set = RF.CreateResourceSet(new ResourceSetDescription(layout, orthoBuffer, view, GD.PointSampler)); } else { set = RF.CreateResourceSet(new ResourceSetDescription(layout, orthoBuffer, sampledTexture, GD.PointSampler)); } GraphicsPipelineDescription gpd = new GraphicsPipelineDescription( BlendStateDescription.SingleOverrideBlend, DepthStencilStateDescription.Disabled, RasterizerStateDescription.Default, PrimitiveTopology.PointList, shaderSet, layout, framebuffer.OutputDescription); Pipeline pipeline = RF.CreateGraphicsPipeline(ref gpd); Vector2[] vertices = new Vector2[] { new Vector2(0.5f, 0.5f), new Vector2(15.5f, 15.5f), new Vector2(25.5f, 26.5f), new Vector2(3.5f, 25.5f), }; DeviceBuffer vb = RF.CreateBuffer( new BufferDescription((uint)(Unsafe.SizeOf <Vector2>() * vertices.Length), BufferUsage.VertexBuffer)); GD.UpdateBuffer(vb, 0, vertices); CommandList cl = RF.CreateCommandList(); for (int i = 0; i < 2; i++) { cl.Begin(); cl.SetFramebuffer(framebuffer); cl.ClearColorTarget(0, RgbaFloat.Black); cl.SetPipeline(pipeline); cl.SetVertexBuffer(0, vb); cl.SetGraphicsResourceSet(0, set); // Modify an unrelated texture. // This must have no observable effect on the next draw call. RgbaFloat pink = RgbaFloat.Pink; GD.UpdateTexture(shouldntBeSampledTexture, (IntPtr)(&pink), (uint)Unsafe.SizeOf <RgbaFloat>(), 0, 0, 0, 1, 1, 1, 0, 0); cl.Draw((uint)vertices.Length); cl.End(); GD.SubmitCommands(cl); GD.WaitForIdle(); } cl.Begin(); cl.CopyTexture(target, staging); cl.End(); GD.SubmitCommands(cl); GD.WaitForIdle(); MappedResourceView <RgbaFloat> readView = GD.Map <RgbaFloat>(staging, MapMode.Read); foreach (Vector2 vertex in vertices) { uint x = (uint)vertex.X; uint y = (uint)vertex.Y; if (!GD.IsUvOriginTopLeft || GD.IsClipSpaceYInverted) { y = framebuffer.Height - y - 1; } Assert.Equal(white, readView[x, y], RgbaFloatFuzzyComparer.Instance); } GD.Unmap(staging); }
public VertexPositionColor(Vector2 position, RgbaFloat color) { Position = position; Color = color; }
private void BeginCurrentRenderPass() { Debug.Assert(_activeRenderPass == VkRenderPass.Null); Debug.Assert(_currentFramebuffer != null); _currentFramebufferEverActive = true; uint attachmentCount = _currentFramebuffer.AttachmentCount; bool haveAnyAttachments = _framebuffer.ColorTargets.Count > 0 || _framebuffer.DepthTarget != null; bool haveAllClearValues = _depthClearValue.HasValue || _framebuffer.DepthTarget == null; bool haveAnyClearValues = _depthClearValue.HasValue; for (int i = 0; i < _currentFramebuffer.ColorTargets.Count; i++) { if (!_validColorClearValues[i]) { haveAllClearValues = false; haveAnyClearValues = true; } else { haveAnyClearValues = true; } } VkRenderPassBeginInfo renderPassBI = VkRenderPassBeginInfo.New(); renderPassBI.renderArea = new VkRect2D(_currentFramebuffer.RenderableWidth, _currentFramebuffer.RenderableHeight); renderPassBI.framebuffer = _currentFramebuffer.CurrentFramebuffer; if (!haveAnyAttachments || !haveAllClearValues) { renderPassBI.renderPass = _newFramebuffer ? _currentFramebuffer.RenderPassNoClear_Init : _currentFramebuffer.RenderPassNoClear_Load; vkCmdBeginRenderPass(_cb, ref renderPassBI, VkSubpassContents.Inline); _activeRenderPass = renderPassBI.renderPass; if (haveAnyClearValues) { if (_depthClearValue.HasValue) { ClearDepthStencil(_depthClearValue.Value.depthStencil.depth, (byte)_depthClearValue.Value.depthStencil.stencil); _depthClearValue = null; } for (uint i = 0; i < _currentFramebuffer.ColorTargets.Count; i++) { if (_validColorClearValues[i]) { _validColorClearValues[i] = false; VkClearValue vkClearValue = _clearValues[i]; RgbaFloat clearColor = new RgbaFloat( vkClearValue.color.float32_0, vkClearValue.color.float32_1, vkClearValue.color.float32_2, vkClearValue.color.float32_3); ClearColorTarget(i, clearColor); } } } } else { // We have clear values for every attachment. renderPassBI.renderPass = _currentFramebuffer.RenderPassClear; fixed(VkClearValue *clearValuesPtr = &_clearValues[0]) { renderPassBI.clearValueCount = attachmentCount; renderPassBI.pClearValues = clearValuesPtr; if (_depthClearValue.HasValue) { _clearValues[_currentFramebuffer.ColorTargets.Count] = _depthClearValue.Value; _depthClearValue = null; } vkCmdBeginRenderPass(_cb, ref renderPassBI, VkSubpassContents.Inline); _activeRenderPass = _currentFramebuffer.RenderPassClear; Util.ClearArray(_validColorClearValues); } } _newFramebuffer = false; }
public void Points_WithUIntColor() { Texture target = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.RenderTarget)); Texture staging = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Staging)); Framebuffer framebuffer = RF.CreateFramebuffer(new FramebufferDescription(null, target)); DeviceBuffer infoBuffer = RF.CreateBuffer(new BufferDescription(16, BufferUsage.UniformBuffer)); DeviceBuffer orthoBuffer = RF.CreateBuffer(new BufferDescription(64, BufferUsage.UniformBuffer)); Matrix4x4 orthoMatrix = Matrix4x4.CreateOrthographicOffCenter( 0, framebuffer.Width, framebuffer.Height, 0, -1, 1); GD.UpdateBuffer(orthoBuffer, 0, ref orthoMatrix); ShaderSetDescription shaderSet = new ShaderSetDescription( new VertexLayoutDescription[] { new VertexLayoutDescription( new VertexElementDescription("Position", VertexElementSemantic.TextureCoordinate, VertexElementFormat.Float2), new VertexElementDescription("Color_UInt", VertexElementSemantic.TextureCoordinate, VertexElementFormat.UInt4)) }, TestShaders.LoadVertexFragment(RF, "UIntVertexAttribs")); ResourceLayout layout = RF.CreateResourceLayout(new ResourceLayoutDescription( new ResourceLayoutElementDescription("InfoBuffer", ResourceKind.UniformBuffer, ShaderStages.Vertex), new ResourceLayoutElementDescription("Ortho", ResourceKind.UniformBuffer, ShaderStages.Vertex))); ResourceSet set = RF.CreateResourceSet(new ResourceSetDescription(layout, infoBuffer, orthoBuffer)); GraphicsPipelineDescription gpd = new GraphicsPipelineDescription( BlendStateDescription.SingleOverrideBlend, DepthStencilStateDescription.Disabled, RasterizerStateDescription.Default, PrimitiveTopology.PointList, shaderSet, layout, framebuffer.OutputDescription); Pipeline pipeline = RF.CreateGraphicsPipeline(ref gpd); uint colorNormalizationFactor = 2500; UIntVertexAttribsVertex[] vertices = new UIntVertexAttribsVertex[] { new UIntVertexAttribsVertex { Position = new Vector2(0.5f, 0.5f), Color_Int = new UInt4 { X = (uint)(0.25f * colorNormalizationFactor), Y = (uint)(0.5f * colorNormalizationFactor), Z = (uint)(0.75f * colorNormalizationFactor), } }, new UIntVertexAttribsVertex { Position = new Vector2(10.5f, 12.5f), Color_Int = new UInt4 { X = (uint)(0.25f * colorNormalizationFactor), Y = (uint)(0.5f * colorNormalizationFactor), Z = (uint)(0.75f * colorNormalizationFactor), } }, new UIntVertexAttribsVertex { Position = new Vector2(25.5f, 35.5f), Color_Int = new UInt4 { X = (uint)(0.75f * colorNormalizationFactor), Y = (uint)(0.5f * colorNormalizationFactor), Z = (uint)(0.25f * colorNormalizationFactor), } }, new UIntVertexAttribsVertex { Position = new Vector2(49.5f, 49.5f), Color_Int = new UInt4 { X = (uint)(0.15f * colorNormalizationFactor), Y = (uint)(0.25f * colorNormalizationFactor), Z = (uint)(0.35f * colorNormalizationFactor), } }, }; DeviceBuffer vb = RF.CreateBuffer( new BufferDescription((uint)(Unsafe.SizeOf <UIntVertexAttribsVertex>() * vertices.Length), BufferUsage.VertexBuffer)); GD.UpdateBuffer(vb, 0, vertices); GD.UpdateBuffer(infoBuffer, 0, new UIntVertexAttribsInfo { ColorNormalizationFactor = colorNormalizationFactor }); CommandList cl = RF.CreateCommandList(); cl.Begin(); cl.SetFramebuffer(framebuffer); cl.SetFullViewports(); cl.SetFullScissorRects(); cl.ClearColorTarget(0, RgbaFloat.Black); cl.SetPipeline(pipeline); cl.SetVertexBuffer(0, vb); cl.SetGraphicsResourceSet(0, set); cl.Draw((uint)vertices.Length); cl.CopyTexture(target, staging); cl.End(); GD.SubmitCommands(cl); GD.WaitForIdle(); MappedResourceView <RgbaFloat> readView = GD.Map <RgbaFloat>(staging, MapMode.Read); foreach (UIntVertexAttribsVertex vertex in vertices) { uint x = (uint)vertex.Position.X; uint y = (uint)vertex.Position.Y; if (!GD.IsUvOriginTopLeft || GD.IsClipSpaceYInverted) { y = framebuffer.Height - y - 1; } RgbaFloat expectedColor = new RgbaFloat( vertex.Color_Int.X / (float)colorNormalizationFactor, vertex.Color_Int.Y / (float)colorNormalizationFactor, vertex.Color_Int.Z / (float)colorNormalizationFactor, 1); Assert.Equal(expectedColor, readView[x, y], RgbaFloatFuzzyComparer.Instance); } GD.Unmap(staging); }
public LineVectorStyleUBO(RgbaFloat lineColor, float lineWidth = 1.0f) { spa1 = new Vector3(); LineColor = lineColor; LineWidth = lineWidth; }
public void ClearColorTarget(uint index, RgbaFloat clearColor) { _commands.Add(_clearColorTargetEntryPool.Rent().Init(index, clearColor)); }
override protected void CreateResources() { RgbaFloat lightColor = RgbaFloat.White; // RgbaFloat lightColor = RgbaFloat.LightGrey; //var lightPos = new Vector4(-0.5f,0.1f,10,1); var lightPos = new Vector4(0.0f, 0.0f, 0, 1); var lookAt = new Vector4(0, 0, 0, 1) - new Vector4(0, 1, 0, 1); //var lightCam = new OrthographicCamera(50.0f, 50.0f, lightPos, lookAt); //_sceneRuntimeState.Light = new Light(lightCam,lightColor,0.1f); _sceneRuntimeState.Camera = Camera; _sceneRuntimeState.SpotLight = Light.NO_POINTLIGHT; var omniCameras = CubeMap.GenerateOmniCameras(lightPos, 1024, 1024); _sceneRuntimeState.OmniLights = Light.GenerateOmniLights(omniCameras, lightColor, 0.1f); // string filePath = Path.Combine(AppContext.BaseDirectory, "armor/armor.dae"); // string filePath = Path.Combine(AppContext.BaseDirectory, "nanosuit/nanosuit.obj"); var scale = Matrix4x4.CreateScale(0.05f, 0.05f, 0.05f); //var scale = Matrix4x4.CreateScale(1.00f,1.00f,1.00f); string filePath = "models/chinesedragon.dae"; // string filePath = "Models/Box.dae"; var model = AssimpLoader.LoadFromFileWithRealtimeMaterial <VertexPositionNormal>(AppContext.BaseDirectory, filePath, VertexPositionNormal.HenzaiType); var newModelTranslation = Matrix4x4.CreateTranslation(new Vector3(0, 20, 0)); var modelRuntimeState = new ModelRuntimeDescriptor <VertexPositionNormal>(model, "PhongOmni", "PhongOmni", VertexRuntimeTypes.VertexPositionNormal, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); modelRuntimeState.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPN; model.SetNewWorldTransformation(ref newModelTranslation, true); //TODO: Write method to remove ambient terms var sponzaModels = AssimpLoader.LoadRealtimeModelsFromFile(AppContext.BaseDirectory, "sponza/sponza.obj"); var sponzaPNTTB = sponzaModels.modelPNTTB; var sponzaPC = sponzaModels.modelPC; for (int i = 0; i < sponzaPNTTB.MaterialCount; i++) { sponzaPNTTB.GetMaterial(i).ambient = new Vector4(0.3f, 0.3f, 0.3f, 1.0f); } for (int i = 0; i < sponzaPC.MaterialCount; i++) { sponzaPC.GetMaterial(i).ambient = new Vector4(0.3f, 0.3f, 0.3f, 1.0f); } sponzaPNTTB.SetNewWorldTransformation(ref scale, true); sponzaPC.SetNewWorldTransformation(ref scale, true); var sponzaRuntimeState //TOOD: Omni Fragment shader produces a runtime error = new ModelRuntimeDescriptor <VertexPositionNormalTextureTangentBitangent>(sponzaPNTTB, "PhongBitangentTextureOmni", "PhongBitangentTextureOmni", VertexRuntimeTypes.VertexPositionNormalTextureTangentBitangent, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); sponzaRuntimeState.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPNTTB; sponzaRuntimeState.CallSamplerGeneration += ResourceGenerator.GenerateTriLinearSampler; sponzaRuntimeState.CallTextureResourceLayoutGeneration += ResourceGenerator.GenerateTextureResourceLayoutForNormalMapping; sponzaRuntimeState.CallTextureResourceSetGeneration += ResourceGenerator.GenerateTextureResourceSetForNormalMapping; var sponzaRuntimeStateColorOnly = new ModelRuntimeDescriptor <VertexPositionColor>(sponzaPC, "Color", "Color", VertexRuntimeTypes.VertexPositionColor, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); sponzaRuntimeStateColorOnly.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPC; /// var floor = new Model <VertexPositionNormalTextureTangentBitangent, RealtimeMaterial>("paving/", GeometryFactory.GenerateQuadPNTTB_XY(), new RealtimeMaterial()); var floorMeshZero = floor.GetMesh(0); var flootMaterialZero = floor.GetMaterial(0); flootMaterialZero.textureDiffuse = "pavingColor.jpg"; flootMaterialZero.textureNormal = "pavingNorm.jpg"; flootMaterialZero.ambient = new Vector4(0.3f, 0.3f, 0.3f, 1.0f); var floorTranslation = Matrix4x4.CreateTranslation(-6, 0, -7); var floorScale = Matrix4x4.CreateScale(100.0f, 100.0f, 1); var newTrans = Matrix4x4.Multiply(floorScale, floorTranslation); floor.SetNewWorldTransformation(ref floorTranslation, true); var floorRuntimeState = new ModelRuntimeDescriptor <VertexPositionNormalTextureTangentBitangent>(floor, "PhongBitangentTextureOmni", "PhongBitangentTextureOmni", VertexRuntimeTypes.VertexPositionNormalTextureTangentBitangent, PrimitiveTopology.TriangleStrip, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); floorRuntimeState.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPNTTB; floorRuntimeState.CallTextureResourceLayoutGeneration += ResourceGenerator.GenerateTextureResourceLayoutForNormalMapping; floorRuntimeState.CallTextureResourceSetGeneration += ResourceGenerator.GenerateTextureResourceSetForNormalMapping; floorRuntimeState.CallSamplerGeneration += ResourceGenerator.GenerateTriLinearSampler; ///// var floor2 = new Model <VertexPositionNormalTextureTangentBitangent, RealtimeMaterial>("paving/", GeometryFactory.GenerateQuadPNTTB_XZ(), new RealtimeMaterial()); var floorMeshZero2 = floor2.GetMesh(0); var flootMaterialZero2 = floor2.GetMaterial(0); flootMaterialZero2.textureDiffuse = "pavingColor.jpg"; flootMaterialZero2.textureNormal = "pavingNorm.jpg"; flootMaterialZero2.ambient = new Vector4(0.3f, 0.3f, 0.3f, 1.0f); var floorTranslation2 = Matrix4x4.CreateTranslation(0, -5, 0); var floorScale2 = Matrix4x4.CreateScale(100.0f, 1.0f, 100.0f); var newTrans2 = Matrix4x4.Multiply(floorScale2, floorTranslation2); floor2.SetNewWorldTransformation(ref newTrans2, true); var floorRuntimeState2 = new ModelRuntimeDescriptor <VertexPositionNormalTextureTangentBitangent>(floor2, "PhongBitangentTextureOmni", "PhongBitangentTextureOmni", VertexRuntimeTypes.VertexPositionNormalTextureTangentBitangent, PrimitiveTopology.TriangleStrip, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); floorRuntimeState2.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPNTTB; floorRuntimeState2.CallTextureResourceLayoutGeneration += ResourceGenerator.GenerateTextureResourceLayoutForNormalMapping; floorRuntimeState2.CallTextureResourceSetGeneration += ResourceGenerator.GenerateTextureResourceSetForNormalMapping; floorRuntimeState2.CallSamplerGeneration += ResourceGenerator.GenerateTriLinearSampler; // var skyBox = new Model <VertexPosition, RealtimeMaterial>("cloudtop", GeometryFactory.GenerateCube(true), new RealtimeMaterial()); var skyBoxMaterial = skyBox.GetMaterial(0); skyBoxMaterial.AssignCubemapPaths("cloudtop_ft.png", "cloudtop_bk.png", "cloudtop_lf.png", "cloudtop_rt.png", "cloudtop_up.png", "cloudtop_dn.png"); _skyBoxRuntimeState = new ModelRuntimeDescriptor <VertexPosition>(skyBox, "Skybox", "Skybox", VertexRuntimeTypes.VertexPosition, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); _skyBoxRuntimeState.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForP; _skyBoxRuntimeState.CallSamplerGeneration += ResourceGenerator.GenerateBiLinearSampler; _skyBoxRuntimeState.CallTextureResourceLayoutGeneration += ResourceGenerator.GenerateTextureResourceLayoutForCubeMapping; _skyBoxRuntimeState.CallTextureResourceSetGeneration += ResourceGenerator.GenerateTextureResourceSetForCubeMapping; _sun = new Model <VertexPositionNormal, RealtimeMaterial>(string.Empty, GeometryFactory.GenerateSphereNormal(100, 100, 0.3f), new RealtimeMaterial()); _sun.GetMaterial(0).ambient = lightColor.ToVector4(); Vector3 newTranslation = new Vector3(lightPos.X, lightPos.Y, lightPos.Z); _sun.SetNewWorldTranslation(ref newTranslation, true); var sunRuntimeState = new ModelRuntimeDescriptor <VertexPositionNormal>(_sun, "PhongNoShadow", "PhongNoShadow", VertexRuntimeTypes.VertexPositionNormal, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); sunRuntimeState.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPN; var _sun2 = new Model <VertexPositionNormal, RealtimeMaterial>(string.Empty, GeometryFactory.GenerateSphereNormal(100, 100, 0.5f), new RealtimeMaterial()); _sun2.GetMaterial(0).ambient = lightColor.ToVector4(); Vector3 newTranslation2 = new Vector3(5, -2, 1); _sun2.SetNewWorldTranslation(ref newTranslation2, true); var sunRuntimeState2 = new ModelRuntimeDescriptor <VertexPositionNormal>(_sun2, "PhongOmni", "PhongOmni", VertexRuntimeTypes.VertexPositionNormal, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); sunRuntimeState2.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPN; var _sun3 = new Model <VertexPositionNormal, RealtimeMaterial>(string.Empty, GeometryFactory.GenerateSphereNormal(100, 100, 0.5f), new RealtimeMaterial()); _sun3.GetMaterial(0).ambient = lightColor.ToVector4(); Vector3 newTranslation3 = new Vector3(-5, 0, -3.0f); _sun3.SetNewWorldTranslation(ref newTranslation3, true); var sunRuntimeState3 = new ModelRuntimeDescriptor <VertexPositionNormal>(_sun3, "PhongOmni", "PhongOmni", VertexRuntimeTypes.VertexPositionNormal, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); sunRuntimeState3.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPN; var _sun4 = new Model <VertexPositionNormal, RealtimeMaterial>(string.Empty, GeometryFactory.GenerateSphereNormal(100, 100, 0.2f), new RealtimeMaterial()); _sun4.GetMaterial(0).ambient = lightColor.ToVector4(); Vector3 newTranslation4 = new Vector3(0, -2, 0.0f); _sun4.SetNewWorldTranslation(ref newTranslation4, true); var sunRuntimeState4 = new ModelRuntimeDescriptor <VertexPositionNormal>(_sun4, "PhongOmni", "PhongOmni", VertexRuntimeTypes.VertexPositionNormal, PrimitiveTopology.TriangleList, new RenderDescription(RenderFlags.NORMAL | RenderFlags.OMNI_SHADOW_MAPS), new InstancingRenderDescription(RenderFlags.NONE, InstancingDataFlags.EMPTY)); sunRuntimeState4.CallVertexLayoutGeneration += ResourceGenerator.GenerateVertexLayoutForPN; //TODO: Automate this //_modelPNTTBDescriptorList.Add(sponzaRuntimeState); _modelPNTTBDescriptorList.Add(floorRuntimeState); //Rendering this seems to crate aretfacts on the other floor _modelPNTTBDescriptorList.Add(floorRuntimeState2); //_modelPCDescriptorList.Add(sponzaRuntimeStateColorOnly); //_modelPDescriptorList.Add(_skyBoxRuntimeState); _modelPNDescriptorList.Add(sunRuntimeState3); _modelPNDescriptorList.Add(sunRuntimeState); _modelPNDescriptorList.Add(sunRuntimeState2); _modelPNDescriptorList.Add(sunRuntimeState4); //_modelPNDescriptorList.Add(modelRuntimeState); InstanceData[] instancingData = { InstanceData.NO_DATA }; //TODO: Abstrct this foreach (var modelDescriptor in _modelPNTTBDescriptorList) { FillRuntimeDescriptor(modelDescriptor, _sceneRuntimeState, instancingData); PNTTBRuntimeGeometry.AddModel(modelDescriptor); } foreach (var modelDescriptor in _modelPNDescriptorList) { FillRuntimeDescriptor(modelDescriptor, _sceneRuntimeState, instancingData); PNRuntimeGeometry.AddModel(modelDescriptor); } foreach (var modelDescriptor in _modelPTDescriptorList) { FillRuntimeDescriptor(modelDescriptor, _sceneRuntimeState, instancingData); PTRuntimeGeometry.AddModel(modelDescriptor); } foreach (var modelDescriptor in _modelPCDescriptorList) { FillRuntimeDescriptor(modelDescriptor, _sceneRuntimeState, instancingData); PCRuntimeGeometry.AddModel(modelDescriptor); } foreach (var modelDescriptor in _modelPDescriptorList) { FillRuntimeDescriptor(modelDescriptor, _sceneRuntimeState, instancingData); PRuntimeGeometry.AddModel(modelDescriptor); } }
public PolygonVectorStyleUBO(RgbaFloat fillColor) { FillColor = fillColor; }
public void Points_WithUShortNormColor() { Texture target = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.RenderTarget)); Texture staging = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Staging)); Framebuffer framebuffer = RF.CreateFramebuffer(new FramebufferDescription(null, target)); DeviceBuffer orthoBuffer = RF.CreateBuffer(new BufferDescription(64, BufferUsage.UniformBuffer)); Matrix4x4 orthoMatrix = Matrix4x4.CreateOrthographicOffCenter( 0, framebuffer.Width, framebuffer.Height, 0, -1, 1); GD.UpdateBuffer(orthoBuffer, 0, ref orthoMatrix); ShaderSetDescription shaderSet = new ShaderSetDescription( new VertexLayoutDescription[] { new VertexLayoutDescription( new VertexElementDescription("Position", VertexElementSemantic.Position, VertexElementFormat.Float2), new VertexElementDescription("Color", VertexElementSemantic.Color, VertexElementFormat.UShort4_Norm)) }, new Shader[] { TestShaders.Load(RF, "U16NormVertexAttribs", ShaderStages.Vertex, "VS"), TestShaders.Load(RF, "U16NormVertexAttribs", ShaderStages.Fragment, "FS") }); ResourceLayout layout = RF.CreateResourceLayout(new ResourceLayoutDescription( new ResourceLayoutElementDescription("Ortho", ResourceKind.UniformBuffer, ShaderStages.Vertex))); ResourceSet set = RF.CreateResourceSet(new ResourceSetDescription(layout, orthoBuffer)); GraphicsPipelineDescription gpd = new GraphicsPipelineDescription( BlendStateDescription.SingleOverrideBlend, DepthStencilStateDescription.Disabled, RasterizerStateDescription.Default, PrimitiveTopology.PointList, shaderSet, layout, framebuffer.OutputDescription); Pipeline pipeline = RF.CreateGraphicsPipeline(ref gpd); VertexCPU_UShortNorm[] vertices = new VertexCPU_UShortNorm[] { new VertexCPU_UShortNorm { Position = new Vector2(0.5f, 0.5f), R = UShortNorm(0.25f), G = UShortNorm(0.5f), B = UShortNorm(0.75f), }, new VertexCPU_UShortNorm { Position = new Vector2(10.5f, 12.5f), R = UShortNorm(0.25f), G = UShortNorm(0.5f), B = UShortNorm(0.75f), }, new VertexCPU_UShortNorm { Position = new Vector2(25.5f, 35.5f), R = UShortNorm(0.75f), G = UShortNorm(0.5f), B = UShortNorm(0.25f), }, new VertexCPU_UShortNorm { Position = new Vector2(49.5f, 49.5f), R = UShortNorm(0.15f), G = UShortNorm(0.25f), B = UShortNorm(0.35f), }, }; DeviceBuffer vb = RF.CreateBuffer( new BufferDescription((uint)(Unsafe.SizeOf <VertexCPU_UShortNorm>() * vertices.Length), BufferUsage.VertexBuffer)); GD.UpdateBuffer(vb, 0, vertices); CommandList cl = RF.CreateCommandList(); cl.Begin(); cl.SetFramebuffer(framebuffer); cl.SetFullViewports(); cl.SetFullScissorRects(); cl.ClearColorTarget(0, RgbaFloat.Black); cl.SetPipeline(pipeline); cl.SetVertexBuffer(0, vb); cl.SetGraphicsResourceSet(0, set); cl.Draw((uint)vertices.Length); cl.CopyTexture(target, staging); cl.End(); GD.SubmitCommands(cl); GD.WaitForIdle(); MappedResourceView <RgbaFloat> readView = GD.Map <RgbaFloat>(staging, MapMode.Read); foreach (VertexCPU_UShortNorm vertex in vertices) { uint x = (uint)vertex.Position.X; uint y = (uint)vertex.Position.Y; if (!GD.IsUvOriginTopLeft) { y = framebuffer.Height - y - 1; } RgbaFloat expectedColor = new RgbaFloat( vertex.R / (float)ushort.MaxValue, vertex.G / (float)ushort.MaxValue, vertex.B / (float)ushort.MaxValue, 1); Assert.Equal(expectedColor, readView[x, y], RgbaFloatFuzzyComparer.Instance); } GD.Unmap(staging); }
protected override void ClearColorTargetCore(uint index, RgbaFloat clearColor) { _currentCommands.ClearColorTarget(index, clearColor); }
public MTLPipeline(ref GraphicsPipelineDescription description, MTLGraphicsDevice gd) : base(ref description) { PrimitiveType = MTLFormats.VdToMTLPrimitiveTopology(description.PrimitiveTopology); ResourceLayouts = new MTLResourceLayout[description.ResourceLayouts.Length]; NonVertexBufferCount = 0; for (int i = 0; i < ResourceLayouts.Length; i++) { ResourceLayouts[i] = Util.AssertSubtype <ResourceLayout, MTLResourceLayout>(description.ResourceLayouts[i]); NonVertexBufferCount += ResourceLayouts[i].BufferCount; } ResourceBindingModel = description.ResourceBindingModel ?? gd.ResourceBindingModel; CullMode = MTLFormats.VdToMTLCullMode(description.RasterizerState.CullMode); FrontFace = MTLFormats.VdVoMTLFrontFace(description.RasterizerState.FrontFace); FillMode = MTLFormats.VdToMTLFillMode(description.RasterizerState.FillMode); ScissorTestEnabled = description.RasterizerState.ScissorTestEnabled; MTLRenderPipelineDescriptor mtlDesc = MTLRenderPipelineDescriptor.New(); foreach (Shader shader in description.ShaderSet.Shaders) { MTLShader mtlShader = Util.AssertSubtype <Shader, MTLShader>(shader); MTLFunction specializedFunction; if (mtlShader.HasFunctionConstants) { // Need to create specialized MTLFunction. MTLFunctionConstantValues constantValues = CreateConstantValues(description.ShaderSet.Specializations); specializedFunction = mtlShader.Library.newFunctionWithNameConstantValues(mtlShader.EntryPoint, constantValues); AddSpecializedFunction(specializedFunction); ObjectiveCRuntime.release(constantValues.NativePtr); Debug.Assert(specializedFunction.NativePtr != IntPtr.Zero, "Failed to create specialized MTLFunction"); } else { specializedFunction = mtlShader.Function; } if (shader.Stage == ShaderStages.Vertex) { mtlDesc.vertexFunction = specializedFunction; } else if (shader.Stage == ShaderStages.Fragment) { mtlDesc.fragmentFunction = specializedFunction; } } // Vertex layouts VertexLayoutDescription[] vdVertexLayouts = description.ShaderSet.VertexLayouts; MTLVertexDescriptor vertexDescriptor = mtlDesc.vertexDescriptor; for (uint i = 0; i < vdVertexLayouts.Length; i++) { uint layoutIndex = ResourceBindingModel == ResourceBindingModel.Improved ? NonVertexBufferCount + i : i; MTLVertexBufferLayoutDescriptor mtlLayout = vertexDescriptor.layouts[layoutIndex]; mtlLayout.stride = (UIntPtr)vdVertexLayouts[i].Stride; uint stepRate = vdVertexLayouts[i].InstanceStepRate; mtlLayout.stepFunction = stepRate == 0 ? MTLVertexStepFunction.PerVertex : MTLVertexStepFunction.PerInstance; mtlLayout.stepRate = (UIntPtr)Math.Max(1, stepRate); } uint element = 0; for (uint i = 0; i < vdVertexLayouts.Length; i++) { uint offset = 0; VertexLayoutDescription vdDesc = vdVertexLayouts[i]; for (uint j = 0; j < vdDesc.Elements.Length; j++) { VertexElementDescription elementDesc = vdDesc.Elements[j]; MTLVertexAttributeDescriptor mtlAttribute = vertexDescriptor.attributes[element]; mtlAttribute.bufferIndex = (UIntPtr)(ResourceBindingModel == ResourceBindingModel.Improved ? NonVertexBufferCount + i : i); mtlAttribute.format = MTLFormats.VdToMTLVertexFormat(elementDesc.Format); mtlAttribute.offset = (UIntPtr)offset; offset += FormatHelpers.GetSizeInBytes(elementDesc.Format); element += 1; } } VertexBufferCount = (uint)vdVertexLayouts.Length; // Outputs OutputDescription outputs = description.Outputs; BlendStateDescription blendStateDesc = description.BlendState; BlendColor = blendStateDesc.BlendFactor; if (outputs.SampleCount != TextureSampleCount.Count1) { mtlDesc.sampleCount = (UIntPtr)FormatHelpers.GetSampleCountUInt32(outputs.SampleCount); } if (outputs.DepthAttachment != null) { PixelFormat depthFormat = outputs.DepthAttachment.Value.Format; MTLPixelFormat mtlDepthFormat = MTLFormats.VdToMTLPixelFormat(depthFormat, true); mtlDesc.depthAttachmentPixelFormat = mtlDepthFormat; if ((FormatHelpers.IsStencilFormat(depthFormat))) { HasStencil = true; mtlDesc.stencilAttachmentPixelFormat = mtlDepthFormat; } } for (uint i = 0; i < outputs.ColorAttachments.Length; i++) { BlendAttachmentDescription attachmentBlendDesc = blendStateDesc.AttachmentStates[i]; MTLRenderPipelineColorAttachmentDescriptor colorDesc = mtlDesc.colorAttachments[i]; colorDesc.pixelFormat = MTLFormats.VdToMTLPixelFormat(outputs.ColorAttachments[i].Format, false); colorDesc.blendingEnabled = attachmentBlendDesc.BlendEnabled; colorDesc.alphaBlendOperation = MTLFormats.VdToMTLBlendOp(attachmentBlendDesc.AlphaFunction); colorDesc.sourceAlphaBlendFactor = MTLFormats.VdToMTLBlendFactor(attachmentBlendDesc.SourceAlphaFactor); colorDesc.destinationAlphaBlendFactor = MTLFormats.VdToMTLBlendFactor(attachmentBlendDesc.DestinationAlphaFactor); colorDesc.rgbBlendOperation = MTLFormats.VdToMTLBlendOp(attachmentBlendDesc.ColorFunction); colorDesc.sourceRGBBlendFactor = MTLFormats.VdToMTLBlendFactor(attachmentBlendDesc.SourceColorFactor); colorDesc.destinationRGBBlendFactor = MTLFormats.VdToMTLBlendFactor(attachmentBlendDesc.DestinationColorFactor); } RenderPipelineState = gd.Device.newRenderPipelineStateWithDescriptor(mtlDesc); ObjectiveCRuntime.release(mtlDesc.NativePtr); if (outputs.DepthAttachment != null) { MTLDepthStencilDescriptor depthDescriptor = MTLUtil.AllocInit <MTLDepthStencilDescriptor>( nameof(MTLDepthStencilDescriptor)); depthDescriptor.depthCompareFunction = MTLFormats.VdToMTLCompareFunction( description.DepthStencilState.DepthComparison); depthDescriptor.depthWriteEnabled = description.DepthStencilState.DepthWriteEnabled; bool stencilEnabled = description.DepthStencilState.StencilTestEnabled; if (stencilEnabled) { StencilReference = description.DepthStencilState.StencilReference; StencilBehaviorDescription vdFrontDesc = description.DepthStencilState.StencilFront; MTLStencilDescriptor front = MTLUtil.AllocInit <MTLStencilDescriptor>(nameof(MTLStencilDescriptor)); front.readMask = stencilEnabled ? description.DepthStencilState.StencilReadMask : 0u; front.writeMask = stencilEnabled ? description.DepthStencilState.StencilWriteMask : 0u; front.depthFailureOperation = MTLFormats.VdToMTLStencilOperation(vdFrontDesc.DepthFail); front.stencilFailureOperation = MTLFormats.VdToMTLStencilOperation(vdFrontDesc.Fail); front.depthStencilPassOperation = MTLFormats.VdToMTLStencilOperation(vdFrontDesc.Pass); front.stencilCompareFunction = MTLFormats.VdToMTLCompareFunction(vdFrontDesc.Comparison); depthDescriptor.frontFaceStencil = front; StencilBehaviorDescription vdBackDesc = description.DepthStencilState.StencilBack; MTLStencilDescriptor back = MTLUtil.AllocInit <MTLStencilDescriptor>(nameof(MTLStencilDescriptor)); back.readMask = stencilEnabled ? description.DepthStencilState.StencilReadMask : 0u; back.writeMask = stencilEnabled ? description.DepthStencilState.StencilWriteMask : 0u; back.depthFailureOperation = MTLFormats.VdToMTLStencilOperation(vdBackDesc.DepthFail); back.stencilFailureOperation = MTLFormats.VdToMTLStencilOperation(vdBackDesc.Fail); back.depthStencilPassOperation = MTLFormats.VdToMTLStencilOperation(vdBackDesc.Pass); back.stencilCompareFunction = MTLFormats.VdToMTLCompareFunction(vdBackDesc.Comparison); depthDescriptor.backFaceStencil = back; ObjectiveCRuntime.release(front.NativePtr); ObjectiveCRuntime.release(back.NativePtr); } DepthStencilState = gd.Device.newDepthStencilStateWithDescriptor(depthDescriptor); ObjectiveCRuntime.release(depthDescriptor.NativePtr); } DepthClipMode = description.DepthStencilState.DepthTestEnabled ? MTLDepthClipMode.Clip : MTLDepthClipMode.Clamp; }
protected override void ClearColorTargetCore(uint index, RgbaFloat clearColor) { _context.ClearRenderTargetView(D3D11Framebuffer.RenderTargetViews[index], new RawColor4(clearColor.R, clearColor.G, clearColor.B, clearColor.A)); }
public VertexPositionColor(Vector2 position, Color color) { Position = position; Color = color.ToVeldrid(); }
private void BeginCurrentRenderPass() { Debug.Assert(_activeRenderPass == VkRenderPass.Null); Debug.Assert(_currentFramebuffer != null); _currentFramebufferEverActive = true; uint attachmentCount = _currentFramebuffer.AttachmentCount; bool haveAnyAttachments = _framebuffer.ColorTargets.Count > 0 || _framebuffer.DepthTarget != null; bool haveAllClearValues = _depthClearValue.HasValue || _framebuffer.DepthTarget == null; bool haveAnyClearValues = _depthClearValue.HasValue; for (int i = 0; i < _currentFramebuffer.ColorTargets.Count; i++) { if (!_validColorClearValues[i]) { haveAllClearValues = false; haveAnyClearValues = true; } else { haveAnyClearValues = true; } } VkRenderPassBeginInfo renderPassBI = VkRenderPassBeginInfo.New(); renderPassBI.renderArea = new VkRect2D(_currentFramebuffer.RenderableWidth, _currentFramebuffer.RenderableHeight); renderPassBI.framebuffer = _currentFramebuffer.CurrentFramebuffer; if (!haveAnyAttachments || !haveAllClearValues) { renderPassBI.renderPass = _currentFramebuffer.RenderPassNoClear; vkCmdBeginRenderPass(_cb, ref renderPassBI, VkSubpassContents.Inline); _activeRenderPass = _currentFramebuffer.RenderPassNoClear; if (haveAnyClearValues) { if (_depthClearValue.HasValue) { ClearDepthStencil(_depthClearValue.Value.depthStencil.depth, (byte)_depthClearValue.Value.depthStencil.stencil); _depthClearValue = null; } for (uint i = 0; i < _currentFramebuffer.ColorTargets.Count; i++) { if (_validColorClearValues[i]) { _validColorClearValues[i] = false; VkClearValue vkClearValue = _clearValues[i]; RgbaFloat clearColor = new RgbaFloat( vkClearValue.color.float32_0, vkClearValue.color.float32_1, vkClearValue.color.float32_2, vkClearValue.color.float32_3); ClearColorTarget(i, clearColor); } } } } else { // We have clear values for every attachment. renderPassBI.renderPass = _currentFramebuffer.RenderPassClear; fixed(VkClearValue *clearValuesPtr = &_clearValues[0]) { renderPassBI.clearValueCount = attachmentCount; renderPassBI.pClearValues = clearValuesPtr; if (_depthClearValue.HasValue) { _clearValues[_currentFramebuffer.ColorTargets.Count] = _depthClearValue.Value; _depthClearValue = null; } vkCmdBeginRenderPass(_cb, ref renderPassBI, VkSubpassContents.Inline); _activeRenderPass = _currentFramebuffer.RenderPassClear; Util.ClearArray(_validColorClearValues); } } // Set new image layouts foreach (FramebufferAttachment colorTarget in _currentFramebuffer.ColorTargets) { VkTexture vkTex = Util.AssertSubtype <Texture, VkTexture>(colorTarget.Target); VkImageLayout layout = (vkTex.Usage & TextureUsage.Sampled) != 0 ? VkImageLayout.ShaderReadOnlyOptimal : VkImageLayout.ColorAttachmentOptimal; vkTex.SetImageLayout(colorTarget.ArrayLayer, layout); } if (_currentFramebuffer.DepthTarget != null) { VkTexture vkDepthTex = Util.AssertSubtype <Texture, VkTexture>(_currentFramebuffer.DepthTarget.Value.Target); VkImageLayout layout = (vkDepthTex.Usage & TextureUsage.Sampled) != 0 ? VkImageLayout.ShaderReadOnlyOptimal : VkImageLayout.DepthStencilAttachmentOptimal; vkDepthTex.SetImageLayout(_currentFramebuffer.DepthTarget.Value.ArrayLayer, layout); } }
public unsafe InternalSamplerState( SamplerAddressMode addressU, SamplerAddressMode addressV, SamplerAddressMode addressW, SamplerFilter filter, int maxAnisotropy, RgbaFloat borderColor, DepthComparison comparison, int minLod, int maxLod, int lodBias, bool mip) { _samplerID = GL.GenSampler(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureWrapR, (int)OpenGLESFormats.VeldridToGLTextureWrapMode(addressU)); Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureWrapS, (int)OpenGLESFormats.VeldridToGLTextureWrapMode(addressV)); Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureWrapT, (int)OpenGLESFormats.VeldridToGLTextureWrapMode(addressW)); Utilities.CheckLastGLError(); if (addressU == SamplerAddressMode.Border || addressV == SamplerAddressMode.Border || addressW == SamplerAddressMode.Border) { #pragma warning disable CS0618 // TextureBorderColor is not exposed on SamplerParameterName GL.SamplerParameter(_samplerID, All.TextureBorderColor, (float *)&borderColor); #pragma warning restore CS0618 Utilities.CheckLastGLError(); } GL.SamplerParameter(_samplerID, SamplerParameterName.TextureMinLod, (float)minLod); Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureMaxLod, (float)maxLod); Utilities.CheckLastGLError(); if (filter == SamplerFilter.Anisotropic || filter == SamplerFilter.ComparisonAnisotropic) { #pragma warning disable CS0618 // TextureMaxAnisotropyExt is not exposed on SamplerParameterName GL.SamplerParameter(_samplerID, All.TextureMaxAnisotropyExt, (float)maxAnisotropy); #pragma warning restore CS0618 // Type or member is obsolete Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureMinFilter, mip ? (int)TextureMinFilter.LinearMipmapLinear : (int)TextureMinFilter.Linear); Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureMagFilter, (int)TextureMagFilter.Linear); Utilities.CheckLastGLError(); } else { OpenGLESFormats.VeldridToGLTextureMinMagFilter(filter, mip, out TextureMinFilter min, out TextureMagFilter mag); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureMinFilter, (int)min); Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureMagFilter, (int)mag); Utilities.CheckLastGLError(); } if (s_comparisonFilters.Contains(filter)) { GL.SamplerParameter(_samplerID, SamplerParameterName.TextureCompareMode, (int)All.CompareRefToTexture); Utilities.CheckLastGLError(); GL.SamplerParameter(_samplerID, SamplerParameterName.TextureCompareFunc, (int)OpenGLESFormats.ConvertDepthComparison(comparison)); Utilities.CheckLastGLError(); } }
public void ClearColorTarget(uint index, RgbaFloat clearColor) { NoAllocClearColorTargetEntry entry = new NoAllocClearColorTargetEntry(index, clearColor); AddEntry(ClearColorTargetID, ref entry); }
public Light(Camera camera, RgbaFloat color) { LightCam = camera; _color = color.ToVector4(); }
public void Points_WithFloat16Color() { Texture target = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.RenderTarget)); Texture staging = RF.CreateTexture(TextureDescription.Texture2D( 50, 50, 1, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Staging)); Framebuffer framebuffer = RF.CreateFramebuffer(new FramebufferDescription(null, target)); DeviceBuffer infoBuffer = RF.CreateBuffer(new BufferDescription(16, BufferUsage.UniformBuffer)); DeviceBuffer orthoBuffer = RF.CreateBuffer(new BufferDescription(64, BufferUsage.UniformBuffer)); Matrix4x4 orthoMatrix = Matrix4x4.CreateOrthographicOffCenter( 0, framebuffer.Width, framebuffer.Height, 0, -1, 1); GD.UpdateBuffer(orthoBuffer, 0, ref orthoMatrix); ShaderSetDescription shaderSet = new ShaderSetDescription( new VertexLayoutDescription[] { new VertexLayoutDescription( new VertexElementDescription("Position", VertexElementSemantic.TextureCoordinate, VertexElementFormat.Float2), new VertexElementDescription("Color_Half", VertexElementSemantic.TextureCoordinate, VertexElementFormat.Half4)) }, TestShaders.LoadVertexFragment(RF, "F16VertexAttribs")); ResourceLayout layout = RF.CreateResourceLayout(new ResourceLayoutDescription( new ResourceLayoutElementDescription("InfoBuffer", ResourceKind.UniformBuffer, ShaderStages.Vertex), new ResourceLayoutElementDescription("OrthoBuffer", ResourceKind.UniformBuffer, ShaderStages.Vertex))); ResourceSet set = RF.CreateResourceSet(new ResourceSetDescription(layout, infoBuffer, orthoBuffer)); GraphicsPipelineDescription gpd = new GraphicsPipelineDescription( BlendStateDescription.SingleOverrideBlend, DepthStencilStateDescription.Disabled, RasterizerStateDescription.Default, PrimitiveTopology.PointList, shaderSet, layout, framebuffer.OutputDescription); Pipeline pipeline = RF.CreateGraphicsPipeline(ref gpd); uint colorNormalizationFactor = 2500; const ushort f16_375 = 0x5DDC; // 375.0 const ushort f16_500 = 0x5FD0; // 500.0 const ushort f16_625 = 0x60E2; // 625.0 const ushort f16_875 = 0x62D6; // 875.0 const ushort f16_1250 = 0x64E2; // 1250.0 const ushort f16_1875 = 0x6753; // 1875.0 VertexCPU_UShort[] vertices = new VertexCPU_UShort[] { new VertexCPU_UShort { Position = new Vector2(0.5f, 0.5f), R = f16_625, G = f16_1250, B = f16_1875, }, new VertexCPU_UShort { Position = new Vector2(10.5f, 12.5f), R = f16_625, G = f16_1250, B = f16_1875, }, new VertexCPU_UShort { Position = new Vector2(25.5f, 35.5f), R = f16_1875, G = f16_1250, B = f16_625, }, new VertexCPU_UShort { Position = new Vector2(49.5f, 49.5f), R = f16_375, G = f16_500, B = f16_875, }, }; RgbaFloat[] expectedColors = new[] { new RgbaFloat( 625.0f / colorNormalizationFactor, 1250.0f / colorNormalizationFactor, 1875.0f / colorNormalizationFactor, 1), new RgbaFloat( 625.0f / colorNormalizationFactor, 1250.0f / colorNormalizationFactor, 1875.0f / colorNormalizationFactor, 1), new RgbaFloat( 1875.0f / colorNormalizationFactor, 1250.0f / colorNormalizationFactor, 625.0f / colorNormalizationFactor, 1), new RgbaFloat( 375.0f / colorNormalizationFactor, 500.0f / colorNormalizationFactor, 875.0f / colorNormalizationFactor, 1), }; DeviceBuffer vb = RF.CreateBuffer( new BufferDescription((uint)(Unsafe.SizeOf <UIntVertexAttribsVertex>() * vertices.Length), BufferUsage.VertexBuffer)); GD.UpdateBuffer(vb, 0, vertices); GD.UpdateBuffer(infoBuffer, 0, new UIntVertexAttribsInfo { ColorNormalizationFactor = colorNormalizationFactor }); CommandList cl = RF.CreateCommandList(); cl.Begin(); cl.SetFramebuffer(framebuffer); cl.SetFullViewports(); cl.SetFullScissorRects(); cl.ClearColorTarget(0, RgbaFloat.Black); cl.SetPipeline(pipeline); cl.SetVertexBuffer(0, vb); cl.SetGraphicsResourceSet(0, set); cl.Draw((uint)vertices.Length); cl.CopyTexture(target, staging); cl.End(); GD.SubmitCommands(cl); GD.WaitForIdle(); MappedResourceView <RgbaFloat> readView = GD.Map <RgbaFloat>(staging, MapMode.Read); for (int i = 0; i < vertices.Length; i++) { VertexCPU_UShort vertex = vertices[i]; uint x = (uint)vertex.Position.X; uint y = (uint)vertex.Position.Y; if (!GD.IsUvOriginTopLeft || GD.IsClipSpaceYInverted) { y = framebuffer.Height - y - 1; } RgbaFloat expectedColor = expectedColors[i]; Assert.Equal(expectedColor, readView[x, y], RgbaFloatFuzzyComparer.Instance); } GD.Unmap(staging); }
public Light(Camera camera, RgbaFloat color, float intensity) { LightCam = camera; _color = color.ToVector4(); _color.W = intensity; }
internal void SetColor(RgbaFloat color) { _modelColor = color.ToVector4(); }
public Light(Camera camera, RgbaFloat color, Vector4 attenuation) { LightCam = camera; _color = color.ToVector4(); _attenuation = attenuation; }
public static void SolidColor(RgbaFloat color) => VxContext.Instance.SetColor(color);
// TODO: Abstract Resource Crreation for Uniforms, Vertex Layouts, Disposing override protected void CreateResources() { RgbaFloat lightColor = RgbaFloat.LightGrey; var lightLookAt = new Vector4(0, 0, 0, 1); var lightCam = new OrthographicCamera(35, 35, Light.DEFAULT_POSITION, lightLookAt); _sceneRuntimeState.Light = new Light(lightCam, lightColor, 0.1f); // string filePath = Path.Combine(AppContext.BaseDirectory, "Models/sphere.obj"); //string filePath = Path.Combine(AppContext.BaseDirectory, "Models/300_polygon_sphere_100mm.STL"); // string filePath = "Models/sphere_centered.obj"; string filePath = "Models/chinesedragon.dae"; // string filePath = "Models/Box.dae"; _model = AssimpLoader.LoadFromFileWithRealtimeMaterial <VertexPositionNormal>(AppContext.BaseDirectory, filePath, VertexPositionNormal.HenzaiType); //GeometryUtils.GenerateSphericalTextureCoordinatesFor(_model.meshes[0]); /// Uniform 1 - Camera _cameraProjViewBuffer = _factory.CreateBuffer(new BufferDescription(Camera.SizeInBytes, BufferUsage.UniformBuffer | BufferUsage.Dynamic)); var resourceLayoutElementDescription = new ResourceLayoutElementDescription("projViewWorld", ResourceKind.UniformBuffer, ShaderStages.Vertex); ResourceLayoutElementDescription[] resourceLayoutElementDescriptions = { resourceLayoutElementDescription }; var resourceLayoutDescription = new ResourceLayoutDescription(resourceLayoutElementDescriptions); BindableResource[] bindableResources = new BindableResource[] { _cameraProjViewBuffer }; _cameraResourceLayout = _factory.CreateResourceLayout(resourceLayoutDescription); var resourceSetDescription = new ResourceSetDescription(_cameraResourceLayout, bindableResources); _cameraResourceSet = _factory.CreateResourceSet(resourceSetDescription); // Uniform 2 - Material _materialBuffer = _factory.CreateBuffer(new BufferDescription(RealtimeMaterial.SizeInBytes, BufferUsage.UniformBuffer)); var resourceLayoutElementDescriptionMaterial = new ResourceLayoutElementDescription("material", ResourceKind.UniformBuffer, ShaderStages.Fragment); ResourceLayoutElementDescription[] resourceLayoutElementDescriptionsMaterial = { resourceLayoutElementDescriptionMaterial }; var resourceLayoutDescriptionMaterial = new ResourceLayoutDescription(resourceLayoutElementDescriptionsMaterial); BindableResource[] bindableResourcesMaterial = new BindableResource[] { _materialBuffer }; _materialResourceLayout = _factory.CreateResourceLayout(resourceLayoutDescriptionMaterial); var resourceSetDescriptionMaterial = new ResourceSetDescription(_materialResourceLayout, bindableResourcesMaterial); _materialResourceSet = _factory.CreateResourceSet(resourceSetDescriptionMaterial); // Uniform 3 - Light _lightBuffer = _factory.CreateBuffer(new BufferDescription(Light.SizeInBytes, BufferUsage.UniformBuffer)); var resourceLayoutElementDescriptionLight = new ResourceLayoutElementDescription("light", ResourceKind.UniformBuffer, ShaderStages.Fragment); ResourceLayoutElementDescription[] resourceLayoutElementDescriptionsLight = { resourceLayoutElementDescriptionLight }; var resourceLayoutDescriptionLight = new ResourceLayoutDescription(resourceLayoutElementDescriptionsLight); BindableResource[] bindableResourcesLight = new BindableResource[] { _lightBuffer }; _lightResourceLayout = _factory.CreateResourceLayout(resourceLayoutDescriptionLight); var resourceSetDescriptionLight = new ResourceSetDescription(_lightResourceLayout, bindableResourcesLight); _lightResourceSet = _factory.CreateResourceSet(resourceSetDescriptionLight); for (int i = 0; i < _model.MeshCount; i++) { var mesh = _model.GetMesh(i); DeviceBuffer vertexBuffer = _factory.CreateBuffer(new BufferDescription(mesh.Vertices.LengthUnsigned() * VertexPositionNormal.SizeInBytes, BufferUsage.VertexBuffer)); DeviceBuffer indexBuffer = _factory.CreateBuffer(new BufferDescription(mesh.Indices.LengthUnsigned() * sizeof(ushort), BufferUsage.IndexBuffer)); _vertexBuffers.Add(vertexBuffer); _indexBuffers.Add(indexBuffer); GraphicsDevice.UpdateBuffer(vertexBuffer, 0, mesh.Vertices); GraphicsDevice.UpdateBuffer(indexBuffer, 0, mesh.Indices); } VertexLayoutDescription vertexLayout = new VertexLayoutDescription( new VertexElementDescription("Position", VertexElementSemantic.Position, VertexElementFormat.Float3), new VertexElementDescription("Normal", VertexElementSemantic.Normal, VertexElementFormat.Float3) //new VertexElementDescription("UV",VertexElementSemantic.TextureCoordinate,VertexElementFormat.Float2) ); _vertexShader = IO.LoadShader("Phong", ShaderStages.Vertex, GraphicsDevice); _fragmentShader = IO.LoadShader("Phong", ShaderStages.Fragment, GraphicsDevice); GraphicsPipelineDescription pipelineDescription = new GraphicsPipelineDescription() { BlendState = BlendStateDescription.SingleOverrideBlend, DepthStencilState = DepthStencilStateDescription.DepthOnlyLessEqual, RasterizerState = new RasterizerStateDescription( cullMode: FaceCullMode.Back, fillMode: PolygonFillMode.Solid, // Wireframe doesnt seem to work with metal frontFace: FrontFace.Clockwise, depthClipEnabled: true, scissorTestEnabled: false ), PrimitiveTopology = PrimitiveTopology.TriangleList, //ResourceLayouts = new ResourceLayout[] {_cameraResourceLayout,_materialResourceLayout,_lightResourceLayout}, ResourceLayouts = new ResourceLayout[] { _cameraResourceLayout, _lightResourceLayout, _materialResourceLayout }, ShaderSet = new ShaderSetDescription( vertexLayouts: new VertexLayoutDescription[] { vertexLayout }, shaders: new Shader[] { _vertexShader, _fragmentShader } ), Outputs = GraphicsDevice.SwapchainFramebuffer.OutputDescription }; _pipeline = _factory.CreateGraphicsPipeline(pipelineDescription); }
public VertexPosition2ColorTexture(Vector2 position, RgbaFloat color, Vector2 textureCoordinates) { Position = position; Color = color; TextureCoordinates = textureCoordinates; }
private void PushVertex(Vector2 pos, float tx, float ty, RgbaFloat color) { vertices.Add(new VertexPositionColorTexture(pos, color, new Vector2(tx, ty))); }
public VkPipeline(VkGraphicsDevice gd, ref GraphicsPipelineDescription description) : base(ref description) { _gd = gd; IsComputePipeline = false; RefCount = new ResourceRefCount(DisposeCore); VkGraphicsPipelineCreateInfo pipelineCI = VkGraphicsPipelineCreateInfo.New(); // Blend State VkPipelineColorBlendStateCreateInfo blendStateCI = VkPipelineColorBlendStateCreateInfo.New(); int attachmentsCount = description.BlendState.AttachmentStates.Length; VkPipelineColorBlendAttachmentState *attachmentsPtr = stackalloc VkPipelineColorBlendAttachmentState[attachmentsCount]; for (int i = 0; i < attachmentsCount; i++) { BlendAttachmentDescription vdDesc = description.BlendState.AttachmentStates[i]; VkPipelineColorBlendAttachmentState attachmentState = new VkPipelineColorBlendAttachmentState(); attachmentState.srcColorBlendFactor = VkFormats.VdToVkBlendFactor(vdDesc.SourceColorFactor); attachmentState.dstColorBlendFactor = VkFormats.VdToVkBlendFactor(vdDesc.DestinationColorFactor); attachmentState.colorBlendOp = VkFormats.VdToVkBlendOp(vdDesc.ColorFunction); attachmentState.srcAlphaBlendFactor = VkFormats.VdToVkBlendFactor(vdDesc.SourceAlphaFactor); attachmentState.dstAlphaBlendFactor = VkFormats.VdToVkBlendFactor(vdDesc.DestinationAlphaFactor); attachmentState.alphaBlendOp = VkFormats.VdToVkBlendOp(vdDesc.AlphaFunction); attachmentState.blendEnable = vdDesc.BlendEnabled; attachmentState.colorWriteMask = VkColorComponentFlags.R | VkColorComponentFlags.G | VkColorComponentFlags.B | VkColorComponentFlags.A; attachmentsPtr[i] = attachmentState; } blendStateCI.attachmentCount = (uint)attachmentsCount; blendStateCI.pAttachments = attachmentsPtr; RgbaFloat blendFactor = description.BlendState.BlendFactor; blendStateCI.blendConstants_0 = blendFactor.R; blendStateCI.blendConstants_1 = blendFactor.G; blendStateCI.blendConstants_2 = blendFactor.B; blendStateCI.blendConstants_3 = blendFactor.A; pipelineCI.pColorBlendState = &blendStateCI; // Rasterizer State RasterizerStateDescription rsDesc = description.RasterizerState; VkPipelineRasterizationStateCreateInfo rsCI = VkPipelineRasterizationStateCreateInfo.New(); rsCI.cullMode = VkFormats.VdToVkCullMode(rsDesc.CullMode); rsCI.polygonMode = VkFormats.VdToVkPolygonMode(rsDesc.FillMode); rsCI.depthClampEnable = !rsDesc.DepthClipEnabled; rsCI.frontFace = rsDesc.FrontFace == FrontFace.Clockwise ? VkFrontFace.Clockwise : VkFrontFace.CounterClockwise; rsCI.lineWidth = 1f; pipelineCI.pRasterizationState = &rsCI; ScissorTestEnabled = rsDesc.ScissorTestEnabled; // Dynamic State VkPipelineDynamicStateCreateInfo dynamicStateCI = VkPipelineDynamicStateCreateInfo.New(); VkDynamicState *dynamicStates = stackalloc VkDynamicState[2]; dynamicStates[0] = VkDynamicState.Viewport; dynamicStates[1] = VkDynamicState.Scissor; dynamicStateCI.dynamicStateCount = 2; dynamicStateCI.pDynamicStates = dynamicStates; pipelineCI.pDynamicState = &dynamicStateCI; // Depth Stencil State DepthStencilStateDescription vdDssDesc = description.DepthStencilState; VkPipelineDepthStencilStateCreateInfo dssCI = VkPipelineDepthStencilStateCreateInfo.New(); dssCI.depthWriteEnable = vdDssDesc.DepthWriteEnabled; dssCI.depthTestEnable = vdDssDesc.DepthTestEnabled; dssCI.depthCompareOp = VkFormats.VdToVkCompareOp(vdDssDesc.DepthComparison); dssCI.stencilTestEnable = vdDssDesc.StencilTestEnabled; dssCI.front.failOp = VkFormats.VdToVkStencilOp(vdDssDesc.StencilFront.Fail); dssCI.front.passOp = VkFormats.VdToVkStencilOp(vdDssDesc.StencilFront.Pass); dssCI.front.depthFailOp = VkFormats.VdToVkStencilOp(vdDssDesc.StencilFront.DepthFail); dssCI.front.compareMask = vdDssDesc.StencilReadMask; dssCI.front.writeMask = vdDssDesc.StencilWriteMask; dssCI.front.reference = vdDssDesc.StencilReference; dssCI.back.failOp = VkFormats.VdToVkStencilOp(vdDssDesc.StencilBack.Fail); dssCI.back.passOp = VkFormats.VdToVkStencilOp(vdDssDesc.StencilBack.Pass); dssCI.back.depthFailOp = VkFormats.VdToVkStencilOp(vdDssDesc.StencilBack.DepthFail); dssCI.back.compareMask = vdDssDesc.StencilReadMask; dssCI.back.writeMask = vdDssDesc.StencilWriteMask; dssCI.back.reference = vdDssDesc.StencilReference; pipelineCI.pDepthStencilState = &dssCI; // Multisample VkPipelineMultisampleStateCreateInfo multisampleCI = VkPipelineMultisampleStateCreateInfo.New(); VkSampleCountFlags vkSampleCount = VkFormats.VdToVkSampleCount(description.Outputs.SampleCount); multisampleCI.rasterizationSamples = vkSampleCount; pipelineCI.pMultisampleState = &multisampleCI; // Input Assembly VkPipelineInputAssemblyStateCreateInfo inputAssemblyCI = VkPipelineInputAssemblyStateCreateInfo.New(); inputAssemblyCI.topology = VkFormats.VdToVkPrimitiveTopology(description.PrimitiveTopology); pipelineCI.pInputAssemblyState = &inputAssemblyCI; // Vertex Input State VkPipelineVertexInputStateCreateInfo vertexInputCI = VkPipelineVertexInputStateCreateInfo.New(); VertexLayoutDescription[] inputDescriptions = description.ShaderSet.VertexLayouts; uint bindingCount = (uint)inputDescriptions.Length; uint attributeCount = 0; for (int i = 0; i < inputDescriptions.Length; i++) { attributeCount += (uint)inputDescriptions[i].Elements.Length; } VkVertexInputBindingDescription * bindingDescs = stackalloc VkVertexInputBindingDescription[(int)bindingCount]; VkVertexInputAttributeDescription *attributeDescs = stackalloc VkVertexInputAttributeDescription[(int)attributeCount]; int targetIndex = 0; int targetLocation = 0; for (int binding = 0; binding < inputDescriptions.Length; binding++) { VertexLayoutDescription inputDesc = inputDescriptions[binding]; bindingDescs[binding] = new VkVertexInputBindingDescription() { binding = (uint)binding, inputRate = (inputDesc.InstanceStepRate != 0) ? VkVertexInputRate.Instance : VkVertexInputRate.Vertex, stride = inputDesc.Stride }; uint currentOffset = 0; for (int location = 0; location < inputDesc.Elements.Length; location++) { VertexElementDescription inputElement = inputDesc.Elements[location]; attributeDescs[targetIndex] = new VkVertexInputAttributeDescription() { format = VkFormats.VdToVkVertexElementFormat(inputElement.Format), binding = (uint)binding, location = (uint)(targetLocation + location), offset = inputElement.Offset != 0 ? inputElement.Offset : currentOffset }; targetIndex += 1; currentOffset += FormatHelpers.GetSizeInBytes(inputElement.Format); } targetLocation += inputDesc.Elements.Length; } vertexInputCI.vertexBindingDescriptionCount = bindingCount; vertexInputCI.pVertexBindingDescriptions = bindingDescs; vertexInputCI.vertexAttributeDescriptionCount = attributeCount; vertexInputCI.pVertexAttributeDescriptions = attributeDescs; pipelineCI.pVertexInputState = &vertexInputCI; // Shader Stage VkSpecializationInfo specializationInfo; SpecializationConstant[] specDescs = description.ShaderSet.Specializations; if (specDescs != null) { uint specDataSize = 0; foreach (SpecializationConstant spec in specDescs) { specDataSize += VkFormats.GetSpecializationConstantSize(spec.Type); } byte *fullSpecData = stackalloc byte[(int)specDataSize]; int specializationCount = specDescs.Length; VkSpecializationMapEntry *mapEntries = stackalloc VkSpecializationMapEntry[specializationCount]; uint specOffset = 0; for (int i = 0; i < specializationCount; i++) { ulong data = specDescs[i].Data; byte *srcData = (byte *)&data; uint dataSize = VkFormats.GetSpecializationConstantSize(specDescs[i].Type); Unsafe.CopyBlock(fullSpecData + specOffset, srcData, dataSize); mapEntries[i].constantID = specDescs[i].ID; mapEntries[i].offset = specOffset; mapEntries[i].size = (UIntPtr)dataSize; specOffset += dataSize; } specializationInfo.dataSize = (UIntPtr)specDataSize; specializationInfo.pData = fullSpecData; specializationInfo.mapEntryCount = (uint)specializationCount; specializationInfo.pMapEntries = mapEntries; } Shader[] shaders = description.ShaderSet.Shaders; StackList <VkPipelineShaderStageCreateInfo> stages = new StackList <VkPipelineShaderStageCreateInfo>(); foreach (Shader shader in shaders) { VkShader vkShader = Util.AssertSubtype <Shader, VkShader>(shader); VkPipelineShaderStageCreateInfo stageCI = VkPipelineShaderStageCreateInfo.New(); stageCI.module = vkShader.ShaderModule; stageCI.stage = VkFormats.VdToVkShaderStages(shader.Stage); // stageCI.pName = CommonStrings.main; // Meh stageCI.pName = new FixedUtf8String(shader.EntryPoint); // TODO: DONT ALLOCATE HERE stageCI.pSpecializationInfo = &specializationInfo; stages.Add(stageCI); } pipelineCI.stageCount = stages.Count; pipelineCI.pStages = (VkPipelineShaderStageCreateInfo *)stages.Data; // ViewportState VkPipelineViewportStateCreateInfo viewportStateCI = VkPipelineViewportStateCreateInfo.New(); viewportStateCI.viewportCount = 1; viewportStateCI.scissorCount = 1; pipelineCI.pViewportState = &viewportStateCI; // Pipeline Layout ResourceLayout[] resourceLayouts = description.ResourceLayouts; VkPipelineLayoutCreateInfo pipelineLayoutCI = VkPipelineLayoutCreateInfo.New(); pipelineLayoutCI.setLayoutCount = (uint)resourceLayouts.Length; VkDescriptorSetLayout *dsls = stackalloc VkDescriptorSetLayout[resourceLayouts.Length]; for (int i = 0; i < resourceLayouts.Length; i++) { dsls[i] = Util.AssertSubtype <ResourceLayout, VkResourceLayout>(resourceLayouts[i]).DescriptorSetLayout; } pipelineLayoutCI.pSetLayouts = dsls; vkCreatePipelineLayout(_gd.Device, ref pipelineLayoutCI, null, out _pipelineLayout); pipelineCI.layout = _pipelineLayout; // Create fake RenderPass for compatibility. VkRenderPassCreateInfo renderPassCI = VkRenderPassCreateInfo.New(); OutputDescription outputDesc = description.Outputs; StackList <VkAttachmentDescription, Size512Bytes> attachments = new StackList <VkAttachmentDescription, Size512Bytes>(); // TODO: A huge portion of this next part is duplicated in VkFramebuffer.cs. StackList <VkAttachmentDescription> colorAttachmentDescs = new StackList <VkAttachmentDescription>(); StackList <VkAttachmentReference> colorAttachmentRefs = new StackList <VkAttachmentReference>(); for (uint i = 0; i < outputDesc.ColorAttachments.Length; i++) { colorAttachmentDescs[i].format = VkFormats.VdToVkPixelFormat(outputDesc.ColorAttachments[i].Format); colorAttachmentDescs[i].samples = vkSampleCount; colorAttachmentDescs[i].loadOp = VkAttachmentLoadOp.DontCare; colorAttachmentDescs[i].storeOp = VkAttachmentStoreOp.Store; colorAttachmentDescs[i].stencilLoadOp = VkAttachmentLoadOp.DontCare; colorAttachmentDescs[i].stencilStoreOp = VkAttachmentStoreOp.DontCare; colorAttachmentDescs[i].initialLayout = VkImageLayout.Undefined; colorAttachmentDescs[i].finalLayout = VkImageLayout.ShaderReadOnlyOptimal; attachments.Add(colorAttachmentDescs[i]); colorAttachmentRefs[i].attachment = i; colorAttachmentRefs[i].layout = VkImageLayout.ColorAttachmentOptimal; } VkAttachmentDescription depthAttachmentDesc = new VkAttachmentDescription(); VkAttachmentReference depthAttachmentRef = new VkAttachmentReference(); if (outputDesc.DepthAttachment != null) { PixelFormat depthFormat = outputDesc.DepthAttachment.Value.Format; bool hasStencil = FormatHelpers.IsStencilFormat(depthFormat); depthAttachmentDesc.format = VkFormats.VdToVkPixelFormat(outputDesc.DepthAttachment.Value.Format, toDepthFormat: true); depthAttachmentDesc.samples = vkSampleCount; depthAttachmentDesc.loadOp = VkAttachmentLoadOp.DontCare; depthAttachmentDesc.storeOp = VkAttachmentStoreOp.Store; depthAttachmentDesc.stencilLoadOp = VkAttachmentLoadOp.DontCare; depthAttachmentDesc.stencilStoreOp = hasStencil ? VkAttachmentStoreOp.Store : VkAttachmentStoreOp.DontCare; depthAttachmentDesc.initialLayout = VkImageLayout.Undefined; depthAttachmentDesc.finalLayout = VkImageLayout.DepthStencilAttachmentOptimal; depthAttachmentRef.attachment = (uint)outputDesc.ColorAttachments.Length; depthAttachmentRef.layout = VkImageLayout.DepthStencilAttachmentOptimal; } VkSubpassDescription subpass = new VkSubpassDescription(); subpass.pipelineBindPoint = VkPipelineBindPoint.Graphics; subpass.colorAttachmentCount = (uint)outputDesc.ColorAttachments.Length; subpass.pColorAttachments = (VkAttachmentReference *)colorAttachmentRefs.Data; for (int i = 0; i < colorAttachmentDescs.Count; i++) { attachments.Add(colorAttachmentDescs[i]); } if (outputDesc.DepthAttachment != null) { subpass.pDepthStencilAttachment = &depthAttachmentRef; attachments.Add(depthAttachmentDesc); } VkSubpassDependency subpassDependency = new VkSubpassDependency(); subpassDependency.srcSubpass = SubpassExternal; subpassDependency.srcStageMask = VkPipelineStageFlags.ColorAttachmentOutput; subpassDependency.dstStageMask = VkPipelineStageFlags.ColorAttachmentOutput; subpassDependency.dstAccessMask = VkAccessFlags.ColorAttachmentRead | VkAccessFlags.ColorAttachmentWrite; renderPassCI.attachmentCount = attachments.Count; renderPassCI.pAttachments = (VkAttachmentDescription *)attachments.Data; renderPassCI.subpassCount = 1; renderPassCI.pSubpasses = &subpass; renderPassCI.dependencyCount = 1; renderPassCI.pDependencies = &subpassDependency; VkResult creationResult = vkCreateRenderPass(_gd.Device, ref renderPassCI, null, out _renderPass); CheckResult(creationResult); pipelineCI.renderPass = _renderPass; VkResult result = vkCreateGraphicsPipelines(_gd.Device, VkPipelineCache.Null, 1, ref pipelineCI, null, out _devicePipeline); CheckResult(result); ResourceSetCount = (uint)description.ResourceLayouts.Length; DynamicOffsetsCount = 0; foreach (VkResourceLayout layout in description.ResourceLayouts) { DynamicOffsetsCount += layout.DynamicBufferCount; } }
public void ComputeShader3dTexture() { // Just a dumb compute shader that fills a 3D texture with the same value from a uniform multiplied by the depth. string shaderText = @" #version 450 layout(set = 0, binding = 0, rgba32f) uniform image3D TextureToFill; layout(set = 0, binding = 1) uniform FillValueBuffer { float FillValue; float Padding1; float Padding2; float Padding3; }; layout(local_size_x = 16, local_size_y = 16, local_size_z = 1) in; void main() { ivec3 textureCoordinate = ivec3(gl_GlobalInvocationID.xyz); float dataToStore = FillValue * (textureCoordinate.z + 1); imageStore(TextureToFill, textureCoordinate, vec4(dataToStore)); } "; const float FillValue = 42.42f; const uint OutputTextureSize = 32; using Shader computeShader = RF.CreateFromSpirv(new ShaderDescription( ShaderStages.Compute, Encoding.ASCII.GetBytes(shaderText), "main")); using ResourceLayout computeLayout = RF.CreateResourceLayout(new ResourceLayoutDescription( new ResourceLayoutElementDescription("TextureToFill", ResourceKind.TextureReadWrite, ShaderStages.Compute), new ResourceLayoutElementDescription("FillValueBuffer", ResourceKind.UniformBuffer, ShaderStages.Compute))); using Pipeline computePipeline = RF.CreateComputePipeline(new ComputePipelineDescription( computeShader, computeLayout, 16, 16, 1)); using DeviceBuffer fillValueBuffer = RF.CreateBuffer(new BufferDescription((uint)Marshal.SizeOf <FillValueStruct>(), BufferUsage.UniformBuffer)); // Create our output texture. using Texture computeTargetTexture = RF.CreateTexture(TextureDescription.Texture3D( OutputTextureSize, OutputTextureSize, OutputTextureSize, 1, PixelFormat.R32_G32_B32_A32_Float, TextureUsage.Sampled | TextureUsage.Storage)); using TextureView computeTargetTextureView = RF.CreateTextureView(computeTargetTexture); using ResourceSet computeResourceSet = RF.CreateResourceSet(new ResourceSetDescription( computeLayout, computeTargetTextureView, fillValueBuffer)); using CommandList cl = RF.CreateCommandList(); cl.Begin(); cl.UpdateBuffer(fillValueBuffer, 0, new FillValueStruct(FillValue)); // Use the compute shader to fill the texture. cl.SetPipeline(computePipeline); cl.SetComputeResourceSet(0, computeResourceSet); const uint GroupDivisorXY = 16; cl.Dispatch(OutputTextureSize / GroupDivisorXY, OutputTextureSize / GroupDivisorXY, OutputTextureSize); cl.End(); GD.SubmitCommands(cl); GD.WaitForIdle(); // Read back from our texture and make sure it has been properly filled. for (uint depth = 0; depth < computeTargetTexture.Depth; depth++) { RgbaFloat expectedFillValue = new RgbaFloat(new System.Numerics.Vector4(FillValue * (depth + 1))); int notFilledCount = CountTexelsNotFilledAtDepth(GD, computeTargetTexture, expectedFillValue, depth); Assert.Equal(0, notFilledCount); } }