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


HSPTV!掲示板


未解決 解決 停止 削除要請

2017
0508
。。。シューティングゲームでの質問2未解決


。。。

リンク

2017/5/8(Mon) 15:41:54|NO.79600

まず、スクリプトを表示すると。

;shoot72.hsp
#define winx 50
#define winy 60
#define mm 8 ;間隔
#define xcls0 color 0, 0, 0 : boxf 0, 0, winx * mm - 1, winy * mm - 1
#define xcls1 color 0, 30, 50 : boxf winx * mm, 0


*hazimeno
screen 0,700,400,SCREEN_FIXEDSIZE
title "ゲーム"
redraw 0
color:boxf
color $00,$FF,$FF:font "HG明朝E",40:pos (600-50*11)/2,100:mes "シューティング"
button "スタート",*hazimeru
button "やらない",*yameruze
button "説明",*setumei
redraw 1
repeat
stick key
if(key & $10):break
if(key & $80):end
await 20
loop
*yameruze
end
*setumei
cls 4
color $00,$FF,$FF:font "HG明朝E",40:pos (600-50*11)/2,100: mes "↑=上に移動"
mes "↓=下に移動"
  mes "←=左に移動"
  mes "→=右に移動"

  mes  "LVが上がるほど難しくなります。"
  mes  ""
button "BACK",*hazimeno
redraw 1
repeat
await 20
loop
*hazimeru
cls
screen 0,700,400,SCREEN_FIXEDSIZE
title "ゲーム"
redraw 0
color:boxf
color $00,$FF,$FF:font "HG明朝E",40:pos (800-50*11)/2,100:mes "レベルセレクト"
button "LV1",*yeah

redraw 1
repeat
await 20
loop

*yeah
screen 0,600,400,SCREEN_FIXEDSIZE
title "とにかくシューティング"
redraw 0
color:boxf
color $00,$FF,$FF:font "HG明朝E",40:pos (600-50*11)/2,100:mes "とにかくシューティング"
color $FF,$FF,$FF:font "HG明朝E",16:pos (600- 8*15)/2,250:mes "スペースキーで開始"
color $FF,$FF,$FF:font "HG明朝E",16:pos (600- 8*15)/2,282:mes "[ESC]キーで終了"
 
redraw 1
repeat
stick key
if(key & $10):break
if(key & $80):end
await 20
loop
;初期設定 -----;配列宣言
teki = 10 ;敵機の数
dim tkx, teki : dim tky, teki ;敵機の座標
dim tkdx ,teki : dim tkdy, teki ;敵機の移動量
dim tkb, teki ;敵機の状態 0=あり、-1=なし
dim tkg, teki ;敵機の画像
tama = 10 ;自玉の数
dim jtx, tama : dim jty, tama ;自玉の座標
dim jtb, tama ;自玉の状態 0=あり、-1=なし
tama2 = 5 ;敵玉の数
dim ttx, tama2 : dim tty, tama2 ;敵玉の座標
dim ttb, tama2
;敵玉の状態 0=あり、-1=なし;画像読み込み
buffer 1
picload "shoot.bmp"
;メインウィンドウ
screen 0
gmode 2, 32, 32
title "スコア" ;タイトルバー設定
randomize ;乱数初期化
goto *hiscr_read ;ハイスコアー読み込み
*ret1
;スタート -----
*start
jiki = 3 ;自機残数
tokuten = 0
tkgg = 4 ;敵機画像番号
bossf = 0 ;ボスキャラフラグ(0:なし/1:移行/2:出現)
foreach tkb
tkg(cnt) = tkgg ;敵機画像番号1
loop
gosub *title_disp ;タイトル表示
gosub *jiki_disp ;自機残り表示
gosub *score_disp ;得点表示
gosub *hiscr_disp
;ハイスコアー表示;げーむMain -----
*restart
;ゲーム開始前の設定
foreach tkb
tkb(cnt) = -1 ;敵機状態、なし
loop
foreach jtb
jtb(cnt) = -1 ;自玉状態、なし
loop
foreach ttb
ttb(cnt) = -1 ;敵玉状態、なし
loop
jkx = 20 : jky = 55 ;自機の初期位置
jkb = 0 ;自機の状態 0=あり、-1=なし
gosub *restart_disp
tekib = 0 ;敵機爆破数
repeat
redraw 0
xcls0
if bossf != 2 {
;敵機の処理
gosub *teki_job
;自機移動
pos jkx * mm , jky * mm
gcopy 1, 0, 0
;キー入力
gosub *key_input
;自玉移動
gosub *tama_move
;敵玉移動
gosub *tama_move2
;敵玉と自機、自玉の当たり判定・消去・残機減算表示
gosub *atari3
;自玉と敵機の当たり判定・敵機消去・得点加算表示
gosub *atari1
;自機と敵機の当たり判定・自機消去・残機減算表示
gosub *atari2
} else {
;ボス機の処理
gosub *teki2_job
;自機移動
pos jkx * mm , jky * mm
gcopy 1, 0, 0
;キー入力
gosub *key_input
;自玉移動
gosub *tama_move
;敵玉移動
gosub *tama_move2
;敵玉と自機、自玉の当たり判定・消去・残機減算表示
gosub *atari3
;自玉と敵機の当たり判定・敵機消去・得点加算表示
gosub *atari4
;自機と敵機の当たり判定・自機消去・残機減算表示
gosub *atari2
}
if jkb = -1 : break ;自機状態なし
redraw 1
await 80
loop
;ゲームオーバー判定
if jiki > 0 : goto *restart ;自機の残数が0より大きいとき、げーむMainに移動
goto *hiscr_write ;ハイスコアー書き込み
*owari
gosub *hiscr_disp ;ハイスコアー表示
dialog "ゲーム・オーバーです。\nもう一度しますか。", 2, "シューティング・ゲーム"
if stat = 6 :goto *start
end


