Código de Pesquisa

Projeto de Matriz LED RGB ESP32-S3 4 - Ponto Inclinado

Projeto de Matriz LED RGB ESP32-S3 4 - Ponto Inclinado

Projeto 4 - Tilt Dot (Mova o Ponto inclinando a Matriz LED RGB ESP32-S3)

O Projeto 4 apresenta o sensor de movimento embutido no módulo de matriz de LEDs RGB ESP32-S3. Em vez de mover o ponto automaticamente (como no Projeto 1) ou rolar texto (Projetos 2 e 3), este projeto permite controlar a posição do ponto simplesmente inclinando a placa. O ponto se move suavemente pela tela RGB 8×8 com base em leituras ao vivo do acelerômetro QMI8658C na parte traseira do módulo.

Todos os seis projetos desta série são demonstrados em um vídeo no YouTube. O mesmo vídeo está incorporado nesta página, para que você possa ver exatamente como o ponto se move em tempo real à medida que a placa se inclina. O código completo para este projeto é carregado automaticamente abaixo do artigo, e os links de compra afiliados para o módulo aparecem na seção de código.

Visão geral do Módulo de Matriz LED RGB ESP32-S3

Este projeto utiliza o módulo de matriz de LED RGB ESP32-S3, que inclui:

  • Microcontrolador ESP32-S3com Wi-Fi e Bluetooth
  • Matriz LED RGB 8×8(64 LEDs endereçáveis individualmente)
  • Acelerômetro QMI8658Cna parte de trás para detecção de inclinação e movimento
  • porta USBpara programação e energia
  • Botão de inicialização / Resetar
  • Pinos GPIO utilizáveispara futura expansão

O sensor QMI8658C lêX,Y, eZvalores de aceleração e orientação, permitindo que o ponto se mova para cima/baixo/esquerda/direita com base em como a placa está inclinada.:contentReference[oaicite:0]{index=0}

Projetos Abrangidos no Vídeo (Carimbos de Tempo)

  • 00:00- Introdução
  • 02:01- Instalando placas ESP32
  • 03:32- Instalando bibliotecas
  • 05:32- Projeto 1: Ponto Móvel
  • 11:11- Projeto 2: Rolagem de Texto
  • 12:59- Projeto 3: Texto HTTP
  • 16:41-Projeto 4: Tilt Dot (este projeto)
  • 18:55- Projeto 5: Seta Para Cima
  • 20:02- Projeto 6: Jogo de Alvo

Assistir à demonstração de inclinação no vídeo é altamente recomendável, pois você pode ver como o ponto reage suavemente à orientação da placa.:contentReference[oaicite:1]{index=1}

Instalando Placas ESP32 no Arduino IDE

Se você completou algum projeto anterior, o suporte da placa já está instalado. Caso contrário, siga estas etapas:

  1. AbrirFile > Preferences→ Adicione a URL das placas ESP32.
  2. Ir paraTools > Board > Boards Manager…e instalarESP32.
  3. Selecione sua placa ESP32-S3 emTools > Board.
  4. Selecione a porta COM correta emTools > Port.

Instalando Bibliotecas Necessárias

Este projeto requer as seguintes bibliotecas:

  • Adafruit NeoMatrix
  • Adafruit NeoPixel
  • Adafruit GFX Library
  • QMI8658(sensor de movimento)

Instale-os no Gerenciador de Bibliotecas:

  1. AbertoSketch > Include Library > Manage Libraries….
  2. Pesquisar porAdafruit NeoMatrix→ Instalar.
  3. Permitir instalação automática deAdafruit GFXeAdafruit NeoPixel.
  4. Procurar porQMI8658por seu autor listado → Instalar.:contentReference[oaicite:2]{index=2}

Como funciona o Projeto 4

O sensor QMI8658C fornece continuamente dados de aceleração ao longo dos eixos X, Y e Z. Para este projeto, utilizamos apenas os eixos X e Y para decidir:

  • Quão longe mover o ponto para a esquerda ou para a direita (eixo X)
  • Quão longe mover o ponto para cima ou para baixo (eixo Y)

Os valores do sensor são mapeados em uma faixa de coordenadas de 0 a 7 (para a matriz LED 8x8). A posição do ponto é atualizada várias vezes por segundo, proporcionando um efeito de deslizamento suave à medida que você inclina o módulo.:contentReference[oaicite:3]{index=3}

Projeto 4 - Configurações de Código (Tilt Dot)

Abaixo estão as configurações editáveis pelo usuário encontradas perto do topo do código do projeto. O esboço completo aparece abaixo do artigo automaticamente.

Pino e Tamanho da Matriz


// 8×8 RGB matrix configuration
const int MATRIX_PIN    = 14;   // fixed pin for this board
const int MATRIX_WIDTH  = 8;
const int MATRIX_HEIGHT = 8;

SairMATRIX_PINat14Está conectado de forma permanente à matriz a bordo.

Brilho


// Overall brightness (0–255)
uint8_t matrixBrightness = 40;

Aumente se necessário, mas evite brilho extremo ao visualizar de perto.

Cor do ponto


// Dot color (R, G, B)
uint8_t dotRed   = 0;
uint8_t dotGreen = 200;   // light green (default)
uint8_t dotBlue  = 0;

Altere esses valores para criar qualquer cor. Exemplos:

  • Vermelho:(255, 0, 0)
  • Amarelo:(255, 255, 0)
  • Branco:(255, 255, 255)

Sensibilidade ao Movimento

Para prevenir saltos extremos, os valores do acelerômetro são geralmente limitados ou escalonados. Uma configuração típica se parece com:


// How aggressively tilt affects movement
float sensitivity = 4.0f;   // larger = faster movement across screen

Se o ponto se mover muito devagar → aumente o valor. Se o ponto se mover de forma muito brusca → diminua-o.

Taxa de Atualização (Frequência de Atualização)

Você pode adicionar um pequeno atraso entre as atualizações para suavizar o movimento:


// Delay between position updates (ms)
int refreshDelayMs = 20;   // lower = smoother and faster response

Valores entre 10-30 ms parecem muito responsivos.

Resumo

O Projeto 4 dá vida ao acelerômetro QMI8658C embutido no ESP32-S3 permitindo que você controle a matriz de LEDs com movimento físico. Uma leve inclinação da placa move o ponto na mesma direção, tornando este projeto um excelente trampolim para os projetos mais avançados "Seta para Cima" e "Jogo do Alvo".

O esboço completo do Tilt Dot está carregado abaixo deste artigo (automaticamente). Para melhor compreensão, assista à demonstração do tilt no vídeo, onde você pode ver como o ponto se move suavemente à medida que a placa é girada. Links para comprar o módulo de matriz de LEDs RGB ESP32-S3 estão incluídos na seção de código.

Imagens

ESP32 S3 Matrix
ESP32 S3 Matrix
ESP32 S3 Matrix  pin out
ESP32 S3 Matrix pin out
ESP32-S3_RGB_8x8_matrix-3
ESP32-S3_RGB_8x8_matrix-3
ESP32 S3 Matrix displaying rainbow heart
ESP32 S3 Matrix displaying rainbow heart
ESP32-S3_RGB_8x8_matrix1
ESP32-S3_RGB_8x8_matrix1
ESP32-S3_RGB_8x8_matrix-2
ESP32-S3_RGB_8x8_matrix-2
802-ESP32-S3 RGB LED Matrix Project 4 - Tilt dot
Idioma: C++
/*
 * Projeto 4: Tilt Dot - Matriz de LED RGB ESP32-S3 (Waveshare)
 * 
 * Este esboço lê a inclinação do IMU QMI8658C e move suavemente um ponto na matriz de LED RGB 8×8 com base na orientação da placa.
 * 
 * ▶️ Tutorial em Vídeo:
 * https://youtu.be/JKLuYrRcLMI
 * 
 * 📚⬇️ Página de Recursos e Código:
 * https://robojax.com/RJT829
 * 
 * QMI8658_RGB_2
 */
