Project

General

Profile

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

distorted-objectlib / src / main / java / org / distorted / objectlib / objects / TwistyJing.java @ 8f5116ec

1
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2021 Leszek Koltunski                                                               //
3
//                                                                                               //
4
// This file is part of Magic Cube.                                                              //
5
//                                                                                               //
6
// Magic Cube is proprietary software licensed under an EULA which you should have received      //
7
// along with the code. If not, check https://distorted.org/magic/License-Magic-Cube.html        //
8
///////////////////////////////////////////////////////////////////////////////////////////////////
9

    
10
package org.distorted.objectlib.objects;
11

    
12
import static org.distorted.objectlib.touchcontrol.TouchControl.TC_TETRAHEDRON;
13
import static org.distorted.objectlib.touchcontrol.TouchControl.TYPE_NOT_SPLIT;
14

    
15
import org.distorted.library.type.Static3D;
16
import org.distorted.library.type.Static4D;
17

    
18
import org.distorted.objectlib.helpers.FactoryCubit;
19
import org.distorted.objectlib.helpers.ObjectFaceShape;
20
import org.distorted.objectlib.metadata.Metadata;
21
import org.distorted.objectlib.helpers.ObjectVertexEffects;
22
import org.distorted.objectlib.main.InitAssets;
23
import org.distorted.objectlib.scrambling.ScrambleEdgeGenerator;
24
import org.distorted.objectlib.touchcontrol.TouchControlTetrahedron;
25
import org.distorted.objectlib.metadata.ListObjects;
26
import org.distorted.objectlib.helpers.ObjectShape;
27
import org.distorted.objectlib.shape.ShapeTetrahedron;
28

    
29
///////////////////////////////////////////////////////////////////////////////////////////////////
30

    
31
public class TwistyJing extends ShapeTetrahedron
32
{
33
  public static final int JING_2 = 0;
34
  public static final int JING_3 = 1;
35
  public static final int JING_4 = 2;
36
  public static final int JING_5 = 3;
37

    
38
  // Length of the edge of the corner cubit -
39
  // assuming the length of the edge of the whole tetrahedron is numLayers[0]
40
  public static final float[] JING_F = { 0.48f, 0.66f, 0.43f, 0.53f };
41

    
42
  static final Static3D[] ROT_AXIS = new Static3D[]
43
         {
44
           new Static3D(     0,-SQ3/3,-SQ6/3),
45
           new Static3D(     0,-SQ3/3, SQ6/3),
46
           new Static3D( SQ6/3, SQ3/3,     0),
47
           new Static3D(-SQ6/3, SQ3/3,     0),
48
         };
49

    
50
  private int[][] mEdges;
51
  private int[][] mBasicAngle;
52
  private int[] mQuatIndex;
53
  private float[][] mCuts;
54
  private float[][] mCenters;
55

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

    
58
  public TwistyJing(int iconMode, Static4D quat, Static3D move, float scale, Metadata meta, InitAssets asset)
59
    {
60
    super(iconMode, meta.getNumLayers()[0], quat, move, scale, meta, asset);
61
    }
62

    
63
///////////////////////////////////////////////////////////////////////////////////////////////////
64

    
65
  private int getObjectType()
66
    {
67
    return getMetadata().getParam();
68
    }
69

    
70
///////////////////////////////////////////////////////////////////////////////////////////////////
71

    
72
  @Override
73
  protected float[][][] getStickerRadii()
74
    {
75
    int type = getObjectType();
76

    
77
    if( type==JING_3 )
78
      {
79
      float R = 0.06f;
80
      float L = 0.16f;
81
      float[][] t1 = {{ R,R,R,R }};
82
      float[][] t2 = {{ R,R,L,R }};
83
      return new float[][][] { t1,t1,t1,t2 };
84
      }
85

    
86
    return super.getStickerRadii();
87
    }
88

    
89
///////////////////////////////////////////////////////////////////////////////////////////////////
90

    
91
  @Override
92
  public float[][] returnRotationFactor()
93
    {
94
    int numL = getNumLayers()[0];
95
    float[] f = new float[numL];
96
    for(int i=0; i<numL; i++) f[i] = 1.3f;
97
    return new float[][] { f,f,f,f };
98
    }
99

    
100
///////////////////////////////////////////////////////////////////////////////////////////////////
101

    
102
  @Override
103
  public float getPillowCoeff()
104
    {
105
    return 1.25f;
106
    }
107

    
108
///////////////////////////////////////////////////////////////////////////////////////////////////
109

    
110
  public int[][] getScrambleEdges()
111
    {
112
    if( mEdges==null ) mEdges = ScrambleEdgeGenerator.getScrambleEdgesSingle(mBasicAngle);
113
    return mEdges;
114
    }
115

    
116
///////////////////////////////////////////////////////////////////////////////////////////////////
117

    
118
  public float[][] getCuts(int[] numLayers)
119
    {
120
    if( mCuts==null )
121
      {
122
      float[] cut=null;
123
      int type = getObjectType();
124
      final float F = JING_F[type];
125
      int numL = 0;
126

    
127
      switch(type)
128
        {
129
        case JING_2: numL = 2; break;
130
        case JING_3:
131
        case JING_4: numL = 3; break;
132
        case JING_5: numL = 4; break;
133
        }
134

    
135
      switch( type )
136
        {
137
        case JING_2: cut = new float[] { (F-numL*0.25f-0.01f)*(SQ6/3) };
138
                     break;
139
        case JING_3: cut = new float[] { (F-numL*0.25f-0.01f)*(SQ6/3), numL*SQ6/18 };
140
                     break;
141
        case JING_4: cut = new float[] { (F-numL*0.25f-0.01f)*(SQ6/3), (2*F-numL*0.25f-0.01f)*(SQ6/3) };
142
                     break;
143
        case JING_5: cut = new float[] { (F-numL*0.25f-0.01f)*(SQ6/3), (2*F-numL*0.25f-0.01f)*(SQ6/3), numL*SQ6/18 };
144
                     break;
145
        }
146

    
147
      mCuts = new float[][] { cut,cut,cut,cut };
148
      }
149

    
150
    return mCuts;
151
    }
152

    
153
///////////////////////////////////////////////////////////////////////////////////////////////////
154

    
155
  public boolean[][] getLayerRotatable(int[] numLayers)
156
    {
157
    boolean[] tmp = null;
158

    
159
    switch( getObjectType() )
160
      {
161
      case JING_2: tmp = new boolean[] {true,true}; break;
162
      case JING_3:
163
      case JING_4: tmp = new boolean[] {true,true,true}; break;
164
      case JING_5: tmp = new boolean[] {true,true,false,true}; break;
165
      }
166

    
167
    return new boolean[][] { tmp,tmp,tmp,tmp };
168
    }
169

    
170
///////////////////////////////////////////////////////////////////////////////////////////////////
171

    
172
  public int getTouchControlType()
173
    {
174
    return TC_TETRAHEDRON;
175
    }
176

    
177
///////////////////////////////////////////////////////////////////////////////////////////////////
178

    
179
  public int getTouchControlSplit()
180
    {
181
    return TYPE_NOT_SPLIT;
182
    }
183

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

    
186
  public int[][][] getEnabled()
187
    {
188
    return new int[][][] { {{1,2,3}},{{0,2,3}},{{0,1,3}},{{0,1,2}} };
189
    }
190

    
191
///////////////////////////////////////////////////////////////////////////////////////////////////
192

    
193
  public float[] getDist3D(int[] numLayers)
194
    {
195
    return TouchControlTetrahedron.D3D;
196
    }
197

    
198
///////////////////////////////////////////////////////////////////////////////////////////////////
199

    
200
  public Static3D[] getFaceAxis()
201
    {
202
    return TouchControlTetrahedron.FACE_AXIS;
203
    }
204

    
205
///////////////////////////////////////////////////////////////////////////////////////////////////
206

    
207
  public float[][] getCubitPositions(int[] numLayers)
208
    {
209
    if( mCenters==null )
210
      {
211
      int type = getObjectType();
212

    
213
      if( type==JING_2 )
214
        {
215
        mCenters = new float[][]
216
          {
217
            { 0.000f, -SQ2/2,  1.000f },
218
            { 0.000f, -SQ2/2, -1.000f },
219
            {-1.000f,  SQ2/2,  0.000f },
220
            { 1.000f,  SQ2/2,  0.000f },
221

    
222
            { 0.000f, -SQ2/2,  0.000f },
223
            {-0.500f, 0.000f,  0.500f },
224
            { 0.500f, 0.000f,  0.500f },
225
            {-0.500f, 0.000f, -0.500f },
226
            { 0.500f, 0.000f, -0.500f },
227
            { 0.000f,  SQ2/2,  0.000f },
228

    
229
            { 0.000f,  SQ2/6,  1.0f/3 },
230
            { 0.000f,  SQ2/6, -1.0f/3 },
231
            {-1.0f/3, -SQ2/6,  0.000f },
232
            { 1.0f/3, -SQ2/6,  0.000f },
233
          };
234
        }
235
      else if( type==JING_3 )
236
        {
237
        int numL = 3;
238
        final float F = JING_F[JING_3];
239
        final float A = numL*0.25f;
240
        final float B = numL*0.50f;
241
        final float X = F/2;
242
        final float Y = F*SQ2/2;
243
        final float Z = -F/2;
244

    
245
        mCenters = new float[][]
246
          {
247
            {   0, -SQ2*A,  B },
248
            {   0, -SQ2*A, -B },
249
            {  -B,  SQ2*A,  0 },
250
            {   B,  SQ2*A,  0 },
251

    
252
            {   X, -SQ2*A +Y, B+Z },
253
            {  -X, -SQ2*A +Y, B+Z },
254
            {   0, -SQ2*A   , B-F },
255
            {   X, -SQ2*A +Y,-B-Z },
256
            {  -X, -SQ2*A +Y,-B-Z },
257
            {   0, -SQ2*A   ,-B+F },
258

    
259
            {-B-Z,  SQ2*A -Y,   X },
260
            {-B-Z,  SQ2*A -Y,  -X },
261
            {-B+F,  SQ2*A   ,   0 },
262
            { B+Z,  SQ2*A -Y,   X },
263
            { B+Z,  SQ2*A -Y,  -X },
264
            { B-F,  SQ2*A   ,   0 },
265

    
266
            {      0, -SQ2*A +2*Y,  B +2*Z },
267
            {      X, -SQ2*A +  Y,  B +Z-F },
268
            {     -X, -SQ2*A +  Y,  B +Z-F },
269
            {      0, -SQ2*A +2*Y, -B -2*Z },
270
            {      X, -SQ2*A +  Y, -B -Z+F },
271
            {     -X, -SQ2*A +  Y, -B -Z+F },
272
            {-B -2*Z,  SQ2*A -2*Y,       0 },
273
            {-B -Z+F,  SQ2*A -  Y,      -X },
274
            {-B -Z+F,  SQ2*A -  Y,       X },
275
            { B +2*Z,  SQ2*A -2*Y,       0 },
276
            { B +Z-F,  SQ2*A -  Y,      -X },
277
            { B +Z-F,  SQ2*A -  Y,       X },
278
          };
279
        }
280
      else if( type==JING_4 )
281
        {
282
        int numL = 3;
283
        final float A = numL*0.25f;
284
        final float B = numL*0.50f;
285
        final float C = numL*(1.0f/6);
286
        final float D = numL*(SQ2/12);
287
        final float F = JING_F[type];
288
        final float X = F/2;
289
        final float Y = F*SQ2/2;
290
        final float Z = -F/2;
291

    
292
        mCenters = new float[][]
293
          {
294
            {  0, -SQ2*A     ,  B      },
295
            {  X, -SQ2*A +  Y,  B +  Z },
296
            { -X, -SQ2*A +  Y,  B +  Z },
297
            {  0, -SQ2*A     ,  B -  F },
298
            {  0, -SQ2*A +2*Y,  B +2*Z },
299
            {  X, -SQ2*A +  Y,  B +Z-F },
300
            { -X, -SQ2*A +  Y,  B +Z-F },
301

    
302
            {  0, -SQ2*A     , -B      },
303
            {  X, -SQ2*A +  Y, -B -  Z },
304
            { -X, -SQ2*A +  Y, -B -  Z },
305
            {  0, -SQ2*A     , -B +  F },
306
            {  0, -SQ2*A +2*Y, -B -2*Z },
307
            {  X, -SQ2*A +  Y, -B -Z+F },
308
            { -X, -SQ2*A +  Y, -B -Z+F },
309

    
310
            {-B     ,  SQ2*A     ,   0 },
311
            {-B -  Z,  SQ2*A -  Y,   X },
312
            {-B -  Z,  SQ2*A -  Y,  -X },
313
            {-B +  F,  SQ2*A     ,   0 },
314
            {-B -2*Z,  SQ2*A -2*Y,   0 },
315
            {-B -Z+F,  SQ2*A -  Y,  -X },
316
            {-B -Z+F,  SQ2*A -  Y,   X },
317

    
318
            { B     ,  SQ2*A     ,   0 },
319
            { B +  Z,  SQ2*A -  Y,   X },
320
            { B +  Z,  SQ2*A -  Y,  -X },
321
            { B -  F,  SQ2*A     ,   0 },
322
            { B +2*Z,  SQ2*A -2*Y,   0 },
323
            { B +Z-F,  SQ2*A -  Y,  -X },
324
            { B +Z-F,  SQ2*A -  Y,   X },
325

    
326
            { 0,-SQ2*A,  0 },
327
            {-A,     0,  A },
328
            { A,     0,  A },
329
            {-A,     0, -A },
330
            { A,     0, -A },
331
            { 0, SQ2*A,  0 },
332

    
333
            {    0.50f*F, -SQ2*A +F*SQ2/2, 0          },
334
            {   -0.50f*F, -SQ2*A +F*SQ2/2, 0          },
335
            {-A +0.75f*F,         F*SQ2/4, A -0.25f*F },
336
            {-A +0.25f*F,        -F*SQ2/4, A -0.75f*F },
337
            { A -0.75f*F,         F*SQ2/4, A -0.25f*F },
338
            { A -0.25f*F,        -F*SQ2/4, A -0.75f*F },
339
            {-A +0.75f*F,         F*SQ2/4,-A +0.25f*F },
340
            {-A +0.25f*F,        -F*SQ2/4,-A +0.75f*F },
341
            { A -0.75f*F,         F*SQ2/4,-A +0.25f*F },
342
            { A -0.25f*F,        -F*SQ2/4,-A +0.75f*F },
343
            { 0         ,  SQ2*A -F*SQ2/2,    0.50f*F },
344
            { 0         ,  SQ2*A -F*SQ2/2,   -0.50f*F },
345

    
346
            { 0,  D,  C},
347
            { 0,  D, -C},
348
            {-C, -D,  0},
349
            { C, -D,  0},
350
          };
351
        }
352
      else if( type==JING_5 )
353
        {
354
        int numL = 4;
355
        final float A = numL*0.25f;
356
        final float B = numL*0.50f;
357
        final float F = JING_F[type];
358
        final float X = F/2;
359
        final float Y = F*SQ2/2;
360
        final float Z = -F/2;
361

    
362
        mCenters = new float[][]
363
          {
364
            {  0, -SQ2*A     ,  B      },
365
            {  X, -SQ2*A +  Y,  B +  Z },
366
            { -X, -SQ2*A +  Y,  B +  Z },
367
            {  0, -SQ2*A     ,  B -  F },
368
            {  0, -SQ2*A +2*Y,  B +2*Z },
369
            {  X, -SQ2*A +  Y,  B +Z-F },
370
            { -X, -SQ2*A +  Y,  B +Z-F },
371

    
372
            {  0, -SQ2*A     , -B      },
373
            {  X, -SQ2*A +  Y, -B -  Z },
374
            { -X, -SQ2*A +  Y, -B -  Z },
375
            {  0, -SQ2*A     , -B +  F },
376
            {  0, -SQ2*A +2*Y, -B -2*Z },
377
            {  X, -SQ2*A +  Y, -B -Z+F },
378
            { -X, -SQ2*A +  Y, -B -Z+F },
379

    
380
            {-B     ,  SQ2*A     ,   0 },
381
            {-B -  Z,  SQ2*A -  Y,   X },
382
            {-B -  Z,  SQ2*A -  Y,  -X },
383
            {-B +  F,  SQ2*A     ,   0 },
384
            {-B -2*Z,  SQ2*A -2*Y,   0 },
385
            {-B -Z+F,  SQ2*A -  Y,  -X },
386
            {-B -Z+F,  SQ2*A -  Y,   X },
387

    
388
            { B     ,  SQ2*A     ,   0 },
389
            { B +  Z,  SQ2*A -  Y,   X },
390
            { B +  Z,  SQ2*A -  Y,  -X },
391
            { B -  F,  SQ2*A     ,   0 },
392
            { B +2*Z,  SQ2*A -2*Y,   0 },
393
            { B +Z-F,  SQ2*A -  Y,  -X },
394
            { B +Z-F,  SQ2*A -  Y,   X },
395

    
396
            { 2*X, -SQ2*A +2*Y, B+2*Z },
397
            {-2*X, -SQ2*A +2*Y, B+2*Z },
398
            {   0, -SQ2*A     , B-2*F },
399
            { 2*X, -SQ2*A +2*Y,-B-2*Z },
400
            {-2*X, -SQ2*A +2*Y,-B-2*Z },
401
            {   0, -SQ2*A     ,-B+2*F },
402

    
403
            {-B-2*Z, SQ2*A -2*Y,  2*X },
404
            {-B-2*Z, SQ2*A -2*Y, -2*X },
405
            {-B+2*F, SQ2*A     ,    0 },
406
            { B+2*Z, SQ2*A -2*Y,  2*X },
407
            { B+2*Z, SQ2*A -2*Y, -2*X },
408
            { B-2*F, SQ2*A     ,    0 },
409

    
410
            {   X, -SQ2*A+3*Y ,  B+3*Z     },
411
            {-2*X, -SQ2*A+2*Y ,  B+4*Z     },
412
            {   X, -SQ2*A+Y   ,  B+5*Z     },
413
            { 2*X, -SQ2*A+2*Y , -B-4*Z     },
414
            {  -X, -SQ2*A+3*Y , -B-3*Z     },
415
            {  -X, -SQ2*A+Y   , -B-5f*Z    },
416
            {  -B+   2*F,  SQ2*A-2*Y ,-2*Z },
417
            {  -B+2.5f*F,  SQ2*A-  Y ,   Z },
418
            {  -B+1.5f*F,  SQ2*A-3*Y ,   Z },
419
            {   B-1.5f*F,  SQ2*A-3*Y ,  -Z },
420
            {   B-   2*F,  SQ2*A-2*Y , 2*Z },
421
            {   B-2.5f*F,  SQ2*A-  Y ,  -Z },
422

    
423
            {  -X, -SQ2*A+3*Y ,  B+3*Z     },
424
            { 2*X, -SQ2*A+2*Y ,  B+4*Z     },
425
            {  -X, -SQ2*A+Y   ,  B+5*Z     },
426
            {-2*X, -SQ2*A+2*Y , -B-4*Z     },
427
            {   X, -SQ2*A+3*Y , -B-3*Z     },
428
            {   X, -SQ2*A+Y   , -B-5*Z     },
429
            {  -B+   2*F,  SQ2*A-2*Y , 2*Z },
430
            {  -B+2.5f*F,  SQ2*A-  Y ,  -Z },
431
            {  -B+1.5f*F,  SQ2*A-3*Y ,  -Z },
432
            {   B-1.5f*F,  SQ2*A-3*Y ,   Z },
433
            {   B-   2*F,  SQ2*A-2*Y ,-2*Z },
434
            {   B-2.5f*F,  SQ2*A-  Y ,   Z },
435

    
436
            {   0, -SQ2*A+4*Y, B+4*Z },
437
            { 2*X, -SQ2*A+2*Y, B+6*Z },
438
            {-2*X, -SQ2*A+2*Y, B+6*Z },
439
            {   0, -SQ2*A+4*Y,-B-4*Z },
440
            { 2*X, -SQ2*A+2*Y,-B-6*Z },
441
            {-2*X, -SQ2*A+2*Y,-B-6*Z },
442
            { -B-4*Z, SQ2*A-4*Y,   0 },
443
            { -B-6*Z, SQ2*A-2*Y, 2*X },
444
            { -B-6*Z, SQ2*A-2*Y,-2*X },
445
            {  B+4*Z, SQ2*A-4*Y,   0 },
446
            {  B+6*Z, SQ2*A-2*Y, 2*X },
447
            {  B+6*Z, SQ2*A-2*Y,-2*X },
448
          };
449
        }
450
      }
451

    
452
    return mCenters;
453
    }
454

    
455
///////////////////////////////////////////////////////////////////////////////////////////////////
456

    
457
  public Static4D getCubitQuats(int cubit, int[] numLayers)
458
    {
459
    if( mQuatIndex==null )
460
      {
461
      int type = getObjectType();
462

    
463
      if( type==JING_2 )
464
        mQuatIndex = new int[] { 0,10,5,8,
465
                                 0,5,8,6,7,9,
466
                                 0,10,7,3 };
467
      else if( type==JING_3 )
468
        mQuatIndex = new int[] { 0,10,5,8,
469
                                 4,3,0, 7,6,10, 5,2,11, 8,1,9,
470
                                 0,3,4, 10,6,7, 11,5,2, 9,8,1
471
                               };
472
      else if( type==JING_4 )
473
        mQuatIndex = new int[] { 0,0,0,0,0,0,0,10,10,10,10,10,10,10,5,5,5,5,5,5,5,8,8,8,8,8,8,8,
474
                                 0,5,8,6,7,9,
475
                                 0,0,5,5,8,8,6,6,7,7,9,9,
476
                                 0,10,7,3 };
477
      else
478
        mQuatIndex = new int[] { 0,0,0,0,0,0,0,10,10,10,10,10,10,10,5,5,5,5,5,5,5,8,8,8,8,8,8,8,
479
                                 4,3,0, 7,6,10, 5,2,11, 8,1,9,
480
                                 4,3,0, 7,6,10, 5,11,2, 8,1,9,
481
                                 5,8,10,2,1,0,  6,9,3,  7,4,11,
482
                                 0,3,4, 10,6,7, 11,2,5, 9,1,8 };
483
      }
484

    
485
    return mObjectQuats[mQuatIndex[cubit]];
486
    }
487

    
488
///////////////////////////////////////////////////////////////////////////////////////////////////
489

    
490
  private float[][] getVertices(int variant)
491
    {
492
    int type = getObjectType();
493
    int numL = 0;
494
    int munL = 0;
495

    
496
    switch(type)
497
      {
498
      case JING_2: numL = 2; munL = 1; break;
499
      case JING_3: numL = 3; munL = 1; break;
500
      case JING_4: numL = 3; munL = 2; break;
501
      case JING_5: numL = 4; munL = 2; break;
502
      }
503

    
504
    final float F = JING_F[type];
505
    final float X = F/2;
506
    final float Y = F*SQ2/2;
507
    final float Z =-F/2;
508

    
509
    final float L = (numL-3*(numL-1)*F);
510
    final float X2 = L/2;
511
    final float Y2 = L*SQ2/2;
512
    final float Z2 =-L/2;
513
    final float D = F/L;
514
    final float G1 = 0.5f*numL - munL*F;
515
    final float G2 = G1 - F/2;
516
    final float X3 = G2/2;
517
    final float Y3 = G2*SQ2/2;
518
    final float Z3 =-G2/2;
519
    final float G3 = G1 - F;
520
    final float X4 = G3/2;
521
    final float Y4 = G3*SQ2/2;
522
    final float Z4 =-G3/2;
523
    final float K  = 0.2f*(1 - F/(2*G2));
524

    
525
    if( variant==0 )
526
      {
527
      return new float[][]
528
        {
529
            { 0,   0,     0},
530
            { X,   Y,   Z  },
531
            { 0, 2*Y, 2*Z  },
532
            {-X,   Y,   Z  },
533
            { 0,   0,    -F},
534
            { X,   Y,   Z-F},
535
            { 0, 2*Y, 2*Z-F},
536
            {-X,   Y,   Z-F},
537
        };
538
      }
539
    else if( variant==1 && (type==JING_2 || type==JING_4) )
540
      {
541
      return new float[][]
542
        {
543
            { 0,   0,     G1 },
544
            { X,   Y,   Z+G1 },
545
            { 0, 2*Y, 2*Z+G1 },
546
            {-X,   Y,   Z+G1 },
547
            { 0,   0,    -G1 },
548
            { X,   Y,  -Z-G1 },
549
            { 0, 2*Y,-2*Z-G1 },
550
            {-X,   Y,  -Z-G1 },
551
        };
552
      }
553
    else if( variant==1 && (type==JING_3 || type==JING_5) )
554
      {
555
      return new float[][]
556
        {
557
            { 0,   0,   0 },
558
            { X,   Y,   Z },
559
            { 0, 2*Y, 2*Z },
560
            {-X,   Y,   Z },
561
            { 0,   0, -G1 },
562
            { X,   Y, -G1 },
563
            {-X,   Y, -G1 },
564
        };
565
      }
566
    else if( variant==2 && type==JING_3 )
567
      {
568
      return new float[][]
569
        {
570
            {  0,    0,    0 },
571
            { X3,   Y3,   Z3 },
572
            {  0, (2*SQ2/3)*G2, (-2.0f/3)*G2 },
573
            {-X3,   Y3,   Z3 },
574
            {  0,    0,  -G2 },
575
            { K*X3,   K*Y3,  K*Z3-G2 },
576
            {  0, K*(2*SQ2/3)*G2, K*(-2.0f/3)*G2 - G2 },
577
            {-K*X3,   K*Y3,  K*Z3-G2 },
578
        };
579
      }
580
    else if( variant==2 && type==JING_4 )
581
      {
582
      return new float[][]
583
        {
584
            { 0,   0,     G2},
585
            { X,   Y,   Z+G2},
586
            { 0, 2*Y, 2*Z+G2},
587
            {-X,   Y,   Z+G2},
588
            { 0,   0,    -G2},
589
            { X,   Y,  -Z-G2},
590
            { 0, 2*Y,-2*Z-G2},
591
            {-X,   Y,  -Z-G2},
592
        };
593
      }
594
    else if( variant==2 && type==JING_5 )
595
      {
596
      return new float[][]
597
        {
598
            { 0,   0,   0 },
599
            { X,   Y,   Z },
600
            {-X,   Y,   Z },
601
            { 0,   0, -G2 },
602
            { X,   Y, -G2 }
603
        };
604
      }
605
    else if( variant==3 && type==JING_5 )
606
      {
607
      return new float[][]
608
        {
609
            { 0,   0,   0 },
610
            {-X,   Y,  -Z },
611
            { X,   Y,  -Z },
612
            { 0,   0,  G2 },
613
            { X,   Y,  G2 },
614
        };
615
      }
616
    else if( variant==4 && type==JING_5 )
617
      {
618
      return new float[][]
619
        {
620
            {  0,    0,    0 },
621
            { X4,   Y4,   Z4 },
622
            {  0, (2*SQ2/3)*G3, (-2.0f/3)*G3 },
623
            {-X4,   Y4,   Z4 },
624
            {  0,    0,  -G3 },
625
            { K*X4,   K*Y4,  K*Z4-G3 },
626
            {  0, K*(2*SQ2/3)*G3, K*(-2.0f/3)*G3 - G3 },
627
            {-K*X4,   K*Y4,  K*Z4-G3 },
628
        };
629
      }
630
    else
631
      {
632
      return new float[][]
633
        {
634
            {  0     , -2*Y2/3     , -2*Z2/3       },
635
            { X2     ,    Y2/3     ,    Z2/3       },
636
            {-X2     ,    Y2/3     ,    Z2/3       },
637
            {  0     , -2*Y2/3     , -2*Z2/3+2*D*Z2},
638
            { X2-D*X2,    Y2/3-D*Y2,    Z2/3+  D*Z2},
639
            {-X2+D*X2,    Y2/3-D*Y2,    Z2/3+  D*Z2},
640
        };
641
      }
642
    }
643

    
644
///////////////////////////////////////////////////////////////////////////////////////////////////
645

    
646
  public ObjectShape getObjectShape(int variant)
647
    {
648
    int type = getObjectType();
649

    
650
    if( variant==0 )
651
      {
652
      int[][] indices =
653
          {
654
             {0,1,2,3},
655
             {1,0,4,5},
656
             {7,4,0,3},
657
             {1,5,6,2},
658
             {7,3,2,6},
659
             {4,7,6,5}
660
          };
661

    
662
      return new ObjectShape(getVertices(variant), indices);
663
      }
664
    else if( (variant==1 && (type==JING_2 || type==JING_4)) || (variant==2 && type==JING_4)  )
665
      {
666
      int[][] indices =
667
          {
668
             {0,4,5,1},
669
             {3,7,4,0},
670
             {0,1,2,3},
671
             {4,7,6,5},
672
             {1,5,6,2},
673
             {2,6,7,3}
674
          };
675

    
676
      return new ObjectShape(getVertices(variant), indices);
677
      }
678
    else if( (variant==2 && type==JING_3) || (variant==4 && type==JING_5) )
679
      {
680
      int[][] indices =
681
          {
682
             {0,1,2,3},
683
             {0,4,5,1},
684
             {3,7,4,0},
685
             {4,7,6,5},
686
             {1,5,6,2},
687
             {2,6,7,3}
688
          };
689

    
690
      return new ObjectShape(getVertices(variant), indices);
691
      }
692
    else if( variant==1 && (type==JING_3 || type==JING_5)  )
693
      {
694
      int[][] indices =
695
          {
696
             {0,4,5,1},
697
             {3,6,4,0},
698
             {0,1,2,3},
699
             {1,5,2},
700
             {2,6,3},
701
             {4,2,5},
702
             {4,6,2}
703
          };
704

    
705
      return new ObjectShape(getVertices(variant), indices);
706
      }
707
    else if( variant==2 && type==JING_5 )
708
      {
709
      int[][] indices =
710
          {
711
             {0,3,4,1},
712
             {2,3,0},
713
             {0,1,2},
714
             {4,3,2},
715
             {1,4,2}
716
          };
717

    
718
      return new ObjectShape(getVertices(variant), indices);
719
      }
720
    else if( variant==3 && type==JING_5 )
721
      {
722
      int[][] indices =
723
          {
724
             {0,2,4,3},
725
             {3,1,0},
726
             {0,1,2},
727
             {3,4,1},
728
             {1,4,2}
729
          };
730

    
731
      return new ObjectShape(getVertices(variant), indices);
732
      }
733
    else
734
      {
735
      int[][] indices =
736
          {
737
             {0,1,2},
738
             {3,5,4},
739
             {0,3,4,1},
740
             {5,3,0,2},
741
             {4,5,2,1}
742
          };
743

    
744
      return new ObjectShape(getVertices(variant), indices);
745
      }
746
    }
747

    
748
///////////////////////////////////////////////////////////////////////////////////////////////////
749

    
750
  public ObjectFaceShape getObjectFaceShape(int variant)
751
    {
752
    int type = getObjectType();
753
    float R = 0.3f;
754
    float S = 0.5f;
755
    float H = 0.015f;
756

    
757
    if( variant==0 )
758
      {
759
      int I = type!=JING_5 ? 1:0;
760
      int V = type!=JING_5 ? 1:0;
761
      float height = isInIconMode() ? 0.001f : H;
762
      float[][] bands = { {height,35,R,S,5,I,V},{0.001f,1,R,S,5,I,V} };
763
      int[] indices   = { 0,0,0,1,1,1 };
764
      return new ObjectFaceShape(bands,indices,null);
765
      }
766
    else if( variant==1 && (type==JING_2 || type==JING_4) )
767
      {
768
      int N1 = type==JING_2 ? 9:7;
769
      int N2 = type==JING_2 ? 9:4;
770
      float height = isInIconMode() ? 0.001f : H;
771
      float[][] bands = { {height,35,R,S,N1,0,0},{0.001f,1,R,S,N2,0,0} };
772
      int[] indices   = { 0,0,1,1,1,1 };
773
      return new ObjectFaceShape(bands,indices,null);
774
      }
775
    else if( variant==1 && (type==JING_3 || type==JING_5) )
776
      {
777
      int N = type==JING_3 ? 7:5;
778
      float height = isInIconMode() ? 0.001f : H;
779
      float[][] bands = { {height,35,R,S,N,0,0},{0.001f,1,R,S,4,0,0} };
780
      int[] indices   = { 0,0,1,1,1,1,1 };
781
      return new ObjectFaceShape(bands,indices,null);
782
      }
783
    else if( (variant==2 || variant==3) && type==JING_5 )
784
      {
785
      int N = 5;
786
      float height = isInIconMode() ? 0.001f : H;
787
      float[][] bands = { {height,35,R,S,N,0,0},{0.001f,1,R,S,4,0,0} };
788
      int[] indices   = { 0,1,1,1,1,1,1 };
789
      return new ObjectFaceShape(bands,indices,null);
790
      }
791
    else if( variant==2 && type==JING_4 )
792
      {
793
      float height = isInIconMode() ? 0.001f : H;
794
      float[][] bands = { {height,35,R,S,6,0,0},{0.001f,1,R,S,4,0,0} };
795
      int[] indices   = { 0,1,1,1,1,1 };
796
      return new ObjectFaceShape(bands,indices,null);
797
      }
798
    else
799
      {
800
      int N = type==JING_2 ? 5: (type==JING_3 ? 4:2);
801
      float height = isInIconMode() ? 0.001f : H;
802
      float[][] bands = { {height,35,R,S,N,0,0}, {0.001f,1,R,S,N,0,0} };
803
      int[] indices   = { 0,1,1,1,1,1 };
804
      return new ObjectFaceShape(bands,indices,null);
805
      }
806
    }
807

    
808
///////////////////////////////////////////////////////////////////////////////////////////////////
809

    
810
  public ObjectVertexEffects getVertexEffects(int variant)
811
    {
812
    int type = getObjectType();
813
    final float F = JING_F[type];
814
    final float Y = F*SQ2/2;
815
    final float Z =-F/2;
816

    
817
    if( variant==0 )
818
      {
819
      float[][] corners   = { {0.08f,0.10f},{0.04f,0.10f} };
820
      int[] cornerIndices = { 0,1,1,1,1,-1,-1,-1 };
821
      float[][] centers   = { { 0.0f, Y, Z-F/2} };
822
      int[] centerIndices = { 0,0,0,0,0,-1,-1,-1 };
823
      return FactoryCubit.generateVertexEffect(getVertices(variant),corners,cornerIndices,centers,centerIndices);
824
      }
825
    else if( variant==1 )
826
      {
827
      float[][] corners   = { { 0.05f,0.10f} };
828
      int[] cornerIndices = { 0,-1,-1,-1,0,-1,-1,-1 };
829
      float[][] centers   = { { 0, F*SQ2/2, 0 } };
830
      int[] centerIndices = { 0,-1,-1,-1,0,-1,-1,-1 };
831
      return FactoryCubit.generateVertexEffect(getVertices(variant),corners,cornerIndices,centers,centerIndices);
832
      }
833
    else return null;
834
    }
835

    
836
///////////////////////////////////////////////////////////////////////////////////////////////////
837

    
838
  public int getNumCubitVariants(int[] numLayers)
839
    {
840
    switch(getObjectType())
841
      {
842
      case JING_2:
843
      case JING_3: return 3;
844
      case JING_4: return 4;
845
      case JING_5: return 5;
846
      }
847

    
848
    return 0;
849
    }
850

    
851
///////////////////////////////////////////////////////////////////////////////////////////////////
852

    
853
  public int getCubitVariant(int cubit, int[] numLayers)
854
    {
855
    switch( getObjectType() )
856
      {
857
      case  JING_2: return cubit< 4 ? 0 : (cubit<10 ? 1:2);
858
      case  JING_3: return cubit< 4 ? 0 : (cubit<16 ? 1:2);
859
      case  JING_4: return cubit<28 ? 0 : (cubit<34 ? 1 : (cubit<46 ? 2:3) );
860
      case  JING_5: return cubit<28 ? 0 : (cubit<40 ? 1 : (cubit<52 ? 2: (cubit<64 ? 3:4)) );
861
      }
862

    
863
    return 0;
864
    }
865

    
866
///////////////////////////////////////////////////////////////////////////////////////////////////
867

    
868
  public float getStickerRadius()
869
    {
870
    switch( getObjectType() )
871
      {
872
      case JING_2: return 0.05f;
873
      case JING_3: return 0.06f;
874
      case JING_4: return 0.07f;
875
      case JING_5: return 0.08f;
876
      }
877

    
878
    return 0;
879
    }
880

    
881
///////////////////////////////////////////////////////////////////////////////////////////////////
882

    
883
  public float getStickerStroke()
884
    {
885
    boolean icon = isInIconMode();
886

    
887
    switch( getObjectType() )
888
      {
889
      case JING_2: return icon ? 0.10f : 0.05f;
890
      case JING_3: return icon ? 0.14f : 0.07f;
891
      case JING_4: return icon ? 0.12f : 0.06f;
892
      case JING_5: return icon ? 0.16f : 0.08f;
893
      }
894

    
895
    return 0;
896
    }
897

    
898
///////////////////////////////////////////////////////////////////////////////////////////////////
899

    
900
  public float[][][] getStickerAngles()
901
    {
902
    return null;
903
    }
904

    
905
///////////////////////////////////////////////////////////////////////////////////////////////////
906
// PUBLIC API
907

    
908
  public Static3D[] getRotationAxis()
909
    {
910
    return ROT_AXIS;
911
    }
912

    
913
///////////////////////////////////////////////////////////////////////////////////////////////////
914

    
915
  public int[][] getBasicAngles()
916
    {
917
    if( mBasicAngle==null )
918
      {
919
      int num = getNumLayers()[0];
920
      int[] tmp = new int[num];
921
      for(int i=0; i<num; i++) tmp[i] = 3;
922
      mBasicAngle = new int[][] { tmp,tmp,tmp,tmp };
923
      }
924

    
925
    return mBasicAngle;
926
    }
927

    
928
///////////////////////////////////////////////////////////////////////////////////////////////////
929

    
930
  public String getShortName()
931
    {
932
    switch( getObjectType() )
933
      {
934
      case JING_2: return ListObjects.JING_2.name();
935
      case JING_3: return ListObjects.JING_3.name();
936
      case JING_4: return ListObjects.JING_4.name();
937
      case JING_5: return ListObjects.JING_5.name();
938
      }
939

    
940
    return null;
941
    }
942

    
943
///////////////////////////////////////////////////////////////////////////////////////////////////
944

    
945
  public String[][] getTutorials()
946
    {
947
    if( getObjectType()==JING_2 )
948
      return new String[][]
949
                         {
950
                          {"gb","0T8Iw6aI2gA","Jing's Pyraminx Tutorial","SuperAntoniovivaldi"},
951
                          {"es","Na27_GUIzqY","Resolver Jing Pyraminx","Cuby"},
952
                          {"ru","rlQXFzjsyAo","Как собрать Jing's pyraminx","Илья Топор-Гилка"},
953
                          {"fr","zC9dGqZRSic","Résolution du Jing's Pyraminx","Asthalis"},
954
                          {"de","6ihN4fdHH6o","Jings Pyraminx - Tutorial","GerCubing"},
955
                          {"pl","nRYoJAy1c_8","Jing's Pyraminx TUTORIAL PL","MrUK"},
956
                          {"vn","yX9KjDpHjws","Tutorial N.50 - Jing's Pyraminx","Duy Thích Rubik"},
957
                         };
958
    else if( getObjectType()==JING_3 )
959
      return new String[][]
960
                         {
961
                          {"gb","FYHdSpeMdqA","Four Layer Tetrahedral Solve","Superantoniovivaldi"},
962
                          {"es","NH0x_zn8xtU","Tutorial: Magic Tower 4x4","QBAndo"},
963
                          {"ru","E1O5KauTBeI","Как собрать Magic Tower 4x4","Алексей Ярыгин"},
964
                          {"tw","DFJ6q11B03Q","四階魔塔 教學","不正常魔術方塊研究中心"},
965
                         };
966
    else if( getObjectType()==JING_4 )
967
      return new String[][]
968
                         {
969
                          {"gb","81xWI6iqMAc","Five Layer Tetrahedral Solve","Superantoniovivaldi"},
970
                          {"es","JRojNv32amY","Tutorial: Magic Tower 5x5","Víctor Martínez"},
971
                          {"ru","wHwG6dqjwh0","Как собрать Magic Tower 5x5","Алексей Ярыгин"},
972
                          {"vn","DWZbEydn98E","Tutorial N.143 - 5x5 Pyramid","Duy Thích Rubik"},
973
                          {"tw","w7rCoRsgsA0","五階魔塔 教學","不正常魔術方塊研究中心"},
974
                         };
975
    else if( getObjectType()==JING_5 )
976
      return new String[][]
977
                         {
978
                          {"gb","bNJ-SJ1uUrE","6 Layer Jing Pyraminx Tutorial","Sassy Monk"},
979
                          {"vn","rP3GPrSs35g","Tutorial N.162 - 6x6 Pyramid","Duy Thích Rubik"},
980
                          {"tw","eHbvOZDv4D8","六階魔塔 教學","不正常魔術方塊研究中心"},
981
                         };
982
    else
983
      return null;
984
    }
985
}
(26-26/59)