Protogame.DefaultRenderBatcher.FlushRequests C# (CSharp) Méthode

FlushRequests() public méthode

public FlushRequests ( IGameContext gameContext, IRenderContext renderContext ) : void
gameContext IGameContext
renderContext IRenderContext
Résultat void
        public void FlushRequests(IGameContext gameContext, IRenderContext renderContext)
        {
            LastBatchCount = 0;
            LastApplyCount = 0;
            LastBatchSaveCount = 0;

            if (renderContext.IsCurrentRenderPass<I3DBatchedRenderPass>())
            {
                using (_profiler.Measure("render-flush"))
                {
                    foreach (var kv in _requestLookup)
                    {
                        if (_requestInstances[kv.Key].Count == 0)
                        {
                            continue;
                        }

                        LastBatchCount++;
                        LastBatchSaveCount += (ulong)(_requestInstances[kv.Key].Count - 1);

                        var request = kv.Value;

                        int pc;
                        SetupForRequest(renderContext, request, out pc, false);
                        request.Effect.NativeEffect.Parameters["View"]?.SetValue(renderContext.View);
                        request.Effect.NativeEffect.Parameters["Projection"]?.SetValue(renderContext.Projection);

#if PLATFORM_WINDOWS
                        var allowInstancedCalls = false;
#else
                        var allowInstancedCalls = false;
#endif
                        
                        if (allowInstancedCalls &&
                            request.Effect.NativeEffect.Techniques[request.TechniqueName + "Batched"] != null)
                        {
#if PLATFORM_WINDOWS
                            if (_vertexBuffer == null ||
                                _requestInstances[kv.Key].Count > _vertexBufferLastInstanceCount)
                            {
                                _vertexBuffer?.Dispose();

                                _vertexBuffer = new VertexBuffer(
                                    renderContext.GraphicsDevice,
                                    _vertexDeclaration,
                                    _requestInstances[kv.Key].Count,
                                    BufferUsage.WriteOnly);
                                _vertexBufferLastInstanceCount = _requestInstances[kv.Key].Count;
                            }

                            var matrices = _requestInstances[kv.Key];
                            _vertexBuffer.SetData(matrices.ToArray(), 0, matrices.Count);
                            renderContext.GraphicsDevice.SetVertexBuffers(
                                new VertexBufferBinding(request.MeshVertexBuffer),
                                new VertexBufferBinding(_vertexBuffer, 0, 1));

                            foreach (var pass in request.Effect.NativeEffect.Techniques[request.TechniqueName + "Batched"].Passes)
                            {
                                pass.Apply();

                                renderContext.GraphicsDevice.DrawInstancedPrimitives(
                                    request.PrimitiveType,
                                    0,
                                    0,
                                    request.MeshVertexBuffer.VertexCount,
                                    0,
                                    pc,
                                    matrices.Count);
                            }
#endif
                        }
                        else
                        {
                            // If there's less than 5 instances, just push the draw calls to the GPU.
                            if (_requestInstances[kv.Key].Count <= 5 || !request.SupportsComputingInstancesToCustomBuffers)
                            {
                                renderContext.GraphicsDevice.SetVertexBuffer(request.MeshVertexBuffer);

                                foreach (var instance in _requestInstances[kv.Key])
                                {
                                    request.Effect.NativeEffect.Parameters["World"]?.SetValue(instance);

                                    foreach (var pass in request.Effect.NativeEffect.Techniques[request.TechniqueName].Passes)
                                    {
                                        pass.Apply();

                                        LastApplyCount++;

                                        renderContext.GraphicsDevice.DrawIndexedPrimitives(
                                            request.PrimitiveType,
                                            0,
                                            0,
                                            pc);
                                    }
                                }
                            }
                            else
                            {
                                var buffersNeedComputing = false;
                                var vertexBuffer = _renderAutoCache.AutoCache("renderbatcher-" + kv.Key, new object[]
                                {
                                    _requestInstances[kv.Key].Count,
                                    request.MeshVertexBuffer.VertexCount,
                                    request.MeshVertexBuffer.VertexDeclaration
                                }, gameContext, () =>
                                {
                                    buffersNeedComputing = true;
                                    return new VertexBuffer(
                                        renderContext.GraphicsDevice,
                                        request.MeshVertexBuffer.VertexDeclaration,
                                        _requestInstances[kv.Key].Count*request.MeshVertexBuffer.VertexCount,
                                        BufferUsage.WriteOnly);
                                });
                                var indexBuffer = _renderAutoCache.AutoCache("renderbatcher-" + kv.Key, new object[]
                                {
                                    _requestInstances[kv.Key].Count,
                                    request.MeshVertexBuffer.VertexCount,
                                }, gameContext, () =>
                                {
                                    buffersNeedComputing = true;
                                    return new IndexBuffer(
                                        renderContext.GraphicsDevice,
                                        IndexElementSize.ThirtyTwoBits,
                                        _requestInstances[kv.Key].Count*request.MeshIndexBuffer.IndexCount,
                                        BufferUsage.WriteOnly);
                                });

                                if (buffersNeedComputing)
                                {
                                    // Compute a pre-transformed vertex and index buffer for rendering.
                                    request.ComputeInstancesToCustomBuffers(
                                        _requestInstances[kv.Key],
                                        vertexBuffer,
                                        indexBuffer);
                                }

                                renderContext.GraphicsDevice.SetVertexBuffer(vertexBuffer);
                                renderContext.GraphicsDevice.Indices = indexBuffer;
                                request.Effect.NativeEffect.Parameters["World"]?.SetValue(Matrix.Identity);

                                foreach (
                                    var pass in
                                        request.Effect.NativeEffect.Techniques[request.TechniqueName].Passes
                                    )
                                {
                                    pass.Apply();

                                    renderContext.GraphicsDevice.DrawIndexedPrimitives(
                                        request.PrimitiveType,
                                        0,
                                        0,
                                        pc * _requestInstances[kv.Key].Count);
                                }
                            }
                        }

                        _requestInstances[kv.Key].Clear();
                    }

                    _requestLookup.Clear();
                    _requestInstances.Clear();
                }
            }
        }