Project

General

Profile

Download (8.68 KB) Statistics
| Branch: | Revision:

library / src / main / java / org / distorted / library / DistortedSurface.java @ 6e7c8721

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.library;
21

    
22
import java.util.HashMap;
23
import java.util.LinkedList;
24

    
25
///////////////////////////////////////////////////////////////////////////////////////////////////
26
/**
27
 * Keep all objects created in a static LinkedList. The point: we need to be able to mark
28
 * Objects for deletion, and delete all marked Objects later at a convenient time (that's
29
 * because we can only delete from a thread that holds the OpenGL context so here we provide a
30
 * framework where one is able to mark for deletion at any time and actual deletion takes place
31
 * on the next render).
32
*/
33
abstract class DistortedSurface
34
  {
35
  static final int FAILED_TO_CREATE = 1;
36
  static final int NOT_CREATED_YET  = 2;
37
  static final int DONT_CREATE      = 3;
38
  static final int CREATED          = 4;
39

    
40
  static final int TYPE_USER = 0;
41
  static final int TYPE_TREE = 1;
42
  static final int TYPE_SYST = 2;
43

    
44
  private static final int JOB_CREATE = 0;
45
  private static final int JOB_DELETE = 1;
46

    
47
  private class Job
48
    {
49
    DistortedSurface surface;
50
    int action;
51

    
52
    Job(DistortedSurface s, int a)
53
      {
54
      surface = s;
55
      action  = a;
56
      }
57
    }
58

    
59
  private static boolean mToDo = false;
60
  private static LinkedList<DistortedSurface> mDoneList = new LinkedList<>();
61
  private static HashMap<Long,Job> mToDoMap = new HashMap<>();
62
  private static long mNextClientID = 0;
63
  private static long mNextSystemID = 0;
64

    
65
  private long mID;
66
  private int mType;
67
  int mColorCreated;
68
  int[] mColorH = new int[1];
69
  int mWidth, mHeight;
70

    
71
///////////////////////////////////////////////////////////////////////////////////////////////////
72

    
73
  abstract void create();
74
  abstract void delete();
75
  abstract void recreate();
76

    
77
///////////////////////////////////////////////////////////////////////////////////////////////////
78
// must be called from a thread holding OpenGL Context
79

    
80
  static synchronized void toDo()
81
    {
82
    if( mToDo )
83
      {
84
      Job job;
85
      DistortedSurface surface;
86

    
87
      for(Long key: mToDoMap.keySet())
88
        {
89
        job = mToDoMap.get(key);
90
        surface = job.surface;
91

    
92
        //android.util.Log.d("SURFACE", "  ---> need to "+(job.action==JOB_CREATE ? "create":"delete")+" surfaceID="+surface.getID() );
93

    
94
        if( job.action==JOB_CREATE )
95
          {
96
          surface.create();
97
          mDoneList.add(surface);
98
          }
99
        else if( job.action==JOB_DELETE )
100
          {
101
          surface.delete();
102
          }
103
        }
104

    
105
      mToDoMap.clear();
106
      mToDo = false;
107
      }
108
    }
109

    
110
///////////////////////////////////////////////////////////////////////////////////////////////////
111

    
112
  static synchronized void onPause()
113
    {
114
    DistortedSurface surface;
115
    int num = mDoneList.size();
116

    
117
    for(int i=0; i<num; i++)
118
      {
119
      surface = mDoneList.removeFirst();
120
      mToDoMap.put(surface.getID(), surface.new Job(surface,JOB_CREATE) );
121
      surface.recreate();
122
      }
123

    
124
    mToDo = true;
125
    }
126

    
127
///////////////////////////////////////////////////////////////////////////////////////////////////
128

    
129
  static synchronized void onDestroy()
130
    {
131
    mToDoMap.clear();
132
    mDoneList.clear();
133

    
134
    mToDo = true;
135
    mNextClientID = 0;
136
    }
137

    
138
///////////////////////////////////////////////////////////////////////////////////////////////////
139

    
140
  @SuppressWarnings("unused")
141
  static void debugLists()
142
    {
143
    android.util.Log.e("Surface", "Done list:");
144

    
145
    DistortedSurface surface;
146
    int num = mDoneList.size();
147

    
148
    for(int i=0; i<num; i++)
149
      {
150
      surface = mDoneList.get(i);
151
      surface.print(i, "");
152
      }
153

    
154
    android.util.Log.e("Surface", "ToDo list:");
155

    
156
    Job job;
157
    int i=0;
158

    
159
    for(Long key: mToDoMap.keySet())
160
      {
161
      job = mToDoMap.get(key);
162
      job.surface.print(i++, job.action==JOB_CREATE ? " create":" delete");
163
      }
164
    }
165

    
166
///////////////////////////////////////////////////////////////////////////////////////////////////
167

    
168
  private void print(int i, String extra)
169
    {
170
    String str;
171

    
172
    if( this instanceof DistortedFramebuffer ) str = (i+": Framebuffer ");
173
    else if( this instanceof DistortedTexture) str = (i+": Texture     ");
174
    else if( this instanceof DistortedScreen ) str = (i+": Screen      ");
175
    else                                       str = (i+": UNKNOWN     ");
176

    
177
    str += ("("+getWidth()+","+getHeight()+") surfaceID:"+getID());
178

    
179
    switch(mType)
180
      {
181
      case TYPE_SYST: str+=" SYSTEM"; break;
182
      case TYPE_USER: str+=" USER"  ; break;
183
      case TYPE_TREE: str+=" TREE"  ; break;
184
      default       : str+=" ERROR??";
185
      }
186

    
187
    android.util.Log.e("Surface", str+extra);
188
    }
189

    
190
///////////////////////////////////////////////////////////////////////////////////////////////////
191

    
192
  DistortedSurface(int width, int height, int create, int type)
193
    {
194
    mWidth        = width ;
195
    mHeight       = height;
196
    mColorCreated = create;
197
    mColorH[0]    = 0;
198
    mID           = type==TYPE_SYST ? --mNextSystemID : ++mNextClientID;
199
    mType         = type;
200

    
201
    if( create!=DONT_CREATE )
202
      {
203
      mToDoMap.put(mID, new Job(this,JOB_CREATE) );
204
      mToDo = true;
205
      }
206
    }
207

    
208
///////////////////////////////////////////////////////////////////////////////////////////////////
209

    
210
  synchronized void markForCreation()
211
    {
212
    mDoneList.remove(this);
213
    mToDoMap.put(mID, new Job(this,JOB_CREATE) );
214
    mToDo = true;
215
    }
216

    
217
///////////////////////////////////////////////////////////////////////////////////////////////////
218
// PUBLIC API
219
///////////////////////////////////////////////////////////////////////////////////////////////////
220
/**
221
 * Mark the underlying OpenGL object for deletion. Actual deletion will take place on the next render.
222
 */
223
  synchronized public void markForDeletion()
224
    {
225
    mDoneList.remove(this);
226
    mToDoMap.put(mID, new Job(this,JOB_DELETE) );
227
    mToDo = true;
228
    }
229

    
230
////////////////////////////////////////////////////////////////////////////////////////////////////
231
/**
232
 * Return unique ID of this Surface.
233
 */
234
  public long getID()
235
    {
236
    return mID;
237
    }
238

    
239
///////////////////////////////////////////////////////////////////////////////////////////////////
240

    
241
/**
242
 * Return the width of this Surface.
243
 *
244
 * @return width of the Object, in pixels.
245
 */
246
  public int getWidth()
247
    {
248
    return mWidth;
249
    }
250

    
251
///////////////////////////////////////////////////////////////////////////////////////////////////
252
/**
253
 * Return the height of this Surface.
254
 *
255
 * @return height of the Object, in pixels.
256
 */
257
  public int getHeight()
258
    {
259
    return mHeight;
260
    }
261

    
262
///////////////////////////////////////////////////////////////////////////////////////////////////
263
/**
264
 * Return the depth of this Surface.
265
 * <p>
266
 * Admittedly quite a strange method. Why do we need to pass a Mesh to it? Because one cannot determine
267
 * 'depth' of a Surface (bitmap really!) when rendered based only on the texture itself, that depends
268
 * on the Mesh it is rendered with.
269
 *
270
 * @return depth of the Object, in pixels.
271
 */
272
  public int getDepth(MeshObject mesh)
273
    {
274
    return mesh==null ? 0 : (int)(mWidth*mesh.zFactor);
275
    }
276
  }
(12-12/24)