0

MusicMaker trys to play System~1/ file
Moderators: adafruit_support_bill, adafruit

Please be positive and constructive with your questions and comments.

MusicMaker trys to play System~1/ file

by nickmart1 on Thu Apr 21, 2022 5:16 pm

Thanks to your great support help, I was able to get the MP3 music player shield working well. The sd Card has 9 files labeled track001.mp3 through track009.mp3. I have a PIR connected to digital I/O pin 3. When motion is detected the music maker will select and play a random file. I noticed something unusual in that while there is no file labeled System~1/, the card attempts to play it. This causes the listener to think it stopped working although the loop is fast enough to see motion and play another file. While I can live with this, I'm curious as to where this file is coming from. With random file selection, it's possible that System~1/ will play twice in a row.
Is this a library issue or is it a sketch programming error?
Note that I was careful to set windows to view hidden files and extensions when exploring the files on the sd card.
See sketch and monitor screen capture.
thanks,
Nick
Attachments
Screenshot 2022-04-19 171532.jpg
screen shot of serial monitor
Screenshot 2022-04-19 171532.jpg (138.36 KiB) Viewed 200 times
final code_working.txt
Working sketch
(5.06 KiB) Downloaded 6 times

nickmart1
 
Posts: 16
Joined: Thu Apr 07, 2022 12:14 pm

Re: MusicMaker trys to play System~1/ file

by nickmart1 on Tue May 17, 2022 9:50 pm

nickmart1 wrote:Thanks to your great support help, I was able to get the MP3 music player shield working well. The sd Card has 9 files labeled track001.mp3 through track009.mp3. I have a PIR connected to digital I/O pin 3. When motion is detected the music maker will select and play a random file. I noticed something unusual in that while there is no file labeled System~1/, the card attempts to play it. This causes the listener to think it stopped working although the loop is fast enough to see motion and play another file. While I can live with this, I'm curious as to where this file is coming from. With random file selection, it's possible that System~1/ will play twice in a row.
Is this a library issue or is it a sketch programming error?
Note that I was careful to set windows to view hidden files and extensions when exploring the files on the sd card.
See sketch and monitor screen capture.
thanks,
Nick

Hi again,
I have not seen a reply to this issue. Any ideas why I'm seeing a file playing called System~1/? The PIR is connected to digital I/O pin 2, not pin 3.
Thanks,
Nick

nickmart1
 
Posts: 16
Joined: Thu Apr 07, 2022 12:14 pm

Re: MusicMaker trys to play System~1/ file

by neradoc on Wed May 18, 2022 4:50 am

Hi, SYSTEM~1 is how systems that can only understand 8 characters file names (old DOS for example) show "long" character names.
I would think it is "System Volume Information", and your "chooseRandomFile" function doesn't know to ignore it.

You could change that function to test "entry.isDirectory()" and skip the entry.
Or test for files ending in "MP3" and other allowed file formats and ignore the rest.

"System Volume Information" might be completely hidden by windows, according to some results on the web, which is why you can't see it.
https://www.minitool.com/lib/system-vol ... ation.html

neradoc
 
Posts: 174
Joined: Wed Apr 27, 2016 2:38 pm

Re: MusicMaker trys to play System~1/ file

by nickmart1 on Wed May 18, 2022 7:06 am

Thanks. That makes perfect sense. I had thought changing windows to view all hidden files and extensions would reveal it.
Nick

nickmart1
 
Posts: 16
Joined: Thu Apr 07, 2022 12:14 pm

Re: MusicMaker trys to play System~1/ file

by nickmart1 on Tue May 24, 2022 4:44 pm

OK,
I tried changing the SD directory from "/" to "/MP3/" and moved all the mp3 files into the subdirectory /MP3? on the SD card. The program found the files ok but now the PIR function quit working. Do I need to add the subdirectory somewhere else?
thanks,
Nick

nickmart1
 
Posts: 16
Joined: Thu Apr 07, 2022 12:14 pm

Re: MusicMaker trys to play System~1/ file

by neradoc on Thu May 26, 2022 9:00 am

nickmart1 wrote:OK,
I tried changing the SD directory from "/" to "/MP3/" and moved all the mp3 files into the subdirectory /MP3? on the SD card. The program found the files ok but now the PIR function quit working. Do I need to add the subdirectory somewhere else?
thanks,
Nick

