コンピュータを楽しもう!!

今、自分が面白くていろいろやってみたことを書き綴りたいと思います。連絡先はtarosa.yでgmail.comです。

文字コードの話(2)

自作プログラムの環境をUTF-8に変えるために、文字コードについて調べてUTF-8,UTF-16*1,S-JISそれぞれへの変換プログラムを作ったので、早速、UTF-8対応の文字表示プログラムを試作しました。

ソースをUTF-8に変更して気づいたことですが、Programmers Notepad2で2バイト文字をカーソルが正常に移動することです。さすがUnicodeという感じです。こういうことなら、早くUnicode環境にすべきだったなぁ。

void ShinoPrint8(uint16* screen,int x,int y,u8 *st,u16 Fcolor,u16 Bcolor,u8 kaki);

従来のShinoPrintはSJIS対応だったのですが、ShinoPrint8はUTF-8対応です。引数は従来のShinoPrintと同じです。下記にUTF-8の文字を表示するプログラムを示します。フォントデータはまだ作成していないので、UTF-8UTF-16SJISコードに変換して表示しています。

UTF-8UTF-16に変換するプログラム

void  UTF82UTF16( unsigned char *code )
{
  if( code[0]<0x80 ){
    code[1] = code[0];
    code[0] = 0;
  }
  else if( code[0]<0xe0 ){
    code[1] = (code[1] & 0x3f) + (code[0]<<6);
    code[0] = (code[0] & 0x1f)>>2;
  }
  else{
    code[0] = (code[0]<<4) + ((code[1] & 0x3f)>>2);
    code[1] = (code[1]<<6) + (code[2] & 0x3f);
  }
}

UTF-16SJISに変換するプログラム

int  UTF162SJIS( unsigned char *code )
{
long  utf16;

  if( code[0]==0 && code[1]==0 ){  return( 1 );  }

  utf16 = 2*((long)code[1] + (long)code[0]*256);
  code[0] = utf162sjis_bin[utf16];
  code[1] = utf162sjis_bin[utf16+1];

  if( code[0]==0 ){
    code[0] = code[1];
    code[1] = 0;
    return( 1 );
  }
  return( 2 );
}

UTF-8の文字を表示するプログラム

