我修改了一小段pyqt代码,以生成用户表达式的实时渲染。我已经使用了sympy的漂亮打印功能,但输出没有正确显示,因为QTextBrowser使用比例而不是等宽字体。
作为初学者,我也欢迎您对代码有任何其他想法。
非常感谢和祝福, 格迪斯
from __future__ import division
import sys
import sympy
from PyQt4.QtCore import *
from PyQt4.QtGui import *
class Form(QDialog):
def __init__(self, parent=None):
super(Form, self).__init__(parent)
self.browser = QTextBrowser()
self.lineedit = QLineEdit("please type an expression")
self.lineedit.selectAll()
layout = QVBoxLayout()
layout.addWidget(self.browser)
layout.addWidget(self.lineedit)
self.setLayout(layout)
self.lineedit.setFocus()
self.connect(self.lineedit, SIGNAL("textChanged (const QString&)"),self.updateUi)
def updateUi(self):
text = unicode(self.lineedit.text())
for z in range(0,9):
text = text.replace('x'+str(z),'x^'+str(z))
text = text.replace(')'+str(z),')^'+str(z))
text = text.replace(str(z)+'x',str(z)+'*x')
text = text.replace(str(z)+'(',str(z)+'*(')
try:
self.browser.append(sympy.printing.pretty(sympy.sympify(text)))
self.browser.clear()
self.browser.append(sympy.printing.pretty(sympy.sympify(text)))
except:
if text=='': self.browser.clear()
app = QApplication(sys.argv)
form = Form()
form.show()
app.exec_()
答案 0 :(得分:3)
您应该可以使用setFontFamily
更改字体。
关于你的代码:我还没有真正使用PyQt(只有一些像qbzr中的字体系列那样的黑客......),所以我不能告诉你一切是否正常。但以下不是一个好主意:
except:
if text=='': self.browser.clear()
except:
捕获所有例外情况。这也会像SystemExit
一样捕获BaseException
,除非你有理由这样做,否则不应该抓住它。始终捕获特定的异常,或者如果您处于最高级别(在执行未处理的异常处理程序之前)并且想要记录错误,请使用except Exception:
,它仅处理基于Exception
的异常。< / LI>
if text==''
- 我认为if not text
更像是“pythonic”。答案 1 :(得分:1)
QTextBrowser继承QTextEdit,因此您可以使用setCurrentFont(QFont)
方法设置等宽字体。
self.browser = QTextBrowser()
self.browser.setCurrentFont(QFont("Courier New")) #Or whatever monospace font family you want...
至于关于样式的一般评论,可能有一种方法可以将updateUi()
中的文本替换内容更改为正则表达式,但我不能确定没有看到样本数据来弄清楚你要做什么
另外,你应该重构
try:
self.browser.append(sympy.printing.pretty(sympy.sympify(text)))
self.browser.clear()
self.browser.append(sympy.printing.pretty(sympy.sympify(text)))
except:
if text=='': self.browser.clear()
更像是:
self.browser.clear()
try:
self.browser.append(sympy.printing.pretty(sympy.sympify(text)))
except:
if text=='': self.browser.clear()
除了可能捕捉到您期望的实际异常外。
修改强> 这里的等式正常化它看起来像你想要做的,它适用于小写的a-z和实数:
def updateUi(self):
text = unicode(self.lineedit.text())
text = re.sub(r'(\d+)([\(]|[a-z])',r'\1*\2',text) #for multiplication
text = re.sub(r'([a-z]|[\)])(\d+)',r'\1^\2',text) #for exponentiation
第一个模式查找一个或多个数字\d+
,后跟一个左括号或单个字母a-z [\(]|[a-z]
。它使用括号来捕获模式的数字部分和模式的可变部分,并在它们之间插入*。 \1*\2
。
第二个模式查找变量a-z或右括号[a-z]|[\)]
,后跟一个或多个数字\d+
。它使用分组括号再次捕获数字和变量,并在它们之间插入^ \1^\2
。
它不是很完美(不处理xy --> x*y
)但它更接近。如果你想建立一个完整的计算机代数系统,你可能需要建立一个专用的解析器:)