簡體   English   中英

如何使用灰度像素值從位圖創建 ByteBuffer?

[英]How to create a ByteBuffer from Bitmap using grayscale pixel value?

我正在嘗試在我的 android 應用程序中使用tflite模型。 當我必須從位圖創建一個 ByteBuffer 並將其用作模型的輸入時,就會出現問題。

問題:位圖是 ARGB_8888(32 位)而我需要(8 位)灰度圖像。

Bitmap轉ByteBuffer的方法:

mImgData = ByteBuffer
                .allocateDirect(4 * 28 * 28 * 1);

private void convertBitmapToByteBuffer(Bitmap bitmap) throws NullPointerException {
    if (mImgData == null) {
        throw new NullPointerException("Error: ByteBuffer not initialized.");
    }

    mImgData.rewind();

    for (int i = 0; i < DIM_IMG_SIZE_WIDTH; i++) {
        for (int j = 0; j < DIM_IMG_SIZE_HEIGHT; j++) {
            int pixelIntensity = bitmap.getPixel(i, j);
            unpackPixel(pixelIntensity, i, j);
            Log.d(TAG, String.format("convertBitmapToByteBuffer: %d -> %f", pixelIntensity, convertToGrayScale(pixelIntensity)));
            mImgData.putFloat(convertToGrayScale(pixelIntensity));
        }
    }

}

private float convertToGrayScale(int color) {
    return (((color >> 16) & 0xFF) + ((color >> 8) & 0xFF) + (color & 0xFF)) / 3.0f / 255.0f;
}

但是,所有像素值都是 -1 或 -16777216。 請注意,這里提到的 unpackPixel 方法不起作用,因為無論如何所有值都具有相同的 int 值。 (在下面發布更改以供參考。)

private void unpackPixel(int pixel, int row, int col) {
    short red,green,blue;
    red = (short) ((pixel >> 16) & 0xFF);
    green = (short) ((pixel >> 8) & 0xFF);
    blue = (short) ((pixel >> 0) & 0xFF);
}

您可以在像素值上調用Color.red()或 green/blue ,它將返回灰度強度。 然后使用putFloat()將其放入字節緩沖區。 使用bitmap.getPixels()獲取單個數組中的所有像素值也比bitmap.getPixel(i, j)快。 這是我如何在我的 tflite 模型中加載灰度圖像:

private ByteBuffer getByteBuffer(Bitmap bitmap){
    int width = bitmap.getWidth();
    int height = bitmap.getHeight();
    ByteBuffer mImgData = ByteBuffer
            .allocateDirect(4 * width * height);
    mImgData.order(ByteOrder.nativeOrder());
    int[] pixels = new int[width*height];
    bitmap.getPixels(pixels, 0, width, 0, 0, width, height);
    for (int pixel : pixels) {
        mImgData.putFloat((float) Color.red(pixel));
    }
    return mImgData;
}

如果您需要歸一化值,只需除以 255:

float value = (float) Color.red(pixel)/255.0f;
mImgData.putFloat(value);

然后,您可以在解釋器中使用它作為:

ByteBuffer input = getByteBuffer(bitmap);
tflite.run(input, outputValue);

希望這可以幫助人們在未來尋找這個!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM