⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lcd.c

📁 C51单片机端
💻 C
字号:

#include <stdarg.h>
#include <stdio.h>

#include "system.h"
#include "compiler.h"
#include "lcd.h"
#include "dot.h"

char etxt[40];  

void lprintf(Uchar Ox,Uchar Oy,unsigned char att,char * fmt, ...) 
{
  va_list arg_ptr;
  va_start (arg_ptr, fmt); //规格化字符串
  vsprintf (etxt, fmt, arg_ptr);
  dprintf (Ox, Oy, etxt,att)  //汉字字母混合显示
  va_end (arg_ptr);
}

// 写指令代码子程序
void vComToLcd( Uchar ComByte ) 
{
  vLcdCmdPort(ComByte);
}

// 写参数及显示数据子程序
void vDataToLcd( Uchar dataW )
{
  vLcdDataPort(dataW);
}

/*=====================================
 初始化子程序
======================================*/
void vInitLcd( void ) {

	Uchar i;
		
	vComToLcd( SystemSet );			// 系统参数设置
	for (i=0;i<8;i++) {				
		vDataToLcd( ParaSysTable8[i] );	//
	}

	vComToLcd( Scroll ); 			//设定显示区域起始地址
	for (i=0;i<10;i++) {
		vDataToLcd( ParaScrTableA[i] );
	}

	vComToLcd( HdotScr );		// 写入点位移指令代码
	vDataToLcd( 0 );			// 写入P1参数
	vComToLcd( Ovlay );			// 显示合成方式设置
	vDataToLcd( 0x0c );  		// 0000 0100 显示一区三区图形,二重"或"合成
	vComToLcd( DispOn );		// 写入指令代码
	vDataToLcd( 0x54 );			// 显示 1~4 区开显示,光标关显示
}

/*==============================================================================
; 汉字写入子程序(图形方式)。每次调用输出一个汉字
; 支持图形方式使用,完成汉字点阵码的输出。
; 携入参数: Ox,Oy....写入显示的左上角坐标,Ox是以字节单位,Oy以行扫描线单位
			Ptr......汉字码,库内的排列编码,大型程序时请改用Uint类型
; 无返回数据。
 ==============================================================================*/
void vDrawLogo(Uchar mOx, Uchar mOy, Uint mLogoWidth, Uchar mLogoHigh, Uchar mPosion) 
{
	unsigned int  DotPtr,Optr;
	unsigned char ColCount,RowCount,mByte;
	
	DotPtr = 0;	
	Optr = (Uint)mOy*paraP9 + mOx;     //显示单元起始位置
	if(mPosion)Optr += ((Uint)BasePart2)<<8; //指向第二区加上第二区首地址
	mByte = (Uchar)(mLogoWidth/8);			   //一行显示字节

	for(RowCount=0;RowCount<mLogoHigh;RowCount++) 	
	{
		//光标起点定位
		vComToLcd(CsrW); 		           //光标定位指令
		vDataToLcd((Uchar)(Optr&0xff));	   //设置光标地址CSR
		vDataToLcd((Uchar)(Optr/256 ));	   
	
		vComToLcd(CsrDirR);			       //光标自动右移。
	
		//显示一行
		vComToLcd(mWrite);				   //数据写指令
		for (ColCount=0;ColCount<mByte;ColCount++) 
		{
			vDataToLcd(CdotLogolib[DotPtr]);	 //写入数据
			DotPtr++;
		}
	    Optr += 0x28;
	}
	
}

