Mit der Turbo Delphi Explorer Edition Daten auf Papier bringen

Delphi macht Druck

Holger Klemt

Seit Anfang September sind die neuen Borland-Turbo-Versionen verfügbar. Immerhin hat Borland auch die versprochene kostenlose Turbo-Explorer-Version rechtzeitig zum Download bereitgestellt, auch wenn man kleine Details bei den Einschränkungen dieser Versionen zunächst wohl vergessen hat.

So ließen sich anfänglich in der ersten Version über den Umweg der Datei dclusr.dpk auch ohne irgendwelche Tricks zusätzliche Komponenten installieren. Mittlerweile hat Borland durch ein Update diese Lücke jedoch geschlossen, sodass Anwender dieser Versionen auf vorinstallierte Komponenten oder dynamisch erzeugte Komponenten angewiesen ist. Dieser Artikel zeigt auf Basis des dynamischen Datenbankbeispiels aus der letzten Ausgabe des Entwickler Magazin einen flexiblen Weg auf, wie man Daten auch mit der Explorer Edition auf Papier bringen kann, obwohl keine Komponenten für die Zwecke mitgeliefert werden.

Erweiterungen in der Beispielanwendung

Zunächst wird das Projekt [1] aus optischen Gründen um eine Tpagecontrol-Komponente erweitert, auf der dann mit der rechten Maustaste zwei Tabsheets angelegt werden. Die Tabsheet-Komponente, die als Container für die Datenbankanzeigeelemente benutzt werden soll, bekommt den Namen tsDaten. Bei der dynamischen Erzeugung von Controls ist es wichtig, den Owner als Parameter für den Konstruktor zu übergeben. Dieser sollte üblicherweise das aktuelle Formular sein, welches über das Schlüsselwort self referenziert werden kann. Der Owner sorgt beim Zerstören dafür, dass alle Komponenten, die zu diesem Owner gehören, vorher zerstört werden.

Bei visuellen Komponenten ist es zusätzlichen wichtig, die Eigenschaft Parent zu setzen, weil mit dieser erst der Bereich referenziert wird, auf dem die Komponente gezeichnet wird. In der ursprünglichen Version wurden dbgrid und dbnavigator direkt auf dem Formular erzeugt, in der neuen Version bekommen diese als Parent jedoch das Tabsheet tsDaten.

  DBNavigator1:=TDBNavigator.create(Self);
  with DBNavigator1 do
  begin
    align:=alTop;
    Parent := tsDaten;
    Datasource:=Datasource1;
  end;

Es ist auf diesem Wege möglich, Komponenten verschachtelt zu organisieren. Für diesen Zweck bieten sich Tpanel, Tpagecontrol und viele andere Container-Objekte aus der VCL an. Das fertige Formular sieht nach dem Programmstart wie in Abbildung 1 aus.

Abb. 1: Die Anwendung mit Pagecontrol

Auf der zweiten Seite werden im nächsten Schritt die Komponenten für eine einfache Druckvorschau und Ausgabe aufgenommen. Dabei wird zunächst ein Tpanel mit der Eigenschaft Align=alTop und ein weiteres Tpanel mit der Eigenschaft Align=alClient im Tabsheet tsDaten aufgenommen. Auf dem oberen Panel werden Tbutton für die integrierte Vorschau, Druckersetup, den Druckdialog und den direkten Ausdruck ohne Dialog aufgenommen. Im unteren Panel wird ein TWebBrowser-Objekt aufgenommen, das als integrierte Druckvorschau benutzt wird. Dabei handelt es sich im Prinzip um einen vollständigen Internet Explorer, der sehr flexibel einsetzbar ist.

Wenn man sich im Internet umschaut, sieht man auch, welche Möglichkeiten sich durch den Einsatz des TWebBrowsers ergeben. Die möglichen HTML-Tags, die der Internet Explorer unterstützt, ermöglichen eine sehr flexible Druckausgabe. Mithilfe der Prozedur erzeugeDruckdaten werden nun die Daten aus der Tabelle in eine HTML-Seite geschrieben (Listing 1).

Listing 1

