Project

General

Profile

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

examples / src / main / java / org / distorted / examples / starwars / StarWarsRenderer.java @ 611ea379

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

    
22
import java.io.IOException;
23
import java.io.InputStream;
24
import java.util.Random;
25

    
26
import javax.microedition.khronos.egl.EGLConfig;
27
import javax.microedition.khronos.opengles.GL10;
28

    
29
import org.distorted.examples.R;
30

    
31
import org.distorted.library.GridFlat;
32
import org.distorted.library.EffectNames;
33
import org.distorted.library.type.Dynamic1D;
34
import org.distorted.library.type.Dynamic3D;
35
import org.distorted.library.DistortedObjectTree;
36
import org.distorted.library.type.Static1D;
37
import org.distorted.library.type.Static3D;
38
import org.distorted.library.type.Static4D;
39
import org.distorted.library.message.EffectListener;
40
import org.distorted.library.message.EffectMessage;
41
import org.distorted.library.Distorted;
42
import org.distorted.library.DistortedTexture;
43
import org.distorted.library.DistortedEffectQueues;
44

    
45
import android.graphics.Bitmap;
46
import android.graphics.BitmapFactory;
47
import android.graphics.Canvas;
48
import android.graphics.Paint;
49
import android.graphics.Typeface;
50
import android.opengl.GLES20;
51
import android.opengl.GLSurfaceView;
52

    
53
///////////////////////////////////////////////////////////////////////////////////////////////////
54

    
55
class StarWarsRenderer implements GLSurfaceView.Renderer, EffectListener
56
  {
57
  private final String[] mGFFAString = 
58
         
59
            { "A long time ago, in a galaxy far,",
60
              "far away...." };                    // yes, there really was a four-dot ellipsis
61

    
62
  private final String[] mCRAWLString = 
63
      
64
            { "It is a period of civil war.",      // in the original 1977 version, there was no 
65
              "Rebel spaceships, striking",        // 'Episode IV New Hope' subtitle line before
66
              "from a hidden base, have",          // the crawl. Lets keep to the classic.
67
              "won their first victory",
68
              "against the evil Galactic",
69
              "Empire.",
70
              "",
71
              "During the battle, rebel",
72
              "spies managed to steal",
73
              "secret plans to the Empire's",
74
              "ultimate weapon, the",
75
              "DEATH STAR, an armored",
76
              "space station with enough",
77
              "power to destroy an entire",
78
              "planet.",
79
              "",
80
              "Pursued by the Empire's",
81
              "sinister agents, Princess",
82
              "Leia races home aboard her",
83
              "starship, custodian of the",
84
              "stolen plans that can save",
85
              "her people and restore",
86
              "freedom to the galaxy...." };      // four-dot.
87
   
88
  private final int NUM_STARS = 40;
89
   
90
  private final int CRAWL_COLOR = 0xffffe81f;
91
  private final int GFFA_COLOR  = 0xff0000ff;
92
  private final int FONT_HEIGHT      = 40;
93
  private final int VERTICAL_SPACING = 10;
94
  private final String CRAWL_TYPEFACE = "News Gothic";
95
   
96
  private final int CRAWL_WIDTH = 500;
97
  private final int CRAWL_HEIGHT= (FONT_HEIGHT+VERTICAL_SPACING)*(mCRAWLString.length+1);
98
   
99
  private final int GFFA_WIDTH = 600;
100
  private final int GFFA_HEIGHT= (FONT_HEIGHT+VERTICAL_SPACING)*(mGFFAString.length+1);
101
   
102
  private final float CRAWL_ANGLE = -30.0f;
103
   
104
  private GLSurfaceView mView;
105
  private DistortedTexture mScreenTexture, mGFFATexture, mLogoTexture, mCrawlTexture, mCrawlBackgroundTexture, mStarTexture;
106
  private DistortedEffectQueues mScreenQueue, mGFFAQueue, mLogoQueue, mCrawlQueue, mCrawlBackgroundQueue;
107
  private DistortedEffectQueues[] mStarQueue;
108
  private long gffaID, logoID, crawlID;
109
    
110
  private Random mRnd = new Random(0);
111
  private DistortedObjectTree mRoot, mBackground;
112
  private GridFlat mQuad;
113

    
114

    
115
///////////////////////////////////////////////////////////////////////////////////////////////////
116

    
117
  StarWarsRenderer(GLSurfaceView v)
118
    {
119
    mView = v;
120

    
121
    mQuad = new GridFlat(1,1);
122

    
123
    mScreenQueue          = new DistortedEffectQueues();
124
    mGFFAQueue            = new DistortedEffectQueues();
125
    mLogoQueue            = new DistortedEffectQueues();
126
    mCrawlQueue           = new DistortedEffectQueues();
127
    mCrawlBackgroundQueue = new DistortedEffectQueues();
128

    
129
    mStarQueue = new DistortedEffectQueues[NUM_STARS];
130
    mStarQueue[0] = new DistortedEffectQueues();
131

    
132
    for(int i=1; i<NUM_STARS; i++) mStarQueue[i] = new DistortedEffectQueues(mStarQueue[0],Distorted.CLONE_VERTEX);
133

    
134
    Distorted.setProjection(60.0f, 0.0f, 0.0f);
135
    }
136

    
137
///////////////////////////////////////////////////////////////////////////////////////////////////
138
   
139
  public void onDrawFrame(GL10 glUnused) 
140
    {
141
    GLES20.glClear( GLES20.GL_DEPTH_BUFFER_BIT | GLES20.GL_COLOR_BUFFER_BIT);
142
    mRoot.draw(System.currentTimeMillis());
143
    }
144

    
145
///////////////////////////////////////////////////////////////////////////////////////////////////
146
    
147
  public void onSurfaceChanged(GL10 glUnused, int width, int height) 
148
    { 
149
    Distorted.onSurfaceChanged(width, height); 
150
    setupScreen(width,height);
151
    }
152

    
153
///////////////////////////////////////////////////////////////////////////////////////////////////
154
    
155
  public void onSurfaceCreated(GL10 glUnused, EGLConfig config) 
156
    {
157
    GLES20.glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
158

    
159
    setupBitmaps();
160
         
161
    try
162
      {
163
      Distorted.onSurfaceCreated(mView.getContext());
164
      }
165
    catch(Exception ex)
166
      {
167
      android.util.Log.e("Star Wars", ex.getMessage() );
168
      }
169
    }
170
    
171
///////////////////////////////////////////////////////////////////////////////////////////////////
172

    
173
  private void setupScreen(int w, int h)
174
    {
175
    mScreenTexture = new DistortedTexture(w,h,0);
176
    mRoot = new DistortedObjectTree(mScreenTexture,mScreenQueue,mQuad);
177
      
178
    mCrawlBackgroundTexture = new DistortedTexture(w,(int)(Math.sqrt(3.0)*h),0);
179
       
180
    int randomA, randomX, randomY, randomTime;
181
    float randomS, randomAlpha1, randomAlpha2;
182
       
183
    Static3D center = new Static3D(0,0,0);
184
    Static3D axis   = new Static3D(0,0,1);
185
    Static1D alphaNoise = new Static1D(0.4f);
186

    
187
    for(int i=0; i<NUM_STARS; i++)
188
      {
189
      randomX = mRnd.nextInt(w);
190
      randomY = mRnd.nextInt(h);
191
      randomS = 0.2f+ 0.8f*mRnd.nextFloat();
192
      randomA = (int)(180*mRnd.nextFloat());
193
      randomAlpha1 = 0.2f + 0.8f*mRnd.nextFloat();
194
      randomAlpha2 = 0.8f + 0.2f*mRnd.nextFloat();
195
      randomTime = 500+mRnd.nextInt(2000);
196
      
197
      mStarQueue[i].move( new Static3D(randomX,randomY,0) );
198
      mStarQueue[i].scale(randomS);
199
      mStarQueue[i].rotate( new Static1D(randomA), axis, center );
200
      
201
      Dynamic1D di = new Dynamic1D(randomTime,0.0f);
202
      di.setNoise(alphaNoise);
203
      di.add(new Static1D(randomAlpha1));
204
      di.add(new Static1D(randomAlpha2));
205
      
206
      mStarQueue[i].alpha(di);
207
      
208
      mRoot.attach(mStarTexture, mStarQueue[i], mQuad);
209
      }
210
      
211
    float scale = (0.5f*w/mGFFATexture.getWidth());
212
    
213
    Dynamic1D di = new Dynamic1D(6000,0.5f);
214
    di.add(new Static1D(1.0f));
215
    di.add(new Static1D(1.0f));
216
    di.add(new Static1D(0.0f));
217
    
218
    mGFFAQueue.move( new Static3D(w/5,h/3,0) );
219
    mGFFAQueue.scale( new Static3D(scale,scale,scale) );
220
    mGFFAQueue.alpha(di);
221
      
222
    mRoot.attach(mGFFATexture, mGFFAQueue, mQuad);
223
    mGFFAQueue.addEventListener(this);
224
    }
225
    
226
///////////////////////////////////////////////////////////////////////////////////////////////////
227

    
228
  private void setupBitmaps()
229
    {
230
    InputStream is1 = mView.getContext().getResources().openRawResource(R.raw.starwars);
231
    InputStream is2 = mView.getContext().getResources().openRawResource(R.raw.star);
232
    
233
    Bitmap bitmapStar, bitmapGFFA, bitmapLogo, bitmapText;
234
      
235
    try 
236
      {
237
      bitmapLogo = BitmapFactory.decodeStream(is1);
238
      bitmapStar = BitmapFactory.decodeStream(is2);
239
      } 
240
    finally 
241
      {
242
      try 
243
        {
244
        is1.close();
245
        is2.close();
246
        } 
247
      catch(IOException e) { }
248
      } 
249
      
250
    Paint paint = new Paint();
251
    paint.setAntiAlias(true);
252
    paint.setTextAlign(Paint.Align.LEFT);
253
    paint.setTextSize(FONT_HEIGHT);
254
    paint.setColor(GFFA_COLOR);
255
      
256
    Typeface tf = Typeface.create(CRAWL_TYPEFACE, Typeface.BOLD);
257
    paint.setTypeface(tf);     
258
 
259
    ///// create GFFA ///////////////////
260
    mGFFATexture  = new DistortedTexture(GFFA_WIDTH, GFFA_HEIGHT, 0);
261
    bitmapGFFA = Bitmap.createBitmap(GFFA_WIDTH,GFFA_HEIGHT,Bitmap.Config.ARGB_8888);
262
    bitmapGFFA.eraseColor(0x00000000);
263
    Canvas gffaCanvas = new Canvas(bitmapGFFA);
264
      
265
    for(int i=0; i<mGFFAString.length; i++)
266
      {
267
      gffaCanvas.drawText(mGFFAString[i], 0, (i+1)*(FONT_HEIGHT+VERTICAL_SPACING), paint);  
268
      }
269
  
270
    mGFFATexture.setTexture(bitmapGFFA);
271
      
272
    ///// create Logo ///////////////////
273
    mLogoTexture  = new DistortedTexture(bitmapLogo.getWidth(),bitmapLogo.getHeight(),0);
274
    mLogoTexture.setTexture(bitmapLogo);
275

    
276
    ///// create CRAWL //////////////////
277
    mCrawlTexture = new DistortedTexture(CRAWL_WIDTH, CRAWL_HEIGHT, 0);
278
    bitmapText = Bitmap.createBitmap(CRAWL_WIDTH,CRAWL_HEIGHT,Bitmap.Config.ARGB_8888);
279
    bitmapText.eraseColor(0x00000000);
280
    Canvas textCanvas = new Canvas(bitmapText);
281
    paint.setColor(CRAWL_COLOR);
282
  
283
    for(int i=0; i<mCRAWLString.length; i++)
284
      {
285
      displayJustified(mCRAWLString[i], 0, (i+1)*(FONT_HEIGHT+VERTICAL_SPACING), CRAWL_WIDTH, textCanvas, paint);  
286
      }
287
      
288
    mCrawlTexture.setTexture(bitmapText);
289
      
290
    ///// create Stars ///////////////////
291
    mStarTexture = new DistortedTexture(bitmapStar.getWidth(),bitmapStar.getHeight(),0);
292
    mStarTexture.setTexture(bitmapStar);
293

    
294
    gffaID = mGFFAQueue.getID();
295
    logoID = mLogoQueue.getID();
296
    crawlID= mCrawlQueue.getID();
297
    }
298
 
299
///////////////////////////////////////////////////////////////////////////////////////////////////
300

    
301
  private void displayJustified(String str, int x, int y, int length, Canvas c, Paint paint)
302
    { 
303
    int len       = str.length();
304
    int numspaces = retNumSpaces(str);
305
    
306
    if( len>0 && str.charAt(len-1) == ' ' ) numspaces--;
307

    
308
    float left=x,w = (numspaces>0 ? (length-paint.measureText(str))/numspaces : 0);
309
    String tmp;
310
    int begin,end=0;
311

    
312
    while( end<len )
313
      {
314
      begin=end;
315
      end = str.indexOf(' ', begin)+1;
316
      if( end<=0 ) end = len;
317

    
318
      tmp = str.substring(begin,end);
319
      c.drawText( tmp, left, y, paint);
320
      left+= (paint.measureText(tmp)+w);
321
      }  
322
    }
323

    
324
///////////////////////////////////////////////////////////////////////////////////////////////////
325
   
326
  private int retNumSpaces(String str)
327
    {
328
    int begin=0, ret=0;
329

    
330
    while( true )
331
      {
332
      begin = str.indexOf(' ', begin) +1;
333

    
334
      if( begin>0 ) ret++;
335
      else break;
336
      }
337

    
338
    return ret;
339
    }
340
    
341
///////////////////////////////////////////////////////////////////////////////////////////////////
342
// the library sending messages to us. This is running on a library 'MessageSender' thread.
343

    
344
  public void effectMessage(final EffectMessage em, final long effectID, final EffectNames effectName, final long objectID, final String message)
345
    {
346
    if( em==EffectMessage.EFFECT_FINISHED )
347
      {
348
      if( objectID == gffaID )
349
        {
350
        mRoot.detach(mGFFAQueue);
351
        mGFFAQueue.delete();
352
        mGFFATexture.delete();
353

    
354
        int screenW=mScreenTexture.getWidth();
355
        int screenH=mScreenTexture.getHeight();
356
        
357
        int logoW = mLogoTexture.getWidth();
358
        int logoH = mLogoTexture.getHeight();
359
      
360
        int initSize= (int)(3.0f*screenW/logoW);
361
        int finaSize= (int)(0.1f*screenW/logoW);
362
      
363
        Dynamic3D di = new Dynamic3D(10000,0.5f);
364
        di.add(new Static3D(initSize,initSize,1));
365
        di.add(new Static3D(finaSize,finaSize,1));
366

    
367
        mLogoQueue.move( new Static3D(screenW/2,screenH/2,0) );
368
        mLogoQueue.scale(di);
369
        mLogoQueue.move( new Static3D(-logoW/2,-logoH/2,0) );
370
      
371
        mRoot.attach(mLogoTexture,mLogoQueue,mQuad);
372
        mLogoQueue.addEventListener(this);
373
        }
374
      else if( objectID==logoID )
375
        {
376
        mRoot.detach(mLogoQueue);
377
        mLogoQueue.delete();
378
        mLogoTexture.delete();
379
        
380
        int crawlW = mCrawlTexture.getWidth();
381
        int crawlH = mCrawlTexture.getHeight();
382
        int screenW= mScreenTexture.getWidth();
383
        int screenH= mScreenTexture.getHeight();
384
        int backH  = mCrawlBackgroundTexture.getHeight();
385
        float scale= (float)screenW/crawlW;
386
      
387
        Dynamic3D di = new Dynamic3D(60000,0.5f);
388
        di.add(new Static3D(screenW/2,+backH       , 0));
389
        di.add(new Static3D(screenW/2,-scale*crawlH, 0));
390
        
391
        mCrawlBackgroundQueue.move( new Static3D(0,screenH-backH,0) );
392
        mCrawlBackgroundQueue.rotate( new Static1D(CRAWL_ANGLE), new Static3D(1,0,0), new Static3D(screenW/2,backH,0) );
393
        
394
        final int transpDist = 5;
395
        Static4D region = new Static4D(screenW/2,(1-transpDist)*backH,transpDist*backH,transpDist*backH);
396
        mCrawlBackgroundQueue.alpha(new Static1D(1-transpDist/2), region, true);
397
        
398
        mCrawlQueue.move(di);
399
        mCrawlQueue.scale( new Static3D(scale,scale,scale) );
400
        mCrawlQueue.move( new Static3D(-crawlW/2,0,0) );
401
        
402
        mBackground = mRoot.attach(mCrawlBackgroundTexture,mCrawlBackgroundQueue,mQuad);
403
        mBackground.attach(mCrawlTexture,mCrawlQueue,mQuad);
404
        mCrawlQueue.addEventListener(this);
405
        }
406
      else if( objectID==crawlID )
407
        {
408
        mRoot.detach(mBackground);
409
        mBackground.detach(mCrawlQueue);
410
        mCrawlQueue.delete();
411
        mCrawlTexture.delete();
412
        mCrawlBackgroundQueue.delete();
413
        mCrawlBackgroundTexture.delete();
414
        }
415
      }
416
    }
417
  }
(2-2/3)