Project

General

Profile

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

distorted-objectlib / src / main / java / org / distorted / objectlib / objects / TwistyMirror.java @ 3bf19410

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.objectlib.objects;
21

    
22
import static org.distorted.objectlib.touchcontrol.TouchControl.TC_CHANGING_MIRROR;
23
import static org.distorted.objectlib.touchcontrol.TouchControl.TYPE_NOT_SPLIT;
24

    
25
import java.io.InputStream;
26

    
27
import org.distorted.library.type.Static3D;
28
import org.distorted.library.type.Static4D;
29

    
30
import org.distorted.objectlib.helpers.ObjectFaceShape;
31
import org.distorted.objectlib.main.ObjectType;
32
import org.distorted.objectlib.helpers.ObjectShape;
33
import org.distorted.objectlib.scrambling.ScrambleState;
34
import org.distorted.objectlib.main.ShapeHexahedron;
35
import org.distorted.objectlib.touchcontrol.TouchControlHexahedron;
36

    
37
///////////////////////////////////////////////////////////////////////////////////////////////////
38

    
39
public class TwistyMirror extends ShapeHexahedron
40
{
41
  static final Static3D[] ROT_AXIS = new Static3D[]
42
         {
43
           new Static3D(1,0,0),
44
           new Static3D(0,1,0),
45
           new Static3D(0,0,1)
46
         };
47

    
48
  private static final int[] FACE_COLORS = new int[] { COLOR_WHITE };
49
  private static final float DX = 0.10f;
50
  private static final float DY = 0.25f;
51
  private static final float DZ = 0.40f;
52

    
53
  private ScrambleState[] mStates;
54
  private float[][] mCuts;
55
  private int[] mBasicAngle;
56
  private float[][] mPositions;
57

    
58
///////////////////////////////////////////////////////////////////////////////////////////////////
59

    
60
  public TwistyMirror(int[] numL, int meshState, int iconMode, Static4D quat, Static3D move, float scale, InputStream stream)
61
    {
62
    super(numL, meshState, iconMode, numL[0], quat, move, scale, stream);
63
    }
64

    
65
///////////////////////////////////////////////////////////////////////////////////////////////////
66

    
67
  @Override
68
  public int getInternalColor()
69
    {
70
    return 0xff333333;
71
    }
72

    
73
///////////////////////////////////////////////////////////////////////////////////////////////////
74

    
75
  @Override
76
  public int getColor(int face)
77
    {
78
    return FACE_COLORS[face];
79
    }
80

    
81
///////////////////////////////////////////////////////////////////////////////////////////////////
82

    
83
  @Override
84
  public int getNumFaceColors()
85
    {
86
    return 1;
87
    }
88

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

    
91
  public ScrambleState[] getScrambleStates()
92
    {
93
    if( mStates==null )
94
      {
95
      int[] numLayers = getNumLayers();
96
      int[][] m = new int[16][];
97
      for(int i=1; i<16; i++) m[i] = createEdges(numLayers[0],i);
98

    
99
      mStates = new ScrambleState[]
100
        {
101
        new ScrambleState( new int[][] { m[ 1], m[ 2], m[ 3] } ),  // 0
102
        new ScrambleState( new int[][] {  null, m[ 4], m[ 5] } ),  // x
103
        new ScrambleState( new int[][] { m[ 6],  null, m[ 7] } ),  // y
104
        new ScrambleState( new int[][] { m[ 8], m[ 8],  null } ),  // z
105
        new ScrambleState( new int[][] { m[10],  null, m[ 7] } ),  // xy
106
        new ScrambleState( new int[][] { m[11], m[ 9],  null } ),  // xz
107
        new ScrambleState( new int[][] {  null, m[12], m[ 5] } ),  // yx
108
        new ScrambleState( new int[][] { m[ 8], m[13],  null } ),  // yz
109
        new ScrambleState( new int[][] {  null, m[ 4], m[14] } ),  // zx
110
        new ScrambleState( new int[][] { m[ 6],  null, m[15] } ),  // zy
111
        new ScrambleState( new int[][] {  null,  null, m[ 5] } ),  // xyx
112
        new ScrambleState( new int[][] {  null, m[ 4],  null } ),  // xzx
113
        new ScrambleState( new int[][] {  null,  null, m[ 7] } ),  // yxy
114
        new ScrambleState( new int[][] { m[ 6],  null,  null } ),  // yzy
115
        new ScrambleState( new int[][] {  null, m[ 9],  null } ),  // zxz
116
        new ScrambleState( new int[][] { m[ 8],  null,  null } ),  // zyz
117
        };
118
      }
119

    
120
    return mStates;
121
    }
122

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

    
125
  private int[] createEdges(int size, int vertex)
126
    {
127
    int[] ret = new int[9*size];
128

    
129
    for(int l=0; l<size; l++)
130
      {
131
      ret[9*l  ] = l;
132
      ret[9*l+1] =-1;
133
      ret[9*l+2] = vertex;
134
      ret[9*l+3] = l;
135
      ret[9*l+4] = 1;
136
      ret[9*l+5] = vertex;
137
      ret[9*l+6] = l;
138
      ret[9*l+7] = 2;
139
      ret[9*l+8] = vertex;
140
      }
141

    
142
    return ret;
143
    }
144

    
145
///////////////////////////////////////////////////////////////////////////////////////////////////
146

    
147
  private int getRow(int cubit, int numLayers, int dim)
148
    {
149
    return (int)(mPositions[cubit][dim] + 0.5f*(numLayers-1));
150
    }
151

    
152
///////////////////////////////////////////////////////////////////////////////////////////////////
153

    
154
  public float[][] getCubitPositions(int[] numLayers)
155
    {
156
    if( mPositions==null )
157
      {
158
      int numL = numLayers[0];
159
      int numCubits = getNumCubitVariants(numLayers);
160
      mPositions = new float[numCubits][];
161

    
162
      float diff = 0.5f*(numL-1);
163
      int currentPosition = 0;
164

    
165
      for(int x = 0; x<numL; x++)
166
        for(int y = 0; y<numL; y++)
167
          for(int z = 0; z<numL; z++)
168
            if( x==0 || x==numL-1 || y==0 || y==numL-1 || z==0 || z==numL-1 )
169
              {
170
              mPositions[currentPosition++] = new float[] {x-diff,y-diff,z-diff};
171
              }
172
      }
173

    
174
    return mPositions;
175
    }
176

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

    
179
  public Static4D getCubitQuats(int cubit, int[] numLayers)
180
    {
181
    return mObjectQuats[0];
182
    }
183

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

    
186
  public ObjectShape getObjectShape(int variant)
187
    {
188
    int numL = getNumLayers()[0];
189
    int xrow = getRow(variant,numL,0);  // cubit == variant
190
    int yrow = getRow(variant,numL,1);
191
    int zrow = getRow(variant,numL,2);
192

    
193
    float XL = -0.5f + (xrow==     0 ? DX : 0);
194
    float XR = +0.5f + (xrow==numL-1 ? DX : 0);
195
    float YL = -0.5f - (yrow==     0 ? DY : 0);
196
    float YR = +0.5f - (yrow==numL-1 ? DY : 0);
197
    float ZL = -0.5f - (zrow==     0 ? DZ : 0);
198
    float ZR = +0.5f - (zrow==numL-1 ? DZ : 0);
199

    
200
    float[][] vertices =
201
          {
202
              { XR, YR, ZR },
203
              { XR, YR, ZL },
204
              { XR, YL, ZR },
205
              { XR, YL, ZL },
206
              { XL, YR, ZR },
207
              { XL, YR, ZL },
208
              { XL, YL, ZR },
209
              { XL, YL, ZL },
210
          };
211

    
212
    int[][] indices =
213
          {
214
              {2,3,1,0},
215
              {7,6,4,5},
216
              {4,0,1,5},
217
              {7,3,2,6},
218
              {6,2,0,4},
219
              {3,7,5,1}
220
          };
221

    
222
    return new ObjectShape(vertices, indices);
223
    }
224

    
225
///////////////////////////////////////////////////////////////////////////////////////////////////
226

    
227
  public ObjectFaceShape getObjectFaceShape(int variant)
228
    {
229
    int extraI, extraV, num, numL = getNumLayers()[0];
230
    float height = isInIconMode() ? 0.001f : 0.045f;
231

    
232
    switch(numL)
233
      {
234
      case 2 : num = 6; extraI = 2; extraV = 2; break;
235
      case 3 : num = 5; extraI = 2; extraV = 2; break;
236
      case 4 : num = 5; extraI = 0; extraV = 0; break;
237
      default: num = 4; extraI = 0; extraV = 0; break;
238
      }
239

    
240
    float[][] bands     = { {height,35,0.5f,0.7f,num,extraI,extraV} };
241
    int[] bandIndices   = { 0,0,0,0,0,0 };
242
    float[][] corners   = { {0.036f,0.12f} };
243
    int[] cornerIndices = { 0,0,0,0,0,0,0,0 };
244
    float[][] centers   = { {0.0f, 0.0f, 0.0f} };
245
    int[] centerIndices = { 0,0,0,0,0,0,0,0 };
246

    
247
    return new ObjectFaceShape(bands,bandIndices,corners,cornerIndices,centers,centerIndices,null);
248
    }
249

    
250
///////////////////////////////////////////////////////////////////////////////////////////////////
251

    
252
  public int getNumCubitVariants(int[] numLayers)
253
    {
254
    int numL = numLayers[0];
255
    return numL>1 ? 6*numL*numL - 12*numL + 8 : 1;
256
    }
257

    
258
///////////////////////////////////////////////////////////////////////////////////////////////////
259

    
260
  public int getCubitVariant(int cubit, int[] numLayers)
261
    {
262
    return cubit;
263
    }
264

    
265
///////////////////////////////////////////////////////////////////////////////////////////////////
266

    
267
  public float[][] getCuts(int[] numLayers)
268
    {
269
    if( mCuts==null )
270
      {
271
      int numL = numLayers[0];
272
      mCuts = new float[3][numL-1];
273

    
274
      for(int i=0; i<numL-1; i++)
275
        {
276
        float cut = (2-numL)*0.5f + i;
277
        mCuts[0][i] = cut;
278
        mCuts[1][i] = cut;
279
        mCuts[2][i] = cut;
280
        }
281
      }
282

    
283
    return mCuts;
284
    }
285

    
286
///////////////////////////////////////////////////////////////////////////////////////////////////
287

    
288
  public boolean[][] getLayerRotatable(int[] numLayers)
289
    {
290
    int num = numLayers[0];
291
    boolean[] tmp = new boolean[num];
292
    for(int i=0; i<num; i++) tmp[i] = true;
293
    return new boolean[][] { tmp,tmp,tmp };
294
    }
295

    
296
///////////////////////////////////////////////////////////////////////////////////////////////////
297

    
298
  public int getTouchControlType()
299
    {
300
    return TC_CHANGING_MIRROR;
301
    }
302

    
303
///////////////////////////////////////////////////////////////////////////////////////////////////
304

    
305
  public int getTouchControlSplit()
306
    {
307
    return TYPE_NOT_SPLIT;
308
    }
309

    
310
///////////////////////////////////////////////////////////////////////////////////////////////////
311

    
312
  public int[][][] getEnabled()
313
    {
314
    return null;
315
    }
316

    
317
///////////////////////////////////////////////////////////////////////////////////////////////////
318

    
319
  public float[] getDist3D(int[] numLayers)
320
    {
321
    int N = numLayers[0];
322
    return new float[] { 0.5f+DX/N, 0.5f-DX/N, 0.5f-DY/N, 0.5f+DY/N, 0.5f-DZ/N, 0.5f+DZ/N };
323
    }
324

    
325
///////////////////////////////////////////////////////////////////////////////////////////////////
326

    
327
  public Static3D[] getFaceAxis()
328
    {
329
    return TouchControlHexahedron.FACE_AXIS;
330
    }
331

    
332
///////////////////////////////////////////////////////////////////////////////////////////////////
333

    
334
  public float getStickerRadius()
335
    {
336
    return 0.10f;
337
    }
338

    
339
///////////////////////////////////////////////////////////////////////////////////////////////////
340

    
341
  public float getStickerStroke()
342
    {
343
    float stroke = 0.08f;
344

    
345
    if( isInIconMode() )
346
      {
347
      int[] numLayers = getNumLayers();
348
      stroke*= ( numLayers[0]==2 ? 1.8f : 2.0f );
349
      }
350

    
351
    return stroke;
352
    }
353

    
354
///////////////////////////////////////////////////////////////////////////////////////////////////
355

    
356
  public float[][] getStickerAngles()
357
    {
358
    return null;
359
    }
360

    
361
///////////////////////////////////////////////////////////////////////////////////////////////////
362
// PUBLIC API
363

    
364
  public Static3D[] getRotationAxis()
365
    {
366
    return ROT_AXIS;
367
    }
368

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

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

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

    
379
  public String getShortName()
380
    {
381
    switch(getNumLayers()[0])
382
      {
383
      case 2: return ObjectType.MIRR_2.name();
384
      case 3: return ObjectType.MIRR_3.name();
385
      case 4: return ObjectType.MIRR_4.name();
386
      }
387

    
388
    return ObjectType.MIRR_2.name();
389
    }
390

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

    
393
  public long getSignature()
394
    {
395
    switch(getNumLayers()[0])
396
      {
397
      case 2: return ObjectType.MIRR_2.ordinal();
398
      case 3: return ObjectType.MIRR_3.ordinal();
399
      case 4: return ObjectType.MIRR_4.ordinal();
400
      }
401

    
402
    return ObjectType.MIRR_2.ordinal();
403
    }
404

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

    
407
  public String getObjectName()
408
    {
409
    switch(getNumLayers()[0])
410
      {
411
      case 2: return "Pocket Mirror";
412
      case 3: return "Mirror Cube";
413
      case 4: return "Master Mirror Blocks";
414
      }
415
    return "Pocket Mirror";
416
    }
417

    
418
///////////////////////////////////////////////////////////////////////////////////////////////////
419

    
420
  public String getInventor()
421
    {
422
    switch(getNumLayers()[0])
423
      {
424
      case 2: return "Thomas de Bruin";
425
      case 3: return "Hidetoshi Takeji";
426
      case 4: return "Traiphum Prungtaengkit";
427
      }
428
    return "Hidetoshi Takeji";
429
    }
430

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

    
433
  public int getYearOfInvention()
434
    {
435
    switch(getNumLayers()[0])
436
      {
437
      case 2: return 2007;
438
      case 3: return 2006;
439
      case 4: return 2014;
440
      }
441
    return 2006;
442
    }
443

    
444
///////////////////////////////////////////////////////////////////////////////////////////////////
445

    
446
  public int getComplexity()
447
    {
448
    switch(getNumLayers()[0])
449
      {
450
      case 2: return 1;
451
      case 3: return 2;
452
      case 4: return 3;
453
      }
454
    return 2;
455
    }
456

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

    
459
  public String[][] getTutorials()
460
    {
461
    int[] numLayers = getNumLayers();
462

    
463
    switch(numLayers[0])
464
      {
465
      case 2: return new String[][] {
466
                          {"gb","rSH-ZEqTmxs","Solve 2x2 Mirror Blocks","King of Cubing"},
467
                          {"es","Ipz-Ajpd4Fg","Como resolver el mirror 2x2","RUBI CUBI"},
468
                          {"ru","rGqZq0bjZlM","Как собрать Зеркальный кубик 2x2","maggam1000"},
469
                          {"de","fFMf1G7MYmA","2x2 Mirror Cube Anfängerlösung","rofrisch"},
470
                          {"pl","C6B_ZT6xilw","Jak ułożyć kostkę mirror 2x2","Lisek Smolisek"},
471
                          {"kr","9S4QTkyNm4Y","2x2 Mirror Cube","큐브놀이터"},
472
                          {"vn","6zENEJlv5gA","Hướng Dẫn Giải Mirror 2x2","Rubik Cube"},
473
                         };
474
      case 3: return new String[][] {
475
                          {"gb","YkzXIWnqbSw","How to Solve the Mirror Cube","Z3"},
476
                          {"es","ZTkunMo51l0","Resolver cubo de Rubik MIRROR","Cuby"},
477
                          {"ru","1QPAD3Q4r78","Как собрать Зеркальный Куб","Алексей Ярыгин"},
478
                          {"fr","tlFLE2UvjFo","Tutoriel: le rubik's cube mirroir","Le Cubiste"},
479
                          {"de","Qf2EadLLiZo","Mirror Cube lösen","Pezcraft"},
480
                          {"pl","r1-MzAL3TxE","Jak ułożyć kostkę mirror","Cube Masters"},
481
                          {"br","HWGGpIKRT_I","Como resolver o Mirror Blocks","Pedro Filho"},
482
                          {"kr","p3OJSbWopqg","미러블럭 해법","듀나메스 큐브 해법연구소"},
483
                          {"vn","F3Gh6JxW1VI","Tutorial N.15 - Mirror Block","Duy Thích Rubik"},
484
                         };
485
      case 4: return new String[][] {
486
                          {"gb","6gyQ5qBK8GU","4x4 Mirror: Introduction","SuperAntoniovivaldi"},
487
                          {"gb","jvKLW7vxKx4","4x4 Mirror: Layer by Layer","SuperAntoniovivaldi"},
488
                          {"gb","efHeHrXFNTQ","4x4 Mirror: Reduction","SuperAntoniovivaldi"},
489
                          {"gb","bKHQn_ARNZ8","4x4 Mirror: Parity Free Solve","SuperAntoniovivaldi"},
490
                          {"gb","Us1Dlr0PyEA","4x4 Mirror: Superparity","SuperAntoniovivaldi"},
491
                          {"es","tN2D3j0o-wk","Como hacer un mirror 4x4x4","JGOM Designer"},
492
                          {"vn","ZGkVOQ3FCOg","Tutorial N.137 - Mirror 4x4x4","Duy Thích Rubik"},
493
                         };
494
      }
495
    return null;
496
    }
497
}
(22-22/34)