feat: notification of dev/nightly version.

This commit is contained in:
huanghongxun
2021-09-28 12:54:54 +08:00
parent b556c51307
commit e476460ab4
9 changed files with 192 additions and 9 deletions

View File

@@ -43,6 +43,8 @@ public final class Metadata {
public static final String PUBLISH_URL = "http://www.mcbbs.net/thread-142335-1-1.html";
public static final String EULA_URL = "https://hmcl.huangyuhui.net/eula";
public static final String BUILD_CHANNEL = JarUtils.thisJar().flatMap(JarUtils::getManifest).map(manifest -> manifest.getMainAttributes().getValue("Build-Channel")).orElse("nightly");
public static final Path MINECRAFT_DIRECTORY = OperatingSystem.getWorkingDirectory("minecraft");
public static final Path HMCL_DIRECTORY = getHMCLDirectory();
@@ -54,4 +56,16 @@ public final class Metadata {
}
return OperatingSystem.getWorkingDirectory("hmcl");
}
public static boolean isStable() {
return "stable".equals(BUILD_CHANNEL);
}
public static boolean isDev() {
return "dev".equals(BUILD_CHANNEL);
}
public static boolean isNightly() {
return !isStable() && !isDev();
}
}

View File

@@ -44,10 +44,13 @@ import javafx.scene.layout.Priority;
import javafx.scene.layout.Region;
import javafx.scene.layout.StackPane;
import javafx.scene.shape.Rectangle;
import javafx.scene.text.Text;
import javafx.scene.text.TextFlow;
import javafx.util.Callback;
import javafx.util.Duration;
import javafx.util.StringConverter;
import org.jackhuang.hmcl.task.Schedulers;
import org.jackhuang.hmcl.ui.construct.JFXHyperlink;
import org.jackhuang.hmcl.util.Logging;
import org.jackhuang.hmcl.util.ResourceNotFoundError;
import org.jackhuang.hmcl.util.i18n.I18n;
@@ -55,9 +58,17 @@ import org.jackhuang.hmcl.util.io.FileUtils;
import org.jackhuang.hmcl.util.javafx.ExtendedProperties;
import org.jackhuang.hmcl.util.javafx.SafeStringConverter;
import org.jackhuang.hmcl.util.platform.OperatingSystem;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;
import org.xml.sax.SAXException;
import javax.swing.*;
import javax.swing.event.HyperlinkEvent;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
@@ -65,6 +76,7 @@ import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
import java.net.URI;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.function.BooleanSupplier;
@@ -687,4 +699,36 @@ public final class FXUtils {
Controllers.showToast(i18n("message.copied"));
}
public static TextFlow segmentToTextFlow(final String segment, Consumer<String> hyperlinkAction) throws ParserConfigurationException, IOException, SAXException {
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document doc = builder.parse(new InputSource(new StringReader("<body>" + segment + "</body>")));
Element r = doc.getDocumentElement();
NodeList children = r.getChildNodes();
List<javafx.scene.Node> texts = new ArrayList<>();
for (int i = 0; i < children.getLength(); i++) {
org.w3c.dom.Node node = children.item(i);
if (node instanceof Element) {
Element element = (Element) node;
if ("a".equals(element.getTagName())) {
String href = element.getAttribute("href");
JFXHyperlink hyperlink = new JFXHyperlink(element.getTextContent());
hyperlink.setOnAction(e -> hyperlinkAction.accept(href));
texts.add(hyperlink);
} else if ("br".equals(element.getTagName())) {
texts.add(new Text("\n"));
} else {
throw new IllegalArgumentException("unsupported tag " + element.getTagName());
}
} else {
texts.add(new Text(node.getTextContent()));
}
}
final TextFlow tf = new TextFlow(texts.toArray(new javafx.scene.Node[0]));
return tf;
}
}

View File

