在Grid的_prepareColumns中加上下面的两句代码在Grid页面会出现导出文件选项:
$this->addExportType('*/*/exportCsv', $this->__('CSV'));
$this->addExportType('*/*/exportXml', $this->__('XML'));
点进去这个方法可以看到如下:
public function addExportType($url, $label)
{
$this->_exportTypes[] = new Varien_Object(
array(
'url' => $this->getUrl($url, array('_current'=>true)),
'label' => $label
)
);
return $this;
}
这就能看出来第一个参数是URL是点击export按钮的时候请求的URL,另一个这是下拉框中展示的Label
在该模块的控制器中分别加入对应的导出控制器,如下:
public function exportCsvAction()
{
$fileName = 'test.csv';
$content = $this->getLayout()->createBlock('test/adminhtml_test_grid')->getCsvFile();
$this->_prepareDownloadResponse($fileName, $content);
}
public function exportXmlAction()
{
$fileName = 'test.xml';
$content = $this->getLayout()->createBlock('test/adminhtml_test_grid')->getExcelFile();
$this->_prepareDownloadResponse($fileName, $content);
}
这么写默认是将Grid中的字段全部导出,
$this->getLayout()->createBlock(‘test/adminhtml_test_grid’)->getExcelFile();这句话的意思是在test/adminhtml_test_grid的block下调用getExcelFile方法,该方法在Grid的父类中,该方法是将Grid中的数据先暂存到指定文件中,然后将文件相关数据返回,如下:
return array(
'type' => 'filename',
'value' => $file,
'rm' => true // can delete file after use
);
$file是文件的存放路径, ‘rm’ => true是文件使用完之后可以删除掉
这里面有几个方法解释一下:
如果想去掉导出文件中的标题,则去掉如下代码:
$io->streamWriteCsv($this->_getExportHeaders());
$io->streamWrite($parser->getRowXml($this->_getExportHeaders()));
下面这个是整理Grid中的数据:
Mage::helper("core")->getEscapedCSVData($this->_getExportTotals())
$io->streamWrite($parser->getRowXml($this->_getExportTotals()));
上面写的是导出整个Grid中包括的字段的数据,下面我讲一下导出指定数据以及新加自己想要的数据:
在Block/Widget/Grid,php中有下面一段代码:
protected $_isExport = false;
这句代码可以控制字段的展示以及隐藏以及字段的导出,如下是在Grid中该字段是隐藏的,但是在导出数据的时候该字段是包含在导出中的,
if ($this->_isExport) {
$this->addColumn('entity_id', array(
'header' => 'ID',
'index' => 'entity_id'
));
}
具体原理是在展示Grid时判断改值是false所以隐藏,但是在导出时,调用的相关导出代码中包含一段代码,这里拿CSV举例:
public function getCsvFile()
{
$this->_isExport = true;
$this->_prepareGrid();
$io = new Varien_Io_File();
通过这段代码就可以看出在导出的时候$this->_isExport的值是true了,所以该字段是导出的;
那么我想加字段在导出的数据中加入我想要,那么久可以重写下面的方法:
public function setCollection($collection)
{
$this->_collection = $collection;
}
如下是我重写的:
public function setCollection($collection)
{
//导出字段
if($this->_isExport){
$collection->getSelect()->joinLeft(array(
'addr'=>$collection->getTable('sales/order_address')),
'addr.parent_id=`main_table`.entity_id AND addr.address_type="shipping"',
array('region','city')
);
}
parent::setCollection($collection);
}
通过该联表增加了字段,这样在导出的时候就会增加该字段,这里面也用了$this->_isExport,也是为了在展示Grid的时候不走这个联表代码;
下面的是导出指定代码的方法:
public function exportCsvAction()
{
$fileName = 'orders.csv';
$grid = $this->getLayout()->createBlock('adminhtml/sales_order_grid');
$csvDataArr = $grid->getArray();
$data = "";
$data .="order_id,mobile"."\n";
foreach ($csvDataArr['items'] as $item) {
$incrementId = $item['increment_id'];
$mobile = $item['mobile'];
$data .='"'.$incrementId.'","'.$mobile.'"'."\n";
}
echo "\xEF\xBB\xBF";
$this->_prepareDownloadResponse($fileName, $data);
}
这里我使用了$grid->getArray(),这个方法是将暂存的文件中的数据组装成数组,然后筛选自己想要的数据导出,这里面根据CSV的数据格式使用如下样式:
$data .="order_id,mobile"."\n";
$data .='"'.$incrementId.'","'.$mobile.'"'."\n";
第一句是导出文件的标题,下面是数据,用\n换行
下面是XML的格式组装:
public function exportExcelAction()
{
$fileName = 'orders.xml';
$grid = $this->getLayout()->createBlock('adminhtml/sales_order_grid');
$csvDataArr = $grid->getArray();
$data = "";
$header = "<?xml version=\"1.0\"?><?mso-application progid=\"Excel.Sheet\"?><Workbook xmlns=\"urn:schemas-microsoft-com:office:spreadsheet\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xmlns:x=\"urn:schemas-microsoft-com:office:excel\" xmlns:x2=\"http://schemas.microsoft.com/office/excel/2003/xml\" xmlns:ss=\"urn:schemas-microsoft-com:office:spreadsheet\" xmlns:o=\"urn:schemas-microsoft-com:office:office\" xmlns:html=\"http://www.w3.org/TR/REC-html40\" xmlns:c=\"urn:schemas-microsoft-com:office:component:spreadsheet\"><OfficeDocumentSettings xmlns=\"urn:schemas-microsoft-com:office:office\"></OfficeDocumentSettings><ExcelWorkbook xmlns=\"urn:schemas-microsoft-com:office:excel\"></ExcelWorkbook>";
$title = "</ExcelWorkbook><Worksheet ss:Name=\"Sheet 1\"><Table><Row><Cell><Data ss:Type=\"String\">order_id</Data></Cell><Cell><Data ss:Type=\"String\">mobile</Data></Cell></Row>";
$data = $header . $title;
foreach ($csvDataArr['items'] as $item) {
$incrementId = $item['increment_id'];
$mobile = $item['mobile'];
$data .="<Row><Cell><Data ss:Type=\"Number\">$incrementId</Data></Cell><Cell><Data ss:Type=\"Number\">$mobile</Data></Cell></Row>";
}
$this->_prepareDownloadResponse($fileName, $data);
}
这里面根据XML的数据格式使用如下样式:
$header = "<?xml version=\"1.0\"?><?mso-application progid=\"Excel.Sheet\"?><Workbook xmlns=\"urn:schemas-microsoft-com:office:spreadsheet\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xmlns:x=\"urn:schemas-microsoft-com:office:excel\" xmlns:x2=\"http://schemas.microsoft.com/office/excel/2003/xml\" xmlns:ss=\"urn:schemas-microsoft-com:office:spreadsheet\" xmlns:o=\"urn:schemas-microsoft-com:office:office\" xmlns:html=\"http://www.w3.org/TR/REC-html40\" xmlns:c=\"urn:schemas-microsoft-com:office:component:spreadsheet\"><OfficeDocumentSettings xmlns=\"urn:schemas-microsoft-com:office:office\"></OfficeDocumentSettings><ExcelWorkbook xmlns=\"urn:schemas-microsoft-com:office:excel\"></ExcelWorkbook>";
$title = "</ExcelWorkbook><Worksheet ss:Name=\"Sheet 1\"><Table><Row><Cell><Data ss:Type=\"String\">order_id</Data></Cell><Cell><Data ss:Type=\"String\">mobile</Data></Cell></Row>";
$data = $header . $title;
$data .="<Row><Cell><Data ss:Type=\"Number\">$incrementId</Data></Cell><Cell><Data ss:Type=\"Number\">$mobile</Data></Cell></Row>";
这里面的$header是xml的一些定义信息
$title是文件的标题
最后一句是数据内容