void ShinoPrint8( uint16* screen, int x, int y, u8 *st, u16 Fcolor, u16 Bcolor, u8 kaki )
{
unsigned char  code[4];  
short i, k, p;
short su, sd, s8;
int  b;

  while( 1 ){
    s8 = *st;
    if( s8<=0x7f ){
      //1バイト
      code[0] = *st;
      st++;
    }
    else if( s8>=0xc2 &&  s8<=0xdf ){
      //2バイト
      code[0] = *st;
      st++;
      code[1] = *st;
      st++;
    }
    else if( s8>=0xe0 &&  s8<=0xef ){
      //3バイト
      code[0] = *st;
      st++;
      code[1] = *st;
      st++;
      code[2] = *st;
      st++;
    }
    else{
      break;
    }
    UTF82UTF16( code );
    b = UTF162SJIS( code );
    su = code[0];
    if( b==2 ){
      sd = code[1];
      if( su==0 || sd==0 )  break;
      k = Sjis2Elisa( su, sd );
      for( i=0; i<6; i++ ){
        p = shinonome_bin[k*18+i*3];
        if((p&0x1)!=0)   Pixel( screen, x+7, y+i*2, Fcolor );
        if((p&0x2)!=0)   Pixel( screen, x+6, y+i*2, Fcolor );
        if((p&0x4)!=0)   Pixel( screen, x+5, y+i*2, Fcolor );
        if((p&0x8)!=0)   Pixel( screen, x+4, y+i*2, Fcolor );
        if((p&0x10)!=0)   Pixel( screen, x+3, y+i*2, Fcolor );
        if((p&0x20)!=0)   Pixel( screen, x+2, y+i*2, Fcolor );
        if((p&0x40)!=0)   Pixel( screen, x+1, y+i*2, Fcolor );
        if((p&0x80)!=0)   Pixel( screen, x+0, y+i*2, Fcolor );
        if( kaki==1 ){
          if((p&0x1)==0)   Pixel( screen, x+7, y+i*2, Bcolor );
          if((p&0x2)==0)   Pixel( screen, x+6, y+i*2, Bcolor );
          if((p&0x4)==0)   Pixel( screen, x+5, y+i*2, Bcolor );
          if((p&0x8)==0)   Pixel( screen, x+4, y+i*2, Bcolor );
          if((p&0x10)==0)   Pixel( screen, x+3, y+i*2, Bcolor );
          if((p&0x20)==0)   Pixel( screen, x+2, y+i*2, Bcolor );
          if((p&0x40)==0)   Pixel( screen, x+1, y+i*2, Bcolor );
          if((p&0x80)==0)   Pixel( screen, x+0, y+i*2, Bcolor );
        }
        p = shinonome_bin[k*18+i*3+1];
        if((p&0x1)!=0)   Pixel( screen, x+7, y+i*2+1, Fcolor );
        if((p&0x2)!=0)   Pixel( screen, x+6, y+i*2+1, Fcolor );
        if((p&0x4)!=0)   Pixel( screen, x+5, y+i*2+1, Fcolor );
        if((p&0x8)!=0)   Pixel( screen, x+4, y+i*2+1, Fcolor );
        if((p&0x10)!=0)   Pixel( screen, x+3, y+i*2+1, Fcolor );
        if((p&0x20)!=0)   Pixel( screen, x+2, y+i*2+1, Fcolor );
        if((p&0x40)!=0)   Pixel( screen, x+1, y+i*2+1, Fcolor );
        if((p&0x80)!=0)   Pixel( screen, x+0, y+i*2+1, Fcolor );
        if( kaki==1 ){
          if((p&0x1)==0)   Pixel( screen, x+7, y+i*2+1, Bcolor );
          if((p&0x2)==0)   Pixel( screen, x+6, y+i*2+1, Bcolor );
          if((p&0x4)==0)   Pixel( screen, x+5, y+i*2+1, Bcolor );
          if((p&0x8)==0)   Pixel( screen, x+4, y+i*2+1, Bcolor );
          if((p&0x10)==0)   Pixel( screen, x+3, y+i*2+1, Bcolor );
          if((p&0x20)==0)   Pixel( screen, x+2, y+i*2+1, Bcolor );
          if((p&0x40)==0)   Pixel( screen, x+1, y+i*2+1, Bcolor );
          if((p&0x80)==0)   Pixel( screen, x+0, y+i*2+1, Bcolor );
        }
        p = shinonome_bin[k*18+i*3+2];
        if((p&0x1)!=0)   Pixel( screen, x+11, y+i*2+1, Fcolor );
        if((p&0x2)!=0)   Pixel( screen, x+10, y+i*2+1, Fcolor );
        if((p&0x4)!=0)   Pixel( screen, x+9, y+i*2+1, Fcolor );
        if((p&0x8)!=0)   Pixel( screen, x+8, y+i*2+1, Fcolor );
        if((p&0x10)!=0)   Pixel( screen, x+11, y+i*2, Fcolor );
        if((p&0x20)!=0)   Pixel( screen, x+10, y+i*2, Fcolor );
        if((p&0x40)!=0)   Pixel( screen, x+9, y+i*2, Fcolor );
        if((p&0x80)!=0)   Pixel( screen, x+8, y+i*2, Fcolor );
        if( kaki==1 ){
          if((p&0x1)==0)   Pixel( screen, x+11, y+i*2+1, Bcolor );
          if((p&0x2)==0)   Pixel( screen, x+10, y+i*2+1, Bcolor );
          if((p&0x4)==0)   Pixel( screen, x+9, y+i*2+1, Bcolor );
          if((p&0x8)==0)   Pixel( screen, x+8, y+i*2+1, Bcolor );
          if((p&0x10)==0)   Pixel( screen, x+11, y+i*2, Bcolor );
          if((p&0x20)==0)   Pixel( screen, x+10, y+i*2, Bcolor );
          if((p&0x40)==0)   Pixel( screen, x+9, y+i*2, Bcolor );
          if((p&0x80)==0)   Pixel( screen, x+8, y+i*2, Bcolor );
        }
      }
      x += 12;
    }
    else{  //半角文字だよ
      if( su==0 )  break;
      for( i=0; i<3; i++ ){
        p = shinonomeank_bin[su*9+i*3];
        if((p&0x80)!=0)  Pixel( screen, x+0, y+i*4, Fcolor );
        if((p&0x40)!=0)   Pixel( screen, x+1, y+i*4, Fcolor );
        if((p&0x20)!=0)   Pixel( screen, x+2, y+i*4, Fcolor );
        if((p&0x10)!=0)   Pixel( screen, x+3, y+i*4, Fcolor );
        if((p&0x8)!=0)   Pixel( screen, x+4, y+i*4, Fcolor );
        if((p&0x4)!=0)   Pixel( screen, x+5, y+i*4, Fcolor );
        if((p&0x2)!=0)   Pixel( screen, x+0, y+i*4+1, Fcolor );
        if((p&0x1)!=0)   Pixel( screen, x+1, y+i*4+1, Fcolor );
        if( kaki==1 ){
          if((p&0x80)==0)  Pixel( screen, x+0, y+i*4, Bcolor );
          if((p&0x40)==0)   Pixel( screen, x+1, y+i*4, Bcolor );
          if((p&0x20)==0)   Pixel( screen, x+2, y+i*4, Bcolor );
          if((p&0x10)==0)   Pixel( screen, x+3, y+i*4, Bcolor );
          if((p&0x8)==0)   Pixel( screen, x+4, y+i*4, Bcolor );
          if((p&0x4)==0)   Pixel( screen, x+5, y+i*4, Bcolor );
          if((p&0x2)==0)   Pixel( screen, x+0, y+i*4+1, Bcolor );
          if((p&0x1)==0)   Pixel( screen, x+1, y+i*4+1, Bcolor );
        }
        p = shinonomeank_bin[su*9+i*3+1];
        if((p&0x80)!=0)  Pixel( screen, x+2, y+i*4+1, Fcolor );
        if((p&0x40)!=0)   Pixel( screen, x+3, y+i*4+1, Fcolor );
        if((p&0x20)!=0)   Pixel( screen, x+4, y+i*4+1, Fcolor );
        if((p&0x10)!=0)   Pixel( screen, x+5, y+i*4+1, Fcolor );
        if((p&0x8)!=0)   Pixel( screen, x+0, y+i*4+2, Fcolor );
        if((p&0x4)!=0)   Pixel( screen, x+1, y+i*4+2, Fcolor );
        if((p&0x2)!=0)   Pixel( screen, x+2, y+i*4+2, Fcolor );
        if((p&0x1)!=0)   Pixel( screen, x+3, y+i*4+2, Fcolor );
        if( kaki==1 ){
          if((p&0x80)==0)  Pixel( screen, x+2, y+i*4+1, Bcolor );
          if((p&0x40)==0)   Pixel( screen, x+3, y+i*4+1, Bcolor );
          if((p&0x20)==0)   Pixel( screen, x+4, y+i*4+1, Bcolor );
          if((p&0x10)==0)   Pixel( screen, x+5, y+i*4+1, Bcolor );
          if((p&0x8)==0)   Pixel( screen, x+0, y+i*4+2, Bcolor );
          if((p&0x4)==0)   Pixel( screen, x+1, y+i*4+2, Bcolor );
          if((p&0x2)==0)   Pixel( screen, x+2, y+i*4+2, Bcolor );
          if((p&0x1)==0)   Pixel( screen, x+3, y+i*4+2, Bcolor );
        }
        p = shinonomeank_bin[su*9+i*3+2];
        if((p&0x80)!=0)  Pixel( screen, x+4, y+i*4+2, Fcolor );
        if((p&0x40)!=0)   Pixel( screen, x+5, y+i*4+2, Fcolor );
        if((p&0x20)!=0)   Pixel( screen, x+0, y+i*4+3, Fcolor );
        if((p&0x10)!=0)   Pixel( screen, x+1, y+i*4+3, Fcolor );
        if((p&0x8)!=0)   Pixel( screen, x+2, y+i*4+3, Fcolor );
        if((p&0x4)!=0)   Pixel( screen, x+3, y+i*4+3, Fcolor );
        if((p&0x2)!=0)   Pixel( screen, x+4, y+i*4+3, Fcolor );
        if((p&0x1)!=0)   Pixel( screen, x+5, y+i*4+3, Fcolor );
        if( kaki==1 ){
          if((p&0x80)==0)  Pixel( screen, x+4, y+i*4+2, Bcolor );
          if((p&0x40)==0)   Pixel( screen, x+5, y+i*4+2, Bcolor );
          if((p&0x20)==0)   Pixel( screen, x+0, y+i*4+3, Bcolor );
          if((p&0x10)==0)   Pixel( screen, x+1, y+i*4+3, Bcolor );
          if((p&0x8)==0)   Pixel( screen, x+2, y+i*4+3, Bcolor );
          if((p&0x4)==0)   Pixel( screen, x+3, y+i*4+3, Bcolor );
          if((p&0x2)==0)   Pixel( screen, x+4, y+i*4+3, Bcolor );
          if((p&0x1)==0)   Pixel( screen, x+5, y+i*4+3, Bcolor );
        }
      }
      x += 6;
    }  
  }
}

