본문 바로가기

아두이노우노 R4

MPU6050, MAX7219 8x8 Dot Matrix 아두이노 모래시계 소스코드 1

반응형
8×8 도트 매트릭스 모듈 2개와 MPU6050 가속도 센서를 사용한 아두이노 모래시계 소스코드입니다. 가속도 센서로 기울기를 감지하여 위쪽 매트릭스의 "모래(LED 불빛)"가 아래쪽 매트릭스로 떨어지도록 구현되었습니다.

 

🛠️ 준비물
  • Arduino Uno 또는 Nano 1개
  • MAX7219 드라이버가 포함된 8x8 도트 매트릭스 모듈 2개
  • MPU6050 가속도/자이로 센서 모듈 1개
  • 점퍼선 수스/암수
🔌 배선 연결 (Wiring)

 

1. MPU6050 ➡ 아두이노
  • VCC ➡ 5V
  • GND ➡ GND
  • SCL ➡ A5
  • SDA ➡ A4
2. 위쪽 매트릭스 (MAX7219) ➡ 아두이노
  • VCC ➡ 5V
  • GND ➡ GND
  • DIN ➡ Pin 12
  • CS ➡ Pin 11
  • CLK ➡ Pin 10
3. 아래쪽 매트릭스 (MAX7219) ➡ 아두이노
  • VCC ➡ 5V
  • GND ➡ GND
  • DIN ➡ Pin 9
  • CS ➡ Pin 8
  • CLK ➡ Pin 7

 

💻 아두이노 소스코드
코드를 업로드하기 전에 아두이노 IDE의 라이브러리 관리자에서 MD_MAX72xx 라이브러리를 반드시 설치해 주세요.
 
현재 MPU 적용 하지 않고 모래처럼 떨어지도록 수정한 코드

 

#include <MD_MAX72xx.h>
#include <SPI.h>

#define HARDWARE_TYPE MD_MAX72XX::FC16_HW

// 핀 설정
#define CLK_PIN_TOP 13
#define DATA_PIN_TOP 11
#define CS_PIN_TOP 10

#define CLK_PIN_BOT 7
#define DATA_PIN_BOT 9
#define CS_PIN_BOT 8

MD_MAX72XX topMatrix = MD_MAX72XX(HARDWARE_TYPE, DATA_PIN_TOP, CLK_PIN_TOP, CS_PIN_TOP, 1);
MD_MAX72XX botMatrix = MD_MAX72XX(HARDWARE_TYPE, DATA_PIN_BOT, CLK_PIN_BOT, CS_PIN_BOT, 1);

bool topGrid[8][8];
bool botGrid[8][8];

// 업데이트 순서를 무작위로 섞기 위한 배열
int pixelOrder[64];

// 유효 좌표 확인
bool isValid(int row, int col) {
  return row >= 0 && row < 8 && col >= 0 && col < 8;
}

// 매트릭스 초기화
void initMatrices() {
  memset(botGrid, 0, sizeof(botGrid));
  botMatrix.clear();
  topMatrix.clear();
  for (int r = 0; r < 8; r++) {
    for (int c = 0; c < 8; c++) {
      topGrid[r][c] = true;
      topMatrix.setPoint(r, c, true);
    }
  }
  // 업데이트 순서 배열 초기화 (0~63)
  for (int i = 0; i < 64; i++) pixelOrder[i] = i;
}

// 화면 출력 (깜빡임 방지를 위해 버퍼 업데이트 사용)
void displayGrids() {
  topMatrix.control(MD_MAX72XX::UPDATE, MD_MAX72XX::OFF);
  botMatrix.control(MD_MAX72XX::UPDATE, MD_MAX72XX::OFF);
  
  for (int r = 0; r < 8; r++) {
    for (int c = 0; c < 8; c++) {
      topMatrix.setPoint(r, c, topGrid[r][c]);
      botMatrix.setPoint(r, c, botGrid[r][c]);
    }
  }
  
  topMatrix.control(MD_MAX72XX::UPDATE, MD_MAX72XX::ON);
  botMatrix.control(MD_MAX72XX::UPDATE, MD_MAX72XX::ON);
}

// 배열 무작위 셔플 (Fisher-Yates) - 하단 매트릭스용
void shuffleOrder() {
  for (int i = 63; i > 0; i--) {
    int j = random(i + 1);
    int temp = pixelOrder[i];
    pixelOrder[i] = pixelOrder[j];
    pixelOrder[j] = temp;
  }
}

