yuga のすべての投稿

第14回 – 配列 2

さて、前回に引き続きfor loopで配列を扱う方法です。
(と言っても前回は殆ど扱いませんでしたが)
では早速例を。

int[] x = new int[3];
int[] y = new int[3];

void setup() {
  size(800, 600, FX2D);

}

void draw() {

  background(0);

  for (int i = 0; i<3; i++) {

    ellipse(x[i], y[i], 5, 5);
    y[i] = y[i] + i+1;
    x[i] = x[i] + i+1;
  }
}

解説

まず、

int[] x = int[3];
int[] y = int[3];

の部分で配列を宣言しています。
int型の配列は変数と同じく、何も代入していなければ最初は全てに0が入っています。

そして、loopの中で、
変数 i を使ってx[0]〜x[2]を呼び出して、自分自身に1とiを足したものを、再び代入しています。
行数としては、ほんの少し短くなってる程度に見えますが、この3の部分を10にしてみましょう。

int[] x = new int[10];
int[] y = new int[10];

void setup() {
  size(800, 600, FX2D);

}

void draw() {

  background(0);

  for (int i = 0; i<10; i++) {

    ellipse(x[i], y[i], 5, 5);
    y[i] = y[i] + i+1;
    x[i] = x[i] + i+1;
  }
}

はい、たったこれだけで10倍です。
100にすれば100倍ですが、こんな風にすると数の変更が簡単です。

マジックナンバーの排除

int number = 10;
int[] x = new int[number];
int[] y = new int[number];

void setup() {
  size(800, 600, FX2D);
}

void draw() {

  background(0);

  for (int i = 0; i<number; i++) {

    ellipse(x[i], y[i], 5, 5);
    y[i] = y[i] + i+1;
    x[i] = x[i] + i+1;
  }
}

こうしておけば、

int number = 10;

の、numberに代入する数字を変更するだけで自動的に全ての円の個数に関係のある場所が変更されて便利です。
また、for loopを使う際に、

for(int i = 0;i<3;i++){ }

のような書き方をすると、この i<3の3が何のための数字だったのか、という事が後から見てわかりにくくなってしまいます。(こういう、実数値で書かれた何に使うのかよくわからない数値の事をマジックナンバーと呼んだりします)

for(int i = 0;i<number;i++){ }

こうしておけば、numberの回数だけ繰り返す、という事がわかります。

100や1000なんかの、for loopを使わなければ出来ないような(流石にコピペで作るのは大変ですから)ものも、少し数値を変更するだけで簡単に作ることが出来ます。

配列とfor loopの便利さがお分かりいただけたでしょうか。

第13回 – 配列 1

さて、今回から配列を紹介していきますが、その前に変数をおさらいしておきましょう。
processingにおいて変数は、値を格納しておける箱のようなものでした。
図形の場所や大きさに変数を用いる事によって、その変数の値を変える(別の値を代入する)だけで図形が変化して見える(=アニメーションして見える)、数値に名前をつけて可読性を高める、同じ変数を複数の場所で利用する事で、後から値をまとめて変更出来る、など、様々な利用方法があります。
しかし、この変数をfor loopと組み合わせて使いたくなった時に、少し不具合が生じます。
例えば、for loopを利用して円を100回描いて、しかもそれをそれぞれアニメーションさせたい、という場合どうしたら良いでしょうか?
いきなり100個はちょっと想像するのが難しいので、試しに3個でやってみましょう。

  
int x1;
int y1;
int x2;
int y2;
int x3;
int y3;
  void setup(){
  size(800, 600); 
}

void draw(){
  
  for(int i = 0;i<3;i++){
    
    ellipse(x1, y1, 50, 50);
    ellipse(x2, y2, 50, 50);
    ellipse(x3, y3, 50, 50);
   
    
    x1 = x1 + 1;
    x2 = x2 + 2;
    x3 = x3 + 3;
    
    y1 = y1 + 1;
    y2 = y2 + 2;
    y3 = y3 + 3;
     //.....あれ?
  }
}

困ってしまいました。
これではfor loopを使う意味がありません。
試しにこのコードをご自分のprocessingにコピペして実行してみた後、for loop { }を削除して以下のコードに書き換えてから実行してみてください。

int x1;
int y1;
int x2;
int y2;
int x3;
int y3;

void setup() {
  size(800, 600);
}

void draw() {

  background(0);

  ellipse(x1, y1, 50, 50);
  ellipse(x2, y2, 50, 50);
  ellipse(x3, y3, 50, 50);

  x1 = x1 + 1;
  x2 = x2 + 2;
  x3 = x3 + 3;

  y1 = y1 + 1;
  y2 = y2 + 2;
  y3 = y3 + 3;
}

そうです、玉の数は3つのまま何も変わらず、スピードだけが3倍になっています。

どうしてこんな事が起きたのでしょうか?

…と、説明するまでもなく、ellipseが3つも書いてあるのだから、そりゃfor loopなんかなくても円は3つ描かれます。
つまり、forがあった時には円は9個描かれていたわけです。単に完全に重なってて見えてなかっただけで。
スピードが3倍になっていたのは、 x1 = x1 + 1;の部分が3回実行されていたからでした。(合計3回1が足されて、スピードが3倍になったのですね。)

この事からもわかるように、3種類の変数を使って、円をその変数と同じ数だけ書く、ということは、for loopには出来ないのです。

では、どうすれば良いのでしょうか?

そう。ここで配列です。

配列を使おう!

配列は、1つの変数(名前)に沢山の値を格納できるものです。
少し解りにくいので喩え話をします。

Aという箱があります。箱にはint型の値を1つ格納出来ます。←これが変数
Aという棚があります。この棚には10段仕切りが付いていて、何段目に入れるかを指定する事で、int型の値を10個格納出来ます。←これが配列

配列にいくつ値を格納できるようにするかは、名前をつける時に同時に宣言します。
int型の、xという名前の変数を宣言する方法が

int x = 0;

だったのに対し、int型の値が10個格納できるxという名前の配列を宣言するには

int[] x = new int[10];

のようにします。

普通の変数との違いは型の指定 int の後に []が付くことと、必ず = new int[10] と、new キーワード、改めて型、そして中に入れたい数の指定が必ず必要です。
100個値を入れたいなら int[100]となります。

名前が1つなのに、どうやって沢山の値を扱うの?

配列として宣言された変数は、名前だけで値を出し入れすることは出来ません。
その配列の何番目の値にアクセスしたいか、というのを必ず指定する必要があります。
そして、指定は配列の名前の後に [ ]  を付けて行います。

int[] x = new int[10];

void setup(){

  size(800,600);
  
 // x = 10; ←何番に入れるか指定していないのでエラーになる
  x[0] = 10;//←エラーにならない
  x[1] = 20;//←エラーにならない
  x[10] = 10;//←x[9]までしか存在しないのでエラーになる

}

ちなみに、配列の1番目の値は0から始まります。
少しややこしいので、慣れるまでは一呼吸置いてください。

int[] x = new int[10]
という配列なら、 x[0]〜x[9]までの10個が確保されます。
宣言時は10なので、x[10]もありそうですが存在しません。
そして、存在しないナンバーにアクセスしようとすると、プログラムはエラーを起こして動作を停止します。
必ず、存在しない値を指定していないか確認しましょう。

少し長くなりましたが今回はここまで、次回は実際にfor loopで配列を使ってみましょう。

第12回 – for loop(繰り返し処理) 4

前回はfor loopの中で変数 i を使って、randomよりももう少し規則性のある繰り返しを作ってみました。

今回は、さらにそのfor loopの中で分岐を使って、もう少し複雑な規則性を持たせたいと思います。

for loopの中で ifを使うと…どうなる?

void setup() {

  size(550, 400);
  background(0);

  for (int i = 0; i<10; i++) {

    if (i < 5) {
      fill(255,0,0);
      ellipse(i * 50 + 50, height/2, 40, 40);
    } else {
      fill(0,255,0);
      ellipse(i * 50 + 50, height/2, 40, 40);
    }
  }
}

さて、このコードは、iが5より小さい時には
fill(255, 0, 0)
を実行し、
そうでない時(else)は、
fill(0, 255, 0)
を使う、というものです。

実行結果はこんな感じ。
sketch_160819b

繰り返しの回数が一定より多い時に色が変わっていることが判ります。

これはもちろん色を変えたい時だけではなく、大きさを変えたい時や、場所を変えたい時などにも利用出来ます。

もう1例見てみましょう。

void setup() {

  size(550, 400);
  background(0);

  for (int i = 0; i<10; i++) {

    if (i % 2 == 0) {
      fill(255,0,0);
      ellipse(i * 50 + 50, height/2, 40, 40);
    } else {
      fill(0,255,0);
      ellipse(i * 50 + 50, height/2, 40, 40);
    }
  }
}

