diff options
author | Krzesimir Nowak <[email protected]> | 2015-09-10 14:15:57 +0200 |
---|---|---|
committer | Brian Paul <[email protected]> | 2015-09-10 09:45:14 -0600 |
commit | d71a3be86008c275b5902de7759385643546a210 (patch) | |
tree | 5bd5a0ec71a4e9fafa550e3fa75050285cac38f7 | |
parent | ac3637dda04fe1315f19099bd142e4f8f6754b1d (diff) |
softpipe: Add functions for computing relative mipmap level
These functions will be used by textureQueryLod.
v2:
- renamed mip_level_* funcs to mip_rel_level_* to indicate that
these functions return mip level relative to base level and
documented them
- renamed a level member in sp_filter_funcs struct to relative_level
- changed mip_rel_level_none and mip_rel_level_nearest to return mip
level relative to base level, mip_rel_level_linear already did
that
- documented clamp_lod function
Reviewed-by: Brian Paul <[email protected]>
-rw-r--r-- | src/gallium/drivers/softpipe/sp_tex_sample.c | 113 | ||||
-rw-r--r-- | src/gallium/drivers/softpipe/sp_tex_sample.h | 7 |
2 files changed, 120 insertions, 0 deletions
diff --git a/src/gallium/drivers/softpipe/sp_tex_sample.c b/src/gallium/drivers/softpipe/sp_tex_sample.c index d7b656e4c97..4a4cddfd308 100644 --- a/src/gallium/drivers/softpipe/sp_tex_sample.c +++ b/src/gallium/drivers/softpipe/sp_tex_sample.c @@ -1936,6 +1936,43 @@ get_gather_component(const float lod_in[TGSI_QUAD_SIZE]) return (*(unsigned int *)lod_in) & 0x3; } +/** + * Clamps given lod to both lod limits and mip level limits. Clamping to the + * latter limits is done so that lod is relative to the first (base) level. + */ +static void +clamp_lod(const struct sp_sampler_view *sp_sview, + const struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float clamped[TGSI_QUAD_SIZE]) +{ + const float min_lod = sp_samp->base.min_lod; + const float max_lod = sp_samp->base.max_lod; + const float min_level = sp_sview->base.u.tex.first_level; + const float max_level = sp_sview->base.u.tex.last_level; + int i; + + for (i = 0; i < TGSI_QUAD_SIZE; i++) { + float cl = lod[i]; + + cl = CLAMP(cl, min_lod, max_lod); + cl = CLAMP(cl, 0, max_level - min_level); + clamped[i] = cl; + } +} + +/** + * Get mip level relative to base level for linear mip filter + */ +static void +mip_rel_level_linear(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]) +{ + clamp_lod(sp_sview, sp_samp, lod, level); +} + static void mip_filter_linear(struct sp_sampler_view *sp_sview, struct sp_sampler *sp_samp, @@ -1999,6 +2036,25 @@ mip_filter_linear(struct sp_sampler_view *sp_sview, /** + * Get mip level relative to base level for nearest mip filter + */ +static void +mip_rel_level_nearest(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]) +{ + int j; + + clamp_lod(sp_sview, sp_samp, lod, level); + for (j = 0; j < TGSI_QUAD_SIZE; j++) + /* TODO: It should rather be: + * level[j] = ceil(level[j] + 0.5F) - 1.0F; + */ + level[j] = (int)(level[j] + 0.5F); +} + +/** * Compute nearest mipmap level from texcoords. * Then sample the texture level for four elements of a quad. * \param c0 the LOD bias factors, or absolute LODs (depending on control) @@ -2049,6 +2105,22 @@ mip_filter_nearest(struct sp_sampler_view *sp_sview, } +/** + * Get mip level relative to base level for none mip filter + */ +static void +mip_rel_level_none(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]) +{ + int j; + + for (j = 0; j < TGSI_QUAD_SIZE; j++) { + level[j] = 0; + } +} + static void mip_filter_none(struct sp_sampler_view *sp_sview, struct sp_sampler *sp_samp, @@ -2087,6 +2159,18 @@ mip_filter_none(struct sp_sampler_view *sp_sview, } +/** + * Get mip level relative to base level for none mip filter + */ +static void +mip_rel_level_none_no_filter_select(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]) +{ + mip_rel_level_none(sp_sview, sp_samp, lod, level); +} + static void mip_filter_none_no_filter_select(struct sp_sampler_view *sp_sview, struct sp_sampler *sp_samp, @@ -2340,6 +2424,18 @@ img_filter_2d_ewa(struct sp_sampler_view *sp_sview, /** + * Get mip level relative to base level for linear mip filter + */ +static void +mip_rel_level_linear_aniso(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]) +{ + mip_rel_level_linear(sp_sview, sp_samp, lod, level); +} + +/** * Sample 2D texture using an anisotropic filter. */ static void @@ -2450,6 +2546,17 @@ mip_filter_linear_aniso(struct sp_sampler_view *sp_sview, } } +/** + * Get mip level relative to base level for linear mip filter + */ +static void +mip_rel_level_linear_2d_linear_repeat_POT(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]) +{ + mip_rel_level_linear(sp_sview, sp_samp, lod, level); +} /** * Specialized version of mip_filter_linear with hard-wired calls to @@ -2516,26 +2623,32 @@ mip_filter_linear_2d_linear_repeat_POT( } static const struct sp_filter_funcs funcs_linear = { + mip_rel_level_linear, mip_filter_linear }; static const struct sp_filter_funcs funcs_nearest = { + mip_rel_level_nearest, mip_filter_nearest }; static const struct sp_filter_funcs funcs_none = { + mip_rel_level_none, mip_filter_none }; static const struct sp_filter_funcs funcs_none_no_filter_select = { + mip_rel_level_none_no_filter_select, mip_filter_none_no_filter_select }; static const struct sp_filter_funcs funcs_linear_aniso = { + mip_rel_level_linear_aniso, mip_filter_linear_aniso }; static const struct sp_filter_funcs funcs_linear_2d_linear_repeat_POT = { + mip_rel_level_linear_2d_linear_repeat_POT, mip_filter_linear_2d_linear_repeat_POT }; diff --git a/src/gallium/drivers/softpipe/sp_tex_sample.h b/src/gallium/drivers/softpipe/sp_tex_sample.h index 2e3976d8034..72b4a1ac3e8 100644 --- a/src/gallium/drivers/softpipe/sp_tex_sample.h +++ b/src/gallium/drivers/softpipe/sp_tex_sample.h @@ -86,6 +86,12 @@ typedef void (*mip_filter_func)(struct sp_sampler_view *sp_sview, const struct filter_args *args, float rgba[TGSI_NUM_CHANNELS][TGSI_QUAD_SIZE]); + +typedef void (*mip_level_func)(struct sp_sampler_view *sp_sview, + struct sp_sampler *sp_samp, + const float lod[TGSI_QUAD_SIZE], + float level[TGSI_QUAD_SIZE]); + typedef void (*fetch_func)(struct sp_sampler_view *sp_sview, const int i[TGSI_QUAD_SIZE], const int j[TGSI_QUAD_SIZE], const int k[TGSI_QUAD_SIZE], @@ -116,6 +122,7 @@ struct sp_sampler_view }; struct sp_filter_funcs { + mip_level_func relative_level; mip_filter_func filter; }; |