我試圖創建一個程序,它直接從Camera2預覽處理圖像,並且在實際處理傳入圖像時,我一直遇到問題。BitmapFactory.getByteArray只適用於字節數組來自存儲器
在我OnImageAvailableListener.onImageAvailable()回調,我發現了一個ImageReader
對象,從中我acquireNextImage()和傳遞Image對象到我的助手功能。從那裏,我將它轉換成一個字節數組,並嘗試進行處理。相反,每次我到達將其轉換爲Bitmap
的部分時,BitmapFactory.getByteArray
都會返回null,即使字節數組的格式是正確格式的JPEG。
private final ImageReader.OnImageAvailableListener mOnImageAvailableListener
= new ImageReader.OnImageAvailableListener() {
@Override
public void onImageAvailable(ImageReader imageReader) {
Image image = imageReader.acquireNextImage();
ProcessBarcode(image);
image.close();
}
};
private void ProcessBarcode(Image image) {
ByteBuffer buffer = image.getPlanes()[0].getBuffer();
int bufferSize = buffer.remaining();
byte[] bytes = new byte[bufferSize];
buffer.get(bytes);
FileOutputStream output = null;
try {
output = new FileOutputStream(mFile);
output.write(bytes);
output.close();
} catch (IOException e) {
// Do something clever
}
// This call FAILS
//Bitmap b = BitmapFactory.decodeByteArray(bytes, 0, buffer.remaining(), o);
// But this call WORKS?
Bitmap b = BitmapFactory.decodeFile(mFile.getAbsolutePath());
detector = new BarcodeDetector.Builder(getActivity())
.setBarcodeFormats(Barcode.EAN_13 | Barcode.ISBN)
.build();
if (b != null) {
Frame isbnFrame = new Frame.Builder().setBitmap(b).build();
SparseArray<Barcode> barcodes = detector.detect(isbnFrame);
if (barcodes.size() != 0) {
Log.d("Barcode decoded: ",barcodes.valueAt(0).displayValue);
}
else {
Log.d(TAG, "No barcode detected");
}
}
else {
Log.d(TAG, "No bitmap detected");
}
}
的ImageReader
設置如下:
mImageReader = ImageReader.newInstance(largest.getWidth(), largest.getHeight(), ImageFormat.JPEG, 2);
mImageReader.setOnImageAvailableListener(mOnImageAvailableListener, mBackgroundHandler);
基本上我看到的是,如果我直接使用字節數組,而不先保存到內部存儲器,相機預覽速度快,瞬間,儘管Bitmap
總是爲空,所以我實際上沒有執行任何處理。如果我將字節數組保存到內存中,那麼我可能會得到2-3fps,但處理按我的意圖工作。
謝謝艾迪!直接獲取'bytes.length'而不是'buffer.remaining()'解決了這個問題。我仍然有可怕的掃描速度,但我認爲這是解碼條形碼的問題,而不是與捕獲圖像有關的任何事情。 – Jared
如果你想要高幀率,不要捕捉JPEG - 通常這些速度很慢(一般爲1-3fps,最好爲10fps)。改爲使用ImageFormat.YUV_420_888,至少在預覽分辨率下保證以30fps運行。您也應該避免爲每個圖像創建一個新的條形碼掃描器;我假設你可以重複使用多次。 –
我發現了另一個涉及這個主題的線程(雖然不是我明顯的錯誤),並且它也提出了YUV_420_888格式,所以我很快就會切換到這個。我確實在預覽模式下修正了幀速率,通過過濾掉相機尚未獲取AF和AE鎖定時拍攝的幀。所以現在我正在顯示所有的預覽幀,但是隻有在我對攝像機進行了正面鎖定之後才進行條形碼掃描。現在已經接近實時。 – Jared