void vClearLcd( void ) 
{
    Uint lcd_ram = 0x2580;
	vComToLcd( CsrDirR ); 		// 光标移动方向定义:自动右移
	vComToLcd( CsrW );			// 光标Locate,定位
	vDataToLcd(0);				// 写入参数CSRL设置参数光标指针低8位
	vDataToLcd(0);				// 写入参数CSRH设置参数光标指针高8位
	vComToLcd( mWrite );		// 数据写入指令,代码0x42
	while(lcd_ram--)	
	{
		vDataToLcd( 0x0 );	    // 写入数据0
	}

	lcd_ram = 0x2580;
	vComToLcd( CsrDirR ); 		// 光标移动方向定义:自动右移
	vComToLcd( CsrW );			// 光标Locate,定位
	vDataToLcd(0x00);			// 写入参数CSRL设置参数光标指针低8位
	vDataToLcd(0x40);			// 写入参数CSRH设置参数光标指针高8位
	vComToLcd( mWrite );		// 数据写入指令,代码0x42
	while(lcd_ram--)	
	{
		vDataToLcd( 0x0 );	    // 写入数据0
	}
}

/*============================================================================
 光标位定位,用于在1区图形方式下。
 输入参数约定:	x...水平方向字节单位坐标,即可以以半个汉字宽度设定水平坐标。
 				y...垂直方向以行线定位的坐标,可以定位到点单位。
				左上角约定坐标为( 0, 0 )

 ============================================================================*/
void Locatexy(Uchar x,Uchar y, Uchar attribs) 
{
    Uint temp;
	temp = (Uint)y*paraP9+x;
	if(attribs)temp += ((Uint)BasePart2)<<8;  // 如果需要就指向第二区,加上第二区首地址
	vComToLcd(CsrW);				          // 光标Locate,定位
	vDataToLcd((Uchar)(temp & 0xff));	      // 写入参数CSRL设置参数光标指针低8位
	vDataToLcd((Uchar)(temp /256 ));	      // 写入参数CSRH设置参数光标指针高8位
}

/*=============================================================================
  ASCII(8*16) 及 汉字(16*16) 混合字符串显示函数	
  输入参数约定:
	x,y显示字符串的左上角xy坐标.x..8点一字节位置; y..一条扫描线定位
							
	*ptr...字符串指针,本函数所指的是flash字串
	att....显示区标志,0...第一区;1...第二区
  返回参数:输出字串长度,留意汉字一个算两个
  其它假定:调用时汉字必须在字库数组中已经存在,否则将输出不正确的结果
==============================================================================*/
Uchar dprintf(Uchar x,Uchar y, char *ptr, Uchar att)
{
    Uchar  c1,c2;
	Uchar i,j,uLen,uRow,uCol,temp;
	Uint  k;
	uRow = x;
	uCol = y;
	uLen=0;

	vComToLcd( CsrDirD ); 						// 光标移动方向定义:自动下移
	Locatexy(uRow,uCol,att);						//起点定位
	while ( (Uchar)*(ptr+uLen) >= 0x10 ){uLen++;};	//探测字串长度
	i=0;
	while(i<uLen)
	{
		c1 = ptr[i];
		c2 = ptr[i+1];

//ascii字符与汉字内码的区别在于128做分界,大于界线的为汉字码
		if(c1 <=128)								// ASCII
		{
			if (c1 >= 0x10)	{
				vComToLcd( mWrite );				// 写数据(命令)
				for(j=0;j<16;j++) vDataToLcd( ASC_MSK[(c1-0x20)*16 +j ]);
			}
			uRow++;									// 列数加1
		}
		else										// 中文
		{
			for(j=0;j<sizeof(Cdotlib)/sizeof(Cdotlib[0]);j++)	// 查找定位
			{
				if((c1 == Cdotlib[j].Index[0]) && (c2 == Cdotlib[j].Index[1]))
					break;
			}
			for(k=0;k<2;k++)						// 分16行输出
			{
				Locatexy(uRow+k,uCol,att);
				vComToLcd( mWrite );				// 写数据(命令)
				for(temp=0;temp<16;temp++) vDataToLcd( Cdotlib[j].Msk[temp*2 + k]);
			}
			uRow +=2;								// 光标右移一大格
			i++;
		}
		if(uRow >= 40)								// 光标后移
		{
			uCol += 16;								// Y坐标
			uRow = 0;					    		// X坐标
			if( uCol >= 240 ) uCol = 0;
		}

		Locatexy(uRow,uCol,att);
		i++;
	}
	return uLen;							//返回字串长度,汉字按2字节计算
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -