📄 splc501.c
字号:
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
prog_uchar HZK[]={
/*-- 文字: 哇 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0xFC,0x04,0x04,0xFC,0x40,0x48,0x48,0x48,0x48,0xFF,0x48,0x48,0x48,0x48,0x40,0x00,
0x0F,0x02,0x02,0x47,0x40,0x44,0x44,0x44,0x44,0x7F,0x44,0x44,0x44,0x44,0x40,0x00,
/*-- 文字: 哈 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0xFC,0x04,0x04,0xFC,0x20,0x20,0x50,0x48,0x44,0x43,0x44,0x48,0x58,0x30,0x10,0x00,
0x07,0x01,0x01,0x03,0x00,0x00,0x7F,0x21,0x21,0x21,0x21,0x21,0x7F,0x00,0x00,0x00,
/*-- 文字: … --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0x00,0xC0,0xC0,0x00,0x00,0x00,0xC0,0xC0,0x00,0x00,0x00,0xC0,0xC0,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
/*-- 文字: 睡 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0xFE,0x22,0x22,0xFE,0x00,0x92,0xF2,0x92,0x92,0xFE,0x91,0x91,0xF1,0x91,0x90,0x00,
0x7F,0x11,0x11,0x3F,0x00,0x48,0x4F,0x48,0x48,0x7F,0x48,0x48,0x4F,0x48,0x08,0x00,
/*-- 文字: 觉 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0x00,0x18,0x09,0xCA,0x4C,0x48,0x49,0x4A,0x4E,0x48,0x48,0xCC,0x0B,0x1A,0x00,0x00,
0x00,0x00,0x80,0x8F,0x40,0x20,0x10,0x0F,0x70,0x80,0x80,0x8F,0x80,0xE0,0x40,0x00,
/*-- 文字: 啦 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0xFC,0x04,0x04,0xFC,0x08,0x08,0xFF,0x88,0x08,0xC8,0x09,0x0E,0x08,0xE8,0x08,0x00,
0x07,0x02,0x02,0x03,0x22,0x41,0x3F,0x00,0x20,0x23,0x2C,0x20,0x2C,0x23,0x20,0x00,
/*-- 文字: 。 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x18,0x24,0x24,0x18,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
/*-- 文字: 嘿 --*/
/*-- 宋体12; 此字体下对应的点阵为:宽x高=16x16 --*/
0xFC,0x04,0x04,0xFC,0x00,0x7E,0x26,0x3A,0x22,0xFE,0x32,0x2E,0x2A,0x7E,0x00,0x00,
0x07,0x02,0x02,0x07,0x44,0x35,0x05,0x15,0x65,0x07,0x15,0x65,0x05,0x15,0x64,0x00};
//#define HZK(i) (pgm_read_byte(HZK+(i)))
#define SPLC501_CLK_PORT PORTA
#define SPLC501_CLK_DDR DDRA
#define SPLC501_DIN_PORT PORTA
#define SPLC501_DIN_DDR DDRA
#define SPLC501_A0_PORT PORTA
#define SPLC501_A0_DDR DDRA
#define SPLC501_RES_PORT PORTA
#define SPLC501_RES_DDR DDRA
#define SPLC501_CS_PORT PORTA
#define SPLC501_CS_DDR DDRA
#define SPLC501_CLK 0x01
#define SPLC501_DIN 0x02
#define SPLC501_A0 0x04
#define SPLC501_RES 0x08
#define SPLC501_CS 0x10
void SPLC501SPIWrite(unsigned char data_command,unsigned char a0) //a0=0时表示发送命令,a0=1时表示发送数据
{
unsigned char i;
if(a0)SPLC501_A0_PORT|=SPLC501_A0; //SPLC501_A0=a0;
else SPLC501_A0_PORT&=~SPLC501_A0;
SPLC501_CS_PORT&=~SPLC501_CS; //SPLC501_CS=0;
for(i=0;i<8;i++)
{
SPLC501_CLK_PORT&=~SPLC501_CLK; //SPLC501_CLK=0;
if((data_command&0x80)==0)SPLC501_DIN_PORT&=~SPLC501_DIN;
else SPLC501_DIN_PORT|=SPLC501_DIN; //SPLC501_DIN=(data_command&0x80)==0?0:1;
data_command<<=1;
SPLC501_CLK_PORT|=SPLC501_CLK; //SPLC501_CLK=1;
}
SPLC501_CS_PORT|=SPLC501_CS; //SPLC501_CS=1;
}
void SPLC501LineRun(unsigned char line) //起始行设置.滚屏功能用
{
//if(line>=0x80)line=0; //line=0~63
SPLC501SPIWrite(0x40+line,0); //设置显示起始行对应RAM
}
void LCD_Init(void) //LCD初始化函数
{
SPLC501_RES_PORT&=~SPLC501_RES; //SPLC501_RES=0; //LCD(低电平)复位
_delay_us(100);
SPLC501_RES_PORT|=SPLC501_RES; //SPLC501_RES=1; // RES置高
_delay_us(100);
SPLC501SPIWrite(0xa2,0);//LCD偏压设置:5V:0xa2;3.3V:0xa1.
SPLC501SPIWrite(0xa1,0);//列地址选择为从右到左对应0~127;0xa1:列地址从左到右;0xa0:列地址从右到左
SPLC501SPIWrite(0xc0,0);//行地址从上到下为0~63;0xc0:行地址从上到下;0xc8:行地址从下到上
SPLC501SPIWrite(0x25,0);//V5电压内部电阻调整设置 一般在24~27之间
SPLC501SPIWrite(0x81,0);//亮度调整命令0~63(暗到亮)
SPLC501SPIWrite(0x10,0);//亮度调节为双字节命令,前一个参数控制字的深浅
SPLC501SPIWrite(0x2f,0);//上电控制,打开调压器、稳压器和电压跟随
SPLC501SPIWrite(0xa6,0);//正相反相显示控制指令,RAM中数据不变.0xa6:白底黑字;0xa7:黑底白字.
SPLC501SPIWrite(0xaf,0);//0xae:set display off.0xaf:set display on
}
void Test(unsigned char a,unsigned char b)//全屏测试
{
unsigned int i,j,page=0xb0;//指向首页命令
for(i=0;i<8;i++)
{
SPLC501SPIWrite(page++,0); //指向对应页
SPLC501SPIWrite(0x10,0); //SET COLUMN(列) ADDRESS MSB(高4位)为0
SPLC501SPIWrite(0x04,0); //SET COLUMN ADDRESS LSB(低4位)为0
//SPLC501SPIWrite(0xee); //读改写模式结束指令
for(j=0;j<64;j++)
{
SPLC501SPIWrite(a,1);
SPLC501SPIWrite(b,1);
}
}
}
//显示一个字或多个字函数
void DisplayWords(unsigned int p, //指向图片数组首地址
unsigned char page_f, //起始页
unsigned char page_sum, //占多少页
unsigned char column_f, //起始列
unsigned char column_sum) //占多少列
{
unsigned char i,j;
unsigned char page=0xb0; //指向首页命令
for(i=page_f;i<page_sum+page_f;i++)
{
SPLC501SPIWrite(page+i,0);
SPLC501SPIWrite(0x10|(column_f>>4),0); //设定列地址高4位为0
SPLC501SPIWrite(0x04|(0x0f&column_f),0); //设定列地址低4位为0
for(j=0;j<column_sum;j++)SPLC501SPIWrite(pgm_read_byte(p++),1);
}
}
//系统时钟:11059200Hz 分频:1024
//CTC TOP值:0x35
//误差:0.000000个系统周期
//Timer2初始化
volatile unsigned int sign_5ms=0;
void Timer2Init(void)
{
TCNT2=0x00;
OCR2=0x35;
TCCR2=(1<<WGM21)|(1<<CS22)|(1<<CS21)|(1<<CS22);
//TCNT2=0xcb;
TIMSK|=1<<OCIE2;
}
//Timer2 CTC中断,此中断发生周期是:5毫秒
ISR(TIMER2_COMP_vect)
{
sign_5ms+=1;
}
//系统时钟:11059200Hz 分频:256
//CTC TOP值:0xA8C0
//误差:0.000000个系统周期
//Timer1初始化
volatile unsigned char sign_1s=0;
void Timer1Init(void)
{
TCCR1A=0;
TCCR1B=(1<<WGM12)|(1<<CS12);
OCR1A=0xA8C0;
TIMSK|=1<<OCIE1A;
}
//Timer1 CTC中断,此中断发生周期是:1000毫秒
ISR(TIMER1_COMPA_vect)
{
sign_1s++;
}
void MCU_Init(void)
{
SPLC501_CLK_DDR|=SPLC501_CLK;
SPLC501_DIN_DDR|=SPLC501_DIN;
SPLC501_A0_DDR|=SPLC501_A0;
SPLC501_CS_DDR|=SPLC501_CS;
SPLC501_RES_DDR|=SPLC501_RES;
}
int main(void)
{
unsigned char i=32;
unsigned char j=0;
unsigned char lie=16;
unsigned char n=0;
unsigned char hang=0;
unsigned char line=0;
MCU_Init();
LCD_Init();
Timer1Init();
Timer2Init();
asm("sei");
//Test(0xaa,0x55); //全屏测试
Test(0x00,0x00); //数据清0
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+j*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+j*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
n=0;
hang+=2;
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+j*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+(j++)*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+2*i ,hang,2,(n++)*lie,16);
DisplayWords((unsigned int)HZK+2*i ,hang,2,(n++)*lie,16);
while(1)
{
//if(sign_5ms>=200)
if(sign_1s)
{
//sign_5ms=0;
sign_1s=0;
line&=0x3f; //line=0~63
SPLC501LineRun(line--); //滚屏
}
}
}
void Frame_dis(unsigned char *p)//显示128×64图像函数,指针p指向图片数组首地址
{ //frame 帧
unsigned char i,j;
unsigned char page=0xb0; //指向首页命令
for(i=0;i<8;i++) //共8页
{
SPLC501SPIWrite(page++,0);
SPLC501SPIWrite(0x10,0); //设定列地址高4位为0
SPLC501SPIWrite(0x04,0); //设定列地址低4位为0
for(j=0;j<128;j++)SPLC501SPIWrite(*p++,1);//共128列
}
}
void Plot(unsigned char *P) //p指向曲线数组首地址
{
unsigned char i,j;
unsigned char x,x1;
unsigned int d;
SPLC501SPIWrite(0x10,0); //SET COLUMN ADDRESS MSB
SPLC501SPIWrite(0x04,0); //SET COLUMN ADDRESS LSB,
for(i=0;i<128;i++)
{
d=*P;
if(d>63)d=63;
x=7-d/8;
x1=7-(d&7);
for(j=0;j<8;j++)
{
SPLC501SPIWrite(0xb0+j,0);//
SPLC501SPIWrite(0x10|((0xf0&i)>>4),0); //SET COLUMN ADDRESS MSB
SPLC501SPIWrite(0x00|(0x0f&i),0); //SET COLUMN ADDRESS LSB,
if(j!=x)SPLC501SPIWrite(0,1);
else SPLC501SPIWrite(1<<x1,1);
}
}
SPLC501SPIWrite(0x40,0); //start h
}
/////----- 图形显示模式 -----/////
void LCD501_PutPixel(unsigned char x,unsigned char y) //画点子程序
{
unsigned char x_low,x_hight; //定义列地址的高低位指令
unsigned char Dot_Mask_Buf=0x01;
unsigned char y_Page; //用于存放要画点的位置所在的byte数据位置
x+=4;
x_low=(x&0x0f); //定位列地址设置的低位指令
x_hight=(x>>4)+0x10; //定位列地址设置的高位指令
y_Page=y&0x07; //取低三位
while(y_Page!=0)
{
Dot_Mask_Buf<<=1;
y_Page--;
}
y_Page=y>>3; //Get the page of the byte
SPLC501SPIWrite(0xb0+y_Page,0);
SPLC501SPIWrite(x_low,0);
SPLC501SPIWrite(x_hight,0);
//SPLC501SPIWrite(0xe0,0); //设置为读写改模式
/*y_Page = F_SPLC501_Read_Data(); //
switch(CurPaintMode)
{
case 2: y_Page=y_Page&(~Dot_Mask_Buf);
break;
case 3: x=y_Page^Dot_Mask_Buf;
x=x&Dot_Mask_Buf;
y_Page=(y_Page&(~Dot_Mask_Buf))|x;
break;
default: y_Page=y_Page|Dot_Mask_Buf;
break;
}*/
y_Page=y_Page|Dot_Mask_Buf;
SPLC501SPIWrite(y_Page,1); //
//SPLC501SPIWrite(0xee,0); //读写改模式结束
}
//参数:x 要画线的x起点坐标 y 要画的线的y起点坐标
// ex 要画线的x终点坐标 ey要画的线的y起点坐标
void LCD501_Line(char x,char y,char ex,char ey) //画直线程序
{
char Offset_x,Offset_y;
char Offset_k=0;
unsigned char signErr_d=1;
if(y>ey)
{
Offset_x=x;
x=ex;
ex=Offset_x;
Offset_x=y;
y=ey;
ey=Offset_x;
}
Offset_x=ex-x;
Offset_y=ey-y;
LCD501_PutPixel(x,y);
if(Offset_x<=0)
{
Offset_x = x-ex;
signErr_d=0;
}
if(Offset_x>Offset_y)
{
while(x!=ex)
{
if(Offset_k>0)
{
y+=1;
Offset_k+=(Offset_y-Offset_x);
}
else Offset_k+=Offset_y;
if(signErr_d)x+=1;
else x-=1;
LCD501_PutPixel(x,y);
}
}
else
{
while(y!=ey)
{
if(Offset_k>0)
{
if(signErr_d)x+=1;
else x-=1;
Offset_k+=(Offset_x-Offset_y);
}
else Offset_k+=Offset_x;
y+=1;
LCD501_PutPixel(x,y);
}
}
}
//参数:x要画的圆心的x坐标 y要画的圆心的y坐标 r半径
// Mode绘点模式:0 画圆框;1 画实心圆
//extern void W_Red_Err(int *a,int *b,int *r);
void LCD_PaintRed_Dot(char x,char y,char a,char b,char mode)//画圆程序
{
if(mode)
{
LCD501_Line(x+a,y+b,x-a,y+b);
LCD501_Line(x+a,y-b,x-a,y-b);
}
else
{
LCD501_PutPixel(x+a,y+b);
LCD501_PutPixel(x-a,y+b);
LCD501_PutPixel(x+a,y-b);
LCD501_PutPixel(x-a,y-b);
}
}
/*
void LCD501_Circle(unsigned char x,unsigned char y,unsigned char r,unsigned char Mode)
{
char arx1=0,ary1,arx2,ary2=0;
unsigned char uiTemp;
ary1=r;
arx2=r;
uiTemp = LCD501_GetPaintMode();
LCD501_SetPaintMode(0);
while(1)
{
LCD_PaintRed_Dot(x,y,arx1,ary1,Mode);
W_Red_Err(&arx1,&ary1,&r);
if(arx1==arx2)
{
LCD_PaintRed_Dot(x,y,arx1,ary1,Mode);
break;
}
LCD_PaintRed_Dot(x,y,arx2,ary2,Mode);
W_Red_Err(&ary2,&arx2,&r);
if(arx1==arx2)
{
LCD_PaintRed_Dot(x,y,arx2,ary2,Mode);
break;
}
}
LCD501_SetPaintMode(uiTemp);
}
//程序:void LCD501_Rectangle(unsigned int left, unsigned int top,
// unsigned int right, unsigned int bottom, unsigned int Mode)
//描述:画矩形程序
//参数:left - 矩形的左上角横坐标,范围0到118
// top - 矩形的左上角纵坐标,范围0到50
// right - 矩形的右下角横坐标,范围1到119
// bottom - 矩形的右下角纵坐标,范围1到51
// Mode - 绘制模式,可以是下列数值之一:
// 0: 矩形框(空心矩形)
// 1: 矩形面(实心矩形)
//声明:xinqiang 20050521 sunnorth Mz Design
//注意:无
void LCD501_Rectangle(unsigned int left, unsigned int top, unsigned int right, unsigned int bottom, unsigned int Mode)
{
unsigned int uiTemp;
if(left>right)
{
uiTemp = left;
left = right;
right = left;
}
if(top>bottom)
{
uiTemp = top;
top = bottom;
bottom = uiTemp;
}
if(Mode==0)
{
LCD501_Line(left,top,left,bottom);
LCD501_Line(left,top,right,top);
LCD501_Line(right,bottom,left+1,bottom);
LCD501_Line(right,bottom,right,top+1);
}
else
{
for(uiTemp=top;uiTemp<=bottom;uiTemp++)
{
LCD501_Line(left,uiTemp,right,uiTemp);
Clear_Watchdog();
}
}
}
//程序:void LCD501_PutString(int x,int y,unsigned int a) [8x16] [6X8]
//描述: 显时8X16、6X8的自带ASCII字符,任意行定位
//参数:x 显示字符的起始列(0~128) y 显示字符的起始行(0~63)
// a ASCII码
//声明: xinqiang 20050519 sunnorth Mz Design
//注意:
void LCD501_PutString(int x,int y,unsigned int * string)
{
unsigned int x_err=6,y_err=8;
if(CurASCIIFont)
{
x_err = 8;
y_err = 16;
}
while(*string!=0)
{
if((x+x_err)>127)
{
x = 0;
y = y+y_err;
}
if(y>63) y =0;
LCD501_PutChar(x,y,*string);
string++;
x+=x_err;
}
}*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -