123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213 |
- package me.hammerle.supersnuvi.util;
- public class CollisionLine extends CollisionObject
- {
- private float x1;
- private float y1;
- private float x2;
- private float y2;
-
- private float cx1;
- private float cy1;
- private float cx2;
- private float cy2;
-
- public CollisionLine(float x1, float y1, float x2, float y2)
- {
- this.x1 = x1;
- this.y1 = y1;
- this.x2 = x2;
- this.y2 = y2;
-
- this.cx1 = x1;
- this.cy1 = y1;
- this.cx2 = x2;
- this.cy2 = y2;
- }
-
- @Override
- public Type getType()
- {
- return Type.LINE;
- }
- @Override
- public CollisionObject copy()
- {
- return new CollisionLine(cx1, cy1, cx2, cy2);
- }
- @Override
- public void save()
- {
- x1 = cx1;
- y1 = cy1;
- x2 = cx2;
- y2 = cy2;
- }
- @Override
- public CollisionObject reset()
- {
- cx1 = x1;
- cy1 = y1;
- cx2 = x2;
- cy2 = y2;
- return this;
- }
- @Override
- public float getWidth()
- {
- return Math.abs(x1 - x2);
- }
- @Override
- public float getHeight()
- {
- return Math.abs(y1 - y2);
- }
- @Override
- public float getMinX()
- {
- return cx1;
- }
- @Override
- public float getMaxX()
- {
- return cx2;
- }
- @Override
- public float getMinY()
- {
- return cy1;
- }
- @Override
- public float getMaxY()
- {
- return cy2;
- }
- @Override
- public CollisionObject expand(float x, float y)
- {
- return this;
- }
- @Override
- public CollisionObject offsetX(float x)
- {
- cx1 += x;
- cx2 += x;
- return this;
- }
- @Override
- public CollisionObject offsetY(float y)
- {
- cy1 += y;
- cy2 += y;
- return this;
- }
- @Override
- public boolean isColliding(CollisionObject cb)
- {
- switch(cb.getType())
- {
- case BOX:
- return cb.isColliding(this);
- case LINE:
- return CollisionLine.intersect(x1, y1, x2, y2, cb.getMinX(), cb.getMinY(), cb.getMaxX(), cb.getMaxY());
- }
- return false;
- }
-
- @Override
- public String toString()
- {
- StringBuilder sb = new StringBuilder("line[x1 = ");
- sb.append(cx1);
- sb.append(", y1 = ");
- sb.append(cy1);
- sb.append(", x2 = ");
- sb.append(cx2);
- sb.append(", y2 = ");
- sb.append(cy2);
- sb.append(']');
- return sb.toString();
- }
-
- public static boolean intersect(float x11, float y11, float x12, float y12, float x21, float y21, float x22, float y22)
- {
- if(compareFloats(x11, x12))
- {
- if(compareFloats(x21, x22))
- {
- return false;
- }
- else
- {
- if(!isBetween(x11, x21, x22))
- {
- return false;
- }
- float k = (y21 - y22) / (x21 - x22);
- float d = y22 - k * x22;
- float y = d + x11 * k;
- return isBetween(y, y11, y12) && isBetween(y, y21, y22);
- }
- }
- else
- {
- if(compareFloats(x21, x22))
- {
- if(!isBetween(x21, x11, x12))
- {
- return false;
- }
- float k = (y11 - y12) / (x11 - x12);
- float d = y12 - k * x12;
- float y = d + x21 * k;
- return isBetween(y, y11, y12) && isBetween(y, y21, y22);
- }
- else
- {
- float k1 = (y11 - y12) / (x11 - x12);
- float k2 = (y21 - y22) / (x21 - x22);
- if(compareFloats(k1, k2))
- {
- return false;
- }
- float d1 = y12 - k1 * x12;
- float d2 = y22 - k2 * x22;
-
- float x = (d1 - d2) / (k2 - k1);
- if(!isBetween(x, x11, x12) || !isBetween(x, x21, x22))
- {
- return false;
- }
- float y = k1 * x + d1;
- return isBetween(y, y11, y12) && isBetween(y, y21, y22);
- }
- }
- }
-
- private static final float ERROR = 1.0f / 512.0f;
-
- private static boolean isBetween(float y, float y1, float y2)
- {
- float min = Math.min(y1, y2) - ERROR;
- float max = Math.max(y1, y2) + ERROR;
- return y >= min && y <= max;
- }
-
- private static boolean compareFloats(float a, float b)
- {
- return Math.abs(a - b) < ERROR;
- }
- }
|