韦东山嵌入式第一期学习笔记DAY_20——17_8_LCD点、线、圆

作者:GWD 时间:2019.7.25

一、课程内容:
概述:实现LCD显示屏的画点、画线、画圈
1、首先实现画点:关键是如何将需要显示的点,与显存对应起来。
在这里插入图片描述

void fb_put_pixel(int x, int y, unsigned int color)
{
	unsigned char  *pc;  /* 8bpp */
	unsigned short *pw;  /* 16bpp */
	unsigned int   *pdw; /* 32bpp */

	unsigned int pixel_base = fb_base + (xres * bpp / 8) * y + x * bpp / 8;

	switch (bpp)
	{
		case 8:
			pc = (unsigned char *) pixel_base;
			*pc = color;
			break;
		case 16:
			pw = (unsigned short *) pixel_base;
			*pw = convert32bppto16bpp(color);
			break;
		case 32:
			pdw = (unsigned int *) pixel_base;
			*pdw = color;
			break;
	}

2、接下来就可以画线画圈了(这部分代码不是讲课的内容,copy过来的)

#include "framebuffer.h"

/*
 * http://blog.csdn.net/p1126500468/article/details/50428613
 */

 //-------------画圆函数。参数:圆心,半径,颜色----------	
 // 	   画1/8圆 然后其他7/8对称画  
 // 		 ---------------->X  
 // 		 |(0,0)   0  
 // 		 |	   7	 1	
 // 		 |	  6 	  2  
 // 		 |	   5	 3	
 // 	  (Y)V		  4  
 //  
 // 	 L = x^2 + y^2 - r^2  
 void draw_circle(int x, int y, int r, int color)  
 {	
	 int a, b, num;  
	 a = 0;  
	 b = r;  
	 while(22 * b * b >= r * r) 		 // 1/8圆即可  
	 {	
		 fb_put_pixel(x + a, y - b,color); // 0~1  
		 fb_put_pixel(x - a, y - b,color); // 0~7  
		 fb_put_pixel(x - a, y + b,color); // 4~5  
		 fb_put_pixel(x + a, y + b,color); // 4~3  
   
		 fb_put_pixel(x + b, y + a,color); // 2~3  
		 fb_put_pixel(x + b, y - a,color); // 2~1  
		 fb_put_pixel(x - b, y - a,color); // 6~7  
		 fb_put_pixel(x - b, y + a,color); // 6~5  
		   
		 a++;  
		 num = (a * a + b * b) - r*r;  
		 if(num > 0)  
		 {	
			 b--;  
			 a--;  
		 }	
	 }	
 }	
   
 //-----------画线。参数:起始坐标,终点坐标,颜色--------	
 void draw_line(int x1,int y1,int x2,int y2,int color)	
 {	
	 int dx,dy,e;  
	 dx=x2-x1;	 
	 dy=y2-y1;	
	 if(dx>=0)	
	 {	
		 if(dy >= 0) // dy>=0  
		 {	
			 if(dx>=dy) // 1/8 octant  
			 {	
				 e=dy-dx/2;  
				 while(x1<=x2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){y1+=1;e-=dx;}	   
					 x1+=1;  
					 e+=dy;  
				 }	
			 }	
			 else		 // 2/8 octant	
			 {	
				 e=dx-dy/2;  
				 while(y1<=y2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){x1+=1;e-=dy;}	   
					 y1+=1;  
					 e+=dx;  
				 }	
			 }	
		 }	
		 else			// dy<0  
		 {	
			 dy=-dy;   // dy=abs(dy)  
			 if(dx>=dy) // 8/8 octant  
			 {	
				 e=dy-dx/2;  
				 while(x1<=x2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){y1-=1;e-=dx;}	   
					 x1+=1;  
					 e+=dy;  
				 }	
			 }	
			 else		 // 7/8 octant	
			 {	
				 e=dx-dy/2;  
				 while(y1>=y2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){x1+=1;e-=dy;}	   
					 y1-=1;  
					 e+=dx;  
				 }	
			 }	
		 }	   
	 }	
	 else //dx<0  
	 {	
		 dx=-dx;	 //dx=abs(dx)  
		 if(dy >= 0) // dy>=0  
		 {	
			 if(dx>=dy) // 4/8 octant  
			 {	
				 e=dy-dx/2;  
				 while(x1>=x2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){y1+=1;e-=dx;}	   
					 x1-=1;  
					 e+=dy;  
				 }	
			 }	
			 else		 // 3/8 octant	
			 {	
				 e=dx-dy/2;  
				 while(y1<=y2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){x1-=1;e-=dy;}	   
					 y1+=1;  
					 e+=dx;  
				 }	
			 }	
		 }	
		 else			// dy<0  
		 {	
			 dy=-dy;   // dy=abs(dy)  
			 if(dx>=dy) // 5/8 octant  
			 {	
				 e=dy-dx/2;  
				 while(x1>=x2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){y1-=1;e-=dx;}	   
					 x1-=1;  
					 e+=dy;  
				 }	
			 }	
			 else		 // 6/8 octant	
			 {	
				 e=dx-dy/2;  
				 while(y1>=y2)	
				 {	
					 fb_put_pixel(x1,y1,color);  
					 if(e>0){x1-=1;e-=dy;}	   
					 y1-=1;  
					 e+=dx;  
				 }	
			 }	
		 }	   
	 }	
 }	

