|
/***********************************************
16x32點(diǎn)陣屏16級(jí)灰度顯示
單片機(jī):STC12C5616AD
程序原創(chuàng):徐長偉
時(shí)間:2015/08/03
//分五場掃描增加亮度,全高PWM掃三場,1/2PWM一場,1/4PWM一場
//每個(gè)char數(shù)據(jù)存兩個(gè)點(diǎn)的數(shù)據(jù)以節(jié)約空間
***********************************************/
#include<STC12C56.H>
#include"mydef.h"
#include"init.h"
/********延時(shí)函數(shù)2***********/
void delay(uint a)
{
uint c;
for(c=0;c<50000;c++)
for(;a>0;a--);
}
/********清0函數(shù)***********/
void delete ()
{
uchar m,n;
for(m=0;m<16;m++)
{
for(n=0;n<16;n++)
{
dispram[n+m*16]=0;
disphuan[n+m*16]=0;
}
}
}
/********串口發(fā)送函數(shù)***********/
void UART_Send (uchar dat)
{
TI=0;
SBUF=dat;
while(!TI);
TI=0;
}
/********灰度修正函數(shù)***********/
void huidu_chuli ()
{
uint i;
uchar x,y;
for(i=0;i<256;i++)
{
x=dispram[i]&0xf0;
y=dispram[i]&0x0f;
x>>=4;
//if(x>0&&x<15)
x-=4;
//if(y>0&&y<15)
y-=4;
if(x>15)x=0;
if(y>15)y=0;
dispram[i]=0;
dispram[i]=x<<4;
dispram[i]|=y;
}
for(i=0;i<256;i++)
{
x=disphuan[i]&0xf0;
y=disphuan[i]&0x0f;
x>>=4;
//if(x>0&&x<15)
x-=4;
//if(y>0&&y<15)
y-=4;
if(x>15)x=0;
if(y>15)y=0;
disphuan[i]=0;
disphuan[i]=x<<4;
disphuan[i]|=y;
}
}
/********74HC595移位寄存器送數(shù)子函數(shù)***********/
/*
void song(uchar z,uchar y)//帶參數(shù)函數(shù)
{
uchar num;//定義變量
for(num=0;num<8;num++)//移動(dòng)8次將數(shù)據(jù)發(fā)送完畢
{
CLK=0;//上升沿送走數(shù)據(jù)
if(z&0x01==1)//將高7位屏蔽掉,保留最低位判斷 ////////上半屏(右半屏)
DATA=1;//為1就將74HC595數(shù)據(jù)端置1
else
DATA=0;//否則給0
if(y&0x01==1)//將高7位屏蔽掉,保留最低位判斷 ////////下半屏(左半屏)
DATA_TOP=1;//為1就將74HC595數(shù)據(jù)端置1
else
DATA_TOP=0;//否則給0
CLK=1;//高電平形成上升沿
z>>=1;//將數(shù)移走一位
y>>=1;
}
}
*/
/********灰度分場處理函數(shù)***********/
void huidu ()
{
static uchar k,l,s,ss,v,num;
uchar temp,temp1,temp2;
v=hang;//下一行
for(k=0;k<32;k++)
{
Gray[k]=0;//清除內(nèi)存
}
for(num=0;num<4;num++)//每次存一行的點(diǎn)的全部4BIT(權(quán)*N,N=0~3)灰度值
{
for(k=0;k<4;k++)//Gray數(shù)組里每個(gè)字節(jié)存4個(gè)點(diǎn)的權(quán)*N位灰度值,32行點(diǎn)陣分為16行*2,所以要4*2=8個(gè)字節(jié)
{
s=8;
for(l=0;l<4;l++)//Gray里每個(gè)字節(jié)存兩個(gè)點(diǎn)的灰度值(16級(jí)灰度來說)每次存兩個(gè)點(diǎn)的各一位灰度(即兩位)循環(huán)4次就是8位
{
ss=s-1;
temp2=l+(k<<2)+(v<<4);
temp=dispram[temp2];//把內(nèi)存里數(shù)據(jù)依次調(diào)出
temp1=disphuan[temp2];//把內(nèi)存里數(shù)據(jù)依次調(diào)出
Gray[k+(num<<3)]|=((temp>>p)&0x01)<<ss;//右移4位后數(shù)據(jù)高4位的后半字節(jié)依次將BIT4-BIT7右移
Gray[k+4+(num<<3)]|=((temp1>>p)&0x01)<<ss;
p-=4;//右移指針等于0處理前半字節(jié)
s--;//左移指針減一以便依次將每一組BIT位從高位至低位順序存入Gray[k]
ss=s-1;
Gray[k+(num<<3)]|=((temp>>p)&0x01)<<ss;//右移0位后數(shù)據(jù)低4位的數(shù)據(jù)前半字節(jié)依次將BIT0-BIT3右移
Gray[k+4+(num<<3)]|=((temp1>>p)&0x01)<<ss;
p+=4;//右移指針等于4處理后半字節(jié)
s--;//左移指針再減一
}
}
p++;//將數(shù)據(jù)灰度值右移一位(第0BIT直到第3BIT)
}
p=4;//右移4位后復(fù)位到4
}
/***************串口初始化函數(shù)*****************/
void UART_OK ()
{
CCAPM1=0X00;
P3M0=0x00;
P3M1=0x00;
SCON=0X40;//串口方式1/REN=0
PCON=0X80;// 波特率倍增
TMOD = 0x20; // TMOD: timer 1, mode 2, 8-bit 重裝
TH1= 0xFD; // TH1: 重裝值 57600 波特率 晶振 33.1776MHz
TL1= 0xFD;
TR1= 1; // TR1: timer 1 打開
PPCA_LVD=0;
EPCA_LVD=0;
ES=0;
REN=1;
PS=1;
IPH|=~PPCA_LVDH;
EA=1;
TR0 = 0;
}
/***************主函數(shù)*****************/
void main()
{
uchar n;
//Init();
delay(3000);
UART_OK();
CCAP1L=PWM_1_8;
CCAP1H=PWM_1_4;
qie=0;
while(1)
{
if(!flag_es_ok)
{
while(aa!=_READY_) //從機(jī)等待主機(jī)發(fā)送的握手信號(hào)
{
UART_Send (_STAR_);
if(RI)
{
aa=SBUF;
RI=0;
}
}
UART_Send (_OK_);
ES=1;
}
check=255;//數(shù)據(jù)校驗(yàn)初值
while(!flag_es_ok);
if(!flag_es_init) huidu_chuli ();//灰度修正
if(!flag_es_init){flag_es_init=1;Init();}
if(qie==TIME_1)
{
LED=1;
aa=_BUSY_;
flag_es_init=0;
flag_es_ok=0;
ISP_CONTR|=SWRST;//軟復(fù)位
}
if(flag_zhen)//如果一幀掃描完就右移一次
{
flag_zhen=0;
if(++hang==16)//顯示16行
{
hang=0;
qie++;
}
}
if(flag_qie){flag_qie=0;huidu ();}//灰度分解
if(flag_chang)////每場進(jìn)入一次/如果一場掃描完再切到下一行避免虛影
{
if(flag_es_ok)
{
for(n=8;n>0;n--)//lienum=595片數(shù)//595片數(shù)=6以上顯示才穩(wěn)定song(~Gray[n-1],~Gray[n+3]);
{
if(n>4)
{
_datu=~Gray[n-5+(t<<3)];
_datd=~Gray[n-1+(t<<3)];
DATA=_datu0;
DATA_T |
|