イベント映像を制作する際になにかしらサイバーっぽいアニメーションを使いたかったため、
openFrameworksにて3D上に平面のライフゲームを描画させました。
lifeGameObject.h
#pragma once
#include "ofMain.h"
class lifeGameObject {
public:
void setup(ofPoint center, int xChellCount,int yChellCount);
void update();
void draw();
private:
ofPoint center; //中央の座標
int xChellCount; // 横のセル数
int yChellCount; // 縦のセル数
bool aliveNow[100][100];
bool aliveNext[100][100];
ofPlanePrimitive plainPrimitive;
};
と宣言し、
lifeGameObject.cpp
#include "lifeGameObject.h"
void lifeGameObject::setup(ofPoint _center, int _xChellCount,int _yChellCount) {
center = _center;
xChellCount = _xChellCount;
yChellCount = _yChellCount;
plainPrimitive = ofPlanePrimitive(8, 8, 2, 2);
// ライフゲームの最初のデータはランダムとしました
for (int i = 0; i < xChellCount; i++) {
for (int j = 0; j < yChellCount; j++) {
aliveNow[i][j] = ((int)ofRandom(2))%2;
aliveNext[i][j] = false;
}
}
}
void lifeGameObject::update() {
// 各セルに対し判定を行う
for (int i = 0; i < xChellCount; i++) {
for (int j = 0; j < yChellCount; j++) {
// 自分の周囲の生存セル数を取得
int aliveCount = (int)aliveNow[i-1][j-1] + (int)aliveNow[i-1][j] + (int)aliveNow[i-1][j+1] + (int)aliveNow[i][j-1] + (int)aliveNow[i][j+1] + (int)aliveNow[i+1][j-1] + (int)aliveNow[i+1][j] + (int)aliveNow[i+1][j+1];
if (aliveNow[i][j] == true) { // 現在生存している場合
if (aliveCount == 2 || aliveCount == 3) {
aliveNext[i][j] = true; // 2か3であれば生存
continue;
}
} else { // 現在死亡している場合
if (aliveCount == 3) { // 3であれば誕生
aliveNext[i][j] = true;
continue;
}
}
aliveNext[i][j] = false;
}
}
for (int i = 0; i < xChellCount; i++) {
for (int j = 0; j < yChellCount; j++) {
aliveNow[i][j] = aliveNext[i][j];
}
}
}
void lifeGameObject::draw() {
ofSetColor(255);
for (int i = 0; i < xChellCount; i++) {
int xPosition = center.x + (i-xChellCount/2) * 10;
for (int j = 0; j < yChellCount; j++) {
int yPosition = center.y + (j-yChellCount/2) * 10;
if (aliveNow[i][j] == true) {
plainPrimitive.setPosition(xPosition, yPosition, center.z);
plainPrimitive.draw();
}
}
}
}
あとは呼び出し元から lifeGameObjects.setup(ofPoint(0,0,0), 100, 100);
といった形で宣言してやり、updateとdrawを適宜呼び出せば動きます。
C++とoFへの理解がまだ薄いせいか、かなり冗長なコードとなってしまいました。