Project

General

Profile

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

library / src / main / java / org / distorted / library / DistortedSurface.java @ 07037b8a

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.LinkedList;
23

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

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

    
43
  private static boolean mToDo = false;
44
  private static LinkedList<DistortedSurface> mDoneList = new LinkedList<>();
45
  private static LinkedList<DistortedSurface> mToDoList = new LinkedList<>();
46
  private static long mNextClientID = 0;
47
  private static long mNextSystemID = 0;
48

    
49
  private long mID;
50
  private boolean mMarked;
51
  private int mType;
52
  int mColorCreated;
53
  int[] mColorH = new int[1];
54
  int mSizeX, mSizeY;  // in screen space
55

    
56
///////////////////////////////////////////////////////////////////////////////////////////////////
57

    
58
  abstract void create();
59
  abstract void delete();
60
  abstract void recreate();
61

    
62
///////////////////////////////////////////////////////////////////////////////////////////////////
63
// must be called form a thread holding OpenGL Context
64

    
65
  static synchronized void toDo()
66
    {
67
    if( mToDo )
68
      {
69
      DistortedSurface surface;
70

    
71
      int num = mToDoList.size();
72

    
73
      for(int i=0; i<num; i++)
74
        {
75
        surface = mToDoList.removeFirst();
76

    
77
        if(surface.mMarked)
78
          {
79
          surface.delete();
80
          surface.mMarked = false;
81
          }
82
        else
83
          {
84
          surface.create();
85
          mDoneList.add(surface);
86
          }
87
        }
88

    
89
      mToDo = false;
90
      }
91
    }
92

    
93
///////////////////////////////////////////////////////////////////////////////////////////////////
94

    
95
  static synchronized void onDestroy()
96
    {
97
    DistortedSurface surface;
98

    
99
    int num = mDoneList.size();
100

    
101
    for(int i=0; i<num; i++)
102
      {
103
      surface = mDoneList.removeFirst();
104

    
105
      if( surface.mType==TYPE_SYST )
106
        {
107
        mToDoList.add(surface);
108
        surface.recreate();
109
        }
110
      }
111

    
112
    num = mToDoList.size();
113

    
114
    for(int i=0; i<num; i++)
115
      {
116
      surface = mToDoList.get(i);
117

    
118
      if( surface.mType!=TYPE_SYST )
119
        {
120
        mDoneList.remove(i);
121
        i--;
122
        num--;
123
        }
124
      }
125

    
126
    mToDo = (num>0);
127
    mNextClientID = 0;
128
    }
129

    
130
///////////////////////////////////////////////////////////////////////////////////////////////////
131

    
132
  synchronized void moveToToDo()
133
    {
134
    if ( mDoneList.remove(this) )
135
      {
136
      mToDoList.add(this);
137
      mToDo = true;
138
      }
139
    }
140

    
141
///////////////////////////////////////////////////////////////////////////////////////////////////
142

    
143
  @SuppressWarnings("unused")
144
  static void debugLists()
145
    {
146
    android.util.Log.e("Surface", "Done list:");
147
    debugList(mDoneList);
148
    android.util.Log.e("Surface", "ToDo list:");
149
    debugList(mToDoList);
150
    }
151

    
152
///////////////////////////////////////////////////////////////////////////////////////////////////
153

    
154
  private static void debugList(LinkedList<DistortedSurface> list)
155
    {
156
    DistortedSurface surface;
157
    String str;
158

    
159
    int num = list.size();
160

    
161
    for(int i=0; i<num; i++)
162
      {
163
      surface = list.get(i);
164

    
165
      if( surface instanceof DistortedFramebuffer ) str = (i+": Framebuffer ");
166
      else if( surface instanceof DistortedTexture) str = (i+": Texture     ");
167
      else if( surface instanceof DistortedScreen ) str = (i+": Screen      ");
168
      else                                          str = (i+": UNKNOWN     ");
169

    
170
      str += ("("+surface.getWidth()+","+surface.getHeight()+") surfaceID:"+surface.getID());
171

    
172
      switch(surface.mType)
173
        {
174
        case TYPE_SYST: str+=" SYSTEM"; break;
175
        case TYPE_USER: str+=" USER"  ; break;
176
        case TYPE_TREE: str+=" TREE"  ; break;
177
        default       : str+=" ERROR??";
178
        }
179

    
180
      android.util.Log.e("Surface", str);
181
      }
182
    }
183

    
184
///////////////////////////////////////////////////////////////////////////////////////////////////
185

    
186
  DistortedSurface(int width, int height, int create, int type)
187
    {
188
    mSizeX        = width ;
189
    mSizeY        = height;
190
    mColorCreated = create;
191
    mColorH[0]    = 0;
192
    mMarked       = false;
193
    mID           = type==TYPE_SYST ? --mNextSystemID : ++mNextClientID;
194
    mType         = type;
195

    
196
    if( create!=DONT_CREATE )
197
      {
198
      mToDoList.add(this);
199
      mToDo = true;
200
      }
201
    }
202

    
203
///////////////////////////////////////////////////////////////////////////////////////////////////
204
// PUBLIC API
205
///////////////////////////////////////////////////////////////////////////////////////////////////
206
/**
207
 * Mark the underlying OpenGL object for deletion. Actual deletion will take place on the next render.
208
 */
209
  public void markForDeletion()
210
    {
211
    if( !mMarked )
212
      {
213
      mToDo   = true;
214
      mMarked = true;
215
      mDoneList.remove(this);
216
      mToDoList.add(this);
217
      }
218
    }
219

    
220
////////////////////////////////////////////////////////////////////////////////////////////////////
221
/**
222
 * Return unique ID of this Surface.
223
 */
224
  public long getID()
225
    {
226
    return mID;
227
    }
228

    
229
///////////////////////////////////////////////////////////////////////////////////////////////////
230

    
231
/**
232
 * Return the height of this Surface.
233
 *
234
 * @return height of the object, in pixels.
235
 */
236
  public int getWidth()
237
    {
238
    return mSizeX;
239
    }
240

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

    
252
///////////////////////////////////////////////////////////////////////////////////////////////////
253
/**
254
 * Return the depth of this Surface.
255
 * <p>
256
 * Admittedly quite a strange method. Why do we need to pass a Mesh to it? Because one cannot determine
257
 * 'depth' of a Surface (bitmap really!) when rendered based only on the texture itself, that depends
258
 * on the Mesh it is rendered with.
259
 *
260
 * @return depth of the Object, in pixels.
261
 */
262
  public int getDepth(MeshObject mesh)
263
    {
264
    return mesh==null ? 0 : (int)(mSizeX*mesh.zFactor);
265
    }
266
  }
(10-10/22)