본문 바로가기

프로젝트/TFT LCD 한글 출력 (아두이노)

Hangul_Directed.H 를 이용한 한글 출력

예제 동영상보기

Hangul_Directed.H
 
//        Hangul_Direct.H    ver 1.0     아두이노용 한글 출력 클래스
//
//            제작자  :  신 옥 진
//          
//        재배포는  금지, 그냥 링크를 사용 하세요.  
//
//           영리목적(  유료 강의 자료, 판매 시스템에 포함 등 )의 사용은 사전 허락을 받아야 합니다.
//
//   < 소스 코드 순서 >
//   #define   _TFTLCD_      myLcd              // myLcd는 원하는 이름으로 하면 됨                                    
//   #include "c:\\Arduino\\HanGul_Direct.H"       // 헤더파일 전체 경로                                        
//   HanGul_TFT  ht;                            // 한글출력 클래스
//
                       

#ifndef _Hangul_Direct_          
#define _Hangul_Direct_      

#include <Adafruit_GFX.h>                                          
#include <UTFTGLUE.h>


#ifndef _MY_COLOR_               //  Color 정의
#define _MY_COLOR_
#define Black        0x0000
#define White        0xFFFF
#define Red          0xF800      
#define Green        0x0400
#define Blue         0x001F
#define Silver       0xC618
#define Gray         0x8410
#define Maroon       0x8000
#define Yellow       0xFFE0
#define Olive        0x8400
#define Lime         0x07E0
#define Aqua         0x07FF
#define Teal         0x0410
#define Navy         0x0010
#define Fuchsia      0xF81F
#define Purple       0x8010
#define Transparent  0xFFFFFFFF
#endif

UTFTGLUE  _TFTLCD_(0x9488,A2,A1,A3,A4,A0);  


struct Box               // 문자열의 사각형 좌표
{
   int x,y,x2,y2;  
} ;

class HanGul_TFT
{
  private:
      unsigned short _HANGUL_FONT[16];               // 폰트 저장변수        
      int  _color=cWhite;                  // 폰트색상
      int  _bkColor = cBlack;              // 폰트배경색      

  public:  
    Box  box;    
   
    HanGul_TFT()
    {  
            pinMode(A0, OUTPUT);                  
            digitalWrite(A0, HIGH);               //  TFT LCD 시작  
    };
    void color(int _c ) ;           // 글자색
    void color(int _c ,int _bk);    // 글자색,  배경색
    void fill(int _c);              // 바로 앞에 출력한 문자열을 _c 색으로 채우기
    void fill() ;                   // 배경색으로 채우기
    void rect(int _c);              // 바로 앞에 출력한 문자열에 _c 색으로 테두리 그리기
    void rect();                    // 문자색으로 테두리 그리기
    void under(int _c);             // 바로 앞에 출력한 문자열에 문자색으로 밑줄 그리기
    void under();                   // 문자색으로 밑줄 그리기
    void print( String s, int x, int y , int mx, int my );  // x,y좌표에 가로 mx배 ,세로 my배로 문장 출력
    void print( String s,int  x, int y  );                  //  1배
    void print( String s,int  x, int y ,int m  );           //  m배
   
  private:
    void _setDot_Func( int col, int row, int x, int y,int mx,int my ,int c );  //폰트의 1bit에 해당하는 점 그리기
    void _drawFont_Func( int x, int y,  int mx , int my);    
    bool _memFont( long code );
    #ifdef _INDEX_2_
    void getFont( long code );
    #endif    
};

void HanGul_TFT::color(int _c )
{
  _color=_c;    
}

void HanGul_TFT::color(int _c ,int _bk)
{
  _color=_c;
  _bkColor=_bk;

}

void HanGul_TFT::fill(int _c)                 // 문자열을  _c색상으로 채우기
{
    _TFTLCD_.setColor( _c  );    
    _TFTLCD_.fillRect(box.x,box.y,box.x2,box.y2);    

}

void HanGul_TFT::fill() { fill(_bkColor); }   // 문자열을  배경색상으로 채우기  // 문자열 지우기에 이용

void HanGul_TFT::rect(int _c)                 // _c색상으로 문자열의 외곽선 그리기
{
    _TFTLCD_.setColor( _c );
    _TFTLCD_.drawRect(box.x,box.y,box.x2,box.y2);    
}

void HanGul_TFT::rect() { rect(_color); }       // 문자색상으로 문자열의 외곽선 그리기

void HanGul_TFT::under(int _c)                  // 문자열에 _c색상으로 밑줄
{
    _TFTLCD_.setColor( _c );
    _TFTLCD_.fillRect(box.x, box.y2-2,box.x2,box.y2+1);    
}
void HanGul_TFT::under(){ under(_color); }                               // 문자열에 문자색상으로 밑줄

void HanGul_TFT::print( String s,int  x, int y  ) {  print( s, x, y , 1 ,1 ); }

void HanGul_TFT::print( String s,int  x, int y ,int m  ) { print( s, x, y , m, m  );  }



void HanGul_TFT::_setDot_Func( int col, int row, int x, int y,int mx,int my ,int c )
{                      
    _TFTLCD_.setColor( c );  
    for(int dx=0 ; dx< mx ;dx++)      
       for( int dy=0;dy<my;dy++)  
          _TFTLCD_.drawPixel(   x+col*mx+dx   ,y+row*my+dy  );  
}

void HanGul_TFT::_drawFont_Func( int x, int y,  int mx , int my)
{                                   // 문자(1자) 그리기
   
    for( int row=0; row< 16 ; row++)    // 폰트 bit 세로방향
    {
          for(int col=0;col<16;col++)      // 폰트 bit 가로방향
          {                                    
                if( _HANGUL_FONT[row] & 0b1000000000000000 )   _setDot_Func(  col,  row, x, y, mx, my, _color);
                else      _setDot_Func(  col,  row, x, y, mx, my, _bkColor  );        
                _HANGUL_FONT[row] <<= 1;                    // bit가 1이면 점그리기 함수 호출
          }
    }
}

bool HanGul_TFT::_memFont( long code )
{
  int size=sizeof(font) /sizeof(Font);  

  for( int f=0; f < size; f++)
  {    
     
      if(font[f].code  == code )
      {
         
          for(int i=0;i<16;i++) _HANGUL_FONT[i]=font[f].f[i];
          return true;
      }
  }
  return (false);
}

void HanGul_TFT::print( String s, int x, int y , int mx, int my )
{  
    box.x=x;
    box.y=y;
    box.y2=y+16*my-1;    

    _TFTLCD_.setTextSize(my*2);            

    for( int p=0; p <s.length() ;p++)
    {                                                
        if(  isAscii(s[p])  )
        {      
            if( s[p]==0x0d )break;                                        
            _TFTLCD_.setCursor(x,y);  
            _TFTLCD_.setTextColor(_color,_bkColor);                                                                                                    
            _TFTLCD_.println(s[p]);          
            if( s[p]==0x20 ) x+=8*my;
            else x+=12*my;        
        }
        else
        {    
            _TFTLCD_.setColor( _color)  ;
           
                  long code =byte(s[p]);              
                  code = code << 8;
                  code+=byte(s[p+1]);              
                  code = code << 8;
                  code+=byte(s[p+2]);  
                  _memFont( code);                    
                  _drawFont_Func( x,  y, mx, my) ;
                  x+=16*mx;
                  p+=2;
                                 
         } // isASCII else
    }// p 스트링 길이 반복  
    box.x2=x-1;
}

#endif
아두이노 소스코드
  // --- 폰트 만들기 2.5 으로 만든 코드입니다.  -----  Hangul_Direct.H보다 앞에 복사 할 것

struct Font  // 폰트구조체

     long            code; //  코드 
     unsigned short f[16]; //  폰트 
}; 

Font font[]={ 
{ /* 화*/ 0xED9994, {0x0000, 0x1F08, 0x0008, 0x7FC8, 0x0008, 0x1F08, 0x2088, 0x208E, 0x2088, 0x1F08, 0x0408, 0x0408, 0x7FE8, 0x0008, 0x0008, 0x0000  } } ,
{ /* 면*/ 0xEBA9B4, {0x0000, 0x3F88, 0x20F8, 0x2088, 0x2088, 0x2088, 0x20F8, 0x2088, 0x3F88, 0x0008, 0x0008, 0x1000, 0x1000, 0x1000, 0x0FF8, 0x0000  } } ,
{ /* 중*/ 0xECA491, {0x0000, 0x1FFC, 0x0080, 0x0140, 0x0630, 0x380E, 0x0000, 0x3FFE, 0x0080, 0x03E0, 0x0C18, 0x1004, 0x1004, 0x0C18, 0x03E0, 0x0000  } } ,
{ /* 앙*/ 0xEC9599, {0x0000, 0x0E08, 0x1108, 0x2088, 0x208E, 0x2088, 0x1108, 0x0E08, 0x0008, 0x03C0, 0x0C30, 0x1008, 0x1008, 0x0C30, 0x03C0, 0x0000  } } ,
{ /* 을*/ 0xEC9D84, {0x0000, 0x03E0, 0x0C18, 0x1004, 0x0C18, 0x03E0, 0x0000, 0x3FFE, 0x0000, 0x1FF8, 0x0004, 0x0FF8, 0x1000, 0x1000, 0x0FFC, 0x0000  } } ,
{ /* 좌*/ 0xECA28C, {0x0000, 0x0008, 0x3FE8, 0x0208, 0x0208, 0x0508, 0x0888, 0x104E, 0x6228, 0x0208, 0x0208, 0x0208, 0x7FE8, 0x0008, 0x0008, 0x0000  } } ,
{ /* 표*/ 0xED919C, {0x0000, 0x0000, 0x1FFC, 0x0000, 0x0410, 0x0410, 0x0410, 0x0220, 0x1FFC, 0x0410, 0x0410, 0x0410, 0x0410, 0x3FFE, 0x0000, 0x0000  } } ,
{ /* 로*/ 0xEBA19C, {0x0000, 0x0000, 0x1FF8, 0x0004, 0x0004, 0x0FF8, 0x1000, 0x1000, 0x1000, 0x0FFC, 0x0080, 0x0080, 0x0080, 0x3FFE, 0x0000, 0x0000  } } ,
{ /* 설*/ 0xEC84A4, {0x0000, 0x0408, 0x0408, 0x0C08, 0x0A78, 0x1108, 0x2088, 0x4048, 0x0000, 0x1FF0, 0x0008, 0x0FF0, 0x1000, 0x1000, 0x0FF8, 0x0000  } } ,
{ /* 정*/ 0xECA095, {0x0000, 0x3F88, 0x0408, 0x0408, 0x0A78, 0x0908, 0x1088, 0x2048, 0x4008, 0x03C0, 0x0C30, 0x1008, 0x1008, 0x0C30, 0x03C0, 0x0000  } }
 };

//--------------------------------------------------

#define   _TFTLCD_      myLcd                                // TFT LCD 이름 정의   myLcd를 원하는 이름으로 변경 하면 됨              
#include  "D:\\myHeader\\Hangul_Direct.H"            //  소스와 같은 경로가 아니면 플패스로 작성
                                    
HanGul_TFT  hp;     // 한글출력 클래스 생성자


int w=480, h=320, x= -130, d=1;    // 디스플레이 너비, 높이 , x좌표 시작 ,   1,4분면이면 1      2,3사분면이면 -1
                                                                                                                   //    y가 양수                y가 음수
int   ax( int _x )             //일반 좌표를 물리적인 디스플레이 좌표로 변환
{
  return  _x+w/2;
}

int ay( int _y)                //일반 좌표를 물리적인 디스플레이 좌표로 변환
{
  return h-(_y+h/2) ;
}

int r(int _x , int _r)                        // X좌표와 반지름(거리)으로 Y좌표 구하기  피타고라스의 정리    X*X +Y*Y = R*R
{
  return   sqrt( _r*_r - _x*_x )   ; //    Y=   Root(  R*R -X*X)
}

void setup() 
{
                            
    myLcd.begin(0x9486); ;     .. // TFT LCD ID
   myLcd.fillScreen(Black);        //  화면 지우기 효과    
   myLcd.setRotation(3);            //3 가로 480x320  //2 세로   320x480
  
  w=480;
  h=320;   
  
}

void loop() 
{   
 
  hp.color(White);
  hp.print("화면 중앙을 0,0 좌표로 설정",0,20);     // 한글 출력 부분
  hp.print("(0,0)",ax(0),ay(0));
  hp.print(String(h/2),ax(0),20);
  hp.print("-"+String(h/2),ax(0),h );                      // 기존 LCD출력 부분 이용해도 됨 ( 하지만 이게 간단함 )
  hp.print("-"+String(w/2),0,h/2);                          //         myLcd.setCursor(  좌표 );
  hp.print(String(w/2),w-40,h/2);                          //          myLcd.print( 문장 );
 
  myLcd.drawLine(0, h/2, w, h/2,Gray);                   // 그래픽은 메소드는  Adafruit_GFX.H 파일에 다 나온다.

  myLcd.drawLine(w/2, 0, w/2, h,Gray);    
  myLcd.drawCircle( ax(0), ay(0), 130,White);
  
   int y=r(x,130)*d;   //   y좌표 구하기                                        // 각종 도형을 다룰 때는 일반적인 수학 좌표가 편함
 
   myLcd.drawLine(ax(x),ay(y),ax(-x),ay(-y),Red)                      //  출력시 좌표값을 디스플레이 좌표로 변환하면 됨
   myLcd.fillCircle( ax(x) ,ay( y  ), 20  ,Yellow );
   myLcd.fillCircle( ax(-x) ,ay( -y  ), 20  ,Green );                       //    (  10,10)    - >    (  250, 150)
   delay(100);
   myLcd.drawLine(ax(x),ay(y),ax(-x),ay(-y),Black);                  //    (   0,    0)   - >     ( 240 , 160)
   myLcd.fillCircle( ax(x) ,ay( y  ), 20  ,Black );
   myLcd.fillCircle( ax(-x) ,ay( -y  ), 20  ,Black );                        //   (  -10,  -10)    - >    (  230, 170)
   x=x+30*d;
   if( x >130 ){ x=130; d= -1; } 
   if( x <-130 ) {  x=-130;  d=1;   }
   
}