Advertisement
AnatolySharapov

IRRemoteControlsDFPlayerMiniMp3.ino

Sep 13th, 2021
289
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 16.72 KB | None | 0 0
  1. /*
  2. File name     : IRRemoteControlsDFPlayerMiniMp3.ino
  3. Description   : this sketch process ir remote decoded  info and
  4.                 controls mp3 player df3mini board  
  5. Author        : Anatoly A. Sharapov
  6. Email         : a.a.sharapov@gmail.com
  7. Phone         : +7 903 231-11-26
  8. Location      : 124575 Moscow, Zelenograd, 1206 - 131
  9.  
  10. Board         : Arduino Nano
  11. Processor     : ATmega328P (Old Bootloader)
  12.  
  13. Controls      : DFPlayer Mini
  14.  
  15. Library1      : SoftwareSerial
  16. Library2      : DFMiniMp3-master
  17. Library3      : IRRemote
  18. Library4      : EEPROM
  19.                
  20. URL1          : https://doc.arduino.ua/ru/prog/SoftwareSerial
  21. URL2          : https://lesson.iarduino.ru/page/urok-17-podklyuchenie-mini-mp3-pleera-k-arduino/
  22. URL3          : https://github.com/Makuna/DFMiniMp3/blob/master/src/DFMiniMp3.h
  23.  
  24. Last revision : 12.09.2021
  25. */
  26.  
  27. #include <SoftwareSerial.h>
  28. #include <DFMiniMp3.h>
  29. #include <IRremote.h>
  30. #include <EEPROM.h>
  31.  
  32. const uint8_t RX = 5;
  33. const uint8_t TX = 4;
  34.  
  35. SoftwareSerial DFPlayerMiniSerial(RX, TX);
  36.  
  37. // SoftwareSerial(uint8_t rxPin, uint8_t txPin, bool inverse_logic = false);
  38. /*
  39.  Схема:
  40.  * RX - цифровой вывод (необходимо соединить с выводом TX другого устройства)
  41.  * TX - цифровой вывод (необходимо соединить с выводом RX другого устройства)
  42. */
  43.  
  44. // forward declare the notify class, just the name
  45. class Mp3Notify;
  46.  
  47. // define a handy type using serial and our notify class
  48. typedef DFMiniMp3 <SoftwareSerial, Mp3Notify> DFMiniMp3_t;
  49.  
  50. // Arduino Nano.D5 (RX) - DFPlayer Mini.3 (TX) - orange
  51. // Arduino Nano.D4 (TX) - through 1kOhm - DFPlayer Mini.2 (RX) - yellow
  52. // Arduino Nano.5V  - DFPlayer Mini.1 (VCC) - red
  53. // Arduino Nano.GND - DFPlayer Mini.7 (GND) - brown
  54.  
  55.  
  56. // instance an object
  57. DFMiniMp3_t DFPlayerMiniMp3(DFPlayerMiniSerial);
  58.  
  59. // implement a notification class,
  60. // its member methods will get called
  61. class Mp3Notify
  62. {
  63. public:
  64.   static void PrintlnPlaybackMode(DfMp3_PlaybackMode PlaybackMode)
  65.   {
  66.     switch (PlaybackMode) {
  67.         case DfMp3_PlaybackMode_Repeat :
  68.             Serial.println(F("DfMp3_PlaybackMode_Repeat"));
  69.             break;
  70.         case DfMp3_PlaybackMode_FolderRepeat :
  71.             Serial.println(F("DfMp3_PlaybackMode_FolderRepeat"));
  72.             break;
  73.         case DfMp3_PlaybackMode_SingleRepeat :
  74.             Serial.println(F("DfMp3_PlaybackMode_SingleRepeat"));
  75.             break;
  76.         case DfMp3_PlaybackMode_Random :
  77.             Serial.println(F("DfMp3_PlaybackMode_Random"));
  78.             break;
  79.         default:
  80.             Serial.println(F("Error - Undefined"));
  81.             break;  
  82.     }
  83.   }
  84.   static void PrintlnSourceAction(DfMp3_PlaySources source, const char* action)
  85.   {
  86.     if (source & DfMp3_PlaySources_Sd)
  87.     {
  88.         Serial.print(F("SD Card, "));
  89.     }
  90.     if (source & DfMp3_PlaySources_Usb)
  91.     {
  92.         Serial.print(F("USB Disk, "));
  93.     }
  94.     if (source & DfMp3_PlaySources_Flash)
  95.     {
  96.         Serial.print(F("Flash, "));
  97.     }
  98.     Serial.println(action);
  99.   }
  100.   static void OnError(DFMiniMp3_t& mp3, uint16_t errorCode)
  101.   {
  102.     // see DfMp3_Error for code meaning
  103.     Serial.println();
  104.     Serial.print(F("errorCode = "));
  105.     Serial.print(errorCode);
  106.     Serial.print(F(" stands for "));
  107.     switch (errorCode) {
  108.         case DfMp3_Error_Busy :
  109.             Serial.print(F("DfMp3_Error_Busy"));
  110.             break;
  111.         case DfMp3_Error_Sleeping :
  112.             Serial.print(F("DfMp3_Error_Sleeping"));
  113.             break;
  114.         case DfMp3_Error_SerialWrongStack :
  115.             Serial.print(F("DfMp3_Error_SerialWrongStack"));
  116.             break;
  117.         case DfMp3_Error_CheckSumNotMatch :
  118.             Serial.print(F("DfMp3_Error_CheckSumNotMatch"));
  119.             break;
  120.         case DfMp3_Error_FileIndexOut :
  121.             Serial.print(F("DfMp3_Error_FileIndexOut"));
  122.             break;
  123.         case DfMp3_Error_FileMismatch :
  124.             Serial.print(F("DfMp3_Error_FileMismatch"));
  125.             break;
  126.         case DfMp3_Error_Advertise :
  127.             Serial.print(F("DfMp3_Error_Advertise"));
  128.             break;
  129.         case DfMp3_Error_RxTimeout :
  130.             Serial.print(F("DfMp3_Error_RxTimeout"));
  131.             break;
  132.         case DfMp3_Error_PacketSize :
  133.             Serial.print(F("DfMp3_Error_PacketSize"));
  134.             break;
  135.         case DfMp3_Error_PacketHeader :
  136.             Serial.print(F("DfMp3_Error_PacketHeader"));
  137.             break;  
  138.         case DfMp3_Error_PacketChecksum :
  139.             Serial.print(F("DfMp3_Error_PacketChecksum"));
  140.             break;
  141.  
  142.         case DfMp3_Error_General :
  143.             Serial.print(F("DfMp3_Error_General"));
  144.             break;
  145.         default :
  146.             Serial.print(F("unknown"));
  147.             break;  
  148.     }    
  149.   }
  150.  
  151.   static void OnPlayFinished(DFMiniMp3_t& mp3, DfMp3_PlaySources source, uint16_t track)
  152.   {
  153.     Serial.print(F("Play finished for source = "));
  154.    
  155.     switch (source) {
  156.         case 0x01 :
  157.             Serial.print(F("USB"));
  158.             break;
  159.         case 0x02 :
  160.             Serial.print(F("SD"));
  161.             break;
  162.         case 0x04 :
  163.             Serial.print(F("PC"));
  164.             break;
  165.         case 0x08 :
  166.             Serial.print(F("Flash"));
  167.             break;            
  168.         default :
  169.             Serial.print(F("unknown"));
  170.             break;  
  171.     }
  172.     Serial.print(F(" and track = "));    
  173.     Serial.println(track);  
  174.   }
  175.   static void OnPlaySourceOnline(DFMiniMp3_t& mp3, DfMp3_PlaySources source)
  176.   {
  177.     PrintlnSourceAction(source, "online");
  178.   }
  179.   static void OnPlaySourceInserted(DFMiniMp3_t& mp3, DfMp3_PlaySources source)
  180.   {
  181.     PrintlnSourceAction(source, "inserted");
  182.   }
  183.   static void OnPlaySourceRemoved(DFMiniMp3_t& mp3, DfMp3_PlaySources source)
  184.   {
  185.     PrintlnSourceAction(source, "removed");
  186.   }
  187. };
  188.  
  189. const int SerialBaudRate = 9600;
  190. const int LedPinNum   = 13;
  191. const int LedStateOff = LOW;
  192. const int LedStateOn  = HIGH;
  193.  
  194. int LedPinState = LedStateOff;
  195.  
  196. const bool LedOff = false;
  197. const bool LedOn  = true;
  198. int LedState;
  199.  
  200. uint8_t DFPlayerMiniInitVolume,
  201.         DFPlayerMiniNewVolume;
  202.          
  203. const uint8_t DFPlayerMiniMinVolume = 0,
  204.               DFPlayerMiniMaxVolume = 30,
  205.               DFPlayerMiniSetVolume = DFPlayerMiniMaxVolume;
  206.                
  207. const int DFPLAYER_MINI_MP3_INTER_COMMANDS_DELAY = 100;
  208.     // Между двумя командами необходимо делать задержку 100 миллисекунд,
  209.     // в противном случае некоторые команды могут работать не стабильно.
  210.  
  211. const bool DFPLAYER_MINI_MP3_INTER_COMMANDS_DELAY_IS_ABSENT = false;
  212. const bool DFPLAYER_MINI_MP3_INTER_COMMANDS_DELAY_IS_PRESENT = true;
  213. bool DFPlayerMiniMp3InterCommandsDelayMode;
  214.  
  215. void DFPlayerMiniMp3InterCommandsDelay() {
  216.     if (DFPlayerMiniMp3InterCommandsDelayMode == DFPLAYER_MINI_MP3_INTER_COMMANDS_DELAY_IS_PRESENT) {
  217.         delay(DFPLAYER_MINI_MP3_INTER_COMMANDS_DELAY);
  218.     }
  219. }                                      
  220.          
  221. uint8_t  CurrentFolderNum;
  222. uint16_t CurrentTrackNum;
  223. uint16_t TotalFolderCount;
  224. uint8_t  CurrentVolume;
  225.  
  226. const int VS1838B_PIN = 11;
  227. IRrecv irrecv(VS1838B_PIN);
  228. decode_results results;
  229.  
  230. uint8_t ir_button;
  231.  
  232. const bool DFPLAYER_MINI_MP3_PAUSED = false;
  233. const bool DFPLAYER_MINI_MP3_PLAYING = true;
  234. bool PlayMode;
  235.  
  236. // older devices: sd:/###/###track name
  237. // newer devices: sd:/##/###track name
  238. // folder and track numbers are zero padded
  239.  
  240. void LoopFolder() {
  241.    
  242.     if (CurrentFolderNum > TotalFolderCount) {
  243.        CurrentFolderNum = TotalFolderCount;
  244.     }
  245.    
  246.     DFPlayerMiniMp3.loopFolder(CurrentFolderNum);  
  247.     DFPlayerMiniMp3InterCommandsDelay();
  248.     Serial.println(F("In LoopFolder ->"));
  249.     Serial.print(F("CurrentFolderNum = "));
  250.     Serial.print(CurrentFolderNum);  
  251.     Serial.print(F(", CurrentTrackNum = "));
  252.     Serial.println(CurrentTrackNum);      
  253. }
  254.  
  255. DFMiniMp3::DfMp3_PlaybackMode PlaybackMode;
  256.  
  257. void LoopPlayBackMode(DFMiniMp3_t::DfMp3_PlaybackMode PlaybackMode) {
  258.     Serial.println(F("In LoopPlayBackMode  ->  PlayBackMode = "));
  259.     DfMp3_PlaybackMode_Print(PlaybackMode);
  260.     DFPlayerMiniMp3.loopGlobalTrack(PlaybackMode);
  261. }  
  262.  
  263. void PlayTrack() {
  264.     DFPlayerMiniMp3.playFolderTrack16(CurrentFolderNum, CurrentTrackNum);
  265.     DFPlayerMiniMp3InterCommandsDelay();
  266.     Serial.println(F("In PlayTrack -> "));
  267.     Serial.print(F("CurrentFolderNum = "));
  268.     Serial.print(CurrentFolderNum);
  269.     Serial.print(F(", CurrentTrackNum = "));
  270.     Serial.println(CurrentTrackNum);        
  271. }      
  272.  
  273. void PlayPrevTrack() {
  274.     Serial.println(F("In PlayPrevTrack -> "));
  275.     CurrentTrackNum = DFPlayerMiniMp3.getCurrentTrack();    
  276.     Serial.print(F("CurrentTrackNum = "));
  277.     Serial.println(CurrentTrackNum);    
  278.     if (CurrentTrackNum > 0) {
  279.        CurrentTrackNum--;
  280.     } else {
  281.         CurrentTrackNum = DFPlayerMiniMp3.getFolderTrackCount(CurrentFolderNum);
  282.     }
  283.     PlayTrack();    
  284. }  
  285.  
  286. void PlayNextTrack() {
  287.     Serial.println(F("In PlayNextTrack -> "));
  288.     CurrentTrackNum = DFPlayerMiniMp3.getCurrentTrack();    
  289.     Serial.print(F("CurrentTrackNum = "));
  290.     Serial.println(CurrentTrackNum);
  291.     if (CurrentTrackNum == DFPlayerMiniMp3.getFolderTrackCount(CurrentFolderNum)) {
  292.         CurrentTrackNum = 0;
  293.     } else {
  294.        CurrentTrackNum++;
  295.     }
  296.     PlayTrack();    
  297. }
  298.  
  299. void SetVolume() {
  300.     DFPlayerMiniMp3.setVolume(CurrentVolume);
  301.     DFPlayerMiniMp3InterCommandsDelay();
  302.     Serial.println(F("In SetVolume ->"));
  303.     Serial.print(F("CurrentVolume = "));
  304.     Serial.println(CurrentVolume);    
  305. }    
  306.  
  307. void IncreaseVolume() {
  308.     CurrentVolume = DFPlayerMiniMp3.getVolume();
  309.     if (CurrentVolume < DFPlayerMiniMaxVolume) {
  310.        CurrentVolume++;
  311.     }
  312.     SetVolume();    
  313. }
  314.  
  315. void DecreaseVolume() {
  316.     CurrentVolume = DFPlayerMiniMp3.getVolume();
  317.     if (CurrentVolume > 0) {
  318.        CurrentVolume--;
  319.     }
  320.     SetVolume();    
  321. }
  322.  
  323. const int EEPROM_ADDRESS_4_CURRENT_FOLDER_NUM       = 0;
  324. const int EEPROM_ADDRESS_4_CURRENT_TRACK_NUM_HIGH   = 1;
  325. const int EEPROM_ADDRESS_4_CURRENT_TRACK_NUM_LOW    = 2;
  326. const int EEPROM_ADDRESS_4_CURRENT_VOLUME           = 3;
  327.  
  328. uint8_t  CurrentTrackNumHigh,
  329.          CurrentTrackNumLow;
  330.  
  331. void SaveParameters2EEPROM() {
  332.     CurrentTrackNumHigh = CurrentTrackNum >> 8;
  333.     CurrentTrackNumLow = CurrentTrackNum & 0xff;
  334.     EEPROM.write(EEPROM_ADDRESS_4_CURRENT_FOLDER_NUM, CurrentFolderNum);
  335.     EEPROM.write(EEPROM_ADDRESS_4_CURRENT_TRACK_NUM_HIGH, CurrentTrackNumHigh);
  336.     EEPROM.write(EEPROM_ADDRESS_4_CURRENT_TRACK_NUM_LOW, CurrentTrackNumLow);
  337.     EEPROM.write(EEPROM_ADDRESS_4_CURRENT_VOLUME, CurrentVolume);
  338. }
  339.  
  340. const uint8_t ParamReadFromEEPROMIsNeverBeenWritten = 255;
  341.  
  342. uint8_t SetInitialParamReadFromEEPROM(uint8_t ParamReadFromEEPROM) {
  343.     if (ParamReadFromEEPROM == ParamReadFromEEPROMIsNeverBeenWritten) {
  344.         ParamReadFromEEPROM = 0;
  345.     }
  346.     return ParamReadFromEEPROM;
  347. }
  348.  
  349. void RestoreParametersFromEEPROM() {
  350.    
  351.     Serial.println("In RestoreParametersFromEEPROM ->");
  352.    
  353.     CurrentFolderNum = SetInitialParamReadFromEEPROM(EEPROM.read(EEPROM_ADDRESS_4_CURRENT_FOLDER_NUM));
  354.     Serial.print(F("CurrentFolderNum = "));
  355.     Serial.print(CurrentFolderNum);
  356.    
  357.     CurrentVolume = SetInitialParamReadFromEEPROM(EEPROM.read(EEPROM_ADDRESS_4_CURRENT_VOLUME));
  358.     Serial.print(F(", CurrentVolume = "));
  359.     Serial.print(CurrentVolume);
  360.    
  361.     CurrentTrackNumHigh = SetInitialParamReadFromEEPROM(EEPROM.read(EEPROM_ADDRESS_4_CURRENT_TRACK_NUM_HIGH));
  362.     CurrentTrackNumLow  = SetInitialParamReadFromEEPROM(EEPROM.read(EEPROM_ADDRESS_4_CURRENT_TRACK_NUM_LOW));
  363.     CurrentTrackNum     = CurrentTrackNumHigh << 8 & CurrentTrackNumLow;
  364.     Serial.print(F(", CurrentTrackNum = "));
  365.     Serial.println(CurrentTrackNum);  
  366.    
  367. }
  368.  
  369. void setup() {
  370.    
  371.     PlayMode = DFPLAYER_MINI_MP3_PAUSED;
  372.     DFPlayerMiniMp3InterCommandsDelayMode = DFPLAYER_MINI_MP3_INTER_COMMANDS_DELAY_IS_ABSENT;    
  373.    
  374.     Serial.begin(SerialBaudRate);
  375.     while (!Serial);  // wait for serial port to connect. Needed for native USB
  376.     Serial.println(F("PS2KeyboardControlsDFPlayerMiniMp3 is started"));
  377.  
  378.     RestoreParametersFromEEPROM();    
  379.  
  380.     DFPlayerMiniMp3.begin();
  381.     DFPlayerMiniMp3InterCommandsDelay();
  382.    
  383.     PlaybackMode = DFPlayerMiniMp3.DfMp3_PlaybackMode_FolderRepeat;
  384.     DfMp3_PlaybackMode_Print(PlaybackMode);
  385.    
  386.     TotalFolderCount = DFPlayerMiniMp3.getTotalFolderCount();
  387.     Serial.print(F("TotalFolderCount = "));
  388.     Serial.println(TotalFolderCount);  
  389.    
  390.     pinMode(LedPinNum, OUTPUT);    
  391.     LedPinState = LedStateOff;
  392.     digitalWrite(LedPinNum, LedPinState);
  393.    
  394.     irrecv.enableIRIn();      // Start the receiver
  395.  
  396.     ir_button = 100;    
  397.      
  398. }
  399.  
  400. void loop() {
  401.    
  402.   if (irrecv.decode()) {
  403.  
  404.     switch (irrecv.decodedIRData.decodedRawData) {
  405.         case 0xBA45FF00 :
  406.             ir_button = 1;
  407.             CurrentFolderNum = 1;
  408.             CurrentTrackNum  = 0;
  409.             Serial.println(F("*Pressed 1"));
  410.             LoopFolder();
  411.             break;
  412.         case 0xB946FF00 :
  413.             ir_button = 2;
  414.             CurrentFolderNum = 2;
  415.             CurrentTrackNum  = 0;            
  416.             Serial.println(F("Pressed 2"));
  417.             LoopFolder();
  418.             break;            
  419.         case 0xB847FF00 :
  420.             ir_button = 3;
  421.             CurrentFolderNum = 3;
  422.             CurrentTrackNum  = 0;            
  423.             Serial.println(F("Pressed 3"));
  424.             LoopFolder();
  425.             break;            
  426.         case 0xBB44FF00 :
  427.             ir_button = 4;
  428.             CurrentFolderNum = 4;
  429.             CurrentTrackNum  = 0;            
  430.             Serial.println(F("Pressed 4"));
  431.             LoopFolder();
  432.             break;            
  433.         case 0xBF40FF00 :
  434.             ir_button = 5;
  435.             CurrentFolderNum = 5;
  436.             CurrentTrackNum  = 0;            
  437.             Serial.println(F("Pressed 5"));
  438.             LoopFolder();
  439.             break;            
  440.         case 0xBC43FF00 :
  441.             ir_button = 6;
  442.             CurrentFolderNum = 6;
  443.             CurrentTrackNum  = 0;            
  444.             Serial.println(F("Pressed 6"));
  445.             LoopFolder();
  446.             break;            
  447.         case 0xF807FF00 :
  448.             ir_button = 7;
  449.             CurrentFolderNum = 7;
  450.             CurrentTrackNum  = 0;            
  451.             Serial.println(F("Pressed 7"));
  452.             LoopFolder();
  453.             break;            
  454.         case 0xEA15FF00 :
  455.             ir_button = 8;
  456.             CurrentFolderNum = 8;
  457.             CurrentTrackNum  = 0;            
  458.             Serial.println(F("Pressed 8"));
  459.             LoopFolder();
  460.             break;            
  461.         case 0xF609FF00 :
  462.             ir_button = 9;
  463.             CurrentFolderNum = 9;
  464.             CurrentTrackNum  = 0;            
  465.             Serial.println(F("Pressed 9"));
  466.             LoopFolder();
  467.             break;            
  468.         case 0xE619FF00 :
  469.             ir_button = 0;
  470.             CurrentFolderNum = 0;
  471.             CurrentTrackNum  = 0;            
  472.             Serial.println(F("Pressed 0"));
  473.             LoopFolder();
  474.             break;            
  475.         case 0xE916FF00 :
  476.             ir_button = 10;        
  477.             Serial.println(F("Pressed *"));
  478.             SaveParameters2EEPROM();
  479.             break;            
  480.         case 0xF20DFF00 :
  481.             ir_button = 11;        
  482.             Serial.println(F("Pressed #"));
  483.             DFPlayerMiniMp3.playRandomTrackFromAll();
  484.             DFPlayerMiniMp3InterCommandsDelay();
  485.             break;            
  486.         case 0xE718FF00 :
  487.             ir_button = 12;        
  488.             Serial.println(F("Pressed Arrow Up"));
  489.             IncreaseVolume();
  490.             break;            
  491.         case 0xAD52FF00 :
  492.             ir_button = 13;        
  493.             Serial.println(F("Pressed Arrow Down"));
  494.             DecreaseVolume();
  495.             break;    
  496.         case 0xF708FF00 :
  497.             ir_button = 14;        
  498.             Serial.println(F("Pressed Arrow Left"));
  499.             PlayPrevTrack();
  500.             break;            
  501.         case 0xA55AFF00 :
  502.             ir_button = 15;        
  503.             Serial.println(F("Pressed Arrow Right"));
  504.             PlayNextTrack();
  505.             break;            
  506.         case 0xE31CFF00 :
  507.             ir_button = 16;        
  508.             Serial.println("Pressed Ok");
  509.             if (PlayMode == DFPLAYER_MINI_MP3_PAUSED) {
  510.                 DFPlayerMiniMp3.start();
  511.                 DFPlayerMiniMp3InterCommandsDelay();              
  512.                 PlayMode = DFPLAYER_MINI_MP3_PLAYING;
  513.             }
  514.             else {
  515.                 DFPlayerMiniMp3.pause();
  516.                 DFPlayerMiniMp3InterCommandsDelay();          
  517.                 PlayMode = DFPLAYER_MINI_MP3_PAUSED;                
  518.             }                
  519.             break;            
  520.         default: // иначе просто печатать все обычные символы
  521.             // Serial.println(irrecv.decodedIRData.decodedRawData, HEX);
  522.             break;            
  523.     }
  524.    
  525.     irrecv.resume(); // Receive the next value
  526.    
  527.   }  
  528.  
  529. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement