Как создать список для печати, который правильно охватывает несколько страниц - PullRequest
2 голосов
/ 05 января 2012

Фон

Это только мой второй проект PyQt4. Разработка приложения для Windows, в котором одним из его компонентов является управление счетом.

Вопрос

Мне нужны предложения о том, как успешно создать список, который можно чисто распечатать, даже если он охватывает несколько страниц.
Что-то вроде QTableView или QTableWidget.

Подробности интерфейса

Несколько строк заголовка (информация о клиенте, номер счета и т. Д.), За которыми следуют строки: | SKU # | ИМЯ | ОПИСАНИЕ | КОЛИЧЕСТВО | ЦЕНА
С некоторыми промежуточными итогами и общими итогами внизу.

Функциональность печати

Когда нажаты [Ctrl] + P или выбран File -> Print, должно появиться диалоговое окно системного принтера, позволяющее распечатать счет, который может занимать несколько страниц размера Letter.
Опционально, есть ли быстрый и простой способ реализовать предварительный просмотр?

Я не хочу тратить 3 дня, используя QTableWidget + QPrinter, только чтобы узнать, что он не может делать то, что мне нужно. Нужны помощь / советы / понимание вашего прошлого опыта, которые сэкономят мне время и усилия.

Спасибо

1 Ответ

1 голос
/ 07 января 2012

Я уверен, что все, чего вы хотите добиться, возможно с помощью PyQt4.

Ниже я добавил базовый скрипт, который демонстрирует функциональность, которую вы ищете.Формат печатной таблицы очень грубый, но вы можете легко добиться чего-то более изумительного, используя html вместо простой текстовой таблицы, которую я использовал.

from PyQt4 import QtGui, QtCore

class Window(QtGui.QWidget):
    def __init__(self):
        QtGui.QWidget.__init__(self)
        self.setWindowTitle(self.tr('Document Printer'))
        self.table = QtGui.QTableWidget(200, 5, self)
        for row in range(self.table.rowCount()):
            for col in range(self.table.columnCount()):
                item = QtGui.QTableWidgetItem('(%d, %d)' % (row, col))
                item.setTextAlignment(QtCore.Qt.AlignCenter)
                self.table.setItem(row, col, item)
        self.table.setHorizontalHeaderLabels(
            'SKU #|NAME|DESCRIPTION|QUANTITY|PRICE'.split('|'))
        self.buttonPrint = QtGui.QPushButton('Print', self)
        self.buttonPrint.clicked.connect(self.handlePrint)
        self.buttonPreview = QtGui.QPushButton('Preview', self)
        self.buttonPreview.clicked.connect(self.handlePreview)
        layout = QtGui.QGridLayout(self)
        layout.addWidget(self.table, 0, 0, 1, 2)
        layout.addWidget(self.buttonPrint, 1, 0)
        layout.addWidget(self.buttonPreview, 1, 1)

    def handlePrint(self):
        dialog = QtGui.QPrintDialog()
        if dialog.exec_() == QtGui.QDialog.Accepted:
            self.handlePaintRequest(dialog.printer())

    def handlePreview(self):
        dialog = QtGui.QPrintPreviewDialog()
        dialog.paintRequested.connect(self.handlePaintRequest)
        dialog.exec_()

    def handlePaintRequest(self, printer):
        document = QtGui.QTextDocument()
        cursor = QtGui.QTextCursor(document)
        table = cursor.insertTable(
            self.table.rowCount(), self.table.columnCount())
        for row in range(table.rows()):
            for col in range(table.columns()):
                cursor.insertText(self.table.item(row, col).text())
                cursor.movePosition(QtGui.QTextCursor.NextCell)
        document.print_(printer)

if __name__ == '__main__':

    import sys
    app = QtGui.QApplication(sys.argv)
    window = Window()
    window.resize(640, 480)
    window.show()
    sys.exit(app.exec_())
...