Animated GIF using LWUIT
Since a couple of weeks ago, I'm working on moving my mobile applications to a new attractive user interface using LWUIT (LightWeigth User Interface Toolkit).
I found LWUIT really very impressive and the results are really excellent: my mobile apps now are much nicer then before.
But I found some little lacks in LWUIT. The most relevant is the lack of a class to manage animated GIF at runtime.
As of this writing, the current version of LWUIT supports animated gifs only if they are added in the resource file by the Resource Editor as "Animated Images". Such animated images can be added to a Label, to a Button or to another component and are animated when shown.
What I mean is that there are no way to use an animated GIF as animated image in a component if the gif is loaded at runtime from an input stream. Also, there is no way to manage the animation loop programmatically (i.e. stopping and starting the animation).
So, I googled a little to find a solution. First of all I found several posts related to that. This means that such a lack is involving several programmers. Second, I found the class GifDecoder ported to J2ME for decoding any animated gif.
Starting from that class and reading how the class StaticAnimation of LWUIT is implemented I wrote a new class AnimatedGIF, derived from the class com.sun.lwuit.Image, that allows to use animated gif at runtime in your applications.
You can use it as any other image.
The following is a snippet that shows how to create a Button with a animated gif image:
AnimatedGIF image = AnimatedGIF.createAnimatedGIF(
new ByteArrayInputStream(btImage));
Button btn = new Button();
btn.setIcon(image);
The source code can be downloaded from here and it is published under LGPL.
Mainly this is the most relevant topics:
- the package must be com.sun.lwuit because I need the costructor Image(Object) that has package visibility (I think it should have protected visibility)
- an animated gif is rapresented as an array of frames
- the frames are generated by the class GifDecoder
- a gif is animated if it has more then one frame
- the animation can be started and stopped on demand by the method start and stop
- the loop counter can be set by the method setLoopCount
- the rest of the code has been taken and adapted from the class StaticAnimation
For more info about LWUIT visit this url http://lwuit.dev.java.net).
14 commenti:
Thanks a lot Ugo. I was looking forward for this one, Will try it out now :)
Hi, Ugo
I tried your class, I got error as below when I run it, do you know why?
ALERT: java/lang/VerifyError: com/sun/lwuit/AnimatedGIF$GifDecoder
Hi Mikezang,
It's very strange. I'm using it without any problem.
What preverifier are you using?
Thanks for your reply.
I am using C:\Program Files\NetBeans 6.7\mobility8\Java_ME_platform_SDK_3.0.
Then that error don't happen if I run a special Proguard, I can send proguard config file to you if you want to confirm.
hey can u please be kind enuf to tell me, how do i put your class in com.sun.lwuit . kindly reply :)
PS : amazing job. i am exited to test it !!
ok, i got that done...but the problem is you are asking for byte array as an argument. i have an image which i want to animate...and i cant find a way to convert this image into pngbytearray. thanks for help.
Thanks for the great code Ugo. I posted a modified version to the incubator/blog with an example of how to seamlessly integrate this with LWUIT without modifying code:
http://lwuit.blogspot.com/2010/05/animated-gifs-everywhere.html
This does not work by sadly,
i copied your class,
and it does not work,
I want to solve problem, please if you have any way to solve animated gif problem in lwuit please help me!
In my apps it works perfectly.
What does exactly happen in you app?
Please if you can, Upload the solution
I cannot upload one of my apps!!!
Please why you are saying that it doesn't work?
when i try to use it, the first frame had been displayed, this is the code snippet :
Label figureLabel=new Label();
figureLabel.getStyle().setBgTransparency(255);
figureLabel.getStyle().setFgColor(0x000000);
// figureLabel.getStyle().setBgColor(0xFFACCD);
figureLabel.setAlignment(Label.CENTER);
AnimatedGIF image=null;
try {
image = AnimatedGIF.createAnimatedGIF(new ByteArrayInputStream(obtainByteData(imgName)));
image.start();
figureLabel.setIcon(image);
figureLabel.animate();
registerAnimated(figureLabel);
} catch (IOException ex) {
ex.printStackTrace();
}
getContentPane().addComponent(figureLabel);
this is the method to obtain byte array
-----------------------------------
private byte[] obtainByteData(String filename) throws IOException {
is=null;
is = getClass().getResourceAsStream("/"+filename+".gif");
if(is==null)
{
System.out.println("Is is empty");
}
ByteArrayOutputStream outputStream = new ByteArrayOutputStream(1024);
byte[] bytes = new byte[512];
// Read bytes from the input stream in bytes.length-sized chunks and write
// them into the output stream
int readBytes;
while ((readBytes = is.read(bytes)) > 0) {
outputStream.write(bytes, 0, readBytes);
}
// Convert the contents of the output stream into a byte array
byte[] byteData = outputStream.toByteArray();
// Close the streams
is.close();
outputStream.close();
return byteData;
}
-----------------------------------
and in the your class have errors
i want to post new post contains urls for snapshots of errors in your class
----------------
Thanks a lot for replaying
and Thanks a lot for this excellent subject
=========
Regards
Mohammad
I uploaded the figures on my Facebook i think it is the shortest way,
this it's url
http://www.facebook.com/album.php?aid=41757&id=100000181362995&l=781e10cc3c
you can see them
please help me!
Thanks a lot
how we set that animation into infinite entry.please mention. i am also looking for this.i already tried this methods set loop count , animate,set loop, start , stop methods separately and with the combinations also. and also what you mentioned that order also i followed. will you please help me .
Posta un commento