最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

java如何根據(jù)提供word模板導(dǎo)出word文檔詳解

 更新時間:2023年09月28日 09:19:50   作者:吳巴格  
在日常的開發(fā)工作中,我們時常會遇到導(dǎo)出Word文檔報表的需求,比如公司的財務(wù)報表、醫(yī)院的患者統(tǒng)計報表、電商平臺的銷售報表等等,這篇文章主要給大家介紹了關(guān)于java如何根據(jù)提供word模板導(dǎo)出word文檔的相關(guān)資料,需要的朋友可以參考下

本文主要講解,利用poi-tl在word中動態(tài)生成表格行,進(jìn)行文字、圖片填充。一共提供了兩種方式,1.基于本地文件 2.基于網(wǎng)絡(luò)文件

本文講解思路,1.先看示例,2. 示例對應(yīng)的代碼展示 3. 基本概念講解(api自行查閱文檔)。

這樣便于快速展示,不符合你的業(yè)務(wù)需求的可以直接劃走

1.效果示例圖

1.1 word模板

注意:這里提前闡述幾個概念。

  • 基本上所有的變量都由{{}}包裹,交給poi-tl解析(變量命名隨便你,中文,英文都可以)
  • {{工作經(jīng)歷列表}}下方的[序號]、[公司名]、[工作時長]、[salary]、[聯(lián)系]、[崗位],就是使用了 poi-tl的表格行插件,動態(tài)渲染表格行的語法,可以簡單理解為此處表格對應(yīng)的每一行就是一個對象實體類,而{{工作經(jīng)歷列表}}就是一個list
  • {{?申明項列表}} {{item}} {{/申明項列表}},此處則是使用了poi-tl的區(qū)塊對標(biāo)簽。區(qū)塊對在此處的,我只是用它來實現(xiàn)渲染同一個表格內(nèi)的多行文本渲染,可以理解為<申明項列表>標(biāo)簽對應(yīng)的就是一個list,< item >就是一個list中的一個個對象元素。并且此處會觸發(fā),換行后序號累加的word編排編號樣式。
  • {{@員工簽字圖片}},此處需要注意,word模板中代表圖片的變量,必須要加上@特殊符號修飾!

1.2 參數(shù)替換后的word

看到這里,如果對應(yīng)的效果不滿足你的需求,那么你可以出門右轉(zhuǎn)了。

2.代碼展示

maven 依賴,使用poi-tl需要支持 poi高版本

<!--    POI 依賴 使用xlsx xml的格式(即XSSFWorkbook)   -->
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi</artifactId>
            <version>5.2.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-ooxml</artifactId>
            <version>5.2.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-scratchpad</artifactId>
            <version>3.17</version>
        </dependency>
        <!--     poi模板導(dǎo)入,主力包      -->
        <dependency>
            <groupId>com.deepoove</groupId>
            <artifactId>poi-tl</artifactId>
            <version>1.12.1</version>
        </dependency>

