| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
| Name | Name | Last commit date | ||
|---|---|---|---|---|
Elemental is a portable low-level game platform library that targets only next-gen features. It is exposed as a simple C header and other language bindings also exist.
It is a great choice if you want to:
Warning
The project is currently in heavy development. API may have a lot of breaking changes until the first release.
Elemental aims to simplify and standardize game development across different platforms by offering a unified API.
Back in the days of DirectX11 and OpenGL, it was very easy to start working on its own game or custom engine that took full advantage of the GPU. Newer apis give more control to the developpers but they are hard to use. They also provide many ways of doing things because they must maintain backward compatibility.
Elemental bridges this gap by focusing on powerful, next-gen features without the overhead of backward compatibility. This approach not only facilitates learning and using graphics programming as in earlier times but also gears developers up for future advancements without compromising on performance.
It doesn't mean that it will simplify or abstract graphics development. It is a challenging topic but developers can now focus on learning graphics programming like in the old days by focusing on graphics algorithms and not on the complicated platform specific implementation details.
The library is still in heavy development stage. The goal is not to be compatible with the majority of graphics cards now but to be ready for the future.
In order to simplify the API, the library makes the following assumptions:
Implemented features for current version 1.0.0-DEV4:
It currently runs on:
| Platform | Graphics API | Tools Supported |
|---|---|---|
| DirectX12, Vulkan | ✅ | |
| Vulkan/Wayland | ✅ | |
| Metal3 | ✅ | |
| Metal3 |
The library is exposed as a C library but other bindings will be available:
| Binding | Status | Download |
|---|---|---|
| WIP | Not available |
For shader development, the shader compiler supports the following languages and platforms:
| Shader Language | Target API | Compilation Platforms |
|---|---|---|
| HLSL | DirectX12 | |
| HLSL | Vulkan | |
| HLSL | Metal3 |
Here is a minimal application that displays a colored triangle using a mesh shader.
#include "Elemental.h"
#include "ElementalTools.h"
const char* shaderSource =
"struct Vertex { float3 Position; float4 Color; };"
"struct VertexOutput { float4 Position: SV_Position; float4 Color: TEXCOORD0; };"
"static Vertex triangleVertices[] ="
"{"
" { float3(-0.5, 0.5, 0.0), float4(1.0, 0.0, 0.0, 1.0) },"
" { float3(0.5, 0.5, 0.0), float4(0.0, 1.0, 0.0, 1.0) },"
" { float3(-0.5, -0.5, 0.0), float4(0.0, 0.0, 1.0, 1.0) }"
"};"
"[shader(\"mesh\")]"
"[OutputTopology(\"triangle\")]"
"[NumThreads(32, 1, 1)]"
"void MeshMain(in uint groupThreadId : SV_GroupThreadID, out vertices VertexOutput vertices[3], out indices uint3 indices[1])"
"{"
" const uint meshVertexCount = 3;"
" SetMeshOutputCounts(meshVertexCount, 1);"
" if (groupThreadId < meshVertexCount)"
" {"
" vertices[groupThreadId].Position = float4(triangleVertices[groupThreadId].Position, 1);"
" vertices[groupThreadId].Color = triangleVertices[groupThreadId].Color;"
" }"
" if (groupThreadId == 0)"
" {"
" indices[groupThreadId] = uint3(0, 1, 2);"
" }"
"}"
"[shader(\"pixel\")]"
"float4 PixelMain(const VertexOutput input) : SV_Target0"
"{"
" return input.Color;"
"}";
typedef struct
{
ElemWindow Window;
ElemGraphicsDevice GraphicsDevice;
ElemCommandQueue CommandQueue;
ElemSwapChain SwapChain;
ElemPipelineState GraphicsPipeline;
} ApplicationPayload;
void UpdateSwapChain(const ElemSwapChainUpdateParameters* updateParameters, void* payload);
void InitSample(void* payload)
{
ApplicationPayload* applicationPayload = (ApplicationPayload*)payload;
applicationPayload->Window = ElemCreateWindow(NULL);
applicationPayload->GraphicsDevice = ElemCreateGraphicsDevice(NULL);
applicationPayload->CommandQueue= ElemCreateCommandQueue(applicationPayload->GraphicsDevice, ElemCommandQueueType_Graphics, NULL);
applicationPayload->SwapChain= ElemCreateSwapChain(applicationPayload->CommandQueue, applicationPayload->Window, UpdateSwapChain, &(ElemSwapChainOptions) { .UpdatePayload = payload });
ElemSwapChainInfo swapChainInfo = ElemGetSwapChainInfo(applicationPayload->SwapChain);
ElemSystemInfo systemInfo = ElemGetSystemInfo();
ElemGraphicsDeviceInfo graphicsDeviceInfo = ElemGetGraphicsDeviceInfo(applicationPayload->GraphicsDevice);
ElemShaderSourceData shaderSourceData = { .ShaderLanguage = ElemShaderLanguage_Hlsl, .Data = { .Items = (uint8_t*)shaderSource, .Length = strlen(shaderSource) } };
ElemShaderCompilationResult compilationResult = ElemCompileShaderLibrary((ElemToolsGraphicsApi)graphicsDeviceInfo.GraphicsApi, (ElemToolsPlatform)systemInfo.Platform, &shaderSourceData, NULL);
ElemShaderLibrary shaderLibrary = ElemCreateShaderLibrary(applicationPayload->GraphicsDevice, (ElemDataSpan) { .Items = compilationResult.Data.Items, .Length = compilationResult.Data.Length });
applicationPayload->GraphicsPipeline = ElemCompileGraphicsPipelineState(applicationPayload->GraphicsDevice, &(ElemGraphicsPipelineStateParameters) {
.ShaderLibrary = shaderLibrary,
.MeshShaderFunction = "MeshMain",
.PixelShaderFunction = "PixelMain",
.TextureFormats = { .Items = (ElemTextureFormat[]) { swapChainInfo.Format }, .Length = 1 }
});
ElemFreeShaderLibrary(shaderLibrary);
}
void FreeSample(void* payload)
{
ApplicationPayload* applicationPayload = (ApplicationPayload*)payload;
ElemFreePipelineState(applicationPayload->GraphicsPipeline);
ElemFreeSwapChain(applicationPayload->SwapChain);
ElemFreeCommandQueue(applicationPayload->CommandQueue);
ElemFreeGraphicsDevice(applicationPayload->GraphicsDevice);
}
void UpdateSwapChain(const ElemSwapChainUpdateParameters* updateParameters, void* payload)
{
ApplicationPayload* applicationPayload = (ApplicationPayload*)payload;
ElemCommandList commandList = ElemGetCommandList(applicationPayload->CommandQueue, NULL);
ElemBeginRenderPass(commandList, &(ElemBeginRenderPassParameters) {
.RenderTargets =
{
.Items = (ElemRenderPassRenderTarget[]) {{
.RenderTarget = updateParameters->BackBufferTexture,
.LoadAction = ElemRenderPassLoadAction_Clear
}},
.Length = 1
}
});
ElemBindPipelineState(commandList, applicationPayload->GraphicsPipeline);
ElemDispatchMesh(commandList, 1, 1, 1);
ElemEndRenderPass(commandList);
ElemCommitCommandList(commandList);
ElemExecuteCommandList(applicationPayload->CommandQueue, commandList, NULL);
ElemPresentSwapChain(applicationPayload->SwapChain);
}
int main(int argc, const char* argv[])
{
ElemRunApplication(&(ElemRunApplicationParameters) {
.InitHandler = InitSample,
.FreeHandler = FreeSample,
.Payload = &(ApplicationPayload){}
});
}Tip
Please note that this code uses both Elemental and ElementalTools. In a real world app, you should compile your shaders offline.
Warning
This code will only runs on platforms that support shader compilation. (Windows, MacOS, Linux) If you want to run code on other platforms you should compile your shaders offline.
You will find detailled examples in the samples folder.
| Back | FazBrowse Home | New Git URL |