首页 > 其他分享 >基于51单片机的 智能路灯系统 纯原创

基于51单片机的 智能路灯系统 纯原创

时间:2024-10-08 20:48:51浏览次数:9  
标签:路灯 Delay 51 unsigned param char 单片机 LCD Line

题目

硬件

用到 单片机三块 一个主控 两个副控 分为主路控制器和支路控制器

两个LED灯

一个LCD屏幕 

两个红外感应

两个双端光敏电阻

一个三端光敏电阻

以及 时钟模块

代码

主要模块代码

主控

#include <REGX52.H>
#include "DS1302.h"
#include "LCD1602.h"
#include "XPT2046.h"
#include "MatrixKey.h"
#include "Buzzer.h"


unsigned char Key=0;
unsigned char Time[] = {24,10,10,17,59,55,1};//


unsigned char SetTimeA[] = {18,0,5};
unsigned char OffTimeA[] = {6,0,0};


unsigned char SetTimeB[] = {18,0,10};
unsigned char OffTimeB[] = {6,0,0};

unsigned char WT;
unsigned char ADValue;
unsigned char ifopen = 0;

unsigned int TimeO;
unsigned int TimeA;
unsigned int TimeB;


///

void LCD_time()
{
	 DS1302_ReadTime();
	 LCD_ShowNum(1,1,DS1302_Time[0],2);
	 LCD_ShowChar(1,3,'/');
	 LCD_ShowNum(1,4,DS1302_Time[1],2);
	 LCD_ShowChar(1,6,'/');
	 LCD_ShowNum(1,7,DS1302_Time[2],2);
	 
	 LCD_ShowNum(2,1,DS1302_Time[3],2);
	 LCD_ShowChar(2,3,':');
	 LCD_ShowNum(2,4,DS1302_Time[4],2);
	 LCD_ShowChar(2,6,':');
	 LCD_ShowNum(2,7,DS1302_Time[5],2);
}

void LCD_ShowTimechange()
{
   LCD_ShowNum(1,1,Time[0],2);
	 LCD_ShowChar(1,3,'/');
	 LCD_ShowNum(1,4,Time[1],2);
	 LCD_ShowChar(1,6,'/');
	 LCD_ShowNum(1,7,Time[2],2);
	 
	 LCD_ShowNum(2,1,Time[3],2);
	 LCD_ShowChar(2,3,':');
	 LCD_ShowNum(2,4,Time[4],2);
	 LCD_ShowChar(2,6,':');
	 LCD_ShowNum(2,7,Time[5],2);
}


void LCD_ShowSetTimeA()
{
   LCD_ShowNum(2,1+8,SetTimeA[0],2);
	 LCD_ShowChar(2,3+8,':');
	 LCD_ShowNum(2,4+8,SetTimeA[1],2);
	 LCD_ShowChar(2,6+8,':');
	 LCD_ShowNum(2,7+8,SetTimeA[2],2);
}

void LCD_ShowOffTimeA()
{
   LCD_ShowNum(1,1+8,OffTimeA[0],2);
	 LCD_ShowChar(1,3+8,':');
	 LCD_ShowNum(1,4+8,OffTimeA[1],2);
	 LCD_ShowChar(1,6+8,':');
	 LCD_ShowNum(1,7+8,OffTimeA[2],2);
}

void LCD_ShowSetTimeB()
{
   LCD_ShowNum(2,1+8,SetTimeB[0],2);
	 LCD_ShowChar(2,3+8,':');
	 LCD_ShowNum(2,4+8,SetTimeB[1],2);
	 LCD_ShowChar(2,6+8,':');
	 LCD_ShowNum(2,7+8,SetTimeB[2],2);
}

void LCD_ShowOffTimeB()
{
   LCD_ShowNum(1,1+8,OffTimeB[0],2);
	 LCD_ShowChar(1,3+8,':');
	 LCD_ShowNum(1,4+8,OffTimeB[1],2);
	 LCD_ShowChar(1,6+8,':');
	 LCD_ShowNum(1,7+8,OffTimeB[2],2);
}


void InitDS1302WithTime()
{
	DS1302_init();
	DS1302_WriteByte(0x8E,0x00);
	//Give time
  DS1302_SetTime();
}



void Int0_Init(void)
{
	IT0=1;
	IE0=0;
	EX0=1;
	EA=1;
	PX0=1;
}

//

void ReadTimeToDs1302()
{
   int i = 0;
	 DS1302_ReadTime();
	 for(i = 0;i<=7;i++)
	 {
	    Time[i] = DS1302_Time[i];
	 }
}

void WriteTimeToDs1302()
{
   int i = 0;
	 for(i = 0;i<=7;i++)
	 {
			DS1302_Time[i] = Time[i];  
	 }
	 DS1302_SetTime();
}

