diff --git a/tools/cooja/java/se/sics/cooja/plugins/VisBattery.java b/tools/cooja/java/se/sics/cooja/plugins/VisBattery.java deleted file mode 100644 index 736ebf342..000000000 --- a/tools/cooja/java/se/sics/cooja/plugins/VisBattery.java +++ /dev/null @@ -1,136 +0,0 @@ -/* - * Copyright (c) 2006, Swedish Institute of Computer Science. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the Institute nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $Id: VisBattery.java,v 1.5 2008/10/28 15:36:25 fros4943 Exp $ - */ - -package se.sics.cooja.plugins; - -import java.awt.*; -import java.util.*; -import org.apache.log4j.Logger; - -import se.sics.cooja.*; -import se.sics.cooja.interfaces.Battery; - -/** - * A Battery Visualizer indicates mote energy levels by painting them in - * different colors. The mote is painted in a grayscale where white is max - * energy and black is no energy left. If a mote has no battery interface or - * infinite energy, it is painted blue. If a mote is dead it is painted red. - * - * A VisBattery observers both the simulation and all mote batteries. - * - * @author Fredrik Osterlind - */ -@ClassDescription("Battery Visualizer") -@PluginType(PluginType.SIM_PLUGIN) -public class VisBattery extends Visualizer2D { - private static final long serialVersionUID = 1L; - private static Logger logger = Logger.getLogger(VisBattery.class); - - private Simulation simulation; - - private Observer simObserver = null; // Watches simulation changes - private Observer batteryObserver = null; // Watches mote battery changes - - /** - * Creates a new battery visualizer. - * - * @param simulationToVisualize - * Simulation to visualize - */ - public VisBattery(Simulation simulationToVisualize, GUI gui) { - super(simulationToVisualize, gui); - setTitle("Battery Visualizer"); - - simulation = simulationToVisualize; - - // Always observe all motes in simulation - batteryObserver = new Observer() { - public void update(Observable obs, Object obj) { - getCurrentCanvas().repaint(); - } - }; - simulation.addObserver(simObserver = new Observer() { - public void update(Observable obs, Object obj) { - // Register (or reregister) as observer on all motes - for (int i = 0; i < simulation.getMotesCount(); i++) { - Battery battery = simulation.getMote(i).getInterfaces().getBattery(); - if (battery != null) { - battery.addObserver(batteryObserver); - } - } - } - }); - simObserver.update(null, null); - - } - - public Color[] getColorOf(Mote mote) { - if (mote.getState() == Mote.State.DEAD) { - return new Color[]{Color.RED}; - } - - Battery battery = mote.getInterfaces().getBattery(); - if (battery == null) { - return new Color[]{Color.BLUE}; - } - - if (battery.hasInfiniteEnergy()) { - return new Color[]{Color.BLUE}; - } - - double currentEnergy = battery.getEnergyLeftRatio(); - - if (currentEnergy < 0.0) { - return new Color[]{Color.RED}; - } - - int grayValue = (int) (255 * currentEnergy); - return new Color[]{new Color(grayValue, grayValue, grayValue)}; - } - - public void closePlugin() { - if (simObserver != null) { - simulation.deleteObserver(simObserver); - - // Delete all state observers - for (int i = 0; i < simulation.getMotesCount(); i++) { - Battery battery = simulation.getMote(i).getInterfaces().getBattery(); - if (battery != null) { - battery.deleteObserver(batteryObserver); - } - } - } - - super.closePlugin(); - } - - -} diff --git a/tools/cooja/java/se/sics/cooja/plugins/VisState.java b/tools/cooja/java/se/sics/cooja/plugins/VisState.java deleted file mode 100644 index 999f1ae1f..000000000 --- a/tools/cooja/java/se/sics/cooja/plugins/VisState.java +++ /dev/null @@ -1,151 +0,0 @@ -/* - * Copyright (c) 2006, Swedish Institute of Computer Science. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the Institute nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $Id: VisState.java,v 1.6 2009/03/10 21:20:39 fros4943 Exp $ - */ - -package se.sics.cooja.plugins; - -import java.awt.*; -import java.util.*; -import org.apache.log4j.Logger; - -import se.sics.cooja.*; -import se.sics.cooja.Mote.State; - -/** - * A State Visualizer indicates mote states by painting them in different colors. - * Active motes are green, sleeping motes are gray and dead motes are read. - * - * The inner color indicates the mote type. - * - * A VisState observes both the simulation and all mote states. - * - * @author Fredrik Osterlind - */ -@ClassDescription("State Visualizer") -@PluginType(PluginType.SIM_STANDARD_PLUGIN) -public class VisState extends Visualizer2D { - private static final long serialVersionUID = 1L; - private static Logger logger = Logger.getLogger(VisState.class); - - private Simulation simulation; - - private static final Color moteTypeColors[] = new Color[] { - Color.MAGENTA, - Color.CYAN, - Color.ORANGE, - Color.GREEN, - Color.BLUE, - Color.RED, - Color.YELLOW, - }; - - private Observer simObserver = null; // Watches simulation changes - private Observer stateObserver = null; // Watches mote state changes - - /** - * Creates a new state visualizer. - * - * @param simulationToVisualize Simulation to visualize - */ - public VisState(Simulation simulationToVisualize, GUI gui) { - super(simulationToVisualize, gui); - setTitle("State Visualizer"); - - simulation = simulationToVisualize; - - // Always observe all motes in simulation - stateObserver = new Observer() { - public void update(Observable obs, Object obj) { - getCurrentCanvas().repaint(); - } - }; - simulation.addObserver(simObserver = new Observer() { - public void update(Observable obs, Object obj) { - // Register (or reregister) as observer on all motes - for (int i=0; i < simulation.getMotesCount(); i++) { - Mote mote = simulation.getMote(i); - if (mote != null) { - mote.addStateObserver(stateObserver); - } - } - } - }); - simObserver.update(null, null); - - setLocation( - gui.getDesktopPane().getWidth() - getWidth(), - 0); - - } - - public Color[] getColorOf(Mote mote) { - Color[] returnColors = new Color[2]; - - // If mote is sleeping, make outer circle blue - if (mote.getState() == Mote.State.LPM) { - returnColors[1] = Color.GRAY; - } else if (mote.getState() == State.DEAD) { - returnColors[1] = Color.RED; - } else { - returnColors[1] = Color.GREEN; // make outer circle green - } - - - // Associate different colors with different mote types - MoteType[] allTypes = simulation.getMoteTypes(); - int numberOfTypes = allTypes.length; - - for (int colCounter=0; colCounter < numberOfTypes && colCounter < moteTypeColors.length; colCounter++) { - if (mote.getType() == allTypes[colCounter]) { - returnColors[0] = moteTypeColors[colCounter]; - return returnColors; - } - } - - returnColors[0] = Color.WHITE; - return returnColors; - } - - public void closePlugin() { - if (simObserver != null) { - simulation.deleteObserver(simObserver); - - // Delete all state observers - for (int i=0; i < simulation.getMotesCount(); i++) { - Mote mote = simulation.getMote(i); - if (mote != null) { - mote.deleteStateObserver(stateObserver); - } - } - } - - super.closePlugin(); - } -} diff --git a/tools/cooja/java/se/sics/cooja/plugins/VisTraffic.java b/tools/cooja/java/se/sics/cooja/plugins/VisTraffic.java deleted file mode 100644 index c89796685..000000000 --- a/tools/cooja/java/se/sics/cooja/plugins/VisTraffic.java +++ /dev/null @@ -1,239 +0,0 @@ -/* - * Copyright (c) 2006, Swedish Institute of Computer Science. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the Institute nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $Id: VisTraffic.java,v 1.6 2007/02/28 09:50:00 fros4943 Exp $ - */ - -package se.sics.cooja.plugins; - -import java.awt.*; -import java.util.*; -import javax.swing.SwingUtilities; -import org.apache.log4j.Logger; - -import se.sics.cooja.*; -import se.sics.cooja.interfaces.Position; -import se.sics.cooja.interfaces.Radio; - -/** - * A Traffic Visualizer visualizes radio traffic by painting lines between - * communicating motes. - * - * A VisTraffic observers the current simulation radio medium. - * - * @author Fredrik Osterlind - */ -@ClassDescription("Traffic Visualizer") -@PluginType(PluginType.SIM_PLUGIN) -public class VisTraffic extends Visualizer2D { - protected boolean USE_ALPHA = false; - - protected boolean USE_HISTORY = true; - - protected int MAX_PAINTED_CONNS = 50; - - private static final long serialVersionUID = 1L; - - private static Logger logger = Logger.getLogger(VisTraffic.class); - - private RadioMedium radioMedium; - - public Vector allPaintedConnections = new Vector(); - - private Simulation simulation; - - private Observer radioObserver = null; - - /** - * Creates a new VisTraffic visualizer. - * - * @param simulationToVisualize - * Simulation to visualize - */ - public VisTraffic(Simulation simulationToVisualize, GUI gui) { - super(simulationToVisualize, gui); - setTitle("Traffic Visualizer"); - simulation = simulationToVisualize; - - radioMedium = simulationToVisualize.getRadioMedium(); - - // Listen to radio medium and paint any new data transfers - simulationToVisualize.getRadioMedium().addRadioMediumObserver( - radioObserver = new Observer() { - public void update(Observable obs, Object obj) { - if (radioMedium == null) - return; - - final RadioConnection[] connsToAdd = radioMedium - .getLastTickConnections(); - if (connsToAdd != null && connsToAdd.length > 0) { - - SwingUtilities.invokeLater(new Runnable() { - public void run() { - if (!USE_HISTORY) - allPaintedConnections.clear(); - - for (RadioConnection conn : connsToAdd) { - if (conn != null) { - Color connColor = getColorOf(conn); - int duration = getDurationOf(conn); - if (connColor != null && duration > 0) - allPaintedConnections.add(0, new PaintedConnection( - conn, duration, connColor)); - } - } - - getCurrentCanvas().repaint(); - } - }); - } - } - }); - } - - /** - * Paints given connection on given graphics. - * - * @param connection - * Connection - * @param g2d - * Graphics to paint on - */ - protected void paintConnection(PaintedConnection connection, Graphics g2d) { - Point sourcePixelPosition = transformPositionToPixel(connection.radioConnection.getSource().getPosition()); - g2d.setColor(connection.getColor(simulation.isRunning())); - for (Radio destRadio : connection.radioConnection.getDestinations()) { - Position destPosition = destRadio.getPosition(); - Point destPixelPosition = transformPositionToPixel(destPosition); - g2d.drawLine(sourcePixelPosition.x, sourcePixelPosition.y, - destPixelPosition.x, destPixelPosition.y); - } - } - - /** - * Returns color the given connection should be painted in. If returned color - * is null, the connection will not be painted. - * - * @param connection - * Connection - * @return Color - */ - protected Color getColorOf(RadioConnection connection) { - return Color.BLACK; - } - - /** - * Returns duration the given connection should be visible. If negative, the - * connection will not be painted. Observe that the duration is the number of - * repaints, not related to time. - * - * @param connection - * Connection - * @return Duration in repaints - */ - protected int getDurationOf(RadioConnection connection) { - return 10; - } - - public void closePlugin() { - super.closePlugin(); - - // Remove radio observer - radioMedium.deleteRadioMediumObserver(radioObserver); - } - - public Color[] getColorOf(Mote m) { - return null; - } - - protected void visualizeSimulation(Graphics g) { - - // Clean up old connections - Vector newPaintedConnections = new Vector(); - for (PaintedConnection conn : allPaintedConnections) - if (!conn.shouldBeRemoved()) - newPaintedConnections.add(conn); - allPaintedConnections = newPaintedConnections; - if (allPaintedConnections.size() > MAX_PAINTED_CONNS) - allPaintedConnections.setSize(MAX_PAINTED_CONNS); - - for (PaintedConnection conn : allPaintedConnections) - paintConnection(conn, (Graphics2D) g); - } - - public class PaintedConnection { - public RadioConnection radioConnection; - - private int duration; - - private int colorVal; - - private int repaintsLeft; - - private Color staticColor; - - /** - * @param conn - * Radio connection to visualize - * @param duration - * Number of repaints - * @param color - * Base color of painted connection - */ - public PaintedConnection(RadioConnection conn, int duration, Color color) { - radioConnection = conn; - colorVal = color.getRGB() & 0xffffff; - repaintsLeft = duration; - this.duration = duration; - staticColor = color; - } - - /** - * Get color this connection should be painted in. - * - * @param isRunning - * True if current simulation is running - * @return Color - */ - public Color getColor(boolean isRunning) { - if (isRunning) - repaintsLeft--; - - if (!USE_ALPHA) - return staticColor; - - int alpha = 127 + 128 * repaintsLeft / duration; - return new Color(colorVal | (alpha << 24), true); - } - - public boolean shouldBeRemoved() { - return repaintsLeft <= 0; - } - } - -} diff --git a/tools/cooja/java/se/sics/cooja/plugins/VisUDGM.java b/tools/cooja/java/se/sics/cooja/plugins/VisUDGM.java deleted file mode 100644 index d0e228f34..000000000 --- a/tools/cooja/java/se/sics/cooja/plugins/VisUDGM.java +++ /dev/null @@ -1,345 +0,0 @@ -package se.sics.cooja.plugins; - -import java.awt.Color; -import java.awt.Graphics; -import java.awt.Point; -import java.awt.event.MouseEvent; -import java.awt.event.MouseListener; -import java.util.Observable; -import java.util.Observer; -import java.util.Vector; - -import javax.swing.JSpinner; -import javax.swing.SpinnerNumberModel; -import javax.swing.event.ChangeEvent; -import javax.swing.event.ChangeListener; - -import se.sics.cooja.ClassDescription; -import se.sics.cooja.GUI; -import se.sics.cooja.Mote; -import se.sics.cooja.PluginType; -import se.sics.cooja.RadioConnection; -import se.sics.cooja.Simulation; -import se.sics.cooja.contikimote.interfaces.ContikiRadio; -import se.sics.cooja.interfaces.Position; -import se.sics.cooja.interfaces.Radio; -import se.sics.cooja.plugins.Visualizer2D; -import se.sics.cooja.radiomediums.UDGM; - -/** - * Visualizes radio traffic in the UDGM radio medium. - * Allows a user to change the collective TX/interference ranges, - * and the TX/RX success ratio. - * - * Sending motes are blue, receiving motes are green and motes that hear noise - * are painted red. Motes without radios are painted gray, and the rest are - * white. - * - * @author Fredrik Osterlind - */ -@ClassDescription("UDGM Visualizer") -@PluginType(PluginType.SIM_PLUGIN) -public class VisUDGM extends Visualizer2D { - private JSpinner txRangeSpinner = null; - private JSpinner interferenceRangeSpinner = null; - private JSpinner successRatioTxSpinner = null; - private JSpinner successRatioRxSpinner = null; - - private UDGM radioMedium = null; - private Observer radioMediumObserver; - - private Mote selectedMote = null; - - private class RangeMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - return true; - } - - public String getDescription(Mote mote) { - return "Change transmission ranges"; - } - - public void doAction(Mote mote) { - txRangeSpinner.setVisible(true); - interferenceRangeSpinner.setVisible(true); - repaint(); - } - }; - - private class SuccessRatioMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - return true; - } - - public String getDescription(Mote mote) { - return "Change transmission success ratio"; - } - - public void doAction(Mote mote) { - successRatioTxSpinner.setVisible(true); - successRatioRxSpinner.setVisible(true); - repaint(); - } - }; - - public VisUDGM(Simulation sim, GUI gui) { - super(sim, gui); - setTitle("UDGM Visualizer"); - - radioMedium = (UDGM) sim.getRadioMedium(); - - // Create spinners for changing ranges - SpinnerNumberModel transmissionModel = new SpinnerNumberModel(); - transmissionModel.setValue(new Double(radioMedium.TRANSMITTING_RANGE)); - transmissionModel.setStepSize(new Double(1.0)); // 1m - transmissionModel.setMinimum(new Double(0.0)); - - SpinnerNumberModel interferenceModel = new SpinnerNumberModel(); - interferenceModel.setValue(new Double(radioMedium.INTERFERENCE_RANGE)); - interferenceModel.setStepSize(new Double(1.0)); // 1m - interferenceModel.setMinimum(new Double(0.0)); - - SpinnerNumberModel successRatioTxModel = new SpinnerNumberModel(); - successRatioTxModel.setValue(new Double(radioMedium.SUCCESS_RATIO_TX)); - successRatioTxModel.setStepSize(new Double(0.001)); // 0.1% - successRatioTxModel.setMinimum(new Double(0.0)); - successRatioTxModel.setMaximum(new Double(1.0)); - - SpinnerNumberModel successRatioRxModel = new SpinnerNumberModel(); - successRatioRxModel.setValue(new Double(radioMedium.SUCCESS_RATIO_RX)); - successRatioRxModel.setStepSize(new Double(0.001)); // 0.1% - successRatioRxModel.setMinimum(new Double(0.0)); - successRatioRxModel.setMaximum(new Double(1.0)); - - JSpinner.NumberEditor editor; - txRangeSpinner = new JSpinner(transmissionModel); - editor = new JSpinner.NumberEditor(txRangeSpinner, "0m"); - txRangeSpinner.setEditor(editor); - interferenceRangeSpinner = new JSpinner(interferenceModel); - editor = new JSpinner.NumberEditor(interferenceRangeSpinner, "0m"); - interferenceRangeSpinner.setEditor(editor); - successRatioTxSpinner = new JSpinner(successRatioTxModel); - editor = new JSpinner.NumberEditor(successRatioTxSpinner, "0.0%"); - successRatioTxSpinner.setEditor(editor); - successRatioRxSpinner = new JSpinner(successRatioRxModel); - editor = new JSpinner.NumberEditor(successRatioRxSpinner, "0.0%"); - successRatioRxSpinner.setEditor(editor); - - - ((JSpinner.DefaultEditor) txRangeSpinner.getEditor()).getTextField().setColumns(5); - ((JSpinner.DefaultEditor) interferenceRangeSpinner.getEditor()).getTextField().setColumns(5); - ((JSpinner.DefaultEditor) successRatioTxSpinner.getEditor()).getTextField().setColumns(5); - ((JSpinner.DefaultEditor) successRatioRxSpinner.getEditor()).getTextField().setColumns(5); - txRangeSpinner.setToolTipText("Transmitting range (m)"); - interferenceRangeSpinner.setToolTipText("Interference range (m)"); - successRatioTxSpinner.setToolTipText("Transmission success ratio (%)"); - successRatioRxSpinner.setToolTipText("Reception success ratio (%)"); - - txRangeSpinner.addChangeListener(new ChangeListener() { - public void stateChanged(ChangeEvent e) { - radioMedium.TRANSMITTING_RANGE = ((SpinnerNumberModel) - txRangeSpinner.getModel()).getNumber().doubleValue(); - repaint(); - } - }); - - interferenceRangeSpinner.addChangeListener(new ChangeListener() { - public void stateChanged(ChangeEvent e) { - radioMedium.INTERFERENCE_RANGE = ((SpinnerNumberModel) - interferenceRangeSpinner.getModel()).getNumber().doubleValue(); - repaint(); - } - }); - - successRatioTxSpinner.addChangeListener(new ChangeListener() { - public void stateChanged(ChangeEvent e) { - radioMedium.SUCCESS_RATIO_TX = ((SpinnerNumberModel) - successRatioTxSpinner.getModel()).getNumber().doubleValue(); - repaint(); - } - }); - - successRatioRxSpinner.addChangeListener(new ChangeListener() { - public void stateChanged(ChangeEvent e) { - radioMedium.SUCCESS_RATIO_RX = ((SpinnerNumberModel) - successRatioRxSpinner.getModel()).getNumber().doubleValue(); - repaint(); - } - }); - - getCurrentCanvas().add(txRangeSpinner); - getCurrentCanvas().add(interferenceRangeSpinner); - getCurrentCanvas().add(successRatioTxSpinner); - getCurrentCanvas().add(successRatioRxSpinner); - - txRangeSpinner.setVisible(false); - interferenceRangeSpinner.setVisible(false); - successRatioTxSpinner.setVisible(false); - successRatioRxSpinner.setVisible(false); - - /* Enable user to select mote by mouse click */ - getCurrentCanvas().addMouseListener(new MouseListener() { - public void mouseExited(MouseEvent e) { } - public void mouseEntered(MouseEvent e) { } - public void mouseReleased(MouseEvent e) { } - public void mouseClicked(MouseEvent e) { } - - public void mousePressed(MouseEvent e) { - Vector clickedMotes = findMotesAtPosition(e.getX(), e.getY()); - if (clickedMotes == null || clickedMotes.size() == 0) { - selectedMote = null; - txRangeSpinner.setVisible(false); - interferenceRangeSpinner.setVisible(false); - successRatioTxSpinner.setVisible(false); - successRatioRxSpinner.setVisible(false); - repaint(); - return; - } - - /* Several motes may have been clicked: select another one */ - if (clickedMotes.contains(selectedMote)) { - int pos = clickedMotes.indexOf(selectedMote); - if (pos < clickedMotes.size() - 1) { - selectedMote = clickedMotes.get(pos + 1); - } else { - selectedMote = clickedMotes.firstElement(); - } - } else { - selectedMote = clickedMotes.firstElement(); - } - repaint(); - } - }); - - // Register change ranges and change success ratio action - addMoteMenuAction(new RangeMenuAction()); - addMoteMenuAction(new SuccessRatioMenuAction()); - - // Observe radio medium - radioMedium.addRadioMediumObserver(radioMediumObserver = new Observer() { - public void update(Observable obs, Object obj) { - getCurrentCanvas().repaint(); - } - }); - } - - public void closePlugin() { - super.closePlugin(); - radioMedium.deleteRadioMediumObserver(radioMediumObserver); - } - - public Color[] getColorOf(Mote mote) { - Radio moteRadio = mote.getInterfaces().getRadio(); - if (moteRadio == null) { - return new Color[] { Color.BLACK }; - } - - if (mote.getState() == Mote.State.DEAD) { - return new Color[] { Color.BLACK }; - } - - if (selectedMote != null && mote == selectedMote) { - return new Color[] { Color.CYAN }; - } - - if (moteRadio instanceof ContikiRadio && !((ContikiRadio) moteRadio).isOn()) { - return new Color[] { Color.GRAY }; - } - - if (moteRadio.isTransmitting()) { - return new Color[] { Color.BLUE }; - } - - if (moteRadio.isInterfered()) { - return new Color[] { Color.RED }; - } - - if (moteRadio.isReceiving()) { - return new Color[] { Color.GREEN }; - } - - return new Color[] { Color.WHITE }; - } - - public void visualizeSimulation(Graphics g) { - - /* Paint transmission and interference range for select mote */ - if (selectedMote != null) { - Position motePos = selectedMote.getInterfaces().getPosition(); - - Point pixelCoord = transformPositionToPixel(motePos); - int x = pixelCoord.x; - int y = pixelCoord.y; - - // Fetch current output power indicator (scale with as percent) - if (selectedMote.getInterfaces().getRadio() != null) { - Radio selectedRadio = selectedMote.getInterfaces().getRadio(); - double moteInterferenceRange = - radioMedium.INTERFERENCE_RANGE - * ((double) selectedRadio.getCurrentOutputPowerIndicator() - / (double) selectedRadio.getOutputPowerIndicatorMax()); - double moteTransmissionRange = - radioMedium.TRANSMITTING_RANGE - * ((double) selectedRadio.getCurrentOutputPowerIndicator() - / (double) selectedRadio.getOutputPowerIndicatorMax()); - - Point translatedZero = transformPositionToPixel(0.0, 0.0, 0.0); - Point translatedInterference = transformPositionToPixel(moteInterferenceRange, moteInterferenceRange, 0.0); - Point translatedTransmission = transformPositionToPixel(moteTransmissionRange, moteTransmissionRange, 0.0); - - translatedInterference.x = Math.abs(translatedInterference.x - translatedZero.x); - translatedInterference.y = Math.abs(translatedInterference.y - translatedZero.y); - translatedTransmission.x = Math.abs(translatedTransmission.x - translatedZero.x); - translatedTransmission.y = Math.abs(translatedTransmission.y - translatedZero.y); - - // Interference - g.setColor(Color.DARK_GRAY); - g.fillOval( - x - translatedInterference.x, - y - translatedInterference.y, - 2 * translatedInterference.x, - 2 * translatedInterference.y); - - // Transmission - g.setColor(Color.GREEN); - g.fillOval( - x - translatedTransmission.x, - y - translatedTransmission.y, - 2 * translatedTransmission.x, - 2 * translatedTransmission.y); - } - } - - // Let parent paint motes - super.visualizeSimulation(g); - - /* Paint active connections in black */ - RadioConnection[] conns = radioMedium.getActiveConnections(); - if (conns != null) { - g.setColor(Color.BLACK); - for (RadioConnection conn : conns) { - Point sourcePoint = transformPositionToPixel(conn.getSource().getPosition()); - for (Radio destRadio : conn.getDestinations()) { - Position destPos = destRadio.getPosition(); - Point destPoint = transformPositionToPixel(destPos); - g.drawLine(sourcePoint.x, sourcePoint.y, destPoint.x, destPoint.y); - } - } - } - - /* Paint past connections in gray */ - conns = radioMedium.getLastTickConnections(); - if (conns != null) { - g.setColor(Color.GRAY); - for (RadioConnection conn : conns) { - Point sourcePoint = transformPositionToPixel(conn.getSource().getPosition()); - for (Radio dest : conn.getDestinations()) { - Position destPos = dest.getPosition(); - Point destPoint = transformPositionToPixel(destPos); - g.drawLine(sourcePoint.x, sourcePoint.y, destPoint.x, destPoint.y); - } - } - } - - } -} diff --git a/tools/cooja/java/se/sics/cooja/plugins/Visualizer2D.java b/tools/cooja/java/se/sics/cooja/plugins/Visualizer2D.java deleted file mode 100644 index 88c2c7a42..000000000 --- a/tools/cooja/java/se/sics/cooja/plugins/Visualizer2D.java +++ /dev/null @@ -1,879 +0,0 @@ -/* - * Copyright (c) 2006, Swedish Institute of Computer Science. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the Institute nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $Id: Visualizer2D.java,v 1.16 2009/02/26 13:29:30 fros4943 Exp $ - */ - -package se.sics.cooja.plugins; - -import java.awt.*; -import java.awt.datatransfer.DataFlavor; -import java.awt.datatransfer.Transferable; -import java.awt.datatransfer.UnsupportedFlavorException; -import java.awt.dnd.DnDConstants; -import java.awt.dnd.DropTarget; -import java.awt.dnd.DropTargetDragEvent; -import java.awt.dnd.DropTargetDropEvent; -import java.awt.dnd.DropTargetEvent; -import java.awt.dnd.DropTargetListener; -import java.awt.event.*; -import java.io.File; -import java.io.IOException; -import java.util.*; -import java.util.List; - -import javax.swing.*; -import javax.swing.Timer; - -import org.apache.log4j.Logger; - -import se.sics.cooja.*; -import se.sics.cooja.GUI.MoteRelation; -import se.sics.cooja.interfaces.*; - -/** - * Visualizer2D is an abstract mote visualizer for simulations. All motes are - * painted in the XY-plane, as seen from positive Z axis. - * - * An implementation of this class must colorize the different motes, each mote - * has two different colors; inner and outer. - * - * By right-clicking the mouse on a mote a popup menu will be displayed. From - * this menu mote plugins can be started. or the mote can be moved. Each - * implementation may also register its own actions to be accessed from this - * menu. - * - * A Visualizer2D observers both the simulation and all mote positions. - * - * @author Fredrik Osterlind - */ -@ClassDescription("2D Mote Visualizer") -@PluginType(PluginType.SIM_PLUGIN) -public abstract class Visualizer2D extends VisPlugin { - private static final long serialVersionUID = 1L; - private static Logger logger = Logger.getLogger(Visualizer2D.class); - - private double factorXCoordToPixel; - private double factorYCoordToPixel; - private double smallestXCoord; - private double smallestYCoord; - - private GUI myGUI = null; - private Simulation simulation = null; - private final JPanel canvas; - private Visualizer2D myPlugin; - - private static final int CANVAS_BORDER_WIDTH = 25; - private static final int MOTE_RADIUS = 8; - - private boolean moteIsBeingMoved = false; - private long moteMoveBeginTime = -1; - private Mote moteToMove = null; - private Cursor moveCursor = new Cursor(Cursor.MOVE_CURSOR); - - private Observer simObserver = null; // Watches simulation changes - private Observer posObserver = null; // Watches position changes - - private Observer moteHighligtObserver = null; - private Observer moteRelationsObserver = null; - private Mote highlightedMote = null; - private Color highlightColor = Color.GRAY; - private Timer highlightTimer = null; - - public interface MoteMenuAction { - public boolean isEnabled(Mote mote); - public String getDescription(Mote mote); - public void doAction(Mote mote); - } - - private class MoveMoteMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - return true; - } - public String getDescription(Mote mote) { - return "Move " + mote; - } - public void doAction(Mote mote) { - moteMoveBeginTime = -1; - beginMoveRequest(mote); - } - }; - - private class ButtonClickMoteMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - return mote.getInterfaces().getButton() != null - && !mote.getInterfaces().getButton().isPressed(); - } - public String getDescription(Mote mote) { - return "Click button on " + mote; - } - public void doAction(Mote mote) { - mote.getInterfaces().getButton().clickButton(); - } - }; - - private class DeleteMoteMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - return true; - } - public String getDescription(Mote mote) { - return "Delete " + mote; - } - public void doAction(Mote mote) { - simulation.removeMote(mote); - } - }; - - private class ShowLEDMoteMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - return mote.getInterfaces().getLED() != null; - } - public String getDescription(Mote mote) { - return "Show LEDs on " + mote; - } - public void doAction(Mote mote) { - LED led = mote.getInterfaces().getLED(); - if (led == null) { - return; - } - - /* Extract description (input to plugin) */ - String desc = GUI.getDescriptionOf(mote.getInterfaces().getLED()); - - MoteInterfaceViewer viewer = - (MoteInterfaceViewer) simulation.getGUI().startPlugin( - MoteInterfaceViewer.class, - simulation.getGUI(), - simulation, - mote); - viewer.setSelectedInterface(desc); - viewer.pack(); - } - }; - - private class ShowSerialMoteMenuAction implements MoteMenuAction { - public boolean isEnabled(Mote mote) { - SerialPort serialPort = null; - for (MoteInterface intf: mote.getInterfaces().getInterfaces()) { - try { - /* Try casting to serial port */ - serialPort = (SerialPort) intf; - return true; - } catch (Exception e) { - } - } - return false; - } - public String getDescription(Mote mote) { - return "Show serial port on " + mote; - } - public void doAction(Mote mote) { - SerialPort serialPort = null; - for (MoteInterface intf: mote.getInterfaces().getInterfaces()) { - try { - /* Try casting to serial port */ - serialPort = (SerialPort) intf; - break; - } catch (Exception e) { - } - } - - if (serialPort == null) { - return; - } - - /* Extract description (input to plugin) */ - String desc = GUI.getDescriptionOf(serialPort); - - MoteInterfaceViewer viewer = - (MoteInterfaceViewer) simulation.getGUI().startPlugin( - MoteInterfaceViewer.class, - simulation.getGUI(), - simulation, - mote); - viewer.setSelectedInterface(desc); - viewer.pack(); - } - }; - - private Vector menuActions = new Vector(); - - /** - * Registers as an simulation observer and initializes the canvas. - * - * @param simulationToVisualize - * Simulation to visualize - */ - public Visualizer2D(Simulation simulationToVisualize, GUI gui) { - super("Visualizer2D", gui); - - myGUI = gui; - myPlugin = this; - - // Set initial bounds of frame - this.setBounds(150, 150, 300, 300); - setVisible(true); - - simulation = simulationToVisualize; - - // Create "canvas" to paint on - canvas = new JPanel() { - private static final long serialVersionUID = 1L; - public void paintComponent(Graphics g) { - super.paintComponent(g); - visualizeSimulation(g); - } - }; - canvas.setPreferredSize(new Dimension(getSize().width - 16, - getSize().height - 38)); - canvas.setBorder(BorderFactory.createLineBorder(Color.GREEN, 2)); - canvas.setBackground(Color.WHITE); - calculateTransformations(); - - this.setContentPane(canvas); - - // Detect general simulation changes - posObserver = new Observer() { - public void update(Observable obs, Object obj) { - calculateTransformations(); - canvas.repaint(); - } - }; - simulation.addObserver(simObserver = new Observer() { - public void update(Observable obs, Object obj) { - canvas.setPreferredSize(new Dimension(getSize().width - 16, - getSize().height - 38)); - - // Register (or reregister) as observer on all mote positions - for (int i = 0; i < simulation.getMotesCount(); i++) { - Position posIntf = simulation.getMote(i).getInterfaces() - .getPosition(); - if (posIntf != null) { - posIntf.addObserver(posObserver); - } - } - - calculateTransformations(); - canvas.repaint(); - } - }); - simObserver.update(null, null); - - // Detect mote highligts - myGUI.addMoteHighlightObserver(moteHighligtObserver = new Observer() { - public void update(Observable obs, Object obj) { - if (!(obj instanceof Mote)) { - return; - } - - if (highlightTimer != null && highlightTimer.isRunning()) { - highlightTimer.stop(); - } - - highlightTimer = new Timer(100, null); - highlightedMote = (Mote) obj; - highlightTimer.addActionListener(new ActionListener() { - public void actionPerformed(ActionEvent e) { - // Decrease delay - if (highlightTimer.getDelay() < 90) { - highlightTimer.stop(); - highlightedMote = null; - repaint(); - return; - } - - // Toggle color - if (highlightColor == Color.GRAY) { - highlightColor = Color.CYAN; - } else { - highlightColor = Color.GRAY; - } - highlightTimer.setDelay(highlightTimer.getDelay()-1); - repaint(); - } - }); - highlightTimer.start(); - } - }); - - /* Paint mote relations */ - myGUI.addMoteRelationsObserver(moteRelationsObserver = new Observer() { - public void update(Observable obs, Object obj) { - repaint(); - } - }); - - canvas.addMouseMotionListener(new MouseMotionListener() { - public void mouseMoved(MouseEvent e) { - myPlugin.handleMoveRequest(e.getPoint().x, e.getPoint().y, false); - } - public void mouseDragged(MouseEvent e) { - myPlugin.handleMoveRequest(e.getPoint().x, e.getPoint().y, false); - } - }); - - // Detect mouse events - canvas.addMouseListener(new MouseListener() { - public void mousePressed(MouseEvent e) { - if (e.isPopupTrigger()) { - myPlugin.handlePopupRequest(e.getPoint().x, e.getPoint().y); - } else if (SwingUtilities.isLeftMouseButton(e)){ - //myPlugin.handleMoveRequest(e.getPoint().x, e.getPoint().y, false); - beginMoveRequest(e.getPoint().x, e.getPoint().y); - } - } - public void mouseReleased(MouseEvent e) { - if (e.isPopupTrigger()) { - myPlugin.handlePopupRequest(e.getPoint().x, e.getPoint().y); - } else { - myPlugin.handleMoveRequest(e.getPoint().x, e.getPoint().y, true); - } - } - public void mouseEntered(MouseEvent e) { - if (e.isPopupTrigger()) { - myPlugin.handlePopupRequest(e.getPoint().x, e.getPoint().y); - } - } - public void mouseExited(MouseEvent e) { - if (e.isPopupTrigger()) { - myPlugin.handlePopupRequest(e.getPoint().x, e.getPoint().y); - } - } - public void mouseClicked(MouseEvent e) { - if (e.isPopupTrigger()) { - myPlugin.handlePopupRequest(e.getPoint().x, e.getPoint().y); - } - } - }); - - // Detect component events - addComponentListener(new ComponentListener() { - public void componentMoved(ComponentEvent ce) { - // NOP - } - public void componentShown(ComponentEvent ce) { - // NOP - } - public void componentHidden(ComponentEvent ce) { - // NOP - } - public void componentResized(ComponentEvent ce) { - canvas.setPreferredSize(new Dimension(getSize().width - 16, - getSize().height - 38)); - calculateTransformations(); - canvas.repaint(); - } - }); - - // Add menu action for moving motes - addMoteMenuAction(new MoveMoteMenuAction()); - - /* Add some commonly used mote interface actions */ - addMoteMenuAction(new ButtonClickMoteMenuAction()); - addMoteMenuAction(new ShowLEDMoteMenuAction()); - addMoteMenuAction(new ShowSerialMoteMenuAction()); - - // Add menu action for deleting mote - addMoteMenuAction(new DeleteMoteMenuAction()); - - try { - setSelected(true); - } catch (java.beans.PropertyVetoException e) { - // Could not select - } - - /* Drag and drop files to motes */ - DropTargetListener dTargetListener = new DropTargetListener() { - public void dragEnter(DropTargetDragEvent dtde) { - if (acceptOrRejectDrag(dtde)) { - dtde.acceptDrag(DnDConstants.ACTION_COPY_OR_MOVE); - } else { - dtde.rejectDrag(); - } - } - public void dragExit(DropTargetEvent dte) { - } - public void dropActionChanged(DropTargetDragEvent dtde) { - if (acceptOrRejectDrag(dtde)) { - dtde.acceptDrag(DnDConstants.ACTION_COPY_OR_MOVE); - } else { - dtde.rejectDrag(); - } - } - public void dragOver(DropTargetDragEvent dtde) { - if (acceptOrRejectDrag(dtde)) { - dtde.acceptDrag(DnDConstants.ACTION_COPY_OR_MOVE); - } else { - dtde.rejectDrag(); - } - } - public void drop(DropTargetDropEvent dtde) { - Transferable transferable = dtde.getTransferable(); - - /* Only accept single files */ - File file = null; - if (!transferable.isDataFlavorSupported(DataFlavor.javaFileListFlavor)) { - dtde.rejectDrop(); - return; - } - - dtde.acceptDrop(DnDConstants.ACTION_COPY_OR_MOVE); - - try { - List transferList = Arrays.asList( - transferable.getTransferData(DataFlavor.javaFileListFlavor) - ); - if (transferList.size() != 1) { - return; - } - List list = (List) transferList.get(0); - if (list.size() != 1) { - return; - } - file = list.get(0); - } - catch (Exception e) { - return; - } - - if (file == null || !file.exists()) { - return; - } - - handleDropFile(file, dtde.getLocation()); - } - private boolean acceptOrRejectDrag(DropTargetDragEvent dtde) { - Transferable transferable = dtde.getTransferable(); - - /* Make sure one, and only one, mote exists under mouse pointer */ - Point point = dtde.getLocation(); - Vector motes = findMotesAtPosition(point.x, point.y); - if (motes == null || motes.size() != 1) { - return false; - } - - /* Only accept single files */ - File file; - if (!transferable.isDataFlavorSupported(DataFlavor.javaFileListFlavor)) { - return false; - } - try { - List transferList = Arrays.asList( - transferable.getTransferData(DataFlavor.javaFileListFlavor) - ); - if (transferList.size() != 1) { - return false; - } - List list = (List) transferList.get(0); - if (list.size() != 1) { - return false; - } - file = list.get(0); - } catch (UnsupportedFlavorException e) { - return false; - } catch (IOException e) { - return false; - } - - /* Extract file extension */ - return isDropFileAccepted(file); - } - }; - canvas.setDropTarget( - new DropTarget(canvas, DnDConstants.ACTION_COPY_OR_MOVE, dTargetListener, true, null) - ); - } - - /** - * Add new mote menu action. - * - * @see MoteMenuAction - * @param menuAction Menu action - */ - public void addMoteMenuAction(MoteMenuAction menuAction) { - menuActions.add(menuAction); - } - - private void handlePopupRequest(final int x, final int y) { - final Vector foundMotes = findMotesAtPosition(x, y); - if (foundMotes == null || foundMotes.size() == 0) { - return; - } - - JPopupMenu pickMoteMenu = new JPopupMenu(); - pickMoteMenu.add(new JLabel("Select action:")); - pickMoteMenu.add(new JSeparator()); - - // Add 'show mote plugins'-actions - for (final Mote mote : foundMotes) { - pickMoteMenu.add(simulation.getGUI().createMotePluginsSubmenu(mote)); - } - - // Add the rest of the actions - for (final MoteMenuAction menuAction : menuActions) { - for (final Mote mote : foundMotes) { - if (menuAction.isEnabled(mote)) { - JMenuItem menuItem = new JMenuItem(menuAction.getDescription(mote)); - menuItem.addActionListener(new ActionListener() { - public void actionPerformed(ActionEvent e) { - menuAction.doAction(mote); - } - }); - pickMoteMenu.add(menuItem); - } - } - } - - // Show menu - Point pos = new Point(canvas.getLocationOnScreen().x + x, canvas - .getLocationOnScreen().y - + y); - pickMoteMenu.setLocation(pos.x, pos.y); - pickMoteMenu.setInvoker(canvas); - pickMoteMenu.setVisible(true); - } - - private void beginMoveRequest(final int x, final int y) { - final Vector foundMotes = findMotesAtPosition(x, y); - if (foundMotes == null || foundMotes.size() == 0) { - return; - } - - moteMoveBeginTime = System.currentTimeMillis(); - beginMoveRequest(foundMotes.get(0)); - } - - private void beginMoveRequest(Mote moteToMove) { - moteIsBeingMoved = true; - this.moteToMove = moteToMove; - canvas.repaint(); - } - - private void handleMoveRequest(final int x, final int y, - boolean wasJustReleased) { - - if (!moteIsBeingMoved) { - return; - } - - if (!wasJustReleased) { - // Still moving mote - canvas.setCursor(moveCursor); - return; - } - - // Stopped moving mote - canvas.setCursor(Cursor.getDefaultCursor()); - moteIsBeingMoved = false; - - Position newXYValues = transformPixelToPositon(new Point(x, y)); - - if (moteMoveBeginTime <= 0 || System.currentTimeMillis() - moteMoveBeginTime > 300) { - int returnValue = JOptionPane.showConfirmDialog(myPlugin, "Move mote to" - + "\nX=" + newXYValues.getXCoordinate() + "\nY=" - + newXYValues.getYCoordinate() + "\nZ=" - + moteToMove.getInterfaces().getPosition().getZCoordinate()); - - if (returnValue == JOptionPane.OK_OPTION) { - moteToMove.getInterfaces().getPosition().setCoordinates( - newXYValues.getXCoordinate(), newXYValues.getYCoordinate(), - moteToMove.getInterfaces().getPosition().getZCoordinate()); - } - } - moteMoveBeginTime = -1; - moteToMove = null; - repaint(); - } - - /** - * Returns all motes at given position. - * - * @param clickedX - * X coordinate - * @param clickedY - * Y coordinate - * @return All motes at given position - */ - protected Vector findMotesAtPosition(int clickedX, int clickedY) { - double xCoord = factorXPixelToCoord(clickedX); - double yCoord = factorYPixelToCoord(clickedY); - - Vector motesFound = new Vector(); - - // Calculate painted mote radius in coordinates - double paintedMoteWidth = factorXPixelToCoord(MOTE_RADIUS) - - factorXPixelToCoord(0); - double paintedMoteHeight = factorYPixelToCoord(MOTE_RADIUS) - - factorYPixelToCoord(0); - - for (int i = 0; i < simulation.getMotesCount(); i++) { - Position pos = simulation.getMote(i).getInterfaces().getPosition(); - - // Transform to unit circle before checking if mouse hit this mote - double distanceX = Math.abs(xCoord - pos.getXCoordinate()) - / paintedMoteWidth; - double distanceY = Math.abs(yCoord - pos.getYCoordinate()) - / paintedMoteHeight; - - if (distanceX * distanceX + distanceY * distanceY <= 1) { - motesFound.add(simulation.getMote(i)); - } - } - if (motesFound.size() == 0) { - return null; - } - - return motesFound; - } - - /** - * Get colors a certain mote should be painted with. May be overridden to get - * a different color scheme. - * - * Normally this method returns an array of two colors, one for the state - * (outer circle), the other for the type (inner circle). - * - * If this method only returns one color, the entire mote will be painted - * using that. - * - * @param mote - * Mote to paint - * @return Color[] { Inner color, Outer color } - */ - abstract public Color[] getColorOf(Mote mote); - - protected void visualizeSimulation(Graphics g) { - Mote[] allMotes = simulation.getMotes(); - for (Mote mote: allMotes) { - Color moteColors[] = getColorOf(mote); - Position motePos = mote.getInterfaces().getPosition(); - - Point pixelCoord = transformPositionToPixel(motePos); - int x = pixelCoord.x; - int y = pixelCoord.y; - - if (mote == highlightedMote) { - g.setColor(highlightColor); - g.fillOval(x - MOTE_RADIUS, y - MOTE_RADIUS, 2 * MOTE_RADIUS, - 2 * MOTE_RADIUS); - } else if (mote == moteToMove) { - // Don't fill mote - } else if (moteColors.length >= 2) { - g.setColor(moteColors[0]); - g.fillOval(x - MOTE_RADIUS, y - MOTE_RADIUS, 2 * MOTE_RADIUS, - 2 * MOTE_RADIUS); - - g.setColor(moteColors[1]); - g.fillOval(x - MOTE_RADIUS / 2, y - MOTE_RADIUS / 2, MOTE_RADIUS, - MOTE_RADIUS); - - } else if (moteColors.length >= 1) { - g.setColor(moteColors[0]); - g.fillOval(x - MOTE_RADIUS, y - MOTE_RADIUS, 2 * MOTE_RADIUS, - 2 * MOTE_RADIUS); - } - - g.setColor(Color.BLACK); - g.drawOval(x - MOTE_RADIUS, y - MOTE_RADIUS, 2 * MOTE_RADIUS, - 2 * MOTE_RADIUS); - } - - /* Paint mote relations */ - MoteRelation[] relations = simulation.getGUI().getMoteRelations(); - for (MoteRelation r: relations) { - Position sourcePos = r.source.getInterfaces().getPosition(); - Position destPos = r.dest.getInterfaces().getPosition(); - - Point sourcePoint = transformPositionToPixel(sourcePos); - Point destPoint = transformPositionToPixel(destPos); - - Point middlePoint = new Point( - (destPoint.x*9 + sourcePoint.x*1)/10, - (destPoint.y*9 + sourcePoint.y*1)/10 - ); - - /* "Arrow body" is painted gray */ - g.setColor(Color.LIGHT_GRAY); - g.drawLine(sourcePoint.x, sourcePoint.y, middlePoint.x, middlePoint.y); - - /* "Arrow head" is painted black */ - g.setColor(Color.BLACK); - g.drawLine(middlePoint.x, middlePoint.y, destPoint.x, destPoint.y); - } - } - - /** - * Recalculate size of canvas and factors for transforming between real and - * pixel coordinates. This method is called every time this frame is resized - * or created. - */ - protected void calculateTransformations() { - if (simulation.getMotesCount() == 0) { - smallestXCoord = 0; - smallestYCoord = 0; - factorXCoordToPixel = 1; - factorYCoordToPixel = 1; - return; - } - - double biggestXCoord, biggestYCoord; - - Position motePos = simulation.getMote(0).getInterfaces().getPosition(); - smallestXCoord = biggestXCoord = motePos.getXCoordinate(); - smallestYCoord = biggestYCoord = motePos.getYCoordinate(); - - // Get extreme coordinates - for (int i = 0; i < simulation.getMotesCount(); i++) { - motePos = simulation.getMote(i).getInterfaces().getPosition(); - - if (motePos.getXCoordinate() < smallestXCoord) { - smallestXCoord = motePos.getXCoordinate(); - } - - if (motePos.getXCoordinate() > biggestXCoord) { - biggestXCoord = motePos.getXCoordinate(); - } - - if (motePos.getYCoordinate() < smallestYCoord) { - smallestYCoord = motePos.getYCoordinate(); - } - - if (motePos.getYCoordinate() > biggestYCoord) { - biggestYCoord = motePos.getYCoordinate(); - } - - } - - if ((biggestXCoord - smallestXCoord) == 0) { - factorXCoordToPixel = 1; - } else { - factorXCoordToPixel = ((double) canvas.getPreferredSize().width - 2 * CANVAS_BORDER_WIDTH) - / (biggestXCoord - smallestXCoord); - } - - if ((biggestYCoord - smallestYCoord) == 0) { - factorYCoordToPixel = 1; - } else { - factorYCoordToPixel = ((double) canvas.getPreferredSize().height - 2 * CANVAS_BORDER_WIDTH) - / (biggestYCoord - smallestYCoord); - } - } - - /** - * Transforms a real-world position to a pixel which can be painted onto the - * current sized canvas. - * - * @param pos - * Real-world position - * @return Pixel coordinates - */ - public Point transformPositionToPixel(Position pos) { - return new Point(factorXCoordToPixel(pos.getXCoordinate()), - factorYCoordToPixel(pos.getYCoordinate())); - } - - /** - * Transforms real-world coordinates to a pixel which can be painted onto the - * current sized canvas. - * - * @param x Real world X - * @param y Real world Y - * @param z Real world Z (ignored) - * @return Pixel coordinates - */ - public Point transformPositionToPixel(double x, double y, double z) { - return new Point(factorXCoordToPixel(x), factorYCoordToPixel(y)); - } - - /** - * Transforms a pixel coordinate to a real-world. Z-value will always be 0. - * - * @param pixelPos - * On-screen pixel coordinate - * @return Real world coordinate (z=0). - */ - public Position transformPixelToPositon(Point pixelPos) { - Position dummyPosition = new Position(null); - dummyPosition.setCoordinates(factorXPixelToCoord(pixelPos.x), - factorYPixelToCoord(pixelPos.y), 0.0); - return dummyPosition; - } - - /** - * @return The current canvas to paint on - */ - public JPanel getCurrentCanvas() { - return canvas; - } - - private int factorXCoordToPixel(double xCoordinate) { - return (int) ((xCoordinate - smallestXCoord) * factorXCoordToPixel + CANVAS_BORDER_WIDTH); - } - private int factorYCoordToPixel(double yCoordinate) { - return (int) ((yCoordinate - smallestYCoord) * factorYCoordToPixel) - + CANVAS_BORDER_WIDTH; - } - private double factorXPixelToCoord(int xPixel) { - return ((xPixel - CANVAS_BORDER_WIDTH) / factorXCoordToPixel) - + smallestXCoord; - } - private double factorYPixelToCoord(int yPixel) { - return ((yPixel - CANVAS_BORDER_WIDTH) / factorYCoordToPixel) - + smallestYCoord; - } - - public void closePlugin() { - if (moteHighligtObserver != null) { - myGUI.deleteMoteHighlightObserver(moteHighligtObserver); - } - if (moteRelationsObserver != null) { - myGUI.deleteMoteRelationsObserver(moteRelationsObserver); - } - - if (simObserver != null) { - simulation.deleteObserver(simObserver); - - for (int i = 0; i < simulation.getMotesCount(); i++) { - Position posIntf = simulation.getMote(i).getInterfaces().getPosition(); - if (posIntf != null) { - posIntf.deleteObserver(posObserver); - } - } - } - } - - protected boolean isDropFileAccepted(File file) { - return true; /* TODO */ - } - - protected void handleDropFile(File file, Point point) { - logger.fatal("Drag and drop not implemented: " + file); - } - - -}