找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 10787|回复: 8
打印 上一主题 下一主题
收起左侧

st7920控制的12864画线,画圆,作图成功(上图),拿来分享(注释很详细)

  [复制链接]
跳转到指定楼层
楼主
ID:68618 发表于 2014-11-22 15:29 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
在这里首先要感谢那些好心人,没有他们的帮忙我是写不出来,真的很谢谢你们。我把最近所调试成功的,都一一给大家说明,并上图和相关资料,希望对大家用。
1、打点部分
  该部分已在该论坛发帖,这里不就重复了
  (打点是所有绘图的基础)
2、画线部分
  先看程序
/********************************************************
* 名称:GUI_Line()
      采用布兰森汉姆(Bresenham)算法画线
* 功能:任意两点间的直线。根据硬件特点,实现加速。
* 入口参数:x0       直线起点所在行的位置
*         y0       直线起点所在列的位置
*         x1     直线终点所在行的位置
‘       y1     直线终点所在列的位置
* 出口参数:   无
* 说明:操作失败原因是指定地址超出缓冲区范围。
*********************************************************/
void GUI_Line8(uchar x0,uchar y0,uchar x1,uchar y1)
{
int temp;
int dx,dy;               //定义起点到终点的横、纵坐标增加值
int s1,s2,status,i;
int Dx,Dy,sub;

dx=x1-x0;
if(dx>=0)                 //X的方向是增加的
  s1=1;
else                     //X的方向是降低的
  s1=-1;     
dy=y1-y0;                 //判断Y的方向是增加还是降到的
if(dy>=0)
  s2=1;
else
  s2=-1;
  
Dx=fabs(x1-x0);             //计算横、纵标志增加值的绝对值
Dy=fabs(y1-y0);
if(Dy>Dx)                 //               
  {                     //以45度角为分界线,靠进Y轴是status=1,靠近X轴是status=0
  temp=Dx;
  Dx=Dy;
  Dy=temp;
  status=1;
  }
else
  status=0;

/********判断垂直线和水平线********/
if(dx==0)                   //横向上没有增量,画一条水平线
  GUI_XLine(x0,y0,y1,1);
if(dy==0)                   //纵向上没有增量,画一条垂直线
  GUI_YLine(x0,y0,x1,1);


/*********Bresenham算法画任意两点间的直线********/
  sub=2*Dy-Dx;                 //第1次判断下个点的位置
  for(i=0;i<Dx;i++)
  {
    GUI_Point(x0,y0,1);           //画点
    if(sub>=0)                              
    {
    if(status==1)               //在靠近Y轴区,x值加1
      x0+=s1;
    else                     //在靠近X轴区,y值加1               
      y0+=s2;
    sub-=2*Dx;                 //判断下下个点的位置
    }
    if(status==1)
  y0+=s2;
    else      
    x0+=s1;
    sub+=2*Dy;
        
  }
}

下面是图片:在(0,0)到(127,32)之间画线
        在(0,0)到(63,63)之间画线
大家可以看到,直线越长其线性越差,主要是算法的问题



3、画圆部分
  主要思路是用Bresenham算法先画1/8个圆,在利用对称行画出其余的部分
  程序如下:
  /*****************************************
名称:Draw_circle (在任意位置画圆)
说明:使用Bresenham法画1/8个圆,在用对称性画出其他的7/8个圆
   

    按下图把圆分为8份
        0
      7     1
    6       2
      5     3
        4
*****************************************/
void Draw_circle(uchar x0,uchar y0,uchar r)
{
int a,b;
int di;
a=0;
b=r;
di=3-2*r;             //判断下个点位置的标志
while(a<=b)
{
  GUI_Point(x0-b,y0-a,1);             //3           
  GUI_Point(x0+b,y0-a,1);             //0           
  GUI_Point(x0-a,y0+b,1);             //1      
  GUI_Point(x0-b,y0-a,1);             //7           
  GUI_Point(x0-a,y0-b,1);             //2            
  GUI_Point(x0+b,y0+a,1);             //4               
  GUI_Point(x0+a,y0-b,1);             //5
  GUI_Point(x0+a,y0+b,1);             //6
  GUI_Point(x0-b,y0+a,1);            
  a++;
  /***使用Bresenham算法画圆**/     
  if(di<0)
  di +=4*a+6;
  else
  {
    di +=10+4*(a-b);   
    b--;
  }
  GUI_Point(x0+a,y0+b,1);
  }
}
这是在以(63,32)为圆心,32为半径画的圆(小问题是当圆大后,会有部分画不出来,有待完善)


4、整屏画图部分
这个比较简单,就直接上程序了
void LCD_fulldisplay_picture_2(const uchar *pic) //全屏显示图片方法2
{
unsigned int x=0;
unsigned char i,j;
Write_command(0x34);                 //扩展指令动作
Write_command(0x36);                 //扩展指令动作

for(i=0;i<32;i++)                   //上半屏显示
{
  Write_command(0x80|i);             //列位置
  Write_command(0x80);               //行位置
for(j=0;j<16;j++)                 //256/8=32 byte
{                           //列位置每行自动增加
  Write_data(*pic);
  pic++;
}
}

for(i=0;i<32;i++)                   //下半屏显示
{
Write_command(0x80|i);               //列位置
Write_command(0x88);               //行位置
for(j=0;j<16;j++)                 //256/8=32 byte
{
  Write_data(*pic);
  pic++;
}
}
Write_command(0x30);
}
下面是照片

5、图片和文字在一起显示
我用的是带字库的,所以显示汉字较简单,即先作图,之后关闭绘图模式,打开普通模式就可以显示汉字了,先上个图片
这个程序很简单,就是先画5个圆,再在下面写汉字,就不用上传了。

希望我的东西对大家有用,如果有更优的源码可以交流交流,
下面是关于一些算法的资料


基于Bresenham的高效直线生成集成算法.pdf

312.93 KB, 下载次数: 66, 下载积分: 黑币 -5

快速直线生成算法.pdf

361.29 KB, 下载次数: 53, 下载积分: 黑币 -5

嵌入式LCD中画圆算法的改进与实现.pdf

256.5 KB, 下载次数: 48, 下载积分: 黑币 -5

分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏11 分享淘帖 顶 踩
回复

使用道具 举报

沙发
ID:59986 发表于 2014-12-9 22:29 | 只看该作者
回复

使用道具 举报

板凳
ID:184282 发表于 2017-4-18 20:31 | 只看该作者
整屏画图函数我用了,,画出的不是那么回事,,不是整平的
回复

使用道具 举报

地板
ID:35873 发表于 2017-6-18 03:31 | 只看该作者
好资料咋没人顶呢  我顶
回复

使用道具 举报

5#
ID:199188 发表于 2017-10-22 12:26 | 只看该作者
好资料!
回复

使用道具 举报

6#
ID:96218 发表于 2017-10-25 08:55 | 只看该作者
好东西,感谢楼主
回复

使用道具 举报

7#
ID:235673 发表于 2020-2-17 22:18 | 只看该作者
历害,打点的是在什么地方?
回复

使用道具 举报

8#
ID:280405 发表于 2020-7-12 01:05 | 只看该作者
不错,正在努力获得12864的显示自由。
回复

使用道具 举报

9#
ID:71535 发表于 2021-3-23 07:49 | 只看该作者
顶一下希望用在ST7565上面有效。
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表