2학년 프로젝트

아두이노가 연결되지 않았습니다. 시작 버튼을 누르면 연결을 시도합니다.

상태: 대기 중

Arduino 자율주행 코드

2학년 프로젝트에서 사용된 자율주행 로봇의 Arduino 코드입니다.

#include <Arduino.h>

/* ===============================
   ===== 핀 설정 =====
================================ */

// ===== 주행용 스텝/모터 드라이버 (단순화: DC처럼 사용) =====
#define EA 3
#define EB 11
#define M_IN1 4
#define M_IN2 5
#define M_IN3 13
#define M_IN4 12

// ===== 라인 센서 =====
#define LINE_L  A0
#define LINE_R  A1


// ===== 초음파 =====
#define trig 7
#define echo 6

// ===== 팔 DC모터 (L298N) =====
#define ARM_EN   10
#define ARM_IN1  8
#define ARM_IN2  9

/* ===============================
   ===== 파라미터 =====
================================ */
int motor_speed = 180;

#define STOP_DISTANCE  12
#define CLEAR_DISTANCE 25

#define ARM_SPEED     140
#define ARM_MOVE_TIME 300   // ms

/* ===============================
   ===== 소프트웨어 상태 =====
================================ */
bool autoDrive = true;   // 자율주행 ON/OFF
bool armActive = false;  // 팔 동작 중 여부

/* ===============================
   ===== 함수 선언 =====
================================ */
unsigned int read_ultrasonic();

void motorA_con(int M1);
void motorB_con(int M2);

void stopCar();
void forwardCar();
void backwardCar();
void turnLeft();
void turnRight();

void armUp();
void armDown();
void armStop();
void lineTrace();

/* ===============================
   ===== 초기화 =====
================================ */
void setup()
{
  pinMode(EA, OUTPUT);
  pinMode(EB, OUTPUT);
  pinMode(M_IN1, OUTPUT);
  pinMode(M_IN2, OUTPUT);
  pinMode(M_IN3, OUTPUT);
  pinMode(M_IN4, OUTPUT);
  pinMode(LINE_L, INPUT);
  pinMode(LINE_R, INPUT);

  pinMode(trig, OUTPUT);
  pinMode(echo, INPUT);

  pinMode(ARM_EN, OUTPUT);
  pinMode(ARM_IN1, OUTPUT);
  pinMode(ARM_IN2, OUTPUT);

  stopCar();
  armStop();

  delay(2000);
}

/* ===============================
   ===== 메인 루프 =====
================================ */
void loop()
{
  /* ---- 팔 동작 중이면 주행 정지 ---- */
  if (armActive) {
    stopCar();
    return;
  }

  /* ---- 자율주행 OFF 상태 ---- */
  if (!autoDrive) {
    stopCar();
    return;
  }

  lineTrace();

  /* ---- 자율주행 로직 ---- */
  unsigned int distance = read_ultrasonic();

  if (distance > STOP_DISTANCE) {
    forwardCar();
  } 
  else {
    // 가까우면 회피
    stopCar();
    delay(150);

    backwardCar();
    delay(300);

    stopCar();
    delay(150);

    turnRight();
    delay(350);

    stopCar();
    delay(100);
  }

  /* ---- 예시: 일정 조건에서 팔 동작 ---- */
  if (distance < 8) {
    armActive = true;
    armUp();
    delay(500);
    armDown();
    armActive = false;
  }
}

/* ===============================
   ===== 초음파 =====
================================ */
unsigned int read_ultrasonic()
{
  digitalWrite(trig, LOW);
  delayMicroseconds(2);
  digitalWrite(trig, HIGH);
  delayMicroseconds(10);
  digitalWrite(trig, LOW);

  unsigned long t = pulseIn(echo, HIGH, 30000);
  if (t == 0) return 999;

  return (unsigned int)((t * 0.034) / 2);
}

/* ===============================
   ===== 주행 제어 =====
================================ */
void stopCar() {
  motorA_con(0);
  motorB_con(0);
}

void forwardCar() {
  motorA_con(motor_speed);
  motorB_con(motor_speed);
}

