android previewframe-从camera preview获取数据流问题求教!

问题描述

从camera preview获取数据流问题求教!

本人android开发新人,以下是我为了从预览数据流抓取图片并存储而编写的代码。网上说“从camera读取到的预览(preview)图像流一定要输出到一个可见的(Visible)SurfaceView上,然后通过Camera.PreviewCallback的public void onPreviewFrame(byte[] data, Camera camera)函数来获得图像帧数据的拷贝。”那么显示在SurfaceView上的数据流还是完整的吧,不会出现预览停顿的现象吧?为什么我的程序运行之后,预览一闪而过,然后程序重启,如此反复三遍,报出进程意外停止呢?而且也没有保存到图像。这个程序会以什么频率保存图片啊?onPreviewFrame(byte[] data, Camera camera)是每一帧都保存吗?如何控制保存频率?
求大神细心讲解,在线求教!或者QQ:851391489,隐身状态。拜谢!

package com.android.silentcamera;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.util.Iterator;
import java.util.List;
import java.util.UUID;

import android.app.Activity;
import android.content.ContentValues;
import android.content.Context;
import android.content.res.Configuration;
import android.graphics.Bitmap;
import android.graphics.Bitmap.CompressFormat;
import android.hardware.Camera;
import android.hardware.Camera.CameraInfo;
import android.hardware.Camera.PreviewCallback;
import android.media.AudioManager;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.provider.MediaStore.Images.Media;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceHolder.Callback;
import android.view.SurfaceView;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;

public class SilentCameraActivity extends Activity
implements Camera.PreviewCallback, SurfaceHolder.Callback
{

SurfaceView mSurfaceView;
SurfaceHolder mSurfaceHolder;
Camera mCamera;

public void onCreate(Bundle savedInstanceState)
{
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main); 

    mSurfaceView = (SurfaceView) this.findViewById(R.id.surfaceview);
    mSurfaceHolder = mSurfaceView.getHolder();
    mSurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
    mSurfaceHolder.addCallback(this);
}

@Override
public void surfaceDestroyed(SurfaceHolder holder) {
    // TODO Auto-generated method stub
    mCamera.stopPreview();
    mCamera.release();
}

@Override
public void surfaceCreated(SurfaceHolder holder) {
    // TODO Auto-generated method stub
    //打开前置摄像头
    mCamera = Camera.open(CameraInfo.CAMERA_FACING_FRONT);

    //开始预览
    try
    {
        //设置哪个surfaceView显示图片
        mCamera.setPreviewDisplay(mSurfaceHolder);
    }
    catch (IOException e)
    {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

    //设置预览帧的接口,就是通过这个接口,我们来获得预览帧的数据的
    mCamera.setPreviewCallback(SilentCameraActivity.this);
    mCamera.startPreview();
}

@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width,
        int height) {
    // TODO Auto-generated method stub
    mCamera.startPreview();
}

    //拍照+退出
    public void onPreviewFrame(byte[] data, Camera camera)
    {
        int w = camera.getParameters().getPreviewSize().width;
        int h = camera.getParameters().getPreviewSize().height;
        save(w,h,data);
        finish();
    } 

    static public void decodeYUV420SP(int[] rgb, byte[] yuv420sp, int width, int height) {
        final int frameSize = width * height;

        for (int j = 0, yp = 0; j < height; j++) {
        int uvp = frameSize + (j >> 1) * width, u = 0, v = 0;
        for (int i = 0; i < width; i++, yp++) {
            int y = (0xff & ((int) yuv420sp[yp])) - 16;
            if (y < 0) y = 0;
            if ((i & 1) == 0) {
                v = (0xff & yuv420sp[uvp++]) - 128;
                u = (0xff & yuv420sp[uvp++]) - 128;
            }

            int y1192 = 1192 * y;
            int r = (y1192 + 1634 * v);
            int g = (y1192 - 833 * v - 400 * u);
            int b = (y1192 + 2066 * u);

            if (r < 0) r = 0; else if (r > 262143) r = 262143;
            if (g < 0) g = 0; else if (g > 262143) g = 262143;
            if (b < 0) b = 0; else if (b > 262143) b = 262143;

            rgb[yp] = 0xff000000 | ((r << 6) & 0xff0000) | ((g >> 2) & 0xff00) | ((b >> 10) & 0xff);
        }
    }
}

    //保存
    public void save(int w,int h,byte[] data){
        //预览编码为YUV420SP的视频流,需转换为RGB编码
        int[] RGBData = new int[w* h];
        byte[] mYUVData = new byte[data.length]; 

        System.arraycopy(data,0, mYUVData, 0,data.length);
        decodeYUV420SP(RGBData,mYUVData,w,h);

        //图片保存到sdcard
        final Bitmap bitmap = Bitmap.createBitmap(w,h, Bitmap.Config.ARGB_8888);
        try
        {
            FileOutputStream outputStream = new FileOutputStream(Environment.getExternalStorageDirectory().getPath() + UUID.randomUUID() + ".png");
            bitmap.compress(CompressFormat.PNG, 50, outputStream);
            outputStream.close();
        }
        catch(Exception e)
        {
            e.printStackTrace();
        }
    }

}