2.1 根據(jù)網(wǎng)絡(luò)生成word

    /**
     * 根據(jù)網(wǎng)絡(luò)生成word
     **/
    public static void generateByNetWork() {
        String ip = "192.168.x.x";
        // 我這里是用文件服務(wù)器返回的網(wǎng)絡(luò)文件流,你也可以直接放置一個文件的url
        String pictureUrl = "http://" + ip + ":8080/api/file/download?id=b9e0ac0336a84fc0b4ebb4cdf2c805e0.png";
        HashMap<String, Object> finalMap = new HashMap<>();
        finalMap.put("姓名", "張三");
        finalMap.put("身份證號", "511232XXXXXXX");
        finalMap.put("手機號", "1328292xxxx");
        finalMap.put("員工簽字", "張三");
        finalMap.put("日期", "2023-05-16");
        // 從網(wǎng)絡(luò)流讀取圖片,置入word模板,等待編譯
        if (Validator.isNotEmpty(pictureUrl)) {
            PictureRenderData picture = Pictures.ofUrl(pictureUrl).size(40, 30).create();
            finalMap.put("員工簽字圖片", picture);
        }
        ArrayList<Object> workList = CollUtil.newArrayList();
        finalMap.put("工作經(jīng)歷列表", workList);
        for (int i = 0; i < 3; i++) {
            // 模擬從mysql查詢列表數(shù)據(jù)
            HashMap<String, Object> workItem = new HashMap<>();
            workItem.put("序號", i + 1);
            workItem.put("公司名", "四川有限公司" + i);
            workItem.put("工作時長", i + 10 + "小時");
            workItem.put("salary", "800" + i);
            workItem.put("聯(lián)系", "項目經(jīng)理" + i);
            workItem.put("崗位", "java工程師" + i);
            workList.add(workItem);
        }
        // 注意:此處用的是 <區(qū)塊對> key是字符串,value則放置一個集合,類似于模板引擎的foreach標(biāo)簽
        ArrayList<Object> stateList = CollUtil.newArrayList();
        finalMap.put("申明項列表", stateList);
        // 模擬從mysql查詢數(shù)據(jù),改造為word模板所需的數(shù)據(jù)結(jié)構(gòu)
        List<String> stateListFromMySQL = Arrays.asList("本人所遞交的所有辦理人才引進(jìn)材料及填寫的情況均屬實;"
                , "我已認(rèn)真閱讀以上內(nèi)容并確認(rèn);"
                , "若在申請期間信息變更不做變更。若違反,本人愿意承擔(dān)由此產(chǎn)生的后果。");
        for (int i = 0; i < stateListFromMySQL.size(); i++) {
            HashMap<String, Object> stateItem = new HashMap<>();
            // 此處在 每行文字后,都添加\n 的換行符。注意:此換行僅僅只是換行,并不等同于enter,不會觸發(fā)類似于 <在word中enter換行,自動觸發(fā)編排序號累加> 的動作
            stateItem.put("item", stateListFromMySQL.get(i) + "\n");
            stateList.add(stateItem);
        }
        // 從網(wǎng)絡(luò)url 下載word模板到指定文件夾
        File wordTemplate = HttpUtil.downloadFileFromUrl("http://" + ip + ":8080/file/download" + "?id=talentsTemplate.docx", "D://upload" + File.separator);
        // 此處使用了poi-tl的<表格行循環(huán)插件>,此處一定要進(jìn)行參數(shù)bind,方便word模板參數(shù)替換
        LoopRowTableRenderPolicy policy = new LoopRowTableRenderPolicy();
        Configure build = Configure.builder().bind(policy, "工作經(jīng)歷列表").build();
        // 進(jìn)行編譯
        XWPFTemplate render = XWPFTemplate.compile(wordTemplate.getAbsolutePath(), build).render(finalMap);
        File word = new File("D://upload" + File.separator + IdUtil.getSnowflake().nextId() + ".docx");
        try {
            // 關(guān)鍵步驟,
            render.writeToFile(word.getAbsolutePath());
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
        // 下面的方法可以根據(jù)業(yè)務(wù)調(diào)整,我這里是將參數(shù)替換后的word上傳到項目對應(yīng)的文件服務(wù)器,拿到的url進(jìn)行存入數(shù)據(jù)庫
        String json = HttpUtil.createPost("http://" + ip + ":8080/file/upload")
                .header("Content-Type", ContentType.MULTIPART.getValue())
                .form("file", word)
                .execute()
                .body();
        // hutool工具類,刪除 word。因為在這個流程中,word只是一個中間產(chǎn)物,因為我上邊已經(jīng)把該word 上傳到我的文件服務(wù)器,并且文件服務(wù)器 會返回給我它對應(yīng)的url
        FileUtil.del(word);
        List<String> list = JSONUtil.parseArray(json).toList(String.class);
    }

2.2 根據(jù)本地文件流生成word

    /**
     * 根據(jù)本地文件流生成word
     **/
    public static void generateByFile() {
        // 此處直接是本地文件的絕對路徑
        String pictureUrl = "C://Users//x//Desktop//博客//word模板填參//generate//sign.png";
        HashMap<String, Object> finalMap = new HashMap<>();
        finalMap.put("姓名", "張三");
        finalMap.put("身份證號", "511232XXXXXXX");
        finalMap.put("手機號", "1328292xxxx");
        finalMap.put("員工簽字", "張三");
        finalMap.put("日期", "2023-05-16");
        // 從本地讀取圖片,置入word模板,等待編譯
        if (Validator.isNotEmpty(pictureUrl)) {
            PictureRenderData picture = Pictures.ofLocal(pictureUrl).size(60, 50).create();
            finalMap.put("員工簽字圖片", picture);
        }
        ArrayList<Object> workList = CollUtil.newArrayList();
        finalMap.put("工作經(jīng)歷列表", workList);
        for (int i = 0; i < 3; i++) {
            // 模擬從mysql查詢列表數(shù)據(jù)
            HashMap<String, Object> workItem = new HashMap<>();
            workItem.put("序號", i + 1);
            workItem.put("公司名", "成都有限公司" + i);
            workItem.put("工作時長", i + 5 + "小時");
            workItem.put("salary", "1000" + i);
            workItem.put("聯(lián)系", "聯(lián)系人" + i);
            workItem.put("崗位", "崗位" + i);
            workList.add(workItem);
        }
        // 注意:此處用的是 <區(qū)塊對> key是字符串,value則放置一個集合,類似于模板引擎的foreach標(biāo)簽
        ArrayList<Object> stateList = CollUtil.newArrayList();
        finalMap.put("申明項列表", stateList);
        // 模擬從mysql查詢數(shù)據(jù),改造為word模板所需的數(shù)據(jù)結(jié)構(gòu)
        List<String> stateListFromMySQL = Arrays.asList("本人所遞交的所有辦理人才引進(jìn)材料及填寫的情況均屬實;"
                , "我已認(rèn)真閱讀以上內(nèi)容并確認(rèn);"
                , "若在申請期間信息變更不做變更。若違反,本人愿意承擔(dān)由此產(chǎn)生的后果。");
        for (int i = 0; i < stateListFromMySQL.size(); i++) {
            HashMap<String, Object> stateItem = new HashMap<>();
            stateItem.put("item", stateListFromMySQL.get(i) + "");
            stateList.add(stateItem);
        }
        // 從網(wǎng)絡(luò)url 下載word模板到指定文件夾
        File wordTemplate = new File("C://Users//x//Desktop//博客//word模板填參//talentsTemplate.docx");
        // 此處使用了poi-tl的<表格行循環(huán)插件>,此處一定要進(jìn)行參數(shù)bind,方便word模板參數(shù)替換
        LoopRowTableRenderPolicy policy = new LoopRowTableRenderPolicy();
        Configure build = Configure.builder().bind(policy, "工作經(jīng)歷列表").build();
        // 進(jìn)行編譯
        String absolutePath = wordTemplate.getAbsolutePath();
        XWPFTemplate render = XWPFTemplate.compile(absolutePath, build).render(finalMap);
        // 此處是利用File,直接在本地創(chuàng)建文件,將參數(shù)替換后的文件流寫入到該文件,word就是最終的結(jié)果
        File word = new File("C://Users//x//Desktop//博客//word模板填參//generate" + File.separator + IdUtil.getSnowflake().nextId() + ".docx");
        try {
            render.writeToFile(word.getAbsolutePath());
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
        // 下面的方法可以根據(jù)業(yè)務(wù)調(diào)整,我這里是將參數(shù)替換后的word上傳到項目對應(yīng)的文件服務(wù)器,拿到的url進(jìn)行存入數(shù)據(jù)庫
//        FileUtil.del(word);
//        List<String> list = JSONUtil.parseArray(json).toList(String.class);
    }

2.3 方法調(diào)用

    public static void main(String[] args) {
//        generateByNetWork();
        generateByFile();
    }

總結(jié): 上面的備注已經(jīng)說的很清楚了,這邊不做過多解釋。如果有哪里看不懂的,評論區(qū)評論,我有空就來給你解答。

3. 基本介紹

此處不做api介紹,只做基本概念介紹,不需要的可以跳過了!官網(wǎng) http://deepoove.com/poi-tl/

poi-tl(poi template language)是Word模板引擎,使用Word模板和數(shù)據(jù)創(chuàng)建很棒的Word文檔。

方案移植性功能性易用性
Poi-tlJava跨平臺Word模板引擎,基于Apache POI,提供更友好的API低代碼,準(zhǔn)備文檔模板和數(shù)據(jù)即可
Apache POIJava跨平臺Apache項目,封裝了常見的文檔操作,也可以操作底層XML結(jié)構(gòu)文檔不全,這里有一個教程:Apache POI Word快速入門
FreemarkerXML跨平臺僅支持文本,很大的局限性不推薦,XML結(jié)構(gòu)的代碼幾乎無法維護
OpenOffice部署OpenOffice,移植性較差-需要了解OpenOffice的API
HTML瀏覽器導(dǎo)出依賴瀏覽器的實現(xiàn),移植性較差HTML不能很好的兼容Word的格式,樣式糟糕-
Jacob、winlibWindows平臺-復(fù)雜,完全不推薦使用

3.1 功能介紹

3.2 版本說明

本文博客使用的是poi-tl最新版,需要apache poi 5.1.0+,不然會報錯,no such method

3.3 快速開始

依賴引入

maven
<dependency>
  <groupId>com.deepoove</groupId>
  <artifactId>poi-tl</artifactId>
  <version>1.12.1</version>
</dependency>
gradle
implementation 'com.deepoove:poi-tl:1.12.1'

官網(wǎng)demo示例

XWPFTemplate template = XWPFTemplate.compile("template.docx").render(
  new HashMap<String, Object>(){{
    put("title", "Hi, poi-tl Word模板引擎");
}});  
template.writeAndClose(new FileOutputStream("output.docx")); 

基本就是三部曲:

  • compile 編譯模板
  • render 渲染數(shù)據(jù)
  • write 輸出到流
    TDO模式:Template + data-model = output

最后再次貼出官網(wǎng)鏈接,http://deepoove.com/poi-tl/#_why_poi_tl

總結(jié)

到此這篇關(guān)于java如何根據(jù)提供word模板導(dǎo)出word文檔的文章就介紹到這了,更多相關(guān)java導(dǎo)出word文檔內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Java實現(xiàn)隨機驗證碼具體代碼

    Java實現(xiàn)隨機驗證碼具體代碼

    這篇文章主要為大家詳細(xì)介紹了Java實現(xiàn)隨機驗證碼具體代碼,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2017-01-01
  • java正則表達(dá)式的簡單運用

    java正則表達(dá)式的簡單運用

    這篇文章主要為大家詳細(xì)介紹了java正則表達(dá)式的簡單運用,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2018-08-08
  • maven解決包沖突方法詳解

    maven解決包沖突方法詳解

    這篇文章主要介紹了maven解決包沖突方法詳解,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-10-10
  • Mybatis?plus多租戶方案的實戰(zhàn)踩坑記錄

    Mybatis?plus多租戶方案的實戰(zhàn)踩坑記錄

    MybaitsPlus多租戶處理器是一個對于多租戶問題的解決方案,下面這篇文章主要給大家介紹了關(guān)于Mybatis?plus多租戶方案踩坑的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2021-12-12
  • Java生成由時間組成的訂單號方式

    Java生成由時間組成的訂單號方式

    這篇文章主要介紹了Java生成由時間組成的訂單號方式,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-04-04
  • Java中switch判斷語句典型使用實例

    Java中switch判斷語句典型使用實例

    這篇文章主要介紹了Java中switch判斷語句典型使用實例,本文直接給出代碼實例,在忘記switch語法時特別有用,復(fù)制修改即可使用,需要的朋友可以參考下
    2015-06-06
  • Java 關(guān)鍵字static詳解及實例代碼

    Java 關(guān)鍵字static詳解及實例代碼

    這篇文章主要介紹了Java 關(guān)鍵字static詳解及實例代碼的相關(guān)資料,需要的朋友可以參考下
    2017-04-04
  • SpringCache緩存處理詳解

    SpringCache緩存處理詳解

    這篇文章主要介紹了SpringCache緩存處理詳解,SpringCache是一個框架,實現(xiàn)了基于注解緩存功能,只需要簡單地加一個注解,就能實現(xiàn)緩存功能,需要的朋友可以參考下
    2023-09-09
  • Mybatis-plus設(shè)置某個字段值為null的方法總結(jié)

    Mybatis-plus設(shè)置某個字段值為null的方法總結(jié)

    mybatis-plus以下簡稱mp,目前應(yīng)該也算是主流的一款數(shù)據(jù)訪問層應(yīng)用框架,下面這篇文章主要給大家介紹了關(guān)于Mybatis-plus設(shè)置某個字段值為null的相關(guān)資料,文中通過實例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2022-07-07
  • Java方法的返回值及注意事項小結(jié)

    Java方法的返回值及注意事項小結(jié)

    這篇文章主要介紹了Java方法的返回值及注意事項,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2023-04-04

最新評論

镇沅| 连州市| 泸定县| 彭州市| 长沙市| 永新县| 南江县| 阿拉善盟| 辽阳县| 左权县| 恭城| 织金县| 宾阳县| 抚远县| 津市市| 南宁市| 永嘉县| 林芝县| 囊谦县| 弥勒县| 三亚市| 光山县| 闽侯县| 固安县| 原平市| 公安县| 常熟市| 合江县| 沙雅县| 昭苏县| 廉江市| 莱阳市| 肇源县| 南康市| 新疆| 吉木乃县| 正安县| 嵊州市| 西贡区| 修水县| 石家庄市|