From f10b30c16aeec428378d1d560d030b2d39801c4e Mon Sep 17 00:00:00 2001
From: Sven Gothel <sgothel@jausoft.com>
Date: Wed, 11 Apr 2012 19:46:37 +0200
Subject: Refine GLMediaPlayer/TextureSequence, add MovieCube demo, fix minor
 bug in Texture

- Add TextureSequence, base interface of GLMediaPlayer to genralize texture streams

- TextureSequence / GLMediaPlayer: Use inner classes for event and texture data

- getLastTexture() shall never return 'null', initialization of TextureSequence (initGLStream(..), etc)
  shall provide a TextureFrame w/ the stream's dimension.

- GLMediaPlayerImpl.createTexImageImpl() y-flip defaults to 'false'
  impl. shall define y-flip, if required.

- Added MovieCube demo

- Fix Texture: initialize aspectRation for 'wrapping' ctor

-
---
 .../opengl/util/av/GLMediaEventListener.java       | 28 -------
 .../com/jogamp/opengl/util/av/GLMediaPlayer.java   | 69 ++++++-----------
 .../opengl/util/av/GLMediaPlayerFactory.java       |  4 +-
 .../com/jogamp/opengl/util/texture/Texture.java    |  1 +
 .../jogamp/opengl/util/texture/TextureCoords.java  | 20 +----
 .../opengl/util/texture/TextureSequence.java       | 90 ++++++++++++++++++++++
 .../android/av/AndroidGLMediaPlayerAPI14.java      | 26 ++++---
 .../jogamp/opengl/omx/OMXGLMediaPlayer.java        | 28 +++----
 .../jogamp/opengl/util/av/EGLMediaPlayerImpl.java  |  9 ++-
 .../jogamp/opengl/util/av/GLMediaPlayerImpl.java   | 62 +++++++--------
 .../jogamp/opengl/util/av/NullGLMediaPlayer.java   | 34 ++++----
 11 files changed, 198 insertions(+), 173 deletions(-)
 delete mode 100644 src/jogl/classes/com/jogamp/opengl/util/av/GLMediaEventListener.java
 create mode 100644 src/jogl/classes/com/jogamp/opengl/util/texture/TextureSequence.java

(limited to 'src/jogl')

diff --git a/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaEventListener.java b/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaEventListener.java
deleted file mode 100644
index 9887a417c..000000000
--- a/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaEventListener.java
+++ /dev/null
@@ -1,28 +0,0 @@
-
-package com.jogamp.opengl.av;
-
-import javax.media.opengl.GL;
-
-public interface GLMediaEventListener {
-
-    static final int EVENT_CHANGE_SIZE   = 1<<0;
-    static final int EVENT_CHANGE_FPS    = 1<<1;
-    static final int EVENT_CHANGE_BPS    = 1<<2;
-    static final int EVENT_CHANGE_LENGTH = 1<<3;
-
-    /**
-     * @param mp the event source 
-     * @param event_mask the changes attributes
-     * @param when system time in msec. 
-     */
-    public void attributesChanges(GLMediaPlayer mp, int event_mask, long when);
-    
-    /** 
-     * Signaling listeners that {@link GLMediaPlayer#getNextTexture(GL, boolean)} is able to deliver a new frame.
-     * @param mp the event source 
-     * @param when system time in msec. 
-     **/
-    public void newFrameAvailable(GLMediaPlayer mp, long when);
-
-}
-
diff --git a/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayer.java b/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayer.java
index b3827d520..d86c8bfd0 100644
--- a/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayer.java
+++ b/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayer.java
@@ -25,7 +25,7 @@
  * authors and should not be interpreted as representing official policies, either expressed
  * or implied, of JogAmp Community.
  */
-package com.jogamp.opengl.av;
+package com.jogamp.opengl.util.av;
 
 import java.io.IOException;
 import java.net.URLConnection;
@@ -35,8 +35,7 @@ import javax.media.opengl.GLException;
 
 import jogamp.opengl.Debug;
 