解决方案

楼主请问你的视频流的数据可以获取的到吗?

解决方案二:

请问楼主,上面的程序中 final Bitmap bitmap = Bitmap.createBitmap(w,h, Bitmap.Config.ARGB_8888); 在try{}块里, bitmap.compress(CompressFormat.PNG, 50, outputStream); 并没有保存图像的数据,请问该如何解决?

解决方案三:

请问楼主,上面的程序中 final Bitmap bitmap = Bitmap.createBitmap(w,h, Bitmap.Config.ARGB_8888); 在try{}块里, bitmap.compress(CompressFormat.PNG, 50, outputStream); 并没有保存图像的数据,请问该如何解决?

解决方案四:

请问楼主,上面的程序中 final Bitmap bitmap = Bitmap.createBitmap(w,h, Bitmap.Config.ARGB_8888); 在try{}块里, bitmap.compress(CompressFormat.PNG, 50, outputStream); 并没有保存图像的数据,请问该如何解决?

解决方案五:

请问楼主,上面的程序中 final Bitmap bitmap = Bitmap.createBitmap(w,h, Bitmap.Config.ARGB_8888); 在try{}块里, bitmap.compress(CompressFormat.PNG, 50, outputStream); 并没有保存图像的数据,请问该如何解决?

解决方案六:

http://blog.chinaunix.net/uid-26941022-id-3996501.html

时间: 2024-10-31 16:56:12

android previewframe-从camera preview获取数据流问题求教!的相关文章

Android上使用camera拍照,把获取的照片上传到远程服务器

使用Java上传文件 从Apache Software Foundation下载HttpClient 4.3.4. 在工程中添加下面的jar包: 参考sample,写一个简单的上传: ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 public static void main(String[] args) throws Exception {         // TOD

Android自定义照相机Camera出现黑屏的解决方法_Android

本文实例讲述了Android自定义照相机Camera出现黑屏的解决方法.分享给大家供大家参考,具体如下: 对于一些手机,像HTC,当自定义Camera时,调用Camera.Parameters的 parameters.setPreviewSize(width, height)方法时,如果width和height为奇数情况下,则会出现黑屏现象,解决办法可参考SDK提供的ApiDemos中关于Camera的 例子: List<Size> sizes = parameters.getSupporte

Android中使用Camera类编写手机拍照App的实例教程

Camera是Android摄像头硬件的相机类,位于硬件包"android.hardware.Camera"下.它主要用于摄像头捕获图片.启动/停止预览图片.拍照.获取视频帧等,它是设备本地的服务,负责管理设备上的摄像头硬件. Camera既然用于管理设备上的摄像头硬件,那么它也为开发人员提供了相应的方法,并且这些方法大部分都是native的,用C++在底层实现,下面简单介绍一下Camera的一些方法: static Camera open():打开Camera,返回一个Camera实

Android编程调用Camera和相册功能详解

本文实例讲述了Android编程调用Camera和相册功能.分享给大家供大家参考,具体如下: xml: <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:orientation="

ASP.Net Post方式获取数据流的一种简单写法

  这篇文章主要介绍了ASP.Net Post方式获取数据流的一种简单写法,本文直接给出代码实例,需要的朋友可以参考下 最近在弄一些第三方的平台,经常调用第三方的接口实现某些特定的功能 在实现的同时基本上都需要本地的数据经过服务器在Request到第三方的服务器中处理,再返回相应的数据结构体:json/xml 以下是我总结的一个小方法,请农友们笑纳: ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27

Android开发中MotionEvent坐标获取方法分析_Android

本文实例讲述了Android开发中MotionEvent坐标获取方法.分享给大家供大家参考,具体如下: Android MotionEvent中getX()与getRawX()都是获取屏幕坐标(横),但二者又有区别getX()           :   是获取相对当前控件(View)的坐标 getRawX()   :   是获取相对显示屏幕左上角的坐标 演示示例代码 Java代码: public class MainActivity extends Activity implements On

android-小白 在做Android新闻端 用json获取网页数据 出现如下图的报错 不知道怎么改

问题描述 小白 在做Android新闻端 用json获取网页数据 出现如下图的报错 不知道怎么改 !求告知 怎么改!可以看这个http://ask.csdn.net/questions/232048 private Handler getNewsHandler = new Handler(){ public void handleMessage(android.os.Message msg) { String jsonData = (String) msg.obj; System.out.pri

Android下 自定义Camera类如何绑定多个SurfaceView?

问题描述 Android下 自定义Camera类如何绑定多个SurfaceView? 本人正在做一个需求,需要动态地将系统相机的色彩效果显示出来,因此想要能够在多个SurfaceView中显示不同的色彩效果预览界面.各位大大如果有思路有想法还请多多赐教~

android-请教一个Android的从网络上获取数据的问题

问题描述 请教一个Android的从网络上获取数据的问题 Android 从网络上获取数据 跟安卓系统有关系吗,,,,用Android5.0以上的系统的手机请求到的数据跟5.0以下系统的手机请求到的数据不一样.(get请求) Android5,0以上的系统请求到的数据:{ "wegInstLt": [ { "billTypeCode": "0", "channelId": 530, "channelKind"