3、测试函数

#include "geometry.h"
void lcd_test(void)
{
	unsigned int fb_base;
	int xres, yres, bpp;
	int x, y;
	unsigned short *p;
	/* 初始化LCD */
	lcd_init();

	/* 使能LCD */
	lcd_enable();

	/* 获得LCD的参数: fb_base, xres, yres, bpp */
	get_lcd_params(&fb_base, &xres, &yres, &bpp);
	fb_get_lcd_params( );
	/* 往framebuffer中写数据 */
	if (bpp == 16)
	{
		/* 让LCD输出整屏的红色 */

		/* 565: 0xf800 */

		p = (unsigned short *)fb_base;
		for (x = 0; x < xres; x++)
			for (y = 0; y < yres; y++)
				*p++ = 0xf800;

		/* green */
		p = (unsigned short *)fb_base;
		for (x = 0; x < xres; x++)
			for (y = 0; y < yres; y++)
				*p++ = 0x7e0;

		/* blue */
		p = (unsigned short *)fb_base;
		for (x = 0; x < xres; x++)
			for (y = 0; y < yres; y++)
				*p++ = 0x1f;
		/* write */
		p = (unsigned short *)fb_base;
		for (x = 0; x < xres; x++)
			for (y = 0; y < yres; y++)
				*p++ = 0xffff;
			
	}	
	/* 画线 */
	draw_line(0, 0, xres - 1, 0, 0);
	draw_line(xres - 1, 0, xres - 1, yres - 1, 0);
	draw_line(0, yres - 1, xres - 1, yres - 1, 0);
	draw_line(0, 0, 0, yres - 1, 0);
	draw_line(0, 0, xres - 1, yres - 1, 0);
	draw_line(xres - 1, 0, 0, yres - 1, 0);

	/* 画圆 */
	draw_circle(xres/2, yres/2, yres/4, 0);

}

二、学习要点
1、问;C语言中不同的函数间,参数怎么调用?
答:
1)、extern使用,适用于变量的调用,数组之类的;
2)、在各自的文件中分别为需要调用这些参数的函数执行参数获得函数:适用于获得结构体得数值或者函数的返回值作为文件中函数的参数,操作是在各自的文件中封装一次返回函数值的函数,在需要用到文件中函数的另一个文件中调用被封装的函数。
在这里插入图片描述
例如在测试函数中就要为test.c文件中的清屏显示获得一次参数然后再为framebuffer.c文件中的点显示获得一次参数。有参数传递的封装和无参数传递的封装(init函数,enable函数)是有区别的。传址解决的是同时产生多个返回值(分辨率、X、Y这种)解决不了跨文件传参。
2、问:指针作为输入参数时候怎么定义和引用?
答:
定义时:
在这里插入图片描述
引用时:
韦东山嵌入式第一期学习笔记DAY_20——17_8_LCD点、线、圆_第1张图片

你可能感兴趣的:(韦东山第一期,韦东山第一期,ARM裸机)