昨日と同じことをIronPythonでもやってみました。Visual Studio内のIronPython Consoleから実行するとイベントループが回るためコマンドを入力しながらウィンドウを操作することができますが、コマンドプロンプトのipyからだとイベントループが回らないため表示したウィンドウを操作することができません。
WPFを読み込みます。
import clr clr.AddReferenceByPartialName("PresentationCore") clr.AddReferenceByPartialName("PresentationFramework") clr.AddReferenceByPartialName("WindowsBase") from System.Windows import * from System.Windows.Controls import * from System.Windows.Shapes import * from System.Windows.Media import *
ウィンドウを開きます。
w = Window(Title = "Test", Width = 256.0, Height = 256.0) w.Show()
図形を置くためのCanvasを用意します。
canvas = Canvas() w.Content = canvas
四角形を置きます。
r = Rectangle(Width = 40.0, Height = 40.0) Canvas.SetLeft(r, 20.0) Canvas.SetTop(r, 60.0) r.Stroke = SolidColorBrush(Colors.Black) r.Fill = SolidColorBrush(Colors.Cyan) canvas.Children.Add(r)
文字を置きます。
tb = TextBlock(Text = "IronPython", FontSize = 24.0) canvas.Children.Add(tb)
移動がCanvas経由で面倒なため関数にします。
def move(el, x, y): Canvas.SetLeft(el, x) Canvas.SetTop(el, y) move(tb, 20.0, 30.0)
マウスで移動できるようにします。
elem = None click = Point() orig = Point() def down(el, e): global elem, click, orig elem = el orig = Point(Canvas.GetLeft(el), Canvas.GetTop(el)) click = e.GetPosition(canvas) canvas.CaptureMouse() r.MouseDown += lambda sender, e: down(r, e) tb.MouseDown += lambda sender, e: down(tb, e) def canvas_MouseMove(sender, e): global elem, click, orig if elem is not None: p = e.GetPosition(canvas) move(elem, orig.X + p.X - click.X, orig.Y + p.Y - click.Y) canvas.MouseMove += canvas_MouseMove def canvas_MouseUp(sender, e): global elem elem = None canvas.ReleaseMouseCapture() canvas.MouseUp += canvas_MouseUp
冒頭で述べたようにコマンドプロンプトのipyから実行した場合はイベントループが回らないため、明示的にイベントループを回すことで操作できるようになります。
Application().Run()
印象
F#と比較したIronPythonの使用感などです。
コンパイルしたexeの起動はIronPythonの方が遅いです。DLRの初期化の関係でしょうか。
.NETのオブジェクトを操作している限りは、F#もIronPythonも文法が違うだけという印象です。IronPythonの方が文法が簡潔で入力がスムーズです。特に対話モードのセミコロンの有無は大きいです。
型付けの静的・動的の違いについては、対話的な実行ではその場で評価されるためあまり違いを感じませんでした。プログラムとしてはIronPythonでは実行時に例外が発生するまで分からないため、動的型付けだということがはっきりします。