IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 开发工具 -> java操作word替换文字和在固定位置插入表格 -> 正文阅读

[开发工具]java操作word替换文字和在固定位置插入表格

<!-- 需要用的包-->
<!-- https://mvnrepository.com/artifact/org.apache.poi/poi -->
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi</artifactId>
    <version>3.14</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.apache.poi/poi-ooxml -->
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml</artifactId>
    <version>3.14</version>
</dependency>
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-scratchpad</artifactId>
    <version>3.14</version>
</dependency>
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml-schemas</artifactId>
    <version>3.14</version>
</dependency>

package com.example.demo.jisuan;

import org.apache.poi.POIXMLDocument;

import org.apache.poi.openxml4j.opc.OPCPackage;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.usermodel.XWPFParagraph;
import org.apache.poi.xwpf.usermodel.XWPFRun;
import org.apache.poi.xwpf.usermodel.XWPFTable;
import org.apache.poi.xwpf.usermodel.XWPFTableCell;
import org.apache.poi.xwpf.usermodel.XWPFTableRow;

import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.util.*;

import org.apache.xmlbeans.XmlCursor;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.*;

import java.beans.IntrospectionException;
import java.beans.PropertyDescriptor;
import java.io.FileOutputStream;
import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.math.BigInteger;
import java.util.List;

public class WordUtil2 {


    /**
     * 替换word中指定字符串
     * 注意模板需要替换的字符串的格式
     * 1、要连着打出来,或者在别的地方写好粘过来
     * 2、先word转PDF,再将PDF转word
     * <p>
     * 替换word模板并生成新的word
     *
     * @param srcPath  模板地址
     * @param destPath 新的word地址
     * @param map      替换的内容
     * @return 是否成功替换
     */
    public static boolean newWord(String srcPath,
                                  String destPath, Map<String, Object> map) {
        //创建新的word文件
        File errorExcelfile = new File(destPath);
        if (!errorExcelfile.exists()) {
            File file = errorExcelfile.getParentFile();
            if (!file.exists())
                file.mkdirs();
        }
        try {
            OPCPackage opcPackage = POIXMLDocument.openPackage(srcPath);
            CustomXWPFDocument doc = new CustomXWPFDocument(opcPackage);
            // 替换段落中的指定文字
            Iterator<XWPFParagraph> itPara = doc.getParagraphsIterator();
            while (itPara.hasNext()) {
                XWPFParagraph paragraph = (XWPFParagraph) itPara.next();
                List<XWPFRun> runs = paragraph.getRuns();
                for (int i = 0; i < runs.size(); i++) {
                    //遍历读取模板的内容
                    String oneparaString = runs.get(i).getText(runs.get(i).getTextPosition());
                    if (oneparaString == null) {
                        continue;
                    }
                    //遍历要替换的内容  和模板相同字符串的key 被替换为value
                    for (Map.Entry<String, Object> entry : map.entrySet()) {
                        String key = entry.getKey();
                        if (oneparaString.indexOf(key) != -1) {
                            Object value = entry.getValue();
                            if (value instanceof String) {
                                oneparaString = oneparaString.replace(entry.getKey(), entry.getValue().toString());
                            } else if (value instanceof Map) {
                                //判断如果值是map类型 就说明是图片
                                oneparaString = oneparaString.replace(key, "");
                                Map pic = (Map) value;
                                int width = Integer.parseInt(pic.get("width").toString());
                                int height = Integer.parseInt(pic.get("height").toString());
                                int picType = getPictureType(pic.get("type").toString());
                                byte[] byteArray = (byte[]) pic.get("content");
                                ByteArrayInputStream byteInputStream = new ByteArrayInputStream(byteArray);
                                //以字节流的形式 向  XWPFParagraph 添加图片
                                doc.addPictureData(byteInputStream, picType);
                                //创建图片模板
                                doc.createPicture(doc.getAllPictures().size() - 1, width, height, paragraph);
                            }
                        }
                    }
                    runs.get(i).setText(oneparaString, 0);
                }
            }

            FileOutputStream outStream = null;
            outStream = new FileOutputStream(destPath);
            doc.write(outStream);
            outStream.close();
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }

    }

