mirror of
https://github.com/webmproject/libwebp.git
synced 2024-12-27 06:08:21 +01:00
gif2webp: handle 1-frame case properly + fix anim_diff
follow-up to commit b4e046778
Change-Id: I3c7617d09682262ca7929e6a3e56777b163cce45
This commit is contained in:
parent
c7f295d30c
commit
3c74c645ca
@ -425,6 +425,11 @@ static uint32_t GetBackgroundColorGIF(GifFileType* gif) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Find appropriate app extension and get loop count from the next extension.
|
// Find appropriate app extension and get loop count from the next extension.
|
||||||
|
// We use Chrome's interpretation of the 'loop_count' semantics:
|
||||||
|
// if not present -> loop once
|
||||||
|
// if present and loop_count == 0, return 0 ('infinite').
|
||||||
|
// if present and loop_count != 0, it's the number of *extra* loops
|
||||||
|
// so we need to return loop_count + 1 as total loop number.
|
||||||
static uint32_t GetLoopCountGIF(const GifFileType* const gif) {
|
static uint32_t GetLoopCountGIF(const GifFileType* const gif) {
|
||||||
int i;
|
int i;
|
||||||
for (i = 0; i < gif->ImageCount; ++i) {
|
for (i = 0; i < gif->ImageCount; ++i) {
|
||||||
@ -442,12 +447,13 @@ static uint32_t GetLoopCountGIF(const GifFileType* const gif) {
|
|||||||
if (signature_is_ok &&
|
if (signature_is_ok &&
|
||||||
eb2->Function == CONTINUE_EXT_FUNC_CODE && eb2->ByteCount >= 3 &&
|
eb2->Function == CONTINUE_EXT_FUNC_CODE && eb2->ByteCount >= 3 &&
|
||||||
eb2->Bytes[0] == 1) {
|
eb2->Bytes[0] == 1) {
|
||||||
return ((uint32_t)(eb2->Bytes[2]) << 8) +
|
const uint32_t extra_loop = ((uint32_t)(eb2->Bytes[2]) << 8) +
|
||||||
((uint32_t)(eb2->Bytes[1]) << 0);
|
((uint32_t)(eb2->Bytes[1]) << 0);
|
||||||
|
return (extra_loop > 0) ? extra_loop + 1 : 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return 0; // Default.
|
return 1; // Default.
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get duration of 'n'th frame in milliseconds.
|
// Get duration of 'n'th frame in milliseconds.
|
||||||
|
@ -106,7 +106,7 @@ int main(int argc, const char *argv[]) {
|
|||||||
WebPAnimEncoderOptions enc_options;
|
WebPAnimEncoderOptions enc_options;
|
||||||
WebPConfig config;
|
WebPConfig config;
|
||||||
|
|
||||||
int is_first_frame = 1; // Whether we are processing the first frame.
|
int frame_number = 0; // Whether we are processing the first frame.
|
||||||
int done;
|
int done;
|
||||||
int c;
|
int c;
|
||||||
int quiet = 0;
|
int quiet = 0;
|
||||||
@ -282,7 +282,7 @@ int main(int argc, const char *argv[]) {
|
|||||||
|
|
||||||
if (!DGifGetImageDesc(gif)) goto End;
|
if (!DGifGetImageDesc(gif)) goto End;
|
||||||
|
|
||||||
if (is_first_frame) {
|
if (frame_number == 0) {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Canvas screen: %d x %d\n", gif->SWidth, gif->SHeight);
|
printf("Canvas screen: %d x %d\n", gif->SWidth, gif->SHeight);
|
||||||
}
|
}
|
||||||
@ -324,7 +324,6 @@ int main(int argc, const char *argv[]) {
|
|||||||
"a memory error.\n");
|
"a memory error.\n");
|
||||||
goto End;
|
goto End;
|
||||||
}
|
}
|
||||||
is_first_frame = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Some even more broken GIF can have sub-rect with zero width/height.
|
// Some even more broken GIF can have sub-rect with zero width/height.
|
||||||
@ -341,7 +340,11 @@ int main(int argc, const char *argv[]) {
|
|||||||
GIFBlendFrames(&frame, &gif_rect, &curr_canvas);
|
GIFBlendFrames(&frame, &gif_rect, &curr_canvas);
|
||||||
|
|
||||||
if (!WebPAnimEncoderAdd(enc, &curr_canvas, frame_timestamp, &config)) {
|
if (!WebPAnimEncoderAdd(enc, &curr_canvas, frame_timestamp, &config)) {
|
||||||
fprintf(stderr, "%s\n", WebPAnimEncoderGetError(enc));
|
fprintf(stderr, "Error while adding frame #%d: %s\n", frame_number,
|
||||||
|
WebPAnimEncoderGetError(enc));
|
||||||
|
goto End;
|
||||||
|
} else {
|
||||||
|
++frame_number;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Update canvases.
|
// Update canvases.
|
||||||
@ -451,9 +454,12 @@ int main(int argc, const char *argv[]) {
|
|||||||
if (!loop_compatibility) {
|
if (!loop_compatibility) {
|
||||||
if (!stored_loop_count) {
|
if (!stored_loop_count) {
|
||||||
// if no loop-count element is seen, the default is '1' (loop-once)
|
// if no loop-count element is seen, the default is '1' (loop-once)
|
||||||
// and we need to signal it explicitly in WebP.
|
// and we need to signal it explicitly in WebP. Note however that
|
||||||
stored_loop_count = 1;
|
// in case there's a single frame, we still don't need to store it.
|
||||||
loop_count = 1;
|
if (frame_number > 1) {
|
||||||
|
stored_loop_count = 1;
|
||||||
|
loop_count = 1;
|
||||||
|
}
|
||||||
} else if (loop_count > 0) {
|
} else if (loop_count > 0) {
|
||||||
// adapt GIF's semantic to WebP's (except in the infinite-loop case)
|
// adapt GIF's semantic to WebP's (except in the infinite-loop case)
|
||||||
loop_count += 1;
|
loop_count += 1;
|
||||||
|
Loading…
Reference in New Issue
Block a user