和其他許多人一樣,我試圖在相機預覽(使用SurfaceView)上繪製3D對象(使用GLSurfaceView)以及放置在頂部的一些按鈕。我實際上有一個原型工作,但我無法正確地使onResume正常工作。簡歷後,GLSurfaceView留在後面,不再可見。我知道它正在工作,因爲如果從佈局中移除SurfaceView,我可以很好地看到圖紙。如何在Android上正確使用setZOrderMediaOverlay?
目標是Nexus One,運行庫存2.3.3 ROM。
這裏的佈局XML:
<com.example.cameratest.GLPreview
android:id="@+id/cubes"
android:layout_width="fill_parent"
android:layout_height="fill_parent"/>
<com.example.cameratest.Preview
android:id="@+id/camera"
android:layout_width="fill_parent"
android:layout_height="fill_parent"/>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/buttongroup"
android:orientation="vertical"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:layout_gravity="right" android:gravity="center">
<Button android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_gravity="center" android:id="@+id/buttonClose"></Button>
<Button android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_gravity="center" android:id="@+id/buttonMode"></Button>
<Button android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_gravity="center" android:id="@+id/buttonCameraInfo"></Button>
</LinearLayout>
所有這一切都被包裹在一個<merge>
塊,但由於某些原因,我無法包括在上述<code>
上市。 Preview
是擴展SurfaceView
並實現相機預覽邏輯的類。
這項工作正常,當活動啓動。在我啓動另一個活動(例如,通過按下其中一個按鈕)並完成該活動後,主要活動恢復,但3D對象不再可見。
我發現this discussion其中提到setZOrderMediaOverlay()
將有助於解決這種z排序問題。此外,Android document for setZOrderMediaOverlay()說這個函數應該被稱爲「在表面視圖的包含窗口被附加到窗口管理器之前」。我不知道該如何解釋該語句,因此我在代碼中放置了調試語句以查看事件序列。下面是GLSurfaceView
代碼的樣子:
public class GLPreview extends GLSurfaceView
{
private static final String TAG = "GLPreview";
public GLPreview(Context context, AttributeSet attrs)
{
super(context, attrs);
// this.setZOrderMediaOverlay(true);
}
public void onPause()
{
super.onPause();
Log.d(TAG, "GLPreview: OnPause");
}
public void onResume()
{
// this.setZOrderMediaOverlay(true);
super.onResume();
Log.d(TAG, "GLPreview: OnResume");
}
public void surfaceCreated(SurfaceHolder holder)
{
Log.d(TAG, "GLPreview: surfaceCreated");
super.surfaceCreated(holder);
}
public void surfaceChanged(SurfaceHolder holder, int format, int w, int h)
{
Log.d(TAG, String.format("GLPreview: surfaceChanged, format=%d, w=%d, h=%d", format, w, h));
super.surfaceChanged(holder, format, w, h);
}
public void surfaceDestroyed(SurfaceHolder holder)
{
Log.d(TAG, "GLPreview: surfaceDestroyed");
super.surfaceDestroyed(holder);
}
protected void onAttachedToWindow()
{
Log.d(TAG, "GLPreview: onAttachedToWindow");
super.onAttachedToWindow();
}
protected void onDetachedFromWindow()
{
Log.d(TAG, "GLPreview: onDetachedFromWindow");
super.onDetachedFromWindow();
}
protected void onWindowVisibilityChanged (int vis)
{
String newVisibility;
switch (vis)
{
case View.GONE:
newVisibility = "GONE";
break;
case View.INVISIBLE:
newVisibility = "INVISIBLE";
break;
case View.VISIBLE:
newVisibility = "VISIBLE";
break;
default:
newVisibility = String.format("Unknown constant %d", vis);
}
Log.d(TAG, String.format("GLPreview: onWindowVisibilityChanged -> %s", newVisibility));
super.onWindowVisibilityChanged(vis);
}
}
這裏是當我啓動應用程序的事件序列:
GLPreview: OnResume GLPreview: onAttachedToWindow GLPreview: onWindowVisibilityChanged -> VISIBLE GLPreview: surfaceCreated GLPreview: surfaceChanged, format=1, w=800, h=480
所以我認爲setZOrderMediaOverlay()
需要在任何onResume()
或在構造函數中調用。但是,我嘗試了setZOrderMediaOverlay()
與true
或false
,GLSurfaceView
或SurfaceView
類的各種組合,但它們都沒有幫助解決問題。
我在Android編程方面比較新。我到目前爲止,但在這一點上,我需要一些幫助。如果某人在此場景中成功使用setZOrderMediaOverlay()
,並且與onResume()
合作,請告訴我如何完成此操作。
非常感謝!
FWIW,看到http://stackoverflow.com/questions/5648221/fighting-with-surfaceview-camera-and-opengl/25020225#25020225約重疊SurfaceViews一些注意事項。 – fadden 2014-07-29 16:24:55