Replace scaling byte with explicit display size
If the intended display size is different than the size the frame is coded at, then send that size explicitly in the bitstream. Adds a new bit to the frame header to indicate whether the extra size fields are present. Change-Id: I525c66f22d207efaf1e5f903c6a2a91b80245854
This commit is contained in:
@@ -169,10 +169,10 @@ typedef struct VP9Common {
|
|||||||
|
|
||||||
int Width;
|
int Width;
|
||||||
int Height;
|
int Height;
|
||||||
|
int display_width;
|
||||||
|
int display_height;
|
||||||
int last_width;
|
int last_width;
|
||||||
int last_height;
|
int last_height;
|
||||||
int horiz_scale;
|
|
||||||
int vert_scale;
|
|
||||||
|
|
||||||
YUV_TYPE clr_type;
|
YUV_TYPE clr_type;
|
||||||
CLAMP_TYPE clamp_type;
|
CLAMP_TYPE clamp_type;
|
||||||
|
|||||||
@@ -1275,12 +1275,13 @@ int vp9_decode_frame(VP9D_COMP *pbi, const unsigned char **p_data_end) {
|
|||||||
if (data_end - data < 3) {
|
if (data_end - data < 3) {
|
||||||
vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME, "Truncated packet");
|
vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME, "Truncated packet");
|
||||||
} else {
|
} else {
|
||||||
|
int scaling_active;
|
||||||
pc->last_frame_type = pc->frame_type;
|
pc->last_frame_type = pc->frame_type;
|
||||||
pc->frame_type = (FRAME_TYPE)(data[0] & 1);
|
pc->frame_type = (FRAME_TYPE)(data[0] & 1);
|
||||||
pc->version = (data[0] >> 1) & 7;
|
pc->version = (data[0] >> 1) & 7;
|
||||||
pc->show_frame = (data[0] >> 4) & 1;
|
pc->show_frame = (data[0] >> 4) & 1;
|
||||||
first_partition_length_in_bytes =
|
scaling_active = (data[0] >> 5) & 1;
|
||||||
(data[0] | (data[1] << 8) | (data[2] << 16)) >> 5;
|
first_partition_length_in_bytes = data[1] | (data[2] << 8);
|
||||||
|
|
||||||
if (!read_is_valid(data, first_partition_length_in_bytes, data_end))
|
if (!read_is_valid(data, first_partition_length_in_bytes, data_end))
|
||||||
vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
|
vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
|
||||||
@@ -1310,14 +1311,20 @@ int vp9_decode_frame(VP9D_COMP *pbi, const unsigned char **p_data_end) {
|
|||||||
* if we have enough data. Otherwise we will end up with the wrong
|
* if we have enough data. Otherwise we will end up with the wrong
|
||||||
* size.
|
* size.
|
||||||
*/
|
*/
|
||||||
if (data + 5 < data_end) {
|
if (scaling_active && data + 4 < data_end) {
|
||||||
pc->Width = read_le16(data);
|
pc->display_width = read_le16(data + 0);
|
||||||
pc->Height = read_le16(data + 2);
|
pc->display_height = read_le16(data + 2);
|
||||||
|
data += 4;
|
||||||
pc->horiz_scale = data[4] >> 4;
|
}
|
||||||
pc->vert_scale = data[4] & 0x0F;
|
if (data + 4 < data_end) {
|
||||||
|
pc->Width = read_le16(data + 0);
|
||||||
|
pc->Height = read_le16(data + 2);
|
||||||
|
data += 4;
|
||||||
|
}
|
||||||
|
if (!scaling_active) {
|
||||||
|
pc->display_width = pc->Width;
|
||||||
|
pc->display_height = pc->Height;
|
||||||
}
|
}
|
||||||
data += 5;
|
|
||||||
|
|
||||||
if (width != pc->Width || height != pc->Height) {
|
if (width != pc->Width || height != pc->Height) {
|
||||||
if (pc->Width <= 0) {
|
if (pc->Width <= 0) {
|
||||||
|
|||||||
@@ -2270,7 +2270,18 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
|
|||||||
{
|
{
|
||||||
int v;
|
int v;
|
||||||
|
|
||||||
// support arbitrary resolutions
|
if (pc->Width != pc->display_width || pc->Height != pc->display_height) {
|
||||||
|
v = pc->display_width;
|
||||||
|
cx_data[0] = v;
|
||||||
|
cx_data[1] = v >> 8;
|
||||||
|
|
||||||
|
v = pc->display_height;
|
||||||
|
cx_data[2] = v;
|
||||||
|
cx_data[3] = v >> 8;
|
||||||
|
cx_data += 4;
|
||||||
|
extra_bytes_packed += 4;
|
||||||
|
}
|
||||||
|
|
||||||
v = pc->Width;
|
v = pc->Width;
|
||||||
cx_data[0] = v;
|
cx_data[0] = v;
|
||||||
cx_data[1] = v >> 8;
|
cx_data[1] = v >> 8;
|
||||||
@@ -2279,11 +2290,8 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
|
|||||||
cx_data[2] = v;
|
cx_data[2] = v;
|
||||||
cx_data[3] = v >> 8;
|
cx_data[3] = v >> 8;
|
||||||
|
|
||||||
// use a separate byte to store the scale factors, each ranging 0-15
|
extra_bytes_packed += 4;
|
||||||
cx_data[4] = (pc->horiz_scale << 4) | (pc->vert_scale);
|
cx_data += 4;
|
||||||
|
|
||||||
extra_bytes_packed += 5;
|
|
||||||
cx_data += 5;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
vp9_start_encode(&header_bc, cx_data);
|
vp9_start_encode(&header_bc, cx_data);
|
||||||
@@ -2801,11 +2809,15 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
|
|||||||
|
|
||||||
/* update frame tag */
|
/* update frame tag */
|
||||||
{
|
{
|
||||||
int v = (oh.first_partition_length_in_bytes << 5) |
|
int scaling = (pc->Width != pc->display_width
|
||||||
|
|| pc->Height != pc->display_height);
|
||||||
|
int v = (oh.first_partition_length_in_bytes << 8) |
|
||||||
|
(scaling << 5) |
|
||||||
(oh.show_frame << 4) |
|
(oh.show_frame << 4) |
|
||||||
(oh.version << 1) |
|
(oh.version << 1) |
|
||||||
oh.type;
|
oh.type;
|
||||||
|
|
||||||
|
assert(oh.first_partition_length_in_bytes <= 0xffff);
|
||||||
dest[0] = v;
|
dest[0] = v;
|
||||||
dest[1] = v >> 8;
|
dest[1] = v >> 8;
|
||||||
dest[2] = v >> 16;
|
dest[2] = v >> 16;
|
||||||
|
|||||||
@@ -1115,6 +1115,9 @@ static void init_config(VP9_PTR ptr, VP9_CONFIG *oxcf) {
|
|||||||
cm->version = oxcf->Version;
|
cm->version = oxcf->Version;
|
||||||
vp9_setup_version(cm);
|
vp9_setup_version(cm);
|
||||||
|
|
||||||
|
cm->Width = oxcf->Width;
|
||||||
|
cm->Height = oxcf->Height;
|
||||||
|
|
||||||
// change includes all joint functionality
|
// change includes all joint functionality
|
||||||
vp9_change_config(ptr, oxcf);
|
vp9_change_config(ptr, oxcf);
|
||||||
|
|
||||||
@@ -1299,8 +1302,8 @@ void vp9_change_config(VP9_PTR ptr, VP9_CONFIG *oxcf) {
|
|||||||
|
|
||||||
cpi->target_bandwidth = cpi->oxcf.target_bandwidth;
|
cpi->target_bandwidth = cpi->oxcf.target_bandwidth;
|
||||||
|
|
||||||
cm->Width = cpi->oxcf.Width;
|
cm->display_width = cpi->oxcf.Width;
|
||||||
cm->Height = cpi->oxcf.Height;
|
cm->display_height = cpi->oxcf.Height;
|
||||||
|
|
||||||
// VP8 sharpness level mapping 0-7 (vs 0-10 in general VPx dialogs)
|
// VP8 sharpness level mapping 0-7 (vs 0-10 in general VPx dialogs)
|
||||||
if (cpi->oxcf.Sharpness > 7)
|
if (cpi->oxcf.Sharpness > 7)
|
||||||
@@ -1308,18 +1311,6 @@ void vp9_change_config(VP9_PTR ptr, VP9_CONFIG *oxcf) {
|
|||||||
|
|
||||||
cm->sharpness_level = cpi->oxcf.Sharpness;
|
cm->sharpness_level = cpi->oxcf.Sharpness;
|
||||||
|
|
||||||
if (cm->horiz_scale != NORMAL || cm->vert_scale != NORMAL) {
|
|
||||||
int UNINITIALIZED_IS_SAFE(hr), UNINITIALIZED_IS_SAFE(hs);
|
|
||||||
int UNINITIALIZED_IS_SAFE(vr), UNINITIALIZED_IS_SAFE(vs);
|
|
||||||
|
|
||||||
Scale2Ratio(cm->horiz_scale, &hr, &hs);
|
|
||||||
Scale2Ratio(cm->vert_scale, &vr, &vs);
|
|
||||||
|
|
||||||
// always go to the next whole number
|
|
||||||
cm->Width = (hs - 1 + cpi->oxcf.Width * hr) / hs;
|
|
||||||
cm->Height = (vs - 1 + cpi->oxcf.Height * vr) / vs;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Increasing the size of the frame beyond the first seen frame, or some
|
// Increasing the size of the frame beyond the first seen frame, or some
|
||||||
// otherwise signalled maximum size, is not supported.
|
// otherwise signalled maximum size, is not supported.
|
||||||
// TODO(jkoleszar): exit gracefully.
|
// TODO(jkoleszar): exit gracefully.
|
||||||
@@ -4149,6 +4140,7 @@ int vp9_set_internal_size(VP9_PTR comp,
|
|||||||
VPX_SCALING horiz_mode, VPX_SCALING vert_mode) {
|
VPX_SCALING horiz_mode, VPX_SCALING vert_mode) {
|
||||||
VP9_COMP *cpi = (VP9_COMP *) comp;
|
VP9_COMP *cpi = (VP9_COMP *) comp;
|
||||||
VP9_COMMON *cm = &cpi->common;
|
VP9_COMMON *cm = &cpi->common;
|
||||||
|
int hr = 0, hs = 0, vr = 0, vs = 0;
|
||||||
|
|
||||||
if (horiz_mode > ONETWO)
|
if (horiz_mode > ONETWO)
|
||||||
return -1;
|
return -1;
|
||||||
@@ -4156,20 +4148,13 @@ int vp9_set_internal_size(VP9_PTR comp,
|
|||||||
if (vert_mode > ONETWO)
|
if (vert_mode > ONETWO)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (cm->horiz_scale != horiz_mode || cm->vert_scale != vert_mode) {
|
Scale2Ratio(horiz_mode, &hr, &hs);
|
||||||
int UNINITIALIZED_IS_SAFE(hr), UNINITIALIZED_IS_SAFE(hs);
|
Scale2Ratio(vert_mode, &vr, &vs);
|
||||||
int UNINITIALIZED_IS_SAFE(vr), UNINITIALIZED_IS_SAFE(vs);
|
|
||||||
|
|
||||||
cm->horiz_scale = horiz_mode;
|
|
||||||
cm->vert_scale = vert_mode;
|
|
||||||
|
|
||||||
Scale2Ratio(cm->horiz_scale, &hr, &hs);
|
|
||||||
Scale2Ratio(cm->vert_scale, &vr, &vs);
|
|
||||||
|
|
||||||
// always go to the next whole number
|
// always go to the next whole number
|
||||||
cm->Width = (hs - 1 + cpi->oxcf.Width * hr) / hs;
|
cm->Width = (hs - 1 + cpi->oxcf.Width * hr) / hs;
|
||||||
cm->Height = (vs - 1 + cpi->oxcf.Height * vr) / vs;
|
cm->Height = (vs - 1 + cpi->oxcf.Height * vr) / vs;
|
||||||
}
|
|
||||||
assert(cm->Width <= cpi->initial_width);
|
assert(cm->Width <= cpi->initial_width);
|
||||||
assert(cm->Height <= cpi->initial_height);
|
assert(cm->Height <= cpi->initial_height);
|
||||||
update_frame_size(cpi);
|
update_frame_size(cpi);
|
||||||
|
|||||||
Reference in New Issue
Block a user