v3dv: enable smooth line rendering

This is based on a lowering that we are already using in the OpenGL
driver.

Reviewed-by: Iago Toral Quiroga <itoral@igalia.com>
Signed-off-by: Juan A. Suarez Romero <jasuarez@igalia.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/28171>
This commit is contained in:
Juan A. Suarez Romero 2024-03-14 22:19:02 +01:00 committed by Marge Bot
parent f5d4242928
commit 4f6f2cea6a
6 changed files with 65 additions and 2 deletions

View file

@ -27,6 +27,21 @@
#include "vk_common_entrypoints.h"
#include "vk_util.h"
float
v3dv_get_aa_line_width(struct v3dv_pipeline *pipeline,
struct v3dv_cmd_buffer *buffer)
{
float width = buffer->state.dynamic.line_width;
/* If line smoothing is enabled then we want to add some extra pixels to
* the width in order to have some semi-transparent edges.
*/
if (pipeline->line_smooth)
width = floorf(M_SQRT2 * width) + 3;
return width;
}
void
v3dv_job_add_bo(struct v3dv_job *job, struct v3dv_bo *bo)
{

View file

@ -394,7 +394,7 @@ get_features(const struct v3dv_physical_device *physical_device,
/* VK_EXT_line_rasterization */
.rectangularLines = true,
.bresenhamLines = true,
.smoothLines = false,
.smoothLines = true,
.stippledRectangularLines = false,
.stippledBresenhamLines = false,
.stippledSmoothLines = false,

View file

@ -1095,6 +1095,32 @@ static const enum pipe_logicop vk_to_pipe_logicop[] = {
[VK_LOGIC_OP_SET] = PIPE_LOGICOP_SET,
};
static bool
enable_line_smooth(uint8_t topology,
const VkPipelineRasterizationStateCreateInfo *rs_info)
{
if (!rs_info || rs_info->rasterizerDiscardEnable)
return false;
const VkPipelineRasterizationLineStateCreateInfoKHR *ls_info =
vk_find_struct_const(rs_info->pNext,
PIPELINE_RASTERIZATION_LINE_STATE_CREATE_INFO_KHR);
if (!ls_info)
return false;
switch(topology) {
case MESA_PRIM_LINES:
case MESA_PRIM_LINE_LOOP:
case MESA_PRIM_LINE_STRIP:
case MESA_PRIM_LINES_ADJACENCY:
case MESA_PRIM_LINE_STRIP_ADJACENCY:
return ls_info->lineRasterizationMode == VK_LINE_RASTERIZATION_MODE_RECTANGULAR_SMOOTH_KHR;
default:
return false;
}
}
static void
pipeline_populate_v3d_fs_key(struct v3d_fs_key *key,
const VkGraphicsPipelineCreateInfo *pCreateInfo,
@ -1159,6 +1185,8 @@ pipeline_populate_v3d_fs_key(struct v3d_fs_key *key,
key->sample_alpha_to_one = ms_info->alphaToOneEnable;
}
key->line_smoothing = enable_line_smooth(topology, pCreateInfo->pRasterizationState);
/* This is intended for V3D versions before 4.1, otherwise we just use the
* tile buffer load/store swap R/B bit.
*/
@ -1950,6 +1978,8 @@ pipeline_populate_graphics_key(struct v3dv_pipeline *pipeline,
memset(key, 0, sizeof(*key));
key->line_smooth = pipeline->line_smooth;
const bool raster_enabled =
pCreateInfo->pRasterizationState &&
!pCreateInfo->pRasterizationState->rasterizerDiscardEnable;
@ -2950,6 +2980,7 @@ pipeline_init(struct v3dv_pipeline *pipeline,
pipeline_set_sample_mask(pipeline, ms_info);
pipeline_set_sample_rate_shading(pipeline, ms_info);
pipeline->line_smooth = enable_line_smooth(pipeline->topology, rs_info);
pipeline->primitive_restart =
pCreateInfo->pInputAssemblyState->primitiveRestartEnable;

View file

@ -339,6 +339,7 @@ struct v3dv_pipeline_key {
uint8_t f32_color_rb;
uint32_t va_swap_rb_mask;
bool has_multiview;
bool line_smooth;
};
struct v3dv_pipeline_cache_stats {
@ -2297,6 +2298,8 @@ struct v3dv_pipeline {
enum mesa_prim topology;
bool line_smooth;
struct v3dv_pipeline_shared_data *shared_data;
/* It is the combined stages sha1, layout sha1, plus the pipeline key sha1. */
@ -2680,6 +2683,10 @@ v3dv_update_image_layout(struct v3dv_device *device,
bool disjoint,
const VkImageDrmFormatModifierExplicitCreateInfoEXT *explicit_mod_info);
float
v3dv_get_aa_line_width(struct v3dv_pipeline *pipeline,
struct v3dv_cmd_buffer *buffer);
#if DETECT_OS_ANDROID
VkResult
v3dv_gralloc_to_drm_explicit_layout(struct u_gralloc *gralloc,

View file

@ -661,6 +661,15 @@ v3dv_write_uniforms_wg_offsets(struct v3dv_cmd_buffer *cmd_buffer,
cl_aligned_u32(&uniforms, job->cmd_buffer->state.draw_id);
break;
case QUNIFORM_LINE_WIDTH:
cl_aligned_u32(&uniforms, job->cmd_buffer->state.dynamic.line_width);
break;
case QUNIFORM_AA_LINE_WIDTH:
cl_aligned_u32(&uniforms,
v3dv_get_aa_line_width(pipeline, job->cmd_buffer));
break;
default:
unreachable("unsupported quniform_contents uniform type\n");
}

View file

@ -1551,7 +1551,8 @@ v3dX(cmd_buffer_emit_line_width)(struct v3dv_cmd_buffer *cmd_buffer)
v3dv_return_if_oom(cmd_buffer, NULL);
cl_emit(&job->bcl, LINE_WIDTH, line) {
line.line_width = cmd_buffer->state.dynamic.line_width;
line.line_width = v3dv_get_aa_line_width(cmd_buffer->state.gfx.pipeline,
cmd_buffer);
}
cmd_buffer->state.dirty &= ~V3DV_CMD_DIRTY_LINE_WIDTH;