Hi, did you figure it out ?
Without seeing your new code, maybe the issue is that the "chooseRandomFile" function returns the name of the file that you then pass to "musicPlayer.startPlayingFile".
If it takes file paths, I think you need to prefix it with the directory name. Like "/MP3/" (with dir.name). Watch the size of your outFileName buffer.

neradoc
 
Posts: 174
Joined: Wed Apr 27, 2016 2:38 pm

Re: MusicMaker trys to play System~1/ file

by nickmart1 on Thu May 26, 2022 7:13 pm

I'm not sure I understand your suggestion. I did add the following code in an attempt to get around the problem.:

Code: Select all | TOGGLE FULL SIZE
    if (pirState == LOW) {    // we have just turned on
      char fullName[20] = "/MP3/";
      strcat(fullName, MP3);
      (! musicPlayer.startPlayingFile(MP3));
      Serial.println("Motion detected!");

      // We only want to print on the output change, not state
      pirState = HIGH;
    }

[
Where do I find the outFileName buffer size? I only have 9 mp3 files.
Here is the entire code using a directory on the sd card called \MP3\ I can see the files being read in the monitor but the PIR doesn't seem to trigger the files any longer. This is weird since I didn't change this part of the code. I should see "motion detected" in the serial monitor but I don't.
I'm thinking it might be easier to abandon the subdirectory \MP3\ and simply to test for System~1 so it will not try to play. If so, can you give me a code suggestion for that?
Here is the entire code with the changes to \MP3\. Again, somehow, I broke the pir detection.

Code: Select all | TOGGLE FULL SIZE
// include SPI, MP3 and SD libraries
#include <SPI.h>
#include <Adafruit_VS1053.h>
#include <SD.h>

//////////////////////////////////////////////////////////////////////////////////////////////////////
// These are the pins used for the music maker shield
#define SHIELD_RESET  -1      // VS1053 reset pin (unused!)
#define SHIELD_CS     7      // VS1053 chip select pin (output)
#define SHIELD_DCS    6      // VS1053 Data/command select pin (output)
// These are common pins between breakout and shield
#define CARDCS 4     // Card chip select pin
// DREQ should be an Int pin, see http://arduino.cc/en/Reference/attachInterrupt
#define DREQ 3       // VS1053 Data request, ideally an Interrupt pin
Adafruit_VS1053_FilePlayer musicPlayer =
  Adafruit_VS1053_FilePlayer(SHIELD_RESET, SHIELD_CS, SHIELD_DCS, DREQ, CARDCS);

//  Setup PIR sensor
int ledPin = 13;                // choose the pin for the LED
int inputPin = 2;               // choose the input pin (for PIR sensor)
int pirState = LOW;             // we start, assuming no motion detected
int val = 0;                    // variable for reading the pin status
void setup() {
  Serial.begin(9600);  //initialize the serial monitor
  pinMode(ledPin, OUTPUT);      // declare LED as output
  pinMode(inputPin, INPUT);     // declare sensor as input
  //////////////////////////////////////////////////////////////////////////////////////////////////////
  uint32_t seed = 0;  // Generate random seed start
  for ( uint8_t i = 10 ; i ; i-- ) {
    seed = ( seed << 5 ) + ( analogRead( 0 ) * 3 );
  }
  randomSeed( seed );  //set random seed
  //
  Serial.println("Adafruit VS1053 Library Test");
  Serial.print("RandomSeed value = ");
  Serial.println(seed);
  // initialise the music player
  if (! musicPlayer.begin()) { // initialise the music player
    Serial.println(F("Couldn't find VS1053, do you have the right pins defined?"));
    while (1);
  }
  Serial.println(F("VS1053 found"));
  musicPlayer.sineTest(0x44, 500);    // Make a tone to indicate VS1053 is working

  if (!SD.begin(CARDCS)) {
    Serial.println(F("SD failed, or not present"));
    while (1);  // don't do anything more
  }

  Serial.println("SD OK!");

  // list files
  printDirectory(SD.open("/MP3/"), 0);
  // Set volume for left, right channels. lower numbers == louder volume!
  musicPlayer.setVolume(1, 1);

  if (! musicPlayer.useInterrupt(VS1053_FILEPLAYER_PIN_INT))
    Serial.println(F("DREQ pin is not an interrupt pin"));
}
///////////////////////////////////////////////////////////////////////////////////////////////////////
void loop() {
  // put your main code here, to run repeatedly:
  char MP3[15];  // Allocate some room
  File dir = SD.open("/MP3/"); //Root Directory
  chooseRandomFile(dir, MP3); 6763;
  dir.close();
  delay(200);
  // Read pirState to Start/Stop playing a file.
  val = digitalRead(inputPin);  // read input value
  if (val == HIGH) {            // check if the input is HIGH
    digitalWrite(ledPin, HIGH);  // turn LED ON
    if (pirState == LOW) {    // we have just turned on
      char fullName[20] = "/MP3/";
      strcat(fullName, MP3);
      (! musicPlayer.startPlayingFile(MP3));
      Serial.println("Motion detected!");

      // We only want to print on the output change, not state
      pirState = HIGH;
    }
  } else {
    digitalWrite(ledPin, LOW); // turn LED OFF
    if (pirState == HIGH) {    // we have just turned off
      Serial.println("Motion ended!");


      // We only want to print on the output change, not state
      pirState = LOW;
    }

    //  if (! musicPlayer.startPlayingFile(MP3)) {
    //    Serial.println("Could not open file: ");
    //    Serial.println(MP3);
  }


  Serial.print(F("Now playing "));
  Serial.println(MP3);
  while (musicPlayer.playingMusic) {

    delay( 1000 );

  }
  Serial.print("Done playing: ");
  Serial.println(MP3);
  Serial.println();
}
////////////////////////////////////////////////////////////////////////////////////////////////////
/// File listing helper
void printDirectory(File dir, int numTabs) {
  while (true) {

    File entry =  dir.openNextFile();
    if (! entry) {
      // no more files
      //Serial.println("**nomorefiles**");
      break;
    }
    for (uint8_t i = 0; i < numTabs; i++) {
      Serial.print('\t');
    }
    Serial.print(entry.name());
    if (entry.isDirectory()) {
      Serial.println("/");
      printDirectory(entry, numTabs + 1);
    } else {
      // files have sizes, directories do not
      Serial.print("\t\t");
      Serial.println(entry.size(), DEC);
    }
    entry.close();
  }
}
////////////////////////////////////////////////////////////////////////////////////////////////////
// Function to select random mp3
void chooseRandomFile( File dir, char* outFileName) {
  File entry, result;
  int count = 1;

  dir.rewindDirectory();

  while ( entry = dir.openNextFile() ) {
    if ( random( count ) == 0 ) {
      if (result ) {
        result.close();
      }
      result = entry;
    } else {
      entry.close();
    }
    count++;
  }
  strcpy(outFileName, result.name());
  result.close();
}

nickmart1
 
Posts: 16
Joined: Thu Apr 07, 2022 12:14 pm

Re: MusicMaker trys to play System~1/ file

by neradoc on Fri May 27, 2022 7:20 am

I meant increasing the buffer passed to "chooseRandomFile" so that the function would do the strcat and return the full path.
But the way you did it is fine too, except that you have a little error, you are not using fullName:
You want to change musicPlayer.startPlayingFile(MP3) to musicPlayer.startPlayingFile(fullName).

Not sure why you are not seeing serial output. What if you print the file name before trying to play it ? Check you didn't bump your sensor's connection.

I remembered I have a MusicMaker featherwing and ran your code on a feather M0, with the fix (and the pins for the M0).
The code runs and seems to do what it's supposed to do (I have no speakers connected but I see it say that it's playing for the correct duration). I made a few modifications, in particular skipping files smaller than 8kB to skip any system files that MacOS tends to leave around sometimes. (I simulated the input with a wire).

mp3_player.ino
(5.33 KiB) Downloaded 1 time

neradoc
 
Posts: 174
Joined: Wed Apr 27, 2016 2:38 pm

Re: MusicMaker trys to play System~1/ file

by nickmart1 on Fri May 27, 2022 12:58 pm

Thanks so much Neradoc. I changed to musicPlayer.startPlayingFile(fullName). That worked great. Now working and not playing System~1 file.
Nickmart1

nickmart1
 
Posts: 16
Joined: Thu Apr 07, 2022 12:14 pm

Please be positive and constructive with your questions and comments.