Помогите разобраться с UART DFPlayer Mini 2.0

Тема в разделе "Arduino & Shields", создана пользователем Unruly, 27 ноя 2014.

  1. Taraserker

    Taraserker Нерд

    Там булевская переменная, или истина или ложь.
    mp3_single_loop (0 или 1 )
    вероятно разрешает или запрещает режим лупа.
     
  2. ostrov

    ostrov Гуру

    Неужели трудно понять почему?
    И вообще, если вставляете готовый код к себе, то хорошо бы разобраться как он работает хотя бы примерно. Вы же делаете опрос и внутри и снаружи функции, потом удивляетесь почему не работает или работает не так.
     
  3. Taraserker

    Taraserker Нерд

    Стало лучше, но полностью не помогло.
    У меня сейчас на флешке 4 файла, и по изменению сигнала на выводах запускаю один из них.
    Где то каждый третий раз файл не воспроизводиться.
    Опять вставил двойной запуск файла.

    Код (C++):

    void mp3RepeatPlay ( int Mode, int Volume ) {
      mp3_set_volume (Volume);
      delay(50);            // from amperka forum, recomend pause before command
      mp3_single_loop (1);
      delay(50);
      mp3_play (Mode);    //play "mp3/000 'Mode' .mp3"
      mp3_play (Mode);
      delay(50);
      mp3_single_loop (1);

     
      mp3_get_volume();
      Serial.println (" Get Volume : " );
      mp3BufferOut();
      mp3_get_flash_current();
      Serial.println (" Get flash current : " );
      mp3BufferOut();

    }
     
     
  4. olegtur77

    olegtur77 Нерд

    играюсь с таким же модулем, На основе пары готовых проектов написал свой, Тоже столкнулся с проблеммой проигрывания "по кольцу" текущего трека..Но у меня несколько другая задача- иммитатор звука мотора на моделях. Тоже танцы с оператором loop приводили лишь к "иканию" . В итоге решил просто в конце цикла проверок дополнительной строчкой
    mp3_play ();// если трек игрался, повторяем его, и заработало как надо. плеер "помнит" последний трек и достаточно его просто стартануть командой "плей"

    вот мой код
    Код (C++):
    #include <Servo.h>
    #include <SoftwareSerial.h>
    #include <DFPlayer_Mini_Mp3.h>

    int prevThrottle = 0; //предыдущее значение газа
    int currThrottle = 0; // текущее значение газа
    int playingSound = 0; // текущий трек
    int potpin = 0;  // вход для потенциометра, газ
    int pos = 90;    // начально положение сервы "шасси"
    int val;    // переменная ацп
    int buttonPin = 4;     // вход управления сервой шасси, тумлер
    //int motor =  5;      // выход ШИМ для колекторного мотора, газ
    int ledPin =  7;      // индикатор шасси поднято/опущено, один свд на землю, другой на +5
    int buttonState = 0;
    Servo gear;  // объект серво "шасси"
    Servo motor;  // объект серво "мотор" для управления станд регулятором оборотов

    void setup(){
        gear.attach(6);  // объект"шасси"
        motor.attach(5);  // объект "мотор"
        pinMode(ledPin, OUTPUT);  // initialize the pushbutton pin as an input:
        //pinMode(motor, OUTPUT);  // initialize the pushbutton pin as an input:
        pinMode(buttonPin, INPUT_PULLUP);//тумблер, с подтяжкой
        Serial.begin(9600);
        mp3_set_serial (Serial);  //set Serial for DFPlayer-mini mp3 module
        mp3_set_volume (20);//выставляем громкость модуля мр3
      }

      void loop(){
       
    buttonState = digitalRead(buttonPin);//читаем состояние тумблера шасси и отрабатываем, если оно противоположно.

    if (buttonState == LOW) {
            digitalWrite(ledPin, HIGH);
            while ( pos < 90){
            gear.write(pos);
            pos++;          
            delay(20);
            }
            }
         else {
            digitalWrite(ledPin, LOW);
            while( pos >  0){
            gear.write(pos);
            pos --;
            delay(20);
            }
            }


      val = analogRead(potpin); //читаем аналоговый вход, положение газа
      /* val = map(val, 0, 1023, 0, 255);     // обычный ШИМ регулятор для коллекторного мотора, через полевик
      analogWrite(motor,val);                  // преобразовываем значение от ацп в шим 0..255
    */


      val = map(val, 0, 1023, 0, 180);     // или преобразовываем значение от ацп в шим 0..180грд,мин-макс газа регулятора
      motor.write(val);            

         if(val <= 20){   // положение газа минимум(0) - молчим
            currThrottle = 0;
         }
         if((val > 20) && (val <= 50)){
            currThrottle = 1; // газ 1 диапазон
            // mp3_play (); // если трек игрался, повторяем его
       
         }
          if((val > 51) && (val <= 80)){
            currThrottle = 2;// газ 2 диапазон
            }
          if((val > 81) && (val <= 110)){
            currThrottle = 3;// газ 3 диапазон
            }
          if((val > 111) && (val <= 140)){
            currThrottle = 4; // газ 4 диапазон
            }
          if((val > 141) && (val <= 170)){
            currThrottle = 5;// газ 5 диапазон
            }
          if((val > 171) && (val <= 200)){
            currThrottle = 6;// газ 6 диапазон
            }
          if(val > 201){
            currThrottle = 7;// газ 7 диапазон
            }

       
          if(currThrottle != prevThrottle){ // проверяется текущее и предыдущее значение газа, если оно изменилось
         
            if((currThrottle == 0) && (prevThrottle > 0)){
                 mp3_play (8);//shut...трек "сброс газа и глушение мотора", если газ перешел с бОльшего значения на меньшее
                 prevThrottle = currThrottle;//играем трек8, на карте как 0008.мр3
            }
            if(currThrottle == 1){
                 if(currThrottle > prevThrottle){
                 mp3_play (1);//start....трек "заводим мотор ", если газ перешел с меньшего значения на большее
                 }            //играем трек1, на карте как 0001.мр3
                 playingSound = 1;
                 prevThrottle = currThrottle;//сохраняем текущее значение газа как предыдущее
            }
            if(currThrottle == 2){
              mp3_play (2);//играем трек2, на карте как 0002.мр3
              prevThrottle = currThrottle;
              playingSound = 2;
            }
            if(currThrottle == 3){
              mp3_play (3);
              prevThrottle = currThrottle;
              playingSound = 3;
            }
            if(currThrottle == 4){
              mp3_play (4);
              prevThrottle = currThrottle;
             playingSound = 4;
            }
             if(currThrottle == 5){
              mp3_play (5);
              prevThrottle = currThrottle;
             playingSound = 5;
            }
             if(currThrottle == 6){
              mp3_play (6);
              prevThrottle = currThrottle;
             playingSound = 6;
             }
             if(currThrottle == 7){
              mp3_play (7);
              prevThrottle = currThrottle;
             playingSound = 7;
            }
            }
        if(currThrottle = prevThrottle){
           mp3_play ();// если трек игрался, повторяем его
        }
     
    }

     
     
  5. serdod

    serdod Нерд

    Подскажите, пожалуйста, как сделать чтобы case отправлял одну команду mp3_next...А то за одно нажатие отправляет от 3 до 10 команд.

    Код (C++):
    #include <SoftwareSerial.h>
    #includ <DFPlayer_mini_mp3.h>
    #define sensePin A0
    int i=0;
    #define PressMode 1
    #define PressUp 2
    #define PressDn 3
    #define PressLeft 4
    #define PressRight 5
    #define PressNo 6
    int currButton;

    void setup () {
      pinMode(sensePin, INPUT);
      Serial.begin(9600);
       mp3_set_serial (Serial);
      delay(1);
       mp3_set_volume (15);
       void mp3_random_play ();
    }
    int getR() {
      int r = analogRead(sensePin);
      if (r >=420 && r <= 450) return (PressMode);
      if (r >=645 && r <= 665) return (PressUp);
      if (r >=800 && r <= 815) return (PressDn);
      if (r >=900 && r <= 915) return (PressLeft);
      if (r >=970 && r <= 995) return (PressRight);
      return (PressNo);
    }
    void loop() {
      currButton = getR();
      delay(10);
      byte bounceButton = getR();
      if (currButton == bounceButton) {
        switch (currButton) {
          case PressMode: Serial.println("PressMode"); break;
          case PressUp: Serial.println("PressUp"); break;
          case PressDn: Serial.println("PressDn"); break;
          case PressLeft: mp3_next ();Serial.println("PressLeft"); break;
          case PressRight: mp3_prev (); Serial.println("PressRight"); break;
          //case PressNo: Serial.println("PressNo"); break;
        }
      }
    }
         
     
     
  6. Basilio83

    Basilio83 Нерд

    А не подскажите в чем может быть дело.
    Имеется аналоговый датчик тока ACS712 так вот при проигрывании трека показания возрастают
    Код (C++):
    #include <SoftwareSerial.h>
    #include <DFPlayer_Mini_Mp3.h>
    int flag = 0; // переменная равна 0
    #define BUSY_MP3  11 // ножка BUSY занятость мп3 (0-играет, 1-молчит)
    #define SENSOR_PIN A0 // ножка датчика тока
    SoftwareSerial mySerial(9, 10); // RX, TX
    void setup () {
      Serial.begin (9600);
      mySerial.begin (9600);
      mp3_set_serial (mySerial);    //set Serial for DFPlayer-mini mp3 module
      mp3_set_volume (25);
      pinMode(BUSY_MP3, INPUT);// установил вход на 11 пин BUSY_MP3
      pinMode(12, OUTPUT);// установил выход на 12 пин
    }


    //
    void loop ()
    {
      long val = 0;
      if (digitalRead(8) == HIGH && flag == 0)
        // если на 8 входе есть сигнал и переменная равна 0 то...
      {
        Serial.println("@1");
        digitalWrite(12, !digitalRead(12)); //меняем значение выхода на противоположное
        flag = 1; //меняем значение ФЛАГА
        //это нужно для того что бы с каждым нажатием кнопки
        //происходило только одно действие
        // плюс защита от "дребезга"  100%
        delay (1000);
      }

      if (digitalRead(8) == LOW && flag == 1)
        //если на 8 входе нет сигнал и переменная равна 1 то...
      {
        Serial.println("@2");
        flag = 0; //обнуляем переменную
        delay (1000);
      }

      for (int i = 0; i < 1000; ++i) val = val + analogRead(SENSOR_PIN);
      val = val / 1000;
      Serial.println(val);

      if (digitalRead(BUSY_MP3) == HIGH && digitalRead(12) == HIGH)    // если есть сигнал на на 12 выходе и BUSY_MP3 и оба генератора работают то ...
      {
        if (val < 520)
        {
          Serial.println("@3");
          mp3_play (1);//проигрываем 1 трек
          delay (100);
        }

        if (val > 520 && val < 530)
        {
          Serial.println("@4");
          mp3_play (2);//проигрываем 2 трек
          delay (100);
        }

        if (val > 530)
        {
          Serial.println("@5");
          mp3_play (3);//проигрываем 3 трек
          delay (100);
        }
      } //

      if (digitalRead(12) == LOW) // если на 12 выходе нет сигнала то...
      {
        Serial.println("@6");
        mp3_stop ();
      }
    }
     
  7. Taraserker

    Taraserker Нерд

    Ну так 10 мс задержка, просто нажать и быстро отпустить кнопку, это 50 мс в лучшем случае, а то и больше.
    Надо как то это отслеживать, и дребезг контактов.
    я обычно ввожу переменную PreviosPress и если текущее с предыдущим совпало то ничего не делается.
    или переменная, при считывании даю ей значение 5 и пока не станет равной 0 считываний не будет.
     
    serdod нравится это.
  8. Taraserker

    Taraserker Нерд

    Это схемотехническая проблема.
    скорее всего Небольшая просадка питания при появлении дополнительного потребления.
    Попробуйте повесить на выход aref кондендсатор на 10 мкФ.
     
  9. Sergos77

    Sergos77 Нуб

    Уважаемый Onkel подскажите на "пальцах" как вычислить CRC ?
    По пунктам, что за чем делать.
    Ваши команды все прекрасно работают через COM Port Toolkit 4.0 +PL2303+DFPlayer
     
  10. ostrov

    ostrov Гуру

    Если поищите где то тут есть мой код с функцией вычисления CRC. И остальными функциями для работы плеера
     
  11. denis-87

    denis-87 Нуб

    Добрый день!Помогите разобраться требуется управление плеером пультом,но при нажатие на любую кнопку на пульте команда на плеер шлется бесконечное число раз до перезагрузки arduino
    Код (C++):
    #include <RCSwitch.h>
    #include <SoftwareSerial.h>
    #include <DFRobotDFPlayerMini.h>
    SoftwareSerial mySerial(10, 11); // RX, TX
    DFRobotDFPlayerMini myDFPlayer;
    RCSwitch mySwitch = RCSwitch();

    void setup() {
      Serial.begin(9600);
      mySwitch.enableReceive(0);  // Receiver on interrupt 0 => that is pin #2
      mySerial.begin (9600);
      myDFPlayer.begin(mySerial);
     
        delay (3000);
        myDFPlayer.volume (25);
        delay (100);
        myDFPlayer.play (1);
       
    }

    void loop() {
      if (mySwitch.available()) {
       
        int value = mySwitch.getReceivedValue();

        switch (value)
       {
        case 8009997: // кнопка 1
        delay (100);
        myDFPlayer.play (1);
        break;
       
        case 8009998: // кнопка 2
        delay (100);
        myDFPlayer.play (2);
        break;
       
        case 8009999: // кнопка 3
        delay (100);
        myDFPlayer.play (3);
        break;
       
        case 8010000: // кнопка 4
        delay (100);
        myDFPlayer.play (4);
        break;

        case 8010001: // кнопка 5
        delay (100);
        myDFPlayer.play (5);
        break;

        case 8010002: // кнопка 6
        delay (100);
        myDFPlayer.play (6);
        break;

        case 8010003: // кнопка 7
        delay (100);
        myDFPlayer.play (7);
        break;

        case 8010004: // кнопка 8
        delay (100);
        myDFPlayer.play (8);
        break;

        case 8010005: // кнопка 9
        delay (100);
        myDFPlayer.play (9);
        break;

        case 8009994: // кнопка 0
        delay (100);
        myDFPlayer.play (10);
        break;

        case 8009995: // кнопка 100+
        delay (100);
        myDFPlayer.play (11);
        break;
       
        case 8009987:
        delay (100);
        myDFPlayer.volume(10); // кнопка mute
        break;

        case 8009989: // кнопка >>
        delay (100);
        myDFPlayer.next ();
        break;

        case 8009988: // кнопка <<
        delay (100);
        myDFPlayer.previous ();
        break;

        case 8009992: // кнопка +
        delay (100);
       myDFPlayer.volumeUp(); //Volume Up
        break;

        case 8009991: // кнопка -
        delay (100);
        myDFPlayer.volumeDown(); //Volume Down
        break;
       
        case 8009985: // кнопка power
        delay (100);
        myDFPlayer.pause();  //pause the mp3
        break;
       
        case 8009996: // кнопка repeat
        delay (100);
        myDFPlayer.enableLoop(); //enable loop.
        break;
       
        mySwitch.resetAvailable();
        default:
         break;
     
  12. Zharklod

    Zharklod Нуб

    Кому ещё актуально. Нашёл datasheet на предыдущую версию DFPlayer. Там всё более менее адекватно расписано, буду сам разбираться и другим рекомендую. По крайней мере посылки в HEX формате не нужно считать.
     

    Вложения:

  13. variator

    variator Нуб

    Здравствуйте!
    Извиняюсь за глупый вопрос, прошу подсказать как выглядит код для воспроизведения диапазона треков?
    Пробовал так.
    Код (C++):
    #include <SoftwareSerial.h>
    #include <DFPlayer_Mini_Mp3.h>
    void setup() // процедура setup
    {
    Serial.begin(9600);
    mp3_set_serial(Serial); // включаем передачу данных с DFPlayer mini mp3
    delay(100); // задержка в 100ms для установки громкости
    mp3_set_volume(5); // устанавливаем громкость от 0 до 30
    }

    void loop ()
    {
    for (int i=0; i<10; i=i+1) // цикл, считает от 1 до 10
    {
    mp3_play (i); // запускаем трек
    delay (1000);
    }
    }
     
    В результате трек играет 1 секунду и перескакивает на следующий, не дожидаясь окончания.
    Как сделать, чтобы треки проигрывались целиком?
     
  14. ostrov

    ostrov Гуру

    Проверять ножку BUSY, как освободится так играть следующий.
     
    variator нравится это.
  15. variator

    variator Нуб

    Если я правильно понял, то помимо функций
    Код (C++):
    /* mp3_set_volume(); // установка громкости от 0 до 30
    mp3_set_EQ(); // эквалайзер от 0 до 5
    mp3_play(); // запуск воспроизведения

    и т.д)*/
    плеером можно управлять с помощью бинарных команд. Хочется увидеть как это выглядит в коде (например, команда запустить трек), и разобраться вот с этими таблицами. Читаю C++, но без примера въехать непросто.
    Спасибо.
    [​IMG][​IMG]
    [​IMG][​IMG]
     
    Последнее редактирование: 26 янв 2018
  16. ostrov

    ostrov Гуру

    Если поискать, то можно найти мои функции управления плеером именно таким способом. Я их выкладывал.
     
  17. variator

    variator Нуб

    Благодарю!
     
  18. variator

    variator Нуб

    Никто не реализовывал вариант без опрашивания ножки BUSY? Плеер ведь отправляет команды о состоянии. Было бы интересно посмотреть.
     
  19. ARDUIN-щик

    ARDUIN-щик Гик

    Читайте, читайте, читайте: https://www.dfrobot.com/wiki/index.php/DFPlayer_Mini_SKU:DFR0299
    Единственная достоверная информация, да при том на сайте производителя... Заманчиво, не правда ли!?
    (Итересно, перед тем как задать вопрос, кто-нибудь переходит на сайт производителя?)
     
  20. ostrov

    ostrov Гуру

    Связь односторонняя, он все понимает но ничего не говорит. Как собака.