Formatierten Text drucken

Alles rund um die Programmierung mit Qt
Antworten
Fred
Beiträge: 7
Registriert: 22. Dezember 2010 00:20

Formatierten Text drucken

Beitrag von Fred »

Guten Abend,

zur Zeit versuche ich es mit Qt zu bewerkstelligen, einen formatierten Text auszudrucken.
Hierzu verwende ich zunächst mal folgenden Code:

Code: Alles auswählen

QPrinter* printer = new QPrinter(QPrinter::HighResolution);
    printer->setPageSize(QPrinter::A4);
    printer->setPrintRange(QPrinter::AllPages);
    QPrintDialog *dlg = new QPrintDialog( printer, this);
    dlg->setWindowTitle("Print");

    if(dlg->exec()!=QDialog::Accepted)
    {   
         return; 
    }

    QPainter painter(printer);
    
    QString text = ui->cloze_text->toPlainText();
    text += "\n\n\n\n\n";
    
     QStringListIterator it( shuffled_words_ );
    while(it.hasNext())
    {
        text += it.next() + "\n";
    }

    painter.setPen( QPen(Qt::black));
    painter.setFont( QFont("Times", 14) );
    painter.drawText( 0, 200, text );
Das Problem ist jetzt aber, dass der Text nun - wie ich von QPainter auch kaum anders erwartet habe - völlig unformatiert in einer einzigen Zeile dargestellt wird.
Leider finde ich in der Dokumentation bzgl. des Druckens von Text nicht sonderlich viel Hilfe.
Könnt ihr mir sagen, was ich tun könnte, damit der Text formatiert dargestellt wird?

Vielen Dank im Voraus,
Fred
upsala
Beiträge: 3946
Registriert: 5. Februar 2006 20:52
Wohnort: Landshut
Kontaktdaten:

Beitrag von upsala »

Und dein ui->cloze_text hat nicht zufälligerweise eine print()-Methode?
Fred
Beiträge: 7
Registriert: 22. Dezember 2010 00:20

Beitrag von Fred »

Ja mit der Print-Methode habe ich es auch durchaus schon probiert, aber damit lässt sich das ganze nicht ausdrucken. Wenn ich das mache, bleibt das Blatt weiß.
Das ganze sieht dann so aus:

Code: Alles auswählen

 QPrinter* printer = new QPrinter(QPrinter::HighResolution);
    printer->setOutputFormat( QPrinter::NativeFormat );
    printer->setPageSize(QPrinter::A4);
    printer->setPrintRange(QPrinter::AllPages);
    QPrintDialog *dlg = new QPrintDialog( printer, this);
    dlg->setWindowTitle("Print");

    if(dlg->exec()!=QDialog::Accepted)
    {   return; }

    QPainter painter(printer);
    QString text = ui->cloze_text->toPlainText();
    text += "\n\n\n\n\n";
    QStringListIterator it( shuffled_words_ );
    while(it.hasNext())
    {
        text += it.next() + "\n";
    }

    QTextDocument text_doc( text, this);
    text_doc.setDefaultFont( QFont("Times", 14));
    text_doc.print(printer);
Wenn ich hier im Übrigen als OutputFormat "PdfFormat" einstelle, dann wird mir ein einwandfreies PDF ausgegeben. Nur wird eben kein Text gedruckt.
lx2
Beiträge: 75
Registriert: 5. Mai 2009 03:13

die klasse qtextdocument könnte helfen

Beitrag von lx2 »

Hi,

ich habe erstmal eine nicht so befriedigende Antwort von der ich sicher weiß das es geht - ich hatte nämlich auch schonmal ein ähnliches Problem.
Meine lösung damals war recht aufwendig:

Ich hab für jeden einzelnen Textbestandteil die QPainter::drawText() funktion hergenommen.
http://doc.qt.nokia.com/latest/qpainter ... rawText-12
Hab sozusagen jedes einzelne wort genau auf seine x-y-Koordinate gesetzt und dann ein PDF davon generiert.
Das war bei mit einfach möglich da ich ne sehr tabellenartige Datei ausgeben musste.

Aber bin gerade durch die Anleitung
http://doc.qt.nokia.com/latest/printing.html
drauf gekommen dass du eventuell diese Klasse hernehmen kannst:

http://doc.qt.nokia.com/latest/qtextdocument.html

Die hat dann auch ne print methode. Du musst dir nur zusammensuchen wie du das objekt mit deinen Informationen füllen kannst.

Viel Erfolg!
Fred
Beiträge: 7
Registriert: 22. Dezember 2010 00:20

Beitrag von Fred »

Danke für deine Hilfe.
Leider ist deine Lösung auf mein Problem nicht übertragbar. Denn die Menge des Textes kann stark variieren und von daher kann ich nur schwerlich jedes Wort mit x und y Koordinaten versehen und platzieren.
Zu deinem zweiten Lösungs-Vorschlag, schau dir nochmal meinen zweiten Beitrag in diesem Thread an. Da mache ich genau das. Ich packe alles in ein QTextDocument und rufe die print-Methode auf.
Wenn ich den QPrinter anweise ein PDF zu erstellen, funktioniert das auch genauso, wie ich mir das vorstelle, aber ich weiß nicht, wie ich dem Drucker klar machen soll, dass er dann bitteschön auf Papier das druckt, was ich mir wünsche. Denn mit meiner Lösung erhalte ich da nur leere Seiten.
lx2
Beiträge: 75
Registriert: 5. Mai 2009 03:13

Beitrag von lx2 »

Hey Fred , kein wunder dass das nicht klappt!

