2013年12月9日月曜日

マトリクスLEDでライフゲーム

というわけで定番のライフゲームを実装してみた。

動作風景


ソース
----
/*
atmega8 16pu
matrix led(1088bgy) controller
ISP
PC6 RESET
PB5 SCK
PB4 MISO
PB3 MOSI
USART
PD0 RXD
PD1 TXD
LED
ROW PC0,PC1,PC2,PC3,PC4,PC5,PB0,PB1
COL PB6,PB7,PD2,PD3,PD4,PD5,PD6,PD7
*/
#define F_CPU 1000000UL // Clock Speed
#define BAUD 9600
#define MYUBRR (((F_CPU / (BAUD * 16UL))) - 1)
#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include <stdio.h>
#include <stdlib.h>
/* DDRC |= (1 << PC0); */
#define DSET(p,n) (DDR##p|=(1<<P##p##n))
/* PORTC |= (1 << PC0); */
#define PSET(p,n,d) \
if ((d)) { \
(PORT##p|=(1<<P##p##n));\
} else { \
(PORT##p&=~(1<<P##p##n));\
}
void
init_port()
{
// port c output setting
DSET(C,0);
DSET(C,1);
DSET(C,2);
DSET(C,3);
DSET(C,4);
DSET(C,5);
// port b output setting
DSET(B,0);
DSET(B,1);
DSET(B,6);
DSET(B,7);
// port d output setting
DSET(D,2);
DSET(D,3);
DSET(D,4);
DSET(D,5);
DSET(D,6);
DSET(D,7);
}
void
row(int i,int d)
{
switch(i) {
case 0:PSET(C,0,d);break;
case 1:PSET(C,1,d);break;
case 2:PSET(C,2,d);break;
case 3:PSET(C,3,d);break;
case 4:PSET(C,4,d);break;
case 5:PSET(C,5,d);break;
case 6:PSET(B,0,d);break;
case 7:PSET(B,1,d);break;
}
}
void
col(int i,int d)
{
switch(i) {
case 0:PSET(B,6,d);break;
case 1:PSET(B,7,d);break;
case 2:PSET(D,2,d);break;
case 3:PSET(D,3,d);break;
case 4:PSET(D,4,d);break;
case 5:PSET(D,5,d);break;
case 6:PSET(D,6,d);break;
case 7:PSET(D,7,d);break;
}
}
void
allcut()
{
// col
PSET(B,6,0);
PSET(B,7,0);
PSET(D,2,0);
PSET(D,3,0);
PSET(D,4,0);
PSET(D,5,0);
PSET(D,6,0);
PSET(D,7,0);
// row
PSET(C,0,1);
PSET(C,1,1);
PSET(C,2,1);
PSET(C,3,1);
PSET(C,4,1);
PSET(C,5,1);
PSET(B,0,1);
PSET(B,1,1);
}
#define DELAY 500
#define PERIOD 60000000 /* 60sec */
#define INTERVAL 500000 /* 500ms */
void
life(void)
{
int i,j,k,a,b,live;
unsigned long t1,t2;
unsigned char m[2][8];
allcut();
t1 = t2 = k = a = 0;
for(i=0;i<8;i++) {
m[0][i] = 0x0;
m[1][i] = 0x0;
for(j=0;j<8;j++) {
if (rand()%2==0) {
m[0][i]|=(1<<j);
m[1][i]|=(1<<j);
}
}
}
while (t1 < PERIOD) {
if (t2 > INTERVAL) {
t2 = 0;
k++;
a = k % 2;
b = (k+1) % 2;
for(i=0;i<8;i++) {
for(j=0;j<8;j++) {
live = 0;
/*up left*/
if ((m[b][(i+7)%8]&1<<(j+7)%8)) {
live++;
}
/*up*/
if ((m[b][(i+7)%8]&1<<j)) {
live++;
}
/*up right*/
if ((m[b][(i+7)%8]&1<<(j+1)%8)) {
live++;
}
/*left*/
if ((m[b][i]&1<<(j+7)%8)) {
live++;
}
/*right*/
if ((m[b][i]&1<<(j+1)%8)) {
live++;
}
/*down left*/
if ((m[b][(i+1)%8]&1<<(j+7)%8)) {
live++;
}
/*down*/
if ((m[b][(i+1)%8]&1<<j)) {
live++;
}
/*down right*/
if ((m[b][(i+1)%8]&1<<(j+1)%8)) {
live++;
}
if (m[b][i]&1<<j) {
/*die*/
if (live<=1 || live>=4) {
m[a][i]&=~(1<<j);
} else {
m[a][i]|=(1<<j);
}
} else {
/*born*/
if (live==3) {
m[a][i]|=(1<<j);
} else {
m[a][i]&=~(1<<j);
}
}
}
}
}
for(i=0;i<8;i++) {
allcut();
for(j=0;j<8;j++) {
col(j,(m[a][i]&1<<j)>>j);
if (i==j) {
row(j,0);
}
}
_delay_us(DELAY);
t1 += DELAY;
t2 += DELAY;
}
}
}
int
main(void)
{
init_port();
while (1) {
life();
}
return 0;
}
view raw life.c hosted with ❤ by GitHub
----

まあどうってことない。

で、動作確認してて気づいたのだけど、光らない列が1列あった。

調べたらハンダ剥がれとった。ぐむぅ。修正。

0 件のコメント:

amazonアソシエイト