add: switch game by scrolling on the launch button

This commit is contained in:
huanghongxun
2020-03-01 16:01:11 +08:00
parent b117769711
commit de6cdeab52
4 changed files with 45 additions and 39 deletions

View File

@@ -15,23 +15,6 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
/*
* Hello Minecraft! Launcher
* Copyright (C) 2019 huangyuhui <huanghongxun2008@126.com> and contributors
*
* This program 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.
*
* This program 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 this program. If not, see <https://www.gnu.org/licenses/>.
*/
package org.jackhuang.hmcl.ui;
import com.jfoenix.controls.JFXButton;

View File

@@ -70,9 +70,9 @@ public class AccountAdvancedListItem extends AdvancedListItem {
ObservableList<Account> accounts = Accounts.getAccounts();
int currentIndex = accounts.indexOf(account.get());
if (event.getDeltaY() > 0) { // up
currentIndex += 1;
currentIndex--;
} else { // down
currentIndex -= 1;
currentIndex++;
}
Accounts.setSelectedAccount(accounts.get((currentIndex + accounts.size()) % accounts.size()));
});

View File

@@ -36,6 +36,7 @@ import javafx.scene.layout.VBox;
import javafx.scene.shape.Rectangle;
import javafx.util.Duration;
import org.jackhuang.hmcl.Metadata;
import org.jackhuang.hmcl.game.Version;
import org.jackhuang.hmcl.setting.Profile;
import org.jackhuang.hmcl.setting.Profiles;
import org.jackhuang.hmcl.setting.Theme;
@@ -44,10 +45,15 @@ import org.jackhuang.hmcl.ui.SVG;
import org.jackhuang.hmcl.ui.construct.PopupMenu;
import org.jackhuang.hmcl.ui.construct.TwoLineListItem;
import org.jackhuang.hmcl.ui.decorator.DecoratorPage;
import org.jackhuang.hmcl.ui.versions.GameItem;
import org.jackhuang.hmcl.ui.versions.Versions;
import org.jackhuang.hmcl.upgrade.RemoteVersion;
import org.jackhuang.hmcl.upgrade.UpdateChecker;
import org.jackhuang.hmcl.upgrade.UpdateHandler;
import org.jackhuang.hmcl.util.javafx.MappedObservableList;
import java.util.List;
import java.util.stream.IntStream;
import static org.jackhuang.hmcl.ui.FXUtils.SINE;
import static org.jackhuang.hmcl.util.i18n.I18n.i18n;
@@ -61,7 +67,9 @@ public final class MainPage extends StackPane implements DecoratorPage {
private final StringProperty currentGame = new SimpleStringProperty(this, "currentGame");
private final BooleanProperty showUpdate = new SimpleBooleanProperty(this, "showUpdate");
private final StringProperty latestVersion = new SimpleStringProperty(this, "latestVersion");
private final ObservableList<Node> versions = FXCollections.observableArrayList();
private final ObservableList<Version> versions = FXCollections.observableArrayList();
private final ObservableList<Node> versionNodes;
private Profile profile;
private StackPane updatePane;
private JFXButton menuButton;
@@ -109,6 +117,18 @@ public final class MainPage extends StackPane implements DecoratorPage {
StackPane launchPane = new StackPane();
launchPane.setMaxWidth(230);
launchPane.setMaxHeight(55);
launchPane.setOnScroll(event -> {
int index = IntStream.range(0, versions.size())
.filter(i -> versions.get(i).getId().equals(getCurrentGame()))
.findFirst().orElse(-1);
if (index < 0) return;
if (event.getDeltaY() > 0) {
index--;
} else {
index++;
}
profile.setSelectedVersion(versions.get((index + versions.size()) % versions.size()).getId());
});
StackPane.setAlignment(launchPane, Pos.BOTTOM_RIGHT);
{
JFXButton launchButton = new JFXButton();
@@ -128,7 +148,13 @@ public final class MainPage extends StackPane implements DecoratorPage {
launchLabel.setStyle("-fx-font-size: 16px;");
Label currentLabel = new Label();
currentLabel.setStyle("-fx-font-size: 12px;");
currentLabel.textProperty().bind(currentGameProperty());
currentLabel.textProperty().bind(Bindings.createStringBinding(() -> {
if (getCurrentGame() == null) {
return i18n("version.empty");
} else {
return getCurrentGame();
}
}, currentGameProperty()));
graphic.getChildren().setAll(launchLabel, currentLabel);
launchButton.setGraphic(graphic);
@@ -165,7 +191,12 @@ public final class MainPage extends StackPane implements DecoratorPage {
menu.setMaxWidth(545);
menu.setAlwaysShowingVBar(true);
menu.setOnMouseClicked(e -> popup.hide());
Bindings.bindContent(menu.getContent(), versions);
versionNodes = MappedObservableList.create(versions, version -> {
Node node = PopupMenu.wrapPopupMenuItem(new GameItem(profile, version.getId()));
node.setOnMouseClicked(e -> profile.setSelectedVersion(version.getId()));
return node;
});
Bindings.bindContent(menu.getContent(), versionNodes);
}
private void doAnimation(boolean show) {
@@ -254,7 +285,9 @@ public final class MainPage extends StackPane implements DecoratorPage {
this.latestVersion.set(latestVersion);
}
public ObservableList<Node> getVersions() {
return versions;
public void initVersions(Profile profile, List<Version> versions) {
FXUtils.checkFxUserThread();
this.profile = profile;
this.versions.setAll(versions);
}
}

View File

@@ -89,19 +89,13 @@ public class RootPage extends DecoratorNavigatorPage {
private MainPage getMainPage() {
if (mainPage == null) {
mainPage = new MainPage();
MainPage mainPage = new MainPage();
FXUtils.applyDragListener(mainPage, it -> "zip".equals(FileUtils.getExtension(it)), modpacks -> {
File modpack = modpacks.get(0);
Controllers.getDecorator().startWizard(new ModpackInstallWizardProvider(Profiles.getSelectedProfile(), modpack), i18n("install.modpack"));
});
FXUtils.onChangeAndOperate(Profiles.selectedVersionProperty(), version -> {
if (version != null) {
mainPage.setCurrentGame(version);
} else {
mainPage.setCurrentGame(i18n("version.empty"));
}
});
FXUtils.onChangeAndOperate(Profiles.selectedVersionProperty(), mainPage::setCurrentGame);
mainPage.showUpdateProperty().bind(UpdateChecker.outdatedProperty());
mainPage.latestVersionProperty().bind(
BindingMapping.of(UpdateChecker.latestVersionProperty())
@@ -109,21 +103,17 @@ public class RootPage extends DecoratorNavigatorPage {
Profiles.registerVersionsListener(profile -> {
HMCLGameRepository repository = profile.getRepository();
List<Node> children = repository.getVersions().parallelStream()
List<Version> children = repository.getVersions().parallelStream()
.filter(version -> !version.isHidden())
.sorted(Comparator.comparing((Version version) -> version.getReleaseTime() == null ? new Date(0L) : version.getReleaseTime())
.thenComparing(a -> VersionNumber.asVersion(a.getId())))
.map(version -> {
Node node = PopupMenu.wrapPopupMenuItem(new GameItem(profile, version.getId()));
node.setOnMouseClicked(e -> profile.setSelectedVersion(version.getId()));
return node;
})
.collect(Collectors.toList());
runInFX(() -> {
if (profile == Profiles.getSelectedProfile())
mainPage.getVersions().setAll(children);
mainPage.initVersions(profile, children);
});
});
this.mainPage = mainPage;
}
return mainPage;
}