procedure TForm1.erzeugeDruckdaten;
var i,z:integer;
begin
  z:=0;
  JvUIBDataSet1.First;
  with TStringlist.Create do
  begin
    add('Ausdruck');
    add('
‚);
add(‚

‚);
for I := 0 to jvuibDataset1.FieldCount-1
do add(‚

‚);
add(‚

‚);
while not JvUIBDataSet1.eof do
begin
inc(z);
if z mod 20=0
then
begin
add(‚

Daten
‚+
jvuibDataset1.Fields[i].FieldName+‘

‚);
add(‚

‚);
add(‚Seitenwechsel

‚);
add(‚

‚);
add(‚

‚);
for I := 0 to jvuibDataset1.FieldCount-1
do add(‚

‚);
add(‚

‚);
end;
add(‚

‚);
for I := 0 to jvuibDataset1.FieldCount-1
do add(‚

‚);
add(‚

‚);
JvUIBDataSet1.Next;
end;
add(‚

Daten
‚+
jvuibDataset1.Fields[i].FieldName+‘
‚+jvuibDataset1.Fields[i].AsString+‘

‚);
add(“);
savetofile(‚x.html‘);
free;
end;
end;

Es werden verschiedene HTML-Tags in einer Tstringlist-Instanz kombiniert und mit den Daten der Tabelle kombiniert. In diesem Beispiel werden einige wenige für solche Ausgaben interessante Tags benutzt, so zum Beispiel style=“width:120px“, mit dem feste Spaltenbreiten definiert werden können. Damit ist auch eine exakte Positionierung der Elemente möglich. Mit dem Eintrag style=“page-break-before:always“ ist es möglich, den Seitenwechsel manuell zu beeinflussen. Viele Reportgeneratoren haben dabei immer wieder seltsame Phänomene, bei denen es zum ungeplanten Ausdruck leerer Seiten kommt. Weitere interessante HTML-Befehle sind auf der SelfHTML-Seite [2] und [3] zu finden.

Die Ausgabe des Dateiinhalts im Formular als Vorschau kann nun ganz einfach mit der Routine aus Listing 2 erfolgen.

Listing 2

procedure TForm1.btnVorschauClick(Sender: TObject);
begin
  erzeugeDruckdaten;
  WebBrowser1.Navigate('C:x.html');
  repeat
    Application.ProcessMessages;
    Sleep(100);
  until WebBrowser1.ReadyState = READYSTATE_COMPLETE;
end;

Nach dem Erzeugen der HTML-Seite wird der Webbrowser mit der Methode Navigate auf diese Seite geführt und zeigt den Inhalt originalgetreu an. Die Repeat-Schleife ist vorgesehen, um mit dem nächsten Befehl so lange zu warten, bis der Ladevorgang abgeschlossen ist. Um den Ausdruck direkt zu starten, wird in der Methode aus Listing 3 zunächst die Vorschau aufgerufen und dann mit einem einfachen Ausdruck der Ausdruck aus dem Webbrowser gestartet.

Listing 3

procedure WBPrintNoDialog(WB: TWebBrowser) ;
var
   vIn, vOut: OleVariant;
begin
   WB.ControlInterface.ExecWB(OLECMDID_PRINT,
      OLECMDEXECOPT_DONTPROMPTUSER, vIn, vOut) ;
end;

procedure TForm1.btnDruckenClick(Sender: TObject);
begin
  btnVorschauClick(Sender);
  WBPrintNoDialog(WebBrowser1);
end;

Sofern der Standarddrucker keine zwingenden Dialoge mehr einblendet, wird der Inhalt des Browsers nun direkt auf dem Drucker ausgegeben. In der Beispielanwendung [1] sind alternativ auch die anderen Befehle für den Druckdialog und andere optionale Befehle implementiert.

Abb. 2: Die Druckausgabe in der Vorschau

Das hier vorgestellte Verfahren ist anwendbar auf nahezu alle Programmiersprachen und kann modular implementiert werden. Es ist zwar noch einiges an Feinarbeit zu leisten, um auch optisch anspruchsvolle Reports zu realisieren, aber man ist weder an eine bestimmte Datenbankschnittstelle noch an eine bestimmten Formulardesigner und dessen Konzept gebunden. Der Einsatz der HTML-Sprache bietet für nahezu alle denkbaren Fälle passende Formatierungen an und gleichzeitig lassen sich mit diesem Verfahren zum Beispiel Kataloge oder Preislisten für die eigene Webseite erstellen.

Geschrieben von
Holger Klemt
Kommentare

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht.