프로젝트

나도 메이커! 메이커스 여러분들의 작품/프로젝트를 공유하는 공간입니다.

리드 스위치(reed switch)를 이용하여 자전거 속도계를 만들어 봅시다. - 1부 : 이론 및 테스트 편

2015-01-19 16:22:37

개요 및 부품 목록

리드 스위치(reed switch)는 평소에는 유리관 속에 밀봉된 2개의 자성 리드 조각이 스프링의 탄성에 의해 열린 상태로 되어있습니다.

스위치에 자석을 접근시키면 2개의 리드 조각을 통하여 자기회로가 되어 2개의 리드는 끌어당겨져 접점을 닫습니다(그림 b).

다시 자석을 멀리하면 탄성으로 인해서 열린 상태로 돌아갑니다.

 
- 출처 : 네이버 지식백과 - 리드 스위치


이러한 리드 스위치의 특성을 이용하여 자전거 속도계를 만들어 보겠습니다. 
(이번 컨텐츠에서는 테스트용을 만들어서 테스트 해보고, 다음 컨텐츠에서는 실제로 사용가능 하도록 만들어서 사용해 보겠습니다.) 

 

부품 목록

NO 부품명 수량 상세설명
1 오렌지보드 1 아두이노 UNO 호환 보드
2 리드스위치 1 ky021
3 LCD Sparkfun LCD-00709
4 가변저항 1  
5 버튼 1  
6 브레드보드 1  
7 점퍼케이블 21  

 

부품명 오렌지보드 리드스위치 LCD
파트

 

 

부품명 가변저항 버튼 브레드보드 점퍼케이블
파트

 

 

 

하드웨어 making 및 소프트웨어 coding

 

 

브레드보드 레이아웃


 

 

 

회로도


 

 

 

 

 

작동 원리

 

 

자전거 바퀴의 반지름을 이용하여 바퀴 둘레의 길이를 구해줍니다. 이를 이용하여 자전거 바퀴가 한바퀴 돌았을 때 이동한 거리를 확인 할 수 있습니다.



리드 스위치를 이용하여 자전거 바퀴가 한바퀴 돌 때의 시간을 측정하는 방법입니다.
밑의 사진과 같이 리드 스위치를 한점에 고정을 시키고 바퀴에 자석을 붙여서 자전거 바퀴가 돌면서 자석이 다시 리드 스위치가 있는 곳으로 올 때까지의 시간을 측정하면 됩니다. (리드 스위치가 열릴 때 부터 다시 닫힐 때 까지의 시간을 구하면 됩니다.)



속도 = 거리 / 시간 공식을 이용하여 바퀴의 둘레와 바퀴가 한바퀴 도는데 걸리는 시간으로 자전거의 속도를 구해줍니다.

마찬가지로 자전거의 누적 거리는 자전거가 한바퀴 돌 때(이것도 리드 스위치로 확인하면 됩니다.) 자전거의 둘레를 더해주면 됩니다.
 

아두이노 소스

#include <Time.h>
#include <LiquidCrystal.h>

float radius = 20; // 바퀴당 이동 거리를 확인 하기 위해 자전거 바퀴의 반지름을 입력해 줍니다.(Cm 단위)
float circle = (2 * radius * 3.14) / 100;  // 자전거 바퀴의 둘레를 계산(단위를 m로 바꿔주기 위해 100을 나눕니다.)

float bySpeed = 0; // 자전거의 속도
float ckTime = 0;  // 리드스위치가 
float uckTime = 0; // Unckecked
float cycleTime = 0;  // 리드스위치가 인식이 안됬을 시간 부터 인식됬을 때까지의 시간
float distance = 0; // 자전거의 누적 이동 거리
float lcdDis = 0; // 자전거의 이동 거리를 LCD출력에 맞게 바꿔즌 값.(단위 수정 or 소숫점 제거)

int count = 0;  // 리드스위치의 노이즈를 제거하기 위해 카운트를 넣어줍니다.
boolean temp = 0;  // 리드 스위치가 닫혔는지 확인하는 변수

LiquidCrystal lcd(12,11,5,4,3,2);   //RS 핀, E핀, 데이터 핀 4개

