Extracted UI components from Utils into a separate UI class.
Added draw(), update(), and enter() methods in UI to do all the necessary calls (instead of letting the states handle them). Signed-off-by: Jeffrey Han <itdelatrisu@gmail.com>
This commit is contained in:
parent
fb5515efb8
commit
235adc539e
|
@ -185,7 +185,7 @@ public class Opsu extends StateBasedGame {
|
|||
} else
|
||||
songMenu.resetTrackOnLoad();
|
||||
}
|
||||
Utils.resetCursor();
|
||||
UI.resetCursor();
|
||||
this.enterState(Opsu.STATE_SONGMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
return false;
|
||||
}
|
||||
|
|
|
@ -199,7 +199,7 @@ public class Options {
|
|||
@Override
|
||||
public void click(GameContainer container) {
|
||||
super.click(container);
|
||||
Utils.resetCursor();
|
||||
UI.resetCursor();
|
||||
}
|
||||
},
|
||||
DYNAMIC_BACKGROUND ("Enable Dynamic Backgrounds", "The song background will be used as the main menu background.", true),
|
||||
|
|
|
@ -121,7 +121,7 @@ public class ScoreData implements Comparable<ScoreData> {
|
|||
* @param total the total number of buttons
|
||||
*/
|
||||
public static void drawScrollbar(Graphics g, int index, int total) {
|
||||
Utils.drawScrollbar(g, index, total, SongMenu.MAX_SCORE_BUTTONS, 0, baseY,
|
||||
UI.drawScrollbar(g, index, total, SongMenu.MAX_SCORE_BUTTONS, 0, baseY,
|
||||
0, buttonHeight, buttonOffset, null, Color.white, false);
|
||||
}
|
||||
|
||||
|
|
|
@ -183,6 +183,6 @@ public enum SongSort {
|
|||
* @param isHover whether to include a hover effect (unselected only)
|
||||
*/
|
||||
public void draw(boolean selected, boolean isHover) {
|
||||
Utils.drawTab(tab.getX(), tab.getY(), name, selected, isHover);
|
||||
UI.drawTab(tab.getX(), tab.getY(), name, selected, isHover);
|
||||
}
|
||||
}
|
574
src/itdelatrisu/opsu/UI.java
Normal file
574
src/itdelatrisu/opsu/UI.java
Normal file
|
@ -0,0 +1,574 @@
|
|||
/*
|
||||
* opsu! - an open-source osu! client
|
||||
* Copyright (C) 2014, 2015 Jeffrey Han
|
||||
*
|
||||
* opsu! 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! 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!. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package itdelatrisu.opsu;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedList;
|
||||
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
|
||||
import org.newdawn.slick.Animation;
|
||||
import org.newdawn.slick.Color;
|
||||
import org.newdawn.slick.GameContainer;
|
||||
import org.newdawn.slick.Graphics;
|
||||
import org.newdawn.slick.Image;
|
||||
import org.newdawn.slick.Input;
|
||||
import org.newdawn.slick.SlickException;
|
||||
import org.newdawn.slick.state.StateBasedGame;
|
||||
|
||||
/**
|
||||
* Class primarily used for drawing UI components.
|
||||
*/
|
||||
public class UI {
|
||||
/** Back button. */
|
||||
private static MenuButton backButton;
|
||||
|
||||
/** Last cursor coordinates. */
|
||||
private static int lastX = -1, lastY = -1;
|
||||
|
||||
/** Cursor rotation angle. */
|
||||
private static float cursorAngle = 0f;
|
||||
|
||||
/** Stores all previous cursor locations to display a trail. */
|
||||
private static LinkedList<Integer>
|
||||
cursorX = new LinkedList<Integer>(),
|
||||
cursorY = new LinkedList<Integer>();
|
||||
|
||||
/** Time to show volume image, in milliseconds. */
|
||||
private static final int VOLUME_DISPLAY_TIME = 1500;
|
||||
|
||||
/** Volume display elapsed time. */
|
||||
private static int volumeDisplay = -1;
|
||||
|
||||
/** The current bar notification string. */
|
||||
private static String barNotif;
|
||||
|
||||
/** The current bar notification timer. */
|
||||
private static int barNotifTimer = -1;
|
||||
|
||||
/** Duration, in milliseconds, to display bar notifications. */
|
||||
private static final int BAR_NOTIFICATION_TIME = 1250;
|
||||
|
||||
// game-related variables
|
||||
private static GameContainer container;
|
||||
private static StateBasedGame game;
|
||||
private static Input input;
|
||||
|
||||
// This class should not be instantiated.
|
||||
private UI() {}
|
||||
|
||||
/**
|
||||
* Initializes UI data.
|
||||
* @param container the game container
|
||||
* @param game the game object
|
||||
* @throws SlickException
|
||||
*/
|
||||
public static void init(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.container = container;
|
||||
UI.game = game;
|
||||
UI.input = container.getInput();
|
||||
|
||||
// back button
|
||||
if (GameImage.MENU_BACK.getImages() != null) {
|
||||
Animation back = GameImage.MENU_BACK.getAnimation(120);
|
||||
backButton = new MenuButton(back, back.getWidth() / 2f, container.getHeight() - (back.getHeight() / 2f));
|
||||
} else {
|
||||
Image back = GameImage.MENU_BACK.getImage();
|
||||
backButton = new MenuButton(back, back.getWidth() / 2f, container.getHeight() - (back.getHeight() / 2f));
|
||||
}
|
||||
backButton.setHoverExpand(MenuButton.Expand.UP_RIGHT);
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates all UI components by a delta interval.
|
||||
* @param delta the delta interval since the last call.
|
||||
*/
|
||||
public static void update(int delta) {
|
||||
updateCursor(delta);
|
||||
updateVolumeDisplay(delta);
|
||||
updateBarNotification(delta);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the global UI components: cursor, FPS, volume bar, bar notifications.
|
||||
* @param g the graphics context
|
||||
*/
|
||||
public static void draw(Graphics g) {
|
||||
drawBarNotification(g);
|
||||
drawVolume(g);
|
||||
drawFPS();
|
||||
drawCursor();
|
||||
}
|
||||
|
||||
/**
|
||||
* Resets the necessary UI components upon entering a state.
|
||||
*/
|
||||
public static void enter() {
|
||||
backButton.resetHover();
|
||||
resetBarNotification();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the 'menu-back' MenuButton.
|
||||
*/
|
||||
public static MenuButton getBackButton() { return backButton; }
|
||||
|
||||
/**
|
||||
* Draws a tab image and text centered at a location.
|
||||
* @param x the center x coordinate
|
||||
* @param y the center y coordinate
|
||||
* @param text the text to draw inside the tab
|
||||
* @param selected whether the tab is selected (white) or not (red)
|
||||
* @param isHover whether to include a hover effect (unselected only)
|
||||
*/
|
||||
public static void drawTab(float x, float y, String text, boolean selected, boolean isHover) {
|
||||
Image tabImage = GameImage.MENU_TAB.getImage();
|
||||
float tabTextX = x - (Utils.FONT_MEDIUM.getWidth(text) / 2);
|
||||
float tabTextY = y - (tabImage.getHeight() / 2.5f);
|
||||
Color filter, textColor;
|
||||
if (selected) {
|
||||
filter = Color.white;
|
||||
textColor = Color.black;
|
||||
} else {
|
||||
filter = (isHover) ? Utils.COLOR_RED_HOVER : Color.red;
|
||||
textColor = Color.white;
|
||||
}
|
||||
tabImage.drawCentered(x, y, filter);
|
||||
Utils.FONT_MEDIUM.drawString(tabTextX, tabTextY, text, textColor);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the cursor.
|
||||
*/
|
||||
public static void drawCursor() {
|
||||
// determine correct cursor image
|
||||
// TODO: most beatmaps don't skin CURSOR_MIDDLE, so how to determine style?
|
||||
Image cursor = null, cursorMiddle = null, cursorTrail = null;
|
||||
boolean skinned = GameImage.CURSOR.hasSkinImage();
|
||||
boolean newStyle = (skinned) ? true : Options.isNewCursorEnabled();
|
||||
if (skinned || newStyle) {
|
||||
cursor = GameImage.CURSOR.getImage();
|
||||
cursorTrail = GameImage.CURSOR_TRAIL.getImage();
|
||||
} else {
|
||||
cursor = GameImage.CURSOR_OLD.getImage();
|
||||
cursorTrail = GameImage.CURSOR_TRAIL_OLD.getImage();
|
||||
}
|
||||
if (newStyle)
|
||||
cursorMiddle = GameImage.CURSOR_MIDDLE.getImage();
|
||||
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
int removeCount = 0;
|
||||
int FPSmod = (Options.getTargetFPS() / 60);
|
||||
|
||||
// TODO: use an image buffer
|
||||
if (newStyle) {
|
||||
// new style: add all points between cursor movements
|
||||
if (lastX < 0) {
|
||||
lastX = mouseX;
|
||||
lastY = mouseY;
|
||||
return;
|
||||
}
|
||||
addCursorPoints(lastX, lastY, mouseX, mouseY);
|
||||
lastX = mouseX;
|
||||
lastY = mouseY;
|
||||
|
||||
removeCount = (cursorX.size() / (6 * FPSmod)) + 1;
|
||||
} else {
|
||||
// old style: sample one point at a time
|
||||
cursorX.add(mouseX);
|
||||
cursorY.add(mouseY);
|
||||
|
||||
int max = 10 * FPSmod;
|
||||
if (cursorX.size() > max)
|
||||
removeCount = cursorX.size() - max;
|
||||
}
|
||||
|
||||
// remove points from the lists
|
||||
for (int i = 0; i < removeCount && !cursorX.isEmpty(); i++) {
|
||||
cursorX.remove();
|
||||
cursorY.remove();
|
||||
}
|
||||
|
||||
// draw a fading trail
|
||||
float alpha = 0f;
|
||||
float t = 2f / cursorX.size();
|
||||
Iterator<Integer> iterX = cursorX.iterator();
|
||||
Iterator<Integer> iterY = cursorY.iterator();
|
||||
while (iterX.hasNext()) {
|
||||
int cx = iterX.next();
|
||||
int cy = iterY.next();
|
||||
alpha += t;
|
||||
cursorTrail.setAlpha(alpha);
|
||||
// if (cx != x || cy != y)
|
||||
cursorTrail.drawCentered(cx, cy);
|
||||
}
|
||||
cursorTrail.drawCentered(mouseX, mouseY);
|
||||
|
||||
// increase the cursor size if pressed
|
||||
final float scale = 1.25f;
|
||||
int state = game.getCurrentStateID();
|
||||
if (((state == Opsu.STATE_GAME || state == Opsu.STATE_GAMEPAUSEMENU) && Utils.isGameKeyPressed()) ||
|
||||
((input.isMouseButtonDown(Input.MOUSE_LEFT_BUTTON) || input.isMouseButtonDown(Input.MOUSE_RIGHT_BUTTON)) &&
|
||||
!(state == Opsu.STATE_GAME && Options.isMouseDisabled()))) {
|
||||
cursor = cursor.getScaledCopy(scale);
|
||||
if (newStyle)
|
||||
cursorMiddle = cursorMiddle.getScaledCopy(scale);
|
||||
}
|
||||
|
||||
// draw the other components
|
||||
if (newStyle)
|
||||
cursor.setRotation(cursorAngle);
|
||||
cursor.drawCentered(mouseX, mouseY);
|
||||
if (newStyle)
|
||||
cursorMiddle.drawCentered(mouseX, mouseY);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds all points between (x1, y1) and (x2, y2) to the cursor point lists.
|
||||
* @author http://rosettacode.org/wiki/Bitmap/Bresenham's_line_algorithm#Java
|
||||
*/
|
||||
private static void addCursorPoints(int x1, int y1, int x2, int y2) {
|
||||
// delta of exact value and rounded value of the dependent variable
|
||||
int d = 0;
|
||||
int dy = Math.abs(y2 - y1);
|
||||
int dx = Math.abs(x2 - x1);
|
||||
|
||||
int dy2 = (dy << 1); // slope scaling factors to avoid floating
|
||||
int dx2 = (dx << 1); // point
|
||||
int ix = x1 < x2 ? 1 : -1; // increment direction
|
||||
int iy = y1 < y2 ? 1 : -1;
|
||||
|
||||
int k = 5; // sample size
|
||||
if (dy <= dx) {
|
||||
for (int i = 0; ; i++) {
|
||||
if (i == k) {
|
||||
cursorX.add(x1);
|
||||
cursorY.add(y1);
|
||||
i = 0;
|
||||
}
|
||||
if (x1 == x2)
|
||||
break;
|
||||
x1 += ix;
|
||||
d += dy2;
|
||||
if (d > dx) {
|
||||
y1 += iy;
|
||||
d -= dx2;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (int i = 0; ; i++) {
|
||||
if (i == k) {
|
||||
cursorX.add(x1);
|
||||
cursorY.add(y1);
|
||||
i = 0;
|
||||
}
|
||||
if (y1 == y2)
|
||||
break;
|
||||
y1 += iy;
|
||||
d += dx2;
|
||||
if (d > dy) {
|
||||
x1 += ix;
|
||||
d -= dy2;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Rotates the cursor by a degree determined by a delta interval.
|
||||
* If the old style cursor is being used, this will do nothing.
|
||||
* @param delta the delta interval since the last call
|
||||
*/
|
||||
private static void updateCursor(int delta) {
|
||||
cursorAngle += delta / 40f;
|
||||
cursorAngle %= 360;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resets all cursor data and skins.
|
||||
*/
|
||||
public static void resetCursor() {
|
||||
GameImage.CURSOR.destroySkinImage();
|
||||
GameImage.CURSOR_MIDDLE.destroySkinImage();
|
||||
GameImage.CURSOR_TRAIL.destroySkinImage();
|
||||
cursorAngle = 0f;
|
||||
lastX = lastY = -1;
|
||||
cursorX.clear();
|
||||
cursorY.clear();
|
||||
GameImage.CURSOR.getImage().setRotation(0f);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the FPS at the bottom-right corner of the game container.
|
||||
* If the option is not activated, this will do nothing.
|
||||
*/
|
||||
public static void drawFPS() {
|
||||
if (!Options.isFPSCounterEnabled())
|
||||
return;
|
||||
|
||||
String fps = String.format("%dFPS", container.getFPS());
|
||||
Utils.FONT_BOLD.drawString(
|
||||
container.getWidth() * 0.997f - Utils.FONT_BOLD.getWidth(fps),
|
||||
container.getHeight() * 0.997f - Utils.FONT_BOLD.getHeight(fps),
|
||||
Integer.toString(container.getFPS()), Color.white
|
||||
);
|
||||
Utils.FONT_DEFAULT.drawString(
|
||||
container.getWidth() * 0.997f - Utils.FONT_BOLD.getWidth("FPS"),
|
||||
container.getHeight() * 0.997f - Utils.FONT_BOLD.getHeight("FPS"),
|
||||
"FPS", Color.white
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the volume bar on the middle right-hand side of the game container.
|
||||
* Only draws if the volume has recently been changed using with {@link #changeVolume(int)}.
|
||||
* @param g the graphics context
|
||||
*/
|
||||
public static void drawVolume(Graphics g) {
|
||||
if (volumeDisplay == -1)
|
||||
return;
|
||||
|
||||
int width = container.getWidth(), height = container.getHeight();
|
||||
Image img = GameImage.VOLUME.getImage();
|
||||
|
||||
// move image in/out
|
||||
float xOffset = 0;
|
||||
float ratio = (float) volumeDisplay / VOLUME_DISPLAY_TIME;
|
||||
if (ratio <= 0.1f)
|
||||
xOffset = img.getWidth() * (1 - (ratio * 10f));
|
||||
else if (ratio >= 0.9f)
|
||||
xOffset = img.getWidth() * (1 - ((1 - ratio) * 10f));
|
||||
|
||||
img.drawCentered(width - img.getWidth() / 2f + xOffset, height / 2f);
|
||||
float barHeight = img.getHeight() * 0.9f;
|
||||
float volume = Options.getMasterVolume();
|
||||
g.setColor(Color.white);
|
||||
g.fillRoundRect(
|
||||
width - (img.getWidth() * 0.368f) + xOffset,
|
||||
(height / 2f) - (img.getHeight() * 0.47f) + (barHeight * (1 - volume)),
|
||||
img.getWidth() * 0.15f, barHeight * volume, 3
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates volume display by a delta interval.
|
||||
* @param delta the delta interval since the last call
|
||||
*/
|
||||
private static void updateVolumeDisplay(int delta) {
|
||||
if (volumeDisplay == -1)
|
||||
return;
|
||||
|
||||
volumeDisplay += delta;
|
||||
if (volumeDisplay > VOLUME_DISPLAY_TIME)
|
||||
volumeDisplay = -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Changes the master volume by a unit (positive or negative).
|
||||
* @param units the number of units
|
||||
*/
|
||||
public static void changeVolume(int units) {
|
||||
final float UNIT_OFFSET = 0.05f;
|
||||
Options.setMasterVolume(container, Utils.getBoundedValue(Options.getMasterVolume(), UNIT_OFFSET * units, 0f, 1f));
|
||||
if (volumeDisplay == -1)
|
||||
volumeDisplay = 0;
|
||||
else if (volumeDisplay >= VOLUME_DISPLAY_TIME / 10)
|
||||
volumeDisplay = VOLUME_DISPLAY_TIME / 10;
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws loading progress (OSZ unpacking, OsuFile parsing, sound loading)
|
||||
* at the bottom of the screen.
|
||||
*/
|
||||
public static void drawLoadingProgress(Graphics g) {
|
||||
String text, file;
|
||||
int progress;
|
||||
|
||||
// determine current action
|
||||
if ((file = OszUnpacker.getCurrentFileName()) != null) {
|
||||
text = "Unpacking new beatmaps...";
|
||||
progress = OszUnpacker.getUnpackerProgress();
|
||||
} else if ((file = OsuParser.getCurrentFileName()) != null) {
|
||||
text = (OsuParser.isUpdatingDatabase()) ? "Updating database..." : "Loading beatmaps...";
|
||||
progress = OsuParser.getParserProgress();
|
||||
} else if ((file = SoundController.getCurrentFileName()) != null) {
|
||||
text = "Loading sounds...";
|
||||
progress = SoundController.getLoadingProgress();
|
||||
} else
|
||||
return;
|
||||
|
||||
// draw loading info
|
||||
float marginX = container.getWidth() * 0.02f, marginY = container.getHeight() * 0.02f;
|
||||
float lineY = container.getHeight() - marginY;
|
||||
int lineOffsetY = Utils.FONT_MEDIUM.getLineHeight();
|
||||
if (Options.isLoadVerbose()) {
|
||||
// verbose: display percentages and file names
|
||||
Utils.FONT_MEDIUM.drawString(
|
||||
marginX, lineY - (lineOffsetY * 2),
|
||||
String.format("%s (%d%%)", text, progress), Color.white);
|
||||
Utils.FONT_MEDIUM.drawString(marginX, lineY - lineOffsetY, file, Color.white);
|
||||
} else {
|
||||
// draw loading bar
|
||||
Utils.FONT_MEDIUM.drawString(marginX, lineY - (lineOffsetY * 2), text, Color.white);
|
||||
g.setColor(Color.white);
|
||||
g.fillRoundRect(marginX, lineY - (lineOffsetY / 2f),
|
||||
(container.getWidth() - (marginX * 2f)) * progress / 100f, lineOffsetY / 4f, 4
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws a scroll bar.
|
||||
* @param g the graphics context
|
||||
* @param unitIndex the unit index
|
||||
* @param totalUnits the total number of units
|
||||
* @param maxShown the maximum number of units shown at one time
|
||||
* @param unitBaseX the base x coordinate of the units
|
||||
* @param unitBaseY the base y coordinate of the units
|
||||
* @param unitWidth the width of a unit
|
||||
* @param unitHeight the height of a unit
|
||||
* @param unitOffsetY the y offset between units
|
||||
* @param bgColor the scroll bar area background color (null if none)
|
||||
* @param scrollbarColor the scroll bar color
|
||||
* @param right whether or not to place the scroll bar on the right side of the unit
|
||||
*/
|
||||
public static void drawScrollbar(
|
||||
Graphics g, int unitIndex, int totalUnits, int maxShown,
|
||||
float unitBaseX, float unitBaseY, float unitWidth, float unitHeight, float unitOffsetY,
|
||||
Color bgColor, Color scrollbarColor, boolean right
|
||||
) {
|
||||
float scrollbarWidth = container.getWidth() * 0.00347f;
|
||||
float heightRatio = (float) (2.6701f * Math.exp(-0.81 * Math.log(totalUnits)));
|
||||
float scrollbarHeight = container.getHeight() * heightRatio;
|
||||
float scrollAreaHeight = unitHeight + unitOffsetY * (maxShown - 1);
|
||||
float offsetY = (scrollAreaHeight - scrollbarHeight) * ((float) unitIndex / (totalUnits - maxShown));
|
||||
float scrollbarX = unitBaseX + unitWidth - ((right) ? scrollbarWidth : 0);
|
||||
if (bgColor != null) {
|
||||
g.setColor(bgColor);
|
||||
g.fillRect(scrollbarX, unitBaseY, scrollbarWidth, scrollAreaHeight);
|
||||
}
|
||||
g.setColor(scrollbarColor);
|
||||
g.fillRect(scrollbarX, unitBaseY + offsetY, scrollbarWidth, scrollbarHeight);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws a tooltip near the current mouse coordinates, bounded by the
|
||||
* container dimensions.
|
||||
* @param g the graphics context
|
||||
* @param text the tooltip text
|
||||
* @param newlines whether to check for line breaks ('\n')
|
||||
*/
|
||||
public static void drawTooltip(Graphics g, String text, boolean newlines) {
|
||||
int containerWidth = container.getWidth(), containerHeight = container.getHeight();
|
||||
int margin = containerWidth / 100, textMarginX = 2;
|
||||
int offset = GameImage.CURSOR_MIDDLE.getImage().getWidth() / 2;
|
||||
int lineHeight = Utils.FONT_SMALL.getLineHeight();
|
||||
int textWidth = textMarginX * 2, textHeight = lineHeight;
|
||||
if (newlines) {
|
||||
String[] lines = text.split("\\n");
|
||||
int maxWidth = Utils.FONT_SMALL.getWidth(lines[0]);
|
||||
for (int i = 1; i < lines.length; i++) {
|
||||
int w = Utils.FONT_SMALL.getWidth(lines[i]);
|
||||
if (w > maxWidth)
|
||||
maxWidth = w;
|
||||
}
|
||||
textWidth += maxWidth;
|
||||
textHeight += lineHeight * (lines.length - 1);
|
||||
} else
|
||||
textWidth += Utils.FONT_SMALL.getWidth(text);
|
||||
|
||||
// get drawing coordinates
|
||||
int x = input.getMouseX() + offset, y = input.getMouseY() + offset;
|
||||
if (x + textWidth > containerWidth - margin)
|
||||
x = containerWidth - margin - textWidth;
|
||||
else if (x < margin)
|
||||
x = margin;
|
||||
if (y + textHeight > containerHeight - margin)
|
||||
y = containerHeight - margin - textHeight;
|
||||
else if (y < margin)
|
||||
y = margin;
|
||||
|
||||
// draw tooltip text inside a filled rectangle
|
||||
g.setColor(Color.black);
|
||||
g.fillRect(x, y, textWidth, textHeight);
|
||||
g.setColor(Color.darkGray);
|
||||
g.setLineWidth(1);
|
||||
g.drawRect(x, y, textWidth, textHeight);
|
||||
Utils.FONT_SMALL.drawString(x + textMarginX, y, text, Color.white);
|
||||
}
|
||||
|
||||
/**
|
||||
* Submits a bar notification for drawing.
|
||||
* Must be called with {@link #drawBarNotification(Graphics)}.
|
||||
* @param s the notification string
|
||||
*/
|
||||
public static void sendBarNotification(String s) {
|
||||
if (s != null) {
|
||||
barNotif = s;
|
||||
barNotifTimer = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates the bar notification by a delta interval.
|
||||
* @param delta the delta interval since the last call
|
||||
*/
|
||||
private static void updateBarNotification(int delta) {
|
||||
if (barNotifTimer > -1 && barNotifTimer < BAR_NOTIFICATION_TIME) {
|
||||
barNotifTimer += delta;
|
||||
if (barNotifTimer > BAR_NOTIFICATION_TIME)
|
||||
barNotifTimer = BAR_NOTIFICATION_TIME;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Resets the bar notification.
|
||||
*/
|
||||
public static void resetBarNotification() {
|
||||
barNotifTimer = -1;
|
||||
barNotif = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the notification sent from {@link #sendBarNotification(String)}.
|
||||
* @param g the graphics context
|
||||
*/
|
||||
public static void drawBarNotification(Graphics g) {
|
||||
if (barNotifTimer == -1 || barNotifTimer >= BAR_NOTIFICATION_TIME)
|
||||
return;
|
||||
|
||||
float alpha = 1f;
|
||||
if (barNotifTimer >= BAR_NOTIFICATION_TIME * 0.9f)
|
||||
alpha -= 1 - ((BAR_NOTIFICATION_TIME - barNotifTimer) / (BAR_NOTIFICATION_TIME * 0.1f));
|
||||
int midX = container.getWidth() / 2, midY = container.getHeight() / 2;
|
||||
float barHeight = Utils.FONT_LARGE.getLineHeight() * (1f + 0.6f * Math.min(barNotifTimer * 15f / BAR_NOTIFICATION_TIME, 1f));
|
||||
float oldAlphaB = Utils.COLOR_BLACK_ALPHA.a, oldAlphaW = Utils.COLOR_WHITE_ALPHA.a;
|
||||
Utils.COLOR_BLACK_ALPHA.a *= alpha;
|
||||
Utils.COLOR_WHITE_ALPHA.a = alpha;
|
||||
g.setColor(Utils.COLOR_BLACK_ALPHA);
|
||||
g.fillRect(0, midY - barHeight / 2f, container.getWidth(), barHeight);
|
||||
Utils.FONT_LARGE.drawString(
|
||||
midX - Utils.FONT_LARGE.getWidth(barNotif) / 2f,
|
||||
midY - Utils.FONT_LARGE.getLineHeight() / 2.2f,
|
||||
barNotif, Utils.COLOR_WHITE_ALPHA);
|
||||
Utils.COLOR_BLACK_ALPHA.a = oldAlphaB;
|
||||
Utils.COLOR_WHITE_ALPHA.a = oldAlphaW;
|
||||
}
|
||||
}
|
|
@ -33,8 +33,6 @@ import java.util.ArrayList;
|
|||
import java.util.Arrays;
|
||||
import java.util.Date;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
|
||||
import javax.imageio.ImageIO;
|
||||
|
@ -47,8 +45,6 @@ import org.lwjgl.opengl.GL11;
|
|||
import org.newdawn.slick.Animation;
|
||||
import org.newdawn.slick.Color;
|
||||
import org.newdawn.slick.GameContainer;
|
||||
import org.newdawn.slick.Graphics;
|
||||
import org.newdawn.slick.Image;
|
||||
import org.newdawn.slick.Input;
|
||||
import org.newdawn.slick.SlickException;
|
||||
import org.newdawn.slick.UnicodeFont;
|
||||
|
@ -96,35 +92,6 @@ public class Utils {
|
|||
FONT_DEFAULT, FONT_BOLD,
|
||||
FONT_XLARGE, FONT_LARGE, FONT_MEDIUM, FONT_SMALL;
|
||||
|
||||
/** Back button (shared by other states). */
|
||||
private static MenuButton backButton;
|
||||
|
||||
/** Last cursor coordinates. */
|
||||
private static int lastX = -1, lastY = -1;
|
||||
|
||||
/** Cursor rotation angle. */
|
||||
private static float cursorAngle = 0f;
|
||||
|
||||
/** Stores all previous cursor locations to display a trail. */
|
||||
private static LinkedList<Integer>
|
||||
cursorX = new LinkedList<Integer>(),
|
||||
cursorY = new LinkedList<Integer>();
|
||||
|
||||
/** Time to show volume image, in milliseconds. */
|
||||
private static final int VOLUME_DISPLAY_TIME = 1500;
|
||||
|
||||
/** Volume display elapsed time. */
|
||||
private static int volumeDisplay = -1;
|
||||
|
||||
/** The current bar notification string. */
|
||||
private static String barNotif;
|
||||
|
||||
/** The current bar notification timer. */
|
||||
private static int barNotifTimer = -1;
|
||||
|
||||
/** Duration, in milliseconds, to display bar notifications. */
|
||||
private static final int BAR_NOTIFICATION_TIME = 1250;
|
||||
|
||||
/** Set of all Unicode strings already loaded. */
|
||||
private static HashSet<String> loadedGlyphs = new HashSet<String>();
|
||||
|
||||
|
@ -142,8 +109,6 @@ public class Utils {
|
|||
}
|
||||
|
||||
// game-related variables
|
||||
private static GameContainer container;
|
||||
private static StateBasedGame game;
|
||||
private static Input input;
|
||||
|
||||
// This class should not be instantiated.
|
||||
|
@ -157,9 +122,7 @@ public class Utils {
|
|||
*/
|
||||
public static void init(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
Utils.container = container;
|
||||
Utils.game = game;
|
||||
Utils.input = container.getInput();
|
||||
input = container.getInput();
|
||||
|
||||
// game settings
|
||||
container.setTargetFrameRate(Options.getTargetFPS());
|
||||
|
@ -230,44 +193,8 @@ public class Utils {
|
|||
// initialize download nodes
|
||||
DownloadNode.init(width, height);
|
||||
|
||||
// back button
|
||||
if (GameImage.MENU_BACK.getImages() != null) {
|
||||
Animation back = GameImage.MENU_BACK.getAnimation(120);
|
||||
backButton = new MenuButton(back, back.getWidth() / 2f, height - (back.getHeight() / 2f));
|
||||
} else {
|
||||
Image back = GameImage.MENU_BACK.getImage();
|
||||
backButton = new MenuButton(back, back.getWidth() / 2f, height - (back.getHeight() / 2f));
|
||||
}
|
||||
backButton.setHoverExpand(MenuButton.Expand.UP_RIGHT);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the 'menu-back' MenuButton.
|
||||
*/
|
||||
public static MenuButton getBackButton() { return backButton; }
|
||||
|
||||
/**
|
||||
* Draws a tab image and text centered at a location.
|
||||
* @param x the center x coordinate
|
||||
* @param y the center y coordinate
|
||||
* @param text the text to draw inside the tab
|
||||
* @param selected whether the tab is selected (white) or not (red)
|
||||
* @param isHover whether to include a hover effect (unselected only)
|
||||
*/
|
||||
public static void drawTab(float x, float y, String text, boolean selected, boolean isHover) {
|
||||
Image tabImage = GameImage.MENU_TAB.getImage();
|
||||
float tabTextX = x - (Utils.FONT_MEDIUM.getWidth(text) / 2);
|
||||
float tabTextY = y - (tabImage.getHeight() / 2.5f);
|
||||
Color filter, textColor;
|
||||
if (selected) {
|
||||
filter = Color.white;
|
||||
textColor = Color.black;
|
||||
} else {
|
||||
filter = (isHover) ? Utils.COLOR_RED_HOVER : Color.red;
|
||||
textColor = Color.white;
|
||||
}
|
||||
tabImage.drawCentered(x, y, filter);
|
||||
Utils.FONT_MEDIUM.drawString(tabTextX, tabTextY, text, textColor);
|
||||
// initialize UI components
|
||||
UI.init(container, game);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -330,167 +257,6 @@ public class Utils {
|
|||
return val;
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the cursor.
|
||||
*/
|
||||
public static void drawCursor() {
|
||||
// determine correct cursor image
|
||||
// TODO: most beatmaps don't skin CURSOR_MIDDLE, so how to determine style?
|
||||
Image cursor = null, cursorMiddle = null, cursorTrail = null;
|
||||
boolean skinned = GameImage.CURSOR.hasSkinImage();
|
||||
boolean newStyle = (skinned) ? true : Options.isNewCursorEnabled();
|
||||
if (skinned || newStyle) {
|
||||
cursor = GameImage.CURSOR.getImage();
|
||||
cursorTrail = GameImage.CURSOR_TRAIL.getImage();
|
||||
} else {
|
||||
cursor = GameImage.CURSOR_OLD.getImage();
|
||||
cursorTrail = GameImage.CURSOR_TRAIL_OLD.getImage();
|
||||
}
|
||||
if (newStyle)
|
||||
cursorMiddle = GameImage.CURSOR_MIDDLE.getImage();
|
||||
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
int removeCount = 0;
|
||||
int FPSmod = (Options.getTargetFPS() / 60);
|
||||
|
||||
// TODO: use an image buffer
|
||||
if (newStyle) {
|
||||
// new style: add all points between cursor movements
|
||||
if (lastX < 0) {
|
||||
lastX = mouseX;
|
||||
lastY = mouseY;
|
||||
return;
|
||||
}
|
||||
addCursorPoints(lastX, lastY, mouseX, mouseY);
|
||||
lastX = mouseX;
|
||||
lastY = mouseY;
|
||||
|
||||
removeCount = (cursorX.size() / (6 * FPSmod)) + 1;
|
||||
} else {
|
||||
// old style: sample one point at a time
|
||||
cursorX.add(mouseX);
|
||||
cursorY.add(mouseY);
|
||||
|
||||
int max = 10 * FPSmod;
|
||||
if (cursorX.size() > max)
|
||||
removeCount = cursorX.size() - max;
|
||||
}
|
||||
|
||||
// remove points from the lists
|
||||
for (int i = 0; i < removeCount && !cursorX.isEmpty(); i++) {
|
||||
cursorX.remove();
|
||||
cursorY.remove();
|
||||
}
|
||||
|
||||
// draw a fading trail
|
||||
float alpha = 0f;
|
||||
float t = 2f / cursorX.size();
|
||||
Iterator<Integer> iterX = cursorX.iterator();
|
||||
Iterator<Integer> iterY = cursorY.iterator();
|
||||
while (iterX.hasNext()) {
|
||||
int cx = iterX.next();
|
||||
int cy = iterY.next();
|
||||
alpha += t;
|
||||
cursorTrail.setAlpha(alpha);
|
||||
// if (cx != x || cy != y)
|
||||
cursorTrail.drawCentered(cx, cy);
|
||||
}
|
||||
cursorTrail.drawCentered(mouseX, mouseY);
|
||||
|
||||
// increase the cursor size if pressed
|
||||
final float scale = 1.25f;
|
||||
int state = game.getCurrentStateID();
|
||||
if (((state == Opsu.STATE_GAME || state == Opsu.STATE_GAMEPAUSEMENU) && isGameKeyPressed()) ||
|
||||
((input.isMouseButtonDown(Input.MOUSE_LEFT_BUTTON) || input.isMouseButtonDown(Input.MOUSE_RIGHT_BUTTON)) &&
|
||||
!(state == Opsu.STATE_GAME && Options.isMouseDisabled()))) {
|
||||
cursor = cursor.getScaledCopy(scale);
|
||||
if (newStyle)
|
||||
cursorMiddle = cursorMiddle.getScaledCopy(scale);
|
||||
}
|
||||
|
||||
// draw the other components
|
||||
if (newStyle)
|
||||
cursor.setRotation(cursorAngle);
|
||||
cursor.drawCentered(mouseX, mouseY);
|
||||
if (newStyle)
|
||||
cursorMiddle.drawCentered(mouseX, mouseY);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds all points between (x1, y1) and (x2, y2) to the cursor point lists.
|
||||
* @author http://rosettacode.org/wiki/Bitmap/Bresenham's_line_algorithm#Java
|
||||
*/
|
||||
private static void addCursorPoints(int x1, int y1, int x2, int y2) {
|
||||
// delta of exact value and rounded value of the dependent variable
|
||||
int d = 0;
|
||||
int dy = Math.abs(y2 - y1);
|
||||
int dx = Math.abs(x2 - x1);
|
||||
|
||||
int dy2 = (dy << 1); // slope scaling factors to avoid floating
|
||||
int dx2 = (dx << 1); // point
|
||||
int ix = x1 < x2 ? 1 : -1; // increment direction
|
||||
int iy = y1 < y2 ? 1 : -1;
|
||||
|
||||
int k = 5; // sample size
|
||||
if (dy <= dx) {
|
||||
for (int i = 0; ; i++) {
|
||||
if (i == k) {
|
||||
cursorX.add(x1);
|
||||
cursorY.add(y1);
|
||||
i = 0;
|
||||
}
|
||||
if (x1 == x2)
|
||||
break;
|
||||
x1 += ix;
|
||||
d += dy2;
|
||||
if (d > dx) {
|
||||
y1 += iy;
|
||||
d -= dx2;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (int i = 0; ; i++) {
|
||||
if (i == k) {
|
||||
cursorX.add(x1);
|
||||
cursorY.add(y1);
|
||||
i = 0;
|
||||
}
|
||||
if (y1 == y2)
|
||||
break;
|
||||
y1 += iy;
|
||||
d += dx2;
|
||||
if (d > dy) {
|
||||
x1 += ix;
|
||||
d -= dy2;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Rotates the cursor by a degree determined by a delta interval.
|
||||
* If the old style cursor is being used, this will do nothing.
|
||||
* @param delta the delta interval since the last call
|
||||
*/
|
||||
public static void updateCursor(int delta) {
|
||||
cursorAngle += delta / 40f;
|
||||
cursorAngle %= 360;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resets all cursor data and skins.
|
||||
*/
|
||||
public static void resetCursor() {
|
||||
GameImage.CURSOR.destroySkinImage();
|
||||
GameImage.CURSOR_MIDDLE.destroySkinImage();
|
||||
GameImage.CURSOR_TRAIL.destroySkinImage();
|
||||
cursorAngle = 0f;
|
||||
lastX = lastY = -1;
|
||||
cursorX.clear();
|
||||
cursorY.clear();
|
||||
GameImage.CURSOR.getImage().setRotation(0f);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if a game input key is pressed (mouse/keyboard left/right).
|
||||
* @return true if pressed
|
||||
|
@ -504,255 +270,6 @@ public class Utils {
|
|||
input.isKeyDown(Options.getGameKeyRight()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the FPS at the bottom-right corner of the game container.
|
||||
* If the option is not activated, this will do nothing.
|
||||
*/
|
||||
public static void drawFPS() {
|
||||
if (!Options.isFPSCounterEnabled())
|
||||
return;
|
||||
|
||||
String fps = String.format("%dFPS", container.getFPS());
|
||||
FONT_BOLD.drawString(
|
||||
container.getWidth() * 0.997f - FONT_BOLD.getWidth(fps),
|
||||
container.getHeight() * 0.997f - FONT_BOLD.getHeight(fps),
|
||||
Integer.toString(container.getFPS()), Color.white
|
||||
);
|
||||
FONT_DEFAULT.drawString(
|
||||
container.getWidth() * 0.997f - FONT_BOLD.getWidth("FPS"),
|
||||
container.getHeight() * 0.997f - FONT_BOLD.getHeight("FPS"),
|
||||
"FPS", Color.white
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the volume bar on the middle right-hand side of the game container.
|
||||
* Only draws if the volume has recently been changed using with {@link #changeVolume(int)}.
|
||||
* @param g the graphics context
|
||||
*/
|
||||
public static void drawVolume(Graphics g) {
|
||||
if (volumeDisplay == -1)
|
||||
return;
|
||||
|
||||
int width = container.getWidth(), height = container.getHeight();
|
||||
Image img = GameImage.VOLUME.getImage();
|
||||
|
||||
// move image in/out
|
||||
float xOffset = 0;
|
||||
float ratio = (float) volumeDisplay / VOLUME_DISPLAY_TIME;
|
||||
if (ratio <= 0.1f)
|
||||
xOffset = img.getWidth() * (1 - (ratio * 10f));
|
||||
else if (ratio >= 0.9f)
|
||||
xOffset = img.getWidth() * (1 - ((1 - ratio) * 10f));
|
||||
|
||||
img.drawCentered(width - img.getWidth() / 2f + xOffset, height / 2f);
|
||||
float barHeight = img.getHeight() * 0.9f;
|
||||
float volume = Options.getMasterVolume();
|
||||
g.setColor(Color.white);
|
||||
g.fillRoundRect(
|
||||
width - (img.getWidth() * 0.368f) + xOffset,
|
||||
(height / 2f) - (img.getHeight() * 0.47f) + (barHeight * (1 - volume)),
|
||||
img.getWidth() * 0.15f, barHeight * volume, 3
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates volume display by a delta interval.
|
||||
* @param delta the delta interval since the last call
|
||||
*/
|
||||
public static void updateVolumeDisplay(int delta) {
|
||||
if (volumeDisplay == -1)
|
||||
return;
|
||||
|
||||
volumeDisplay += delta;
|
||||
if (volumeDisplay > VOLUME_DISPLAY_TIME)
|
||||
volumeDisplay = -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Changes the master volume by a unit (positive or negative).
|
||||
* @param units the number of units
|
||||
*/
|
||||
public static void changeVolume(int units) {
|
||||
final float UNIT_OFFSET = 0.05f;
|
||||
Options.setMasterVolume(container, Utils.getBoundedValue(Options.getMasterVolume(), UNIT_OFFSET * units, 0f, 1f));
|
||||
if (volumeDisplay == -1)
|
||||
volumeDisplay = 0;
|
||||
else if (volumeDisplay >= VOLUME_DISPLAY_TIME / 10)
|
||||
volumeDisplay = VOLUME_DISPLAY_TIME / 10;
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws loading progress (OSZ unpacking, OsuFile parsing, sound loading)
|
||||
* at the bottom of the screen.
|
||||
*/
|
||||
public static void drawLoadingProgress(Graphics g) {
|
||||
String text, file;
|
||||
int progress;
|
||||
|
||||
// determine current action
|
||||
if ((file = OszUnpacker.getCurrentFileName()) != null) {
|
||||
text = "Unpacking new beatmaps...";
|
||||
progress = OszUnpacker.getUnpackerProgress();
|
||||
} else if ((file = OsuParser.getCurrentFileName()) != null) {
|
||||
text = (OsuParser.isUpdatingDatabase()) ? "Updating database..." : "Loading beatmaps...";
|
||||
progress = OsuParser.getParserProgress();
|
||||
} else if ((file = SoundController.getCurrentFileName()) != null) {
|
||||
text = "Loading sounds...";
|
||||
progress = SoundController.getLoadingProgress();
|
||||
} else
|
||||
return;
|
||||
|
||||
// draw loading info
|
||||
float marginX = container.getWidth() * 0.02f, marginY = container.getHeight() * 0.02f;
|
||||
float lineY = container.getHeight() - marginY;
|
||||
int lineOffsetY = Utils.FONT_MEDIUM.getLineHeight();
|
||||
if (Options.isLoadVerbose()) {
|
||||
// verbose: display percentages and file names
|
||||
Utils.FONT_MEDIUM.drawString(
|
||||
marginX, lineY - (lineOffsetY * 2),
|
||||
String.format("%s (%d%%)", text, progress), Color.white);
|
||||
Utils.FONT_MEDIUM.drawString(marginX, lineY - lineOffsetY, file, Color.white);
|
||||
} else {
|
||||
// draw loading bar
|
||||
Utils.FONT_MEDIUM.drawString(marginX, lineY - (lineOffsetY * 2), text, Color.white);
|
||||
g.setColor(Color.white);
|
||||
g.fillRoundRect(marginX, lineY - (lineOffsetY / 2f),
|
||||
(container.getWidth() - (marginX * 2f)) * progress / 100f, lineOffsetY / 4f, 4
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws a scroll bar.
|
||||
* @param g the graphics context
|
||||
* @param unitIndex the unit index
|
||||
* @param totalUnits the total number of units
|
||||
* @param maxShown the maximum number of units shown at one time
|
||||
* @param unitBaseX the base x coordinate of the units
|
||||
* @param unitBaseY the base y coordinate of the units
|
||||
* @param unitWidth the width of a unit
|
||||
* @param unitHeight the height of a unit
|
||||
* @param unitOffsetY the y offset between units
|
||||
* @param bgColor the scroll bar area background color (null if none)
|
||||
* @param scrollbarColor the scroll bar color
|
||||
* @param right whether or not to place the scroll bar on the right side of the unit
|
||||
*/
|
||||
public static void drawScrollbar(
|
||||
Graphics g, int unitIndex, int totalUnits, int maxShown,
|
||||
float unitBaseX, float unitBaseY, float unitWidth, float unitHeight, float unitOffsetY,
|
||||
Color bgColor, Color scrollbarColor, boolean right
|
||||
) {
|
||||
float scrollbarWidth = container.getWidth() * 0.00347f;
|
||||
float heightRatio = (float) (2.6701f * Math.exp(-0.81 * Math.log(totalUnits)));
|
||||
float scrollbarHeight = container.getHeight() * heightRatio;
|
||||
float scrollAreaHeight = unitHeight + unitOffsetY * (maxShown - 1);
|
||||
float offsetY = (scrollAreaHeight - scrollbarHeight) * ((float) unitIndex / (totalUnits - maxShown));
|
||||
float scrollbarX = unitBaseX + unitWidth - ((right) ? scrollbarWidth : 0);
|
||||
if (bgColor != null) {
|
||||
g.setColor(bgColor);
|
||||
g.fillRect(scrollbarX, unitBaseY, scrollbarWidth, scrollAreaHeight);
|
||||
}
|
||||
g.setColor(scrollbarColor);
|
||||
g.fillRect(scrollbarX, unitBaseY + offsetY, scrollbarWidth, scrollbarHeight);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws a tooltip near the current mouse coordinates, bounded by the
|
||||
* container dimensions.
|
||||
* @param g the graphics context
|
||||
* @param text the tooltip text
|
||||
* @param newlines whether to check for line breaks ('\n')
|
||||
*/
|
||||
public static void drawTooltip(Graphics g, String text, boolean newlines) {
|
||||
int containerWidth = container.getWidth(), containerHeight = container.getHeight();
|
||||
int margin = containerWidth / 100, textMarginX = 2;
|
||||
int offset = GameImage.CURSOR_MIDDLE.getImage().getWidth() / 2;
|
||||
int lineHeight = FONT_SMALL.getLineHeight();
|
||||
int textWidth = textMarginX * 2, textHeight = lineHeight;
|
||||
if (newlines) {
|
||||
String[] lines = text.split("\\n");
|
||||
int maxWidth = FONT_SMALL.getWidth(lines[0]);
|
||||
for (int i = 1; i < lines.length; i++) {
|
||||
int w = FONT_SMALL.getWidth(lines[i]);
|
||||
if (w > maxWidth)
|
||||
maxWidth = w;
|
||||
}
|
||||
textWidth += maxWidth;
|
||||
textHeight += lineHeight * (lines.length - 1);
|
||||
} else
|
||||
textWidth += FONT_SMALL.getWidth(text);
|
||||
|
||||
// get drawing coordinates
|
||||
int x = input.getMouseX() + offset, y = input.getMouseY() + offset;
|
||||
if (x + textWidth > containerWidth - margin)
|
||||
x = containerWidth - margin - textWidth;
|
||||
else if (x < margin)
|
||||
x = margin;
|
||||
if (y + textHeight > containerHeight - margin)
|
||||
y = containerHeight - margin - textHeight;
|
||||
else if (y < margin)
|
||||
y = margin;
|
||||
|
||||
// draw tooltip text inside a filled rectangle
|
||||
g.setColor(Color.black);
|
||||
g.fillRect(x, y, textWidth, textHeight);
|
||||
g.setColor(Color.darkGray);
|
||||
g.setLineWidth(1);
|
||||
g.drawRect(x, y, textWidth, textHeight);
|
||||
FONT_SMALL.drawString(x + textMarginX, y, text, Color.white);
|
||||
}
|
||||
|
||||
/**
|
||||
* Submits a bar notification for drawing.
|
||||
* Must be called with {@link #drawBarNotification(Graphics)}.
|
||||
* @param s the notification string
|
||||
*/
|
||||
public static void sendBarNotification(String s) {
|
||||
if (s != null) {
|
||||
barNotif = s;
|
||||
barNotifTimer = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates the bar notification by a delta interval.
|
||||
* @param delta the delta interval since the last call
|
||||
*/
|
||||
public static void updateBarNotification(int delta) {
|
||||
if (barNotifTimer > -1 && barNotifTimer < BAR_NOTIFICATION_TIME) {
|
||||
barNotifTimer += delta;
|
||||
if (barNotifTimer > BAR_NOTIFICATION_TIME)
|
||||
barNotifTimer = BAR_NOTIFICATION_TIME;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Draws the notification sent from {@link #sendBarNotification(String)}.
|
||||
* @param g the graphics context
|
||||
*/
|
||||
public static void drawBarNotification(Graphics g) {
|
||||
if (barNotifTimer == -1 || barNotifTimer >= BAR_NOTIFICATION_TIME)
|
||||
return;
|
||||
|
||||
float alpha = 1f;
|
||||
if (barNotifTimer >= BAR_NOTIFICATION_TIME * 0.9f)
|
||||
alpha -= 1 - ((BAR_NOTIFICATION_TIME - barNotifTimer) / (BAR_NOTIFICATION_TIME * 0.1f));
|
||||
int midX = container.getWidth() / 2, midY = container.getHeight() / 2;
|
||||
float barHeight = FONT_LARGE.getLineHeight() * (1f + 0.6f * Math.min(barNotifTimer * 15f / BAR_NOTIFICATION_TIME, 1f));
|
||||
float oldAlphaB = Utils.COLOR_BLACK_ALPHA.a, oldAlphaW = Utils.COLOR_WHITE_ALPHA.a;
|
||||
Utils.COLOR_BLACK_ALPHA.a *= alpha;
|
||||
Utils.COLOR_WHITE_ALPHA.a = alpha;
|
||||
g.setColor(Utils.COLOR_BLACK_ALPHA);
|
||||
g.fillRect(0, midY - barHeight / 2f, container.getWidth(), barHeight);
|
||||
FONT_LARGE.drawString(
|
||||
midX - FONT_LARGE.getWidth(barNotif) / 2f,
|
||||
midY - FONT_LARGE.getLineHeight() / 2.2f,
|
||||
barNotif, Utils.COLOR_WHITE_ALPHA);
|
||||
Utils.COLOR_BLACK_ALPHA.a = oldAlphaB;
|
||||
Utils.COLOR_WHITE_ALPHA.a = oldAlphaW;
|
||||
}
|
||||
|
||||
/**
|
||||
* Takes a screenshot.
|
||||
* @author http://wiki.lwjgl.org/index.php?title=Taking_Screen_Shots
|
||||
|
|
|
@ -22,6 +22,7 @@ import itdelatrisu.opsu.ErrorHandler;
|
|||
import itdelatrisu.opsu.GameImage;
|
||||
import itdelatrisu.opsu.Options;
|
||||
import itdelatrisu.opsu.OsuGroupList;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.downloads.Download.Status;
|
||||
|
||||
|
@ -179,7 +180,7 @@ public class DownloadNode {
|
|||
* @param total the total number of buttons
|
||||
*/
|
||||
public static void drawResultScrollbar(Graphics g, int index, int total) {
|
||||
Utils.drawScrollbar(g, index, total, maxResultsShown, buttonBaseX, buttonBaseY,
|
||||
UI.drawScrollbar(g, index, total, maxResultsShown, buttonBaseX, buttonBaseY,
|
||||
buttonWidth * 1.01f, buttonHeight, buttonOffset, BG_NORMAL, Color.white, true);
|
||||
}
|
||||
|
||||
|
@ -190,7 +191,7 @@ public class DownloadNode {
|
|||
* @param total the total number of downloads
|
||||
*/
|
||||
public static void drawDownloadScrollbar(Graphics g, int index, int total) {
|
||||
Utils.drawScrollbar(g, index, total, maxDownloadsShown, infoBaseX, infoBaseY,
|
||||
UI.drawScrollbar(g, index, total, maxDownloadsShown, infoBaseX, infoBaseY,
|
||||
infoWidth, infoHeight, infoHeight, BG_NORMAL, Color.white, true);
|
||||
}
|
||||
|
||||
|
|
|
@ -25,6 +25,7 @@ import itdelatrisu.opsu.Opsu;
|
|||
import itdelatrisu.opsu.OsuGroupList;
|
||||
import itdelatrisu.opsu.OsuGroupNode;
|
||||
import itdelatrisu.opsu.ScoreData;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
import itdelatrisu.opsu.audio.SoundEffect;
|
||||
|
@ -183,7 +184,7 @@ public class ButtonMenu extends BasicGameState {
|
|||
|
||||
// tooltips
|
||||
if (hoverMod != null && hoverMod.isImplemented())
|
||||
Utils.drawTooltip(g, hoverMod.getDescription(), true);
|
||||
UI.drawTooltip(g, hoverMod.getDescription(), true);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -291,9 +292,7 @@ public class ButtonMenu extends BasicGameState {
|
|||
for (int i = 0; i < buttons.length; i++)
|
||||
menuButtons[i].draw(buttons[i].getColor());
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -583,8 +582,7 @@ public class ButtonMenu extends BasicGameState {
|
|||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
if (menuState != null)
|
||||
menuState.update(container, delta, input.getMouseX(), input.getMouseY());
|
||||
}
|
||||
|
@ -622,6 +620,7 @@ public class ButtonMenu extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
if (menuState != null)
|
||||
menuState.enter(container, game);
|
||||
}
|
||||
|
|
|
@ -26,6 +26,7 @@ import itdelatrisu.opsu.OsuGroupList;
|
|||
import itdelatrisu.opsu.OsuGroupNode;
|
||||
import itdelatrisu.opsu.OsuParser;
|
||||
import itdelatrisu.opsu.OszUnpacker;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
import itdelatrisu.opsu.audio.SoundEffect;
|
||||
|
@ -302,25 +303,22 @@ public class DownloadsMenu extends BasicGameState {
|
|||
g.setColor(Utils.COLOR_BLACK_ALPHA);
|
||||
g.fillRect(0, 0, width, height);
|
||||
|
||||
Utils.drawLoadingProgress(g);
|
||||
UI.drawLoadingProgress(g);
|
||||
}
|
||||
|
||||
// back button
|
||||
else
|
||||
Utils.getBackButton().draw();
|
||||
UI.getBackButton().draw();
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
Utils.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
UI.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
prevPage.hoverUpdate(delta, mouseX, mouseY);
|
||||
nextPage.hoverUpdate(delta, mouseX, mouseY);
|
||||
clearButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
|
@ -422,7 +420,7 @@ public class DownloadsMenu extends BasicGameState {
|
|||
return;
|
||||
|
||||
// back
|
||||
if (Utils.getBackButton().contains(x, y)) {
|
||||
if (UI.getBackButton().contains(x, y)) {
|
||||
SoundController.playSound(SoundEffect.MENUBACK);
|
||||
((MainMenu) game.getState(Opsu.STATE_MAINMENU)).reset();
|
||||
game.enterState(Opsu.STATE_MAINMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
|
@ -654,7 +652,7 @@ public class DownloadsMenu extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
Utils.getBackButton().resetHover();
|
||||
UI.enter();
|
||||
prevPage.resetHover();
|
||||
nextPage.resetHover();
|
||||
clearButton.resetHover();
|
||||
|
|
|
@ -29,6 +29,7 @@ import itdelatrisu.opsu.OsuFile;
|
|||
import itdelatrisu.opsu.OsuHitObject;
|
||||
import itdelatrisu.opsu.OsuTimingPoint;
|
||||
import itdelatrisu.opsu.ScoreData;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.HitSound;
|
||||
import itdelatrisu.opsu.audio.MusicController;
|
||||
|
@ -258,8 +259,7 @@ public class Game extends BasicGameState {
|
|||
|
||||
if (GameMod.AUTO.isActive())
|
||||
GameImage.UNRANKED.getImage().drawCentered(width / 2, height * 0.077f);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -365,16 +365,13 @@ public class Game extends BasicGameState {
|
|||
cursorCirclePulse.drawCentered(pausedMouseX, pausedMouseY);
|
||||
}
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
skipButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
|
||||
|
@ -613,10 +610,10 @@ public class Game extends BasicGameState {
|
|||
}
|
||||
break;
|
||||
case Input.KEY_UP:
|
||||
Utils.changeVolume(1);
|
||||
UI.changeVolume(1);
|
||||
break;
|
||||
case Input.KEY_DOWN:
|
||||
Utils.changeVolume(-1);
|
||||
UI.changeVolume(-1);
|
||||
break;
|
||||
case Input.KEY_F12:
|
||||
Utils.takeScreenShot();
|
||||
|
@ -697,12 +694,13 @@ public class Game extends BasicGameState {
|
|||
if (Options.isMouseWheelDisabled() || Options.isMouseDisabled())
|
||||
return;
|
||||
|
||||
Utils.changeVolume((newValue < 0) ? -1 : 1);
|
||||
UI.changeVolume((newValue < 0) ? -1 : 1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
if (restart == Restart.NEW)
|
||||
osu = MusicController.getOsuFile();
|
||||
|
||||
|
|
|
@ -22,6 +22,7 @@ import itdelatrisu.opsu.GameImage;
|
|||
import itdelatrisu.opsu.MenuButton;
|
||||
import itdelatrisu.opsu.Opsu;
|
||||
import itdelatrisu.opsu.Options;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.MusicController;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
|
@ -99,16 +100,13 @@ public class GamePauseMenu extends BasicGameState {
|
|||
retryButton.draw();
|
||||
backButton.draw();
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
continueButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
retryButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
|
@ -135,7 +133,7 @@ public class GamePauseMenu extends BasicGameState {
|
|||
SoundController.playSound(SoundEffect.MENUBACK);
|
||||
((SongMenu) game.getState(Opsu.STATE_SONGMENU)).resetGameDataOnLoad();
|
||||
MusicController.playAt(MusicController.getOsuFile().previewTime, true);
|
||||
Utils.resetCursor();
|
||||
UI.resetCursor();
|
||||
game.enterState(Opsu.STATE_SONGMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
} else {
|
||||
SoundController.playSound(SoundEffect.MENUBACK);
|
||||
|
@ -182,7 +180,7 @@ public class GamePauseMenu extends BasicGameState {
|
|||
MusicController.playAt(MusicController.getOsuFile().previewTime, true);
|
||||
else
|
||||
MusicController.resume();
|
||||
Utils.resetCursor();
|
||||
UI.resetCursor();
|
||||
game.enterState(Opsu.STATE_SONGMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
}
|
||||
}
|
||||
|
@ -190,6 +188,7 @@ public class GamePauseMenu extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
pauseStartTime = System.currentTimeMillis();
|
||||
if (gameState.getRestart() == Game.Restart.LOSE) {
|
||||
MusicController.fadeOut(FADEOUT_TIME);
|
||||
|
|
|
@ -23,6 +23,7 @@ import itdelatrisu.opsu.GameImage;
|
|||
import itdelatrisu.opsu.MenuButton;
|
||||
import itdelatrisu.opsu.Opsu;
|
||||
import itdelatrisu.opsu.OsuFile;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.MusicController;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
|
@ -108,24 +109,21 @@ public class GameRanking extends BasicGameState {
|
|||
retryButton.draw();
|
||||
exitButton.draw();
|
||||
}
|
||||
Utils.getBackButton().draw();
|
||||
UI.getBackButton().draw();
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
if (data.isGameplay()) {
|
||||
retryButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
exitButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
}
|
||||
Utils.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
UI.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -161,12 +159,12 @@ public class GameRanking extends BasicGameState {
|
|||
SoundController.playSound(SoundEffect.MENUBACK);
|
||||
((MainMenu) game.getState(Opsu.STATE_MAINMENU)).reset();
|
||||
((SongMenu) game.getState(Opsu.STATE_SONGMENU)).resetGameDataOnLoad();
|
||||
Utils.resetCursor();
|
||||
UI.resetCursor();
|
||||
game.enterState(Opsu.STATE_MAINMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (Utils.getBackButton().contains(x, y)) {
|
||||
if (UI.getBackButton().contains(x, y)) {
|
||||
returnToSongMenu();
|
||||
return;
|
||||
}
|
||||
|
@ -175,8 +173,8 @@ public class GameRanking extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
Display.setTitle(game.getTitle());
|
||||
Utils.getBackButton().resetHover();
|
||||
if (!data.isGameplay()) {
|
||||
if (!MusicController.isTrackDimmed())
|
||||
MusicController.toggleTrackDimmed(0.5f);
|
||||
|
@ -203,7 +201,7 @@ public class GameRanking extends BasicGameState {
|
|||
songMenu.resetGameDataOnLoad();
|
||||
songMenu.resetTrackOnLoad();
|
||||
}
|
||||
Utils.resetCursor();
|
||||
UI.resetCursor();
|
||||
game.enterState(Opsu.STATE_SONGMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
}
|
||||
|
||||
|
|
|
@ -27,6 +27,7 @@ import itdelatrisu.opsu.Options;
|
|||
import itdelatrisu.opsu.OsuFile;
|
||||
import itdelatrisu.opsu.OsuGroupList;
|
||||
import itdelatrisu.opsu.OsuGroupNode;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.MusicController;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
|
@ -256,28 +257,23 @@ public class MainMenu extends BasicGameState {
|
|||
new SimpleDateFormat("h:mm a").format(new Date())),
|
||||
marginX, height - marginY - lineHeight);
|
||||
|
||||
Utils.drawBarNotification(g);
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
|
||||
// tooltips
|
||||
if (musicPositionBarContains(mouseX, mouseY))
|
||||
Utils.drawTooltip(g, "Click to seek to a specific point in the song.", false);
|
||||
UI.drawTooltip(g, "Click to seek to a specific point in the song.", false);
|
||||
else if (musicPlay.contains(mouseX, mouseY))
|
||||
Utils.drawTooltip(g, (MusicController.isPlaying()) ? "Pause" : "Play", false);
|
||||
UI.drawTooltip(g, (MusicController.isPlaying()) ? "Pause" : "Play", false);
|
||||
else if (musicNext.contains(mouseX, mouseY))
|
||||
Utils.drawTooltip(g, "Next track", false);
|
||||
UI.drawTooltip(g, "Next track", false);
|
||||
else if (musicPrevious.contains(mouseX, mouseY))
|
||||
Utils.drawTooltip(g, "Previous track", false);
|
||||
UI.drawTooltip(g, "Previous track", false);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
Utils.updateBarNotification(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
logo.hoverUpdate(delta, mouseX, mouseY, 0.25f);
|
||||
playButton.hoverUpdate(delta, mouseX, mouseY, 0.25f);
|
||||
|
@ -350,6 +346,8 @@ public class MainMenu extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
|
||||
// reset button hover states if mouse is not currently hovering over the button
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
if (!logo.contains(mouseX, mouseY, 0.25f))
|
||||
|
@ -392,10 +390,10 @@ public class MainMenu extends BasicGameState {
|
|||
if (musicPlay.contains(x, y)) {
|
||||
if (MusicController.isPlaying()) {
|
||||
MusicController.pause();
|
||||
Utils.sendBarNotification("Pause");
|
||||
UI.sendBarNotification("Pause");
|
||||
} else if (!MusicController.isTrackLoading()) {
|
||||
MusicController.resume();
|
||||
Utils.sendBarNotification("Play");
|
||||
UI.sendBarNotification("Play");
|
||||
}
|
||||
} else if (musicNext.contains(x, y)) {
|
||||
boolean isTheme = MusicController.isThemePlaying();
|
||||
|
@ -409,7 +407,7 @@ public class MainMenu extends BasicGameState {
|
|||
}
|
||||
if (Options.isDynamicBackgroundEnabled() && !sameAudio && !MusicController.isThemePlaying())
|
||||
bgAlpha = 0f;
|
||||
Utils.sendBarNotification(">> Next");
|
||||
UI.sendBarNotification(">> Next");
|
||||
} else if (musicPrevious.contains(x, y)) {
|
||||
if (!previous.isEmpty()) {
|
||||
SongMenu menu = (SongMenu) game.getState(Opsu.STATE_SONGMENU);
|
||||
|
@ -418,7 +416,7 @@ public class MainMenu extends BasicGameState {
|
|||
bgAlpha = 0f;
|
||||
} else
|
||||
MusicController.setPosition(0);
|
||||
Utils.sendBarNotification("<< Previous");
|
||||
UI.sendBarNotification("<< Previous");
|
||||
}
|
||||
|
||||
// downloads button actions
|
||||
|
@ -459,7 +457,7 @@ public class MainMenu extends BasicGameState {
|
|||
|
||||
@Override
|
||||
public void mouseWheelMoved(int newValue) {
|
||||
Utils.changeVolume((newValue < 0) ? -1 : 1);
|
||||
UI.changeVolume((newValue < 0) ? -1 : 1);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -483,10 +481,10 @@ public class MainMenu extends BasicGameState {
|
|||
}
|
||||
break;
|
||||
case Input.KEY_UP:
|
||||
Utils.changeVolume(1);
|
||||
UI.changeVolume(1);
|
||||
break;
|
||||
case Input.KEY_DOWN:
|
||||
Utils.changeVolume(-1);
|
||||
UI.changeVolume(-1);
|
||||
break;
|
||||
case Input.KEY_F12:
|
||||
Utils.takeScreenShot();
|
||||
|
|
|
@ -23,6 +23,7 @@ import itdelatrisu.opsu.MenuButton;
|
|||
import itdelatrisu.opsu.Opsu;
|
||||
import itdelatrisu.opsu.Options;
|
||||
import itdelatrisu.opsu.Options.GameOption;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
import itdelatrisu.opsu.audio.SoundEffect;
|
||||
|
@ -224,10 +225,10 @@ public class OptionsMenu extends BasicGameState {
|
|||
}
|
||||
for (OptionTab tab : OptionTab.VALUES_REVERSED) {
|
||||
if (tab != currentTab)
|
||||
Utils.drawTab(tab.button.getX(), tab.button.getY(),
|
||||
UI.drawTab(tab.button.getX(), tab.button.getY(),
|
||||
tab.getName(), false, tab == hoverTab);
|
||||
}
|
||||
Utils.drawTab(currentTab.button.getX(), currentTab.button.getY(),
|
||||
UI.drawTab(currentTab.button.getX(), currentTab.button.getY(),
|
||||
currentTab.getName(), true, false);
|
||||
g.setColor(Color.white);
|
||||
g.setLineWidth(2f);
|
||||
|
@ -235,7 +236,7 @@ public class OptionsMenu extends BasicGameState {
|
|||
g.drawLine(0, lineY, width, lineY);
|
||||
g.resetLineWidth();
|
||||
|
||||
Utils.getBackButton().draw();
|
||||
UI.getBackButton().draw();
|
||||
|
||||
// key entry state
|
||||
if (keyEntryLeft || keyEntryRight) {
|
||||
|
@ -248,18 +249,15 @@ public class OptionsMenu extends BasicGameState {
|
|||
);
|
||||
}
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
Utils.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
UI.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -278,7 +276,7 @@ public class OptionsMenu extends BasicGameState {
|
|||
return;
|
||||
|
||||
// back
|
||||
if (Utils.getBackButton().contains(x, y)) {
|
||||
if (UI.getBackButton().contains(x, y)) {
|
||||
SoundController.playSound(SoundEffect.MENUBACK);
|
||||
game.enterState(Opsu.STATE_SONGMENU, new EmptyTransition(), new FadeInTransition(Color.black));
|
||||
return;
|
||||
|
@ -381,8 +379,8 @@ public class OptionsMenu extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
currentTab = OptionTab.DISPLAY;
|
||||
Utils.getBackButton().resetHover();
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -32,6 +32,7 @@ import itdelatrisu.opsu.OsuParser;
|
|||
import itdelatrisu.opsu.OszUnpacker;
|
||||
import itdelatrisu.opsu.ScoreData;
|
||||
import itdelatrisu.opsu.SongSort;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.HitSound;
|
||||
import itdelatrisu.opsu.audio.MultiClip;
|
||||
|
@ -433,7 +434,7 @@ public class SongMenu extends BasicGameState {
|
|||
startIndex += focusNodes;
|
||||
else if (startNode.index == focusNode.index)
|
||||
startIndex += startNode.osuFileIndex;
|
||||
Utils.drawScrollbar(g, startIndex, totalNodes, MAX_SONG_BUTTONS,
|
||||
UI.drawScrollbar(g, startIndex, totalNodes, MAX_SONG_BUTTONS,
|
||||
width, headerY + DIVIDER_LINE_WIDTH / 2, 0, buttonOffset - DIVIDER_LINE_WIDTH * 1.5f, buttonOffset,
|
||||
Utils.COLOR_BLACK_ALPHA, Color.white, true);
|
||||
}
|
||||
|
@ -445,25 +446,22 @@ public class SongMenu extends BasicGameState {
|
|||
g.setColor(Utils.COLOR_BLACK_ALPHA);
|
||||
g.fillRect(0, 0, width, height);
|
||||
|
||||
Utils.drawLoadingProgress(g);
|
||||
UI.drawLoadingProgress(g);
|
||||
}
|
||||
|
||||
// back button
|
||||
else
|
||||
Utils.getBackButton().draw();
|
||||
UI.getBackButton().draw();
|
||||
|
||||
Utils.drawVolume(g);
|
||||
Utils.drawFPS();
|
||||
Utils.drawCursor();
|
||||
UI.draw(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(GameContainer container, StateBasedGame game, int delta)
|
||||
throws SlickException {
|
||||
Utils.updateCursor(delta);
|
||||
Utils.updateVolumeDisplay(delta);
|
||||
UI.update(delta);
|
||||
int mouseX = input.getMouseX(), mouseY = input.getMouseY();
|
||||
Utils.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
UI.getBackButton().hoverUpdate(delta, mouseX, mouseY);
|
||||
selectModsButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
selectRandomButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
selectMapOptionsButton.hoverUpdate(delta, mouseX, mouseY);
|
||||
|
@ -584,7 +582,7 @@ public class SongMenu extends BasicGameState {
|
|||
return;
|
||||
|
||||
// back
|
||||
if (Utils.getBackButton().contains(x, y)) {
|
||||
if (UI.getBackButton().contains(x, y)) {
|
||||
SoundController.playSound(SoundEffect.MENUBACK);
|
||||
((MainMenu) game.getState(Opsu.STATE_MAINMENU)).reset();
|
||||
game.enterState(Opsu.STATE_MAINMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black));
|
||||
|
@ -881,8 +879,8 @@ public class SongMenu extends BasicGameState {
|
|||
@Override
|
||||
public void enter(GameContainer container, StateBasedGame game)
|
||||
throws SlickException {
|
||||
UI.enter();
|
||||
Display.setTitle(game.getTitle());
|
||||
Utils.getBackButton().resetHover();
|
||||
selectModsButton.resetHover();
|
||||
selectRandomButton.resetHover();
|
||||
selectMapOptionsButton.resetHover();
|
||||
|
|
|
@ -24,6 +24,7 @@ import itdelatrisu.opsu.Options;
|
|||
import itdelatrisu.opsu.OsuGroupList;
|
||||
import itdelatrisu.opsu.OsuParser;
|
||||
import itdelatrisu.opsu.OszUnpacker;
|
||||
import itdelatrisu.opsu.UI;
|
||||
import itdelatrisu.opsu.Utils;
|
||||
import itdelatrisu.opsu.audio.MusicController;
|
||||
import itdelatrisu.opsu.audio.SoundController;
|
||||
|
@ -79,7 +80,7 @@ public class Splash extends BasicGameState {
|
|||
throws SlickException {
|
||||
g.setBackground(Color.black);
|
||||
GameImage.MENU_LOGO.getImage().drawCentered(container.getWidth() / 2, container.getHeight() / 2);
|
||||
Utils.drawLoadingProgress(g);
|
||||
UI.drawLoadingProgress(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
Loading…
Reference in New Issue
Block a user