Project

General

Profile

« Previous | Next » 

Revision 7c969a6d

Added by Leszek Koltunski over 4 years ago

Adjust randomizing new rotations so that:

1) it works for basicAngle=5 (Megaminx) (so now basicAngle=2,3,4,5 supported)
2) it leaves the decision as to what can be the next rotation to the Object class, as in case of certain Objects (the Dino, or the Helicopter, the Megaminx) the next rotation doesn't have to 'intersect' the old rotation always when oldRotAxis != newRotAxis (that's so simple only in case of the Cube and - only partly - the Pyraminx!)

View differences:

src/main/java/org/distorted/effects/scramble/ScrambleEffect.java
63 63
      }
64 64
    }
65 65

  
66
  public static final int START_AXIS = -2;
67
  public static final int STOP_AXIS  = -1;
68

  
66 69
  private RubikPreRender mPreRender;
67 70
  private int mEffectReturned;
68 71
  private int mNumDoubleScramblesLeft, mNumScramblesLeft;
69
  private int mLastVector;
72
  private int mLastRotAxis, mLastRow;
70 73
  private long mDurationSingleTurn;
71 74
  private Random mRnd;
72
  private int mNumAxis;
73 75
  private int mBasicAngle;
74
  private float[] mRowChances;
75 76

  
76 77
  RubikObject mObject;
77 78
  Effect[] mNodeEffects;
......
85 86
  ScrambleEffect()
86 87
    {
87 88
    mRnd = new Random( System.currentTimeMillis() );
88
    mLastVector = -2;
89
    mLastRotAxis = START_AXIS;
89 90
    }
90 91

  
91 92
///////////////////////////////////////////////////////////////////////////////////////////////////
......
98 99
// the time a single quarter-turn takes!
99 100
//
100 101
// Only works for
102
// basicAngle==5, i.e. something whose rotations are by  72 degrees (Megaminx) or
101 103
// basicAngle==4, i.e. something whose rotations are by  90 degrees (RubikCube) or
102
// basicAngle==3, i.e. something whose rotations are by 120 degrees (a Pyramix) or
104
// basicAngle==3, i.e. something whose rotations are by 120 degrees (Pyramix) or
103 105
// basicAngle==2, i.e. something whose rotations are by 180 degrees (e.g. a 3x2x1 'Bunny')
104 106

  
105 107
  private void createBaseEffects(int duration, int numScrambles)
......
110 112

  
111 113
    if( mBasicAngle>=4 )
112 114
      {
115
      int chance = mBasicAngle==4 ? 3:2;
116

  
113 117
      for(int i=0; i<numScrambles; i++)
114 118
        {
115
        if( (mRnd.nextInt() % 3) == 0 )
119
        if( (mRnd.nextInt() % chance) == 0 )
116 120
          {
117 121
          mNumDoubleScramblesLeft++;
118 122
          }
......
125 129
    }
126 130

  
127 131
///////////////////////////////////////////////////////////////////////////////////////////////////
128
// only works if basicAngle<=4, i.e. won't work for something whose basic rotations are by less
129
// than 90 degrees.
132
// only works if basicAngle<=5
130 133

  
131 134
  private void addNewScramble()
132 135
    {
133 136
    if( mNumScramblesLeft>0 )
134 137
      {
135
      if( mLastVector == -2 )
136
        {
137
        mLastVector = mRnd.nextInt(mNumAxis);
138
        }
139
      else
140
        {
141
        int newVector = mRnd.nextInt(mNumAxis-1);
142
        mLastVector = (newVector>=mLastVector ? newVector+1 : newVector);
143
        }
144

  
145
      int row=0;
146
      float rowFloat = mRnd.nextFloat();
147

  
148
      for(int i=0; i<mRowChances.length; i++)
149
        {
150
        if( rowFloat<=mRowChances[i] )
151
          {
152
          row=i;
153
          break;
154
          }
155
        }
138
      int lastRotAxis = mLastRotAxis;
139
      mLastRotAxis = mObject.randomizeNewRotAxis(mRnd,mLastRotAxis);
140
      mLastRow = mObject.randomizeNewRow(mRnd,lastRotAxis,mLastRow,mLastRotAxis);
156 141

  
157
      int rowBitmap  = (1<<row);
142
      int rowBitmap  = (1<<mLastRow);
158 143
      int angle= randomizeAngle();
159 144
      int absAngle = (angle<0 ? -angle : angle);
160 145
      long durationMillis = absAngle*mDurationSingleTurn;
......
167 152
        android.util.Log.e("effect", "ERROR: "+mNumDoubleScramblesLeft);
168 153
        }
169 154

  
170
      mPreRender.addRotation(this, mLastVector, rowBitmap, angle*(360/mBasicAngle), durationMillis);
155
      mPreRender.addRotation(this, mLastRotAxis, rowBitmap, angle*(360/mBasicAngle), durationMillis);
171 156
      }
172 157
    else
173 158
      {
174
      mLastVector = -1;
159
      mLastRotAxis = STOP_AXIS;
175 160

  
176 161
      if( mEffectReturned == mCubeEffectNumber+mNodeEffectNumber )
177 162
        {
......
181 166
    }
182 167

  
183 168
///////////////////////////////////////////////////////////////////////////////////////////////////
184
// only works for basicAngle<=4.
169
// only works for basicAngle<=5.
185 170

  
186 171
  private int randomizeAngle()
187 172
    {
......
318 303
    {
319 304
    mObject     = pre.getObject();
320 305
    mPreRender  = pre;
321
    mRowChances = mObject.getRowChances();
322 306

  
323 307
    mObject.solve();
324 308

  
325
    mNumAxis    = mObject.getRotationAxis().length;
326 309
    mBasicAngle = mObject.getBasicAngle();
327 310

  
328 311
    int numScrambles = pre.getNumScrambles();
src/main/java/org/distorted/objects/RubikCube.java
36 36
import org.distorted.library.type.Static3D;
37 37
import org.distorted.library.type.Static4D;
38 38

  
39
import java.util.Random;
40

  
41
import static org.distorted.effects.scramble.ScrambleEffect.START_AXIS;
42

  
39 43
///////////////////////////////////////////////////////////////////////////////////////////////////
40 44

  
41 45
class RubikCube extends RubikObject
......
314 318
    return getSize();
315 319
    }
316 320

  
321
///////////////////////////////////////////////////////////////////////////////////////////////////
322

  
323
  float[] getRowChances()
324
    {
325
    int size = getSize();
326
    float[] chances = new float[size];
327

  
328
    for(int i=0; i<size; i++)
329
      {
330
      chances[i] = (i+1.0f) / size;
331
      }
332

  
333
    return chances;
334
    }
335

  
317 336
///////////////////////////////////////////////////////////////////////////////////////////////////
318 337
// PUBLIC API
319 338

  
......
338 357

  
339 358
///////////////////////////////////////////////////////////////////////////////////////////////////
340 359

  
341
  public float[] getRowChances()
360
  public float returnRotationFactor(float offset)
342 361
    {
343
    int size = getSize();
344
    float[] chances = new float[size];
362
    return 1.0f;
363
    }
345 364

  
346
    for(int i=0; i<size; i++)
365
///////////////////////////////////////////////////////////////////////////////////////////////////
366

  
367
  public int randomizeNewRotAxis(Random rnd, int oldRotAxis)
368
    {
369
    int numAxis = ROTATION_AXIS.length;
370

  
371
    if( oldRotAxis == START_AXIS )
347 372
      {
348
      chances[i] = (i+1.0f) / size;
373
      return rnd.nextInt(numAxis);
374
      }
375
    else
376
      {
377
      int newVector = rnd.nextInt(numAxis-1);
378
      return (newVector>=oldRotAxis ? newVector+1 : newVector);
349 379
      }
350

  
351
    return chances;
352 380
    }
353 381

  
354 382
///////////////////////////////////////////////////////////////////////////////////////////////////
355 383

  
356
  public float returnRotationFactor(float offset)
384
  public int randomizeNewRow(Random rnd, int oldRotAxis, int oldRow, int newRotAxis)
357 385
    {
358
    return 1.0f;
386
    float rowFloat = rnd.nextFloat();
387

  
388
    for(int row=0; row<mRowChances.length; row++)
389
      {
390
      if( rowFloat<=mRowChances[row] ) return row;
391
      }
392

  
393
    return 0;
359 394
    }
360 395

  
361 396
///////////////////////////////////////////////////////////////////////////////////////////////////
src/main/java/org/distorted/objects/RubikDino.java
42 42
import org.distorted.library.type.Static3D;
43 43
import org.distorted.library.type.Static4D;
44 44

  
45
import java.util.Random;
46

  
47
import static org.distorted.effects.scramble.ScrambleEffect.START_AXIS;
48

  
45 49
///////////////////////////////////////////////////////////////////////////////////////////////////
46 50

  
47 51
public class RubikDino extends RubikObject
......
338 342
    return 2.0f;
339 343
    }
340 344

  
345
///////////////////////////////////////////////////////////////////////////////////////////////////
346

  
347
  float[] getRowChances()
348
    {
349
    float[] chances = new float[3];
350

  
351
    chances[0] = 0.5f;
352
    chances[1] = 0.5f;
353
    chances[2] = 1.0f;
354

  
355
    return chances;
356
    }
357

  
341 358
///////////////////////////////////////////////////////////////////////////////////////////////////
342 359
// PUBLIC API
343 360

  
......
369 386

  
370 387
///////////////////////////////////////////////////////////////////////////////////////////////////
371 388

  
372
  public float[] getRowChances()
389
  public int randomizeNewRotAxis(Random rnd, int oldRotAxis)
373 390
    {
374
    float[] chances = new float[3];
391
    int numAxis = ROTATION_AXIS.length;
375 392

  
376
    chances[0] = 0.5f;
377
    chances[1] = 0.5f;
378
    chances[2] = 1.0f;
393
    if( oldRotAxis == START_AXIS )
394
      {
395
      return rnd.nextInt(numAxis);
396
      }
397
    else
398
      {
399
      int newVector = rnd.nextInt(numAxis-1);
400
      return (newVector>=oldRotAxis ? newVector+1 : newVector);
401
      }
402
    }
379 403

  
380
    return chances;
404
///////////////////////////////////////////////////////////////////////////////////////////////////
405

  
406
  public int randomizeNewRow(Random rnd, int oldRotAxis, int oldRow, int newRotAxis)
407
    {
408
    float rowFloat = rnd.nextFloat();
409

  
410
    switch(oldRotAxis)
411
      {
412
      case 0 : switch(newRotAxis)
413
                 {
414
                 case 1:
415
                 case 2: return oldRow;
416
                 case 3: return 2-oldRow;
417
                 default: android.util.Log.e("dino", "error: oldRotAxis="+oldRotAxis+" newRotAxis:"+newRotAxis);
418
                 }
419
      case 1 : switch(newRotAxis)
420
                 {
421
                 case 0:
422
                 case 3: return oldRow;
423
                 case 2: return 2-oldRow;
424
                 default: android.util.Log.e("dino", "error: oldRotAxis="+oldRotAxis+" newRotAxis:"+newRotAxis);
425
                 }
426
      case 2 : switch(newRotAxis)
427
                 {
428
                 case 0:
429
                 case 3: return oldRow;
430
                 case 1: return 2-oldRow;
431
                 default: android.util.Log.e("dino", "error: oldRotAxis="+oldRotAxis+" newRotAxis:"+newRotAxis);
432
                 }
433
      case 3 : switch(newRotAxis)
434
                 {
435
                 case 1:
436
                 case 2: return oldRow;
437
                 case 0: return 2-oldRow;
438
                 default: android.util.Log.e("dino", "error: oldRotAxis="+oldRotAxis+" newRotAxis:"+newRotAxis);
439
                 }
440
      default: return rowFloat<=0.5f ? 0:2;
441
      }
381 442
    }
382 443

  
383 444
///////////////////////////////////////////////////////////////////////////////////////////////////
src/main/java/org/distorted/objects/RubikObject.java
49 49
import java.io.DataInputStream;
50 50
import java.io.IOException;
51 51
import java.io.InputStream;
52
import java.util.Random;
52 53

  
53 54
///////////////////////////////////////////////////////////////////////////////////////////////////
54 55

  
......
90 91
  private Static3D mObjectScale;
91 92

  
92 93
  float mStart, mStep;
94
  float[] mRowChances;
93 95

  
94 96
  Static1D mRotationAngleStatic, mRotationAngleMiddle, mRotationAngleFinal;
95 97
  DistortedTexture mTexture;
......
124 126
    mNodeScale= new Static3D(1,NODE_RATIO,1);
125 127
    mQuat = quat;
126 128

  
129
    mRowChances = getRowChances();
130

  
127 131
    mRotationAngle= new Dynamic1D();
128 132
    mRotationAxis = new Static3D(1,0,0);
129 133
    mRotateEffect = new VertexEffectRotate(mRotationAngle, mRotationAxis, CENTER);
......
696 700
  abstract void createFaceTexture(Canvas canvas, Paint paint, int face, int left, int top, int side);
697 701
  abstract int getFaceColor(int cubit, int cubitface, int size);
698 702
  abstract float returnMultiplier();
703
  abstract float[] getRowChances();
704

  
699 705
  public abstract Static3D[] getRotationAxis();
700 706
  public abstract int getBasicAngle();
701 707
  public abstract int computeRowFromOffset(float offset);
702 708
  public abstract float returnRotationFactor(float offset);
703 709
  public abstract String retObjectString();
704
  public abstract float[] getRowChances();
710
  public abstract int randomizeNewRotAxis(Random rnd, int oldRotAxis);
711
  public abstract int randomizeNewRow(Random rnd, int oldRotAxis, int oldRow, int newRotAxis);
705 712
  }
src/main/java/org/distorted/objects/RubikPyraminx.java
38 38
import org.distorted.library.type.Static3D;
39 39
import org.distorted.library.type.Static4D;
40 40

  
41
import java.util.Random;
42

  
43
import static org.distorted.effects.scramble.ScrambleEffect.START_AXIS;
44

  
41 45
///////////////////////////////////////////////////////////////////////////////////////////////////
42 46

  
43 47
public class RubikPyraminx extends RubikObject
......
399 403
    return getSize()/0.82f;//(SQ3/2);
400 404
    }
401 405

  
406
///////////////////////////////////////////////////////////////////////////////////////////////////
407

  
408
  float[] getRowChances()
409
    {
410
    int size = getSize();
411
    int total = size*(size+1)/2;
412
    float running=0.0f;
413
    float[] chances = new float[size];
414

  
415
    for(int i=0; i<size; i++)
416
      {
417
      running += (size-i);
418
      chances[i] = running / total;
419
      }
420

  
421
    return chances;
422
    }
423

  
402 424
///////////////////////////////////////////////////////////////////////////////////////////////////
403 425
// PUBLIC API
404 426

  
......
424 446

  
425 447
///////////////////////////////////////////////////////////////////////////////////////////////////
426 448

  
427
  public float[] getRowChances()
449
  public float returnRotationFactor(float offset)
428 450
    {
429 451
    int size = getSize();
430
    int total = size*(size+1)/2;
431
    float running=0.0f;
432
    float[] chances = new float[size];
452
    int row  = (int)(size*offset/(SQ3/2));
433 453

  
434
    for(int i=0; i<size; i++)
454
    return ((float)size)/(size-row);
455
    }
456

  
457
///////////////////////////////////////////////////////////////////////////////////////////////////
458

  
459
  public int randomizeNewRotAxis(Random rnd, int oldRotAxis)