void ChangeTimePart()
{  
	 ReadTimeToDs1302();
	 LCD_time();
	 while(1)
	 {
	  Key = 0;
		while(Key == 0)
		Key = MatrixKey();
		
		WT = Key - 1;
		
		if(Key == 1 || Key == 2 || Key == 3|| Key == 4||Key == 5||Key == 6)//year
		 {
	     while(1)
			 {
				 Key = 0;
				 while(Key == 0)
		     Key = MatrixKey();
				 if(Key == 1)
				 Time[WT] += 1;
				 if(Key == 2)
				 Time[WT] -= 1;
				 if(Key == 3)
				 Time[WT] += 10;
				 if(Key == 4)
				 Time[WT] -= 10;
				 
				 LCD_ShowTimechange();
				 
				 if(Key == 16)
		     {
		     Key = 0;
		     break;
		     }
			 }

				if(Key == 16)
				{
				Key = 0;
				break;
				}
			 
	   }
	 
	  if(Key == 16)
		{
		  Key = 0;
		  break;
		}
	 }
	 
	 WriteTimeToDs1302();
}

void ChangeTimePart_AA()
{
   LCD_ShowSetTimeA();
   while(1)
	 {
	  Key = 0;
		while(Key == 0)
		Key = MatrixKey();
		
		WT = Key - 1;
		
		if(Key == 1 || Key == 2 || Key == 3)
		 {
	     while(1)
			 {
				 Key = 0;
				 while(Key == 0)
		     Key = MatrixKey();
				 if(Key == 1)
				 SetTimeA[WT] += 1;
				 if(Key == 2)
				 SetTimeA[WT] -= 1;
				 if(Key == 3)
				 SetTimeA[WT] += 10;
				 if(Key == 4)
				 SetTimeA[WT] -= 10;
				 
			   LCD_ShowSetTimeA();
				 
				 if(Key == 16)
		     {
		     Key = 0;
		     break;
		     }
			 }

				if(Key == 16)
				{
				Key = 0;
				break;
				}
			 LCD_ShowSetTimeA();
	   }
	 
	  if(Key == 16)
		{
		  Key = 0;
		  break;
		}
	 }
	 
}

void  ChangeTimePart_AB()
{
 LCD_ShowOffTimeA();
   while(1)
	 {
	  Key = 0;
		while(Key == 0)
		Key = MatrixKey();
		
		WT = Key - 1;
		
		if(Key == 1 || Key == 2 || Key == 3)
		 {
	     while(1)
			 {
				 Key = 0;
				 while(Key == 0)
		     Key = MatrixKey();
				 if(Key == 1)
				 OffTimeA[WT] += 1;
				 if(Key == 2)
				 OffTimeA[WT] -= 1;
				 if(Key == 3)
				 OffTimeA[WT] += 10;
				 if(Key == 4)
				 OffTimeA[WT] -= 10;
				 
			   LCD_ShowOffTimeA();
				 
				 if(Key == 16)
		     {
		     Key = 0;
		     break;
		     }
			 }

				if(Key == 16)
				{
				Key = 0;
				break;
				}
			 LCD_ShowOffTimeA();
	   }
	 
	  if(Key == 16)
		{
		  Key = 0;
		  break;
		}
	 }
	 
}

void ChangeTimePart_BA()
{
   LCD_ShowSetTimeB();
   while(1)
	 {
	  Key = 0;
		while(Key == 0)
		Key = MatrixKey();
		
		WT = Key - 1;
		
		if(Key == 1 || Key == 2 || Key == 3)
		 {
	     while(1)
			 {
				 Key = 0;
				 while(Key == 0)
		     Key = MatrixKey();
				 if(Key == 1)
				 SetTimeB[WT] += 1;
				 if(Key == 2)
				 SetTimeB[WT] -= 1;
				 if(Key == 3)
				 SetTimeB[WT] += 10;
				 if(Key == 4)
				 SetTimeB[WT] -= 10;
				 
			   LCD_ShowSetTimeB();
				 
				 if(Key == 16)
		     {
		     Key = 0;
		     break;
		     }
			 }

				if(Key == 16)
				{
				Key = 0;
				break;
				}
			 LCD_ShowSetTimeB();
	   }
	 
	  if(Key == 16)
		{
		  Key = 0;
		  break;
		}
	 }
	 
}

