Challenge

Measuring distance of an object using ultrasonic sensor (HC-SR04)

Measuring distance of an object using ultrasonic sensor (HC-SR04)

Aim:

To implement code for “Measuring distance of an object using ultrasonic distance sensor (HC-SR04).

Objective:

  • Measuring the distance of an object using Ultrasonic Distance Sensor (HC-SR04)
  • Usage of Input Capture Mode

Highlights:

  • Measuring the distance travelled by the wave to the object and gets bounced back from the object to sensor.
  • Measuring Pulse width using Input Capture Mode

Deliverables:

  • The distance travelled by a wave to the object for which we want to measure the distance using Ultrasonic Distance Sensor (HC-SR04).
  • Measuring Pulse width using Input Capture Mode of Timer 1

Steps of Programming

  1. ATmega16 microcontroller needs to transmit at least 10 us trigger pulse to the HC-SR04 Trig Pin.
  2. After getting a trigger pulse, HC-SR04 automatically sends eight 40 kHz sound waves and the microcontroller waits for rising edge output at the Echo pin.
  3. When the rising edge capture occurs at the Echo pin which is connected to an input of ATmega16, start Timer of ATmega16 and again wait for a falling edge on the Echo pin.
  4. As soon as the falling edge is captured at the Echo pin, the microcontroller reads the count of the Timer. This time count is used to calculate the distance to an object.

Calculation (distance in cm) (H1)

Sound velocity = 343.00 m/s = 34300 cm/s

The distance of Object (in cm) = Sound velocity *Timer/2

= 32300*Timer/2

= 17150*Timer

Now, here we have selected an internal 8 MHz oscillator frequency for ATmega16, with No-presale for timer frequency. Then time to execute 1 instruction is 0.125 us.

So, the timer gets incremented after 0.125 us time elapse.

= 17150 x (TIMER value) x 0.125 x 10^-6 cm

= 0.125 x (TIMER value)/58.30 cm

= (TIMER value) / 466.47 cm

Code:

/*

* Project_2.c

*

* Created: 09-03-2024 13:22:08

* Author : VaraPrasad

*/

#define F_CPU 8000000UL

#include <avr/io.h>

#include <avr/interrupt.h>

#include <util/delay.h>

#include <string.h>

#include <stdlib.h>

#define LCD_Data_Dir DDRD // LCD data port direction register

#define LCD_Command_Dir DDRC // LCD command port direction register

#define LCD_Data_Port PORTD // LCD data port

#define LCD_Command_Port PORTC // LCD command port

#define EN PC2 // Enable signal pin

#define RW PC3 // Read/Write signal pin

#define RS PC4 // Register Select (data reg./command reg.) signal pin

void LCD_Command (char); // Function to write LCD command

void LCD_Char (char); // Function to write LCD data

void LCD_Init (void); // Function to initialize LCD

void LCD_String (char*); // Function to send string to LCD

void LCD_String_xy (char,char,char*); // Function to send string to specified row and column of LCD

void LCD_Command (char cmd)

{

LCD_Data_Port = cmd; // Write command data to LCD data port

LCD_Command_Port &= ~((1<<RS)|(1<<RW)); // Make RS LOW (command reg.), RW LOW (Write)

LCD_Command_Port |= (1<<EN); // High to Low transition on EN (Enable)

_delay_us(1);

LCD_Command_Port &= ~(1<<EN);

_delay_ms(3); // Wait a bit

}

void LCD_Char (char char_data)

{

LCD_Data_Port = char_data; // Write data to LCD data port

LCD_Command_Port &= ~(1<<RW); // Make RW LOW (Write)

LCD_Command_Port |= (1<<EN)|(1<<RS); // Make RS HIGH (data reg.) and High to Low transition on EN (Enable)

_delay_us(1);

LCD_Command_Port &= ~(1<<EN);

_delay_ms(1); // Wait a bit

}

void LCD_Init (void)

{

LCD_Command_Dir |= (1<<RS)|(1<<RW)|(1<<EN); // Set LCD command port direction as output

LCD_Data_Dir = 0xFF; // Set LCD data port direction as output

_delay_ms(20); // LCD power up time

LCD_Command (0x38); // Initialize 16X2 LCD in 8bit mode

LCD_Command (0x0C); // Display ON, Cursor OFF command

LCD_Command (0x06); // Auto Increment cursor

LCD_Command (0x01); // Clear LCD command

LCD_Command (0x80); // Set cursor position to start of first line

}

void LCD_String (char *str)

{

int i;

for(i=0;str[i]!=0;i++) // Send each character of string until NULL

{

LCD_Char (str[i]); // Call LCD data write

}

}

void LCD_String_xy (char row, char pos, char *str)

{

if (row == 1)

LCD_Command((pos & 0x0F)|0x80); // Set cursor position for the first row

else if (row == 2)

LCD_Command((pos & 0x0F)|0xC0); // Set cursor position for the second row

LCD_String(str); // Call LCD string function

}

#define Trigger_pin PA0 // Trigger pin for ultrasonic sensor

int TimerOverflow = 0;

ISR(TIMER1_OVF_vect)

{

TimerOverflow++; // Increment Timer Overflow count

}

int main(void)

{

char string[10];

long count;

double distance;

DDRA = 0x01; // Set trigger pin as output

PORTB = 0xFF; // Turn on Pull-up

LCD_Init(); // Initialize LCD

LCD_String_xy(1, 0, "Ultrasonic"); // Display "Ultrasonic" on first row

sei(); // Enable global interrupt

TIMSK = (1 << TOIE1); // Enable Timer1 overflow interrupts

TCCR1A = 0; // Set all bits to zero for Normal operation

while(1)

{

PORTA |= (1 << Trigger_pin); // Give 10us trigger pulse on trigger pin to HC-SR04

_delay_us(10);

PORTA &= (~(1 << Trigger_pin));

TCNT1 = 0; // Clear Timer counter

TCCR1B = 0x41; // Capture on rising edge, No prescaler

TIFR = 1<<ICF1; // Clear ICP flag (Input Capture flag)

TIFR = 1<<TOV1; // Clear Timer Overflow flag

// Calculate width of Echo by Input Capture (ICP)

while ((TIFR & (1 << ICF1)) == 0); // Wait for rising edge

TCNT1 = 0; // Clear Timer counter

TCCR1B = 0x01; // Capture on falling edge, No prescaler

TIFR = 1<<ICF1; // Clear ICP flag (Input Capture flag)

TIFR = 1<<TOV1; // Clear Timer Overflow flag

TimerOverflow = 0; // Clear Timer overflow count

while ((TIFR & (1 << ICF1)) == 0); // Wait for falling edge

count = ICR1 + (65535 * TimerOverflow); // Take count

distance = (double)count / 466.47; // Calculate distance

dtostrf(distance, 2, 2, string); // Convert distance to string

strcat(string, " cm "); // Concatenate unit (cm)

LCD_String_xy(2, 0, "Dist = "); // Display "Dist = " on second row

LCD_String_xy(2, 7, string); // Display distance on second row

_delay_ms(200);

}

}

Circuit:

  • The program is loaded in the Atmega 32 chip.
  • LCD pins are connected to the Atmega32 as shown above.

Output:

  • 84.90 cm is the distance of an object obtained.

Result:

Thus the implementation of code for “Measuring distance of an object using ultrasonic distance sensor (HC-SR04) is done.

Your portfolio, next

Ship work like this
in your own course.

Talk to a career counsellor

Free 20-minute call. We'll map the right course to where you want to work.

By submitting you agree to our Terms and Privacy Policy.