starting graphics resources
continuous-integration/drone/push Build is passing Details

main
cosmonaut 2021-01-25 14:59:27 -08:00
parent d0c79b0846
commit a0705c5037
5 changed files with 69 additions and 1 deletions

View File

@ -1,6 +1,7 @@
--- ---
title: "Graphics Device" title: "Graphics Device"
date: 2021-01-24T20:52:59-08:00 date: 2021-01-24T20:52:59-08:00
weight: 2
--- ---
`GraphicsDevice` is your main entry point for graphics-related behavior. You can obtain a reference to the current `GraphicsDevice` from your `Game` class. `GraphicsDevice` is your main entry point for graphics-related behavior. You can obtain a reference to the current `GraphicsDevice` from your `Game` class.

View File

@ -1,6 +1,7 @@
--- ---
title: "Intro" title: "Intro"
date: 2021-01-24T20:54:00-08:00 date: 2021-01-24T20:54:00-08:00
weight: 1
--- ---
If the other MoonWorks tools have seemed simple so far, MoonWorks.Graphics may surprise you. Graphics is implemented using the [Refresh](https://gitea.moonside.games/MoonsideGames/Refresh) library. Refresh is based on Vulkan, an industry-standard cross-platform graphics API. It provides no "standard" rendering system that you can easily hook into, unlike what you may be used to with an engine like Unity. In order to render to the screen, you will need to set up, at the minimum, a Color Target, Framebuffer, a Render Pass, some Shader Modules, a Graphics Pipeline, and provide vertex data to be rendered through the pipeline. If the other MoonWorks tools have seemed simple so far, MoonWorks.Graphics may surprise you. Graphics is implemented using the [Refresh](https://gitea.moonside.games/MoonsideGames/Refresh) library. Refresh is based on Vulkan, an industry-standard cross-platform graphics API. It provides no "standard" rendering system that you can easily hook into, unlike what you may be used to with an engine like Unity. In order to render to the screen, you will need to set up, at the minimum, a Color Target, Framebuffer, a Render Pass, some Shader Modules, a Graphics Pipeline, and provide vertex data to be rendered through the pipeline.

View File

@ -0,0 +1,41 @@
---
title: "Buffer"
date: 2021-01-25T14:41:43-08:00
---
Buffers are basically containers for data. They are the bread and butter of any renderer.
3D models are represented as a series of vertices. Vertices always have a 3D position, but they can also contain additional information, such as normal vectors or texture coordinates. Buffers are how you let the renderer use this data.
Buffers have a pre-defined length and cannot be resized.
You also need to tell MoonWorks.Graphics how you intend to use the buffer.
To create a buffer, you do this:
```cs
var myIndexBuffer = new Buffer(GraphicsDevice, BufferUsageFlags.Index, 64);
```
This creates a 64-byte buffer intended for use as an [index buffer](https://vulkan-tutorial.com/Vertex_buffers/Index_buffer). Index buffers allow the renderer to reuse vertices when drawing in 3D so you don't need to put a bunch of redundant data in your vertex buffer. Every 3D model format and exporter will give you index data along with vertex data.
To upload data to a buffer, you use the `SetData` method.
```cs
var myVertices = new VertexPositionNormalTexture[128];
var vertexSizeInBytes = Marshal.SizeOf<VertexPositionNormalTexture>();
// set vertex data here
var myVertexBuffer = new Buffer(GraphicsDevice, BufferUsageFlags.Vertex, 128 * vertexSizeInBytes);
myVertexBuffer.SetData(myVertices);
```
To get data from a buffer, you use the `GetData` method.
```cs
var pixelSizeInBytes = Marshal.SizeOf<Color>();
var myPixelData = new Color[width * height];
myPixelBuffer.GetData(myPixelData, width * height * pixelSizeInBytes);
```
There are some important things to note here. The buffer is not guaranteed to actually contain your data until `Submit` is called. Transferring memory to and from the GPU is expensive, so MoonWorks batches these operations aggressively. It *is* safe to assume that any command buffer commands you use after calling `SetData` will have access to the data, but it is *not* safe to assume that the buffer will contain the data you expect right after calling `SetData`. You need to call `GraphicsDevice.Submit` and then `GraphicsDevice.Wait` before the data is guaranteed to exist in the buffer. You should have a *very* good reason for doing this - this kind of behavior is called a "synchronization point" and it is extremely detrimental to performance.

View File

@ -0,0 +1,25 @@
---
title: "Resources"
date: 2021-01-25T14:31:59-08:00
weight: 3
---
MoonWorks provides nine different kinds of graphics resources that you use to construct your renderer.
`Buffer` holds generic data, like vertex information for example. The way this data is interpreted is determined by the pipeline.
`Texture` holds image data in a specified format.
`Sampler` tells a shader how it should sample texture data.
`ComputePipeline` sets up the graphics device to do computational work using [compute shaders](https://anteru.net/blog/2018/intro-to-compute-shaders/index.html).
`GraphicsPipeline` sets up the graphics device to do rendering work.
`RenderTarget` is a structure that can be rendered to.
`Framebuffer` is essentially a collection of `RenderTarget`s.
`RenderPass` is essentially a link that tells the `GraphicsPipeline` how it should use a `Framebuffer`.
This is all pretty abstract. Let's get into some more detail.

View File

@ -4,7 +4,7 @@ date: 2021-01-24T20:43:17-08:00
weight: 1 weight: 1
--- ---
Window management in MoonWorks is implemented using the [SDL2](https://www.libsdl.org) library. All window management is handled through the `Window` class. A reference to this class is automatically created and can be retrieved from your `Game` subclass. Window management in MoonWorks is implemented using the [SDL2](https://www.libsdl.org) library. All window management is handled through the `OSWindow` class. A reference to this class named `Window` is automatically created and can be retrieved from your `Game` subclass.
Your game is assumed to have a window and you must pass a `WindowCreateInfo` struct when creating your `Game`. Your game is assumed to have a window and you must pass a `WindowCreateInfo` struct when creating your `Game`.