add grid to material shader
This commit is contained in:
parent
520dd6c874
commit
5bdaba67e7
@ -5,7 +5,7 @@
|
||||
* ========================== */
|
||||
|
||||
#define ROOTSIG \
|
||||
"RootConstants(num32BitConstants=17, b0), " \
|
||||
"RootConstants(num32BitConstants=18, b0), " \
|
||||
"DescriptorTable(SRV(t0, numDescriptors = unbounded, flags = DESCRIPTORS_VOLATILE)), " \
|
||||
"StaticSampler(s0, " \
|
||||
"filter = FILTER_MIN_MAG_MIP_POINT, " \
|
||||
@ -15,7 +15,7 @@
|
||||
"maxAnisotropy = 1)"
|
||||
|
||||
ConstantBuffer<struct sh_blit_constants> g_constants : register(b0);
|
||||
Texture2D g_nuri_textures[] : register(t0);
|
||||
Texture2D g_textures[] : register(t0);
|
||||
|
||||
SamplerState g_sampler : register(s0);
|
||||
|
||||
@ -64,6 +64,7 @@ struct ps_output {
|
||||
SH_ENTRY(ROOTSIG) struct ps_output ps(struct ps_input input)
|
||||
{
|
||||
struct ps_output output;
|
||||
output.SV_Target = g_nuri_textures[g_constants.texture_id].Sample(g_sampler, input.vs.uv);
|
||||
const float gamma = g_constants.gamma;
|
||||
output.SV_Target = pow(g_textures[g_constants.tex_urid].Sample(g_sampler, input.vs.uv), 1/gamma);
|
||||
return output;
|
||||
}
|
||||
|
||||
@ -4,7 +4,7 @@
|
||||
#define GOLDEN 1.61803398875
|
||||
|
||||
#define DECL(t, n) t n : n
|
||||
#define NURI(i) NonUniformResourceIndex(i)
|
||||
#define NURID(i) NonUniformResourceIndex(i)
|
||||
|
||||
#if !SH_CPU
|
||||
# define INLINE /* For intellisense */
|
||||
|
||||
@ -7,7 +7,8 @@
|
||||
#define ROOTSIG \
|
||||
"RootConstants(num32BitConstants=16, b0), " \
|
||||
"SRV(t0), " \
|
||||
"DescriptorTable(SRV(t1, numDescriptors = unbounded, flags = DESCRIPTORS_VOLATILE)), " \
|
||||
"SRV(t1), " \
|
||||
"DescriptorTable(SRV(t2, numDescriptors = unbounded, flags = DESCRIPTORS_VOLATILE)), " \
|
||||
"StaticSampler(s0, " \
|
||||
"filter = FILTER_MIN_MAG_MIP_POINT, " \
|
||||
"addressU = TEXTURE_ADDRESS_CLAMP, " \
|
||||
@ -17,7 +18,8 @@
|
||||
|
||||
ConstantBuffer<struct sh_material_constants> g_constants : register(b0);
|
||||
StructuredBuffer<struct sh_material_instance> g_instances : register(t0);
|
||||
Texture2D g_nuri_textures[] : register(t1);
|
||||
StructuredBuffer<struct sh_material_grid> g_grids : register(t1);
|
||||
Texture2D g_textures[] : register(t2);
|
||||
|
||||
SamplerState g_sampler : register(s0);
|
||||
|
||||
@ -31,10 +33,12 @@ struct vs_input {
|
||||
};
|
||||
|
||||
struct vs_output {
|
||||
DECL(float4, SV_Position);
|
||||
nointerpolation DECL(uint, flags);
|
||||
nointerpolation DECL(int, tex_nurid);
|
||||
nointerpolation DECL(int, grid_id);
|
||||
DECL(float2, uv);
|
||||
DECL(float4, tint_lin);
|
||||
DECL(uint, texture_nuri);
|
||||
DECL(float4, SV_Position);
|
||||
};
|
||||
|
||||
SH_ENTRY(ROOTSIG) struct vs_output vs(struct vs_input input)
|
||||
@ -52,9 +56,11 @@ SH_ENTRY(ROOTSIG) struct vs_output vs(struct vs_input input)
|
||||
|
||||
struct vs_output output;
|
||||
output.SV_Position = mul(g_constants.projection, float4(world_pos, 0, 1));
|
||||
output.flags = instance.flags;
|
||||
output.tex_nurid = instance.tex_nurid;
|
||||
output.grid_id = instance.grid_id;
|
||||
output.uv = instance.uv0 + ((vert + 0.5) * (instance.uv1 - instance.uv0));
|
||||
output.tint_lin = linear_from_srgb32(instance.tint_srgb);
|
||||
output.texture_nuri = instance.texture_nuri;
|
||||
return output;
|
||||
}
|
||||
|
||||
@ -73,6 +79,44 @@ struct ps_output {
|
||||
SH_ENTRY(ROOTSIG) struct ps_output ps(struct ps_input input)
|
||||
{
|
||||
struct ps_output output;
|
||||
output.SV_Target = g_nuri_textures[NURI(input.vs.texture_nuri)].Sample(g_sampler, input.vs.uv) * input.vs.tint_lin * 1;
|
||||
output.SV_Target = float4(1, 1, 1, 1);
|
||||
|
||||
/* Texture */
|
||||
if (input.vs.tex_nurid >= 0) {
|
||||
output.SV_Target *= g_textures[NURID(input.vs.tex_nurid)].Sample(g_sampler, input.vs.uv);
|
||||
}
|
||||
|
||||
/* Grid */
|
||||
if (input.vs.grid_id >= 0) {
|
||||
struct sh_material_grid grid = g_grids[input.vs.grid_id];
|
||||
float2 grid_pos = input.vs.SV_Position.xy + grid.offset;
|
||||
float half_thickness = grid.line_thickness / 2;
|
||||
float spacing = grid.line_spacing;
|
||||
float4 color = linear_from_srgb32(grid.bg0_srgb);
|
||||
float2 v = abs(round(grid_pos / spacing) * spacing - grid_pos);
|
||||
float dist = min(v.x, v.y);
|
||||
if (grid_pos.y <= half_thickness && grid_pos.y >= -half_thickness) {
|
||||
color = linear_from_srgb32(grid.x_srgb);
|
||||
} else if (grid_pos.x <= half_thickness && grid_pos.x >= -half_thickness) {
|
||||
color = linear_from_srgb32(grid.y_srgb);
|
||||
} else if (dist < half_thickness) {
|
||||
color = linear_from_srgb32(grid.line_srgb);
|
||||
} else {
|
||||
bool checker = false;
|
||||
uint cell_x = (uint)(abs(grid_pos.x) / spacing) + (grid_pos.x < 0);
|
||||
uint cell_y = (uint)(abs(grid_pos.y) / spacing) + (grid_pos.y < 0);
|
||||
if (cell_x % 2 == 0) {
|
||||
checker = cell_y % 2 == 0;
|
||||
} else {
|
||||
checker = cell_y % 2 == 1;
|
||||
}
|
||||
if (checker) {
|
||||
color = linear_from_srgb32(grid.bg1_srgb);
|
||||
}
|
||||
}
|
||||
output.SV_Target *= color;
|
||||
}
|
||||
|
||||
output.SV_Target *= input.vs.tint_lin;
|
||||
return output;
|
||||
}
|
||||
|
||||
@ -11,6 +11,12 @@ INLINE struct sh_uint sh_uint_from_u32(u32 v)
|
||||
return (struct sh_uint) { .v = v };
|
||||
}
|
||||
|
||||
struct sh_int { i32 v; };
|
||||
INLINE struct sh_int sh_int_from_i32(i32 v)
|
||||
{
|
||||
return (struct sh_int) { .v = v };
|
||||
}
|
||||
|
||||
struct sh_float { f32 v; };
|
||||
INLINE struct sh_float sh_float_from_f32(f32 v)
|
||||
{
|
||||
@ -56,24 +62,40 @@ INLINE struct sh_float2x3 sh_float2x3_from_xform(struct xform v)
|
||||
|
||||
SH_STRUCT(sh_blit_constants {
|
||||
SH_DECL(float4x4, projection);
|
||||
SH_DECL(uint, texture_id);
|
||||
SH_DECL(uint, tex_urid);
|
||||
SH_DECL(float, gamma);
|
||||
});
|
||||
SH_ASSERT_32BIT(struct sh_blit_constants, 17); /* Expected 32bit root constant size in shader */
|
||||
SH_ASSERT_32BIT(struct sh_blit_constants, 18); /* Expected 32bit root constant size in shader */
|
||||
|
||||
/* ========================== *
|
||||
* Material shader structures
|
||||
* ========================== */
|
||||
|
||||
#define SH_MATERIAL_FLAG_NONE (0)
|
||||
|
||||
SH_STRUCT(sh_material_constants {
|
||||
SH_DECL(float4x4, projection);
|
||||
});
|
||||
SH_ASSERT_32BIT(struct sh_material_constants, 16); /* Expected 32bit root constant size in shader */
|
||||
|
||||
SH_STRUCT(sh_material_instance {
|
||||
SH_DECL(uint, flags);
|
||||
SH_DECL(int, tex_nurid);
|
||||
SH_DECL(int, grid_id);
|
||||
SH_DECL(float2x3, xf);
|
||||
SH_DECL(float2, uv0);
|
||||
SH_DECL(float2, uv1);
|
||||
SH_DECL(uint, texture_nuri);
|
||||
SH_DECL(uint, tint_srgb);
|
||||
SH_DECL(float, emittance);
|
||||
});
|
||||
|
||||
SH_STRUCT(sh_material_grid {
|
||||
SH_DECL(float, line_thickness);
|
||||
SH_DECL(float, line_spacing);
|
||||
SH_DECL(float2, offset);
|
||||
SH_DECL(uint, bg0_srgb);
|
||||
SH_DECL(uint, bg1_srgb);
|
||||
SH_DECL(uint, line_srgb);
|
||||
SH_DECL(uint, x_srgb);
|
||||
SH_DECL(uint, y_srgb);
|
||||
});
|
||||
|
||||
30
src/draw.c
30
src/draw.c
@ -30,7 +30,7 @@ struct draw_startup_receipt draw_startup(struct gp_startup_receipt *gp_sr,
|
||||
|
||||
void draw_texture(struct gp_handle flow, struct draw_texture_params params)
|
||||
{
|
||||
struct gp_cmd_params cmd = ZI;
|
||||
struct gp_cmd_desc cmd = ZI;
|
||||
cmd.kind = GP_CMD_KIND_DRAW_TEXTURE;
|
||||
cmd.texture.xf = params.xf;
|
||||
cmd.texture.sprite = params.sprite;
|
||||
@ -47,7 +47,7 @@ void draw_texture(struct gp_handle flow, struct draw_texture_params params)
|
||||
|
||||
void draw_poly_ex(struct gp_handle flow, struct v2_array vertices, struct gp_indices indices, u32 color)
|
||||
{
|
||||
struct gp_cmd_params cmd = ZI;
|
||||
struct gp_cmd_desc cmd = ZI;
|
||||
cmd.kind = GP_CMD_KIND_DRAW_MESH;
|
||||
cmd.mesh.vertices = vertices;
|
||||
cmd.mesh.indices = indices;
|
||||
@ -260,17 +260,21 @@ void draw_collider_line(struct gp_handle flow, struct collider_shape shape, stru
|
||||
|
||||
void draw_grid(struct gp_handle flow, struct xform xf, u32 bg0_color, u32 bg1_color, u32 line_color, u32 x_color, u32 y_color, f32 thickness, f32 spacing, struct v2 offset)
|
||||
{
|
||||
struct gp_cmd_params cmd = ZI;
|
||||
cmd.kind = GP_CMD_KIND_DRAW_GRID;
|
||||
cmd.grid.xf = xf;
|
||||
cmd.grid.bg0_color = bg0_color;
|
||||
cmd.grid.bg1_color = bg1_color;
|
||||
cmd.grid.line_color = line_color;
|
||||
cmd.grid.x_color = x_color;
|
||||
cmd.grid.y_color = y_color;
|
||||
cmd.grid.line_thickness = thickness;
|
||||
cmd.grid.line_spacing = spacing;
|
||||
cmd.grid.offset = offset;
|
||||
struct gp_grid_desc grid = ZI;
|
||||
grid.bg0_color = bg0_color;
|
||||
grid.bg1_color = bg1_color;
|
||||
grid.line_color = line_color;
|
||||
grid.x_color = x_color;
|
||||
grid.y_color = y_color;
|
||||
grid.line_thickness = thickness;
|
||||
grid.line_spacing = spacing;
|
||||
grid.offset = offset;
|
||||
|
||||
struct gp_cmd_desc cmd = ZI;
|
||||
cmd.kind = GP_CMD_KIND_DRAW_TEXTURE;
|
||||
cmd.texture.xf = xf;
|
||||
cmd.texture.tint = COLOR_WHITE;
|
||||
cmd.texture.grid = &grid;
|
||||
gp_push_cmd(flow, cmd);
|
||||
}
|
||||
|
||||
|
||||
28
src/gp.h
28
src/gp.h
@ -72,13 +72,23 @@ enum gp_cmd_kind {
|
||||
GP_CMD_KIND_NONE,
|
||||
GP_CMD_KIND_DRAW_MESH,
|
||||
GP_CMD_KIND_DRAW_TEXTURE,
|
||||
GP_CMD_KIND_DRAW_GRID,
|
||||
GP_CMD_KIND_TEST,
|
||||
|
||||
NUM_GP_CMD_KINDS
|
||||
};
|
||||
|
||||
struct gp_cmd_params {
|
||||
struct gp_grid_desc {
|
||||
f32 line_thickness;
|
||||
f32 line_spacing;
|
||||
struct v2 offset;
|
||||
u32 bg0_color;
|
||||
u32 bg1_color;
|
||||
u32 line_color;
|
||||
u32 x_color;
|
||||
u32 y_color;
|
||||
};
|
||||
|
||||
struct gp_cmd_desc {
|
||||
enum gp_cmd_kind kind;
|
||||
union {
|
||||
struct {
|
||||
@ -93,18 +103,8 @@ struct gp_cmd_params {
|
||||
struct clip_rect clip;
|
||||
u32 tint;
|
||||
f32 emittance;
|
||||
struct gp_grid_desc *grid;
|
||||
} texture;
|
||||
struct {
|
||||
struct xform xf;
|
||||
f32 line_thickness;
|
||||
f32 line_spacing;
|
||||
struct v2 offset;
|
||||
u32 bg0_color;
|
||||
u32 bg1_color;
|
||||
u32 line_color;
|
||||
u32 x_color;
|
||||
u32 y_color;
|
||||
} grid;
|
||||
struct {
|
||||
struct xform xf;
|
||||
} test;
|
||||
@ -121,7 +121,7 @@ struct gp_dispatch_params {
|
||||
|
||||
struct gp_handle gp_flow_alloc(void);
|
||||
|
||||
void gp_push_cmd(struct gp_handle gp_flow, struct gp_cmd_params params);
|
||||
void gp_push_cmd(struct gp_handle gp_flow, struct gp_cmd_desc params);
|
||||
|
||||
void gp_dispatch(struct gp_dispatch_params params);
|
||||
|
||||
|
||||
@ -1372,7 +1372,7 @@ struct gp_handle gp_flow_alloc(void)
|
||||
return res;
|
||||
}
|
||||
|
||||
void gp_push_cmd(struct gp_handle gp_flow, struct gp_cmd_params params)
|
||||
void gp_push_cmd(struct gp_handle gp_flow, struct gp_cmd_desc params)
|
||||
{
|
||||
__prof;
|
||||
struct dx11_flow *flow = (struct dx11_flow *)gp_flow.v;
|
||||
|
||||
158
src/gp_dx12.c
158
src/gp_dx12.c
@ -44,7 +44,7 @@
|
||||
|
||||
#define DX12_SWAPCHAIN_BUFFER_COUNT (3)
|
||||
#define DX12_SWAPCHAIN_FORMAT (DXGI_FORMAT_R8G8B8A8_UNORM)
|
||||
//#define DX12_SWAPCHAIN_RTV_FORMAT (DXGI_FORMAT_R8G8B8A8_UNORM_SRGB)
|
||||
//#define DX12_SWAPCHAIN_RTV_FORMAT (DXGI_FORMAT_R8G8B8A8_UNORM_SRGB)
|
||||
|
||||
/* Arbitrary limits */
|
||||
#define DX12_NUM_CBV_SRV_UAV_DESCRIPTORS (1024 * 64)
|
||||
@ -80,10 +80,12 @@ struct pipeline {
|
||||
|
||||
struct pipeline_error *first_error;
|
||||
struct pipeline_error *last_error;
|
||||
i64 compilation_time;
|
||||
i64 compilation_time_ns;
|
||||
|
||||
/* Dict with shader source & included file names as keys */
|
||||
struct dict *dependencies;
|
||||
|
||||
/* Lock global pipelines mutex before accessing */
|
||||
/* Lock global pipelines mutex when accessing */
|
||||
i64 refcount;
|
||||
|
||||
struct pipeline_desc desc;
|
||||
@ -625,9 +627,7 @@ INTERNAL void dx12_init_objects(void)
|
||||
* Dx12 pipeline initialization
|
||||
* ========================== */
|
||||
|
||||
INTERNAL READONLY struct pipeline g_nil_pipeline = ZI;
|
||||
|
||||
INTERNAL void pipeline_alloc_from_descs(u64 num_pipelines, struct pipeline_desc *descs, struct pipeline **pipelines_out);
|
||||
INTERNAL void pipeline_alloc_from_desc(u64 num_pipelines, struct pipeline_desc *descs, struct pipeline **pipelines_out);
|
||||
INTERNAL void pipeline_release(struct pipeline *pipeline);
|
||||
INTERNAL void pipeline_register(u64 num_pipelines, struct pipeline **pipelines);
|
||||
|
||||
@ -669,12 +669,13 @@ INTERNAL void dx12_init_pipelines(void)
|
||||
++num_pipelines;
|
||||
}
|
||||
struct pipeline **pipelines = arena_push_array(scratch.arena, struct pipeline *, num_pipelines);
|
||||
pipeline_alloc_from_descs(num_pipelines, descs, pipelines);
|
||||
pipeline_alloc_from_desc(num_pipelines, descs, pipelines);
|
||||
for (u32 i = 0; i < num_pipelines; ++i) {
|
||||
struct pipeline *pipeline = pipelines[i];
|
||||
if (!pipeline->success) {
|
||||
struct string msg = pipeline->first_error ? pipeline->first_error->msg : LIT("Unknown error");
|
||||
sys_panic(msg);
|
||||
struct string error = pipeline->first_error ? pipeline->first_error->msg : LIT("Unknown error");
|
||||
struct string msg = string_format(scratch.arena, LIT("Error creating pipeline \"%F\":\n\n%F"), FMT_STR(pipeline->name), FMT_STR(error));
|
||||
sys_message_box(SYS_MESSAGE_BOX_KIND_WARNING, msg);
|
||||
}
|
||||
}
|
||||
pipeline_register(num_pipelines, pipelines);
|
||||
@ -1073,7 +1074,7 @@ INTERNAL WORK_TASK_FUNC_DEF(pipeline_load_task, load_arg_raw)
|
||||
|
||||
pipeline->pso = pso;
|
||||
pipeline->rootsig = rootsig;
|
||||
pipeline->compilation_time = sys_time_ns() - start_ns;
|
||||
pipeline->compilation_time_ns = sys_time_ns() - start_ns;
|
||||
pipeline->success = success;
|
||||
|
||||
resource_close(&vs_res);
|
||||
@ -1099,8 +1100,7 @@ INTERNAL WORK_TASK_FUNC_DEF(pipeline_load_task, load_arg_raw)
|
||||
scratch_end(scratch);
|
||||
}
|
||||
|
||||
/* Expects `descs` and `pipelines_out` to be arrays of length `num_pipelines` */
|
||||
INTERNAL void pipeline_alloc_from_descs(u64 num_pipelines, struct pipeline_desc *descs, struct pipeline **pipelines_out)
|
||||
INTERNAL void pipeline_alloc_from_desc(u64 num_pipelines, struct pipeline_desc *descs, struct pipeline **pipelines_out)
|
||||
{
|
||||
__prof;
|
||||
struct work_slate ws = work_slate_begin();
|
||||
@ -1180,28 +1180,31 @@ INTERNAL void pipeline_scope_end(struct pipeline_scope *scope)
|
||||
sys_mutex_unlock(&lock);
|
||||
}
|
||||
|
||||
INTERNAL READONLY struct pipeline g_nil_pipeline = ZI;
|
||||
INTERNAL struct pipeline *pipeline_from_name(struct pipeline_scope *scope, struct string name)
|
||||
{
|
||||
struct pipeline *pipeline = NULL;
|
||||
struct pipeline *res = &g_nil_pipeline;
|
||||
u64 hash = hash_fnv64(HASH_FNV64_BASIS, name);
|
||||
|
||||
pipeline = dict_get(scope->refs, hash);
|
||||
if (!pipeline) {
|
||||
struct pipeline *tmp = dict_get(scope->refs, hash);
|
||||
if (tmp) {
|
||||
res = tmp;
|
||||
} else {
|
||||
{
|
||||
struct sys_lock lock = sys_mutex_lock_e(G.pipelines_mutex);
|
||||
struct pipeline *res = dict_get(G.top_successful_pipelines, hash);
|
||||
if (res) {
|
||||
pipeline = res;
|
||||
++pipeline->refcount;
|
||||
tmp = dict_get(G.top_successful_pipelines, hash);
|
||||
if (tmp) {
|
||||
++tmp->refcount;
|
||||
}
|
||||
sys_mutex_unlock(&lock);
|
||||
}
|
||||
if (pipeline) {
|
||||
dict_set(scope->arena, scope->refs, hash, (u64)pipeline);
|
||||
if (tmp) {
|
||||
dict_set(scope->arena, scope->refs, hash, (u64)tmp);
|
||||
res = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
return pipeline ? pipeline : &g_nil_pipeline;
|
||||
return res;
|
||||
}
|
||||
|
||||
INTERNAL void pipeline_register(u64 num_pipelines, struct pipeline **pipelines)
|
||||
@ -1248,6 +1251,7 @@ INTERNAL RESOURCE_WATCH_CALLBACK_FUNC_DEF(pipeline_resource_watch_callback, name
|
||||
for (struct dict_entry *entry = G.top_pipelines->first; entry; entry = entry->next) {
|
||||
struct pipeline *pipeline = (struct pipeline *)entry->value;
|
||||
if (dict_get(pipeline->dependencies, hash) == 1) {
|
||||
logf_debug("Change detected in shader source file \"%F\", recompiling pipeline \"%F\"", FMT_STR(name), FMT_STR(pipeline->name));
|
||||
*arena_push(scratch.arena, struct pipeline_desc) = pipeline->desc;
|
||||
++num_pipelines;
|
||||
}
|
||||
@ -1257,12 +1261,35 @@ INTERNAL RESOURCE_WATCH_CALLBACK_FUNC_DEF(pipeline_resource_watch_callback, name
|
||||
|
||||
/* Recompile dirty pipelines */
|
||||
struct pipeline **pipelines = arena_push_array(scratch.arena, struct pipeline *, num_pipelines);
|
||||
pipeline_alloc_from_descs(num_pipelines, pipeline_descs, pipelines);
|
||||
pipeline_alloc_from_desc(num_pipelines, pipeline_descs, pipelines);
|
||||
{
|
||||
struct sys_lock lock = sys_mutex_lock_s(G.pipelines_mutex);
|
||||
for (u32 i = 0; i < num_pipelines; ++i) {
|
||||
struct pipeline *pipeline = pipelines[i];
|
||||
if (pipeline->success) {
|
||||
logf_success("Successfully compiled pipeline \"%F\" in %F seconds", FMT_STR(pipeline->name), FMT_FLOAT(SECONDS_FROM_NS(pipeline->compilation_time_ns)));
|
||||
} else {
|
||||
struct pipeline *old_pipeline = dict_get(G.top_successful_pipelines, pipeline->hash);
|
||||
if (old_pipeline) {
|
||||
struct string error = pipeline->first_error ? pipeline->first_error->msg : LIT("Unknown error");
|
||||
struct string msg = string_format(scratch.arena, LIT("Error compiling pipeline \"%F\":\n%F"), FMT_STR(pipeline->name), FMT_STR(error));
|
||||
log_error(msg);
|
||||
} else {
|
||||
/* If no previously successful pipeline exists, then show a message box rather than logging since logs may not be visible to user */
|
||||
struct string error = pipeline->first_error ? pipeline->first_error->msg : LIT("Unknown error");
|
||||
struct string msg = string_format(scratch.arena, LIT("Error compiling pipeline \"%F\":\n\n%F"), FMT_STR(pipeline->name), FMT_STR(error));
|
||||
sys_message_box(SYS_MESSAGE_BOX_KIND_WARNING, msg);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
sys_mutex_unlock(&lock);
|
||||
}
|
||||
pipeline_register(num_pipelines, pipelines);
|
||||
|
||||
scratch_end(scratch);
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
/* ========================== *
|
||||
* Descriptor
|
||||
@ -1321,7 +1348,6 @@ INTERNAL struct cpu_descriptor_heap *cpu_descriptor_heap_alloc(enum D3D12_DESCRI
|
||||
if (num_descriptors == 0 || descriptor_size == 0) {
|
||||
sys_panic(LIT("Unsupported CPU descriptor type"));
|
||||
}
|
||||
|
||||
dh->num_descriptors_capacity = num_descriptors;
|
||||
dh->descriptor_size = descriptor_size;
|
||||
|
||||
@ -1355,6 +1381,7 @@ struct flow {
|
||||
/* Below fields are reset each dispatch */
|
||||
struct sprite_scope *sprite_scope;
|
||||
struct arena *material_instances_arena;
|
||||
struct arena *material_grids_arena;
|
||||
|
||||
struct flow *next_free;
|
||||
};
|
||||
@ -1370,40 +1397,73 @@ INTERNAL struct flow *flow_alloc(void)
|
||||
|
||||
flow->sprite_scope = sprite_scope_begin();
|
||||
flow->material_instances_arena = arena_alloc(GIGABYTE(1));
|
||||
flow->material_grids_arena = arena_alloc(GIGABYTE(1));
|
||||
|
||||
return flow;
|
||||
}
|
||||
|
||||
INTERNAL void flow_reset(struct flow *flow)
|
||||
{
|
||||
sprite_scope_end(flow->sprite_scope);
|
||||
flow->sprite_scope = sprite_scope_begin();
|
||||
arena_reset(flow->material_instances_arena);
|
||||
arena_reset(flow->material_grids_arena);
|
||||
}
|
||||
|
||||
struct gp_handle gp_flow_alloc(void)
|
||||
{
|
||||
struct flow *flow = flow_alloc();
|
||||
return handle_alloc(DX12_HANDLE_KIND_FLOW, flow);
|
||||
}
|
||||
|
||||
void gp_push_cmd(struct gp_handle gp_flow, struct gp_cmd_params params)
|
||||
void gp_push_cmd(struct gp_handle gp_flow, struct gp_cmd_desc desc)
|
||||
{
|
||||
struct flow *flow = handle_get_data(gp_flow, DX12_HANDLE_KIND_FLOW);
|
||||
if (flow) {
|
||||
switch (params.kind) {
|
||||
switch (desc.kind) {
|
||||
default: break;
|
||||
|
||||
case GP_CMD_KIND_DRAW_TEXTURE:
|
||||
{
|
||||
struct dx12_resource *texture = NULL;
|
||||
if (params.texture.texture.gen != 0) {
|
||||
texture = handle_get_data(params.texture.texture, DX12_HANDLE_KIND_RESOURCE);
|
||||
} else if (params.texture.sprite.hash != 0) {
|
||||
struct sprite_texture *st = sprite_texture_from_tag_async(flow->sprite_scope, params.texture.sprite);
|
||||
texture = handle_get_data(st->texture, DX12_HANDLE_KIND_RESOURCE);
|
||||
i32 texture_id = -1;
|
||||
{
|
||||
struct dx12_resource *texture = NULL;
|
||||
if (desc.texture.texture.gen != 0) {
|
||||
texture = handle_get_data(desc.texture.texture, DX12_HANDLE_KIND_RESOURCE);
|
||||
} else if (desc.texture.sprite.hash != 0) {
|
||||
struct sprite_texture *st = sprite_texture_from_tag_async(flow->sprite_scope, desc.texture.sprite);
|
||||
texture = handle_get_data(st->texture, DX12_HANDLE_KIND_RESOURCE);
|
||||
}
|
||||
if (texture) {
|
||||
texture_id = texture->srv_descriptor->index;
|
||||
}
|
||||
}
|
||||
if (texture) {
|
||||
|
||||
i32 grid_id = -1;
|
||||
if (desc.texture.grid) {
|
||||
struct gp_grid_desc *grid_desc = desc.texture.grid;
|
||||
struct sh_material_grid *grid = arena_push(flow->material_grids_arena, struct sh_material_grid);
|
||||
grid->line_thickness = sh_float_from_f32(grid_desc->line_thickness);
|
||||
grid->line_spacing = sh_float_from_f32(grid_desc->line_spacing);
|
||||
grid->offset = sh_float2_from_v2(grid_desc->offset);
|
||||
grid->bg0_srgb = sh_uint_from_u32(grid_desc->bg0_color);
|
||||
grid->bg1_srgb = sh_uint_from_u32(grid_desc->bg1_color);
|
||||
grid->line_srgb = sh_uint_from_u32(grid_desc->line_color);
|
||||
grid->x_srgb = sh_uint_from_u32(grid_desc->x_color);
|
||||
grid->y_srgb = sh_uint_from_u32(grid_desc->y_color);
|
||||
grid_id = ((u8 *)grid - arena_base(flow->material_grids_arena)) / sizeof(grid);
|
||||
}
|
||||
|
||||
if (texture_id >= 0 || grid_id >= 0) {
|
||||
struct sh_material_instance *instance = arena_push(flow->material_instances_arena, struct sh_material_instance);
|
||||
instance->xf = sh_float2x3_from_xform(params.texture.xf);
|
||||
instance->uv0 = sh_float2_from_v2(params.texture.clip.p0);
|
||||
instance->uv1 = sh_float2_from_v2(params.texture.clip.p1);
|
||||
instance->texture_nuri = sh_uint_from_u32(texture->srv_descriptor->index);
|
||||
instance->tint_srgb = sh_uint_from_u32(params.texture.tint);
|
||||
instance->emittance = sh_float_from_f32(params.texture.emittance);
|
||||
instance->flags = sh_uint_from_u32(SH_MATERIAL_FLAG_NONE);
|
||||
instance->tex_nurid = sh_int_from_i32(texture_id);
|
||||
instance->grid_id = sh_int_from_i32(grid_id);
|
||||
instance->xf = sh_float2x3_from_xform(desc.texture.xf);
|
||||
instance->uv0 = sh_float2_from_v2(desc.texture.clip.p0);
|
||||
instance->uv1 = sh_float2_from_v2(desc.texture.clip.p1);
|
||||
instance->tint_srgb = sh_uint_from_u32(desc.texture.tint);
|
||||
instance->emittance = sh_float_from_f32(desc.texture.emittance);
|
||||
}
|
||||
} break;
|
||||
}
|
||||
@ -2173,8 +2233,9 @@ void gp_dispatch(struct gp_dispatch_params params)
|
||||
quad_index_buffer_view.Format = DXGI_FORMAT_R16_UINT;
|
||||
quad_index_buffer_view.SizeInBytes = sizeof(quad_indices);
|
||||
|
||||
/* Upload instance buffer */
|
||||
/* Upload buffers */
|
||||
struct command_buffer *instance_buffer = command_list_push_buffer(cl, STRING_FROM_ARENA(flow->material_instances_arena));
|
||||
struct command_buffer *grid_buffer = command_list_push_buffer(cl, STRING_FROM_ARENA(flow->material_grids_arena));
|
||||
|
||||
/* Upload descriptor heap */
|
||||
struct command_descriptor_heap *descriptor_heap = command_list_push_descriptor_heap(cl, G.cbv_srv_uav_heap);
|
||||
@ -2211,10 +2272,13 @@ void gp_dispatch(struct gp_dispatch_params params)
|
||||
/* Bind instance buffer */
|
||||
ID3D12GraphicsCommandList_SetGraphicsRootShaderResourceView(cl->cl, 1, instance_buffer->resource->gpu_address);
|
||||
|
||||
/* Bind grid buffer */
|
||||
ID3D12GraphicsCommandList_SetGraphicsRootShaderResourceView(cl->cl, 2, grid_buffer->resource->gpu_address);
|
||||
|
||||
/* Bind descriptor heap */
|
||||
ID3D12DescriptorHeap *heaps[] = { descriptor_heap->heap };
|
||||
ID3D12GraphicsCommandList_SetDescriptorHeaps(cl->cl, ARRAY_COUNT(heaps), heaps);
|
||||
ID3D12GraphicsCommandList_SetGraphicsRootDescriptorTable(cl->cl, 2, descriptor_heap->gp_handle);
|
||||
ID3D12GraphicsCommandList_SetGraphicsRootDescriptorTable(cl->cl, 3, descriptor_heap->gp_handle);
|
||||
|
||||
/* Setup Rasterizer State */
|
||||
D3D12_VIEWPORT viewport = viewport_from_rect(params.draw_target_viewport);
|
||||
@ -2237,12 +2301,7 @@ void gp_dispatch(struct gp_dispatch_params params)
|
||||
command_list_close(cl);
|
||||
}
|
||||
pipeline_scope_end(pipeline_scope);
|
||||
|
||||
/* Reset flow */
|
||||
sprite_scope_end(flow->sprite_scope);
|
||||
flow->sprite_scope = sprite_scope_begin();
|
||||
arena_reset(flow->material_instances_arena);
|
||||
|
||||
flow_reset(flow);
|
||||
}
|
||||
|
||||
/* ========================== *
|
||||
@ -2447,7 +2506,8 @@ INTERNAL void present_blit(struct dx12_resource *dst, struct dx12_resource *src,
|
||||
/* Set root constants */
|
||||
struct sh_blit_constants constants = ZI;
|
||||
constants.projection = sh_float4x4_from_mat4x4(vp_matrix);
|
||||
constants.texture_id = sh_uint_from_u32(src->srv_descriptor->index);
|
||||
constants.tex_urid = sh_uint_from_u32(src->srv_descriptor->index);
|
||||
constants.gamma = sh_float_from_f32(2.2);
|
||||
command_list_set_root_constant(cl, &constants, sizeof(constants));
|
||||
|
||||
/* Bind descriptor heap */
|
||||
|
||||
@ -2088,7 +2088,7 @@ void sys_message_box(enum sys_message_box_kind kind, struct string message)
|
||||
} break;
|
||||
}
|
||||
|
||||
//logf_info("Showing message box: \"%F\"", FMT_STR(message));
|
||||
logf_info("Showing message box kind %F with text \"%F\"", FMT_SINT(kind), FMT_STR(message));
|
||||
MessageBoxExW(NULL, message_wstr, title, mbox_type, 0);
|
||||
|
||||
scratch_end(scratch);
|
||||
|
||||
@ -1060,7 +1060,7 @@ INTERNAL void user_update(void)
|
||||
{
|
||||
struct v2 pos = xform_invert_mul_v2(G.world_to_user_xf, V2(0, 0));
|
||||
struct v2 size = xform_basis_invert_mul_v2(G.world_to_user_xf, G.user_size);
|
||||
struct gp_cmd_params cmd = ZI;
|
||||
struct gp_cmd_desc cmd = ZI;
|
||||
cmd.kind = GP_CMD_KIND_TEST;
|
||||
cmd.test.xf = xform_from_rect(RECT_FROM_V2(pos, size));
|
||||
gp_push_cmd(G.world_gp_flow, cmd);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user