void  ChangeTimePart_BB()
{
 LCD_ShowOffTimeB();
   while(1)
	 {
	  Key = 0;
		while(Key == 0)
		Key = MatrixKey();
		
		WT = Key - 1;
		
		if(Key == 1 || Key == 2 || Key == 3)
		 {
	     while(1)
			 {
				 Key = 0;
				 while(Key == 0)
		     Key = MatrixKey();
				 if(Key == 1)
				 OffTimeB[WT] += 1;
				 if(Key == 2)
				 OffTimeB[WT] -= 1;
				 if(Key == 3)
				 OffTimeB[WT] += 10;
				 if(Key == 4)
				 OffTimeB[WT] -= 10;
				 
			   LCD_ShowOffTimeB();
				 
				 if(Key == 16)
		     {
		     Key = 0;
		     break;
		     }
			 }

				if(Key == 16)
				{
				Key = 0;
				break;
				}
			 LCD_ShowOffTimeB();
	   }
	 
	  if(Key == 16)
		{
		  Key = 0;
		  break;
		}
	 }
	 
}

 void Int0_Routine(void) interrupt 0
{
	while(1)
	{
	  while(Key == 0)
	  Key = MatrixKey();

		if(Key == 13)
		{
		   ChangeTimePart();
		}
		
		if(Key == 14)
		{ 
		   ChangeTimePart_AA();
	  }
		
		if(Key == 15)
		{
		   ChangeTimePart_AB();
		}
		
		if(Key == 10)
		{ 
		   ChangeTimePart_BA();
	  }
		
		if(Key == 11)
		{
		   ChangeTimePart_BB();
		}
		
    if(Key == 16)
		{
		  Key = 0;
		  break;
		}
	}
}

//

//unsigned char Time[] = {24,10,10,17,59,55,1};

//unsigned char SetTime[] = {18,0,0};
//unsigned char OffTime[] = {6,0,0};




void LedWithTime()
{
   DS1302_ReadTime();
	 
	 TimeO = DS1302_Time[3]*60*60 + DS1302_Time[4]*60 + DS1302_Time[5];
	 TimeA = SetTimeA[0]*60*60 + SetTimeA[1]*60 + SetTimeA[2];	 
	 TimeB = OffTimeA[0]*60*60 + OffTimeA[1]*60 + OffTimeA[2];	 
	
	 if(TimeO > TimeB && TimeO < TimeA)  
   {
	 P2_0 = 1;
	 ifopen = 0;
	 }
	 else
	 {
	 P2_0 = 0;
	 ifopen = 1;
	 }
	 
	 TimeO = DS1302_Time[3]*60*60 + DS1302_Time[4]*60 + DS1302_Time[5];
	 TimeA = SetTimeB[0]*60*60 + SetTimeB[1]*60 + SetTimeB[2];	 
	 TimeB = OffTimeB[0]*60*60 + OffTimeB[1]*60 + OffTimeB[2];	
	 
	 if(TimeO > TimeB && TimeO < TimeA)  
   {
	 P2_2 = 1;
	 ifopen = 0;
	 }
	 else
	 {
	 P2_2 = 0;
	 ifopen = 1;
	 }
	 
	 
	 ADValue = XPT2046_ReadAD(XPT2046_VBAT); 
	 
	 if(ADValue <= 16)
	 {
	 P2_1 = 0;
	 }
	 else
	 {
	 P2_1 = 1;
	 }
	 
	 
	 
	 if(ADValue >= 28)
	 {
	 while(XPT2046_ReadAD(XPT2046_VBAT)>=28)
	 { 
	 P2_0 = 1;
	 P2_2 = 1;
	 }
	 }
	 else
	 {
	 
	 if(ifopen == 1)
	 {
	 P2_0 = 0;
	 P2_2 = 0;
	 }

	 }

}


void AD()
{
   
	 if(P3_0 == 0)
	 {P2_3 = 0;Buzzer_Time_500HZ(100);}
	 else
	 P2_3 = 1;
	 
	 if(P3_1 == 0)
	 {P2_4 = 0;Buzzer_Time_500HZ(100);}
	 else
	 P2_4 = 1;
}

//

int main()
{
	 LCD_Init();
   Int0_Init();
	 InitDS1302WithTime();
	 
	 while(1)
	 { 
	 LCD_time();
   LedWithTime();
	 AD();
	 }
}

支路控制代码

#include <REGX52.H>

#define uchar unsigned char

sbit key = P3^3;
void Delay(unsigned int t)
{
	while(t--);
}
void Adelay(unsigned int i)
{
	unsigned int j;
	for(;i>0;i--)
		for(j=0;j<333;j++){}
}

void Delay1000ms(void)	//@11.0592MHz
{
	unsigned char data i, j, k;

	i = 8;
	j = 1;
	k = 5;
	do
	{
		do
		{
			while (--k);
		} while (--j);
	} while (--i);
}

void Int0_Init(void)
{
	IT0=1;
	IE0=0;
	EX0=1;
	EA=1;
	PX0=1;
}

//P3_0 == 0 hei
//P3_0 == 1 ming

//P3_1 == 0 qidong
//P3_1 == 1 guanji

//P0_0 == 0 qidong
//P0_0 == 1 guanji


