[Mesa-dev] [PATCH 4/4] st/vdpau: use matrix filter to blur/sharpen video
Maarten Lankhorst
m.b.lankhorst at gmail.com
Mon Feb 13 00:06:47 PST 2012
Op 08-02-12 20:37, Christian König schreef:
> Signed-off-by: Christian König<deathsimple at vodafone.de>
> ---
> src/gallium/state_trackers/vdpau/mixer.c | 78 ++++++++++++++++++++--
> src/gallium/state_trackers/vdpau/query.c | 1 +
> src/gallium/state_trackers/vdpau/vdpau_private.h | 9 ++-
> 3 files changed, 81 insertions(+), 7 deletions(-)
>
> diff --git a/src/gallium/state_trackers/vdpau/mixer.c b/src/gallium/state_trackers/vdpau/mixer.c
> index 87ebe97..5ce40d6 100644
> --- a/src/gallium/state_trackers/vdpau/mixer.c
> +++ b/src/gallium/state_trackers/vdpau/mixer.c
> @@ -93,7 +93,10 @@ vlVdpVideoMixerCreate(VdpDevice device,
> case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L9:
> case VDP_VIDEO_MIXER_FEATURE_INVERSE_TELECINE:
> case VDP_VIDEO_MIXER_FEATURE_LUMA_KEY:
> + break;
> +
> case VDP_VIDEO_MIXER_FEATURE_SHARPNESS:
> + vmixer->sharpness.supported = true;
> break;
>
> case VDP_VIDEO_MIXER_FEATURE_NOISE_REDUCTION:
> @@ -142,7 +145,6 @@ vlVdpVideoMixerCreate(VdpDevice device,
> }
> vmixer->luma_key_min = 0.f;
> vmixer->luma_key_max = 1.f;
> - vmixer->sharpness = 0.f;
>
> return VDP_STATUS_OK;
>
> @@ -253,6 +255,10 @@ VdpStatus vlVdpVideoMixerRender(VdpVideoMixer mixer,
> vl_median_filter_render(vmixer->noise_reduction.filter,
> dst->sampler_view, dst->surface);
>
> + if (vmixer->sharpness.filter)
> + vl_matrix_filter_render(vmixer->sharpness.filter,
> + dst->sampler_view, dst->surface);
> +
> return VDP_STATUS_OK;
> }
>
> @@ -282,6 +288,52 @@ vlVdpVideoMixerUpdateNoiseReductionFilter(vlVdpVideoMixer *vmixer)
> }
> }
>
> +static void
> +vlVdpVideoMixerUpdateSharpnessFilter(vlVdpVideoMixer *vmixer)
> +{
> + assert(vmixer);
> +
> + /* if present remove the old filter first */
> + if (vmixer->sharpness.filter) {
> + vl_matrix_filter_cleanup(vmixer->sharpness.filter);
> + FREE(vmixer->sharpness.filter);
> + vmixer->sharpness.filter = NULL;
> + }
> +
> + /* and create a new filter as needed */
> + if (vmixer->sharpness.enabled&& vmixer->sharpness.value != 0.0f) {
> + float matrix[9];
> + unsigned i;
> +
> + if (vmixer->sharpness.value> 0.0f) {
> + matrix[0] = -1.0f; matrix[1] = -1.0f; matrix[2] = -1.0f;
> + matrix[3] = -1.0f; matrix[4] = 8.0f; matrix[5] = -1.0f;
> + matrix[6] = -1.0f; matrix[7] = -1.0f; matrix[8] = -1.0f;
> +
> + for (i = 0; i< 9; ++i)
> + matrix[i] *= vmixer->sharpness.value;
> +
> + matrix[4] += 1.0f;
> +
> + } else {
> + matrix[0] = 1.0f; matrix[1] = 2.0f; matrix[2] = 1.0f;
> + matrix[3] = 2.0f; matrix[4] = 4.0f; matrix[5] = 2.0f;
> + matrix[6] = 1.0f; matrix[7] = 2.0f; matrix[8] = 1.0f;
> +
> + for (i = 0; i< 9; ++i)
> + matrix[i] *= fabsf(vmixer->sharpness.value) / 16.0f;
> +
> + matrix[4] += 1.0f - fabsf(vmixer->sharpness.value);
> + }
> +
> + vmixer->sharpness.filter = MALLOC(sizeof(struct vl_matrix_filter));
> + vl_matrix_filter_init(vmixer->sharpness.filter,
> + vmixer->device->context->pipe,
> + vmixer->video_width, vmixer->video_height,
> + 3, 3, matrix);
> + }
> +}
> +
> /**
> * Retrieve whether features were requested at creation time.
> */
> @@ -317,10 +369,13 @@ vlVdpVideoMixerGetFeatureSupport(VdpVideoMixer mixer,
> case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L9:
> case VDP_VIDEO_MIXER_FEATURE_INVERSE_TELECINE:
> case VDP_VIDEO_MIXER_FEATURE_LUMA_KEY:
> - case VDP_VIDEO_MIXER_FEATURE_SHARPNESS:
> feature_supports[i] = false;
> break;
>
> + case VDP_VIDEO_MIXER_FEATURE_SHARPNESS:
> + feature_supports[i] = vmixer->sharpness.supported;
> + break;
> +
> case VDP_VIDEO_MIXER_FEATURE_NOISE_REDUCTION:
> feature_supports[i] = vmixer->noise_reduction.supported;
> break;
> @@ -368,7 +423,11 @@ vlVdpVideoMixerSetFeatureEnables(VdpVideoMixer mixer,
> case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L9:
> case VDP_VIDEO_MIXER_FEATURE_INVERSE_TELECINE:
> case VDP_VIDEO_MIXER_FEATURE_LUMA_KEY:
> + break;
> +
> case VDP_VIDEO_MIXER_FEATURE_SHARPNESS:
> + vmixer->sharpness.enabled = feature_enables[i];
> + vlVdpVideoMixerUpdateSharpnessFilter(vmixer);
> break;
>
> case VDP_VIDEO_MIXER_FEATURE_NOISE_REDUCTION:
> @@ -419,12 +478,14 @@ vlVdpVideoMixerGetFeatureEnables(VdpVideoMixer mixer,
> case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L9:
> case VDP_VIDEO_MIXER_FEATURE_INVERSE_TELECINE:
> case VDP_VIDEO_MIXER_FEATURE_LUMA_KEY:
> + break;
> +
> case VDP_VIDEO_MIXER_FEATURE_SHARPNESS:
> + feature_enables[i] = vmixer->sharpness.enabled;
> break;
>
> case VDP_VIDEO_MIXER_FEATURE_NOISE_REDUCTION:
> - vmixer->noise_reduction.enabled = feature_enables[i];
> - vlVdpVideoMixerUpdateNoiseReductionFilter(vmixer);
> + feature_enables[i] = vmixer->noise_reduction.enabled;
> break;
So you did notice it was wrong in previous patch. ;)
> default:
> @@ -500,12 +561,17 @@ vlVdpVideoMixerSetAttributeValues(VdpVideoMixer mixer,
> return VDP_STATUS_INVALID_VALUE;
> vmixer->luma_key_max = val;
> break;
> +
> case VDP_VIDEO_MIXER_ATTRIBUTE_SHARPNESS_LEVEL:
> +
> val = *(float*)attribute_values[i];
> if (val< -1.f || val> 1.f)
> return VDP_STATUS_INVALID_VALUE;
> - vmixer->sharpness = val;
> +
> + vmixer->sharpness.value = val;
> + vlVdpVideoMixerUpdateSharpnessFilter(vmixer);
> break;
> +
> case VDP_VIDEO_MIXER_ATTRIBUTE_SKIP_CHROMA_DEINTERLACE:
> if (*(uint8_t*)attribute_values[i]> 1)
> return VDP_STATUS_INVALID_VALUE;
> @@ -602,7 +668,7 @@ vlVdpVideoMixerGetAttributeValues(VdpVideoMixer mixer,
> *(float*)attribute_values[i] = vmixer->luma_key_max;
> break;
> case VDP_VIDEO_MIXER_ATTRIBUTE_SHARPNESS_LEVEL:
> - *(float*)attribute_values[i] = vmixer->sharpness;
> + *(float*)attribute_values[i] = vmixer->sharpness.value;
> break;
> case VDP_VIDEO_MIXER_ATTRIBUTE_SKIP_CHROMA_DEINTERLACE:
> *(uint8_t*)attribute_values[i] = vmixer->skip_chroma_deint;
> diff --git a/src/gallium/state_trackers/vdpau/query.c b/src/gallium/state_trackers/vdpau/query.c
> index 4110a87..8bb2078 100644
> --- a/src/gallium/state_trackers/vdpau/query.c
> +++ b/src/gallium/state_trackers/vdpau/query.c
> @@ -308,6 +308,7 @@ vlVdpVideoMixerQueryFeatureSupport(VdpDevice device, VdpVideoMixerFeature featur
> return VDP_STATUS_INVALID_POINTER;
>
> switch (feature) {
> + case VDP_VIDEO_MIXER_FEATURE_SHARPNESS:
> case VDP_VIDEO_MIXER_FEATURE_NOISE_REDUCTION:
> *is_supported = VDP_TRUE;
> break;
> diff --git a/src/gallium/state_trackers/vdpau/vdpau_private.h b/src/gallium/state_trackers/vdpau/vdpau_private.h
> index 82e6a8e..f47c0bf 100644
> --- a/src/gallium/state_trackers/vdpau/vdpau_private.h
> +++ b/src/gallium/state_trackers/vdpau/vdpau_private.h
> @@ -39,6 +39,7 @@
> #include "util/u_debug.h"
> #include "util/u_rect.h"
> #include "vl/vl_compositor.h"
> +#include "vl/vl_matrix_filter.h"
> #include "vl/vl_median_filter.h"
>
> #include "vl_winsys.h"
> @@ -314,10 +315,16 @@ typedef struct
> struct vl_median_filter *filter;
> } noise_reduction;
>
> + struct {
> + bool supported, enabled;
> + float value;
> + struct vl_matrix_filter *filter;
> + } sharpness;
> +
> unsigned video_width, video_height;
> enum pipe_video_chroma_format chroma_format;
> unsigned max_layers, skip_chroma_deint, custom_csc;
> - float luma_key_min, luma_key_max, sharpness;
> + float luma_key_min, luma_key_max;
> float csc[16];
> } vlVdpVideoMixer;
>
Wouldn't it make more sense to only have a single matrix filter with
separate matrices for each filter so you only have to run a single
shader? And again, why dynamically allocate the filter.. make the
destructor function handle NULL correctly where needed.
~Maarten
More information about the mesa-dev
mailing list