| 
      1
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      2
     | 
    
      // Copyright 2016 Leszek Koltunski                                                               //
 
     | 
  
  
    | 
      3
     | 
    
      //                                                                                               //
 
     | 
  
  
    | 
      4
     | 
    
      // This file is part of Distorted.                                                               //
 
     | 
  
  
    | 
      5
     | 
    
      //                                                                                               //
 
     | 
  
  
    | 
      6
     | 
    
      // Distorted is free software: you can redistribute it and/or modify                             //
 
     | 
  
  
    | 
      7
     | 
    
      // it under the terms of the GNU General Public License as published by                          //
 
     | 
  
  
    | 
      8
     | 
    
      // the Free Software Foundation, either version 2 of the License, or                             //
 
     | 
  
  
    | 
      9
     | 
    
      // (at your option) any later version.                                                           //
 
     | 
  
  
    | 
      10
     | 
    
      //                                                                                               //
 
     | 
  
  
    | 
      11
     | 
    
      // Distorted is distributed in the hope that it will be useful,                                  //
 
     | 
  
  
    | 
      12
     | 
    
      // but WITHOUT ANY WARRANTY; without even the implied warranty of                                //
 
     | 
  
  
    | 
      13
     | 
    
      // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                                 //
 
     | 
  
  
    | 
      14
     | 
    
      // GNU General Public License for more details.                                                  //
 
     | 
  
  
    | 
      15
     | 
    
      //                                                                                               //
 
     | 
  
  
    | 
      16
     | 
    
      // You should have received a copy of the GNU General Public License                             //
 
     | 
  
  
    | 
      17
     | 
    
      // along with Distorted.  If not, see <http://www.gnu.org/licenses/>.                            //
 
     | 
  
  
    | 
      18
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      19
     | 
    
      
 
     | 
  
  
    | 
      20
     | 
    
      package org.distorted.examples.plainmonalisa;
 
     | 
  
  
    | 
      21
     | 
    
      
 
     | 
  
  
    | 
      22
     | 
    
      import android.content.Context;
 
     | 
  
  
    | 
      23
     | 
    
      import android.view.Choreographer;
 
     | 
  
  
    | 
      24
     | 
    
      import android.view.SurfaceView;
 
     | 
  
  
    | 
      25
     | 
    
      import android.view.SurfaceHolder;
 
     | 
  
  
    | 
      26
     | 
    
      import android.util.Log;
 
     | 
  
  
    | 
      27
     | 
    
      
 
     | 
  
  
    | 
      28
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      29
     | 
    
      
 
     | 
  
  
    | 
      30
     | 
    
      class PlainMonaLisaSurfaceView extends SurfaceView implements SurfaceHolder.Callback, Choreographer.FrameCallback
 
     | 
  
  
    | 
      31
     | 
    
        {
     | 
  
  
    | 
      32
     | 
    
        private static final String TAG = "MonaLisaSurface";
 
     | 
  
  
    | 
      33
     | 
    
        private RenderThread mRenderThread;
 
     | 
  
  
    | 
      34
     | 
    
        private static volatile boolean mPaused = true;
 
     | 
  
  
    | 
      35
     | 
    
      
 
     | 
  
  
    | 
      36
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      37
     | 
    
      
 
     | 
  
  
    | 
      38
     | 
    
        public PlainMonaLisaSurfaceView(Context context)
 
     | 
  
  
    | 
      39
     | 
    
          {
     | 
  
  
    | 
      40
     | 
    
          super(context);
 
     | 
  
  
    | 
      41
     | 
    
          getHolder().addCallback(this);
 
     | 
  
  
    | 
      42
     | 
    
          }
 
     | 
  
  
    | 
      43
     | 
    
      
 
     | 
  
  
    | 
      44
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      45
     | 
    
      
 
     | 
  
  
    | 
      46
     | 
    
        public void surfaceCreated(SurfaceHolder holder)
 
     | 
  
  
    | 
      47
     | 
    
          {
     | 
  
  
    | 
      48
     | 
    
          Log.d(TAG, "surfaceCreated holder=" + holder);
 
     | 
  
  
    | 
      49
     | 
    
      
 
     | 
  
  
    | 
      50
     | 
    
          mRenderThread = new RenderThread(holder, this);
 
     | 
  
  
    | 
      51
     | 
    
          mRenderThread.setName("GL render");
     | 
  
  
    | 
      52
     | 
    
          mRenderThread.start();
 
     | 
  
  
    | 
      53
     | 
    
          mRenderThread.waitUntilReady();
 
     | 
  
  
    | 
      54
     | 
    
      
 
     | 
  
  
    | 
      55
     | 
    
          RenderHandler rh = mRenderThread.getHandler();
 
     | 
  
  
    | 
      56
     | 
    
      
 
     | 
  
  
    | 
      57
     | 
    
          if (rh != null)
 
     | 
  
  
    | 
      58
     | 
    
            {
     | 
  
  
    | 
      59
     | 
    
            rh.sendSurfaceCreated();
 
     | 
  
  
    | 
      60
     | 
    
            }
 
     | 
  
  
    | 
      61
     | 
    
      
 
     | 
  
  
    | 
      62
     | 
    
          Choreographer.getInstance().postFrameCallback(this);
 
     | 
  
  
    | 
      63
     | 
    
          }
 
     | 
  
  
    | 
      64
     | 
    
      
 
     | 
  
  
    | 
      65
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      66
     | 
    
      
 
     | 
  
  
    | 
      67
     | 
    
        public void surfaceChanged(SurfaceHolder holder, int format, int width, int height)
 
     | 
  
  
    | 
      68
     | 
    
          {
     | 
  
  
    | 
      69
     | 
    
          Log.d(TAG, "surfaceChanged fmt=" + format + " size=" + width + "x" + height +" holder=" + holder);
 
     | 
  
  
    | 
      70
     | 
    
      
 
     | 
  
  
    | 
      71
     | 
    
          RenderHandler rh = mRenderThread.getHandler();
 
     | 
  
  
    | 
      72
     | 
    
      
 
     | 
  
  
    | 
      73
     | 
    
          if (rh != null)
 
     | 
  
  
    | 
      74
     | 
    
            {
     | 
  
  
    | 
      75
     | 
    
            rh.sendSurfaceChanged(format, width, height);
 
     | 
  
  
    | 
      76
     | 
    
            }
 
     | 
  
  
    | 
      77
     | 
    
          }
 
     | 
  
  
    | 
      78
     | 
    
      
 
     | 
  
  
    | 
      79
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      80
     | 
    
      
 
     | 
  
  
    | 
      81
     | 
    
        public void surfaceDestroyed(SurfaceHolder holder)
 
     | 
  
  
    | 
      82
     | 
    
          {
     | 
  
  
    | 
      83
     | 
    
          Log.d(TAG, "surfaceDestroyed holder=" + holder);
 
     | 
  
  
    | 
      84
     | 
    
      
 
     | 
  
  
    | 
      85
     | 
    
          // We need to wait for the render thread to shut down before continuing because we
 
     | 
  
  
    | 
      86
     | 
    
          // don't want the Surface to disappear out from under it mid-render.  The frame
 
     | 
  
  
    | 
      87
     | 
    
          // notifications will have been stopped back in onPause(), but there might have
 
     | 
  
  
    | 
      88
     | 
    
          // been one in progress.
 
     | 
  
  
    | 
      89
     | 
    
      
 
     | 
  
  
    | 
      90
     | 
    
          RenderHandler rh = mRenderThread.getHandler();
 
     | 
  
  
    | 
      91
     | 
    
      
 
     | 
  
  
    | 
      92
     | 
    
          if (rh != null)
 
     | 
  
  
    | 
      93
     | 
    
            {
     | 
  
  
    | 
      94
     | 
    
            rh.sendShutdown();
 
     | 
  
  
    | 
      95
     | 
    
      
 
     | 
  
  
    | 
      96
     | 
    
            try
 
     | 
  
  
    | 
      97
     | 
    
              {
     | 
  
  
    | 
      98
     | 
    
              mRenderThread.join();
 
     | 
  
  
    | 
      99
     | 
    
              }
 
     | 
  
  
    | 
      100
     | 
    
            catch (InterruptedException ie)
 
     | 
  
  
    | 
      101
     | 
    
              {
     | 
  
  
    | 
      102
     | 
    
              throw new RuntimeException("join was interrupted", ie);
     | 
  
  
    | 
      103
     | 
    
              }
 
     | 
  
  
    | 
      104
     | 
    
            }
 
     | 
  
  
    | 
      105
     | 
    
          mRenderThread = null;
 
     | 
  
  
    | 
      106
     | 
    
      
 
     | 
  
  
    | 
      107
     | 
    
          Log.d(TAG, "surfaceDestroyed complete");
 
     | 
  
  
    | 
      108
     | 
    
          }
 
     | 
  
  
    | 
      109
     | 
    
      
 
     | 
  
  
    | 
      110
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      111
     | 
    
      
 
     | 
  
  
    | 
      112
     | 
    
        public void onPause()
 
     | 
  
  
    | 
      113
     | 
    
          {
     | 
  
  
    | 
      114
     | 
    
          mPaused = true;
 
     | 
  
  
    | 
      115
     | 
    
      
 
     | 
  
  
    | 
      116
     | 
    
          Log.d(TAG, "onPause unhooking choreographer");
 
     | 
  
  
    | 
      117
     | 
    
          Choreographer.getInstance().removeFrameCallback(this);
 
     | 
  
  
    | 
      118
     | 
    
          }
 
     | 
  
  
    | 
      119
     | 
    
      
 
     | 
  
  
    | 
      120
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      121
     | 
    
      
 
     | 
  
  
    | 
      122
     | 
    
        public void onResume()
 
     | 
  
  
    | 
      123
     | 
    
          {
     | 
  
  
    | 
      124
     | 
    
          mPaused = false;
 
     | 
  
  
    | 
      125
     | 
    
      
 
     | 
  
  
    | 
      126
     | 
    
          if (mRenderThread != null)
 
     | 
  
  
    | 
      127
     | 
    
            {
     | 
  
  
    | 
      128
     | 
    
            Log.d(TAG, "onResume re-hooking choreographer");
 
     | 
  
  
    | 
      129
     | 
    
            Choreographer.getInstance().postFrameCallback(this);
 
     | 
  
  
    | 
      130
     | 
    
            }
 
     | 
  
  
    | 
      131
     | 
    
          }
 
     | 
  
  
    | 
      132
     | 
    
      
 
     | 
  
  
    | 
      133
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      134
     | 
    
      
 
     | 
  
  
    | 
      135
     | 
    
        public static boolean isPaused()
 
     | 
  
  
    | 
      136
     | 
    
          {
     | 
  
  
    | 
      137
     | 
    
          return mPaused;
 
     | 
  
  
    | 
      138
     | 
    
          }
 
     | 
  
  
    | 
      139
     | 
    
      
 
     | 
  
  
    | 
      140
     | 
    
      ///////////////////////////////////////////////////////////////////////////////////////////////////
 
     | 
  
  
    | 
      141
     | 
    
      
 
     | 
  
  
    | 
      142
     | 
    
        @Override
 
     | 
  
  
    | 
      143
     | 
    
        public void doFrame(long frameTimeNanos)
 
     | 
  
  
    | 
      144
     | 
    
          {
     | 
  
  
    | 
      145
     | 
    
          RenderHandler rh = mRenderThread.getHandler();
 
     | 
  
  
    | 
      146
     | 
    
      
 
     | 
  
  
    | 
      147
     | 
    
          if (rh != null)
 
     | 
  
  
    | 
      148
     | 
    
            {
     | 
  
  
    | 
      149
     | 
    
            Choreographer.getInstance().postFrameCallback(this);
 
     | 
  
  
    | 
      150
     | 
    
            rh.sendDoFrame(frameTimeNanos);
 
     | 
  
  
    | 
      151
     | 
    
            }
 
     | 
  
  
    | 
      152
     | 
    
          }
 
     | 
  
  
    | 
      153
     | 
    
        }
 
     | 
  
  
    | 
      154
     | 
    
      
 
     | 
  
  
    | 
      155
     | 
    
      
 
     |