zoukankan      html  css  js  c++  java
  • phpexcel导出

    <?php
    header("Content-type:text/html;charset=utf-8");
    require('./excel/PHPExcel.class.php');
    
    class ExcelExport {
    
        private $obj;
    
        public function __construct() {
            $this->obj = new PHPExcel();
        }
    
        /**
         * EXcel导出,包含标题、时间范围、表头、 数据、总计(本方法可适用于表头多项合并,对数据超过26列进行了处理。)
         * @param String $fileName   导出的excel文件名
         * @param Array $headArr     表头数组   如:  $headArr = ['序号','日期', '收入明细(元)'=>['预定金','安放费','服务费']]
         * @param String $timeRange  时间范围
         * @param Array $tmpFileds   用于计算数据的总计的
         * @param String $startRow   从excel第几行开始导出,默认第 1 行
         * @param String $startCol   从excel第几列开始导出,默认从 A 列
         */
        public function index($fileName, $headArr, $data, $timeRange = "", $tmpFileds = array(), $startRow = 1, $startCol = 'A') {
    //        ini_set("memory_limit",-1);
            //对数据进行检验
            if (empty($data) || !is_array($data)) {
                die("没有符合条件数据");
            }
            //检查文件名
            if (empty($fileName)) {
                exit('请输入文件名');
            }
    
            //创建PHPExcel对象,注意,不能少了
            $objPHPExcel = $this->obj;
    
            $lieNum = $this->_headArrLength($headArr); //dump($lieNum);die;
            $lastCellAscii = $this->_CloumnToAscii($startCol) + $lieNum - 1;
            $lastCell = $this->_AsciiToCloumn($lastCellAscii);
    
            //标题
            $startRow = $this->getExcelTitle($fileName, $lastCell, $startRow, $startCol, $objPHPExcel);
    //        dump($startRow);die;
            //时间范围
            if (!empty($timeRange)) {
                $startRow = $this->getExcelTimeRange($timeRange, $lastCell, $startRow, $startCol, $objPHPExcel);
            }
    
            //表头
            $startRow = $this->getExcelHeader($headArr, $startRow, $startCol, $objPHPExcel);
    
            //表格数据
            $this->getExcelData($data, $startRow, $startCol, $tmpFileds, $objPHPExcel);
    
            $date = date("Y_m_d", time());
            $fileName .= "_{$date}.xls";
    
            $fileName = iconv("utf-8", "gb2312", $fileName);
            //重命名表
            //设置活动单指数到第一个表,所以Excel打开这是第一个表
            $objPHPExcel->setActiveSheetIndex(0);
            ob_end_clean(); //清除缓冲区,避免乱码
            header('Content-Type: application/vnd.ms-excel');
            header("Content-Disposition: attachment;filename=" . $fileName);
            header('Cache-Control: max-age=0');
            $objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel5');
            $objWriter->save('php://output'); //文件通过浏览器下载
            exit;
        }
    
        public function getExcelTitle($fileName, $lastCell, $startRow, $startCol, $objPHPExcel) {
            //标题
            $objPHPExcel->getActiveSheet()->mergeCells($startCol . $startRow . ':' . $lastCell . $startRow);
            $objPHPExcel->setActiveSheetIndex(0)->setCellValue($startCol . $startRow, $fileName);
            $objPHPExcel->getActiveSheet()->getStyle($startCol . $startRow)->applyFromArray(array('font' => array('bold' => true), 'alignment' => array('horizontal' => 'center')));
    
            return $startRow + 1;
        }
    
        public function getExcelTimeRange($timeRange, $lastCell, $startRow, $startCol, $objPHPExcel) {
            //时间范围
            $objPHPExcel->getActiveSheet()->mergeCells($startCol . $startRow . ':' . $lastCell . $startRow);
            $objPHPExcel->setActiveSheetIndex(0)->setCellValue($startCol . $startRow, $timeRange);
            $objPHPExcel->getActiveSheet()->getStyle($startCol . $startRow)->applyFromArray(array('alignment' => array('horizontal' => 'right')));
    
            return $startRow + 1;
        }
    
        public function getExcelData($data, $startRow, $startCol, $tmpFileds, $objPHPExcel) {
            $objActSheet = $objPHPExcel->getActiveSheet();
            $total = array();
            //设置为文本格式
            foreach ($data as $key => $rows) { //行写入
                $ascii = $this->_CloumnToAscii($startCol);
                foreach ($rows as $keyName => $value) {// 列写入
                    $column = $this->_AsciiToCloumn($ascii);
                    //TODO float double
                    if (is_int($value)) {
                        $objActSheet->setCellValueExplicit($column . $startRow, $value, 'n');
                    } elseif (is_float($value)) {
                        $objActSheet->setCellValueExplicit($column . $startRow, sprintf("%.2f", $value), 'n');
                    } else {
                        $objActSheet->setCellValueExplicit($column . $startRow, $value, 's');
                    }
    
                    //是否含有总计
                    if (!empty($tmpFileds) && in_array($keyName, $tmpFileds)) {
                        $total[$column][$keyName] += $value;
                    }
                    $ascii++;
                }
                $startRow++;
            }
    
            //总计
            if (!empty($tmpFileds) && !empty($total)) {
                $objPHPExcel->setActiveSheetIndex(0)->setCellValue($startCol . $startRow, "总计");
                foreach ($total as $lie => $totalVal) {
                    foreach ($totalVal as $k => $v) {
                        $objPHPExcel->setActiveSheetIndex(0)->setCellValue($lie . $startRow, $v);
                    }
                }
            }
        }
    
        //将Ascii值转换为列名
        public function _AsciiToCloumn($accsi) {
            if ($accsi > ord("Z")) {
                $diff = $accsi - ord('Z');
                $sj_1 = ord('A') + intval($diff / 26);
                $sj_2 = ord('A') + $diff % 26;
                $currentCloumn = chr($sj_1) . chr($sj_2); //超过26个字母时才会启用  
            } else {
                $currentCloumn = chr($accsi);
            }
    
            return $currentCloumn;
        }
    
        //将列名转换为Ascii值
        public function _CloumnToAscii($cloumn) {
            if (strlen($cloumn) > 1) {
                $sj_1 = substr($cloumn, 0, 1);
                $sj_2 = substr($cloumn, 1, 1);
                $diff = intval((ord($sj_1) - ord('A') + 1) * 26) + intval(ord($sj_2));
                $currentAcsii = $diff; //超过26个字母时才会启用  
            } else {
                $currentAcsii = ord($cloumn);
            }
    
            return $currentAcsii;
        }
    
        //获取表格表头所行数(数组深度)
        public function _headArrDepth($array) {
            $max_depth = 1;
            foreach ($array as $value) {
                if (is_array($value)) {
                    $depth = $this->_headArrDepth($value) + 1;
                    if ($depth > $max_depth) {
                        $max_depth = $depth;
                    }
                }
            }
            return $max_depth;
        }
    
        //获取表格表头合并个数(数组长度)
        public function _headArrLength($array) {
            $length = 0;
            foreach ($array as $value) {
                if (is_array($value)) {
                    $length += $this->_headArrLength($value);
                } else {
                    $length ++;
                }
            }
            return $length;
        }
    
        public function getExcelHeader($headArr = array(), $startRow = 0, $startColu = 'A', $objPHPExcel) {
    
            //求出表头一共占用多少行,即求出headArr数组的深度
            $death = $this->_headArrDepth($headArr);
            $maxRow = $startRow + $death - 1;
            $this->_getExcelHeader($headArr, $startRow, $startColu, $maxRow, $objPHPExcel);
    
            return $maxRow + 1;
        }
    
        //获取excel表头
        public function _getExcelHeader($headArr = array(), $startRow = 0, $startColu = 'A', $maxRow, $objPHPExcel) {
            $initAscii = $this->_CloumnToAscii($startColu);
    
            if (!empty($headArr)) {
                foreach ($headArr as $k => $v) {
                    $currentCloumn = $this->_AsciiToCloumn($initAscii);
    
                    if (is_array($v)) {
                        $mergeAscii = $initAscii + $this->_headArrLength($v) - 1;
                        $mergeCloumn = $this->_AsciiToCloumn($mergeAscii);
    
                        $objPHPExcel->getActiveSheet()->mergeCells($currentCloumn . $startRow . ':' . $mergeCloumn . $startRow); //跨列合并单元格
                        $objPHPExcel->setActiveSheetIndex(0)->setCellValue($currentCloumn . $startRow, $k);  //给单元格赋值
                        $objPHPExcel->getActiveSheet()->getStyle($currentCloumn . $startRow)->applyFromArray(array('font' => array('bold' => true), 'alignment' => array('horizontal' => 'center'))); //设置单元格样式
                        $startRow++;
                        $this->_getExcelHeader($v, $startRow, $currentCloumn, $maxRow, $objPHPExcel);
                        $initAscii = $mergeAscii + 1;
                        $startRow--;
                    } else {
                        $objPHPExcel->getActiveSheet()->mergeCells($currentCloumn . $startRow . ':' . ($currentCloumn . $maxRow)); //跨行合并单元格
                        $objPHPExcel->setActiveSheetIndex(0)->setCellValue($currentCloumn . $startRow, $v); //给单元格赋值
    
                        $objPHPExcel->getActiveSheet()->getStyle($currentCloumn . $startRow)->getAlignment()->setVertical('center');
                        $objPHPExcel->getActiveSheet()->getStyle($currentCloumn . $startRow)->applyFromArray(array('font' => array('bold' => true), 'alignment' => array('horizontal' => 'center', 'vertical' => 'center')));
                        $initAscii++;
                    }
                }
            }
        }
    
    }
    
    $obj = new ExcelExport();
    $timeRange ='2017-8-1 至 2017-8-10';
    $filename = $timeRange.'销售收费统计表';
    $headArr = [
                                '序号',
                                '日期',
                                '购买人',
                                '墓位',
                                '合同编号',
                                '收入明细(元)'=>[
                                                '预定金',
                                                '墓款'=>[
                                                        '已收预定金',
                                                        '尾款'
                                                    ],
                                                '安放费',
                                                '服务费',
                                                '刻字费',
                                                '商品费',
                                                '瓷像费',
                                                '管理费',
                                                '墓权证',
                                                '绿化',
                                                '维修',
                                                '迁出'
                                         
                                            ],
                                '收入金额(元)'=>[
                                                '总金额',
                                                '折扣金额',
                                                '实际金额',
                                                '本次收费'
                                ],
                                '业务员',
                            ];
                 
    $data = array();
    for($i=0; $i<5; $i++){
        for($j=1;$j<=23; $j++){
            $data[$i][$j] = $j;
        }
    }
    
    $obj->index($filename, $headArr, $data, $timeRange = "", $tmpFileds = array(), $startRow = 1, $startCol = 'A');

     所需的文件: 链接:http://pan.baidu.com/s/1jHWDVXc 密码:phnm

  • 相关阅读:
    !!!C#——进制转换!
    冒泡排序后用二分查找法查找位置
    简陋的4位验证码程序(范围内取随机数)
    这个年龄计算程序相当不科学,体验还是差差哒
    8.7课堂随笔
    字符串中查询关键字
    !汉企的WiFi网速好快
    重度强迫症患者的九九乘法表
    自选数字和范围的整除算法
    day52
  • 原文地址:https://www.cnblogs.com/wgq123/p/7337601.html
Copyright © 2011-2022 走看看