saner transition management
This commit is contained in:
parent
0a0320e81a
commit
1ebf2c2dcb
|
@ -62,8 +62,6 @@ import yugecin.opsudance.core.events.EventBus;
|
|||
import yugecin.opsudance.core.inject.Inject;
|
||||
import yugecin.opsudance.core.inject.InstanceContainer;
|
||||
import yugecin.opsudance.core.state.ComplexOpsuState;
|
||||
import yugecin.opsudance.core.state.transitions.FadeInTransitionState;
|
||||
import yugecin.opsudance.core.state.transitions.FadeOutTransitionState;
|
||||
import yugecin.opsudance.events.BarNotificationEvent;
|
||||
import yugecin.opsudance.events.BubbleNotificationEvent;
|
||||
import yugecin.opsudance.objects.curves.FakeCombinedCurve;
|
||||
|
@ -766,7 +764,7 @@ public class Game extends ComplexOpsuState {
|
|||
|
||||
// focus lost: go back to pause screen
|
||||
else if (!Display.isActive()) {
|
||||
displayContainer.switchStateNow(GamePauseMenu.class);
|
||||
displayContainer.switchState(GamePauseMenu.class);
|
||||
pausePulse = 0f;
|
||||
}
|
||||
|
||||
|
@ -1050,7 +1048,7 @@ public class Game extends ComplexOpsuState {
|
|||
if (MusicController.isPlaying() || isLeadIn()) {
|
||||
pauseTime = trackPosition;
|
||||
}
|
||||
displayContainer.switchStateNow(GamePauseMenu.class);
|
||||
displayContainer.switchStateInstantly(GamePauseMenu.class);
|
||||
}
|
||||
|
||||
// drain health
|
||||
|
@ -1077,7 +1075,7 @@ public class Game extends ComplexOpsuState {
|
|||
rotations = new IdentityHashMap<>();
|
||||
SoundController.playSound(SoundEffect.FAIL);
|
||||
|
||||
displayContainer.switchState(GamePauseMenu.class, FadeOutTransitionState.class, MUSIC_FADEOUT_TIME - LOSE_FADEOUT_TIME, FadeInTransitionState.class, 300);
|
||||
displayContainer.switchState(GamePauseMenu.class, MUSIC_FADEOUT_TIME - LOSE_FADEOUT_TIME, 300);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1158,7 +1156,7 @@ public class Game extends ComplexOpsuState {
|
|||
if (MusicController.isPlaying() || isLeadIn()) {
|
||||
pauseTime = trackPosition;
|
||||
}
|
||||
displayContainer.switchStateNow(GamePauseMenu.class);
|
||||
displayContainer.switchStateInstantly(GamePauseMenu.class);
|
||||
break;
|
||||
case Input.KEY_SPACE:
|
||||
// skip intro
|
||||
|
@ -1311,7 +1309,7 @@ public class Game extends ComplexOpsuState {
|
|||
if (MusicController.isPlaying() || isLeadIn()) {
|
||||
pauseTime = trackPosition;
|
||||
}
|
||||
displayContainer.switchStateNow(GamePauseMenu.class);
|
||||
displayContainer.switchStateInstantly(GamePauseMenu.class);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -48,7 +48,6 @@ import yugecin.opsudance.core.state.OpsuState;
|
|||
import yugecin.opsudance.core.state.specialstates.BarNotificationState;
|
||||
import yugecin.opsudance.core.state.specialstates.BubbleNotificationState;
|
||||
import yugecin.opsudance.core.state.specialstates.FpsRenderState;
|
||||
import yugecin.opsudance.core.state.transitions.*;
|
||||
import yugecin.opsudance.events.BubbleNotificationEvent;
|
||||
import yugecin.opsudance.events.ResolutionOrSkinChangedEvent;
|
||||
import yugecin.opsudance.options.Configuration;
|
||||
|
@ -79,12 +78,6 @@ public class DisplayContainer implements ErrorDumpable, KeyListener, MouseListen
|
|||
private BarNotificationState barNotifState;
|
||||
private BubbleNotificationState bubNotifState;
|
||||
|
||||
private TransitionState outTransitionState;
|
||||
private TransitionState inTransitionState;
|
||||
|
||||
private final TransitionFinishedListener outTransitionListener;
|
||||
private final TransitionFinishedListener inTransitionListener;
|
||||
|
||||
private OpsuState state;
|
||||
|
||||
public final DisplayMode nativeDisplayMode;
|
||||
|
@ -123,31 +116,52 @@ public class DisplayContainer implements ErrorDumpable, KeyListener, MouseListen
|
|||
public final Cursor cursor;
|
||||
public boolean drawCursor;
|
||||
|
||||
class Transition {
|
||||
int in;
|
||||
int out;
|
||||
int total;
|
||||
int progress = -1;
|
||||
OpsuState nextstate;
|
||||
Color OVERLAY = new Color(Color.black);
|
||||
|
||||
public void update() {
|
||||
if (progress == -1) {
|
||||
return;
|
||||
}
|
||||
progress += delta;
|
||||
if (progress > out && nextstate != null) {
|
||||
switchStateInstantly(nextstate);
|
||||
nextstate = null;
|
||||
}
|
||||
if (progress > total) {
|
||||
progress = -1;
|
||||
}
|
||||
}
|
||||
|
||||
public void render(Graphics graphics) {
|
||||
if (progress == -1) {
|
||||
return;
|
||||
}
|
||||
int relprogress = progress;
|
||||
int reltotal = out;
|
||||
if (progress > out) {
|
||||
reltotal = in;
|
||||
relprogress = total - progress;
|
||||
}
|
||||
OVERLAY.a = (float) relprogress / reltotal;
|
||||
graphics.setColor(OVERLAY);
|
||||
graphics.fillRect(0, 0, width, height);
|
||||
}
|
||||
}
|
||||
|
||||
private final Transition transition = new Transition();
|
||||
|
||||
@Inject
|
||||
public DisplayContainer(InstanceContainer instanceContainer) {
|
||||
this.instanceContainer = instanceContainer;
|
||||
this.cursor = new Cursor();
|
||||
drawCursor = true;
|
||||
|
||||
outTransitionListener = new TransitionFinishedListener() {
|
||||
@Override
|
||||
public void onFinish() {
|
||||
state.leave();
|
||||
outTransitionState.getApplicableState().leave();
|
||||
state = inTransitionState;
|
||||
state.enter();
|
||||
inTransitionState.getApplicableState().enter();
|
||||
}
|
||||
};
|
||||
|
||||
inTransitionListener = new TransitionFinishedListener() {
|
||||
@Override
|
||||
public void onFinish() {
|
||||
state.leave();
|
||||
state = inTransitionState.getApplicableState();
|
||||
}
|
||||
};
|
||||
|
||||
EventBus.subscribe(ResolutionOrSkinChangedEvent.class, new EventListener<ResolutionOrSkinChangedEvent>() {
|
||||
@Override
|
||||
public void onEvent(ResolutionOrSkinChangedEvent event) {
|
||||
|
@ -220,6 +234,7 @@ public class DisplayContainer implements ErrorDumpable, KeyListener, MouseListen
|
|||
mouseX = input.getMouseX();
|
||||
mouseY = input.getMouseY();
|
||||
|
||||
transition.update();
|
||||
fpsState.update();
|
||||
|
||||
state.update();
|
||||
|
@ -258,6 +273,8 @@ public class DisplayContainer implements ErrorDumpable, KeyListener, MouseListen
|
|||
}
|
||||
UI.drawTooltip(graphics);
|
||||
|
||||
transition.render(graphics);
|
||||
|
||||
timeSinceLastRender = 0;
|
||||
|
||||
Display.update(false);
|
||||
|
@ -454,16 +471,6 @@ public class DisplayContainer implements ErrorDumpable, KeyListener, MouseListen
|
|||
public void writeErrorDump(StringWriter dump) {
|
||||
dump.append("> DisplayContainer dump\n");
|
||||
dump.append("OpenGL version: ").append(glVersion).append( "(").append(glVendor).append(")\n");
|
||||
if (isTransitioning()) {
|
||||
dump.append("doing a transition\n");
|
||||
dump.append("using out transition ").append(outTransitionState.getClass().getSimpleName()).append('\n');
|
||||
dump.append("using in transition ").append(inTransitionState.getClass().getSimpleName()).append('\n');
|
||||
if (state == inTransitionState) {
|
||||
dump.append("currently doing the in transition\n");
|
||||
} else {
|
||||
dump.append("currently doing the out transition\n");
|
||||
}
|
||||
}
|
||||
state.writeErrorDump(dump);
|
||||
}
|
||||
|
||||
|
@ -471,32 +478,37 @@ public class DisplayContainer implements ErrorDumpable, KeyListener, MouseListen
|
|||
return state.isInstance(state);
|
||||
}
|
||||
|
||||
public boolean isTransitioning() {
|
||||
return state instanceof TransitionState;
|
||||
}
|
||||
|
||||
public void switchState(Class<? extends OpsuState> newState) {
|
||||
switchState(newState, FadeOutTransitionState.class, 200, FadeInTransitionState.class, 300);
|
||||
}
|
||||
|
||||
public void switchStateNow(Class<? extends OpsuState> newState) {
|
||||
switchState(newState, EmptyTransitionState.class, 0, FadeInTransitionState.class, 300);
|
||||
}
|
||||
|
||||
public void switchStateInstantly(Class<? extends OpsuState> newState) {
|
||||
state.leave();
|
||||
state = instanceContainer.provide(newState);
|
||||
state.enter();
|
||||
}
|
||||
|
||||
public void switchState(Class<? extends OpsuState> newState, Class<? extends TransitionState> outTransition, int outTime, Class<? extends TransitionState> inTransition, int inTime) {
|
||||
if (isTransitioning()) {
|
||||
public void switchState(Class<? extends OpsuState> newState, int outtime, int intime) {
|
||||
if (transition.progress != -1) {
|
||||
return;
|
||||
}
|
||||
outTransitionState = instanceContainer.provide(outTransition).set(state, outTime, outTransitionListener);
|
||||
inTransitionState = instanceContainer.provide(inTransition).set(instanceContainer.provide(newState), inTime, inTransitionListener);
|
||||
state = outTransitionState;
|
||||
state.enter();
|
||||
// TODO remove this v
|
||||
OpsuState _newstate = instanceContainer.provide(newState);
|
||||
if (outtime == 0) {
|
||||
switchStateInstantly(_newstate);
|
||||
_newstate = null;
|
||||
}
|
||||
transition.nextstate = _newstate;
|
||||
transition.total = transition.in = intime;
|
||||
transition.out = outtime;
|
||||
transition.total += outtime;
|
||||
transition.progress = 0;
|
||||
}
|
||||
|
||||
@Deprecated // TODO instcontainer
|
||||
public void switchState(Class<? extends OpsuState> state) {
|
||||
switchState(state, 200, 300);
|
||||
}
|
||||
|
||||
@Deprecated // TODO instcontainer
|
||||
public void switchStateInstantly(Class<? extends OpsuState> state) {
|
||||
switchStateInstantly(instanceContainer.provide(state));
|
||||
}
|
||||
|
||||
public void switchStateInstantly(OpsuState state) {
|
||||
this.state.leave();
|
||||
this.state = state;
|
||||
this.state.enter();
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -13,6 +13,7 @@
|
|||
* 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.inject;
|
||||
|
@ -27,9 +28,6 @@ import yugecin.opsudance.core.DisplayContainer;
|
|||
import yugecin.opsudance.core.state.specialstates.BarNotificationState;
|
||||
import yugecin.opsudance.core.state.specialstates.BubbleNotificationState;
|
||||
import yugecin.opsudance.core.state.specialstates.FpsRenderState;
|
||||
import yugecin.opsudance.core.state.transitions.EmptyTransitionState;
|
||||
import yugecin.opsudance.core.state.transitions.FadeInTransitionState;
|
||||
import yugecin.opsudance.core.state.transitions.FadeOutTransitionState;
|
||||
import yugecin.opsudance.core.errorhandling.ErrorHandler;
|
||||
import yugecin.opsudance.options.Configuration;
|
||||
import yugecin.opsudance.options.OptionsService;
|
||||
|
@ -57,10 +55,6 @@ public class OpsuDanceInjector extends Injector {
|
|||
bind(BarNotificationState.class).asEagerSingleton();
|
||||
bind(BubbleNotificationState.class).asEagerSingleton();
|
||||
|
||||
bind(EmptyTransitionState.class).asEagerSingleton();
|
||||
bind(FadeInTransitionState.class).asEagerSingleton();
|
||||
bind(FadeOutTransitionState.class).asEagerSingleton();
|
||||
|
||||
bind(GameObjectRenderer.class).asEagerSingleton();
|
||||
|
||||
bind(Splash.class).asEagerSingleton();
|
||||
|
|
|
@ -1,27 +0,0 @@
|
|||
/*
|
||||
* opsu!dance - fork of opsu! with cursordance auto
|
||||
* Copyright (C) 2017 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.state.transitions;
|
||||
|
||||
public class EmptyTransitionState extends TransitionState {
|
||||
|
||||
@Override
|
||||
public void enter() {
|
||||
finish();
|
||||
}
|
||||
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
/*
|
||||
* opsu!dance - fork of opsu! with cursordance auto
|
||||
* Copyright (C) 2017 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.state.transitions;
|
||||
|
||||
public class FadeInTransitionState extends FadeTransitionState {
|
||||
|
||||
@Override
|
||||
protected float getMaskAlphaLevel(float fadeProgress) {
|
||||
return 1f - fadeProgress;
|
||||
}
|
||||
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
/*
|
||||
* opsu!dance - fork of opsu! with cursordance auto
|
||||
* Copyright (C) 2017 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.state.transitions;
|
||||
|
||||
public class FadeOutTransitionState extends FadeTransitionState {
|
||||
|
||||
@Override
|
||||
protected float getMaskAlphaLevel(float fadeProgress) {
|
||||
return fadeProgress;
|
||||
}
|
||||
|
||||
}
|
|
@ -1,42 +0,0 @@
|
|||
/*
|
||||
* opsu!dance - fork of opsu! with cursordance auto
|
||||
* Copyright (C) 2017 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.state.transitions;
|
||||
|
||||
import org.newdawn.slick.Color;
|
||||
import org.newdawn.slick.Graphics;
|
||||
|
||||
public abstract class FadeTransitionState extends TransitionState {
|
||||
|
||||
private final Color black;
|
||||
|
||||
public FadeTransitionState() {
|
||||
super();
|
||||
black = new Color(Color.black);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void render(Graphics g) {
|
||||
applicableState.render(g);
|
||||
black.a = getMaskAlphaLevel((float) transitionTime / transitionTargetTime);
|
||||
g.setColor(black);
|
||||
g.fillRect(0, 0, displayContainer.width, displayContainer.height);
|
||||
}
|
||||
|
||||
protected abstract float getMaskAlphaLevel(float fadeProgress);
|
||||
|
||||
}
|
|
@ -1,24 +0,0 @@
|
|||
/*
|
||||
* opsu!dance - fork of opsu! with cursordance auto
|
||||
* Copyright (C) 2017 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.state.transitions;
|
||||
|
||||
public interface TransitionFinishedListener {
|
||||
|
||||
void onFinish();
|
||||
|
||||
}
|
|
@ -1,93 +0,0 @@
|
|||
/*
|
||||
* opsu!dance - fork of opsu! with cursordance auto
|
||||
* Copyright (C) 2017 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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package yugecin.opsudance.core.state.transitions;
|
||||
|
||||
import org.newdawn.slick.Graphics;
|
||||
import yugecin.opsudance.core.state.BaseOpsuState;
|
||||
import yugecin.opsudance.core.state.OpsuState;
|
||||
|
||||
import java.io.StringWriter;
|
||||
|
||||
public abstract class TransitionState extends BaseOpsuState {
|
||||
|
||||
protected OpsuState applicableState;
|
||||
|
||||
protected int transitionTargetTime;
|
||||
protected int transitionTime;
|
||||
|
||||
private TransitionFinishedListener listener;
|
||||
|
||||
public final TransitionState set(OpsuState applicableState, int targetTime, TransitionFinishedListener listener) {
|
||||
this.applicableState = applicableState;
|
||||
this.transitionTargetTime = targetTime;
|
||||
this.listener = listener;
|
||||
return this;
|
||||
}
|
||||
|
||||
public final OpsuState getApplicableState() {
|
||||
return applicableState;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update() {
|
||||
applicableState.update();
|
||||
transitionTime += displayContainer.delta;
|
||||
if (transitionTime >= transitionTargetTime) {
|
||||
finish();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void preRenderUpdate() {
|
||||
applicableState.preRenderUpdate();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void render(Graphics g) {
|
||||
applicableState.render(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void enter() {
|
||||
super.enter();
|
||||
transitionTime = 0;
|
||||
}
|
||||
|
||||
protected final void finish() {
|
||||
listener.onFinish();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onCloseRequest() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeErrorDump(StringWriter dump) {
|
||||
dump.append("> TransitionState dump\n");
|
||||
dump.append("progress: ").append(String.valueOf(transitionTime)).append("/").append(String.valueOf(transitionTargetTime)).append('\n');
|
||||
dump.append("applicable state: ");
|
||||
if (applicableState == null) {
|
||||
dump.append("IS NULL");
|
||||
return;
|
||||
}
|
||||
dump.append(applicableState.getClass().getSimpleName()).append('\n');
|
||||
applicableState.writeErrorDump(dump);
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user