Table of Contents

Lampa Interactivă

  • Autor: Neculau Sanda-Elena
  • Grupa: 334 CB

Introducere

Lampă interactivă destinată relaxării, care combină controlul tactil, jocuri de lumini RGB și sunete ambientale pentru a crea o atmosferă plăcută. Utilizatorul poate interacționa cu lampa printr-un senzor capacitiv de atingere, selectând între diverse moduri de iluminare și sunet. Informațiile despre modurile active si a volumului sunt afișat printr-un dispaly. Lampa are si moduri care reacționeză la lumina ambientală schimbându-și intensitatea de luminare și aprizându-se atunci când e intuneric în cameră.

Descriere generală

Hardware Design

Placuta este MEGA 2560, eroare de scriere

Bill of materials
Nume componenta Cantitate Link
Arduino mega2560 1 KIT ARDUINO
Senzor touch TTP223B 1 senzor
led-uri RGB 2 led-uri RGB
LCD+I2C 1 LCD
DFPlayer TF-16P 1 DFPlayer
difuzor 8 ohmi, 0,2W 1 -
rezistoare 220 8 kit arduino
rezistor 10 1 kit arduino
rezistor 1 1 kit arduino
fotorezistor 1 kit arduino
card-microSD 1 card
baterie 9V 1 -
conector baterie 1 kit arduino
Pini folositi
Componentă Pin Arduino Mega Motiv
Senzor Touch TTP223B pin 2 Este un pin care permite întrerupere externă (`attachInterrupt`)
LED RGB 1 pin 3 (PWM) – Albastru, pin 5 (PWM) – Verde, pin 6 (PWM) – Roșu PWM pentru controlul intensității culorilor LED-ului 1
LED RGB 2 pin 9 (PWM) – Roșu, pin 10 (PWM) – Verde, pin 11 (PWM) – Albastru PWM pentru LED 2. Pe Mega, aceste pinii suporta analogWrite()
LCD 1602 I2C SDA: pin 20, SCL: pin 21 Pe Arduino Mega, I2C-ul este pe pinii 20 (SDA) si 21 (SCL)
DFPlayer Mini RX: pin 18, TX: pin 19 UART hardware serial (Serial2).
Difuzor Conectat la SPK\_1 și SPK\_2 pe DFPlayer Nu se leagă direct la Arduino, este controlat de DFPlayer
Fotorezistor + rezistor de 10k A0 (pin analogic) Citire lumina ambientală din camera prin analogRead()
Biblioteci
Componente conectate

Software Design

Mediu de dezvoltare
Librări
Structura software
 void manualSerialInit(long baud) {
  // Setare registri pentru UART0 (Serial)
  // calculare viteza de comunicare, F_CPU(viteza procesorului)
  uint16_t ubrr = F_CPU/16/baud-1;
  // impartim valoare pe 2 registri primi 8 biti si restul
  UBRR0H = (unsigned char)(ubrr>>8);
  UBRR0L = (unsigned char)ubrr;
  // Activeaza receptorul (RXEN0) si transmisorul (TXEN0) pentru UART0
  UCSR0B = (1<<RXEN0)|(1<<TXEN0);
  // seteaza marimea datelor transmise la 8 biti 
  UCSR0C = (1<<UCSZ01)|(1<<UCSZ00);
} 
void manualSerialWrite(unsigned char data) {
  // Asteaptam ca buffer-ul UDRE0 de transmisie sa se goleasca
  // verifica daca bitul UDRE0 e activ
  while (!(UCSR0A & (1<<UDRE0)));
  // Scrie un caracter in registrul de date pentru al transmite
  UDR0 = data;
}
// trimite caracter cu caracter pana ajunge la final
void manualSerialPrint(const char* str) {
  while (*str) {
    manualSerialWrite(*str++);
  }
}
 
// transforma numar intreg in caracter ascii si il transmite caracter cu caracter
void manualSerialPrintNumber(int num) {
  if (num == 0) {
    manualSerialWrite('0');
    return;
  }
  
  char buffer[10];
  int i = 0;
  bool negative = false;
  
  if (num < 0) {
    negative = true;
    num = -num;
  }
  ...
}
void manualSerial1Init(long baud) {
  // Setare registri pentru UART1 (Serial1)
  // calculare viteza de comunicare, F_CPU(viteza procesorului)
  uint16_t ubrr = F_CPU/16/baud-1;
  // impartim pe 2 registri valoarea
  UBRR1H = (unsigned char)(ubrr>>8);
  UBRR1L = (unsigned char)ubrr;
  // Activeaza receptorul (RXEN1) si transmisorul (TXEN1) pentru UART0
  UCSR1B = (1<<RXEN1)|(1<<TXEN1);
  // setez marimea datelor la 8 biti
  UCSR1C = (1<<UCSZ11)|(1<<UCSZ10);
}
void manualSerial1Write(unsigned char data){
...
}
unsigned char manualSerial1Read() {
  // Asteapta sa se primeasca date pe uart1 apoi il citeste, RXC1 = activ => date disponibile
  while (!(UCSR1A & (1<<RXC1)));
  return UDR1;
}
bool manualSerial1Available() {
  // Verifica daca exista date primite in buffer-ul UART1
  return (UCSR1A & (1<<RXC1));
}
  1. Configurare pini: Setează LED-urile ca OUTPUT
  2. Întrerupere: attachInterrupt() pentru detectarea atingerii
  3. Inițializare comunicații: Serial pentru debug, Serial1 pentru DFPlayer
  4. Configurare LCD: Pornește backlight-ul și afișează interfața
  5. Configurare DFPlayer: Setează volumul și începe redarea
void setup() {
  // setare pini rgb pentru iesire
  int pins[] = {led1R, led1G, led1B, led2R, led2G, led2B};
  for (int i = 0; i < 6; i++) pinMode(pins[i], OUTPUT);

  // pinul touch(2) ca input
  pinMode(touchPin, INPUT);
  // Seteaza o intrerupere hardware pe pinul conectat la senzorul de atingere (touchPin), 
  // care va executa automat functia schimbareMod() atunci cand semnalul de pe pin trece
  // de la LOW la HIGH (adica o atingere pe senzor).
  attachInterrupt(digitalPinToInterrupt(touchPin), schimbareMod, RISING);

  // initializare comunicatii seriale manual
  manualSerialInit(9600);
  manualSerial1.begin(9600); //dfplayer manual
  
  // pornire lcd
  lcd.begin();
  lcd.backlight();

  if (!player.begin(manualSerial1)) {
    manualSerialPrintln("DFPlayer nu a fost gasit!");
    while (true);
  }

  // setam pe dfplayer volumul si melodia
  player.volume(volum);
  player.play(mode);

  // afisam pe lcd
  lcd.setCursor(0, 0); lcd.print("Mod: ");
  lcd.setCursor(0, 1); lcd.print("Volum: ");
  afiseazaMod();
  afiseazaVolum();
}

loop()

Moduri de luminare

schimbareMod()

setAll()

Cod github

Proiect IP

Rezultate Obţinute

Dupa terminarea constructiei hardware si software, am realizat prototipul la lampa(fara exterior prietenos vizual care sa arate ca o lampa). La pornirea ei se va porni automat modul 1 de luminat care este afisat si pe lcd impreuna cu volumul difuzorului. La primul mod nu o sa porneasca luminile automat daca in camera lumina este puternica, daca in camera este intuneric atunci va incepe jocul de lumini, melodia este redata in fundal indiferent de lumina de afara. Celelalte moduri nu depind de lumina ambientala, fiecare mod are o melodie proprie si joc de lumini propriu. Pentru a schimba modul trebuie facut o singura apasare pe senzor, pentru a marii volumul 2 apasari pe senzor, iar pentru a scade volumul 3 apasari.

Concluzii

A fost un proiect interesant de implementat si mi-a facut placere sa lucrez la el. Pe parcursul lui am intampinat si mici probleme cum ar fi lipirea pinilor de la adaptorul I2C la lcd (nu mi-a iesit si am cumparat altul gata lipit :-D), dar si probleme de afisare a scrisului pe lcd (solutia a fost o alta biblioteca decat cele gasite pe arduino IDE, se află in arhiva cu proiectul), probleme cu citirea dfplayer-ului, dupa ore de stat si de analizat problema, mi-am pus intrebarea daca poate sa fie de la pinul care a venit lipit prost. Asa ca am mai cumparat alt dfplayer si inca un card microsd cu o clasa mai inferioara (de preferat clasele 1-4 si maxim 32gb) si pana la urma a functionat, iar in cod mi-a placut sa ma joc cu modurile de luminat.

Download

Arhiva contine: poze cu schema, biblioteca de la lcd+i2c si codul.

lampa_interactiva_neculau_sanda.zip

Bibliografie/Resurse

Pentru a afla registri pentru scrierea sriala m-am documentat din urmatoarele resurse documentatie placuta artmega 2560, pagina 400(tabel cu registri descrisi)

Pentru a implementa functiile de scriere citire si transmitere pe serial datasheet, paginile 149, 150, 151, 152 Export to PDF