HSPポータル
サイトマップ お問い合わせ


HSPTV!掲示板


未解決 解決 停止 削除要請

2018
0104
おぼシューティングゲームのスクリプトで質問です。3解決


おぼ

リンク

2018/1/4(Thu) 10:52:24|NO.82158

おはようございます。おぼです。

今まで、サンプルにしていたスクリプトのよくわかっていないところを、そういうものだ。で通していたのですが、それでは今後ダメになることがよく分かったので、サンプルについての質問です。


#include "hsp3dish.as" title "Dish Shooting" *init ; 画面の準備 ; celload "title.png",2 celload "chr.png",3 celload "bg.png",4 mmload "explos.wav",0 mmload "inject.wav",1 mmload "sel.wav",2 mmload "cappi08.mp3",3 *gtitle_start mmstop mmplay 2 *gtitle ; スタートボタンチェック ; stick a,$130 if a&128 : end if a&$130 : goto *gamestart redraw 0 ; タイトルの表示 ; gmode 0,320,480 pos 0,0:gcopy 2,0,0 ; スコアの表示 ; color 255,255,255 pos 0,0:mes "SCORE:"+score redraw 1 await 1000/30 goto *gtitle *gamestart ; ゲーム開始時の変数リセット ; mmplay 3 ; 音楽を鳴らす mmplay 2 score = 0 ; スコア sizex=ginfo_sx:sizey=ginfo_sy ; 画面サイズ mx=sizex/2:my=sizey-80 ; 自機のX,Y座標 mxlimit=sizex-48 ; 自機X最大値 mylimit=sizey-48 ; 自機Y最大値 mapx=0:mapy=0 ; 背景表示用の座標 mflag=0 ; 自機の爆発フラグ frame=0 ; フレーム数 ; 自機レーザー用変数リセット ; lmax=4 dim lflag,lmax dim lx,lmax dim ly,lmax ; 敵用変数リセット ; emax=16 etime=0 einter=18 dim eflag,emax : dim etype,emax dim ex,emax : dim ey,emax dim epx,emax : dim epy,emax exlimit = sizex+48 eylimit = sizey+48 ; 敵ミサイル用変数リセット ; amax=16 msrint=2 dim aflag,amax dim ax,amax : dim ay,amax dim apx,amax : dim apy,amax axlimit = exlimit * 100 aylimit = eylimit * 100 *main redraw 0 ; 背景の表示 ; gmode 0,320,480 pos 0,mapy:gcopy 4,0,0 if mapy>0 { gmode 0,320,mapy pos 0,0:gcopy 4,0,960-mapy } mapy=mapy+2:if mapy>960 : mapy=mapy-960 ; それぞれの処理を呼び出す ; stick a,$10f if a&128 : end gosub *my_move gosub *laser_move gosub *enemy_move gosub *missile_move ; スコアの表示 ; color 255,255,255 pos 0,0:mes "SCORE:"+score redraw 1 await 1000/30 if mflag>150 : goto *gtitle_start frame++ goto *main *my_move ; 自機の移動と表示 ; if mflag>0 : goto *my_end if a&256 : goto *my_mouse if a&2 : my=my-6 if a&8 : my=my+6 if a&1 : mx=mx-6 if a&4 : mx=mx+6 goto *my_check *my_mouse x=mousex-24:y=mousey-24 px = x - mx if px>6 : px=6 if px<-6 : px=-6 mx = mx + px py = y - my if py>6 : py=6 if py<-6 : py=-6 my = my + py *my_check if mx<0 : mx=0 if mx>mxlimit : mx=mxlimit if my<240 : my=240 if my>mylimit : my=mylimit pos mx,my:gmode 2,48,48:gcopy 3,0,0 return *my_end ; 自機の爆発 ; mflag=mflag+1:a=0:i=mflag/4\3+5 pos mx,my:gmode 2,48,48:gcopy 3,i*48,0 return *my_hit ; 座標(x,y)が自機の領域内かを調べる ; if mflag>0 : vx=999 : vy=999 : return vx=mx-x:if vx<0 : vx=-vx vy=my-y:if vy<0 : vy=-vy return *laser_move ; 自機レーザーの処理 ; ;if (a&16)=0 : goto *noshoot if mflag>0 : goto *noshoot if frame&7 : goto *noshoot repeat lmax if lflag.cnt=0 { lflag.cnt=1 lx.cnt=mx : ly.cnt=my break } loop ;mmplay 1 *noshoot gmode 2,48,48,256 repeat lmax if lflag.cnt>0 { ly.cnt=ly.cnt-12 if ly.cnt<-48 : lflag.cnt=0 x=lx.cnt:y=ly.cnt pos x,y : gcopy 3,48,0 gosub *enemy_hit if hit>0 : mmplay 0 : lflag.cnt=0 : score=score+50 } loop return *enemy_move ; 敵の処理 ; etime=etime+1 if etime<einter : goto *enemy_put etime=0 ; 敵を発生させる ; y=-48 x=rnd(sizex)-24 type=rnd(2)+3 px=rnd(5)-2 py=1 speed=rnd(4)+2 px=px*speed/2:py=py*speed+1 repeat emax if eflag.cnt=0 { eflag.cnt=1 ex.cnt=x : ey.cnt=y epx.cnt=px : epy.cnt=py etype.cnt=type break } loop *enemy_put ; 敵を表示する ; gmode 2,48,48 repeat emax if eflag.cnt=0 : goto *noenemy x=ex.cnt:y=ey.cnt if eflag.cnt>1 : goto *edead x=x+epx.cnt:y=y+epy.cnt pos x,y : gcopy 3,etype.cnt*48,0 if x<-48 : eflag.cnt=0 if x>exlimit : eflag.cnt=0 if y<-48 : eflag.cnt=0 if y>eylimit : eflag.cnt=0 ex.cnt=x:ey.cnt=y gosub *my_hit if vx<48 : if vy<48 : mflag=1 : mmplay 0 ; 敵からミサイル発射 ; msrate=rnd(100) if msrate<msrint : gosub *missile_add *noenemy loop return *edead ; 敵の爆発 ; i=eflag.cnt+1:if i>16 : i=0 : goto *edead2 pos x,y : gcopy 3,(i/4\3+5)*48,0 *edead2 eflag.cnt=i:goto *noenemy *missile_add ; 敵ミサイルを発生させる ; (x,y)の位置に発生させる repeat amax if aflag.cnt>0 : goto *mslnext aflag.cnt=1 ax.cnt=x*100 : ay.cnt=y*100 px=mx-x : py=my-y if py>=0 : apy.cnt=600 if py<0 : py=-py : apy.cnt=-600 if py=0 : py=1 px=px*600/py if px>800 : px=800 if px<-800 : px=-800 apx.cnt=px break *mslnext loop return *missile_move ; 敵ミサイルの処理 ; gmode 2,32,32 repeat amax if aflag.cnt=0 : goto *nomsl x=ax.cnt:y=ay.cnt x+=apx.cnt y+=apy.cnt if x<-3200 : aflag.cnt=0 if x>axlimit : aflag.cnt=0 if y<-3200 : aflag.cnt=0 if y>aylimit : aflag.cnt=0 ax.cnt=x:ay.cnt=y x=x/100:y=y/100 pos x,y : gcopy 3,96,0 gosub *my_hit if vx<32 : if vy<32 : mflag=1 *nomsl loop return *enemy_hit ; 座標(x,y)が敵の領域内かを調べる ; hit=0 repeat emax if eflag.cnt!=1 : continue vx=ex.cnt-x:if vx<0 : vx=-vx vy=ey.cnt-y:if vy<0 : vy=-vy if vx<48 : if vy<48 : eflag.cnt=2 : hit=1 loop return
が、全部のスクリプトです。

