1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106
#!/usr/bin/python # coding: iso-8859-1 import math import Tkinter from Tkconstants import * # Screen resolution: RESX = 800 RESY = 600 XFAC = 100 XSUM = 400 YFAC = 90 YSUM = 300 class AgnesiWindow: def __init__(self): self.mw = Tkinter.Tk() self.mw.option_add("*font", ("Arial", 12, "normal")) self.mw.title("Agnesi") self.mw.geometry("+90+45") self.cv = Tkinter.Canvas(self.mw, bg = "white", width = RESX, height = RESY) self.cv.pack() self.btn = Tkinter.Button(self.mw, text = "Ok", command = self.mw.destroy) self.btn.bind(sequence = "<Return>", func = self.bindFunc) self.btn.focus() self.btn.pack(side = RIGHT, padx = 10, pady = 10) self.w = 90 self.points = {"up" : [math.cos(math.radians(270)), math.sin(math.radians(270))], "low" : [math.cos(math.radians(90)), math.sin(math.radians(90))], "circle" : [0, 0], "line" : [-3.6, 0]} self.withdraw = [] self.cv.create_line(0, self.points["up"][1] * YFAC + YSUM, 800, self.points["up"][1] * YFAC + YSUM) self.cv.create_line(0, self.points["low"][1] * YFAC + YSUM, 800, self.points["low"][1] * YFAC + YSUM) self.plotDot(self.points["low"], withdraw = False) self.mw.after(1000, self.draw) self.mw.mainloop() def bindFunc(self, a): self.mw.destroy() def plotPoint(self, point): a = [point[0] * XFAC + XSUM, point[1] * YFAC + YSUM] self.cv.create_line(a[0], a[1], a[0] + 1, a[1] + 1) def plotDot(self, point, withdraw = False): a = [point[0] * XFAC + XSUM, point[1] * YFAC + YSUM] if withdraw: self.withdraw.append(self.cv.create_oval(a[0] - 5, a[1] - 5, a[0] + 5, a[1] + 5, fill = 'black')) else: self.cv.create_oval(a[0] - 5, a[1] - 5, a[0] + 5, a[1] + 5, fill = 'black') def drawLine(self, from_, to_, withdraw = False): a = [from_[0] * XFAC + XSUM, from_[1] * YFAC + YSUM] b = [to_[0] * XFAC + XSUM, to_[1] * YFAC + YSUM] if withdraw: self.withdraw.append(self.cv.create_line(a[0], a[1], b[0], b[1])) else: self.cv.create_line(a[0], a[1], b[0], b[1]) def draw(self): if self.w <= 450: for i in self.withdraw: self.cv.delete(i) self.points["circle"] = [math.cos(math.radians(self.w)), math.sin(math.radians(self.w))] self.plotDot(self.points["circle"], withdraw = True) self.plotPoint(self.points["circle"]) self.w += 1 b = math.pow(self.points["line"][0], 2) self.points["line"][1] = 1 - (8. / (4. + b)) self.plotPoint(self.points["line"]) self.plotDot(self.points["line"], withdraw = True) self.plotDot([self.points["line"][0], self.points["up"][1]], withdraw = True) self.drawLine(self.points["low"], [self.points["line"][0], self.points["up"][1]], withdraw = True) self.plotDot([self.points["line"][0], self.points["low"][1]], withdraw = True) self.drawLine([self.points["line"][0], self.points["up"][1]], [self.points["line"][0], self.points["low"][1]], withdraw = True) self.points["line"][0] += 0.02 self.mw.after(50, self.draw) if __name__ == "__main__": app = AgnesiWindow()
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129
#!/usr/bin/python import math import Tkinter as tk # Screen resolution: RESX = 800 RESY = 600 # Zoom-factor and Up/Down-correction: XFAC = 70 XSUM = RESX // 2 YFAC = 60 YSUM = RESY // 2 class AgnesiWindow: def __init__(self): self.mw = tk.Tk() self.mw.option_add("*font", ("Arial", 12, "normal")) self.mw.title("Agnesi") self.mw.geometry("+90+45") self.cv = tk.Canvas(self.mw, bg = "white", width = RESX, height = RESY) self.cv.pack() self.btn = tk.Button(self.mw, text = "Ok", command = self.mw.destroy) self.mw.bind(sequence = "<Key-space>", func = lambda k: self.pause()) self.mw.bind(sequence = "<Return>", func = lambda k: self.mw.destroy()) self.mw.bind(sequence = "<Control-q>", func = lambda k: self.mw.destroy()) self.btn.pack(side = tk.RIGHT, padx = 10, pady = 10) self.angle = 130 self.points = {"up" : [math.cos(math.radians(270)), math.sin(math.radians(270))], "down" : [math.cos(math.radians(90)), math.sin(math.radians(90))], "circle" : [math.cos(math.radians(self.angle)), math.sin(math.radians(self.angle))], "upline" : [0, 0], "downline" : [0, 0], "curve" : [0, 0]} self.withdraw = [] self.drawStatic() self.calculatePoints() self.drawDynamic() self.running = -1 self.mw.after(1000, self.run) self.mw.mainloop() def run(self): self.running = 1 self.draw() def pause(self): self.running *= -1 if self.running == 1: self.draw() def getZoom(self, point): return [point[0] * XFAC + XSUM, point[1] * YFAC + YSUM] def plotPoint(self, point): point = self.getZoom(point) self.cv.create_line(point[0], point[1], point[0] + 1, point[1] + 1) def plotDot(self, point, withdraw = False): point = self.getZoom(point) o = self.cv.create_oval(point[0] - 5, point[1] - 5, point[0] + 5, point[1] + 5, fill = 'black') if withdraw: self.withdraw.append(o) def drawLine(self, from_, to_, withdraw = False): from_ = self.getZoom(from_) to_ = self.getZoom(to_) self.withdraw.append(self.cv.create_line(from_[0], from_[1], to_[0], to_[1])) def drawStatic(self): self.cv.create_line(0, self.points["up"][1] * YFAC + YSUM, RESX, self.points["up"][1] * YFAC + YSUM) self.cv.create_line(0, self.points["down"][1] * YFAC + YSUM, RESX, self.points["down"][1] * YFAC + YSUM) self.cv.create_oval((self.points["up"][0] - math.cos(math.radians(0))) * XFAC + XSUM, self.points["up"][1] * YFAC + YSUM, (self.points["up"][0] + math.cos(math.radians(0))) * XFAC + XSUM, self.points["down"][1] * YFAC + YSUM) self.plotDot(self.points["down"], withdraw = False) def drawDynamic(self): self.drawLine(self.points["down"], self.points["upline"]) self.drawLine(self.points["upline"], self.points["downline"]) self.drawLine(self.points["curve"], self.points["circle"]) self.plotDot(self.points["circle"], withdraw = True) self.plotDot(self.points["upline"], withdraw = True) self.plotDot(self.points["downline"], withdraw = True) self.plotDot(self.points["curve"], withdraw = True) self.plotPoint(self.points["curve"]) def calculatePoints(self): self.points["circle"] = [math.cos(math.radians(self.angle)), math.sin(math.radians(self.angle))] # Strahlensatz: d = self.points["up"][1] - self.points["down"][1] a = self.points["circle"][1] - self.points["down"][1] b = self.points["down"][0] - self.points["circle"][0] self.points["upline"] = [self.points["down"][0] - d / a * b, self.points["up"][1]] self.points["downline"] = [self.points["upline"][0], self.points["down"][1]] self.points["curve"] = [self.points["upline"][0], self.points["circle"][1]] def draw(self): if self.running == -1: return if self.angle <= 410: for i in self.withdraw: self.cv.delete(i) self.calculatePoints() self.drawDynamic() self.angle += 1 self.mw.after(50, self.draw) if __name__ == "__main__": app = AgnesiWindow()