pyqt5 qtextdocument从右到左对齐并导出为pdf?
pyqt5 qtextdocument align from right to left and export to pdf?
我正在开发 pyqt5 项目,我需要将 tableview 导出为 pdf 或 docx。
- 导出为 pdf 可以正常工作,但我需要设置对齐方式
右 o 左,我也试过 html table 但我无法对齐
从右到左。
- 当我尝试导出为 docx 时,它有时无法正常工作,我得到
最后一行,有时我会得到迭代错误。
代码
from PyQt5.QtCore import Qt
from PyQt5.Qt import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *
from PyQt5 import QtCore, QtGui, QtWidgets, uic
from PyQt5.QtSql import *
from PyQt5 import QtPrintSupport as printSupport
from docx import Document
from docx.enum.table import WD_TABLE_DIRECTION
import xlsxwriter
import sys
class Window(QWidget):
def __init__(self):
super(QWidget, self).__init__()
self.setLayoutDirection(Qt.RightToLeft)
self.setLocale(QLocale(QLocale.Arabic, QLocale.Libya))
self.printer = printSupport.QPrinter()
# Configure defaults:
self.printer.setOrientation(printSupport.QPrinter.Portrait)
self.printer.setPageSize(QtGui.QPageSize(QtGui.QPageSize.A4))
pageSizeDictionary = {"a2": QPrinter.A2, "a3": QPrinter.A3, "a4": QPrinter.A4}
# self.printer.setPageSize(pageSizeDictionary.get(self.size.lower(), QPrinter.A4))
self.printer.setPageMargins(15, 15, 15, 15, QPrinter.Millimeter)
self.dpi = 72
self.documentWidth = 8.5 * self.dpi
self.documentHeight = 11 * self.dpi
self.database()
self.query = QSqlQuery()
self.queryModel = QSqlQueryModel()
self.productTableView = QTableView()
self.printPushButton = QPushButton('print table', self)
self.printPushButton.clicked.connect(self.printTableView)
self.printPreviewPushButton = QPushButton('print preview', self)
self.printPreviewPushButton.clicked.connect(self.printPreviewTableView)
self.exportAsDOCXPushButton = QPushButton('export as docx', self)
self.exportAsDOCXPushButton.clicked.connect(self.exportAsDOCX)
self.exportAsEXCELPushButton = QPushButton('export as excel', self)
self.exportAsEXCELPushButton.clicked.connect(self.exportAsExcel)
self.insertToDatabasePushButton = QPushButton('insert data to database', self)
self.insertToDatabasePushButton.clicked.connect(self.insertToDatabase)
self.gridLayout = QGridLayout(self)
self.gridLayout.addWidget(self.insertToDatabasePushButton, 0, 0)
self.gridLayout.addWidget(self.productTableView, 1, 0)
self.horizontalLayout = QHBoxLayout()
self.horizontalLayout.addWidget(self.printPushButton)
self.horizontalLayout.addWidget(self.printPreviewPushButton)
self.horizontalLayout.addWidget(self.exportAsDOCXPushButton)
self.horizontalLayout.addWidget(self.exportAsEXCELPushButton)
self.gridLayout.addLayout(self.horizontalLayout,2,0)
self.setLayout(self.gridLayout)
self.productsTableView()
def productsTableView(self):
sqlQuery = 'SELECT * FROM product '
self.queryModel.setQuery(sqlQuery)
self.productTableView.setModel(self.queryModel)
self.queryModel.setHeaderData(0, Qt.Horizontal, 'رقم المنتج')
self.queryModel.setHeaderData(1, Qt.Horizontal, 'اسم المنتج')
self.queryModel.setHeaderData(2, Qt.Horizontal, 'الكمية')
self.productTableView.horizontalHeader().setSectionResizeMode(QHeaderView.ResizeToContents)
self.productTableView.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch)
self.productTableView.setSortingEnabled(True)
def paintRequest(self,printer):
model = self.productTableView.model()
##########
tableFormat = QtGui.QTextTableFormat()
tableFormat.setHeaderRowCount(1)
tableFormat.setAlignment(Qt.AlignHCenter)
tableFormat.setAlignment(Qt.AlignVCenter)
tableFormat.setCellPadding(2.0)
tableFormat.setCellSpacing(2.0)
tableFormat.setWidth(
QtGui.QTextLength(QtGui.QTextLength.PercentageLength, 100))
##########
textOption = QtGui.QTextOption()
textOption.setTextDirection(Qt.RightToLeft)
textOption.setAlignment(Qt.AlignRight | Qt.AlignHCenter)
##########
document = QtGui.QTextDocument()
document.setPageSize(QtCore.QSizeF(self.documentWidth, self.documentHeight))
document.setDefaultFont(QtGui.QFont("Console , Verdana, Arial, Helvetica, sans-serif", 16))
document.setDefaultStyleSheet('body{ Background-color: red}')
document.setDefaultTextOption(textOption)
document.setDocumentMargin(30.0)
document.setDefaultTextOption(textOption)
cursor = QtGui.QTextCursor(document)
# charFormat = cursor.charFormat()
# charFormat.setFont(QtGui.QFont("Segoe UI Light", 28))
table = cursor.insertTable(
model.rowCount(), model.columnCount(), tableFormat)
for row in range(table.rows()):
for column in range(table.columns()):
index = model.index(row, column)
cursor.insertText(str(model.data(index)))
cursor.movePosition(QtGui.QTextCursor.NextCell)
document.print_(printer)
def printTableView(self):
dialog = printSupport.QPrintDialog(self.printer, self)
if dialog.exec_() == QDialog.Accepted:
self.paintRequest(dialog.printer())
def printPreviewTableView(self):
dialog = printSupport.QPrintPreviewDialog()
dialog.paintRequested.connect(self.paintRequest)
dialog.exec_()
if __name__ == '__main__':
app = QtWidgets.QApplication(sys.argv)
app.setStyleSheet("""
QPushButton {padding:10px;font-size:16px;font-weight: 400;}
QTableView{
border:1px solid #999;
font-family: Console , Verdana, Arial, Helvetica, sans-serif;
font-weight: 400;
font-size: 16px;
}
QTableView::item
{
border:1px solid #999;
color: #000;
text-align: center;
}QHeaderView::section{border:1px solid #999;font-family: Console , Verdana, Arial, Helvetica, sans-serif;
font-weight: 400;
font-size: 16px;}
""")
window = Window()
window.setFixedWidth(500)
window.setFixedHeight(300)
window.show()
sys.exit(app.exec_())
感谢@musicamante 只需以相反的顺序循环列
for row in range(table.rows()):
for column in range(table.columns()- 1, -1, -1):
index = model.index(row, column)
cursor.insertText(str(model.data(index)))
cursor.movePosition(QtGui.QTextCursor.NextCell)
我正在开发 pyqt5 项目,我需要将 tableview 导出为 pdf 或 docx。
- 导出为 pdf 可以正常工作,但我需要设置对齐方式 右 o 左,我也试过 html table 但我无法对齐 从右到左。
- 当我尝试导出为 docx 时,它有时无法正常工作,我得到
最后一行,有时我会得到迭代错误。
代码
from PyQt5.QtCore import Qt
from PyQt5.Qt import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *
from PyQt5 import QtCore, QtGui, QtWidgets, uic
from PyQt5.QtSql import *
from PyQt5 import QtPrintSupport as printSupport
from docx import Document
from docx.enum.table import WD_TABLE_DIRECTION
import xlsxwriter
import sys
class Window(QWidget):
def __init__(self):
super(QWidget, self).__init__()
self.setLayoutDirection(Qt.RightToLeft)
self.setLocale(QLocale(QLocale.Arabic, QLocale.Libya))
self.printer = printSupport.QPrinter()
# Configure defaults:
self.printer.setOrientation(printSupport.QPrinter.Portrait)
self.printer.setPageSize(QtGui.QPageSize(QtGui.QPageSize.A4))
pageSizeDictionary = {"a2": QPrinter.A2, "a3": QPrinter.A3, "a4": QPrinter.A4}
# self.printer.setPageSize(pageSizeDictionary.get(self.size.lower(), QPrinter.A4))
self.printer.setPageMargins(15, 15, 15, 15, QPrinter.Millimeter)
self.dpi = 72
self.documentWidth = 8.5 * self.dpi
self.documentHeight = 11 * self.dpi
self.database()
self.query = QSqlQuery()
self.queryModel = QSqlQueryModel()
self.productTableView = QTableView()
self.printPushButton = QPushButton('print table', self)
self.printPushButton.clicked.connect(self.printTableView)
self.printPreviewPushButton = QPushButton('print preview', self)
self.printPreviewPushButton.clicked.connect(self.printPreviewTableView)
self.exportAsDOCXPushButton = QPushButton('export as docx', self)
self.exportAsDOCXPushButton.clicked.connect(self.exportAsDOCX)
self.exportAsEXCELPushButton = QPushButton('export as excel', self)
self.exportAsEXCELPushButton.clicked.connect(self.exportAsExcel)
self.insertToDatabasePushButton = QPushButton('insert data to database', self)
self.insertToDatabasePushButton.clicked.connect(self.insertToDatabase)
self.gridLayout = QGridLayout(self)
self.gridLayout.addWidget(self.insertToDatabasePushButton, 0, 0)
self.gridLayout.addWidget(self.productTableView, 1, 0)
self.horizontalLayout = QHBoxLayout()
self.horizontalLayout.addWidget(self.printPushButton)
self.horizontalLayout.addWidget(self.printPreviewPushButton)
self.horizontalLayout.addWidget(self.exportAsDOCXPushButton)
self.horizontalLayout.addWidget(self.exportAsEXCELPushButton)
self.gridLayout.addLayout(self.horizontalLayout,2,0)
self.setLayout(self.gridLayout)
self.productsTableView()
def productsTableView(self):
sqlQuery = 'SELECT * FROM product '
self.queryModel.setQuery(sqlQuery)
self.productTableView.setModel(self.queryModel)
self.queryModel.setHeaderData(0, Qt.Horizontal, 'رقم المنتج')
self.queryModel.setHeaderData(1, Qt.Horizontal, 'اسم المنتج')
self.queryModel.setHeaderData(2, Qt.Horizontal, 'الكمية')
self.productTableView.horizontalHeader().setSectionResizeMode(QHeaderView.ResizeToContents)
self.productTableView.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch)
self.productTableView.setSortingEnabled(True)
def paintRequest(self,printer):
model = self.productTableView.model()
##########
tableFormat = QtGui.QTextTableFormat()
tableFormat.setHeaderRowCount(1)
tableFormat.setAlignment(Qt.AlignHCenter)
tableFormat.setAlignment(Qt.AlignVCenter)
tableFormat.setCellPadding(2.0)
tableFormat.setCellSpacing(2.0)
tableFormat.setWidth(
QtGui.QTextLength(QtGui.QTextLength.PercentageLength, 100))
##########
textOption = QtGui.QTextOption()
textOption.setTextDirection(Qt.RightToLeft)
textOption.setAlignment(Qt.AlignRight | Qt.AlignHCenter)
##########
document = QtGui.QTextDocument()
document.setPageSize(QtCore.QSizeF(self.documentWidth, self.documentHeight))
document.setDefaultFont(QtGui.QFont("Console , Verdana, Arial, Helvetica, sans-serif", 16))
document.setDefaultStyleSheet('body{ Background-color: red}')
document.setDefaultTextOption(textOption)
document.setDocumentMargin(30.0)
document.setDefaultTextOption(textOption)
cursor = QtGui.QTextCursor(document)
# charFormat = cursor.charFormat()
# charFormat.setFont(QtGui.QFont("Segoe UI Light", 28))
table = cursor.insertTable(
model.rowCount(), model.columnCount(), tableFormat)
for row in range(table.rows()):
for column in range(table.columns()):
index = model.index(row, column)
cursor.insertText(str(model.data(index)))
cursor.movePosition(QtGui.QTextCursor.NextCell)
document.print_(printer)
def printTableView(self):
dialog = printSupport.QPrintDialog(self.printer, self)
if dialog.exec_() == QDialog.Accepted:
self.paintRequest(dialog.printer())
def printPreviewTableView(self):
dialog = printSupport.QPrintPreviewDialog()
dialog.paintRequested.connect(self.paintRequest)
dialog.exec_()
if __name__ == '__main__':
app = QtWidgets.QApplication(sys.argv)
app.setStyleSheet("""
QPushButton {padding:10px;font-size:16px;font-weight: 400;}
QTableView{
border:1px solid #999;
font-family: Console , Verdana, Arial, Helvetica, sans-serif;
font-weight: 400;
font-size: 16px;
}
QTableView::item
{
border:1px solid #999;
color: #000;
text-align: center;
}QHeaderView::section{border:1px solid #999;font-family: Console , Verdana, Arial, Helvetica, sans-serif;
font-weight: 400;
font-size: 16px;}
""")
window = Window()
window.setFixedWidth(500)
window.setFixedHeight(300)
window.show()
sys.exit(app.exec_())
感谢@musicamante 只需以相反的顺序循环列
for row in range(table.rows()):
for column in range(table.columns()- 1, -1, -1):
index = model.index(row, column)
cursor.insertText(str(model.data(index)))
cursor.movePosition(QtGui.QTextCursor.NextCell)