Solved

How to add/remove/modify a custom papersize programmatically?

Posted on 2011-09-11
7
1,012 Views
Last Modified: 2012-05-12
Hi there,

I need to add/remove/modify a custom papersize to the windows 7 / xp print server programmatically.

(The result should be accessible/shown under  the print server properties after adding...)

Any ideas?

TIA- Peter
printserver.png
0
Comment
Question by:bytecook
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 4
  • 3
7 Comments
 
LVL 25

Expert Comment

by:epasquier
ID: 36521849
I'm not too good with german, do you mean add a USER paper size for use in the printer config ?
here is a start :
http://www.efg2.com/Lab/Library/UseNet/2000/0314.txt
0
 

Author Comment

by:bytecook
ID: 36521939
Hello epasquier,

thank you for that info, it is in  fact a user paper size, but selecting an user entry is not really aproblem.
I'm in search of ADDING a user custom papersize, and, setting the new form as default value for all printjobs... yesterday evening I found the registry entries for custom papersizes, but tbh, there should
be a better method to add a new printer form.

0
 

Author Comment

by:bytecook
ID: 36521949
@epasquier

btw, have seen that in the botttom text is DMPAPER_USER described - perhaps you're right!

cheers,

Peter
0
Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 25

Expert Comment

by:epasquier
ID: 36521950
you can also have a look at that very complete component TPrinterPreview
http://www.delphiarea.com/products/delphi-components/preview/

it has the ability to set the paper size at runtime according to the one you set in the component, so I guess you can find all you need in the source code (free)

it will look like this (setting of an existing papersize in the printer DEVMODE) :
http://www.efg2.com/Lab/Library/UseNet/2000/0526c.txt

here is also a code I found to add custom paper size, in C. I will try to convert it in Delphi
FORM_INFO_1 form1;
FORM_INFO_1 *pForm = NULL;
HANDLE hPrinter;
DWORD cByteNeeded, nReturned, cByteUsed;
SIZEL sz;
RECTL rc;
int i;

// récupération du handle sur l'imprimante
if (!OpenPrinter("HP DeskJet 1200C",&hPrinter,NULL))
return NULL;
// Récupére la quantité de mémoire à allouer
EnumForms(hPrinter, 1,
NULL,0,(LPDWORD)&cByteNeeded,(LPDWORD)&nReturned);

// allocation
pForm = (FORM_INFO_1 *)malloc(cByteNeeded);
ZeroMemory(pForm, cByteNeeded);

// remplit pForm avec l'ensemble des formats
EnumForms(hPrinter,1,(LPBYTE)pForm, cByteNeeded, (LPDWORD)&cByteUsed,
(LPDWORD)&nReturned);

// affichage du nom du format
for (i=0;i<nReturned;i++)
printf("%s\n",pForm.pName);

// désallocation
free(pForm);

// ajout d'un nouveau format
ZeroMemory(&form1, sizeof(FORM_INFO_1));
form1.Flags = FORM_USER;
form1.pName ="mon format";
sz.cx = 215900;
sz.cy = 279400;
rc.left = 0;
rc.top = 0;
rc.bottom = 279400;
rc.right = 215900;
form1.Size = sz;
form1.ImageableArea =rc;
AddForm(hPrinter,1,(LPBYTE)&form1);

// fermeture
ClosePrinter(hPrinter);

Open in new window

0
 
LVL 25

Accepted Solution

by:
epasquier earned 500 total points
ID: 36522136
Here you go :
unit Main;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, Spin;

type
  TForm1 = class(TForm)
    cbPrinters: TComboBox;
    lbPages: TListBox;
    GroupBox1: TGroupBox;
    edtFormWidth: TSpinEdit;
    edtFormHeight: TSpinEdit;
    btnAddForm: TButton;
    edtFormName: TEdit;
    procedure FormCreate(Sender: TObject);
    procedure cbPrintersChange(Sender: TObject);
    procedure btnAddFormClick(Sender: TObject);
  private
    { Déclarations privées }
  public
    { Déclarations publiques }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

Uses Winspool,Printers;

procedure ListPrinterForms(PrinterName:String;L:TStrings);
var
  HPrinter: THandle;
  Forms: array of TFormInfo1;
  Count, Needed, Returned: DWORD;
  i: Integer;
begin
 L.BeginUpdate;
 L.Clear;
 if OpenPrinter(PChar(PrinterName), HPrinter, nil) then
  begin
   try
    if not EnumForms(HPrinter, 1, nil, 0, Needed, Returned) then
     begin
      // we should fail here since we didn't pass a buffer
      if GetLastError <> ERROR_INSUFFICIENT_BUFFER then RaiseLastOSError;
      Count := (Needed div SizeOf(TFormInfo1)) + 1;
      SetLength(Forms, Count);
      if EnumForms(HPrinter, 1, @Forms[0], SizeOf(TFormInfo1) * Count, Needed, Returned) then
       begin
        if Returned < Count then SetLength(Forms, Returned);
        for i := 0 to Returned - 1 do
         begin
          L.Add(Format('%s - %dmm x %dmm', [Forms[i].pName,Forms[i].Size.cx div 1000,Forms[i].Size.cy div 1000]))
         end;
       end else RaiseLastOSError;
     end;
  finally
   ClosePrinter(HPrinter);
  end;
 end else RaiseLastOSError;
 L.EndUpdate;
