最近做了一个用java Graphics2D 根据设计稿和原始图片生成一张新的图片的功能,感觉挺有意思,跟小伙伴们分享下,废话不多说直接上代码:
//1、提供给外部直接调用的方法中的主要代码
ShareImageUtil shareImageUtil = new ShareImageUtil(240 * 8, 426 * 8 + 20); RoundRectangle2D clip = new RoundRectangle2D.Double(8, 5, 35, 35, 10, 10); Font font = new Font("PingFangSC-Regular", Font.BOLD, 12 * 8); //画背景 shareImageUtil.drawBg(getImageInputStream("网络图片地址"), 0, 0, 240 * 8, 426 * 8 + 20, null); //画用户头像 clip = new RoundRectangle2D.Double(8 * 8, 5 * 8, 40 * 8, 40 * 8, 320, 320); shareImageUtil.drawImage(getImageInputStream(user.getAvatar()), 8 * 8, 5 * 8, 40 * 8, 40 * 8, clip, null); //画用户头像右边的title shareImageUtil.drawString("好友分享,给特别的你", 55 * 8, 29 * 8, new Color(51, 51, 51), font, null); //画商品主图 clip = new RoundRectangle2D.Double(8 * 8, 50 * 8, 223 * 8, 223 * 8, 10, 10); shareImageUtil.drawImage(getImageInputStream(groupDetailsData.getProductThumb()), 8 * 8, 50 * 8, 223 * 8, 223 * 8, clip, null); //画商品图片下面的字 int length = stringLength(groupDetailsData.getProductName()); if (length <= 35) { shareImageUtil.drawString(getStr(groupDetailsData.getProductName(), 0, 35), 8 * 8, 290 * 8, new Color(51, 51, 51), font, null); } else if (length > 35 && length < 67) { shareImageUtil.drawString(getStr(groupDetailsData.getProductName(), 0, 35), 8 * 8, 290 * 8, new Color(51, 51, 51), font, null); shareImageUtil.drawString(getStr(groupDetailsData.getProductName(), 35, 34), 10 * 8, 310 * 8, new Color(51, 51, 51), font, null); } else { shareImageUtil.drawString(getStr(groupDetailsData.getProductName(), 0, 35), 8 * 8, 290 * 8, new Color(51, 51, 51), font, null); shareImageUtil.drawString(getStr(groupDetailsData.getProductName(), 35, 33) + "...", 10 * 8, 310 * 8, new Color(51, 51, 51), font, null); } StringBuilder sb = new StringBuilder(); sb.append("groupId").append("=").append(groupId); InputStream qRCodeinputStream = qRCodeUtil.getQRCode(accessTocken, "pages/index", 430, sb.toString()); if (qRCodeinputStream == null) { return ResponseWrapper.markError(); } //画二维码 //clip = new RoundRectangle2D.Double(8 * 2,320 * 2, 100 * 2, 110 * 2, 10, 10); shareImageUtil.drawQRCodeImage(qRCodeinputStream, 8 * 8, 340 * 8, 80 * 8, 80 * 8, null, null); //画商品优惠价 font = new Font("PingFangSC-Regular", Font.BOLD, 18 * 8); shareImageUtil.drawString("¥" + groupDetailsData.getActualPrice().floatValue(), 110 * 8, 360 * 8, Color.red, font, null); //画商品原价 font = new Font("PingFangSC-Regular", Font.BOLD, 12 * 8); shareImageUtil.drawString("¥" + groupDetailsData.getPrice().floatValue(), 180 * 8, 360 * 8, new Color(153, 153, 153), font, null); //画删除线 shareImageUtil.drawStrikethrough(180 * 8, 355 * 8, 225 * 8, 355 * 8, new Color(122, 144, 153)); shareImageUtil.drawStrikethrough(180 * 8, 355 * 8 + 1, 225 * 8, 355 * 8 + 1, new Color(122, 144, 153)); shareImageUtil.drawStrikethrough(180 * 8, 355 * 8 + 2, 225 * 8, 355 * 8 + 2, new Color(122, 144, 153)); //画优惠券 //clip = new RoundRectangle2D.Double(110 * 2,380 * 2, 118 * 2, 45 * 2, 0, 0); shareImageUtil.drawImage(getImageInputStream("网络图片地址"), 110 * 8, 374 * 8, 118 * 8, 45 * 8, null, null); ByteArrayOutputStream output = new ByteArrayOutputStream(); ImageIO.write(shareImageUtil.graphicsGeneration(), "jpeg", output); result.put("code", 200); result.put("imageUrl", QiniuUploadFileUtils.uploadToQiNiu(output));
//2、相关工具类
private InputStream getImageInputStream(String imageUrl) throws IOException { URL url = new URL(imageUrl); //HttpURLConnection conn = (HttpURLConnection) url.openConnection(); try { // 连接超时 /*conn.setDoInput(true); conn.setDoOutput(true); conn.setConnectTimeout(25000); // 读取超时 --服务器响应比较慢,增大时间 conn.setReadTimeout(25000); conn.setRequestMethod("GET"); conn.addRequestProperty("Accept-Language", "zh-cn"); conn.addRequestProperty("Content-type", "image/jpeg"); conn.addRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 5.1; Trident/4.0; .NET CLR 2.0.50727)"); conn.connect();*/ url.openConnection(); return url.openStream(); } catch (Exception e) { logger.error("连接七牛云获取图片失败"); } return null; }
public class ShareImageUtil { private BufferedImage image; private int width; //图片的宽度 private int height; //图片的高度 Logger logger = LoggerFactory.getLogger(this.getClass()); public ShareImageUtil(int width, int height){ this.height = height; this.width = width; this.image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); } public BufferedImage graphicsGeneration(){ return this.image; } //画背景的方法 public void drawBg(InputStream inputStream, int x, int y,int width, int height, ImageObserver observer) throws IOException { try { Graphics2D main = image.createGraphics(); main.drawImage(javax.imageio.ImageIO.read(inputStream).getScaledInstance(width, height, Image.SCALE_SMOOTH), x, y, observer); main.dispose(); }catch (Exception e){ logger.info("微信分享朋友圈图片-画图失败,原因:{}",e.getMessage()); } } //画图的方法 public void drawImage(InputStream inputStream, int x, int y,int width, int height, RoundRectangle2D clip, ImageObserver observer) throws IOException { try{ Graphics2D imageGraphics = image.createGraphics(); RenderingHints renderingHints = new RenderingHints(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); renderingHints.put(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY); imageGraphics.setRenderingHints(renderingHints); if(clip != null){ imageGraphics.setClip(clip); } imageGraphics.drawImage(javax.imageio.ImageIO.read(inputStream).getScaledInstance(width, height, Image.SCALE_SMOOTH), x, y, width, height,null); imageGraphics.dispose(); if(inputStream != null){ inputStream.close(); } }catch (Exception e){ logger.info("微信分享朋友圈图片-画图失败,原因:{}",e.getMessage()); } } //画二维码的方法 public void drawQRCodeImage(InputStream inputStream, int x, int y,int width, int height, RoundRectangle2D clip, ImageObserver observer) throws IOException { try{ Graphics2D imageGraphics = image.createGraphics(); RenderingHints renderingHints = new RenderingHints(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); renderingHints.put(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY); imageGraphics.setRenderingHints(renderingHints); if(clip != null){ imageGraphics.setClip(clip); } imageGraphics.drawImage(javax.imageio.ImageIO.read(inputStream).getScaledInstance(width, height, Image.SCALE_SMOOTH), x, y, width, height,null); imageGraphics.dispose(); if(inputStream != null){ inputStream.close(); } }catch (Exception e){ logger.error("每天生成微信二维图片次数超过限制"); } } //画字的方法 public void drawString(String text, int x, int y, Color color, Font font, ImageObserver observer){ Graphics2D stringGra = image.createGraphics(); stringGra.getDeviceConfiguration().createCompatibleImage(this.width,this.height,Transparency.TRANSLUCENT); stringGra.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); stringGra.setColor(color); stringGra.setFont(font); stringGra.drawString(text, x, y); stringGra.dispose(); } //画长方形的方法 public void drawRectangle(int x, int y,int width, int height, Color color, Font font){ Graphics2D rectangleGra = image.createGraphics(); rectangleGra.setColor(color); rectangleGra.fillRect(x, y, width, height); rectangleGra.setColor(color); rectangleGra.drawRect(x, y, width, height); rectangleGra.setColor(color); rectangleGra.dispose(); } //画删除线的方法 public void drawStrikethrough(int fromX, int fromY,int toX, int toY, Color color){ Graphics2D strikethroughGra = image.createGraphics(); strikethroughGra.setColor(color); strikethroughGra.drawLine(fromX, fromY, toX, toY); strikethroughGra.dispose(); } /*public Font loadFont(File file, float fontSize){ //第一个参数是外部字体名,第二个是字体大小 try{ //File file = new File(fontFileName); FileInputStream aixing = new FileInputStream(file); Font dynamicFont = Font.createFont(Font.TRUETYPE_FONT, aixing); Font dynamicFontPt = dynamicFont.deriveFont(fontSize); aixing.close(); return dynamicFontPt; } catch(Exception e){//异常处理 e.printStackTrace(); return new Font("PingFang", Font.PLAIN, 12 * 2); } }*/ }