当前位置: 首页 > 知识库问答 >
问题:

MediaPlayer尝试在Android应用程序中播放音频时出错

山疏珂
2023-03-14

我正在做一个简单的媒体录制/播放器应用程序,录制部分已成功完成。但现在我对媒体播放器的角色有了问题。让我告诉你这些问题:

当我尝试用媒体播放器播放媒体文件时,会显示如下准备错误:

JAVAio。IOException:准备失败:状态=0x1

我如何解决这个问题?

我的三门课:

-RecordFragment.java:

import android.Manifest;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.media.MediaRecorder;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AlertDialog;
import androidx.core.content.ContextCompat;
import androidx.core.content.res.ResourcesCompat;
import androidx.fragment.app.Fragment;

import android.os.Environment;
import android.os.SystemClock;
import android.provider.Settings;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Chronometer;
import android.widget.TextView;
import android.widget.Toast;

import com.airbnb.lottie.LottieAnimationView;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.venomapps.voicerecorder.R;
import com.venomapps.voicerecorder.Utils.Constants;

import java.io.File;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;

public class RecordFragment extends Fragment {

    private TextView textViewInformation;
    private FloatingActionButton floatingActionButtonStartRecording;
    private FloatingActionButton floatingActionButtonFinishRecording;
    private FloatingActionButton floatingActionButtonCancelRecording;
    private int recordingStatus = 0;
    private String fileName = "";
    private Context context;
    String[] permissions = {Manifest.permission.RECORD_AUDIO, Manifest.permission.WRITE_EXTERNAL_STORAGE};
    private MediaRecorder mediaRecorder;
    private String outPutFilePath;
    private Chronometer chronometerRecord;
    private boolean running;
    private long pauseOffset;
    private LottieAnimationView lottieAnimationViewVoice;

    public RecordFragment() {
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        return inflater.inflate(R.layout.fragment_record, container, false);
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        context = getActivity();
        bindUI(view);
        setListeners();
    }

    private void bindUI(View view) {
        textViewInformation = view.findViewById(R.id.textViewInformation);
        floatingActionButtonStartRecording = view.findViewById(R.id.floatingActionButtonStartRecording);
        floatingActionButtonFinishRecording = view.findViewById(R.id.floatingActionButtonFinishRecording);
        floatingActionButtonCancelRecording = view.findViewById(R.id.floatingActionButtonCancelRecording);
        chronometerRecord = view.findViewById(R.id.chronometerRecord);
        lottieAnimationViewVoice = view.findViewById(R.id.lottieAnimationViewVoice);
    }

