Pythonでベジエ曲線

Python->Tkinter->Canvasで2次ベジエ曲線描きます。



標準ではないっぽい。ググったら以下のページを見つけました。
http://www.pygame.org/wiki/BezierCurve?parent=CookBook

よく見るとcalculate_bezier関数で自前で計算しているので、こいつを使わせてもらうことにしました。中身ははさっぱりわからない。
http://www.niksula.cs.hut.fi/~hkankaan/Homepages/bezierfast.html
こちらを参考にしているらしい。ライセンスは・・、Pygameで使ってるってことは少なくともLGPLはokなはず。えと、よくわからん。

vec2dはよく分からんけど、
>>>from vec2d import *
>>>a = vec2d(100,100) + vec2d(50,50)
>>>print a
vec2d(150,150)
>>>b = vec2d(100,100) * vec2d(5,5)
>>>print b
vec2d(500,500)
で、xとyを独立に計算してるだけっぽいので、リストでもいいやってと思ってリストでやった。

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:
import Tkinter
 
def calculate_bezier(p, steps = 30):
"""
Calculate a bezier curve from 4 control points and return a
list of the resulting points.
 
The function uses the forward differencing algorithm described here:
http://www.niksula.cs.hut.fi/~hkankaan/Homepages/bezierfast.html
"
""
 
t = 1.0 / steps
temp = t*t
 
f = p[0]
fd = 3 * (p[1] - p[0]) * t
fdd_per_2 = 3 * (p[0] - 2 * p[1] + p[2]) * temp
fddd_per_2 = 3 * (3 * (p[1] - p[2]) + p[3] - p[0]) * temp * t
 
fddd = fddd_per_2 + fddd_per_2
fdd = fdd_per_2 + fdd_per_2
fddd_per_6 = fddd_per_2 * (1.0 / 3)
 
points = []
for x in range(steps):
points.append(f)
f = f + fd + fdd_per_2 + fddd_per_6
fd = fd + fdd + fddd_per_2
fdd = fdd + fddd
fdd_per_2 = fdd_per_2 + fddd_per_2
points.append(f)
return points
 
def main():
 
window = Tkinter.Tk()
canvas = Tkinter.Canvas(window, bg = "white",width = 300, height = 200)
canvas.pack()
 
#point = [start_p,control_p1,control_p2,end_p]
point = [[3,30],[150,10],[150,130],[240,140]]
 
#draw dot
for i in range(len(point)):
canvas.create_oval(point[i],point[i],outline = "red", width = 5)
 
#draw line
sl = [[point[0][0],point[0][1],point[1][0],point[1][1]],
[point[1][0],point[1][1],point[2][0],point[2][1]],
[point[2][0],point[2][1],point[3][0],point[3][1]]]
canvas.create_line(sl,fill="red",width=1)
 
#draw curve
pp = [point[0][0],point[1][0],point[2][0],point[3][0]]
sp = [point[0][1],point[1][1],point[2][1],point[3][1]]
pp = calculate_bezier(pp)
sp = calculate_bezier(sp)
 
ll=[]
for i in range(len(pp)-1):
tl = [pp[i],sp[i],pp[i+1],sp[i+1]]
ll = ll + tl
 
canvas.create_line(ll,fill="green",width=3)
window.mainloop()
 
 
if __name__ == '__main__':
main()
 

up_20080816082613.jpg

けど、数値関係はArrayの方が速いらしいのでArrayでやった方がいいのかも。こんぐらいじゃ変わらないかなぁ。

目次へ
関連記事

コメント

コメントの投稿

非公開コメント

このブログについて
□ ブログ内容
決まった趣旨はありません。
興味を持ったこと・日常で行ったことを何でも書きます。

3DCG・プログラミングなどが多めです。

□ 現在の活動
・ウェブサイト制作
 (http://tiblab.net)
・3Dゲーム制作
 (コックパニック)
検索フォーム
ユーザータグ

Blender キャプチャ blendファイル BGE Python GameEngine ムービー Android CG  Red5 Terragen C# C++ 

カテゴリー
プロフィール

TiBra

Author:TiBra
趣味でCG制作、プログラミング等を行っています。メイカーズに憧れています。

ネットを通じた交流を広げたく思っていますので、コメント・メールはお気軽にどぞー

戯言程度のことは、こちらのブログに投稿しています。基本戯言なので、実質移転しているようなものです。

Mail:tibraあっとlive.jp
HP:TibLabmemocode
動画:VimeoFC2動画ニコニコ
ファイル:SkyDrive
企画:3Dゲーム作業実況

Blogリンク
不都合がございましたらご連絡ください。
当ブログのリンクバナー
FC2 ID
FC2カウンター
RSSフィード+解析コード