    /**
     * 根据图片类型,取得对应的图片类型代码
     *
     * @param picType
     * @return int
     */
    private static int getPictureType(String picType) {
        int res = CustomXWPFDocument.PICTURE_TYPE_PICT;
        if (picType != null) {
            if (picType.equalsIgnoreCase("png")) {
                res = CustomXWPFDocument.PICTURE_TYPE_PNG;
            } else if (picType.equalsIgnoreCase("dib")) {
                res = CustomXWPFDocument.PICTURE_TYPE_DIB;
            } else if (picType.equalsIgnoreCase("emf")) {
                res = CustomXWPFDocument.PICTURE_TYPE_EMF;
            } else if (picType.equalsIgnoreCase("jpg") || picType.equalsIgnoreCase("jpeg")) {
                res = CustomXWPFDocument.PICTURE_TYPE_JPEG;
            } else if (picType.equalsIgnoreCase("wmf")) {
                res = CustomXWPFDocument.PICTURE_TYPE_WMF;
            }
        }
        return res;
    }



    public static void main(String[] args) {
        System.out.println("hello world");
        List<Person> dtos = new ArrayList<>();
        for (int i = 0; i < 20; i++) {
            Person dto = new Person();
            if(i%3==0){
                dto.setName("张三" + i);
                dto.setSex("nan" + i);
                dto.setAge("11" + i);
                dtos.add(dto);
            }else{
                dto.setName("");
                dto.setSex("nan" + i);
                dto.setAge("");
                dtos.add(dto);
            }

        }
        List<String> head = new ArrayList<>();
        head.add("姓名");
        head.add("年龄");
        head.add("性别");
        String srcPath = "F:\\jinxin.docx";
        String targetPath = "F:\\jinxin1.docx";
        String key = "liebiaotable";// 在文档中需要替换插入表格的位置
        exportBg(head, dtos, srcPath, targetPath, key);
    }

//    public static void main(String[] args) {
//        Map<String,Object> map = new HashMap<>();
//        map.put("需求说明","测试替换");
//        newWord("F:\\jin.docx","F:\\jinxin.docx",map);
//    }

    /**
     * 替换word中指定字符串(这里用来将字符串替换为表格,上边的newWord用来替换文字等)
     * @param head 表头
     * @param data 数据
     * @param srcPath 需要操作的文档模板
     * @param targetPath 操作完后输出的位置
     * @param key 需要替换的文字,如果需要替换多个位置就用个map啥的
     * @param <T>
     */
    //创建一个表格插入到key标记的位置
    public static <T> void exportBg(List<String> head, List<T> data, String srcPath, String targetPath, String key) {
        XWPFDocument doc = null;
        try {
            doc = new XWPFDocument(POIXMLDocument.openPackage(srcPath));
            List<XWPFParagraph> paragraphList = doc.getParagraphs();
            if (paragraphList != null && paragraphList.size() > 0) {
                for (XWPFParagraph paragraph : paragraphList) {
                    List<XWPFRun> runs = paragraph.getRuns();
                    for (int i = 0; i < runs.size(); i++) {
                        String text = runs.get(i).getText(0);
                        if (text != null) {
                            text = text.trim();
                            if (text.indexOf(key) >= 0) {
                                runs.get(i).setText(text.replace(key, ""), 0);
                                XmlCursor cursor = paragraph.getCTP().newCursor();
                                // 在指定游标位置插入表格
                                XWPFTable table = doc.insertNewTbl(cursor);

                                CTTblPr tablePr = table.getCTTbl().getTblPr();
                                CTTblWidth width = tablePr.addNewTblW();
                                //获取这个东西用来改表格宽度
                                width.setW(BigInteger.valueOf(7000));

                                insertInfo(table, head, data);
                                break;
                            }
                        }
                    }
                }
            }
            FileOutputStream os = new FileOutputStream(targetPath);
            doc.write(os);
            os.flush();
            os.close();
        } catch (IOException | IllegalAccessException | IntrospectionException | InvocationTargetException e) {
            e.printStackTrace();
        }


    }

