16:弾(たま)を当てるには

いよいよ敵てきをやっつけられるんだな!
じゃあいつものように。敵てきをやっつけるって、なにをすればいいのかな?
そんなのカンタンだぜ!敵てきにタマが当あたったら敵てきがブッこわれる!
じゃあ、敵てきに弾たまが当あたったらって、どうやったらわかるかな?
そんなのカンタンだぜ!敵てきにタマが・・・あれ?スマイルベーシックってそんな事こともわかんねーのかよ!
前回ぜんかいハカセが言いってたとおり、プログラミング言語げんごってのは命令めいれいした事ことしかしないんだ。そして敵てきに弾たまが当あたったかどうか調しらべる命令めいれいなんて存在そんざいしないし、そもそもどれが敵てきでどれが弾たまかなんて事ことも知しらない。全部ぜんぶプログラムしてあげなきゃダメなのさ。
ワタシは違ちがいますがネー!
出でやがったなダミー!
でやがったななんて人ひとをオバケのように言いっちゃだめでショートサカ頭あたま!アタシは人ひとでないですがネーHAHAHAハハハー
おいインテリ、こいつもプログラムなんだろう?なんでこんなにへらず口ぐちをたたけるんだ!
口くちは減へるもんじゃナイヨ。減へって足たりないのはオマエサンの脳味噌のうみそだヨ!
ダミーはAIエーアイだからねえ。直接ちょくせつこのしゃべり方かたをプログラムしたわけじゃなくて、たくさんのおしゃべりを学習がくしゅうしたら勝手かってにこんなしゃべり方かたになっちゃってこまってるんだよ・・・
インテリ、ドンマイ!悩なやみがあるなら相談そうだんにノルヨ!人生じんせい相談そうだんもいっぱい学習がくしゅうしたカラね!
ああ・・・
・・・
ともかく話はなしを先さきに進すすめよう。あらためて、敵てきに弾たまが当あたったらって、どうやったらわかるかな?
そんなのカンタンだぜ!当あたり判定はんていデスヨ!
アタリハンテイ?なんだそりゃ?
ああもう、答こたえを言いっちゃったし。そう、当あたり判定はんていっていうのを使つかうんだ。
当あたり判定はんていってのは、その名なの通とおり、当あたったかどうかを判定はんていするっていう意味いみだよ。
つまり、敵てきと弾たまが当あたったか当あたらないかを、その当あたり判定はんていっていうので判定はんていできるってこと?
そういうこと!
なんだよ、ベンリな物ものがあるんじゃねーか!ダミーお前まえ知しってんだろう?そいつを教おしえろよ!
いや知しらネー
なにい?
ワタシのプログラムには使つかわれてマセンし。当あたり判定はんてい大おおきすぎだこのクソゲー!とか当あたり判定はんていバグってるこのクソゲー!言いってる人ひとならネットにいまシタよ。
そんだけかよ!
ダミーが拾ひろってきたのは、ゲームの当あたり判定はんていが気きに入いらなくて文句もんく言いっている人達ひとたちの話はなしで、プログラミングとは無関係むかんけいだね。実際じっさいダミーのプログラムでは当あたり判定はんていは必要ひつようないから組くみ込こまれていないよ。
当あたり判定はんていっていうのはさきも言いった通とおり当あたったかどうかを判定はんていするっていうだけの意味いみで、判定はんていする方法ほうほうにはいろんな方法ほうほうがあるんだ。今回こんかいは一番いちばんカンタンな方法ほうほうを使つかおう。実じつはSmileBASICスマイルベーシックのスプライトはカンタンな当あたり判定はんていを行おこなう機能きのうが入はいっているんだ。
まずはSPCOLエスピーコル命令めいれい。これはスプライトに当あたり判定はんてい用ようの長方形ちょうほうけいを設定せっていする命令めいれいさ。設定せってい方法ほうほうは何種類なんしゅるいかあるけど、まずは一番いちばんカンタンなのを使つかおう。
スプライトの絵えと全まったく同おなじ場所ばしょ・大おおきさの長方形ちょうほうけいでいいなら、これだけでいいよ!

 SPCOL スプライトID

当あたりを判定はんていしたいスプライトには全部ぜんぶ設定せっていする必要ひつようがあるから注意ちゅういしてね。今回こんかいは敵てきと弾たま両方りょうほうだね。
あとは、例たとえば敵てきと弾たまの当あたりをチェックしたい時ときに、SPHITSPエスピーヒットエスピー関数かんすうを使つかえばOK!。当あたったら1、当あたっていなかったら0を返かえすんだ。

 IF SPHITSP(敵,弾)==1 THEN 当った時の処理

