动态创建excel文件,动态合并单元格并提供下载

1.动态生成excel的原因

这里写图片描述

**

出现的效果:

**
这里写图片描述

员工姓名没有自动合并单元格,在http://jxls.sourceforge.net/reference/xls_area.html 上面找了半天没有相关的案例,于是就自己代码生成

2.动态生成excel文件,并动态合并单元格

package com.baptechs.zeus.domain.base.xls;

import com.baptechs.zeus.domain.headquarters.customerapp.posprepay.NozzleAuthExport;
import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFFont;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.util.CellRangeAddress;

import java.io.FileNotFoundException;
import java.io.OutputStream;
import java.util.List;

/**
 * Created by Amence on 2017/9/14.
 * <p/>
 * 该类只针对动态创建 员工考核报表
 */
public class AttendanceXLSXUtil {


    public static void createXLSX(List<NozzleAuthExport> nozzleAuthExports, String startTime, String endTime, OutputStream os) throws FileNotFoundException {
        //新建excel报表
        HSSFWorkbook excel = new HSSFWorkbook();
        //添加一个sheet,名字叫"加油工考核表"
        HSSFSheet hssfSheet = excel.createSheet("加油工考核表");
        //excel格式
        HSSFCellStyle style = excel.createCellStyle();

        //字体样式
        HSSFFont font1 = excel.createFont();


        CellRangeAddress cellRangeAddress1 = new CellRangeAddress(0, 2, 1, 10);
        //在sheet里增加合并单元格
        hssfSheet.addMergedRegion(cellRangeAddress1);
        //生成第一行
        Row row = hssfSheet.createRow(0);
        Cell cell = row.createCell(1);
        cell.setCellValue("加油站员工考核表");
        _setBorder(style, font1, 26, true, HSSFCellStyle.ALIGN_CENTER);
        cell.setCellStyle(style);
        //在sheet里增加合并单元格时间
        CellRangeAddress cellRangeAddress2 = new CellRangeAddress(4, 4, 1, 2);//第四行到第四行 第一列到第二列
        hssfSheet.addMergedRegion(cellRangeAddress2);
        //在sheet里增加合并单元格时间(获取)
        CellRangeAddress cellRangeAddress3 = new CellRangeAddress(4, 4, 3, 4);
        hssfSheet.addMergedRegion(cellRangeAddress3);
        Row row1 = hssfSheet.createRow(4);
        row1.setHeightInPoints(20);
        Cell cell1 = row1.createCell(1);
        cell1.setCellValue("开始时间:");

        HSSFFont font = excel.createFont();
        HSSFCellStyle style1 = excel.createCellStyle();
        _setBorder(style1, font, 11, false, HSSFCellStyle.ALIGN_RIGHT);
        cell1.setCellStyle(style1);

        Cell cell2 = row1.createCell(3);
        cell2.setCellValue(startTime);
        HSSFCellStyle style2 = excel.createCellStyle();
        _setBorder(style2, font, 11, false, HSSFCellStyle.ALIGN_LEFT);
        cell2.setCellStyle(style2);

        //在sheet里增加合并单元格 结束时间
        CellRangeAddress cellRangeAddress4 = new CellRangeAddress(4, 4, 7, 8);
        hssfSheet.addMergedRegion(cellRangeAddress4);
        //在sheet里增加合并单元格时间(获取)
        CellRangeAddress cellRangeAddress5 = new CellRangeAddress(4, 4, 9, 10);
        hssfSheet.addMergedRegion(cellRangeAddress5);
        Cell cell3 = row1.createCell(7);
        cell3.setCellValue("结束时间:");
        HSSFCellStyle style3 = excel.createCellStyle();
        _setBorder(style3, font, 11, false, HSSFCellStyle.ALIGN_RIGHT);
        cell3.setCellStyle(style3);

        Cell cell4 = row1.createCell(9);
        cell4.setCellValue(endTime);
        HSSFCellStyle style4 = excel.createCellStyle();
        _setBorder(style4, font, 11, false, HSSFCellStyle.ALIGN_LEFT);
        cell4.setCellStyle(style4);
        String[] title = {"员工姓名", "油品", "加油次数", "加油升数", "销售额"};

        Row row2 = hssfSheet.createRow(5);
        row2.setHeightInPoints(40);//设置行高
        for (int i = 0; i < title.length; i++) {
            CellRangeAddress cellRangeAddress6 = new CellRangeAddress(5, 5, 2 * i + 1, 2 * (i + 1));
            hssfSheet.addMergedRegion(cellRangeAddress6);
            //表头  第6行
            //从第二列开始
            for (int y = 2 * i + 1; y < 2 * (i + 1) + 1; y++) {
                Cell cell5 = row2.createCell(y);
                cell5.setCellValue(title[i]);
                HSSFCellStyle style5 = excel.createCellStyle();
                HSSFFont font2 = excel.createFont();
                font2.setBold(true);
                setBorder(style5, font2, 18);
                cell5.setCellStyle(style5);
            }
        }

        int weight = 0;                                       //上一行的高度
        //填充XMSL数据
        for (int i = 0; i < nozzleAuthExports.size(); i++) { // 员工数

            int high = nozzleAuthExports.get(i).getInfos().size(); //获取新增高度
            if (i != 0) {
                weight += nozzleAuthExports.get(i - 1).getInfos().size() + 1;  //从第二行算起
            }
            int rowHigh = 0;                                      //姓名初始单元格初始化高度
            Row row3;
            Cell cell6;
            for (int y = 0; y < high + 1; y++) {  //油品数 + 小计

                rowHigh = 6 + y + weight;                         //动态定位行

                row3 = hssfSheet.createRow(rowHigh);             //创建行

                for (int x = 1; x < 3; x++) {           //必须要每个cell都要创建
                    //创建姓名
                    cell6 = row3.createCell(x);
                    cell6.setCellValue(nozzleAuthExports.get(i).getUserName());
                    HSSFCellStyle style6 = excel.createCellStyle();
                    HSSFFont font3 = excel.createFont();
                    setBorder(style6, font3, 11);
                    cell6.setCellStyle(style6);
                }

                row3.setHeightInPoints(20);//设置行高
                for (int z = 0; z < 4; z++) { //填充数据
                    //创建单元格

                    CellRangeAddress cellRangeAddress6 = new CellRangeAddress(rowHigh, rowHigh, 2 * z + 3, 2 * z + 4); //合并单元格,行-行。列-列

                    hssfSheet.addMergedRegion(cellRangeAddress6);

                    for (int m = 2 * z + 3; m < 2 * z + 5; m++) {
                        Cell cell5 = row3.createCell(m);  //定义列


                        HSSFCellStyle style5 = excel.createCellStyle();
                        HSSFFont font2 = excel.createFont();

                        if (y == nozzleAuthExports.get(i).getInfos().size()) { //小计
                            switch (z) {
                                case 0:
                                    cell5.setCellValue("小计");
                                    break;
                                case 1:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getAllOilCount());
                                    break;
                                case 2:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getAllVolume().toString());

                                    break;
                                case 3:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getAllSale().toString());

                                    break;

                            }
                            font2.setBold(true);


                        } else {
                            switch (z) {
                                case 0:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getInfos().get(y).getFlueName());
                                    break;
                                case 1:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getInfos().get(y).getOilCount());
                                    break;
                                case 2:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getInfos().get(y).getVolume().toString());
                                    break;
                                case 3:
                                    cell5.setCellValue(nozzleAuthExports.get(i).getInfos().get(y).getSales().toString());
                                    break;

                            }
                            font2.setBold(false);
                        }
                        setBorder(style5, font2, 11);
                        cell5.setCellStyle(style5);
                    }

                }

            }

            //合并姓名单元格
            CellRangeAddress cellRangeAddress7 = new CellRangeAddress(6 + weight, rowHigh, 1, 2);
            hssfSheet.addMergedRegion(cellRangeAddress7);
        }

        try {
            excel.write(os);
            os.flush();
            os.close();
        } catch (Exception e) {
            e.printStackTrace();
        }

    }


    public static void setBorder(HSSFCellStyle style, HSSFFont font, int fontSize) {
        font.setFontHeightInPoints((short) fontSize);
        style.setFont(font);
        style.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);//垂直
        style.setAlignment(HSSFCellStyle.ALIGN_CENTER);//水平
        style.setBorderBottom(HSSFCellStyle.BORDER_THIN); //下边框
        style.setBorderLeft(HSSFCellStyle.BORDER_THIN);//左边框
        style.setBorderTop(HSSFCellStyle.BORDER_THIN);//上边框
        style.setBorderRight(HSSFCellStyle.BORDER_THIN);//右边框

    }

    public static void _setBorder(HSSFCellStyle style, HSSFFont font, int fontSize, boolean bold, short alignment) {

        font.setFontHeightInPoints((short) fontSize);
        font.setBold(bold);
        style.setFont(font);
        style.setAlignment(alignment);
        style.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);//垂直


    }
}