// 물리 엔진 업데이트
void updatePhysics() {
  // 1. 하단 매트릭스 업데이트 (기존 방식 유지)
  shuffleOrder();
  for (int i = 0; i < 64; i++) {
    int r = pixelOrder[i] / 8;
    int c = pixelOrder[i] % 8;
    
    if (botGrid[r][c]) {
      if (r < 7 && c < 7 && !botGrid[r + 1][c + 1]) {
        botGrid[r][c] = false;
        botGrid[r + 1][c + 1] = true;
      } else {
        int dir = random(2);
        if (dir == 0) {
          if (r < 7 && !botGrid[r + 1][c]) { botGrid[r][c] = false; botGrid[r + 1][c] = true; }
          else if (c < 7 && !botGrid[r][c + 1]) { botGrid[r][c] = false; botGrid[r][c + 1] = true; }
        } else {
          if (c < 7 && !botGrid[r][c + 1]) { botGrid[r][c] = false; botGrid[r][c + 1] = true; }
          else if (r < 7 && !botGrid[r + 1][c]) { botGrid[r][c] = false; botGrid[r + 1][c] = true; }
        }
      }
    }
  }

  // 2. 위 -> 아래 전배 (깜빡임 방지 및 입구 고정 불빛 제거를 위해 딜레이 적용)
  static int spawnDelay = 0;
  if (spawnDelay > 0) {
    spawnDelay--;
  } else if (!botGrid[0][0]) {
    // 상단 매트릭스에서 가장 위쪽(r+c가 작은 순서)에 있는 모래알 찾기
    bool found = false;
    for (int s = 0; s <= 14; s++) { // s = r + c
      for (int r = 0; r <= s; r++) {
        int c = s - r;
        if (isValid(r, c) && topGrid[r][c]) {
          topGrid[r][c] = false; // 맨 위 표면의 모래알 제거
          botGrid[0][0] = true;  // 하단 입구로 이동
          found = true;
          spawnDelay = 2;        // 다음 모래알이 나오기 전까지 2프레임 지연 (한 알씩 떨어지는 효과)
          break;
        }
      }
      if (found) break;
    }
  }

  // 3. 상단 매트릭스 내부 물리는 불필요하므로 비활성화 (깜빡임의 원인)
}

// 상단 매트릭스가 비었는지 확인
bool isTopEmpty() {
  for (int r = 0; r < 8; r++) {
    for (int c = 0; c < 8; c++) {
      if (topGrid[r][c]) return false;
    }
  }
  return true;
}

void setup() {
  randomSeed(analogRead(0));
  topMatrix.begin();
  botMatrix.begin();
  topMatrix.control(MD_MAX72XX::INTENSITY, 2);
  botMatrix.control(MD_MAX72XX::INTENSITY, 2);
  initMatrices();
}

unsigned long lastUpdate = 0;
const int frameDelay = 200; // 프레임 지연 (속도를 늦추기 위해 200ms로 조절)

void loop() {
  if (millis() - lastUpdate >= frameDelay) {
    updatePhysics();
    displayGrids();
    lastUpdate = millis();

    // 상단이 비워지면 3초 대기 후 초기화
    if (isTopEmpty()) {
      delay(3000);
      initMatrices();
    }
  }
}

 

 

반응형

캐어랩 고객 지원

취업, 창업의 막막함, 외주 관리, 제품 부재!

당신의 고민은 무엇입니까? 현실과 동떨어진 교육, 실패만 반복하는 외주 계약, 아이디어는 있지만 구현할 기술이 없는 막막함.

우리는 알고 있습니다. 문제의 원인은 '명확한 학습, 실전 경험과 신뢰할 수 있는 기술력의 부재'에서 시작됩니다.

이제 고민을 멈추고, 캐어랩을 만나세요!

코딩(펌웨어), 전자부품과 디지털 회로설계, PCB 설계 제작, 고객(시장/수출) 발굴과 마케팅 전략으로 당신을 지원합니다.

제품 설계의 고수는 성공이 만든 게 아니라 실패가 만듭니다. 아이디어를 양산 가능한 제품으로!

귀사의 제품을 만드세요. 교육과 개발 실적으로 신뢰할 수 있는 파트너를 확보하세요.

지난 30년 여정, 캐어랩이 얻은 모든 것을 함께 나누고 싶습니다.

카카오 채널 추가하기

카톡 채팅방에서 무엇이든 물어보세요

당신의 성공을 위해 캐어랩과 함께 하세요.

캐어랩 온라인 채널 바로가기

캐어랩