Revision 4946b635
Added by Leszek Koltunski over 2 years ago
src/main/java/org/distorted/objects/Movement.java | ||
---|---|---|
34 | 34 |
private final float[] mPoint, mCamera, mTouch; |
35 | 35 |
private final float[] mPoint2D, mMove2D; |
36 | 36 |
private final int[] mEnabledRotAxis; |
37 |
private final float mDistanceCenterFace3D, mDistanceCenterFace2D;
|
|
37 |
private final float mDistanceCenterFace3D; |
|
38 | 38 |
private final Static3D[] mFaceAxis; |
39 | 39 |
|
40 | 40 |
private int mLastTouchedFace; |
41 | 41 |
private float[][][] mCastedRotAxis; |
42 | 42 |
private Static4D[][] mCastedRotAxis4D; |
43 |
private float[][] mTouchBorders, mA, mB; |
|
43 | 44 |
|
44 | 45 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
45 | 46 |
|
46 | 47 |
abstract boolean isInsideFace(int face, float[] point); |
47 | 48 |
abstract void computeEnabledAxis(int face, float[] touchPoint, int[] enabledAxis); |
48 |
abstract int computeRowFromOffset(int face, int axisIndex, int numLayers, float offset); |
|
49 | 49 |
public abstract float returnRotationFactor(int numLayers, int row); |
50 | 50 |
|
51 | 51 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
52 | 52 |
|
53 |
Movement(Static3D[] rotAxis, Static3D[] faceAxis, float distance3D, float distance2D)
|
|
53 |
Movement(Static3D[] rotAxis, Static3D[] faceAxis, float[][] cuts, boolean[][] rotatable, float distance3D, int size)
|
|
54 | 54 |
{ |
55 | 55 |
mPoint = new float[3]; |
56 | 56 |
mCamera= new float[3]; |
... | ... | |
65 | 65 |
mEnabledRotAxis = new int[rotAxis.length+1]; |
66 | 66 |
|
67 | 67 |
mDistanceCenterFace3D = distance3D; // distance from the center of the object to each of its faces |
68 |
mDistanceCenterFace2D = distance2D; // distance from the center of a face to its edge |
|
69 | 68 |
|
70 | 69 |
computeCastedAxis(rotAxis); |
70 |
computeBorders(cuts,rotatable,size); |
|
71 |
computeLinear(distance3D,rotAxis,faceAxis); |
|
71 | 72 |
} |
72 | 73 |
|
73 | 74 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
... | ... | |
249 | 250 |
|
250 | 251 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
251 | 252 |
|
252 |
float[] computeBorder(float scale, float[] cuts, boolean[] rotatable)
|
|
253 |
private float[] computeBorder(float[] cuts, boolean[] rotatable, int size)
|
|
253 | 254 |
{ |
254 | 255 |
int len = cuts.length; |
255 | 256 |
float[] border = new float[len]; |
... | ... | |
262 | 263 |
} |
263 | 264 |
else |
264 | 265 |
{ |
265 |
if( rotatable[i+1] ) border[i] = scale*cuts[i];
|
|
266 |
if( rotatable[i+1] ) border[i] = cuts[i]/size;
|
|
266 | 267 |
else |
267 | 268 |
{ |
268 | 269 |
int found = -1; |
... | ... | |
276 | 277 |
} |
277 | 278 |
} |
278 | 279 |
|
279 |
border[i] = found>0 ? scale*(cuts[i]+cuts[found-1])/2 : Float.MAX_VALUE;
|
|
280 |
border[i] = found>0 ? (cuts[i]+cuts[found-1])/(2*size) : Float.MAX_VALUE;
|
|
280 | 281 |
} |
281 | 282 |
} |
282 | 283 |
} |
... | ... | |
285 | 286 |
} |
286 | 287 |
|
287 | 288 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
289 |
// size, not numLayers (see Master Skewb where size!=numLayers) |
|
288 | 290 |
|
289 |
float[][] computeBorders(float coeff, float[][] cuts, boolean[][] rotatable)
|
|
291 |
void computeBorders(float[][] cuts, boolean[][] rotatable, int size)
|
|
290 | 292 |
{ |
291 | 293 |
int numCuts = cuts.length; |
292 |
float[][] borders = new float[numCuts][];
|
|
294 |
mTouchBorders = new float[numCuts][];
|
|
293 | 295 |
|
294 | 296 |
for(int i=0; i<numCuts; i++) |
295 | 297 |
{ |
296 |
borders[i] = computeBorder(coeff,cuts[i],rotatable[i]); |
|
298 |
mTouchBorders[i] = computeBorder(cuts[i],rotatable[i],size); |
|
299 |
} |
|
300 |
} |
|
301 |
|
|
302 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
|
303 |
|
|
304 |
private int computeSign(Static3D a, Static3D b) |
|
305 |
{ |
|
306 |
float a1 = a.get0(); |
|
307 |
float a2 = a.get1(); |
|
308 |
float a3 = a.get2(); |
|
309 |
float b1 = b.get0(); |
|
310 |
float b2 = b.get1(); |
|
311 |
float b3 = b.get2(); |
|
312 |
|
|
313 |
return a1*b1+a2*b2+a3*b3 < 0 ? 1:-1; |
|
314 |
} |
|
315 |
|
|
316 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
|
317 |
|
|
318 |
private float crossProductLen(Static3D a, Static3D b) |
|
319 |
{ |
|
320 |
float a1 = a.get0(); |
|
321 |
float a2 = a.get1(); |
|
322 |
float a3 = a.get2(); |
|
323 |
float b1 = b.get0(); |
|
324 |
float b2 = b.get1(); |
|
325 |
float b3 = b.get2(); |
|
326 |
|
|
327 |
float x1 = a2*b3-a3*b2; |
|
328 |
float x2 = a3*b1-a1*b3; |
|
329 |
float x3 = a1*b2-a2*b1; |
|
330 |
|
|
331 |
return (float)Math.sqrt(x1*x1 + x2*x2 + x3*x3); |
|
332 |
} |
|
333 |
|
|
334 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
|
335 |
// compute the array of 'A' and 'B' coeffs of the Ax+B linear function by which we need to multiply |
|
336 |
// the 3D 'cuts' to translate it from 3D (i.e. with respect to the rotAxis) to 2D in-face (i.e. with |
|
337 |
// respect to the 2D rotAxis cast into a particular face) |
|
338 |
|
|
339 |
void computeLinear(float distance3D, Static3D[] rotAxis, Static3D[] faceAxis) |
|
340 |
{ |
|
341 |
int numFaces = faceAxis.length; |
|
342 |
int numRot = rotAxis.length; |
|
343 |
|
|
344 |
mA = new float[numFaces][numRot]; |
|
345 |
mB = new float[numFaces][numRot]; |
|
346 |
|
|
347 |
for(int i=0; i<numFaces; i++) |
|
348 |
for(int j=0; j<numRot; j++) |
|
349 |
{ |
|
350 |
mA[i][j] = crossProductLen(faceAxis[i],rotAxis[j]); |
|
351 |
|
|
352 |
if( mA[i][j]!=0.0f ) |
|
353 |
{ |
|
354 |
float coeff = (float)Math.sqrt(1/(mA[i][j]*mA[i][j]) -1); |
|
355 |
int sign = computeSign(faceAxis[i],rotAxis[j]); |
|
356 |
mB[i][j] = sign*distance3D*coeff; |
|
357 |
} |
|
358 |
else mB[i][j] = 0.0f; |
|
359 |
|
|
360 |
android.util.Log.e("D", "face="+i+" rot="+j+" a="+mA[i][j]+" B="+mB[i][j]); |
|
361 |
} |
|
362 |
} |
|
363 |
|
|
364 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
|
365 |
|
|
366 |
private int computeRowFromOffset(int face, int axisIndex, float offset) |
|
367 |
{ |
|
368 |
float[] borders = mTouchBorders[axisIndex]; |
|
369 |
int len = borders.length; |
|
370 |
float A = mA[face][axisIndex]; |
|
371 |
|
|
372 |
if( A!=0.0f ) |
|
373 |
{ |
|
374 |
float B = mB[face][axisIndex]; |
|
375 |
|
|
376 |
for(int i=0; i<len; i++) |
|
377 |
{ |
|
378 |
float translated = B + borders[i]/A; |
|
379 |
|
|
380 |
android.util.Log.e("D", "offset="+offset+" borders[i]="+borders[i]+" translated="+translated+" A="+A+" B="+B); |
|
381 |
|
|
382 |
if( offset<translated ) return i; |
|
383 |
} |
|
297 | 384 |
} |
298 | 385 |
|
299 |
return borders;
|
|
386 |
return len;
|
|
300 | 387 |
} |
301 | 388 |
|
302 | 389 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
... | ... | |
328 | 415 |
|
329 | 416 |
/////////////////////////////////////////////////////////////////////////////////////////////////// |
330 | 417 |
|
331 |
public Static2D newRotation(int numLayers, Static4D rotatedTouchPoint, float objectRatio)
|
|
418 |
public Static2D newRotation(Static4D rotatedTouchPoint, float objectRatio) |
|
332 | 419 |
{ |
333 | 420 |
mPoint[0] = rotatedTouchPoint.get0()/objectRatio; |
334 | 421 |
mPoint[1] = rotatedTouchPoint.get1()/objectRatio; |
... | ... | |
343 | 430 |
computeEnabledAxis(mLastTouchedFace, mPoint2D, mEnabledRotAxis); |
344 | 431 |
int rotIndex = computeRotationIndex(mLastTouchedFace, mMove2D, mEnabledRotAxis); |
345 | 432 |
float offset = computeOffset(mPoint2D, mCastedRotAxis[mLastTouchedFace][rotIndex]); |
346 |
int row = computeRowFromOffset(mLastTouchedFace,rotIndex,numLayers,offset);
|
|
433 |
int row = computeRowFromOffset(mLastTouchedFace,rotIndex,offset); |
|
347 | 434 |
|
348 | 435 |
return new Static2D(rotIndex,row); |
349 | 436 |
} |
Also available in: Unified diff
Major abstraction - automatically compute the 'computeRowFromOffset()' function from CUTS.
Still one thing left: it appears like the CUTS of Mega/Kilominxes are not correct.