void setup(){
  Serial.begin(9600);  // 측정된 값을 시리얼 모니터로 확인하기 위해 bps를 설정해 줍니다.
  
  lcd.begin(16,2); // LCD 크기 지정, 2줄 16칸
  lcd.clear();     // 화면 초기화
}

void loop(){
  boolean check = digitalRead(A0); // 리드스위치의 상태를 확인합니다.
  
  if(check == 1 && temp == 0){  // 리드 스위치가 열릴 때(닫힘 -> 열림)
    ckTime = millis();  // 시간을 확인해서 저장합니다.
    temp = 1;  // temp값을 1로 바꿔줍니다.(리드스위치가 열려있는 상태값 저장)
  }
  
  else if(check == 0 && temp == 1 && count > 5){  // 리드 스위치가 닫히고(열림 -> 닫힘), 노이즈 방지 카운트가 5이상일때
    uckTime = millis();  // 시간을 확인해서 저장합니다.
      
    cycleTime = (uckTime - ckTime) / 1000;
    // 열릴 때 시각과 닫힐 때 시각의 차를 이용하여 바퀴가 한바퀴 돌때 걸린 시간을 계산합니다.
    bySpeed = (circle / cycleTime) * 3.6; // 바퀴가 한바퀴 돌때의 거리와 시간을 가지고 속도를 구해줍니다.(단위는 Km/h입니다.)
    temp = 0; 
    count = 0; 
    distance += circle;  // 한바퀴 돌았으면 이동거리를 누적 이동거리에 더해줍니다.
  }
  
  if(check == 1){  // 리드 스위치가 열려있으면 카운트를 1씩 증가 시켜 줍니다.
    count++;
    if(count > 150){ // 카운트가 150이 넘어가면(자전거가 멈췄을 때) 속도를 0으로 바꿔줍니다.
      bySpeed = 0;
    }
  }
  
  if(digitalRead(A1) == 0){  // 버튼을 누르면 누적거리를 0으로 초기화 합니다.
    distance = 0;
  }


  lcd.setCursor(0,0);          //커서를 0,0에 지정
  lcd.print("Speed: "); 
  if(bySpeed < 10){            // 속도가 한자리라면 앞에 0을 붙여 줍니다.
    lcd.print('0');
  }
  lcd.print(bySpeed);               
  lcd.print("Km/h");           // 속도를 lcd에 출력합니다.("Speed: xx.xxKm/h");
  
  lcdDis = distance / 1000;  
  lcd.setCursor(0,1);          // 커서를 0,1에 지정
  lcd.print("Distance: ");  
  if(lcdDis >= 100){           // 이동거리가 100Km가 넘어가면 소숫점을 지워줍니다.
    lcd.print((int)lcdDis);
  }
  else{
    lcd.print(lcdDis);               
  }            
  lcd.print("Km");             // 이동거리를 lcd에 출력합니다.("Distance: xx.xxKm")
  
  lcd.print("               ");        //전 글씨 삭제
  Serial.print("Speed : ");
  Serial.print(bySpeed);
  Serial.println(" km/h");             // 시리얼 모니터를 이용하여 속도를 확인합니다.
}

 

아두이노 소스 설명

 

float radius = 20; // 바퀴당 이동 거리를 확인 하기 위해 자전거 바퀴의 반지름을 입력해 줍니다.(Cm 단위)
float circle = (2 * radius * 3.14) / 100;  // 자전거 바퀴의 둘레를 계산(단위를 m로 바꿔주기 위해 100을 나눕니다.)

자전거 바퀴의 반지름을 입력해야 합니다. 자신이 사용하는 자전거 바퀴의 반지름을 측정하여 radius에 넣어줍니다.(정확하게 입력해야 속도가 정확하게 나옵니다.)
* 현재는 20으로 적혀 있는데 임의의 값을 넣은 것입니다. 자신에게 맞는 값으로 꼭 바꿔주세요.


