/*
** xmsgsaver ver 1
**
** font.c -- font operation with VFlib
**   This file has Japanese string, so this file must be coded by EUC-japan
**
** Sep 5,1999 by T.Kudoh(CDR/TK)
**
** Sep 5,1999  -- ver 1.1
** Sep 5,1999  -- ver 1.2
** Oct 28,1999 -- ver 1.4
*/

#include<stdio.h>
#include<VF.h>

extern char *Myname;

static int Default_vfcap;

typedef unsigned JIS;

/* character translation table */

static const unsigned char Char_trans[] = 
"¡¡¡ª¡í¡ô¡ð¡ó¡õ¡Ç¡Ê¡Ë¡ö¡Ü¡¤¡Ý¡¥¡¿£°£±£²£³£´£µ£¶£·£¸£¹¡§¡¨¡ã¡á¡ä¡©"
"¡÷£Á£Â£Ã£Ä£Å£Æ£Ç£È£É£Ê£Ë£Ì£Í£Î£Ï£Ð£Ñ£Ò£Ó£Ô£Õ£Ö£×£Ø£Ù£Ú¡Î¡ï¡Ï¡°¡²"
"¡Æ£á£â£ã£ä£å£æ£ç£è£é£ê£ë£ì£í£î£ï£ð£ñ£ò£ó£ô£õ£ö£÷£ø£ù£ú¡Ð¡Ã¡Ñ¡±";

static unsigned char Bit_reorder[256];


#define euc2jis(p)	((((JIS)(p)[0]) << 8 | (JIS)(p)[1]) & 0x7f7f)


static int init_VFlib( char *vfcap )
{
  int i;

  Default_vfcap = vfcap ? 0 : 1;

  i = VF_Init(vfcap);
  if( i < 0 )
    fprintf(stderr,"%s: VF_Init: failed.\n",Myname);
  return i;
}

static int open_font( char *font )
{
  int fid;

  fid = VF_OpenFont(font);
  if( fid < 0 ){
    fprintf(stderr,
    	"%s: VF_OpenFont: cannot open '%s'. Trying 'min'.\n",Myname,font);
    fid = VF_OpenFont("min");
    if( fid < 0 )
      fprintf(stderr,"%s: VF_OpenFont: failed.\n",Myname);
  }
  return fid;
}


int translate( unsigned char *str, JIS *jis )
{
  const unsigned char *p;

  if( str[0] & 0x80 ){
    if( str[1] & 0x80 ){
      *jis = euc2jis(str);
      return 2;
    }
    jis = 0;
    return 1;
  }

  if( str[0] == 0x0a ){
    *jis = 1;
    return 1;
  }

  if( str[0] >= 32 && str[0] <= 126 ){
    p = Char_trans + (str[0] - 32) * 2;
    *jis = euc2jis(p);
    return 1;
  }

  *jis = 0;
  return 1;
}


void FONT_get_size( unsigned char *msg, int *column, int *row, int dual_size )
{
  int c,r,c_max,s;
  JIS jis;

  c = r = c_max = 0;
  while( *msg ){
    s = translate(msg,&jis);
    msg += s;
    if( jis == 0 )
      continue;
    if( c == 0 )
      r++;
    if( jis == 1 ){
      c_max = c > c_max ? c : c_max;
      c = 0;
      continue;
    }
    c += dual_size ? s : 1;
  }
  c_max = c > c_max ? c : c_max;
  *column = c_max;
  *row = r;
}

int FONT_get_bitmap( unsigned char *msg, char *font,
			unsigned char *buf, int buf_width,
			int size_h, int size_v, int add_h, int add_v,
			int dual_size )
{
  JIS jis;
  int fid,i;
  int x;
  int s;
  int result;

  fid = open_font(font);
  if( fid < 0 ){
    if( Default_vfcap )
      return -1;
    fprintf(stderr,"%s: Trying default vfontcap.\n",Myname);
    if( VF_Deinit() < 0 ){
      fprintf(stderr,"%s: VF_Deinit: failed.\n",Myname);
      return -1;
    }
    if( init_VFlib(NULL) < 0 )
      return -1;
    fid = open_font(font);
    if( fid < 0 )
      return -1;
  }

  x = 0;
  while( *msg ){
    s = translate(msg,&jis);
    msg += s;
    if( jis == 0 )
      continue;
    if( jis == 1 ){
      x = 0;
      buf += buf_width * add_v;
      continue;
    }
    if( !dual_size )
      s = 1;
    i = VF_GetBitmap(jis,fid,size_h*s,size_v,buf_width,x%8,buf+x/8);
    if( i < 0 ){
      fprintf(stderr,"%s: VF_GetBitmap: failed.\n",Myname);
      VF_CloseFont(fid);
      return i;
    }
    x += add_h * s;
  }
  return VF_CloseFont(fid);
}
  

void FONT_bit_reorder( unsigned char *dst, unsigned char *src, int len )
{
  while( len-- )
    *dst++ = Bit_reorder[*src++];
}


int FONT_init( char *vfcap )
{
  int i,rmask,wmask,result;

  if( init_VFlib(vfcap) < 0 )
    return -1;

  for( i = 0 ; i < 256 ; i++ ){
    result = 0;
    for( wmask = 1, rmask = 0x80 ; rmask ; wmask <<= 1, rmask >>= 1 )
      if( i & rmask )
        result |= wmask;
    Bit_reorder[i] = result;
  }
  return 0;
}

int FONT_deinit( void )
{
  return VF_Deinit();
}
