mirror of
https://github.com/webmproject/libwebp.git
synced 2025-02-13 07:22:52 +01:00
properly report back encoding error code in WebPFrameCacheAddFrame()
User-hook can fail but error was not propagated back. Change-Id: Ic79f9543bf767634a127eccfef90af855ff15c34 Also: some ad-hoc clean-up and API dusting. More to come later...
This commit is contained in:
parent
90090d99b5
commit
f05fe006c2
@ -415,11 +415,15 @@ static int GetColorCount(const WebPPicture* const pic) {
|
|||||||
#undef HASH_SIZE
|
#undef HASH_SIZE
|
||||||
#undef HASH_RIGHT_SHIFT
|
#undef HASH_RIGHT_SHIFT
|
||||||
|
|
||||||
static int SetFrame(const WebPConfig* const config, int allow_mixed,
|
static WebPEncodingError SetFrame(const WebPConfig* const config,
|
||||||
int is_key_frame, const WebPPicture* const prev_canvas,
|
int allow_mixed, int is_key_frame,
|
||||||
WebPPicture* const frame, const WebPFrameRect* const rect,
|
const WebPPicture* const prev_canvas,
|
||||||
|
WebPPicture* const frame,
|
||||||
|
const WebPFrameRect* const rect,
|
||||||
const WebPMuxFrameInfo* const info,
|
const WebPMuxFrameInfo* const info,
|
||||||
WebPPicture* const sub_frame, EncodedFrame* encoded_frame) {
|
WebPPicture* const sub_frame,
|
||||||
|
EncodedFrame* encoded_frame) {
|
||||||
|
WebPEncodingError error_code = VP8_ENC_OK;
|
||||||
int try_lossless;
|
int try_lossless;
|
||||||
int try_lossy;
|
int try_lossy;
|
||||||
int try_both;
|
int try_both;
|
||||||
@ -446,6 +450,7 @@ static int SetFrame(const WebPConfig* const config, int allow_mixed,
|
|||||||
WebPConfig config_ll = *config;
|
WebPConfig config_ll = *config;
|
||||||
config_ll.lossless = 1;
|
config_ll.lossless = 1;
|
||||||
if (!EncodeFrame(&config_ll, sub_frame, &mem1)) {
|
if (!EncodeFrame(&config_ll, sub_frame, &mem1)) {
|
||||||
|
error_code = sub_frame->error_code;
|
||||||
goto Err;
|
goto Err;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -461,6 +466,7 @@ static int SetFrame(const WebPConfig* const config, int allow_mixed,
|
|||||||
FlattenSimilarBlocks(prev_canvas, rect, frame);
|
FlattenSimilarBlocks(prev_canvas, rect, frame);
|
||||||
}
|
}
|
||||||
if (!EncodeFrame(&config_lossy, sub_frame, &mem2)) {
|
if (!EncodeFrame(&config_lossy, sub_frame, &mem2)) {
|
||||||
|
error_code = sub_frame->error_code;
|
||||||
goto Err;
|
goto Err;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -478,12 +484,12 @@ static int SetFrame(const WebPConfig* const config, int allow_mixed,
|
|||||||
} else {
|
} else {
|
||||||
GetEncodedData(try_lossless ? &mem1 : &mem2, encoded_data);
|
GetEncodedData(try_lossless ? &mem1 : &mem2, encoded_data);
|
||||||
}
|
}
|
||||||
return 1;
|
return error_code;
|
||||||
|
|
||||||
Err:
|
Err:
|
||||||
WebPMemoryWriterClear(&mem1);
|
WebPMemoryWriterClear(&mem1);
|
||||||
WebPMemoryWriterClear(&mem2);
|
WebPMemoryWriterClear(&mem2);
|
||||||
return 0;
|
return error_code;
|
||||||
}
|
}
|
||||||
|
|
||||||
#undef MIN_COLORS_LOSSY
|
#undef MIN_COLORS_LOSSY
|
||||||
@ -518,7 +524,8 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
WebPPicture* const frame,
|
WebPPicture* const frame,
|
||||||
WebPMuxFrameInfo* const info) {
|
WebPMuxFrameInfo* const info) {
|
||||||
int ok = 0;
|
int ok = 0;
|
||||||
WebPFrameRect rect = *orig_rect;
|
WebPEncodingError error_code = VP8_ENC_OK;
|
||||||
|
WebPFrameRect rect;
|
||||||
WebPPicture sub_image; // View extracted from 'frame' with rectangle 'rect'.
|
WebPPicture sub_image; // View extracted from 'frame' with rectangle 'rect'.
|
||||||
WebPPicture* const prev_canvas = &cache->prev_canvas;
|
WebPPicture* const prev_canvas = &cache->prev_canvas;
|
||||||
const size_t position = cache->count;
|
const size_t position = cache->count;
|
||||||
@ -526,11 +533,23 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
EncodedFrame* const encoded_frame = CacheGetFrame(cache, position);
|
EncodedFrame* const encoded_frame = CacheGetFrame(cache, position);
|
||||||
assert(position < cache->size);
|
assert(position < cache->size);
|
||||||
|
|
||||||
|
if (frame == NULL || info == NULL) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (orig_rect != NULL) {
|
||||||
|
rect = *orig_rect;
|
||||||
// Snap to even offsets (and adjust dimensions if needed).
|
// Snap to even offsets (and adjust dimensions if needed).
|
||||||
rect.width += (rect.x_offset & 1);
|
rect.width += (rect.x_offset & 1);
|
||||||
rect.height += (rect.y_offset & 1);
|
rect.height += (rect.y_offset & 1);
|
||||||
rect.x_offset &= ~1;
|
rect.x_offset &= ~1;
|
||||||
rect.y_offset &= ~1;
|
rect.y_offset &= ~1;
|
||||||
|
} else {
|
||||||
|
rect.width = frame->width;
|
||||||
|
rect.height = frame->height;
|
||||||
|
rect.x_offset = 0;
|
||||||
|
rect.y_offset = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (!WebPPictureView(frame, rect.x_offset, rect.y_offset,
|
if (!WebPPictureView(frame, rect.x_offset, rect.y_offset,
|
||||||
rect.width, rect.height, &sub_image)) {
|
rect.width, rect.height, &sub_image)) {
|
||||||
@ -543,8 +562,9 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
|
|
||||||
if (cache->is_first_frame || IsKeyFrame(frame, &rect, prev_canvas)) {
|
if (cache->is_first_frame || IsKeyFrame(frame, &rect, prev_canvas)) {
|
||||||
// Add this as a key frame.
|
// Add this as a key frame.
|
||||||
if (!SetFrame(config, allow_mixed, 1, NULL, NULL, NULL, info, &sub_image,
|
error_code = SetFrame(config, allow_mixed, 1, NULL, NULL, NULL,
|
||||||
encoded_frame)) {
|
info, &sub_image, encoded_frame);
|
||||||
|
if (error_code != VP8_ENC_OK) {
|
||||||
goto End;
|
goto End;
|
||||||
}
|
}
|
||||||
cache->keyframe = position;
|
cache->keyframe = position;
|
||||||
@ -556,8 +576,9 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
++cache->count_since_key_frame;
|
++cache->count_since_key_frame;
|
||||||
if (cache->count_since_key_frame <= cache->kmin) {
|
if (cache->count_since_key_frame <= cache->kmin) {
|
||||||
// Add this as a frame rectangle.
|
// Add this as a frame rectangle.
|
||||||
if (!SetFrame(config, allow_mixed, 0, prev_canvas, frame, &rect, info,
|
error_code = SetFrame(config, allow_mixed, 0, prev_canvas, frame,
|
||||||
&sub_image, encoded_frame)) {
|
&rect, info, &sub_image, encoded_frame);
|
||||||
|
if (error_code != VP8_ENC_OK) {
|
||||||
goto End;
|
goto End;
|
||||||
}
|
}
|
||||||
cache->flush_count = cache->count;
|
cache->flush_count = cache->count;
|
||||||
@ -566,12 +587,12 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
} else {
|
} else {
|
||||||
WebPPicture full_image;
|
WebPPicture full_image;
|
||||||
WebPMuxFrameInfo full_image_info;
|
WebPMuxFrameInfo full_image_info;
|
||||||
int frame_added;
|
|
||||||
int64_t curr_delta;
|
int64_t curr_delta;
|
||||||
|
|
||||||
// Add frame rectangle to cache.
|
// Add frame rectangle to cache.
|
||||||
if (!SetFrame(config, allow_mixed, 0, prev_canvas, frame, &rect, info,
|
error_code = SetFrame(config, allow_mixed, 0, prev_canvas, frame, &rect,
|
||||||
&sub_image, encoded_frame)) {
|
info, &sub_image, encoded_frame);
|
||||||
|
if (error_code != VP8_ENC_OK) {
|
||||||
goto End;
|
goto End;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -587,10 +608,10 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
full_image_info.y_offset = rect.y_offset;
|
full_image_info.y_offset = rect.y_offset;
|
||||||
|
|
||||||
// Add key frame to cache, too.
|
// Add key frame to cache, too.
|
||||||
frame_added = SetFrame(config, allow_mixed, 1, NULL, NULL, NULL,
|
error_code = SetFrame(config, allow_mixed, 1, NULL, NULL, NULL,
|
||||||
&full_image_info, &full_image, encoded_frame);
|
&full_image_info, &full_image, encoded_frame);
|
||||||
WebPPictureFree(&full_image);
|
WebPPictureFree(&full_image);
|
||||||
if (!frame_added) goto End;
|
if (error_code != VP8_ENC_OK) goto End;
|
||||||
|
|
||||||
// Analyze size difference of the two variants.
|
// Analyze size difference of the two variants.
|
||||||
curr_delta = KeyFramePenalty(encoded_frame);
|
curr_delta = KeyFramePenalty(encoded_frame);
|
||||||
@ -620,6 +641,8 @@ int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
|||||||
FrameRelease(encoded_frame);
|
FrameRelease(encoded_frame);
|
||||||
--cache->count; // We reset the count, as the frame addition failed.
|
--cache->count; // We reset the count, as the frame addition failed.
|
||||||
}
|
}
|
||||||
|
frame->error_code = error_code; // report error_code
|
||||||
|
assert(ok || error_code != VP8_ENC_OK);
|
||||||
return ok;
|
return ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -54,8 +54,9 @@ WebPFrameCache* WebPFrameCacheNew(int width, int height,
|
|||||||
void WebPFrameCacheDelete(WebPFrameCache* const cache);
|
void WebPFrameCacheDelete(WebPFrameCache* const cache);
|
||||||
|
|
||||||
// Given an image described by 'frame', 'info' and 'orig_rect', optimize it for
|
// Given an image described by 'frame', 'info' and 'orig_rect', optimize it for
|
||||||
// WebP, encode it and add it to 'cache'.
|
// WebP, encode it and add it to 'cache'. 'orig_rect' can be NULL.
|
||||||
// This takes care of frame disposal too, according to 'info->dispose_method'.
|
// This takes care of frame disposal too, according to 'info->dispose_method'.
|
||||||
|
// Returns false in case of error (and sets frame->error_code accordingly).
|
||||||
int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
int WebPFrameCacheAddFrame(WebPFrameCache* const cache,
|
||||||
const WebPConfig* const config,
|
const WebPConfig* const config,
|
||||||
const WebPFrameRect* const orig_rect,
|
const WebPFrameRect* const orig_rect,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user