GLSurfaceView dentro del fragmento que no se representa cuando se reinicia
Tengo una disposición de GLSurfaceView
y la representación según lo esperado usando un GLSurfaceView.Renderer
. Mi aplicación utiliza fragmentos del paquete de soporte de Android. Cuando surfaceDestroyed
a un nuevo fragmento surfaceDestroyed
se llama, pero cuando vuelvo al fragmento a través de la backstack el GLSurfaceView
no renderizar, las llamadas a requestRender
no dan lugar a una llamada onDraw
.
Soy consciente de que tengo que llamar onResume
y onPause
en la vista de la superficie y estoy haciendo esto desde el fragmento de alojamiento, pero no parece resolver el problema. Todos los ejemplos sobre su método se refieren a la actividad, ¿podría ser esta la cuestión? Y si es así, ¿cómo usar un GLSurfaceView
dentro de un fragmento.
- Primeros pasos para crear un efecto de chroma key utilizando la cámara android
- ¿Cómo medir el consumo de VRAM en Android?
- Cómo dibujar círculo básico en OpenGL ES 2.0 Android
- Rajawali cámara giratoria con Sensor.TYPE_ROTATION_VECTOR comportamiento extraño
- Cómo mejorar el rendimiento de la representación de ping-pong (para desenfoque) en OpenGL ES
Cualquier penetración apreciada grandemente, yo está feliz de fijar el código pero parece ser más de una pregunta general a mí,
Gracias
- Cómo hacer una cámara personalizada con Live Stickers
- Cómo llenar cada lado de un cubo con texturas diferentes en OpenGL ES 1.1?
- OpenGL ES 3.0. Textura de punto flotante
- Libgdx: SpriteBatch, shader de fragmentos en dispositivos Samsung Android funcionan incorrectamente
- Ayuda para rectificar escalas de línea en Android OpenGL 2.0 con RQAR
- Cómo guardar bitmap de GLSurfaceView (Sólo bitmap, no toda la textura)
- Cómo tratar NaN o inf en los shaders de OpenGL ES 2.0
- ¿Qué tipo de efectos secundarios tiene libgdx numSamples?
Así es como tengo mi configuración GLSurfaceView en un fragmento:
onCreateView() { glSurfaceView = new GLSurfaceView(getActivity()); ... } onPause() { if (glSurfaceView != null) { glSurfaceView.onPause(); } ... } onResume() { if (glSurfaceView != null) { glSurfaceView.onResume(); } ... }
}
Por lo tanto, similar a lo que haría en una actividad. Esto funciona en mi caso de uso, por lo que parece que funcionan en fragmentos. Es difícil decir más sin saber cómo se ve su código.
Sé que es demasiado tarde, pero puede ser útil para otros Esta es mi respuesta, ya que ya lo han implementado y funciona bien en el emulador y en el dispositivo también. Tengo fragmento de uso y supportV4.Hope te va a gustar.
import android.opengl.GLSurfaceView; import android.os.Bundle; import android.support.v4.app.Fragment; import android.support.v4.app.FragmentManager; import android.support.v4.app.FragmentTransaction; import android.util.Log; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import com.example.opengles20.glsurfaceview.GlSurfaceViewClass; import com.example.opengles20.renderer.RendererClass; public class MYGlclass extends Fragment { private GlSurfaceViewClass mGLView; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { if (container == null) { return null; } View view=inflater.inflate(R.layout.main, container, false); mGLView=(GlSurfaceViewClasss)view.findViewById(R.id.gl_surface_view); mGLView.setEGLContextClientVersion(2); RendererClass rendererclass=new RendererClass(getActivity()); mGLView.setRenderer(rendererclass); mGLView.setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY); return view; } }
Un par de cosas que necesita para darse cuenta cuando se utilizan fragmentos con un glsurfaceview. Se pone un poco complicado pero quédate conmigo. Cuando navegas a un nuevo fragmento, ondestroyview se llama automáticamente a tu fragmento con glsurfaceview, lo que destruye tu vista (la glsurfaceview que creaste y devuelve en oncreateview).
Así que cuando navegas a un nuevo fragmento, entonces la onpausa, onstop, ondestroyview se llama automáticamente, sin ningún trabajo de tu parte. Cuando vuelves a ese fragmento con la vista glsurface entonces oncreateview, onactivitycreated, onstart y onresume se llama automáticamente, sin ningún trabajo de tu parte.
La clave de su pregunta es comprender el ciclo de vida de los fragmentos que se puede encontrar en el sitio web de desarrolladores de android y comprender cómo funciona glsurfaceview.
Ahora, usando el glsurfaceview tienes que implementar el renderizador, usando onsurfacecreated, onsurfacechanged, y ondrawframe. Navegar a otro fragmento y luego volver a su fragmento con el glsurfaceview resultará en onsurfacecreated ser llamado de nuevo, ya que su glsurfaceview fue destruido en ondestroyview, su contexto se ha perdido y usted necesita recargar todos sus recursos en el hilo gl.
Por último, de su pregunta se ve que no se está llamando ondrawframe, lo que probablemente se deba a que no recrear su vista, establecer el renderizador y devolver su vista desde oncreateview.
Así que en oncreateview necesitas algo como esto
@Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { View mView = inflater.inflate(R.layout.fragment_layout, null); surface = (GLSurfaceView) mView.findViewById (R.id.glsurfaceview); surface.setEGLContextClientVersion(2); //return your view here return mView; } @Override public void onActivityCreated(Bundle mState) { super.onActivityCreated(mState); //setting your renderer here causes onSurfaceCreated to be called //if you set your renderer here then you have a context to load resources surface.setRenderer( shader ); }
No quieres crear tu clase de representación (shader) en oncreateview a menos que quieras que tu clase de renderizado empiece de nuevo cada vez que regreses a tu fragmento con glsurfaceview. En su lugar, cree su clase de representación en su Creación de fragmentos, de esa manera si tiene las cosas configuradas entonces comenzará a donde salió ya que simplemente configurar el renderizador le proporcionará la superficie que hará que el onsurfacecreated, onsurfacechanged y ondrawframe sean invocados automáticamente. Asegúrese de volver a cargar los recursos que utilizó por última vez en onsurfacecreated, en el marco de presentación antes de dibujarlos.
@Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); shader = new Shader(this); Log.d("Fragment", "OnCreate"); }
Cuando se trata de pausar y reanudar el fragmento, entonces en la mayoría de los casos esto se maneja automáticamente cuando se reemplaza dinámicamente un fragmento y se agrega al backstack, por lo que simplemente coloque surface.onpause () y surface.onResume () en los lugares correctos Y usted es bueno para ir.
Para hacer las cosas cristalinas tratar de poner declaraciones de registro en los métodos que giran alrededor del ciclo de vida del fragmento y renderizador glsurfaceview y usted será capaz de ver lo que está y no está sucediendo.
No trabajo con fragmentos, pero si la glsurface fue destruida, tal vez tenga que crear una instancia de nuevo de OpenGLRenderer y reassing a la glsurface, este código de trabajo para mí en las actividades de cambio de orientación y volver a crear toda la pantalla, en este caso tengo que Configure el contenido de layout de nuevo para restablecer el glsurfaceview:
view.onPause(); setContentView(R.layout.slidegl); view = (GLSurfaceView) this.findViewById(R.id.glSurface); renderer = new OpenGLRenderer(); view.setRenderer(renderer); view.onResume();
Si no desea reiniciar y configurar todo el contenido de la vista, intente crear un nuevo objeto de GLSurface:
this.view = new GLSurfaceView();
Im no un experto con OpenGL
ES
, pero he luchado mi camino alrededor de fragmentos y su ciclo de vida suficiente. Lo que sugiero que hagas es establecer onCreateView
para tu fragmento, decirle al renderizador que empiece a dibujar de nuevo, y si eso no funciona intenta hacerlo desde el onResume
del fragmento. No debería haber necesidad de hacer nada desde el nivel de actividad cuando se trata del dibujo de la superficie GL
en el fragmento.
- ¿Cómo configuramos Android Studio para ejecutar su pelusa en cada compilación?
- Versión beta en la tienda de juegos Android. ¿Dónde está el enlace opt-in para probadores?