最近公司要弄个报表相关的功能,话不多说,先上图

   前一种是POI 生成的,后一种是Echarts生成的。报表我想大家都不陌生,基本上在公司业务中都会使用到。先说说POI,jquery.table2excel.js,Echarts这三种使用区别吧,本篇博客主要是使用上,如果只是像表格那样标准格式的导出的话,我想用table2挺好,只要把相关的js引入就可以使用,不用像poi那样生成模板,添加样式什么的。在网上都能搜到一大堆代码,当然了能不能用就不知道了。https://blog.csdn.net/weixin_36751895/article/details/79303854 这是相关链接;

   POI虽然麻烦点,但是可以随着我们的心意基本上可以实现,就如第一种那种特殊样式的报表。

   POI一般分为三个步骤:

          1. 首先是POI 样式/模板的生成,你需要什么样式/模板,这是相关代码:

import java.io.*;
import java.text.SimpleDateFormat;

import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFClientAnchor;
import org.apache.poi.hssf.usermodel.HSSFFont;
import org.apache.poi.hssf.usermodel.HSSFPatriarch;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.VerticalAlignment;
import org.apache.poi.ss.usermodel.ClientAnchor.AnchorType;
import org.apache.poi.ss.util.CellRangeAddress;
import java.net.HttpURLConnection;
import java.net.URL;

import com.cn.jr.model.JrUser;
import com.cn.rz.model.JrUserOrders;

public class ExportExcel {

    public void getValue(JrUser jrUser, JrUserOrders jrUserOrders, String imageUrl, OutputStream outData) {
          if (jrUser == null || jrUserOrders == null) {
            jrUser = new JrUser();
            jrUserOrders = new JrUserOrders();
          }
        HSSFWorkbook workbook = new HSSFWorkbook();

          try {
            // 1.创建工作簿
            // 1.1创建合并单元格对象
            CellRangeAddress callRangeAddress = new CellRangeAddress(0, 2, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress1 = new CellRangeAddress(3, 4, 0, 2);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress20 = new CellRangeAddress(3, 4, 3, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress21 = new CellRangeAddress(5, 6, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress22 = new CellRangeAddress(7, 8, 0, 2);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress31 = new CellRangeAddress(7, 8, 3, 4);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress32 = new CellRangeAddress(7, 8, 5, 7);// 起始行,结束行,起始列,结束列

            CellRangeAddress callRangeAddress34 = new CellRangeAddress(9, 10, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress35 = new CellRangeAddress(11, 12, 0, 2);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress36 = new CellRangeAddress(11, 12, 3, 4);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress37 = new CellRangeAddress(11, 12, 5, 7);// 起始行,结束行,起始列,结束列

            CellRangeAddress callRangeAddress38 = new CellRangeAddress(13, 14, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress39 = new CellRangeAddress(15, 16, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress40 = new CellRangeAddress(17, 18, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress41 = new CellRangeAddress(19, 20, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress42 = new CellRangeAddress(21, 22, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress43 = new CellRangeAddress(23, 24, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress44 = new CellRangeAddress(25, 26, 0, 7);// 起始行,结束行,起始列,结束列

            CellRangeAddress callRangeAddress45 = new CellRangeAddress(27, 34, 0, 7);// 起始行,结束行,起始列,结束列
            CellRangeAddress callRangeAddress47 = new CellRangeAddress(35, 35, 0, 7);// 起始行,结束行,起始列,结束列

            HSSFCellStyle erStyle = createCellStyle(workbook, (short) 13, true, true, false);
            HSSFCellStyle sanStyle = createCellStyle(workbook, (short) 10, true, false, false);

            HSSFCellStyle nameStyle = createCellStyle(workbook, (short) 10, false, false, false);
            HSSFCellStyle dataStyle = createCellStyle(workbook, (short) 10, false, true, false);
            // 创建工作表
            HSSFSheet sheet = workbook.createSheet();
            // 加载合并单元格对象
            sheet.addMergedRegion(callRangeAddress);
            sheet.addMergedRegion(callRangeAddress1);
            sheet.addMergedRegion(callRangeAddress20);
            sheet.addMergedRegion(callRangeAddress21);
            sheet.addMergedRegion(callRangeAddress22);
            sheet.addMergedRegion(callRangeAddress31);
            sheet.addMergedRegion(callRangeAddress32);

            sheet.addMergedRegion(callRangeAddress34);
            sheet.addMergedRegion(callRangeAddress35);
            sheet.addMergedRegion(callRangeAddress36);
            sheet.addMergedRegion(callRangeAddress37);
            sheet.addMergedRegion(callRangeAddress38);
            sheet.addMergedRegion(callRangeAddress39);
            sheet.addMergedRegion(callRangeAddress40);
            sheet.addMergedRegion(callRangeAddress41);
            sheet.addMergedRegion(callRangeAddress42);
            sheet.addMergedRegion(callRangeAddress43);
            sheet.addMergedRegion(callRangeAddress44);
            sheet.addMergedRegion(callRangeAddress45);
            sheet.addMergedRegion(callRangeAddress47);
            // 设置默认列宽
            sheet.setDefaultColumnWidth(15);
            // 标题
            HSSFRow rower = sheet.createRow(0);
            HSSFCell celler = rower.createCell(0);
            celler.setCellStyle(erStyle);
            celler.setCellValue("融资租赁收费确认单");

            // 客户姓名,手机号码
            HSSFRow rowsan = sheet.createRow(3);
            HSSFCell cellsan = rowsan.createCell(0);
            HSSFCell cellsan2 = rowsan.createCell(3);
            cellsan.setCellStyle(sanStyle);
            cellsan.setCellValue("客户姓名: " + jrUser.getRealName());
            cellsan2.setCellStyle(sanStyle);
            cellsan2.setCellValue("手机号码: " + jrUser.getTelphone());
            // 车型
            HSSFRow rowCar = sheet.createRow(5);
            HSSFCell carsan = rowCar.createCell(0);
            carsan.setCellStyle(sanStyle);
            if ("0".equals(jrUserOrders.getCarType())) {
                carsan.setCellValue("车型: " + "新车");
            } else if ("1".equals(jrUserOrders.getCarType())) {
                carsan.setCellValue("车型: " + "二手车");
            } else {
                carsan.setCellValue("车型: " + "");
            }

            // 车价,购置税,保险
            HSSFRow rowpersion = sheet.createRow(7);
            HSSFCell cellpersion = rowpersion.createCell(0);
            HSSFCell cellpersion1 = rowpersion.createCell(3);
            HSSFCell cellpersion2 = rowpersion.createCell(5);
            cellpersion.setCellStyle(sanStyle);
            cellpersion.setCellValue("车价: " + jrUserOrders.getCarPrice() + " 元");
            cellpersion1.setCellStyle(sanStyle);
            cellpersion1.setCellValue("购置税: " + jrUserOrders.getPurchaseTax() + " 元");
            cellpersion2.setCellStyle(sanStyle);
            cellpersion2.setCellValue("保险: " + jrUserOrders.getInsurance() + " 元");
            // 首付贷
            HSSFRow rowOne = sheet.createRow(9);
            HSSFCell onesan = rowOne.createCell(0);
            onesan.setCellStyle(sanStyle);
            onesan.setCellValue("首付贷: " + jrUserOrders.getDownPayments() + " 元");
            // 车价,购置税,保险
            HSSFRow rowRz = sheet.createRow(11);
            HSSFCell cellrz = rowRz.createCell(0);
            HSSFCell cellqs = rowRz.createCell(3);
            HSSFCell cellmonth = rowRz.createCell(5);
            cellrz.setCellStyle(sanStyle);
            cellrz.setCellValue("融资金额: " + jrUserOrders.getRzAmt() + " 元");
            cellqs.setCellStyle(sanStyle);
            cellqs.setCellValue("期数: " + jrUserOrders.getRzqs() + " 期");
            cellmonth.setCellStyle(sanStyle);
            cellmonth.setCellValue("月还款额: " + jrUserOrders.getMonthPay() + " 元");
            // 保证金
            HSSFRow rowamt = sheet.createRow(13);
            HSSFCell amtsan = rowamt.createCell(0);
            amtsan.setCellStyle(sanStyle);
            amtsan.setCellValue("保证金: " + jrUserOrders.getBond() + " 元" + " (总额5%)");

            // 手续费
            HSSFRow proceduresrow = sheet.createRow(15);
            HSSFCell proceduresAmt = proceduresrow.createCell(0);
            proceduresAmt.setCellStyle(sanStyle);
            proceduresAmt.setCellValue("手续费: " + jrUserOrders.getProceduresAmt() + " 元" + " (总额3%)");
            // 续保押金
            HSSFRow renewDepositrow = sheet.createRow(17);
            HSSFCell renewDeposit = renewDepositrow.createCell(0);
            renewDeposit.setCellStyle(sanStyle);
            renewDeposit.setCellValue("续保押金: " + jrUserOrders.getRenewDeposit() + " 元");
            // GPS费
            HSSFRow gps = sheet.createRow(19);
            HSSFCell gpssan = gps.createCell(0);
            gpssan.setCellStyle(sanStyle);
            gpssan.setCellValue("GPS费: " + jrUserOrders.getGpsAmt() + " 元");
            // 公证费
            HSSFRow notarization = sheet.createRow(21);
            HSSFCell notarizationAmt = notarization.createCell(0);
            notarizationAmt.setCellStyle(sanStyle);
            notarizationAmt.setCellValue("公证费: " + jrUserOrders.getNotarizationAmt() + " 元");
            // 家访费
            HSSFRow home = sheet.createRow(23);
            HSSFCell homesan = home.createCell(0);
            homesan.setCellStyle(sanStyle);
            homesan.setCellValue("家访费: " + jrUserOrders.getHomeVisitAmt() + " 元");
            // 其他
            HSSFRow other = sheet.createRow(25);
            HSSFCell othersan = other.createCell(0);
            othersan.setCellStyle(sanStyle);
            othersan.setCellValue("其他: " + jrUserOrders.getHomeVisitAmt() + " 元");
            // 签名
            HSSFRow png = sheet.createRow(27);
            HSSFCell pngsan = png.createCell(0);
            pngsan.setCellStyle(nameStyle);
            pngsan.setCellValue("以上收费标准本人已确认无误.客户签名: ");

            HSSFPatriarch patriarch = sheet.createDrawingPatriarch();
            drawPictureInfoExcel(workbook, patriarch, imageUrl);

            // 签名日期
            HSSFRow pngDate = sheet.createRow(35);
            HSSFCell pngDatesan = pngDate.createCell(0);
            pngDatesan.setCellStyle(dataStyle);
            SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
            pngDatesan.setCellValue("日期: " + simpleDateFormat.format(jrUserOrders.getCreatedate()));

            // 5.输出
            workbook.write(outData);
            // workbook.close();
            // out.close();

            } catch (Exception e) {
              e.printStackTrace();
            }
    }

          

          /** 单元格样式*/

          private static HSSFCellStyle createCellStyle(HSSFWorkbook workbook, short fontsize, boolean flagRow, boolean flagC,boolean flagDate) {
                // TODO Auto-generated method stub
                HSSFCellStyle style = workbook.createCellStyle();
                // 是否水平居中
              if (flagRow) {
                  style.setVerticalAlignment(VerticalAlignment.CENTER);// 水平居中
              } else {
                  style.setVerticalAlignment(VerticalAlignment.TOP);
              }

              // 创建字体
              HSSFFont font = workbook.createFont();
              // 是否加粗字体
              if (flagC) {
                style.setAlignment(HorizontalAlignment.CENTER);// 垂直居中
                font.setFontHeightInPoints((short) 10);
              }
              if (flagDate) {
                style.setAlignment(HorizontalAlignment.RIGHT);// 垂直居右
                font.setFontHeightInPoints((short) 8);
              }

                font.setFontHeightInPoints(fontsize);
            // 加载字体
                style.setFont(font);
                return style;
              }

           public static void drawPictureInfoExcel(HSSFWorkbook wb, HSSFPatriarch patriarch, String imageUrl) {
              try {
                URL url = new URL(imageUrl);
                  // 打开链接
                HttpURLConnection conn = (HttpURLConnection) url.openConnection();
                // 设置请求方式为"GET"
                conn.setRequestMethod("GET");
                // 超时响应时间为5秒
                conn.setConnectTimeout(5 * 1000);
                // 通过输入流获取图片数据
                InputStream inStream = conn.getInputStream();
                byte[] data = readInputStream(inStream);
                // anchor主要用于设置图片的属性
                // HSSFClientAnchor hssfClientAnchor = new
                // HSSFClientAnchor(dx1,dy1,dx2,dy2,col1,row1,col2,row2);
                HSSFClientAnchor anchor = new HSSFClientAnchor(0, 0, 0, 0, (short) 0, 28, (short) 8, 35);
                // 图片在单元格的位置
                anchor.setAnchorType(AnchorType.DONT_MOVE_AND_RESIZE);
                patriarch.createPicture(anchor, wb.addPicture(data, HSSFWorkbook.PICTURE_TYPE_JPEG));

              } catch (Exception e) {
                e.printStackTrace();
              }
          }

            private static byte[] readInputStream(InputStream inStream) throws Exception {
                  ByteArrayOutputStream outStream = new ByteArrayOutputStream();
                  // 创建一个Buffer字符串
                  byte[] buffer = new byte[1024];
                  // 每次读取的字符串长度,如果为-1,代表全部读取完毕
                  int len = 0;
                  // 使用一个输入流从buffer里把数据读取出来
              while ((len = inStream.read(buffer)) != -1) {
                  // 用输出流往buffer里写入数据,中间参数代表从哪个位置开始读,len代表读取的长度
                  outStream.write(buffer, 0, len);
                }
              // 关闭输入流
              inStream.close();
              // 把outStream里的数据写入内存
              return outStream.toByteArray();
          }

        /*
          * public static void main(String args[]){ //模拟部分数据 try { FileOutputStream
          * fout = new FileOutputStream("I:/333.xls"); // new
          * ExportExcel().getValue(fout); fout.close(); } catch (Exception e) {
          * e.printStackTrace(); }
          *
        * }*/

    }

    其中单元格样式网上大部分的POI 都是老版本的,所以有许多代码没有相关的api, 上面的代码中单元格样式相关API是新版的,代码都可以直接使用。

          2. 样式什么的都创建好了,接下来就是使用调用了(controller),

          SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
          String date = simpleDateFormat.format(new Date()).toString();
          String fileName = date + jrUser.getRealName() + "/融资租赁收费确认单";
          OutputStream outData = response.getOutputStream();
          response.reset();
          response.setContentType("application/vnd.ms-excel;charset=gbk");
          response.addHeader("Content-Disposition",
          "attachment;filename=" + new String((fileName + ".xls").getBytes("gbk"), "ISO-8859-1"));

          ExportExcel exportExcel = new ExportExcel();

          String basePath = request.getContextPath();
          String imagePath = request.getScheme() + "://" + request.getServerName() + ":" + request.getServerPort()
                    + basePath + "/ui/rzJs/orders.png";
          exportExcel.getValue(jrUser, jrUserOrders, imagePath, outData);

          3. jsp当然少不了,当然了,如果你不是做成弹窗式下载,就可以不要弹窗jsp,把2中的代码改成用流写入到本地位置即可

          <form id="myform" enctype="multipart/form-data"   action="<%=basePath%>/rzJrUsre/batchExport" method="post"    role="form">
                      <table>
                <tr>
                  <td><input type="submit" value="导出"       style="margin-left: 1550px;" /></td>
                </tr>
              </table>
          </form>

    以上代码都是可以直接使用的,当然了如果有什么不能使用的地方,就需要各位大神自己动手改改相关代码了,毕竟环境,需求不可能一定相同。其实POI使用原理也挺简单的,就是弄个模板,然后用流将信息写入,用流操作。明白这些使用POI也不难。

    最后是Echarts,是百度的一款做报表的相关开源API,http://www.echartsjs.com/index.html  这是首页链接,使用相对于来说跟table2一样也挺简单,引入js,使用api。 当然了也有其局限性:数据量一大就不行了,不过其美观性方面确实不错。 这有一个基于Echarts开发的软件:http://www.smartbi.com.cn/spreadsheet  其做的相对很好。其中大量案例,模板,可以进去看看,再根据Echarts官方的API,文档就很容易理解,上手Echarts了。

     Echarts导出有图片时,传到后台的是base64编码的字符串,所以后台接收需要做出相关处理。

          function getFullCanvasDataURL(divId){
                    //将第一个画布作为基准。
                    var baseCanvas = $("#"+divId).find("canvas").first()[0];
                    if(!baseCanvas){
                        return false;
                      };
                  var width = baseCanvas.width;
                  var height = baseCanvas.height;
                  var ctx = baseCanvas.getContext("2d");
                  //遍历,将后续的画布添加到在第一个上
                  $("#"+divId).find("canvas").each(function(i,canvasObj){
                  if(i>0){
                      var canvasTmp = $(canvasObj)[0];
                      ctx.drawImage(canvasTmp,0,0,width,height);
                    }
             });
                  //获取base64位的url
                  return baseCanvas.toDataURL();
              }

             function importBtnn() {
                  var data = getFullCanvasDataURL("main");
                  $("#img").val(data);
                  var img= $("#img").val();
                  $("#myform").submit();
              };

    我想有了这三种制作表格的方式足以实现业务中的需求了。有不懂的, 有问题,有建议欢迎大家随时提出,自己也是刚开始写博客。希望能坚持,努力下去,学无止境。

    在此,希望此篇博客能帮助到一些人。有不足之处,有问题的话可以博客上Q我,看到就会回复

  

报表生成(POI,jquery.table2excel.js,Echarts)的更多相关文章

  1. jquery插件导出word:jquery.wordexport.js

    前言 今天项目中遇到一个需求把我们系统中的统计数据导出来(主要是表格).其实实现的的方法有很多,而此次针对我的系统第一获取数据有点慢,加上前不久写了一个在线阅读pdf,故此这次也想用前端的方式来导出. ...

  2. jquery.table2excel,将HTML的table标签数据导出成excel

    <!DOCTYPE> <html> <head> <meta http-equiv="Content-Type" content=&quo ...

  3. jquery.wordexport.js打印echarts.js画出的柱状图

    jquery.wordexport.js打印echarts.js画出的柱状图. echarts画出的图是不能直接打印出来的(echarts的柱状图是用canvas画出来的),而jquery.worde ...

  4. jquery.js和jquery.min.js的区别和springboot整合echarts.min.js

    1.区别:jquery官网提供2种jQuery的下载,一种是jquery.js另一种是jquery.min.js文件名不一定完全相同,但通常情况下:jquery.js是完整的未压缩的jQuery库,文 ...

  5. Spring Data Jpa+SpringMVC+Jquery.pagination.js实现分页

    本博客介绍基于Spring Data这款orm框架加上Jquery.pagination插件实现的分页功能. 介绍一下Spring Data框架 spring Data : Spring 的一个子项目 ...

  6. a页面通过url传值,b页面如何接收(jquery.params.js实现)

    用于两个html页面之间的传值 我的应用场景是:用echarts在a页面做完中国地图后,点击某个省份在b页面显示某个省份的地图.(在b页面显示点击了的那个省份的地图,等于说b页面是个“容器”页) 假设 ...

  7. SaaS系统怎么做物流行业年度经营报告,MVC+js+echarts实现

    前言 马上就到年底了,很多公司都要汇总这一年的经营情况,如果一个系统没有自动生成年报的功能, 需要人工手工去做年报,我相信可能是一个不小的工作量,最近我通过一个星期的时间,结合系统情况自动生成年报,全 ...

  8. jquery和Js的区别和基础操作

    jqery的语法和js的语法一样,算是把js升级了一下,这两种语法可以一起使用,只不过是用jqery更加方便 一个页面想要使用jqery的话,先要引入一下jqery包,jqery包从网上下一个就可以, ...

  9. jQuery.template.js 简单使用

    之前看了一篇文章<我们为什么要尝试前后端分离>,深有同感,并有了下面的评论: 我最近也和前端同事在讨论这个问题,比如有时候前端写好页面给后端了,然后后端把这些页面拆分成很多的 views, ...

随机推荐

  1. selenium窗口截图操作

    selenium窗口截图操作 使用背景:在自动化测试过程中,可能遇到执行错误情况,那么怎么样及时捕获出错信息/界面? 可以使用  get_screenshot_as_file(self,filenam ...

  2. windows 使用ssh连接docker容器

    在Windows上搭建docker服务器需要在Windows模拟一个Linux平台,然后在Linux平台上搭建的docker服务器,所以在使用ssh工具连接docker容器的时候,使用的ip地址不是d ...

  3. Go语言实现:【剑指offer】对称的二叉树

    该题目来源于牛客网<剑指offer>专题. 请实现一个函数,用来判断一颗二叉树是不是对称的.注意,如果一个二叉树同此二叉树的镜像是同样的,定义其为对称的. Go语言实现: 方法一:递归 / ...

  4. 11-HTTP请求协议

    今日知识 1. http 2. Tomcat使用 3. 知识总结 HTTP 1. 概念:Hyper Text Transfer Protocol * 传输协议:定义了,客户端和服务器通信时,发送的数据 ...

  5. 增加yum源方式 安装升级 Mysql

             MySQL官方新提供了一种安装MySQL的方法--使用YUM源安装MySQL 1.MySQL官方网站下载MySQL的YUM源,  https://dev.mysql.com/down ...

  6. [RHEL8]开启BBR

    # sysctl net.ipv4.tcp_congestion_control net.ipv4.tcp_congestion_control = cubic # sysctl net.ipv4.t ...

  7. 查看Linux系统内存、CPU、磁盘使用率和详细信息

    一.查看内存占用 1.free # free -m 以MB为单位显示内存使用情况 [root@localhost ~]# free -m total used free shared buff/cac ...

  8. Yet Another Broken Keyboard[双指针]

    题目大意: 求贡献,已知公式n*(n+1)/2,求总和 收获: long long的转换技巧只能在乘或除上进行 题目链接 #include<bits/stdc++.h> typedef l ...

  9. Linux安装Redis,在测试阶段即make test出现“You need tcl 8.5 or newer in order to run the Redis test”问题解决方案

    Linux安装Redis,在测试阶段即make test出现"You need tcl 8.5 or newer in order to run the Redis test"问题 ...

  10. python新手如何编写一个猜数字小游戏

    此文章只针对新手,希望大家勿喷,感谢!话不多说先上代码: import random if __name__ == '__main__': yourname = input("你好! 你的名 ...