-
-
Notifications
You must be signed in to change notification settings - Fork 1.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Check if transparent color is really used when examining frame transparency #401
Comments
If there is no transparency flag set |
Thank you for the reply. I added a log statement at this line:
and also in the Here is the logcat snippet after dragging the seek bar (as you can see,
|
I've opened that GIF with a cat in hex editor, and it seems that values read by I'm not sure what So transparent color index reading seems to be correct. Maybe condition here can be refactored to better find key frames.
What do you think @storix ? |
@koral-- Thank you very much for verifying this. Indeed it seems that What's important here is the fact that the transparency flag doesn't guarantee that a frame will use transparency color.
I think, it is not necessary to iterate over the entire pixels array. Every pixel in a GIF frame is represented by an index in a color table (regardless, global or local). During pixels composition we can save all theses indices in a set data structure. This set will give us possibility to verify in a constant time O(1) whether the given transparent color is presented. It also shouldn't increase the memory usage too much because:
I have a lot of GIFs where the transparent colors seem to be not used at all. Unfortunately, I currently have very limited time to implement and test this. |
Yeah, but pixels composition does not happen in all cases. E.g. if seek just created drawable to frames which weren't rendered yet. Of course, we can assume that frame is not transparent in such cases.
So have I. I'll keep this issue open and if you (or someone else) provide PR I'll review immediately but, I can't promise when and if at all I'll implement this feature myself. |
Is it possible to render the requested frame excluding the pixels with transparent colors and without analyzing all the previous frames disposal methods? We then could just compare the resulting pixel number to the gif bounds pixel number. It they are equal then the frame is full and no other actions are required. If not - fallback to current implementation. However, in this case when rendering the previous frames the already rendered pixels of this frame must be taken into account. |
Technically drawing a transparent pixel is just skipping of draw operation. It happens here: https://github.com/koral--/android-gif-drawable/blob/master/android-gif-drawable/src/main/c/drawing.c#L54 But the code in that loop is only executed when draw is needed. Maybe it will be better to solve this issue in another way. Introduce additional, let's say mode when entire frames are buffered into memory. So will have intant seeking in any direction (like sample from iOS app you mentioned) at the cost of higher memory usage. |
OMG, I thought for some reason that the lib is already caching the frames. It is clear now why there is so big difference in seeking performance between Android and iOS app. On iOS I'm using this lib. As you can see here, it caches up to 50 frames. Maybe it's better to implement an adaptive buffer size depending on the available memory using something like Glide or Picasso. Taking into account new considerations, I think, you can close this issue. I can open another one when I will have something to bring to the table regarding the caching approach. |
OK, feel free to send PRs. |
Hi,
I've been trying to increase the
GifDrawable
seeking performance because, as you may know, it is currently very poor (especially when seeking backwards). And I encountered the following issue: for a lot of GIFs ImageMagick reportsTransparent color: none
for all frames. You can check it with this command:identify -verbose GIF_IMAGE.gif | grep -C 1 Transparent
However, here
controlBlock.TransparentColor
returns different strange values like 127, 98, 0 etc. You can verify this with such code:__android_log_print(ANDROID_LOG_DEBUG, "LOG_TAG", "TransparentColor is %u", controlBlock.TransparentColor);
It seems that the control block returns the incorrect transparent color. And if it is really incorrect than it's a great performance hit because break cannot be reached and a lot of unneeded frames must be rendered. BTW, the same GIFs can be sought very quickly in my iOS app.
I created a new branch in my forked version to experiment with the seeking functionality. I added there:
Transparent color: none
for all framesmaxFramesToRenderWhenSeeking
to 1 it is guaranteed that no more than one frame will be rendered when seeking.-1
means the default unbounded behavior. And if you try to quickly drag the seek bar thumb forwards and backwards with the default behavior the sample is often stuck withHope all this will be helpful.
The text was updated successfully, but these errors were encountered: