Qt打印

来源:互联网 发布:网络加速器 编辑:程序博客网 时间:2024/05/16 11:56

1、普通打印图片,例如

MainWindow::MainWindow(QWidget *parent) :    QMainWindow(parent),    ui(new Ui::MainWindow){    ui->setupUi(this);    image.load("flower.jpg");//导入图片}

void MainWindow::printImage(){    QPrinter printer(QPrinter::HighResolution);    QPrintDialog printDialog(&printer,this);    if(printDialog.exec())    {        QPainter painter(&printer);        QRect rect=painter.viewport();        QSize size=image.size();        size.scale(rect.size(),Qt::KeepAspectRatio);//保证图片显示完整,当源区域和目标区域大小不同时,源区域将会按指定的内容缩放以符合目标区域,缩放比例取决于Qt::AspectRatioMode        painter.setViewport(rect.x(),rect.y(),size.width(),size.height());        painter.setWindow(image.rect());        painter.drawImage(0,0,image);//绘制图片    }}
2、抓取窗口并打印,例如

PrintImage::PrintImage(QWidget *parent, Qt::WFlags flags)    : QMainWindow(parent, flags){    labImage = new QLabel(this);    labImage->setSizePolicy(QSizePolicy::Ignored,QSizePolicy::Ignored);    labImage->setScaledContents(true);    setCentralWidget(labImage);    if(image.load("background.png"))    {        labImage->setPixmap(QPixmap::fromImage(image));//窗口显示图片        resize(image.width(),image.height());    }}

void PrintImage::print(){    QPrinter printer;    QPrintDialog printDlg(&printer,this);    if(printDlg.exec())    {        QPainter painter(&printer);        QRect rect = painter.viewport();        QSize size = image.size();        size.scale(rect.size(),Qt::KeepAspectRatio);        painter.setViewport(rect.x(),rect.y(),size.width(),size.height());        painter.setWindow(image.rect());        painter.drawPixmap(0,0,QPixmap::grabWidget(this,this->rect()));//抓取窗口    }}
3、打印前预览,例如

void Widget::preView(){    QPrinter printer(QPrinter::HighResolution);    QPrintPreviewDialog preview(&printer,0);    connect(&preview, SIGNAL(paintRequested(QPrinter *)),this,SLOT(print(QPrinter *)));//<span style="font-family: Arial, Helvetica, sans-serif;">print(QPrinter *)函数自己实现</span>    preview.exec();//等待预览界面退出,预览界面含有打印功能}

4、打印特殊窗口部件,例如Graphics View框架

Graphics View框架通过场景的QGraphicsScene::render()函数和视图的QGraphicsView::render()函数均可以完成打印。这两个函数的差别在于坐标不同。GraphicsScene::render()函数通常用来绘制没有变换的场景,如几何函数、文本文档。QGraphicsView::render()函数用来实现屏幕快照,它默认的行为是将视口的数据绘制到指定的绘图设备。

void MainWindow::print(){    QPrinter printer;    if (QPrintDialog(&printer).exec() == QDialog::Accepted) {        QPainter painter(&printer);        painter.setRenderHint(QPainter::Antialiasing);        view->render(&painter);//打印视图        //scene->render(&painter);//打印场景    }}
其他典型窗口部件的打印函数

QSvgWidget----------------------QSvgRenderer::render()

QTextEdit     ----------------------QTextDocument::print()

QTextLayout----------------------QTextLayout::draw()

QTextLine    ----------------------QTextLine::draw()

5、打印文本,例如

void MainWindow::print(const QString &strHtml,const QString &strPdfFile, int iFormat = 1){    // strHtml是HTML格式的打印内容,strPdfFile是PDF文件路径    QString strPdfFile("./document1.pdf");//最终pdf上显示的可能是乱码    QPrinter printer;    QTextDocument doc;    doc.setHtml(strHtml);    if (iFormat == 1)    {        printer.setPageSize(QPrinter::A4);        printer.setOutputFormat(QPrinter::PdfFormat);        printer.setOutputFileName(strPdfFile);        doc.print(&printer);    }    else    {        doc.setPageSize(QSizeF(printer.logicalDpiX()*(80/25.4),printer.logicalDpiY()*(297/25.4)));        printer.setOutputFormat(QPrinter::NativeFormat);        doc.print(&printer);    }}
6、打印表格,例如(此处参考了http://blog.csdn.net/prochsh/article/details/5529944)
void QCurveQueryTool::printTable(QPrinter *printer){    QString title = QString("曲线打印");    printTableWidget(table,title,printer);}void QCurveQueryTool::printTableWidget(const QTableWidget* view,QString stitile,QPrinter *printer) //printFlag =1,打印表格{    double totalWidth = 0.0;    double totalHeight = 0.0;    double totalPageHeight=0.0;        int rows = view->model()->rowCount();   //行总数    const int cols = view->model()->columnCount(); //列总数        for (int c = 0; c < cols; ++c)  //求出列宽    {        totalWidth += view->columnWidth(c);    }        for (int r = 0; r < rows; ++r) //求出行宽    {        totalHeight += view->rowHeight(r);    }        QPainter painter(printer);    painter.setRenderHints(QPainter::Antialiasing | QPainter::TextAntialiasing);    painter.begin(printer);    QRect area = printer->paperRect();// paperRect();    QVector<int> startRow;    QVector<int> endRow;    int iCount = 0;    qreal left,top,right,bottom;    printer->getPageMargins(&left,&top,&right,&bottom,QPrinter::Point);    cout << "left = " << left << ", right = " << right << ", top = " << top << ", bottom = " << bottom << endl;    area.setHeight( int(area.height() - top - bottom) );    area.setWidth( int(area.width() - left - right) );        for (int p=0; p < rows; p++) //rows中保存了所有的行数 , 找出每次打印的开始行和结束行    {        totalPageHeight += view->rowHeight(p); //求出所有的列高度        int pageFooter = 50 ;  //页脚的高度        int pageHeader = 50;   //页眉的高度        if (startRow.size() == 0)        {            pageFooter = 50 ;            pageHeader = 500;        }        if ((totalPageHeight >= (area.height() - pageFooter - pageHeader)) || (p == rows -1))  //如果目前累加列的高度大于或者等于可用页面高度 || 到达最后一行        {            totalPageHeight = view->rowHeight(p);            if (p == rows -1)            {                if (p - iCount - 2 < 0)                {                    startRow.push_back(0);                }                else                {                    startRow.push_back(p - iCount - 2);                }                endRow.push_back(p);                //cout << startRow.at(startRow.size() - 1) << " " << endRow.at(endRow.size() - 1) << endl;            }            else            {                if (p - iCount - 2 < 0)                {                    startRow.push_back(0);                    endRow.push_back(p - 2);                }                else                {                    startRow.push_back(p - iCount - 1);                    endRow.push_back(p - 3);                }                //cout << startRow.at(startRow.size() - 1) << " " << endRow.at(endRow.size() - 1) << endl;            }            iCount = 0;        }        iCount++;    }        QTableWidget *printTable = new QTableWidget();    //printTable->horizontalHeader()->setResizeMode(QHeaderView::ResizeToContents);    //printTable->horizontalHeader()->setDefaultAlignment(Qt::AlignCenter);    //printTable->verticalHeader()->setResizeMode(QHeaderView::ResizeToContents);    //printTable->verticalHeader()->setDefaultAlignment(Qt::AlignCenter);    const double xscale = area.width() / totalWidth;    const double yscale = area.height() / totalHeight;    //const double pscale = area.height() / totalPageHeight;    //painter.scale(xscale , yscale); // With the scaling 3 It is Printing all    //painter.translate(area.x() + xscale, area.y() + pscale); //This is original    painter.translate(area.x() + xscale, area.y() + yscale);    //painter.save(); //commented    //int y=0 ;// This is introduced for the columns    //view->paintEvent(&event);    //QPainter paint(this);    //paint.setPen(Qt::red);    //paint.drawRect(0, 0, 0, 0);    QStyleOptionViewItem option;      QPen pen;    pen.setColor(Qt::black);    pen.setWidth(1);    painter.setPen(pen);        int irowcount = -1;    float rate = 1;    for(int ipage = 0; ipage < startRow.size();ipage++)  //startRow有大,就有多少页需要打印    {        printTable->setColumnCount(view->columnCount() + 1);  //打印的列数为view的列数        printTable->setRowCount(endRow[ipage] - startRow[ipage] + 2);  //设置当前打印页的行数        for(int c = 1;c < cols + 1;c++)        {            printTable->setColumnWidth( c,(view->columnWidth(c - 1)) );            QTableWidgetItem *newItem = printTable->item(0,c);            if (!newItem)  //如果printTable的首行不存在,添加文字或者序号            {                if (view->horizontalHeaderItem(c - 1)) //Returns the horizontal(水平的) header item for column                    newItem = new QTableWidgetItem(view->horizontalHeaderItem(c - 1)->text());                else                    newItem = new QTableWidgetItem(QString::number(c));                printTable->setItem(0,c ,newItem);            }            else    //否则,直接设置文字或者序号            {                if (view->horizontalHeaderItem(c - 1))                    newItem->setText(view->horizontalHeaderItem(c - 1)->text());                else                    newItem->setText(QString::number(c));            }        }                /////////////////////////求出合适的比率,用来完美表格的显示        QRect firstTable , lastTable;        QModelIndex firstIndex = printTable->model()->index(0,0);        QModelIndex lastIndex = printTable->model()->index(0,cols);        firstTable = printTable->visualRect(firstIndex);        lastTable =  printTable->visualRect(lastIndex);        float totalTableWidth = lastTable.topRight().x() - firstTable.topLeft().x();        float pagerWidth = printer->paperRect().width() - 20 - 20;        rate = totalTableWidth/pagerWidth;        cout << "totalTableWidth = " << totalTableWidth << ", pagerWidth = " << pagerWidth << ", rate = " << rate << endl;        /////////////////////////求出合适的比率,用来完美表格的显示                for(int c = 1;c < cols + 1;c++)  //重设宽度        {            printTable->setColumnWidth( c,int((view->columnWidth(c - 1))/rate) );        }        printTable->setColumnWidth(0,view->verticalHeader()->width());  //Returns the table view's vertical header.        int iRow = 0;        for(int ir = startRow[ipage]; ir <= endRow[ipage];ir++) //ir变量用来标识当前打印的是哪些行,设置当前打印页的首行        {            printTable->setRowHeight(iRow,view->rowHeight(ir));  //Sets the height of the given row to be height.            for(int ic = 0; ic < view->columnCount(); ic++)  //设置每个单元格的内容            {                QTableWidgetItem *newItem = printTable->item(iRow  + 1,ic + 1);                if (!newItem)                {                    if (view->item(ir,ic))                        newItem = new QTableWidgetItem(view->item(ir,ic)->text());                    else                        newItem = new QTableWidgetItem("");                    printTable->setItem(iRow + 1,ic + 1,newItem);                }                else                {                    if (view->item(ir,ic))                        newItem->setText(view->item(ir,ic)->text());                    else                        newItem->setText("");                }            }            iRow++;        }        qreal ioffx = (area.width() - totalWidth)/2;        qreal ioffy = 50;        if (ipage == 0)        {            ioffy = 500;            QwtPlotPrintFilter filter;            int options = QwtPlotPrintFilter::PrintAll;            options &= ~QwtPlotPrintFilter::PrintBackground;            options |= QwtPlotPrintFilter::PrintFrameWithScales;            filter.setOptions(options);            d_plot->print(&painter,QRect(50,65,650,400),filter);                    }        rows = printTable->rowCount();        iRow = 1;        for(int ir = startRow[ipage] ; ir <= endRow[ipage] ; ir++)  //ir变量用来标识当前打印的是哪些行,设置当前打印页的首列序号        {            QTableWidgetItem *newItem = printTable->item(iRow,0);            if (!newItem)            {                if (view->verticalHeaderItem(ir))                    newItem = new QTableWidgetItem(view->verticalHeaderItem(ir)->text());                else                    newItem = new QTableWidgetItem(QString::number(iRow));                printTable->setItem(iRow,0,newItem);            }            else            {                if (view->verticalHeaderItem(ir))                    newItem->setText(view->verticalHeaderItem(ir)->text());                else                    newItem->setText(QString::number(iRow));            }            iRow ++;        }                QPointF offPt(20,ioffy);  //20表示边框的空格        for (int r = 0; r < rows; r++)        {            QRect rt1,rt2;            QModelIndex idx1 = printTable->model()->index(r,0);            QModelIndex idx2 = printTable->model()->index(r,cols);            rt1 = printTable->visualRect(idx1);            rt2 = printTable->visualRect(idx2);            painter.drawLine( (rt1.bottomLeft() + offPt) , (rt2.bottomRight() + offPt) );            if (r == 0)            {                painter.drawLine( (rt1.topLeft() + offPt) , (rt2.topRight() + offPt) );            }        }        for (int c = 0; c < cols + 1; c++)        {            QRect rt1,rt2;            QModelIndex idx1 = printTable->model()->index(0,c);            QModelIndex idx2 = printTable->model()->index(rows - 1,c);            rt1 = printTable->visualRect(idx1);            rt2 = printTable->visualRect(idx2);            painter.drawLine( (rt1.topLeft() + offPt) , (rt2.bottomLeft() + offPt) );            if (c == cols)            {                painter.drawLine( (rt1.topRight() + offPt) , (rt2.bottomRight() + offPt) );            }        }        for (int r = 0; r < rows; r++)        {            irowcount ++;            for(int c = 0; c < cols  + 1; c++)            {                QModelIndex idx = printTable->model()->index(r,c);                option.rect = printTable->visualRect(idx);                if (printTable->item(r,c))                {                    QRectF rt(option.rect.left() + 3,option.rect.top(),option.rect.width(),option.rect.height());                    rt = rt.translated(offPt);                    if (r != 0 && c == 0)                    {                        painter.drawText(rt,Qt::AlignCenter,QString("%1").arg(irowcount));                    }                    else                    {                        if (r == 0)                        {                            painter.drawText(rt,Qt::AlignCenter,printTable->item(r,c)->text());                        }                        else                        {                            painter.drawText(rt,Qt::AlignVCenter,printTable->item(r,c)->text());                        }                    }                }            }        }        //ipage        if (ipage == 0)  //设置标题        {            QRectF rttt(area.left(),area.top(),area.width(),50);            painter.drawText(rttt,Qt::AlignCenter,stitile);        }        QRectF rttt(area.left(),area.bottom() - 65,area.width(),25);        painter.drawText(rttt,Qt::AlignCenter,QString::number(ipage + 1));        if (ipage < startRow.size() - 1)        {            printer->newPage();            irowcount--;        }    }    painter.end();    }

0 0
原创粉丝点击