直接上代码。效果图:

这里写图片描述

主要的代码就是

 CellRangeAddress cellRangeAddress7 = new CellRangeAddress(6 + weight, rowHigh, 1, 2);

 hssfSheet.addMergedRegion(cellRangeAddress7);

其余的代码都是按需求生成表格。对于合并单元格后的边框问题。需要把合并的单元个全部创建出来。我没有找到更好的方法,其他人的说的不清不楚。

  for (int x = 1; x < 3; x++) {           //必须要每个cell都要创建
                    //创建姓名
                    cell6 = row3.createCell(x);
                    cell6.setCellValue(nozzleAuthExports.get(i).getUserName());
                    HSSFCellStyle style6 = excel.createCellStyle();
                    HSSFFont font3 = excel.createFont();
                    setBorder(style6, font3, 11);
                    cell6.setCellStyle(style6);
                }

3.提供下载功能

javaWeb的下载 直接上代码

 HttpServletResponse response = getHttpServletResponse();
        String startTime = nozzleAuthInfo.getStartTime() == null ? "不限" : DateUtil.formatDateToString(nozzleAuthInfo.getStartTime());
        String endTime = nozzleAuthInfo.getEndTime() == null ? "不限" : DateUtil.formatDateToString(nozzleAuthInfo.getEndTime());


        try {
            response.setContentType(MediaType.APPLICATION_OCTET_STREAM.toString());
            response.setCharacterEncoding("UTF-8");
            response.setHeader("Content-Disposition", "attachment; filename=" + new String("员工考核".getBytes("gbk"), "iso-8859-1") + new SimpleDateFormat("yyyyMMddHHmmss").format(new Date()) + ".xlsx");
            response.setContentType("application/octet-stream");
            OutputStream os  = new BufferedOutputStream(response.getOutputStream());
            AttendanceXLSXUtil.createXLSX(nozzleAuthExports, startTime, endTime,os);
        } catch (IOException e) {
            e.printStackTrace();
        }
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值