本当ほんとうはちゃんと数学的すうがくてきな基本きほんから覚おぼえといた方ほうがいいんだけど、ちょっと難むずかしいから説明せつめいは省略しょうりゃくするよ。ともかく、これでスプライト同士どうしが当あたったかどうかはチェックできるよ。
なんだよ、さんざん脅おどかしといていいモノがあるじゃねえか!
あとは当あたった時ときの処理しょりだね。当あたったらどうしたい?
そりゃあ爆発ばくはつだろう!ゲージュツ的てきに爆発ばくはつさせようぜ!
爆発ばくはつさせるのはまだちょっと難むずかしいかな。今回こんかいは音おとを出だして敵てきを消けすだけにしようか。
チェッ、つまらねえが今日きょうのところは勘弁かんべんしといてやるぜ。
スプライトを消けすのは、この前まえ使つかったSPCLRエスピークリア命令めいれいを使つかうよ。
音おとを出だすにはBEEPビープ命令めいれいを使つかうよ。BEEP 音おと番号ばんごうでいろんな音おとを鳴ならせるんだ。音おと番号ばんごうはスマイルツールで確認かくにんできるよ。
よし、それだけわかれば十分じゅうぶんだ!

・テキに当あたり判定はんていをつける
・テキがいるときだけテキを動うごかす
・SPHITSPでタマに当あたってるか調しらべて、当あたってたらテキとタマを消けす

