Added easing functions for all-around better animations.
These are Robert Penner's easing functions (http://robertpenner.com/easing/), refactored by CharlotteGore to only take a t parameter (https://github.com/CharlotteGore/functional-easing). Licensed under BSD (the former) and MIT (the latter). Related changes: - Added "AnimatedValue" utility class for updating values used in animations. - MenuButton now uses AnimatedValue to handle its animations (still linear by default). - Added in-out-back easings on logo, mods, and various other elements; added out-bounce easings on button menu. Signed-off-by: Jeffrey Han <itdelatrisu@gmail.com>
This commit is contained in:
@@ -31,6 +31,8 @@ import itdelatrisu.opsu.beatmap.BeatmapSetList;
|
||||
import itdelatrisu.opsu.beatmap.BeatmapSetNode;
|
||||
import itdelatrisu.opsu.ui.MenuButton;
|
||||
import itdelatrisu.opsu.ui.UI;
|
||||
import itdelatrisu.opsu.ui.animations.AnimatedValue;
|
||||
import itdelatrisu.opsu.ui.animations.AnimationEquation;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
@@ -261,8 +263,11 @@ public class ButtonMenu extends BasicGameState {
|
||||
/** The actual title string list, generated upon entering the state. */
|
||||
private List<String> actualTitle;
|
||||
|
||||
/** The horizontal center offset, used for the initial button animation. */
|
||||
private AnimatedValue centerOffset;
|
||||
|
||||
/** Initial x coordinate offsets left/right of center (for shifting animation), times width. (TODO) */
|
||||
private static final float OFFSET_WIDTH_RATIO = 1 / 18f;
|
||||
private static final float OFFSET_WIDTH_RATIO = 1 / 25f;
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
@@ -336,18 +341,14 @@ public class ButtonMenu extends BasicGameState {
|
||||
*/
|
||||
public void update(GameContainer container, int delta, int mouseX, int mouseY) {
|
||||
float center = container.getWidth() / 2f;
|
||||
boolean centerOffsetUpdated = centerOffset.update(delta);
|
||||
float centerOffsetX = centerOffset.getValue();
|
||||
for (int i = 0; i < buttons.length; i++) {
|
||||
menuButtons[i].hoverUpdate(delta, mouseX, mouseY);
|
||||
|
||||
// move button to center
|
||||
float x = menuButtons[i].getX();
|
||||
if (i % 2 == 0) {
|
||||
if (x < center)
|
||||
menuButtons[i].setX(Math.min(x + (delta / 5f), center));
|
||||
} else {
|
||||
if (x > center)
|
||||
menuButtons[i].setX(Math.max(x - (delta / 5f), center));
|
||||
}
|
||||
if (centerOffsetUpdated)
|
||||
menuButtons[i].setX((i % 2 == 0) ? center + centerOffsetX : center - centerOffsetX);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -404,9 +405,10 @@ public class ButtonMenu extends BasicGameState {
|
||||
*/
|
||||
public void enter(GameContainer container, StateBasedGame game) {
|
||||
float center = container.getWidth() / 2f;
|
||||
float centerOffset = container.getWidth() * OFFSET_WIDTH_RATIO;
|
||||
float centerOffsetX = container.getWidth() * OFFSET_WIDTH_RATIO;
|
||||
centerOffset = new AnimatedValue(700, centerOffsetX, 0, AnimationEquation.OUT_BOUNCE);
|
||||
for (int i = 0; i < buttons.length; i++) {
|
||||
menuButtons[i].setX(center + ((i % 2 == 0) ? centerOffset * -1 : centerOffset));
|
||||
menuButtons[i].setX(center + ((i % 2 == 0) ? centerOffsetX : centerOffsetX * -1));
|
||||
menuButtons[i].resetHover();
|
||||
}
|
||||
|
||||
|
||||
@@ -48,6 +48,7 @@ import itdelatrisu.opsu.replay.Replay;
|
||||
import itdelatrisu.opsu.replay.ReplayFrame;
|
||||
import itdelatrisu.opsu.ui.MenuButton;
|
||||
import itdelatrisu.opsu.ui.UI;
|
||||
import itdelatrisu.opsu.ui.animations.AnimationEquation;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.LinkedList;
|
||||
@@ -1425,6 +1426,8 @@ public class Game extends BasicGameState {
|
||||
Image skip = GameImage.SKIP.getImage();
|
||||
skipButton = new MenuButton(skip, width - skip.getWidth() / 2f, height - (skip.getHeight() / 2f));
|
||||
}
|
||||
skipButton.setHoverAnimationDuration(350);
|
||||
skipButton.setHoverAnimationEquation(AnimationEquation.IN_OUT_BACK);
|
||||
skipButton.setHoverExpand(1.1f, MenuButton.Expand.UP_LEFT);
|
||||
|
||||
// load other images...
|
||||
|
||||
@@ -27,6 +27,7 @@ import itdelatrisu.opsu.audio.SoundController;
|
||||
import itdelatrisu.opsu.audio.SoundEffect;
|
||||
import itdelatrisu.opsu.ui.MenuButton;
|
||||
import itdelatrisu.opsu.ui.UI;
|
||||
import itdelatrisu.opsu.ui.animations.AnimationEquation;
|
||||
|
||||
import org.lwjgl.input.Keyboard;
|
||||
import org.newdawn.slick.Color;
|
||||
@@ -227,6 +228,14 @@ public class GamePauseMenu extends BasicGameState {
|
||||
continueButton = new MenuButton(GameImage.PAUSE_CONTINUE.getImage(), width / 2f, height * 0.25f);
|
||||
retryButton = new MenuButton(GameImage.PAUSE_RETRY.getImage(), width / 2f, height * 0.5f);
|
||||
backButton = new MenuButton(GameImage.PAUSE_BACK.getImage(), width / 2f, height * 0.75f);
|
||||
final int buttonAnimationDuration = 300;
|
||||
continueButton.setHoverAnimationDuration(buttonAnimationDuration);
|
||||
retryButton.setHoverAnimationDuration(buttonAnimationDuration);
|
||||
backButton.setHoverAnimationDuration(buttonAnimationDuration);
|
||||
final AnimationEquation buttonAnimationEquation = AnimationEquation.IN_OUT_BACK;
|
||||
continueButton.setHoverAnimationEquation(buttonAnimationEquation);
|
||||
retryButton.setHoverAnimationEquation(buttonAnimationEquation);
|
||||
backButton.setHoverAnimationEquation(buttonAnimationEquation);
|
||||
continueButton.setHoverExpand();
|
||||
retryButton.setHoverExpand();
|
||||
backButton.setHoverExpand();
|
||||
|
||||
@@ -33,6 +33,7 @@ import itdelatrisu.opsu.downloads.Updater;
|
||||
import itdelatrisu.opsu.states.ButtonMenu.MenuState;
|
||||
import itdelatrisu.opsu.ui.MenuButton;
|
||||
import itdelatrisu.opsu.ui.MenuButton.Expand;
|
||||
import itdelatrisu.opsu.ui.animations.AnimationEquation;
|
||||
import itdelatrisu.opsu.ui.UI;
|
||||
|
||||
import java.awt.Desktop;
|
||||
@@ -145,9 +146,18 @@ public class MainMenu extends BasicGameState {
|
||||
exitButton = new MenuButton(exitImg,
|
||||
width * 0.75f - exitOffset, (height / 2) + (exitImg.getHeight() / 2f)
|
||||
);
|
||||
logo.setHoverExpand(1.05f);
|
||||
playButton.setHoverExpand(1.05f);
|
||||
exitButton.setHoverExpand(1.05f);
|
||||
final int logoAnimationDuration = 350;
|
||||
logo.setHoverAnimationDuration(logoAnimationDuration);
|
||||
playButton.setHoverAnimationDuration(logoAnimationDuration);
|
||||
exitButton.setHoverAnimationDuration(logoAnimationDuration);
|
||||
final AnimationEquation logoAnimationEquation = AnimationEquation.IN_OUT_BACK;
|
||||
logo.setHoverAnimationEquation(logoAnimationEquation);
|
||||
playButton.setHoverAnimationEquation(logoAnimationEquation);
|
||||
exitButton.setHoverAnimationEquation(logoAnimationEquation);
|
||||
final float logoHoverScale = 1.1f;
|
||||
logo.setHoverExpand(logoHoverScale);
|
||||
playButton.setHoverExpand(logoHoverScale);
|
||||
exitButton.setHoverExpand(logoHoverScale);
|
||||
|
||||
// initialize music buttons
|
||||
int musicWidth = GameImage.MUSIC_PLAY.getImage().getWidth();
|
||||
@@ -170,6 +180,8 @@ public class MainMenu extends BasicGameState {
|
||||
// initialize downloads button
|
||||
Image dlImg = GameImage.DOWNLOADS.getImage();
|
||||
downloadsButton = new MenuButton(dlImg, width - dlImg.getWidth() / 2f, height / 2f);
|
||||
downloadsButton.setHoverAnimationDuration(350);
|
||||
downloadsButton.setHoverAnimationEquation(AnimationEquation.IN_OUT_BACK);
|
||||
downloadsButton.setHoverExpand(1.03f, Expand.LEFT);
|
||||
|
||||
// initialize repository button
|
||||
@@ -179,6 +191,8 @@ public class MainMenu extends BasicGameState {
|
||||
repoButton = new MenuButton(repoImg,
|
||||
startX - repoImg.getWidth(), startY - repoImg.getHeight()
|
||||
);
|
||||
repoButton.setHoverAnimationDuration(350);
|
||||
repoButton.setHoverAnimationEquation(AnimationEquation.IN_OUT_BACK);
|
||||
repoButton.setHoverExpand();
|
||||
startX -= repoImg.getWidth() * 1.75f;
|
||||
} else
|
||||
|
||||
Reference in New Issue
Block a user