2010-06-08 100 views
5

我是Android開發人員的新手,並且在指定的時間間隔後具有讀取幀緩衝區數據的任務。Android源代碼不工作,通過glReadPixels讀取幀緩衝區

我想出了下面的代碼:

public class mainActivity extends Activity { 
    Bitmap mSavedBM; 
    private EGL10 egl; 
    private EGLDisplay display; 
    private EGLConfig config;  
    private EGLSurface surface; 
    private EGLContext eglContext; 
    private GL11 gl; 
    protected int width, height; 


//Called when the activity is first created. 
@Override 
public void onCreate(Bundle savedInstanceState) 
{ 
    super.onCreate(savedInstanceState); 

    // get the screen width and height 
    DisplayMetrics dm = new DisplayMetrics(); 
    getWindowManager().getDefaultDisplay().getMetrics(dm); 
    int screenWidth = dm.widthPixels; 
    int screenHeight = dm.heightPixels; 

    String SCREENSHOT_DIR = "/screenshots"; 
    initGLFr(); //GlView initialized. 
    savePixels(0, 10, screenWidth, screenHeight, gl); //this gets the screen to the mSavedBM. 
    saveBitmap(mSavedBM, SCREENSHOT_DIR, "capturedImage"); 

    //Now we need to save the bitmap (the screen capture) to some location. 
    setContentView(R.layout.main); //This displays the content on the screen 

} 
private void initGLFr() 
{ 
    egl = (EGL10) EGLContext.getEGL(); 
    display = egl.eglGetDisplay(EGL10.EGL_DEFAULT_DISPLAY); 
    int[] ver = new int[2]; 
    egl.eglInitialize(display, ver); 

    int[] configSpec = {EGL10.EGL_NONE}; 
    EGLConfig[] configOut = new EGLConfig[1]; 
    int[] nConfig = new int[1]; 
    egl.eglChooseConfig(display, configSpec, configOut, 1, nConfig); 
    config = configOut[0]; 
    eglContext = egl.eglCreateContext(display, config, EGL10.EGL_NO_CONTEXT, null); 
    surface = egl.eglCreateWindowSurface(display, config, SurfaceHolder.SURFACE_TYPE_GPU, null); 
    egl.eglMakeCurrent(display, surface, surface, eglContext); 
    gl = (GL11) eglContext.getGL(); 
} 
public void savePixels(int x, int y, int w, int h, GL10 gl) 
{ 
    if (gl == null) 
      return; 

    synchronized (this) { 
    if (mSavedBM != null) { 
    mSavedBM.recycle(); 
    mSavedBM = null; 
    } 
    } 

    int b[] = new int[w * (y + h)]; 
    int bt[] = new int[w * h]; 
    IntBuffer ib = IntBuffer.wrap(b); 
    ib.position(0); 
    gl.glReadPixels(x, 0, w, y + h, GL10.GL_RGBA,GL10.GL_UNSIGNED_BYTE,ib); 

    for (int i = 0, k = 0; i < h; i++, k++) 
    { 
     //OpenGLbitmap is incompatible with Android bitmap 
     //and so, some corrections need to be done. 
      for (int j = 0; j < w; j++) 
      { 
        int pix = b[i * w + j]; 
        int pb = (pix >> 16) & 0xff; 
        int pr = (pix << 16) & 0x00ff0000; 
        int pix1 = (pix & 0xff00ff00) | pr | pb; 
        bt[(h - k - 1) * w + j] = pix1; 
      } 
    } 

    Bitmap sb = Bitmap.createBitmap(bt, w, h, Bitmap.Config.ARGB_8888); 
    synchronized (this) 
    { 
     mSavedBM = sb; 
    } 
} 

static String saveBitmap(Bitmap bitmap, String dir, String baseName) { 
    try { 
     File sdcard = Environment.getExternalStorageDirectory(); 
     File pictureDir = new File(sdcard, dir); 
     pictureDir.mkdirs(); 
     File f = null; 
     for (int i = 1; i < 200; ++i) { 
      String name = baseName + i + ".png"; 
      f = new File(pictureDir, name); 
      if (!f.exists()) { 
       break; 
      } 
     } 
     if (!f.exists()) { 
      String name = f.getAbsolutePath(); 
      FileOutputStream fos = new FileOutputStream(name); 
      bitmap.compress(Bitmap.CompressFormat.PNG, 100, fos); 
      fos.flush(); 
      fos.close(); 
      return name; 
     } 
    } catch (Exception e) { 

    } finally { 

     //if (fos != null) { 
     // fos.close(); 
     // } 

    } 
    return null; 
} 

}

另外,如果有一個人能告訴我到更好的方式來讀取幀緩衝區將是巨大的。我正在使用Android 2.2和API級別8的虛擬設備。 我經歷了很多以前的討論,發現我們無法直接通過「/ dev/graphics/fb0」讀取幀緩衝區。

(編輯:重新格式化的代碼第一行)

+0

你對這段代碼有什麼問題? – Alan 2010-06-08 16:13:37

+0

它在模擬器的「對不起,應用程序意外停止」給出錯誤窗口 – AliR 2010-06-10 07:39:51

回答

2

問題解決了,對於上述代碼的執行。但仍然無法讀取幀緩衝區數據。

我已經深入研究了內部結構,並追溯了以前有關訪問較舊版本Android 1.5之前的framebuffer的所有聲明。

Android 1.5之前的移植確實有直接通過/ dev/fb0訪問framebuffer的帖子。這不適用於更高版本,Android開發團隊沒有計劃在Android谷歌組中提到他們。

我希望這可以幫助很多人花費大量的時間找出一個辦法。

問候, 阿里

+2

解決方法如何?請發佈您的解決方案 – davenpcj 2010-06-14 00:51:27