라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED

라즈베리파이 초음파 센서 ( HC-SR04 ) 제어 작성자 : 네오즈

1. 초음파센서 테스트 회로 구성

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED

                            ( HC-SR04 초음파 센서 1EA, , 1KΩ 저항 1EA Echo연결, 2KΩ 저항 1EA GND 연결 )

                                          Trig: GPIO 17번 연결, Echo: GPIO 18번 연결

주의사항 : echo 핀에 High level 신호 발생시 5V를 전송 하게 된다. 그러나 라즈베리파이는 3.3V로

작동되므로 라즈베리파이 손상을 방지하기 위해 1KΩ, 2KΩ 저항으로 3.3V로 낮춰줘야 한다.

코드 작성 및 실행 방법은 " 라즈베리파이 GPIO 포트 ( LED, 버튼 ) 제어 " 가이드 참조

2. 초음파센서 테스트 Python 코드

초음파가 물체에 부딪쳐 반사되어 돌아오는데 까지 걸리는 시간을 측정하여 물체의 거리를 계산한다.

import RPi.GPIO as GPIO                    # RPi.GPIO에 정의된 기능을 GPIO라는 명칭으로 사용
import time                                # time 모듈

GPIO.setmode(GPIO.BCM)                     # GPIO 이름은 BCM 명칭 사용
GPIO.setup(17, GPIO.OUT)                   # Trig=17 초음파 신호 전송핀 번호 지정 및 출력지정
GPIO.setup(18, GPIO.IN)                    # Echo=18 초음파 수신하는 수신 핀 번호 지정 및 입력지정

print “Press SW or input Ctrl+C to quit”   # 메세지 화면 출력

try:
    while True:
            GPIO.output(17, False)         
            time.sleep(0.5)

            GPIO.output(17, True)          # 10us 펄스를 내보낸다.
            time.sleep(0.00001)            # Python에서 이 펄스는 실제 100us 근처가 될 것이다
            GPIO.output(17, False)         # 하지만 HC-SR04 센서는 이 오차를 받아준다

            while GPIO.input(18) == 0:     # 18번 핀이 OFF 되는 시점을 시작 시간으로 잡는다
               start = time.time()

            while GPIO.input(18) == 1:     # 18번 핀이 다시 ON 되는 시점을 반사파 수신시간으로 잡는다
               stop = time.time()

            time_interval = stop – start      # 초음파가 수신되는 시간으로 거리를 계산한다
            distance = time_interval * 17000
            distance = round(distance, 2)

            print “Distance => “, distance, “cm”

except KeyboardInterrupt:                  # Ctrl-C 입력 시
    GPIO.cleanup()                         # GPIO 관련설정 Clear
    Print "bye~"

3. 초음파센서 테스트 C코드

#include                               // stdio.h 파일 포함( printf() 사용하기 위해 )
#include                            // wiringPi.h 파일 포함

int main(void )
{
   Float distance, start, stop;

   wiringPiSetup();
                                                // wiringPi 기준으로 PIN 번호 매김
   pinMode(0, OUTPUT);                          // wiringPi GPIO 0번  = Python(BCM) 17번 
   pinMode(1, INPUT);                           // wiringPi GPIO 1번  = Python(BCM) 18번

  while(1)
  {
      digitalWrite(0,0);                        // wiringPi 0번핀을 Low로 출력
      digitalWrite(0,1);                        // wiringPi 0번핀을 High로 출력
      delayMicroseconds(10);                    // 10마이크로초 동안 멈춘다
      digitalWrite(0,0);
    
      while(digitalRead(1) == 0)                // wiringPi 1번핀을 Low일 경우
         start = micros();                      // 마이크로초 저장
      while(digitalRead(1) == 1)                // wiringPi 1번핀을 High일 경우
         stop = micros();                       // 마이크로초 저장

      distance = (stop – start) / 58;           // 시간의 차이를 이용하여 거리를 도출한다
      printf(“Distance=> %2f cm \n”,distance);  
      delay(1000);
  }

  return 0;
}

※ e4ds make에 등록된 자료는 e4ds와 지식 제공자(기업포함) 이외에는 상업화 용도로 사용할 수 없습니다. 영리 목적 이외의 사용 시 출처를 밝혀야 합니다.

Comments

관련 Make

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED

관련 상품

Download raspberry-gpio-python for free. A Python module to control the GPIO on a Raspberry Pi. To get started with RPi.GPIO, it would be worthwhile reading the examples in the project wiki (link above). Note that this module is unsuitable for real-time or

반응형

PWM

PWM(Pulse Width Modulation => 펄스 폭 변조)는 디지털 출력으로 아날로그 회로를 제어하는 기술이다.

일정한 주기 내에서 Duty 비를 변화시켜서 평균 전압을 제어하는 기술이다.