    /**
     * 把信息插入表格
     */
    private static <T> void insertInfo(XWPFTable table, List<String> head, List<T> data) throws IntrospectionException, InvocationTargetException, IllegalAccessException {
        //获取第一行
        XWPFTableRow row = table.getRow(0);
//        //获取这个东西用来改表格宽度
//        CTTblPr tblPr = table.getCTTbl().getTblPr();
//        //改变长度策略为自己调整 默认为auto
//        tblPr.getTblW().setType(STTblWidth.DXA);
//        //设置表格宽度为7000
//        tblPr.getTblW().setW(BigInteger.valueOf(10));
        //根据头创建表格head
        for (int col = 1; col < head.size(); col++) {//默认会创建一列,即从第2列开始
            // 第一行创建了多少列,后续增加的行自动增加列
            CTTcPr cPr = row.createCell().getCTTc().addNewTcPr();
            //设置单元格高度为500
            row.getCtRow().addNewTrPr().addNewTrHeight().setVal(BigInteger.valueOf(500));
            //可以用来设置单元格长度
            //CTTblWidth width = cPr.addNewTcW();
            //width.setW(BigInteger.valueOf(2000));
        }
        //循环给表格添加头信息
        for (int i = 0; i < head.size(); i++) {
            //往表格里面写入头信息
            row.getCell(i).setText(head.get(i));
        }
        //计数器
        int i = 0;
        //循环填充body列表(列表为vo数组)
        for (T item : data) {
            //获取类
            Class<?> clazz = item.getClass();
            //获取item字段
            Field[] fields = item.getClass().getDeclaredFields();
            //创建行
            row = table.createRow();
            //修改行高为500
            row.getCtRow().addNewTrPr().addNewTrHeight().setVal(BigInteger.valueOf(1000));
            //循环获取vo类的属性
            for (Field field : fields) {
                //获取当前field的属性描述器
                PropertyDescriptor descriptor = new PropertyDescriptor(field.getName(), clazz);
                //获取field字段的get方法
                Method readMethod = descriptor.getReadMethod();
                //执行get方法并填充到表格中
                row.getCell(i).setText(String.valueOf(readMethod.invoke(item)));
                //计数器+1
                i++;
            }
            //执行完一行计数器归零
            i = 0;
        }
        mergeCellsVertically(table,0,1,4);

    }

    /**
     *
     * @param table 自己猜
     * @param col  第几列
     * @param fromRow  开始行
     * @param toRow   结束行
     */
    // word跨行并单元格
    public static void mergeCellsVertically(XWPFTable table, int col, int fromRow, int toRow) {
        for (int rowIndex = fromRow; rowIndex <= toRow; rowIndex++) {
            XWPFTableCell cell = table.getRow(rowIndex).getCell(col);
            if ( rowIndex == fromRow ) {
                // The first merged cell is set with RESTART merge value
                cell.getCTTc().addNewTcPr().addNewVMerge().setVal(STMerge.RESTART);
            } else {
                // Cells which join (merge) the first one, are set with CONTINUE
                cell.getCTTc().addNewTcPr().addNewVMerge().setVal(STMerge.CONTINUE);
            }
        }
    }

    /**
     * 列的我这里没用,留着备用
     * @param table
     * @param row
     * @param fromCell
     * @param toCell
     */
//    // word跨列合并单元格
//    public  void mergeCellsHorizontal(XWPFTable table, int row, int fromCell, int toCell) {
//        for (int cellIndex = fromCell; cellIndex <= toCell; cellIndex++) {
//            XWPFTableCell cell = table.getRow(row).getCell(cellIndex);
//            if (cellIndex == fromCell) {
//                // The first merged cell is set with RESTART merge value
//                cell.getCTTc().addNewTcPr().addNewHMerge().setVal(STMerge.RESTART);
//            } else {
//                // Cells which join (merge) the first one, are set with CONTINUE
//                cell.getCTTc().addNewTcPr().addNewHMerge().setVal(STMerge.CONTINUE);
//            }
//        }
//    }


}

、、

<!-- 之前打算用这个包的方法开发来着,没研究明白所以放弃了 -->
<dependencies>
<!--        <dependency>-->
<!--            <groupId>e-iceblue</groupId>-->
<!--            <artifactId>spire.doc.free</artifactId>-->
<!--            <version>3.9.0</version>-->
<!--        </dependency>-->
<!--        <dependency>-->
<!--            <groupId>e-iceblue</groupId>-->
<!--            <artifactId>spire.xls.free</artifactId>-->
<!--            <version>3.9.1</version>-->
<!--        </dependency>-->
<!--        <dependency>-->
<!--            <groupId> e-iceblue </groupId>-->
<!--            <artifactId>spire.office</artifactId>-->
<!--            <version>4.8.0</version>-->
<!--        </dependency>-->
</dependencies>
<repositories>
        <repository>
            <id>com.e-iceblue</id>
            <url>https://repo.e-iceblue.cn/repository/maven-public/</url>
        </repository>
    </repositories>

  开发工具 最新文章
Postman接口测试之Mock快速入门
ASCII码空格替换查表_最全ASCII码对照表0-2
如何使用 ssh 建立 socks 代理
Typora配合PicGo阿里云图床配置
SoapUI、Jmeter、Postman三种接口测试工具的
github用相对路径显示图片_GitHub 中 readm
Windows编译g2o及其g2o viewer
解决jupyter notebook无法连接/ jupyter连接
Git恢复到之前版本
VScode常用快捷键
上一篇文章      下一篇文章      查看所有文章
加:2022-03-13 22:01:22  更:2022-03-13 22:01:45 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年9日历 -2024/9/22 17:33:22-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码