diff --git a/src/yugecin/opsudance/sbv2/MoveStoryBoard.java b/src/yugecin/opsudance/sbv2/MoveStoryBoard.java
index d4e7d682..aa3f36d7 100644
--- a/src/yugecin/opsudance/sbv2/MoveStoryBoard.java
+++ b/src/yugecin/opsudance/sbv2/MoveStoryBoard.java
@@ -24,6 +24,7 @@ import itdelatrisu.opsu.ui.UI;
import org.newdawn.slick.GameContainer;
import org.newdawn.slick.Graphics;
import yugecin.opsudance.sbv2.movers.LinearStoryboardMover;
+import yugecin.opsudance.sbv2.movers.QuadraticStoryboardMover;
import yugecin.opsudance.ui.SimpleButton;
import java.lang.reflect.InvocationHandler;
@@ -106,6 +107,7 @@ public class MoveStoryboard {
getCurrentMoveOrCreateNew().add(new LinearStoryboardMover());
}
if (btnAddQuadratic.isHovered()) {
+ getCurrentMoveOrCreateNew().add(new QuadraticStoryboardMover());
}
if (btnAddCubic.isHovered()) {
}
diff --git a/src/yugecin/opsudance/sbv2/StoryboardMoveImpl.java b/src/yugecin/opsudance/sbv2/StoryboardMoveImpl.java
index f89b3bbf..5edefd8d 100644
--- a/src/yugecin/opsudance/sbv2/StoryboardMoveImpl.java
+++ b/src/yugecin/opsudance/sbv2/StoryboardMoveImpl.java
@@ -63,9 +63,7 @@ public class StoryboardMoveImpl implements StoryboardMove {
public void add(StoryboardMover mover) {
mover.end = end;
if (movers.size() == 0) {
- mover.start = start;
- mover.recalculateLength();
- totalLength += mover.getLength();
+ mover.setInitialStart(start);
} else {
StoryboardMover lastMover = movers.get(movers.size() - 1);
Vec2f mid = new Vec2f(
@@ -77,8 +75,10 @@ public class StoryboardMoveImpl implements StoryboardMove {
totalLength -= lastMover.getLength();
lastMover.recalculateLength();
totalLength += lastMover.getLength();
- mover.start = mid;
+ mover.setInitialStart(mid);
}
+ mover.recalculateLength();
+ totalLength += mover.getLength();
movers.add(mover);
recalculateTimes();
}
@@ -100,6 +100,9 @@ public class StoryboardMoveImpl implements StoryboardMove {
@Override
public void update(int delta, int x, int y) {
+ for (StoryboardMover mover : movers) {
+ mover.update(delta, x, y);
+ }
if (currentPoint != null) {
moveCurrentPoint(x, y);
recalculateDelay -= delta;
@@ -114,12 +117,17 @@ public class StoryboardMoveImpl implements StoryboardMove {
@Override
public void mousePressed(int x, int y) {
int i = 0;
+ for(StoryboardMover mover : movers) {
+ if (mover.mousePressed(x, y)) {
+ return;
+ }
+ }
for (Vec2f point : midPoints) {
if (point.x - POINTSIZE <= x && x <= point.x + POINTSIZE && point.y - POINTSIZE <= y && y <= point.y + POINTSIZE) {
currentPoint = point;
prevMover = movers.get(i);
nextMover = movers.get(i + 1);
- break;
+ return;
}
i++;
}
@@ -149,6 +157,15 @@ public class StoryboardMoveImpl implements StoryboardMove {
movers.remove(i);
totalLength -= mover.getLength();
recalculateTimes();
+ return;
+ }
+ }
+ for(StoryboardMover mover : movers) {
+ float prevLen = mover.getLength();
+ if (mover.mouseReleased(x, y)) {
+ mover.recalculateLength();
+ totalLength += mover.getLength() - prevLen;
+ recalculateTimes();
}
}
} else {
diff --git a/src/yugecin/opsudance/sbv2/movers/StoryboardMover.java b/src/yugecin/opsudance/sbv2/movers/StoryboardMover.java
index b869614c..e3a2f72f 100644
--- a/src/yugecin/opsudance/sbv2/movers/StoryboardMover.java
+++ b/src/yugecin/opsudance/sbv2/movers/StoryboardMover.java
@@ -17,6 +17,7 @@
*/
package yugecin.opsudance.sbv2.movers;
+import itdelatrisu.opsu.Utils;
import itdelatrisu.opsu.objects.curves.Vec2f;
import org.newdawn.slick.Color;
import org.newdawn.slick.Graphics;
@@ -28,7 +29,7 @@ public abstract class StoryboardMover {
protected float length;
public Vec2f start;
public Vec2f end;
- private Color renderColor;
+ private final Color renderColor;
public float timeLengthPercentOfTotalTime;
public StoryboardMover(Color renderColor) {
@@ -36,12 +37,41 @@ public abstract class StoryboardMover {
}
public abstract float[] getPointAt(float t);
- public abstract void recalculateLength();
-
public float getLength() {
return length;
}
+ /**
+ * Set the start position after just creating this mover
+ * @param start start position
+ */
+ public void setInitialStart(Vec2f start) {
+ this.start = start;
+ }
+
+ public void update(int delta, int x, int y) {
+ }
+
+ /**
+ *
+ * @param x x pos of mouse
+ * @param y y pos of mouse
+ * @return true if mouse pressed something and consecutive checks should be ignored
+ */
+ public boolean mousePressed(int x, int y) {
+ return false;
+ }
+
+ /**
+ *
+ * @param x x pos of mouse
+ * @param y y pos of mouse
+ * @return true if mouse released something and length should be recalculated
+ */
+ public boolean mouseReleased(int x, int y) {
+ return false;
+ }
+
public void render(Graphics g) {
g.setColor(renderColor);
for (float t = 0; t <= 1f; t += StoryboardMover.CALC_DRAW_INTERVAL) {
@@ -50,4 +80,14 @@ public abstract class StoryboardMover {
}
}
+ public void recalculateLength() {
+ this.length = 0;
+ float[] lastPoint = new float[] { start.x, start.y };
+ for (float t = StoryboardMover.CALC_DRAW_INTERVAL; t <= 1f; t += StoryboardMover.CALC_DRAW_INTERVAL) {
+ float[] p = getPointAt(t);
+ this.length += Utils.distance(lastPoint[0], lastPoint[1], p[0], p[1]);
+ lastPoint = p;
+ }
+ }
+
}
diff --git a/src/yugecin/opsudance/sbv2/movers/StoryboardMultipointMover.java b/src/yugecin/opsudance/sbv2/movers/StoryboardMultipointMover.java
new file mode 100644
index 00000000..d54388d4
--- /dev/null
+++ b/src/yugecin/opsudance/sbv2/movers/StoryboardMultipointMover.java
@@ -0,0 +1,86 @@
+/*
+ * opsu!dance - fork of opsu! with cursordance auto
+ * Copyright (C) 2016 yugecin
+ *
+ * opsu!dance is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * opsu!dance 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with opsu!dance. If not, see .
+ */
+package yugecin.opsudance.sbv2.movers;
+
+import itdelatrisu.opsu.objects.curves.Vec2f;
+import org.newdawn.slick.Color;
+import org.newdawn.slick.Graphics;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public abstract class StoryboardMultipointMover extends StoryboardMover {
+
+ private static final int POINTSIZE = 6;
+
+ private List points;
+ private final Color pointColor;
+
+ private Vec2f currentPoint;
+
+ public StoryboardMultipointMover(Color renderColor, Color pointColor) {
+ super(renderColor);
+ this.pointColor = pointColor;
+ this.points = new ArrayList<>();
+ }
+
+ public void addPoint(Vec2f point) {
+ points.add(point);
+ }
+
+ @Override
+ public void update(int delta, int x, int y) {
+ if (currentPoint != null) {
+ currentPoint.x = x;
+ currentPoint.y = y;
+ }
+ }
+
+ @Override
+ public boolean mousePressed(int x, int y) {
+ for (Vec2f point : points) {
+ if (point.x - POINTSIZE <= x && x <= point.x + POINTSIZE && point.y - POINTSIZE <= y && y <= point.y + POINTSIZE) {
+ currentPoint = point;
+ return true;
+ }
+ }
+ return false;
+ }
+
+ @Override
+ public boolean mouseReleased(int x, int y) {
+ if (currentPoint != null) {
+ currentPoint = null;
+ return true;
+ }
+ return false;
+ }
+
+ protected Vec2f getPoint(int index) {
+ return points.get(index);
+ }
+
+ @Override
+ public void render(Graphics g) {
+ g.setColor(pointColor);
+ for (Vec2f point : points) {
+ g.fillRect(point.x - POINTSIZE, point.y - POINTSIZE, POINTSIZE * 2 + 1, POINTSIZE * 2 + 1);
+ }
+ super.render(g);
+ }
+}