이때 모터나 센서가 on되는 시간을 duty라고 한다.
duty가 50이다 -> 전체에서 50퍼만 쓴다라는 뜻으로 해석할 수 있다.
(모터의 속도조절은 PWM의 기술을 사용한것이라고 한다)

엘레베이터로 예시를 들어보자.
엘레베이터를 타고 제일 꼭대기층에 간다고하면,
고속으로 가다가 해당층에 도달하면 천천히 줄어들면서 멈춘다.( -> 목표에 도달하면서 모터의 힘을 서서히 바꾸는 것)
이 기술의 원리가 PWM 기술을통해 duty를 점점 줄이면서 작동하는 원리라고 볼 수 있다.

 

직류에서는 0, 1 밖에 존재하지 않는데 어떻게 5V에서 2.5V의 힘을 줄 수 있을까?(어떻게 duty를 조절할 수 있을까?)

 

0을 보내는 신호일때 0V, 1을 보내는 신호일때는 5V의 전압을 준다고 가정해보자.

만약 어떤 기기가 1초에 5V의 힘을 낸다고 가정하면,

1초 동안 2.5V의 힘을 얻고싶을때는 1초 동안 5V의 힘을 내는 받는 기기를 0.5초 동안의 힘만 내면 된다.

따라서 대략적인 그래프로 표현했을때 0.5초 동안 받는 5V와 1초 동안 받는 2.5V의 면적(duty)이 같다고 볼 수 있다.

 

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED

 

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
두 그래프의 면적이 같다고 볼 수 있다

 

 

이제 PWM의 원리를 적용하여 LED의 밝기를 조절해보자.

하얀색 LED의 + 극에 21번핀,

                   - 에 GND를 연결해서 해당 코드를 실행해보자.

 

1. PWM의 원리를 이용하여 LED의 밝기를 변화시키는 회로와 코드 작성

#-*-coding: utf-8-*-
# 파일이름 : ledPwm1.py

import RPi.GPIO as GPIO
import time

ledPin = 21

GPIO.setmode(GPIO.BCM)
GPIO.setup(ledPin, GPIO.OUT)

p = GPIO.PWM(ledPin, 255)

p.start(0)

try:
   while True:
      for i in range(20):
         p.ChangeDutyCycle(5*i)
         time.sleep(0.1)
      for i in reversed(range(20)):
         p.ChangeDutyCycle(5*i)
         time.sleep(0.1)

except KeyboardInterrupt:
   print()
   GPIO.cleanup()
라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
하얀색 LED가 밝아졌다가 어두워지는 것을 확인할 수 있다

이러한 원리로 무드등 제어의 원리를 알 수 있다.

 

 

2. 밝기를 직접 입력하여 LED 밝기를 조절하는 코드 작성

#-*-coding: utf-8-*-
# 파일이름 : ledPwm.py

import RPi.GPIO as GPIO

ledPin = 21

GPIO.setmode(GPIO.BCM)
GPIO.setup(ledPin, GPIO.OUT)

p = GPIO.PWM(ledPin, 255)
p.start(0)

while True:
   d = input("Enter Brightness(0 to 100) : ")  # LED 밝기 입력
   duty = int(d)                               # 입력받은 값이 정수인지 확인

   if(duty == 100):
      p.stop()
      GPIO.cleanup()
      break
   else:
      p.ChangeDutyCycle(duty)
라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
입력한 숫자에따라 LED의 밝기가 달라진다.

 

 

초음파 센서 제어

초음파 센서는 주파수를 보냈을때의 시간과 주파수를 보낸후 반사되어 돌아오는 시간의 차이를 측정해서 대략적인 거리를 알 수 있게하는 센서이다.

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
출처 : http://www.3demp.com/community/boardDetails.php?cbID=124

Trig핀에 10u/s의 트리거 신호를 주면 초음파를 발생시켜서 물체에 쏘고, 

Echo 핀에서 초음파가 돌아오는 시점의 시간을 측정하여 거리를 재는 원리이다.

 

 

라즈베리파이를 통해 초음파 센서를 제어해보자.

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
출처 : https://steemkr.com/arduino/@jhis21c/45kpa4

맨 왼쪽 VCC 자리에는 5V,

맨 오른쪽 GND 자리에는 그라운드,

왼쪽에서 두번째 Trig 자리에는 14번핀,

오른쪽에서 두번째 Echo 자리에는 4번 핀에 연결하고 밑의 코드를 실행해보자.

 

3. 초음파 센서 제어

#-*-coding: utf-8 -*-
# 파일이름 : ultrasonic01.py

import RPi.GPIO as GPIO
import time

triggerPin = 14
echoPin = 4

