蓝桥杯——第三届省赛_自动售水机系统

一、使用到的模块

数码管,按键,AD,LED,继电器

在这里插入图片描述

二、代码部分

实验平台:CT107D
实验芯片:stc15f2k60s2
实验现象:完成题目要求
代码如下

iic.c

/*
  程序说明: IIC总线驱动程序
  软件环境: Keil uVision 4.10 
  硬件环境: CT107单片机综合实训平台(12MHz)
  日    期: 2011-8-9
*/

#include "iic.h"
void Delay5us()		//@12.000MHz
{
	unsigned char i;

	_nop_();
	_nop_();
	i = 12;
	while (--i);
}
//总线启动条件
void IIC_Start(void)
{
	SDA = 1;
	SCL = 1;
	somenop;
	SDA = 0;
	somenop;
	SCL = 0;	
}

//总线停止条件
void IIC_Stop(void)
{
	SDA = 0;
	SCL = 1;
	somenop;
	SDA = 1;
}

//应答位控制
void IIC_Ack(unsigned char ackbit)
{
	if(ackbit) 
	{	
		SDA = 0;
	}
	else 
	{
		SDA = 1;
	}
	somenop;
	SCL = 1;
	somenop;
	SCL = 0;
	SDA = 1; 
	somenop;
}

//等待应答
bit IIC_WaitAck(void)
{
	SDA = 1;
	somenop;
	SCL = 1;
	somenop;
	if(SDA)    
	{   
		SCL = 0;
		IIC_Stop();
		return 0;
	}
	else  
	{ 
		SCL = 0;
		return 1;
	}
}

//通过I2C总线发送数据
void IIC_SendByte(unsigned char byt)
{
	unsigned char i;
	for(i=0;i<8;i++)
	{   
		if(byt&0x80) 
		{	
			SDA = 1;
		}
		else 
		{
			SDA = 0;
		}
		somenop;
		SCL = 1;
		byt <<= 1;
		somenop;
		SCL = 0;
	}
}

//从I2C总线上接收数据
unsigned char IIC_RecByte(void)
{
	unsigned char da;
	unsigned char i;
	
	for(i=0;i<8;i++)
	{   
		SCL = 1;
		somenop;
		da <<= 1;
		if(SDA) 
		da |= 0x01;
		SCL = 0;
		somenop;
	}
	return da;
}
void write_adc(unsigned char add)
{
	 IIC_Start();
	 IIC_SendByte(0x90);
	 IIC_WaitAck();
	 IIC_SendByte(add);
	 IIC_WaitAck();
	 IIC_Stop();
}

unsigned char read_adc(unsigned char add)
{
	 unsigned char temp;
	 EA = 0;
	 IIC_Start();
	 IIC_SendByte(0x90);
	 IIC_WaitAck();
	 IIC_SendByte(add);
	 IIC_WaitAck();
	 IIC_Start();
	 IIC_SendByte(0x91);
	 IIC_WaitAck();
	 temp = IIC_RecByte();
	 IIC_WaitAck();
	 IIC_Stop();
	 EA = 1;
	 return temp;
}

void write_24c02(unsigned char add,unsigned char date1)
{
	 IIC_Start();
	 IIC_SendByte(0xa0);
	 IIC_WaitAck();
	 IIC_SendByte(add);
	 IIC_WaitAck();
	 IIC_SendByte(date1);
	 IIC_WaitAck();
	 IIC_Stop();
}

unsigned char read_24c02(unsigned char add)
{ 
   	 unsigned char temp;
	 EA = 0;
	 IIC_Start();
	 IIC_SendByte(0xa0);
	 IIC_WaitAck();
	 IIC_SendByte(add);
	 IIC_WaitAck();

	 IIC_Start();
	 IIC_SendByte(0xa1);
	 IIC_WaitAck();
	 temp = IIC_RecByte();
	 IIC_WaitAck();
	 IIC_Stop();
	 EA = 1;
	 return temp;
}

iic.h

#ifndef _IIC_H
#define _IIC_H

#include "stc15f2k60s2.h"
#include "intrins.h"

#define somenop Delay5us() ;
#define SlaveAddrW 0xA0
#define SlaveAddrR 0xA1

//总线引脚定义
sbit SDA = P2^1;  /* 数据线 */
sbit SCL = P2^0;  /* 时钟线 */

//函数声明
void IIC_Start(void); 
void IIC_Stop(void);  
void IIC_Ack(unsigned char ackbit); 
void IIC_SendByte(unsigned char byt); 
bit IIC_WaitAck(void);  
unsigned char IIC_RecByte(void); 

