溺水妖精

就这样沉溺在水中,一个失败的妖精

  博客园 :: 首页 :: 博问 :: 闪存 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::
绘制中文

    思想:找到相应点的坐标,将所有点连接起来就是一个汉字,如老式的点阵打印机
   我们绘制中文,就需要获取这个汉字所有的点的信息,把他们描绘出来。绘制中文需要有汉字的点阵字库,字库里面保存的是国际区位码,我们从这里面读取汉字信息(chs16.fon字库文件)。 
   首先,我们要知道,汉字是由16*16个点构成的,有点的位置为1,否则为0,如下图:
C字符的信息如下:
第0行:00000000
第1行:00111110
第2行:01110000
第3行:01110000
第4行:01110000
第5行:01110000
第6行:00111110
第7行:00000000
用双循环去找点的位置,并画出来。8行8列。
中文是用2个高位为1的ASCII码表示。

区位码与机内码的换算公式为
【区位码】+(10100000 10100000)=【机内码】。即:
    区位码0 + (10100000) = 机内码0;
    区位码1 + (10100000) = 机内码1;
这样的话,点阵数据,就可以通过汉字"机内码"-> "区位码"进行索引、查找。
由于一个汉字用了32个字节,而GB-2312区位码表表有94行、94列,那么,只要知道该字符在表中是第几个,再乘以32就行了。
用区位码就可以查找在区位码表中第几个了,区位码表示(区,位)

步骤:

1.用ORD可以获取一个字元的机内码,再通过上面的换算公式,得出区位码(一个汉字的第一个字元是区的信息,第二个是位的信息)
2.通过区位码,查出字符在字库中的位置,并得出点阵信息
3.把点阵信息放入数组
4.如果为1,在相应的位置绘制点

原理就这么简单:)

下面给一段代码:是别人的代码
/*************************************
*     文件名:'draw1.0.inc.php
**    中文显示点阵输出   version 1.0
**    只提供简单的操作:输出默认大小的纯中文字符串到图片的坐标(0,0)上
**    更多功能,请见下一版本。
*
****************************************/
function draw($image,$string,$color)
{
   $fp=fopen("chs16.fon","rb");//二进制方式读点阵字库chs16.fon
   if (!feof($fp))//如果文件指针到了文件末尾,退出,不要忘记关闭文件
   {
      while($string)//当字符串不为0
      {
         $qh=ord(substr($string,0,1))-0xa0;
      $wh=ord(substr($string,1,2))-0xa0;
/* 这两行代码,其实是获取一个中文的机内码。通过运算到了区位码。*/
         $offset=(94*($qh-1)+($wh-1))*32;
/*得到了汉字的区位值后,就开始计算偏移量了。*/
     fseek($fp,$offset,SEEK_SET);
/*在字库文件$fp中,将文件指针定位到偏移量。*/
         $buffer=preg_split('//', fread($fp,32), -1, PREG_SPLIT_NO_EMPTY);
/* fread($fp,32);是从$fp中读取32个字节数据,然后通过preg_split();分配到数组$buffer中。preg_split();是一个支持正则表达的函数。*/
        for($i=0;$i<16;$i++)              //点阵的行数:16 列数也应该是16
       for($j=0;$j<2;$j++)             //因为是两个字节,那么,就要一个一个地画了
        for($k=0;$k<8;$k++)          //每个字节,都有8个点的数据
      if(((ord($buffer[$i*2+$j])>>(7-$k))&0x01))//如果这个点的值为1,输出;否则,没有
      {
         imagesetpixel($image,$x+8*$j+$k, $i, $color);
             }
      $string=substr($string,2); //中文由两个字节表示,所以,输出一个汉字后,就要去掉两个字节。
      $x=24; //一个汉字输出结束,空开一点,给下一个汉字。因为这个汉字是16×16点,那么,$x的值设为16,就够了。但,太挤了不是?
     }
  }
  fclose($fp);
 }
 

posted on 2004-03-05 13:30  溺水妖精  阅读(2121)  评论(1编辑  收藏  举报