Link to home
Start Free TrialLog in
Avatar of NetGeek
NetGeek

asked on

getting a printers paperforms and their sizes

Hi there,

I'm having problems finding the size of the different paper forms a printer support. Enumerating for the forms is no problem, but getting the actual size in millimeters or similiar is. Im using DeviceCapabilities to get the form names, but then what ? I've found EnumForms in the API but can't figure out how to use it correctly (it doesn't return any forms, and how the heck do i get the size from a sizel type ??)

Any help ?

Best regards
NetGeek
ASKER CERTIFIED SOLUTION
Avatar of geobul
geobul

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of geobul
geobul

If you want to get the sizes only:

procedure TForm1.Button3Click(Sender: TObject);
var
  p: array [0..10000] of char;
  a: array of TPoint;
  i, res: integer;
begin
  res := DeviceCapabilities(PChar(lb.Items[lb.ItemIndex]), nil, DC_PAPERSIZE, p, nil);
  if res > 0 then begin
    SetLength(a, res);
    move(p, a[0], res * SizeOf(Tpoint));
    for i := 0 to res - 1 do begin
      re.Lines.Add(IntToStr(a[i].x)+':'+IntToStr(a[i].y));
    end;
  end;
end;

Regards, Geo
Avatar of NetGeek

ASKER

thank you very much geobul :) it wa the openprinter i'd forgotten.

got any code at hand showing how to select a specific form by name for the current printer ?

Best regards
Netgeek
I don't have the code but I think you could try Printer.GetPrinter and Printer.SetPrinter methods. First call GetPrinter in order to obtain the DEVMODE structure. Then set dmFields to DM_FORMNAME and dmFormName member of that structure to the name of the form you want to set to (and others also perhaps - dmPaperLength and dmPaperWidth). Then use Printer.SetPrinter to save the change. Help says that this member doesn't work in Win9x though. There are predefined form constants in Windows.pas (DMPAPER_LETTER = 1, etc.). You may also use them setting dmPaperSize member of DEVMODE only. What is interesting is DMPAPER_USER constant. You can create your own page size setting dmPaperSize to DMPAPER_USER and dmPaperWidth and dmPaperLength to what you need (in tenths of millimeter). Something like:

var
Device : array[0..255] of char;
Driver : array[0..255] of char;
Port   : array[0..255] of char;
hDMode : THandle;
PDMode : PDEVMODE;
begin
 Printer.GetPrinter(Device, Driver, Port, hDMode);
 if hDMode <> 0 then begin
   pDMode := GlobalLock(hDMode);
   if pDMode <> nil then begin

    {Set to legal}
     pDMode^.dmFields := pDMode^.dmFields or dm_PaperSize;
     pDMode^.dmPaperSize := DMPAPER_LEGAL;

    {or Set to custom size}
     pDMode^.dmFields := pDMode^.dmFields or
                         DM_PAPERSIZE or
                         DM_PAPERWIDTH or
                         DM_PAPERLENGTH;
     pDMode^.dmPaperSize := DMPAPER_USER;
     pDMode^.dmPaperWidth := 1000;
     pDMode^.dmPaperLength := 2000;

    {Set the bin to use}
     pDMode^.dmFields := pDMode^.dmFields or DMBIN_MANUAL;
     pDMode^.dmDefaultSource := DMBIN_MANUAL;
     
     Printer.SetPrinter(Device,Driver,Port,hDMode);

     GlobalUnlock(hDMode);
  end;
 end;
...

Regards, Geo