スポンサーサイト

上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

「境界球生成プログラム」を作ってみた

【リンク】 ◆解説系TOP◆

とりあえず、境界球生成プログラムを作りました。
自分は3Dモデルの当たり判定を境界球で行う予定なのですが、

そのためには まず境界球を生成して、可視化するプログラム
作っとかないと駄目かなーと思い、作ってみました。

↓こんな感じで、座標と半径を指定してやれば 後は勝手に頂点や法線を算出後、
描画してくれます。
-------------------------------
Sphere tS;
D3DXVECTOR3 t(0,0,0);
tS.Create(t,1);

//描画部分//
tS.Draw();

-------------------------------
※(0,0,0)が中心の、半径1の球を描画。

【参考画像】
球
球2
※上が半径1、下が半径3の球です。

明日(土曜日)あたりに、
境界球の生成法具体的なプログラムを追記してみようと思います(`・ω・´)+

【追記】
では早速やり方を書きます。
-----------------------------------------------------------------------------------
【1】半径と中心座標の情報を受け取る
【2】頂点の場所を算出する。
【3】頂点同士をD3DPT_TRIANGLESTRIPで結びつける
   順番を調べる。

-----------------------------------------------------------------------------------
大まかにこんな流れになります。

【参考画像】
球の定義



で、頂点の場所の算出する方法について。

まず、 球の真上から半分の地点まで任意の高さの円の円周上の頂点を
調べていきます。

※ハンバーガーみたいに
球を横に割って出来る円の、円周上の点を求める感じです。

【参考画像】
頂点の算出

で、このままだと、
水色の円のY座標 及び 半径が分からないので、90°付近(※)から、0°に向かって
cosθの値を半径sinθをy座標として 計算して行くことにします。

※90°= 球の真上 は、頂点が1つになるので、円にならない。
 よって90°からは始めない。



例えば、原点中心、半径1の球 の場合は、下記の様になります。
--------------------------------------------------------------------
60°の時は、 Y軸座標 = 0+0.86  半径0.5の円
30°の時は、 Y軸座標 = 0+0.5   半径0.86の円

--------------------------------------------------------------------
【参考画像】
頂点の算出2
※球の半径が1ではない場合は、 円の半径も その分拡大させてください。
半径10の球であれば、それぞれ半径5の円、半径8.6の円になります。



で、円のy座標と半径が分かったので、
今度は、円周上の頂点の求め方を解説します。

・・・と言っても、別に変わったことはしません。
円に対しても、同じようにsinθとcosθで座標を求めるだけです。

注:求めるのは第1象限の範囲まででOKです。
第1象限・・・横軸が+の範囲かつ、縦軸も+の範囲の場所。下の図を見れば分かるかも。

【参考画像】
頂点の算出3

※↑半径0.5、y座標が(球の中心から)0.86の円の場合です。
また、"pt"は 球の中心座標です。


それと、法線の求め方についてですが、球(円)の性質上、
中心から円周上の点へのベクトル = 法線
となります。

【参考画像】
法線
※法線・・・光が反射する方向だと思ってください。

なので、次の2つの手順で求められます。
-----------------------------------------------------------------------
【1】(円周上の点の座標 - 中心の座標)で、ベクトルを求める。
【2】正規化する。

-----------------------------------------------------------------------

一応 具体例。
中心座標が(2 0 0)で、半径が4 、 そして(球?)周上の点(2 4 0)の法線は、
-------------------------------------------------------

//円周上の座標 - 中心座標
2 - 2 = 0  (x)
4 - 0 = 4  (y)
0 - 0 = 0  (z)

//ベクトルの大きさを算出
(0*0) + (4*4) + (0*0) = 16
√16 = 4  ←ベクトルの大きさ

//正規化
0÷4 = 0
4÷4 = 1
0÷4 = 0

(0 1 0) ←法線

-------------------------------------------------------
※1:ベクトルの大きさは、xyzそれぞれの2乗を足して、平方根を取る。
※2:"正規化"は、ベクトルの大きさでxyzをそれぞれ割る事。


これで、 円周上の頂点、及び法線の出し方はOKな筈です!(`・ω・´)
で、先ほど第1象限までの頂点を出せば良い、と言ったんですけども、

何故か?というと、第1象限の頂点さえ求めれば、
後は符号を変えるだけで全ての頂点が出る
からです。

【参考画像】
頂点の算出4

何度も掛け算をしたり平方根を取ったりする必要が無いので、
こっちの方が確実に早いです。

あと、球の半分まででOKとも言いましたが、
コレも同じ理由です。

半分まで求めたら、あとはy座標を反転すれば
境界球を定義するための全ての頂点が求まります。

【参考画像】
頂点の算出5




ついでに、今回のソースコードの一部です。
【参考画像】
コード_球


多少、改良したい所もあるので、参考程度にどうぞ。
(法線を求める処理を、関数化したりとか)

改良版は、後日出します。

そして、記事が縦長になりそうなので、
ポリゴンを作る 頂点の順番を決める部分は 「境界球生成 後編」へと続きます。
(今回が前編という位置づけになります)
スポンサーサイト

テーマ : ゲーム製作 関連 - ジャンル : ゲーム

コメント

No title

いつか試そうと思っていた球体の頂点算出で参考にさせていただきます。

カテゴリの分類をもっと詳細にわけてもいいと思います。
1記事に複数登録できるともっといいです。
この記事なら
DirectX3D, 3D, 境界球, 解説
くらいに詳細に分類してほしいくらいです。
これをプログラミング1個に分類されると範囲として大きいです。

No title

確かにそろそろカテゴリを分類したほうがいいかもしれませんねe-260
("アクセス数"とか、明らかに無用の長物と化したカテゴリとかありますし)

一応、プログラミングの中の「解説系」は、
TOP記事の『役に立つかもしれない解説』をクリックすれば、
リンクが纏めてあるページに飛ぶようになってます。
(応急措置的な対応 & 気付きにくいかもしれないので、ちょっとカテゴリを作ってみます)

No title

非常に参考になりました。ありがとうございます!
境界球の動的生成はやってみたかったんですが、やり方が全くわからなかったので助かりました。
(ネット上にも情報が無かったので…)

conioさんが何か参考にされた書籍等はありますか?

No title

おぉ!、参考になれば嬉しいですv-411
あと、主に下記の様なサイトや書籍でDirectXの基礎や仕様なんかを把握していきました。
【1】超初心者のプログラム入門http://www13.plala.or.jp/kmaeda/directx9/directx9.htm
【2】Gameつくろー!
http://marupeke296.com/GameMain.html
【3】ゲームプログラミングのページ
http://hikari-hinomoto.hp.infoseek.co.jp/
【4】DirectXゲームグラフィックスプログラミングhttp://www.amazon.co.jp/gp/product/4797341874/ref=olp_product_details?ie=UTF8&me=&seller=

あと、今回の作成したプログラム(後編に記載)の
縮退三角形に関しては 【4】、
cosやsinは、 高校の三角関数の授業で覚えた知識
頂点の具体的な求め方は、 「球の切断面は円になるから、・・・・」と言う風に
処理手順や方法を紙に書いたりして、自分で徐々に作っていきましたe-454

No title

ご丁寧にありがとうございます!
境界球はご自分で編み出したのですね。すごい。

URL参考にさせて頂きますv-15

これからも更新楽しみにしてます。就活頑張って下さい。

No title

有り難うございますv-290

これからも役に立つ内容などを更新して行こうと思います!v-411
(何時決まるかは分かりませんが、
        就職活動も頑張ります(`・ω・´)+)
コメントの投稿
管理者にだけ表示を許可する



上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。