这是一个用51将HT6221红外编码解码 并将码通过串口发送给PC 用vb编写PC接收程序实现鼠标移动、待机、一键虚拟键盘、小键盘、鼠标左键单双击、鼠标右键单击的程序,没有多键触控,设置串口码率1200bps com4 无奇偶校验 屏幕分辨率1280*800,下面是51程序,AT89S52测试通过
//*********************************************************
//利用HT6221接收遥控器编码,并用1602实时显示 串口发送给电脑
//2010年1月15日 by ch
//*********************************************************
#include<reg52x2.h>
#include <intrins.h>
typedef unsigned char INT8U; //无符号8位数
typedef signed char INT8S; //有符号8位数
typedef unsigned int INT16U; //无符号16位数
typedef signed int INT16S; //有符号16位数
typedef unsigned long INT32U; //无符号32位数
typedef signed long INT32S; //有符号32位数
typedef float FP32; //单精度浮点数
typedef double FP64; //双精度浮点数
INT8U SRDATA[]={'0','0',0x0d,0x0a,0x00} ;
INT8U IRCommandData;
INT8U da[4]={0,0,0,0};
INT8U temp;
INT8U code dsptab[16]={'0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f'};//字符代表码;
sbit LCD_RS= P2^0;//定义LCD引脚
sbit LCD_RW= P2^1;
sbit LCD_E= P2^2;
sbit IR=P3^6;//接红外
sbit beep=P3^7;
//---------------------------------------------------------------
//-------------------延时子程序----------------------------------
void delay(INT16U a) //延时程序
{
INT16U b;
for (b=0;b<a;b++);
}
void delayKms(INT8U pp) //延时程序
{
while (pp--)
{
unsigned char j;
for (j = 0;j<123;j++); //j进行的内部循环,1次延迟8us,延迟1ms
}
}
/*----------------------------------------------------------------
-------------------读状态----------------------------------------*/
//读状态子程序;有返回值;返回值类型为CHAR型;
//读回的状态通过RETURN返回;
INT8U read_estate(void) //定义有返回值的函数;
{
P0=0Xff; //把LCD端口全置1方便读取信号;
LCD_RS=0; //RS置0;
LCD_RW=1; //RW置1;
LCD_E=0; //E端置0;
delay(10); //短延时;
LCD_E=1; //E端置1;以锁存数据;
while (P0&0x80); //检测忙,则一直循环;
return(P0); //返回读取的信号;
}
/*------------------------------------------------------------------
------------------ 写数据------------------------------------------*/
//写数据子程序;无返回值;输入变量I;
//I为要写入LCD中的数据;
//数据类型CHAR形;
void write_data(INT8U i) //定义输入变量值I;
{
read_estate(); //检测忙信号;
P0=i; //把I中数据送到LCD数据端;
LCD_RS=1; //RS置1;
LCD_RW=0; //RW置0;
LCD_E=0; //E置0;
delay(10); //短延时;
LCD_E=1; //E置1;以锁存数据;
}
/*---------------------------------------------------------------------
------------------ 写指令--------------------------------------------*/
//写指令子程序;无返回值;输入二个变量I和J.
//I为要写入LCD的指令;J为判断要不要检测忙.
//如果J为0则不判断检测忙;
//如果J为1则判断检测忙;
void write_dictate(INT8U i,j) //定义二个变量;
{
if (j)read_estate(); //根据需要检测忙;
P0=i; //把要写入的数据送到LCD数据端;
LCD_RS=0; //RS置0;
LCD_RW=0; //RW置0;
LCD_E =0; //E端置0;
delay(10); //延时;
LCD_E =1; //E端置1;以锁存数据;
}
/*---------------------------------------------------------------
-------------------读数据--------------------------------------*/
//读数据子程序;有返回值,返回值类型为CHAR型;
/*
INT8U read_data(void) //定义有返回值的子函数;
{
LCD_DATA=0Xff; //LCD数据端口置1;
LCD_RS=1; //RS置1;
LCD_RW=1; //RW置1;
LCD_E=0; //E置0;
delay(10); //短延时;
LCD_E=1; //E置1;以锁存数据;
return(LCD_DATA); //返回读取的值;
}
*/
/*---------------------------------------------------------------------
------------------ LCD初始化-----------------------------------------*/
//LCD初始化程序;主要作用初始化LCD,对LCD进行复位以及设置;
void initialization(void) //定义函数;
{
delay(50); //延时5MS;
write_dictate(0x38,0); //写指令38H;不检测忙;
delay(50); //延时5MS;
write_dictate(0x38,0); //写指令38H;不检测忙;
delay(50); //延时5MS;
write_dictate(0x38,0); //写指令38H;不检测忙;
delay(50);
write_dictate(0x38,1); //显示模式设置;检测忙;
write_dictate(0x08,1); //关闭显示;检测忙;
write_dictate(0x01,1); //显示清屏;检测忙;
write_dictate(0x06,1); //显示光标移动设置;检测忙;
write_dictate(0x0C,1); //显示开及光标设置;检测忙;
}
/*---------------------------------------------------------------
-------------------在指定位置显示一个字符----------------------*/
void displayonechar(INT8U x, y,ddata)
{
y &= 0x01;
x &= 0x0f; //限制X不能大于15,Y不能大于1
if (y) x+= 0x40; //当要显示第二行时地址码+0x40;
x+= 0x80; //算出指令码
write_dictate(x,0); //这里不检测忙信号,发送地址码
write_data(ddata);
}
/*---------------------------------------------------------------
-------------------在指定位置显示一串字符----------------------*/
void displaylistchar(INT8U x,y,INT8U code *ddata)
{
INT8U a=0;
y&=0x01;
x&=0xf;
while (ddata[a]>0x20)
{
if (x<=0xff)
{
displayonechar(x, y,ddata[a]);
a++;
x++;
}
}
}
//============主程序====================================================
//============主程序====================================================
void d870us(void)
{
//delay(108);//12M
INT8U i;
for (i=0;i<219;i++)
{
_nop_();
}
}
void d1000us(void)
{
INT8U k;
for (k=0;k<248;k++)
{
_nop_();
}
}
void d4740us(void)
{
// delay(593);//12M
INT16U j;
for (j=0;j<720;j++)
{
_nop_();
}
}
//----------------------------------------------------
//-----------------------------------------------
// ht6221解码程序
//-----------------------------------------------
INT8U IRDecode(void)
{
INT8U i,m,n;
for (i=0;i<10;i++)
{
d870us();
if (IR)
{
break;
}
}
while (!IR);
d4740us();
//开始解码
for (m=0;m<4;m++)
{
for (n=0;n<8;n++)
{
while (!IR);
d870us();
if (IR)
{
d1000us();
da[m]=da[m]>>1;
da[m]=da[m]|0x80;
}
else
{
da[m]=da[m]>>1;
da[m]=da[m]|0;
}
// while(IR);
//while(!IR);
}
}
if ((da[0]==0x0)&&(da[1]==0xFF))
{
if (da[2]==(~da[3]))
{
beep=0;
delayKms(50);
beep=1;
return da[2];
}
}
}
void SendData(INT8U c)
{
P0=c;
}
[
本帖最后由 ch0721 于 2011-2-19 21:43 编辑 ]