2021-01-20 03:33:27 +00:00
|
|
|
using System;
|
|
|
|
using System.Runtime.InteropServices;
|
2021-02-10 06:51:30 +00:00
|
|
|
using MoonWorks.Math;
|
2021-01-20 03:33:27 +00:00
|
|
|
using RefreshCS;
|
|
|
|
|
|
|
|
namespace MoonWorks.Graphics
|
|
|
|
{
|
|
|
|
public class CommandBuffer
|
|
|
|
{
|
|
|
|
public GraphicsDevice Device { get; }
|
|
|
|
public IntPtr Handle { get; internal set; }
|
|
|
|
|
|
|
|
// called from RefreshDevice
|
|
|
|
internal CommandBuffer(GraphicsDevice device)
|
|
|
|
{
|
|
|
|
Device = device;
|
|
|
|
Handle = IntPtr.Zero;
|
|
|
|
}
|
|
|
|
|
2021-02-10 06:51:30 +00:00
|
|
|
public unsafe void BeginRenderPass(
|
|
|
|
RenderPass renderPass,
|
|
|
|
Framebuffer framebuffer,
|
|
|
|
in Rect renderArea,
|
|
|
|
in DepthStencilValue depthStencilClearValue
|
|
|
|
) {
|
|
|
|
Refresh.Refresh_BeginRenderPass(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
renderPass.Handle,
|
|
|
|
framebuffer.Handle,
|
|
|
|
renderArea.ToRefresh(),
|
|
|
|
IntPtr.Zero,
|
|
|
|
0,
|
|
|
|
depthStencilClearValue.ToRefresh()
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2021-01-20 03:33:27 +00:00
|
|
|
public unsafe void BeginRenderPass(
|
|
|
|
RenderPass renderPass,
|
|
|
|
Framebuffer framebuffer,
|
2021-01-22 01:27:25 +00:00
|
|
|
in Rect renderArea,
|
|
|
|
in DepthStencilValue depthStencilClearValue,
|
2021-02-10 06:51:30 +00:00
|
|
|
params Vector4[] clearColors
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
2021-02-10 06:51:30 +00:00
|
|
|
Refresh.Vec4* colors = stackalloc Refresh.Vec4[clearColors.Length];
|
|
|
|
|
|
|
|
for (var i = 0; i < clearColors.Length; i++)
|
2021-01-20 03:33:27 +00:00
|
|
|
{
|
2021-02-10 06:51:30 +00:00
|
|
|
colors[i] = new Refresh.Vec4
|
|
|
|
{
|
|
|
|
x = clearColors[i].X,
|
|
|
|
y = clearColors[i].Y,
|
|
|
|
z = clearColors[i].Z,
|
|
|
|
w = clearColors[i].W
|
|
|
|
};
|
2021-01-20 03:33:27 +00:00
|
|
|
}
|
2021-02-10 06:51:30 +00:00
|
|
|
|
|
|
|
Refresh.Refresh_BeginRenderPass(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
renderPass.Handle,
|
|
|
|
framebuffer.Handle,
|
|
|
|
renderArea.ToRefresh(),
|
|
|
|
(IntPtr) colors,
|
|
|
|
(uint)clearColors.Length,
|
|
|
|
depthStencilClearValue.ToRefresh()
|
|
|
|
);
|
|
|
|
|
2021-01-20 03:33:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
public unsafe void BeginRenderPass(
|
|
|
|
RenderPass renderPass,
|
|
|
|
Framebuffer framebuffer,
|
2021-01-22 01:27:25 +00:00
|
|
|
in Rect renderArea,
|
2021-02-11 01:15:46 +00:00
|
|
|
params Vector4[] clearColors
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
2021-02-11 01:15:46 +00:00
|
|
|
Refresh.Vec4* colors = stackalloc Refresh.Vec4[clearColors.Length];
|
|
|
|
|
|
|
|
for (var i = 0; i < clearColors.Length; i++)
|
2021-01-20 03:33:27 +00:00
|
|
|
{
|
2021-02-11 01:15:46 +00:00
|
|
|
colors[i] = new Refresh.Vec4
|
|
|
|
{
|
|
|
|
x = clearColors[i].X,
|
|
|
|
y = clearColors[i].Y,
|
|
|
|
z = clearColors[i].Z,
|
|
|
|
w = clearColors[i].W
|
|
|
|
};
|
2021-01-20 03:33:27 +00:00
|
|
|
}
|
2021-02-11 01:15:46 +00:00
|
|
|
|
|
|
|
Refresh.Refresh_BeginRenderPass(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
renderPass.Handle,
|
|
|
|
framebuffer.Handle,
|
|
|
|
renderArea.ToRefresh(),
|
|
|
|
(IntPtr) colors,
|
|
|
|
(uint) clearColors.Length,
|
|
|
|
IntPtr.Zero
|
|
|
|
);
|
2021-01-20 03:33:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
public void BindComputePipeline(
|
|
|
|
ComputePipeline computePipeline
|
|
|
|
) {
|
|
|
|
Refresh.Refresh_BindComputePipeline(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
computePipeline.Handle
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public unsafe void BindComputeBuffers(
|
|
|
|
params Buffer[] buffers
|
|
|
|
) {
|
|
|
|
var bufferPtrs = stackalloc IntPtr[buffers.Length];
|
|
|
|
|
|
|
|
for (var i = 0; i < buffers.Length; i += 1)
|
|
|
|
{
|
|
|
|
bufferPtrs[i] = buffers[i].Handle;
|
|
|
|
}
|
|
|
|
|
|
|
|
Refresh.Refresh_BindComputeBuffers(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
(IntPtr) bufferPtrs
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public unsafe void BindComputeTextures(
|
|
|
|
params Texture[] textures
|
|
|
|
) {
|
|
|
|
var texturePtrs = stackalloc IntPtr[textures.Length];
|
|
|
|
|
|
|
|
for (var i = 0; i < textures.Length; i += 1)
|
|
|
|
{
|
|
|
|
texturePtrs[i] = textures[i].Handle;
|
|
|
|
}
|
|
|
|
|
|
|
|
Refresh.Refresh_BindComputeTextures(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
(IntPtr) texturePtrs
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void BindGraphicsPipeline(
|
|
|
|
GraphicsPipeline graphicsPipeline
|
|
|
|
) {
|
|
|
|
Refresh.Refresh_BindGraphicsPipeline(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
graphicsPipeline.Handle
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public unsafe void BindVertexBuffers(
|
|
|
|
uint firstBinding,
|
|
|
|
params BufferBinding[] bufferBindings
|
|
|
|
) {
|
|
|
|
var bufferPtrs = stackalloc IntPtr[bufferBindings.Length];
|
|
|
|
var offsets = stackalloc ulong[bufferBindings.Length];
|
|
|
|
|
|
|
|
for (var i = 0; i < bufferBindings.Length; i += 1)
|
|
|
|
{
|
|
|
|
bufferPtrs[i] = bufferBindings[i].Buffer.Handle;
|
|
|
|
offsets[i] = bufferBindings[i].Offset;
|
|
|
|
}
|
|
|
|
|
|
|
|
Refresh.Refresh_BindVertexBuffers(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
firstBinding,
|
|
|
|
(uint) bufferBindings.Length,
|
|
|
|
(IntPtr) bufferPtrs,
|
|
|
|
(IntPtr) offsets
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2021-01-22 21:54:49 +00:00
|
|
|
public unsafe void BindVertexBuffers(
|
|
|
|
params Buffer[] buffers
|
|
|
|
) {
|
|
|
|
var bufferPtrs = stackalloc IntPtr[buffers.Length];
|
|
|
|
var offsets = stackalloc ulong[buffers.Length];
|
|
|
|
|
|
|
|
for (var i = 0; i < buffers.Length; i += 1)
|
|
|
|
{
|
|
|
|
bufferPtrs[i] = buffers[i].Handle;
|
|
|
|
offsets[i] = 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
Refresh.Refresh_BindVertexBuffers(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
0,
|
|
|
|
(uint) buffers.Length,
|
|
|
|
(IntPtr) bufferPtrs,
|
|
|
|
(IntPtr) offsets
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2021-01-20 03:33:27 +00:00
|
|
|
public void BindIndexBuffer(
|
|
|
|
Buffer indexBuffer,
|
2021-01-22 21:56:24 +00:00
|
|
|
IndexElementSize indexElementSize,
|
|
|
|
uint offset = 0
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
|
|
|
Refresh.Refresh_BindIndexBuffer(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
indexBuffer.Handle,
|
|
|
|
offset,
|
2021-01-22 03:55:09 +00:00
|
|
|
(Refresh.IndexElementSize) indexElementSize
|
2021-01-20 03:33:27 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public unsafe void BindVertexSamplers(
|
2021-02-11 20:25:12 +00:00
|
|
|
TextureSamplerBinding[] textureSamplerBindings,
|
|
|
|
int length
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
2021-01-22 21:57:49 +00:00
|
|
|
var texturePtrs = stackalloc IntPtr[textureSamplerBindings.Length];
|
|
|
|
var samplerPtrs = stackalloc IntPtr[textureSamplerBindings.Length];
|
2021-01-20 03:33:27 +00:00
|
|
|
|
2021-02-11 20:25:12 +00:00
|
|
|
for (var i = 0; i < length; i += 1)
|
2021-01-20 03:33:27 +00:00
|
|
|
{
|
2021-01-22 21:57:49 +00:00
|
|
|
texturePtrs[i] = textureSamplerBindings[i].Texture.Handle;
|
|
|
|
samplerPtrs[i] = textureSamplerBindings[i].Sampler.Handle;
|
2021-01-20 03:33:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
Refresh.Refresh_BindVertexSamplers(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
(IntPtr) texturePtrs,
|
|
|
|
(IntPtr) samplerPtrs
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2021-02-11 20:25:12 +00:00
|
|
|
public unsafe void BindVertexSamplers(
|
2021-01-20 03:33:27 +00:00
|
|
|
params TextureSamplerBinding[] textureSamplerBindings
|
2021-02-11 20:25:12 +00:00
|
|
|
) {
|
|
|
|
BindVertexSamplers(textureSamplerBindings, textureSamplerBindings.Length);
|
|
|
|
}
|
|
|
|
|
|
|
|
public unsafe void BindFragmentSamplers(
|
|
|
|
TextureSamplerBinding[] textureSamplerBindings,
|
|
|
|
int length
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
|
|
|
var texturePtrs = stackalloc IntPtr[textureSamplerBindings.Length];
|
|
|
|
var samplerPtrs = stackalloc IntPtr[textureSamplerBindings.Length];
|
|
|
|
|
2021-02-11 20:25:12 +00:00
|
|
|
for (var i = 0; i < length; i += 1)
|
2021-01-20 03:33:27 +00:00
|
|
|
{
|
|
|
|
texturePtrs[i] = textureSamplerBindings[i].Texture.Handle;
|
|
|
|
samplerPtrs[i] = textureSamplerBindings[i].Sampler.Handle;
|
|
|
|
}
|
|
|
|
|
|
|
|
Refresh.Refresh_BindFragmentSamplers(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
(IntPtr) texturePtrs,
|
|
|
|
(IntPtr) samplerPtrs
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2021-02-11 20:25:12 +00:00
|
|
|
public unsafe void BindFragmentSamplers(
|
|
|
|
params TextureSamplerBinding[] textureSamplerBindings
|
|
|
|
) {
|
|
|
|
BindFragmentSamplers(textureSamplerBindings, textureSamplerBindings.Length);
|
|
|
|
}
|
|
|
|
|
2021-01-22 22:16:38 +00:00
|
|
|
public unsafe void Clear(
|
|
|
|
in Rect clearRect,
|
2021-02-09 03:22:27 +00:00
|
|
|
ClearOptionsFlags clearOptions,
|
2021-01-22 22:16:38 +00:00
|
|
|
in DepthStencilValue depthStencilClearValue,
|
2021-02-10 06:51:30 +00:00
|
|
|
params Vector4[] clearColors
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
2021-02-10 06:51:30 +00:00
|
|
|
Refresh.Vec4* colors = stackalloc Refresh.Vec4[clearColors.Length];
|
|
|
|
for (var i = 0; i < clearColors.Length; i++)
|
|
|
|
{
|
|
|
|
colors[i] = new Refresh.Vec4
|
|
|
|
{
|
|
|
|
x = clearColors[i].X,
|
|
|
|
y = clearColors[i].Y,
|
|
|
|
z = clearColors[i].Z,
|
|
|
|
w = clearColors[i].W
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
2021-01-20 03:33:27 +00:00
|
|
|
Refresh.Refresh_Clear(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 22:16:38 +00:00
|
|
|
clearRect.ToRefresh(),
|
2021-02-09 03:22:27 +00:00
|
|
|
(Refresh.ClearOptionsFlags)clearOptions,
|
2021-01-22 22:16:38 +00:00
|
|
|
(IntPtr) colors,
|
|
|
|
(uint) clearColors.Length,
|
|
|
|
depthStencilClearValue.ToRefresh()
|
2021-01-20 03:33:27 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void DrawInstancedPrimitives(
|
|
|
|
uint baseVertex,
|
|
|
|
uint startIndex,
|
|
|
|
uint primitiveCount,
|
|
|
|
uint instanceCount,
|
|
|
|
uint vertexParamOffset,
|
|
|
|
uint fragmentParamOffset
|
|
|
|
) {
|
|
|
|
Refresh.Refresh_DrawInstancedPrimitives(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
baseVertex,
|
|
|
|
startIndex,
|
|
|
|
primitiveCount,
|
|
|
|
instanceCount,
|
|
|
|
vertexParamOffset,
|
|
|
|
fragmentParamOffset
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void DrawIndexedPrimitives(
|
|
|
|
uint baseVertex,
|
|
|
|
uint startIndex,
|
|
|
|
uint primitiveCount,
|
|
|
|
uint vertexParamOffset,
|
|
|
|
uint fragmentParamOffset
|
|
|
|
) {
|
|
|
|
Refresh.Refresh_DrawIndexedPrimitives(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
baseVertex,
|
|
|
|
startIndex,
|
|
|
|
primitiveCount,
|
|
|
|
vertexParamOffset,
|
|
|
|
fragmentParamOffset
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void DrawPrimitives(
|
|
|
|
uint vertexStart,
|
|
|
|
uint primitiveCount,
|
|
|
|
uint vertexParamOffset,
|
|
|
|
uint fragmentParamOffset
|
|
|
|
) {
|
|
|
|
Refresh.Refresh_DrawPrimitives(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
|
|
|
vertexStart,
|
|
|
|
primitiveCount,
|
|
|
|
vertexParamOffset,
|
|
|
|
fragmentParamOffset
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void EndRenderPass()
|
|
|
|
{
|
|
|
|
Refresh.Refresh_EndRenderPass(
|
|
|
|
Device.Handle,
|
|
|
|
Handle
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void QueuePresent(
|
2021-01-21 22:05:10 +00:00
|
|
|
in Texture texture,
|
|
|
|
in Rect destinationRectangle,
|
|
|
|
Filter filter
|
|
|
|
)
|
|
|
|
{
|
|
|
|
var refreshRect = destinationRectangle.ToRefresh();
|
|
|
|
var refreshTextureSlice = new Refresh.TextureSlice
|
|
|
|
{
|
|
|
|
texture = texture.Handle,
|
|
|
|
rectangle = new Refresh.Rect
|
|
|
|
{
|
|
|
|
x = 0,
|
|
|
|
y = 0,
|
|
|
|
w = (int)texture.Width,
|
|
|
|
h = (int)texture.Height
|
|
|
|
},
|
|
|
|
layer = 0,
|
|
|
|
level = 0,
|
|
|
|
depth = 0
|
|
|
|
};
|
|
|
|
|
|
|
|
Refresh.Refresh_QueuePresent(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 01:27:25 +00:00
|
|
|
refreshTextureSlice,
|
|
|
|
refreshRect,
|
2021-01-21 22:05:10 +00:00
|
|
|
(Refresh.Filter)filter
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void QueuePresent(
|
|
|
|
in TextureSlice textureSlice,
|
|
|
|
in Rect destinationRectangle,
|
2021-01-20 21:32:48 +00:00
|
|
|
Filter filter
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
|
|
|
var refreshTextureSlice = textureSlice.ToRefreshTextureSlice();
|
2021-01-20 21:32:48 +00:00
|
|
|
var refreshRect = destinationRectangle.ToRefresh();
|
2021-01-20 03:33:27 +00:00
|
|
|
|
|
|
|
Refresh.Refresh_QueuePresent(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 01:27:25 +00:00
|
|
|
refreshTextureSlice,
|
|
|
|
refreshRect,
|
2021-01-20 21:32:48 +00:00
|
|
|
(Refresh.Filter) filter
|
2021-01-20 03:33:27 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void QueuePresent(
|
2021-01-21 22:05:10 +00:00
|
|
|
in TextureSlice textureSlice,
|
2021-01-20 21:32:48 +00:00
|
|
|
Filter filter
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
|
|
|
Refresh.Refresh_QueuePresent(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 01:27:25 +00:00
|
|
|
textureSlice.ToRefreshTextureSlice(),
|
2021-01-20 03:33:27 +00:00
|
|
|
IntPtr.Zero,
|
2021-01-20 21:32:48 +00:00
|
|
|
(Refresh.Filter) filter
|
2021-01-20 03:33:27 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void QueuePresent(
|
|
|
|
Texture texture,
|
2021-01-20 21:32:48 +00:00
|
|
|
Filter filter
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
|
|
|
var refreshTextureSlice = new Refresh.TextureSlice
|
|
|
|
{
|
|
|
|
texture = texture.Handle,
|
|
|
|
rectangle = new Refresh.Rect
|
|
|
|
{
|
|
|
|
x = 0,
|
|
|
|
y = 0,
|
|
|
|
w = (int) texture.Width,
|
|
|
|
h = (int) texture.Height
|
|
|
|
},
|
|
|
|
layer = 0,
|
|
|
|
level = 0,
|
|
|
|
depth = 0
|
|
|
|
};
|
|
|
|
|
|
|
|
Refresh.Refresh_QueuePresent(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 01:27:25 +00:00
|
|
|
refreshTextureSlice,
|
2021-01-20 03:33:27 +00:00
|
|
|
IntPtr.Zero,
|
2021-01-20 21:32:48 +00:00
|
|
|
(Refresh.Filter) filter
|
2021-01-20 03:33:27 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void CopyTextureToTexture(
|
2021-01-21 22:05:10 +00:00
|
|
|
in TextureSlice sourceTextureSlice,
|
|
|
|
in TextureSlice destinationTextureSlice,
|
2021-01-20 21:32:48 +00:00
|
|
|
Filter filter
|
2021-01-20 03:33:27 +00:00
|
|
|
) {
|
|
|
|
var sourceRefreshTextureSlice = sourceTextureSlice.ToRefreshTextureSlice();
|
|
|
|
var destRefreshTextureSlice = destinationTextureSlice.ToRefreshTextureSlice();
|
|
|
|
|
|
|
|
Refresh.Refresh_CopyTextureToTexture(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 01:27:25 +00:00
|
|
|
sourceRefreshTextureSlice,
|
|
|
|
destRefreshTextureSlice,
|
2021-01-20 21:32:48 +00:00
|
|
|
(Refresh.Filter) filter
|
2021-01-20 03:33:27 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void CopyTextureToBuffer(
|
2021-01-21 22:05:10 +00:00
|
|
|
in TextureSlice textureSlice,
|
2021-01-20 03:33:27 +00:00
|
|
|
Buffer buffer
|
|
|
|
) {
|
|
|
|
var refreshTextureSlice = textureSlice.ToRefreshTextureSlice();
|
|
|
|
|
|
|
|
Refresh.Refresh_CopyTextureToBuffer(
|
|
|
|
Device.Handle,
|
|
|
|
Handle,
|
2021-01-22 01:27:25 +00:00
|
|
|
refreshTextureSlice,
|
2021-01-20 03:33:27 +00:00
|
|
|
buffer.Handle
|
|
|
|
);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|