このうち

*my_move ; 自機の移動と表示 ; if mflag>0 : goto *my_end if a&256 : goto *my_mouse if a&2 : my=my-6 if a&8 : my=my+6 if a&1 : mx=mx-6 if a&4 : mx=mx+6 goto *my_check *my_mouse x=mousex-24:y=mousey-24 px = x - mx if px>6 : px=6 if px<-6 : px=-6 mx = mx + px py = y - my if py>6 : py=6 if py<-6 : py=-6 my = my + py *my_check if mx<0 : mx=0 if mx>mxlimit : mx=mxlimit if my<240 : my=240 if my>mylimit : my=mylimit pos mx,my:gmode 2,48,48:gcopy 3,0,0 return
の部分の
*my_mouseの部分が一行ごとに何をしているのかわかりませんでした。わかる方おられましたらご教授願います。
*my_checkも同様にわからなかったので、ご指導願えれば助かります。

コメントをつけてくださるのでも助かります。

よろしくお願いいたします。



この記事に返信する


あまら

リンク

2018/1/4(Thu) 14:07:50|NO.82159

画像ファイル及びサウンドファイルが無くて確認できないので、
推測レベルになります。


x=mousex-24:y=mousey-24 px = x - mx if px>6 : px=6 if px<-6 : px=-6 mx = mx + px

