이게 전체 소스입니다. 아래꺼는 lcd의 1라인에 영어로 HERMESTA! 라고 출력도되고
2라인에 한글로 헤르메스야 라고 출력되면서 오른쪽에서 왼쪽으로 시프트되는 소스입니다.
이걸 1라인에 헤르메스야 라고 출력하고 2라인에 HERMESYA!라고 출력하면서 오른쪽에서 왼쪽으로 시프트되고 또 왼쪽으로 끝까지 시프트되면 다시 왼쪽에서 오른쪽으로 시프트되는 동작이 반복되게 하려고 합니다.
회로에 다른 스위치는 업구요 리셋 스위치 하나만 들어갔습니다.
어디를 고쳐야 하는지 좀 알려주세요. 설명을 동반해주시면 좋겠습니다 감사합니다.
#include <AT89X51.h> // I/O가 정의 되어 있는 헤더 파일
unsigned char count,anim,animc,flag; // 전역 변수
//LCD로 디스플레이할 문자
code unsigned char msg1[]=" HERMESYA !";
code unsigned char msg2[]=" ";
code unsigned char hangle[]= {0x04,0x04,0x1f,0x00,0x0e,0x11,0x11,0x0e, //ㅎ
0x05,0x05,0x05,0x05,0x1d,0x05,0x05,0x05, //ㅔ
0x1f,0x01,0x1f,0x10,0x1f,0x00,0x00,0x1f, //르
0x1f,0x11,0x11,0x11,0x11,0x11,0x11,0x1f, //ㅁ
0x05,0x05,0x05,0x05,0x1d,0x05,0x05,0x05, //ㅔ
0x04,0x04,0x11,0x11,0x11,0x00,0x00,0x1f, //스
0x0e,0x11,0x11,0x11,0x11,0x11,0x11,0x0e, //ㅇ
0x10,0x10,0x1c,0x10,0x10,0x1c,0x10,0x10, //ㅑ
};
code unsigned char form[]= {'*',0x00,0x01,0x02,0x03,0x04,0x05,0x06,,0x07,0x08,'~','~','~','~'};
// P0.0 ~ P0.7 : 데이터, P2_4=RS, P2_5=RW,P2_6=E
#include "LCD8.h" // LCD 초기설정 루틴이 정의
// 8비트 데이터 메모리로 사용할 경우(MDA-A_D8051 TRAINER)
//#include "LCDM.h" // LCD 초기설정 루틴이 정의
// 타이머1 인터럽트
void T1_int(void) interrupt 3
{
TR1 = 0; // 타이머1 OFF
count--; // count - 1
if(count == 0){ // 0.5초
count = 15; // 카운터 클리어
flag = 1; // 인터럽트 플래그 셋
} // count if문
// 시정수 저장
TH1 = TL1 = 0;
TR1 = 1; // 타이머1 ON
}
// 한글 디스플레이
void HAN_DISP(void)
{
unsigned char i;
// 2라인을 지운다.
COMMAND(0xc0); // 커서 2라인 첫번째
for ( i=0; i <16; i++) CHAR_O(0x20);
// 커서 설정
COMMAND(anim);
// animc 만큼 한글 디스플레이
for (i=0 ;i < animc; i++) CHAR_O(form[i]);
COMMAND(0xd0); // 커서 라인 끝으로
}
// 메인
void main(void)
{
unsigned char i;
TMOD = 0x10; // 타이머1 모드1 지정.
TH1 = TL1 = 0; // 시정수 65536저장.
PT1 =1;
ET1 = 1;
EA = 1;
L_INIT(); // LCD 초기 설정
DISPLAY(); // msg1, msg2 디스플레이
// 한글 폰트 로드
for (i=0; i < 64; i++){
COMMAND(i | 0x40); // 캐릭터 RAM 어드레스 설정
CHAR_O(hangle[i]); // 폰트 로드
}
// 65536 x 0.54[us] x 15 = 0.5초
count = 15;
anim = 0xcf; // 애니메이션 초기 어드레스
animc = 1; // 애니메이션 카운터 초기 값
TR1 = 1; // 타이머1 ON
// 0.5초 대기
do{
flag = 0; // 인터럽트 플래그 클리어
while(!flag); // 인터럽트 대기
// 한글 디스플레이
HAN_DISP();
anim = ((anim-1) & 0x0f) | 0xc0; // 애니메이션 어드레스 업데이트
animc++; // 애니메이션 카운트 + 1
if ( animc == 17) animc = 1; // 끝이면 초기 값 저장
}while(1);
}
결론은 이 소스를 님이 원하시는 목적대로 고치고 싶다는건가요??
// 한글 디스플레이
void HAN_DISP(void)
{
unsigned char i;
// 2라인을 지운다.
COMMAND(0xc0); // 커서 2라인 첫번째
for ( i=0; i <16; i++) CHAR_O(0x20);
// 커서 설정
COMMAND(anim);
// animc 만큼 한글 디스플레이
for (i=0 ;i < animc; i++) CHAR_O(form[i]);
COMMAND(0xd0); // 커서 라인 끝으로
}
COMMAND(0xc0); 이것은 커서를 2행 0열로 옮기라는 것이므로 0xc0을 1행0열로 바꿔주면 되겠죠.. char_o(0x20)은 기존 글자를 전부 지우는것(공백으로)
command(anim); 은 쉬프트되는 자리로 이동하는것이겠죠..
쉬프트된 이후에 for문을 돌면서 해당글자를 출력하고 나서
command(0xd0); 으로 커서를 줄 끝으로 이동하는것이지요..
쉬프트 되는 내용은 결국 변수 anim 에 의해 이루어 지므로
main 함수에서 anim을 구워 삶으면 원하는 내용대로 할 수 있겠습니다.
"오른쪽에서 왼쪽으로 시프트되고 또 왼쪽으로 끝까지 시프트되면 다시 왼쪽에서 오른쪽으로 시프트되는 동작이 반복되게 하려고 합니다. "
animc++; // 애니메이션 카운트 + 1
if ( animc == 17) animc = 1; // 끝이면 초기 값 저장
위 소스가 왼쪽으로 쉬프트 되는거니 이것을 살짝만 바꿔주면 되겠죠.
char dir;// 왼쪽 or 오른쪽 쉬프트 저장
if(dir==1) 오른쪽
animc++;
else
animc--;
if(animc==17)
dir=0;
if(animc==0)
dir=1;
머 이런식으로 해주면 되겠지요..약간 고쳐야겠지만 이건 님의 몫입니다..
흐흐~~~~~~~
님 질문내용이 무슨 내용인지 몰라 한참 읽었습니다-_-;;
우선 감사합니다 ^^ 공부해볼게요.ㅋ
animc++; // 애니메이션 카운트 + 1
if ( animc == 17) animc = 1; // 끝이면 초기 값 저장
위 소스가 왼쪽으로 쉬프트 되는거니 이것을 살짝만 바꿔주면 되겠죠.
------------------------------------------------------------------
살짝만 바꿔주면 된다고하셧는데 제가 워낙 몰라서;
왼쪽으로 시프트되었다가 다시 오른쪽으로 시프트되게.. 알려주실수없을까요
예로 보여주신건.. 하하;;; 먼지 잘모르겟어요;; animc--; 이걸로 쓰면되는건지;
음...좀더 힌트를 들이자면
animc 의 값은 lcd 행의 커서위치를 말하는것입니다.
16x2 겠죠?... 그럼 16에 해당하는 값이 되겠죠..
이 값들을 뒤로 갈꺼냐 앞으로 갈꺼냐 즉 14,15,16 이런식으로 할꺼냐 16,15,14 이런식으로 할꺼냐에 따라서 앞으로 갔다 뒤로 갔다 쉬프트되겠습니다.
animc--;<== 1감소하니 현재 15번째부터 커서부터 뿌려진다면 그담에는 14번째부터 뿌려지겠죠..
그럼 열심히 하시길...홈피 업데이트 하느라 ...
anim = ((anim-1) & 0x0f) | 0xc0; // 애니메이션 어드레스 업데이트
animc++; // 애니메이션 카운트 + 1
if ( animc == 17) animc = 1; // 끝이면 초기 값 저장
--------------------------------------------------------
여기서요 anim = ((anim-1) & 0x0f) | 0xc0; 이건 무슨뜻이에요?
0xc0 하고 0x0f는 어떻게 나오는건지..
저 의미로는
0x0f 는 하위 4바이트를 앤드 연산자 하므로
anim 값에서 상위 4바이트는 버리고 하위 4바이트만 취하게 되고
| 연산자에 0xc0이 있으므로 상위 4바이트에 1100을 or 시키게 되겠죠
결국 1100 + anim값의 하위 4바이트 가 anim값이 되겠네요.
제가 해봤는데요 . 영이상하게 나오네요;; 멀 잘못한건지..
내용은 간단한거 같은데.. 괜찬으시면 한번 직접 하신다고 생각하시고 해서 보여주세요ㅜㅜ
부탁드립니다. 시간이 많이 없어서;..
항상 하드웨어와 소프트웨어가 결합된 형태이기때문에 제가 상상만으로 짜기가 좀 그렇군요..
문제가 어디에서 일어나는지 확실히 알았으면 좋겠네요..
하드웨어 테스트는 끝난건가요??
프로그램도 기능별로 나누어서 테스트해보고
각 명령줄이 무슨 역할을 하는지 하나씩 파악해보세요..
원래의 소스에서 한줄씩 주석으로만들어 보고 실행해보고 하면서 말이죠..
디버깅환경이 어떤지 모르겠으나 내부에서 값이 변경되는것을 외부에서 확인할 수 있게 만들면 좋을듯 한데요..
오른쪽 왼쪽 시프트되가는것도.. 움직일지 않아요; 오른쪽 왼쪽 시프트되가는것이라도 대충이라
도 써주실순없는지..
정말 애매하군요 마이다스 제품 쓰시고 계산거 같은데
LCD 라이브러리는 전부 비공개이고 제품설명도 없이 소스만 주시고 하라고 하면
동일한 제품을 쓰지 않는 사람이면 하기 힘든데요.
1. 사용하는 LCD모델 모름(데이터 쉬트 확인해야하기 때문)
2. LCD.H 포로토타입 모름
3. 회로구성 모름
님이 올리신 소스가 정상적으로 된다는 가정하에 유추해서 답변을 드린것입니다.
정확한것은 위 3가지가 있어야 가능하겠네요..
처음 말씀드린것처럼 이런류의 질문은 정확한 정보를 제공해줘야 해요..
보는 사람은 정말 답답하거든요...
anim = ((anim-1) & 0x0f) | 0xc0; // 애니메이션 어드레스 업데이트