Skip to content

Commit

Permalink
F Introduce bouncing GridElements. #1 Introduce CollisionDetectionResult
Browse files Browse the repository at this point in the history
  • Loading branch information
Dominic authored and Dominic committed Jun 2, 2020
1 parent 111d9dd commit ebfa6dc
Show file tree
Hide file tree
Showing 22 changed files with 146 additions and 59 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
import javax.swing.SwingUtilities;

import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResultImpl;
import com.myownb3.piranha.core.grid.gridelement.GridElement;
import com.myownb3.piranha.core.grid.position.Position;
import com.myownb3.piranha.core.moveables.EndPointMoveable;
Expand All @@ -24,14 +26,18 @@ public CollisionDetectionHandlerImpl(Stoppable stoppable, MainWindow mainWindow)
}

@Override
public void handleCollision(GridElement otherGridElement, GridElement movedGridElement, Position newPosition) {
if (stoppable.isRunning() && isCollisionWithMoveable(movedGridElement)) {
stoppable.stop();
if (moveableController != null) {
moveableController.stop();
public CollisionDetectionResult handleCollision(GridElement otherGridElement, GridElement movedGridElement, Position newPosition) {
if (stoppable.isRunning()) {
if (isCollisionWithMoveable(movedGridElement)) {
stoppable.stop();
if (moveableController != null) {
moveableController.stop();
}
SwingUtilities.invokeLater(() -> mainWindow.showCollisionInfo());
}
SwingUtilities.invokeLater(() -> mainWindow.showCollisionInfo());
}
return new CollisionDetectionResultImpl(false, newPosition);
}

private static boolean isCollisionWithMoveable(GridElement gridElement) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ public MazePostMoveForwardHandler(MainWindowHolder windowHolder, MoveableControl

@Override
public void handlePostMoveForward(MoveResult moveResult) {
super.handlePostMoveForward(moveResult);
Moveable moveable = getMoveableController().getMoveable();
lightBarrier.checkGridElement(moveable);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ public interface CollisionDetectionHandler {
* the {@link GridElement} which caused the collision with the other {@link GridElement}
* @param newPosition
* the Position at which the collision occurred
* @return a {@link CollisionDetectionResult} which contains the results of the collision handling
*/
void handleCollision(GridElement otherGridElement, GridElement movedGridElement, Position newPosition);
CollisionDetectionResult handleCollision(GridElement otherGridElement, GridElement movedGridElement, Position newPosition);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package com.myownb3.piranha.core.grid.collision;

import com.myownb3.piranha.core.grid.Grid;
import com.myownb3.piranha.core.grid.position.Position;

/**
* The {@link CollisionDetectionResult} contains the result of a collision, detected by a {@link CollisionDetectionHandler}
*
* @author Dominic
*
*/
public interface CollisionDetectionResult {

/**
* @return the by the {@link Grid} moved {@link Position}
*/
Position getMovedPosition();


/**
* @return <code>true</code> if there was a collision or <code>false</code> if not
*/
boolean isCollision();
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,9 @@ public interface CollisionDetector {
* the new Position after the movement
* @param gridElements2Check
* all {@link GridElement}s which are in reach to collide and which are also 'avoidable'
* @return a result about the detection which was made by this {@link CollisionDetector}
*/
void checkCollision(CollisionDetectionHandler collisionDetectionHandler, GridElement movedGridElement, Position oldPosition, Position newPosition,
List<GridElement> gridElements2Check);
CollisionDetectionResult checkCollision(CollisionDetectionHandler collisionDetectionHandler, GridElement movedGridElement, Position oldPosition,
Position newPosition, List<GridElement> gridElements2Check);

}
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@

import com.myownb3.piranha.core.detector.Detector;
import com.myownb3.piranha.core.grid.Grid;
import com.myownb3.piranha.core.grid.collision.CollisionDetectedException;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.gridelement.shape.Shape;
import com.myownb3.piranha.core.grid.position.Position;
import com.myownb3.piranha.core.moveables.Moveable;
Expand Down Expand Up @@ -85,16 +87,20 @@ public interface GridElement {

/**
* Checks for every given {@link GridElement} if there is a collision when this {@link GridElement} is moving
* from it's current Position to the new Position
* from it's current Position to the new Position.
* The returned {@link CollisionDetectionResult} contains further information about any detected collision. Depending on the
* {@link CollisionDetectionHandler} it may be thrown a {@link CollisionDetectedException}
*
* @param collisionDetectionHandler
* the {@link CollisionDetectionHandler} which handles the collision if one occurred
* @param newPosition
* the new Position after the movement
* @param gridElements2Check
* the {@link GridElement}s to check
* @return the result of the collision detection
*/
void check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition, List<GridElement> gridElements2Check);
CollisionDetectionResult check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
List<GridElement> gridElements2Check);

/**
* Returns <code>true</code> if this {@link GridElement} is gridElement or <code>false</code> if not.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@
import java.util.List;

import com.myownb3.piranha.core.detector.Detector;
import com.myownb3.piranha.core.grid.collision.CollisionDetectedException;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.gridelement.GridElement;
import com.myownb3.piranha.core.grid.gridelement.shape.path.PathSegment;
import com.myownb3.piranha.core.grid.position.Position;
Expand All @@ -30,17 +32,22 @@ public interface Shape extends Cloneable {
List<PathSegment> getPath();

/**
* Checks for every given {@link GridElement} if there is a collision when the {@link GridElement} of this {@link Shape} is moving
* from it's current Position to the new Position
* Checks for every given {@link GridElement} if there is a collision when this {@link GridElement} is moving
* from it's current Position to the new Position.
* The returned {@link CollisionDetectionResult} contains further information about any detected collision. Depending on the
* {@link CollisionDetectionHandler} it may be thrown a {@link CollisionDetectedException}
*
* @param collisionDetectionHandler
* the {@link CollisionDetectionHandler} which handles the collision if one occurred
* @param newPosition
* the new Position after the movement
* @param gridElements2Check
* all {@link GridElement}s which are in reach to collide and which are also 'avoidable'
* the {@link GridElement}s to check
* @return the result of the collision detection
*/
void check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition, List<GridElement> gridElements2Check);
CollisionDetectionResult check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
List<GridElement> gridElements2Check);


/**
* Evaluates if the {@link GridElement} of this {@link Shape} at the given {@link Position} is in reach to this Shape or it's path to be
Expand Down
17 changes: 7 additions & 10 deletions MoveableImpl/src/com/myownb3/piranha/core/grid/DefaultGrid.java
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
import java.util.stream.Collectors;

import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.collision.DefaultCollisionDetectionHandlerImpl;
import com.myownb3.piranha.core.grid.direction.Direction;
import com.myownb3.piranha.core.grid.exception.GridElementOutOfBoundsException;
Expand Down Expand Up @@ -111,15 +112,13 @@ public Position moveBackward(GridElement gridElement) {
double newX = getNewXValue(gridElement, direction.getBackwardX());
double newY = getNewYValue(gridElement, direction.getBackwardY());
checkBounds(newX, newY);
Position newPosition = Positions.of(direction, newX, newY);
checkCollision(gridElement, newPosition);

return newPosition;
CollisionDetectionResult collisionDetectionResult = checkCollision(gridElement, Positions.of(direction, newX, newY));
return collisionDetectionResult.getMovedPosition();
}

private void checkCollision(GridElement gridElement, Position newPosition) {
private CollisionDetectionResult checkCollision(GridElement gridElement, Position newPosition) {
List<GridElement> gridElements2Check = getGridElements4CollisionCheckWithinDistanceInternal(gridElement, maxDistance);
gridElement.check4Collision(collisionDetectionHandler, newPosition, gridElements2Check);
return gridElement.check4Collision(collisionDetectionHandler, newPosition, gridElements2Check);
}

/**
Expand All @@ -137,10 +136,8 @@ public Position moveForward(GridElement gridElement) {
double newX = getNewXValue(gridElement, direction.getForwardX());
double newY = getNewYValue(gridElement, direction.getForwardY());
checkBounds(newX, newY);
Position newPosition = Positions.of(direction, newX, newY);
checkCollision(gridElement, newPosition);

return newPosition;
CollisionDetectionResult collisionDetectionResult = checkCollision(gridElement, Positions.of(direction, newX, newY));
return collisionDetectionResult.getMovedPosition();
}

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package com.myownb3.piranha.core.grid.collision;

import com.myownb3.piranha.core.grid.position.Position;

public class CollisionDetectionResultImpl implements CollisionDetectionResult {

private Position movedPosition;
private boolean isCollision;

public CollisionDetectionResultImpl(boolean isCollision, Position movedPosition) {
this.isCollision = isCollision;
this.movedPosition = movedPosition;
}

@Override
public Position getMovedPosition() {
return movedPosition;
}

@Override
public boolean isCollision() {
return isCollision;
}
}
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
package com.myownb3.piranha.core.grid.collision;

import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.gridelement.GridElement;
import com.myownb3.piranha.core.grid.position.Position;

public class DefaultCollisionDetectionHandlerImpl implements CollisionDetectionHandler {

@Override
public void handleCollision(GridElement otherGridElement, GridElement movedGridElement, Position newPosition) {
public CollisionDetectionResult handleCollision(GridElement otherGridElement, GridElement movedGridElement, Position newPosition) {
throw new CollisionDetectedException("Collision with GridElement '" + otherGridElement.getPosition()
+ "' and the moved GridElement '" + movedGridElement + "', on Position x='" + newPosition.getX() + "', y='" + newPosition.getY() + "'");
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import com.myownb3.piranha.core.detector.Detector;
import com.myownb3.piranha.core.grid.Grid;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.gridelement.shape.AbstractShape;
import com.myownb3.piranha.core.grid.gridelement.shape.Shape;
import com.myownb3.piranha.core.grid.gridelement.shape.position.PositionShape.PositionShapeBuilder;
Expand Down Expand Up @@ -73,9 +74,9 @@ public void isDetectedBy(Position detectorPosition, Detector detector) {
}

@Override
public void check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
public CollisionDetectionResult check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
List<GridElement> gridElements2Check) {
shape.check4Collision(collisionDetectionHandler, newPosition, gridElements2Check);
return shape.check4Collision(collisionDetectionHandler, newPosition, gridElements2Check);
}

@Override
Expand Down Expand Up @@ -121,6 +122,10 @@ public String getName() {
return name;
}

public void setPosition(Position position) {
this.position = position;
}

public abstract static class AbstractGridElementBuilder<T extends AbstractGridElement> {

protected Position position;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
import java.util.stream.Collectors;

import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.collision.CollisionDetector;
import com.myownb3.piranha.core.grid.gridelement.GridElement;
import com.myownb3.piranha.core.grid.gridelement.position.Positions;
Expand Down Expand Up @@ -44,9 +45,10 @@ protected CollisionDetector buildCollisionDetector() {
}

@Override
public void check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
public CollisionDetectionResult check4Collision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
List<GridElement> gridElements2Check) {
collisionDetector.checkCollision(collisionDetectionHandler, gridElement, null/*old value not necessary*/, newPosition, gridElements2Check);
return collisionDetector.checkCollision(collisionDetectionHandler, gridElement, null/*old value not necessary*/, newPosition,
gridElements2Check);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
import java.util.List;

import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResultImpl;
import com.myownb3.piranha.core.grid.gridelement.GridElement;
import com.myownb3.piranha.core.grid.gridelement.shape.Shape;
import com.myownb3.piranha.core.grid.gridelement.shape.circle.Circle;
Expand All @@ -25,12 +27,14 @@ public CircleCollisionDetectorImpl(Circle circle) {
}

@Override
public void checkCollision(CollisionDetectionHandler collisionDetectionHandler, GridElement movedGridElement, Position oldPosition,
Position newPosition, List<GridElement> gridElements2Check) {
public CollisionDetectionResult checkCollision(CollisionDetectionHandler collisionDetectionHandler, GridElement movedGridElement,
Position oldPosition, Position newPosition, List<GridElement> gridElements2Check) {
Shape ourCircleAtNewPos = getOurShapeAtNewPos(newPosition, circle);
gridElements2Check.stream()
return gridElements2Check.stream()
.filter(isGridElementsInsideOrOnShape(newPosition, ourCircleAtNewPos))
.forEach(handleCollision(collisionDetectionHandler, newPosition, movedGridElement));
.findFirst()
.map(handleCollision(collisionDetectionHandler, newPosition, movedGridElement))
.orElse(new CollisionDetectionResultImpl(false, newPosition));
}

private static Shape getOurShapeAtNewPos(Position newPosition, Shape shape) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,12 @@

import java.util.Comparator;
import java.util.List;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Predicate;

import com.myownb3.piranha.core.grid.Grid;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.collision.CollisionDetector;
import com.myownb3.piranha.core.grid.collision.Intersection;
import com.myownb3.piranha.core.grid.collision.IntersectionImpl;
Expand All @@ -33,8 +34,8 @@ protected AbstractCollisionDetector() {
margin = 1d / Moveable.STEP_WITDH;
}

protected Consumer<? super GridElement> handleCollision(CollisionDetectionHandler collisionDetectionHandler, Position newPosition,
GridElement movedGridElement) {
protected Function<? super GridElement, CollisionDetectionResult> handleCollision(CollisionDetectionHandler collisionDetectionHandler,
Position newPosition, GridElement movedGridElement) {
return otherGridElement -> collisionDetectionHandler.handleCollision(otherGridElement, movedGridElement, newPosition);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,12 @@

import com.myownb3.piranha.core.grid.Grid;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionHandler;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResult;
import com.myownb3.piranha.core.grid.collision.CollisionDetectionResultImpl;
import com.myownb3.piranha.core.grid.collision.CollisionDetector;
import com.myownb3.piranha.core.grid.gridelement.GridElement;
import com.myownb3.piranha.core.grid.gridelement.shape.detection.AbstractCollisionDetector;
import com.myownb3.piranha.core.grid.position.Position;
import com.myownb3.piranha.util.vector.VectorUtil;

/**
* The {@link PositionCollisionDetectorImpl} implements the {@link CollisionDetector}. It is able to check if a {@link Position} has
Expand All @@ -36,12 +37,14 @@ private PositionCollisionDetectorImpl(int collisionDistance) {
}

@Override
public void checkCollision(CollisionDetectionHandler collisionDetectionHandler, GridElement movedGridElement, Position oldPosition,
Position newPosition, List<GridElement> gridElements2Check) {
Float64Vector lineFromOldToNew = VectorUtil.getVector(oldPosition.getDirection());
gridElements2Check.stream()
public CollisionDetectionResult checkCollision(CollisionDetectionHandler collisionDetectionHandler, GridElement movedGridElement,
Position oldPosition, Position newPosition, List<GridElement> gridElements2Check) {
Float64Vector lineFromOldToNew = oldPosition.getDirection().getVector();
return gridElements2Check.stream()
.filter(isCollision(oldPosition, newPosition, lineFromOldToNew))
.forEach(handleCollision(collisionDetectionHandler, newPosition, movedGridElement));
.findFirst()
.map(handleCollision(collisionDetectionHandler, newPosition, movedGridElement))
.orElse(new CollisionDetectionResultImpl(false, newPosition));
}

private Predicate<? super GridElement> isCollision(Position oldPosition, Position newPosition, Float64Vector lineFromOldToNew) {
Expand Down
Loading

0 comments on commit ebfa6dc

Please sign in to comment.