void main()
{
  Int0_Init();
	
  P3_1 = 1;
	P1_6 = 1;
	P1_5 = 0;
  P1_4 = 1;
	P2_1 = 1;
	while(1)
	{
	while(P3_1 == 0)
	{
	  P1_7 = 1;
	  if(P1_6 == 0)
		{
		   break;
		}
		
		if(P1_4 == 1)
		{
		   P2_1 = 0;
			 P0_0 = 0;
			 while(P1_4 == 1);
			 P2_1 = 1;
			 P0_1 = 1;
		}
		
		if(P3_0 == 1)//PWM
		{
		    P0_0 = 0;
				Delay(2);
				P0_0 = 1;
				Delay(8);
		}
		
		if(P3_0 == 0)//PWM
		{
		    P0_0 = 0;
				Delay(7);
				P0_0 = 1;
				Delay(3);
		}

	}
	
	P2_0 = 0;
	
	}
	
	
}

 void Int0_Routine(void) interrupt 0
{
  if(P3_1 == 0)
  {
	P0_0= 0;
	P1_7= 0;
  while(P3_2 == 0);
  }
}








头文件补充

LCD1602

#include <REGX52.H>

//引脚配置:
sbit LCD_RS=P2^6;
sbit LCD_RW=P2^5;
sbit LCD_EN=P2^7;
#define LCD_DataPort P0

//函数定义:
/**
  * @brief  LCD1602延时函数,12MHz调用可延时1ms
  * @param  无
  * @retval 无
  */
void LCD_Delay()
{
	unsigned char i, j;

	i = 2;
	j = 239;
	do
	{
		while (--j);
	} while (--i);
}

/**
  * @brief  LCD1602写命令
  * @param  Command 要写入的命令
  * @retval 无
  */
void LCD_WriteCommand(unsigned char Command)
{
	LCD_RS=0;
	LCD_RW=0;
	LCD_DataPort=Command;
	LCD_EN=1;
	LCD_Delay();
	LCD_EN=0;
	LCD_Delay();
}

/**
  * @brief  LCD1602写数据
  * @param  Data 要写入的数据
  * @retval 无
  */
void LCD_WriteData(unsigned char Data)
{
	LCD_RS=1;
	LCD_RW=0;
	LCD_DataPort=Data;
	LCD_EN=1;
	LCD_Delay();
	LCD_EN=0;
	LCD_Delay();
}

/**
  * @brief  LCD1602设置光标位置
  * @param  Line 行位置,范围:1~2
  * @param  Column 列位置,范围:1~16
  * @retval 无
  */
void LCD_SetCursor(unsigned char Line,unsigned char Column)
{
	if(Line==1)
	{
		LCD_WriteCommand(0x80|(Column-1));
	}
	else if(Line==2)
	{
		LCD_WriteCommand(0x80|(Column-1+0x40));
	}
}

/**
  * @brief  LCD1602初始化函数
  * @param  无
  * @retval 无
  */
void LCD_Init()
{
	LCD_WriteCommand(0x38);//八位数据接口,两行显示,5*7点阵
	LCD_WriteCommand(0x0c);//显示开,光标关,闪烁关
	LCD_WriteCommand(0x06);//数据读写操作后,光标自动加一,画面不动
	LCD_WriteCommand(0x01);//光标复位,清屏
}

/**
  * @brief  在LCD1602指定位置上显示一个字符
  * @param  Line 行位置,范围:1~2
  * @param  Column 列位置,范围:1~16
  * @param  Char 要显示的字符
  * @retval 无
  */
void LCD_ShowChar(unsigned char Line,unsigned char Column,char Char)
{
	LCD_SetCursor(Line,Column);
	LCD_WriteData(Char);
}

/**
  * @brief  在LCD1602指定位置开始显示所给字符串
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  String 要显示的字符串
  * @retval 无
  */
void LCD_ShowString(unsigned char Line,unsigned char Column,char *String)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=0;String[i]!='\0';i++)
	{
		LCD_WriteData(String[i]);
	}
}

/**
  * @brief  返回值=X的Y次方
  */
int LCD_Pow(int X,int Y)
{
	unsigned char i;
	int Result=1;
	for(i=0;i<Y;i++)
	{
		Result*=X;
	}
	return Result;
}

/**
  * @brief  在LCD1602指定位置开始显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~65535
  * @param  Length 要显示数字的长度,范围:1~5
  * @retval 无
  */
void LCD_ShowNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number/LCD_Pow(10,i-1)%10+'0');
	}
}

/**
  * @brief  在LCD1602指定位置开始以有符号十进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:-32768~32767
  * @param  Length 要显示数字的长度,范围:1~5
  * @retval 无
  */
void LCD_ShowSignedNum(unsigned char Line,unsigned char Column,int Number,unsigned char Length)
{
	unsigned char i;
	unsigned int Number1;
	LCD_SetCursor(Line,Column);
	if(Number>=0)
	{
		LCD_WriteData('+');
		Number1=Number;
	}
	else
	{
		LCD_WriteData('-');
		Number1=-Number;
	}
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number1/LCD_Pow(10,i-1)%10+'0');
	}
}

