본문 바로가기

Embeded/ATmega128

FND+LED+SW 사용 두더지 잡기 게임 만들기

// 두더지 잡기 게임
#include <stdlib.h>
#include "header/io.h"

#define LED_DDR DDRF
#define LED_OUT PORTF
#define KEY PINC
#define FND_DDR DDRE
#define FND_OUT PORTE

#define CPU_CLOCK 16000000
#define TICKS_PER_SEC 1000
#define PRESCALER 128

volatile unsigned int g_elapsed_time; // 시간변수

/* 함수 원형 설정 */
void sleep(unsigned int elapsed_time); // sleep함수
void init_LED(void); // LED포트 초기화 함수 원형
void init_TIMER(int timers); // Timer Counter 설정
void init_TC0(void); // Timer0 초기화 함수 원형
void delay(char *a, int speed); // SW입력 대기 함수 원형

int main()
{
/* 변수 설정 */
char count;
char t_count=0;
char led=1;
char score=0;
char score1=0;
char fnd=0;
int delay_ms;
/* 사용 설정 초기화 */
SREG = SREG|(1<<7); // 전체 인터럽트 활성화
DDRC=0x00;
init_LED(); // LED포트 초기화
init_TC0(); // Timer0 초기화
init_TIMER(OCIE0); // 타이머 설정
OCR0 = 0x7D; // 비교매치 인터럽트 비교값 설정
sei(); // 인터럽트 활성화 함수

/* 프로그램 작성 시작 */
while(1) //  난수 함수 시작점을 다르게하기 위한 무한 루프
{
delay_ms=500;
t_count++;
for(count=0; 8>count; count++)
{
LED_OUT=~(1<<count);
delay(&fnd, delay_ms);
if(5==fnd) // 0+1번 스위치가 눌려지면 두더지 게임 시작
{
for(count=0; 8>=count; count++)
{
LED_OUT=~(1<<count);
sleep(200);
}
LED_OUT=0x00;
FND_OUT=0x00;
for(count=5; 1<=count; count--) // 게임 시작 카운트 5~0
{
LED_OUT=0xff;
sleep(500);
LED_OUT=0x00;
FND_OUT=count+(count<<4);
sleep(500);
}
LED_OUT=0xff;
FND_OUT=0;
sleep(1000); // 게임 시작전 0.5초 지연
srand((unsigned int)t_count); // 난수 발생 함수
delay_ms=1000;
break; // 게임 시작을 위해 무한루프 브레이크
}
}
if(5==fnd)
{
fnd=0;
break;
}
}
/* 두더지 게임 시작 */
for(count=0; ;) // 무한 루프
{
for(count=0; count<25; count++) // 25번의 두더지 생성(LED On/off)
{
LED_OUT = ~(led<<rand()%7); // 두더지(LED)의 생성 위치 변경
delay(&fnd, delay_ms); // 1초간 지연하면서 스위치 입력 대기
if(2==fnd) // 두더지를 잡으면 점수 5점씩 올림
{
fnd=0;
score += 5;
if(score==0x0a)
{
score=0x00;
score1+=0x10;
}
}
else if(score1==0xa0||10==fnd) // 6+7번SW or 점수가 100점이 되면 FND,LED on/off 6회반복
{
score=0x00;
score1=0x00;
LED_OUT=0x00;
FND_OUT=0x00;
for(count=0; 6>=count; count++)
{
LED_OUT=~LED_OUT;
FND_OUT=~FND_OUT;
sleep(200);
}
sleep(2000);
FND_OUT=0;
fnd=0;
break; // on/off 6회 반복 끝나면 프로그램 종료!
}
FND_OUT = score+score1; // 점수 표시
LED_OUT = 0xff; // 두더지 숨기(LED off)
sleep(1000); // 1초 지연
}
delay_ms-=200;
if(25<=count) // 100점이면 게임 계속 실행
{ // 100점미만이면 게임 종료
return 0;
}
}
return 1;
}


/* 1초간 스위치 입력 대기 */
void delay(char *a, int speed)
{
g_elapsed_time=0;
while(g_elapsed_time<speed)
{
if(KEY == 0xfc) // 0~1번 SW Start
{
*a=5; // fnd변수에 5대입
break;
}
else if(KEY == 0x3f) // 6~7번 SW clear
{
*a=10; // fnd변수에 10대입
break;
}
else if(LED_OUT == KEY) // LED와 스위치가 같이 같으면 실행
{
*a=2; // fnd변수에 2대입
break;
}
}
}

/* LED포트 초기화 설정 함수 */
void init_LED(void)
{
LED_DDR = 0xFF; // PORTF 출력모드 설정
LED_OUT = 0xFF; // PORTF 초기화
FND_DDR = 0xFF;
FND_OUT = 0x00;
}

/* 타이머 설정 함수 */
void init_TIMER(int timers)
{
TIMSK=(1<<timers);
}

/* Timer0 초기화 설정 함수 */
void init_TC0(void)
{
//TCCR0 = 0x0D; // TCCR0 CTC모드 설정 / 분주비 설정
TCCR0 = 1<<2|0<<1|0<<0; // 이런식으로 설정도 가능함
}

/* 딜레이 함수 */
void sleep(unsigned int elapsed_time)
{
g_elapsed_time=0;
while(g_elapsed_time<elapsed_time)
{
}
}

/*     시그널 함수 */
/*  비교매치 인터럽트 */
void __vector_15(void)
{
g_elapsed_time++;
}