X-Git-Url: https://mograsim.net/gitweb/?a=blobdiff_plain;f=net.mograsim.logic.model%2Fsrc%2Fnet%2Fmograsim%2Flogic%2Fmodel%2Fmodel%2Fwires%2FGUIWire.java;h=7146d63166189dca4348eb7d9208b23efa2c69d3;hb=657f9c901e20c7b2efe53e0daa4b56c8082854b9;hp=d9b7cb9102496c70a534e1cab1141e000bda4846;hpb=c5c0d07286a29994a11ba8b01eaffb21964b6c1b;p=Mograsim.git diff --git a/net.mograsim.logic.model/src/net/mograsim/logic/model/model/wires/GUIWire.java b/net.mograsim.logic.model/src/net/mograsim/logic/model/model/wires/GUIWire.java index d9b7cb91..7146d631 100644 --- a/net.mograsim.logic.model/src/net/mograsim/logic/model/model/wires/GUIWire.java +++ b/net.mograsim.logic.model/src/net/mograsim/logic/model/model/wires/GUIWire.java @@ -2,9 +2,8 @@ package net.mograsim.logic.model.model.wires; import java.util.ArrayList; import java.util.Arrays; -import java.util.HashSet; import java.util.List; -import java.util.Set; +import java.util.function.Consumer; import org.eclipse.swt.SWT; @@ -59,8 +58,7 @@ public class GUIWire private double[] effectivePath; private final List redrawListeners; - - private final Set pathChangedListeners; + private final List> pathChangedListeners; /** * A LogicObserver calling redrawListeners. Used for logic model bindings. @@ -150,8 +148,6 @@ public class GUIWire */ public GUIWire(ViewModelModifiable model, Pin pin1, Pin pin2, Point... path) { - pathChangedListeners = new HashSet<>(); - logicObs = (i) -> callRedrawListeners(); this.model = model; this.logicWidth = pin1.logicWidth; if (pin2.logicWidth != pin1.logicWidth) @@ -164,6 +160,9 @@ public class GUIWire this.bounds = new Rectangle(0, 0, -1, -1); redrawListeners = new ArrayList<>(); + pathChangedListeners = new ArrayList<>(); + + logicObs = (i) -> callRedrawListeners(); pin1.addPinMovedListener(p -> pinMoved()); pin2.addPinMovedListener(p -> pinMoved()); @@ -288,6 +287,8 @@ public class GUIWire gc.drawPolyline(effectivePath); } + // operations concerning the path + /** * The user-defined path between {@link #pin1} and {@link #pin2}. Note that this is not neccessarily equal to the effective path drawn * in {@link #render(GeneralGC)}.
@@ -298,7 +299,77 @@ public class GUIWire */ public Point[] getPath() { - return path == null ? null : path.clone(); + return deepPathCopy(path); + } + + public void setPath(Point... path) + { + this.path = deepPathCopy(path); + recalculateEffectivePath(); + callPathChangedListeners(); + callRedrawListeners(); + } + + public Point getPathPoint(int index) + { + return pointCopy(path[index]); + } + + public void setPathPoint(Point p, int index) + { + path[index] = pointCopy(p); + recalculateEffectivePath(); + callPathChangedListeners(); + callRedrawListeners(); + } + + public void insertPathPoint(Point p, int index) + { + if (path == null) + path = new Point[] { pointCopy(p) }; + else + { + Point[] oldPath = path; + path = new Point[oldPath.length + 1]; + System.arraycopy(oldPath, 0, path, 0, index); + if (index < oldPath.length) + System.arraycopy(oldPath, index, path, index + 1, oldPath.length - index); + path[index] = pointCopy(p); + } + } + + public void removePathPoint(int index) + { + if (path.length == 0) + path = null; + else + { + Point[] oldPath = path; + path = new Point[oldPath.length - 1]; + System.arraycopy(oldPath, 0, path, 0, index); + if (index < oldPath.length - 1) + System.arraycopy(oldPath, index + 1, path, index, oldPath.length - index - 1); + } + } + + public double[] getEffectivePath() + { + return Arrays.copyOf(effectivePath, effectivePath.length); + } + + private static Point[] deepPathCopy(Point[] path) + { + if (path == null) + return null; + Point[] copy = new Point[path.length]; + for (int i = 0; i < path.length; i++) + copy[i] = pointCopy(path[i]); + return copy; + } + + private static Point pointCopy(Point p) + { + return new Point(p.x, p.y); } // logic model binding @@ -354,29 +425,14 @@ public class GUIWire // listeners // @formatter:off - public void addRedrawListener (Runnable listener) {redrawListeners .add (listener);} + public void addRedrawListener (Runnable listener) {redrawListeners .add (listener);} + public void addPathChangedListener (Consumer listener) {pathChangedListeners.add (listener);} - public void removeRedrawListener(Runnable listener) {redrawListeners .remove(listener);} + public void removeRedrawListener (Runnable listener) {redrawListeners .remove(listener);} + public void removePathChangedListener(Consumer listener) {pathChangedListeners.remove(listener);} - private void callRedrawListeners() {redrawListeners.forEach(l -> l.run());} - - public void addPathChangedListener(PathChangedListener l) { pathChangedListeners.add(l); } - - public void removePathChangedListener(PathChangedListener l) { pathChangedListeners.remove(l); } - - public void callPathChangedListeners(int diff) { pathChangedListeners.forEach(l -> l.pathChanged(this, diff)); } - - @FunctionalInterface - public static interface PathChangedListener - { - /** - * Called whenever the {@link Wire}'s path changes - * - * @param wire The wire which had its path changed - * @param diff The length difference between before and after the path change. - */ - public void pathChanged(GUIWire wire, int diff); - } + private void callRedrawListeners () {redrawListeners .forEach(l -> l.run ( ));} + private void callPathChangedListeners() {pathChangedListeners.forEach(l -> l.accept(this));} // @formatter:on @Override @@ -384,65 +440,4 @@ public class GUIWire { return "GUIWire [" + pin1 + "---" + pin2 + ", value=" + (end == null ? "null" : end.getValues()) + "]"; } - - public void setPath(Point[] path) - { - int diff = (path == null ? 0 : path.length) - (this.path == null ? 0 : this.path.length); - this.path = path == null ? null : path.clone(); - recalculateEffectivePath(); - callPathChangedListeners(diff); - callRedrawListeners(); - } - - public void setPathPoint(Point p, int index) - { - path[index] = p; - recalculateEffectivePath(); - callPathChangedListeners(0); - callRedrawListeners(); - } - - public void insertPathPoint(Point p, int index) - { - Point[] path = getPath(); - if (path == null) - setPath(new Point[] { p }); - else - { - Point[] newPath = new Point[path.length + 1]; - System.arraycopy(path, 0, newPath, 0, index); - if (index < path.length) - System.arraycopy(path, index, newPath, index + 1, path.length - index); - newPath[index] = p; - setPath(newPath); - } - } - - public void removePathPoint(int index) - { - Point[] path = getPath(); - Point[] newPath = new Point[path.length - 1]; - System.arraycopy(path, 0, newPath, 0, index); - if (index < path.length - 1) - System.arraycopy(path, index + 1, newPath, index, path.length - index - 1); - setPath(newPath); - } - - /** - * @throws IndexOutOfBoundsException - */ - public Point getPathPoint(int index) - { - return path[index]; - } - - public int getPathLength() - { - return path.length; - } - - public double[] getEffectivePath() - { - return effectivePath.clone(); - } } \ No newline at end of file