6

While Converting from JPG to PNG background transparency Image , I don't want a dotted border at converted image

My Original Image (JPG) My Original Image

My Converted Image (PNG)

enter image description here

My source code is

import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Toolkit;
import java.awt.image.BufferedImage;
import java.awt.image.FilteredImageSource;
import java.awt.image.ImageFilter;
import java.awt.image.ImageProducer;
import java.awt.image.RGBImageFilter;
import java.io.File;

import javax.imageio.ImageIO;

public class DemoTransparent {

    public static void main(String[] args) throws Exception {

        URL url = new URL("https://i.stack.imgur.com/jEqbx.jpg");
        Image  image1 = ImageIO.read(url);
        BufferedImage source = (BufferedImage) image1;
        int color = source.getRGB(0, 0);
        Image image = makeColorTransparent(source, new Color(color));
        BufferedImage transparent = imageToBufferedImage(image);
        File out = new File("D:\\Demo.png");
        ImageIO.write(transparent, "PNG", out);

    }

    private static BufferedImage imageToBufferedImage(Image image) {

        BufferedImage bufferedImage = new BufferedImage(image.getWidth(null), image.getHeight(null), BufferedImage.TYPE_4BYTE_ABGR_PRE);

        Graphics2D g2 = bufferedImage.createGraphics();
        g2.drawImage(image, 0, 0, null);
        g2.dispose();
        return bufferedImage;

    }

    public static Image makeColorTransparent(BufferedImage im, final Color color) {
        ImageFilter filter = new RGBImageFilter() {

            public int markerRGB = color.getRGB() | 0xFF000000;
            public final int filterRGB(int x, int y, int rgb) {
                if ((rgb | 0xFF000000) == markerRGB) {
                    return 0x00FFFFFF & rgb;
                } else {
                    return rgb;
                }
            }


        };
        ImageProducer ip = new FilteredImageSource(im.getSource(), filter);
        return Toolkit.getDefaultToolkit().createImage(ip);
    }

}

I want only png background transparency Image

Panchotiya Vipul
  • 1,226
  • 5
  • 17
  • 42
  • It's very possible that the areas that are not converting are not the exact same color that you're making transparent. Even if it's off by a tiny amount (0xFE000000 versus 0xFF000000) you're approach will ignore the pixel. – Mark Sholund Nov 07 '15 at 04:57

1 Answers1

7

Normally what we do to extract a color which is exactly equal or nearly equal to a color is take a threshold.

Here is your code with little modifications :

// Take another parameter i.e. threshold
public static Image makeColorTransparent(BufferedImage im, final Color color, float threshold) {
    ImageFilter filter = new RGBImageFilter() {
        public float markerAlpha = color.getRGB() | 0xFF000000;
        public final int filterRGB(int x, int y, int rgb) {
            int currentAlpha = rgb | 0xFF000000;           // just to make it clear, stored the value in new variable
            float diff = Math.abs((currentAlpha - markerAlpha) / markerAlpha);  // Now get the difference
            if (diff <= threshold) {                      // Then compare that threshold value
                return 0x00FFFFFF & rgb;
            } else {
                return rgb;
            }
        }
    };
    ImageProducer ip = new FilteredImageSource(im.getSource(), filter);
    return Toolkit.getDefaultToolkit().createImage(ip);
}

Then call the function as makeColorTransparent(image, color, 0.05f);
But there is a problem in your image. The color of pixels on the corners of oval is exactly equal to the colors of pixel inside (at bottom right) of the oval. So algo is also removing those pixels.

And sadly you cannot include those pixels. I tried to do it with different threshold values. But either the corners are included or some pixels of oval are getting removed. What you can do for this is to use 0.05f as threshold and then paint the areas where you want by hand (Using photoshop or any simple image editor).

enter image description here

afzalex
  • 8,598
  • 2
  • 34
  • 61
  • Thanks for answer but when I convert image display white dotted in bottom of image – Panchotiya Vipul Nov 07 '15 at 05:30
  • Yeah @PanchotiyaVipul, I already explained reason for it. And it is sad that it can't be ignored. – afzalex Nov 07 '15 at 05:32
  • 1
    Or another idea is to compare values of nearby pixels and if x% of nearby pixels pass a condition then include it otherwise exclude that pixel. But I doubt if that approach will work. – afzalex Nov 07 '15 at 05:35
  • If the image has always that shape, apply a mask before making pixels transparent – Stephan Nov 07 '15 at 06:08
  • Excellent answer, that is what I was getting at in my comment but I couldn't take it to actual code on my phone. – Mark Sholund Nov 07 '15 at 21:08