【发布时间】:2014-04-22 03:53:44
【问题描述】:
我有以下代码在圆的圆周上绘制椭圆,然后在椭圆之间绘制和弦。和弦画得很好,但事件轰炸了我,进入了无限循环。
def binomial(i, n):
return math.factorial(n) / float(
math.factorial(i) * math.factorial(n - i))
def bernstein(t, i, n):
return binomial(i, n) * (t ** i) * ((1 - t) ** (n - i))
def bezier(t, points):
n = len(points) - 1
x = y = 0
for i, pos in enumerate(points):
bern = bernstein(t, i, n)
x += pos[0] * bern
y += pos[1] * bern
return x, y
def bezier_curve_range(n, points):
for i in xrange(n):
t = i / float(n - 1)
yield bezier(t, points)
def getControlPt(x1, y1, x2, y2, t):
new_px = (1 - t) * x1 + t * x2
new_py = (1 - t) * y1 + t * y2
return new_px, new_py
class Temp1(QWidget):
def __init__(self, c, parent=None):
super(Temp1, self).__init__(parent)
self.text = "Hi"
self.cords = c
def paintEvent(self, e):
qp = QPainter(self)
qp.setPen(Qt.red)
bluePen = QPen(Qt.blue, 1, Qt.DashLine)
steps = 10000
for i in range(15):
for j in range(15):
if i == j:
continue
px, py = getControlPt(self.cords[i][0], self.cords[i][1], self.cords[j][0], self.cords[j][1], 0.55)
px1, py1 = getControlPt(px, py, self.cords[j][0], self.cords[j][1], 0.25)
px2, py2 = getControlPt(px1, py1, self.cords[j][0], self.cords[j][1], 0.75)
cp = (self.cords[i], (px, py) , (px1, py1), (px2, py2), self.cords[j])
oldPoint = cp[0]
qp.setPen(bluePen)
for point in bezier_curve_range(steps, cp):
qp.drawLine(oldPoint[0], oldPoint[1], point[0], point[1])
oldPoint = point
class Temp(QPushButton):
def __init__(self, x, y, w, h, theta, cords, parent=None):
super(Temp, self).__init__(parent)
self.w = w
self.h = h
self.x = x
self.y = y
self.text = "test"
self.angle = theta
self.cords = cords
def paintEvent(self, e):
qp = QPainter(self)
qp.setPen(Qt.red)
qp.drawEllipse(0, 0, self.w - 2, self.h -2)
class Example(QWidget):
def __init__(self):
super(Example, self).__init__()
self.cords = []
self.initUI()
def initUI(self):
self.setWindowTitle('Points')
self.drawP()
def drawP(self):
theta = 2 * np.pi / 15
for i in range(15):
angle = theta * (i + 1)
dx = int(round(400 + 300 * np.cos(angle)))
dy = int(round(400 + 300 * np.sin(angle)))
self.cords.append((dx, dy))
for i in range(15):
t = Temp(self.cords[i][0], self.cords[i][1], 45, 20, np.degrees(angle), self.cords, parent=self)
t.setGeometry(self.cords[i][0], self.cords[i][1] , 45, 20)
t1 = Temp1(self.cords, parent = self)
t1.setGeometry(0, 0, 800, 600)
app = QApplication(sys.argv)
ex = Example()
ex.setGeometry(0, 0, 800, 600)
ex.show()
sys.exit(app.exec_())
问题出在 Temp1 类的 paintevent 函数上。
【问题讨论】:
-
不要从
paintEvent调用setGeometry- 这是一个逻辑错误。 -
我无法测试 Temp1.paintEvent 因为我没有您使用的功能,但其余代码看起来不错。可能问题出在其他地方。您是否考虑过使用
QGraphicsView?它更方便您的任务。您不必继承任何东西并重新实现绘制事件。 Qt 还支持贝塞尔曲线(例如QPainterPath::cubicTo)。 -
@PavelStrakhov 您好,我添加了贝塞尔曲线的代码,如果这有助于您了解可能发生的情况,请告诉我。
标签: python qt user-interface pyside