How to get byte array form javafx.scene.image.Image object? - java

I want to save image into database. I have a Customer model that has Image property in it. I am creating a class that handle all the customer related database operations. In that class I have a method that takes in Customer object and inserts it into the database. Therefore, I have only Customer object to work with. How can I convert that Image object into byte array so that I can insert it into the datbase?
I know how to extract byte array from a file object. Should I change the customer model to contain image file instead of image object?

This worked for me:
Image image = customer.getImage();
BufferedImage bufferedImage = SwingFXUtils.fromFXImage(image, null);
ByteArrayOutputStream byteArrayInputStream = new ByteArrayOutputStream();
try {
ImageIO.write(bufferedImage, "jpeg", byteArrayInputStream);
} catch (IOException e) {
e.printStackTrace();
}
byte[] buffer = byteArrayInputStream.toByteArray();

Related

Vaadin Convert and display image as PDF

Does anyone know how image file can be easily converted into PDF format. What I need is to get the image from database and display it on the screen as PDF. What am I doing wrong? I tried to use iText but with no results.
My code:
StreamResource resource = file.downloadFromDatabase();//get file from db
Document converToPdf=new Document();//Create Document Object
PdfWriter.getInstance(convertToPdf, new FileOutputStream(""));//Create PdfWriter for Document to hold physical file
convertToPdf.open();
Image convertJpg=Image.getInstance(resource); //Get the input image to Convert to PDF
convertToPdf.add(convertJpg);//Add image to Document
Embedded pdf = new Embedded("", convertToPdf);//display document
pdf.setMimeType("application/pdf");
pdf.setType(Embedded.TYPE_BROWSER);
pdf.setSizeFull();
Thanks.
You're not using iText correctly:
You never close your writer, so the addition of the image never gets written to the outputstream.
You pass an empty string to your FileOutputStream. If you want to keep the pdf in memory, use a ByteArrayOutputStream. If not, define a temporary name instead.
You pass your Document object, which is a iText-specific object to your Embedded object and treat it like a file. It is not a pdf-file or byte[]. You'll probably want to pass either your ByteArrayOutputStream or read the temp file as a ByteArrayOutputStream into memory and pass that to Embedded.
Maybe someone will use (Vaadin + iText)
Button but = new Button("FV");
StreamResource myResource = getPDFStream();
FileDownloader fileDownloader = new FileDownloader(myResource);
fileDownloader.extend(but);
hboxBottom.addComponent( but );
private StreamResource getPDFStream() {
StreamResource.StreamSource source = new StreamResource.StreamSource() {
public InputStream getStream() {
// step 1
com.itextpdf.text.Document document = new com.itextpdf.text.Document();
// step 2
ByteArrayOutputStream baos = new ByteArrayOutputStream();
try {
com.itextpdf.text.pdf.PdfWriter.getInstance(document, baos);
// step 3
document.open();
document.add(Chunk.NEWLINE); //Something like in HTML :-)
document.add(new Paragraph("TEST" ));
document.add(Chunk.NEWLINE); //Something like in HTML :-)
document.newPage(); //Opened new page
//document.add(list); //In the new page we are going to add list
document.close();
//file.close();
System.out.println("Pdf created successfully..");
} catch (DocumentException ex) {
Logger.getLogger(WndOrderZwd.class.getName()).log(Level.SEVERE, null, ex);
}
ByteArrayOutputStream stream = baos;
InputStream input = new ByteArrayInputStream(stream.toByteArray());
return input;
}
};
StreamResource resource = new StreamResource ( source, "test.pdf" );
return resource;
}

how to get picture size when reading from a excel file?

I am converting excel (xls, xlsx) file to html. But when image is there I am not able to get image size(dimention) which is there in the excel file. I am using apache poi.
How to get image size of that file? Please help me on that.
This source explains how to get picture data from the excel file: http://poi.apache.org/spreadsheet/quick-guide.html#Images.
Within the loop there is a
byte[] data = pict.getData();
You can use that byte array, write it to a ByteArrayOutputStream object and call the size() method to retrieve the size of the file written to the outputstream.
ByteArrayOutputStream baos = new ByteArrayOutputStream();
baos.write(data);
int fileSizeInBytes = baos.size();
I hope this helps.
This may be an overkill, but you can create an image from the byte array and check its size. For example:
for (HSSFPictureData pic : workbook.getAllPictures()) {
InputStream in = new ByteArrayInputStream(pic.getData());
BufferedImage image = ImageIO.read(in);
System.out.println(image.getWidth() + ":" + image.getHeight());
}

How to get byte[] from javafx imageView?