@@ -0,0 +1,60 @@
/*
* Hello Minecraft! Launcher
* Copyright (C) 2021 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.construct;
import javafx.scene.control.Label;
import javafx.scene.layout.VBox;
import javafx.scene.text.Text;
import javafx.scene.text.TextFlow;
import org.jackhuang.hmcl.ui.Controllers;
import org.jackhuang.hmcl.ui.FXUtils;
import java.util.logging.Level;
import static org.jackhuang.hmcl.util.Logging.LOG;
public class AnnouncementCard extends VBox {
public AnnouncementCard(String title, String content) {
TextFlow tf;
try {
tf = FXUtils.segmentToTextFlow(content, AnnouncementCard::onAction);
} catch (Exception e) {
LOG.log(Level.WARNING, "Failed to parse announcement content", e);
tf = new TextFlow();
tf.getChildren().setAll(new Text(content));
}
Label label = new Label(title);
label.getStyleClass().add("title");
getChildren().setAll(label, tf);
setSpacing(14);
getStyleClass().addAll("card", "announcement");
}
private static void onAction(String href) {
if (href.startsWith("hmcl://")) {
if ("hmcl://settings/feedback".equals(href)) {
Controllers.getSettingsPage().showFeedback();
Controllers.navigate(Controllers.getSettingsPage());
}
} else {
FXUtils.openLink(href);
}
}
}

View File

@@ -130,6 +130,10 @@ public class LauncherSettingsPage extends BorderPane implements DecoratorPage {
tab.getSelectionModel().select(gameTab);
}
public void showFeedback() {
tab.getSelectionModel().select(feedbackTab);
}
@Override
public ReadOnlyObjectProperty<State> stateProperty() {
return state.getReadOnlyProperty();

View File

@@ -44,6 +44,7 @@ import org.jackhuang.hmcl.setting.Profiles;
import org.jackhuang.hmcl.setting.Theme;
import org.jackhuang.hmcl.ui.FXUtils;
import org.jackhuang.hmcl.ui.SVG;
import org.jackhuang.hmcl.ui.construct.AnnouncementCard;
import org.jackhuang.hmcl.ui.construct.PopupMenu;
import org.jackhuang.hmcl.ui.construct.TwoLineListItem;
import org.jackhuang.hmcl.ui.decorator.DecoratorPage;
@@ -73,8 +74,9 @@ public final class MainPage extends StackPane implements DecoratorPage {
private final ObservableList<Node> versionNodes;
private Profile profile;
private StackPane updatePane;
private JFXButton menuButton;
private final VBox announcementPane;
private final StackPane updatePane;
private final JFXButton menuButton;
{
HBox titleNode = new HBox(8);
@@ -92,6 +94,8 @@ public final class MainPage extends StackPane implements DecoratorPage {
setPadding(new Insets(20));
announcementPane = new VBox(16);
updatePane = new StackPane();
updatePane.setVisible(false);
updatePane.getStyleClass().add("bubble");
@@ -198,7 +202,7 @@ public final class MainPage extends StackPane implements DecoratorPage {
launchPane.getChildren().setAll(launchButton, separator, menuButton);
}
getChildren().setAll(updatePane, launchPane);
getChildren().setAll(announcementPane, updatePane, launchPane);
menu.setMaxHeight(365);
menu.setMaxWidth(545);
@@ -212,6 +216,14 @@ public final class MainPage extends StackPane implements DecoratorPage {
Bindings.bindContent(menu.getContent(), versionNodes);
}
public MainPage() {
if (Metadata.isNightly()) {
announcementPane.getChildren().add(new AnnouncementCard(i18n("update.channel.nightly.title"), i18n("update.channel.nightly.hint")));
} else if (Metadata.isDev()) {
announcementPane.getChildren().add(new AnnouncementCard(i18n("update.channel.dev.title"), i18n("update.channel.dev.hint")));
}
}
private void doAnimation(boolean show) {
Duration duration = Duration.millis(320);
Timeline nowAnimation = new Timeline();

View File

@@ -120,6 +120,19 @@
-fx-text-fill: rgba(0.0, 0.0, 0.0, 0.87);
}
.announcement {
}
.announcement .title {
-fx-font-size: 14px;
-fx-font-weight: bold;
}
.announcement JFXHyperlink, .announcement Text {
-fx-font-size: 12px;
}
.rippler-container {
-jfx-rippler-fill: #a2a2a2;
}

View File

@@ -839,8 +839,20 @@ system.operating_system=OS
update=Update
update.accept=Update
update.changelog=Changes
update.channel.dev=Update to beta version
update.channel.stable=Update to stable version
update.channel.dev=Beta
update.channel.dev.hint=You are using the beta version, which may include some extra functionalities compared to the release version, only used for testing.\n\
Beta version should be unstable!\n\
If you met some problems, you can go to <a href="hmcl://settings/feedback">the feedback page</a> to report them, or join chat <a href="https://discord.gg/jVvC7HfM6U">Discord</a> or <a href="https://kaihei.co/Kx7n3t">KaiHeiLa</a> to report problems.\n\n\
To hide this hint, you need to <a href="https://hmcl.huangyuhui.net/api/redirect/sponsor">donate</a> or make impressive contribution in feedback.
update.channel.dev.title=Hints for beta version
update.channel.dev.update=Update to beta version
update.channel.nightly=Alpha
update.channel.nightly.hint=You are using the alpha version, which may include some extra functionalities compared to the beta and release version, only used for testing.\n\
Alpha version should be unstable!\n\
If you met some problems, you can go to <a href="hmcl://settings/feedback">the feedback page</a> to report them, or join chat <a href="https://discord.gg/jVvC7HfM6U">Discord</a> or <a href="https://kaihei.co/Kx7n3t">KaiHeiLa</a> to report problems.\n\n\
To hide this hint, you need to <a href="https://hmcl.huangyuhui.net/api/redirect/sponsor">donate</a> or make impressive contribution in feedback.
update.channel.nightly.title=Hints for alpha version
update.channel.stable.update=Update to release version
update.checking=Checking for updates
update.failed=Failed to perform update
update.found=Update Available!

View File

@@ -838,8 +838,20 @@ system.operating_system=操作系統
update=啟動器更新
update.accept=更新
update.changelog=更新日誌
update.channel.dev=更新到開發
update.channel.stable=更新到建議版本
update.channel.dev=測試
update.channel.dev.hint=你正在使用測試版。測試版包含一些未在正式版中包含的測試性功能,僅用於體驗新功能。\n\
測試版功能未受充分驗證,使用起來可能不穩定!\n\
如果你遇到了使用問題,可以在設置的 <a href="hmcl://settings/feedback">回饋頁面</a> 中進行回饋,或加入回饋頁面中提供的 <a href="https://discord.gg/jVvC7HfM6U">Discord</a> 或 <a href="https://kaihei.co/Kx7n3t">開黑啦</a>群以回饋問題。\n\n\
你需要 <a href="https://hmcl.huangyuhui.net/api/redirect/sponsor">贊助</a> 或在回饋過程中作出貢獻以隱藏本提示。
update.channel.dev.title=測試版提示
update.channel.dev.update=更新到開發版
update.channel.nightly=預覽版
update.channel.nightly.hint=你正在使用預覽版。預覽版可能會每天更新一次,包含一些未在正式版和測試版中包含的測試性功能,僅用於體驗新功能\n\
測試版功能未受充分驗證,使用起來可能不穩定!\n\
如果你遇到了使用問題,可以在設置的 <a href="hmcl://settings/feedback">回饋頁面</a> 中進行回饋,或加入回饋頁面中提供的 <a href="https://discord.gg/jVvC7HfM6U">Discord</a> 或 <a href="https://kaihei.co/Kx7n3t">開黑啦</a>群以回饋問題。\n\n\
你需要 <a href="https://hmcl.huangyuhui.net/api/redirect/sponsor">贊助</a> 或在回饋過程中作出貢獻以隱藏本提示。
update.channel.nightly.title=預覽版提示
update.channel.stable.update=更新到建議版本
update.checking=正在檢查更新
update.failed=更新失敗
update.found=發現到更新

View File

@@ -838,8 +838,20 @@ system.operating_system=操作系统
update=启动器更新
update.accept=更新
update.changelog=更新日志
update.channel.dev=更新到开发
update.channel.stable=更新到推荐版本
update.channel.dev=测试
update.channel.dev.hint=你正在使用测试版。测试版包含一些未在正式版中包含的测试性功能,仅用于体验新功能。\n\
测试版功能未受充分验证,使用起来可能不稳定!\n\
如果你遇到了使用问题,可以在设置的 <a href="hmcl://settings/feedback">反馈页面</a> 中进行反馈,或加入反馈页面中提供的 <a href="https://discord.gg/jVvC7HfM6U">Discord</a> 或 <a href="https://kaihei.co/Kx7n3t">开黑啦</a>群以反馈问题。\n\n\
你需要 <a href="https://hmcl.huangyuhui.net/api/redirect/sponsor">赞助</a> 或在反馈过程中作出贡献以隐藏本提示。
update.channel.dev.title=测试版提示
update.channel.dev.update=更新到开发版
update.channel.nightly=预览版
update.channel.nightly.hint=你正在使用预览版。预览版可能会每天更新一次,包含一些未在正式版和测试版中包含的测试性功能,仅用于体验新功能。\n\
测试版功能未受充分验证,使用起来可能不稳定!\n\
如果你遇到了使用问题,可以在设置的 <a href="hmcl://settings/feedback">反馈页面</a> 中进行反馈,或加入反馈页面中提供的 <a href="https://discord.gg/jVvC7HfM6U">Discord</a> 或 <a href="https://kaihei.co/Kx7n3t">开黑啦</a>群以反馈问题。\n\n\
你需要 <a href="https://hmcl.huangyuhui.net/api/redirect/sponsor">赞助</a> 或在反馈过程中作出贡献以隐藏本提示。
update.channel.nightly.title=预览版提示
update.channel.stable.update=更新到推荐版本
update.checking=正在检查更新
update.failed=更新失败
update.found=发现更新