-import com.jogamp.opengl.util.texture.Texture;
-import com.jogamp.opengl.util.texture.TextureCoords;
+import com.jogamp.opengl.util.texture.TextureSequence;
 
 /**
  * Lifecycle of an GLMediaPlayer:
@@ -49,8 +48,23 @@ import com.jogamp.opengl.util.texture.TextureCoords;
  *   <tr><td>{@link #destroy(GL)}</td>                     <td>ANY</td>                 <td>Uninitialized</td></tr>
  * </table>
  */
-public interface GLMediaPlayer {
+public interface GLMediaPlayer extends TextureSequence {
     public static final boolean DEBUG = Debug.debug("GLMediaPlayer");
+        
+    public interface GLMediaEventListener extends TexSeqEventListener<GLMediaPlayer> {
+    
+        static final int EVENT_CHANGE_SIZE   = 1<<0;
+        static final int EVENT_CHANGE_FPS    = 1<<1;
+        static final int EVENT_CHANGE_BPS    = 1<<2;
+        static final int EVENT_CHANGE_LENGTH = 1<<3;
+    
+        /**
+         * @param mp the event source 
+         * @param event_mask the changes attributes
+         * @param when system time in msec. 
+         */
+        public void attributesChanges(GLMediaPlayer mp, int event_mask, long when);    
+    }
     
     public enum State {
         Uninitialized(0), Stopped(1), Playing(2), Paused(3); 
@@ -62,38 +76,14 @@ public interface GLMediaPlayer {
         }
     }
     
-    public static class TextureFrame {
-        public TextureFrame(Texture t) {
-            texture = t;
-            // stMatrix = new float[4*4];
-            // ProjectFloat.makeIdentityf(stMatrix, 0);
-        }
-        
-        public final Texture getTexture() { return texture; }
-        // public final float[] getSTMatrix() { return stMatrix; }
-        
-        public String toString() {
-            return "TextureFrame[" + texture + "]";
-        }
-        protected final Texture texture;
-        // protected final float[] stMatrix;
-    }
-    
     public int getTextureCount();
     
-    public int getTextureTarget();
-    
     /** Defaults to 0 */
     public void setTextureUnit(int u);
-    public int getTextureUnit();
-    
     /** Sets the texture min-mag filter, defaults to {@link GL#GL_NEAREST}. */
     public void setTextureMinMagFilter(int[] minMagFilter);
-    public int[] getTextureMinMagFilter();
-    
     /** Sets the texture min-mag filter, defaults to {@link GL#GL_CLAMP_TO_EDGE}. */
     public void setTextureWrapST(int[] wrapST);
-    public int[] getTextureWrapST();
     
     /** 
      * Sets the stream to be used. Initializes all stream related states inclusive OpenGL ones,
@@ -157,27 +147,17 @@ public interface GLMediaPlayer {
     public long seek(long msec);
 
     /**
-     * @return the last updated texture. Maybe <code>null</code> in case no last frame is available. 
-     *         Not blocking. 
+     * {@inheritDoc}
      */
-    public TextureFrame getLastTexture();
-    
+    public TextureSequence.TextureFrame getLastTexture();
+
     /**
-     * Returns the next texture to be rendered. 
-     * <p>
-     * Implementation shall block until next frame is available if <code>blocking</code> is <code>true</code>,
-     * otherwise it shall return the last frame in case a new frame is not available.
-     * </p>
-     * <p>
-     * Shall return <code>null</code> in case <i>no</i> frame is available.
-     * </p>
+     * {@inheritDoc}
      * 
      * @see #addEventListener(GLMediaEventListener)
      * @see GLMediaEventListener#newFrameAvailable(GLMediaPlayer, long)
      */
-    public TextureFrame getNextTexture(GL gl, boolean blocking);
-    
-    public TextureCoords getTextureCoords();
+    public TextureSequence.TextureFrame getNextTexture(GL gl, boolean blocking);
     
     public URLConnection getURLConnection();
 
@@ -226,5 +206,6 @@ public interface GLMediaPlayer {
 
     public void removeEventListener(GLMediaEventListener l);
 
-    public GLMediaEventListener[] getEventListeners();
+    public GLMediaEventListener[] getEventListeners();    
+    
 }
diff --git a/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayerFactory.java b/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayerFactory.java
index 1894f411f..df12fd12c 100644
--- a/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayerFactory.java
+++ b/src/jogl/classes/com/jogamp/opengl/util/av/GLMediaPlayerFactory.java
@@ -25,9 +25,9 @@
  * authors and should not be interpreted as representing official policies, either expressed
  * or implied, of JogAmp Community.
  */
-package com.jogamp.opengl.av;
+package com.jogamp.opengl.util.av;
 
-import jogamp.opengl.av.NullGLMediaPlayer;
+import jogamp.opengl.util.av.NullGLMediaPlayer;
 
 import com.jogamp.common.os.AndroidVersion;
 import com.jogamp.common.os.Platform;
diff --git a/src/jogl/classes/com/jogamp/opengl/util/texture/Texture.java b/src/jogl/classes/com/jogamp/opengl/util/texture/Texture.java
index 208fd053d..a94b1f827 100644
--- a/src/jogl/classes/com/jogamp/opengl/util/texture/Texture.java
+++ b/src/jogl/classes/com/jogamp/opengl/util/texture/Texture.java
@@ -197,6 +197,7 @@ public class Texture {
         this.mustFlipVertically = mustFlipVertically;
         this.texWidth = texWidth;
         this.texHeight = texHeight;
+        aspectRatio = (float) imgWidth / (float) imgHeight;
         setImageSize(imgWidth, imgHeight, target);
     }
 
diff --git a/src/jogl/classes/com/jogamp/opengl/util/texture/TextureCoords.java b/src/jogl/classes/com/jogamp/opengl/util/texture/TextureCoords.java
index 61f5d116c..39647039b 100644
--- a/src/jogl/classes/com/jogamp/opengl/util/texture/TextureCoords.java
+++ b/src/jogl/classes/com/jogamp/opengl/util/texture/TextureCoords.java
@@ -36,8 +36,6 @@
 
 package com.jogamp.opengl.util.texture;
 
-import java.nio.FloatBuffer;
-
 /** Specifies texture coordinates for a rectangular area of a
     texture. Note that some textures are inherently flipped vertically
     from OpenGL's standard coordinate system. This class takes care of
@@ -79,22 +77,6 @@ public class TextureCoords {
         return d;
     }
     
-    /** Transfers <code>{s * ss, t * ts}</code> from this object into the given FloatBuffer in the following order:
-     * <pre>
-     *   left,  bottom
-     *   right, bottom
-     *   left,  top
-     *   right  top
-     * </pre>
-     */
-    public FloatBuffer getST_LB_RB_LT_RT(FloatBuffer d, float ss, float ts) {
-        d.put( left  *ss);  d.put( bottom*ts);
-        d.put( right *ss);  d.put( bottom*ts);
-        d.put( left  *ss);  d.put( top   *ts);
-        d.put( right *ss);  d.put( top   *ts);
-        return d;
-    }
-    
     /** Returns the leftmost (x) texture coordinate of this
         rectangle. */
     public float left() { return left; }
@@ -110,4 +92,6 @@ public class TextureCoords {
     /** Returns the topmost (y) texture coordinate of this
         rectangle. */
     public float top() { return top; }
+    
+    public String toString() { return "TexCoord[h: "+left+" - "+right+", v: "+bottom+" - "+top+"]"; }
 }
diff --git a/src/jogl/classes/com/jogamp/opengl/util/texture/TextureSequence.java b/src/jogl/classes/com/jogamp/opengl/util/texture/TextureSequence.java
new file mode 100644
index 000000000..e6d21c613
--- /dev/null
+++ b/src/jogl/classes/com/jogamp/opengl/util/texture/TextureSequence.java
@@ -0,0 +1,90 @@
+/**
+ * Copyright 2012 JogAmp Community. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ * 
+ *    1. Redistributions of source code must retain the above copyright notice, this list of
+ *       conditions and the following disclaimer.
+ * 
+ *    2. Redistributions in binary form must reproduce the above copyright notice, this list
+ *       of conditions and the following disclaimer in the documentation and/or other materials
+ *       provided with the distribution.
+ * 
+ * THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
+ * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ * 
+ * The views and conclusions contained in the software and documentation are those of the
+ * authors and should not be interpreted as representing official policies, either expressed
+ * or implied, of JogAmp Community.
+ */
+package com.jogamp.opengl.util.texture;
+
+import javax.media.opengl.GL;
+
+public interface TextureSequence {
+
+    public static class TextureFrame {
+        public TextureFrame(Texture t) {
+            texture = t;
+            // stMatrix = new float[4*4];
+            // ProjectFloat.makeIdentityf(stMatrix, 0);
+        }
+        
+        public final Texture getTexture() { return texture; }
+        // public final float[] getSTMatrix() { return stMatrix; }
+        
+        public String toString() {
+            return "TextureFrame[" + texture + "]";
+        }
+        protected final Texture texture;
+        // protected final float[] stMatrix;
+    }
+
+    public interface TexSeqEventListener<T extends TextureSequence> {
+        /** 
+         * Signaling listeners that {@link TextureSequence#getNextTexture(GL, boolean)} is able to deliver a new frame.
+         * @param ts the event source 
+         * @param when system time in msec. 
+         **/
+        public void newFrameAvailable(T ts, long when);
+    }
+    
+    public int getTextureTarget();
+
+    public int getTextureUnit();
+
+    public int[] getTextureMinMagFilter();
+
+    public int[] getTextureWrapST();
+
+    /**
+     * Returns the last updated texture. 
+     * <p>
+     * In case the instance is just initialized, it shall return a <code>TextureFrame</code>
+     * object with valid attributes. The texture content may be undefined 
+     * until the first call of {@link #getNextTexture(GL, boolean)}.<br>
+     * </p> 
+     * Not blocking. 
+     */
+    public TextureFrame getLastTexture();
+
+    /**
+     * Returns the next texture to be rendered. 
+     * <p>
+     * Implementation shall block until next frame is available if <code>blocking</code> is <code>true</code>,
+     * otherwise it shall return the last frame in case a new frame is not available.
+     * </p>
+     * <p>
+     * Shall return <code>null</code> in case <i>no</i> frame is available.
+     * </p>
+     */
+    public TextureFrame getNextTexture(GL gl, boolean blocking);
+}
\ No newline at end of file
diff --git a/src/jogl/classes/jogamp/opengl/android/av/AndroidGLMediaPlayerAPI14.java b/src/jogl/classes/jogamp/opengl/android/av/AndroidGLMediaPlayerAPI14.java
index ae45662db..a50f1507f 100644
--- a/src/jogl/classes/jogamp/opengl/android/av/AndroidGLMediaPlayerAPI14.java
+++ b/src/jogl/classes/jogamp/opengl/android/av/AndroidGLMediaPlayerAPI14.java
@@ -32,10 +32,10 @@ import java.io.IOException;
 import javax.media.opengl.GL;
 import javax.media.opengl.GLES2;
 
-import com.jogamp.opengl.util.texture.TextureCoords;
+import com.jogamp.opengl.util.texture.TextureSequence;
 
 import jogamp.common.os.android.StaticContext;
-import jogamp.opengl.av.GLMediaPlayerImpl;
+import jogamp.opengl.util.av.GLMediaPlayerImpl;
 
 import android.graphics.SurfaceTexture;
 import android.graphics.SurfaceTexture.OnFrameAvailableListener;
@@ -51,7 +51,7 @@ public class AndroidGLMediaPlayerAPI14 extends GLMediaPlayerImpl {
     MediaPlayer mp;
     volatile boolean updateSurface = false;
     Object updateSurfaceLock = new Object();
-    TextureFrame lastTexFrame = null;
+    TextureSequence.TextureFrame lastTexFrame = null;
 
     /**
     private static String toString(MediaPlayer m) {
@@ -133,12 +133,12 @@ public class AndroidGLMediaPlayerAPI14 extends GLMediaPlayerImpl {
     }
 
     @Override
-    public TextureFrame getLastTexture() {
+    public TextureSequence.TextureFrame getLastTexture() {
         return lastTexFrame;
     }
 
     @Override
-    public TextureFrame getNextTexture(GL gl, boolean blocking) {
+    public TextureSequence.TextureFrame getNextTexture(GL gl, boolean blocking) {
         if(null != stex && null != mp) {
             // Only block once, no while-loop. 
             // This relaxes locking code of non crucial resources/events.
@@ -166,11 +166,6 @@ public class AndroidGLMediaPlayerAPI14 extends GLMediaPlayerImpl {
         return lastTexFrame;
     }
     
-    @Override
-    public TextureCoords getTextureCoords() {
-        return texFrames[0].getTexture().getImageTexCoords();
-    }
-    
     private void wakeUp(boolean newFrame) {
         synchronized(updateSurfaceLock) {
             if(newFrame) {
@@ -226,12 +221,19 @@ public class AndroidGLMediaPlayerAPI14 extends GLMediaPlayerImpl {
             totalFrames = 0;
             duration = mp.getDuration();
             acodec = "unknown";
-            vcodec = "unknown";
+            vcodec = "unknown";            
         }
     }
     
     @Override
-    protected void destroyTexImage(GL gl, TextureFrame imgTex) {
+    protected TextureSequence.TextureFrame createTexImage(GL gl, int idx, int[] tex) {
+        lastTexFrame = new TextureSequence.TextureFrame( createTexImageImpl(gl, idx, tex, true) );
+        // lastTexFrame = super.createTexImage(gl, idx, tex);
+        return lastTexFrame; 
+    }
+    
+    @Override
+    protected void destroyTexImage(GL gl, TextureSequence.TextureFrame imgTex) {
         if(null != stex) {
             stex.release();
             stex = null;
diff --git a/src/jogl/classes/jogamp/opengl/omx/OMXGLMediaPlayer.java b/src/jogl/classes/jogamp/opengl/omx/OMXGLMediaPlayer.java
index 7c775dd9f..c005c2ea6 100644
--- a/src/jogl/classes/jogamp/opengl/omx/OMXGLMediaPlayer.java
+++ b/src/jogl/classes/jogamp/opengl/omx/OMXGLMediaPlayer.java
@@ -7,11 +7,10 @@ import java.net.URL;
 import javax.media.opengl.GL;
 import javax.media.opengl.GLException;
 
-import com.jogamp.opengl.av.GLMediaEventListener;
-import com.jogamp.opengl.util.texture.TextureCoords;
+import com.jogamp.opengl.util.texture.TextureSequence;
 
-import jogamp.opengl.av.EGLMediaPlayerImpl;
 import jogamp.opengl.egl.EGL;
+import jogamp.opengl.util.av.EGLMediaPlayerImpl;
 
 public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
     protected long moviePtr = 0;
@@ -26,7 +25,7 @@ public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
     protected long o_totalFrames = 0;
     protected long o_duration = 0;
         
-    protected TextureFrame lastTex = null;
+    protected TextureSequence.TextureFrame lastTex = null;
 
     public OMXGLMediaPlayer() {
         super(TextureType.KHRImage, true);
@@ -41,7 +40,7 @@ public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
     }
     
     @Override
-    protected TextureFrame createTexImage(GL gl, int idx, int[] tex) {
+    protected TextureSequence.TextureFrame createTexImage(GL gl, int idx, int[] tex) {
         final EGLTextureFrame eglTex = (EGLTextureFrame) super.createTexImage(gl, idx, tex);
         _setStreamEGLImageTexture2D(moviePtr, idx, tex[idx], eglTex.getImage(), eglTex.getSync());
         lastTex = eglTex;
@@ -49,8 +48,9 @@ public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
     }
     
     @Override
-    protected void destroyTexImage(GL gl, TextureFrame imgTex) {
-        super.destroyTexImage(gl, imgTex);
+    protected void destroyTexImage(GL gl, TextureSequence.TextureFrame imgTex) {
+        lastTex = null;
+        super.destroyTexImage(gl, imgTex);        
     }
     
     @Override
@@ -76,7 +76,7 @@ public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
     
         System.out.println("setURL: p1 "+this);
         _setStream(moviePtr, textureCount, path);
-        System.out.println("setURL: p2 "+this);
+        System.out.println("setURL: p2 "+this);        
     }
     
     @Override
@@ -135,18 +135,18 @@ public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
     }
 
     @Override
-    public TextureFrame getLastTexture() {
+    public TextureSequence.TextureFrame getLastTexture() {
         return lastTex;
     }
     
     @Override
-    public synchronized TextureFrame getNextTexture(GL gl, boolean blocking) {
+    public synchronized TextureSequence.TextureFrame getNextTexture(GL gl, boolean blocking) {
         if(0==moviePtr) {
             throw new GLException("OMX native instance null");
         }
         final int nextTex = _getNextTextureID(moviePtr, blocking);
         if(0 < nextTex) {
-            final TextureFrame eglImgTex = texFrameMap.get(new Integer(_getNextTextureID(moviePtr, blocking)));
+            final TextureSequence.TextureFrame eglImgTex = texFrameMap.get(new Integer(_getNextTextureID(moviePtr, blocking)));
             if(null!=eglImgTex) {
                 lastTex = eglImgTex;
             }
@@ -154,12 +154,6 @@ public class OMXGLMediaPlayer extends EGLMediaPlayerImpl {
         return lastTex;
     }
     
-    @Override
-    public TextureCoords getTextureCoords() {
-        return lastTex.getTexture().getImageTexCoords();
-    }
-    
-
     protected void attributesUpdated() {
         int event_mask = 0;
         if( o_width != width || o_height != height ) {
diff --git a/src/jogl/classes/jogamp/opengl/util/av/EGLMediaPlayerImpl.java b/src/jogl/classes/jogamp/opengl/util/av/EGLMediaPlayerImpl.java
index 2f6744fc5..52378d0fd 100644
--- a/src/jogl/classes/jogamp/opengl/util/av/EGLMediaPlayerImpl.java
+++ b/src/jogl/classes/jogamp/opengl/util/av/EGLMediaPlayerImpl.java
@@ -25,7 +25,7 @@
  * authors and should not be interpreted as representing official policies, either expressed
  * or implied, of JogAmp Community.
  */
-package jogamp.opengl.av;
+package jogamp.opengl.util.av;
 
 import java.nio.IntBuffer;
 
@@ -33,6 +33,7 @@ import javax.media.opengl.GL;
 
 import com.jogamp.common.nio.Buffers;
 import com.jogamp.opengl.util.texture.Texture;
+import com.jogamp.opengl.util.texture.TextureSequence;
 
 import jogamp.opengl.egl.EGL;
 import jogamp.opengl.egl.EGLContext;
@@ -53,7 +54,7 @@ public abstract class EGLMediaPlayerImpl extends GLMediaPlayerImpl {
         }
     }    
     
-    public static class EGLTextureFrame extends TextureFrame {
+    public static class EGLTextureFrame extends TextureSequence.TextureFrame {
         
         public EGLTextureFrame(Texture t, long khrImage, long khrSync) {
             super(t);
@@ -83,7 +84,7 @@ public abstract class EGLMediaPlayerImpl extends GLMediaPlayerImpl {
     }
 
     @Override
-    protected TextureFrame createTexImage(GL gl, int idx, int[] tex) {
+    protected TextureSequence.TextureFrame createTexImage(GL gl, int idx, int[] tex) {
         final Texture texture = super.createTexImageImpl(gl, idx, tex, true);
         final long image;
         final long sync;
@@ -123,7 +124,7 @@ public abstract class EGLMediaPlayerImpl extends GLMediaPlayerImpl {
     }
     
     @Override
-    protected void destroyTexImage(GL gl, TextureFrame imgTex) {
+    protected void destroyTexImage(GL gl, TextureSequence.TextureFrame imgTex) {
         final EGLContext eglCtx = (EGLContext) gl.getContext();
         final EGLExt eglExt = eglCtx.getEGLExt();
         final EGLDrawable eglDrawable = (EGLDrawable) eglCtx.getGLDrawable();
diff --git a/src/jogl/classes/jogamp/opengl/util/av/GLMediaPlayerImpl.java b/src/jogl/classes/jogamp/opengl/util/av/GLMediaPlayerImpl.java
index acd707288..bc3fa0919 100644
--- a/src/jogl/classes/jogamp/opengl/util/av/GLMediaPlayerImpl.java
+++ b/src/jogl/classes/jogamp/opengl/util/av/GLMediaPlayerImpl.java
@@ -25,7 +25,7 @@
  * authors and should not be interpreted as representing official policies, either expressed
  * or implied, of JogAmp Community.
  */
-package jogamp.opengl.av;
+package jogamp.opengl.util.av;
 
 import java.io.IOException;
 import java.net.URLConnection;
@@ -37,9 +37,9 @@ import javax.media.opengl.GL;
 import javax.media.opengl.GLES2;
 import javax.media.opengl.GLException;
 
-import com.jogamp.opengl.av.GLMediaPlayer;
-import com.jogamp.opengl.av.GLMediaEventListener;
+import com.jogamp.opengl.util.av.GLMediaPlayer;
 import com.jogamp.opengl.util.texture.Texture;
+import com.jogamp.opengl.util.texture.TextureSequence;
 
 /**
  * After object creation an implementation may customize the behavior:
@@ -86,8 +86,8 @@ public abstract class GLMediaPlayerImpl implements GLMediaPlayer {
 
     protected long frameNumber = 0;
     
-    protected TextureFrame[] texFrames = null;
-    protected HashMap<Integer, TextureFrame> texFrameMap = new HashMap<Integer, TextureFrame>();
+    protected TextureSequence.TextureFrame[] texFrames = null;
+    protected HashMap<Integer, TextureSequence.TextureFrame> texFrameMap = new HashMap<Integer, TextureSequence.TextureFrame>();
     private ArrayList<GLMediaEventListener> eventListeners = new ArrayList<GLMediaEventListener>();
 
     protected GLMediaPlayerImpl() {
@@ -172,27 +172,29 @@ public abstract class GLMediaPlayerImpl implements GLMediaPlayer {
         }
         this.urlConn = urlConn;
         if (this.urlConn != null) {
-            try {
-                if(null!=texFrames) {
-                    removeAllImageTextures(gl);
-                } else {
-                    texFrames = new TextureFrame[textureCount];
-                }
-            
-                final int[] tex = new int[textureCount];
-                {
-                    gl.glGenTextures(textureCount, tex, 0);
-                    final int err = gl.glGetError();
-                    if( GL.GL_NO_ERROR != err ) {
-                        throw new RuntimeException("TextureNames creation failed (num: "+textureCount+"): err "+toHexString(err));
+            try {                
+                if(null != gl) {
+                    if(null!=texFrames) {
+                        // re-init ..
+                        removeAllImageTextures(gl);
+                    } else {
+                        texFrames = new TextureSequence.TextureFrame[textureCount];
+                    }
+                    final int[] tex = new int[textureCount];
+                    {
+                        gl.glGenTextures(textureCount, tex, 0);
+                        final int err = gl.glGetError();
+                        if( GL.GL_NO_ERROR != err ) {
+                            throw new RuntimeException("TextureNames creation failed (num: "+textureCount+"): err "+toHexString(err));
+                        }
+                    }
+                    initGLStreamImpl(gl, tex);
+                    
+                    for(int i=0; i<textureCount; i++) {
+                        final TextureSequence.TextureFrame tf = createTexImage(gl, i, tex); 
+                        texFrames[i] = tf;
+                        texFrameMap.put(tex[i], tf);
                     }
-                }
-                initGLStreamImpl(gl, tex);
-                
-                for(int i=0; i<textureCount; i++) {
-                    final TextureFrame tf = createTexImage(gl, i, tex); 
-                    texFrames[i] = tf;
-                    texFrameMap.put(tex[i], tf);
                 }
                 state = State.Stopped;
                 return state;
@@ -216,9 +218,9 @@ public abstract class GLMediaPlayerImpl implements GLMediaPlayer {
      * @see #vcodec
     */
     protected abstract void initGLStreamImpl(GL gl, int[] texNames) throws IOException;
-
-    protected TextureFrame createTexImage(GL gl, int idx, int[] tex) {
-        return new TextureFrame( createTexImageImpl(gl, idx, tex, true) );
+    
+    protected TextureSequence.TextureFrame createTexImage(GL gl, int idx, int[] tex) {
+        return new TextureSequence.TextureFrame( createTexImageImpl(gl, idx, tex, false) );
     }
     
     protected Texture createTexImageImpl(GL gl, int idx, int[] tex, boolean mustFlipVertically) {
@@ -264,14 +266,14 @@ public abstract class GLMediaPlayerImpl implements GLMediaPlayer {
                      mustFlipVertically);        
     }
     
-    protected void destroyTexImage(GL gl, TextureFrame imgTex) {
+    protected void destroyTexImage(GL gl, TextureSequence.TextureFrame imgTex) {
         imgTex.getTexture().destroy(gl);        
     }
     
     protected void removeAllImageTextures(GL gl) {
         if(null != texFrames) {
             for(int i=0; i<textureCount; i++) {
-                final TextureFrame imgTex = texFrames[i];
+                final TextureSequence.TextureFrame imgTex = texFrames[i];
                 if(null != imgTex) {
                     destroyTexImage(gl, imgTex);
                     texFrames[i] = null;
diff --git a/src/jogl/classes/jogamp/opengl/util/av/NullGLMediaPlayer.java b/src/jogl/classes/jogamp/opengl/util/av/NullGLMediaPlayer.java
index a5d41bc9c..c97f04225 100644
--- a/src/jogl/classes/jogamp/opengl/util/av/NullGLMediaPlayer.java
+++ b/src/jogl/classes/jogamp/opengl/util/av/NullGLMediaPlayer.java
@@ -25,7 +25,7 @@
  * authors and should not be interpreted as representing official policies, either expressed
  * or implied, of JogAmp Community.
  */
-package jogamp.opengl.av;
+package jogamp.opengl.util.av;
 
 import java.io.IOException;
 import java.net.URLConnection;
@@ -34,21 +34,21 @@ import java.nio.ByteBuffer;
 import javax.media.opengl.GL;
 import javax.media.opengl.GLProfile;
 
-import jogamp.opengl.av.GLMediaPlayerImpl;
+import jogamp.opengl.util.av.GLMediaPlayerImpl;
 
 import com.jogamp.common.nio.Buffers;
 import com.jogamp.common.util.IOUtil;
 import com.jogamp.opengl.util.texture.Texture;
-import com.jogamp.opengl.util.texture.TextureCoords;
 import com.jogamp.opengl.util.texture.TextureData;
 import com.jogamp.opengl.util.texture.TextureIO;
+import com.jogamp.opengl.util.texture.TextureSequence;
 
 /***
  * A dummy null media player implementation using a static test frame (if available).
  */
 public class NullGLMediaPlayer extends GLMediaPlayerImpl {
     private TextureData texData = null;
-    private TextureFrame frame = null;
+    private TextureSequence.TextureFrame frame = null;
     private long pos_ms = 0;
     private long pos_start = 0;
     
@@ -91,20 +91,15 @@ public class NullGLMediaPlayer extends GLMediaPlayerImpl {
     }
     
     @Override
-    public TextureFrame getLastTexture() {
+    public TextureSequence.TextureFrame getLastTexture() {
         return frame;
     }
 
     @Override
-    public TextureFrame getNextTexture(GL gl, boolean blocking) {
+    public TextureSequence.TextureFrame getNextTexture(GL gl, boolean blocking) {
         return frame;
     }
     
-    @Override
-    public TextureCoords getTextureCoords() {
-        return frame.getTexture().getImageTexCoords();
-    }
-    
     @Override
     public long getCurrentPosition() {
         pos_ms = System.currentTimeMillis() - pos_start;
@@ -151,20 +146,23 @@ public class NullGLMediaPlayer extends GLMediaPlayerImpl {
     }
     
     @Override
-    protected void destroyTexImage(GL gl, TextureFrame imgTex) {
-        super.destroyTexImage(gl, imgTex);
-    }
-    
-    @Override
-    protected TextureFrame createTexImage(GL gl, int idx, int[] tex) {
+    protected TextureSequence.TextureFrame createTexImage(GL gl, int idx, int[] tex) {
         Texture texture = super.createTexImageImpl(gl, idx, tex, false);
         if(null != texData) {
             texture.updateImage(gl, texData);
+            texData.destroy();
+            texData = null;
         }                      
-        frame = new TextureFrame( texture );
+        frame = new TextureSequence.TextureFrame( texture );
         return frame;
     }
     
+    @Override
+    protected void destroyTexImage(GL gl, TextureSequence.TextureFrame imgTex) {
+        frame = null;
+        super.destroyTexImage(gl, imgTex);
+    }
+    
     private void validatePos() {
         boolean considerPausing = false;
         if( 0 > pos_ms) {
-- 
cgit v1.2.3