Word從2003開始支持XML格式,用XML還作就很簡單了。java
大體的思路是先用office2003或者2007編輯好word的樣式,而後另存爲xml,以下圖所示:數據庫
將xml翻譯爲FreeMarker模板,最後用java來解析FreeMarker模板並輸出Doc,如圖所示的操做:app
後臺生成word的代碼以下:測試
package net.gvsun.service;ui
import java.io.BufferedWriter;this
import java.io.File;spa
import java.io.FileOutputStream;翻譯
import java.io.IOException;code
import java.io.OutputStreamWriter;orm
import java.io.Writer;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
public class WordHandler {
private Configuration configuration = null;
public WordHandler() {
configuration = new Configuration();
configuration.setDefaultEncoding("utf-8");
}
public File createDoc(String templatePath, String templateName, Map dataMap,String fileName) {
/* // 要填入模本的數據文件
Map dataMap = new HashMap();
getData(dataMap);*/
// 設置模本裝置方法和路徑,FreeMarker支持多種模板裝載方法。能夠重servlet,classpath,數據庫裝載,
// ftl文件存放路徑
configuration.setClassForTemplateLoading(this.getClass(), templatePath);
Template t = null;
try {
// test.ftl爲要裝載的模板
t = configuration.getTemplate(templateName);
t.setEncoding("utf-8");
} catch (IOException e) {
e.printStackTrace();
}
// 輸出文檔路徑及名稱
String root = System.getProperty("dhulims.root");
String upLoad=root+"upload"+File.separator;
// File sendPath = new File(upLoad+projectNO);
File file = new File(upLoad);
if(!file.exists()){
file.mkdirs();
}
File outFile = new File(upLoad+fileName+".doc");
Writer out = null;
try {
out = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(outFile), "utf-8"));
} catch (Exception e1) {
e1.printStackTrace();
}
try {
t.process(dataMap, out);
/*out.close();*/
} catch (TemplateException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return outFile;
}
public static void main(String templatePath, String templateName, Map dataMap,String fileName) {
new WordHandler().createDoc(templatePath,templateName,dataMap,fileName);
}
}
control導出word並傳入參數的代碼以下:
/**
* 下載實驗項目的word文檔
* 做者:彭文玉
*/
@RequestMapping("/downloadLmsExperiment")
public void downloadLmsExperiment(@RequestParam int idKey,HttpServletResponse response)
{
response.setContentType("application/doc;charset=UTF-8");
byte b[] = new byte[1024];
//轉換startDate的時間格式;
SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");
//根據主鍵idKey查找到LmsExperiment
LmsExperiment lmsexperiment=lmsExperimentDAO.findLmsExperimentByPrimaryKey(idKey);
//若是lmsexperiment的系部不爲空
if(lmsexperiment.getSysDepartment()!=null){
//映射lmsexperiment的departmentName給departName;
dataMap.put("departName",lmsexperiment.getSysDepartment().getDepartmentName());
}
//不然設置lmsexperiment的null爲departName
else{
dataMap.put("departName", "");
}
//映射lmsexperiment的experimentNumber給experimentNumber;
dataMap.put("experimentNumber",lmsexperiment.getExperimentNumber());
//映射Experiment的ExperimentName給ExperimentName;
dataMap.put("ExperimentName",lmsexperiment.getExperimentName());
//映射lmsexperiment的experimentCardNumber給experimentCardNumber;
dataMap.put("experimentCardNumber",lmsexperiment.getExperimentCardNumber());
//映射lmsexperiment的experimentMajor給experimentMajor;
dataMap.put("experimentMajor",lmsexperiment.getExperimentMajor());
//映射lmsexperiment的totalCourseHours給totalCourseHours;
dataMap.put("totalCourseHours",lmsexperiment.getTotalCourseHours());
//映射lmsexperiment的totalExperimentHours給totalExperimentHours;
dataMap.put("totalExperimentHours",lmsexperiment.getTotalExperimentHours());
//映射lmsexperiment的thisExperimentHours給thisExperimentHours;
dataMap.put("thisExperimentHours",lmsexperiment.getThisExperimentHours());
//映射lmsexperiment的experimentEachNumber給experimentEachNumber;
dataMap.put("experimentEachNumber",lmsexperiment.getExperimentEachNumber());
//映射lmsexperiment的experimentGroup給experimentGroup;
dataMap.put("experimentGroup",lmsexperiment.getExperimentGroup());
//映射lmsexperiment的experimentCreatedAt給experimentCreatedAt;
dataMap.put("experimentCreatedAt",sdf.format(lmsexperiment.getExperimentCreatedAt().getTime()));
//映射lmsexperiment的experimentChangelog給experimentChangelog;
dataMap.put("experimentChangelog",lmsexperiment.getExperimentChangelog());
//映射lmsexperiment的experimentDesign給experimentDesign;
dataMap.put("experimentDesign",lmsexperiment.getExperimentDesign());
//映射lmsexperiment的experimentRequired給experimentRequired;
dataMap.put("experimentRequired",lmsexperiment.getExperimentRequired());
//映射lmsexperiment的experimentPurposes給experimentPurposes;
dataMap.put("experimentPurposes",lmsexperiment.getExperimentPurposes());
//映射lmsexperiment的experimentAward給experimentAward;
dataMap.put("experimentAward",lmsexperiment.getExperimentAward());
//若是lmsexperiment的學院不爲空
if(lmsexperiment.getSysAcademy()!=null){
//映射lmsexperiment的AcademyName給academyName;
dataMap.put("academyName",lmsexperiment.getSysAcademy().getAcademyName());
}
//不然設置lmsexperiment的null爲academyName
else{
dataMap.put("academyName", "");
}
//若是lmsexperiment的課程不爲空
if(lmsexperiment.getSysCourse()!=null){
//映射lmsexperiment的CourseName給courseName;
dataMap.put("courseName",lmsexperiment.getSysCourse().getCourseName());
}
//不然設置lmsexperiment的null爲courseName
else{
dataMap.put("courseName","");
}
//若是lmsexperiment的實驗室不爲空
if(lmsexperiment.getLmsLab()!=null){
//映射lmsexperiment的labName給labName;
dataMap.put("labName",lmsexperiment.getLmsLab().getLabName());
}
//不然設置lmsexperiment的null爲courseName
else{
dataMap.put("courseName","");
}
//若是lmsexperiment的項目類型不爲空
if(lmsexperiment.getDataFieldByExperimentCategory()!=null){
//映射lmsexperiment的categoryName給categoryName;
dataMap.put("categoryName",lmsexperiment.getDataFieldByExperimentCategory().getName());
}
//不然設置lmsexperiment的null爲categoryName
else{
dataMap.put("categoryName","");
}
WordHandler handler = new WordHandler();
//生成word
File outFile =handler.createDoc("/com/ftl", "AA.ftl", dataMap,lmsexperiment.getExperimentName());
//下面的代碼是導出word
FileInputStream in = null;
OutputStream o = null;
try {
in = new FileInputStream(outFile);
o = response.getOutputStream();
response.setContentType("application/x-tar");
response.setHeader("Content-disposition", "attachment; filename="
+ URLEncoder.encode(lmsexperiment.getExperimentName()+".doc", "UTF-8"));// 指定下載的文件名
response.setHeader("Content_Length",String.valueOf( outFile.length())); // download the file.
int n = 0;
while ((n = in.read (b))!= -1)
{
o.write(b, 0, n);
}
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
in.close();
o.flush();
o.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
經測試這樣方式生成導出word文檔徹底符合office標準,樣式、內容控制很是便利,打印也不會變形,生成的文檔和office中編輯文檔徹底同樣。