◆ TOP INDEX へもどる |
■ 6月22日 (日) ◆ 「イルカくるくる」 先日、突然に「 3D でイルカ!」と思い立ち、 Direct-3D を使ったイルカが泳ぎ回るプログラムを書き始める。 いや、 Direct-X SDK に付いてくる「イルカが泳ぎ回る」サンプル "Dolphin.exe" を見ていたら、ムショーに「泳ぐイルカ」が作りたくなったもので。 ちなみに開発環境は、 Delphi 5 + Quadruple 2.00 + Direct-X7 SDK 。 「 Quadruple 」は、 Delphi で Direct-X を「簡単に使う」ライブラリで、 Direct-3D IM (直接モード)の補助関数が豊富なのである。 "Dolphin.exe" のソース "Dolphin.cpp" を見ると、 Direct-3D IM 用の機能豊富なライブラリ "d3dframe" や "d3dfile" を使ってシンプルに書いてある。 「 .X ファイル」形式であるイルカの 3D モデリングデータを "d3dfile" ライブラリを使って読み込み、 "d3dframe" ライブラリを使って簡単にシーンやメッシュの設定をしているのである。 つらつらと眺めていたら、「かの『 Quadruple 』を使えば Delphi でも "Dolphin.exe" のよーなものが出来るのでは……?」、と考えが浮かぶ。 思い立ったが吉日、と、まずは 3D イルカを表示するプログラムを書いてみることにしたのである。 これが、どツボの始まりとは気付かずに。 (笑) まずは、イルカの 3D モデル "Dolphin.x" ( .X ファイル形式)を、「 Quadruple 」用の .SX 形式のデータに変換である。 Quadruple 付属のツール「 SX-Simplify 」を使って .SX 形式に変換…… ……できない。 幾つかの frame に分けられたメッシュデータを含む .X ファイルを読み込めないよーである。 ここで、 Direct-X7 SDK のヘルプを読んで .X ファイル・フォーマットのお勉強。 そう簡単には、うまくいかないものである。 改めて、データ "Dolphin.x" (テキストファイル)の中身を見ると、……コレ、ちょっとフォーマットはずれてませんカ? 頂点データなどはそのまま使えるので、エディタでカリカリと書き直し。 も一度「 SX-Simplify 」を使って変換。 無事に .SX 形式のイルカ・モデルが出来たのである。 一応 .SX 形式データのビューアで、表示できるか確認。 …………………何も写りませんが。 他の .X ファイルを .SX ファイルに変換すると、ビューアで表示される。 イルカ・モデルだけ表示されず。 うーん、頂点データはしっかり読み込まれているのだが。 写らないイルカ・モデルをグリグリと回転させてみると、はじっこにチラリとポリゴンの影……。 さては、 と、ビューアのカメラを思いっきり引いて見ると、超巨大なイルカ・モデルが。(笑) そう、実はイルカ・モデルが大きかった為に、カメラはイルカの中に入ってしまっていたのである。 元のプログラム "Dophin.cpp" を見ると、イルカ・モデルを読み込んだ後に "too big.." な為、 1/100 にスケール・ダウンしておりましたとさ。 とりあえず、イルカの 3D モデリングデータは、確保成功である。 お次は、イルカ・データにテクスチャの貼り付け。 眼と模様が貼られただけで、なかなかカワイイ。 しかし、テクスチャ・データのドットが引き延ばされて、ちょっとカクカクした柄になってしまったのである。 ここは、 SetTextureStageState(0, D3DTSS_MAGFILTER, Integer(D3DTFG_LINEAR)); SetTextureStageState(0, D3DTSS_MINFILTER, Integer(D3DTFG_LINEAR)); と、「テクスチャが拡大されるときリニアに拡大縮小( 2x2 pixel 補間)」する設定にして、イルカ君の柄をなめらかに。 (縮小補間はいらんかったか) お次は、シーンの設定である。 海の中だからライト(光源)と反射光を、青みがけて設定。 うんうん、海中のようになってきたぞ。 影の部分が暗すぎるので、アンビエント(環境光)を設定………するも変わらず。 色々やってみたが、環境光は変わらないのである。 しょーがないので、光源の方向を変えて影が目立たないようにする。 根本的な解決になっておらぬが。 お次は、フォグ(霧)の設定。 物が遠くへゆくと霞む効果を出すのである。 海中なので、遠くへゆくと蒼く霞んで消えてゆく…、とゆー設定。 遠くのオブジェクトをレンダリングしなくてもいいので、一石二鳥である。 しかし! はた、と、フォグの範囲を設定する段階で、困る。 フォグの範囲を指定する数値は浮動小数点( float )であるが、 SetRenderState に受け渡すパラメータは「 DWORD 型である float 変数のアドレス」でなくてはならぬのである。 C であれば、 "*(( DWORD * ) ( &fFogStart ))" などと簡単に書けるのだが(簡単でもないか)、 PASCAL (Delphi) ではそーもいかない。 うう、 PASCAL の限界か。 ここで、「 Quadruple 」の作者 SANDMAN さんが作ったサンプル、「 LandScape 」を発見。 ありがたくソースを拝見。 このソースでは、インライン・アセンブラを使用してキャストしていた。 ( move( Single , Result , 4 ); ) これまたありがたく使わせていただく。 フォグを設定して、イルカ君を遠くにやると、 おお、海の向こうへ霞んでゆくようである。 とりあえず、フォグ効果は成功。 お次は! イルカの泳ぐアニメーションである。 元ソースの "Dolphin.cpp" を読むと、イルカの泳ぐ様子は、頂点データと法線データをいじって変形させているよーである。 ならば簡単! ………と、思ったが甘かった。 ソースをよく読むと、3種類のイルカ「尾を下げているイルカ」「尾が真っ直ぐのイルカ」「尾を上げているイルカ」の 3D モデルデータを読み込み、3種類のデータをブレンド(頂点の座標を混ぜ合わせる)しているのである。 そして、その3種類イルカ・データ "Dolphin_group.x" は、1つのファイルで「3つのフレームを含んだ『バイナリ・データ』」………。 (泣) 手持ちのツールでは、 .SX 形式のデータに変換するのは無理である。 何とか3匹のイルカ君を切り出す方法は無いものか…。 Delphi で "d3dframe" を使う方法なぞを延々と検索。 (ロシアで Delphi 用の "d3dframe" を発表しているサイト発見したりする。) ここで、 Direct-X8 SDK 付属のイルカ・サンプルは、全イルカ・データがテキスト形式の .X ファイルであることを発見。 手元にあった Direct-X8 SDK のイルカ・サンプルだけを、抜き出す。 ハイ、ここで何故 Direct-X8 SDK に替えなかったかは、つっこまないよーに。 「尾を下げているイルカ」「尾が真っ直ぐのイルカ」「尾を上げているイルカ」の .X ファイルが個別に手に入ったので、ちょちょっと書き換え、ツールで .SX 形式ファイルに変換。 3つのポーズのイルカ・データが、見事に表示できたのである。 あとは、これらのイルカ・データと、デフォルトのイルカ・データの頂点 (x,y,z) と法線 (nx,ny,nz) をブレンドして尾を上げ下げすれば一段落………せず。 (泣) 頂点・法線をブレンドすると、でろーんと、イルカの形が崩れて「この世にいないよーな生物」になってしまうのである。 これでは UMA である。 データを見ると、同じイルカでも、 Direct-X7 SDK 付属のイルカ・データと、 Direct-X8 SDK 付属のイルカ・データは、頂点のデータがまったく異なる。 = 故に、ブレンドすると崩れるのである。 しょーがないので、頂点のデータが同じ(とゆーか関連のある) Direct-X8 SDK 付属イルカ・データをデフォルトのデータにする。 すると、ブレンドは成功。 イルカ君は、尾を上げ下げするのである。 が、何故かテクスチャが張り込まれず、のっぺらぼうのイルカ君。 Direct-X8 SDK 付属イルカ・データを見ると、テクスチャ用の座標データ ( tu , tv ) が無い。 何とかテクスチャをラップするよう張り込もうとしたが、その度に「この世にはいないクトゥルーの眷属」のよーな生物が出来上がるのである。 ここで、ちょいと行き詰まる。 Direct-X8 SDK 付属イルカ・データを使えば、イルカ君の尾の上げ下げは上手く行く。 だけど、テクスチャがうまく貼れない。 元の Direct-X7 SDK 付属イルカ・データを使えば、今まで通りに表示されるが、訳判らぬ "Dolphin_Group.x" を読み込まねば尾の上げ下げは出来ない。 ちょいとしばらく思案して、 "Dolphin_Group.x" から頂点データ「だけ」を切り出すことに決定。 Direct-X7 SDK のヘルプを読んで、バイナリの .X ファイルのフォーマットをお勉強。 Delphi で "Dolphin_Group.x" から、頂点データを切り出すツールを作り始める。 (ここから、手段と目的が入れ替わっております。) Delphi におけるバイナリ・ファイルの扱いと、4バイトのバイナリから浮動小数点値に変換する方法に手間取りつつも、ペキペキとツール製作。 "Dolphin_Group.x" 内の頂点データの位置は、頂点数 285 ( $11D ) がカギである。 (バイナリデータで "1D 01 00 00" ) 頂点データの先頭と思われるアドレスにシークして読み込み、浮動小数点に変換して、 ( x , y , z ) と表示させると……。 ビンゴ! 元イルカ・データから変形されたと思われる、3種類のイルカデータを切り出すことに成功。 (これだけ眺めていると、もう座標値で判るわい) そして、切り出したデータを .SX 形式のファイルに変換。 元のイルカ・データとブレンドすると……。 見事にイルカ君が尾を上げ下げするようになったのである。 う、うれしい……。 と、ゆーか、表示するだけでこれだけ苦労する私もアレである。 さて、尾の上げ下げは、Application の OnIdle イベント内で行っていたのであるが( Timer では不正確故)、当然ながら速いPCではイルカ君がピチピチと「ハトヤのCM」状態。 システム・タイマーを参照( QueryPerformanceCounter )して同期をとり、ゆったりと尾を上げ下げ。 イルカ君がまったりと動いているのを見て、一段落。 あとは、自由に泳がせたいトコロである。 ◆ 「イルカくるくる・ファイル」 話だけではナニなので、とりあえず、データとコンパイルしたファイルを「らいぶらり」にアップロード。 興味のある方は、どーぞ。 ◆ 「 Delphi Dolphin 」の DownLoad ★ 注意 ・ 左クリック・ドラッグで回転、右クリック・ドラッグで拡大縮小 ・ Direct-X7 以降、必須 ・ 未完成なのでハングするかもしれません。 御自身の責任でどーぞ。 ◆ 「謝辞」 「 Quadruple 」とサンプルを制作した SANDMAN 氏に深く感謝いたします。 ◆ 「 Electrical Fireworks 」 → |