;-------------------------;----- Subroutine;自玉と敵機の当たり判定・敵機消去・得点加算表示 -----
;ボス機の処理 -----
*teki2_job
;敵機の数(配列の個数)だけ繰り返す;敵機初期位置・移動量設定
if tkb(0) = -1 {
tkx(0) = rnd(winx - 4) + 1 ;x座標
tky(0) = -4 ;y座標
tkdx(0) = 0 ;移動量x
tkdy(0) = 1 ;移動量y
tkb(0) = 0 ;敵機状態
tkg(0) = 3 ;敵機画像番号
bosscnt = 0 ;*****
}
;敵機移動
pos tkx(0) * mm , tky(0) * mm
gcopy 1, 32 * tkg(0), 0
;自機に向かわせる
tkr = rnd(20) ;乱数発生0〜19
if tkr = 0 { ;tkr=0
if jkx - tkx(0) > 0: tkdx(0) = 1
if jkx - tkx(0) < 0: tkdx(0) = -1
}
if tkr > 15 : tkdx(0) = 0 ;tkr=16,17,18,19
if tky(0) < 10 {
tkx(0) = tkx(0) + tkdx(0)
tky(0) = tky(0) + tkdy(0)
}
;ウィンドウ外
;if tky(0) >= winy : tkb(0) = -1 ;下枠
;if tkx(0) < 0 : tkb(0) = -1 ;左枠
;if tkx(0) > winx - 4 : tkb(0) = -1 ;右枠
;敵機爆破アニメーション
if tkb(0) >= 1 {
pos tkx(0) * mm , tky(0) * mm
gcopy 1, (4 - tkb(0)) * 32, 32
tkb(0) = tkb(0) - 1
if tkb(0) = 0 : tkb(0) = -1
}
;敵機玉発射             ←この部分
tr = rnd(20)
cnt1 = 0
if tr = 1 {
foreach ttb
if ttb(cnt) = -1 & tkb(cnt1) = 0{
ttx(cnt) = tkx(cnt1)
tty(cnt) = tky(cnt1)
ttb(cnt) = 0
break
}
loop
}
return
;自玉とボス機の当たり判定・ボス機消去・得点加算表示 -----
*atari4
foreach jtx ;自玉の個数分
cnt1 = cnt
if jtb(cnt) = -1 : continue
if tkb(0) = 0 & abs(tky(0) - jty(cnt1) + 1) <= 2 & abs(tkx(0) - jtx(cnt1) + 1) <= 2 {
jtb(cnt1) = -1 ;自玉消去
bosscnt = bosscnt + 1
if bosscnt > 20 {
tkb(0) = 3 ;敵機消去(爆破)
bossf = 0
}
tokuten = tokuten + 10 ;得点加算
gosub *score_disp ;得点表示
}
loop
return
*atari1
foreach jtx ;自玉の個数分
cnt1 = cnt
if jtb(cnt) = -1 : continue
foreach tkx ;敵機の個数分
if tkb(cnt) = 0 & abs(tky(cnt) - jty(cnt1) + 1) <= 2 & abs(tkx(cnt) - jtx(cnt1) + 1) <= 2 {
jtb(cnt1) = -1 ;自玉消去
tkb(cnt) = 3 ;敵機消去(爆破)
tekib = tekib + 1 ;敵機爆破数加算
if tekib = 100 {
jiki = jiki + 1 ;自機加算
if jiki > 5 : jiki = 5 ;自機数の制限
tekib = 0 ;敵機爆破数クリア
tkgg = tkgg \ 3 + 1 ;敵機画像変更
gosub *jiki_disp ;自機残り表示
}
tokuten = tokuten + 10 ;得点加算
gosub *score_disp ;得点表示
if tokuten = 100 : bossf = 1 ;*****
}
loop
loop
return
;自機と敵機の当たり判定・自機消去・残機減算表示 -----
*atari2
foreach tkx ;敵機の個数分
if tkb(cnt) = 0 & abs(jky - tky(cnt)) <= 2 & abs(jkx - tkx(cnt)) <= 2 {
;爆破アニメーション
redraw 1
pos jkx * mm , jky * mm
repeat 3, 1
gcopy 1, cnt * 32, 32
wait 50
loop
jkb = -1 ;自機状態なし 設定
jiki = jiki - 1 ;自機1減
gosub *jiki_disp ;自機残り表示
break
}
loop
return
;敵玉と自機、自玉の当たり判定・消去・残機減算表示 -----
*atari3
foreach ttb
;敵玉の個数分;敵玉と自機
if ttb(cnt) + jkb = 0 & abs(jky - tty(cnt) + 1) <= 2 & abs(jkx - ttx(cnt) + 1) <= 2 {
;爆破アニメーション
redraw 1
pos jkx * mm , jky * mm
repeat 3, 1
gcopy 1, cnt * 32, 32
wait 50
loop
jkb = -1 ;自機状態なし 設定
jiki = jiki - 1 ;自機1減
gosub *jiki_disp
break
}
;敵玉と自玉
cnt1 = cnt
foreach jtb ;自玉の個数分
if ttb(cnt1) + jtb(cnt) = 0 & abs(tty(cnt1) - jty(cnt)) <= 1 & abs(ttx(cnt1) - jtx(cnt)) <= 1 {
ttb(cnt1) = -1 ;敵機消去(爆破)
jtb(cnt) = -1 ;自玉消去
}
loop
loop
return
;自玉移動 -----
*tama_move
foreach jtx
if jtb(cnt) = 0 { ;自玉状態ありのとき
pos jtx(cnt) * mm, jty(cnt) * mm
gcopy 1, 0, 32, 16, 16
jty(cnt) = jty(cnt) - 1
if jty(cnt) = -2 : jtb(cnt) = -1 ;上の壁を越えたとき自玉状態なしに設定
}
loop
return
;敵玉移動 -----
*tama_move2
foreach ttb
if ttb(cnt) = 0 {
tty(cnt) = tty(cnt) + 2
pos ttx(cnt) * mm, tty(cnt) * mm
gcopy 1, 16, 32, 16, 16
if tty(cnt) >= winy : ttb(cnt) = -1
}
loop
return
;キー入力 -----
*key_input
stick kk, 15 ;キー入力情報
if kk & 128 : end ;[Esc]
if kk & 1 : jkx = jkx - 4 ;[←]
if kk & 2 : jky = jky - 4 ;[↑]
if kk & 4 : jkx = jkx + 4 ;[→]
if kk & 8 : jky = jky + 4 ;[↓]
 
jkx = limit(jkx, 0, winx - 4) ;左右の壁の制限
jky = limit(jky, 0, winy - 4) ;上下の壁の制限
if kk & 16 { ;[SPACE]
foreach jtx
if jtb(cnt) = -1 { ;自玉状態なしのとき
jtx(cnt) = jkx + 1 ;x座標
jty(cnt) = jky - 1 ;y座標
jtb(cnt) = 0 ;自玉状態、あり
break
}
loop
}
return
;敵機の処理 -----
*teki_job
tksum = 0 ;*****
foreach tkx
tksum = tksum - tkb(cnt) ;*****
if tksum = teki & bossf = 1 : bossf = 2
;敵機の数(配列の個数)だけ繰り返す;敵機初期位置・移動量設定
if tkb(cnt) = -1 & rnd(5) = 0 & bossf = 0{
tkx(cnt) = rnd(winx - 4) + 1 ;x座標
tky(cnt) = -4 ;y座標
tkdx(cnt) = 2 ;移動量x
tkdy(cnt) = 2 ;移動量y
tkb(cnt) = 0 ;敵機状態
tkg(cnt) = tkgg ;敵機画像番号
}
;敵機移動
if tkb(cnt) = 0 { ;敵機がありの時だけ移動処理をする
pos tkx(cnt) * mm , tky(cnt) * mm
gcopy 1, 32 * tkg(cnt), 0
;自機に向かわせる
tkr = rnd(20) ;乱数発生0〜19
if tkr = 0 { ;tkr=0
if jkx - tkx(cnt) > 0: tkdx(cnt) = 1
if jkx - tkx(cnt) < 0: tkdx(cnt) = -1
}
if tkr > 15 : tkdx(cnt) = 0 ;tkr=16,17,18,19
tkx(cnt) = tkx(cnt) + tkdx(cnt)
tky(cnt) = tky(cnt) + tkdy(cnt)
;ウィンドウ外
if tky(cnt) >= winy : tkb(cnt) = -1 ;下枠
if tkx(cnt) < 0 : tkb(cnt) = -1 ;左枠
if tkx(cnt) > winx - 4 : tkb(cnt) = -1 ;右枠
}
;敵機爆破アニメーション
if tkb(cnt) >= 1 {
pos tkx(cnt) * mm , tky(cnt) * mm
gcopy 1, (4 - tkb(cnt)) * 32, 32
tkb(cnt) = tkb(cnt) - 1
if tkb(cnt) = 0 : tkb(cnt) = -1
}
;敵機玉発射             ←この部分
tr = rnd(20)
cnt1 = cnt
if tr = 1 {
foreach ttb
if ttb(cnt) = -1 & tkb(cnt1) = 0{
ttx(cnt) = tkx(cnt1)
tty(cnt) = tky(cnt1)
ttb(cnt) = 0
break
}
loop
}
loop
return
;スタート表示 -----
*restart_disp
xcls0
font "MS ゴシック", 18, 1
color 200, 200, 200
pos 18 * mm, 28 * mm
mes "START"
wait 100
return
;タイトル表示 -----
*title_disp
xcls1 ;表示領域全消去
font "MS ゴシック", 18, 3 ;フォント設定
pos (winx + 1) * mm + 2, 1 * mm + 2
color 100, 100, 0
mes "" ;影
pos (winx + 1) * mm, 1 * mm
color 200, 200, 0
mes "スコア表示" ;本体
return
;自機残り表示 -----
*jiki_disp
if jiki <= 0 : return ;残り0なら戻る
color 0, 30, 50 ;表示領域の色
boxf (winx + 4) * mm, 55 * mm ;自機消去
repeat jiki - 1
pos (winx + 4 + cnt * 4) * mm, 55 * mm
gcopy 1, 0, 0
loop
return
;得点表示 -----
*score_disp
color 0, 30, 50 ;表示領域の色
boxf (winx + 2) * mm, 5 * mm, (winx + 28) * mm, 7 * mm ;スコアー消去
font "MS ゴシック", 18, 1 ;フォント設定
color 255, 0, 255 ;スコアーの文字色
pos (winx + 2) * mm, 5 * mm
mes strf("スコアー:%06d", tokuten)
return
;ハイスコアー表示 -----
*hiscr_disp
color 0, 30, 50 ;表示領域の色
boxf (winx + 2) * mm, 12 * mm, (winx + 28) * mm, 23 * mm ;ハイスコアー表示領域消去
font "MS ゴシック", 18, 1 ;フォント設定
color 255, 255, 255 ;ハイスコアーの文字色
pos (winx + 2) * mm, 12 * mm
repeat length(scr) - 1
mes strf("第%d位 ", cnt + 1) + strf("%06d ", scr(cnt)) + namae(cnt)
loop
return
;ハイスコアー書き込み -----
*hiscr_write
hiscr = "" ;メモリノートパッド用変数クリア
notesel hiscr ;メモリノートパッド設定
last = length(scr) - 1 ;配列最後の添字
if tokuten <= scr(last) : goto *owari
;得点と5番目の比較;文字列入力ダイアログ
screen 2, 200, 120, 8 ;ダイアログ用ウィンドウ
dat = ""
mes "名前を入力して下さい。"
pos 25, 32
input dat, 150 ;入力ボックス
pos 65, 64
button "OK", *ok ;ボタン
stop
*ok
gsel 2, -1 ;ID2非表示
gsel 0, 1 ;ID0アクティブ
scr(last) = tokuten ;得点を配列の最後に格納
namae(last) = dat ;名前を配列の最後に格納
gosub *sort ;ソート
foreach scr ;配列データをメモリノートパッドに追加
noteadd str(scr(cnt))
noteadd namae(cnt)
loop
notesave "block.txt" ;メモリノートパッド保存
noteunsel ;メモリノートパッド解放
goto *owari
*sort
repeat length(scr) - 1
d1 = cnt
repeat length(scr) - (d1 + 1), d1 + 1
if scr(d1) < scr(cnt){
ww = scr(d1) : sww = namae(d1)
scr(d1) = scr(cnt) : namae(d1) = namae(cnt)
scr(cnt) = ww : namae(cnt) = sww
}
loop
loop
return
;ハイスコアー読み込み -----
*hiscr_read
onerror gosub *hserr ;エラー処理
dim scr, 5 : sdim namae, 5 ;ハイスコアー用配列
hiscr = "" ;メモリノートパッド用変数クリア(文字型にする)
notesel hiscr ;メモリノートパッド設定
noteload "block.txt" ;メモリノートパッド読み込み
foreach scr
noteget sscr, cnt * 2 ;スコアー取り出し
noteget namae(cnt), cnt * 2 + 1 ;名前取り出し
scr(cnt) = int(sscr) ;スコアーを整数に変換
loop
noteunsel ;メモリノートパッド解放
goto *ret1 ;呼び出しの次行に戻る
*hserr
if wparam = 12 { ;ファイルがないエラー
foreach scr
noteadd "0"
noteadd "none"
loop
return
}
dialog "エラーです。終了します。" + wparam + "/" + lparam, 1