end;

procedure AddPrinterForm(PrinterName,FormName:String;Width,Height:Integer;
                  MarginLeft:Integer=0;MarginTop:Integer=0;MarginRight:Integer=0;MarginBottom:Integer=0);
Var
 Form1:TFormInfo1;
 HPrinter: THandle;
 Size: TSize;
 ImageableArea: TRect;
begin
 if OpenPrinter(PChar(PrinterName), HPrinter, nil) then
  try
   ZeroMemory(@Form1, sizeof(Form1));
   form1.Flags := FORM_USER;
   form1.pName := PChar(FormName);
   Size.cx := Width;
   Size.cy := Height;
   ImageableArea.left  := MarginLeft;
   ImageableArea.top   := MarginTop;
   ImageableArea.right := Width-MarginRight;
   ImageableArea.bottom:= Height-MarginBottom;
   form1.Size := Size;
   form1.ImageableArea :=ImageableArea;
   AddForm(hPrinter,1,@Form1);
  finally
   ClosePrinter(HPrinter);
  end;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
 cbPrinters.Items.Assign(Printer.Printers);
end;

procedure TForm1.btnAddFormClick(Sender: TObject);
begin
 AddPrinterForm(cbPrinters.Text,edtFormName.Text,edtFormWidth.Value,edtFormHeight.Value);
 ListPrinterForms(cbPrinters.Text,lbPages.Items);
end;

procedure TForm1.cbPrintersChange(Sender: TObject);
begin
 if cbPrinters.ItemIndex<0 then Exit;
 ListPrinterForms(cbPrinters.Text,lbPages.Items);
end;

end.

// DFM
object Form1: TForm1
  Left = 0
  Top = 0
  AutoSize = True
  BorderWidth = 8
  Caption = 'Form1'
  ClientHeight = 393
  ClientWidth = 218
  Color = clBtnFace
  Font.Charset = DEFAULT_CHARSET
  Font.Color = clWindowText
  Font.Height = -11
  Font.Name = 'Tahoma'
  Font.Style = []
  OldCreateOrder = False
  OnCreate = FormCreate
  PixelsPerInch = 96
  TextHeight = 13
  object cbPrinters: TComboBox
    Left = 0
    Top = 0
    Width = 218
    Height = 21
    Style = csDropDownList
    TabOrder = 0
    OnChange = cbPrintersChange
  end
  object lbPages: TListBox
    Left = 0
    Top = 27
    Width = 217
    Height = 278
    ItemHeight = 13
    TabOrder = 1
  end
  object GroupBox1: TGroupBox
    Left = 0
    Top = 311
    Width = 217
    Height = 82
    Caption = 'New Form Name'
    TabOrder = 2
    object edtFormWidth: TSpinEdit
      Left = 9
      Top = 52
      Width = 65
      Height = 22
      MaxValue = 0
      MinValue = 0
      TabOrder = 0
      Value = 0
    end
    object edtFormHeight: TSpinEdit
      Left = 80
      Top = 52
      Width = 65
      Height = 22
      MaxValue = 0
      MinValue = 0
      TabOrder = 1
      Value = 0
    end
    object btnAddForm: TButton
      Left = 159
      Top = 49
      Width = 50
      Height = 25
      Caption = 'Add'
      TabOrder = 2
      OnClick = btnAddFormClick
    end
    object edtFormName: TEdit
      Left = 8
      Top = 24
      Width = 201
      Height = 21
      MaxLength = 31
      TabOrder = 3
    end
  end
end

Open in new window

0
 
LVL 25

Expert Comment

by:epasquier
ID: 36522151
Note that in my sample application, I do not set the margin of the paper, but the AddPrinterForm procedure can handle it.
0
 

Author Closing Comment

by:bytecook
ID: 36522254
Many thanks epasquier!

All the best,

Peter
0

Featured Post

[Live Webinar] The Cloud Skills Gap

As Cloud technologies come of age, business leaders grapple with the impact it has on their team's skills and the gap associated with the use of a cloud platform.

Join experts from 451 Research and Concerto Cloud Services on July 27th where we will examine fact and fiction.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Creating an auto free TStringList The TStringList is a basic and frequently used object in Delphi. On many occasions, you may want to create a temporary list, process some items in the list and be done with the list. In such cases, you have to…
Have you ever had your Delphi form/application just hanging while waiting for data to load? This is the article to read if you want to learn some things about adding threads for data loading in the background. First, I'll setup a general applica…
There are cases when e.g. an IT administrator wants to have full access and view into selected mailboxes on Exchange server, directly from his own email account in Outlook or Outlook Web Access. This proves useful when for example administrator want…
Monitoring a network: how to monitor network services and why? Michael Kulchisky, MCSE, MCSA, MCP, VTSP, VSP, CCSP outlines the philosophy behind service monitoring and why a handshake validation is critical in network monitoring. Software utilized …
Suggested Courses
Course of the Month4 days, 16 hours left to enroll

635 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question