間違い探しゲーム
チュートリアルを始める前に
今回作るもの
25個の色ブロックの中から、違う色を見つけるゲーム。 シンプルだけど結構難しい間違い探しゲーム。
このチュートリアルの対象者
Processingの課題集1を終えた人
チュートリアルを始める前に必要な知識
- 変数
- 繰り返し処理(for)
- 条件分岐(if)
ではチュートリアル開始!
1) まずは基本の型
基本の型を書きます。
void setup(){ size(600, 400);}void draw(){ background(255);}
2) 黒いブロックを1つ描く
いきなり完成形を目指して作るのではなく、少しずつ作るのがコツです。
まずは黒いブロックを1つ描きましょう。
void setup(){ size(600, 400);}void draw(){ background(255); noStroke(); rectMode(CENTER); fill(0); rect(140, 80, 50, 50); // 左から140、上から80の場所に、四角形を描く。}
3) 黒いブロックを横に5個並べる
横80の間隔を空けて配置します。
void setup(){ size(600, 400);}void draw(){ background(255); noStroke(); rectMode(CENTER); fill(0); rect(140, 80, 50, 50); rect(140 + 80, 80, 50, 50); rect(140 + 80 * 2, 80, 50, 50); rect(140 + 80 * 3, 80, 50, 50); rect(140 + 80 * 4, 80, 50, 50);}
4) 繰り返し処理を使って横に5個描く
繰り返し処理(for)を使った書き方に直していきます。
void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 5; for(int i=0; i<loopCount; i++){ int x = 140 + 80 * i; fill(0); rect(x, 80, 50, 50); }}
5) 今度は縦に5個並べる
繰り返し処理を使って、縦に5個並べます。縦の間隔は60にします。
void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 5; for(int i=0; i<loopCount; i++){ int y = 80 + 60 * i; fill(0); rect(140, y, 50, 50); }}
6) 5x5のブロックを描く
横と縦の繰り返し処理を組み合わせて、25個のブロックを描きます。
void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 25; // 変更 for(int i=0; i<loopCount; i++){ int x = 140 + 80 * (i % 5); // 「%」を使ってiの値から「0〜4」の数値を作る int y = 80 + 60 * (i / 5); // 「/」を使ってiの値から「0〜4の数値を作る fill(0); rect(x, y, 50, 50); }}
7) 色をランダムにする
黒いブロックしか表示されていないため、色を変えます。
起動するたびに色がランダムになります。
float r;float g;float b;void setup(){ size(600, 400); // 色の要素「r, g, b」の値をランダムで作る r = random(255); g = random(255); b = random(255);}void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 25; for(int i=0; i<loopCount; i++){ int x = 140 + 80 * (i % 5); int y = 80 + 60 * (i / 5); fill(r, g, b); // ここを変えた rect(x, y, 50, 50); }}
8) 1個目のブロックだけ色を変える
透明度を指定して色を変えます。
透明度は「アルファチャンネル」と呼びます。
void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 25; for(int i=0; i<loopCount; i++){ int x = 140 + 80 * (i % 5); int y = 80 + 60 * (i / 5); fill(r, g, b); // 条件分岐(if)を使います。 if(i == 0){ fill(r, g, b, 255 / 2); // 透明度を半分に。 }else{ fill(r, g, b, 255); } rect(x, y, 50, 50); }}
9) 色が変わるブロックをランダムにする
色が変わるブロックをランダムにします。
どれくらいの透明度になるか、をランダムにします。
float r;float g;float b;float a; // アルファチャンネル用の変数を用意。int seikai; // 色が変わるブロックが何番目かの変数を用意。void setup(){ size(600, 400); r = random(255); g = random(255); b = random(255); // アルファチャンネルを100〜200の範囲でランダムにする a = random(100, 200); // 少し難しいですが、0〜24のランダムな「整数」を作っています seikai = (int)random(0, 25 - 1);}void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 25; for(int i=0; i<loopCount; i++){ int x = 140 + 80 * (i % 5); int y = 80 + 60 * (i / 5); fill(r, g, b); if(i == seikai){ fill(r, g, b, a); // アルファチャンネルを適用 }else{ fill(r, g, b, 255); } rect(x, y, 50, 50); }}
10) クリックされる度に、問題が変わるようにする
mousePressed()を使うと、クリックしたときの処理が書けます。
void mousePressed(){ r = random(255); g = random(255); b = random(255); a = random(100, 200); seikai = (int)random(0, 25 - 1);}
11) 同じ処理を1つにまとめる
クリックされた時の処理と、setupの処理、どちらも同じことをしている処理があることに気付きましたか?(ランダムの処理)
同じ処理は書かないようにしましょう。
DRY = Don’t Repeat Yourself。同じことを書かないのがプログラマの腕の見せ所です。
void setup(){ size(600, 400); shuffle(); // 定義した命令を呼び出す}void mousePressed(){ shuffle(); // 定義した命令を呼び出す}// 命令を定義する。ここでは「シャッフル」という名前の命令にしましたvoid shuffle(){ r = random(255); g = random(255); b = random(255); a = random(100, 200); seikai = (int)random(0, 25 - 1);}
12) 正解のブロックをクリックしたときだけ問題が変わるようにする
ブロックをクリックしたかは、ブロックの表示座標と、マウスの座標を比較します。
void mousePressed(){ int seikai_x = 140 + 80 * (seikai % 5); int seikai_y = 80 + 60 * (seikai / 5); // 横の位置を比較 if(mouseX > seikai_x - 25 && mouseX < seikai_x + 25){ // 縦の位置を比較 if(mouseY > seikai_y - 25 && mouseY < seikai_y + 25){ // 正解の処理 shuffle(); } }}
13) スコアを表示する(完成)
正解ごとにスコアが1増えるようにしましょう。
float r;float g;float b;float a;int seikai;int score; // スコア用の変数void setup(){ size(600, 400); shuffle();}void draw(){ background(255); noStroke(); rectMode(CENTER); int loopCount = 25; for(int i=0; i<loopCount; i++){ int x = 140 + 80 * (i % 5); int y = 80 + 60 * (i / 5); fill(r, g, b); if(i == seikai){ fill(r, g, b, a); }else{ fill(r, g, b, 255); } rect(x, y, 50, 50); } // スコアを表示する処理 fill(0); textSize(32); textAlign(CENTER); text(score, width/2, 40);}void mousePressed(){ int seikai_x = 140 + 80 * (seikai % 5); int seikai_y = 80 + 60 * (seikai / 5); if(mouseX > seikai_x - 25 && mouseX < seikai_x + 25){ if(mouseY > seikai_y - 25 && mouseY < seikai_y + 25){ // seikai score += 1; shuffle(); } }}void shuffle(){ r = random(255); g = random(255); b = random(255); a = random(100, 200); seikai = (int)random(0, 25 - 1);}
チュートリアル終了!
どうでしたか?無事に動いたでしょうか? 今回覚えたことを、きちんと身につけるようにしましょう。
もう一度自分一人だけで作ってみましょう。
もう一度、自分一人で作ってみてください。 チュートリアルを見ずに作って、理解を確実なものにしましょう。
それから、機能を追加して面白くしましょう。例えば、
- タイムトライアルモード
- 最初は簡単、だんだん難しくなるようにする
- ブロックの数を増やす
- BGMを入れてみる
- 間違えたときのペナルティを入れてみる
カスタマイズしたサンプルゲーム「ぬめ」
「め」を探そう。
このように自分でカスタマイズして、面白いオリジナルゲームにカスタマイズしてみましょう。