Я использую: w5500, arduino nano, DFPlayer Mini
Библиотеки:
ArduinoJson.h
SPI.h
Ethernet2.h
DFRobotDFPlayerMini.h
SoftwareSerial.h
В документации к библиотеки DFRobotDFPlayerMini приводится код для обработки ошибок:
void printDetail(uint8_t type, int value){
switch (type) {
case TimeOut:
Serial.println(F("Время вышло"));
break;
case WrongStack:
Serial.println(F("Стек неправильный!"));
errorMp3();
break;
case DFPlayerCardInserted:
Serial.println(F("Карта вставлена!"));
if(read == 1){
asm volatile("jmp 0x00");
read =0;
}
break;
case DFPlayerCardRemoved:
Serial.println(F("Карта извлечена!"));
read = 1;
break;
case DFPlayerCardOnline:
Serial.println(F("Карта онлайн!"));
if(read == 1){
asm volatile("jmp 0x00");
read =0;
}
break;
case DFPlayerUSBInserted:
Serial.println("USB вставлен!");
break;
case DFPlayerUSBRemoved:
Serial.println("USB удален!");
break;
case DFPlayerPlayFinished:
Serial.println(F("Воспроизведение завершено!"));
break;
case DFPlayerError:
Serial.print(F("Ошибка DFPlayer:"));
switch (value) {
case Busy:
Serial.println(F("Карта не найдена "));errorMp3();
break;
case Sleeping:
Serial.println(F("Спящий "));errorMp3();
break;
case SerialWrongStack:
Serial.println(F("Получите неправильный стек"));errorMp3();
break;
case CheckSumNotMatch:
Serial.println(F("Контрольная сумма не совпадает "));errorMp3();
break;
case FileIndexOut:
Serial.println(F("Индекс файла вышел за пределы "));errorMp3();
break;
case FileMismatch:
Serial.println(F("Невозможно найти файл "));errorMp3();
break;
case Advertise:
Serial.println(F("В рекламе "));errorMp3();
break;
default:
break;
}
break;
default:
break;
}
}
printDetail(myDFPlayer.readType(), myDFPlayer.read());
myDFPlayer.readType() и myDFPlayer.read() содержат в себе коды, например: myDFPlayer.readType()==3 и myDFPlayer.read()==0 означает что карта памяти не вставлена. Так и не понял, почему это имеено так работает, если внутри этой функции printDetail() обрабатываются не коды, а названия, например: DFPlayerCardRemoved - карта извлечена.
Теперь я по этим кодам пытаюсь обработать воспроизведение mp3 файла, выглядит это так:
myDFPlayer.playMp3Folder(ID);
if(myDFPlayer.readType()==3 && myDFPlayer.read()==0){
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Карта памяти не вставлена! 0000";
doc["status"] = false;
}else{
Serial.println();
Serial.print(myDFPlayer.readType());Serial.print("|");Serial.print(myDFPlayer.read());
Serial.println();
if(myDFPlayer.readType()==6 && myDFPlayer.read()==6){
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Такого файла нет! 0";
doc["status"] = false;
doc["E1"] = myDFPlayer.readType();
doc["E2"] = myDFPlayer.read();
}else if(myDFPlayer.readType()==5 && myDFPlayer.read()==1){
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Файл воспроизводится! 1";
doc["status"] = true;
doc["E1"] = myDFPlayer.readType();
doc["E2"] = myDFPlayer.read();
}else{
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Произошла не известная ошибка!";
doc["status"] = false;
doc["E1"] = myDFPlayer.readType();
doc["E2"] = myDFPlayer.read();
}
}
serializeJsonPretty(doc,client); //Отдать инфу клиенту
Теперь, когда я включаю ардуино, и после инциализации пытаюсь открыть ссылку мойip/?dir=mp3&name=1, где name =1 это тот файл который я запускаю. В первый раз, после запуска arduino, я получаю код “4|1” что под моим подсчетам является “карта онлайн”. И не важно есть файл или нет, я всегда получаю “4|1”, если такой файл есть, плеер его воспроизводит. Повторно когда я открываю эту ссылку, я получаю либо “6|6” о чем мне говорит что файла нет, либо 5.1 что говорит о том, что файл запустился.
Теперь вопрос, почему при старте я получаю код “4|1”? и по итогу не правильную инфу о файле…
теперь я обнаружил другой косяк:
когда открываю сайт и проверяю на сайте работу get запросов, которые имеют точно такую же ссылку, только отправляются ajax запросом, у меня от куда то появляется код “5|2”… и причем если у меня файла нет, я сначала получу код “5|2” а при повторном нажатии код “6|6”
Весь код на мой скетч:
#include <ArduinoJson.h>
#include <SPI.h>
#include <Ethernet2.h>
#include "DFRobotDFPlayerMini.h"
#include <SoftwareSerial.h>
DFRobotDFPlayerMini myDFPlayer;
int type = 0;
int read = 0;
SoftwareSerial mySoftwareSerial(8, 9);
int launchMp3 = 1; // звук при старте
int ErMp3 = 1; // звук при ошибке
int start = 1;
int countMp3 = 0;
int total_files_cnt = 0;
int files_in_folder = 0;
byte mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED };
IPAddress ip(192, 168, 1, 177);
EthernetServer server(80);
int startArduino = 0;
void setup() {
startArduino = 1;
Serial.begin(9600);
Ethernet.begin(mac, ip);
server.begin();
Serial.print("IP: ");
Serial.println(Ethernet.localIP());
mySoftwareSerial.begin(9600);
Serial.begin(9600);
Serial.println();
Serial.println("Инициализация...");
if (!myDFPlayer.begin(mySoftwareSerial)) {
read = 1;
Serial.println("Не удается начать:");
Serial.println("1.Пожалуйста, еще раз проверьте подключение!");
Serial.println("2.Пожалуйста, вставьте SD-карту!");
//delay(1000);
} else {
//Получаю информацию о количестве файлов и настраиваю плеер
total_files_cnt = myDFPlayer.readFileCounts();
delay(300);
files_in_folder = myDFPlayer.readFileCountsInFolder(1);
delay(300);
myDFPlayer.volume(30);
myDFPlayer.EQ(DFPLAYER_EQ_NORMAL);
myDFPlayer.outputDevice(DFPLAYER_DEVICE_SD);
Serial.println(F("Инициализация прошла успешно!"));
delay(100);
countMp3 = total_files_cnt - files_in_folder;
}
}
int types = 0;
String ase = "";
void loop() {
if (startArduino == 1) {
myDFPlayer.playFolder(01, 1);
startArduino = 0;
}
if (myDFPlayer.available()) {
printDetail(myDFPlayer.readType(), myDFPlayer.read());
// Serial.println(ase);//Вывести подробное сообщение от DFPlayer для обработки различных ошибок и состояний. }
}
EthernetClient client = server.available();
if (client) {
boolean ok = true;
String val;
while (client.connected()) {
if (client.available()) {
char c = client.read();
val += c;
if (c == '\n') {
//Сначала я получаю get из строки http://192.168.1.177/?dir=mp3&name=2
/*Тут я получаю GET первого параметра*/
int getSearch = val.indexOf("?");
int getSearchL = val.indexOf("=");
String GET = val.substring(getSearch + 1, getSearchL);
//тут я получаю значение первого параметра
int keySearch = val.indexOf("=");
int keySearchL = val.indexOf("&");
String DIR = val.substring(keySearch + 1, keySearchL);
/*Тут я получаю GET второго параметра*/
int getSearch1 = val.indexOf("&");
int getSearchL1 = val.lastIndexOf("=");
String GET1 = val.substring(getSearch1 + 1, getSearchL1);
//тут я получаю значение второго параметра
int keySearch1 = val.lastIndexOf("=");
int keySearchL1 = val.lastIndexOf(" ");
String key = val.substring(keySearch1 + 1, keySearchL1);
int ID = atoi(key.c_str());
int k = GET1.indexOf("&") + 1; //Если нет второго параметра и я использую первый параметр
val = "";
/*
GET - первый параметр
DIR - и его значение
GET1- второй параметр
ID - и его значение
*/
JsonDocument doc; //Переменная json
if (GET == "dir") {
if (DIR == "mp3") {
//если я пытаюсь запустить файл из папки mp3
if (GET1 == "name") { //Проверяю название параметра
if (ID > 0) { //Если я пытаюсь запустить файл с названием больше чем 0000.mp3
Serial.print("Пытаюсь запустить файл под номером: ");
Serial.println(ID);
//пытаюсь запустить файл
myDFPlayer.playMp3Folder(ID);
if (myDFPlayer.readType() == 3 && myDFPlayer.read() == 0) {
//Если карта памяти не вставлена, то вывжу json инфу об этом клиенту
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Карта памяти не вставлена! 0000";
doc["status"] = false;
} else {
Serial.println();
Serial.print(myDFPlayer.readType());
Serial.print("|");
Serial.print(myDFPlayer.read());
Serial.println();
if (myDFPlayer.readType() == 6 && myDFPlayer.read() == 6) {
//Если файла нет
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Такого файла нет! 0";
doc["status"] = false;
doc["E1"] = myDFPlayer.readType();
doc["E2"] = myDFPlayer.read();
} else if (myDFPlayer.readType() == 5 && myDFPlayer.read() == 1) {
//Если файл есть
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Файл воспроизводится! 1";
doc["status"] = true;
doc["E1"] = myDFPlayer.readType();
doc["E2"] = myDFPlayer.read();
} else {
//Если что то пошло не так
doc["SD"] = "mp3";
doc["MP3"] = ID;
doc["statusText"] = "Произошла не известная ошибка!";
doc["status"] = false;
doc["E1"] = myDFPlayer.readType();
doc["E2"] = myDFPlayer.read();
}
}
serializeJsonPretty(doc, client); //Отдать инфу клиенту
} else {
//если пустой параметр или название файла меньше 1
Serial.println("пустой параметр или название файла меньше 1");
}
} else {
Serial.print("Значение: ");
Serial.print(GET1);
Serial.print(" нет в базе данных");
Serial.println("");
}
} else {
if (k == 0) {
int keySearch0 = DIR.indexOf("");
int keySearchL0 = DIR.lastIndexOf(" ");
String DIRs = DIR.substring(keySearch0, keySearchL0);
if (DIRs == "info") { //Тут в цикле мы выводим какую то инфу, в данном случае информацию о состоянии SD карты
if (myDFPlayer.readType() == 3 && myDFPlayer.read() == 0) {
//Если карта памяти извлечена
doc["SD"] = false;
types = 1;
} else {
if (read == 1) {
doc["SD"] = false;
types = 1;
} else {
doc["SD"] = true;
if (types == 1) {
asm volatile("jmp 0x00");
types = 0;
}
}
}
} else {
doc["error"] = "Мы не можем найти такую директорию";
}
serializeJsonPretty(doc, client); //Отдать инфу клиенту
break;
} else {
doc["error"] = "Мы не можем найти такую директорию";
serializeJsonPretty(doc, client); //Отдать инфу клиенту
}
break;
}
break;
} else {
Serial.println("Открываю сайт");
site(client);
break;
}
}
}
}
delay(1);
client.stop();
}
}
void site(EthernetClient client) {
//Собственно сам сайт
client.println("<!DOCTYPE HTML>");
client.print("<html><head><meta charset='UTF-8'><title>Главная</title>");
client.print(F("<style>.info{display:none;width: 250px;margin: 0 auto;min-height: 100px;position: fixed;background: #d82a2a;left: 50%;margin-left: -125px;box-shadow: 0 0 6px 5px #000;color: #fff;}.title{text-align: center;font-size: 20px;font-weight: 700;}#home1 .button{width: 241px;padding: 5px;margin: 6px 2px;background: #2a51d8;color: #fff;border: none;border-radius: 7px;box-shadow: 0 0 2px 1px #000;cursor: pointer;}.homeInfo p{padding: 0;margin: 0;}#home1,#documentation1,#settings1{ padding: 5px;}.content .activeBlock{display: block;}.content{width: 500px;margin: 0 auto;min-height: 500px;box-shadow: 0 0 6px 1px #000;}.menu{width: 100%;background: #2a51d8;}.menu{width: 100%;background: #2a51d8;}.menu span{padding: 18px 0;display: inline-block;color: #ffffff;width: 162px;text-align: center;}.menu span:hover{background: #00000026;cursor: pointer;}.menu .active{background: #00000026;}i{width: 7px;display: inline-block;}</style></head>"));
client.print(F("<body><div class='info'></div><div class='content'>"));
client.print(F("<div class='menu'><span onclick='menu(this)' id='home' class='active'>Главное</span><i></i><span onclick='menu(this)' id='documentation'>Документация</span><i></i><span onclick='menu(this)' id='settings'>Настройки</span></div>"));
client.print(F("<div id='home1' class='activeBlock'>"));
client.print(F("<div class=homeInfo><p class=title>Информация</p><p id=stmp3>Статус mp3 проигрователя: online</p><p id=sdonline>Активность карты памяти: Работает</p><p id=colMp3>Всего mp3 файлов на sd:"));
client.print(total_files_cnt);
client.print(F("шт.</p><p>MP3 файлов в папке mp3:"));
client.print(countMp3);
client.print(F("шт</p>"));
if (files_in_folder > 0) {
//Если нужно будет обрабатывать 01 папку
//client.print(F("<p>MP3 файлов в папке 01:")); client.print(files_in_folder); client.print(F("шт</p>"));
}
client.print(F("<div><p class='title'>Тест MP3 файлов в папке mp3</p>"));
for (int i = 1; i <= countMp3; i++) {
client.print(F("<button class='button' onclick="
"\"mp3('mp3',"));
client.print(i);
client.print(F(")"
"\">Запустить аудиофайл №"));
client.print(i);
client.print(F("</button>"));
}
client.print(F("</div>"));
client.print(F("<div style='display:none' id='documentation1'>Документы</div>"));
client.print(F("<div style='display:none' id='settings1'>Настройки</div>"));
client.print(F("<script>function menu(data){var id = data.id;document.querySelector('.active').removeAttribute('class');document.querySelector('#'+id).setAttribute("
"\"class"
"\",'active');document.querySelector('.activeBlock').setAttribute('style','display: none;');document.querySelector('.activeBlock').removeAttribute('class');document.querySelector('#'+id+'1').removeAttribute('style');document.querySelector('#'+id+'1').setAttribute("
"\"class"
"\",'activeBlock');}"));
client.print(F("function mp3(d,f){ajax({url:"
"\"/?dir="
"\"+d+"
"\"&name="
"\"+f,success: function(data){console.log(data)}});}"));
//client.print(F("window.onload = function(){};"));
client.print(F("var asse=0; setInterval(function (){ajax({url:'/?dir=info',success: function(data){if(data.SD==false){asse=1}if(data.SD==true){if(asse==1){location.reload();asse=0}}}});},1000);"));
client.print(F("function ajax(e) {var url = e.url;document.querySelector('.info').innerHTML='';let xhr = new XMLHttpRequest();xhr.open('GET', url);xhr.send();xhr.responseType = 'json';xhr.onload = function() {let responseObj = xhr.response;e.success(responseObj);}}</script>"));
client.print("</body></html");
}
void errorMp3() { //эту функцию еще не реализовывал
//if(myDFPlayer.readFileCountsInFolder(1)){myDFPlayer.playFolder(01,2);}
}
void printDetail(uint8_t type, int value) { //функция ошибок
switch (type) {
case TimeOut:
//Serial.println(F("Время вышло"));
return "Время вышло";
break;
case WrongStack:
//Serial.println(F("Стек неправильный!"));
return "Стек неправильный!";
errorMp3();
break;
case DFPlayerCardInserted:
//Serial.println(F("Карта вставлена!"));
return "Карта вставлена!";
if (read == 1) {
asm volatile("jmp 0x00");
read = 0;
}
break;
case DFPlayerCardRemoved:
read = 1;
return "Карта извлечена!";
//Serial.println(F("Карта извлечена!"));
break;
case DFPlayerCardOnline:
//Serial.println(F("Карта онлайн!"));
if (read == 1) {
asm volatile("jmp 0x00");
read = 0;
}
return "Карта онлайн!";
break;
case DFPlayerUSBInserted:
Serial.println("USB вставлен!");
break;
case DFPlayerUSBRemoved:
Serial.println("USB удален!");
break;
case DFPlayerPlayFinished:
return "Воспроизведение завершено!";
Serial.println(F("Воспроизведение завершено!"));
break;
case DFPlayerError:
return "Ошибка DFPlayer:";
Serial.print(F("Ошибка DFPlayer:"));
switch (value) {
case Busy:
return "Время вышло";
Serial.println(F("Карта не найдена "));
errorMp3();
break;
case Sleeping:
Serial.println(F("Спящий "));
errorMp3();
return "Время вышло";
break;
case SerialWrongStack:
Serial.println(F("Получите неправильный стек"));
errorMp3();
return "Время вышло";
break;
case CheckSumNotMatch:
Serial.println(F("Контрольная сумма не совпадает "));
errorMp3();
return "Время вышло";
break;
case FileIndexOut:
Serial.println(F("Индекс файла вышел за пределы "));
errorMp3();
return "Время вышло";
break;
case FileMismatch:
Serial.println(F("Невозможно найти файл "));
errorMp3();
return "Время вышло";
break;
case Advertise:
Serial.println(F("В рекламе "));
errorMp3();
break;
default:
break;
}
break;
default:
break;
}
}