VBAテトリス 詳細編 SCORE等を計算する
どうもこんばんは。
エクセルのマクロでこんな感じのテトリスを作りました。
programminghajimetemita.hatenablog.com
今回もこのテトリスのコードについて解説していきます。
今回はブロックを消去したときにSCORE等を計算する処理に関するコードです。
1.テトリスの挙動
毎度のことですが、まずはテトリスの挙動について触れておきます。
私が参考にしたのはテトリスミニの挙動ですので、
以下の内容はそれを指しているものとご理解ください。
テトリスではブロックの揃った行を消去すると、
その行の数に応じてSCOREを計算し、
計算後のSCOREが画面に表示されます。
ブロックの消去により変動する要素は、
SCORE以外にもLINESとLEVELというものがあります。
LINESは消去した行数をカウントするものです。
4行消去⇒LINES=4、3行消去⇒LINES=7、といったように、
ブロックの揃った行が消去される度に、消去した行数が加算されていきます。
LEVELはLINESの値に応じて上昇する変数になります。
LINESが10増えるごとにLEVELが1増えていきます。
なお、このLEVELの値によってテトリミノの落下スピードが変わります。
上記2つの要素についても、SCOREと同様に、
消去のたびに計算が行われ、計算結果がゲーム画面に表示されます。
さて、再度SCOREの計算の話に戻ります。
消去した行数に応じ計算する、とは具体的にどんな計算をしているのかについてです。
SCOREは、一度に消去した行数と消去時のLEVELによって以下のとおり計算されます。
1行の場合:10×LEVEL
2行の場合:30×LEVEL
3行の場合:50×LEVEL
4行の場合:80×LEVEL
以上、SCORE等に関してのテトリスの挙動についてでした。
次はこれらをもとにどういう処理が必要になるかを考えます。
2.必要な処理
先ほど解説したテトリスの挙動を踏まえると、
必要な処理は大まかにわけて以下の2つです。
・値を計算する
・計算した値を画面に表示する
それぞれ詳しくみていきましょう。
・値を計算する
SCORE、LINES、LEVELのそれぞれの要素について、
一定のルールに従って値を計算する必要があります。
これは単純に変数を準備して計算してやればよいですね。
それぞれの計算ルールはテトリスの挙動で解説したとおりですが、
あらためて以下に記述しておきます。(ざっくりですが)
SCORE:消去した行数に応じた点数×LEVEL
LINES:消去した行数
LEVEL:消去した行数が10に達する度に1加算
なお、いずれの要素も累計値になりますので、
実際にコードを書く際には結果が累計値になるようにしておく必要がある点、
ご留意ください。
・画面に表示する
私が作ったテトリスの画面は以下のようなデザインになっています。
画面を見ていただいてわかるとおり、
各要素を表示する箇所がありますので、
ここに計算結果を表示すればOKです。
表示方法は簡単で、各要素が表示されているセルの値を、
計算後の変数の値に変更するのみです。
処理が明確になったところで次はコードの内容について考えましょう。
3.SCORE等を計算するコード
まず、計算に使用した変数を紹介します。
計算には4つの変数を使用しました。
score、tmp_line、line、levelの4つです。
変数の名前のとおりで、
scoreはSCOREの、lineはLINESの、levelはLEVELの計算を行う変数です。
いずれもゲーム開始から終了までの累計値を表すものになります。
残りのtmp_lineというのは、消去時の行数をカウントする変数になります。
SCOREは消去時の行数に応じて計算される要素ですので、
行数については累計値のみでなく、消去時の値も計算する必要があります。
そのためにこの変数が必要ということですね。
次に、各変数の値を計算するコードについてです。
scoreについてはテトリスの挙動で解説した計算式を使って値を計算します。
消去時の行数に応じて計算式が変わりますが、そこは条件分岐で対応すればOKです。
Select Case tmp_line
Case 1
score = score + 10 * level
Case 2
score = score + 30 * level
Case 3
score = score + 50 * level
Case 4
score = score + 80 * level
End Select
繰り返しになりますが、scoreは累計値とすべきものですので、
計算前のscoreに消去時に獲得するscoreを加算することで累計値としています。
LINESについては消去した行数の累計値を計算すればよいので、
コードは以下のようになります。
line = line + tmp_line
ちなみにtmp_lineはどのように計算しているかというと、
ブロックの消去の処理を行うときについでに計算しています。
前回の記事で、未消去の行を下に落とす、という処理を解説しましたが、
その中で計算を行っています。コードは以下のとおりです。
Application.ScreenUpdating = False
Application.Calculation = xlCalculationManual
For r = end_r To start_r Step -1
If checklinewhite(r) = True Then
tmp_line = tmp_line + 1
Range(Cells(start_r, leftedge_c), Cells(r - 1, rightedge_c))
.Copy Destination:=
Range(Cells(start_r + 1, leftedge_c), Cells(r, rightedge_c))
r = r + 1
End If
Next r
上記処理は消去行の数だけ処理が行われますので、
処理のたびに1加算すれば消した行数になるというわけです。
なお、tmp_lineの計算後、何も手を加えなければ、
計算結果が変数に残り続けてしまいますので、
ブロック消去の一番初めの処理として、
tmp_lineの値をゼロにするコードを入れています。
(tmp_line = 0)
さて、最後にLEVELの計算です。
LEVELは消去行数が10増えるごとに1増えていくものと解説しました。
LEVELは1からスタートしますので、
LINESが10になったらLEVELは2、20になったらLEVELは3という感じです。
また、LINESが1~9のときLEVELは1、11~19のときLEVELは2とも言えますね。
このように考えると、
LINESの値を10で割った値(少数点以下切り捨て)に1を足せば、
出したい値にすることができそうです。
例えば、
LINESが5の場合:5 ÷ 10 + 1
= 0.5 + 1
= 0 + 1 = 1
LINESが10の場合:10 ÷ 10 + 1
= 1 + 1 = 2
LINESが11の場合:11 ÷ 10 + 1
= 1.1 + 1
= 1 + 1 = 2
という感じで、思ったような結果になりましたね。
あとはこれをコード化すればよいわけです。
実際に作ったコードは以下の通りです。
level = Int(line / 10) + 1
Intを使えば計算結果が正の値であれば必ず小数点以下を切り捨ててくれます。
ワークシート関数のRoundDownを使っても可能かと思いますが、
こちらの方がコードの内容がすっきりしていてシンプルでわかりやすいと思ったので、
これを採用しました。
各要素を計算するコードの解説は以上です。
あとは画面に表示するコードですが、
セルの値を変数に格納された値とすればよいので、
表示したいセル.Value = 変数(score, line, level)でOKです。
ここまでのコードをまとめると以下のようになります。
Sub calculatescore()
'SCOREの計算
Select Case tmp_line
Case 1
score = score + 10 * level
Case 2
score = score + 30 * level
Case 3
score = score + 50 * level
Case 4
score = score + 80 * level
End Select
Cells(18, 21).Value = score
'LINESの計算
line = line + tmp_line
Cells(22, 21).Value = line
'LEVELの計算
level = Int(line / 10) + 1
Cells(13, 21).Value = level
End Sub
以上でコードの解説を終わります。
4.おわりに
今回はSCORE等を計算するコードについて解説しました。
これまでの内容と比べると簡単な内容だったかと思います。
次回の内容もそれほど難しくない内容ですので、
テトリス完成までもうひと踏ん張り頑張りましょう。
ではまた。