/**
  * @brief  在LCD1602指定位置开始以十六进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~0xFFFF
  * @param  Length 要显示数字的长度,范围:1~4
  * @retval 无
  */
void LCD_ShowHexNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i,SingleNumber;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		SingleNumber=Number/LCD_Pow(16,i-1)%16;
		if(SingleNumber<10)
		{
			LCD_WriteData(SingleNumber+'0');
		}
		else
		{
			LCD_WriteData(SingleNumber-10+'A');
		}
	}
}

/**
  * @brief  在LCD1602指定位置开始以二进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~1111 1111 1111 1111
  * @param  Length 要显示数字的长度,范围:1~16
  * @retval 无
  */
void LCD_ShowBinNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number/LCD_Pow(2,i-1)%2+'0');
	}
}

 DS1302

#include <REGX52.H>

//引脚配置:
sbit LCD_RS=P2^6;
sbit LCD_RW=P2^5;
sbit LCD_EN=P2^7;
#define LCD_DataPort P0

//函数定义:
/**
  * @brief  LCD1602延时函数,12MHz调用可延时1ms
  * @param  无
  * @retval 无
  */
void LCD_Delay()
{
	unsigned char i, j;

	i = 2;
	j = 239;
	do
	{
		while (--j);
	} while (--i);
}

/**
  * @brief  LCD1602写命令
  * @param  Command 要写入的命令
  * @retval 无
  */
void LCD_WriteCommand(unsigned char Command)
{
	LCD_RS=0;
	LCD_RW=0;
	LCD_DataPort=Command;
	LCD_EN=1;
	LCD_Delay();
	LCD_EN=0;
	LCD_Delay();
}

/**
  * @brief  LCD1602写数据
  * @param  Data 要写入的数据
  * @retval 无
  */
void LCD_WriteData(unsigned char Data)
{
	LCD_RS=1;
	LCD_RW=0;
	LCD_DataPort=Data;
	LCD_EN=1;
	LCD_Delay();
	LCD_EN=0;
	LCD_Delay();
}

/**
  * @brief  LCD1602设置光标位置
  * @param  Line 行位置,范围:1~2
  * @param  Column 列位置,范围:1~16
  * @retval 无
  */
void LCD_SetCursor(unsigned char Line,unsigned char Column)
{
	if(Line==1)
	{
		LCD_WriteCommand(0x80|(Column-1));
	}
	else if(Line==2)
	{
		LCD_WriteCommand(0x80|(Column-1+0x40));
	}
}

/**
  * @brief  LCD1602初始化函数
  * @param  无
  * @retval 无
  */
void LCD_Init()
{
	LCD_WriteCommand(0x38);//八位数据接口,两行显示,5*7点阵
	LCD_WriteCommand(0x0c);//显示开,光标关,闪烁关
	LCD_WriteCommand(0x06);//数据读写操作后,光标自动加一,画面不动
	LCD_WriteCommand(0x01);//光标复位,清屏
}

/**
  * @brief  在LCD1602指定位置上显示一个字符
  * @param  Line 行位置,范围:1~2
  * @param  Column 列位置,范围:1~16
  * @param  Char 要显示的字符
  * @retval 无
  */
void LCD_ShowChar(unsigned char Line,unsigned char Column,char Char)
{
	LCD_SetCursor(Line,Column);
	LCD_WriteData(Char);
}

/**
  * @brief  在LCD1602指定位置开始显示所给字符串
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  String 要显示的字符串
  * @retval 无
  */
void LCD_ShowString(unsigned char Line,unsigned char Column,char *String)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=0;String[i]!='\0';i++)
	{
		LCD_WriteData(String[i]);
	}
}

/**
  * @brief  返回值=X的Y次方
  */
int LCD_Pow(int X,int Y)
{
	unsigned char i;
	int Result=1;
	for(i=0;i<Y;i++)
	{
		Result*=X;
	}
	return Result;
}

/**
  * @brief  在LCD1602指定位置开始显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~65535
  * @param  Length 要显示数字的长度,范围:1~5
  * @retval 无
  */
void LCD_ShowNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number/LCD_Pow(10,i-1)%10+'0');
	}
}

/**
  * @brief  在LCD1602指定位置开始以有符号十进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:-32768~32767
  * @param  Length 要显示数字的长度,范围:1~5
  * @retval 无
  */
void LCD_ShowSignedNum(unsigned char Line,unsigned char Column,int Number,unsigned char Length)
{
	unsigned char i;
	unsigned int Number1;
	LCD_SetCursor(Line,Column);
	if(Number>=0)
	{
		LCD_WriteData('+');
		Number1=Number;
	}
	else
	{
		LCD_WriteData('-');
		Number1=-Number;
	}
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number1/LCD_Pow(10,i-1)%10+'0');
	}
}

/**
  * @brief  在LCD1602指定位置开始以十六进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~0xFFFF
  * @param  Length 要显示数字的长度,范围:1~4
  * @retval 无
  */