Du baust dir erst ein QPainter und "belegest" damit den Drucker völlig sinnfrei. Er hat bei mir sogar Fehlermeldungen ausgegeben als ich den Code ausgeführt hab. QPainter::begin: A paint device can only be painted by one painter at a time.
(Nächstet mal bitte Debugnachrichten genau lesen)

Danach machst du aus nem schönen , schon fertig formatierten Text einen unformatierten (toPlainText) und schleifst ihn ganz komisch durch nen Stringlisteniterator... dass da nix schönes rauskommt dürfte klar sein :shock: :wink:


Mach dir doch das Leben leichter - so geht's:

Code: Alles auswählen

   // Drucker erstellen
   QPrinter *meinPrinter = new QPrinter();

   // Druckerdialog
   QPrintDialog *WelcherDruckerDialog = new QPrintDialog(meinPrinter, this);
   WelcherDruckerDialog->setWindowTitle(tr("Mit welchem Drucker soll ich drucken"));

   // Abbruchbehandlung
   if (WelcherDruckerDialog->exec() != QDialog::Accepted)return;

   // Neue Seite einfügen
   meinPrinter->newPage();

   //Der entscheidenede Punkt: Hole aus deinem QTextEdit ein echtes QTextDocument raus und nicht irgendeinen Listen-Murks
   QTextDocument* text_doc = ui->txt_main->document();

   //Drucke dein QTextDocument
   text_doc->print(meinPrinter);
Ich hab lediglich ein QTextEdit mit dem Namen txt_main erstellt.
Konnte txt_main dann formatiert(!) ausdrucken. D.h. Fett, Kursiv, Farbig, dass volle Programm :D
Willst du was am Layout machen (z.B. Querformat) schau in der Dokumentation von QPrinter nach.

Nicht persönlich nehmen ;) , ich lern auch immer noch dazu
Beste Grüße aus München
Fred
Beiträge: 7
Registriert: 22. Dezember 2010 00:20

Beitrag von Fred »

Okay vielen Dank. Das "printer->newPage()" hat bei mir gefehlt und deshalb hat er nicht gedruckt. Wer kann denn auch ahnen, dass der Drucker nicht selbst drauf kommt, dass er eine neue Seite erstellen soll ;), wo soll er denn auch sonst hindrucken^^.

Ansonsten hast du meinen Code allerdings ein bisschen missverstanden. Denn ich schleife meinen Text nicht völlig sinnlos durch eine QStringList, sondern lese eine solche aus. Mein Text setzt sich quasi aus zwei Elementen zusammen. Aus dem Text, das aus einem Text-Edit-Feld kommt und aus einzlenen Einträgen, die aus einer Liste kommen.

Ach ja, eines will ich aber nicht unerwähnt lassen: toPlainText macht aus einem formatierten Text keinen unformatierten Text. alle Formatierungen bleiben als Escape-Sequenzen innerhalb des Strings erhalten und wenn ich diesen String dann ausgebe, ist dieser genauso formatiert. Lediglich spezielle Einstellungen, wie Frabe oder Font gehen natürlich verloren, weil diese direkt mit dem Element zusammenhängen, aus dem der Text kommt. Aber solange es um die Formatierung geht, bleibt alles beim alten ;).

Aber das ist ja nebensächlich. Darum ging es mir ja nicht, wichtig ist, dass jetzt richtig gedruckt wird und das tut es. Vielen Dank also nochmal :).
Dieter Dorsch
Beiträge: 1
Registriert: Gestern 16:49

Re: Formatierten Text drucken

Beitrag von Dieter Dorsch »

Hier ist mein Beispiel mit HTML Formatierung und Vorschau Anzeige

// 1. Drucken initialisieren
QPrinter printer(QPrinter::HighResolution);
QPrintDialog printDialog(&printer, this);

// 2. Daten in doc mit HTML Formatierung
QTextDocument doc;
QString txt = "<h1>KNX Geräte "+ QString::fromStdString(ProjektName)+ "</h1>";
txt += "<table>";
for(int n=0; n<PAs.KNXGeräte.size();n++)
{
KNXdevice dev = PAs.KNXGeräte[n];
string Ort = dev.Ort;
if (Ort == "") Ort = "----------";
txt += "</table>";
txt += "<h2>"+ dev.toString()+ " " + dev.Manufacturer + "</h2";
txt += "<p> Einbauort:"+ Ort + " Hardware:"+ dev.HW + "</p>";
txt += "<table>";
txt += "<tr>";
txt += "<th>ComObj </th>";
txt += "<th> Name ---------------------- </th>";
txt += "<th> DPT--- </th>";
txt += "<th> Gruppe 1</th>";
txt += "<th></th>";
txt += "</tr>";
for (int Nr = 0; Nr < dev.ComObjects.size(); Nr++)
{
ComObject Obj = dev.ComObjects[Nr];
if (Obj.Gr1 != 0){
txt += "<tr>";
txt += "<td>"+ to_string(Obj.Number) + "</td>";
txt += "<td>"+ Obj.Name + "</td>";
txt += "<td>"+ Obj.DPT + "</td>";
txt += "<td>"+ GAtoStr(Obj.Gr1) +"</td>";
Gruppe* Gr = GAs.finde(Obj.Gr1);
if (Gr != NULL) txt += "<td>"+Gr->Name+"</td";
txt += "</tr>";
}
}
txt += "</table>";
}

// 3. Texteditor
QTextEdit *textEditor = new QTextEdit("");
textEditor->setHtml(txt);

// 4. Drucken mit Vorschau
QPrintPreviewDialog preview(&printer, nullptr);
connect(&preview, &QPrintPreviewDialog::paintRequested, textEditor->document(), &QTextDocument::print);
preview.exec();
m.f.G. Dieter
Antworten