mirror of
https://github.com/PrismLauncher/PrismLauncher.git
synced 2025-04-29 22:24:26 +02:00
Merge remote-tracking branch 'upstream/develop' into xml-logs
This commit is contained in:
commit
2031859731
103
.github/actions/get-merge-commit/action.yml
vendored
Normal file
103
.github/actions/get-merge-commit/action.yml
vendored
Normal file
@ -0,0 +1,103 @@
|
||||
# This file incorporates work covered by the following copyright and
|
||||
# permission notice
|
||||
#
|
||||
# Copyright (c) 2003-2025 Eelco Dolstra and the Nixpkgs/NixOS contributors
|
||||
#
|
||||
# Permission is hereby granted, free of charge, to any person obtaining
|
||||
# a copy of this software and associated documentation files (the
|
||||
# "Software"), to deal in the Software without restriction, including
|
||||
# without limitation the rights to use, copy, modify, merge, publish,
|
||||
# distribute, sublicense, and/or sell copies of the Software, and to
|
||||
# permit persons to whom the Software is furnished to do so, subject to
|
||||
# the following conditions:
|
||||
#
|
||||
# The above copyright notice and this permission notice shall be
|
||||
# included in all copies or substantial portions of the Software.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
|
||||
name: Get merge commit
|
||||
description: Get a merge commit of a given pull request
|
||||
|
||||
inputs:
|
||||
repository:
|
||||
description: Repository containing the pull request
|
||||
required: false
|
||||
pull-request-id:
|
||||
description: ID of a pull request
|
||||
required: true
|
||||
|
||||
outputs:
|
||||
merge-commit-sha:
|
||||
description: Git SHA of a merge commit
|
||||
value: ${{ steps.query.outputs.merge-commit-sha }}
|
||||
|
||||
runs:
|
||||
using: composite
|
||||
|
||||
steps:
|
||||
- name: Wait for GitHub to report merge commit
|
||||
id: query
|
||||
shell: bash
|
||||
env:
|
||||
GITHUB_REPO: ${{ inputs.repository || github.repository }}
|
||||
PR_ID: ${{ inputs.pull-request-id }}
|
||||
# https://github.com/NixOS/nixpkgs/blob/8f77f3600f1ee775b85dc2c72fd842768e486ec9/ci/get-merge-commit.sh
|
||||
run: |
|
||||
set -euo pipefail
|
||||
|
||||
log() {
|
||||
echo "$@" >&2
|
||||
}
|
||||
|
||||
# Retry the API query this many times
|
||||
retryCount=5
|
||||
# Start with 5 seconds, but double every retry
|
||||
retryInterval=5
|
||||
|
||||
while true; do
|
||||
log "Checking whether the pull request can be merged"
|
||||
prInfo=$(gh api \
|
||||
-H "Accept: application/vnd.github+json" \
|
||||
-H "X-GitHub-Api-Version: 2022-11-28" \
|
||||
"/repos/$GITHUB_REPO/pulls/$PR_ID")
|
||||
|
||||
# Non-open PRs won't have their mergeability computed no matter what
|
||||
state=$(jq -r .state <<<"$prInfo")
|
||||
if [[ "$state" != open ]]; then
|
||||
log "PR is not open anymore"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
mergeable=$(jq -r .mergeable <<<"$prInfo")
|
||||
if [[ "$mergeable" == "null" ]]; then
|
||||
if ((retryCount == 0)); then
|
||||
log "Not retrying anymore. It's likely that GitHub is having internal issues: check https://www.githubstatus.com/"
|
||||
exit 3
|
||||
else
|
||||
((retryCount -= 1)) || true
|
||||
|
||||
# null indicates that GitHub is still computing whether it's mergeable
|
||||
# Wait a couple seconds before trying again
|
||||
log "GitHub is still computing whether this PR can be merged, waiting $retryInterval seconds before trying again ($retryCount retries left)"
|
||||
sleep "$retryInterval"
|
||||
|
||||
((retryInterval *= 2)) || true
|
||||
fi
|
||||
else
|
||||
break
|
||||
fi
|
||||
done
|
||||
|
||||
if [[ "$mergeable" == "true" ]]; then
|
||||
echo "merge-commit-sha=$(jq -r .merge_commit_sha <<<"$prInfo")" >> "$GITHUB_OUTPUT"
|
||||
else
|
||||
echo "# 🚨 The PR has a merge conflict!" >>> "$GITHUB_STEP_SUMMARY"
|
||||
exit 2
|
||||
fi
|
35
.github/workflows/codeql.yml
vendored
35
.github/workflows/codeql.yml
vendored
@ -1,6 +1,39 @@
|
||||
name: "CodeQL Code Scanning"
|
||||
|
||||
on: [push, pull_request, workflow_dispatch]
|
||||
on:
|
||||
push:
|
||||
# NOTE: `!` doesn't work with `paths-ignore` :(
|
||||
# So we a catch-all glob instead
|
||||
# https://github.com/orgs/community/discussions/25369#discussioncomment-3247674
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/codeql.yml"
|
||||
- "!flatpak/"
|
||||
- "!nix/"
|
||||
- "!scripts/"
|
||||
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
pull_request:
|
||||
# See above
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/codeql.yml"
|
||||
- "!flatpak/"
|
||||
- "!nix/"
|
||||
- "!scripts/"
|
||||
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
CodeQL:
|
||||
|
40
.github/workflows/flatpak.yml
vendored
40
.github/workflows/flatpak.yml
vendored
@ -2,22 +2,38 @@ name: Flatpak
|
||||
|
||||
on:
|
||||
push:
|
||||
paths-ignore:
|
||||
- "**.md"
|
||||
- "**/LICENSE"
|
||||
- ".github/ISSUE_TEMPLATE/**"
|
||||
- ".markdownlint**"
|
||||
- "nix/**"
|
||||
# We don't do anything with these artifacts on releases. They go to Flathub
|
||||
tags-ignore:
|
||||
- "*"
|
||||
# NOTE: `!` doesn't work with `paths-ignore` :(
|
||||
# So we a catch-all glob instead
|
||||
# https://github.com/orgs/community/discussions/25369#discussioncomment-3247674
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/flatpak.yml"
|
||||
- "!nix/"
|
||||
- "!scripts/"
|
||||
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
pull_request:
|
||||
paths-ignore:
|
||||
- "**.md"
|
||||
- "**/LICENSE"
|
||||
- ".github/ISSUE_TEMPLATE/**"
|
||||
- ".markdownlint**"
|
||||
- "nix/**"
|
||||
# See above
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/flatpak.yml"
|
||||
- "!nix/"
|
||||
- "!scripts/"
|
||||
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
|
55
.github/workflows/nix.yml
vendored
55
.github/workflows/nix.yml
vendored
@ -4,28 +4,34 @@ on:
|
||||
push:
|
||||
tags:
|
||||
- "*"
|
||||
paths-ignore:
|
||||
- ".github/**"
|
||||
- "!.github/workflows/nix.yml"
|
||||
- "flatpak/"
|
||||
- "scripts/"
|
||||
# NOTE: `!` doesn't work with `paths-ignore` :(
|
||||
# So we a catch-all glob instead
|
||||
# https://github.com/orgs/community/discussions/25369#discussioncomment-3247674
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/nix.yml"
|
||||
- "!flatpak/"
|
||||
- "!scripts/"
|
||||
|
||||
- ".git*"
|
||||
- ".envrc"
|
||||
- "**.md"
|
||||
- "!COPYING.md"
|
||||
- "renovate.json"
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
pull_request_target:
|
||||
paths-ignore:
|
||||
- ".github/**"
|
||||
- "flatpak/"
|
||||
- "scripts/"
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/nix.yml"
|
||||
- "!flatpak/"
|
||||
- "!scripts/"
|
||||
|
||||
- ".git*"
|
||||
- ".envrc"
|
||||
- "**.md"
|
||||
- "!COPYING.md"
|
||||
- "renovate.json"
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
@ -61,11 +67,20 @@ jobs:
|
||||
id-token: write
|
||||
|
||||
steps:
|
||||
- name: Get merge commit
|
||||
if: ${{ github.event_name == 'pull_request_target' }}
|
||||
id: merge-commit
|
||||
uses: PrismLauncher/PrismLauncher/.github/actions/get-merge-commit@develop
|
||||
with:
|
||||
pull-request-id: ${{ github.event.pull_request.id }}
|
||||
|
||||
- name: Checkout repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: ${{ steps.merge-commit.outputs.merge-commit-sha || github.sha }}
|
||||
|
||||
- name: Install Nix
|
||||
uses: DeterminateSystems/nix-installer-action@v16
|
||||
uses: DeterminateSystems/nix-installer-action@v17
|
||||
with:
|
||||
determinate: ${{ env.USE_DETERMINATE }}
|
||||
|
||||
|
46
.github/workflows/trigger_builds.yml
vendored
46
.github/workflows/trigger_builds.yml
vendored
@ -4,21 +4,39 @@ on:
|
||||
push:
|
||||
branches-ignore:
|
||||
- "renovate/**"
|
||||
paths-ignore:
|
||||
- "**.md"
|
||||
- "**/LICENSE"
|
||||
- "flake.lock"
|
||||
- "packages/**"
|
||||
- ".github/ISSUE_TEMPLATE/**"
|
||||
- ".markdownlint**"
|
||||
# NOTE: `!` doesn't work with `paths-ignore` :(
|
||||
# So we a catch-all glob instead
|
||||
# https://github.com/orgs/community/discussions/25369#discussioncomment-3247674
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/build.yml"
|
||||
- ".github/workflows/trigger_builds.yml"
|
||||
- "!flatpak/"
|
||||
- "!nix/"
|
||||
- "!scripts/"
|
||||
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
pull_request:
|
||||
paths-ignore:
|
||||
- "**.md"
|
||||
- "**/LICENSE"
|
||||
- "flake.lock"
|
||||
- "packages/**"
|
||||
- ".github/ISSUE_TEMPLATE/**"
|
||||
- ".markdownlint**"
|
||||
# See above
|
||||
paths:
|
||||
- "**"
|
||||
- "!.github/**"
|
||||
- ".github/workflows/build.yml"
|
||||
- ".github/workflows/trigger_builds.yml"
|
||||
- "!flatpak/"
|
||||
- "!nix/"
|
||||
- "!scripts/"
|
||||
|
||||
- "!.git*"
|
||||
- "!.envrc"
|
||||
- "!**.md"
|
||||
- "COPYING.md"
|
||||
- "!renovate.json"
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
|
18
flake.lock
generated
18
flake.lock
generated
@ -3,11 +3,11 @@
|
||||
"libnbtplusplus": {
|
||||
"flake": false,
|
||||
"locked": {
|
||||
"lastModified": 1699286814,
|
||||
"narHash": "sha256-yy0q+bky80LtK1GWzz7qpM+aAGrOqLuewbid8WT1ilk=",
|
||||
"lastModified": 1744811532,
|
||||
"narHash": "sha256-qhmjaRkt+O7A+gu6HjUkl7QzOEb4r8y8vWZMG2R/C6o=",
|
||||
"owner": "PrismLauncher",
|
||||
"repo": "libnbtplusplus",
|
||||
"rev": "23b955121b8217c1c348a9ed2483167a6f3ff4ad",
|
||||
"rev": "531449ba1c930c98e0bcf5d332b237a8566f9d78",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
@ -18,11 +18,11 @@
|
||||
},
|
||||
"nixpkgs": {
|
||||
"locked": {
|
||||
"lastModified": 1744463964,
|
||||
"narHash": "sha256-LWqduOgLHCFxiTNYi3Uj5Lgz0SR+Xhw3kr/3Xd0GPTM=",
|
||||
"lastModified": 1744932701,
|
||||
"narHash": "sha256-fusHbZCyv126cyArUwwKrLdCkgVAIaa/fQJYFlCEqiU=",
|
||||
"owner": "NixOS",
|
||||
"repo": "nixpkgs",
|
||||
"rev": "2631b0b7abcea6e640ce31cd78ea58910d31e650",
|
||||
"rev": "b024ced1aac25639f8ca8fdfc2f8c4fbd66c48ef",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
@ -35,11 +35,11 @@
|
||||
"qt-qrcodegenerator": {
|
||||
"flake": false,
|
||||
"locked": {
|
||||
"lastModified": 1731907326,
|
||||
"narHash": "sha256-5+iYwsbX8wjKZPCy7ENj5HCYgOqzeSNLs/YrX2Vc7CQ=",
|
||||
"lastModified": 1737616857,
|
||||
"narHash": "sha256-6SugPt0lp1Gz7nV23FLmsmpfzgFItkSw7jpGftsDPWc=",
|
||||
"owner": "nayuki",
|
||||
"repo": "QR-Code-generator",
|
||||
"rev": "f40366c40d8d1956081f7ec643d240c02a81df52",
|
||||
"rev": "2c9044de6b049ca25cb3cd1649ed7e27aa055138",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
|
@ -138,6 +138,8 @@
|
||||
|
||||
{
|
||||
default = pkgs.mkShell {
|
||||
name = "prism-launcher";
|
||||
|
||||
inputsFrom = [ packages'.prismlauncher-unwrapped ];
|
||||
|
||||
packages = with pkgs; [
|
||||
|
@ -1 +1 @@
|
||||
Subproject commit 1f8e591b263eef8a0dc04929f2da135af59fac3c
|
||||
Subproject commit f5d368a31d6ef046eb2955c74ec6f54f32ed5c4e
|
@ -195,15 +195,10 @@ class BaseInstance : public QObject, public std::enable_shared_from_this<BaseIns
|
||||
virtual QProcessEnvironment createEnvironment() = 0;
|
||||
virtual QProcessEnvironment createLaunchEnvironment() = 0;
|
||||
|
||||
/*!
|
||||
* Returns a matcher that can maps relative paths within the instance to whether they are 'log files'
|
||||
*/
|
||||
virtual IPathMatcher::Ptr getLogFileMatcher() = 0;
|
||||
|
||||
/*!
|
||||
* Returns the root folder to use for looking up log files
|
||||
*/
|
||||
virtual QString getLogFileRoot() = 0;
|
||||
virtual QStringList getLogFileSearchPaths() = 0;
|
||||
|
||||
virtual QString getStatusbarDescription() = 0;
|
||||
|
||||
|
@ -44,10 +44,7 @@ class InstancePageProvider : protected QObject, public BasePageProvider {
|
||||
// values.append(new GameOptionsPage(onesix.get()));
|
||||
values.append(new ScreenshotsPage(FS::PathCombine(onesix->gameRoot(), "screenshots")));
|
||||
values.append(new InstanceSettingsPage(onesix));
|
||||
auto logMatcher = inst->getLogFileMatcher();
|
||||
if (logMatcher) {
|
||||
values.append(new OtherLogsPage(inst, logMatcher));
|
||||
}
|
||||
values.append(new OtherLogsPage(inst));
|
||||
return values;
|
||||
}
|
||||
|
||||
|
@ -57,8 +57,7 @@ class NullInstance : public BaseInstance {
|
||||
QProcessEnvironment createEnvironment() override { return QProcessEnvironment(); }
|
||||
QProcessEnvironment createLaunchEnvironment() override { return QProcessEnvironment(); }
|
||||
QMap<QString, QString> getVariables() override { return QMap<QString, QString>(); }
|
||||
IPathMatcher::Ptr getLogFileMatcher() override { return nullptr; }
|
||||
QString getLogFileRoot() override { return instanceRoot(); }
|
||||
QStringList getLogFileSearchPaths() override { return {}; }
|
||||
QString typeName() const override { return "Null"; }
|
||||
bool canExport() const override { return false; }
|
||||
bool canEdit() const override { return false; }
|
||||
|
@ -1004,19 +1004,10 @@ QMap<QString, QString> MinecraftInstance::createCensorFilterFromSession(AuthSess
|
||||
return filter;
|
||||
}
|
||||
|
||||
IPathMatcher::Ptr MinecraftInstance::getLogFileMatcher()
|
||||
{
|
||||
auto combined = std::make_shared<MultiMatcher>();
|
||||
combined->add(std::make_shared<RegexpMatcher>(".*\\.log(\\.[0-9]*)?(\\.gz)?$"));
|
||||
combined->add(std::make_shared<RegexpMatcher>("crash-.*\\.txt"));
|
||||
combined->add(std::make_shared<RegexpMatcher>("IDMap dump.*\\.txt$"));
|
||||
combined->add(std::make_shared<RegexpMatcher>("ModLoader\\.txt(\\..*)?$"));
|
||||
return combined;
|
||||
}
|
||||
|
||||
QString MinecraftInstance::getLogFileRoot()
|
||||
QStringList MinecraftInstance::getLogFileSearchPaths()
|
||||
{
|
||||
return gameRoot();
|
||||
return { FS::PathCombine(gameRoot(), "crash-reports"), FS::PathCombine(gameRoot(), "logs"), gameRoot() };
|
||||
}
|
||||
|
||||
QString MinecraftInstance::getStatusbarDescription()
|
||||
|
@ -139,9 +139,7 @@ class MinecraftInstance : public BaseInstance {
|
||||
QProcessEnvironment createEnvironment() override;
|
||||
QProcessEnvironment createLaunchEnvironment() override;
|
||||
|
||||
IPathMatcher::Ptr getLogFileMatcher() override;
|
||||
|
||||
QString getLogFileRoot() override;
|
||||
QStringList getLogFileSearchPaths() override;
|
||||
|
||||
QString getStatusbarDescription() override;
|
||||
|
||||
|
@ -43,16 +43,18 @@
|
||||
|
||||
#include <FileSystem.h>
|
||||
#include <GZip.h>
|
||||
#include <QDir>
|
||||
#include <QDirIterator>
|
||||
#include <QFileSystemWatcher>
|
||||
#include <QShortcut>
|
||||
#include "RecursiveFileSystemWatcher.h"
|
||||
#include <QUrl>
|
||||
|
||||
OtherLogsPage::OtherLogsPage(InstancePtr instance, IPathMatcher::Ptr fileFilter, QWidget* parent)
|
||||
OtherLogsPage::OtherLogsPage(InstancePtr instance, QWidget* parent)
|
||||
: QWidget(parent)
|
||||
, ui(new Ui::OtherLogsPage)
|
||||
, m_instance(instance)
|
||||
, m_path(instance->getLogFileRoot())
|
||||
, m_fileFilter(fileFilter)
|
||||
, m_watcher(new RecursiveFileSystemWatcher(this))
|
||||
, m_basePath(instance->gameRoot())
|
||||
, m_logSearchPaths(instance->getLogFileSearchPaths())
|
||||
, m_model(new LogModel(this))
|
||||
{
|
||||
ui->setupUi(this);
|
||||
@ -78,11 +80,7 @@ OtherLogsPage::OtherLogsPage(InstancePtr instance, IPathMatcher::Ptr fileFilter,
|
||||
m_model->setOverflowMessage(tr("Cannot display this log since the log length surpassed %1 lines.").arg(m_model->getMaxLines()));
|
||||
m_proxy->setSourceModel(m_model.get());
|
||||
|
||||
m_watcher->setMatcher(fileFilter);
|
||||
m_watcher->setRootDir(QDir::current().absoluteFilePath(m_path));
|
||||
|
||||
connect(m_watcher, &RecursiveFileSystemWatcher::filesChanged, this, &OtherLogsPage::populateSelectLogBox);
|
||||
populateSelectLogBox();
|
||||
connect(&m_watcher, &QFileSystemWatcher::directoryChanged, this, &OtherLogsPage::populateSelectLogBox);
|
||||
|
||||
auto findShortcut = new QShortcut(QKeySequence(QKeySequence::Find), this);
|
||||
connect(findShortcut, &QShortcut::activated, this, &OtherLogsPage::findActivated);
|
||||
@ -108,29 +106,54 @@ void OtherLogsPage::retranslate()
|
||||
|
||||
void OtherLogsPage::openedImpl()
|
||||
{
|
||||
m_watcher->enable();
|
||||
const QStringList failedPaths = m_watcher.addPaths(m_logSearchPaths);
|
||||
|
||||
for (const QString& path : m_logSearchPaths) {
|
||||
if (failedPaths.contains(path))
|
||||
qDebug() << "Failed to start watching" << path;
|
||||
else
|
||||
qDebug() << "Started watching" << path;
|
||||
}
|
||||
|
||||
populateSelectLogBox();
|
||||
}
|
||||
|
||||
void OtherLogsPage::closedImpl()
|
||||
{
|
||||
m_watcher->disable();
|
||||
const QStringList failedPaths = m_watcher.removePaths(m_logSearchPaths);
|
||||
|
||||
for (const QString& path : m_logSearchPaths) {
|
||||
if (failedPaths.contains(path))
|
||||
qDebug() << "Failed to stop watching" << path;
|
||||
else
|
||||
qDebug() << "Stopped watching" << path;
|
||||
}
|
||||
}
|
||||
|
||||
void OtherLogsPage::populateSelectLogBox()
|
||||
{
|
||||
const QString prevCurrentFile = m_currentFile;
|
||||
|
||||
ui->selectLogBox->blockSignals(true);
|
||||
ui->selectLogBox->clear();
|
||||
ui->selectLogBox->addItems(m_watcher->files());
|
||||
if (m_currentFile.isEmpty()) {
|
||||
setControlsEnabled(false);
|
||||
ui->selectLogBox->setCurrentIndex(-1);
|
||||
} else {
|
||||
const int index = ui->selectLogBox->findText(m_currentFile);
|
||||
ui->selectLogBox->addItems(getPaths());
|
||||
ui->selectLogBox->blockSignals(false);
|
||||
|
||||
if (!prevCurrentFile.isEmpty()) {
|
||||
const int index = ui->selectLogBox->findText(prevCurrentFile);
|
||||
if (index != -1) {
|
||||
ui->selectLogBox->blockSignals(true);
|
||||
ui->selectLogBox->setCurrentIndex(index);
|
||||
ui->selectLogBox->blockSignals(false);
|
||||
setControlsEnabled(true);
|
||||
// don't refresh file
|
||||
return;
|
||||
} else {
|
||||
setControlsEnabled(false);
|
||||
}
|
||||
}
|
||||
|
||||
on_selectLogBox_currentIndexChanged(ui->selectLogBox->currentIndex());
|
||||
}
|
||||
|
||||
void OtherLogsPage::on_selectLogBox_currentIndexChanged(const int index)
|
||||
@ -140,7 +163,7 @@ void OtherLogsPage::on_selectLogBox_currentIndexChanged(const int index)
|
||||
file = ui->selectLogBox->itemText(index);
|
||||
}
|
||||
|
||||
if (file.isEmpty() || !QFile::exists(FS::PathCombine(m_path, file))) {
|
||||
if (file.isEmpty() || !QFile::exists(FS::PathCombine(m_basePath, file))) {
|
||||
m_currentFile = QString();
|
||||
ui->text->clear();
|
||||
setControlsEnabled(false);
|
||||
@ -157,8 +180,7 @@ void OtherLogsPage::on_btnReload_clicked()
|
||||
setControlsEnabled(false);
|
||||
return;
|
||||
}
|
||||
|
||||
QFile file(FS::PathCombine(m_path, m_currentFile));
|
||||
QFile file(FS::PathCombine(m_basePath, m_currentFile));
|
||||
if (!file.open(QFile::ReadOnly)) {
|
||||
setControlsEnabled(false);
|
||||
ui->btnReload->setEnabled(true); // allow reload
|
||||
@ -270,7 +292,7 @@ void OtherLogsPage::on_btnDelete_clicked()
|
||||
QMessageBox::Yes, QMessageBox::No) == QMessageBox::No) {
|
||||
return;
|
||||
}
|
||||
QFile file(FS::PathCombine(m_path, m_currentFile));
|
||||
QFile file(FS::PathCombine(m_basePath, m_currentFile));
|
||||
|
||||
if (FS::trash(file.fileName())) {
|
||||
return;
|
||||
@ -283,7 +305,7 @@ void OtherLogsPage::on_btnDelete_clicked()
|
||||
|
||||
void OtherLogsPage::on_btnClean_clicked()
|
||||
{
|
||||
auto toDelete = m_watcher->files();
|
||||
auto toDelete = getPaths();
|
||||
if (toDelete.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
@ -306,7 +328,9 @@ void OtherLogsPage::on_btnClean_clicked()
|
||||
}
|
||||
QStringList failed;
|
||||
for (auto item : toDelete) {
|
||||
QFile file(FS::PathCombine(m_path, item));
|
||||
QString absolutePath = FS::PathCombine(m_basePath, item);
|
||||
QFile file(absolutePath);
|
||||
qDebug() << "Deleting log" << absolutePath;
|
||||
if (FS::trash(file.fileName())) {
|
||||
continue;
|
||||
}
|
||||
@ -360,6 +384,29 @@ void OtherLogsPage::setControlsEnabled(const bool enabled)
|
||||
ui->btnClean->setEnabled(enabled);
|
||||
}
|
||||
|
||||
QStringList OtherLogsPage::getPaths()
|
||||
{
|
||||
QDir baseDir(m_basePath);
|
||||
|
||||
QStringList result;
|
||||
|
||||
for (QString searchPath : m_logSearchPaths) {
|
||||
QDir searchDir(searchPath);
|
||||
|
||||
QStringList filters{ "*.log", "*.log.gz" };
|
||||
|
||||
if (searchPath != m_basePath)
|
||||
filters.append("*.txt");
|
||||
|
||||
QStringList entries = searchDir.entryList(filters, QDir::Files | QDir::Readable, QDir::SortFlag::Time);
|
||||
|
||||
for (const QString& name : entries)
|
||||
result.append(baseDir.relativeFilePath(searchDir.filePath(name)));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void OtherLogsPage::on_findButton_clicked()
|
||||
{
|
||||
auto modifiers = QApplication::keyboardModifiers();
|
||||
|
@ -39,6 +39,7 @@
|
||||
|
||||
#include <Application.h>
|
||||
#include <pathmatcher/IPathMatcher.h>
|
||||
#include <QFileSystemWatcher>
|
||||
#include "LogPage.h"
|
||||
#include "ui/pages/BasePage.h"
|
||||
|
||||
@ -52,7 +53,7 @@ class OtherLogsPage : public QWidget, public BasePage {
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit OtherLogsPage(InstancePtr instance, IPathMatcher::Ptr fileFilter, QWidget* parent = 0);
|
||||
explicit OtherLogsPage(InstancePtr instance, QWidget* parent = 0);
|
||||
~OtherLogsPage();
|
||||
|
||||
QString id() const override { return "logs"; }
|
||||
@ -85,13 +86,16 @@ class OtherLogsPage : public QWidget, public BasePage {
|
||||
private:
|
||||
void setControlsEnabled(bool enabled);
|
||||
|
||||
QStringList getPaths();
|
||||
|
||||
private:
|
||||
Ui::OtherLogsPage* ui;
|
||||
InstancePtr m_instance;
|
||||
QString m_path;
|
||||
/** Path to display log paths relative to. */
|
||||
QString m_basePath;
|
||||
QStringList m_logSearchPaths;
|
||||
QString m_currentFile;
|
||||
IPathMatcher::Ptr m_fileFilter;
|
||||
RecursiveFileSystemWatcher* m_watcher;
|
||||
QFileSystemWatcher m_watcher;
|
||||
|
||||
LogFormatProxyModel* m_proxy;
|
||||
shared_qobject_ptr<LogModel> m_model;
|
||||
|
@ -54,7 +54,7 @@ SystemTheme::SystemTheme(const QString& styleName, const QPalette& defaultPalett
|
||||
m_colorPalette = defaultPalette;
|
||||
} else {
|
||||
auto style = QStyleFactory::create(styleName);
|
||||
m_colorPalette = style->standardPalette();
|
||||
m_colorPalette = style != nullptr ? style->standardPalette() : defaultPalette;
|
||||
delete style;
|
||||
}
|
||||
}
|
||||
|
@ -1 +1 @@
|
||||
Subproject commit 1f820dc98d0a520c175433bcbb0098327d82aac6
|
||||
Subproject commit a3d9394aba4b35789293378e04fb7473d65edf97
|
@ -97,6 +97,19 @@ public final class StandardLauncher extends AbstractLauncher {
|
||||
gameArgs.add(worldName);
|
||||
}
|
||||
|
||||
StringBuilder joinedGameArgs = new StringBuilder();
|
||||
for (String gameArg : gameArgs) {
|
||||
if (joinedGameArgs.length() > 0) {
|
||||
joinedGameArgs.append('\u001F'); // unit separator, designed for this purpose
|
||||
}
|
||||
joinedGameArgs.append(gameArg);
|
||||
}
|
||||
|
||||
// pass the real main class and game arguments in so mods can access them
|
||||
System.setProperty("org.prismlauncher.launch.mainclass", mainClassName);
|
||||
// unit separator ('\u001F') delimited list of game args
|
||||
System.setProperty("org.prismlauncher.launch.gameargs", joinedGameArgs.toString());
|
||||
|
||||
// find and invoke the main method
|
||||
MethodHandle method = ReflectionUtils.findMainMethod(mainClassName);
|
||||
method.invokeExact(gameArgs.toArray(new String[0]));
|
||||
|
@ -1 +1 @@
|
||||
Subproject commit 531449ba1c930c98e0bcf5d332b237a8566f9d78
|
||||
Subproject commit 23b955121b8217c1c348a9ed2483167a6f3ff4ad
|
@ -1 +1 @@
|
||||
Subproject commit 3fd3b299b875fbd2beac4894b8a870d80022cad7
|
||||
Subproject commit 8aeb3f7d8254f4bf1f7c6cf2a8f59c2ca141a552
|
Loading…
x
Reference in New Issue
Block a user