Pico Headers
|
A powerful graphics library based on Sokol GFX, written in C99. More...
#include "sokol_gfx.h"
#include <stdbool.h>
#include <stddef.h>
Go to the source code of this file.
Classes | |
struct | pg_blend_mode_t |
Blend mode. More... | |
struct | pg_vertex_buf_t |
Vertex buffer description. More... | |
struct | pg_vertex_attr_t |
Vertex attribute description. More... | |
struct | pg_pipeline_layout_t |
Pipeline layout. More... | |
struct | pg_pipeline_opts_t |
Pipeline creation options. More... | |
struct | pg_texture_opts_t |
Texture creation options. More... | |
struct | pg_sampler_opts_t |
Sampler options. More... | |
struct | pg_shader_internal_t |
Macros | |
#define | PG_MAX_VERTEX_ATTRIBUTES SG_MAX_VERTEX_ATTRIBUTES |
#define | PG_MAX_VERTEX_BUFFERS SG_MAX_VERTEXBUFFER_BINDSLOTS |
#define | PG_MAX_TEXTURE_SLOTS SG_MAX_IMAGE_BINDSLOTS |
#define | PG_MAX_SAMPLER_SLOTS SG_MAX_SAMPLER_BINDSLOTS |
#define | pg_create_shader(ctx, prefix) |
Creates the shader with the given prefix The prefix should refer to the shader program name in a shader compiled by sokol-shdc . For example the sprite shader in the examples would have the prefix 'shader' (without quotation marks) | |
Typedefs | |
typedef struct pg_ctx_t | pg_ctx_t |
Contains core data/state for an instance of the graphics library. | |
typedef struct pg_pipeline_t | pg_pipeline_t |
Render state information. | |
typedef struct pg_shader_t | pg_shader_t |
Vertex/fragment shader program. | |
typedef struct pg_texture_t | pg_texture_t |
Represents an image or render target in VRAM. | |
typedef struct pg_sampler_t | pg_sampler_t |
Represents sampler. | |
typedef struct pg_buffer_t | pg_buffer_t |
A vertex or index array buffer. | |
typedef struct pg_pipeline_opts_t | pg_pipeline_opts_t |
Pipeline creation options. | |
typedef struct pg_texture_opts_t | pg_texture_opts_t |
Texture creation options. | |
Functions | |
void | pg_init (void) |
Loads pico_gfx and sokol_gfx. | |
void | pg_shutdown (void) |
Tears down pico_gfx and sokol_gfx. | |
pg_ctx_t * | pg_create_context (int window_width, int window_height, void *mem_ctx) |
Creates a graphics context. | |
void | pg_destroy_context (pg_ctx_t *ctx) |
Destroys a graphics context. | |
pg_backend_t | pg_backend (void) |
Returns the backend in use at runtime. | |
void | pg_set_window_size (pg_ctx_t *ctx, int width, int height, bool reset) |
Sets the window dimensions. | |
void | pg_get_window_size (pg_ctx_t *ctx, int *width, int *height) |
Gets the window size. | |
void | pg_begin_pass (pg_ctx_t *ctx, pg_texture_t *target, bool clear) |
Starts a render pass (mandatory) | |
void | pg_end_pass (pg_ctx_t *ctx) |
Ends a render pass (mandatory) | |
void | pg_flush (pg_ctx_t *ctx) |
Flush commands. | |
void | pg_push_state (pg_ctx_t *ctx) |
Pushes the active state onto the stack. | |
void | pg_pop_state (pg_ctx_t *ctx) |
Pops a state off the stack and makes it the active state. | |
void | pg_set_clear_color (pg_ctx_t *ctx, float r, float g, float b, float a) |
Sets the clear color state to be placed at the top of the state stack. | |
void | pg_reset_clear_color (pg_ctx_t *ctx) |
void | pg_set_viewport (pg_ctx_t *ctx, int x, int y, int w, int h) |
Sets the viewport state to be placed at the top of the state stack. | |
void | pg_reset_viewport (pg_ctx_t *ctx) |
void | pg_set_scissor (pg_ctx_t *ctx, int x, int y, int w, int h) |
Sets the scissor state to be placed at the top of the state stack. | |
void | pg_reset_scissor (pg_ctx_t *ctx) |
void | pg_set_pipeline (pg_ctx_t *ctx, pg_pipeline_t *pipeline) |
Sets the pipeline state. | |
void | pg_reset_pipeline (pg_ctx_t *ctx) |
void | pg_bind_buffer (pg_ctx_t *ctx, int slot, pg_buffer_t *buffer) |
Binds a buffer to the specified slot. | |
void | pg_reset_buffers (pg_ctx_t *ctx) |
Clears buffer bindings. | |
void | pg_set_index_buffer (pg_ctx_t *ctx, pg_buffer_t *buffer) |
Sets the active index buffer. | |
void | pg_reset_index_buffer (pg_ctx_t *ctx) |
Disables indexed rednering. | |
void | pg_bind_texture (pg_shader_t *shader, const char *name, pg_texture_t *texture) |
Binds a texture to a slot in the current state. | |
void | pg_reset_textures (pg_shader_t *shader) |
Resets the texture bindings for the current state. | |
void | pg_bind_sampler (pg_shader_t *shader, const char *name, pg_sampler_t *sampler) |
Binds a sampler to a slot in the current state. | |
void | pg_reset_samplers (pg_shader_t *shader) |
Resets the sampler bindings for the current state. | |
void | pg_reset_state (pg_ctx_t *ctx) |
Resets the active state to defaults. | |
void | pg_destroy_shader (pg_shader_t *shader) |
Destroys a shader. | |
uint32_t | pg_get_shader_id (const pg_shader_t *shader) |
Returns a shader ID. | |
void | pg_set_uniform_block (pg_shader_t *shader, const char *name, const void *data) |
Sets a uniform block (UB) | |
pg_pipeline_t * | pg_create_pipeline (pg_ctx_t *ctx, pg_shader_t *shader, const pg_pipeline_opts_t *opts) |
Creates a rendering pipeline (encapsulates render state) | |
void | pg_destroy_pipeline (pg_pipeline_t *pipeline) |
Destroys a render pipeline. | |
pg_shader_t * | pg_get_shader (const pg_pipeline_t *pipeline) |
Returns the shader associated with the pipeline. | |
const pg_blend_mode_t * | pg_get_blend_mode (const pg_pipeline_t *pipeline) |
Returns the blend mode associated with the pipeline. | |
pg_texture_t * | pg_create_texture (pg_ctx_t *ctx, int width, int height, const uint8_t *data, size_t size, const pg_texture_opts_t *opts) |
Creates a texture from an RGBA8 image. | |
pg_texture_t * | pg_create_render_texture (pg_ctx_t *ctx, int width, int height, const pg_texture_opts_t *opts) |
Creates a render target. | |
void | pg_destroy_texture (pg_texture_t *texture) |
Destroys a texture. | |
uint32_t | pg_get_texture_id (const pg_texture_t *texture) |
Returns a texture ID. | |
void | pg_get_texture_size (const pg_texture_t *texture, int *width, int *height) |
Gets a texture's dimensions. | |
void | pg_update_texture (pg_texture_t *texture, char *data, int width, int height) |
Updates a texture with the given data. This can only be called once per frame. | |
pg_sampler_t * | pg_create_sampler (pg_ctx_t *ctx, const pg_sampler_opts_t *opts) |
Creates a sampler represents an object that can control how shaders transform and filter texture resource data. | |
void | pg_destroy_sampler (pg_sampler_t *sampler) |
Destroys a sampler object. | |
pg_buffer_t * | pg_create_vertex_buffer (pg_ctx_t *ctx, pg_buffer_usage_t usage, const void *data, size_t count, size_t max_elements, size_t element_size) |
Creates a vertex buffer. | |
pg_buffer_t * | pg_create_index_buffer (pg_ctx_t *ctx, pg_buffer_usage_t usage, const void *data, size_t count, size_t max_elements) |
Creates a vertex buffer. | |
void | pg_destroy_buffer (pg_buffer_t *buffer) |
Destroys a vertex or index buffer. | |
void | pg_update_buffer (pg_buffer_t *buffer, void *data, size_t count) |
int | pg_append_buffer (pg_buffer_t *buffer, void *data, size_t count) |
Appends data to a buffer. This can happen more than once per frame, and cannot happen after an update. | |
int | pg_get_buffer_offset (pg_buffer_t *buffer) |
Returns the buffer offset. | |
void | pg_set_buffer_offset (pg_buffer_t *buffer, int offset) |
Sets the buffer offset. | |
void | pg_reset_buffer (pg_buffer_t *buffer) |
Destroys and recreates buffer. | |
void | pg_draw (const pg_ctx_t *ctx, size_t start, size_t count, size_t instances) |
Draws from the buffers that are bound to the current state. | |
pg_shader_t * | pg_create_shader_internal (pg_ctx_t *ctx, pg_shader_internal_t internal) |
A powerful graphics library based on Sokol GFX, written in C99.
This library is compatible with the sokol_gfx header file: https://github.com/empyreanx/pico_headers/blob/main/examples_pico_gfx/sokol_gfx.h
pico_gfx may not reflect current revisions in the https://github.com/floooh/sokol repository.
pico_gfx is a thin wrapper for sokol_gfx, a low-level graphics library that supports OpenGL, Metal, D3D, and WebGPU. pico_gfx is designed make the common case intuitive and convenient. It provides access to low-level constructs, such as buffers, render passes and pipelines, in a way that is easy to use and understand.
pico_gfx comes with three examples; basic quad rendering (to a render texture and the screen), a scene graph demo, and a particle system demo. These are the best source of information regadring how to use the API.
In constrast with earlier versions, pico_gfx no longer includes a default shader or pipeline. This was a hard decision to make, but the header is less cluttered, and more generic. It is also hard to define what default really means. Pipeline layouts must now be specified explicitly. The examples demonstrate several ways of doing this.
Shaders must be compiled with the sokol compiler (sokol-shdc
). Binary versions of which can be found here. The source code for the compiler can be found here. An example of how to use the compiler can be found in the build_pico_gfx_shader
directory. There are also two compiled shaders included with the examples that are more or less generic for rendering sprites and particles.
One thing pico_gfx does not support (and neither does sokol_gfx) is window and graphics context creation. See here for some examples. It is worth mentioning that SDL2 can supply both a window and OpenGL context out of the box. SDL2 is used in the demos.
Another library that supports window/context creation on all supported backends is sokol_app, but it has yet to be tested with pico_gfx.
The state that pico_gfx manages includes:
- Pipelines/shaders - Uniform blocks - Vertex buffers - Index buffers - Clear color - Viewport - Scissor - Textures - Samplers
Most changes to the state can be isolated by using the state stack (pg_push_state/pg_pop_state
). Simply push the current state onto the stack, make some local changes, and then pop the stack to restore the original state. The exceptions are textures and samplers that are shader state and not global state.
Shaders expose uniforms in blocks.They may then be set by calling pg_set_uniform_block
. This functions operate on structs supplied by a compiled shader,
Please see the examples for more details.
In this iteration, pico_gfx is a C only library. Proper C++ compatibility may be introduced in the future.
To use this library in your project, add
#define PICO_GFX_IMPLEMENTATION #include "pico_gfx.h"
to a source file.
IMPORTANT: sokol_gfx.h must be in the include path!
You must also define one of
#define PICO_GFX_GL #define PICO_GFX_GLES #define PICO_GFX_D3D #define PICO_GFX_METAL #define PICO_GFX_WEBGPU
before including pico_gfx.h
See the examples for build details.
The above (constants/macros) must be defined before PICO_GFX_IMPLEMENTATION
#define PG_MAX_VERTEX_ATTRIBUTES SG_MAX_VERTEX_ATTRIBUTES |
#define PG_MAX_VERTEX_BUFFERS SG_MAX_VERTEXBUFFER_BINDSLOTS |
#define PG_MAX_TEXTURE_SLOTS SG_MAX_IMAGE_BINDSLOTS |
#define PG_MAX_SAMPLER_SLOTS SG_MAX_SAMPLER_BINDSLOTS |
#define pg_create_shader | ( | ctx, | |
prefix | |||
) |
Creates the shader with the given prefix The prefix should refer to the shader program name in a shader compiled by sokol-shdc
. For example the sprite shader in the examples would have the prefix 'shader' (without quotation marks)
typedef struct pg_pipeline_t pg_pipeline_t |
Render state information.
typedef struct pg_shader_t pg_shader_t |
Vertex/fragment shader program.
typedef struct pg_texture_t pg_texture_t |
Represents an image or render target in VRAM.
typedef struct pg_sampler_t pg_sampler_t |
Represents sampler.
typedef struct pg_buffer_t pg_buffer_t |
A vertex or index array buffer.
typedef struct pg_pipeline_opts_t pg_pipeline_opts_t |
Pipeline creation options.
typedef struct pg_texture_opts_t pg_texture_opts_t |
Texture creation options.
enum pg_backend_t |
enum pg_primitive_t |
Drawing primitives.
enum pg_blend_factor_t |
Blend factors.
enum pg_blend_eq_t |
enum pg_vertex_format_t |
Vertex attribute pixel formats.
enum pg_buffer_usage_t |
void pg_init | ( | void | ) |
Loads pico_gfx and sokol_gfx.
IMPORTANT: A valid graphics API context (OpenGL, Metal, D3D) must exist for this function to succeed. This function must be called before any other pico_gfx functions.
NOTE: This function calls sg_setup
.
void pg_shutdown | ( | void | ) |
Tears down pico_gfx and sokol_gfx.
NOTE: This function calls sg_shutdown
pg_ctx_t * pg_create_context | ( | int | window_width, |
int | window_height, | ||
void * | mem_ctx | ||
) |
Creates a graphics context.
window_width | The window width |
window_height | The window height |
void pg_destroy_context | ( | pg_ctx_t * | ctx | ) |
Destroys a graphics context.
pg_backend_t pg_backend | ( | void | ) |
Returns the backend in use at runtime.
void pg_set_window_size | ( | pg_ctx_t * | ctx, |
int | width, | ||
int | height, | ||
bool | reset | ||
) |
Sets the window dimensions.
ctx | The graphics context |
width | The window width |
height | The window height |
reset | Resets the viewport and scissor if true |
void pg_get_window_size | ( | pg_ctx_t * | ctx, |
int * | width, | ||
int * | height | ||
) |
Gets the window size.
void pg_begin_pass | ( | pg_ctx_t * | ctx, |
pg_texture_t * | target, | ||
bool | clear | ||
) |
Starts a render pass (mandatory)
NOTE: The default pass should be the last pass of a frame.
ctx | The graphics context |
pass | The render pass (NULL for the default pass) |
clear | Clears the render target or window |
void pg_end_pass | ( | pg_ctx_t * | ctx | ) |
Ends a render pass (mandatory)
void pg_flush | ( | pg_ctx_t * | ctx | ) |
Flush commands.
Must be called at the end of a frame (after pg_end_pass
).
void pg_push_state | ( | pg_ctx_t * | ctx | ) |
Pushes the active state onto the stack.
State consists of the pipeline, draw color, scissor, viewport, and default MVP transform, buffers, textures, and samplers
void pg_pop_state | ( | pg_ctx_t * | ctx | ) |
Pops a state off the stack and makes it the active state.
void pg_set_clear_color | ( | pg_ctx_t * | ctx, |
float | r, | ||
float | g, | ||
float | b, | ||
float | a | ||
) |
Sets the clear color state to be placed at the top of the state stack.
void pg_reset_clear_color | ( | pg_ctx_t * | ctx | ) |
Resets the clear color
void pg_set_viewport | ( | pg_ctx_t * | ctx, |
int | x, | ||
int | y, | ||
int | w, | ||
int | h | ||
) |
Sets the viewport state to be placed at the top of the state stack.
void pg_reset_viewport | ( | pg_ctx_t * | ctx | ) |
Resets the viewport
void pg_set_scissor | ( | pg_ctx_t * | ctx, |
int | x, | ||
int | y, | ||
int | w, | ||
int | h | ||
) |
Sets the scissor state to be placed at the top of the state stack.
void pg_reset_scissor | ( | pg_ctx_t * | ctx | ) |
Resets the scissor
void pg_set_pipeline | ( | pg_ctx_t * | ctx, |
pg_pipeline_t * | pipeline | ||
) |
Sets the pipeline state.
ctx | The graphics context |
pipeline | The pipeline to be activated |
void pg_reset_pipeline | ( | pg_ctx_t * | ctx | ) |
Resets the pipeline
void pg_bind_buffer | ( | pg_ctx_t * | ctx, |
int | slot, | ||
pg_buffer_t * | buffer | ||
) |
Binds a buffer to the specified slot.
void pg_reset_buffers | ( | pg_ctx_t * | ctx | ) |
Clears buffer bindings.
void pg_set_index_buffer | ( | pg_ctx_t * | ctx, |
pg_buffer_t * | buffer | ||
) |
Sets the active index buffer.
If an index buffer is set, pg_draw will use indexing.
void pg_reset_index_buffer | ( | pg_ctx_t * | ctx | ) |
Disables indexed rednering.
void pg_bind_texture | ( | pg_shader_t * | shader, |
const char * | name, | ||
pg_texture_t * | texture | ||
) |
Binds a texture to a slot in the current state.
shader | The shader associated with the texture |
slot | The binding slot |
texture | The texture to bind |
void pg_reset_textures | ( | pg_shader_t * | shader | ) |
Resets the texture bindings for the current state.
void pg_bind_sampler | ( | pg_shader_t * | shader, |
const char * | name, | ||
pg_sampler_t * | sampler | ||
) |
Binds a sampler to a slot in the current state.
shader | The shader associated with the sampler |
slot | The binding slot |
sampler | The sampler to bind |
void pg_reset_samplers | ( | pg_shader_t * | shader | ) |
Resets the sampler bindings for the current state.
void pg_reset_state | ( | pg_ctx_t * | ctx | ) |
Resets the active state to defaults.
void pg_destroy_shader | ( | pg_shader_t * | shader | ) |
Destroys a shader.
uint32_t pg_get_shader_id | ( | const pg_shader_t * | shader | ) |
Returns a shader ID.
void pg_set_uniform_block | ( | pg_shader_t * | shader, |
const char * | name, | ||
const void * | data | ||
) |
Sets a uniform block (UB)
shader | The shader owning the UB |
name | The name of the UB as supplied by sokol_shdc |
data | The data to set (must be the whole UB) |
pg_pipeline_t * pg_create_pipeline | ( | pg_ctx_t * | ctx, |
pg_shader_t * | shader, | ||
const pg_pipeline_opts_t * | opts | ||
) |
Creates a rendering pipeline (encapsulates render state)
shader | The shader used by this pipeline |
opts | Pipeline creation options (required!) |
void pg_destroy_pipeline | ( | pg_pipeline_t * | pipeline | ) |
Destroys a render pipeline.
pg_shader_t * pg_get_shader | ( | const pg_pipeline_t * | pipeline | ) |
Returns the shader associated with the pipeline.
const pg_blend_mode_t * pg_get_blend_mode | ( | const pg_pipeline_t * | pipeline | ) |
Returns the blend mode associated with the pipeline.
pg_texture_t * pg_create_texture | ( | pg_ctx_t * | ctx, |
int | width, | ||
int | height, | ||
const uint8_t * | data, | ||
size_t | size, | ||
const pg_texture_opts_t * | opts | ||
) |
Creates a texture from an RGBA8 image.
width | Image width |
height | Image height |
data | Image data (format must be RGBA8) |
size | Size of the data in bytes |
opts | Texture creation options (NULL for defaults) |
pg_texture_t * pg_create_render_texture | ( | pg_ctx_t * | ctx, |
int | width, | ||
int | height, | ||
const pg_texture_opts_t * | opts | ||
) |
Creates a render target.
width | Render target width |
height | Render target height |
opts | Texture creation options (NULL for defaults) |
void pg_destroy_texture | ( | pg_texture_t * | texture | ) |
Destroys a texture.
uint32_t pg_get_texture_id | ( | const pg_texture_t * | texture | ) |
Returns a texture ID.
void pg_get_texture_size | ( | const pg_texture_t * | texture, |
int * | width, | ||
int * | height | ||
) |
Gets a texture's dimensions.
void pg_update_texture | ( | pg_texture_t * | texture, |
char * | data, | ||
int | width, | ||
int | height | ||
) |
Updates a texture with the given data. This can only be called once per frame.
pg_sampler_t * pg_create_sampler | ( | pg_ctx_t * | ctx, |
const pg_sampler_opts_t * | opts | ||
) |
Creates a sampler represents an object that can control how shaders transform and filter texture resource data.
opts | Sampler options |
void pg_destroy_sampler | ( | pg_sampler_t * | sampler | ) |
Destroys a sampler object.
pg_buffer_t * pg_create_vertex_buffer | ( | pg_ctx_t * | ctx, |
pg_buffer_usage_t | usage, | ||
const void * | data, | ||
size_t | count, | ||
size_t | max_elements, | ||
size_t | element_size | ||
) |
Creates a vertex buffer.
usage | Determines whether the buffer is static, dynamic, or streaming |
data | Vertex data elements (can be NULL) |
count | The number of elements (can be zero) |
max_elements | The maximum number of elements in the buffer |
element_size | The size (in bytes) of each individual element |
pg_buffer_t * pg_create_index_buffer | ( | pg_ctx_t * | ctx, |
pg_buffer_usage_t | usage, | ||
const void * | data, | ||
size_t | count, | ||
size_t | max_elements | ||
) |
Creates a vertex buffer.
usage | Determines whether the buffer is static, dynamic, or streaming |
data | Index data (can be NULL) |
count | The number of indices (can be zero) |
max_elements | The maximum number of indices in the buffer |
void pg_destroy_buffer | ( | pg_buffer_t * | buffer | ) |
Destroys a vertex or index buffer.
void pg_update_buffer | ( | pg_buffer_t * | buffer, |
void * | data, | ||
size_t | count | ||
) |
Replaces the data in a buffer. This may only happen once per frame and cannot happen after appending data
int pg_append_buffer | ( | pg_buffer_t * | buffer, |
void * | data, | ||
size_t | count | ||
) |
Appends data to a buffer. This can happen more than once per frame, and cannot happen after an update.
int pg_get_buffer_offset | ( | pg_buffer_t * | buffer | ) |
Returns the buffer offset.
void pg_set_buffer_offset | ( | pg_buffer_t * | buffer, |
int | offset | ||
) |
Sets the buffer offset.
void pg_reset_buffer | ( | pg_buffer_t * | buffer | ) |
Destroys and recreates buffer.
void pg_draw | ( | const pg_ctx_t * | ctx, |
size_t | start, | ||
size_t | count, | ||
size_t | instances | ||
) |
Draws from the buffers that are bound to the current state.
ctx | The graphics context |
start | The position of the first element |
count | The number of elements to draw |
instances | The number of instances |
pg_shader_t * pg_create_shader_internal | ( | pg_ctx_t * | ctx, |
pg_shader_internal_t | internal | ||
) |