2012-07-28 91 views
0

我正在研究一个应用程序,需要在拍摄后访问图片中的像素数组。主要活动如下。我拥有大量的Java体验,但过去在屏幕上显示图像的经历非常有限。我看到字节数组传递给图片回调方法,但我不知道它是如何格式化的。如何获取包含捕获图像中的RGB分量的像素阵列?我试图通过堆栈溢出论坛找到这个,但是我得到了几百页的结果,并且只搜索了前10个左右,所以我很抱歉,如果这已经被问到,我只是没有看到它。从使用摄像头拍摄的图像中检索像素阵列

public class ConverterActivity extends Activity 
{ 
    private Camera mCamera; 
    private CameraPreview mPreview; 
private PictureCallback mPicture = new PictureCallback() { 
private String TAG; 
@Override 
public void onPictureTaken(byte[] data, Camera camera) { 
File pictureFile = getOutputMediaFile(MEDIA_TYPE_IMAGE); 
if (pictureFile == null){ 
// Log.d(TAG, "Error creating media file, check storage permissions: " + 
// e.getMessage()); 
return; 
} 
try { 
FileOutputStream fos = new FileOutputStream(pictureFile); 
fos.write(data); 
fos.close(); 
} catch (FileNotFoundException e) { 
Log.d(TAG, "File not found: " + e.getMessage()); 
} catch (IOException e) { 
Log.d(TAG, "Error accessing file: " + e.getMessage()); 
} 
} 
}; 

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

// Add a listener to the Capture button 
Button captureButton = (Button) findViewById(R.id.button_capture); 
captureButton.setOnClickListener(
new View.OnClickListener() { 
@Override 
public void onClick(View v) { 
// get an image from the camera 
mCamera.takePicture(null, null, mPicture); 
} 
} 
); 
     // Create an instance of Camera 
     mCamera = Camera.open(this.getBackCamera()); 
     // Create our Preview view and set it as the content of our activity. 
     mPreview = new CameraPreview(this, mCamera); 
     FrameLayout preview = (FrameLayout) findViewById(R.id.camera_preview); 
     preview.addView(mPreview); 
} 
@Override 
    protected void onPause() 
    { 
     super.onPause(); 
     releaseCamera();    // release the camera immediately on pause event 
    } 
    private void releaseCamera(){ 
     if (mCamera != null){ 
      mCamera.release();  // release the camera for other applications 
      mCamera = null; 
     } 
    } 
public static final int MEDIA_TYPE_IMAGE = 1; 
public static final int MEDIA_TYPE_VIDEO = 2; 
/** Create a file Uri for saving an image or video */ 
private static Uri getOutputMediaFileUri(int type){ 
return Uri.fromFile(getOutputMediaFile(type)); 
} 
/** Create a File for saving an image or video */ 
private static File getOutputMediaFile(int type){ 
// To be safe, you should check that the SDCard is mounted 
// using Environment.getExternalStorageState() before doing this. 
File mediaStorageDir = new File(Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_PICTURES), "MyCameraApp"); 
// This location works best if you want the created images to be shared 
// between applications and persist after your app has been uninstalled. 
// Create the storage directory if it does not exist 
if (! mediaStorageDir.exists()){ 
if (! mediaStorageDir.mkdirs()){ 
Log.d("MyCameraApp", "failed to create directory"); 
return null; 
} 
} 
// Create a media file name 
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date()); 
File mediaFile; 
if (type == MEDIA_TYPE_IMAGE){ 
mediaFile = new File(mediaStorageDir.getPath() + File.separator + 
"IMG_"+ timeStamp + ".jpg"); 
} else if(type == MEDIA_TYPE_VIDEO) { 
mediaFile = new File(mediaStorageDir.getPath() + File.separator + 
"VID_"+ timeStamp + ".mp4"); 
} else { 
return null; 
} 
return mediaFile; 
} 
public int getBackCamera() 
{ 
int numCameras = Camera.getNumberOfCameras(); 
CameraInfo cInfo = new CameraInfo(); 
for (int i = 0; i < numCameras; i++) 
{ 
Camera.getCameraInfo(i, cInfo); 
if (cInfo.facing == CameraInfo.CAMERA_FACING_BACK) 
{ 
return i; 
} 
} 
return -1; 
} 
} 

回答

0

如果使用这样的代码拍照:

imgFile = new File(Environment.getExternalStorageDirectory() + "/somefolder/" + name + ".jpg"); 

    String fileName = imgFile.getAbsolutePath(); 

    Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); 
    intent.putExtra(android.provider.MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(fileName))); 

    startActivityForResult(intent, REQUEST_FROM_CAMERA); 

那么你应该可以,当你得到的结果,从这一意图回来,用这样的代码来访问位图

if (imgFile.exists()) { 
     String fileName = file.getAbsolutePath(); 
     BitmapFactory.Options opts = new BitmapFactory.Options(); 
     Bitmap bm; 

     opts.inJustDecodeBounds = false; 

     bm = BitmapFactory.decodeFile(fileName, opts); 
     return bm; 
    } 
    else return null; 

然后你可以使用bitmapfactory工具,如压缩到流,然后 转换为byte []

ByteArrayOutputStream stream = new ByteArrayOutputStream(); 
    bm.compress(Bitmap.CompressFormat.JPEG, 100, stream); // 100 = max quality 
    byte[] byteArray = stream.toByteArray(); 
+0

谢谢,虽然我有几个问题,但我对android和图像很不熟悉。首先是什么代码替换?只是拍照并保存?还是取代了相机预览?那么字节数组是如何表示像素的?如何使用您提供的内容检索特定像素的RGB分量? – 2012-07-29 03:23:40

+0

您还必须使用bitmapfactory设置组件类型。 options.inPreferredConfig = Bitmap.Config.RGB_565将其设置为每个组件2和3个像素,而ARGB_8888将其设置为alpha,红色,绿色和蓝色中的每个像素8位。我还没有尝试过,但我想象你可以索引到组件的这个字节数组,然后将x和y计算为单个整数 – Martin 2012-07-30 03:57:27

+0

非常感谢。我很抱歉不得不提出另一个问题,但是你是否介意在最后一句中澄清你的意思? “我没有尝试过,但我想象你可以索引到组件上的字节数组,然后将x和y计算为单个整数”我不明白你是通过索引到组件上的字节数组还是什么你的意思是“将x和y计算成单个整数” – 2012-07-30 04:12:55