【Android應用開發技術:媒體開發】錄影

來源:互聯網
上載者:User

標籤:

郭孝星
微博:郭孝星的新浪微博
郵箱:[email protected]
部落格:http://blog.csdn.net/allenwells
Github:https://github.com/AllenWells

一 啟用相機1.1 請求相機許可權
<manifest ... >    <uses-feature android:name="android.hardware.camera"                  android:required="true" />    ...</manifest>

如果我們的App使用相機,但相機並不是應用的正常運行所必不可少的組件,可以將android:required 設定為false。這樣的話,Google Play也會允許沒有相機的裝置下載該應用。當然在有必要在使用相機之前通過調用以下方法:

hasSystemFeature(PackageManager.FEATURE_CAMERA);

來檢查裝置上是否有相機。如果沒有,我們應該禁用和相機相關的功能。

1.2 建立Intent對象

利用一個描述了做什麼的Intent對象,Android可以將某些執行任務委託給其他應用。整個過程包含三部分:

  • Intent本身
  • 一個函數調用來啟動外部的 Activity
  • 當焦點返回到你的Activity時,處理返回映像資料的代碼。

舉例

發送一個Intent來錄製視頻

static final int REQUEST_VIDEO_CAPTURE = 1;private void dispatchTakeVideoIntent() {    Intent takeVideoIntent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);//注意在調用startActivityForResult()方法之前,先調用resolveActivity(),這個方法會返回能處理該Intent的第一個Activity,即即檢查有沒有能處理這個Intent的Activity。執行這個檢查是必要的,因為如果你調用startActivityForResult()時,沒有應用能處理該Intent,應用將會崩潰。所以只要返回結果不為null,使用該Intent就是安全的。    if (takeVideoIntent.resolveActivity(getPackageManager()) != null)     {        startActivityForResult(takeVideoIntent, REQUEST_VIDEO_CAPTURE);    }}
1.3 查看視頻

Android的相機程式會把指向視頻儲存地址的Uri添加到Intent中,並傳送給onActivityResult())方法。

舉例

擷取該視頻並顯示到一個VideoView當中。

@Overrideprotected void onActivityResult(int requestCode, int resultCode, Intent data) {    if (requestCode == REQUEST_VIDEO_CAPTURE && resultCode == RESULT_OK) {        Uri videoUri = intent.getData();        mVideoView.setVideoURI(videoUri);    }}
二 控制相機2.1 開啟相機對象

擷取一個Camera對象是直接控制相機的第一步。正如Android內建的相機程式一樣,訪問相機推薦的方式是在onCreate())方法裡面另起一個線程來開啟相機。這種辦法可以避免因為啟動時間較長導致UI線程被阻塞。還有一種更好的方法,可以把開啟相機的操作延遲到onResume())方法裡面去執行,這樣使得代碼更容易重用,並且保持控制流程程簡單。

private boolean safeCameraOpen(int id) {    boolean qOpened = false;    try {        releaseCameraAndPreview();        mCamera = Camera.open(id);        qOpened = (mCamera != null);    } catch (Exception e) {        Log.e(getString(R.string.app_name), "failed to open Camera");        e.printStackTrace();    }    return qOpened;    }private void releaseCameraAndPreview() {    mPreview.setCamera(null);    if (mCamera != null) {        mCamera.release();        mCamera = null;    }}
2.2 建立相機預覽介面

拍照通常需要向使用者提供一個預覽介面來顯示待拍攝的事物,我們可以使用SurfaceView來展現照相機採集的映像。

//為了顯示一個預覽介面,我們需要建立一個Preview類。這個類需要實現 android.view.SurfaceHolder.Callback介面,用這個介面把相機硬體擷取的資料傳遞給程式,該Preview類必須在映像即時預覽開始之前傳遞給Camera對象。class Preview extends ViewGroup implements SurfaceHolder.Callback {    SurfaceView mSurfaceView;    SurfaceHolder mHolder;    Preview(Context context) {        super(context);        mSurfaceView = new SurfaceView(context);        addView(mSurfaceView);        // Install a SurfaceHolder.Callback so we get notified when the        // underlying surface is created and destroyed.        mHolder = mSurfaceView.getHolder();        mHolder.addCallback(this);        mHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);    }...}

Preview建立後,接下來我們就可以設定和啟動Preview。Camera執行個體與它相關的Preview必須以特定的順序來建立,其中Camera對象首先被建立。

舉例

將初始化Canera的動作封裝起來

public void setCamera(Camera camera) {    if (mCamera == camera) { return; }    stopPreviewAndFreeCamera();    mCamera = camera;    if (mCamera != null) {        List<Size> localSizes = mCamera.getParameters().getSupportedPreviewSizes();        mSupportedPreviewSizes = localSizes;        requestLayout();        try {            mCamera.setPreviewDisplay(mHolder);        } catch (IOException e) {            e.printStackTrace();        }        // Important: Call startPreview() to start updating the preview        // surface. Preview must be started before you can take a picture.        mCamera.startPreview();    }}
2.3 修改相機設定

相機設定可以改變拍照的方式。

舉例

改變預覽大小,如下所示:

public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {    // Now that the size is known, set up the camera parameters and begin    // the preview.    Camera.Parameters parameters = mCamera.getParameters();    parameters.setPreviewSize(mPreviewSize.width, mPreviewSize.height);    requestLayout();    mCamera.setParameters(parameters);    // Important: Call startPreview() to start updating the preview surface.    // Preview must be started before you can take a picture.    mCamera.startPreview();}

大多數相機程式會鎖定預覽為橫屏狀態,因為該方向是相機感應器的自然方向。當然這一設定並不會阻止拍豎屏的照片,因為裝置的方向資訊會被記錄在EXIF頭中。setCameraDisplayOrientation())方法可以讓你在不影響照片拍攝過程的情況下,改變預覽的方向。然而,對於Android API Level 14及以下版本的系統,在改變方向之前,必須先停止預覽,然後再去重啟它。

2.4 拍攝照片

預覽開始之後,可以進行照片的拍攝。

拍攝照片:調用Camera.takePicture(),將建立的Camera.PictureCallback與Camera.ShutterCallback對象傳遞到該方法內。

連續拍攝照片:調用Camera.takePicture(),建立一個Camera.PreviewCallback並實現onPreviewFrame()方法。我們可以拍攝選中的預覽幀,或是為調用takePicture())建立一個延遲。

在拍攝好圖片後,你必須在使用者拍下一張圖片之前重啟預覽。

舉例

利用快門來實現重啟,如下所示:

@Overridepublic void onClick(View v) {    switch(mPreviewState) {    case K_STATE_FROZEN:        mCamera.startPreview();        mPreviewState = K_STATE_PREVIEW;        break;    default:        mCamera.takePicture( null, rawCallback, null);        mPreviewState = K_STATE_BUSY;    } // switch    shutterBtnConfig();}
2.5 停止預覽並釋放相機

當程式使用相機完畢後,有必要做清理的動作。特別地,必須釋放Camera對象,不然可能會引起其他應用崩潰,包括我們自己應用的新執行個體。在預覽的Surface被銷毀之後,可以做停止預覽並釋放相機的動作。

public void surfaceDestroyed(SurfaceHolder holder) {    // Surface will be destroyed when we return, so stop the preview.    if (mCamera != null) {        // Call stopPreview() to stop updating the preview surface.        mCamera.stopPreview();    }}/** * When this function returns, mCamera will be null. */private void stopPreviewAndFreeCamera() {    if (mCamera != null) {        // Call stopPreview() to stop updating the preview surface.        mCamera.stopPreview();        // Important: Call release() to release the camera for use by other        // applications. Applications should release the camera immediately        // during onPause() and re-open() it during onResume()).        mCamera.release();        mCamera = null;    }}

著作權聲明:本文為博主原創文章,未經博主允許不得轉載。

【Android應用開發技術:媒體開發】錄影

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.