add debug ui for collision grids
This commit is contained in:
@@ -110,6 +110,7 @@ add_shader(character_shadow)
|
|||||||
add_shader(world)
|
add_shader(world)
|
||||||
add_shader(placeable)
|
add_shader(placeable)
|
||||||
add_shader(grid)
|
add_shader(grid)
|
||||||
|
add_shader(collision_grid)
|
||||||
|
|
||||||
add_custom_target(shaders-spv DEPENDS ${SHADERS_SPV})
|
add_custom_target(shaders-spv DEPENDS ${SHADERS_SPV})
|
||||||
add_custom_target(shaders-wgsl DEPENDS ${SHADERS_WGSL})
|
add_custom_target(shaders-wgsl DEPENDS ${SHADERS_WGSL})
|
||||||
|
|||||||
+43
-4
@@ -91,6 +91,8 @@ static vec2 mouse_pos;
|
|||||||
|
|
||||||
static bool in_editor;
|
static bool in_editor;
|
||||||
static bool show_grid = true;
|
static bool show_grid = true;
|
||||||
|
static bool show_static_collision_grid;
|
||||||
|
static bool show_water_collision_grid;
|
||||||
|
|
||||||
static vec2 editor_camera_position;
|
static vec2 editor_camera_position;
|
||||||
static float editor_camera_distance = 30.0f;
|
static float editor_camera_distance = 30.0f;
|
||||||
@@ -206,6 +208,9 @@ struct Map {
|
|||||||
|
|
||||||
R_Texture texture;
|
R_Texture texture;
|
||||||
R_Buffer placeables_buffer;
|
R_Buffer placeables_buffer;
|
||||||
|
|
||||||
|
R_Texture debug_static_collision_grid_texture;
|
||||||
|
R_Texture debug_water_collision_grid_texture;
|
||||||
};
|
};
|
||||||
|
|
||||||
static Uint32 num_loaded_maps;
|
static Uint32 num_loaded_maps;
|
||||||
@@ -490,8 +495,11 @@ static void recalculate_static_collision_grid(Map *world) {
|
|||||||
|
|
||||||
for (int i = 0; i < world->num_placeables; i++) {
|
for (int i = 0; i < world->num_placeables; i++) {
|
||||||
u32vec2 pos = world->placeables[i].pos;
|
u32vec2 pos = world->placeables[i].pos;
|
||||||
world->static_collision_grid[pos.y * (world->size.x - 2) + pos.x] = 1;
|
world->static_collision_grid[pos.y * (world->size.x - 1) + pos.x] = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (world->debug_static_collision_grid_texture) renderer_texture_destroy(world->debug_static_collision_grid_texture);
|
||||||
|
world->debug_static_collision_grid_texture = renderer_texture_create(R_TEXTURE_FORMAT_R8_UINT, R_TEXTURE_USAGE_STORAGE, false, world->size.x - 1, world->size.y - 1, world->static_collision_grid, "debug_static_collision_grid_texture");
|
||||||
}
|
}
|
||||||
|
|
||||||
static void recalculate_water_collision_grid(Map *world) {
|
static void recalculate_water_collision_grid(Map *world) {
|
||||||
@@ -506,9 +514,12 @@ static void recalculate_water_collision_grid(Map *world) {
|
|||||||
(get_corner_info(world, x + 0, y + 1) & (0xff << 8)) |
|
(get_corner_info(world, x + 0, y + 1) & (0xff << 8)) |
|
||||||
(get_corner_info(world, x + 1, y + 1) & (0xff << 0));
|
(get_corner_info(world, x + 1, y + 1) & (0xff << 0));
|
||||||
|
|
||||||
world->water_collision_grid[y * (world->size.x - 2) + x] = grid_corner_info == ((TILEKIND_WATER << 24) | (TILEKIND_WATER << 16) | (TILEKIND_WATER << 8) | (TILEKIND_WATER << 0));
|
world->water_collision_grid[y * (world->size.x - 1) + x] = grid_corner_info == ((TILEKIND_WATER << 24) | (TILEKIND_WATER << 16) | (TILEKIND_WATER << 8) | (TILEKIND_WATER << 0));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (world->debug_water_collision_grid_texture) renderer_texture_destroy(world->debug_water_collision_grid_texture);
|
||||||
|
world->debug_water_collision_grid_texture = renderer_texture_create(R_TEXTURE_FORMAT_R8_UINT, R_TEXTURE_USAGE_STORAGE, false, world->size.x - 1, world->size.y - 1, world->water_collision_grid, "debug_water_collision_grid_texture");
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool save_worlds_list() {
|
static bool save_worlds_list() {
|
||||||
@@ -1631,6 +1642,8 @@ static void update_state_editor() {
|
|||||||
ImGui::SetNextWindowPos({ viewport->WorkPos.x + viewport->WorkSize.x - 10.0f, viewport->WorkPos.y + 10.0f }, ImGuiCond_Always, { 1.0f, 0.0f });
|
ImGui::SetNextWindowPos({ viewport->WorkPos.x + viewport->WorkSize.x - 10.0f, viewport->WorkPos.y + 10.0f }, ImGuiCond_Always, { 1.0f, 0.0f });
|
||||||
if (ImGui::Begin("Overlay", NULL, ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoFocusOnAppearing | ImGuiWindowFlags_NoNav)) {
|
if (ImGui::Begin("Overlay", NULL, ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoFocusOnAppearing | ImGuiWindowFlags_NoNav)) {
|
||||||
ImGui::Checkbox("Grid", &show_grid);
|
ImGui::Checkbox("Grid", &show_grid);
|
||||||
|
ImGui::Checkbox("Static Collision", &show_static_collision_grid);
|
||||||
|
ImGui::Checkbox("Water Collision", &show_water_collision_grid);
|
||||||
}
|
}
|
||||||
ImGui::End();
|
ImGui::End();
|
||||||
|
|
||||||
@@ -1762,6 +1775,32 @@ static void render_editor() {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (show_static_collision_grid) {
|
||||||
|
ZoneScopedN("Draw Static Collision Grid");
|
||||||
|
|
||||||
|
renderer_frame_set_shader(R_SHADER_COLLISION_GRID);
|
||||||
|
renderer_frame_draw(NULL, NULL, NULL, 4, (current_map->size.x - 1) * (current_map->size.y - 1), &(R_Draw_Resources){
|
||||||
|
.vertex_storage_textures = (R_Texture[]){ current_map->debug_static_collision_grid_texture },
|
||||||
|
.vertex_uniform_buffers = (R_Buffer[]){ view_projection_matrix_buffer, per_frame_buffer },
|
||||||
|
|
||||||
|
.num_vertex_storage_textures = 1,
|
||||||
|
.num_vertex_uniform_buffers = 2,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (show_water_collision_grid) {
|
||||||
|
ZoneScopedN("Draw Water Collision Grid");
|
||||||
|
|
||||||
|
renderer_frame_set_shader(R_SHADER_COLLISION_GRID);
|
||||||
|
renderer_frame_draw(NULL, NULL, NULL, 4, (current_map->size.x - 1) * (current_map->size.y - 1), &(R_Draw_Resources){
|
||||||
|
.vertex_storage_textures = (R_Texture[]){ current_map->debug_water_collision_grid_texture },
|
||||||
|
.vertex_uniform_buffers = (R_Buffer[]){ view_projection_matrix_buffer, per_frame_buffer },
|
||||||
|
|
||||||
|
.num_vertex_storage_textures = 1,
|
||||||
|
.num_vertex_uniform_buffers = 2,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
{
|
{
|
||||||
ZoneScopedN("ImGui Render");
|
ZoneScopedN("ImGui Render");
|
||||||
ImGui::Render();
|
ImGui::Render();
|
||||||
@@ -1783,10 +1822,10 @@ static bool try_queued_move() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (target_position != player.position) {
|
if (target_position != player.position) {
|
||||||
if (current_map->static_collision_grid[target_position.y * (current_map->size.x - 2) + target_position.x] == 1)
|
if (current_map->static_collision_grid[target_position.y * (current_map->size.x - 1) + target_position.x] == 1)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (current_map->water_collision_grid[target_position.y * (current_map->size.x - 2) + target_position.x] == 1)
|
if (current_map->water_collision_grid[target_position.y * (current_map->size.x - 1) + target_position.x] == 1)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
player.target_position = target_position;
|
player.target_position = target_position;
|
||||||
|
|||||||
@@ -13,6 +13,7 @@ typedef enum : Uint32 {
|
|||||||
R_SHADER_WORLD,
|
R_SHADER_WORLD,
|
||||||
R_SHADER_PLACEABLE,
|
R_SHADER_PLACEABLE,
|
||||||
R_SHADER_GRID,
|
R_SHADER_GRID,
|
||||||
|
R_SHADER_COLLISION_GRID,
|
||||||
R_SHADER_COUNT,
|
R_SHADER_COUNT,
|
||||||
} R_Shader;
|
} R_Shader;
|
||||||
|
|
||||||
@@ -32,6 +33,7 @@ typedef enum : Uint32 {
|
|||||||
} R_Texture_Usage;
|
} R_Texture_Usage;
|
||||||
|
|
||||||
typedef enum : Uint32 {
|
typedef enum : Uint32 {
|
||||||
|
R_TEXTURE_FORMAT_R8_UINT,
|
||||||
R_TEXTURE_FORMAT_R8_UNORM,
|
R_TEXTURE_FORMAT_R8_UNORM,
|
||||||
R_TEXTURE_FORMAT_R16_UINT,
|
R_TEXTURE_FORMAT_R16_UINT,
|
||||||
R_TEXTURE_FORMAT_RGBA8_UNORM,
|
R_TEXTURE_FORMAT_RGBA8_UNORM,
|
||||||
|
|||||||
@@ -41,6 +41,7 @@ static SDL_GPUSampler *bilinear_sampler;
|
|||||||
static SDL_GPUGraphicsPipeline *shaders[R_SHADER_COUNT];
|
static SDL_GPUGraphicsPipeline *shaders[R_SHADER_COUNT];
|
||||||
|
|
||||||
static SDL_GPUTextureFormat texture_formats[] = {
|
static SDL_GPUTextureFormat texture_formats[] = {
|
||||||
|
[R_TEXTURE_FORMAT_R8_UINT] = SDL_GPU_TEXTUREFORMAT_R8_UINT,
|
||||||
[R_TEXTURE_FORMAT_R8_UNORM] = SDL_GPU_TEXTUREFORMAT_R8_UNORM,
|
[R_TEXTURE_FORMAT_R8_UNORM] = SDL_GPU_TEXTUREFORMAT_R8_UNORM,
|
||||||
[R_TEXTURE_FORMAT_R16_UINT] = SDL_GPU_TEXTUREFORMAT_R16_UINT,
|
[R_TEXTURE_FORMAT_R16_UINT] = SDL_GPU_TEXTUREFORMAT_R16_UINT,
|
||||||
[R_TEXTURE_FORMAT_RGBA8_UNORM] = SDL_GPU_TEXTUREFORMAT_R8G8B8A8_UNORM,
|
[R_TEXTURE_FORMAT_RGBA8_UNORM] = SDL_GPU_TEXTUREFORMAT_R8G8B8A8_UNORM,
|
||||||
@@ -51,6 +52,7 @@ static SDL_GPUTextureFormat texture_formats[] = {
|
|||||||
static_assert(SDL_arraysize(texture_formats) == R_TEXTURE_FORMAT_COUNT);
|
static_assert(SDL_arraysize(texture_formats) == R_TEXTURE_FORMAT_COUNT);
|
||||||
|
|
||||||
static Uint32 texel_sizes[] = {
|
static Uint32 texel_sizes[] = {
|
||||||
|
[R_TEXTURE_FORMAT_R8_UINT] = 1,
|
||||||
[R_TEXTURE_FORMAT_R8_UNORM] = 1,
|
[R_TEXTURE_FORMAT_R8_UNORM] = 1,
|
||||||
[R_TEXTURE_FORMAT_R16_UINT] = 2,
|
[R_TEXTURE_FORMAT_R16_UINT] = 2,
|
||||||
[R_TEXTURE_FORMAT_RGBA8_UNORM] = 4,
|
[R_TEXTURE_FORMAT_RGBA8_UNORM] = 4,
|
||||||
@@ -1058,6 +1060,123 @@ bool renderer_init(SDL_Window *window_) {
|
|||||||
SDL_ReleaseGPUShader(device, fragment_shader);
|
SDL_ReleaseGPUShader(device, fragment_shader);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{ // Collision Grid
|
||||||
|
const Uint8 shader_source[] = {
|
||||||
|
#embed "shaders/spirv/collision_grid.spv"
|
||||||
|
};
|
||||||
|
|
||||||
|
SDL_GPUShader *vertex_shader = SDL_CreateGPUShader(device, &(SDL_GPUShaderCreateInfo){
|
||||||
|
.code_size = sizeof(shader_source),
|
||||||
|
.code = shader_source,
|
||||||
|
.entrypoint = "main_vertex",
|
||||||
|
|
||||||
|
.format = SDL_GPU_SHADERFORMAT_SPIRV,
|
||||||
|
.stage = SDL_GPU_SHADERSTAGE_VERTEX,
|
||||||
|
|
||||||
|
.num_samplers = 0,
|
||||||
|
.num_storage_textures = 1,
|
||||||
|
.num_storage_buffers = 0,
|
||||||
|
.num_uniform_buffers = 2,
|
||||||
|
});
|
||||||
|
|
||||||
|
SDL_GPUShader *fragment_shader = SDL_CreateGPUShader(device, &(SDL_GPUShaderCreateInfo){
|
||||||
|
.code_size = sizeof(shader_source),
|
||||||
|
.code = shader_source,
|
||||||
|
.entrypoint = "main_fragment",
|
||||||
|
|
||||||
|
.format = SDL_GPU_SHADERFORMAT_SPIRV,
|
||||||
|
.stage = SDL_GPU_SHADERSTAGE_FRAGMENT,
|
||||||
|
|
||||||
|
.num_samplers = 0,
|
||||||
|
.num_storage_textures = 0,
|
||||||
|
.num_storage_buffers = 0,
|
||||||
|
.num_uniform_buffers = 0,
|
||||||
|
});
|
||||||
|
|
||||||
|
SDL_PropertiesID properties = SDL_CreateProperties();
|
||||||
|
SDL_SetStringProperty(properties, SDL_PROP_GPU_BUFFER_CREATE_NAME_STRING, "R_SHADER collision_grid");
|
||||||
|
|
||||||
|
shaders[R_SHADER_COLLISION_GRID] = SDL_CreateGPUGraphicsPipeline(device, &(SDL_GPUGraphicsPipelineCreateInfo){
|
||||||
|
.vertex_shader = vertex_shader,
|
||||||
|
.fragment_shader = fragment_shader,
|
||||||
|
|
||||||
|
.vertex_input_state = {
|
||||||
|
.vertex_buffer_descriptions = (SDL_GPUVertexBufferDescription[]) {},
|
||||||
|
.num_vertex_buffers = 0,
|
||||||
|
|
||||||
|
.vertex_attributes = (SDL_GPUVertexAttribute[]) {},
|
||||||
|
.num_vertex_attributes = 0,
|
||||||
|
},
|
||||||
|
|
||||||
|
.primitive_type = SDL_GPU_PRIMITIVETYPE_LINELIST,
|
||||||
|
|
||||||
|
.rasterizer_state = {
|
||||||
|
.fill_mode = SDL_GPU_FILLMODE_FILL,
|
||||||
|
.cull_mode = SDL_GPU_CULLMODE_BACK,
|
||||||
|
.front_face = SDL_GPU_FRONTFACE_COUNTER_CLOCKWISE,
|
||||||
|
|
||||||
|
.depth_bias_constant_factor = 0.0f,
|
||||||
|
.depth_bias_clamp = 0.0f,
|
||||||
|
.depth_bias_slope_factor = 0.0f,
|
||||||
|
|
||||||
|
.enable_depth_bias = false,
|
||||||
|
.enable_depth_clip = false,
|
||||||
|
},
|
||||||
|
|
||||||
|
.multisample_state = {
|
||||||
|
.sample_count = SDL_GPU_SAMPLECOUNT_8,
|
||||||
|
.sample_mask = 0,
|
||||||
|
.enable_mask = 0,
|
||||||
|
|
||||||
|
.enable_alpha_to_coverage = false,
|
||||||
|
},
|
||||||
|
|
||||||
|
.depth_stencil_state = {
|
||||||
|
.compare_op = SDL_GPU_COMPAREOP_GREATER_OR_EQUAL,
|
||||||
|
|
||||||
|
.back_stencil_state = { .fail_op = SDL_GPU_STENCILOP_INVALID, .pass_op = SDL_GPU_STENCILOP_INVALID, .depth_fail_op = SDL_GPU_STENCILOP_INVALID, .compare_op = SDL_GPU_COMPAREOP_INVALID, },
|
||||||
|
.front_stencil_state = { .fail_op = SDL_GPU_STENCILOP_INVALID, .pass_op = SDL_GPU_STENCILOP_INVALID, .depth_fail_op = SDL_GPU_STENCILOP_INVALID, .compare_op = SDL_GPU_COMPAREOP_INVALID, },
|
||||||
|
|
||||||
|
.compare_mask = 0,
|
||||||
|
.write_mask = 0,
|
||||||
|
|
||||||
|
.enable_depth_test = false,
|
||||||
|
.enable_depth_write = false,
|
||||||
|
.enable_stencil_test = false,
|
||||||
|
},
|
||||||
|
|
||||||
|
.target_info = {
|
||||||
|
.color_target_descriptions = (SDL_GPUColorTargetDescription[]){
|
||||||
|
{
|
||||||
|
.format = texture_formats[surface.format],
|
||||||
|
.blend_state = {
|
||||||
|
.src_color_blendfactor = SDL_GPU_BLENDFACTOR_SRC_ALPHA,
|
||||||
|
.dst_color_blendfactor = SDL_GPU_BLENDFACTOR_ONE_MINUS_SRC_ALPHA,
|
||||||
|
.color_blend_op = SDL_GPU_BLENDOP_ADD,
|
||||||
|
|
||||||
|
.src_alpha_blendfactor = SDL_GPU_BLENDFACTOR_SRC_ALPHA,
|
||||||
|
.dst_alpha_blendfactor = SDL_GPU_BLENDFACTOR_ONE_MINUS_SRC_ALPHA,
|
||||||
|
.alpha_blend_op = SDL_GPU_BLENDOP_ADD,
|
||||||
|
|
||||||
|
.color_write_mask = 0,
|
||||||
|
|
||||||
|
.enable_blend = true,
|
||||||
|
.enable_color_write_mask = false,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
.num_color_targets = 1,
|
||||||
|
|
||||||
|
.depth_stencil_format = SDL_GPU_TEXTUREFORMAT_INVALID,
|
||||||
|
.has_depth_stencil_target = false,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
SDL_DestroyProperties(properties);
|
||||||
|
SDL_ReleaseGPUShader(device, vertex_shader);
|
||||||
|
SDL_ReleaseGPUShader(device, fragment_shader);
|
||||||
|
}
|
||||||
|
|
||||||
for (int i = 0; i < R_SHADER_COUNT; i++) {
|
for (int i = 0; i < R_SHADER_COUNT; i++) {
|
||||||
SDL_assert(shaders[i]);
|
SDL_assert(shaders[i]);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -44,6 +44,7 @@ static R_Shader current_shader;
|
|||||||
static WGPUSampler bilinear_sampler;
|
static WGPUSampler bilinear_sampler;
|
||||||
|
|
||||||
static WGPUTextureFormat texture_formats[] = {
|
static WGPUTextureFormat texture_formats[] = {
|
||||||
|
[R_TEXTURE_FORMAT_R8_UINT] = WGPUTextureFormat_R8Uint,
|
||||||
[R_TEXTURE_FORMAT_R8_UNORM] = WGPUTextureFormat_R8Unorm,
|
[R_TEXTURE_FORMAT_R8_UNORM] = WGPUTextureFormat_R8Unorm,
|
||||||
[R_TEXTURE_FORMAT_R16_UINT] = WGPUTextureFormat_R16Uint,
|
[R_TEXTURE_FORMAT_R16_UINT] = WGPUTextureFormat_R16Uint,
|
||||||
[R_TEXTURE_FORMAT_RGBA8_UNORM] = WGPUTextureFormat_RGBA8Unorm,
|
[R_TEXTURE_FORMAT_RGBA8_UNORM] = WGPUTextureFormat_RGBA8Unorm,
|
||||||
@@ -54,6 +55,7 @@ static WGPUTextureFormat texture_formats[] = {
|
|||||||
static_assert(SDL_arraysize(texture_formats) == R_TEXTURE_FORMAT_COUNT);
|
static_assert(SDL_arraysize(texture_formats) == R_TEXTURE_FORMAT_COUNT);
|
||||||
|
|
||||||
static Uint32 texel_sizes[] = {
|
static Uint32 texel_sizes[] = {
|
||||||
|
[R_TEXTURE_FORMAT_R8_UINT] = 1,
|
||||||
[R_TEXTURE_FORMAT_R8_UNORM] = 1,
|
[R_TEXTURE_FORMAT_R8_UNORM] = 1,
|
||||||
[R_TEXTURE_FORMAT_R16_UINT] = 2,
|
[R_TEXTURE_FORMAT_R16_UINT] = 2,
|
||||||
[R_TEXTURE_FORMAT_RGBA8_UNORM] = 4,
|
[R_TEXTURE_FORMAT_RGBA8_UNORM] = 4,
|
||||||
@@ -1163,6 +1165,90 @@ bool renderer_init(SDL_Window *window_) {
|
|||||||
wgpuShaderModuleRelease(shader);
|
wgpuShaderModuleRelease(shader);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{ // Collision Grid
|
||||||
|
const char shader_source[] = {
|
||||||
|
#embed "shaders/wgsl/collision_grid.wgsl"
|
||||||
|
};
|
||||||
|
|
||||||
|
WGPUShaderModule shader = wgpuDeviceCreateShaderModule(device, &(WGPUShaderModuleDescriptor){
|
||||||
|
.nextInChain = (WGPUChainedStruct *)&(WGPUShaderSourceWGSL){
|
||||||
|
.chain = { .next = NULL, .sType = WGPUSType_ShaderSourceWGSL },
|
||||||
|
.code = { .data = shader_source, .length = SDL_arraysize(shader_source) },
|
||||||
|
},
|
||||||
|
.label = { .data = "collision_grid shader", .length = WGPU_STRLEN }
|
||||||
|
});
|
||||||
|
|
||||||
|
shaders[R_SHADER_COLLISION_GRID] = wgpuDeviceCreateRenderPipeline(device, &(WGPURenderPipelineDescriptor){
|
||||||
|
.label = { .data = "collision_grid render_pipeline", .length = WGPU_STRLEN },
|
||||||
|
|
||||||
|
.layout = wgpuDeviceCreatePipelineLayout(device, &(WGPUPipelineLayoutDescriptor){
|
||||||
|
.label = { .data = "collision_grid pipeline_layout", .length = WGPU_STRLEN },
|
||||||
|
.bindGroupLayoutCount = 4,
|
||||||
|
.bindGroupLayouts = (WGPUBindGroupLayout[]){
|
||||||
|
wgpuDeviceCreateBindGroupLayout(device, &(WGPUBindGroupLayoutDescriptor){
|
||||||
|
.entryCount = 1,
|
||||||
|
.entries = (WGPUBindGroupLayoutEntry[]){
|
||||||
|
{ .binding = 0, .visibility = WGPUShaderStage_Vertex, .texture = { .sampleType = WGPUTextureSampleType_Uint, .viewDimension = WGPUTextureViewDimension_2D } },
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
wgpuDeviceCreateBindGroupLayout(device, &(WGPUBindGroupLayoutDescriptor){
|
||||||
|
.entryCount = 2,
|
||||||
|
.entries = (WGPUBindGroupLayoutEntry[]){
|
||||||
|
{ .binding = 0, .visibility = WGPUShaderStage_Vertex, .buffer = { .type = WGPUBufferBindingType_Uniform } },
|
||||||
|
{ .binding = 1, .visibility = WGPUShaderStage_Vertex, .buffer = { .type = WGPUBufferBindingType_Uniform } },
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
wgpuDeviceCreateBindGroupLayout(device, &(WGPUBindGroupLayoutDescriptor){
|
||||||
|
.entryCount = 0,
|
||||||
|
.entries = (WGPUBindGroupLayoutEntry[]){},
|
||||||
|
}),
|
||||||
|
wgpuDeviceCreateBindGroupLayout(device, &(WGPUBindGroupLayoutDescriptor){
|
||||||
|
.entryCount = 0,
|
||||||
|
.entries = (WGPUBindGroupLayoutEntry[]){},
|
||||||
|
}),
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
|
||||||
|
.vertex = {
|
||||||
|
.module = shader,
|
||||||
|
.entryPoint = { .data = "main_vertex", .length = WGPU_STRLEN },
|
||||||
|
.constantCount = 0,
|
||||||
|
.constants = NULL,
|
||||||
|
.bufferCount = 0,
|
||||||
|
.buffers = (WGPUVertexBufferLayout[]){
|
||||||
|
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
|
.primitive = {
|
||||||
|
.topology = WGPUPrimitiveTopology_LineList,
|
||||||
|
.stripIndexFormat = WGPUIndexFormat_Undefined,
|
||||||
|
.frontFace = WGPUFrontFace_CCW,
|
||||||
|
.cullMode = WGPUCullMode_Back,
|
||||||
|
.unclippedDepth = false,
|
||||||
|
},
|
||||||
|
|
||||||
|
.depthStencil = NULL,
|
||||||
|
|
||||||
|
.multisample = {
|
||||||
|
.count = 4,
|
||||||
|
.mask = ~0u,
|
||||||
|
.alphaToCoverageEnabled = false,
|
||||||
|
},
|
||||||
|
|
||||||
|
.fragment = &(WGPUFragmentState){
|
||||||
|
.module = shader,
|
||||||
|
.entryPoint = { .data = "main_fragment", .length = WGPU_STRLEN },
|
||||||
|
.constantCount = 0,
|
||||||
|
.constants = NULL,
|
||||||
|
.targetCount = 1,
|
||||||
|
.targets = &color_target_state,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
wgpuShaderModuleRelease(shader);
|
||||||
|
}
|
||||||
|
|
||||||
for (int i = 0; i < R_SHADER_COUNT; i++) {
|
for (int i = 0; i < R_SHADER_COUNT; i++) {
|
||||||
SDL_assert(shaders[i]);
|
SDL_assert(shaders[i]);
|
||||||
}
|
}
|
||||||
|
|||||||
Binary file not shown.
@@ -0,0 +1,53 @@
|
|||||||
|
#language 2026
|
||||||
|
|
||||||
|
#include "shared.slang"
|
||||||
|
#include "wgsl_workaround.slang"
|
||||||
|
|
||||||
|
struct VertexShaderInput {
|
||||||
|
uint32_t vertex_index : SV_VulkanVertexID;
|
||||||
|
uint32_t instance_index : SV_VulkanInstanceID;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct VertexShaderOutput {
|
||||||
|
float4 pos : SV_Position;
|
||||||
|
|
||||||
|
uint is_collider;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct FragmentShaderOutput {
|
||||||
|
float4 color : SV_Target;
|
||||||
|
};
|
||||||
|
|
||||||
|
[format("r8ui")]
|
||||||
|
[vk::binding(0, 0)] Texture2D<uint32_t> grid_texture;
|
||||||
|
|
||||||
|
[shader("vertex")]
|
||||||
|
VertexShaderOutput main_vertex(VertexShaderInput input) {
|
||||||
|
var output: VertexShaderOutput;
|
||||||
|
|
||||||
|
var vertex_pos = float2(0, 0);
|
||||||
|
|
||||||
|
switch (input.vertex_index) {
|
||||||
|
case 0: { vertex_pos = float2(-0.5, -0.5); } break;
|
||||||
|
case 1: { vertex_pos = float2( 0.5, 0.5); } break;
|
||||||
|
case 2: { vertex_pos = float2( 0.5, -0.5); } break;
|
||||||
|
case 3: { vertex_pos = float2(-0.5, 0.5); } break;
|
||||||
|
default: {}
|
||||||
|
}
|
||||||
|
|
||||||
|
let tile_pos = uint32_t2(input.instance_index % (per_frame.map_width - 1), input.instance_index / (per_frame.map_width - 1));
|
||||||
|
|
||||||
|
output.is_collider = grid_texture.Load(uint32_t3(tile_pos, 0));
|
||||||
|
output.pos = mul(float4(tile_pos + vertex_pos, 0, 1), view_projection_matrix);
|
||||||
|
|
||||||
|
return output;
|
||||||
|
}
|
||||||
|
|
||||||
|
[shader("pixel")]
|
||||||
|
FragmentShaderOutput main_fragment(VertexShaderOutput input) {
|
||||||
|
var output: FragmentShaderOutput;
|
||||||
|
|
||||||
|
output.color = input.is_collider != 0 ? float4(1, 0, 0, 1) : float4(0, 0, 0, 0);
|
||||||
|
|
||||||
|
return output;
|
||||||
|
}
|
||||||
@@ -0,0 +1,90 @@
|
|||||||
|
struct Per_Frame_Data_std140_0
|
||||||
|
{
|
||||||
|
@align(16) drag_start_0 : vec2<i32>,
|
||||||
|
@align(8) mouse_0 : vec2<i32>,
|
||||||
|
@align(16) grid_offset_0 : vec2<f32>,
|
||||||
|
@align(8) grid_width_0 : u32,
|
||||||
|
@align(4) map_width_0 : u32,
|
||||||
|
@align(16) grid_height_0 : u32,
|
||||||
|
};
|
||||||
|
|
||||||
|
@binding(1) @group(1) var<uniform> per_frame_0 : Per_Frame_Data_std140_0;
|
||||||
|
@binding(0) @group(0) var grid_texture_0 : texture_2d<u32>;
|
||||||
|
|
||||||
|
struct _MatrixStorage_float4x4_ColMajorstd140_0
|
||||||
|
{
|
||||||
|
@align(16) data_0 : array<vec4<f32>, i32(4)>,
|
||||||
|
};
|
||||||
|
|
||||||
|
@binding(0) @group(1) var<uniform> view_projection_matrix_0 : _MatrixStorage_float4x4_ColMajorstd140_0;
|
||||||
|
struct VertexShaderOutput_0
|
||||||
|
{
|
||||||
|
@builtin(position) pos_0 : vec4<f32>,
|
||||||
|
@location(0) is_collider_0 : u32,
|
||||||
|
};
|
||||||
|
|
||||||
|
@vertex
|
||||||
|
fn main_vertex(@builtin(vertex_index) vertex_index_0 : u32, @builtin(instance_index) instance_index_0 : u32) -> VertexShaderOutput_0
|
||||||
|
{
|
||||||
|
var output_0 : VertexShaderOutput_0;
|
||||||
|
const _S1 : vec2<f32> = vec2<f32>(0.0f, 0.0f);
|
||||||
|
var vertex_pos_0 : vec2<f32>;
|
||||||
|
switch(vertex_index_0)
|
||||||
|
{
|
||||||
|
case u32(0):
|
||||||
|
{
|
||||||
|
vertex_pos_0 = vec2<f32>(-0.5f, -0.5f);
|
||||||
|
}
|
||||||
|
case u32(1):
|
||||||
|
{
|
||||||
|
vertex_pos_0 = vec2<f32>(0.5f, 0.5f);
|
||||||
|
}
|
||||||
|
case u32(2):
|
||||||
|
{
|
||||||
|
vertex_pos_0 = vec2<f32>(0.5f, -0.5f);
|
||||||
|
}
|
||||||
|
case u32(3):
|
||||||
|
{
|
||||||
|
vertex_pos_0 = vec2<f32>(-0.5f, 0.5f);
|
||||||
|
}
|
||||||
|
default :
|
||||||
|
{
|
||||||
|
vertex_pos_0 = _S1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var _S2 : u32 = instance_index_0 % (per_frame_0.map_width_0 - u32(1));
|
||||||
|
var _S3 : u32 = instance_index_0 / (per_frame_0.map_width_0 - u32(1));
|
||||||
|
var _S4 : vec2<u32> = vec2<u32>(_S2, _S3);
|
||||||
|
var _S5 : vec3<i32> = vec3<i32>(vec3<u32>(_S4, u32(0)));
|
||||||
|
output_0.is_collider_0 = (textureLoad((grid_texture_0), ((_S5)).xy, ((_S5)).z).x);
|
||||||
|
output_0.pos_0 = (((mat4x4<f32>(view_projection_matrix_0.data_0[i32(0)][i32(0)], view_projection_matrix_0.data_0[i32(1)][i32(0)], view_projection_matrix_0.data_0[i32(2)][i32(0)], view_projection_matrix_0.data_0[i32(3)][i32(0)], view_projection_matrix_0.data_0[i32(0)][i32(1)], view_projection_matrix_0.data_0[i32(1)][i32(1)], view_projection_matrix_0.data_0[i32(2)][i32(1)], view_projection_matrix_0.data_0[i32(3)][i32(1)], view_projection_matrix_0.data_0[i32(0)][i32(2)], view_projection_matrix_0.data_0[i32(1)][i32(2)], view_projection_matrix_0.data_0[i32(2)][i32(2)], view_projection_matrix_0.data_0[i32(3)][i32(2)], view_projection_matrix_0.data_0[i32(0)][i32(3)], view_projection_matrix_0.data_0[i32(1)][i32(3)], view_projection_matrix_0.data_0[i32(2)][i32(3)], view_projection_matrix_0.data_0[i32(3)][i32(3)])) * (vec4<f32>(vec2<f32>(_S4) + vertex_pos_0, 0.0f, 1.0f))));
|
||||||
|
return output_0;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct FragmentShaderOutput_0
|
||||||
|
{
|
||||||
|
@location(0) color_0 : vec4<f32>,
|
||||||
|
};
|
||||||
|
|
||||||
|
struct pixelInput_0
|
||||||
|
{
|
||||||
|
@location(0) is_collider_1 : u32,
|
||||||
|
};
|
||||||
|
|
||||||
|
@fragment
|
||||||
|
fn main_fragment( _S6 : pixelInput_0, @builtin(position) pos_1 : vec4<f32>) -> FragmentShaderOutput_0
|
||||||
|
{
|
||||||
|
var output_1 : FragmentShaderOutput_0;
|
||||||
|
var _S7 : vec4<f32>;
|
||||||
|
if((_S6.is_collider_1) != u32(0))
|
||||||
|
{
|
||||||
|
_S7 = vec4<f32>(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
_S7 = vec4<f32>(0.0f, 0.0f, 0.0f, 0.0f);
|
||||||
|
}
|
||||||
|
output_1.color_0 = _S7;
|
||||||
|
return output_1;
|
||||||
|
}
|
||||||
|
|
||||||
Reference in New Issue
Block a user