Печать документа в Windows

Общие вопросы, не зависящие от языка реализации.

Модераторы: Duncon, Hawk, Romeo, Eugie

Аватара пользователя
Decoder
Сообщения: 308
Зарегистрирован: 19 фев 2008, 23:11
Откуда: Moscow

Здравствуйте!
Возник такой вот житейский вопрос: каким образом из приложения можно печатать документы без использования дополнительных генераторов отчётов, а только средствами C++ и Windows (Win32API, MFC, WTL)? Имеется документ (например платёжное поручение), у которого бланк стандартный, а меняются только данные в соответствующих полях. Самый простой способ - напечатать заранее бланки документов, а потом печатать данные поверх бланка в заранее указанных местах. Но хотелось делать всё за один раз, без повторной заправки бумаги в принтер. Каким образом это можно сделать?
Аватара пользователя
Naeel Maqsudov
Сообщения: 2570
Зарегистрирован: 20 фев 2004, 19:17
Откуда: Moscow, Russia
Контактная информация:

Word используется для этих целей.
Аватара пользователя
Decoder
Сообщения: 308
Зарегистрирован: 19 фев 2008, 23:11
Откуда: Moscow

Про OLE-автоматизацию офисных приложений я знаю, поэтому и не хочу их использовать для этой цели. Мне бы как-то без посторонних приложений. Чтобы моя программа сама умела печатать и бланк документа и данные в него вписывать.
Можно конечно графическими функциями типа MoveTo(), LineTo() и TextOut() сформировать бланк документа...
Но это такой геморрой, это каждую линию, каждую надпись нужно будет позиционировать с точностью до полумиллиметра. Сколько бумаги напрасно изведу и времени потрачу пока добьюсь этого. А если потом что-то поменять нужно будет, то снова придётся всё заново размечать? Есть же наверно какой-то более удобный способ для этого...
Аватара пользователя
Decoder
Сообщения: 308
Зарегистрирован: 19 фев 2008, 23:11
Откуда: Moscow

Про OLE-автоматизацию офисных приложений я знаю, поэтому и не хочу их использовать для этой цели. Мне бы как-то без посторонних приложений. Чтобы моя программа сама умела печатать и бланк документа и данные в него вписывать.
Можно конечно графическими функциями типа MoveTo(), LineTo() и TextOut() сформировать бланк документа...
Но это такой геморрой, это каждую линию, каждую надпись нужно будет позиционировать с точностью до полумиллиметра. Сколько бумаги напрасно изведу и времени потрачу пока добьюсь этого. А если потом что-то поменять нужно будет, то снова придётся всё заново размечать? Есть же наверно какой-то более удобный способ для этого...
Аватара пользователя
WinMain
Сообщения: 929
Зарегистрирован: 14 янв 2005, 10:30
Откуда: Москва
Контактная информация:

Есть весьма тупой, но в то же время довольно простой способ справиться с задачей - напечатать бланк и отсканировать его. Потом из программы печатать сначала картинку с изображением документа и сразу же поверх неё необходимые данные. Правда, если сканировать с высоким разрешением, чтобы обеспечить хорошее качество документа, то размеры файла с бланком документа получаются довольно внушительными. Из-за этого печать документа будет идти медленно.
Я для этого использую другой способ - хранить бланк документа не в растровом образе, а в виде векторного рисунка. Для этого используются расширенные метафайлы Windows (файлы с расширением .emf). Тогда размер файла получается сравнительно небольшой и печатается он довольно быстро. В составе Win32API есть специальные функции для работы с метафайлами.
BBB
Сообщения: 1298
Зарегистрирован: 27 дек 2005, 13:37

WinMain, в этом случае, если я правильно понял, все равно остается задача "выверения до миллиметра" места, куда вписываются данные (либо на уровне программы, либо на уровне ее настройки, скажем, ini-файла, где записаны смещения X,Y точек начала печати текстов).

Насчет печати бланка "из картинки", а потом поверх него текста. У нас некоторое время назад использовалась подобная технология. Потом, именно для ускорения процесса печати, придумали более хитрую. Исходный бланк - в PDF. В него программно (средствами библиотеки iText) "вбиваем" данные для печати (тут все равно надо либо выверять позиции, куда "вбивать" текст, либо пользоваться полями, которые надо вставлять уже в сам исходный бланк PDF-а). И затем печатаем полученный, "отредактированный", PDF.
Аватара пользователя
WinMain
Сообщения: 929
Зарегистрирован: 14 янв 2005, 10:30
Откуда: Москва
Контактная информация:

Так оно и есть. При формировании "многослойного" документа обязательно возникает задача точного сведения слоёв в один рисунок. В данном случае это не так уж сложно, в этом плане у меня есть кое-какие наработки. Могу предложить другой способ - формирование готового документа средствами С++. Если не нравится OLE - автоматизация, то можно воспользоваться другими технологиями. Сейчас это делается на основе XML, а лет 10 назад я генерировал готовые RTF-файлы, которые затем открывались в Word и выводились на печать.
Аватара пользователя
Decoder
Сообщения: 308
Зарегистрирован: 19 фев 2008, 23:11
Откуда: Moscow

Я слышал про метафайлы, но до их практического применения дело не доходило. Как мне с ними работать? Их же надо как-то создавать, загружать из файла, выводить на печать...
Аватара пользователя
WinMain
Сообщения: 929
Зарегистрирован: 14 янв 2005, 10:30
Откуда: Москва
Контактная информация:

Загружать метафайлы довольно легко, для этого есть функция GetEnhMetaFile(). Если метафайл берётся из ресурсов приложения, а не из файла на диске, то используется функция SetEnhMetaFileBits().
Отрисовывается метафайл с помощью функции PlayEnhMetaFile().
Размер рисунка в метрических единицах можно узнать из заголовка метафайла при помощи функции GetEnhMetaFileHeader().
Аватара пользователя
Decoder
Сообщения: 308
Зарегистрирован: 19 фев 2008, 23:11
Откуда: Moscow

Спасибо за информацию. Но как мне создать сам метафайл, каким редактором?
Ответить