阿里云OSS上传PDF文件同时加上图片水印"/>
阿里云OSS上传PDF文件同时加上图片水印
根据IO流的处理,简单思想是在上传主机建立一个临时文件 存放加水印之后的新PDF文件,上传服务器完成之后 删除临时文件
具体代码如下:
1、针对普通的文件上传 如果知道本地路径可以通过简单方法加水印
public static void main(String[] args) throws DocumentException, IOException { // // 要输出的pdf文件 // BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(new File("D:/conc.pdf"))); // String waterMarkName = "美丽修行"; // // 将pdf文件先加水印然后输出setWatermark(bos, "D:/1.pdf", waterMarkName); // setImgWatermark(bos, "D:/1.pdf","D:/111.png");addTextWaterMark("D:/conc1.pdf","D:/conc2.pdf",waterMarkName);// 添加水印之后的文件 如果不存在会新建BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(new File("D:/out.pdf")));// 将pdf文件先加水印然后输出setImgWatermark(bos, "D:/conc2.pdf", "D:/11.png");}
1.1、添加文本水印
public static void setWatermark(BufferedOutputStream bos, String input, String waterMarkName)throws DocumentException, IOException {PdfReader reader = new PdfReader(input);PdfStamper stamper = new PdfStamper(reader, bos);int total = reader.getNumberOfPages() + 1;PdfContentByte content;BaseFont base = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.EMBEDDED);PdfGState gs = new PdfGState();Rectangle pageRect = null;//初始化水印labelJLabel label = new JLabel();FontMetrics metrics;int textH = 0;int textW = 0;label.setText(waterMarkName);metrics = label.getFontMetrics(label.getFont());textH = metrics.getHeight();textW = metrics.stringWidth(label.getText());for (int i = 1; i < total; i++) {pageRect = reader.getPageSizeWithRotation(i);content = stamper.getOverContent(i);// 在内容上方加水印// content = stamper.getUnderContent(i);//在内容下方加水印//設置透明度gs.setFillOpacity(0.001f);// content.setGState(gs);content.beginText();content.setColorFill(BaseColor.LIGHT_GRAY);content.setFontAndSize(base, 20); // content.showTextAligned(Element.ALIGN_CENTER, waterMarkName, 300, 350, 55);//计算长款铺满整屏for (int height = interval + textH; height < pageRect.getHeight(); height = height + textH*7) {for (int width = interval + textW; width < pageRect.getWidth() + textW; width = width + textW*7){content.showTextAligned(Element.ALIGN_LEFT,waterMarkName, width - textW,height - textH, 30);}}content.endText();}stamper.close();}
/** *2、 添加图片水印* @param bos 输出文件的位置* @param input* 原PDF位置* @param imgSrc 水印图片路径* 权限码* @throws DocumentException* @throws IOException*/ public static void setImgWatermark(BufferedOutputStream bos, String input, String imgSrc)throws DocumentException, IOException {PdfReader reader = new PdfReader(input);PdfStamper stamper = new PdfStamper(reader, bos);Rectangle pageRect = null;int total = reader.getNumberOfPages() + 1;PdfContentByte content;BaseFont base = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.EMBEDDED);PdfGState gs = new PdfGState();float imgH = 0;float imgW = 0;Image image = Image.getInstance(imgSrc);//设置水印的覆盖尺寸image.scaleToFit(300, 300);imgH = image.getScaledHeight();imgW = image.getScaledWidth();for (int i = 1; i < total; i++) {content = stamper.getOverContent(i);// 在内容上方加水印pageRect = reader.getPageSizeWithRotation(i);gs.setFillOpacity(0.2f);content.beginText();content.setColorFill(BaseColor.BLACK);content.setFontAndSize(base, 8);//你可以随心所欲的改你自己想要的角度for (float height = interval + imgH; height < pageRect.getHeight()+ imgH; height = height + imgH ) {for (float width = interval + imgW; width < pageRect.getWidth() + imgW; width = width + imgW) {image.setAbsolutePosition(width - imgW, height - imgH); // set the first backgroundcontent.addImage(image);content.showTextAligned(Element.ALIGN_CENTER, "1111", width - imgW, height - imgH, 30);}}content.endText();}stamper.close(); }
本来写了一个根据文件名来处理的方法,后来发现OSS文件上传的实体类MultipartFile 文件对象里面并不能拿到文件的本地路径,所以改为如下方式;
public static MultipartFile addPicMarkToMutipartFileNew(MultipartFile multipartFile, cn.bevol.bebd.model.entitymon.File waterMark) throws IOException ,DocumentException{if(null==waterMark||null==waterMark.getFileSrc()){throw ExceptionConstant.bussinessException(ExceptionCodeEnum.waterMarkIsNull);}Image image = Image.getInstance(waterMark.getFileSrc());if(null==image){throw ExceptionConstant.bussinessException(ExceptionCodeEnum.waterMarkIsNull);}final File pdfFile = File.createTempFile("temp", ".pdf");//创建临时文件log.info("临时文件所在的本地路径:" + pdfFile.getCanonicalPath());BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(pdfFile));// 获取文件名 // BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(new File("D:/out111.pdf")));String originFileName = multipartFile.getOriginalFilename();// 获取原文件后缀int lastSplit = originFileName.lastIndexOf(".");String suffix = originFileName.substring(lastSplit + 1);// 获取文件原始信息String dOriginFileName = multipartFile.getOriginalFilename();String dContentType = multipartFile.getContentType();// 是Pdf才加水印if (suffix.equalsIgnoreCase("pdf") ) {InputStream inputStream = multipartFile.getInputStream();PdfReader reader = new PdfReader(inputStream);PdfStamper stamper = new PdfStamper(reader, bos);Rectangle pageRect = null; // 添加水印的时候,就已经在outputStream写入了int total = reader.getNumberOfPages() + 1;PdfContentByte content;BaseFont base = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.EMBEDDED);PdfGState gs = new PdfGState();float imgH = 0;float imgW = 0; // Image image = Image.getInstance("D:/11.png");//设置水印的覆盖尺寸image.scaleToFit(300, 300);imgH = image.getScaledHeight();imgW = image.getScaledWidth();for (int i = 1; i < total; i++) {content = stamper.getOverContent(i);// 在内容上方加水印pageRect = reader.getPageSizeWithRotation(i);gs.setFillOpacity(0.2f);content.beginText();content.setColorFill(BaseColor.BLACK);content.setFontAndSize(base, 8);//你可以随心所欲的改你自己想要的角度for (float height = interval + imgH; height < pageRect.getHeight()+ imgH; height = height + imgH ) {for (float width = interval + imgW; width < pageRect.getWidth() + imgW; width = width + imgW) {image.setAbsolutePosition(width - imgW, height - imgH); // set the first backgroundcontent.addImage(image);}}content.endText();}stamper.close();InputStream newInsStream = new FileInputStream(pdfFile);String dOriginFileName1 = multipartFile.getOriginalFilename();MultipartFile multipartFileNew = new MockMultipartFile(dOriginFileName1,dOriginFileName1,dContentType,newInsStream);//使用完成之后删除临时文件pdfFile.deleteOnExit();return multipartFileNew;}//返回加了水印的上传对象return multipartFile;}
现在有个问题其实也没解决,希望不通过临时文件来存储,直接将加水印之后的数据存储在HttpServletResponse中,但是处理完的水印PDF数据存储在OutputStream里面,需要将这个数据重新转成inputStream再到 MultipartFile 方能通过OSS服务方法上传,其中OutPutStram如何转成inputStream 没有找到直观的方法,后续再试试,
public static MultipartFile addPicMarkToMutipartFileNew(MultipartFile multipartFile,HttpServletResponse response, String markImg) throws IOException ,DocumentException{// 获取文件名String originFileName = multipartFile.getOriginalFilename();// 获取原文件后缀int lastSplit = originFileName.lastIndexOf(".");String suffix = originFileName.substring(lastSplit + 1);// 获取文件原始信息String dOriginFileName = multipartFile.getOriginalFilename();String dContentType = multipartFile.getContentType();// 是Pdf才加水印if (suffix.equalsIgnoreCase("pdf") ) {// 获取outputStream???????OutputStream outputStream = response.getOutputStream();InputStream inputStream = multipartFile.getInputStream();// 添加水印的时候,就已经在outputStream写入了PdfReader reader = new PdfReader(inputStream);PdfStamper stamper = new PdfStamper(reader, outputStream);int total = reader.getNumberOfPages() + 1;PdfContentByte content;BaseFont base = BaseFont.createFont("STSongStd-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED);PdfGState gs = new PdfGState();for (int i = 1; i < total; i++) {content = stamper.getOverContent(i);// 在内容上方加水印//content = stamper.getUnderContent(i);//在内容下方加水印gs.setFillOpacity(0.2f);content.setGState(gs);content.beginText();content.setColorFill(com.itextpdf.text.BaseColor.LIGHT_GRAY);content.setFontAndSize(base, 50);content.setTextMatrix(70, 200);//将文字显示在pdf页面中// content.showTextAligned(Element.ALIGN_CENTER, "国际财富管理协会(中国)!", 300,350, 55);//设置文字颜色content.setColorFill(com.itextpdf.text.BaseColor.BLACK);//设置文字大小content.setFontAndSize(base, 8);//将内容显示在pdf底部String waterMarkName = "111111";content.showTextAligned(Element.ALIGN_CENTER, "下载时间:" + waterMarkName + "", 300, 10, 0);content.endText();} //将输出流转换成输入流// ByteArrayInputStream input = new ByteArrayInputStream(outputStream);??????? 没找到转换方法,如果你看到这里有好的建议欢迎留言 //转换之后的流文件重写 // multipartFile = new MockMultipartFile(dOriginFileName,dOriginFileName,dContentType,input);stamper.close();outputStream.close();}//返回加了水印的上传对象return multipartFile;}
更多推荐
阿里云OSS上传PDF文件同时加上图片水印
发布评论