Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

PRINTING A DISPLAYED TABLE FROM DATABASE



  • HELLO FRIENDS I need your help please, i have an application which is able to display tables from the data base using the tableview. Now want to be able to print these tables.Please any one with examples on how to print tables from data base or any code which can help me, i will really appreciate your help


  • Lifetime Qt Champion



  • Thanks for your help,However, after trying one of your examples,when the function to print was triggered,the application just hung and it forcefully close itself without any error.Still need help.

    MY .CPP IS HERE.

    #include "pupils_paid_sch_fees_by_grade.h"
    #include "ui_pupils_paid_sch_fees_by_grade.h"
    #include<QPrinter>
    #include<QPrintDialog>
    #include<QTextDocument>
    #include<QPainter>
    
    
    PUPILS_PAID_SCH_FEES_BY_GRADE::PUPILS_PAID_SCH_FEES_BY_GRADE(QWidget *parent) :
        QDialog(parent),
        ui(new Ui::PUPILS_PAID_SCH_FEES_BY_GRADE)
    {
        ui->setupUi(this);
    }
    
    PUPILS_PAID_SCH_FEES_BY_GRADE::~PUPILS_PAID_SCH_FEES_BY_GRADE()
    {
        delete ui;
    }
    
    

    MY .H IS HERE.

    #include <QDialog>
    #include<QMessageBox>
    #include<QtSql>
    #include<QSqlDatabase>
    #include<QSqlQueryModel>
    #include<QPrinter>
    #include<QPrintDialog>
    #include<QPainter>
    #include<QTextDocument>
    
    
    
    namespace Ui {
    class PUPILS_PAID_SCH_FEES_BY_GRADE;
    }
    
    class PUPILS_PAID_SCH_FEES_BY_GRADE : public QDialog
    {
        Q_OBJECT
    
    public:
        explicit PUPILS_PAID_SCH_FEES_BY_GRADE(QWidget *parent = nullptr);
        ~PUPILS_PAID_SCH_FEES_BY_GRADE();
    
    private slots:
        void on_VIEW_PUPILS_clicked();
    
        void on_PRINT_clicked();
    
    private:
        Ui::PUPILS_PAID_SCH_FEES_BY_GRADE *ui;
        QSqlQueryModel *querymodel;
        QWidget* widget;
    };
    
    #endif // PUPILS_PAID_SCH_FEES_BY_GRADE_H
    
    
    void PUPILS_PAID_SCH_FEES_BY_GRADE::on_PRINT_clicked()
    {
    
    
    
          QPrinter printer(QPrinter::HighResolution);
          printer.setOrientation(QPrinter::Landscape);
          printer.setOutputFormat(QPrinter::PdfFormat);
          printer.setPaperSize(QPrinter::A4);
          printer.setOutputFileName("test.pdf"); // will be in build folder
    
          QPixmap pix(widget->size());
          QPainter painter(&pix);
          widget->render(&painter);
          painter.end();
    
          painter.begin(&printer);
          double xscale = printer.pageRect().width() / double(pix.width());
          double yscale = printer.pageRect().height() / double(pix.height());
          double scale = qMin(xscale, yscale);
          painter.translate(printer.paperRect().x() + printer.pageRect().width() / 2,
                            printer.paperRect().y() + printer.pageRect().height() / 2);
          painter.scale(scale, scale);
          painter.translate(-widget->width() / 2, -widget->height() / 2);
          painter.drawPixmap(0, 0, pix);
    
        QTextDocument doc;
    
        doc.setHtml("htmlcontent");
        doc.drawContents(&painter);
    
          painter.end();
        }
    

  • Lifetime Qt Champion

    Hi

    What does widget variable point to ?

    it seems just to be a dangling pointer if you only have
    QWidget* widget; // points to random stuff

    its not allocated and the reason for the crash.

    it should be set to what ever widget you want to print.



  • @mrjj Thanks alot, the widget am referring to is a tableView.I have changed the code a bit and it is now able to print successfully,however i have two problem now:

    1. The table is only position at the middle of the page , leaving alot of space above and below as shown here
      TABLE2.PNG
      2.The second problem is that even if the table is large where the scroll bar are used,it is only printing the only part shown on the screen/window leaving the rest of data below or above.What can be a solution? The code is below:
    void PUPILS_PAID_SCH_FEES_BY_GRADE::on_PRINT_clicked()
    {
    
    
    
          QPrinter printer(QPrinter::HighResolution);
          printer.setOrientation(QPrinter::Portrait);
          printer.setFullPage(true);
    
         // printer.setOutputFormat(QPrinter::PdfFormat);
          printer.setPaperSize(QPrinter::A4);
          //printer.setOutputFileName("test.pdf"); // will be in build folder
          QPrintDialog dialog(&printer,this);
          if(dialog.exec()!=QDialog::Accepted)
          return;
          //ui->tableView->paint();
          QPixmap pix(ui->tableView->size());
          QPainter painter(&pix);
          ui->tableView->render(&painter);
          painter.end();
    
          painter.begin(&printer);
          double xscale = printer.pageRect().width() / double(pix.width());
          double yscale = printer.pageRect().height() / double(pix.height());
          double scale = qMin(xscale, yscale);
          painter.translate(printer.paperRect().x() + printer.pageRect().width() / 2,
                            printer.paperRect().y() + printer.pageRect().height() / 2);
          painter.scale(scale, scale);
          painter.translate(-ui->tableView->width() / 2, -ui->tableView->height() / 2);
          painter.drawPixmap(0, 0, pix);
    
        QTextDocument doc;
    
        doc.setHtml("htmlcontent");
        doc.drawContents(&painter);
    
          painter.end();
        }
    

    I will appreciate any help given.


  • Lifetime Qt Champion

    Hi
    The code prints the actual widget so it cannot be used if many items as then not all are printed.
    You can use the way Gojir4 shows using a QTextDocument or using html as i did here
    https://forum.qt.io/topic/52652/solved-pdf-print-in-multiple-pages/21

    In any case you have to control the printing yourself and if you have many items so that cannot be on one page then you also need to handle new pages etc.



  • @GREYON said in PRINTING A DISPLAYED TABLE FROM DATABASE:

    Now want to be able to print these tables

    You may want to take a look at QtRPT report generator. Spoiler alert: I haven't used it myself.



  • @mrjj thanks let me try it



  • @Pablo-J-Rogina okey thanks,I will try it dear



  • @GREYON

    Just to add:

    PUPILS_PAID_SCH_FEE_BY_GRADE is a horrible name for any c++ class. Name your widgets after what they are, not what content they display, since the content could change. In addition it's way too long, as you can see from how your cpp file looks like :)

    PupilFeeDialog for example, would be much shorter and easier to handle.



  • @Pl45m4 thanks noted



  • @Pablo-J-Rogina
    So where and how is the function PrintTable() declared?



  • @mrjj how and where is function PrintTable declared in your example?


  • Lifetime Qt Champion

    @GREYON

    Its there. :)
    just scroll the code. there are more than shown first.

    alt text



  • @mrjj
    I can just see the function call,or maybe it's in the.h file?


  • Lifetime Qt Champion

    @GREYON

    Im not sure what you see ?
    it should all be there. just need to scroll more :)

    void PrintTable( QPrinter* printer, QSqlQuery& Query )
    is in any case.

    bool createConnection() {
    QSqlDatabase db = QSqlDatabase::addDatabase("QSQLITE");
    db.setDatabaseName(":memory:");
    if (!db.open()) {
    QMessageBox::critical(0, qApp->tr("Cannot open database"), "Click Cancel to exit.", QMessageBox::Cancel);
    return false;
    }
    QSqlQuery query;
    qDebug() << "table:" << query.exec("create table person (id int primary key, "
    "firstname varchar(20), lastname varchar(20), num int )");
    query.exec("insert into person values(101, 'Dennis', 'Young','1')");
    query.exec("insert into person values(102, 'Christine', 'Holand','2')");
    query.exec("insert into person values(103, 'Lars junior', 'Gordon','4')");
    query.exec("insert into person values(104, 'Roberto', 'Robitaille','5')");
    query.exec("insert into person values(105, 'Maria', 'Papadopoulos','3')");
    return true;
    }

    // credits to. (i adabted from his) https://stackoverflow.com/questions/3147030/qtableview-printing/4079676#4079676

    void PrintTable( QPrinter* printer, QSqlQuery& Query ) {
    QString strStream;
    QTextStream out(&strStream);

    const int rowCount = Query.size();
    const int columnCount = Query.record().count();

    out << "<html>\n"
    "<head>\n"
    "<meta Content="Text/html; charset=Windows-1251">\n"
    << QString("<title>%1</title>\n").arg("TITLE OF TABLE")
    << "</head>\n"
    "<body bgcolor=#ffffff link=#5000A0>\n"
    "<table border=1 cellspacing=0 cellpadding=2>\n";

    // headers
    out << "<thead><tr bgcolor=#f0f0f0>";
    for (int column = 0; column < columnCount; column++)
    out << QString("<th>%1</th>").arg(Query.record().fieldName(column));
    out << "</tr></thead>\n";

    while (Query.next()) {
    out << "<tr>";
    for (int column = 0; column < columnCount; column++) {
    QString data = Query.value(column).toString();
    out << QString("<td bkcolor=0>%1</td>").arg((!data.isEmpty()) ? data : QString(" "));
    }
    out << "</tr>\n";
    }

    out << "</table>\n"
    "</body>\n"
    "</html>\n";

    QTextDocument document;
    document.setHtml(strStream);
    document.print(printer);

    }

    void print() {
    QPrinter printer(QPrinter::HighResolution);
    printer.setOrientation(QPrinter::Portrait);
    printer.setPageSize(QPrinter::A4);
    printer.setOutputFormat(QPrinter::PdfFormat);
    // printer.setOutputFileName("e:/file.pdf"); // just for me testing
    QPrintDialog dlg(&printer, 0);
    if(dlg.exec() == QDialog::Accepted) {
    QSqlQuery query;
    query.exec("SELECT * from person");
    PrintTable(&printer, query);
    }
    }



  • @mrjj
    I can just see the function definition,or maybe it's in the.h file?


  • Lifetime Qt Champion

    @GREYON

    The function is there. there is no .h file.
    but full function is.



  • okey I have seen it now!,let me try to use it


  • Lifetime Qt Champion

    @GREYON
    Ok good :)


Log in to reply