在做项目的时候遇到过很多奇葩的需求,其中一个是:导出excel报表,报表要求按照指定格式导出,问题就出在这个指定格式上面,什么居中,合并单元格这些基本需求就不细说了,其中一个要求是导出报表中一列字段是由多条记录查询统计拼接出来的,要求把拼接的时候其中重复的值标红展示。
刚看见这个需求的时候就呆住了,poi能实现这个功能吗?好像没有见过这样用呀,不都是一个一个单元格设置style吗?于是急不可耐的去查找API,网上各种搜索,终于让我找到了;
POI中的HSSFFont 是用来设置样式的,但是一直以来都是使用cellStyle.setFont(font);直接给单元格设置整体属性,这次才知道原来可以同个给HSSFRichTextString 来给单元格中字符串设置不同的样式,具体使用方法如下:
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.hssf.util.HSSFColor;
import java.io.File;
import java.io.IOException;
public static void main( String[] args ) throws IOException {
HSSFWorkbook workbook = new HSSFWorkbook();
HSSFSheet sheet = workbook.createSheet("自定义单元格部分内容颜色");
HSSFRow row = sheet.createRow(5);
HSSFCell cell = row.createCell(5);
HSSFCellStyle cellStyle = workbook.createCellStyle();
HSSFFont font = workbook.createFont();
font.setColor(HSSFColor.HSSFColorPredefined.BLACK.getColor().getIndex());
HSSFFont font2 = workbook.createFont();
font2.setColor(HSSFColor.HSSFColorPredefined.RED.getColor().getIndex());
font2.setBold(true);
cellStyle.setFont(font);
cell.setCellStyle(cellStyle);
String txt = "abcdefghijklmnopqrsREDtuvwxyzredssssssssssss";
HSSFRichTextString text = new HSSFRichTextString(txt);
text.applyFont(txt.indexOf("RED"),txt.indexOf("RED")+3,font2);
cell.setCellValue(text);
sheet.autoSizeColumn(5,true);
File file = new File("C:\\Users\\95398\\Desktop\\我要变成红色的字体.xls");
if(file.exists()){
file.delete();
}
file.createNewFile();
workbook.write(new FileOutputStream( file ));
}
但是在这个测试类导出之后,的确是变红了,但是奇怪的是在变红之后,并没有按照我指定的要求,标红中间那一部分,在字符串'RED'之后的部分也标红了,这就奇怪了,不知道是遇见了什么bug,于是想了个折中的办法,如下:
String txt = "abcdefghijklmnopqrsREDtuvwxyzredssssssssssss";
HSSFRichTextString text = new HSSFRichTextString(txt);
text.applyFont(txt.indexOf("RED"),txt.indexOf("RED")+3,font2);
text.applyFont(txt.indexOf("RED")+3,txt.length(),font);
text.applyFont(txt.indexOf("red"),txt.indexOf("red")+3,font2);
text.applyFont(txt.indexOf("red")+3,txt.length(),font);
cell.setCellValue(text);
对,你没有看错,就是分段式的设置样式,这样就能解决上面遇到的那个问题,但是这个bug是如何产生的,也没有去细想,毕竟这样的需求也不多见,就见招拆招解决了。