void write_adc(unsigned char add);
unsigned char read_adc(unsigned char add);
void write_24c02(unsigned char add,unsigned char date1);
unsigned char read_24c02(unsigned char add);

#endif

main.c

#include <stc15f2k60s2.h>
#include <iic.h>
#include "intrins.h"

#define uchar unsigned char
#define uint unsigned int

sbit relay = P0^4;
sbit buzz = P0^6;

bit openwater = 0;
bit ql = 0;

uchar trg,cont;//按键
uchar mode=1;//数字显示模式
uint csl,sf;
uint dianya;
uint count_time = 0;
uchar duan[] = {0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x00,0x40,0xBF, //0-9,black,-
				0xBF,0x86,0xDB,0xCF,0xE6,0xED,0xFD,0x87,0xFF,0xEF};	//0.-9. 
uchar disbuff[8];

void clzbuzz()
{
	P2 = P2&0x1f|0xa0;
	buzz = 0;
	relay = 0;
	P2 = P2&0x1f;
}

void display()
{
	static uchar index;

	P2 = P2&0x1f|0xe0;//选择所有段码
	P0 = 0xff;//消影
	P2 = P2&0x1f;

	P2 = P2&0x1f|0xc0;
	P0 = 1<<index;
	P2 = P2&0x1f;

	P2 = P2&0x1f|0xe0;
	P0 = ~duan[disbuff[index]];
	P2 = P2&0x1f;

	index++;
	index &= 0x07;
}

void keyscan()
{
	uchar readdate = P3^0xff;
	trg = readdate&(readdate^cont);
	cont = readdate; 
}

void keyfun()
{
	if(trg == 0x01)
	{
		P2 = P2&0x1f|0xa0;
		buzz = 0;
		relay = 1;
		P2 = P2&0x1f;

		if(ql == 0)
		{
			openwater = 1;
			mode = 1;
			ql = 1;
			csl = 0;
			count_time = 0;
		}
		
	}
	else if(trg == 0x02)
	{
		openwater = 0;
		mode = 2;
		ql = 0;

		P2 = P2&0x1f|0xa0;
		buzz = 0;
		relay = 0;
		P2 = P2&0x1f;
		
	}
}

void show_num()
{
//	csl = count_time*100;

	sf = csl*0.5;
	if(mode == 1)
	{
	disbuff[0] = 10;
	disbuff[1] = 13;
	disbuff[2] = 5;
	disbuff[3] = 0;
	disbuff[4] = csl/1000;
	disbuff[5] = csl/100%10+13;
	disbuff[6] = csl/10%10;
	disbuff[7] = csl%10;
	}

	else if(mode == 2)
	{
	disbuff[0] = 10;
	disbuff[1] = 13;
	disbuff[2] = 5;
	disbuff[3] = 0;
	disbuff[4] = sf/1000;
	disbuff[5] = sf/100%10+13;
	disbuff[6] = sf/10%10;
	disbuff[7] = sf%10;
	}
}

void Timer0Init(void)		//1毫秒@11.0592MHz
{
	AUXR |= 0x80;		//定时器时钟1T模式
	TMOD &= 0xF0;		//设置定时器模式
	TL0 = 0xCD;		//设置定时初值
	TH0 = 0xD4;		//设置定时初值
	TF0 = 0;		//清除TF0标志
	TR0 = 1;		//定时器0开始计时
	ET0 = 1;
	EA = 1;
}

void Timer0() interrupt 1
{
	static uint count = 0;
	TL0 = 0xCD;		//设置定时初值
	TH0 = 0xD4;		//设置定时初值
	keyscan();
	keyfun();
	display();
	if(openwater == 1)
	{
		if(++count >= 100)
		{
			count = 0;
			count_time++;
			csl = count_time; 
		    if(csl >= 9900)
			{
				openwater = 0;
				mode = 2;
			}
		}		
	}
}

void main()
{
	clzbuzz();
	Timer0Init();
	write_adc(0x01); //初始化adc
	while(1)
	{
		show_num();
		dianya = read_adc(0x01);
		dianya = dianya*5/255.0f;
		if(dianya<1.25)
		{
			P2 = P2&0x1f|0x80;
			P0 = 0xff;
			P2 = P2&0x1f;
		}
		else 
		{
			P2 = P2&0x1f|0x80;
			P0 = 0xfe;
			P2 = P2&0x1f;
		}
	}
}
				 

猜你喜欢

转载自blog.csdn.net/FuckerGod/article/details/104279872