Chapter 6. 아날로그 입력 및 모터 제어 (가변저항, SG90 서보모터)
0과 1뿐만 아니라 연속적인 아날로그 값을 다뤄봅니다. 가변저항의 아날로그 값을 읽어 정밀 제어용 관절 소자인 서보모터의 회전 각도를 제어해 봅니다.
6.1 가변저항의 아날로그 값(ADC) 읽기
Pico 2는 12비트 아날로그-디지털 변환기(ADC)를 내장하고 있으나, 마이크로파이썬 내부 표준에 의해 16비트 범위인 0 ~ 65535 값으로 변환되어 읽힙니다.
가변저항 3핀: 좌측 핀→3V3, 중앙(Wiper) 핀→GP26(ADC0), 우측 핀→GND. 노브를 돌리면 GP26에서 읽히는 전압이 0V~3.3V 사이로 변합니다.
from machine import ADC, Pin
import time
# Pico 2의 ADC0번 채널(GPIO 26번 핀)에 가변저항 가운데 핀 연결
potentiometer = ADC(Pin(26))
while True:
# 아날로그 전압 읽기 (범위: 0 ~ 65535)
raw_value = potentiometer.read_u16()
# 아날로그 값을 실제 인가되는 전압(0.0V ~ 3.3V) 값으로 환산계산
voltage = (raw_value * 3.3) / 65535
print(f"정밀 ADC 데이터: {raw_value} | 환산 전압: {voltage:.2f} V")
time.sleep(0.3)
💡 ADC란 무엇이고 왜 필요한가요?
ADC(Analog-to-Digital Converter, 아날로그-디지털 변환기)는 연속적으로 변하는 아날로그 전압(0V~3.3V)을 컴퓨터가 이해할 수 있는 디지털 숫자로 바꿔주는 장치입니다. 디지털 핀은 0(LOW) 또는 1(HIGH)만 표현하지만, 가변저항·조도센서·마이크 등 아날로그 부품은 그 사이의 무한한 값을 출력하기 때문에 반드시 ADC를 거쳐야 마이크로컨트롤러가 값을 읽을 수 있습니다. Pico 2는 GP26, GP27, GP28번 핀이 ADC 전용(ADC0~ADC2) 핀으로 지정되어 있습니다.
📐 0~65535 값을 백분율(%)로 바꾸기
ADC 원시값을 사람이 이해하기 쉬운 퍼센트로 변환하려면 아래와 같이 계산합니다.
from machine import ADC, Pin
import time
potentiometer = ADC(Pin(26))
while True:
raw_value = potentiometer.read_u16()
voltage = (raw_value * 3.3) / 65535 # 전압(V) 환산
percent = (raw_value / 65535) * 100 # 백분율(%) 환산
print(f"raw={raw_value} | {voltage:.2f}V | {percent:.1f}%")
time.sleep(0.3)
read_u16()은 항상 0~65535 범위(부호 없는 16비트)로 결과를 돌려줍니다. Pico 2의 ADC 하드웨어 자체는 12비트(0~4095) 해상도이지만, MicroPython이 이를 16비트 범위로 스케일링하여 다른 보드와 코드 호환성을 유지해 줍니다.
🏆 과제 해결해보기!
과제 1. 가변저항 값에 따라 LED 밝기 3단계 표시하기
가변저항 값을 백분율로 바꿔서, 0~33%이면 "낮음", 34~66%이면 "보통", 67~100%이면 "높음"을 출력하는 코드를 작성해 보세요.
6.2 SG90 서보모터 정밀 각도 통제
서보모터는 50Hz 주기의 PWM 펄스 폭을 조절하여 0도부터 180도까지의 원하는 각도를 정밀 조율합니다.
SG90 서보: 빨간선→VSYS(5V), 주황선→GP19(PWM), 갈색선→GND. 서보는 5V 구동이 필요하므로 VSYS 핀을 사용합니다. USB 전원 시 최대 전류 제한에 주의하세요.
💡 서보모터 듀티(duty) 값은 어떻게 계산되나요?
SG90 서보모터는 50Hz(1초에 50번, 즉 20ms 주기)의 펄스를 받아 그 중 HIGH로 유지되는 시간(펄스 폭)에 따라 각도가 결정됩니다. 일반적으로 펄스 폭이 0.5ms이면 0°, 1.5ms이면 90°, 2.5ms이면 180°를 가리킵니다.
MicroPython의 duty_u16()은 0~65535 범위로 "주기 대비 HIGH 비율"을 지정합니다. 계산 공식은 다음과 같습니다.
# duty_u16 = (펄스 폭(ms) / 주기(20ms)) × 65535
# 0도: (0.5 / 20) × 65535 ≈ 1638
# 90도: (1.5 / 20) × 65535 ≈ 4915
# 180도: (2.5 / 20) × 65535 ≈ 8192
본 교재의 set_angle() 함수는 이 1638(0°)과 8192(180°) 두 지점을 기준으로 각도(0~180)를 선형 비례식으로 환산하여 duty_u16()에 전달합니다.
[응용 실습] 가변저항 돌리는 대로 서보모터 동적 조각하기
from machine import Pin, PWM, ADC
import time
pot = ADC(Pin(26))
servo = PWM(Pin(19))
servo.freq(50) # 서보모터 표준 동작 주파수 50Hz 설정
# SG90 서보모터 마이크로파이썬 16비트 기준 듀티값 정의
# 0도 일 때 대략 1638 / 180도 일 때 대략 8192
def set_angle(angle):
duty = int(1638 + (angle * (8192 - 1638) / 180))
servo.duty_u16(duty)
print("연동 제어 시스템 가동. 가변저항을 돌려보세요.")
while True:
pot_val = pot.read_u16()
# 0~65535 의 가변저항 범위를 0~180도 모터 각도 범위로 매핑변환
target_angle = (pot_val * 180) / 65535
set_angle(target_angle)
print(f"가변저항 위치: {pot_val} -> 모터 제어 각도: {target_angle:.1f}°")
time.sleep(0.05)
🏆 과제 해결해보기!
과제 1. 서보모터로 0°→180°→0° 왕복운동 만들기
for 반복문을 사용하여 서보모터를 0도부터 180도까지 서서히 회전시킨 뒤, 다시 180도부터 0도까지 되돌아오는 왕복운동 코드를 작성해 보세요. (힌트: range()를 활용하면 각도를 1도씩 증가·감소시킬 수 있습니다.)
과제 2. 가변저항 값에 따라 3단계 경보등 만들기
가변저항 값을 백분율로 환산해서, 70% 이상이면 서보모터를 180도(경보 발생 위치)로 돌리고, 그렇지 않으면 0도(평상시 위치)로 유지하는 코드를 작성해 보세요.
6.3 Wokwi 시뮬레이션으로 실습하기
Chapter 1의 1.8 실물 없이도 실습! Wokwi 온라인 시뮬레이터에서 소개한 대로, Wokwi를 이용하면 가변저항과 SG90 서보모터가 없어도 브라우저에서 곧바로 회로를 구성하고 코드를 검증할 수 있습니다.
📄 diagram.json 예시 (가변저항 + SG90 서보)
{
"version": 1,
"author": "picostudy",
"editor": "wokwi",
"parts": [
{ "type": "wokwi-pi-pico", "id": "pico", "top": 0, "left": 0, "attrs": {} },
{ "type": "wokwi-potentiometer", "id": "pot1", "top": -60, "left": 200, "attrs": {} },
{ "type": "wokwi-servo", "id": "servo1", "top": 100, "left": 220, "attrs": {} }
],
"connections": [
[ "pico:GP26", "pot1:SIG", "yellow", [] ],
[ "pico:3V3", "pot1:VCC", "red", [] ],
[ "pico:GND", "pot1:GND", "black", [] ],
[ "pico:GP19", "servo1:PWM", "orange", [] ],
[ "pico:VSYS", "servo1:V+", "red", [] ],
[ "pico:GND", "servo1:GND", "black", [] ]
]
}
회로를 구성한 뒤 main.py 탭에 이 챕터의 6.1 또는 6.2 코드를 붙여넣고 화면 상단의 ▶️ (초록색 재생) 버튼을 누르면 시뮬레이션이 시작됩니다. Wokwi 화면에서 가변저항 노브를 마우스로 드래그하면 실시간으로 ADC 값이 바뀌고, 서보모터 화살표가 회전하는 모습을 눈으로 확인할 수 있습니다.
시뮬레이터 사용 시 주의사항
Wokwi 라이브러리의 부품명은 "Potentiometer", "Servo Motor" 등으로 검색해 정확한 type 값을 확인하세요 (환경에 따라 wokwi-potentiometer-onoff 처럼 전원 스위치가 달린 버전도 있습니다). 시뮬레이션 상의 서보모터는 실제 SG90의 미세한 오차나 반응 지연을 완벽히 재현하지 않으므로, 코드 로직 검증 용도로만 활용하고 최종 동작 확인은 실제 부품으로 진행하세요.