How do i get byte[] from javafx image/imageview class? I want to store my image as a Blob into my database.This is the method that i use for it
public PreparedStatement prepareQuery(HSQLDBConnector connector) {
try {
Blob logoBlob = connector.connection.createBlob();
logoBlob.setBytes(0,logo.getImage());//stuck here
for (int i = 0, a = 1; i < data.length; i++, a++) {
connector.prepStatCreateProfile.setString(a, data[i]);
}
//store LOB
connector.prepStatCreateProfile.setBlob(11, logoBlob);
} catch (SQLException ex) {
ex.printStackTrace();
}
return connector.prepStatCreateProfile;
}
Is there a way to convert from my current object (imageview),image) into byte[]?, or shoud i start to think about using other class for my image/ alternatively point to the location with reference and work with paths/urls?
try this one:
BufferedImage bImage = SwingFXUtils.fromFXImage(logo.getImage(), null);
ByteArrayOutputStream s = new ByteArrayOutputStream();
ImageIO.write(bImage, "png", s);
byte[] res = s.toByteArray();
s.close(); //especially if you are using a different output stream.
should work depending on the logo class
you need to specify a format while writing and reading, and as far as I remember bmp is not supported so you will end up with a png byte array on the database
pure java fx solution trace ( == you will have to fill in missing points :)
Image i = logo.getImage();
PixelReader pr = i.getPixelReader();
PixelFormat f = pr.getPixelFormat();
WriteablePixelFromat wf = f.getIntArgbInstance(); //???
int[] buffer = new int[size as desumed from the format f, should be i.width*i.height*4];
pr.getPixels(int 0, int 0, int i.width, i.height, wf, buffer, 0, 0);
Lorenzo's answer is correct, this answer just examines efficiency and portability aspects.
Depending on the image type and storage requirements, it may be efficient to convert the image to a compressed format for storage, for example:
ByteArrayOutputStream byteOutput = new ByteArrayOutputStream();
ImageIO.write(SwingFXUtils.fromFXImage(fxImage, null), "png", byteOutput);
Blob logoBlob = connector.connection.createBlob();
logoBlob.setBytes(0, byteOutput.toByteArray());
Another advantage of doing a conversion to a common format like png before persisting the image is that other programs which deal with the database would be able to read the image without trying to convert it from a JavaFX specific byte array storage format.

Exporting more than one image in one JPG file

I have a JSP that allows the user to export some data. You can choose differents formats (excel, csv). Also, with the excel are exported the charts corresponding to the data (pie chart, line chart and bar chart) The user want to export the charts in a unique jpg file.
What I did is (all in Java):
Generate the charts using JFreeChart
Convert the chart into a JPG image using: ChartUtilities.saveChartAsJPEG
Then I retrieve theimage bytes:
The code:
InputStream is = null;
try {
is = new FileInputStream(image);
}catch (FileNotFoundException e) {
e.printStackTrace();
}
byte[] bytes = null;
try {
bytes = IOUtils.toByteArray(is);
}catch (IOException e) {
e.printStackTrace();
}
This is working well, I have the bytes for each chart. Then I put the bytes for each chart in a byte array:
byte[] imageBytes = getImageAsBytes(chart1,chart2,chart3);
res.setContentType("image/jpg");
res.setHeader("Content-Disposition", "attachment; filename=" + "MyCharts" + ".jpg");
res.setContentLength(imageBytes.length);
try{
OutputStream output = res.getOutputStream();
output.write(imageBytes);
output.flush();
output.close();
} catch (IOException e) {
e.printStackTrace();
}
The problem is: when I open the JPG, only one image is displayed. I tested the export for each chart and works well, but when I put all the chart bytes, is only displayed one image (always the first in the imageBytes array)
I don't know if I have to create some kind of canvas, or just is not possible put 3 images or more in the same JPG by this way.
The JPG file format isn't going to let you get away with that. My suggestion would be to create a new BufferedImage with a large enough canvas to contain all three images, render your three images onto it at staggered Y axis offsets, and then dump it out to JPG with ImageIO.

Byte Array to Image object

I am given a byte[] array in Java which contains the bytes for an image, and I need to output it into an image. How would I go about doing this?
Much thanks
BufferedImage img = ImageIO.read(new ByteArrayInputStream(bytes));
If you know the type of image and only want to generate a file, there's no need to get a BufferedImage instance. Just write the bytes to a file with the correct extension.
try (OutputStream out = new BufferedOutputStream(new FileOutputStream(path))) {
out.write(bytes);
}
From Database.
Blob blob = resultSet.getBlob("pictureBlob");
byte [] data = blob.getBytes( 1, ( int ) blob.length() );
BufferedImage img = null;
try {
img = ImageIO.read(new ByteArrayInputStream(data));
} catch (IOException e) {
e.printStackTrace();
}
drawPicture(img); // void drawPicture(Image img);
Since it sounds like you already know what format the byte[] array is in (e.g. RGB, ARGB, BGR etc.) you might be able to use BufferedImage.setRGB(...), or a combination of BufferedImage.getRaster() and WritableRaster.setPixels(...) or WritableRaster.setSamples(...). Unforunately both of these methods require you transform your byte[] into one of int[], float[] or double[] depending on the image format.
According to the Java docs, it looks like you need to use the MemoryImageSource Class to put your byte array into an object in memory, and then use Component.createImage(ImageProducer) next (passing in your MemoryImageSource, which implements ImageProducer).

Categories

Resources