I am trying to rotate an image in Java, but when I do the transparency in the png goes away. Is there any way i can rotate the image AND keep the transparency?
AffineTransform trans = new AffineTransform();
trans.setTransform(identity);
trans.translate(100, 100);
trans.rotate( Math.toRadians(45) );
gr.drawImage(image.getImage(), trans, this);
This makes the transparency in the png black, but
gr.drawImage(image.getImage(), 0, 200, null);
Has no problem with the transparency.
Try to set rendering hints on Graphics2D object.
gr.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY );
Check reference for optimal settings.
Related
by using Canvas and JS I can draw a shape like this and have the x,y of each point :
Tha area can be choosen by more than 4 points, look at this link to have an idea.
I need to save and crop the image of the selected area by using the points. I can not use BufferedImage as it is just rectangular. Which lib in java I can use?
Okay, so starting with...
I used...
BufferedImage source = ImageIO.read(new File("Example.jpg"));
GeneralPath clip = new GeneralPath();
clip.moveTo(65, 123);
clip.lineTo(241, 178);
clip.lineTo(268, 405);
clip.lineTo(145, 512);
clip.closePath();
Rectangle bounds = clip.getBounds();
BufferedImage img = new BufferedImage(bounds.width, bounds.height, BufferedImage.TYPE_INT_ARGB);
Graphics2D g2d = img.createGraphics();
clip.transform(AffineTransform.getTranslateInstance(-65, -123));
g2d.setClip(clip);
g2d.translate(-65, -123);
g2d.drawImage(source, 0, 0, null);
g2d.dispose();
ImageIO.write(img, "png", new File("Clipped.png"));
to generate...
Now, the image is rectangular, that's just the way it works
Now, setClip is quite rough and isn't effect by any RenderingHints, you could make use of "soft clipping" instead, which is more involved, but generates a nicer results. See this example and this exmaple for more details
I need a function/method that can mold(crop and resize) an imported (.png format) image into a circle of exact 150x150 pixels and it should keep transparency. I have searched all over internet, also I have my own code but I think its completely useless. I need this function for a code I am using to make GUI of a social-media app database.
private ImageIcon logo = new ImageIcon(getClass().getResource("/test/test200x200.png"));
toCircle(logo);
I need the code for the following function:
public ImageIcon toCircle(ImageIcon icon)
{
//code
return icon;
}
This function should convert this picture:
To this:
Create a new transparent image
Get a Graphics object from the image.
Set a clip for the graphics object.
Paint the PNG format image.
See also this answer that uses a clipped region.
An alternative approach, that might be more straight-forward to implement for this use case, is:
Create a transparent BufferedImage the size of your icon
Create Graphics2D from image, set hints for antialias
Fill a circle the size of your background circle
Draw the image on top of your circle, using AlphaComposite.SrcIn
Something like:
public Icon toCircle(ImageIcon logo) {
BufferedImage image = new BufferedImage(150, 150); // Assuming logo 150x150
Graphics2D g = image.createGraphics();
g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g.fillOval(1, 1, 148, 148); // Leaving some room for antialiasing if needed
g.setComposite(AlphaComposite.SrcIn);
g.drawImage(logo.getImage(), 0, 0, null);
g.dispose();
return new ImageIcon(image);
}
I have some problem with string antialiasing in Java. If I use this code
g.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
on normal (not rotated string), all is fine. But, when I try use antialiasing on rotated image, where I draw string - this string rendering without antialiasing feature.
This is example of my code, where antialiasing doesn't work:
Graphics2D g = originalImage.createGraphics();
AffineTransform affineTransform2 = new AffineTransform();
affineTransform2.setToIdentity();
affineTransform2.translate(125, 325);
affineTransform2.rotate(Math.toRadians(345));
BufferedImage positionImage = new BufferedImage(100, 40, BufferedImage.TYPE_INT_ARGB);
Graphics2D positionImageG2D = positionImage.createGraphics();
positionImageG2D.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
positionImageG2D.setFont(getFont(30f));
positionImageG2D.drawString("Some Text",100, 40);
positionImageG2D.dispose();
g.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
g.drawImage(positionImage, affineTransform2, null);
You don't draw text to g (last line), so whatever value you pass to KEY_TEXT_ANTIALIASING won't have any effect.
You are drawing a rotated image with already antialiased text. Try setting KEY_INTERPOLATION to VALUE_INTERPOLATION_BICUBIC or VALUE_INTERPOLATION_BILINEAR, which should effect scaling and rotation of images.
Another thing you could try, is to draw the text (rotated) directly onto g, without the temporary image. Should also work, but you might have to adjust positioning relative to the rotation.
The below code resizes an image. Unfortunately the image which is a vertical image has black bars on the sides. It looks as though the transparent, or blank space is being filled with black. I've tried setting the background color to white, and using alphaRGB but can't seem to shake it.
OrderProductAssetEntity orderProductAssetEntity = productAssets.get(jobUnitEntity.getId());
File asset = OrderProductAssetService.getAssetFile(orderProductAssetEntity);
if (asset.exists()) {
//resize the asset to a smaller size
BufferedImage resizedImage = new BufferedImage(200, 200, BufferedImage.TYPE_INT_RGB);
Graphics2D g = resizedImage.createGraphics();
g.setBackground(Color.WHITE);
g.drawImage(ImageIO.read(asset), 0, 0, width, height, null);
g.dispose();
jobUnitImages.put(orderProductAssetEntity.getOriginalLocation(), new PDJpeg(document, resizedImage));
} else {
jobUnitImages.put(orderProductAssetEntity.getOriginalLocation(), null);
}
First, if you need transparency, BufferedImage.TYPE_INT_RGB won't work, you'll need BufferedImage.TYPE_INT_ARGB. Not sure if you already tried it, just want to be clear.
Second, this line:
g.setBackground(Color.WHITE);
...does only set the current background color for the graphics context. It does not fill the background with that color. For that, you'll need to do g.clearRect(0, 0, width, height) as well. But I usually prefer to use g.setColor(...) and g.fillRect(...) instead to avoid confusion.
Or, if you like, you can also use the drawImage method that takes a Color as the second last parameter like this:
g.drawImage(image, 0, 0, width, height, Color.WHITE, null);
EDIT:
Third, the class name PDJpeg implies that the image is later stored as JPEG, so you will probably lose transparency anyway. So the best is probably to stick with TYPE_INT_RGB, and fill the background with the right color (and do it the right way ;-).
I created an ARGB BufferedImage. Now I'd like to reinitialize it with a transparent background. I tried the following code:
(...)
if( this.offscreen==null ||
this.offscreen.getWidth()!= dim.width ||
this.offscreen.getHeight()!= dim.height )
{
this.offscreen=new BufferedImage(
dim.width,
dim.height,
BufferedImage.TYPE_INT_ARGB);
}
Graphics2D g=this.offscreen.createGraphics();
g.setColor(new Color(255,255,255,0));
g.clearRect(0, 0, dim.width, dim.height);
(...)
but it didn't work.
Any idea on how to do this please ?
Thanks !
g.clearRect(..) fills the selected rectangle with the background colour of the Graphics2D object. You're better off doing g.fillRect(..) which would give the intended result with your code, or set the background colour of the Graphics2D object beforehand (g.setBackground(..)).
Also, you may have to do g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC)); before the fill so that it sets the buffer properly (ignore destination buffer data, only use source data -- in this case, the fill operation). Not sure what the default is for this value, but you should set it back to that afterwards to ensure proper operation.
I had this problem before and I solved it with a really narrow trick.
Here is the deal:
In the constructor of the paint Class take a screen shot of the System but be careful
BufferedImage image = new Robot().createScreenCapture(new Rectangle(0, 23, xScreen, yScreen));
And where you want to clear the screen
g2D.drawImage(image, null, /*your Image observer*/);