11 |
11 |
|
12 |
12 |
import java.util.ArrayList;
|
13 |
13 |
|
|
14 |
import static org.distorted.objectlib.bandaged.BandagedObjectMegaminx.MEGA_D;
|
|
15 |
import static org.distorted.objectlib.bandaged.BandagedObjectMegaminx.SIN18;
|
14 |
16 |
import static org.distorted.objectlib.main.TwistyObject.SQ2;
|
15 |
17 |
import static org.distorted.objectlib.main.TwistyObject.SQ3;
|
16 |
18 |
import static org.distorted.objectlib.main.TwistyObject.SQ6;
|
|
19 |
import static org.distorted.objectlib.objects.TwistyBandagedMegaminx.KILOMINX3;
|
|
20 |
import static org.distorted.objectlib.objects.TwistyBandagedMegaminx.KILOMINX5;
|
|
21 |
import static org.distorted.objectlib.objects.TwistyBandagedMegaminx.MEGAMINX3;
|
|
22 |
import static org.distorted.objectlib.objects.TwistyBandagedMegaminx.MEGAMINX5;
|
17 |
23 |
import static org.distorted.objectlib.scrambling.ScrambleStateLocallyBandaged.MAX_SUPPORTED_SIZE;
|
|
24 |
import static org.distorted.objectlib.touchcontrol.TouchControlDodecahedron.C2;
|
|
25 |
import static org.distorted.objectlib.touchcontrol.TouchControlDodecahedron.COS54;
|
|
26 |
import static org.distorted.objectlib.touchcontrol.TouchControlDodecahedron.LEN;
|
|
27 |
import static org.distorted.objectlib.touchcontrol.TouchControlDodecahedron.SIN54;
|
18 |
28 |
|
19 |
29 |
import org.distorted.library.helpers.QuatHelper;
|
|
30 |
import org.distorted.objectlib.bandaged.BandagedObjectMegaminx;
|
|
31 |
import org.distorted.objectlib.bandaged.FactoryBandagedMegaminx;
|
20 |
32 |
import org.distorted.objectlib.bandaged.FactoryBandagedPyraminx;
|
|
33 |
import org.distorted.objectlib.touchcontrol.TouchControlDodecahedron;
|
21 |
34 |
|
22 |
35 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
23 |
36 |
|
... | ... | |
41 |
54 |
{-SQ2/2, 0.5f, 0, 0.5f },
|
42 |
55 |
};
|
43 |
56 |
|
|
57 |
private static final float[][] mRotAxisMegaminx =
|
|
58 |
{
|
|
59 |
{ C2/LEN, SIN54/LEN, 0 },
|
|
60 |
{ -C2/LEN, SIN54/LEN, 0 },
|
|
61 |
{ 0 , C2/LEN, SIN54/LEN },
|
|
62 |
{ 0 , -C2/LEN, SIN54/LEN },
|
|
63 |
{ SIN54/LEN, 0 , C2/LEN },
|
|
64 |
{ SIN54/LEN, 0 , -C2/LEN }
|
|
65 |
};
|
|
66 |
|
|
67 |
private static final float[][] mQuatsMegaminx =
|
|
68 |
{
|
|
69 |
{ COS54* C2/LEN, COS54*SIN54/LEN, 0 , SIN54 },
|
|
70 |
{ -COS54* C2/LEN, COS54*SIN54/LEN, 0 , SIN54 },
|
|
71 |
{ 0 , COS54* C2/LEN, COS54*SIN54/LEN, SIN54 },
|
|
72 |
{ 0 ,-COS54* C2/LEN, COS54*SIN54/LEN, SIN54 },
|
|
73 |
{ COS54*SIN54/LEN, 0 , COS54* C2/LEN, SIN54 },
|
|
74 |
{ COS54*SIN54/LEN, 0 ,-COS54* C2/LEN, SIN54 }
|
|
75 |
};
|
|
76 |
|
44 |
77 |
private long[] mSignature;
|
45 |
78 |
private int[] mLayer;
|
46 |
79 |
private int[][][][] mCycles;
|
... | ... | |
52 |
85 |
private int[] mNumInneCyclesPerLayer;
|
53 |
86 |
private String mName=null;
|
54 |
87 |
private float[] mTmp;
|
|
88 |
private int mParam;
|
55 |
89 |
|
56 |
90 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
57 |
91 |
// a cube of size N has 12*(N-1)^2 possible places two adjacent cubies can be 'glued'; therefore
|
58 |
92 |
// the signature must contain ceil( 12*(N-1)^2 / 64 ) bytes.
|
59 |
93 |
// a pyraminx of size N has 4 + 6*(N-1)(N-2) places two adjacent cubies can be 'glued' so much less.
|
60 |
94 |
|
|
95 |
// Gigaminx has 480 such places (so more if N<=7)
|
|
96 |
|
61 |
97 |
private static int computeNum()
|
62 |
98 |
{
|
63 |
99 |
int max = MAX_SUPPORTED_SIZE-1;
|
64 |
|
return (int)(0.95f + (3*max*max)/16.0f);
|
|
100 |
int ret = (int)(0.99f + (12*max*max)/64.0f);
|
|
101 |
int giga= (int)(0.99f + ( 480)/64.0f);
|
|
102 |
|
|
103 |
return Math.max(ret,giga);
|
65 |
104 |
}
|
66 |
105 |
|
67 |
106 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
... | ... | |
93 |
132 |
mTouchRows = sig.mTouchRows;
|
94 |
133 |
mName = sig.mName;
|
95 |
134 |
mTmp = sig.mTmp;
|
|
135 |
mParam = sig.mParam;
|
96 |
136 |
|
97 |
137 |
mNumCubitTouches = sig.mNumCubitTouches;
|
98 |
138 |
mNumCentCyclesPerLayer = sig.mNumCentCyclesPerLayer;
|
... | ... | |
111 |
151 |
|
112 |
152 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
113 |
153 |
// locally created bandaged cuboids created from JSON (version2)
|
114 |
|
// or locally created bandaged pyraminxes.
|
115 |
|
// How to tell apart: pyraminx's shortName starts with a 'P'.
|
|
154 |
// or locally created bandaged pyraminxes, or locally bandaged megaminxes.
|
|
155 |
// How to tell apart: pyraminx's shortName starts with a 'P'; megaminx's shortName starts with a 'M'.
|
116 |
156 |
|
117 |
157 |
public ObjectSignature(String shortName, long[] signature)
|
118 |
158 |
{
|
119 |
159 |
setUpSignature(signature);
|
120 |
160 |
|
121 |
|
if( shortName.charAt(0) != 'P' )
|
122 |
|
{
|
123 |
|
int x=shortName.charAt(0)-'0';
|
124 |
|
int y=shortName.charAt(1)-'0';
|
125 |
|
int z=shortName.charAt(2)-'0';
|
126 |
|
mLayer=new int[]{x, y, z};
|
127 |
|
prepareCubitTouch();
|
128 |
|
prepareTouchRows();
|
129 |
|
prepareAllCycles();
|
130 |
|
}
|
131 |
|
else
|
|
161 |
char name = shortName.charAt(0);
|
|
162 |
|
|
163 |
if( name == 'P' )
|
132 |
164 |
{
|
133 |
165 |
mTmp = new float[4];
|
134 |
166 |
int x=shortName.charAt(1)-'0';
|
135 |
|
mLayer=new int[]{x, x, x, x};
|
|
167 |
mLayer=new int[] {x,x,x,x};
|
136 |
168 |
prepareCubitTouchPyraminx();
|
137 |
169 |
prepareTouchRowsPyraminx();
|
138 |
170 |
prepareAllCyclesPyraminx();
|
139 |
171 |
}
|
|
172 |
else if( name == 'M' )
|
|
173 |
{
|
|
174 |
mTmp = new float[4];
|
|
175 |
mParam=shortName.charAt(1)-'0';
|
|
176 |
int x=-1;
|
|
177 |
|
|
178 |
switch(mParam)
|
|
179 |
{
|
|
180 |
case 2:
|
|
181 |
case 3: x = 3; break;
|
|
182 |
case 4:
|
|
183 |
case 5: x = 5; break;
|
|
184 |
}
|
|
185 |
|
|
186 |
mLayer=new int[] {x,x,x,x,x,x};
|
|
187 |
prepareCubitTouchMegaminx();
|
|
188 |
prepareTouchRowsMegaminx();
|
|
189 |
prepareAllCyclesMegaminx();
|
|
190 |
}
|
|
191 |
else
|
|
192 |
{
|
|
193 |
int x=shortName.charAt(0)-'0';
|
|
194 |
int y=shortName.charAt(1)-'0';
|
|
195 |
int z=shortName.charAt(2)-'0';
|
|
196 |
mLayer=new int[] {x,y,z};
|
|
197 |
prepareCubitTouchCuboid();
|
|
198 |
prepareTouchRowsCuboid();
|
|
199 |
prepareAllCyclesCuboid();
|
|
200 |
}
|
140 |
201 |
}
|
141 |
202 |
|
142 |
203 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
... | ... | |
148 |
209 |
|
149 |
210 |
mLayer = new int[] {size,size,size};
|
150 |
211 |
|
151 |
|
prepareCubitTouch();
|
152 |
|
prepareTouchRows();
|
153 |
|
prepareAllCycles();
|
|
212 |
prepareCubitTouchCuboid();
|
|
213 |
prepareTouchRowsCuboid();
|
|
214 |
prepareAllCyclesCuboid();
|
154 |
215 |
}
|
155 |
216 |
|
156 |
217 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
... | ... | |
171 |
232 |
mLayer = new int[] {lenx,leny,lenz};
|
172 |
233 |
mSignature = new long[SIZE];
|
173 |
234 |
|
174 |
|
prepareCubitTouch();
|
175 |
|
prepareTouchRows();
|
176 |
|
prepareAllCycles();
|
|
235 |
prepareCubitTouchCuboid();
|
|
236 |
prepareTouchRowsCuboid();
|
|
237 |
prepareAllCyclesCuboid();
|
177 |
238 |
|
178 |
239 |
for(float[] pos : position)
|
179 |
240 |
{
|
... | ... | |
191 |
252 |
float yj = pos[3*j+1];
|
192 |
253 |
float zj = pos[3*j+2];
|
193 |
254 |
|
194 |
|
if(areNeighbours(xi-xj,yi-yj,zi-zj))
|
|
255 |
if(areNeighboursCuboid(xi-xj,yi-yj,zi-zj))
|
195 |
256 |
{
|
196 |
257 |
float xc = (xi+xj)/2;
|
197 |
258 |
float yc = (yi+yj)/2;
|
... | ... | |
260 |
321 |
}
|
261 |
322 |
}
|
262 |
323 |
|
|
324 |
|
|
325 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
326 |
// Locally created bandaged megaminxes size 2<=N<=5
|
|
327 |
|
|
328 |
public ObjectSignature(float[][] position, int param)
|
|
329 |
{
|
|
330 |
int size = -1;
|
|
331 |
|
|
332 |
switch(param)
|
|
333 |
{
|
|
334 |
case KILOMINX3: size = 2; break;
|
|
335 |
case MEGAMINX3: size = 3; break;
|
|
336 |
case KILOMINX5: size = 4; break;
|
|
337 |
case MEGAMINX5: size = 5; break;
|
|
338 |
}
|
|
339 |
|
|
340 |
mLayer = new int[] {size,size,size,size,size,size};
|
|
341 |
mSignature = new long[SIZE];
|
|
342 |
mTmp = new float[4];
|
|
343 |
|
|
344 |
prepareCubitTouchMegaminx();
|
|
345 |
prepareTouchRowsMegaminx();
|
|
346 |
prepareAllCyclesMegaminx();
|
|
347 |
|
|
348 |
for(float[] pos : position)
|
|
349 |
{
|
|
350 |
int numCenters = pos.length/3;
|
|
351 |
|
|
352 |
for(int i=0; i<numCenters; i++)
|
|
353 |
{
|
|
354 |
float xi = pos[3*i ];
|
|
355 |
float yi = pos[3*i+1];
|
|
356 |
float zi = pos[3*i+2];
|
|
357 |
|
|
358 |
for(int j=i+1; j<numCenters; j++)
|
|
359 |
{
|
|
360 |
float xj = pos[3*j ];
|
|
361 |
float yj = pos[3*j+1];
|
|
362 |
float zj = pos[3*j+2];
|
|
363 |
|
|
364 |
if( areNeighboursMegaminx(param,xi-xj,yi-yj,zi-zj) )
|
|
365 |
{
|
|
366 |
float xc = (xi+xj)/2; // TODO
|
|
367 |
float yc = (yi+yj)/2;
|
|
368 |
float zc = (zi+zj)/2;
|
|
369 |
|
|
370 |
int bitIndex = getIndexOfCubitTouch(xc,yc,zc);
|
|
371 |
setBit(bitIndex,1);
|
|
372 |
}
|
|
373 |
}
|
|
374 |
}
|
|
375 |
}
|
|
376 |
}
|
|
377 |
|
263 |
378 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
264 |
379 |
|
265 |
380 |
public void setSignature(int signature)
|
... | ... | |
328 |
443 |
public boolean isUnblockedFromLeft(int axis, int layer)
|
329 |
444 |
{
|
330 |
445 |
if(layer>0)
|
331 |
|
for(int index=0; index<mNumCubitTouches; index++)
|
332 |
|
if( getBit(index)!=0 && mTouchRows[index][axis]==layer ) return false;
|
|
446 |
{
|
|
447 |
int[] touch = mTouchRows[axis];
|
|
448 |
|
|
449 |
for( int index=0; index<mNumCubitTouches; index++)
|
|
450 |
if( touch[index]==layer && getBit(index)!=0 )
|
|
451 |
{
|
|
452 |
android.util.Log.e("D", "axis "+axis+" layer "+layer+" is blocked from Left");
|
|
453 |
return false;
|
|
454 |
}
|
|
455 |
}
|
333 |
456 |
|
334 |
457 |
return true;
|
335 |
458 |
}
|
... | ... | |
348 |
471 |
// it can happen that there are no cycles in this layer: 2x1x2 axis 0 layer 0.
|
349 |
472 |
if( cycles!=null && cycles.length>0 && cycles[0]!=null )
|
350 |
473 |
{
|
351 |
|
if( cycles[0].length==4 ) for(int[] cyc : cycles) ret.cycle4(turn,cyc);
|
|
474 |
if( cycles[0].length==5 ) for(int[] cyc : cycles) ret.cycle5(turn,cyc);
|
|
475 |
else if( cycles[0].length==4 ) for(int[] cyc : cycles) ret.cycle4(turn,cyc);
|
352 |
476 |
else if( cycles[0].length==3 ) for(int[] cyc : cycles) ret.cycle3(turn,cyc);
|
353 |
|
else for(int[] cyc : cycles) ret.cycle2(cyc);
|
|
477 |
else if( cycles[0].length==2 ) for(int[] cyc : cycles) ret.cycle2(cyc);
|
354 |
478 |
}
|
355 |
479 |
}
|
356 |
480 |
|
... | ... | |
432 |
556 |
|
433 |
557 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
434 |
558 |
|
435 |
|
private void prepareCubitTouch()
|
|
559 |
private void cycle5(int turn, int[] cyc)
|
|
560 |
{
|
|
561 |
int index0 = cyc[0];
|
|
562 |
int index1 = cyc[1];
|
|
563 |
int index2 = cyc[2];
|
|
564 |
int index3 = cyc[3];
|
|
565 |
int index4 = cyc[4];
|
|
566 |
|
|
567 |
long b0 = getBit(index0);
|
|
568 |
long b1 = getBit(index1);
|
|
569 |
long b2 = getBit(index2);
|
|
570 |
long b3 = getBit(index3);
|
|
571 |
long b4 = getBit(index4);
|
|
572 |
|
|
573 |
switch(turn)
|
|
574 |
{
|
|
575 |
case 1: setBit(index0,b4);
|
|
576 |
setBit(index1,b0);
|
|
577 |
setBit(index2,b1);
|
|
578 |
setBit(index3,b2);
|
|
579 |
setBit(index4,b3);
|
|
580 |
break;
|
|
581 |
case 2: setBit(index0,b3);
|
|
582 |
setBit(index1,b4);
|
|
583 |
setBit(index2,b0);
|
|
584 |
setBit(index3,b1);
|
|
585 |
setBit(index4,b2);
|
|
586 |
break;
|
|
587 |
case 3: setBit(index0,b2);
|
|
588 |
setBit(index1,b3);
|
|
589 |
setBit(index2,b4);
|
|
590 |
setBit(index3,b0);
|
|
591 |
setBit(index4,b1);
|
|
592 |
break;
|
|
593 |
case 4: setBit(index0,b1);
|
|
594 |
setBit(index1,b2);
|
|
595 |
setBit(index2,b3);
|
|
596 |
setBit(index3,b4);
|
|
597 |
setBit(index4,b0);
|
|
598 |
break;
|
|
599 |
}
|
|
600 |
}
|
|
601 |
|
|
602 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
603 |
|
|
604 |
private void prepareCubitTouchCuboid()
|
436 |
605 |
{
|
437 |
606 |
int numCenters = mLayer[0]*mLayer[1]*mLayer[2];
|
438 |
607 |
if( mLayer[0]>1 && mLayer[1]>1 && mLayer[2]>1 ) numCenters -= (mLayer[0]-2)*(mLayer[1]-2)*(mLayer[2]-2);
|
... | ... | |
463 |
632 |
float y2 = c1[1];
|
464 |
633 |
float z2 = c1[2];
|
465 |
634 |
|
466 |
|
if( areNeighbours(x1-x2,y1-y2,z1-z2) )
|
|
635 |
if( areNeighboursCuboid(x1-x2,y1-y2,z1-z2) )
|
467 |
636 |
{
|
468 |
637 |
float xc = (x1+x2)/2;
|
469 |
638 |
float yc = (y1+y2)/2;
|
... | ... | |
506 |
675 |
|
507 |
676 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
508 |
677 |
|
509 |
|
private void prepareTouchRows()
|
|
678 |
private void prepareTouchRowsCuboid()
|
510 |
679 |
{
|
511 |
|
mTouchRows = new int[mNumCubitTouches][3];
|
|
680 |
mTouchRows = new int[3][mNumCubitTouches];
|
512 |
681 |
|
513 |
682 |
for(int i=0; i<mNumCubitTouches; i++)
|
514 |
683 |
{
|
... | ... | |
517 |
686 |
for(int a=0; a<3; a++)
|
518 |
687 |
{
|
519 |
688 |
int l = (int)(2*touch[a] + mLayer[a] + 0.01f);
|
520 |
|
mTouchRows[i][a] = ( (l%2)==0 ) ? l/2 : -1;
|
|
689 |
mTouchRows[a][i] = ( (l%2)==0 ) ? l/2 : -1;
|
521 |
690 |
}
|
522 |
691 |
}
|
523 |
692 |
}
|
524 |
693 |
|
525 |
694 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
526 |
695 |
|
527 |
|
private void prepareAllCycles()
|
|
696 |
private void prepareAllCyclesCuboid()
|
528 |
697 |
{
|
529 |
698 |
ArrayList<float[][]> cycles0 = new ArrayList<>();
|
530 |
699 |
ArrayList<float[][]> cycles1 = new ArrayList<>();
|
... | ... | |
698 |
867 |
float yc=(2*ty+oy)/3;
|
699 |
868 |
float zc=(2*tz+oz)/3;
|
700 |
869 |
|
701 |
|
float[] touch=new float[]{xc, yc, zc};
|
|
870 |
float[] touch = new float[] {xc, yc, zc};
|
702 |
871 |
mTouch.add(touch);
|
703 |
872 |
}
|
704 |
873 |
}
|
... | ... | |
712 |
881 |
|
713 |
882 |
private void prepareTouchRowsPyraminx()
|
714 |
883 |
{
|
715 |
|
mTouchRows = new int[mNumCubitTouches][4];
|
|
884 |
mTouchRows = new int[4][mNumCubitTouches];
|
716 |
885 |
int num = mLayer[0];
|
717 |
886 |
final int N = 10;
|
718 |
887 |
|
... | ... | |
725 |
894 |
float[] ax = mRotAxisPyraminx[a];
|
726 |
895 |
float l = whichLayerPyraminx(touch,ax,num);
|
727 |
896 |
int ll = (int)(N*l);
|
728 |
|
mTouchRows[i][a] = ( (ll%N)==0 ) ? ll/N : -1;
|
|
897 |
mTouchRows[a][i] = ( (ll%N)==0 ) ? ll/N : -1;
|
729 |
898 |
}
|
730 |
899 |
}
|
731 |
900 |
}
|
... | ... | |
826 |
995 |
return getIndexOfCubitTouch(mTmp[0],mTmp[1],mTmp[2]);
|
827 |
996 |
}
|
828 |
997 |
|
|
998 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
999 |
|
|
1000 |
private float[] getPosition(int index, float[][][] centers, int len)
|
|
1001 |
{
|
|
1002 |
int num = 0, i1=0, i2=0;
|
|
1003 |
|
|
1004 |
for(int i=0; i<len; i++)
|
|
1005 |
{
|
|
1006 |
int t = centers[i].length;
|
|
1007 |
|
|
1008 |
if( t > index-num )
|
|
1009 |
{
|
|
1010 |
i1 = i;
|
|
1011 |
i2 = index-num;
|
|
1012 |
break;
|
|
1013 |
}
|
|
1014 |
else
|
|
1015 |
{
|
|
1016 |
num += t;
|
|
1017 |
}
|
|
1018 |
}
|
|
1019 |
|
|
1020 |
return centers[i1][i2];
|
|
1021 |
}
|
|
1022 |
|
|
1023 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1024 |
|
|
1025 |
private void prepareCubitTouchMegaminx()
|
|
1026 |
{
|
|
1027 |
FactoryBandagedMegaminx factory = FactoryBandagedMegaminx.getInstance();
|
|
1028 |
float[][][] centers = factory.getPositions(mLayer);
|
|
1029 |
int size = mLayer[0];
|
|
1030 |
|
|
1031 |
int numCubits=0;
|
|
1032 |
int numVariants = centers.length;
|
|
1033 |
for(float[][] center : centers) numCubits += center.length;
|
|
1034 |
|
|
1035 |
ArrayList<float[]> mTouch = new ArrayList<>();
|
|
1036 |
|
|
1037 |
for(int i=0; i<numCubits; i++)
|
|
1038 |
{
|
|
1039 |
float[] first = getPosition(i,centers,numVariants);
|
|
1040 |
|
|
1041 |
for(int j = i+1; j<numCubits; j++)
|
|
1042 |
{
|
|
1043 |
float[] second = getPosition(j,centers,numVariants);
|
|
1044 |
|
|
1045 |
float ox = first[0];
|
|
1046 |
float oy = first[1];
|
|
1047 |
float oz = first[2];
|
|
1048 |
float tx = second[0];
|
|
1049 |
float ty = second[1];
|
|
1050 |
float tz = second[2];
|
|
1051 |
|
|
1052 |
if( areNeighboursMegaminx(size, ox-tx, oy-ty, oz-tz) )
|
|
1053 |
{
|
|
1054 |
float xc = (tx+ox)/2; // TODO; wrong
|
|
1055 |
float yc = (ty+oy)/2;
|
|
1056 |
float zc = (tz+oz)/2;
|
|
1057 |
|
|
1058 |
float[] touch = new float[] {xc, yc, zc};
|
|
1059 |
mTouch.add(touch);
|
|
1060 |
}
|
|
1061 |
}
|
|
1062 |
}
|
|
1063 |
|
|
1064 |
mNumCubitTouches = mTouch.size();
|
|
1065 |
mCubitTouch = new float[mNumCubitTouches][];
|
|
1066 |
for(int i=0; i<mNumCubitTouches; i++) mCubitTouch[i] = mTouch.remove(0);
|
|
1067 |
}
|
|
1068 |
|
|
1069 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1070 |
|
|
1071 |
private void prepareTouchRowsMegaminx()
|
|
1072 |
{
|
|
1073 |
mTouchRows = new int[6][mNumCubitTouches];
|
|
1074 |
int num = mLayer[0];
|
|
1075 |
final int N = 10;
|
|
1076 |
|
|
1077 |
for(int i=0; i<mNumCubitTouches; i++)
|
|
1078 |
{
|
|
1079 |
float[] touch = mCubitTouch[i];
|
|
1080 |
|
|
1081 |
for(int a=0; a<6; a++)
|
|
1082 |
{
|
|
1083 |
float[] ax = mRotAxisMegaminx[a];
|
|
1084 |
float l = whichLayerMegaminx(touch,ax,num);
|
|
1085 |
int ll = (int)(N*l);
|
|
1086 |
mTouchRows[a][i] = ( (ll%N)==0 ) ? ll/N : -1;
|
|
1087 |
}
|
|
1088 |
}
|
|
1089 |
}
|
|
1090 |
|
|
1091 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1092 |
|
|
1093 |
private void prepareAllCyclesMegaminx()
|
|
1094 |
{
|
|
1095 |
ArrayList<float[][]> cycles0 = new ArrayList<>();
|
|
1096 |
ArrayList<float[][]> cycles1 = new ArrayList<>();
|
|
1097 |
ArrayList<float[][]> cycles2 = new ArrayList<>();
|
|
1098 |
ArrayList<float[][]> cycles3 = new ArrayList<>();
|
|
1099 |
ArrayList<float[][]> cycles4 = new ArrayList<>();
|
|
1100 |
ArrayList<float[][]> cycles5 = new ArrayList<>();
|
|
1101 |
|
|
1102 |
generate5CyclesMegaminx(cycles0,0);
|
|
1103 |
generate5CyclesMegaminx(cycles1,1);
|
|
1104 |
generate5CyclesMegaminx(cycles2,2);
|
|
1105 |
generate5CyclesMegaminx(cycles3,3);
|
|
1106 |
generate5CyclesMegaminx(cycles4,4);
|
|
1107 |
generate5CyclesMegaminx(cycles5,5);
|
|
1108 |
|
|
1109 |
mCycles = new int[6][][][];
|
|
1110 |
|
|
1111 |
int numLayers = mLayer[0];
|
|
1112 |
mCycles[0] = fillUpCyclesMegaminx(cycles0,0,numLayers);
|
|
1113 |
mCycles[1] = fillUpCyclesMegaminx(cycles1,1,numLayers);
|
|
1114 |
mCycles[2] = fillUpCyclesMegaminx(cycles2,2,numLayers);
|
|
1115 |
mCycles[3] = fillUpCyclesMegaminx(cycles3,3,numLayers);
|
|
1116 |
mCycles[4] = fillUpCyclesMegaminx(cycles4,4,numLayers);
|
|
1117 |
mCycles[5] = fillUpCyclesMegaminx(cycles5,5,numLayers);
|
|
1118 |
}
|
|
1119 |
|
|
1120 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1121 |
|
|
1122 |
private void generate5CyclesMegaminx(ArrayList<float[][]> cycles, int ax)
|
|
1123 |
{
|
|
1124 |
for(int i=0; i<mNumCubitTouches; i++)
|
|
1125 |
{
|
|
1126 |
int i0 = rotateIndex5(ax,i);
|
|
1127 |
if( i0<=i ) continue;
|
|
1128 |
int i1 = rotateIndex5(ax,i0);
|
|
1129 |
if( i1<=i ) continue;
|
|
1130 |
int i2 = rotateIndex5(ax,i1);
|
|
1131 |
if( i2<=i ) continue;
|
|
1132 |
int i3 = rotateIndex5(ax,i2);
|
|
1133 |
if( i3<=i ) continue;
|
|
1134 |
|
|
1135 |
float[] f0 = getCubitTouchOfIndex(i);
|
|
1136 |
float[] f1 = getCubitTouchOfIndex(i0);
|
|
1137 |
float[] f2 = getCubitTouchOfIndex(i1);
|
|
1138 |
float[] f3 = getCubitTouchOfIndex(i2);
|
|
1139 |
float[] f4 = getCubitTouchOfIndex(i3);
|
|
1140 |
|
|
1141 |
float[][] cycle = new float[][] { f0,f1,f2,f3,f4 };
|
|
1142 |
cycles.add(cycle);
|
|
1143 |
}
|
|
1144 |
}
|
|
1145 |
|
|
1146 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1147 |
|
|
1148 |
private int[][][] fillUpCyclesMegaminx(ArrayList<float[][]> cyc, int axis, int numLayers)
|
|
1149 |
{
|
|
1150 |
int numCycles = cyc.size();
|
|
1151 |
int[] index = new int[numLayers];
|
|
1152 |
int[] numC = new int[numLayers];
|
|
1153 |
float[] ax = mRotAxisMegaminx[axis];
|
|
1154 |
|
|
1155 |
for(int i=0; i<numCycles; i++)
|
|
1156 |
{
|
|
1157 |
float[][] cycle = cyc.get(i);
|
|
1158 |
int layer = (int)whichLayerMegaminx(cycle[0],ax,numLayers);
|
|
1159 |
numC[layer]++;
|
|
1160 |
}
|
|
1161 |
|
|
1162 |
int[][][] ret = new int[numLayers][][];
|
|
1163 |
for(int i=0; i<numLayers; i++) ret[i] = new int[numC[i]][];
|
|
1164 |
|
|
1165 |
for(int i=0; i<numCycles; i++)
|
|
1166 |
{
|
|
1167 |
float[][] cycle = cyc.remove(0);
|
|
1168 |
int layer = (int)whichLayerMegaminx(cycle[0],ax,numLayers);
|
|
1169 |
|
|
1170 |
int i0 = getIndexOfCubitTouch(cycle[0][0],cycle[0][1],cycle[0][2]);
|
|
1171 |
int i1 = getIndexOfCubitTouch(cycle[1][0],cycle[1][1],cycle[1][2]);
|
|
1172 |
int i2 = getIndexOfCubitTouch(cycle[2][0],cycle[2][1],cycle[2][2]);
|
|
1173 |
int i3 = getIndexOfCubitTouch(cycle[3][0],cycle[3][1],cycle[3][2]);
|
|
1174 |
int i4 = getIndexOfCubitTouch(cycle[4][0],cycle[4][1],cycle[4][2]);
|
|
1175 |
|
|
1176 |
ret[layer][index[layer]] = new int[] {i0,i1,i2,i3,i4};
|
|
1177 |
index[layer]++;
|
|
1178 |
}
|
|
1179 |
|
|
1180 |
return ret;
|
|
1181 |
}
|
|
1182 |
|
|
1183 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1184 |
|
|
1185 |
private float whichLayerMegaminx(float[] point, float[] ax, int numLayers)
|
|
1186 |
{
|
|
1187 |
float d = point[0]*ax[0] + point[1]*ax[1] + point[2]*ax[2];
|
|
1188 |
float C = 0.85f;
|
|
1189 |
|
|
1190 |
switch(numLayers)
|
|
1191 |
{
|
|
1192 |
case 2: return d<0 ? 0:1;
|
|
1193 |
case 3: float D3 = 3*TouchControlDodecahedron.DIST3D;
|
|
1194 |
float X3 = 2*D3/(2+SIN18);
|
|
1195 |
float G3 = X3*(0.5f-MEGA_D);
|
|
1196 |
float cut3 = -D3 + C*G3;
|
|
1197 |
return d<-cut3 ? 0 : d<cut3 ? 1:2;
|
|
1198 |
case 4: float D4 = 5*TouchControlDodecahedron.DIST3D;
|
|
1199 |
float X4 = 2*D4/(2+SIN18);
|
|
1200 |
float G4 = X4*0.25f;
|
|
1201 |
float cut41 = -D4 + C*G4;
|
|
1202 |
float cut42 = -D4 + (1+C)*G4;
|
|
1203 |
return d<-cut41 ? 0 : d<-cut42 ? 1: d<cut42 ? 2: d<cut41 ? 3:4;
|
|
1204 |
case 5: float D5 = 5*TouchControlDodecahedron.DIST3D;
|
|
1205 |
float X5 = 2*D5/(2+SIN18);
|
|
1206 |
float G5 = X5*(0.5f-MEGA_D)/2;
|
|
1207 |
float cut51 = -D5 + C*G5;
|
|
1208 |
float cut52 = -D5 + (1+C)*G5;
|
|
1209 |
return d<-cut51 ? 0 : d<-cut52 ? 1: d<cut52 ? 2: d<cut51 ? 3:4;
|
|
1210 |
}
|
|
1211 |
|
|
1212 |
return 0;
|
|
1213 |
}
|
|
1214 |
|
|
1215 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1216 |
|
|
1217 |
private int rotateIndex5(int ax, int index)
|
|
1218 |
{
|
|
1219 |
float[] touch = getCubitTouchOfIndex(index);
|
|
1220 |
QuatHelper.rotateVectorByQuat(mTmp, touch[0], touch[1], touch[2], 1.0f, mQuatsMegaminx[ax]);
|
|
1221 |
return getIndexOfCubitTouch(mTmp[0],mTmp[1],mTmp[2]);
|
|
1222 |
}
|
|
1223 |
|
829 |
1224 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
830 |
1225 |
|
831 |
1226 |
private int getIndexOfCubitTouch(float x, float y, float z)
|
... | ... | |
853 |
1248 |
|
854 |
1249 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
855 |
1250 |
|
856 |
|
private boolean areNeighbours(float dx, float dy, float dz)
|
|
1251 |
private boolean areNeighboursCuboid(float dx, float dy, float dz)
|
857 |
1252 |
{
|
858 |
1253 |
return dx*dx+dy*dy+dz*dz < 1.01f;
|
859 |
1254 |
}
|
... | ... | |
865 |
1260 |
return dx*dx+dy*dy+dz*dz < SQ6/4 + 0.01f;
|
866 |
1261 |
}
|
867 |
1262 |
|
|
1263 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
|
1264 |
|
|
1265 |
private boolean areNeighboursMegaminx(int size, float dx, float dy, float dz)
|
|
1266 |
{
|
|
1267 |
float fact = size==2 ? 1.5f : (size==4 ? 1.25f : 1.0f);
|
|
1268 |
|
|
1269 |
dx /= fact;
|
|
1270 |
dy /= fact;
|
|
1271 |
dz /= fact;
|
|
1272 |
|
|
1273 |
return BandagedObjectMegaminx.isAdjacent(size,dx,dy,dz);
|
|
1274 |
}
|
|
1275 |
|
868 |
1276 |
///////////////////////////////////////////////////////////////////////////////////////////////////
|
869 |
1277 |
|
870 |
1278 |
private long getBit(int index)
|
progress with TwistyBandagedMegaminx.