これに以下のことを行うためにはどのようなことを打つといいのか教えてください
詳しく説明してくれるとありがたいです。
:壁の表示(あたり判定あり)
:障害物の表示(写真を使わず、単色のもの あたり判定あり)
:敵機の倍増
:ボスを倒すとステージクリア
:ボスが弾を打つスピードを速くする。
;ボスを複数体表示
:ボスが打つを弾大きくする
長くなってすいません。



この記事に返信する


クロノス

リンク

2017/5/8(Mon) 20:27:01|NO.79606

>:壁の表示(あたり判定あり)
boxf命令で壁を作り、if命令で壁の座標の変数を使うのはどうでしょうか?
>:障害物の表示(写真を使わず、単色のもの あたり判定あり)
if命令で障害物の座標の変数を使うのはどうでしょうか?
>:ボスを倒すとステージクリア

;(sample01.hsp) bosslife = 100 //ボスの体力 gosub *getbosslife objsize 70,20 : pos 10,10 button gosub "ボスにダメージ",*bd stop //ボスにダメージ *bd bosslife = bosslife - 1 gosub *getbosslife if bosslife <= 0 { dialog "ステージクリア", 1, "ゲームクリア" end } return //ボスの体力を表示 *getbosslife title "ボスのHP:" + bosslife return
とりあえず抜いている部分はありますがどうでしょうか?^^



。。。

リンク

2017/5/10(Wed) 15:51:31|NO.79633

bosslife = 100 //ボスの体力

gosub *getbosslife
objsize 70,20 : pos 10,10
button gosub "ボスにダメージ",*bd
stop

ここの部分に時間制限を設け、その設定した時間を過ぎた場合、前の部分に
戻るようにするにはどうすればよいですか。



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