Skip to content
Open
16 changes: 11 additions & 5 deletions HMCL/src/main/java/org/jackhuang/hmcl/ui/main/SettingsPage.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,10 +37,7 @@
import org.jackhuang.hmcl.ui.SVG;
import org.jackhuang.hmcl.ui.construct.*;
import org.jackhuang.hmcl.ui.construct.MessageDialogPane.MessageType;
import org.jackhuang.hmcl.upgrade.RemoteVersion;
import org.jackhuang.hmcl.upgrade.UpdateChannel;
import org.jackhuang.hmcl.upgrade.UpdateChecker;
import org.jackhuang.hmcl.upgrade.UpdateHandler;
import org.jackhuang.hmcl.upgrade.*;
import org.jackhuang.hmcl.util.Lang;
import org.jackhuang.hmcl.util.StringUtils;
import org.jackhuang.hmcl.util.i18n.I18n;
Expand Down Expand Up @@ -121,17 +118,26 @@ protected int getTrailingTextIndex() {
updateButton.setManaged(outdated);
updatePane.pseudoClassStateChanged(PseudoClass.getPseudoClass("active"), outdated);

if (UpdateChecker.isOutdated()) {
if (outdated) {
lblUpdateSubProperty.set(i18n("update.newest_version", UpdateChecker.getLatestVersion().version()));
} else if (UpdateChecker.isCheckingUpdate()) {
lblUpdateSubProperty.set(i18n("update.checking"));
} else if (UpdateChecker.errorProperty().get() != null) {
Throwable t = UpdateChecker.errorProperty().get();
if (t instanceof SelfVerificationException) {
lblUpdateSubProperty.set(i18n("update.unverified"));
} else {
String msg = t.getClass().getSimpleName() + ": " + t.getLocalizedMessage();
lblUpdateSubProperty.set(i18n("update.check_failed", msg));
}
} else {
lblUpdateSubProperty.set(i18n("update.latest"));
}
};
UpdateChecker.latestVersionProperty().addListener(new WeakInvalidationListener(updateListener));
UpdateChecker.outdatedProperty().addListener(new WeakInvalidationListener(updateListener));
UpdateChecker.checkingUpdateProperty().addListener(new WeakInvalidationListener(updateListener));
UpdateChecker.errorProperty().addListener(new WeakInvalidationListener(updateListener));
updateListener.invalidated(null);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/*
* Hello Minecraft! Launcher
* Copyright (C) 2026 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.upgrade;

import java.io.IOException;

public class SelfVerificationException extends IOException {

public SelfVerificationException() {
super("Self verification failed");
}

}
17 changes: 15 additions & 2 deletions HMCL/src/main/java/org/jackhuang/hmcl/upgrade/UpdateChecker.java
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
import org.jackhuang.hmcl.Metadata;
import org.jackhuang.hmcl.util.io.NetworkUtils;
import org.jackhuang.hmcl.util.versioning.VersionNumber;
import org.jetbrains.annotations.Nullable;

import java.io.IOException;
import java.util.LinkedHashMap;
Expand Down Expand Up @@ -54,6 +55,7 @@ private UpdateChecker() {
},
latestVersion);
private static final ReadOnlyBooleanWrapper checkingUpdate = new ReadOnlyBooleanWrapper(false);
private static final ReadOnlyObjectWrapper<@Nullable Throwable> error = new ReadOnlyObjectWrapper<>();

public static void init() {
requestCheckUpdate(UpdateChannel.getChannel(), settings().acceptPreviewUpdateProperty().get());
Expand Down Expand Up @@ -83,9 +85,13 @@ public static ReadOnlyBooleanProperty checkingUpdateProperty() {
return checkingUpdate.getReadOnlyProperty();
}

public static ReadOnlyObjectProperty<@Nullable Throwable> errorProperty() {
return error.getReadOnlyProperty();
}

private static RemoteVersion checkUpdate(UpdateChannel channel, boolean preview) throws IOException {
if (!IntegrityChecker.DISABLE_SELF_INTEGRITY_CHECK && !IntegrityChecker.isSelfVerified()) {
throw new IOException("Self verification failed");
throw new SelfVerificationException();
}

var query = new LinkedHashMap<String, String>();
Expand All @@ -109,16 +115,23 @@ public static void requestCheckUpdate(UpdateChannel channel, boolean preview) {

thread(() -> {
RemoteVersion result = null;
Throwable t = null;
try {
result = checkUpdate(channel, preview);
LOG.info("Latest version (" + channel + ", preview=" + preview + ") is " + result);
} catch (Throwable e) {
t = e;
LOG.warning("Failed to check for update", e);
}
Throwable throwable = t;

RemoteVersion finalResult = result;
Platform.runLater(() -> {
if (finalResult != null) {
if (throwable != null) {
latestVersion.set(null);
error.set(throwable);
} else {
error.set(null);
latestVersion.set(finalResult);
}
Comment thread
ToobLac marked this conversation as resolved.
checkingUpdate.set(false);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ private static void applyUpdate(Path target) throws IOException {

Path self = getCurrentLocation();
if (!IntegrityChecker.DISABLE_SELF_INTEGRITY_CHECK && !IntegrityChecker.isSelfVerified()) {
throw new IOException("Self verification failed");
throw new SelfVerificationException();
}
ExecutableHeaderHelper.copyWithHeader(self, target);

Expand Down
2 changes: 2 additions & 0 deletions HMCL/src/main/resources/assets/lang/I18N.properties
Original file line number Diff line number Diff line change
Expand Up @@ -1853,6 +1853,7 @@ update.channel.nightly.hint=You are currently using a Nightly channel build of t
update.channel.nightly.title=Nightly Channel Notice
update.channel.stable=Stable
update.checking=Checking for updates
update.check_failed=Failed to check for update. %s
update.disable_auto_show_update_dialog=Do not show update dialog automatically
update.disable_auto_show_update_dialog.subtitle=Enable this option to prevent HMCL from automatically showing the update dialog.
update.failed=Failed to update
Expand All @@ -1867,6 +1868,7 @@ update.no_browser=Cannot open in system browser. But we copied the link to your
update.tooltip=Update
update.preview=Preview HMCL releases early
update.preview.subtitle=Enable this option to receive new versions of HMCL early for testing before their official release.
update.unverified=Update unavailable due to this launcher instance not verified

warning.java_interpreted_mode=HMCL is running in an interpreted Java environment, which will greatly affect performance.\n\
\n\
Expand Down
2 changes: 2 additions & 0 deletions HMCL/src/main/resources/assets/lang/I18N_zh.properties
Original file line number Diff line number Diff line change
Expand Up @@ -1650,6 +1650,7 @@ update.channel.nightly.hint=你正在使用 HMCL 預覽版。預覽版更新較
update.channel.nightly.title=預覽版提示
update.channel.stable=穩定版
update.checking=正在檢查更新
update.check_failed=檢查更新失敗 %s
update.disable_auto_show_update_dialog=不自動顯示更新彈窗
update.disable_auto_show_update_dialog.subtitle=啟用此選項,HMCL 將不會自動彈出更新彈窗。
update.failed=更新失敗
Expand All @@ -1664,6 +1665,7 @@ update.no_browser=無法開啟瀏覽器。網址已經複製到剪貼簿了,
update.tooltip=更新
update.preview=提前測試 HMCL 預覽版本
update.preview.subtitle=啟用此選項,你將可以提前取得 HMCL 的新版本,以便在正式發布前進行測試。
update.unverified=更新不可用,因為無法驗證此啟動器例項完整性

warning.java_interpreted_mode=HMCL 正在執行於直譯器模式的 Java 環境中,效能將會受到很大影響。\n我們建議你使用支援 JIT 的 Java 開啟 HMCL 以獲得最佳體驗。
warning.software_rendering=HMCL 正在使用軟體繪製,效能將會受到很大影響。
Expand Down
2 changes: 2 additions & 0 deletions HMCL/src/main/resources/assets/lang/I18N_zh_CN.properties
Original file line number Diff line number Diff line change
Expand Up @@ -1650,6 +1650,7 @@ update.channel.nightly.hint=你正在使用 HMCL 预览版。预览版更新较
update.channel.nightly.title=预览版提示
update.channel.stable=稳定版
update.checking=正在检查更新
update.check_failed=检查更新失败 %s
update.disable_auto_show_update_dialog=不自动显示更新弹窗
update.disable_auto_show_update_dialog.subtitle=启用此选项,HMCL 将不会自动弹出更新弹窗。
update.failed=更新失败
Expand All @@ -1664,6 +1665,7 @@ update.no_browser=无法打开浏览器。网址已经复制到剪贴板,你
update.tooltip=更新
update.preview=提前预览 HMCL 版本
update.preview.subtitle=启用此选项,你将可以提前获取 HMCL 的新版本,以便在正式发布前进行测试。
update.unverified=更新不可用,因为无法验证此启动器实例完整性

warning.java_interpreted_mode=HMCL 正在运行在解释器模式的 Java 环境中,性能将会受到很大影响。\n我们建议你使用支持 JIT 的 Java 启动 HMCL 以获取最佳体验。
warning.software_rendering=HMCL 正在使用软件渲染,性能将会受到很大影响。\n你可以访问 https://docs.hmcl.net/help.html 页面寻求帮助。
Expand Down