って事ことだな。仕様しようもバッチリ。じゃあプログラムを書かくぜ!

 '---てき----------------------------
 'てきのかず
 ECOUNT=10
 'てきのざひょう
 DIM EX[ECOUNT]
 DIM EY[ECOUNT]
 'てきのそくど
 DIM EVX[ECOUNT]
 DIM EVY[ECOUNT]
 'てきのいどうじかん
 DIM ETIME[ECOUNT]
 'てきがいる?
 DIM ENEMY[ECOUNT]
 'てきのスプライトID
 DIM EID[ECOUNT]
 
 'てきざひょうしょきか
 FOR I=0 TO ECOUNT-1
  EX[I]=200
  EY[I]=60
 NEXT
 
 'てきのスプライトをつくる
 FOR I=0 TO ECOUNT-1
  EID[I]=100+I
  SPSET EID[I],1203
  SPOFS EID[I],EX[I],EY[I]
  SPCOL EID[I]:'てきにあたりはんていをつける
  ENEMY[I]=1 'てきがいるときは1に
 NEXT
 
 '---プレイヤー-------------------------
 'プレイヤーのざひょう
 PX=200
 PY=200
 'プレイヤーのスプライトID
 PID=10
 'プレイヤーのえのばんごう
 PPIC=3323
 'たまのスプライトID
 TID=20
 'たまのえのばんごう
 TPIC=3386
 'たまがある?
 TAMA=0
 
 'プレイヤーのスプライトをつくる
 SPSET PID,PPIC
 SPOFS PID,PX,PY
 
 '---メインループ-----------------------
 LOOP
  '---プレイヤーしょり----------------------
  'さゆうにうごかす
  IF BUTTON(1,#B_LLEFT)==1 THEN PX=PX-1
  IF BUTTON(1,#B_LRIGHT)==1 THEN PX=PX+1
  IF PX<0 THEN PX=0
  IF PX>400-16 THEN PX=400-16
  SPOFS PID,PX,PY
  'まずたまがないことをチェック
  IF TAMA==0 THEN
   'つぎにボタンをチェック
   IF BUTTON(1,#B_RRIGHT)==1 THEN
    'たまはっしゃ!
    'たまのざひょうはプレイヤーとおなじ!
    TX=PX:TY=PY
    SPSET TID,TPIC
    SPOFS TID,TX,TY
    SPCOL TID:'たまもあたるように!
    BEEP 111:'はっしゃおんもだすぜ!
    TAMA=1
   ENDIF
  ENDIF
  'たまがあるときだけ!
  IF TAMA==1 THEN
   'たまをうえにうごかす
   TY=TY-5
   SPOFS TID,TX,TY
   'たまががめんからとびでたか?
   IF TY<0 THEN
    TAMA=0
    SPCLR TID
   ENDIF
  ENDIF
 
  '---てきしょり-------------------------
  FOR I=0 TO ECOUNT-1
   IF ENEMY[I]==1 THEN
    IF ETIME[I]==0 THEN
     'うごくほうこうをきめる
     EVX[I]=RND(3)-1
     EVY[I]=RND(3)-1
     ETIME[I]=20
    ENDIF
 
    'てきをうごかす
    ETIME[I]=ETIME[I]-1
    EX[I]=EX[I]+EVX[I]
    EY[I]=EY[I]+EVY[I]
    SPOFS EID[I],EX[I],EY[I]
 
    IF SPHITSP(TID,EID[I]) THEN
     'あたった!
     BEEP 11:'ばくはつ!
     SPCLR EID[I]:'てきをけす
     ENEMY[I]=0:'てきがいなくなったので0にする
     SPCLR TID:'たまもけす
     TAMA=0
    ENDIF
   ENDIF
  NEXT
  VSYNC
 ENDLOOP

あんがいカンタンに書かけたな。いきおいで弾たまの発射音はっしゃおんもつけてやったぜ!
ワンパク君くん、カンペキだよ!敵てきに弾たまが当あたった時ときに、敵てきだけじゃなくちゃんと弾たまも消けしてるじゃないか。きっとそのまま飛とんで行いくだろうと思おもったのに。
ヒヒヒ。ほめても何なにも出でないぜ!
SmileBASICスマイルベーシックはゲームで良よく使つかうけど書かくのが大変たいへんな処理しょりをカンタンに書かける命令めいれいをいろいろ持もっているんだ。当あたり判定はんていもそのひとつだね。スプライトの絵えだけじゃなく音おともゲーム用ようの効果音こうかおんやBGMビージーエムをいっぱい持もっているよ。
なに?BGMビージーエムもならせるのか!せっかくだからなんかならそうぜ!
そうだね。じゃあスマイルツールを使つかって、鳴ならしたいBGMビージーエムを探さがしてみてよ
どれどれ・・・よし、40番ばんだ!もっとかっこいい曲きょくもあるけど、それはすげえラスボス用ようにとっておくぜ
OK!BGMビージーエムを鳴ならす方法ほうほうはカンタンだよ。BGMPLAYビージーエムプレイ 曲きょくの番号ばんごう で鳴ならせるんだ。
なるほどな、じゃあプログラムの一番最初いちばんさいしょにBGMPLAY 40と書かいて、実行じっこう!


おー!
音おとがつくと一気いっきに本物ほんもののゲームっぽくなるね!
そうだね!音おとってのはゲームを盛もり上あげるすごく大事だいじな要素ようそなんだ。だから中なかには音おとは一番いちばん最後さいごにつける人ひともいるんだよ。
盛もり上あげる大事だいじな要素ようそなら一番いちばん最初さいしょにつけといた方ほうがいいんじゃねえか?
ゲームが本当ほんとうにおもしろいかどうかが音おとでごまかされちゃうのを嫌きらうんだ。音おとがなくても本当ほんとうに面白おもしろいゲームは面白おもしろいからっていうリクツだね。
ふん、世よの中なかにはいろんなヤツがいるな。オレはもちろん最初さいしょから盛もり上あがる方ほうがいいぜ!
その考かんがえ方かたはワンパク君くんらしいのう!ところで、音おとで盛もり上あがっているが、なんかこう物足ものたりないところはないかのう。
なんだジジイ、人ひとの成果せいかにケチつけにきたのか?不満点ふまんてんなんてないぜ!並なみいる敵てきを連射れんしゃ連射れんしゃ・・・あれ、連射れんしゃがきかねえぞ?
まさに音おとでごまかされるとるのう。
くそっ、インテリ!どうすりゃ連射れんしゃできるんだ!
連射れんしゃかあ・・・敵てきを増ふやしたのとおなじような事ことを弾たまでもやればいいんだけど・・・
ムリムリー、大改造だいかいぞうじゃないデスカ。インテリさん、ニワトリみたいな頭あたまにはムリですヨー、3歩ぽアルいたら忘わすれちゃいマス。
うおー、ダミーてめえ!
IF文ぶんふたつつなげるだけで論理ろんり演算えんざんも使つかえないようなヤツにはムリムリー。じゃあサヨナラー。
うっ
うっ
インテリ!ジジイ!そのロンリーエンジンだかなんだかを教おしえろ!ギザギザ女おんなを見返みかえしてやるぜ!
うう・・・
うう・・・
二人ふたりそろって渋しぶい顔かおしてどうしたの?



今回のポイント

当たり判定

ゲーム内ないの物もの同士どうしが当あたったかどうかを調しらべる事ことを当あたり判定はんていと言いいます。また、ゲーム内ないの物ものに当あたり判定はんてい用ようの情報じょうほうを設定せっていする事ことを当あたり判定はんていをつけると言いったりします。
当あたり判定はんていの調しらべ方かたはいろいろな方法ほうほうがありますが、SmileBASICスマイルベーシックではAABBエーエービービー法ほう(軸じく平行へいこう境界きょうかいボックス法ほう)というシンプルな方法ほうほうを使つかった当あたり判定用はんていよう命令めいれいが用意よういされています。

SPCOL

スプライトに当あたり判定はんていを設定せっていする命令めいれいです。SPCOLエスピーコル スプライト番号ばんごうで指定していしたスプライトに絵えと同おなじ場所ばしょ・大おおきさの当あたり判定はんていを設定せっていする事ことができます。他ほかにも大おおきさや位置いちを自分じぶんでセットしたりする使つかい方かたもありますので、ヘルプを参照さんしょうして下ください。

SPHITSP

SPCOLエスピーコルで当あたり判定はんていを設定せっていしたスプライト同士どうしが当あたっているかどうかを返かえす関数かんすうです。SPHITSPエスピーヒットエスピー(スプライト番号ばんごうA,スプライト番号ばんごうB)で、スプライトAとスプライトBが当あたっているかどうかを調しらべる事ことができます。他ほかにも何通なんとおりかの使つかい方かたがあるので、ヘルプを参照さんしょうして下ください。

BEEP

効果音こうかおんを鳴ならす命令めいれいです。効果音こうかおんとは、弾たまを発射はっしゃしたり、ジャンプしたり、物ものが壊こわれたりといった時ときに鳴ならす音おとの事ことです。BEEPビープ 音番号おとばんごう で、指定していした音おとを鳴ならせます。音番号おとばんごうはスマイルツールで探さがす事ことができます。

BGMPLAY

BGMビージーエムを再生さいせいする命令めいれいです。BGMビージーエムはゲーム中なかに流ながれている音楽おんがくの事ことです。BGMPLAYビージーエムプレイ BGMビージーエム番号ばんごうで、指定していしたBGMビージーエムを再生さいせいできます。BGMビージーエム番号ばんごうはスマイルツールで探さがす事ことができます。

BGMSTOP

本編ほんぺんには出でてきませんが、BGMビージーエムを止とめる命令めいれいです。引数ひきすうなしのBGMSTOPビージーエムストップで現在げんざい流ながれているBGMビージーエムが止とまります。引数ひきすうを1個こつけると、流ながれているBGMビージーエムの音量おんりょうを徐々じょじょに小ちいさくして止とめる事ことができます(フェードアウトと言いいます)。ヘルプを参照さんしょうして下ください。

SNDSTOP

この命令めいれいも本編ほんぺんには出でてきませんが、覚おぼえておくと便利べんりな命令めいれいです。SNDSTOPサウンドストップ命令はその時再生ときさいせいされている音おとをすべて止とめます。BEEPビープやBGMPLAYビージーエムプレイでいろいろ試ためした時ときにBGMSTOPビージエムストップでも音おとが止とまらなくなる事ことがありますが、そのような時ときにもSNDSTOPサウンドストップはすべての音おとを止とめる事ことができます。

サンプルプログラムの公開キー

4QJS3EE83



やれやれ、次回じかいは論理ろんり演算えんざんか。ワンパク君くんも神崎かんざき君くんも、もちろん画面がめんの向むこうのキミも乗のり越こえられるといいんじゃがのう。
それはさておき、問題もんだいを出だすぞい!
その1:いろんな曲きょくをBGMビージーエムにしてプログラムを動うごかしてみるのじゃ!このゲームに合あわない曲きょくをつけるとびっくりするくらいおもしろくなくなるぞい。BGMビージーエムは大事だいじじゃのう。
その2:インテリ君くんが「敵てきに弾たまが当あたった時ときに、敵てきだけじゃなくちゃんと弾たまも消けしてるじゃないか。きっとそのまま飛とんで行いくだろうと思おもったのに。」と言いっておったのう?実際じっさい、敵てきに当あたった時ときに弾たまを消けさなかった場合ばあいどうなるかプログラムをいじって調しらべてみてくれい。いじるのは107行目ぎょうめと108行目ぎょうめあたりじゃなかろうかの!
今回こんかいは以上いじょうじゃ!