void LCD_ShowHexNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i,SingleNumber;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		SingleNumber=Number/LCD_Pow(16,i-1)%16;
		if(SingleNumber<10)
		{
			LCD_WriteData(SingleNumber+'0');
		}
		else
		{
			LCD_WriteData(SingleNumber-10+'A');
		}
	}
}

/**
  * @brief  在LCD1602指定位置开始以二进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~1111 1111 1111 1111
  * @param  Length 要显示数字的长度,范围:1~16
  * @retval 无
  */
void LCD_ShowBinNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number/LCD_Pow(2,i-1)%2+'0');
	}
}

XPT2046

#include <REGX52.H>

//引脚配置:
sbit LCD_RS=P2^6;
sbit LCD_RW=P2^5;
sbit LCD_EN=P2^7;
#define LCD_DataPort P0

//函数定义:
/**
  * @brief  LCD1602延时函数,12MHz调用可延时1ms
  * @param  无
  * @retval 无
  */
void LCD_Delay()
{
	unsigned char i, j;

	i = 2;
	j = 239;
	do
	{
		while (--j);
	} while (--i);
}

/**
  * @brief  LCD1602写命令
  * @param  Command 要写入的命令
  * @retval 无
  */
void LCD_WriteCommand(unsigned char Command)
{
	LCD_RS=0;
	LCD_RW=0;
	LCD_DataPort=Command;
	LCD_EN=1;
	LCD_Delay();
	LCD_EN=0;
	LCD_Delay();
}

/**
  * @brief  LCD1602写数据
  * @param  Data 要写入的数据
  * @retval 无
  */
void LCD_WriteData(unsigned char Data)
{
	LCD_RS=1;
	LCD_RW=0;
	LCD_DataPort=Data;
	LCD_EN=1;
	LCD_Delay();
	LCD_EN=0;
	LCD_Delay();
}

/**
  * @brief  LCD1602设置光标位置
  * @param  Line 行位置,范围:1~2
  * @param  Column 列位置,范围:1~16
  * @retval 无
  */
void LCD_SetCursor(unsigned char Line,unsigned char Column)
{
	if(Line==1)
	{
		LCD_WriteCommand(0x80|(Column-1));
	}
	else if(Line==2)
	{
		LCD_WriteCommand(0x80|(Column-1+0x40));
	}
}

/**
  * @brief  LCD1602初始化函数
  * @param  无
  * @retval 无
  */
void LCD_Init()
{
	LCD_WriteCommand(0x38);//八位数据接口,两行显示,5*7点阵
	LCD_WriteCommand(0x0c);//显示开,光标关,闪烁关
	LCD_WriteCommand(0x06);//数据读写操作后,光标自动加一,画面不动
	LCD_WriteCommand(0x01);//光标复位,清屏
}

/**
  * @brief  在LCD1602指定位置上显示一个字符
  * @param  Line 行位置,范围:1~2
  * @param  Column 列位置,范围:1~16
  * @param  Char 要显示的字符
  * @retval 无
  */
void LCD_ShowChar(unsigned char Line,unsigned char Column,char Char)
{
	LCD_SetCursor(Line,Column);
	LCD_WriteData(Char);
}

/**
  * @brief  在LCD1602指定位置开始显示所给字符串
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  String 要显示的字符串
  * @retval 无
  */
void LCD_ShowString(unsigned char Line,unsigned char Column,char *String)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=0;String[i]!='\0';i++)
	{
		LCD_WriteData(String[i]);
	}
}

/**
  * @brief  返回值=X的Y次方
  */
int LCD_Pow(int X,int Y)
{
	unsigned char i;
	int Result=1;
	for(i=0;i<Y;i++)
	{
		Result*=X;
	}
	return Result;
}

/**
  * @brief  在LCD1602指定位置开始显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~65535
  * @param  Length 要显示数字的长度,范围:1~5
  * @retval 无
  */
void LCD_ShowNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number/LCD_Pow(10,i-1)%10+'0');
	}
}

/**
  * @brief  在LCD1602指定位置开始以有符号十进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:-32768~32767
  * @param  Length 要显示数字的长度,范围:1~5
  * @retval 无
  */
void LCD_ShowSignedNum(unsigned char Line,unsigned char Column,int Number,unsigned char Length)
{
	unsigned char i;
	unsigned int Number1;
	LCD_SetCursor(Line,Column);
	if(Number>=0)
	{
		LCD_WriteData('+');
		Number1=Number;
	}
	else
	{
		LCD_WriteData('-');
		Number1=-Number;
	}
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number1/LCD_Pow(10,i-1)%10+'0');
	}
}

/**
  * @brief  在LCD1602指定位置开始以十六进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~0xFFFF
  * @param  Length 要显示数字的长度,范围:1~4
  * @retval 无
  */
