I'm creating a UI using Swing and I want to display an image in a JLabel. The code I use is the following:
JLabel label = new JLabel(new ImageIcon(ImageIO.read(new File("img.jpg"))));
This works fine if I use png images but when it comes to jpg (only some of them), I get a redish image (a different one than the one I see in Paint.NET).
The image I used is this one: img.jpg
So I tried (as an alternative):
Toolkit.getDefaultToolkit().createImage(new File("img.jpg").getAbsolutePath());
Does anyone have an idea of why this happening? Is it a special JPEG format which is not supported?
I've read on this forum that most people recommend to use ImageIO (here for example). Why?
Thanks a lot
As discussed here, your JPEG image may contain spurious transparency information. One simple expedient is to render the image in a buffer having a compatible color model, as shown here.
It looks like you have found a bug in ImageIO.read... (I can reproduce the red tint, and it is definitely not how it should look like).
You can try to
save the JPEG files with other settings
open/re-save the file with other programs (hoping to get a more common JPEG-encoding)
or use the Toolkit method (if you don't control the images).
The only problem with the Toolkit method is that the getImage() method returns immediately after it is invoked and the loading is happening on a background thread, so you cannot start working with the Image object immediately.
Related
Hi im new to programming and im starting to program with java im creating a program that will paint in the applet and everything seems good.
The thing is i want to save the paint that i have done and i was wondering it is possible to convert that applet or the paint method to png file. If not i was working on that everytime the user paint it will save the coordinates, color and size and save it in txt then i have to create a reader or a display for it.
Is it possible to make an applet to png file ?
You can convert an image into a png file by using ImageIO.write(...). Hopefully it should be fairly easy to extract the image from your painting, but this depends on much that has not yet been shown to us. Please show us your pertinent code so that I can improve this answer with concrete code.
Assuming that you're drawing within a JPanel's paintComponent method or an Applet's paint method, then you can instead paint into a BufferedImage, and then use that Image to convert to your png file.
The other issue is writing from the applet itself to the file on the disk, and there may be permission issues with this. Myself, I avoid programming applets like the plague, since they're really not used much any more, and in fact some browsers don't allow use of them.
Coming from AWT/Swing, I've started experimenting a bit with JavaFX the last few days. I realized that what I used to do in thousands lines of codes can now be done in a few hundred.
One problem I came across is, however, the following: I'm trying to develop a small painting app where the user can choose brush size and color for its strokes. For all the strokes the user makes, I use the JavaFX class Path and add these paths to a Group (which is added to a Pane) where they are - automagically - painted. Now I want to store the resulting image as a jpg and try to raster all the paths in a BufferedImage. However, I found no functions in the API that help me do that.
I tried to use Canvas and its GraphicsContext, but that did not help. How could I raster all the JavaFX Paths from a list on an image?
Take a snapshot of your Group to get a JavaFX Image.
Use SwingFXUtils to convert your JavaFX image snapshot to a buffered image.
Use ImageIO to convert your buffered image to a jpeg, png, etc
There are various ways of reading an image file in java such as BufferedImage and ImageIcon to name a few. I want to know what is the difference between these cases? Are they context dependent that in a particular case only one of them can be used?
What would be the best way of reading a image selected by JFileChooser by the user and separating the color channels of an image?
A good way is to use the different ImageIO.read methods, which return BufferedImage objects.
Image is an abstract class, so I think the real question is which subclass is more efficient for your program. Use VolatileImage if you need hardware acceleration. More on that here.
ImageIcon (and Toolkit#createImage/Toolkit#getImage) use a background loading process. That is, after you call these methods, they will return immediately, having created a background thread to actually load the image data.
These were/are used when loading large images across slow connections, like ye old 28k modems (ah, how I remember the days). This means that your application can continue running while the images are been downloaded.
You'll find in the Graphics class the drawImage methods accept an ImageObserver interface and that java.awt.Component implements this interface, this allows components the ability to automatically update themselves once the image has actually finished loading.
ImageIO on the other hand will not return until the image is fully loaded. It also makes it easier to introduce new readers/writers, making the API far more flexible then the original API. ImageIO also supports a wider range of images out of the box.
BufferedImage is also a far more flexible image class, especially when it comes to apply effects to the image.
Now, I, personally, prefer ImageIO. If I know I'm loading large images or images over a potentially slow connection, I will create my own background thread to load them. While a little more complicated, the trade offs greatly out weight the small amount of extra work -IMHO
What would be the best way of reading a image selected by JFileChooser by the user and separating the color channels of an image?
ImageIO without a doubt. In order to do any serious manipulation of an image loaded using something ImageIcon, you'd have to convert that image to a BufferedImage anyway
I develop an application in which I want to display a grid with a list of images. For each image I create an instance of a class myImage. MyImage class, extends JCompoment and create an thumbnail and after draw it with overide thepaintCompoment(Graphics g).
All is ok, but in big size images I have a lot of delay to create the thumbnail.
Now I think to when I scan the folders for image(to create the list I said above to create an thumbanail of each image and save it to disc. For each image I will have a database record to save the image path and thumbnail path.So is this a good solution of the problem?
Is there a way to get the thumbnails of the system creates for each image, in file manager. Or a more effective solution than I try.
Thank you!!
Your best bet is to use something like imagemagick to convert the image and create the thumbnail. There's a project called JMagick which provides JNI hooks into Imagemagick, but running a process work too.
Imagemagick is heavily optimized C code for manipulating images. It will also be able to handle images that Java won't and with much less memory usage.
I work for a website where we let users upload art and create thumbnails on the fly, and it absolutely needs to be fast, so that's what we use.
The following is Groovy code, but it can modified to Java code pretty easily:
public boolean createThumbnail(InputStream input, OutputStream output){
def cmd = "convert -colorspace RGB -auto-orient -thumbnail 125x125 -[0] jpg:-"
Process p = cmd.execute()
p.consumeProcessErrorStream(System.out)
p.consumeProcessOutputStream(output)
p.out << input
p.out.close()
p.waitForOrKill(8000)
return p.exitValue()==0
}
This creates a thumbnail using pipes without actually writing any data to disk. The outputStream can be to a file if you wanted to immediately write it as well.
One way to avoid OS dependance is to use getScaledInstance(), as shown in this example. See the cited articles for certain limitations. If it's taking too long, use a SwingWorker to do the load and scale in the background.
I haven't used it for the creation of thumbnails, but you may also want to take a look at the ImageIO API.
ImageIO
Has anybody managed to convince ImageIO to write an animated GIF, and in particular setting the correct metadata? My first attempt is roughly as follows (where b1 and b2 are BufferedImages):
ImageTypeSpecifier spec = new ImageTypeSpecifier(b1);
ImageWriter wr = ImageIO.getImageWriters(spec, "GIF").next();
wr.setOutput(ImageIO.createImageOutputStream(new File("C:\\Flashing.gif")));
ImageWriteParam param = wr.getDefaultWriteParam();
IIOMetadata meta = wr.getDefaultImageMetadata(spec, param);
wr.prepareWriteSequence(meta);
wr.writeToSequence(new IIOImage(b1, null, null), param);
wr.writeToSequence(new IIOImage(b2, null, null), param);
This appears to almost work, but:
I clearly need to somehow set "proper" metadata to set the time between the images and ideally make them loop (I was naively hoping the default would do something sensible, but hey...)
whatever metadata it is writing by default is obviously not quite right: the GIMP gives a couple of error messages when loading the file, although embedding the image in a test web page in Firefox does display the two images in very quick succession, which is tantilisingly close to what I want...
If anyone has got writing animated GIFs from ImageIO to work and can share a snippet of working code or how to fix the above problems, it would be greatly appreciated!
I ran across this question, and decided to try it out; It took a small but non-trivial amount create a usable class (thanks ax) -- so I thought I might share the code around: here is a small class for creating an animated gif image from a number of other images. Archived version