#include <Arduino.h>
#include <math.h>

#include <Adafruit_GFX.h>
#include <Adafruit_NeoMatrix.h>
#include <Adafruit_NeoPixel.h>

#include <QMI8658.h> // por Lahav Gahali

 // -------- CONFIGURAÇÃO DA MATRIZ LED --------
#define MATRIX_PIN    14
#define MATRIX_WIDTH  8
#define MATRIX_HEIGHT 8

Adafruit_NeoMatrix matrix = Adafruit_NeoMatrix(
  MATRIX_WIDTH, MATRIX_HEIGHT, MATRIX_PIN,
  NEO_MATRIX_TOP + NEO_MATRIX_LEFT +
  NEO_MATRIX_ROWS + NEO_MATRIX_PROGRESSIVE,
  NEO_RGB + NEO_KHZ800
);

 // -------- CONFIGURAÇÃO DO IMU QMI8658 --------
QMI8658 imu;
QMI8658_Data imuData;

 // -------- CONFIGURAÇÕES DO USUÁRIO --------

 // verdadeiro -> ponto no lado oposto: USB↔OUSB, 34↔15
 // falso -> ponto do mesmo lado que CIMA
bool useOppositeMapping = false;

 // Cor do ponto (0-255 cada)
uint8_t dotRed   = 0;
uint8_t dotGreen = 100;
uint8_t dotBlue  = 0;

 // Lados da placa
enum Side {
  SIDE_CENTER = 0,
  SIDE_USB,
  SIDE_OUSB,
  SIDE_15,
  SIDE_34
};

 // Posição do ponto suave (em coordenadas de pixel, mas mantida como float para facilitar)
float dotPosX = 3.0f; // começar no centro
float dotPosY = 3.0f;

 // Fator de suavização: menor = movimento mais lento (0,1 muito lento, 0,5 mais rápido)
const float dotSmooth = 0.25f;


bool isFlat = false;

const char* sideName(Side s) {
  switch (s) {
    case SIDE_CENTER: return "CENTER";
    case SIDE_USB:    return "USB";
    case SIDE_OUSB:   return "OUSB";
    case SIDE_15:     return "15";
    case SIDE_34:     return "34";
    default:          return "?";
  }
}

 // Detectar qual lado está para CIMA usando eixos calibrados:
 // +X = USB, -X = OUSB, +Y = 34, -Y = 15
Side detectSideUp(float ax_g, float ay_g, float az_g) {
 // Detecção de planos
  const float flatThreshXY = 0.15f;
  const float flatThreshZ  = 0.15f;

  if (fabs(ax_g) < flatThreshXY &&
      fabs(ay_g) < flatThreshXY &&
      fabs(az_g - 1.0f) < flatThreshZ) {
    isFlat = true;
    return SIDE_CENTER;
  }
  isFlat = false;

 // Limiares para dizer "este eixo está realmente inclinado"
  const float tiltThreshY = 0.5f;
  const float tiltThreshX = 0.5f;

 // 1) Prefira o eixo Y para 15 / 34 se estiver claramente inclinado
  if (fabs(ay_g) >= tiltThreshY) {
    if (ay_g > 0) {
      return SIDE_15; // +Y = 34 para cima
    } else {
      return SIDE_34; // -Y = 15 para cima
    }
  }

 // 2) Caso contrário, verifique o eixo X para USB / OUSB
  if (fabs(ax_g) >= tiltThreshX) {
    if (ax_g > 0) {
      return SIDE_USB; // +X = USB para cima
    } else {
      return SIDE_OUSB; // -X = OUSB para cima
    }
  }

 // Se nada estiver fortemente inclinado, basta chamá-lo de CENTRO.
  return SIDE_CENTER;
}

 // Mapa do lado UP para onde o ponto deve ir