・マウス左上24ドットの座標を取得(移動先となる座標)

・現在の自機座標と移動先座標の2点の距離を算出
・もし2点の距離が6ドットよりも大きければ6にする
・もし2点の距離が-6ドットよりも小さければ-6にする
・現在の自機座標の位置を移動先座標に向かわせる

簡単に説明するとこのような感じになります。
6ドットが1フレームの最大移動速度となるようですね。


私ならこうするかなと少しだけ手を加えさせていただくと

#define move_speed 6 ; 自機移動速度の設定 ソースの初めの辺りで宣言 ;move_speed = 6 ; こっちでも可 ;************* 中略 **************** if a&2 : my=my-move_speed if a&8 : my=my+move_speed if a&1 : mx=mx-move_speed if a&4 : mx=mx+move_speed ;************* 中略 **************** px = x - mx if px>move_speed : px=move_speed if px<-move_speed : px=-move_speed mx = mx + px py = y - my if py>move_speed : py=move_speed if py<-move_speed : py=-move_speed my = my + py

こうすると後で速度を調整するときに一々全て書き変えなくても一括で変更できますし、
何らかのアイテムを使うと速度が速くなる遅くなるみたいな演出もやりやすくなります。



speed_alpha = 1 ; 通常速度 speed_alpha = 0.5 ; 減速する speed_alpha = 2 ; 加速する if a&2 : my=my-move_speed*speed_alpha ;******************** 以下同様 ***************************
こういう方法もあります。

変数名は自分でわかりやすい物に変えるのも理解するコツですよ。
安直ですが mx → jiki_pos_x とかなど。

それから変数の頭文字が p の変数は位置座標(pos)系だったり
パラメータの意味で(p, pr, prm, paramなどなど)一時的な計算に必要な変数として
使われている事が多いようです。



あまら

リンク

2018/1/4(Thu) 20:55:53|NO.82164

> *my_checkも同様にわからなかったので、ご指導願えれば助かります。
失礼。こちらの文を見逃していました。

*my_check if mx<0 : mx=0 if mx>mxlimit : mx=mxlimit if my<240 : my=240 if my>mylimit : my=mylimit pos mx,my:gmode 2,48,48:gcopy 3,0,0
こちらは様々なゲームでよく見るタイプの内容です。
やってることは単純に画面上で自機が移動できる範囲を設定しているだけです。

mx、myはそれぞれ自機の左上座標XYっぽいので

if mx<0 : mx=0
if mx>mxlimit : mx=mxlimit
X座標は画面内から出ないようにしているようです。
画面の外に行ってしまうと自機が表示されなくなって何もできなくなりますから。

0 <= mx <= mxlimit これが自機の横方向の移動可能範囲


if my<240 : my=240
if my>mylimit : my=mylimit
Y座標は理由は不明ですが画面のY座標0〜239には移動できないようにしているようです。
下は画面の一番下まで行ったらそれ以上の下に移動できないようにしています。

240 <= my <= mylimit こちらが自機の縦方向の移動可能範囲


pos mx,my:gmode 2,48,48:gcopy 3,0,0
これは説明するまでもなく自機の表示処理ですね。



おぼ

リンク

2018/1/5(Fri) 13:26:23|NO.82174

こんにちは。おぼです。

>>あまらさん

本当に丁寧な解説ありがとうございます。やはりわかっていないことを先延ばしにするのはよくないということがよくわかりました。

今後、また初歩的なことを質問するかもしれませんが、よろしくお願いいたします。

この度はありがとうございました。



ONION software Copyright 1997-2021(c) All rights reserved.