void LCD_ShowHexNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i,SingleNumber;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		SingleNumber=Number/LCD_Pow(16,i-1)%16;
		if(SingleNumber<10)
		{
			LCD_WriteData(SingleNumber+'0');
		}
		else
		{
			LCD_WriteData(SingleNumber-10+'A');
		}
	}
}

/**
  * @brief  在LCD1602指定位置开始以二进制显示所给数字
  * @param  Line 起始行位置,范围:1~2
  * @param  Column 起始列位置,范围:1~16
  * @param  Number 要显示的数字,范围:0~1111 1111 1111 1111
  * @param  Length 要显示数字的长度,范围:1~16
  * @retval 无
  */
void LCD_ShowBinNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length)
{
	unsigned char i;
	LCD_SetCursor(Line,Column);
	for(i=Length;i>0;i--)
	{
		LCD_WriteData(Number/LCD_Pow(2,i-1)%2+'0');
	}
}

Mkey

#include <REGX52.H>
#include "Delay.h"

/**
  * @brief  矩阵键盘读取按键键码
  * @param  无
  * @retval KeyNumber 按下按键的键码值
			如果按键按下不放,程序会停留在此函数,松手的一瞬间,返回按键键码,没有按键按下时,返回0
  */
unsigned char MatrixKey()
{
	unsigned char KeyNumber=0;
	
	P1=0xFF;
	P1_3=0;
	if(P1_7==0){Delay(20);while(P1_7==0);Delay(20);KeyNumber=1;}
	if(P1_6==0){Delay(20);while(P1_6==0);Delay(20);KeyNumber=5;}
	if(P1_5==0){Delay(20);while(P1_5==0);Delay(20);KeyNumber=9;}
	if(P1_4==0){Delay(20);while(P1_4==0);Delay(20);KeyNumber=13;}
	
	P1=0xFF;
	P1_2=0;
	if(P1_7==0){Delay(20);while(P1_7==0);Delay(20);KeyNumber=2;}
	if(P1_6==0){Delay(20);while(P1_6==0);Delay(20);KeyNumber=6;}
	if(P1_5==0){Delay(20);while(P1_5==0);Delay(20);KeyNumber=10;}
	if(P1_4==0){Delay(20);while(P1_4==0);Delay(20);KeyNumber=14;}
	
	P1=0xFF;
	P1_1=0;
	if(P1_7==0){Delay(20);while(P1_7==0);Delay(20);KeyNumber=3;}
	if(P1_6==0){Delay(20);while(P1_6==0);Delay(20);KeyNumber=7;}
	if(P1_5==0){Delay(20);while(P1_5==0);Delay(20);KeyNumber=11;}
	if(P1_4==0){Delay(20);while(P1_4==0);Delay(20);KeyNumber=15;}
	
	P1=0xFF;
	P1_0=0;
	if(P1_7==0){Delay(20);while(P1_7==0);Delay(20);KeyNumber=4;}
	if(P1_6==0){Delay(20);while(P1_6==0);Delay(20);KeyNumber=8;}
	if(P1_5==0){Delay(20);while(P1_5==0);Delay(20);KeyNumber=12;}
	if(P1_4==0){Delay(20);while(P1_4==0);Delay(20);KeyNumber=16;}
	
	return KeyNumber;
}

Delay


void Delay(unsigned int xms)
{
	unsigned char i, j;
	while(xms--)
	{
		i = 2;
		j = 239;
		do
		{
			while (--j);
		} while (--i);
	}
}

Buzzer

#include <REGX52.H>
#include <INTRINS.H>

//蜂鸣器端口:
sbit Buzzer=P2^5;

/**
  * @brief  蜂鸣器私有延时函数,延时500us
  * @param  无
  * @retval 无
  */
	
	void Delay10us(unsigned int n)		//@11.0592MHz
{
	unsigned char i;
	while(n--)
	{i = 2;
	while (--i);
	}
}
void Delay2ms()		//@11.0592MHz
{
	unsigned char i, j;

	_nop_();
	i = 4;
	j = 146;
	do
	{
		while (--j);
	} while (--i);
}

	
	
void Buzzer_Delay500us()		//@11.0592MHz
{
	unsigned char i;

	_nop_();
	i = 227;
	while (--i);
}


/**
  * @brief  蜂鸣器发声
  * @param  ms 发声的时长,范围:0~32767
  * @retval 无
  */
void Buzzer_Time(unsigned int ms)//2000hz的相应
{
	unsigned int i;
	for(i=0;i<ms*2;i++)
	{
		Buzzer=!Buzzer;
		Buzzer_Delay500us();
	}
}
void Buzzer_Time_500HZ(unsigned int ms)//500hz
{
	unsigned int i;
	for(i=0;i<ms/2+1;i++)
	{
		Buzzer=!Buzzer;
		Delay2ms();
	}
}

/**
  * @brief  蜂鸣器发声
  * @param  ms 发声的时长,范围:0~32767
  * @retval hz 频率 
  */
