Project

General

Profile

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

library / src / main / java / org / distorted / library / DistortedRenderState.java @ b3120b1b

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 android.opengl.GLES30;
23

    
24
///////////////////////////////////////////////////////////////////////////////////////////////////
25
/**
26
 * Remember the OpenGL state.
27
 * <p>
28
 * This is a member of DistortedNode. Remembers the OpenGL state we want to set just before rendering
29
 * the Node.
30
 */
31
class DistortedRenderState
32
{
33
  // TODO: figure this out dynamically; this assumes 8 bit stencil buffer.
34
  private static final int STENCIL_MASK = (1<<8)-1;
35

    
36
  private static int sColorMaskR, sColorMaskG, sColorMaskB, sColorMaskA;   //
37
  private static int sDepthMask;                                           //
38
  private static int sStencilMask;                                         //
39
  private static int sDepthTest;                                           //
40
  private static int sStencilTest;                                         //
41
  private static int sStencilFuncFunc, sStencilFuncRef, sStencilFuncMask;  // current OpenGL state
42
  private static int sStencilOpSfail, sStencilOpDpfail, sStencilOpDppass;  //
43
  private static int sDepthFunc;                                           //
44
  private static int sBlend;                                               //
45
  private static int sBlendSrc, sBlendDst;                                 //
46

    
47
  private int mColorMaskR, mColorMaskG, mColorMaskB, mColorMaskA;          //
48
  private int mDepthMask;                                                  //
49
  private int mStencilMask;                                                //
50
  private int mDepthTest;                                                  //
51
  private int mStencilTest;                                                //
52
  private int mStencilFuncFunc, mStencilFuncRef, mStencilFuncMask;         // The state we want to have
53
  private int mStencilOpSfail, mStencilOpDpfail, mStencilOpDppass;         //
54
  private int mDepthFunc;                                                  //
55
  private int mBlend;                                                      //
56
  private int mBlendSrc, mBlendDst;                                        //
57
  private int mClear;                                                      // This does not have a 'static' compatriot
58

    
59
  private static int rStencilTest;                                         //
60
  private static int rStencilFuncFunc;                                     //
61
  private static int rStencilFuncRef;                                      // Remember values of Stencil.
62
  private static int rStencilFuncMask;                                     //
63
  private static int rStencilMask;                                         //
64

    
65
///////////////////////////////////////////////////////////////////////////////////////////////////
66
// default: color writes on, depth test and writes on, blending on, stencil off.
67

    
68
  DistortedRenderState()
69
    {
70
    mColorMaskR = 1;
71
    mColorMaskG = 1;
72
    mColorMaskB = 1;
73
    mColorMaskA = 1;
74

    
75
    mDepthTest  = 1;
76
    mDepthMask  = 1;
77
    mDepthFunc  = GLES30.GL_LEQUAL;
78

    
79
    mBlend      = 1;
80
    mBlendSrc   = GLES30.GL_SRC_ALPHA;
81
    mBlendDst   = GLES30.GL_ONE_MINUS_SRC_ALPHA;
82

    
83
    mStencilTest     = 0;
84
    mStencilMask     = STENCIL_MASK;
85
    mStencilFuncFunc = GLES30.GL_NEVER;
86
    mStencilFuncRef  = 0;
87
    mStencilFuncMask = STENCIL_MASK;
88
    mStencilOpSfail  = GLES30.GL_KEEP;
89
    mStencilOpDpfail = GLES30.GL_KEEP;
90
    mStencilOpDppass = GLES30.GL_KEEP;
91

    
92
    mClear = 0;
93
    }
94

    
95
///////////////////////////////////////////////////////////////////////////////////////////////////
96
// reset state of everything to 'unknown'
97

    
98
  static void reset()
99
    {
100
    sColorMaskR = -1;
101
    sColorMaskG = -1;
102
    sColorMaskB = -1;
103
    sColorMaskA = -1;
104

    
105
    sDepthTest  = -1;
106
    sDepthMask  = -1;
107
    sDepthFunc  = -1;
108

    
109
    sBlend      = -1;
110
    sBlendSrc   = -1;
111
    sBlendDst   = -1;
112

    
113
    sStencilTest     = -1;
114
    sStencilMask     = -1;
115
    sStencilFuncFunc = -1;
116
    sStencilFuncRef  = -1;
117
    sStencilFuncMask = -1;
118
    sStencilOpSfail  = -1;
119
    sStencilOpDpfail = -1;
120
    sStencilOpDppass = -1;
121
    }
122

    
123
///////////////////////////////////////////////////////////////////////////////////////////////////
124

    
125
  static void colorDepthStencilOn()
126
    {
127
    if( sColorMaskR!=1 || sColorMaskG!=1 || sColorMaskB!=1 || sColorMaskA!=1 )
128
      {
129
      sColorMaskR = 1;
130
      sColorMaskG = 1;
131
      sColorMaskB = 1;
132
      sColorMaskA = 1;
133
      GLES30.glColorMask(true,true,true,true);
134
      }
135
    if( sDepthMask!=1 )
136
      {
137
      sDepthMask = 1;
138
      GLES30.glDepthMask(true);
139
      }
140
    if( sStencilMask!= STENCIL_MASK )
141
      {
142
      sStencilMask = STENCIL_MASK;
143
      GLES30.glStencilMask(sStencilMask);
144
      }
145
    }
146

    
147
///////////////////////////////////////////////////////////////////////////////////////////////////
148

    
149
  static void switchOffDrawing()
150
    {
151
    GLES30.glEnable(GLES30.GL_SCISSOR_TEST);
152
    GLES30.glScissor(0,0,0,0);
153
    }
154

    
155
///////////////////////////////////////////////////////////////////////////////////////////////////
156

    
157
  static void restoreDrawing()
158
    {
159
    GLES30.glDisable(GLES30.GL_SCISSOR_TEST);
160
    }
161

    
162
///////////////////////////////////////////////////////////////////////////////////////////////////
163

    
164
  static void setUpStencilMark()
165
    {
166
    if( sStencilTest!=1 )
167
      {
168
      sStencilTest = 1;
169
      //android.util.Log.d("State", "stencil test on");
170
      GLES30.glEnable(GLES30.GL_STENCIL_TEST);
171
      }
172
    if( sStencilFuncFunc!=GLES30.GL_ALWAYS || sStencilFuncRef!=1 || sStencilFuncMask!=STENCIL_MASK )
173
      {
174
      sStencilFuncFunc = GLES30.GL_ALWAYS;
175
      sStencilFuncRef  = 1;
176
      sStencilFuncMask = STENCIL_MASK;
177
      //android.util.Log.d("State", "stencil func on");
178
      GLES30.glStencilFunc(sStencilFuncFunc,sStencilFuncRef,sStencilFuncMask);
179
      }
180
    if( sStencilOpSfail!=GLES30.GL_KEEP || sStencilOpDpfail!=GLES30.GL_KEEP || sStencilOpDppass!=GLES30.GL_REPLACE )
181
      {
182
      sStencilOpSfail = GLES30.GL_KEEP;
183
      sStencilOpDpfail= GLES30.GL_KEEP;
184
      sStencilOpDppass= GLES30.GL_REPLACE;
185
      //android.util.Log.d("State", "stencil op on");
186
      GLES30.glStencilOp(sStencilOpSfail,sStencilOpDpfail,sStencilOpDppass);
187
      }
188
    if( sColorMaskR!=0 || sColorMaskG!=0 || sColorMaskB!=0 || sColorMaskA!=0 )
189
      {
190
      sColorMaskR = 0;
191
      sColorMaskG = 0;
192
      sColorMaskB = 0;
193
      sColorMaskA = 0;
194
      //android.util.Log.d("State", "switch off color writing");
195
      GLES30.glColorMask(false,false,false,false);
196
      }
197
    if( sDepthMask!=0 )
198
      {
199
      sDepthMask = 0;
200
      //android.util.Log.d("State", "switch off depth writing");
201
      GLES30.glDepthMask(false);
202
      }
203
    if( sStencilMask!= STENCIL_MASK )
204
      {
205
      sStencilMask = STENCIL_MASK;
206
      //android.util.Log.d("State", "stencil mask on");
207
      GLES30.glStencilMask(sStencilMask);
208
      }
209
    }
210

    
211
///////////////////////////////////////////////////////////////////////////////////////////////////
212

    
213
  static void useStencilMark()
214
    {
215
    if( sStencilTest!=1 )
216
      {
217
      rStencilTest = sStencilTest;
218
      sStencilTest = 1;
219
      GLES30.glEnable(GLES30.GL_STENCIL_TEST);
220
      }
221
    if( sStencilFuncFunc!=GLES30.GL_EQUAL || sStencilFuncRef!=1 || sStencilFuncMask!=STENCIL_MASK )
222
      {
223
      rStencilFuncFunc = sStencilFuncFunc;
224
      rStencilFuncRef  = sStencilFuncRef;
225
      rStencilFuncMask = sStencilFuncMask;
226
      sStencilFuncFunc = GLES30.GL_EQUAL;
227
      sStencilFuncRef  = 1;
228
      sStencilFuncMask = STENCIL_MASK;
229
      GLES30.glStencilFunc(sStencilFuncFunc,sStencilFuncRef,sStencilFuncMask);
230
      }
231

    
232
    // TODO: Debatable
233
    if( sStencilMask!= 0x00 )
234
      {
235
      rStencilMask = sStencilMask;
236
      sStencilMask = 0x00;
237
      GLES30.glStencilMask(sStencilMask);
238
      }
239
    }
240

    
241
///////////////////////////////////////////////////////////////////////////////////////////////////
242

    
243
  static void unuseStencilMark()
244
    {
245
    if( rStencilTest!=sStencilTest )
246
      {
247
      sStencilTest = rStencilTest;
248

    
249
      if (sStencilTest == 0)
250
        {
251
        GLES30.glDisable(GLES30.GL_STENCIL_TEST);
252
        }
253
      else
254
        {
255
        GLES30.glEnable(GLES30.GL_STENCIL_TEST);
256
        }
257
      }
258

    
259
    if( rStencilFuncFunc!=sStencilFuncFunc || rStencilFuncRef!=sStencilFuncRef || rStencilFuncMask!=sStencilFuncMask )
260
      {
261
      sStencilFuncFunc = rStencilFuncFunc;
262
      sStencilFuncRef  = rStencilFuncRef ;
263
      sStencilFuncMask = rStencilFuncMask;
264
      GLES30.glStencilFunc(sStencilFuncFunc,sStencilFuncRef,sStencilFuncMask);
265
      }
266

    
267
    if( rStencilMask!=sStencilMask )
268
      {
269
      sStencilMask = rStencilMask;
270
      GLES30.glStencilMask(sStencilMask);
271
      }
272
    }
273

    
274
///////////////////////////////////////////////////////////////////////////////////////////////////
275

    
276
  void apply()
277
    {
278
    //android.util.Log.e("State", "APPLYING STATE");
279

    
280
    /////////////////////////////////////////////////////
281
    // 1. Write to color buffer?
282
    if( mColorMaskR!=sColorMaskR || mColorMaskG!=sColorMaskG || mColorMaskB!=sColorMaskB || mColorMaskA!=sColorMaskA)
283
      {
284
      //android.util.Log.d("State", "setting color mask");
285
      sColorMaskR = mColorMaskR;
286
      sColorMaskG = mColorMaskG;
287
      sColorMaskB = mColorMaskB;
288
      sColorMaskA = mColorMaskA;
289
      GLES30.glColorMask(sColorMaskR==1,sColorMaskG==1,sColorMaskB==1,sColorMaskA==1);
290
      }
291

    
292
    /////////////////////////////////////////////////////
293
    // 2. Enable Depth test?
294
    if( mDepthTest!=sDepthTest )
295
      {
296
      sDepthTest = mDepthTest;
297

    
298
      if (sDepthTest == 0)
299
        {
300
        //android.util.Log.d("State", "disabling depth test");
301
        GLES30.glDisable(GLES30.GL_DEPTH_TEST);
302
        }
303
      else
304
        {
305
        //android.util.Log.d("State", "enable depth test");
306
        GLES30.glEnable(GLES30.GL_DEPTH_TEST);
307
        }
308
      }
309

    
310
    /////////////////////////////////////////////////////
311
    // 3. Change Depth Function?
312
    if( mDepthFunc!=sDepthFunc )
313
      {
314
      //android.util.Log.d("State", "setting depth func");
315
      sDepthFunc = mDepthFunc;
316
      GLES30.glDepthFunc(sDepthFunc);
317
      }
318

    
319
    /////////////////////////////////////////////////////
320
    // 4. Write to Depth buffer?
321
    if( mDepthMask!=sDepthMask )
322
      {
323
      //android.util.Log.d("State", "setting depth mask");
324
      sDepthMask = mDepthMask;
325
      GLES30.glDepthMask(sDepthMask==1);
326
      }
327

    
328
    /////////////////////////////////////////////////////
329
    // 5. Enable Blending?
330
    if( mBlend!=sBlend )
331
      {
332
      sBlend = mBlend;
333

    
334
      if (sBlend == 0)
335
        {
336
        //android.util.Log.d("State", "disabling blending");
337
        GLES30.glDisable(GLES30.GL_BLEND);
338
        }
339
      else
340
        {
341
        //android.util.Log.d("State", "enabling blending");
342
        GLES30.glEnable(GLES30.GL_BLEND);
343
        }
344
      }
345

    
346
    /////////////////////////////////////////////////////
347
    // 6. Change Blend function?
348
    if( mBlendSrc!=sBlendSrc || mBlendDst!=sBlendDst )
349
      {
350
      //android.util.Log.d("State", "setting blend function");
351
      sBlendSrc = mBlendSrc;
352
      sBlendDst = mBlendDst;
353
      GLES30.glBlendFunc(sBlendSrc,sBlendDst);
354
      }
355

    
356
    /////////////////////////////////////////////////////
357
    // 7. Enable/Disable Stencil Test?
358
    if( mStencilTest!=sStencilTest )
359
      {
360
      sStencilTest = mStencilTest;
361

    
362
      if (sStencilTest == 0)
363
        {
364
        //android.util.Log.d("State", "disabling stencil test");
365
        GLES30.glDisable(GLES30.GL_STENCIL_TEST);
366
        }
367
      else
368
        {
369
        //android.util.Log.d("State", "enabling stencil test");
370
        GLES30.glEnable(GLES30.GL_STENCIL_TEST);
371
        }
372
      }
373

    
374
    /////////////////////////////////////////////////////
375
    // 8. Adjust Stencil function?
376
    if( mStencilFuncFunc!=sStencilFuncFunc || mStencilFuncRef!=sStencilFuncRef || mStencilFuncMask!=sStencilFuncMask )
377
      {
378
      //android.util.Log.d("State", "setting stencil function");
379
      sStencilFuncFunc = mStencilFuncFunc;
380
      sStencilFuncRef  = mStencilFuncRef ;
381
      sStencilFuncMask = mStencilFuncMask;
382
      GLES30.glStencilFunc(sStencilFuncFunc,sStencilFuncRef,sStencilFuncMask);
383
      }
384

    
385
    /////////////////////////////////////////////////////
386
    // 9. Adjust Stencil operation?
387
    if( mStencilOpSfail!=sStencilOpSfail || mStencilOpDpfail!=sStencilOpDpfail || mStencilOpDppass!=sStencilOpDppass )
388
      {
389
      //android.util.Log.d("State", "setting stencil op");
390
      sStencilOpSfail = mStencilOpSfail;
391
      sStencilOpDpfail= mStencilOpDpfail;
392
      sStencilOpDppass= mStencilOpDppass;
393
      GLES30.glStencilOp(sStencilOpSfail,sStencilOpDpfail,sStencilOpDppass);
394
      }
395

    
396
    /////////////////////////////////////////////////////
397
    // 10. Write to Stencil buffer?
398
    if( mStencilMask!=sStencilMask )
399
      {
400
      //android.util.Log.d("State", "setting stencil mask");
401
      sStencilMask = mStencilMask;
402
      GLES30.glStencilMask(sStencilMask);
403
      }
404

    
405
    /////////////////////////////////////////////////////
406
    // 11. Clear buffers?
407
    if( mClear!=0 )
408
      {
409
      //android.util.Log.d("State", "clearing buffer");
410
      GLES30.glClear(mClear);
411
      }
412
    }
413

    
414
///////////////////////////////////////////////////////////////////////////////////////////////////
415

    
416
  void glColorMask(boolean r, boolean g, boolean b, boolean a)
417
    {
418
    mColorMaskR = (r ? 1:0);
419
    mColorMaskG = (g ? 1:0);
420
    mColorMaskB = (b ? 1:0);
421
    mColorMaskA = (a ? 1:0);
422
    }
423

    
424
///////////////////////////////////////////////////////////////////////////////////////////////////
425

    
426
  void glDepthMask(boolean mask)
427
    {
428
    mDepthMask = (mask ? 1:0);
429
    }
430

    
431
///////////////////////////////////////////////////////////////////////////////////////////////////
432

    
433
  void glStencilMask(int mask)
434
    {
435
    mStencilMask = mask;
436
    }
437

    
438
///////////////////////////////////////////////////////////////////////////////////////////////////
439

    
440
  void glEnable(int test)
441
    {
442
         if( test==GLES30.GL_DEPTH_TEST   ) mDepthTest   = 1;
443
    else if( test==GLES30.GL_STENCIL_TEST ) mStencilTest = 1;
444
    else if( test==GLES30.GL_BLEND        ) mBlend       = 1;
445
    }
446

    
447
///////////////////////////////////////////////////////////////////////////////////////////////////
448

    
449
  void glDisable(int test)
450
    {
451
         if( test==GLES30.GL_DEPTH_TEST   ) mDepthTest   = 0;
452
    else if( test==GLES30.GL_STENCIL_TEST ) mStencilTest = 0;
453
    else if( test==GLES30.GL_BLEND        ) mBlend       = 0;
454
    }
455

    
456
///////////////////////////////////////////////////////////////////////////////////////////////////
457

    
458
  void glStencilFunc(int func, int ref, int mask)
459
    {
460
    mStencilFuncFunc = func;
461
    mStencilFuncRef  = ref;
462
    mStencilFuncMask = mask;
463
    }
464

    
465
///////////////////////////////////////////////////////////////////////////////////////////////////
466

    
467
  void glStencilOp(int sfail, int dpfail, int dppass)
468
    {
469
    mStencilOpSfail = sfail;
470
    mStencilOpDpfail= dpfail;
471
    mStencilOpDppass= dppass;
472
    }
473

    
474
///////////////////////////////////////////////////////////////////////////////////////////////////
475

    
476
  void glDepthFunc(int func)
477
    {
478
    mDepthFunc = func;
479
    }
480

    
481
///////////////////////////////////////////////////////////////////////////////////////////////////
482

    
483
  void glBlendFunc(int src, int dst)
484
    {
485
    mBlendSrc = src;
486
    mBlendDst = dst;
487
    }
488

    
489
///////////////////////////////////////////////////////////////////////////////////////////////////
490

    
491
  void glClear(int mask)
492
    {
493
    mClear = mask;
494
    }
495
}
(10-10/26)