Project

General

Profile

Download (14.2 KB) Statistics
| Branch: | Tag: | Revision:

magiccube / src / main / java / org / distorted / objects / TwistyCube.java @ 7ee89540

1
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2019 Leszek Koltunski                                                               //
3
//                                                                                               //
4
// This file is part of Magic Cube.                                                              //
5
//                                                                                               //
6
// Magic Cube 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
// Magic Cube 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 Magic Cube.  If not, see <http://www.gnu.org/licenses/>.                           //
18
///////////////////////////////////////////////////////////////////////////////////////////////////
19

    
20
package org.distorted.objects;
21

    
22
import static org.distorted.objects.Movement.TYPE_NOT_SPLIT;
23

    
24
import android.content.res.Resources;
25

    
26
import org.distorted.helpers.ObjectShape;
27
import org.distorted.helpers.ObjectSticker;
28
import org.distorted.helpers.ScrambleState;
29
import org.distorted.library.main.DistortedEffects;
30
import org.distorted.library.main.DistortedTexture;
31
import org.distorted.library.mesh.MeshSquare;
32
import org.distorted.library.type.Static3D;
33
import org.distorted.library.type.Static4D;
34
import org.distorted.main.R;
35

    
36
///////////////////////////////////////////////////////////////////////////////////////////////////
37

    
38
class TwistyCube extends Twisty6
39
{
40
  static final Static3D[] ROT_AXIS = new Static3D[]
41
         {
42
           new Static3D(1,0,0),
43
           new Static3D(0,1,0),
44
           new Static3D(0,0,1)
45
         };
46

    
47
  private static final int[][][] ENABLED = new int[][][]
48
      {
49
          {{1,2}},{{1,2}},{{0,2}},{{0,2}},{{0,1}},{{0,1}},
50
      };
51

    
52
  private ScrambleState[] mStates;
53
  private Static4D[] mQuats;
54
  private float[][] mCuts;
55
  private boolean[][] mLayerRotatable;
56
  private int[] mBasicAngle;
57
  private ObjectSticker[] mStickers;
58
  private Movement mMovement;
59

    
60
///////////////////////////////////////////////////////////////////////////////////////////////////
61

    
62
  TwistyCube(int size, Static4D quat, DistortedTexture texture, MeshSquare mesh,
63
             DistortedEffects effects, int[][] moves, Resources res, int scrWidth)
64
    {
65
    super(size, size, quat, texture, mesh, effects, moves, ObjectList.CUBE, res, scrWidth);
66
    }
67

    
68
///////////////////////////////////////////////////////////////////////////////////////////////////
69

    
70
  ScrambleState[] getScrambleStates()
71
    {
72
    if( mStates==null )
73
      {
74
      int size = getNumLayers();
75
      int[][] m = new int[16][];
76
      for(int i=1; i<16; i++) m[i] = createEdges(size,i);
77

    
78
      mStates = new ScrambleState[]
79
        {
80
        new ScrambleState( new int[][] { m[ 1], m[ 2], m[ 3] } ),  // 0
81
        new ScrambleState( new int[][] {  null, m[ 4], m[ 5] } ),  // x
82
        new ScrambleState( new int[][] { m[ 6],  null, m[ 7] } ),  // y
83
        new ScrambleState( new int[][] { m[ 8], m[ 8],  null } ),  // z
84
        new ScrambleState( new int[][] { m[10],  null, m[ 7] } ),  // xy
85
        new ScrambleState( new int[][] { m[11], m[ 9],  null } ),  // xz
86
        new ScrambleState( new int[][] {  null, m[12], m[ 5] } ),  // yx
87
        new ScrambleState( new int[][] { m[ 8], m[13],  null } ),  // yz
88
        new ScrambleState( new int[][] {  null, m[ 4], m[14] } ),  // zx
89
        new ScrambleState( new int[][] { m[ 6],  null, m[15] } ),  // zy
90
        new ScrambleState( new int[][] {  null,  null, m[ 5] } ),  // xyx
91
        new ScrambleState( new int[][] {  null, m[ 4],  null } ),  // xzx
92
        new ScrambleState( new int[][] {  null,  null, m[ 7] } ),  // yxy
93
        new ScrambleState( new int[][] { m[ 6],  null,  null } ),  // yzy
94
        new ScrambleState( new int[][] {  null, m[ 9],  null } ),  // zxz
95
        new ScrambleState( new int[][] { m[ 8],  null,  null } ),  // zyz
96
        };
97
      }
98

    
99
    return mStates;
100
    }
101

    
102
///////////////////////////////////////////////////////////////////////////////////////////////////
103

    
104
  private int[] createEdges(int size, int vertex)
105
    {
106
    int[] ret = new int[9*size];
107

    
108
    for(int l=0; l<size; l++)
109
      {
110
      ret[9*l  ] = l;
111
      ret[9*l+1] =-1;
112
      ret[9*l+2] = vertex;
113
      ret[9*l+3] = l;
114
      ret[9*l+4] = 1;
115
      ret[9*l+5] = vertex;
116
      ret[9*l+6] = l;
117
      ret[9*l+7] = 2;
118
      ret[9*l+8] = vertex;
119
      }
120

    
121
    return ret;
122
    }
123

    
124
///////////////////////////////////////////////////////////////////////////////////////////////////
125

    
126
  private void initializeQuats()
127
    {
128
    mQuats = new Static4D[]
129
         {
130
         new Static4D(  0.0f,   0.0f,   0.0f,   1.0f),
131
         new Static4D(  1.0f,   0.0f,   0.0f,   0.0f),
132
         new Static4D(  0.0f,   1.0f,   0.0f,   0.0f),
133
         new Static4D(  0.0f,   0.0f,   1.0f,   0.0f),
134

    
135
         new Static4D( SQ2/2,  SQ2/2,  0.0f ,   0.0f),
136
         new Static4D( SQ2/2, -SQ2/2,  0.0f ,   0.0f),
137
         new Static4D( SQ2/2,   0.0f,  SQ2/2,   0.0f),
138
         new Static4D(-SQ2/2,   0.0f,  SQ2/2,   0.0f),
139
         new Static4D( SQ2/2,   0.0f,   0.0f,  SQ2/2),
140
         new Static4D( SQ2/2,   0.0f,   0.0f, -SQ2/2),
141
         new Static4D(  0.0f,  SQ2/2,  SQ2/2,   0.0f),
142
         new Static4D(  0.0f,  SQ2/2, -SQ2/2,   0.0f),
143
         new Static4D(  0.0f,  SQ2/2,   0.0f,  SQ2/2),
144
         new Static4D(  0.0f,  SQ2/2,   0.0f, -SQ2/2),
145
         new Static4D(  0.0f,   0.0f,  SQ2/2,  SQ2/2),
146
         new Static4D(  0.0f,   0.0f,  SQ2/2, -SQ2/2),
147

    
148
         new Static4D(  0.5f,   0.5f,   0.5f,   0.5f),
149
         new Static4D(  0.5f,   0.5f,  -0.5f,   0.5f),
150
         new Static4D(  0.5f,   0.5f,  -0.5f,  -0.5f),
151
         new Static4D(  0.5f,  -0.5f,   0.5f,  -0.5f),
152
         new Static4D( -0.5f,  -0.5f,  -0.5f,   0.5f),
153
         new Static4D( -0.5f,   0.5f,  -0.5f,  -0.5f),
154
         new Static4D( -0.5f,   0.5f,   0.5f,  -0.5f),
155
         new Static4D( -0.5f,   0.5f,   0.5f,   0.5f)
156
         };
157
    }
158

    
159
///////////////////////////////////////////////////////////////////////////////////////////////////
160

    
161
  int[] getSolvedQuats(int cubit, int numLayers)
162
    {
163
    if( mQuats ==null ) initializeQuats();
164
    int status = retCubitSolvedStatus(cubit,numLayers);
165
    return status<0 ? null : buildSolvedQuats(Movement6.FACE_AXIS[status], mQuats);
166
    }
167

    
168
///////////////////////////////////////////////////////////////////////////////////////////////////
169

    
170
  ObjectShape getObjectShape(int cubit, int numLayers)
171
    {
172
    int extraI, extraV, num;
173
    float height;
174

    
175
    switch(numLayers)
176
      {
177
      case 2 : num = 6; extraI = 2; extraV = 2; height = 0.045f; break;
178
      case 3 : num = 5; extraI = 2; extraV = 2; height = 0.045f; break;
179
      case 4 : num = 5; extraI = 1; extraV = 1; height = 0.045f; break;
180
      default: num = 5; extraI = 0; extraV = 0; height = 0.045f; break;
181
      }
182

    
183
    double[][] vertices = new double[][]
184
          {
185
              { 0.5, 0.5, 0.5 },
186
              { 0.5, 0.5,-0.5 },
187
              { 0.5,-0.5, 0.5 },
188
              { 0.5,-0.5,-0.5 },
189
              {-0.5, 0.5, 0.5 },
190
              {-0.5, 0.5,-0.5 },
191
              {-0.5,-0.5, 0.5 },
192
              {-0.5,-0.5,-0.5 },
193
          };
194

    
195
    int[][] vert_indices = new int[][]
196
          {
197
              {2,3,1,0},
198
              {7,6,4,5},
199
              {4,0,1,5},
200
              {7,3,2,6},
201
              {6,2,0,4},
202
              {3,7,5,1}
203
          };
204

    
205
    float[][] bands     = new float[][] { {height,35,0.5f,0.7f,num,extraI,extraV} };
206
    int[] bandIndices   = new int[] { 0,0,0,0,0,0};
207
    float[][] corners   = new float[][] { {0.036f,0.12f} };
208
    int[] cornerIndices = new int[] { 0,0,0,0,0,0,0,0 };
209
    float[][] centers   = new float[][] { {0.0f, 0.0f, 0.0f} };
210
    int[] centerIndices = new int[] { 0,0,0,0,0,0,0,0 };
211

    
212
    return new ObjectShape(vertices,vert_indices,bands,bandIndices,corners,cornerIndices,centers,centerIndices,getNumCubitFaces(), null);
213
    }
214

    
215
///////////////////////////////////////////////////////////////////////////////////////////////////
216

    
217
  Static4D getQuat(int cubit, int numLayers)
218
    {
219
    if( mQuats ==null ) initializeQuats();
220
    return mQuats[0];
221
    }
222

    
223
///////////////////////////////////////////////////////////////////////////////////////////////////
224

    
225
  int getNumCubitVariants(int numLayers)
226
    {
227
    return 1;
228
    }
229

    
230
///////////////////////////////////////////////////////////////////////////////////////////////////
231

    
232
  int getCubitVariant(int cubit, int numLayers)
233
    {
234
    return 0;
235
    }
236

    
237
///////////////////////////////////////////////////////////////////////////////////////////////////
238

    
239
  ObjectSticker retSticker(int face)
240
    {
241
    if( mStickers==null )
242
      {
243
      final float[][] STICKERS = new float[][]  { { -0.5f, -0.5f, 0.5f, -0.5f, 0.5f, 0.5f, -0.5f, 0.5f } };
244
      final float radius = 0.10f;
245
      final float stroke = 0.08f;
246
      final float[] radii = {radius,radius,radius,radius};
247
      mStickers = new ObjectSticker[STICKERS.length];
248
      mStickers[0] = new ObjectSticker(STICKERS[0],null,radii,stroke );
249
      }
250

    
251
    return mStickers[face/NUM_FACE_COLORS];
252
    }
253

    
254
///////////////////////////////////////////////////////////////////////////////////////////////////
255

    
256
  float[][] getCubitPositions(int numLayers)
257
    {
258
    int numCubits = numLayers>1 ? 6*numLayers*numLayers - 12*numLayers + 8 : 1;
259
    float[][] tmp = new float[numCubits][];
260

    
261
    float diff = 0.5f*(numLayers-1);
262
    int currentPosition = 0;
263

    
264
    for(int x = 0; x<numLayers; x++)
265
      for(int y = 0; y<numLayers; y++)
266
        for(int z = 0; z<numLayers; z++)
267
          if( x==0 || x==numLayers-1 || y==0 || y==numLayers-1 || z==0 || z==numLayers-1 )
268
            {
269
            tmp[currentPosition++] = new float[] {x-diff,y-diff,z-diff};
270
            }
271

    
272
    return tmp;
273
    }
274

    
275
///////////////////////////////////////////////////////////////////////////////////////////////////
276

    
277
  Static4D[] getQuats()
278
    {
279
    if( mQuats ==null ) initializeQuats();
280
    return mQuats;
281
    }
282

    
283
///////////////////////////////////////////////////////////////////////////////////////////////////
284

    
285
  float[][] getCuts(int numLayers)
286
    {
287
    if( numLayers<2 ) return null;
288

    
289
    if( mCuts==null )
290
      {
291
      mCuts = new float[3][numLayers-1];
292

    
293
      for(int i=0; i<numLayers-1; i++)
294
        {
295
        float cut = (2-numLayers)*0.5f + i;
296
        mCuts[0][i] = cut;
297
        mCuts[1][i] = cut;
298
        mCuts[2][i] = cut;
299
        }
300
      }
301

    
302
    return mCuts;
303
    }
304

    
305
///////////////////////////////////////////////////////////////////////////////////////////////////
306

    
307
  private void getLayerRotatable(int numLayers)
308
    {
309
    if( mLayerRotatable==null )
310
      {
311
      int numAxis = ROT_AXIS.length;
312
      boolean[] tmp = new boolean[numLayers];
313
      for(int i=0; i<numLayers; i++) tmp[i] = true;
314
      mLayerRotatable = new boolean[numAxis][];
315
      for(int i=0; i<numAxis; i++) mLayerRotatable[i] = tmp;
316
      }
317
    }
318

    
319
///////////////////////////////////////////////////////////////////////////////////////////////////
320

    
321
  int getSolvedFunctionIndex()
322
    {
323
    return 0;
324
    }
325

    
326
///////////////////////////////////////////////////////////////////////////////////////////////////
327

    
328
  int getNumStickerTypes(int numLayers)
329
    {
330
    return 1;
331
    }
332

    
333
///////////////////////////////////////////////////////////////////////////////////////////////////
334

    
335
  int getNumCubitFaces()
336
    {
337
    return 6;
338
    }
339

    
340
///////////////////////////////////////////////////////////////////////////////////////////////////
341

    
342
  int getFaceColor(int cubit, int cubitface, int numLayers)
343
    {
344
    return CUBITS[cubit].mRotationRow[cubitface/2] == (cubitface%2==0 ? (1<<(numLayers-1)):1) ? cubitface : NUM_TEXTURES;
345
    }
346

    
347
///////////////////////////////////////////////////////////////////////////////////////////////////
348
// PUBLIC API
349

    
350
  public Static3D[] getRotationAxis()
351
    {
352
    return ROT_AXIS;
353
    }
354

    
355
///////////////////////////////////////////////////////////////////////////////////////////////////
356

    
357
  public Movement getMovement()
358
    {
359
    if( mMovement==null )
360
      {
361
      int numLayers = getNumLayers();
362
      if( mCuts==null ) getCuts(numLayers);
363
      getLayerRotatable(numLayers);
364
      mMovement = new Movement6(ROT_AXIS,mCuts,mLayerRotatable,numLayers,TYPE_NOT_SPLIT,ENABLED);
365
      }
366
    return mMovement;
367
    }
368

    
369
///////////////////////////////////////////////////////////////////////////////////////////////////
370

    
371
  public int[] getBasicAngle()
372
    {
373
    if( mBasicAngle==null ) mBasicAngle = new int[] { 4,4,4 };
374
    return mBasicAngle;
375
    }
376

    
377
///////////////////////////////////////////////////////////////////////////////////////////////////
378

    
379
  public int getObjectName(int numLayers)
380
    {
381
    switch(numLayers)
382
      {
383
      case 2: return R.string.cube2;
384
      case 3: return R.string.cube3;
385
      case 4: return R.string.cube4;
386
      case 5: return R.string.cube5;
387
      }
388
    return R.string.cube3;
389
    }
390

    
391
///////////////////////////////////////////////////////////////////////////////////////////////////
392

    
393
  public int getInventor(int numLayers)
394
    {
395
    switch(numLayers)
396
      {
397
      case 2: return R.string.cube2_inventor;
398
      case 3: return R.string.cube3_inventor;
399
      case 4: return R.string.cube4_inventor;
400
      case 5: return R.string.cube5_inventor;
401
      }
402
    return R.string.cube3_inventor;
403
    }
404

    
405
///////////////////////////////////////////////////////////////////////////////////////////////////
406

    
407
  public int getComplexity(int numLayers)
408
    {
409
    switch(numLayers)
410
      {
411
      case 2: return 4;
412
      case 3: return 6;
413
      case 4: return 8;
414
      case 5: return 10;
415
      }
416
    return 6;
417
    }
418
}
(17-17/38)