Я использую генератор текстовых документов для PHP для модуля отчетов веб-приложения, которое я разрабатываю. Я выбираю PHPWord, потому что бесплатная версия PHPDocX имеет очень ограниченную функциональность, плюс у нее есть нижний колонтитул, что это только бесплатная версия. У меня есть шаблон, заданный клиентом. Я хочу, чтобы я хотел загрузить шаблон и добавить к нему динамические элементы, как дополнительный текст или таблицы. Мой код здесь:
<?php require_once '../PHPWord.php'; $PHPWord = new PHPWord(); $document = $PHPWord->loadTemplate('Template.docx'); $document->setValue('Value1', 'Great'); $section = $PHPWord->createSection(); $section->addText('Hello World!'); $section->addTextBreak(2); $document->setValue('Value2', $section); $document->save('test.docx'); ?>
Я попытался создать новый раздел и попытался присвоить его одной переменной в шаблоне (Value2), но эта ошибка появилась:
[28-Jan-2013 10:36:37 UTC] PHP Warning: utf8_encode() expects parameter 1 to be string, object given in /Users/admin/localhost/PHPWord_0.6.2_Beta/PHPWord/Template.php on line 99
setValue ожидает, что второй параметр будет простой строкой. Невозможно предоставить объект раздела.
Я нырнул в код, и нет простого способа вернуть объект сечения, возвращающий значение, которое может использоваться функцией setValue.
Поскольку у меня была та же проблема, я написал патч для файла Template.php, который позволяет клонировать строки таблицы перед заменой их тегов на setValue. Каждая строка получает уникальный идентификатор, позволяющий идентифицировать теги шаблонов для каждой отдельной строки.
Вот как это работает:
Добавьте эту функцию в файл Template.php (находящийся внутри каталога PHPWord)
public function cloneRow($search, $numberOfClones) { if(substr($search, 0, 2) !== '${' && substr($search, -1) !== '}') { $search = '${'.$search.'}'; } $tagPos = strpos($this->_documentXML, $search); $rowStartPos = strrpos($this->_documentXML, "<w:tr", ((strlen($this->_documentXML) - $tagPos) * -1)); $rowEndPos = strpos($this->_documentXML, "</w:tr>", $tagPos) + 7; $result = substr($this->_documentXML, 0, $rowStartPos); $xmlRow = substr($this->_documentXML, $rowStartPos, ($rowEndPos - $rowStartPos)); for ($i = 1; $i <= $numberOfClones; $i++) { $result .= preg_replace('/\$\{(.*?)\}/','\${\\1#'.$i.'}', $xmlRow); } $result .= substr($this->_documentXML, $rowEndPos); $this->_documentXML = $result; }
В файле шаблона добавьте в каждую таблицу одну строку, которую вы будете использовать в качестве строки шаблона. Предположим, вы добавили в эту строку тег $ {first_name}.
Чтобы получить таблицу с 3-мя строчными вызовами: $ document-> cloneRow ('first_name', 3);
Рабочая копия вашего шаблона теперь обновляется таблицей, содержащей 3 строки. Каждый тег внутри строки добавлен с номером # и номером строки.
Чтобы установить значения, используйте setValue $ document-> setValue ('first_name # 1', 'Name в первой строке'); $ document-> setValue ('first_name # 2', 'Name во второй строке'); $ document-> setValue ('first_name # 3', 'Name on the third row');
Надеюсь, это полезно! Я сохраню обновленную версию кода и документации здесь: http://jeroen.is/phpword-templates-with-repeating-rows/
Полностью новая версия CloneRow и setValue
Теперь вы можете клонировать объединенные ячейки. Исправлено множество ошибок с тегами OOXML.
И новый метод setValue – теперь игнорирует трэш-теги внутри вашего шаблона. подобно
{My<trash ooxml tags>Pattern}
Здесь вы можете найти код, документы и примеры: https://github.com/Arisse/PHPWord_CloneRow
Согласно документации, вы не можете добавлять контент в файл, когда работаете с шаблонами.
Невозможно добавить новые элементы PHPWord в загруженный файл шаблона.
Документация