Side dotSideFromUpSide(Side upSide) {
  switch (upSide) {
    case SIDE_USB:
      return useOppositeMapping ? SIDE_OUSB : SIDE_USB;

    case SIDE_OUSB:
      return useOppositeMapping ? SIDE_USB : SIDE_OUSB;

    case SIDE_34:
      return useOppositeMapping ? SIDE_15 : SIDE_34;

    case SIDE_15:
      return useOppositeMapping ? SIDE_34 : SIDE_15;

    case SIDE_CENTER:
    default:
      return SIDE_CENTER;
  }
}

 // Converter a posição do ponto para coordenadas da matriz
void getDotPixel(Side dotSide, int &px, int &py) {
 // Matriz (0,0) = canto superior esquerdo
 // top center: (3,0) → USB
 // centro inferior: (3,7) → OUSB
 // centro esquerdo: (0,3) → 15
 // centro direito: (7,3) → 34
 // centro: (3,3)

  switch (dotSide) {
    case SIDE_USB:   px = 3; py = 0; break;
    case SIDE_OUSB:  px = 3; py = 7; break;
    case SIDE_15:    px = 0; py = 3; break;
    case SIDE_34:    px = 7; py = 3; break;
    case SIDE_CENTER:
    default:         px = 3; py = 3; break;
  }
}

void setup() {
  Serial.begin(115200);
  delay(500);

  matrix.begin();
  matrix.setBrightness(20);
  matrix.fillScreen(0);
  matrix.show();

 // IMU: SDA=11, SCL=12 para ESP32-S3-Matrix
  if (!imu.begin(11, 12)) {
    Serial.println("Failed to initialize QMI8658!");
    while (1) { delay(1000); }
  }

  imu.setAccelUnit_mg(true);
  imu.setGyroUnit_dps(true);
  imu.setDisplayPrecision(4);

  Serial.print("QMI8658 initialized. useOppositeMapping = ");
  Serial.println(useOppositeMapping ? "TRUE" : "FALSE");
}

void loop() {
  if (!imu.readSensorData(imuData)) {
    return;
  }

  float ax_g = imuData.accelX / 1000.0f;
  float ay_g = imuData.accelY / 1000.0f;
  float az_g = imuData.accelZ / 1000.0f;

  Side upSide  = detectSideUp(ax_g, ay_g, az_g);
  Side dotSide = dotSideFromUpSide(upSide);

  int targetX, targetY;
  getDotPixel(dotSide, targetX, targetY);

 // --- Movimento suave em direção ao alvo ---
  dotPosX += (targetX - dotPosX) * dotSmooth;
  dotPosY += (targetY - dotPosY) * dotSmooth;

 // Converter para coordenadas de pixels inteiros
  int px = (int)round(dotPosX);
  int py = (int)round(dotPosY);

 // Grampe apenas por precaução
  if (px < 0) px = 0;
  if (px > 7) px = 7;
  if (py < 0) py = 0;
  if (py > 7) py = 7;

 // --- Desenhar ponto ---
  matrix.fillScreen(0);
  uint16_t color = matrix.Color(dotRed, dotGreen, dotBlue);
  matrix.drawPixel(px, py, color);
  matrix.show();

 // Depurar
  Serial.print("AX="); Serial.print(ax_g, 3);
  Serial.print(" AY="); Serial.print(ay_g, 3);
  Serial.print(" AZ="); Serial.print(az_g, 3);
  Serial.print(" | UP=");  Serial.print(sideName(upSide));
  Serial.print(" | DOT="); Serial.print(sideName(dotSide));
  Serial.print(" | px=");  Serial.print(px);
  Serial.print(" py=");    Serial.println(py);

  delay(80);
}




Coisas que você pode precisar

Recursos e referências

Arquivos📁

Arquivo Fritzing