java 签名抠图

1import com.drew.imaging.ImageMetadataReader; 2import com.drew.imaging.ImageProcessingException; 3import com.drew.metadata.Directory; 4import com.drew.metadata.Metadata; 5import com.drew.metadata.Tag; 6 7import javax.imageio.ImageIO; 8import javax.swing.*; 9import java.awt.*; 10import java.awt.image.BufferedImage; 11import java.io.*; 12 13public class ImageUtils { 14 15 16 /** 17 * 图片去白色的背景,并裁切 18 * 19 * @param image 图片 20 * @param range 范围 1-255 越大 容错越高 去掉的背景越多 21 * @return 图片 22 * @throws Exception 异常 23 */ 24 public static byte[] transferAlpha(Image image, InputStream in, int range) throws Exception { 25 ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); 26 try { 27 ImageIcon imageIcon = new ImageIcon(image); 28 BufferedImage bufferedImage = new BufferedImage(imageIcon 29 .getIconWidth(), imageIcon.getIconHeight(), 30 BufferedImage.TYPE_4BYTE_ABGR); 31 Graphics2D g2D = (Graphics2D) bufferedImage.getGraphics(); 32 g2D.drawImage(imageIcon.getImage(), 0, 0, imageIcon 33 .getImageObserver()); 34 int alpha = 0; 35 int minX = bufferedImage.getWidth(); 36 int minY = bufferedImage.getHeight(); 37 int maxX = 0; 38 int maxY = 0; 39 40 for (int j1 = bufferedImage.getMinY(); j1 < bufferedImage 41 .getHeight(); j1++) { 42 for (int j2 = bufferedImage.getMinX(); j2 < bufferedImage 43 .getWidth(); j2++) { 44 int rgb = bufferedImage.getRGB(j2, j1); 45 46 int R = (rgb & 0xff0000) >> 16; 47 int G = (rgb & 0xff00) >> 8; 48 int B = (rgb & 0xff); 49 if (((255 - R) < range) && ((255 - G) < range) && ((255 - B) < range)) { //去除白色背景; 50 rgb = ((alpha + 1) << 24) | (rgb & 0x00ffffff); 51 } else { 52 minX = minX <= j2 ? minX : j2; 53 minY = minY <= j1 ? minY : j1; 54 maxX = maxX >= j2 ? maxX : j2; 55 maxY = maxY >= j1 ? maxY : j1; 56 } 57 bufferedImage.setRGB(j2, j1, rgb); 58 } 59 } 60 int width = maxX - minX; 61 int height = maxY - minY; 62 BufferedImage sub = bufferedImage.getSubimage(minX, minY, width, height); 63 int degree = getDegree(in); 64 sub = rotateImage(sub,degree); 65 ImageIO.write(sub, "png", byteArrayOutputStream); 66 67 } catch (Exception e) { 68 e.printStackTrace(); 69 throw e; 70 } 71 72 return byteArrayOutputStream.toByteArray(); 73 } 74 75 /** 76 * 图片旋转 77 * @param bufferedimage bufferedimage 78 * @param degree 旋转的角度 79 * @return BufferedImage 80 */ 81 public static BufferedImage rotateImage(final BufferedImage bufferedimage, 82 final int degree) { 83 int w = bufferedimage.getWidth(); 84 int h = bufferedimage.getHeight(); 85 Rectangle rect_des = CalcRotatedSize(new Rectangle(new Dimension( 86 w, h)), degree); 87 int type = bufferedimage.getColorModel().getTransparency(); 88 BufferedImage img; 89 Graphics2D graphics2d; 90 (graphics2d = (img = new BufferedImage(rect_des.width, rect_des.height, type)) 91 .createGraphics()).setRenderingHint( 92 RenderingHints.KEY_INTERPOLATION, 93 RenderingHints.VALUE_INTERPOLATION_BILINEAR); 94 graphics2d.translate((rect_des.width - w) / 2, 95 (rect_des.height - h) / 2); 96 graphics2d.rotate(Math.toRadians(degree), w / 2, h / 2); 97 graphics2d.drawImage(bufferedimage, 0, 0, null); 98 graphics2d.dispose(); 99 return img; 100 } 101 102 /** 103 * 计算旋转后图像的大小 104 * @param src Rectangle 105 * @param degree 旋转的角度 106 * @return Rectangle 107 */ 108 public static Rectangle CalcRotatedSize(Rectangle src, int degree) { 109 if (degree >= 90) { 110 if(degree / 90 % 2 == 1){ 111 int temp = src.height; 112 src.height = src.width; 113 src.width = temp; 114 } 115 degree = degree % 90; 116 } 117 118 double r = Math.sqrt(src.height * src.height + src.width * src.width) / 2; 119 double len = 2 * Math.sin(Math.toRadians(degree) / 2) * r; 120 double angel_alpha = (Math.PI - Math.toRadians(degree)) / 2; 121 double angel_dalta_width = Math.atan((double) src.height / src.width); 122 double angel_dalta_height = Math.atan((double) src.width / src.height); 123 124 int len_dalta_width = (int) (len * Math.cos(Math.PI - angel_alpha 125 - angel_dalta_width)); 126 int len_dalta_height = (int) (len * Math.cos(Math.PI - angel_alpha 127 - angel_dalta_height)); 128 int des_width = src.width + len_dalta_width * 2; 129 int des_height = src.height + len_dalta_height * 2; 130 return new java.awt.Rectangle(new Dimension(des_width, des_height)); 131 } 132 133 /** 134 * byte[] ------>BufferedImage 135 * 136 * @param byteImage byteImage 137 * @return return 138 * @throws IOException IOException 139 */ 140 public static BufferedImage ByteToBufferedImage(byte[] byteImage) throws IOException { 141 ByteArrayInputStream in = new ByteArrayInputStream(byteImage); 142 return ImageIO.read(in); 143 } 144 145 146 /** 147 * 获取照片信息的旋转角度 148 * @param inputStream 照片的路径 149 * @return 角度 150 */ 151 public static int getDegree(InputStream inputStream) { 152 try { 153 Metadata metadata = ImageMetadataReader.readMetadata(new BufferedInputStream(inputStream),true); 154 for (Directory directory : metadata.getDirectories()) { 155 for (Tag tag : directory.getTags()) { 156 if ("Orientation".equals(tag.getTagName())) { 157 return turn(getOrientation(tag.getDescription())); 158 } 159 } 160 } 161 } catch (ImageProcessingException e) { 162 e.printStackTrace(); 163 return 0; 164 } catch (IOException e) { 165 e.printStackTrace(); 166 return 0; 167 } 168 return 0; 169 } 170 171 /** 172 * 获取旋转的角度 173 * @param orientation orientation 174 * @return 旋转的角度 175 */ 176 public static int turn(int orientation) { 177 Integer turn = 360; 178 if (orientation == 0 || orientation == 1) { 179 turn = 360; 180 } else if (orientation == 3) { 181 turn = 180; 182 } else if (orientation == 6) { 183 turn = 90; 184 } else if (orientation == 8) { 185 turn = 270; 186 } 187 return turn; 188 } 189 190 /** 191 * 根据图片自带的旋转的信息 获取 orientation 192 * @param orientation orientation 193 * @return orientation 194 */ 195 public static int getOrientation(String orientation) { 196 int tag = 0; 197 if ("Top, left side (Horizontal / normal)".equalsIgnoreCase(orientation)) { 198 tag = 1; 199 } else if ("Top, right side (Mirror horizontal)".equalsIgnoreCase(orientation)) { 200 tag = 2; 201 } else if ("Bottom, right side (Rotate 180)".equalsIgnoreCase(orientation)) { 202 tag = 3; 203 } else if ("Bottom, left side (Mirror vertical)".equalsIgnoreCase(orientation)) { 204 tag = 4; 205 } else if ("Left side, top (Mirror horizontal and rotate 270 CW)".equalsIgnoreCase(orientation)) { 206 tag = 5; 207 } else if ("Right side, top (Rotate 90 CW)".equalsIgnoreCase(orientation)) { 208 tag = 6; 209 } else if ("Right side, bottom (Mirror horizontal and rotate 90 CW)".equalsIgnoreCase(orientation)) { 210 tag = 7; 211 } else if ("Left side, bottom (Rotate 270 CW)".equalsIgnoreCase(orientation)) { 212 tag = 8; 213 } 214 return tag; 215 } 216}
点赞
收藏

评论区

加载中...

相关推荐

MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1

文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s

Oracle 分组与拼接字符串同时使用

SELECTT.,ROWNUMIDFROM(SELECTT.EMPLID,T.NAME,T.BU,T.REALDEPART,T.FORMATDATE,SUM(T.S0)S0,MAX(UPDATETIME)CREATETIME,LISTAGG(TOCHAR(

手写Java HashMap源码

HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22

Java日期时间API系列31

  时间戳是指格林威治时间1970年01月01日00时00分00秒起至现在的总毫秒数,是所有时间的基础,其他时间可以通过时间戳转换得到。Java中本来已经有相关获取时间戳的方法,Java8后增加新的类Instant等专用于处理时间戳问题。 1获取时间戳的方法和性能对比1.1获取时间戳方法Java8以前

Java爬虫之JSoup使用教程

title:Java爬虫之JSoup使用教程date:201812248:00:000800update:201812248:00:000800author:mecover:https://imgblog.csdnimg.cn/20181224144920712(https://www.oschin

Java日期时间API系列35

  通过Java日期时间API系列1Jdk7及以前的日期时间类(https://www.oschina.net/action/GoToLink?urlhttps%3A%2F%2Fwww.cnblogs.com%2Fxkzhangsanx%2Fp%2F12032719.html)中得知,Java8以前除了java.sql.Timestamp扩充