踩完百度首页坑,亲测可用android录像,mediaRecord

本文作者通过两部不同系统版本的手机实测,分享了使用MediaRecord进行Android录像的踩坑经验,强调了权限开启的重要性,并提供了相关布局概述。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

本人两部手机5.1和6.0系统,亲测可用~~~~花了几个小时踩坑,希望大家少走弯路

先上权限,记住开权限

<!--权限-->
<uses-permission android:name="android.permission.RECORD_AUDIO" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-feature android:name="android.hardware.camera" />
这里要记得锁死横屏,不然就要设置角度为90度

<activity
    android:name=".VideoActivity"
    android:configChanges="layoutDirection|screenSize|screenLayout|keyboard|keyboardHidden"
    android:screenOrientation="landscape">
    <intent-filter>
        <action android:name="android.intent.action.MAIN" />
        <category android:name="android.intent.category.LAUNCHER" />
    </intent-filter>
</activity>
下面是正式的代码

布局:

<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    >
    <SurfaceView
        android:id="@+id/video_surface"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
        <ToggleButton
            android:id="@+id/start_btn"
            android:layout_width="60dp"
            android:layout_height="60dp"
            />
</FrameLayout>
活动:

/**
 * 2017/4/28 17:17
 * Created by jiangchen
 * 作用:视频录制Activity
 */
public class VideoActivity extends Activity{
    private SurfaceView videoSurface;       //显示
    private ToggleButton startBtn;          //开始结束按钮
    private MediaRecorder mediarecorder;    // 录制视频的类
    SurfaceHolder mholder;                  //holder
    Camera camera;                          //camera

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //去标题栏
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        setContentView(R.layout.activity_video);
        //实例化控件
        videoSurface = (SurfaceView) findViewById(R.id.video_surface);
        startBtn = (ToggleButton) findViewById(R.id.start_btn);
        mholder = videoSurface.getHolder();     // 取得holder
        mholder.setFixedSize(1280,720);
        mholder.addCallback(surfaceCallback);   // holder加入回调接口
        // setType必须设置,要不出错.设置缓冲类型
        mholder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);

        startBtn.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked){
                    try {
                        //prepare()必须在start之前
                        /**
                        *2017/4/29 15:00
                        *Created by jiangchen
                        *官方API:
                         * A common case of using MediaRecorder to record audio works as follows:

                         MediaRecorder recorder = new MediaRecorder();
                         recorder.setAudioSource(MediaRecorder.AudioSource.MIC);
                         recorder.setOutputFormat(MediaRecorder.OutputFormat.THREE_GPP);
                         recorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB);
                         recorder.setOutputFile(PATH_NAME);
                         recorder.prepare();
                         recorder.start();   // Recording is now started
                         ...
                         recorder.stop();
                         recorder.reset();   // You can reuse the object by going back to setAudioSource() step
                         recorder.release(); // Now the object cannot be reused

                         */
                        /**prepare()
                         * This method must be called after setting up
                         * the desired audio and video sources, encoders, file format, etc., but before start()
                         * 必须在设置资源、编码方式、路径之后,必须在start方法之前
                         */
                        mediarecorder.prepare();
                        mediarecorder.start();
                    } catch (Exception e) {
                        Log.e("jiangchen", "onCheckedChanged: "+e.toString() );
                    }
                }else {
                    mediarecorder.stop();
                    mediarecorder.release();
                    mediarecorder=null;
                    mholder.removeCallback(surfaceCallback);finish();
                }
            }
        });
    }
    /**
     * SurfaceHolder回调函数。重写SurfaceHolder.Callback接口的surfaceCreated、surfaceChanged、surfaceDestroyed方法。
     */
    SurfaceHolder.Callback surfaceCallback = new SurfaceHolder.Callback() {

        public void surfaceCreated(SurfaceHolder holder) {
            mediarecorder = new MediaRecorder();
            //这设置之后不容易崩
            mediarecorder.setOnErrorListener(null);
            mediarecorder.setOnInfoListener(null);
            mediarecorder.setPreviewDisplay(null);
            camera = Camera.open();                 //打开摄像头
            Log.e("--------", "surfaceCreated");
            try {
//              camera.setDisplayOrientation(90);   //设置camera预览的角度,因为默认图片是倾斜90度的
                camera.setPreviewDisplay(holder);   //设置holder主要是用于surfaceView的图片的实时预览,以及获取图片等功能
                Camera.Parameters parameters = camera.getParameters();
                camera.setParameters(parameters);
                camera.startPreview();                  //开始预览
                camera.unlock();
            } catch (IOException e) {
                camera.release();                   //释放
            }
            mediarecorder.setCamera(camera);
            mediarecorder.reset();
            mediarecorder.setPreviewDisplay(holder.getSurface());
            // 设置录制视频源为Camera(相机)
            mediarecorder.setAudioSource(MediaRecorder.AudioSource.MIC);
            mediarecorder.setVideoSource(MediaRecorder.VideoSource.DEFAULT);
            // 设置录制完成后视频的封装格式THREE_GPP为3gp.MPEG_4为mp4
            mediarecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);
            // 设置录制的视频编码
            mediarecorder.setVideoEncoder(MediaRecorder.VideoEncoder.MPEG_4_SP);
            mediarecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB);
            // 设置视频录制的分辨率。必须放在设置编码和格式的后面,否则报错,而且这个值要适配
            //手机,不然也会在后面stop方法报错!
            mediarecorder.setVideoSize(1280,720);
            // 设置录制的视频帧率。必须放在设置编码和格式的后面,否则报错,这样设置变清晰
            mediarecorder.setVideoEncodingBitRate(5*1024*1024);
            mediarecorder.setOutputFile(Environment.getExternalStorageDirectory().getAbsolutePath()+
                    File.separator +"VisitInsData" + File.separator + "video.mp4");
        }

        public void surfaceChanged(SurfaceHolder holder, int format, int width,
                                   int height) {

        }

        public void surfaceDestroyed(SurfaceHolder holder) {
            //释放资源
            camera.lock();
            camera.stopPreview();   // stop preview
            camera.release();       // Release camera resources
            camera = null;
            mediarecorder.release();
            mediarecorder=null;
        }
    };
@Override
protected void onStop() {
    super.onStop();
//退出释放资源 if (camera!=null){ camera.release(); camera=null; } if (mediarecorder!=null){ mediarecorder.release(); mediarecorder=null; } if (mholder!=null){ mholder.removeCallback(surfaceCallback); } }}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值