void Buzzer_Time_hz(unsigned int ms,unsigned int hz)
{
		unsigned int i;
	unsigned int n = 100000 / hz;
	for(i=0;i<ms*100;i++)
	{
		Buzzer=!Buzzer;
		Delay10us(n);
	}
}

应用

       主控板 控制时间 每个灯允许量的时间 灯光亮度 是否灭灯

       副控板 控制灯的亮灭 互相交流是否灭灯 PWM调光

如果看得懂代码 大概也知道引脚口对应的什么功能

        主控P2口主动给副板发信息 

        主控P3口接受信息 

        副控P3 P1接受信息 P2开关灯 P1与另一个板子交流

        详细欢迎于本人交流,我主要留痕

标签:路灯,Delay,51,unsigned,param,char,单片机,LCD,Line
From: https://blog.csdn.net/forccct/article/details/142767430

相关文章

  • 如何入门STM32单片机编程
    入门STM32单片机编程需要掌握以下内容:STM32的基本概念和特点:了解STM32系列单片机的特点、硬件结构、功能模块以及常用的开发工具和资源。KeilMDK开发环境的安装和使用:KeilMDK是一款非常常用的STM32开发工具,通过安装和配置KeilMDK,可以进行STM32的编译、下载和调试操作。......
  • abc351F Double Sum
    给定数组A[N],对所有1<=i<j<=N,计算max(A[j]-A[i],0)之和。2<=N<=4E5;0<=A[i]<=1E8分析:从左到后依次处理,用平衡树维护左侧A[i],对于A[j],只需要统计值小于A[j]的那些A[i]即可,可以合并求和过程转化为前缀和。#include<bits/stdc++.h>usingi64=longlong;template<typename......
  • 51单片机的自动烘手器【proteus仿真+程序+报告+原理图+演示视频】
    1、主要功能 该系统由AT89C51/STC89C52单片机+LCD1602显示模块+温度传感器+红外传感器+时钟模块+继电器+LED和按键等模块构成。适用于智能干手器、智能烘干器、自动感应烘干器等相似项目。可实现功能:1、LCD1602实时显示当前日期、时间和环境温度2、温度传感器DS18B20采......
  • 【星汇极客】单片机竞赛之嵌入式设计竞赛(持续更新)
    前言        本人是一名嵌入式学习者,在大学期间也参加了不少的竞赛并获奖,包括:江苏省电子设计竞赛省一、睿抗机器人国二、中国高校智能机器人国二、嵌入式设计竞赛国三、光电设计竞赛国三、节能减排竞赛国三等。    暑假的时候参加了太多的比赛,作为队长要写代......
  • 代码随想录算法训练营第八天| 151.翻转字符串里的单词
    151.翻转字符串里的单词文章链接:https://programmercarl.com/0151.翻转字符串里的单词.html#思路视频链接:https://www.bilibili.com/video/BV1uT41177fX/?vd_source=6cb513d59bf1f73f86d4225e9803d47b题目链接:https://leetcode.cn/problems/reverse-words-in-a-string/classS......
  • 51nod1548 欧姆诺姆和糖果
    有红蓝两种糖果,红色糖果每颗重wr克,甜度为hr;蓝色糖果每颗重wb克,甜度为hb;有容量为C克的盒子,求能装下的最大甜度。1<=C,hr,hb,wr,wb<=1E9分析:记S=lcm(wr,wb),那么对于S克容量,可以装S/wr颗蓝色糖果,也可以装S/wb颗红色糖果,甜度分别为S*hb/wr和S*hr/wb,应该选甜度更大的。因此在枚举时,红......
  • 基于单片机智能温室控制系统
    文章目录前言概要设计思路软件设计效果图程序文章目录前言......
  • SEHS4517 Web Application Development
    SEHS4517WebApplicationDevelopmentandManagementSemester1,2024-2025AssignmentIndividualAssignment(30%oftheassessmentofthiscourse)Thisindividualassignmentaims:Toconductresearchonrelevantreferencematerialsorsources.Todeve......
  • FIT5147 Data Exploration and Visualisation
    MonashUniversityFIT5147DataExplorationandVisualisationSemester2,2024ProgrammingExercise3:D3(5%)ProgrammingExercise3:D3Pleasecarefullyreviewalltherequirementsbelowtoensureyouhaveagoodunderstandingofwhatisrequiredforyo......
  • 【STC15】单片机中常说的 1T 和 12T 的意思
    标准51单片机是12T的,就是说12个时钟周期(晶振周期,例如12M的,周期是1/12M,单位秒),机器做一个指令周期,刚好就是1/12M*12=1us,常见指令例如_nop_就是一个周期,刚好1us,其他的大多多于一个周期,乘除法更多。所以如果计算指令时间可以这样算。而现在51核的单片机工艺质量上去后,频率大大提高,增......