    private void setListeners() {
        floatingActionButtonStartRecording.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                if (ContextCompat.checkSelfPermission(context,
                        Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED && ContextCompat.checkSelfPermission(context,
                        Manifest.permission.RECORD_AUDIO) == PackageManager.PERMISSION_GRANTED) {
                    switch (recordingStatus) {
                        case 0:
                            startRecording();
                            break;
                        case 1:
                            if (Build.VERSION.SDK_INT >= 24) {
                                pauseRecording();
                            } else {
                                finishRecording();
                            }
                            break;
                        case 2:
                            resumeRecording();
                        case 3:
                            break;
                    }
                } else {
                    askPermissions();
                }
            }
        });
        floatingActionButtonFinishRecording.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("SetTextI18n")
            @Override
            public void onClick(View view) {
                if (recordingStatus == 1 || recordingStatus == 2) {
                    finishRecording();
                } else {
                    Toast.makeText(getActivity(), getString(R.string.not_recording), Toast.LENGTH_SHORT).show();
                }
            }
        });
        floatingActionButtonCancelRecording.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("SetTextI18n")
            @Override
            public void onClick(View view) {
                if (recordingStatus == 1 || recordingStatus == 2) {
                    cancelRecording();
                } else {
                    Toast.makeText(getActivity(), getString(R.string.not_recording), Toast.LENGTH_SHORT).show();
                }
            }
        });
        chronometerRecord.setOnChronometerTickListener(new Chronometer.OnChronometerTickListener() {
            @Override
            public void onChronometerTick(Chronometer chronometer) {
                long time = SystemClock.elapsedRealtime() - chronometer.getBase();
                int h = (int) (time / 3600000);
                int m = (int) (time - h * 3600000) / 60000;
                int s = (int) (time - h * 3600000 - m * 60000) / 1000;
                String t = (h < 10 ? "0" + h : h) + ":" + (m < 10 ? "0" + m : m) + ":" + (s < 10 ? "0" + s : s);
                chronometer.setText(t);
            }
        });
    }

    @SuppressLint("SetTextI18n")
    private void startRecording() {
        String basePath = Environment.getExternalStorageDirectory().toString();
        String date = getCurrentDateFormatted();
        String myDirectory = "Voice Recorder";
        fileName = getString(R.string.recording_file) + date;
        fileName = fileName.replace(" ", "");
        fileName = fileName.replace("|", "");
        fileName = fileName + ".mp3";
        outPutFilePath = basePath + File.separator + myDirectory + File.separator + fileName;
        String filePath = basePath + File.separator + myDirectory;
        File newFolder = new File(filePath);
        if (!newFolder.exists()) {
            boolean createFolder = newFolder.mkdirs();
            if (createFolder) {
                Log.d("VOICE_RECORDER", "Created folder successfully!");
            }
        }
        recordingStatus = 1;
        mediaRecorder = new MediaRecorder();
        if (Build.VERSION.SDK_INT >= 24) {
            floatingActionButtonStartRecording.setImageDrawable(ResourcesCompat.getDrawable(getResources(), R.drawable.ic_pause_orange, null));
        } else {
            floatingActionButtonStartRecording.setImageDrawable(ResourcesCompat.getDrawable(getResources(), R.drawable.ic_stop_red, null));
        }
        textViewInformation.setText(getString(R.string.recording));
        lottieAnimationViewVoice.playAnimation();
        lottieAnimationViewVoice.setVisibility(View.VISIBLE);
        mediaRecorder.setAudioSource(MediaRecorder.AudioSource.MIC);
        mediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);
        mediaRecorder.setOutputFile(outPutFilePath);
        mediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AAC);
        mediaRecorder.setAudioEncodingBitRate(16 * 44100);
        mediaRecorder.setAudioSamplingRate(44100);
        try {
            mediaRecorder.prepare();
            mediaRecorder.start();
            if (!running) {
                chronometerRecord.setVisibility(View.VISIBLE);
                chronometerRecord.setBase(SystemClock.elapsedRealtime());
                chronometerRecord.start();
                running = true;
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private void pauseRecording() {
        if (Build.VERSION.SDK_INT >= 24) {
            mediaRecorder.pause();
        }
        if (running) {
            chronometerRecord.stop();
            pauseOffset = SystemClock.elapsedRealtime() - chronometerRecord.getBase();
            running = false;
        }
        lottieAnimationViewVoice.cancelAnimation();
        lottieAnimationViewVoice.setFrame(0);
        lottieAnimationViewVoice.setVisibility(View.INVISIBLE);
        recordingStatus = 2;
        floatingActionButtonStartRecording.setImageDrawable(ResourcesCompat.getDrawable(getResources(), R.drawable.ic_play_green, null));
        textViewInformation.setText(getString(R.string.tap_to_resume));
        Toast.makeText(context, getString(R.string.paused), Toast.LENGTH_SHORT).show();
    }

    private void resumeRecording() {
        if (Build.VERSION.SDK_INT >= 24) {
            mediaRecorder.resume();
        }
        chronometerRecord.setBase(SystemClock.elapsedRealtime() - pauseOffset);
        chronometerRecord.start();
        lottieAnimationViewVoice.playAnimation();
        lottieAnimationViewVoice.setVisibility(View.VISIBLE);
        recordingStatus = 1;
        floatingActionButtonStartRecording.setImageDrawable(ResourcesCompat.getDrawable(getResources(), R.drawable.ic_pause_orange, null));
        textViewInformation.setText(getString(R.string.recording));
        Toast.makeText(context, getString(R.string.resume), Toast.LENGTH_SHORT).show();
    }

    @SuppressLint("SetTextI18n")
    private void finishRecording() {
        chronometerRecord.setVisibility(View.INVISIBLE);
        chronometerRecord.stop();
        chronometerRecord.setBase(SystemClock.elapsedRealtime());
        pauseOffset = 0;
        mediaRecorder.stop();
        mediaRecorder = null;
        recordingStatus = 3;
        floatingActionButtonStartRecording.setImageDrawable(ResourcesCompat.getDrawable(getResources(), R.drawable.ic_app, null));
        Toast.makeText(context, getString(R.string.saved) + " " + fileName, Toast.LENGTH_LONG).show();
        textViewInformation.setText(getString(R.string.tap_to_record));
        lottieAnimationViewVoice.cancelAnimation();
        lottieAnimationViewVoice.setFrame(0);
        lottieAnimationViewVoice.setVisibility(View.INVISIBLE);
        recordingStatus = 0;
    }

    @SuppressLint("SetTextI18n")
    private void cancelRecording() {
        chronometerRecord.setVisibility(View.INVISIBLE);
        chronometerRecord.stop();
        chronometerRecord.setBase(SystemClock.elapsedRealtime());
        pauseOffset = 0;
        try {
            mediaRecorder.stop();
        } catch (RuntimeException e) {
            e.printStackTrace();
            mediaRecorder = null;
            mediaRecorder = new MediaRecorder();
        } finally {
            if (mediaRecorder != null) {
                mediaRecorder = null;
            }
        }
        File file = new File(outPutFilePath);
        if (file.exists()) {
            boolean deleted = file.delete();
            if (deleted) {
                Log.d("Voice Recorder", "Deleted file successfully!");
            }
        }
        recordingStatus = 3;
        floatingActionButtonStartRecording.setImageDrawable(ResourcesCompat.getDrawable(getResources(), R.drawable.ic_app, null));
        Toast.makeText(context, getString(R.string.cancelled) + " " + fileName, Toast.LENGTH_LONG).show();
        textViewInformation.setText(getString(R.string.tap_to_record));
        lottieAnimationViewVoice.cancelAnimation();
        lottieAnimationViewVoice.setFrame(0);
        lottieAnimationViewVoice.setVisibility(View.INVISIBLE);
        recordingStatus = 0;
    }

    private String getCurrentDateFormatted() {
        return new SimpleDateFormat("dd-MM-yy|hh:mm:ss", Locale.getDefault()).format(new Date());
    }

    private void askPermissions() {
        if (ContextCompat.checkSelfPermission(context,
                Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED || ContextCompat.checkSelfPermission(context,
                Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) {
            assert getParentFragment() != null;
            requestPermissions(permissions, Constants.RECORD_AUDIO_AND_WRITE_EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
        }
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull final String[] permissions, @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        if (ContextCompat.checkSelfPermission(context,
                Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED && ContextCompat.checkSelfPermission(context,
                Manifest.permission.RECORD_AUDIO) == PackageManager.PERMISSION_GRANTED) {
            Toast.makeText(context, getString(R.string.permission_granted), Toast.LENGTH_SHORT).show();
        } else {
            AlertDialog.Builder builder = new AlertDialog.Builder(context);
            builder.setMessage(getString(R.string.no_read_permission))
                    .setPositiveButton(getString(R.string.ok), new DialogInterface.OnClickListener() {
                        @Override
                        public void onClick(DialogInterface dialogInterface, int i) {
                            dialogInterface.dismiss();
                            if (ContextCompat.checkSelfPermission(context,
                                    Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED || ContextCompat.checkSelfPermission(context,
                                    Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) {
                                requestPermissions(permissions, Constants.RECORD_AUDIO_AND_WRITE_EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
                            }
                        }
                    }).setNegativeButton(getString(R.string.go_to_settings), new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    Intent intent = new Intent();
                    intent.setAction(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
                    Uri uri = Uri.fromParts("package", "com.venomapps.voicerecorder", null);
                    intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
                    intent.setData(uri);
                    context.startActivity(intent);
                    requireActivity().finish();
                }
            });
            builder.create();
            builder.show();
        }
    }
}

播放片段。java:

import android.content.Context;
import android.media.AudioAttributes;
import android.media.AudioManager;
import android.media.MediaPlayer;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.constraintlayout.widget.ConstraintLayout;
import androidx.fragment.app.Fragment;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;

import android.os.Environment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

import com.google.android.material.bottomsheet.BottomSheetBehavior;
import com.venomapps.voicerecorder.Adapters.PlaylistAdapter;
import com.venomapps.voicerecorder.R;

import java.io.File;
import java.io.IOException;

public class PlaylistFragment extends Fragment implements  PlaylistAdapter.onItemListClick {

    private BottomSheetBehavior bottomSheetBehavior;
    private RecyclerView recyclerViewPlaylist;
    private File[] files;
    private PlaylistAdapter playlistAdapter;
    private MediaPlayer mediaPlayer = null;
    private boolean isPlaying = false;
    private File fileToPlay;

    public PlaylistFragment() {
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        getFiles();
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_playlist_item_list, container, false);

        // Set the adapter
        if (view instanceof RecyclerView) {
            Context context = view.getContext();
            RecyclerView recyclerView = (RecyclerView) view;
            LinearLayoutManager linearLayoutManager = new LinearLayoutManager(context);
            recyclerView.setLayoutManager(linearLayoutManager);
        }
        return view;
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        bindUI(view);
        setListeners();
        setAdapter();
    }

    private void bindUI(View view) {
        ConstraintLayout constraintLayoutMediaPlayer = view.findViewById(R.id.constraintLayoutMediaPlayer);
        bottomSheetBehavior = BottomSheetBehavior.from(constraintLayoutMediaPlayer);
        recyclerViewPlaylist = view.findViewById(R.id.recyclerViewPlaylist);
    }

    private void setListeners() {
        bottomSheetBehavior.addBottomSheetCallback(new BottomSheetBehavior.BottomSheetCallback() {
            @Override
            public void onStateChanged(@NonNull View bottomSheet, int newState) {
                if (newState == BottomSheetBehavior.STATE_HIDDEN) {
                    bottomSheetBehavior.setState(BottomSheetBehavior.STATE_COLLAPSED);
                }
            }

            @Override
            public void onSlide(@NonNull View bottomSheet, float slideOffset) {

            }
        });
    }

    private void getFiles() {
        String path = Environment.getExternalStorageDirectory().toString() + File.separator + "Voice Recorder";
        File directory = new File(path);
        files = directory.listFiles();
    }

    private void setAdapter() {
        playlistAdapter = new PlaylistAdapter(files, this);
        recyclerViewPlaylist.setHasFixedSize(true);
        recyclerViewPlaylist.setLayoutManager(new LinearLayoutManager(getContext()));
        recyclerViewPlaylist.setAdapter(playlistAdapter);
    }

    @Override
    public void onClickListener(File file, int position) throws IOException {
        if(isPlaying){
            stopAudio();
            playAudio(fileToPlay);
        }else{
            fileToPlay = file;
            playAudio(fileToPlay);
        }
    }

    private void playAudio(File fileToPlay) {
        mediaPlayer = new MediaPlayer();
        try {
            mediaPlayer.setDataSource(fileToPlay.getAbsolutePath());
            mediaPlayer.prepare();
            mediaPlayer.start();
        }catch (Exception e){
            e.printStackTrace();
        }

        isPlaying = true;
    }

    private void stopAudio(){
        isPlaying = false;
    }
}

-播放适配器。java:

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageButton;
import android.widget.TextView;

import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;

import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.venomapps.voicerecorder.Utils.TimeAgo;
import com.venomapps.voicerecorder.R;

import java.io.File;
import java.io.IOException;

public class PlaylistAdapter extends RecyclerView.Adapter<PlaylistAdapter.PlaylistViewHolder> {

    private static File[] files;
    private TimeAgo timeAgo;
    private Context context;

    private static onItemListClick onItemListClick;

    public PlaylistAdapter(File[] files, onItemListClick onItemListClick) {
        PlaylistAdapter.files = files;
        PlaylistAdapter.onItemListClick = onItemListClick;
    }

    @NonNull
    @Override
    public PlaylistViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.fragment_playlist_item, parent, false);
        context = parent.getContext();
        timeAgo = new TimeAgo();
        return new PlaylistViewHolder(view);
    }

    @Override
    public void onBindViewHolder(@NonNull PlaylistViewHolder holder, int position) {
        holder.textViewPlaylistFileName.setText(files[position].getName());
        holder.textViewPlaylistStats.setText(timeAgo.getTimeAgo(files[position].lastModified(), context));
        if(position == getItemCount() - 1){
            holder.playlistSeparator.setVisibility(View.INVISIBLE);
        }
    }

    @Override
    public int getItemCount() {
        return files.length;
    }

    public static class PlaylistViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
        private final TextView textViewPlaylistFileName;
        private final TextView textViewPlaylistStats;
        private final View playlistSeparator;
        private final FloatingActionButton floatingActionButtonPlaylistPlay;
        private final ImageButton imageButtonPlaylistItem;

        public PlaylistViewHolder(@NonNull View itemView) {
            super(itemView);

            textViewPlaylistFileName = itemView.findViewById(R.id.textViewPlaylistFileName);
            textViewPlaylistStats = itemView.findViewById(R.id.textViewPlaylistStats);
            playlistSeparator = itemView.findViewById(R.id.playlistSeparator);
            floatingActionButtonPlaylistPlay = itemView.findViewById(R.id.floatingActionButtonPlaylistPlay);
            imageButtonPlaylistItem = itemView.findViewById(R.id.imageButtonPlaylistItem);

            floatingActionButtonPlaylistPlay.setOnClickListener(this);
        }

        @Override
        public void onClick(View v) {
            try {
                onItemListClick.onClickListener(files[getAdapterPosition()], getAdapterPosition());
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    public interface onItemListClick{
        void onClickListener(File file, int position) throws IOException;
    }
}

共有1个答案

洪高刚
2023-03-14

首先,我建议您发布完整的错误日志,并且只发布产生问题的代码(而不是整个项目…)

有3种可能会产生您的问题:

  1. 文件问题(路径或文件不存在)

更多信息请参见:https://stackoverflow.com/a/11977292/10952503

 类似资料:
  • 今天,我制作了一个在Android中播放音乐的应用程序。 使用MediaPlayer播放音频文件时失败;它无法播放任何文件音频。此异常引发日志cat,如: E/MediaPlayer:错误(1,-2147483648) 带系统。错误:java。io。IOException:准备失败:状态=0x1 W/System.err:android.media.MediaPlayer.prepare(本机方法

  • 我需要能够在普通的Java项目中播放音频文件(MP3 / Wav)。我更喜欢使用新的JavaFX MediaPlayer而不是JMF。我写了一些代码来测试这一点: 当我运行它时,我得到异常:Toolkit未初始化 我知道这与JavaFX线程有关。我的问题是,我该如何解决这个问题?我是否需要创建一个JavaFX面板来播放正常应用程序后台的一些音频文件,还是有其他方法? 编辑:堆栈跟踪:

  • 本文向大家介绍Android多媒体应用使用MediaPlayer播放音频,包括了Android多媒体应用使用MediaPlayer播放音频的使用技巧和注意事项,需要的朋友参考一下 Android提供了对常用音频和视频格式的支持,它所支持的音频格式有MP3(.mp3)、3GPP(.3gp)、Ogg(.ogg)和WAVE(.ave)等,支持的视频格式有3GPP(.3gp)和MPEG-4(.mp4)等。

  • 本文向大家介绍Android MediaPlayer 播放音频的方式,包括了Android MediaPlayer 播放音频的方式的使用技巧和注意事项,需要的朋友参考一下 主要介绍使用MediaPlayer播放音频的方式。关于MediaPlayer的基础知识,比如状态,可以参考Android MediaPlayer 基础简介。 为了方便表达,定义变量名为mediaPlayer。 MediaPlay

  • 主要内容:本节引言:,1.相关方法详解,2.使用代码示例,3.本节示例代码下载:,本节小结:本节引言: 本节带来的是Android多媒体中的——MediaPlayer,我们可以通过这个API来播放音频和视频 该类是Androd多媒体框架中的一个重要组件,通过该类,我们可以以最小的步骤来获取,解码 和播放音视频。它支持三种不同的媒体来源: 本地资源 内部的URI,比如你可以通过ContentResolver来获取 外部URL(流) 对于Android所支持的的媒体格式列表 对于Androi

  • 问题内容: 我正在制作一个Java应用程序,我需要播放音频。尽管我计划循环播放背景音乐,但我主要播放的是我的大炮射击(它是大炮射击游戏)和弹丸爆炸的小声音文件。我找到了两种不同的方法来实现此目的,但是两种方法都不符合我的要求。 第一种方法实际上是一种方法: 问题是我的整个程序停止运行,直到声音文件完成或至少接近完成。 第二种方法是这样的: 我这里的问题是,每次声音文件提早结束或根本不播放时,这取决