php axios excel

本文介绍了一个名为ExcelService的PHP类,它利用PhpSpreadsheet库处理Excel文件,包括设置列宽、插入单元格值、插入图片以及导出XLSX格式文件。类中详细展示了如何操作工作表、绘制和处理图片数据。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

<?php
<?php

namespace app\common\service;

use Generator;
use PhpOffice\PhpSpreadsheet\Cell\Coordinate;
use PhpOffice\PhpSpreadsheet\IOFactory;
use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\Worksheet\Drawing;
use PhpOffice\PhpSpreadsheet\Worksheet\Worksheet;
use PhpOffice\PhpSpreadsheet\Writer\Exception;

class ExcelService
{
    const   READ  = 0;
    const   WRITE = 1;

    private $spreadsheet       = null;
    private $sheet             = null;
    private $drawingCollection = [];

    const TYPE_DRAWING = 1;


    /**
     * @var array
     * [
     *  [col=>'A',width=>20,title=>'',field='',type=1]
     * ]
     */
    private $columns = [];

    /**
     * @throws \think\Exception
     */
    public function __construct($rw = self::WRITE, string $filename = '')
    {
        if ($rw === self::WRITE) {
            $this->spreadsheet = new Spreadsheet();
        } else {
            if ($filename === '') throw new \think\Exception('缺少文件');
            $this->spreadsheet = IOFactory::load($filename);
        }

        $this->sheet = $this->spreadsheet->getActiveSheet();
    }

    /**
     * @param Worksheet|null $sheet
     */
    public function setSheet(Worksheet $sheet): ExcelService
    {
        $this->sheet = $sheet;
        return $this;
    }

    /**
     * @param array $columns
     * [
     *  [col=>'A',width=>20,title=>'',field='',type=1]
     * ]
     */
    public function setColumns(array $columns): ExcelService
    {
        $this->columns = $columns;
        foreach ($this->columns as $column) {
            $this->sheet->getColumnDimension($column['col'])->setWidth($column['width'] ?? 20);
            $this->sheet->setCellValue($column['col'] . '1', $column['title']);
        }

        return $this;
    }


    /**
     * @param array $values
     * @return $this
     * @throws \PhpOffice\PhpSpreadsheet\Exception
     */
    public function setCellValues(array $values): ExcelService
    {
        if (empty($values)) return $this;
        if (empty($this->columns)) return $this;

        $index = 2;
        foreach ($values as $value) {
            foreach ($this->columns as $column) {
                if (isset($column['type']) && $column['type'] === self::TYPE_DRAWING) {
                	//$drawing = new \PhpOffice\PhpSpreadsheet\Worksheet\MemoryDrawing();
                    //$drawing->setImageResource(imagecreatefrompng('https://xxx.png');
                    //$drawing->setRenderingFunction(\PhpOffice\PhpSpreadsheet\Worksheet\MemoryDrawing::RENDERING_JPEG);
                    //$drawing->setMimeType(\PhpOffice\PhpSpreadsheet\Worksheet\MemoryDrawing::MIMETYPE_DEFAULT);
                    $drawing = new Drawing();
                    $drawing->setWorksheet($this->sheet);
                    $path = $value[$column['field']] ?? '';
                    $drawing->setPath($path);
                    $drawing->setWidth(20);//图片宽
                    $drawing->setHeight(20);//图片高
                    $drawing->setCoordinates($column['col'] . $index);//将图片放置于单元格
                } else {
                    $this->sheet->setCellValue($column['col'] . $index, $value[$column['field']] ?? '');
                }
            }
            ++$index;
        }
        return $this;
    }

    /**
     * @param string $filename
     * @return void
     * @throws Exception
     */
    public function exportXlsx(string $filename)
    {
        $filename = $filename . '-' . date('YmdHis') . '.xlsx';

        header('Content-Type: application/vnd.ms-excel');
        header('Content-Disposition: attachment;filename=' . urlencode($filename));
        header('Cache-Control: max-age=0');


        $writer = IOFactory::createWriter($this->spreadsheet, 'Xlsx');
        $writer->save('php://output');

        exit();
    }

    /**
     * @param int $rowIdx 开始行索引
     * @param array $columns
     * [
     *  ['col'=>'A','field'=>'']
     * ]
     * @return Generator
     * @throws \PhpOffice\PhpSpreadsheet\Exception
     */
    public function yieldData(int $rowIdx, array $columns): Generator
    {
        $highest = $this->sheet->getHighestRow();

        while ($rowIdx <= $highest) {
            $datum = [];
            foreach ($columns as $col) {
                $coordinate = $col['col'] . $rowIdx;

                $val = $this->drawingCollection[$coordinate] ?? trim($this->sheet->getCell($coordinate)->getValue());

                $datum[$col['field']] = $val;
            }
            ++$rowIdx;

            yield $datum;
        }
    }

    /**
     * @throws \PhpOffice\PhpSpreadsheet\Exception
     * @throws \Exception
     */
    public function dealImg(): ExcelService
    {
        $pub = public_path() . 'temp/excelimg/';
        if (!is_dir($pub)) {
            mkdir($pub, 0755, true);
        }

        foreach ($this->sheet->getDrawingCollection() as $drawing) {
            $c = $drawing->getCoordinates();
            list($startColumn, $startRow) = Coordinate::coordinateFromString($c);//拆分成 ['A','4'];
            $path = $pub . $c . mt_rand(1000, 9999) . $drawing->getFilename();
            switch ($drawing->getExtension()) {
                case 'jpg':
                case 'jpeg':
                    $source = imagecreatefromjpeg($drawing->getPath());
                    imagejpeg($source, $path);
                    break;
                case 'gif':
                    $source = imagecreatefromgif($drawing->getPath());
                    imagegif($source, $path);
                    break;
                case 'png':
                    $source = imagecreatefrompng($drawing->getPath());
                    imagepng($source, $path);
                    break;
                default:
                    throw new \Exception('不支持的图片格式');
            }

            $this->drawingCollection[] = [$startColumn . $startRow => $path];
        }
        return $this;
    }
}
const fileDownload = (res, filename) => {
  let blob = new Blob([res.data]); // 将返回的数据通过Blob的构造方法,创建Blob对象
  if ("msSaveOrOpenBlob" in navigator) {
    window.navigator.msSaveOrOpenBlob(blob, filename); // 针对浏览器
  } else {
    const elink = document.createElement("a"); // 创建a标签
    elink.download = filename;
    elink.style.display = "none";
    // 创建一个指向blob的url,这里就是点击可以下载文件的根结
    elink.href = URL.createObjectURL(blob);
    // 兼容:某些浏览器不支持HTML5的download属性
    if (typeof elink.download === "undefined") {
      elink.setAttribute("target", "_blank");
    }
    document.body.appendChild(elink);
    elink.click();
    URL.revokeObjectURL(elink.href); //移除链接
    document.body.removeChild(elink); //移除a标签
  }
};

export function _download(url, formData, errorback) {
  return new Promise((resolve, reject) => {
    axios
      .post(url, formData, { responseType: "blob" })
      .then(res => {
        // 提取文件名
        const fileName = decodeURI(
          res.headers["content-disposition"].match(/filename=(.*)/)[1]
        );
        if (res.status === 200) {
          fileDownload(res, fileName);
        }
      })
      .catch(error => {
        reject(error);
      });
  });
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值