%は、前の数を後の数で割って、その余りを求めるという演算子です。
この場合だと、2で割った時の余りが0になる、つまり割り切れる時、という指定になります。
2で割り切る事が出来る…つまり、偶数ですね。

実行結果はこのようになります。

sketch_160819b

for loopでif文を使う時には、この i という変数がそのループの回数(何回目か)を表している、というところに着目すると、色々な使い方が出来るのでおすすめです。

もちろん、今後出てくる配列やリストなどを用いて、もっと複雑な表現をすることも可能です。
しかし、現段階ではこの i に注目する思考法にトライしてください。

さて、一旦if文はこれで終わりですが、今後もif文は沢山出てくるので、しっかり復習しておいてください。
では!

第11回 – for loop(繰り返し処理) 3

さて、前回はrandomとforを使って、大量の円を画面いっぱいに描く、というのをやりました。

しかし、聡明なる読者の皆さまのことでありますから、こう思ったに違いありません。

「あれ?このforとかいうやつ、ランダムに描く時にしか使えない事ない……???」

そんなことはありません。forを使って任意の位置に円を沢山描く方法はいくつか存在します。
いくつか存在しますが、今回はそのうちの一つ、変数 i を使う方法をご紹介します。
今後「配列」や「動的配列」、「class」などを学習すれば、さらにfor loopの使い方は広がるのですが、今回はその最初の一歩です。

for loopの変数 i を使って円を並べよう

では、さっそく具体的な方法を見ていきましょう。

void setup(){

  size(600, 600);
  background(0);
  
  for(int i = 0;i<10;i++){
    
    ellipse(i*50,100, 50, 50);
  }

}

 

sketch_160809a_と_Update

最もシンプルなのがこの形です。

左端の円が半分はみ出していますが、円そのものは綺麗に横に並んでいます。

何が起こっているのか少し解りにくいので、for loop内で起こっていることを順番に書いてみます。

//1周目
void setup(){

  size(600, 600);
  background(0);
  
  for(int i = 0;i<10;i++){
    
    ellipse(i*50,100, 50, 50); 
    //1周目は、iが0なので、実際には
    // ellipse(0*50,100, 50, 50)が実行される
    //*は✕(かける)と同じ意味なので、0✕50が行われて、0になる。
    //つまり、1周めに実行されるのは
    // ellipse(0,100, 50, 50)という命令
  }

}
 
//2周目
void setup(){

  size(600, 600);
  background(0);
  
  for(int i = 0;i<10;i++){
    
    ellipse(i*50,100, 50, 50); 
    //2周目は、iが1なので、実際には
    // ellipse(1*50,100, 50, 50)が実行される
    //*は✕(かける)と同じ意味なので、1✕50が行われて、50になる。
    //つまり、2周めに実行されるのは
    // ellipse(50,100, 50, 50)という命令
  }

}
 
//3周目
void setup(){

  size(600, 600);
  background(0);
  
  for(int i = 0;i<10;i++){
    
    ellipse(i*50,100, 50, 50); 
    //3周目は、iが2なので、実際には
    // ellipse(2*50,100, 50, 50)が実行される
    //*は✕(かける)と同じ意味なので、2✕50が行われて、100になる。
    //つまり、2周めに実行されるのは
    // ellipse(100,100, 50, 50)という命令
  }

}

…という風に、iが0〜9になるまで実行されます。
0〜10ではないのは、指定が

i<10

10より小さいだからです。
この指定の部分を、 i <= 10 にすれば、0〜10まで合計11回実行されます。 が、10と書いてあるのに11回実行されてしまい、少し解りにくいので、常に iと指定回数の間は < と書くようにした方が良いでしょう。 しかし、この方法では円が半分表示されなくなってしまっています。 そこで、円を全体的に右側にずらしてやる必要があります。

方法はいくつかありますが、最も単純なのはこのような方法でしょう。

void setup(){

  size(600, 600);
  background(0);
  
  for(int i = 0;i<10;i++){
    
    ellipse(i*50 + 100,100, 50, 50); 
    
    //i * 50の後の + 100 で、全ての円の位置を100だけ右にずらす
    //四則演算は、 *(かける)や/(割る)が実行された後に +(足す) や -(引く)が実行されます。
    //普通の算数のルールと一緒ですね!
  }

}

