TemplateEngine.Docx Word產出好工具
前言
最近工作上面遇到一個需求,需要根據DB資料去產製一份審核書,
需要處理的部分是使用者個人資訊部分(姓名、電話、地址),
和一些相關表格(Table)資訊。
來源
這個套件主要是由 DocX library 衍生出來,透過維護Word Template在根據設定好的控制項去填寫內容,
所以整個過程會分為兩個部分。
- 建立一個 Word Template 檔案
- 程式填寫此檔案內容
安裝
我們可以透過 Nuget 來安裝此套件,
Steps 1
建立一個簡單的word Template 供後續程式操作,這邊要特別注意的是 Word 本身是沒有開啟開發者模式的,需要去左上方檔案頁籤
看到開發者頁籤出現就代表第一步驟已經完成囉~
內容控制項設定
- 開啟設計模式
- 新增內容控制項
- 輸入控制項文字
- 設定邊標題與標籤
重複控制項
- 開啟設計模式
- 新增重複控制項
- 設定邊標題與標籤
- 欄位放置文字控制項
根據上方兩項設定我們就可以透過程式來操作填寫我們的Word Template,
透過置換我們預留的控制項,達成資料填寫的目的。
Steps 2
透過程式填寫檔案內容,範例由一個基本的webform 專案示範,
畫面上僅有一個簡單的 button 來產出word文件。
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Web.UI;
using TemplateEngine.Docx;
namespace DocXTemplateEngineDemo
{
public partial class index : Page
{
protected void Page_Load(object sender, EventArgs e)
{
}
protected void downloadFile_btn_OnClick(object sender, EventArgs e)
{
//1.複製至目標路徑
var targetPath = "D:/demo/";
string fileName = $"{DateTime.Now:yyyyMMddHHmmss}.docx";
File.Copy(Server.MapPath("~/Template/template.docx"), targetPath + fileName);
//2.設定檔案內容
//FieldContent部分
var valuesToFill = new Content();
valuesToFill.Fields.Add(new FieldContent("name", "王小明"));
valuesToFill.Fields.Add(new FieldContent("special_1", "■"));
valuesToFill.Fields.Add(new FieldContent("special_2", "□"));
var tableContent = new TableContent("row");
foreach (var f in FakeData())
tableContent.AddRow(
new FieldContent("r_name", f.Name),
new FieldContent("r_chinese", f.Chinese),
new FieldContent("r_english", f.English),
new FieldContent("r_math", f.Math)
);
//TableContent部分
valuesToFill.Tables.Add(tableContent);
var avg_chinese = FakeData().Average(x => Convert.ToDecimal(x.Chinese));
var avg_english = FakeData().Average(x => Convert.ToDecimal(x.English));
var avg_math = FakeData().Average(x => Convert.ToDecimal(x.Math));
valuesToFill.Fields.Add(new FieldContent("avg_chinese", avg_chinese.ToString("0.0")));
valuesToFill.Fields.Add(new FieldContent("avg_english", avg_english.ToString("0.0")));
valuesToFill.Fields.Add(new FieldContent("avg_math", avg_math.ToString("0.0")));
//3.儲存變更
using (var outputDocument = new TemplateProcessor(targetPath + fileName).SetRemoveContentControls(true))
{
outputDocument.FillContent(valuesToFill);
outputDocument.SaveChanges();
}
}
//假資料
public List<ScoreSheet> FakeData()
{
return new List<ScoreSheet>
{
new ScoreSheet
{
Name = "王XX",
Chinese = "100",
English = "70",
Math = "90"
},
new ScoreSheet
{
Name = "鄭XX",
Chinese = "90",
English = "60",
Math = "80"
},
new ScoreSheet
{
Name = "陳XX",
Chinese = "80",
English = "50",
Math = "60"
},
new ScoreSheet
{
Name = "張XX",
Chinese = "70",
English = "80",
Math = "70"
}
};
}
public class ScoreSheet
{
public string Name { get; set; }
public string Chinese { get; set; }
public string English { get; set; }
public string Math { get; set; }
}
}
}
產出結果
結論
此專案範本 Gitbub 範例
目前專案僅使用到兩種就解決了問題,所以只有介紹上面兩種FiledContent、TableContent,
下方是原專案提供所有的Content,若有需要可以自行實作。
原本專案 Github : https://github.com/UNIT6-open/TemplateEngine.Docx