private static void EncodeJobConstants(int index, ref MyDecalConstants constants) { Matrix worldMatrix = Matrix.Transpose(m_jobs[index].WorldMatrix); Matrix inverseMatrix = Matrix.Transpose(Matrix.Invert(m_jobs[index].WorldMatrix)); constants.WorldMatrix = worldMatrix; constants.FadeAlpha = m_jobs[index].FadeAlpha; constants.__padding = new Vector3(0, 0, 1); constants.InvWorldMatrix = inverseMatrix; }
unsafe static void DrawBatches(MyRenderContext rc, MyStringId material, int matIndex, bool transparent) { if (m_jobs.Count == 0) { return; } var matDesc = m_materials[material][matIndex]; rc.PixelShader.SetSrv(0, MyGBuffer.Main.DepthStencil.SrvDepth); rc.PixelShader.SetSrv(1, MyGlobalResources.Gbuffer1Copy); if (transparent) { rc.PixelShader.Set(m_psColorMapTransparent); } else { rc.SetRtvs(MyGBuffer.Main, MyDepthStencilAccess.ReadOnly); MyFileTextureEnum type = matDesc.DecalType; switch (type) { case MyFileTextureEnum.NORMALMAP_GLOSS: rc.PixelShader.Set(m_psNormalMap); break; case MyFileTextureEnum.COLOR_METAL: rc.PixelShader.Set(m_psColorMap); break; case MyFileTextureEnum.COLOR_METAL | MyFileTextureEnum.NORMALMAP_GLOSS: rc.PixelShader.Set(m_psNormalColorMap); break; case MyFileTextureEnum.COLOR_METAL | MyFileTextureEnum.NORMALMAP_GLOSS | MyFileTextureEnum.EXTENSIONS: rc.PixelShader.Set(m_psNormalColorExtMap); break; default: throw new Exception("Unknown decal type"); } MyMeshMaterials1.BindMaterialTextureBlendStates(rc, type); } // factor 1 makes overwriting of gbuffer color & subtracting from ao MyFileTextureManager texManager = MyManagers.FileTextures; rc.PixelShader.SetSrv(3, texManager.GetTexture(matDesc.AlphamaskTexture, MyFileTextureEnum.ALPHAMASK)); rc.PixelShader.SetSrv(4, texManager.GetTexture(matDesc.ColorMetalTexture, MyFileTextureEnum.COLOR_METAL)); rc.PixelShader.SetSrv(5, texManager.GetTexture(matDesc.NormalmapTexture, MyFileTextureEnum.NORMALMAP_GLOSS)); rc.PixelShader.SetSrv(6, texManager.GetTexture(matDesc.ExtensionsTexture, MyFileTextureEnum.EXTENSIONS)); var decalCb = MyCommon.GetObjectCB(sizeof(MyDecalConstants) * DECAL_BATCH_SIZE); int batchCount = m_jobs.Count / DECAL_BATCH_SIZE + 1; int offset = 0; for (int i1 = 0; i1 < batchCount; i1++) { var mapping = MyMapping.MapDiscard(decalCb); int leftDecals = m_jobs.Count - offset; int decalCount = leftDecals > DECAL_BATCH_SIZE ? DECAL_BATCH_SIZE : leftDecals; for (int i2 = 0; i2 < decalCount; ++i2) { MyDecalConstants constants = new MyDecalConstants(); EncodeJobConstants(i2 + offset, ref constants); mapping.WriteAndPosition(ref constants); } mapping.Unmap(); // Draw a box without buffer: 36 vertices -> 12 triangles. 2 triangles per face -> 6 faces MyImmediateRC.RC.DrawIndexed(36 * decalCount, 0, 0); offset += DECAL_BATCH_SIZE; } }
unsafe static void DrawBatches(MyRenderContext RC, MyStringId material, int matIndex, bool transparent) { if (m_jobs.Count == 0) { return; } var matDesc = m_materials[material][matIndex]; MyScreenDecalType type = matDesc.DecalType; if (transparent) { // Always fallback to colormap for transparent surface decals type = MyScreenDecalType.ColorMap; } switch (type) { case MyScreenDecalType.NormalMap: BindResources(RC); RC.SetPS(m_psNormalMap); RC.SetBS(MyRender11.BlendDecalNormal); break; case MyScreenDecalType.ColorMap: if (transparent) { BindResourcesTransparentBillboards(RC); RC.SetPS(m_psColorMapTransparent); } else { BindResources(RC); RC.SetPS(m_psColorMap); RC.SetBS(MyRender11.BlendDecalColor); } break; case MyScreenDecalType.NormalColorMap: BindResources(RC); RC.SetPS(m_psNormalColorMap); RC.SetBS(MyRender11.BlendDecalNormalColor); break; case MyScreenDecalType.NormalColorExtMap: BindResources(RC); RC.SetPS(m_psNormalColorExtMap); RC.SetBS(MyRender11.BlendDecalNormalColorExt); break; default: throw new Exception("Unknown decal type"); } // factor 1 makes overwriting of gbuffer color & subtracting from ao RC.DeviceContext.PixelShader.SetShaderResource(3, MyTextures.GetView(matDesc.AlphamaskTexture)); RC.DeviceContext.PixelShader.SetShaderResource(4, MyTextures.GetView(matDesc.ColorMetalTexture)); RC.DeviceContext.PixelShader.SetShaderResource(5, MyTextures.GetView(matDesc.NormalmapTexture)); RC.DeviceContext.PixelShader.SetShaderResource(6, MyTextures.GetView(matDesc.ExtensionsTexture)); var decalCb = MyCommon.GetObjectCB(sizeof(MyDecalConstants) * DECAL_BATCH_SIZE); int batchCount = m_jobs.Count / DECAL_BATCH_SIZE + 1; int offset = 0; for (int i1 = 0; i1 < batchCount; i1++) { var mapping = MyMapping.MapDiscard(decalCb); int leftDecals = m_jobs.Count - offset; int decalCount = leftDecals > DECAL_BATCH_SIZE ? DECAL_BATCH_SIZE : leftDecals; for (int i2 = 0; i2 < decalCount; ++i2) { MyDecalConstants constants = new MyDecalConstants(); EncodeJobConstants(i2, ref constants); mapping.WriteAndPosition(ref constants); } mapping.Unmap(); // Draw a box without buffer: 36 vertices -> 12 triangles. 2 triangles per face -> 6 faces MyImmediateRC.RC.DeviceContext.DrawIndexed(36 * decalCount, 0, 0); offset += DECAL_BATCH_SIZE; } }