他にも、

	for(int i = 1;i<=11;i++){
	ellipse(i*50 + 100,100, 50, 50); 
}

という風に、iを最初0でない値から始めるという方法があります。

この方法は一見とても正しいように見えますが、実はあまり使わないほうが良いです。
理由は「配列のindexが0から始まるから」なのですが、また配列を紹介する時に説明します。
今は「iを0から始める方法は採用しない方が無難」とだけ覚えておいてください。

少し長くなってしまいましたが今回はここまで。
次回はfor loopの中で条件分岐をする、をやります!
ただの組み合わせですが、重要なテクニックです。

それでは!

第10回 – for loop(繰り返し処理) 2

今回は具体的なfor loopの使用例を見ていきましょう。

例えば、画面のランダムな位置に10個の円を描きたい場合、通常であればこんな風に10回、円を描け!と命令する必要があります。

void setup(){

	size(800, 800);
	background(0);
	ellipse(random(width), random(height), 50, 50);//1個目
	ellipse(random(width), random(height), 50, 50);//2個目
	ellipse(random(width), random(height), 50, 50);//3個目
	ellipse(random(width), random(height), 50, 50);//4個目
	ellipse(random(width), random(height), 50, 50);//5個目
	ellipse(random(width), random(height), 50, 50);//6個目
	ellipse(random(width), random(height), 50, 50);//7個目
	ellipse(random(width), random(height), 50, 50);//8個目
	ellipse(random(width), random(height), 50, 50);//9個目
	ellipse(random(width), random(height), 50, 50);//10個目
}

確かにこの方法でも書けますし、ただコピペするだけなのでそれほど難しくもないでしょう。(実際このプログラムは動くので、processingに貼り付けて実行してみてください。)
ですが、これが100個だったら?1000個だったら?コピペします?マジで?

そうです、こういう時にfor loopを使うのです。

void setup(){

  size(600, 600);
  background(0);
  
  for(int i = 0;i<1000;i++){
    
    ellipse(random(width), random(height), 50, 50);//1〜1000個目
  }

}

前回お伝えした通り、この i < 1000の部分が、繰り返す回数を規定しています。 今回はガッと一気に1000個の円が描かれたはずです。 カブりまくってちゃんと1000個描かれているか確認しづらいかも知れませんが…。 ちなみに、widthやrandomが何なのか思い出せない方は、もう一度この記事を読んで戻ってきましょう! 第6回 – IF(条件分岐)3

問題

問題1.

1000個描かれている円の数を、500個に変更しなさい。

問題2.

円のサイズを半分にしなさい。

第9回 – for loop(繰り返し処理) 1

 プログラミングで映像を制御する大きな魅力の1つは、手で書き込んだりしていたのではとても間に合わないような量の図形を簡単に扱うことが出来る、という点にあります。
 そして、それを実現するのが繰り返し処理で、今回から数回かけて繰り返し処理の最も初歩的な構文である「for loop」について学んでいきます。
 

for loopって?

for loopは、指定した範囲を何度も繰り返し実行するための構文です。
具体的には

for(int i = 0;i<100;i++){


}

のように書きます。
すると、{ }の間が、今回の場合は100回繰り返して実行されます。

もう少し具体的に、このfor loopがどのような仕組みになっているかを説明します。

for(条件の初期状態の指定, 繰り返し条件, 繰り返される毎に行われる処理){
 繰り返し実行したい内容
}

まず、この「条件の初期状態の指定」の部分で、「条件に使うための変数」を宣言します。
例では
int i = 0;
となっていますが、実際にfor loopの条件としてint型のiという名前の変数が使われることが多いようです。

次に、「繰り返し条件」ですがここが trueの間はこの{ と } の間が延々ループされます。
この条件の部分に

true

などと書こうものなら、無限ループに陥ってしまいます。

for(int i = 0;true;i++){
こう書くと無限ループ(プログラムがクラッシュして強制終了される)
}

色々なループ条件を指定することも出来ますが、例のように

i < 100

などと、「最初の部分で宣言した変数の値がxxより小さい場合」のように指定する事が一般的です。

for(int i = 0;i<100;i++){
こう書くと、この部分が100回繰り返される
}

最後に、「繰り返される毎に行われうる処理」のところに

i++

と書いてありますが、これは 「iに1を足せ」という意味です。

i = i + 1;

と書くのと全く同じですが、この処理は色々なシーンで多用されるので、短く書けるように ++という特別なキーワードが用意されています。(インクリメントと呼びます)

