Печать через спулер на матричный принтер

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Печать через спулер на матричный принтер

Сообщение gvido » 20.07.2013 06:54:04

Можно ли адаптировать данный код под freepascal (lazarus)?
Код: Выделить всё
var
  pcbNeeded: DWORD;
  FDevice: PChar;
  FPort: PChar;
  FDriver: PChar;
  FPrinterHandle: THandle;
  FDeviceMode: THandle;
  FJob: PADDJOBINFO1;
  Stream: TFileStream;
begin
  GetMem(FDevice, 128);
  GetMem(FDriver, 128);
  GetMem(FPort, 128);
  Printer.GetPrinter(FDevice, FDriver, FPort, FDeviceMode);
  if FDeviceMode = 0 then
    Printer.GetPrinter(FDevice, FDriver, FPort, FDeviceMode);
  if OpenPrinter(FDevice, FPrinterHandle, nil) then
  begin
    GetMem(FJob, 1024);
    //Добавляем задание, получаем имя файла в директории windows\spoool\
    AddJob(FPrinterHandle, 1, FJob, 1024, pcbNeeded);
    Stream := TFileStream.Create(FJob.Path, fmCreate);
    // Дальше пишем текст (+ESC команды!!!!) прямо в Stream
    // и не забываем переводить в DOS - кодировку
    .........
    Stream.Free;
    //Постановка задания в очередь - только теперь принтер начинает печатать
    ScheduleJob(FPrinterHandle, FJob.JobID);
    FreeMem(FJob);
    ClosePrinter(FPrinterHandle);
  end;
  FreeMem(FDevice, 128);
  FreeMem(FDriver, 128);
  FreeMem(FPort, 128);
end;

взят с
http://www.delphisources.ru/pages/faq/base/print_spuler_across.html
gvido
постоялец
 
Сообщения: 188
Зарегистрирован: 28.03.2012 11:35:31

Re: Печать через спулер на матричный принтер

Сообщение debi12345 » 20.07.2013 15:12:45

Можете посмотреть приаатченные модули (с рабочего проекта). Заточено под МСЕ, но много менять не придется.
У вас нет необходимых прав для просмотра вложений в этом сообщении.
Аватара пользователя
debi12345
долгожитель
 
Сообщения: 5761
Зарегистрирован: 10.05.2006 23:41:15
Откуда: Ташкент (Узбекистан)

Re: Печать через спулер на матричный принтер

Сообщение gvido » 20.07.2013 16:36:39

Спасибо за код. :D "Моск" вскипал три раза, литр пива не помог найти истину. :) Протрезвею, продолжу поиски. О результатах отпишусь. :)
gvido
постоялец
 
Сообщения: 188
Зарегистрирован: 28.03.2012 11:35:31

Re: Печать через спулер на матричный принтер

Сообщение debi12345 » 21.07.2013 00:08:45

Есть два способа печати на "матричник" - сразу файл целиком (стартовый пример), или с возможнстью печатать построчно (без RAW-записи в спул-файла) - см. последний ататач. Специфика задачи ("портянки" в десятки метров длиной, печатающиеся часы напролет) потребовала именно построчной печати - она дает возможснть 1) показывать стадию (процентовку) печати и 2) возможность отмены печати, если что-то пошло не так.
Аватара пользователя
debi12345
долгожитель
 
Сообщения: 5761
Зарегистрирован: 10.05.2006 23:41:15
Откуда: Ташкент (Узбекистан)

Re: Печать через спулер на матричный принтер

Сообщение gvido » 21.07.2013 12:00:59

Ээээх, буду адаптировать вышеприведенный код под фрипаскаль. Заодно в голове уложится алгоритм работы с принтером. Раньше на матричники печатал прямой записью в порт.

Хрень какая-то...

Код: Выделить всё
var
   PrintList: TStrings;
   MWPrinter: TWinPrinter;
begin

     MWPrinter:=TWinPrinter.Create;
     ShowMessage(MWprinter.PrinterName);
     //PrintList:=TStrings.Create ;
     //Printlist:=mWPrinter.Printers;
     //ShowMessage(MWprinter.PrinterName);

    if OpenPrinter(lpwstr(UTF8ToSys(mwPrinter.PrinterName)),PPrinterHandle,nil)
//пробовал без перекодировки     
    then showmessage('Ура!!!!!!')
    else
         showmessage('Хрень какая-то...');
end.
//результат всегда false;




Что, блин, не так делаю????
gvido
постоялец
 
Сообщения: 188
Зарегистрирован: 28.03.2012 11:35:31

Re: Печать через спулер на матричный принтер

Сообщение v-t-l » 22.07.2013 10:29:35

У объекта Printer из модуля Printers из LCL есть свойство RawMode и методы BeginDoc, Write, EndDoc.
Попробуйте с ними поэспериментировать. Возможно, это поможет сделать код проще и кроссплатформеннее :)
v-t-l
энтузиаст
 
Сообщения: 741
Зарегистрирован: 13.05.2007 16:27:22
Откуда: Belarus

Re: Печать через спулер на матричный принтер

Сообщение gvido » 23.07.2013 06:21:01

Соорудил, или у кого то "упрЁр" и переделал такое:
Код: Выделить всё
procedure PrintTStrings(Lst : TStrings) ;
var
  I,J,
  Line : Integer;
  TempStrs: TStringList;
begin
  I := 0;
  Line := 0 ;
  TempStrs:=TStringList.Create;
  Printer.BeginDoc ;
  Printer.Canvas.Font.Size:=8 ;                    //Если не указать то печатает
  Printer.Canvas.Font.Name:='Courier New' ;//оооочень мелко..
  for I := 0 to Lst.Count - 1 do begin
    if UtF8Length(Lst[i])> 118 then //если строка больше 118 симоволов, то в строку печатаем 118 символов . а остальное переносим на следующую строку.
       begin
            if TempStrs.Count>0  then  Tempstrs.Clear;
            TempStrs.Append(Utf8Copy(Lst[I],1,118));
            TempStrs.Append(Utf8Copy(Lst[I],119,UTF8Length(Lst[i])-118));
            for j:=0 to tempstrs.Count - 1 do
                begin
                     Printer.Canvas.TextOut(0, Line, TempStrs[j]);
                     Line := Line + Abs(Printer.Canvas.Font.Height);
                end;
       end
    else
    begin
         Printer.Canvas.TextOut(0, Line, Lst[I]);
         Line := Line + Abs(Printer.Canvas.Font.Height);
    end;
    {Font.Height is calculated as -Font.Size * 72 / Font.PixelsPerInch which returns
     a negative number. So Abs() is applied to the Height to make it a non-negative
     value}
    if (Line >= Printer.PageHeight) then
      Printer.NewPage;
  end;
  TempStrs.Destroy;
  Printer.EndDoc;

Пока проверил на лазерном принтере - работает.
gvido
постоялец
 
Сообщения: 188
Зарегистрирован: 28.03.2012 11:35:31


Вернуться в Lazarus

Кто сейчас на конференции

Сейчас этот форум просматривают: mike и гости: 237

Рейтинг@Mail.ru