UART MP3 Voice Module with 8MB Flash Memory / DFR0534
Dependents: DFR0534_MP3_Test_os5 TYBLE16_MP3_Air
see /users/kenjiArai/notebook/mp3--voice-module-dfr0534/
Revision 0:466200f304c9, committed 2019-12-29
- Comitter:
- kenjiArai
- Date:
- Sun Dec 29 02:55:07 2019 +0000
- Commit message:
- 1st working sample (need to update)
Changed in this revision
diff -r 000000000000 -r 466200f304c9 DRF0534_command.txt --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/DRF0534_command.txt Sun Dec 29 02:55:07 2019 +0000 @@ -0,0 +1,249 @@ +/* + Original information: + https://wiki.dfrobot.com/Voice_Module_SKU__DFR0534 + */ + +Three types + SIMPLE + PARAMETER + ANSWER + +---------- COMMREQ ------------------------------------------------------------- +-------------------------------------------------------------------------------- +<<ANSWER>> +Check Playback Status(0x01) + Command: AA 01 00 AB + Return: AA 01 01 Playback status SM + Explanation: You can check the play status at any time. +-------------------------------------------------------------------------------- +<<SIMPLE>> +Play(0x02) + Command: AA 02 00 AC + Return: None + Explanation: Play the current track from the beginning at any time. +-------------------------------------------------------------------------------- +<<SIMPLE>> +Pause(0x03) + Command: AA 03 00 AD + Return: None +-------------------------------------------------------------------------------- +<<SIMPLE>> +Playstop(0x04) + Command: AA 04 00 AE + Return: None +-------------------------------------------------------------------------------- +<<SIMPLE>> +Prev Audio(0x05) + Command: AA 05 00 AF + Return: None +-------------------------------------------------------------------------------- +<<SIMPLE>> +Next Audio(0x06) + Command: AA 06 00 B0 + Return: None +-------------------------------------------------------------------------------- +<<PARAMETER>> +Specified Audio:(0x07) + Command: AA 07 02 Upper-Byte Lower-Byte SM + Return: None + E.g. AA 07 02 00 08 BB + will specify to play the eighth audio in the current drive, + and the audio number is from 1 to 65535. +-------------------------------------------------------------------------------- +<<PARAMETER>> +Play the audio in specified drive of specified path.(0x08) + Command: AA 08 length drive path SM + Return: None + Explanation: length= drive length + path length=1+ path length +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the current online drive.(0x09) + Command: AA 09 00 B3 + Return: AA 09 01 Drive SM + Explanation: The online drive is differentiated + by bitwise usb:bit (0) sd:bit (1) flash:bit (2) + It can check the current online drive. + It is recommended that you check the current online drive + before switching the drive. +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the current drive(0x0A) to play + Command: AA 0A 00 84 + Return: AA 0A 01 Drive SM +-------------------------------------------------------------------------------- +<<PARAMETER>> +Switch to the specified drive(0x0B) + Command: AA 0B 01 drive SM + Return: None + Explanation: It is drive switching command. If the current drive is online, + you can switch it to the corresponding drive and wait to play. + After switching, the module plays the first audio of this drive. + It is recommended to check whether the drive is online before you switch. +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the total audios(0x0C) + Command: AA 0C 00 B6 + Return: AA 0C 02 Upper-byte Lower-byte SM +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the current audio(0x0D) + Command: AA 0D 00 B7 + Return: AA 0D 02 upper-byte lower-byte SM +-------------------------------------------------------------------------------- +<<SIMPLE>> +The Directory of the previous folder(0x0E) + Command: AA 0E 00 B8 + Return: None + Explanation: The first audio in the folder will be played after switching. +-------------------------------------------------------------------------------- +<<SIMPLE>> +The directory of the next folder(0x0F) + Command: AA 0F 00 B9 + Return: None + Explanation: The first audio in the folder will be played after switching. +-------------------------------------------------------------------------------- +<<SIMPLE>> +End to play(0x10) + Command: AA 10 00 BA + Explanation: This command can end the current operations in advance. + If the command end a cut-in, + it will end in advance and return to the original status. +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the first audio in the folder(0x11) + Command: AA 11 00 BB + Return: AA 11 02 Upper-byte Lower-byte SM + Explanation: It is the sequence number of the first audio. +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the total numbers of audio in all folders(0x12) + Command: AA 12 00 BC + Return: AA 12 02 Upper-byte Lower-byte SM + Explanation: + This number does not contain the number of files in subdirectories. +-------------------------------------------------------------------------------- +<<PARAMETER>> +Volume settings(0x13) + Command: AA 13 01 VOL SM + Return: None + Explanation: AA 13 01 14 D2 Set volume to level 20. +-------------------------------------------------------------------------------- +<<SIMPLE>> +Increase the volume(0x14) + Command: AA 14 00 BE + Return: None +-------------------------------------------------------------------------------- +<<SIMPLE>> +Reduce the volume(0x15) + Command: AA 15 00 BF + Return: None +-------------------------------------------------------------------------------- +<<PARAMETER>> +Cut-in a specific audio(0x16) + Command: AA 16 03 drive Upper-byte Lower-byte SM + Return: None + E.g. AA 16 03 00 00 09 CC Cut-in the 9th audio in the USB flash drive. + Explanation: + Continue to play the original audio when cut-in audio is played. +-------------------------------------------------------------------------------- +<<PARAMETER>> +Cut-in the audio on the specified path(0x17) + Command: AA 17 Length Drive Path SM + Return: None + Explanation: length= drive length + path length=1+ path length +-------------------------------------------------------------------------------- +<<PARAMETER>> +Set the loop mode(0x18) + Command: AA 18 01 loop mode + Return: None + E.g. Set to end single play AA 18 01 03 C6 +-------------------------------------------------------------------------------- +<<PARAMETER>> +Set the number of loop times(0x19) + Command: AA 19 02 Upper-byte Lower-byte SM + Return: None + Explain: This command is only valid when the loop mode is Full Loop, + Single Loop, Catalog Loop. + E.g. AA 19 02 00 06 CB Repeat 6 times. +-------------------------------------------------------------------------------- +<<PARAMETER>> +EQ Setting (0x1A) + Command: AA 1A 01 EQ SM + Return: None + E.g. AA 1A 01 02 C7 Set EQ to ROCK +-------------------------------------------------------------------------------- +<<PARAMETER>> +Combination Play(0x1B) + Command: AA 1B Upper-byte of the audio 1, + Lower-byte of the audio 1...Upper-byte of the audio n, + Lower byte of the audio n. + Return: None + E.g. AA1B04303130328C, + audios with file names of 01 and 02 are grouped together to play + Explanation: The combination of file names is very convenient, + more accurate than combined file numbers, + and is not restricted by the copy order limitation. +-------------------------------------------------------------------------------- +<<SIMPLE>> +End Combination Play(0x1C) + Command: AA 1C 00 C6 + Return: None + Explanation: End combination playback, + and return the play state before the combination. +-------------------------------------------------------------------------------- +<<PARAMETER>> +Set channels(0x1D) + Command: AA 1D 01 channels SM + Return: None +-------------------------------------------------------------------------------- +<<ANSWER>> +Check the short-file name(0x1E) + Command: AA 1E 00 C8 + Return: AA 1E The length of short-file name Short-file name SM +-------------------------------------------------------------------------------- +<<PARAMETER>> +Select audio but do not play(0x1F) + Command: AA 1F 02 Upper-byte Lower-byte SM + Return: None +-------------------------------------------------------------------------------- +<<PARAMETER>> +Control of Repetition(0x20) + Command: AA 20 04 beginning-minute beginning-second + ending-minute ending-second SM + Return: None +-------------------------------------------------------------------------------- +<<SIMPLE>> +End repetition(0x21) + Command: AA 21 00 CB + Return: None +-------------------------------------------------------------------------------- +<<PARAMETER>> +Specify the time to rewind(0x22) + Command: AA 22 02 Upper-byte Lower-byte SM + Return: None + Explanation: The unit is seconds +-------------------------------------------------------------------------------- +<<PARAMETER>> +Specify the time to wind(0x23) + Command: AA 23 02 Upper-byte Lower-byte SM + Return: None + Explanation: The unit is seconds +-------------------------------------------------------------------------------- +<<ANSWER>> +Get the total time of the current audio(0x24) + Command: AA 24 00 CE + Return: AA 24 03 hour minute second SM +-------------------------------------------------------------------------------- +<<ANSWER>> +Start the playback time sending(0x25) + Command: AA 25 00 CF + Return: AA 25 03 hour minute second SM + Explanation: Start to send playing time, + Return automatically when the time is updated. +-------------------------------------------------------------------------------- +<<SIMPLE>> +End to send the playing time(0x26) + Command: AA 26 00 D0 + Return: None + Explanation: End the playback time sending. +-------------------------------------------------------------------------------- \ No newline at end of file
diff -r 000000000000 -r 466200f304c9 drf0534.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/drf0534.cpp Sun Dec 29 02:55:07 2019 +0000 @@ -0,0 +1,333 @@ +/* + * Mbed Library program + * UART MP3 Voice Module with 8MB Flash Memory / DFR0534 + * + * Copyright (c) 2019 Kenji Arai / JH1PJL + * http://www.page.sannet.ne.jp/kenjia/index.html + * https://os.mbed.com/users/kenjiArai/ + * Created: December 28th, 2019 + * Revised: December 29th, 2019 + */ + +/* + Reference information: + http://akizukidenshi.com/catalog/g/gM-13708/ + https://wiki.dfrobot.com/Voice_Module_SKU__DFR0534 + */ + +#include "drf0534.h" + +#if MBED_MAJOR_VERSION == 2 +#define WAIT_MS(x) wait_ms(x) +#elif MBED_MAJOR_VERSION == 5 +#define WAIT_MS(x) ThisThread::sleep_for(x) +#else +#error "Running on Unknown OS" +#endif + +//#define DEBUG + +DFR0534::DFR0534(PinName tx, PinName rx, PinName busy) + :_mp3(tx, rx), _bsy(busy) +{ + _mp3.baud(9600); + _mp3.attach(callback(this,&DFR0534::_rx_handler), Serial::RxIrq); + volume_setting(0); +} + +void DFR0534::play_one(uint16_t track_num) +{ + _wait_busy(); + _sum = 0xaa; + _mp3.putc(_sum); + WAIT_MS(2); + _sum += 0x07; + _mp3.putc(0x07); + WAIT_MS(2); + _sum += 0x02; + _mp3.putc(0x02); + WAIT_MS(2); + uint8_t dt = track_num >> 8; + _sum += dt; + _mp3.putc(dt); + WAIT_MS(2); + dt = (uint8_t)track_num; + _sum += dt; + _mp3.putc(dt); + WAIT_MS(2); + _mp3.putc(_sum); +} + +void DFR0534::volume_setting(uint8_t vol) +{ + _sum = 0xaa; + _mp3.putc(_sum); + WAIT_MS(2); + _sum += 0x13; + _mp3.putc(0x13); + WAIT_MS(2); + _sum += 0x01; + _mp3.putc(0x01); + WAIT_MS(2); + uint8_t dt = vol; + if (dt > VOL_MAX) { + dt = VOL_MAX; + } + _sum += dt; + _mp3.putc(dt); + WAIT_MS(2); + _mp3.putc(_sum); +} + +void DFR0534::volume_increase() +{ + _command(0x14); +} + +void DFR0534::volume_decrease() +{ + _command(0x15); +} + +void DFR0534::command(enum simple_commands cmds) +{ + _command(cmds); +} + +uint16_t DFR0534::total_num_of_audio() +{ + uint16_t dt = 0; + char c; + + _rxbuf.reset(); // clear buffer + _command(0x0c); + WAIT_MS(50); + for (uint32_t i = 0; i < 6; i++) { + while(_rxbuf.empty() == true) {;} + _rxbuf.pop(c); + _buf[i] = c; + } +#if defined(DEBUG) + for (uint32_t i = 0; i < 6; i++) { + printf("0x%02x, ",_buf[i]); + } + printf("\r\n"); +#endif + if (_buf[0] == 0xaa) { + _sum = 0xaa; + _sum += _buf[1]; + _sum += _buf[2]; + dt = _buf[3] << 8; + _sum += _buf[3]; + dt += _buf[4]; + _sum += _buf[4]; + if (_sum == _buf[5]) { + return dt; // success + } + } + return 0; // error +} + +uint16_t DFR0534::current_num_of_audio() +{ + uint16_t dt = 0; + char c; + + _rxbuf.reset(); // clear buffer + _command(0x0d); + WAIT_MS(50); + for (uint32_t i = 0; i < 6; i++) { + while(_rxbuf.empty() == true) {;} + _rxbuf.pop(c); + _buf[i] = c; + } +#if defined(DEBUG) + for (uint32_t i = 0; i < 6; i++) { + printf("0x%02x, ",_buf[i]); + } + printf("\r\n"); +#endif + if (_buf[0] == 0xaa) { + _sum = 0xaa; + _sum += _buf[1]; + _sum += _buf[2]; + dt = _buf[3] << 8; + _sum += _buf[3]; + dt += _buf[4]; + _sum += _buf[4]; + if (_sum == _buf[5]) { + return dt; // success + } + } + return 0; // error +} + +void DFR0534::get_file_name(char *buf) +{ + uint16_t dt = 0; + char c, num; + char *p; + + _rxbuf.reset(); // clear buffer + _command(0x1e); + WAIT_MS(50); + for (uint32_t i = 0; i < 3; i++) { + while(_rxbuf.empty() == true) {;} + _rxbuf.pop(c); + _buf[i] = c; + } +#if defined(DEBUG) + for (uint32_t i = 0; i < 3; i++) { + printf("H: 0x%02x, ",_buf[i]); + } + printf("\r\n"); +#endif + if (_buf[0] == 0xaa) { + _sum = 0xaa; + _sum += _buf[1]; + _sum += _buf[2]; + } else { // error + *buf = 0; + return; + } + num = _buf[2] + 1; +#if defined(DEBUG) + printf("number = %d\r\n", num); +#endif + for (uint32_t i = 0; i < num; i++) { + while(_rxbuf.empty() == true) {;} + _rxbuf.pop(c); + _buf[i] = c; + } +#if defined(DEBUG) + for (uint32_t i = 0; i < num; i++) { + printf("T: 0x%02x, ",_buf[i]); + } +#endif + num -= 1; + for (uint32_t i = 0; i < num; i++) { + _sum += _buf[i]; + } + if (_sum == _buf[num]) { +#if defined(DEBUG) + printf("Sum is okay! sum = %d, buf = %d\r\n", _sum, _buf[num]); +#endif + p = buf; + for (uint32_t i = 0; i < num; i++) { + *p++ = _buf[i]; + } + *p = 0; +#if defined(DEBUG) + printf("%s\r\n", buf); + } else { + printf("Sum is NG! sum = %d, buf = %d\r\n", _sum, _buf[num]); + } +#else + } +#endif +} + +uint32_t DFR0534::get_play_time() +{ + _rxbuf.reset(); // clear buffer + _command(0x24); + return get_time(); +} + +uint32_t DFR0534::get_play_back_time() +{ + _rxbuf.reset(); // clear buffer + _command(0x25); + return get_time(); +} + +uint32_t DFR0534::get_time() +{ + uint16_t dt = 0; + char c, h, m, s; + + WAIT_MS(50); + for (uint32_t i = 0; i < 7; i++) { + while(_rxbuf.empty() == true) {;} + _rxbuf.pop(c); + _buf[i] = c; + } +#if defined(DEBUG) + for (uint32_t i = 0; i < 7; i++) { + printf("0x%02x, ",_buf[i]); + } + printf("\r\n"); +#endif + if (_buf[0] == 0xaa) { + _sum = 0xaa; + _sum += _buf[1]; + _sum += _buf[2]; + h = _buf[3]; + _sum += _buf[3]; + m = _buf[4]; + _sum += _buf[4]; + s = _buf[5]; + _sum += _buf[5]; + if (_sum == _buf[6]) { +#if defined(DEBUG) + printf("Sum is okay! sum = %d, buf = %d\r\n", _sum, _buf[6]); +#endif + // success + return ((uint32_t)h * 3600 + (uint32_t)m * 60 + (uint32_t)s); +#if defined(DEBUG) + } else { + printf("Sum is NG! sum = %d, buf = %d\r\n", _sum, _buf[6]); + } +#else + } +#endif + } + return 0; // error +} + +// Interrupt Hander +void DFR0534::_rx_handler(void) +{ + while(_mp3.readable()) { + _rxbuf.push(_mp3.getc()); + } +} + +void DFR0534::_command(uint8_t cmd_no) +{ + _sum = 0xaa; + _mp3.putc(_sum); + _sum += cmd_no; + WAIT_MS(2); + _mp3.putc(cmd_no); + WAIT_MS(2); + _mp3.putc(0x00); + WAIT_MS(2); + _mp3.putc(_sum); +} + +void DFR0534::_command_w_para(uint8_t cmd_no, uint8_t *parameter, uint8_t len) +{ + _sum = 0xaa; + _mp3.putc(_sum); + _sum += cmd_no; + WAIT_MS(2); + _mp3.putc(cmd_no); + WAIT_MS(2); + _mp3.putc(0x00); + WAIT_MS(2); + for (uint32_t i = 0; i < len; i++) { + uint8_t dt = *parameter++; + _sum += dt; + _mp3.putc(dt); + WAIT_MS(2); + } + _mp3.putc(_sum); +} + +void DFR0534::_wait_busy(void) +{ + while (_bsy.read() == 1) { + WAIT_MS(20); + } +}
diff -r 000000000000 -r 466200f304c9 drf0534.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/drf0534.h Sun Dec 29 02:55:07 2019 +0000 @@ -0,0 +1,142 @@ +/* + * Mbed Library program + * UART MP3 Voice Module with 8MB Flash Memory / DFR0534 + * + * Copyright (c) 2019 Kenji Arai / JH1PJL + * http://www.page.sannet.ne.jp/kenjia/index.html + * https://os.mbed.com/users/kenjiArai/ + * Created: December 28th, 2019 + * Revised: December 29th, 2019 + */ + +/* + Reference information: + http://akizukidenshi.com/catalog/g/gM-13708/ + https://wiki.dfrobot.com/Voice_Module_SKU__DFR0534 + */ + +#ifndef DFR0534_H +#define DFR0534_H + +#include "mbed.h" + +#define VOL_MIN 0 +#define VOL_MAX 30 + +enum simple_commands{ + Play = 0x02, + Pause, + Playstop, + Prev_Audio, + Next_Audio, + The_Directory_of_the_previous_folder = 0x0e, + The_directory_of_the_next_folder, + End_to_play, + Increase_the_volume = 0x14, + Reduce_the_volume, + End_Combination_Play = 0x1c, + End_repetition = 0x21, + End_to_send_the_playing_time = 0x26 +}; + +/** UART MP3 Voice Module with 8MB Flash Memory / DFR0534 + * @code + * #include "mbed.h" + * #include "drf0534.h" + * + * DFR0534 mp3(PA_0, PA_1, PA_4); // tx, rx, busy + * + * int main() { + * mp3.volume_setting(VOL_MAX / 2); + * uint32_t num = mp3.total_num_of_audio(); + * while(true) { + * for (uint32_t i = 1; i < num + 1; i++) { + * mp3.play_one(i); + * mp3.get_file_name(name_buf); + * printf("File name = %s\r\n", name_buf); + * } + * } + * } + * @endcode + */ + +class DFR0534 +{ +public: + /** Create the DFR0534 object + * @param PinName communication line TX & RX & Busy signal input + */ + DFR0534(PinName tx, PinName rx, PinName busy); + + /** Play specific truck + * @param truck number + */ + void play_one(uint16_t track_num); + + /** set volume + * @param volume value(VOL_MIN to VOL_MAX, 0 to 30) + */ + void volume_setting(uint8_t vol); + + /** increase volume + * @param none + */ + void volume_increase(); + + /** decrease volume + * @param none + */ + void volume_decrease(); + + /** direct command (simple type -> No parameter & no return value) + * @param command + */ + void command(enum simple_commands cmds); + + /** Check the total number of audio track + * @param none + * @return total number of audio + */ + uint16_t total_num_of_audio(); + + /** Check the current audio track number + * @param none + * @return number + */ + uint16_t current_num_of_audio(); + + /** get file name + * @param buffer pointer (buffer size > 32) + * @return name into buffer + */ + void get_file_name(char *buf); + + /** get play time + * @param none + * @return time[seconds] + */ + uint32_t get_play_time(); + + /** get play back time + * @param none + * @return time[seconds] + */ + uint32_t get_play_back_time(); + +private: + RawSerial _mp3; + DigitalIn _bsy; + + void _rx_handler(void); + void _command(uint8_t cmd_no); + void _command_w_para(uint8_t cmd_no, uint8_t *parameter, uint8_t len); + void _wait_busy(void); + uint32_t get_time(void); + + CircularBuffer<char, 32> _rxbuf; // small ring buffer + uint8_t _sum; + char _buf[32]; + +}; + +#endif // DFR0534_H \ No newline at end of file