デモプログラム

下記のようなプログラムで表示を試して見ました。ソースはUTF-8文字コードで保存しています。

//**************************************************
//メイン関数
//**************************************************
int main( void )
{
  VRAM_MODE5_INI();    //グラフィックをMode5に初期化する
  lcdMainOnTop();      //メイン画面を上にする

  ClearBGL( MainScreenA,RGB(0,0,0));
  ClearBGL( SubScreenA,RGB(0,0,0));
  
  ShinoPrint( MainScreenA, 6*0, 12*1, (u8*)"S-JIS表示:祝!向陽高校、初戦突破", RGB(31,31,31), RGB(0,0,0), 1 );
  ShinoPrint8( MainScreenA, 6*0, 12*3, (u8*)"UTF-8表示:祝!向陽高校、初戦突破", RGB(31,31,31), RGB(0,0,0), 1 );

  while( true );
  //システムの電源を切ります
  powerOn(PM_SYSTEM_PWR);
  while(1){  swiWaitForVBlank();  }
  return( 0 );
}

実行結果

SJISを表示するShinoPrintでは文字が化けてしまっていますが、ShinoPrint8()では正常に表示されました。

今日はこの辺で・・・。

本当にやりたいことリスト

(ブログの終わりにやりたいことを書いておきたいと思います)

  • 求職活動・・・このブログで興味を持った人一声かけてください。m(_ _)m
  • Androidプログラム
  • Web系のプログラム

*1:UTF-16UTF-16(BE:Big Endian)を使用しています