Commit 199a2f40 authored by Urvang Joshi's avatar Urvang Joshi

Palette: Don't use top-right pixel for context of color indices.

This reduces the complexity in a number of ways:
- We need just 3 neighbors instead of 4.
- Possible contexts reduce from 16 to 5.
- On hardware side, getting the contexts for a whole block will be more
parallelizable.

At the same time, compression performance improves very slightly:
- Screen-content set (videos) (Google): BDRate improved by 0.32
- screenshots set (images) (AWCY): PSNR improved by 0.62:
https://arewecompressedyet.com/?job=palette_withTR2%402017-01-27T21%3A30%3A28.890Z&job=palette_noTR2%402017-01-27T21%3A41%3A34.312Z

Change-Id: Ie84ca32f05d55ad481a51c2d3abc579468597189
parent 79c0f32c
This diff is collapsed.
......@@ -32,7 +32,7 @@ extern "C" {
#endif // CONFIG_EXT_INTER
#if CONFIG_PALETTE
#define PALETTE_COLOR_CONTEXTS 16
#define PALETTE_COLOR_CONTEXTS 5
#define PALETTE_MAX_SIZE 8
#define PALETTE_BLOCK_SIZES (BLOCK_LARGEST - BLOCK_8X8 + 1)
#define PALETTE_Y_MODE_CONTEXTS 3
......@@ -438,10 +438,10 @@ static INLINE int av1_ceil_log2(int n) {
#if CONFIG_PALETTE
// Returns the context for palette color index at row 'r' and column 'c',
// along with the 'color_order' of neighbors and the 'color_idx'.
// The 'color_map' is a 2D array with the given 'width' and 'stride'.
int av1_get_palette_color_context(const uint8_t *color_map, int width,
int stride, int r, int c, int palette_size,
uint8_t *color_order, int *color_idx);
// The 'color_map' is a 2D array with the given 'stride'.
int av1_get_palette_color_context(const uint8_t *color_map, int stride, int r,
int c, int palette_size, uint8_t *color_order,
int *color_idx);
#endif // CONFIG_PALETTE
#ifdef __cplusplus
......
......@@ -329,7 +329,7 @@ void av1_decode_palette_tokens(MACROBLOCKD *const xd, int plane,
for (i = 0; i < rows; ++i) {
for (j = (i == 0 ? 1 : 0); j < cols; ++j) {
const int color_ctx = av1_get_palette_color_context(
color_map, cols, plane_block_width, i, j, n, color_order, NULL);
color_map, plane_block_width, i, j, n, color_order, NULL);
const int color_idx = aom_read_tree(r, av1_palette_color_tree[n - 2],
prob[n - 2][color_ctx], ACCT_STR);
assert(color_idx >= 0 && color_idx < n);
......
......@@ -2429,7 +2429,7 @@ static int rd_pick_palette_intra_sby(const AV1_COMP *const cpi, MACROBLOCK *x,
for (j = (i == 0 ? 1 : 0); j < cols; ++j) {
int color_idx;
const int color_ctx = av1_get_palette_color_context(
color_map, cols, block_width, i, j, k, color_order, &color_idx);
color_map, block_width, i, j, k, color_order, &color_idx);
assert(color_idx >= 0 && color_idx < k);
palette_mode_cost +=
cpi->palette_y_color_cost[k - 2][color_ctx][color_idx];
......@@ -4510,9 +4510,8 @@ static void rd_pick_palette_intra_sbuv(const AV1_COMP *const cpi, MACROBLOCK *x,
for (i = 0; i < rows; ++i) {
for (j = (i == 0 ? 1 : 0); j < cols; ++j) {
int color_idx;
const int color_ctx =
av1_get_palette_color_context(color_map, cols, plane_block_width,
i, j, n, color_order, &color_idx);
const int color_ctx = av1_get_palette_color_context(
color_map, plane_block_width, i, j, n, color_order, &color_idx);
assert(color_idx >= 0 && color_idx < n);
this_rate += cpi->palette_uv_color_cost[n - 2][color_ctx][color_idx];
}
......
......@@ -408,9 +408,8 @@ void av1_tokenize_palette_sb(const AV1_COMP *cpi,
for (i = 0; i < rows; ++i) {
for (j = (i == 0 ? 1 : 0); j < cols; ++j) {
int color_new_idx;
const int color_ctx =
av1_get_palette_color_context(color_map, cols, plane_block_width, i,
j, n, color_order, &color_new_idx);
const int color_ctx = av1_get_palette_color_context(
color_map, plane_block_width, i, j, n, color_order, &color_new_idx);
assert(color_new_idx >= 0 && color_new_idx < n);
if (dry_run == DRY_RUN_COSTCOEFFS)
this_rate += cpi->palette_y_color_cost[n - 2][color_ctx][color_new_idx];
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment