从 C 中尽快填充 Android 位图中的数据

2022-09-03 16:04:39

我已经设法创建了一个android.graphics.Bitmap,并且我通过SetPixels命令成功填充了它。

问题是我从RGBA数据开始。然后,我创建了一个 jintArray。然后,我调用 SetIntArray(有效地将数据导入缓冲区)。然后,最后,我调用setPixels来实际设置像素(这可能会导致另一个副本)。

这样做的一个大问题是,无论我使用R8G8B8A8还是R5G6B5或A8,我仍然必须将我的像素数据转换为R8G8B8A8数据。

理想情况下,我想要一种方法来仅使用一个副本填充缓冲区,并允许我在不进行像素格式转换的情况下执行此操作。

有没有办法直接获取位图中包含的缓冲区数据?我看到JNI中有一个函数GetDirectBufferAddress,但我能找到的文档表明它仅限于java.nio.buffer。我可以使用此功能直接获取像素数据吗?也许通过获取位图类使用的内部缓冲区?

我使用它来创建全局 Ref'd Java.nio.buffer 的唯一方法是否是每次我想更新时,将我的像素数据复制到其中,然后使用 copyPixelsFromBuffer?这仍然涉及2个副本,但至少可以消除像素格式更改。这会比我已经使用的方法更有效吗?

有没有更好的方法来做到这一点?

顺便说一句,我知道我可以使用<android / bitmap.h中的功能>但我真的希望不要失去对Android 2.1和Android 2.2的支持...

提前干杯!


答案 1

这里有一个肮脏但工作的解决方案,从Android 1.5到4.0工作。代码已C++。

                              //decls of some partial classes from Skia library
class SkRefCnt{
public:
   virtual ~SkRefCnt(){}
private:
   mutable int fRefCnt;
};

//----------------------------

class SkPixelRef: public SkRefCnt{
public:
   virtual class Factory getFactory() const;
   virtual void flatten(class SkFlattenableWriteBuffer&) const;
protected:
   virtual void* onLockPixels(class SkColorTable**) = 0;
   virtual void onUnlockPixels() = 0;
public:
   void *GetPixels(){
      SkColorTable *ct;
      return onLockPixels(&ct);
   }
};

jobject java_bitmap;  //your Bitmap object
jclass java_bitmap_class = env.GetObjectClass(java_bitmap);
class SkBitmap;
SkBitmap *sk_bitmap = (SkBitmap*)env.CallIntMethod(java_bitmap, env.GetMethodID(java_bitmap_class, "ni", "()I"));
SkPixelRef *sk_pix_ref;
sk_pix_ref = (SkPixelRef*)((int*)sk_bitmap)[1];
// get pointer to Bitmap's pixel memory, and lenght of single line in bytes
int buffer_pitch = env.CallIntMethod(java_bitmap, env.GetMethodID(java_bitmap_class, "getRowBytes", "()I"));
void *buffer = sk_pix_ref->GetPixels();

答案 2

AFAIK,静态方法:

public static Bitmap createBitmap (int[] colors, int offset, int stride, int width, int height, Bitmap.Config config)

不涉及复制数据,而是在现有像素数组上创建(不可变)位图结构。这样,您可以提前准备此类位图,然后从本机代码操作缓冲区。这将支持不同的像素格式。用法示例可在此处找到:

http://javaocr.svn.sourceforge.net/viewvc/javaocr/trunk/demos/recognizer/src/net/sf/javaocr/demos/android/recognizer/Recognizer.java?revision=239&view=markup

( 第520行 )


推荐