이렇게 입력한 반지름을 이용해서 자전거 바퀴의 둘레를 구해줍니다.(반지름 * 2 * 3.14)

 

  if(check == 1 && temp == 0){  // 리드 스위치가 열릴 때(닫힘 -> 열림)
    ckTime = millis();  // 시간을 확인해서 저장합니다.
    temp = 1;  // temp값을 1로 바꿔줍니다.(리드스위치가 열려있는 상태값 저장)
  }
  
  else if(check == 0 && temp == 1 && count > 5){  // 리드 스위치가 닫히고(열림 -> 닫힘), 노이즈 방지 카운트가 5이상일때
    uckTime = millis();  // 시간을 확인해서 저장합니다.
      
    cycleTime = (uckTime - ckTime) / 1000;
    // 열릴 때 시각과 닫힐 때 시각의 차를 이용하여 바퀴가 한바퀴 돌때 걸린 시간을 계산합니다.
    bySpeed = (circle / cycleTime) * 3.6; // 바퀴가 한바퀴 돌때의 거리와 시간을 가지고 속도를 구해줍니다.(단위는 Km/h입니다.)
    temp = 0; 
    count = 0; 
    distance += circle;  // 한바퀴 돌았으면 이동거리를 누적 이동거리에 더해줍니다.
  }

리드 스위치를 이용하여 자전거의 바퀴가 한바퀴 돌 때 까지의 시간을 구하고, 자전거 바퀴의 둘레를(거리) 이용하여 자전거의 속도를 구해줍니다.

리드 스위치의 상태가 변할 때의 시간을 저장해서 열릴때의 시간과 닫힐 때의 시간 차로 시간을 구합니다.

가끔 리드 스위치와 자석이 근접했는데 인식을 못해서 속도값이 오류가 날 수도 있으니, Count를 넣어서 오류가 나는 속도값을 무시합니다.(잠깐 인식을 못할 경우를 무시)
 

  lcd.setCursor(0,0);          //커서를 0,0에 지정
  lcd.print("Speed: "); 
  if(bySpeed < 10){            // 속도가 한자리라면 앞에 0을 붙여 줍니다.
    lcd.print('0');
  }
  lcd.print(bySpeed);               
  lcd.print("Km/h");           // 속도를 lcd에 출력합니다.("Speed: xx.xxKm/h");
  
  lcdDis = distance / 1000;  
  lcd.setCursor(0,1);          // 커서를 0,1에 지정
  lcd.print("Distance: ");  
  if(lcdDis >= 100){           // 이동거리가 100Km가 넘어가면 소숫점을 지워줍니다.
    lcd.print((int)lcdDis);
  }
  else{
    lcd.print(lcdDis);               
  }            
  lcd.print("Km");             // 이동거리를 lcd에 출력합니다.("Distance: xx.xxKm")

LCD에 속도와 누적 이동 거리를 출력하는 부분입니다. 속도는 2자리를 출력을 기준으로 해서, 속도가 1자리일 경우 앞에 0을 추가로 출력해서 2자리를 맞춥니다.
(EX : 8.10Km/h -> 08.10Km/h)

이동거리는 Km단위로 바꿔준 후 LCD에 출력합니다.(소숫점 두자리까지 출력합니다.) 누적 이동거리가 100Km가 넘었을 경우는 소숫점을 제외하고 출력해 줍니다.


리드 스위치에 자석을 근접했다가 멀어지는 것을 반복하면 속도가 나옵니다.(반지름 세팅한 것에 따라 측정값과 이동거리가 다르게 나옵니다.)

여기까지가 속도계 테스트 입니다. 다음 컨텐츠에서는 속도계를 자전거에 세팅해 보고 직접 테스트 해보겠습니다.

판다마니아

아두이노, 리드 스위치, 자석, 버튼, 자전거 속도, 자전거 이동거리
profile

라니유리 2017-04-25 18:18:22

코딩에서 리셋부분이 동작을 안하는데요 ㅠㅠ 다르게 코딩 하는 방법이 있나요?

오히려 잘못동작해서 거리가 자꾸 0으로 떨어져버려요 리셋을 안해두 버튼하고 저항으로 리셋하게 설정했습니다.

profile

as17894 2017-06-06 19:44:50

판다마니아님 저도 이 회로를 보고 똑같이 만들어 보았는데 거리가 기록이 되지 않는데 코딩에서 어떠한점이 문제가 있나요????