Design of Ultrasonic Distance Meter Based on 51 Single Chip Microcomputer

Publisher:幸福时刻Latest update time:2019-12-17 Source: 51hei Reading articles on mobile phones Scan QR code
Read articles on your mobile phone anytime, anywhere

This is a 51 single-chip microcomputer course design I made. The single-chip microcomputer model is STC89C52, and the ultrasonic module is HC-SR04

The microcontroller source program is as follows:

#include //Call the MCU header file

#define uchar unsigned char //unsigned character macro definition variable range 0~255

#define uint unsigned int //Unsigned integer macro definition variable range 0~65535

#include

uchar a_a;



//Digital tube segment selection definition 0 1 2 3 4 5 6 7 8 9        

uchar code smg_du[]={0x28,0xee,0x32,0xa2,0xe4,0xa1,0x21,0xea,0x20,0xa0,

                                           0x60,0x25,0x39,0x26,0x31,0x71,0xff}; //Broken code



uchar dis_smg[8] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8};


// Definition of digital tube position selection

sbit smg_we1 = P3^4; //digital tube bit selection definition

sbit smg_we2 = P3^5;

sbit smg_we3 = P3^6;

sbit smg_we4 = P3^7;


sbit c_send = P3^2; //ultrasonic emission

sbit c_recive = P3^3; //ultrasonic receiving


sbit beep = P2^3; //Buzzer IO port definition

uchar smg_i = 3; //Show the single digit of the digital tube

bit flag_300ms;


long distance; //distance

uint set_d; //distance

uchar flag_csb_juli; //Ultrasonic wave exceeds the range

uint flag_time0; //Used to save timer 0


uchar menu_1; //Menu design variables



/**************************1ms delay function********************************/

void delay_1ms(uint q)

