Призываю PHPExcel или создание xls документов из шаблона

20 Июн
2012

Речь пойдет о том как использовать бланки таблиц на PHP. Где то я встречал вариант заполнения бланка счета средствами PHP, но я хочу пойти дальше и предложить концепцию использования шаблонов или меток данных. Итак начнем.
Цель: используя шаблон создать таблицу товаров для поставщика.
Средства: PHP5, PHPExcel.
Решение: о нем подробнее.

Для начала стоит определится с типами данных которые мы хотим обработать. Предположим что нам нужны строковые значения (пусть будут %key%), цифровые (%key%) и табличные строки (%row.row_name%).
Подготовим шаблон. Для примера я возьму просто файл с хаотично записанными данными в формате MS Excel 2003 (ВАЖНО!).
Вот изображение файла и сам файл. Теперь осталось дело за малым.
Подключаем PHPExcel и вызываем заполнялку шаблона
ini_set('include_path', ini_get('include_path').';'.dirname(__FILE__) . '/PHPExcel/');
include_once dirname(__FILE__) . '/PHPExcel/PHPExcel.php';
include_once dirname(__FILE__) . '/PHPExcel.addon.php';
print ""; PHPExcelAddon::convert (dirname(__FILE__).'/sample2.xls',array ( 'test'=>111, 'test.data'=>222, 'row.t'=>array (1,2,3,4,5), 'row.d'=>array (11,22,33,44,55), ));
Наш класс в файле PHPExcel.addon.php
class PHPExcelAddon {
	
	public function __construct () {
		
	}
	
	public static function convert ($file, $data=array ()) {
		$objPHPExcel = PHPExcel_IOFactory::load( $file );
		$objPHPExcel->setActiveSheetIndex(0);
		
		$aSheet = $objPHPExcel->getActiveSheet();
		
		/*
		 * Всякая стандартная лабуда
		 */
		$objPHPExcel->getProperties()->setCreator("Maarten Balliauw");
		$objPHPExcel->getProperties()->setLastModifiedBy("Maarten Balliauw");
		$objPHPExcel->getProperties()->setTitle("Office 2007 XLSX Test Document");
		$objPHPExcel->getProperties()->setSubject("Office 2007 XLSX Test Document");
		$objPHPExcel->getProperties()->setDescription("Test document for Office 2007 XLSX, generated using PHP classes.");
		
		// Получим итератор строки и пройдемся по нему циклом
		foreach($aSheet->getRowIterator() as $row){
			// Получим итератор ячеек текущей строки
			$cellIterator = $row->getCellIterator();
			// Пройдемся циклом по ячейкам строки
			foreach($cellIterator as $cell){
				// Берем значение ячейки
				$val = $cell->getValue();
				
				// Проверяем содержит ли ячейка указатель на динамические данные шаблона (то что внутри %%)
				// Если да, то обрабатываем и заносим инфу
				if (preg_match( "#^%([^%]+)%$#sei", $val, $match )) {
					$column = $cell->getColumn ();
					$row 	= $cell->getRow ();
					
					$key_insert = $match['1'];
					
					print 'key '. $key_insert." \r\n";
					
					// Если строка пишем как строку
					if (isset ($data[$key_insert]) AND is_string ($data[$key_insert])) {
						print 'set string value '.$data[$key_insert]." \r\n";
						$cell->setValue ($data[$key_insert]);
					}
					// Заполняем строки дублируя стили
					else if (isset ($data[$key_insert]) AND is_array ($data[$key_insert])) {
						// взяли стиль ячейки
						$crew_template = $aSheet->getStyle($column.$row);
						foreach ($data[$key_insert] as $_colVal) {
							// применили стиль ячейки/ячеек
							$aSheet->duplicateStyle($crew_template,$column.$row);
							print 'set row value '.$column.$row.' = '.$_colVal." \r\n";
							$objPHPExcel->getActiveSheet()->SetCellValue($column.$row, $_colVal);
							$row = $row+1;
						}
						
					}
					// Если цифра
					else if (isset ($data[$key_insert]) AND is_numeric ($data[$key_insert])) {
						print 'set number value '.$data[$key_insert]." \r\n";
						// <hh user=TODO> может кому то потребовать указать тип ячейки как цифровой 
						$cell->setValue ($data[$key_insert]);
					}
					// Если любая другая
					else if (isset ($data[$key_insert])) {
						print 'set value '.$data[$key_insert]." \r\n";
						$objPHPExcel->getActiveSheet()->getStyle('C'.$i)->getNumberFormat()->setFormatCode(PHPExcel_Style_NumberFormat::FORMAT_TEXT);
						$cell->setValue ($data[$key_insert]);
					}
					// Если данный ключ шаблона не передан в нашу заполнялку
					else {
						print "key value is empty \r\n";
					}
					//var_dump ($cell);
				}
			}
		}
		
		// При желании можем изменить имя активного листа ))
		//$objPHPExcel->getActiveSheet()->setTitle('ThisIsХорошо');
		
		// Тут мы просто записываем файл
		$objWriter = new PHPExcel_Writer_Excel2007($objPHPExcel);
		
		$objWriter->save(dirname($file).'/file.xlsx');
		
		// Говорим буферу и классу Давайдосвидания
		$objPHPExcel->disconnectWorksheets();
		unset($objPHPExcel);
	}
}
Результат изображение файла и сам файл. В целом задача решается довольно просто. Но до простого бывает не всем легко додуматься, особенно когда перероешь кучу информации и нигде похожего не найдешь ( Надеюсь было интересно и полезно. P.S. ООП и прочие штучки опустил для упрощения кода. Все же концепт должен быть идеей а не готовым решением.
По материалам Хабрахабр.



загрузка...

Комментарии:

Наверх