Here is the code I have now:
File file= new File("C:\Documents and Settings\vasanth\Desktop\s.PNG");
BufferedImage image;
try {
image = ImageIO.read(file);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Raster raster = image.getRaster();
BufferedImage image2 = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_RGB);
WritableRaster raster2 = image2.getRaster();
BufferedImage image3 = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_RGB);
WritableRaster raster3 = image3.getRaster();
Should I keep the image that I am using here? Even though I have specified the full path to the image file, I still get an error.
Use double slash in java strings. Single slash is considered a character escape sequence.
So you should open the file like so:
File file= new File("C:\\Documents and Settings\\vasanth\\Desktop\\s.PNG");
Along with what Ivaylo said, have a look at this portion of code:
BufferedImage image;
try {
image = ImageIO.read(file);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Raster raster = image.getRaster();
Have you considered what happens if you have an exception assigning image? You will call a method on a null object and that will kill your app entirely with a NullPointerException.
You need to stop whatever you wanted to do with the image if an exception occurs. You can put all of it within the try...catch block to fix this.
Related
Using Selenium Webdriver to take screenshot for specific UI Element as suggested by other post, I am using getSubimage method to capture the screenelement. But, receiving failure exception.
I am unsure about the difference in uielement's getLocation().getX() and getSize().getWidth().getX(). If someone can clarify this, as inside the WritableRaster method's condition it always checks for y+height
File imgSrc=((TakesScreenshot)driver).getScreenshotAs(OutputType.FILE);
Point point = uiElem.getLocation();
Point bottomright = new Point(uiElem.getSize().getWidth(),
uiElem.getSize().getHeight());
int xcord = point.getX();
int ycord = point.getY();
BufferedImage img;
try {
img = ImageIO.read(imgSrc);
BufferedImage dest = img.getSubimage(xcord, ycord, bottomright.getX(), bottomright.getY());
ImageIO.write(dest, "png", imgSrc);
FileUtils.copyFile(imgSrc, new File(".\\Screenshots\\123.png"));
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
While debugging, I noticed that the img (width 1366 and height = 613). and getSubImage() has (194,1335,960,15). It will always fail for condition (y+ height) >(this.minY + this.height ) inside createWritableChildMethod. So,can anyone point,where it's going wrong, also it doesn't make sense , as why we adding (y+height)of sub-image is greater?
Found a workaround, just notices it's better to use getScreenshotAs() directly on UIElement without doing alot of manipulation on the element.
public void takeSmallScreenshot(WebDriver driver, WebElement uiElem)
{
File uiElementSrc = uiElem.getScreenshotAs(OutputType.FILE);
try {
FileUtils.copyFile(uiElementSrc, new File(".\\Screenshots\\"+uiElem.getText().substring(0,5)+".png"));
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
I have an image and I do somethings with it, finally I get an BufferedImage object(the sub image of original image), now I want to save the sub image to FastDFS without save it in my local, what should I do?
I have already save sub image as file to my local, but I don't want to do like this, because it makes waste.
String oriPicPathInFastDFS = "http://127.0.0.1/xx/xx/xx/xx";
BufferedImage image = null;
try {
image = ImageIO.read(new URL(oriPicPathInFastDFS));
} catch (IOException e) {
e.printStackTrace();
}
// do something
// this is the sub image that I want to save to FastDFS
BufferedImage subImage = image.getSubimage(5, 5, 5, 5);
// these code can save the sub image to my local and then upload to fastDFS
String localPath = "/home/xx/x/xx.jpg";
File detectionFile = new File(localPath);
try {
detectionFile.createNewFile();
ImageIO.write(subImage, "jpg", detectionFile);
} catch (IOException e) {
e.printStackTrace();
}
// upload to fast dfs
I want to upload the subImage to fastDFS without save it to my local.
Fine, I got a method to solve this question.
// change the BufferedImage to byte[]
ByteArrayOutputStream out = new ByteArrayOutputStream();
try {
boolean flag = ImageIO.write(sunImage, "jpg", out);
} catch (IOException e) {
e.printStackTrace();
}
byte[] byteArray = out.toByteArray();
// then save the byteArray to fast DFS
I have the code below on a tomcat server. The goal is to save in .jpg an image (that is sent in String) and create the equivalent thumbnails.
The goal is properly achieved nevertheless I noticed that at every execution (even after trying to set almost all used variables "null"), the server memomy increases by 6 Megabytes which are never freed. Since I have a very small RAM's server, this is really problematic. By the way images sent are close to 30 kilobytes only.
public boolean saveImage(String picInString)
throws IOException {
byte[] bytes = null;
try {
bytes = Base64.decode(picInString);
} catch (Base64DecodingException e) {
e.printStackTrace(System.out);
}
ByteArrayInputStream bis = new ByteArrayInputStream(bytes);
Iterator<?> readers = ImageIO.getImageReadersByFormatName("png");
ImageReader reader = (ImageReader) readers.next();
Object source = bis;
ImageInputStream iis = ImageIO.createImageInputStream(source);
Graphics2D g2 = null;
try {
reader.setInput(iis, true);
ImageReadParam param = reader.getDefaultReadParam();
Image image = reader.read(0, param);
// got an image file
BufferedImage bufferedImage = new BufferedImage(image.getWidth(null),
image.getHeight(null), BufferedImage.TYPE_INT_RGB);
// bufferedImage is the RenderedImage to be written
g2 = bufferedImage.createGraphics();
g2.drawImage(image, null, null);
ImageIO.write(bufferedImage, "jpg", new File("/image.jpg"));
ImageIO.write(Scalr.resize(MyImageClass.cropImage(bufferedImage), 100, 100),
"jpg", new File("/image_mini.jpg"));
bufferedImage.flush();
bufferedImage = null;
} catch (Exception e) {
e.printStackTrace(System.out);
} finally {
if (reader != null) {
reader.dispose();
}
if (g2 != null) {
g2.dispose();
}
bis.close();
iis.close();
reader = null;
bis = null;
iis = null;
}
return false;
}
Any help will be appreciated!
Someone gave me a clue to the answer but I am not able to see the comment anymore.
Actually, setting the variable "image" to null at the end of the process has solved the issue.
You shouldn't tame an image as it is. You should down sample it like it is done in android. Scaling is a must to prevent memory errors and exceptions. This SO questions is the solution to all your problems.
How to improve the performance of g.drawImage() method for resizing images
I am a beginner in java, and I am trying to write a simple screen-capture program. I wrote a simple SWING desktop app with a button and a text-field, and what I am trying to do is, when a user clicks that button the app takes a snapshot of the screen using awt.Robot, and sends that image and the text to a PHP script on my server.
My snapshot function so far is:
private void takeSnapShot(){
try {
Robot robot = new Robot();
Rectangle area = new Rectangle(Toolkit.getDefaultToolkit().getScreenSize());
BufferedImage bufferedImage = robot.createScreenCapture(area);
//Try to save the captured image
try {
File file = new File("screenshot_full.png");
ImageIO.write(bufferedImage, "png", file);
} catch (IOException ex) {
Logger.getLogger(ScrCaptFrm.class.getName()).log(Level.SEVERE, null, ex);
}
} catch (AWTException ex) {
Logger.getLogger(ScrCaptFrm.class.getName()).log(Level.SEVERE, null, ex);
}
}
As you can see it's fairly simple so far, however I am not sure how to send that image to my PHP script without actually storing the image on user's PC.
Oh and I am using apache httpClient library for communicating to the web server. For the text I guess I can pass it in the URL as a get query, but I am not sure what to do about the image.
ImageIO.write can to an OutputStream of your choice.
So if you don't want to write the image to a File, you can simply write it to a different stream instead...
For example...
OutputStream os = null;
try {
Robot robot = new Robot();
Rectangle area = new Rectangle(Toolkit.getDefaultToolkit().getScreenSize());
BufferedImage bufferedImage = robot.createScreenCapture(area);
//Try to save the captured image
try {
os = ...;
ImageIO.write(bufferedImage, "png", os);
} catch (IOException ex) {
Logger.getLogger(ScrCaptFrm.class.getName()).log(Level.SEVERE, null, ex);
} finally {
try {
os.close();
} catch (Exception exp) {
}
}
} catch (AWTException ex) {
Logger.getLogger(ScrCaptFrm.class.getName()).log(Level.SEVERE, null, ex);
}
Of course, I have no idea where you're sending the data, so you'll need to define the OutputStream yourself.
If you have the memory for it, you could write it a ByteArrayOutputStream and then write this to whatever output stream you need in the future...
To slightly modify your existing method, perhaps you could use a temporarily file and then delete it when you are finished with it. Perhaps it might look something like:
private void takeSnapShot(){
try {
Robot robot = new Robot();
Rectangle area = new Rectangle(Toolkit.getDefaultToolkit().getScreenSize());
BufferedImage bufferedImage = robot.createScreenCapture(area);
//Try to save the captured image
try {
File file = File.createTempFile(Long.toString(System.currentTimeMillis()), ".png");
ImageIO.write(bufferedImage, "png", file);
//send image
file.delete();
} catch (IOException ex) {
Logger.getLogger(ScrCaptFrm.class.getName()).log(Level.SEVERE, null, ex);
}
} catch (AWTException ex) {
Logger.getLogger(ScrCaptFrm.class.getName()).log(Level.SEVERE, null, ex);
}
}
Another alternative would be to construct an int[][] from your BufferedImage which will hold the RGB values for every pixel of the image:
public int[][] getColors(final BufferedImage image){
assert image != null;
final int[][] colors = new int[image.getWidth()][image.getHeight()];
for(int x = 0; x < colors.length; x++)
for(int y = 0; y < colors[x].length; y++)
colors[x][x] = image.getRGB(x, y);
return colors;
}
I am a little unsure about what you hope to achieve; What do you plan on doing with the image?
Why don't you make this a WebsService and let your PHP consume it? You could send the binary data through the WebsService using some sort of Base64 encoder.
You could do this to get the bytes of the BufferedImage:
byte[] binaryData = ((DataBufferByte) bufferedImage.getData().getDataBuffer()).getData();
I am trying to convert a PNG image to a JPEG image following this tutorial. But I encounter a problem. The resulting image has a pink layer.
Does anyone have a solution for this problem? Or what code should I use in order to convert the image into the desired format?
Thanks in advance!
Create a BufferedImage of desired size, e.g.:
BufferedImage img = new BufferedImage(w,h,BufferedImage.TYPE_INT_RGB)
fill it with a proper background color:
img.getGraphics().fillRect(....)
Call drawImage on the image's graphics atop of that background:
img.getGraphics().drawImage(image, 0, 0, null);
then write down your image as JPG as usual.
Which color mode are you using? While you create buffered image object, try adding the type like this option.
File newFile = new File(path + fileName + "." + Strings.FILE_TYPE);
Image image = null;
try {
image = ImageIO.read(url); // I was using an image from web
} catch (IOException e1) {
e1.printStackTrace();
}
image = image.getScaledInstance(width, height, Image.SCALE_SMOOTH);
try {
BufferedImage img = toBufferedImage(image);
ImageIO.write(img, "jpg", newFile);
} catch (IOException e) {
e.printStackTrace();
}
}
private static BufferedImage toBufferedImage(Image src) {
int w = src.getWidth(null);
int h = src.getHeight(null);
int type = BufferedImage.TYPE_INT_RGB; // other options
BufferedImage dest = new BufferedImage(w, h, type);
Graphics2D g2 = dest.createGraphics();
g2.drawImage(src, 0, 0, null);
g2.dispose();
return dest;
}