460
    {
461
    int numAxis = ROTATION_AXIS.length;
462

  
463
    if( oldRotAxis == START_AXIS )
435 464
      {
436
      running += (size-i);
437
      chances[i] = running / total;
465
      return rnd.nextInt(numAxis);
466
      }
467
    else
468
      {
469
      int newVector = rnd.nextInt(numAxis-1);
470
      return (newVector>=oldRotAxis ? newVector+1 : newVector);
438 471
      }
439

  
440
    return chances;
441 472
    }
442 473

  
443 474
///////////////////////////////////////////////////////////////////////////////////////////////////
444 475

  
445
  public float returnRotationFactor(float offset)
476
  public int randomizeNewRow(Random rnd, int oldRotAxis, int oldRow, int newRotAxis)
446 477
    {
447
    int size = getSize();
448
    int row  = (int)(size*offset/(SQ3/2));
478
    float rowFloat = rnd.nextFloat();
449 479

  
450
    return ((float)size)/(size-row);
480
    for(int row=0; row<mRowChances.length; row++)
481
      {
482
      if( rowFloat<=mRowChances[row] ) return row;
483
      }
484

  
485
    return 0;
451 486
    }
452 487

  
453 488
///////////////////////////////////////////////////////////////////////////////////////////////////

Also available in: Unified diff