慣れるまでは、とりあえず繰り返したい回数を i < x のxの場所に書いた

for(int i = 0;i<100;i++){
こう書くと100回
}

for(int i = 0;i<1000;i++){
こう書くと1000回
}

for(int i = 0;i<5;i++){
こう書くと5回、この中が繰り返される
}

この形式をそのまま使ってしまって良いと思います。
直接値を書くパターン以外に.lengthを使うパターンや、動的配列でremoveを使うために逆回転させる場合や、拡張for文を使う場合など色々な例外が今後出てきますが、今は気にしないことにしましょう。

次回は、for loopの具体的な使い方をいくつか見ていきたいと思います。

第8回 – IF(条件分岐)5

float x = 0;
float y = 0;

void setup() {

  size(800, 800);
}


void draw() {
  background(0);
  fill(255);
  rect(width/2, height/2, 300, 300);
  fill(255);
  if (width/2 < x & width/2 + 300 > x & height/2 < y & height/2 + 300 > y) {
    fill(255,0,0);
  }
  ellipse(x, y, 20, 20);

  y = y + 10;

  if (y > height) {

    y = 0;
    x = random(width);
  }
}

さて、前回のコードはこんな感じでした。
このプログラムは、if文の中に
fill(255,0,0);
を入れる事によって、条件に合致する場合のみ、ifの前に実行されている
fill(255);
の効果を上書きする事によって色を変化させていました。

elseを使う

しかし、もし四角形の中でのみ、円の大きさを変化させたい、という場合には(変数を新たに用意する、という方法もありますが)、elseというifの対になっている構文を使うのが便利です。

float x = 0;
float y = 0;

void setup() {

  size(800, 800);
}


void draw() {
  background(0);
  fill(255);
  rect(width/2, height/2, 300, 300);
  fill(255);
  if (width/2 < x & width/2 + 300 > x & height/2 < y & height/2 + 300 > y) {
    fill(255,0,0);
     ellipse(x, y, 50, 50);
  } else {
  
   ellipse(x, y, 20, 20);
  }
 

  y = y + 10;

  if (y > height) {

    y = 0;
    x = random(width);
  }
}

実装はこんな感じ。
sketch_160730a_と_新規投稿を追加_‹_作曲家のためのプログラミング入門_—_WordPress

elseは、もしif文の条件式に当てはまらなかった場合にはこちらを実行しなさい、という意味です。
なので、ifの後のブロックか、elseの後のブロックのどちらかが必ず実行されます。

さらに、elseの後にifで他の条件式を加える
else if()
という構文も存在します。

else ifはif文の後に複数付けることが出来、しかもどの条件にも当てはまらなかった場合には何も実行されない、という可能性も残しています。

float x = 0;
float y = 0;

void setup() {

  size(800, 800);
}


void draw() {
  background(0);
  fill(255);
  rect(width/2, height/2, 300, 300);
  fill(255);
  if (width/2 < x & width/2 + 300 > x & height/2 < y & height/2 + 300 > y) {
    fill(255, 0, 0);
    ellipse(x, y, 50, 50);
  } else if ( y < height/2 ) {
    ellipse(x, y, 5, 5);
  } else {
    ellipse(x, y, 20, 20);
  }


  y = y + 10;

  if (y > height) {

    y = 0;
    x = random(width);
  }
}

この例では、画面の上半分に玉がある場合にはサイズを5に、半分以下なら20に、そして四角形の中ならば50にしています。
もし最後のelse{ }がなければ、玉が下半分に来た時に消えて(描画されなくなって)しまいます。

問題

最後のelse { }を、elseキーワードごと消して、ボールが下半分に来た時に消えてしまう事を確認せよ。
そして、消えてしまう理由について考えなさい。

第7回 – IF(条件分岐)4

引き続き条件分岐です。
前回の

float x = 0;
float y = 0;
 
void setup() {
 
  size(800, 800);
}
 
 
void draw() {
  background(0);
  fill(255);
  rect(width/2, height/2, 300, 300);
  fill(255);
  ellipse(x, y, 20, 20);
 
  y = y + 10;
 
  if (y > height) {
 
    y = 0;
    x = random(width);
  }
}

このプログラムに、どうしたら「四角形の中だけ円が赤になる」という機能を付けることが出来るか、というお話でした。

そのためには、if()の条件式の中に、 & を使う必要があります。