{

        uint i,j;

        for(i=0;i                for(j=0;j<120;j++);

}


/***********************Processing distance function********************************/

void smg_display()

{

        dis_smg[0] = smg_du[distance % 10];

        dis_smg[1] = smg_du[distance / 10 % 10];

        dis_smg[2] = smg_du[distance / 100 % 10] & 0xdf; ;        

}



#define RdCommand 0x01 //Define ISP operation command

#define PrgCommand 0x02

#define EraseCommand 0x03 

#define Error 1

#define Ok 0

#define WaitTime 0x01 //Define the CPU waiting time

sfr ISP_DATA=0xe2; //Register declaration

sfr ISP_ADDRH=0xe3;

sfr ISP_ADDRL=0xe4;

sfr ISP_CMD=0xe5;

sfr ISP_TRIG=0xe6;

sfr ISP_CONTR=0xe7;


/* ================= Turn on ISP, IAP function ================= */

void ISP_IAP_enable(void)

{

         EA = 0; /* Disable interrupt */

         ISP_CONTR = ISP_CONTR & 0x18; /* 0001,1000 */

         ISP_CONTR = ISP_CONTR | WaitTime; /* Write hardware delay*/

         ISP_CONTR = ISP_CONTR | 0x80; /* ISPEN=1 */

}

/* =============== Turn off ISP, IAP function ================== */

void ISP_IAP_disable(void)

{

         ISP_CONTR = ISP_CONTR & 0x7f; /* ISPEN = 0 */

         ISP_TRIG = 0x00;

         EA = 1; /* Enable interrupt */

}

/* ================= Public trigger code ==================== */

void ISPgoon(void)

{

         ISP_IAP_enable(); /* Enable ISP, IAP function*/

         ISP_TRIG = 0x46; /* Trigger ISP_IAP command byte 1 */

         ISP_TRIG = 0xb9; /* Trigger ISP_IAP command byte 2 */

         _nop_();

}

/* ==================== Byte Read========================= */

unsigned char byte_read(unsigned int byte_addr)

{

        EA = 0;

         ISP_ADDRH = (unsigned char)(byte_addr >> 8);/* address assignment*/

         ISP_ADDRL = (unsigned char)(byte_addr & 0x00ff);

         ISP_CMD = ISP_CMD & 0xf8; /* Clear the lower 3 bits */

         ISP_CMD = ISP_CMD | RdCommand; /* Write read command*/

         ISPgoon(); /* trigger execution */

         ISP_IAP_disable(); /* Disable ISP, IAP function*/

         EA = 1;

         return (ISP_DATA); /* Return the read data */

}

/* ================== Sector Erase ========================= */

void SectorErase(unsigned int sector_addr)

{

         unsigned int iSectorAddr;

         iSectorAddr = (sector_addr & 0xfe00); /* Get sector address*/

         ISP_ADDRH = (unsigned char)(iSectorAddr >> 8);

         ISP_ADDRL = 0x00;

         ISP_CMD = ISP_CMD & 0xf8; /* Clear the lower 3 bits */

         ISP_CMD = ISP_CMD | EraseCommand; /* Erase command 3 */

         ISPgoon(); /* trigger execution */

         ISP_IAP_disable(); /* Disable ISP, IAP function*/

}

/* ==================== Byte Write========================= */

void byte_write(unsigned int byte_addr, unsigned char original_data)

{

         EA = 0;

// SectorErase(byte_addr);

         ISP_ADDRH = (unsigned char)(byte_addr >> 8); /* Get address */

         ISP_ADDRL = (unsigned char)(byte_addr & 0x00ff);

         ISP_CMD = ISP_CMD & 0xf8; /* Clear the lower 3 bits*/

         ISP_CMD = ISP_CMD | PrgCommand; /* Write command 2 */

         ISP_DATA = original_data; /* Prepare to write data*/

         ISPgoon(); /* trigger execution */

         ISP_IAP_disable(); /* Disable IAP function*/

         EA =1;

}



/******************Save the data to the eeprom inside the microcontroller******************/

void write_eeprom()

{

        SectorErase(0x2000);

        byte_write(0x2000, set_d % 256);

        byte_write(0x2001, set_d / 256);

        byte_write(0x2058, a_a);        

}


/******************Read the data from the eeprom inside the microcontroller*****************/

void read_eeprom()

{

        set_d = byte_read(0x2001);

        set_d <<= 8;

        set_d |= byte_read(0x2000);

        a_a = byte_read(0x2058);

}


/**************Power on self-test eeprom initialization*****************/

void init_eeprom()

{

        read_eeprom(); //Read first

        if(a_a != 1) //New MCU initial MCU internal eeprom

        {

                set_d = 50;

                a_a = 1;

                write_eeprom(); //Save data

        }        

}


/************************Independent key program*****************/

uchar key_can; //key value


void key() //Independent key program

{

        static uchar key_new;

        key_can = 20; //key value restoration

        P2 |= 0x07;

        if((P2 & 0x07) != 0x07) //Button pressed

        {

                delay_1ms(1); //key debounce

                if(((P2 & 0x07) != 0x07) && (key_new == 1))

                { //Confirm that the button was pressed

                        key_new = 0;

                        switch(P2 & 0x07)

                        {

                                case 0x06: key_can = 3; break; //Get the k2 key value

                                case 0x05: key_can = 2; break; //Get the k3 key value

                                case 0x03: key_can = 1; break; //Get the k4 key value

                        }

                }                        

        }

        else 

                key_new = 1;        

}


/****************Key processing display function***************/

void key_with()

{

        if(key_can == 1) //Set key

        {

                menu_1++;

                if(menu_1 >= 2)

                {

                        menu_1 = 0;

                        smg_i = 3; //Only display 3-digit digital tube 

                }

                if(menu_1 == 1)

                {

                        smg_i = 4; //Only display 4-digit digital tube 

                }

        }

        if(menu_1 == 1) //Set alarm

        {

                if(key_can == 2)

                {

                        set_d++; //add 1

                        if(set_d > 400)

                                set_d = 400;

                }

                if(key_can == 3)

                {

                        set_d -- ; //decrement 1

                        if(set_d <= 1)

                                set_d = 1;

                }

                dis_smg[0] = smg_du[set_d % 10]; //Decimal display

                dis_smg[1] = smg_du[set_d / 10 % 10] ; // Display the unit digit

                dis_smg[2] = smg_du[set_d / 100 % 10] & 0xdf ; //Take the tenth digit for display

                dis_smg[3] = 0x60; //a

                write_eeprom(); //Save data

        }        

}  


/********************Alarm function*******************/

void clock_h_l()

{

        static uchar value;

        if(distance <= set_d)

        {

                value ++; // Eliminate interference when the actual distance changes around the set distance

                if(value >= 2)

                {

                        beep = ~beep; //Buzzer alarm        

                }

        }

        else 

        {

                value = 0; 

                beep = 1; //Cancel the alarm

        }        

}


/***********************Digit selection function*********************************/

void smg_we_switch(uchar i)

{

        switch(i)

        {

                case 0: smg_we1 = 0; smg_we2 = 1; smg_we3 = 1; smg_we4 = 1; break;

                case 1: smg_we1 = 1; smg_we2 = 0; smg_we3 = 1; smg_we4 = 1; break;

                case 2: smg_we1 = 1; smg_we2 = 1; smg_we3 = 0; smg_we4 = 1; break;

                case 3: smg_we1 = 1; smg_we2 = 1; smg_we3 = 1; smg_we4 = 0; break;

        }        

}


/***********************Digital display function********************************/

void display()

{

        static uchar i;   

        i++;

        if(i >= smg_i)

                i = 0;        

        smg_we_switch(i); //bit selection

        P1 = dis_smg[i]; //segment selection                

}


/******************Small delay function*****************/

void delay()

{

        _nop_(); //Executing a _nop_() instruction takes 1us

        _nop_(); 

        _nop_(); 

        _nop_(); 

        _nop_(); 

        _nop_(); 

        _nop_(); 

        _nop_(); 

        _nop_();  

        _nop_(); 

}



/*********************Ultrasonic distance measurement program********************************/

void send_wave()

{

        c_send = 1; //10us high level trigger 

        delay();

        c_send = 0;         

        TH0 = 0; // Clear timer 0

        TL0 = 0;

        TR0 = 0; //Turn off timer 0

        while(!c_recive); //Wait when c_recive is zero

        TR0=1;

        while(c_recive) //When c_recive is 1, count and wait

        {

                flag_time0 = TH0 * 256 + TL0;

                if((flag_time0 > 40000)) //When the ultrasonic wave exceeds the measurement range, 3 888 will be displayed

                {

                        TR0 = 0;

                        flag_csb_juli = 2;

                        distance = 888;

                        break ;                

                }

                else 

                {

                        flag_csb_juli = 1;        

[1] [2]
Reference address:Design of Ultrasonic Distance Meter Based on 51 Single Chip Microcomputer

Previous article:Eight-way buzzer based on 51 single chip microcomputer
Next article:Traffic light course design based on 51 single chip microcomputer

Latest Microcontroller Articles
  • Download from the Internet--ARM Getting Started Notes
    A brief introduction: From today on, the ARM notebook of the rookie is open, and it can be regarded as a place to store these notes. Why publish it? Maybe you are interested in it. In fact, the reason for these notes is ...
  • Learn ARM development(22)
    Turning off and on interrupts Interrupts are an efficient dialogue mechanism, but sometimes you don't want to interrupt the program while it is running. For example, when you are printing something, the program suddenly interrupts and another ...
  • Learn ARM development(21)
    First, declare the task pointer, because it will be used later. Task pointer volatile TASK_TCB* volatile g_pCurrentTask = NULL;volatile TASK_TCB* vol ...
  • Learn ARM development(20)
    With the previous Tick interrupt, the basic task switching conditions are ready. However, this "easterly" is also difficult to understand. Only through continuous practice can we understand it. ...
  • Learn ARM development(19)
    After many days of hard work, I finally got the interrupt working. But in order to allow RTOS to use timer interrupts, what kind of interrupts can be implemented in S3C44B0? There are two methods in S3C44B0. ...
  • Learn ARM development(14)
  • Learn ARM development(15)
  • Learn ARM development(16)
  • Learn ARM development(17)
Change More Related Popular Components

EEWorld
subscription
account

EEWorld
service
account

Automotive
development
circle

About Us Customer Service Contact Information Datasheet Sitemap LatestNews


Room 1530, 15th Floor, Building B, No.18 Zhongguancun Street, Haidian District, Beijing, Postal Code: 100190 China Telephone: 008610 8235 0740

Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved 京ICP证060456号 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号