Je n'arrive pas à comprendre pourquoi MediaPlayer
joue parfois et parfois ne joue pas le même fichier. Il y a ca. 2000 fichiers audio dans le répertoire. Cela peut arriver à n'importe lequel d'entre eux. À la prochaine exécution de l'application, il peut y avoir d'autres fichiers qui sont affectés. Je n'ai aucune explication à cela.MediaPlayer ne joue pas toujours
Voici le code:
private void play(List<Integer> lineIndices, final MediaPlayer.OnCompletionListener completionListener) {
Log.d("ENTER lineIndices.size()=", lineIndices.size());
File sdcard = (RUNS_ON_EMULATOR) ? Environment.getExternalStorageDirectory() : new File("/storage/sdcard1");
final List<MediaPlayer> players = new ArrayList<>();
for (Integer index : lineIndices) {
Uri uri = Uri.fromFile(new File(sdcard + DEFAULT_FOLDER + getFileName(index)));
Log.d("File URI=%s", uri.toString());
MediaPlayer player = MediaPlayer.create(context, uri);
players.add(player);
}
for (int i = 0; i < players.size() - 1; i++) {
players.get(i).setNextMediaPlayer(players.get(i + 1));
}
MediaPlayer.OnCompletionListener listener = new MediaPlayer.OnCompletionListener() {
@Override
public void onCompletion(MediaPlayer mediaPlayer) {
completionListener.onCompletion(mediaPlayer);
for (MediaPlayer player : players) {
player.release();
}
}
};
if (!players.isEmpty()) {
players.get(players.size() - 1).setOnCompletionListener(listener);
Log.d("Before players.get(0).start();");
players.get(0).start();
}
Log.d("EXIT");
}
La sortie du journal indique que le fichier est déterminé et players.get(0).start()
est appelé:
com.android.vocabularytrainer D/VocabularyTrainerModelImpl: [play] ENTER lineIndices.size()=
com.android.vocabularytrainer D/VocabularyTrainerModelImpl: [play] File URI=file:///storage/sdcard1/tmp/english/vocabulary/000010.wav
com.android.vocabularytrainer D/VocabularyTrainerModelImpl: [play] Before players.get(0).start();
com.android.vocabularytrainer D/VocabularyTrainerModelImpl: [play] EXIT
J'ai essayé de le résoudre en utilisant une seule MediaPlayer
par exemple, non en utilisant la méthode setNextMediaPlayer
et en introduisant des appels de méthode setDataSource(), prepare()
et reset()
. Cela a amélioré un peu la situation, mais il peut toujours arriver qu'un fichier ne soit pas joué. Cependant, cela n'arrive pas si souvent que précédemment.
private void play(final List<Integer> lineIndices, final MediaPlayer.OnCompletionListener completionListener) {
Log.d("ENTER lineIndices.size()=%d", lineIndices.size());
if (!lineIndices.isEmpty()) {
final File sdcard = (RUNS_ON_EMULATOR) ? Environment.getExternalStorageDirectory() : new File("/storage/sdcard1");
final MediaPlayer player = new MediaPlayer();
final Uri uri = Uri.fromFile(new File(sdcard + DEFAULT_FOLDER + getFileName(lineIndices.get(0))));
try {
player.setDataSource(context, uri);
MediaPlayer.OnCompletionListener listener = new MediaPlayer.OnCompletionListener() {
private int i = 1;
@Override
public void onCompletion(MediaPlayer mediaPlayer) {
if (i < lineIndices.size()) {
final Uri uri = Uri.fromFile(new File(sdcard + DEFAULT_FOLDER + getFileName(lineIndices.get(i++))));
try {
mediaPlayer.reset();
mediaPlayer.setDataSource(context, uri);
mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
@Override
public void onPrepared(MediaPlayer mediaPlayer) {
Log.d("%s", uri.toString());
mediaPlayer.start();
}
});
mediaPlayer.prepare();
return;
} catch (IOException e) {
Log.e("Unable to play file", e);
}
}
completionListener.onCompletion(mediaPlayer);
mediaPlayer.release();
}
};
player.setOnCompletionListener(listener);
player.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
@Override
public void onPrepared(MediaPlayer mediaPlayer) {
Log.d("%s", uri.toString());
player.start();
}
});
player.prepare();
} catch (IOException e) {
Log.e("Unable to play file", e);
}
}
Log.d("EXIT");
}
Oui. Cela peut arriver à n'importe lequel de ces 2000 fichiers. S'il vous plaît regardez la deuxième version de la méthode dans ma réponse. Je viens de l'ajouter. – ka3ak
Merci pour la réponse, mais je n'ai pas essayé de trouver une solution. J'ai décidé de contourner le problème en utilisant le fichier texte et Google TTS au lieu de milliers de fichiers audio. Mais en ce qui concerne mediaplayer, je pense que certaines de ses fonctionnalités ne sont pas fiables (au moins dans Android 4.2.1). Par exemple. J'ai remarqué que seekTo() ne fonctionne pas bien si le fichier audio dure 2-3 heures. Je suppose que mediaplayer a quelques problèmes avec la lecture de milliers de fichiers qui ne durent que 1 à 2 secondes. Il se peut qu'il ne gère pas bien ce cas d'utilisation. – ka3ak