そもそも、「四角形の中」とはどういう状態でしょうか?

現在この四角形は、rectという命令によって描かれていて、
rect(width/2, height/2, 300, 300);
という値が指定されています。
これはつまり、
「四角形の左上の点は、ウインドウサイズの横幅の半分の位置、且つウインドウサイズ縦幅の半分の位置で、そこから右に300、下に300の大きさを持っている」
という事を意味します。

その「中」はつまり、
「ウインドウサイズの横幅の半分よりも右」 且つ 「ウインドウサイズの横幅の半分に300足した位置よりも左側」 で
「ウインドウサイズの縦幅の半分よりも下」 且つ 「ウインドウサイズの縦幅の半分に300足した位置よりも上側」
である、という事です。
なんとなくかなりややこしいですが、図を描いて考えてみればわかりやすいかと思います。

sketch_160730a_と_sketch_160730a___Processing_3_1_1

この、
「ウインドウサイズの横幅の半分よりも右」 且つ 「ウインドウサイズの横幅の半分に300足した位置よりも左側」 で
「ウインドウサイズの縦幅の半分よりも下」 且つ 「ウインドウサイズの縦幅の半分に300足した位置よりも上側」
を、ifの条件文に直すと

if (width/2 < x & width/2 + 300 > x & height/2 < y & height/2 + 300 > y) {


}

となります。
(理解できるまで何度も読んでみてください)

で、このifのブロックの中に、fill(255,0,0);を入れてあげれば良いのです。

完成品はこちら。

float x = 0;
float y = 0;

void setup() {

  size(800, 800);
}


void draw() {
  background(0);
  fill(255);
  rect(width/2, height/2, 300, 300);
  fill(255);
  if (width/2 < x & width/2 + 300 > x & height/2 < y & height/2 + 300 > y) {
    fill(255,0,0);
  }
  ellipse(x, y, 20, 20);

  y = y + 10;

  if (y > height) {

    y = 0;
    x = random(width);
  }
}

今回の場合には、fill()が、「出現以降全ての図形を書く命令に影響を与える」というグローバルな効果を持っているため、このような実装が可能でしたが、他の…例えば、四角形の中だけ円のサイズを変えたい、などの場合には else 「さもなくば」という構文を組み込んであげる必要があります。

elseについては次回。
条件分岐について沢山見てきましたが、次回で最後です。

第6回 – IF(条件分岐)3

条件分岐の3回目です。

 条件分岐の2回目は、 | 「もしくは」を導入することによって全く同じ処理が行われる場合には1つにまとめる事で書かなければいけないコードの数を減らす、という内容でした。
今回は、 & 「かつ」 を導入することによって、より条件を絞っていく方法について書こうと思います。

例1

float x = 0;
float y = 0;

void setup() {

  size(800, 800);
}


void draw() {
  background(0);
  fill(255);
  rect(width/2, height/2, 300, 300);
  fill(255);
  ellipse(x, y, 20, 20);

  y = y + 10;

  if (y > height) {

    y = 0;
    x = random(width);
  }
}

まず、このコードをご自身のエディタに書き写して実行してみてください。
コピーしても構いませんが、手で写すとより効果的です。
sketch_160730a_と_sketch_160730a___Processing_3_1_1

こんな画面になったと思います。
上から円が落ちてきて、一番下まで行くと、また一番上に戻る、という感じです。

新しく、
width
height
rect
random
fill
の5つの見慣れない文字列が出てきていますので、まず解説します。

新出命令

width

widthは、size();の中で指定した横幅が、自動的に代入されている定数です。
size(800,800)と指定しているので、widthは 800と書いているのと同値です。
800と書けばいいじゃないか、と思うかも知れませんが、widthを使う利点は2つあります。
1つは、後から見た時に可読性(理解しやすさ)が格段に向上することです。
ひと目で「あ、ウインドウサイズの横幅と同じなんだ」という事が判ります。これはとても大切なことです。
もう1つは、何らかの事情でsize()の中の数字を後から変更した場合や、fullScreenで実行して環境によって画面サイズが変わっても、自動的にこの中の数字が書き換わってくれるので手でいちいち対応しなくても良い、という点です。
これは、ウインドウサイズを使う箇所が100箇所などになってくると、とても効果的です。
ウインドウサイズを指定したい場合には必ずwidthを使うようにしましょう。

height

これはwidthの縦幅バージョンです。

rect