GPIO.setmode(GPIO.BCM)
GPIO.setup(triggerPin, GPIO.OUT)   # 트리거핀을 출력으로 사용
GPIO.setup(echoPin, GPIO.IN)       # 에코핀을 입력으로 사용

try:
    while True:
      #구형파 발생
      GPIO.output(triggerPin, GPIO.LOW)  # 10m/s 동안 초음파를 쏴야함
      time.sleep(0.00001)                # 기초단위가 1초라서 10us는 10의 마이너스 5승으로 처리
      GPIO.output(triggerPin, GPIO.HIGH)

      #시간측정
      while GPIO.input(echoPin) == 0:  # 펄스 발생(초음파 전송이 끝나는 시간을 start에 저장)
         start = time.time()
      while GPIO.input(echoPin) == 1:  # 펄스 돌아옴(초음파 수신이 완료될때까지의 시간을 stop에 저장)
         stop = time.time()

      rtTotime = stop - start   # 리턴 투 타임 = (end시간 - start시간)

      # 거리 = 시간 * 속력
      # 이때 소리의  속력은 340m/s인데 cm로 단위를 바꿔줘야함=> 34000 cm/s
      # 그리고 340m/s 는 왕복속도라서 편도로 봐야하니 나누기 2를 해줘야함
      distance = rtTotime * ( 34000 / 2 )
      print("distance : %.2f cm" %distance) # 거리를 출력
      time.sleep(1)  # 1초마다 받아옴

except KeyboardInterrupt:
   GPIO.cleanup()
라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
초음파센서에 손이나 물건을 갖다대서 거리 수치 변화를 관찰해보자

 

 

4. 초음파센서와 부저센서를 이용한 후방감지센서 만들기

초음파센서를통해 물체와의 거리를 잴 수 있게 됬으니, 자동차의 후방센서를 구현해보자.

초음파센서에 물체와의 거리가 점점 좁혀지면 부저센서에서 더 빠르게 소리를 출력하는 원리를 구현해보자.

라즈베리 파이 초음파센서 거리 LED - lajeubeli pai cho-eumpasenseo geoli LED
회로구성
 #-*-coding: utf-8 -*-

import RPi.GPIO as GPIO
import time

triggerPin = 14
echoPin = 4
pinPiezo = 21

GPIO.setmode(GPIO.BCM)
GPIO.setup(triggerPin, GPIO.OUT)    # 출력
GPIO.setup(echoPin, GPIO.IN)        # 입력
GPIO.setup(pinPiezo, GPIO.OUT)

Buzz = GPIO.PWM(pinPiezo, 440)      # 부저센서 초기화

try:
   while True:
      #구형파 발생
      GPIO.output(triggerPin, GPIO.LOW)  
      time.sleep(0.00001) 
      GPIO.output(triggerPin, GPIO.HIGH)

      #시간측정
      while GPIO.input(echoPin) == 0:  # 펄스 발생
         start = time.time()
      while GPIO.input(echoPin) == 1:  # 펄스 돌아옴
         stop = time.time()

      rtTotime = stop - start                   # 리턴 투 타임 = (end시간 - start시간)

      distance = rtTotime * (34000 / 2 )
      print("distance : %.2f cm" %distance)     # 거리 출력
      time.sleep(0.2)  

      if(distance <= 40 and distance > 25):     # 26 ~ 40 cm 일때
         Buzz.start(50)
         Buzz.ChangeFrequency(523)
         time.sleep(0.3)
         Buzz.stop()
         time.sleep(0.3)
      elif(distance <= 25 and distance > 10):   # 25 ~ 11 cm 일때
         Buzz.start(50)
         Buzz.ChangeFrequency(523)
         time.sleep(0.15)
         Buzz.stop()
         time.sleep(0.1)
      elif(distance <= 10):                     # 10cm 이하일때
         Buzz.start(99)
         Buzz.ChangeFrequency(523) 
         time.sleep(0.05)
         Buzz.stop()
         time.sleep(0.05)
      else:                                     # 그 외(겁나 멀때)
         Buzz.stop()
         time.sleep(0.5)

except KeyboardInterrupt:
   GPIO.cleanup()

영상을 확인해보면 거리에따라 부저센서가 울리는 빈도수 변화를 관찰할 수 있다.

 

반응형

공유하기

게시글 관리

구독하기취준생 일지

저작자표시 비영리 변경금지

'개발자과정준비 > 라즈베리파이(Raspberry Pi)' 카테고리의 다른 글

라즈베리파이 파이썬 Cron식, Sqlite  (0)2021.05.27라즈베리파이 Flask 웹 서버 제어  (1)2021.05.26라즈베리파이 풀업, 풀다운 회로 구현  (0)2021.05.26라즈베리파이로 부저센서 출력, 피아노 구현  (0)2021.05.25[RaspberryPi] 블루투스와 비콘  (0)2020.09.23