#android #file #inputstream #fileoutputstream
#Android #файл #входной поток #fileoutputstream
Вопрос:
Итак, у меня есть небольшой аудиофайл в папке assets, и я хотел открыть входной поток для записи в буфер, затем записать во временный файл, затем я открываю MediaPlayer для воспроизведения этого временного файла. Проблема в том, что когда медиаплеер нажимает mp.Prepare (), он не воспроизводится и никогда не достигает toast. Кто-нибудь когда-нибудь делал это раньше?
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
InputStream str;
try {
str = this.getAssets().open("onestop.mid");
Toast.makeText(this, "Successful Input Stream Opened.", Toast.LENGTH_SHORT).show();
takeInputStream(str);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}//end on create
public void takeInputStream(InputStream stream) throws IOException
{
//fileBeingBuffered = (FileInputStream) stream;
//Toast.makeText(this, "sucessful stream conversion.", Toast.LENGTH_SHORT).show();
try
{
convertedFile = File.createTempFile("convertedFile", ".dat", getDir("filez", 0));
Toast.makeText(this, "Successful file and folder creation.", Toast.LENGTH_SHORT).show();
out = new FileOutputStream(convertedFile);
Toast.makeText(this, "Success out set as output stream.", Toast.LENGTH_SHORT).show();
//RIGHT AROUND HERE -----------
byte buffer[] = new byte[16384];
int length = 0;
while ( (length = stream.read(buffer)) != -1 )
{
out.write(buffer,0, length);
}
//stream.read(buffer);
Toast.makeText(this, "Success buffer is filled.", Toast.LENGTH_SHORT).show();
out.close();
playFile();
}catch(Exception e)
{
Log.e(TAG, e.toString());
e.printStackTrace();
}//end catch
}//end grabBuffer
public void playFile()
{
try {
String path = convertedFile.getAbsolutePath();
mp = new MediaPlayer();
mp.setDataSource(path);
Toast.makeText(this, "Success, Path has been set", Toast.LENGTH_SHORT).show();
mp.setAudioStreamType(AudioManager.STREAM_MUSIC);
mp.prepare();
Toast.makeText(this, "Media Player prepared", Toast.LENGTH_SHORT).show();
mp.start();
Toast.makeText(this, "Media Player playing", Toast.LENGTH_SHORT).show();
} catch (IllegalArgumentException e) {
Log.e(TAG, e.toString());
e.printStackTrace();
} catch (IllegalStateException e) {
Log.e(TAG, e.toString());
e.printStackTrace();
} catch (IOException e) {
Log.e(TAG, e.toString());
e.printStackTrace();
}
}//end playFile
Комментарии:
1. Что вы подразумеваете под «это останавливается»?
2. о, извините, я имел в виду, что он «никогда не воспроизводится» после достижения prepare. Он никогда не достигает Toast.
3. Вы получаете какие-либо исключения? Кроме того, это неправильный способ использования MediaPlayer, вам нужно дождаться, пока придет событие onPrepared, но я не уверен, что это связано.
4. Насколько я вижу, ничего подобного. Все остальные примеры, похоже, работают нормально без использования onPrepared. Я попробую это с ним и посмотрю, что получится.
5. @Rion КСТАТИ, обычный аудиофайл успешно воспроизводится?
Ответ №1:
Исправлено. Оказывается, что после записи буфера во временный файл, созданный с помощью «File», вы можете открыть этот файл с помощью FileInputStream, а затем продолжить воспроизведение, показанное ниже. Спасибо за всю вашу помощь, ребята.
mp = new MediaPlayer();
FileInputStream fis = new FileInputStream(convertedFile);
mp.setDataSource(fis.getFD());
Toast.makeText(this, "Success, Path has been set", Toast.LENGTH_SHORT).show();
mp.prepare();
mp.start();
Комментарии:
1. Отличный ответ, однако у меня есть сомнения. Когда подходящее время закрыть «fis»?
2. Вы должны закрыть FIS сразу после вызова setDataSource. В документации говорится: «Устанавливает источник данных (FileDescriptor) для использования. Ответственность за закрытие файлового дескриптора лежит на вызывающем устройстве. Это безопасно сделать, как только этот вызов вернется. »
3. что не так с простым «Uri.fromFile(преобразованный файл)»?!
Ответ №2:
Это код, который сработал у меня
//preserved to stop previous actions
MediaPlayer lastmp;
public void playSound(String file) {
try {
if (lastmp!=null) lastmp.stop();
MediaPlayer mp = new MediaPlayer();
lastmp = mp;
AssetFileDescriptor descriptor;
AssetManager assetManager = act.getAssets();
descriptor = assetManager.openFd(fileName);
mp.setDataSource(descriptor.getFileDescriptor(), descriptor.getStartOffset(), descriptor.getLength());
descriptor.close();
mp.prepare();
mp.start();
} catch (Exception e) {
e.printStackTrace();
}
}
файл должен находиться в папке assets