Commit 7e27f9b6 authored by Eric Tobias's avatar Eric Tobias

2.1.4 - Made SpatialMatrix a Singleton and added a return to the update call.

+ A call to update will now return whether the update changed the underlying data structure
+ Added PositionChangeListener
+ Called above listener when the underlying data structures are changed on a spatial event.
+ Made SpatialMatrix a singleton to better reflect its nature as a class maintaining some of the application state.
+ Added various test classes.
parent 5ff4cc20
2.1.4
+ Added test method for various classes.
+ Changed update method to return whether the underlying data structure have indeed been changed.
+ Added PositionChangeListener.
2.1.3
+ Added method to retrieve widgets aligned with one another horizontally and vertically.
......
/**
* Copyright Luxembourg Institute of Science and Technology, 2015. All rights reserved.
*
* This file is part of TULIP.
*
* TULIP is free software: you can redistribute it and/or modify it under the terms of the GNU
* Lesser General Public License as published by the Free Software Foundation, version 3 of the
* License.
*
* TULIP is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even
* the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser
* General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License along with TULIP. If
* not, see <http://www.gnu.org/licenses/lgpl-3.0.html>.
*/
package lu.list.itis.dkd.tui.event;
import lu.list.itis.dkd.tui.adapter.TangibleObject;
import java.util.EventObject;
/**
* @author Eric Tobias [eric.tobias@list.lu]
* @since 2.1
* @version 2.1.4
*/
public class PositionChangeEvent extends EventObject {
private static final long serialVersionUID = -7146965508061315693L;
/**
* The source that triggered the event.
*
* @param source
*/
public PositionChangeEvent(TangibleObject source) {
super(source);
}
}
\ No newline at end of file
/**
* Copyright Luxembourg Institute of Science and Technology, 2015. All rights reserved.
*
* This file is part of TULIP.
*
* TULIP is free software: you can redistribute it and/or modify it under the terms of the GNU
* Lesser General Public License as published by the Free Software Foundation, version 3 of the
* License.
*
* TULIP is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even
* the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser
* General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License along with TULIP. If
* not, see <http://www.gnu.org/licenses/lgpl-3.0.html>.
*/
package lu.list.itis.dkd.tui.event;
import lu.list.itis.dkd.tui.space.SpatialPositioningManager;
import java.util.EventListener;
/**
* @author Eric Tobias [eric.tobias@list.lu]
* @since 2.1
* @version 2.1.4
*/
public interface PositionChangeListener extends EventListener {
/**
* Method invoked when a position tracked by the spatial position manager has been changed.
*
* @param manager
* The manager holding information on the spatial layout.
*/
public void positionChanged(SpatialPositioningManager manager);
}
\ No newline at end of file
......@@ -36,6 +36,18 @@ public class SpatialMatrix {
private ArrayList<TangibleObject> horizontal = new ArrayList<>();
private ArrayList<TangibleObject> vertical = new ArrayList<>();
private static final SpatialMatrix INSTANCE = new SpatialMatrix();
private SpatialMatrix() {}
/**
* Singleton getter.
*
* @return The unique, single instance of this class.
*/
public static SpatialMatrix getInstance() {
return INSTANCE;
}
/**
* Method used to add an element to the matrix. The method will insert the element into the
......@@ -74,10 +86,20 @@ public class SpatialMatrix {
*
* @param object
* The object to update.
* @return Will return <code>true</code> if the underlying horizontal or vertical lists have
* been changed, that is, if the order of any of those lists have been changed. The
* method will use an equality check on the lists before (using a copy) and after the
* operations. The method will return <code>false</code> if both lists are equal.
* @see ArrayList#equals(Object)
*/
public synchronized void update(TangibleObject object) {
public synchronized boolean update(TangibleObject object) {
ArrayList<TangibleObject> horizontalCopy = new ArrayList<>(horizontal);
ArrayList<TangibleObject> verticalCopy = new ArrayList<>(vertical);
remove(object);
add(object);
return !(horizontalCopy.equals(horizontal) && verticalCopy.equals(vertical));
}
......@@ -393,4 +415,12 @@ public class SpatialMatrix {
return "Vertical : " + verticalBuilder.toString() + "\n" + "Horizontal : " + horizontalbuilder.toString(); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
}
/**
* Method used to clear the internal maps held by the matrix. Useful during unit testing.
*/
public void clear() {
horizontal.clear();
vertical.clear();
}
}
\ No newline at end of file
......@@ -20,6 +20,7 @@ import lu.list.itis.dkd.dbc.annotation.NonNullByDefault;
import lu.list.itis.dkd.dbc.annotation.Nullable;
import lu.list.itis.dkd.tui.TangibleObjectManager;
import lu.list.itis.dkd.tui.adapter.TangibleObject;
import lu.list.itis.dkd.tui.event.PositionChangeListener;
import lu.list.itis.dkd.tui.event.SpatialEvent;
import lu.list.itis.dkd.tui.event.SpatialEventListener;
import lu.list.itis.dkd.tui.utility.Point;
......@@ -63,7 +64,9 @@ public class SpatialPositioningManager implements SpatialEventListener {
private static final Properties properties = PropertiesFetcher.fetchProperties();
private static final SpatialPositioningManager INSTANCE = new SpatialPositioningManager();
private SpatialMatrix spatialMatrix = new SpatialMatrix();
private List<PositionChangeListener> positionChangeListeners = new ArrayList<>();
private SpatialMatrix spatialMatrix = SpatialMatrix.getInstance();
/**
* Enumeration showing all alignment types this class supports.
......@@ -127,7 +130,9 @@ public class SpatialPositioningManager implements SpatialEventListener {
}
/**
* {@inheritDoc} <br/>
* {@inheritDoc} The method will also notify all {@link PositionChangeListener} instances of any
* change, that is, it will notify all of any insertion or removals but only notify on updates
* if there is indeed a change to the underlying spatial matrix.<br/>
* <br/>
*
* The event will not be registered if the if of the tangible is not recognized by the
......@@ -142,13 +147,17 @@ public class SpatialPositioningManager implements SpatialEventListener {
switch (event.getType()) {
case UPDATE:
spatialMatrix.update(event.getSource());
if (spatialMatrix.update(event.getSource())) {
notifyPositionChangeListeners(this);
}
break;
case INSERT:
spatialMatrix.add(event.getSource());
notifyPositionChangeListeners(this);
break;
case REMOVE:
spatialMatrix.remove(event.getSource());
notifyPositionChangeListeners(this);
break;
default:
logger.log(Level.SEVERE, "Spatial event type \"" + event.getType() + "\" not recognized!"); //$NON-NLS-1$ //$NON-NLS-2$
......@@ -169,6 +178,26 @@ public class SpatialPositioningManager implements SpatialEventListener {
// // //$NON-NLS-2$
}
/**
* Method used to add a position change listener to this instance of the manager.
*
* @param listener
* The listener to add and notify of any changes.
*/
public void addPositionChangeListener(PositionChangeListener listener) {
this.positionChangeListeners.add(listener);
}
/**
* Method invoked to notify all {@link PositionChangeListener} instances of a change.
*
* @param manager
* The manager holding information on the spatial layout.
*/
public void notifyPositionChangeListeners(SpatialPositioningManager manager) {
positionChangeListeners.forEach(listener -> listener.positionChanged(manager));
}
/**
* The method will return the left-most widget, that is, the first widget found based based on
* its x-axis coordinate. The retrieval is based on the underlying handles.
......@@ -418,6 +447,6 @@ public class SpatialPositioningManager implements SpatialEventListener {
* testing.
*/
public void reinitialize() {
spatialMatrix = new SpatialMatrix();
spatialMatrix.clear();
}
}
\ No newline at end of file
......@@ -172,7 +172,6 @@ public class SpatialMatrixTest {
/**
* @throws Exception
*
*/
@BeforeClass
public static void setUpBefore() throws Exception {
......@@ -181,7 +180,6 @@ public class SpatialMatrixTest {
builderTwo = new TangibleObjectBuilder(2, Type.BLOB, 20, 20);
builderThree = new TangibleObjectBuilder(3, Type.OBJECT, 30, 30);
builderFour = new TangibleObjectBuilder(4, Type.CURSOR, 40, 40);
}
/**
......@@ -205,6 +203,12 @@ public class SpatialMatrixTest {
@After
public void after() {
SpatialPositioningManager.getInstance().reinitialize();
objectZero.getPosition().toCameraCoordinates().setLocation(new Point(0, 0, 0));
objectOne.getPosition().toCameraCoordinates().setLocation(new Point(10, 10, 10));
objectTwo.getPosition().toCameraCoordinates().setLocation(new Point(20, 20, 20));
objectThree.getPosition().toCameraCoordinates().setLocation(new Point(30, 30, 30));
objectFour.getPosition().toCameraCoordinates().setLocation(new Point(40, 40, 40));
}
/**
......@@ -301,6 +305,31 @@ public class SpatialMatrixTest {
assertEquals(5, matrix.getHorizontal().size());
}
/**
* Test method for
* {@link lu.list.itis.dkd.tui.space.SpatialMatrix#update(lu.list.itis.dkd.tui.adapter.TangibleObject)}
* , specifically, for testing its return value.
*/
@Test
public void voidTestUpdateReturn() {
application.getAdapter().notifyListeners(new SpatialEvent(objectZero, objectZero.getPosition(), SpatialEventType.INSERT));
application.getAdapter().notifyListeners(new SpatialEvent(objectOne, objectOne.getPosition(), SpatialEventType.INSERT));
application.getAdapter().notifyListeners(new SpatialEvent(objectThree, objectThree.getPosition(), SpatialEventType.INSERT));
application.getAdapter().notifyListeners(new SpatialEvent(objectTwo, objectTwo.getPosition(), SpatialEventType.INSERT));
application.getAdapter().notifyListeners(new SpatialEvent(objectFour, objectFour.getPosition(), SpatialEventType.INSERT));
assertFalse(matrix.update(objectOne));
objectOne.getPosition().toCameraCoordinates().setLocation(new Point(1, 1, 1));
assertFalse(matrix.update(objectOne));
objectThree.getPosition().toCameraCoordinates().setLocation(new Point(45, 45, 45));
assertTrue(matrix.update(objectThree));
objectThree.getPosition().toCameraCoordinates().setLocation(new Point(5, 5, 5));
assertTrue(matrix.update(objectThree));
}
/**
* Test method for {@link lu.list.itis.dkd.tui.space.SpatialMatrix#leftOf(int)}.
*/
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment