Project

General

Profile

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

magiccube / src / main / java / org / distorted / solvers / SolverIvyCube.java @ 742401b4

1
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2023 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.solvers;
11

    
12
import android.content.res.Resources;
13

    
14
import org.distorted.main.R;
15
import org.distorted.objectlib.main.ObjectSignatures;
16
import org.distorted.objectlib.main.TwistyObject;
17
import org.distorted.objectlib.tablebases.ImplementedTablebasesList;
18
import org.distorted.objectlib.tablebases.TablebaseHelpers;
19
import org.distorted.objectlib.tablebases.TablebasesAbstract;
20

    
21
///////////////////////////////////////////////////////////////////////////////////////////////////
22

    
23
public class SolverIvyCube extends SolverTablebase
24
{
25
  private static final int ERROR_CENTER_O_MISSING = -1;
26
  private static final int ERROR_CENTER_W_MISSING = -2;
27
  private static final int ERROR_CENTER_G_MISSING = -3;
28
  private static final int ERROR_CENTER_Y_MISSING = -4;
29
  private static final int ERROR_CENTER_B_MISSING = -5;
30
  private static final int ERROR_CENTER_R_MISSING = -6;
31
  private static final int ERROR_TWO_CENTERS_SWAP = -7;
32
  private static final int ERROR_CORNERS_CANNOT   = -8;
33

    
34
  TablebasesAbstract mSolver;
35

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

    
38
  private int checkAllCentersPresent(int[] centers)
39
    {
40
    int numCenters = centers.length;
41

    
42
    for(int color=0; color<numCenters; color++)
43
      {
44
      boolean error = true;
45
      int center;
46

    
47
      for(center=0; center<numCenters; center++)
48
        if( centers[center]==color )
49
          {
50
          error = false;
51
          break;
52
          }
53

    
54
      if( error )
55
        {
56
        switch(color)
57
          {
58
          case 0: return ERROR_CENTER_Y_MISSING;
59
          case 1: return ERROR_CENTER_W_MISSING;
60
          case 2: return ERROR_CENTER_B_MISSING;
61
          case 3: return ERROR_CENTER_G_MISSING;
62
          case 4: return ERROR_CENTER_R_MISSING;
63
          case 5: return ERROR_CENTER_O_MISSING;
64
          }
65
        }
66
      }
67

    
68
    return 0;
69
    }
70

    
71
///////////////////////////////////////////////////////////////////////////////////////////////////
72

    
73
  private boolean checkCommonColor(int[] buffer, int index, int[] c1, int[] c2)
74
    {
75
    if( c1[0]==c1[1] || c1[0]==c1[2] || c1[1]==c1[2] ) return false;
76
    if( c2[0]==c2[1] || c2[0]==c2[2] || c2[1]==c2[2] ) return false;
77

    
78
    if( c1[0]==c2[0] && c1[1]!=c2[1] && c1[1]!=c2[2] && c1[2]!=c2[1] && c1[2]!=c2[2] )
79
      {
80
      buffer[index] = c1[0];
81
      return true;
82
      }
83
    if( c1[0]==c2[1] && c1[1]!=c2[0] && c1[1]!=c2[2] && c1[2]!=c2[0] && c1[2]!=c2[2] )
84
      {
85
      buffer[index] = c1[0];
86
      return true;
87
      }
88
    if( c1[0]==c2[2] && c1[1]!=c2[0] && c1[1]!=c2[1] && c1[2]!=c2[0] && c1[2]!=c2[1] )
89
      {
90
      buffer[index] = c1[0];
91
      return true;
92
      }
93

    
94
    if( c1[1]==c2[0] && c1[0]!=c2[1] && c1[0]!=c2[2] && c1[2]!=c2[1] && c1[2]!=c2[2] )
95
      {
96
      buffer[index] = c1[1];
97
      return true;
98
      }
99
    if( c1[1]==c2[1] && c1[0]!=c2[0] && c1[0]!=c2[2] && c1[2]!=c2[0] && c1[2]!=c2[2] )
100
      {
101
      buffer[index] = c1[1];
102
      return true;
103
      }
104
    if( c1[1]==c2[2] && c1[0]!=c2[0] && c1[0]!=c2[1] && c1[2]!=c2[0] && c1[2]!=c2[1] )
105
      {
106
      buffer[index] = c1[1];
107
      return true;
108
      }
109

    
110
    if( c1[2]==c2[0] && c1[1]!=c2[1] && c1[1]!=c2[2] && c1[0]!=c2[1] && c1[0]!=c2[2] )
111
      {
112
      buffer[index] = c1[2];
113
      return true;
114
      }
115
    if( c1[2]==c2[1] && c1[1]!=c2[0] && c1[1]!=c2[2] && c1[0]!=c2[0] && c1[0]!=c2[2] )
116
      {
117
      buffer[index] = c1[2];
118
      return true;
119
      }
120
    if( c1[2]==c2[2] && c1[1]!=c2[0] && c1[1]!=c2[1] && c1[0]!=c2[0] && c1[0]!=c2[1] )
121
      {
122
      buffer[index] = c1[2];
123
      return true;
124
      }
125

    
126
    return false;
127
    }
128

    
129
///////////////////////////////////////////////////////////////////////////////////////////////////
130

    
131
  private int computeFaceColor(int[] buffer, int[][] corners)
132
    {
133
    boolean success0 = checkCommonColor(buffer,0,corners[0],corners[3]);
134
    if( !success0 ) return ERROR_CORNERS_CANNOT;
135
    boolean success1 = checkCommonColor(buffer,1,corners[1],corners[2]);
136
    if( !success1 ) return ERROR_CORNERS_CANNOT;
137
    boolean success2 = checkCommonColor(buffer,2,corners[0],corners[1]);
138
    if( !success2 ) return ERROR_CORNERS_CANNOT;
139
    boolean success3 = checkCommonColor(buffer,3,corners[2],corners[3]);
140
    if( !success3 ) return ERROR_CORNERS_CANNOT;
141
    boolean success4 = checkCommonColor(buffer,4,corners[0],corners[2]);
142
    if( !success4 ) return ERROR_CORNERS_CANNOT;
143
    boolean success5 = checkCommonColor(buffer,5,corners[1],corners[3]);
144
    if( !success5 ) return ERROR_CORNERS_CANNOT;
145

    
146
    return 0;
147
    }
148

    
149
///////////////////////////////////////////////////////////////////////////////////////////////////
150

    
151
  private int computeCenterColors(int[] buffer, int[] faceColors, int[] centers)
152
    {
153
    int numCenters = faceColors.length;
154

    
155
    for(int color=0; color<numCenters; color++)
156
      for(int center=0; center<numCenters; center++)
157
        if( centers[center]==faceColors[color] )
158
          {
159
          buffer[center]=color;
160
          }
161

    
162
    return TablebaseHelpers.permutationIsEven(buffer) ? 0 : ERROR_TWO_CENTERS_SWAP;
163
    }
164
////////////////////////////////////////////////////////////////////////////////////////
165

    
166
  private int computeCornerTwist(int[] corner, int color)
167
    {
168
    if( corner[0]==color ) return 0;
169
    if( corner[1]==color ) return 1;
170
    return 2;
171
    }
172

    
173
///////////////////////////////////////////////////////////////////////////////////////////////////
174

    
175
  public SolverIvyCube(Resources res, TwistyObject object)
176
    {
177
    super(res,object);
178
    }
179

    
180
///////////////////////////////////////////////////////////////////////////////////////////////////
181

    
182
  public int tablebaseIndex(TwistyObject object)
183
    {
184
    int[][] corners     = new int[4][3];
185
    int[] centers       = new int[6];
186
    int[] twist         = new int[4];
187
    int[] face_colors   = new int[6];
188
    int[] center_colors = new int[6];
189

    
190
    for(int i=0; i<4; i++)
191
      for(int j=0; j<3; j++)
192
        corners[i][j] = object.getCubitFaceStickerIndex(i,j);
193

    
194
    for(int i=0; i<6; i++)
195
      centers[i] = object.getCubitFaceStickerIndex(i+4,0) - 6;
196

    
197
    int result1 = checkAllCentersPresent(centers);
198
    if( result1<0 ) return result1;
199

    
200
    int result2 = computeFaceColor(face_colors,corners);
201
    if( result2<0 ) return result2;
202

    
203
    int result3 = computeCenterColors(center_colors, face_colors, centers);
204
    if( result3<0 ) return result3;
205

    
206
    twist[0] = computeCornerTwist(corners[0],face_colors[4]);
207
    twist[1] = computeCornerTwist(corners[1],face_colors[5]);
208
    twist[2] = computeCornerTwist(corners[2],face_colors[4]);
209
    twist[3] = computeCornerTwist(corners[3],face_colors[5]);
210

    
211
    int perm_num = TablebaseHelpers.computeEvenPermutationNum(center_colors);
212

    
213
    return perm_num + 360*(twist[0]+ 3*(twist[1]+ 3*(twist[2]+ 3*twist[3])));
214
    }
215

    
216
///////////////////////////////////////////////////////////////////////////////////////////////////
217

    
218
  public String error(int index, Resources res)
219
    {
220
    switch(index)
221
      {
222
      case ERROR_CENTER_W_MISSING  : String colorW = res.getString(R.string.color_white2);
223
                                     return res.getString(R.string.solver_generic_missing_center,colorW);
224
      case ERROR_CENTER_O_MISSING  : String colorO = res.getString(R.string.color_orange2);
225
                                     return res.getString(R.string.solver_generic_missing_center,colorO);
226
      case ERROR_CENTER_G_MISSING  : String colorG = res.getString(R.string.color_green2);
227
                                     return res.getString(R.string.solver_generic_missing_center,colorG);
228
      case ERROR_CENTER_Y_MISSING  : String colorY = res.getString(R.string.color_yellow2);
229
                                     return res.getString(R.string.solver_generic_missing_center,colorY);
230
      case ERROR_CENTER_B_MISSING  : String colorB = res.getString(R.string.color_blue2);
231
                                     return res.getString(R.string.solver_generic_missing_center,colorB);
232
      case ERROR_CENTER_R_MISSING  : String colorR = res.getString(R.string.color_red2);
233
                                     return res.getString(R.string.solver_generic_missing_center,colorR);
234
      case ERROR_TWO_CENTERS_SWAP  : return res.getString(R.string.solver_generic_two_centers);
235
      case ERROR_CORNERS_CANNOT    : return res.getString(R.string.solver_generic_corners_cannot);
236
      }
237

    
238
    return null;
239
    }
240

    
241
///////////////////////////////////////////////////////////////////////////////////////////////////
242

    
243
  public int[][] solution(int index, Resources res)
244
    {
245
    if( mSolver==null )
246
      {
247
      mSolver = ImplementedTablebasesList.createPacked(res, ObjectSignatures.IVY_2);
248
      }
249

    
250
    return mSolver!=null ? mSolver.solution(index,null) : null;
251
    }
252
}  
253

    
(6-6/13)