これは、四角形を描け、というメソッドです。
rect(四角形の左上のx座標の位置, 四角形の左上のy座標の位置,横幅,縦幅)
という風に指定すると、四角形を描いてくれます。
x座標の位置とか、y座標の位置とか解りづらいので、
左からの距離、上からの距離、と読み替えて理解すると良いかもしれません。

random

これは前々回の例題でも少し出てきましたが、
random(上限の値)
としてやると、0 〜上限の値 – 1までの数がランダムに返ってきます。
例えば、

 float n = random(100);

とした場合、nには0.0〜99.0までのランダムな値が入ります。
小数点付の数値が返ってくるため、int型の変数に代入しようとするとエラーが出ます。
float型を使うようにしましょう。(int型にキャストする方法もありますが、それはまたのちほど紹介します)

fill

これは、中に0〜255段階の明るさを指定する事によって、
この命令以降に出てくる全ての図形を、指定した明るさで塗りつぶす、というメソッドです。
以降、ですので、例えコードの一番下に書いてあったとしても、次のフレームの別のfill()メソッドが出てくるまでは有効です。
また、r g bそれぞれの値を指定してやることによって、好きな色で塗りつぶすことも出来ます。
その場合、
fill(255,0,0)
のように、数字を3つ指定する事になります。
それぞれ0から255までの数値で、左から
fill(赤味、緑味、青味);
です。全て255だと白、全て0だと黒になります。

メソッド?

さっきから自然にメソッドという名前で呼んでいますが、processingでは 名前() で終わるものをメソッドと呼びます。
()の中に指定する数字を引数(ひきすう)と呼び、入れた値によって効果を変化させる事が出来ます。
また、メソッドは自分で作ることも出来ます(これはまたのちほど紹介します。)

  
y = y + 10;

  if (y > height) {

    y = 0;
    x = random(width);
  }
  

つまり、この部分はyの値に10ずつ足していって(yの値が10増えると円の位置が10ピクセル下に下る)、height(画面の高さ)よりも大きくなったらifの中が実行されてyは0(一番上)に戻り、xの位置がランダムな位置に変わる、というわけです。

本題…?

では、このプログラムで、円が四角形の中に入った時だけ、円の色を赤にする、という風にしたい場合にはどうしたら良いでしょう?
長くなってきたので、本題は次回にしたいと思います。
この記事と、次の記事を並べて表示すると理解しやすくて良いかも知れません。

第5回 – IF(条件分岐)2

引き続き条件分岐です。
前回によく似ていますが、円が徐々に大きくなった後、徐々に小さくなる、というのを繰り返す例を示します。
コメントは、前回と同じ部分は省略しています。

int ellipseSize = 50;
int addSize = 1;

void setup(){
  size(800,800);
  background(0);
}

void draw(){
 
  background(0);
  ellipse(400,400,ellipseSize,ellipseSize);
  
  
  // この下で、ellipseSizeにaddSizeを足している。
 // 最初はaddSizeの中は1なので、1増える。
  ellipseSize = ellipseSize + addSize;	
  
  
 //この下のif文では、もしellipseSizeが200よりも
 //大きかったら、addSizeに -1を掛けろ、
 //という命令が記されている。
    if(ellipseSize > 200){		
    addSize = addSize*(-1);
  }
  
  //←この下のif文でも同じく、ellipseSizeが50よりも小さかったら、
  //addSizeに -1 を掛けろ、という命令が記されている。
  if(ellipseSize < 50){			
    addSize = addSize*(-1);
  }
  
}

この2つのif分に注目してください。

 
    if(ellipseSize > 200){		
    addSize = addSize*(-1);
  }
  
  if(ellipseSize < 50){			
    addSize = addSize*(-1);
  }
  

if()の中の条件は違うが、ブロック { }の中で行われている処理は全く同じなので、実は下のようにまとめてこのように書くことが出来できます。

   
    if(ellipseSize > 200 | ellipseSize < 50){
    addSize = addSize*(-1);
  }
  

この | は、「もしくは」という意味で、今回の場合、ellipseSizeが200よりも大きいか、50よりも小さいかのいずれかでifの中身が実行されます。

この「もしくは」は、if文の中で実行している内容が全く同じ箇所がある場合にはたいてい使えるはずなので、もし自分でプログラムを書いていて内容が全く同じif文が出てきたら | が使えないかを考えてみてください。

問題

 例2のif文2つを、を | を使った形に書き換えなさい。