Рассмотрим распространенную проблему, с которой сталкиваются разработчики в 1С: необходимость распечатать многостраничный HTML-документ с заданными отступами (полями) без использования предварительного просмотра. На первый взгляд задача кажется простой. Многие пробуют использовать обращение к DOM-модели, например, через конструкцию Документ.body.style.marginTop = "40mm". Однако на практике выясним, что этот подход применяется только один раз — к первой странице документа. Если страниц несколько, форматирование ломается.
Также разработчики пытаются применять стандартные средства CSS, встраивая в тело документа правило @page { margin: 3cm 1cm 1cm 1.5cm; }. Но платформа 1С зачастую игнорирует эту синтаксическую конструкцию при прямой отправке на принтер. Проанализируем причину такого поведения и разберем по шагам рабочие альтернативные способы решения этой задачи.
Выясним причину проблемы. Начиная с версии платформы 8.3.14, фирма 1С отказалась от компонента Internet Explorer для отрисовки поля HTML-документа и перевела платформу на использование встроенного движка WebKit (в частности, сборку WinCairo). Этот переход привел к ряду технических особенностей:
@page и позиционировании элементов при разбивке на листы для печати.Поскольку "в лоб" задачу решить в рамках объектов 1С не получается, рассмотрим несколько альтернативных вариантов вывода на печать.
Если на клиентском компьютере установлен MS Office, мы можем программно сохранить HTML-код во временный файл, открыть его скрытно через COM-объект приложения Word, установить нужные параметры страницы и отправить на печать. Посмотрим на пример реализации данного подхода.
// Получаем HTML текст из поля документа
ТекстHTML = ПолеДокумента.Документ.body.outerHTML;
// Создаем и записываем временный файл
ФайлТекст = Новый ТекстовыйДокумент;
ФайлТекст.УстановитьТекст(ТекстHTML);
Путь = КаталогВременныхФайлов() + "htmltext_" + Формат(ТекущаяДата(), "ДФ=yyyyMMddHHmmss") + ".html";
ФайлТекст.Записать(Путь, КодировкаТекста.UTF8);
Попытка
// Подключаемся к Word
Word = Новый COMОбъект("Word.Application");
ThisDocument = Word.Documents.Open(Путь);
Word.Visible = Ложь; // Скрываем приложение
// Настраиваем отступы (значения задаются в пунктах, 1 см ~ 28.35 пунктов)
ThisDocument.PageSetup.TopMargin = 96;
ThisDocument.PageSetup.RightMargin = 25;
ThisDocument.PageSetup.LeftMargin = 25;
ThisDocument.PageSetup.BottomMargin = 60;
// Отправляем на печать (здесь можно добавить вызов метода PrintOut)
// ThisDocument.PrintOut();
Word.Visible = Истина; // Показываем результат (или закрываем документ)
Исключение
// Обработка ошибки инициализации COM
КонецПопытки;
Недостатки метода: Как отмечают практики, при конвертации HTML в Word "на лету" могут слетать шрифты, CSS-стили и сложное выравнивание. Word пытается перерисовать веб-верстку в свой внутренний формат, что не всегда проходит гладко. Также этот метод медленный и требует установленного офисного пакета.
Разберем более надежный способ, который позволяет сохранить 100% исходного форматирования. Мы можем использовать бесплатные консольные утилиты для конвертации HTML в PDF. Самая популярная из них — wkhtmltopdf.
Алгоритм действий следующий:
ПолеHTMLДокумента во временный файл с расширением .html.--margin-top 40mm --margin-bottom 20mm.Этот способ лишен проблем с "поехавшей" версткой и гарантирует одинаковый результат на любых принтерах.
Поскольку встроенный в платформу WebKit не всегда справляется с печатью, проанализируем ситуацию с точки зрения современных внешних браузеров (Chrome, Edge, Яндекс.Браузер). Их движки печати прекрасно распознают CSS-конструкцию @page.
Добавьте в ваш HTML-шаблон блок со стилями:
<style>
@page {
size: A4;
margin: 30mm 25mm 25mm 25mm;
}
body {
margin: 0;
}
</style>
Затем сохраните текст во временный файл и вызовите открытие этого файла в операционной системе:
ПутьКФайлу = ПолучитьИмяВременногоФайла("html");
// ... запись текста HTML в файл ...
ЗапуститьПриложение(ПутьКФайлу);
Документ откроется в браузере пользователя, который установлен по умолчанию. При нажатии "Печать" браузер корректно применит заданные в @page отступы ко всем страницам документа.
В завершение разберем методологическую сторону вопроса. Согласно стандартам разработки интерфейсов и отчетов фирмы 1С, объект ПолеHTMLДокумента изначально не предназначен для формирования строгих печатных форм, где критичен точный контроль над постраничным выводом.
Для задач, где необходимо управлять верхними, нижними полями, колонтитулами и масштабом на каждой странице, 1С настоятельно рекомендует генерировать классический ТабличныйДокумент. В табличном документе свойства страницы контролируются программно, предсказуемо и абсолютно одинаково работают на всех релизах платформы, не требуя сторонних конвертеров или вызова COM-объектов.