前回は基本描画APIを使って静止画を描くプログラムを紹介しましたが、今回はアニメーションやマウスイベントなどを使った動的なグラフィックの描画について解説します。また、曲線の描画、乱数の利用についても解説します。
動きのあるグラフィックの描画
まずは、以下のプログラム(リスト1)と実行結果をご覧ください。前回解説したキャンバスの回転の例(TransformSample)に動きを加えたものです。
描画関数 draw
前回までは描画プログラムをコンストラクタ内に記述していましたが、リスト1ではdraw()関数内に場所を変えています(1)[1]。draw()は一定の時間間隔で繰り返し実行される特別な関数です。時間間隔はフレームレートで指定した値によって決まります。フレームレートが30であれば間隔は1/30秒です。
グラフィックはdraw()が実行される度にクリアされ、毎回新しく描画されることになります。リスト1ではキャンバスの回転角度を変化させることでグラフィックに動きを与えています(2)。
drawの制御
draw()は自動的に繰り返し実行されますが、次の関数で停止・再開を制御できます。
draw()の描画プログラムを明示的に実行する場合はredraw()を使います。
初期化関数 setup
リスト1のsetup()はプログラムの表示時に実行されます(3)。繰り返し実行する必要がない初期化の処理などを記述します。
draw()はsetup()の実行後に開始されます。
イベントとの対応
setup()とdraw()は自動的にFlashのイベントに割り当てられます。次の表で関数と対応するイベントを確認してください。
表1 イベントとの対応
関数名 | イベント |
draw | Event.ENTER_FRAME |
setup | Event.ADDED_TO_STAGE |
※クラス内でこれらの関数を実装する場合はpublic属性を指定する必要があります。
マウスとキーボードの処理
AS3でマウスやキーボードのイベント処理を行う場合はイベントリスナーを記述する必要がありますが、Frocessingではイベントに対応した名前で関数を記述するだけでイベントを受け取ることができます。AS2のイベント処理と同じようなものです。
イベント関数
次のFlashはリスト1にマウスイベント処理を行うプログラム(リスト2)を追加したものです。マウスを押すとアニメーションが停止し、離すと再開されます。
マウス・キーボードイベントに対応した関数は次の6つです。
※関数名はProcessingに準じているためFlashのイベント名と異なります。
表2 マウス・キーボードのイベント関数
関数名 | イベント |
mousePressed | MouseEvent.MOUSE_DOWN |
mouseReleased | MouseEvent.MOUSE_UP |
mouseClicked | MouseEvent.CLICK |
mouseMoved | MouseEvent.MOUSE_MOVE |
keyPressed | KeyboardEvent.KEY_DOWN |
keyReleased | KeyboardEvent.KEY_UP |
マウス・キーボードのプロパティ
次のプロパティは、よく使われるマウスとキーボードの状態を示します。
表3 マウス・キーボードのプロパティ
プロパティ | 状態 |
isMousePressed | マウスが押されている(Boolean) |
pmouseX | 直前のマウス座標(Number) |
pmouseY | 直前のマウス座標(Number) |
isKeyPressed | キーが押されている(Boolean) |
keyCode | 最後に押されたキーコード(uint) |
曲線の描画
Graphicsクラスでは2次ベジェ曲線(curveTo)を使って曲線を描画することができますが、描きたい曲線によってはプログラムが冗長になる場合があります。Frocessingは2次ベジェ曲線に加えて、3次ベジェ曲線、スプライン曲線のAPIが提供されており、場合によって使い分けることができます。
今回はスプライン曲線について解説します。
スプライン曲線
スプライン曲線は任意の座標を通る滑らかな曲線を描きたい場合に適しています。ベジェ曲線のようにコントロール点を指定する必要がありません(図3)。
4点を指定してスプライン曲線を描画します。実際に描画されるのは(x2,y2)、(x3,y3)を結ぶ曲線です。
curveVertex
より複数の座標を指定して連続した曲線を描画する場合はcurveVertex()を使います(リスト3)。前後に記述するbeignShape()、endShape()は座標の開始と終了を示します。curve()と同様に最初と最後の座標には曲線が描画されない点に注意してください。
第1回で紹介したサンプルコード(FrocessingSample)はこの方法で曲線を描画しています。
vertex
vertex()はcurveVertex()と同じように複数の座標を指定する関数で、曲線ではなく直線が描画されます(リスト4)。GraphicsクラスのmoveTo()、lineTo()に該当します。
次のFlashはマウスドラッグにより曲線(curveVertex)を描画するプログラムです。何かキーを押すと曲線が直線(vertex)となるので違いを確認してみましょう。プログラムはWonderflでご覧ください。
乱数の利用
Frocessingには乱数を発生させる関数が2つ用意されています。random()とnoise()です。
random()は引数で指定した値a~bの範囲で乱数を発生させます。bを省略した場合は0~aの範囲となります。
noise()はPerlinノイズを発生させます。yとzは省略できます。
連続的な引数を指定することで自然に変化する乱数を得ることができます(リスト6・図5)。
第1回で紹介したサンプルコード(FrocessingSample)の曲線の動きでnoise()を使用しているので参考にしてください。
ペイントプログラムをつくってみよう
最後に、マウスを使ったペイントプログラムをつくってみましょう。
まずは、次のプログラム(リスト6)と実行結果をご覧ください。マウスの移動に沿って線を描き、クリックで描画内容をクリアするシンプルなペイントプログラムです。
F5MovieClip2DBmp
リスト6のスーパークラスは、これまで利用していたF5MovieClip2DではなくF5MovieClip2DBmpです。違いはdraw()で描画されたグラフィックが画像データ(BitmapData)に重ねて描画される点です[2]。このクラスを利用することで描画した内容をクリアせずに残すことができます。
リスト6では直線を重ねて描くことでマウスの軌跡を表現しています(3)。
キャンバスのサイズ
size()はキャンバスのサイズを指定します(1)。F5MovieClip2DBmpでは描画される画像データ(BitmapData)のサイズとなります。
背景色の指定
background()はキャンバスの背景色を指定します(2)。色の指定方法はstroke()やfill()と同じです(色の指定方法)。background()を実行すると描画内容はクリアされます。
描画部分を変えてみる
F5MovieClip2DBmpを利用すれば手軽にペイントプログラムをつくることができます。リスト6の描画部分(直線)に手を加えて、いろいろなペイントプログラムを試してみてください。
次のFlashは直線の描画をrandom()を使った円のパーティクルに変更したものです。プログラムはWonderflでご覧ください。
まとめ
今回解説したdraw()やイベントの関数を使うことで手早くインタラクティブなプログラムをつくることができます。描画プログラムのプロトタイプなどで利用してみてください。次回はペイントプログラムを発展させる過程を紹介する予定です。