void backwardCar() {
  motorA_con(-motor_speed);
  motorB_con(-motor_speed);
}

void turnLeft() {
  motorA_con(-motor_speed);
  motorB_con(motor_speed);
}

void turnRight() {
  motorA_con(motor_speed);
  motorB_con(-motor_speed);
}
// 라인트레이싱
void lineTrace()
{
  int left = digitalRead(LINE_L);
  int right = digitalRead(LINE_R);

  // ● 검은 선 = LOW, ○ 흰 바닥 = HIGH

  if (left == LOW && right == LOW) {
    // ● ●  → 직진
    forwardCar();
  }
  else if (left == LOW && right == HIGH) {
    // ● ○  → 왼쪽이 선 → 좌회전
    motorA_con(motor_speed * 0.6);
    motorB_con(motor_speed);
  }
  else if (left == HIGH && right == LOW) {
    // ○ ●  → 오른쪽이 선 → 우회전
    motorA_con(motor_speed);
    motorB_con(motor_speed * 0.6);
  }
  else {
    // ○ ○  → 선 이탈 → 정지 or 탐색
    stopCar();
  }
}

/* ===============================
   ===== 팔 제어 =====
================================ */
void armUp() {
  digitalWrite(ARM_IN1, HIGH);
  digitalWrite(ARM_IN2, LOW);
  analogWrite(ARM_EN, ARM_SPEED);
  delay(ARM_MOVE_TIME);
  armStop();
}

void armDown() {
  digitalWrite(ARM_IN1, LOW);
  digitalWrite(ARM_IN2, HIGH);
  analogWrite(ARM_EN, ARM_SPEED);
  delay(ARM_MOVE_TIME);
  armStop();
}

void armStop() {
  digitalWrite(ARM_IN1, LOW);
  digitalWrite(ARM_IN2, LOW);
  analogWrite(ARM_EN, 0);
}

/* ===============================
   ===== 모터 드라이버 =====
================================ */
void motorA_con(int M1)
{
  if (M1 > 0) {
    digitalWrite(M_IN1, HIGH);
    digitalWrite(M_IN2, LOW);
  } 
  else if (M1 < 0) {
    digitalWrite(M_IN1, LOW);
    digitalWrite(M_IN2, HIGH);
  } 
  else {
    digitalWrite(M_IN1, LOW);
    digitalWrite(M_IN2, LOW);
  }
  analogWrite(EA, abs(M1));
}

void motorB_con(int M2)
{
  if (M2 > 0) {
    digitalWrite(M_IN3, HIGH);
    digitalWrite(M_IN4, LOW);
  } 
  else if (M2 < 0) {
    digitalWrite(M_IN3, LOW);
    digitalWrite(M_IN4, HIGH);
  } 
  else {
    digitalWrite(M_IN3, LOW);
    digitalWrite(M_IN4, LOW);
  }
  analogWrite(EB, abs(M2));
}

보고서

!완전 구현 실패 사유

  • 1

    설계 및 시간 관리 미흡

    초기 설계 단계, 오류와 하드웨어 완벽 구현을 위한 시간 확보 미흡

  • 2

    협업 및 의사소통 제약

    팀원 간 일정 조율 어려움으로 인해 실시간 협업 및 의사소통 제약 발생

  • 3

    하드웨어 연결 오류

    아두이노 모듈 간 연결 오류로 인해 많은 시간 소요

개선 방안

  • 1

    하드웨어 재분석

    작품 설계 및 회로 구성, 발열 문제 등에 대한 체계적인 재분석

  • 2

    소프트웨어 심화 학습

    ESP32 마이크로 컨트롤러 문법 및 통신 프로토콜 심화 학습으로 연결 오류 근본 해결

  • 3

    정기 회의 체계 구축

    팀 협업 효율성을 위해 주 3회 정기 소규모 회의 운영, 진행 상황 공유 및 즉각 피드백 체계 구축

연락처

궁금한 점이 있으시면 언제든 연락해주세요.

단국대학교부속소프트웨어고등학교 3F 응용 프로그래밍실