;
; キャラクターを移動する(空を飛ぶ、クォータニオン)
;
#include "e3dhsp.as"
;/////////////////
;
; 初期化
;
E3DInit
dim keybuf, 256 ;キー入力
E3DCreateFont 24,12,400,,,,"MS ゴシック",fontid ;フォントの設定
fkabe = 0 ;壁データとの当たり判定(0:off / 1:on)
;/////////////////
;
; カメラの初期化
;
E3DSetProjection 100, 50000
;/////////////////
;
; ライトの設定
;
E3DCreateLight lid1 ;光源を作成
lightdirx1 = 1 ;平行光の向き
lightdiry1 = -1
lightdirz1 = 0
lightr1 = 255 ;平行光の色
lightg1 = 255
lightb1 = 255
E3DSetDirectionalLight lid1, lightdirx1, lightdiry1, lightdirz1, lightr1, lightg1, lightb1 ;光源を平行光源に設定
;/////////////////
;
; 形状データのロード
;
sdim mediadir, 2048
mediadir = curdir + "\\tako.sig"
E3DSigLoad mediadir, hsid1
E3DSetPos hsid1, 5000, 0, 5000
E3DSetBeforePos hsid1
E3DCreateQ axisqid
;/////////////////
;
; 地面の作成
;
sdim pathbuf, 2048, 4
pathbuf.0 = curdir + "\\yama.bmp" ;地面の座標情報
pathbuf.1 = curdir + "\\michi.bmp" ;地面の道の情報
pathbuf.2 = curdir + "\\kawa.bmp" ;地面の川の情報
pathbuf.3 = curdir + "\\bazou.bmp" ;地面、道、川の模様を決める、BMPファイル
;地面作成用の値
mapsize = 60000 ;X,Z座標の最大値
mapdiv = 120 ;座標の分割数
mapheight = 3000 ;高さの最大値
E3DLoadGroundBMP pathbuf.0, pathbuf.1, pathbuf.2, pathbuf.3, mapsize, mapsize, mapdiv, mapdiv, mapheight, hsid0
; 壁の作成
;道のマップをそのまま壁の生成に使います。
E3DSetMovableArea pathbuf.1, mapsize, mapsize, mapdiv, mapdiv, mapheight+100, hsid2
;////////////////////////////////////////////////////////////////
;/////////////////
;
; メインループ
;
*main
E3DGetKeyboardState keybuf ;キー状態取得
if keybuf.VK_ESCAPE = 1 : goto *bye ; [ESC]で終了
gosub *MoveChara ;キャラクター移動
;バックバッファへの書き込み作業を行う
E3DBeginScene ;-----シーンスタート
;モデルが、視野内にあるか判定
E3DChkInView hsid1 ;キャラクター
E3DChkInView hsid0 ;地面
E3DChkInView hsid2 ;壁
gosub *ChkConf ;地面との当たり判定(E3DChkInViewより後で呼ぶ)
gosub *MoveCamera ;カメラ移動
;バックバッファにレンダリングする。
E3DRender hsid1, 0
E3DRender hsid0, 0
E3DEndScene ;-----シーン終了
E3DPresent ;バックバッファの内容を、プライマリバッファに転送。描画する。
E3DSetBeforePos hsid1
E3DWaitbyFPS 60 : await 0
goto *main
;////////////////////////////////////////////////////////////////
;
; サブルーチン
;
;/////////////////
;
; 終了処理
;
*bye
E3DDestroyLight lid1 ;ライトを破棄
E3DBye
end
;/////////////////
;
; キャラクター移動
;
*MoveChara
forwardstep = 200 ;移動速度(前進)
backstep = -forwardstep ;移動速度(後退)
degstep = 5
mdegstep = -degstep
E3DGetDirQ2 hsid1, axisqid
if keybuf.VK_UP = 1 {
E3DRotateQLocalX axisqid, -1,1 ;矢印上
E3DSetDirQ2 hsid1, axisqid
}
if keybuf.VK_DOWN = 1 {
E3DRotateQLocalX axisqid, 1,1 ;矢印下
E3DSetDirQ2 hsid1, axisqid
}
if keybuf.'Z' = 1 : E3DPosForward hsid1, forwardstep ;z
if keybuf.'X' = 1 : E3DPosForward hsid1, backstep ;x
if keybuf.VK_LEFT = 1 : E3DRotateY hsid1, mdegstep ;矢印左
if keybuf.VK_RIGHT = 1 : E3DRotateY hsid1, degstep ;矢印右
return
;/////////////////
;
; カメラ移動(キャラクター追跡型)
;
*MoveCamera
;キャラクターを後ろに2500移動して座標を取得。backpos
E3DGetPos hsid1, saveposx1, saveposy1, saveposz1
E3DPosForward hsid1, -2500
E3DGetPos hsid1, backposx, backposy, backposz
E3DSetPos hsid1, saveposx1, saveposy1, saveposz1
;カメラをキャラクタ後方に設置
E3DSetCameraPos backposx, backposy + 1500, backposz
E3DSetCameraTarget saveposx1, saveposy1 + 800, saveposz1, 0, 1, 0
return
;/////////////////
;
; キャラクタの地面との当たり判定
;
*ChkConf
; 壁データとキャラクター
if fkabe ! 0 {
; 壁(hsid2)とキャラクタ(hsid1)のあたり判定
resultwall = 0
E3DChkConfWall hsid1, hsid2, 10, resultwall, adjustx1, adjusty1, adjustz1, nx1, ny1, nz1
if resultwall!0 {
E3DDrawTextByFontID fontid, 10,10,"壁に激突しました!", 255,255,255,255 ;壁に激突したときのメッセージ。
E3DSetPos hsid1, adjustx1, adjusty1, adjustz1
}
}
; 地面データとキャラクター
mapminy = -100 ;地面データのY座標の最小値。実際の最小値より、少し小さな値を入れる。
E3DChkConfGround hsid1, hsid0, 1, mapheight, mapminy, result, adjustx, adjusty, adjustz, nx, ny, nz
if ( result != 0 ) {
E3DGetPos hsid1, posx, posy, posz
if posy>adjusty {
E3DSetPos hsid1, posx, posy, posz ;空中
} else {
E3DSetPos hsid1, adjustx, adjusty, adjustz ;地面の上に移動
}
}
return
|