520 lines
20 KiB
Bash
520 lines
20 KiB
Bash
#!/usr/bin/env bash
|
||
set -u
|
||
|
||
PLUGIN_ID="local.omarchy-citizen"
|
||
PLUGIN_VERSION="1.0.0"
|
||
|
||
XDG_CONFIG_HOME="${XDG_CONFIG_HOME:-$HOME/.config}"
|
||
XDG_DATA_HOME="${XDG_DATA_HOME:-$HOME/.local/share}"
|
||
XDG_STATE_HOME="${XDG_STATE_HOME:-$HOME/.local/state}"
|
||
XDG_CACHE_HOME="${XDG_CACHE_HOME:-$HOME/.cache}"
|
||
|
||
PLUGIN_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)"
|
||
SELF="$(readlink -f "${BASH_SOURCE[0]}")"
|
||
STATE_DIR="$XDG_STATE_HOME/citizen-launcher"
|
||
CACHE_DIR="$XDG_CACHE_HOME/citizen-launcher"
|
||
DATA_DIR="$XDG_DATA_HOME/citizen-launcher"
|
||
LOG_FILE="$STATE_DIR/omarchy-citizen.log"
|
||
UPDATER_LOG="$STATE_DIR/updater.log"
|
||
RSI_LOG="$STATE_DIR/rsi-launcher.log"
|
||
SANITIZER="$PLUGIN_DIR/support-sanitize.py"
|
||
BACKEND_EXTERNAL="$HOME/.local/lib/citizen-launcher/citizen-launcher"
|
||
BACKEND_BUNDLED="$PLUGIN_DIR/backend/bin/citizen-launcher"
|
||
MANAGED_LUG="$DATA_DIR/vendor/lug-helper/lug-helper.appimage"
|
||
MANAGED_WINE="$DATA_DIR/vendor/wine/current"
|
||
|
||
mkdir -p "$STATE_DIR" "$CACHE_DIR"
|
||
ACTION="${1:-status}"
|
||
|
||
rotate_log() {
|
||
local max=$((4 * 1024 * 1024)) keep=$((2 * 1024 * 1024)) size=0
|
||
if [[ -f "$LOG_FILE" ]]; then
|
||
size="$(stat -c '%s' "$LOG_FILE" 2>/dev/null || echo 0)"
|
||
if (( size > max )); then
|
||
tail -c "$keep" "$LOG_FILE" > "$LOG_FILE.tmp" 2>/dev/null || true
|
||
mv -f "$LOG_FILE.tmp" "$LOG_FILE" 2>/dev/null || true
|
||
fi
|
||
fi
|
||
}
|
||
|
||
log_line() {
|
||
printf '%s [%s] %s\n' "$(date '+%Y-%m-%dT%H:%M:%S%z')" "$$" "$*" >>"$LOG_FILE" 2>/dev/null || true
|
||
}
|
||
|
||
rotate_log
|
||
log_line "action=$ACTION version=$PLUGIN_VERSION"
|
||
|
||
notify() {
|
||
local title="$1" body="$2"
|
||
if command -v omarchy-notification-send >/dev/null 2>&1; then
|
||
omarchy-notification-send "$title" "$body" >/dev/null 2>&1 || true
|
||
elif command -v notify-send >/dev/null 2>&1; then
|
||
notify-send "$title" "$body" >/dev/null 2>&1 || true
|
||
fi
|
||
}
|
||
|
||
notify_error() {
|
||
local body="$1"
|
||
log_line "error=$body"
|
||
if command -v zenity >/dev/null 2>&1; then
|
||
zenity --error --width=560 --title="Citizen Launcher" --text="$body" >/dev/null 2>&1 || true
|
||
else
|
||
notify "Citizen Launcher" "$body"
|
||
printf 'Citizen Launcher: %s\n' "$body" >&2
|
||
fi
|
||
}
|
||
|
||
find_backend() {
|
||
if [[ -x "$BACKEND_EXTERNAL" ]]; then
|
||
printf '%s\n' "$BACKEND_EXTERNAL"
|
||
elif [[ -x "$BACKEND_BUNDLED" ]]; then
|
||
printf '%s\n' "$BACKEND_BUNDLED"
|
||
else
|
||
return 1
|
||
fi
|
||
}
|
||
|
||
backend_exec() {
|
||
local backend
|
||
backend="$(find_backend)" || {
|
||
printf 'Go-Backend nicht gefunden. Plugin bitte neu installieren.\n' >&2
|
||
return 127
|
||
}
|
||
"$backend" "$@"
|
||
}
|
||
|
||
backend_game_status() { backend_exec game-status; }
|
||
backend_plugin_status() { backend_exec status; }
|
||
backend_game_install() { backend_exec game-install; }
|
||
backend_game_launch() { backend_exec game-launch; }
|
||
backend_game_repair() { backend_exec game-repair; }
|
||
autopilot_enable() { backend_exec autopilot enable; }
|
||
autopilot_maintain() { backend_exec maintain; }
|
||
wine_doctor() { backend_exec doctor; }
|
||
|
||
kv_get() {
|
||
local key="$1"
|
||
sed -n "s/^${key}=//p" | head -n1
|
||
}
|
||
|
||
status() {
|
||
local game="" plugin=""
|
||
local health="setup" hardware="unknown" hardware_reason="" gpu="" vulkan="unknown"
|
||
local prefix="missing" launcher="missing" game_state="missing" wine="" dxvk="" lug="" game_autopilot="false"
|
||
local backend_state="missing" backend_version="" managed="manual" auto_apply="false" auto_maintain="false"
|
||
local update="unavailable" local_commit="" remote_commit="" maintenance=""
|
||
|
||
if game="$(backend_game_status 2>/dev/null)"; then
|
||
health="$(printf '%s\n' "$game" | kv_get health)"
|
||
hardware="$(printf '%s\n' "$game" | kv_get hardware)"
|
||
hardware_reason="$(printf '%s\n' "$game" | kv_get hardware_reason)"
|
||
gpu="$(printf '%s\n' "$game" | kv_get gpu)"
|
||
vulkan="$(printf '%s\n' "$game" | kv_get vulkan)"
|
||
prefix="$(printf '%s\n' "$game" | kv_get prefix_state)"
|
||
launcher="$(printf '%s\n' "$game" | kv_get launcher_state)"
|
||
game_state="$(printf '%s\n' "$game" | kv_get game_state)"
|
||
wine="$(printf '%s\n' "$game" | kv_get wine_version)"
|
||
dxvk="$(printf '%s\n' "$game" | kv_get dxvk_version)"
|
||
lug="$(printf '%s\n' "$game" | kv_get lug_version)"
|
||
game_autopilot="$(printf '%s\n' "$game" | kv_get autopilot)"
|
||
fi
|
||
|
||
if plugin="$(backend_plugin_status 2>/dev/null)"; then
|
||
backend_state="ready"
|
||
backend_version="$(printf '%s\n' "$plugin" | kv_get backend_version)"
|
||
managed="$(printf '%s\n' "$plugin" | kv_get managed)"
|
||
auto_apply="$(printf '%s\n' "$plugin" | kv_get auto_apply)"
|
||
auto_maintain="$(printf '%s\n' "$plugin" | kv_get auto_maintain)"
|
||
update="$(printf '%s\n' "$plugin" | kv_get update)"
|
||
local_commit="$(printf '%s\n' "$plugin" | kv_get local_commit)"
|
||
remote_commit="$(printf '%s\n' "$plugin" | kv_get remote_commit)"
|
||
maintenance="$(printf '%s\n' "$plugin" | kv_get maintenance_result)"
|
||
fi
|
||
|
||
[[ -n "$health" ]] || health="setup"
|
||
[[ -n "$prefix" ]] || prefix="missing"
|
||
[[ -n "$launcher" ]] || launcher="missing"
|
||
[[ -n "$game_state" ]] || game_state="missing"
|
||
[[ -n "$hardware" ]] || hardware="unknown"
|
||
[[ -n "$vulkan" ]] || vulkan="unknown"
|
||
[[ -n "$update" ]] || update="unavailable"
|
||
|
||
printf 'plugin_version=%s\n' "$PLUGIN_VERSION"
|
||
printf 'health=%s\n' "$health"
|
||
printf 'deps=ready\n'
|
||
printf 'deps_missing=\n'
|
||
printf 'helper=%s\n' "$([[ -n "$lug" ]] && echo ready || echo missing)"
|
||
printf 'helper_managed=optional\n'
|
||
printf 'helper_version=%s\n' "$lug"
|
||
printf 'update=unknown\n'
|
||
printf 'update_version=\n'
|
||
printf 'prefix=%s\n' "$prefix"
|
||
printf 'prefix_detail=%s\n' "$([[ "$prefix" == partial ]] && echo unvollständig || true)"
|
||
printf 'launcher=%s\n' "$launcher"
|
||
printf 'game=%s\n' "$game_state"
|
||
printf 'backend=%s\n' "$backend_state"
|
||
printf 'backend_version=%s\n' "$backend_version"
|
||
printf 'plugin_managed=%s\n' "$managed"
|
||
printf 'plugin_auto=%s\n' "$auto_apply"
|
||
printf 'plugin_update=%s\n' "$update"
|
||
printf 'plugin_local_commit=%s\n' "$local_commit"
|
||
printf 'plugin_remote_commit=%s\n' "$remote_commit"
|
||
printf 'autopilot=%s\n' "$([[ "$auto_maintain" == true ]] && echo true || echo "$game_autopilot")"
|
||
printf 'managed_lug_version=%s\n' "$lug"
|
||
printf 'managed_wine_version=%s\n' "$wine"
|
||
printf 'managed_dxvk_version=%s\n' "$dxvk"
|
||
printf 'maintenance_result=%s\n' "$maintenance"
|
||
printf 'hardware=%s\n' "$hardware"
|
||
printf 'hardware_reason=%s\n' "$hardware_reason"
|
||
printf 'hardware_gpu=%s\n' "$gpu"
|
||
printf 'hardware_vulkan=%s\n' "$vulkan"
|
||
}
|
||
|
||
hardware_info() {
|
||
local game reason gpu vulkan
|
||
game="$(backend_game_status 2>/dev/null || true)"
|
||
reason="$(printf '%s\n' "$game" | kv_get hardware_reason)"
|
||
gpu="$(printf '%s\n' "$game" | kv_get gpu)"
|
||
vulkan="$(printf '%s\n' "$game" | kv_get vulkan)"
|
||
if command -v zenity >/dev/null 2>&1; then
|
||
zenity --warning --width=620 --title="Omarchy Citizen – Hardware" \
|
||
--text="<b>Star Citizen ist auf diesem System noch nicht spielbereit.</b>\n\nGPU:\n${gpu:-nicht erkannt}\n\nVulkan: ${vulkan:-unbekannt}\n\n${reason:-Hardware-Prüfung fehlgeschlagen.}" >/dev/null 2>&1 || true
|
||
else
|
||
printf 'GPU: %s\nVulkan: %s\n%s\n' "${gpu:-nicht erkannt}" "${vulkan:-unbekannt}" "${reason:-Hardware-Prüfung fehlgeschlagen.}"
|
||
fi
|
||
}
|
||
|
||
probe_detached_start() {
|
||
local label="$1"; shift
|
||
"$@" >>"$LOG_FILE" 2>&1 &
|
||
local pid=$! rc=0
|
||
sleep 0.35
|
||
if ! kill -0 "$pid" 2>/dev/null; then
|
||
wait "$pid" || rc=$?
|
||
if (( rc != 0 )); then
|
||
log_line "$label failed rc=$rc"
|
||
return "$rc"
|
||
fi
|
||
else
|
||
disown "$pid" 2>/dev/null || true
|
||
fi
|
||
log_line "$label accepted"
|
||
}
|
||
|
||
launch_terminal_action() {
|
||
local action="$1"
|
||
log_line "launch-terminal action=$action"
|
||
if command -v uwsm-app >/dev/null 2>&1 && command -v xdg-terminal-exec >/dev/null 2>&1; then
|
||
probe_detached_start "uwsm-xdg-terminal" setsid uwsm-app -- xdg-terminal-exec \
|
||
--app-id=org.omarchy.terminal --title="Citizen Launcher" -e bash "$SELF" "$action" && return 0
|
||
fi
|
||
if command -v xdg-terminal-exec >/dev/null 2>&1; then
|
||
probe_detached_start "xdg-terminal" xdg-terminal-exec --title="Citizen Launcher" -e bash "$SELF" "$action" && return 0
|
||
fi
|
||
if command -v omarchy-launch-floating-terminal-with-presentation >/dev/null 2>&1; then
|
||
probe_detached_start "omarchy-terminal" omarchy-launch-floating-terminal-with-presentation bash "$SELF" "$action" && return 0
|
||
fi
|
||
notify_error "Das Omarchy-Citizen-Terminal konnte nicht geöffnet werden. Bitte ein Support-Paket erstellen."
|
||
return 1
|
||
}
|
||
|
||
install_stack_terminal() {
|
||
set -Ee
|
||
exec > >(tee -a "$LOG_FILE") 2>&1
|
||
setup_failed() {
|
||
local rc=$?
|
||
trap - ERR
|
||
echo
|
||
echo "=================================================="
|
||
echo " SETUP KONNTE NICHT ABGESCHLOSSEN WERDEN"
|
||
echo "=================================================="
|
||
echo "Fehlercode: $rc"
|
||
echo "Alle Details wurden protokolliert. Im SC-Panel genügt 'Support-Paket erstellen'."
|
||
notify "Citizen Launcher" "Setup fehlgeschlagen. Bitte Support-Paket erstellen."
|
||
if [[ -t 0 ]]; then read -r -p "Drücke Enter zum Schließen … " _ || true; fi
|
||
exit "$rc"
|
||
}
|
||
trap setup_failed ERR
|
||
|
||
echo "=================================================="
|
||
echo " Omarchy Citizen – Spielbereit machen"
|
||
echo "=================================================="
|
||
echo
|
||
|
||
local game health reason
|
||
game="$(backend_game_status 2>/dev/null || true)"
|
||
health="$(printf '%s\n' "$game" | kv_get health)"
|
||
if [[ "$health" == "hardware-blocked" ]]; then
|
||
reason="$(printf '%s\n' "$game" | kv_get hardware_reason)"
|
||
echo "Hardware-Prüfung nicht bestanden:"
|
||
echo "${reason:-Keine Star-Citizen-taugliche Vulkan-GPU erkannt.}"
|
||
trap - ERR
|
||
return 2
|
||
fi
|
||
|
||
echo "1/4 Autopilot aktivieren und Gaming-Stack synchronisieren …"
|
||
autopilot_enable
|
||
echo
|
||
echo "2/4 Wine-Runner auf diesem Rechner prüfen …"
|
||
wine_doctor
|
||
echo
|
||
echo "3/4 Wine-Prefix, Komponenten und offiziellen RSI Launcher einrichten …"
|
||
backend_game_install
|
||
echo
|
||
echo "4/4 Wartungsstand abschließend synchronisieren …"
|
||
autopilot_maintain || true
|
||
|
||
trap - ERR
|
||
echo
|
||
echo "=================================================="
|
||
echo " SOFTWARE-STACK BEREIT"
|
||
echo "=================================================="
|
||
echo "Der offizielle RSI Launcher ist eingerichtet. Anmeldung und Spieldownload erfolgen dort."
|
||
notify "Citizen Launcher" "Software-Stack ist bereit. RSI Launcher kann gestartet werden."
|
||
}
|
||
|
||
repair_stack_terminal() {
|
||
set -Ee
|
||
exec > >(tee -a "$LOG_FILE") 2>&1
|
||
repair_failed() {
|
||
local rc=$?
|
||
trap - ERR
|
||
echo
|
||
echo "REPARATUR FEHLGESCHLAGEN (Code $rc)"
|
||
echo "Bitte im SC-Panel ein Support-Paket erstellen."
|
||
notify "Citizen Launcher" "Reparatur fehlgeschlagen. Bitte Support-Paket erstellen."
|
||
if [[ -t 0 ]]; then read -r -p "Drücke Enter zum Schließen … " _ || true; fi
|
||
exit "$rc"
|
||
}
|
||
trap repair_failed ERR
|
||
|
||
echo "Omarchy Citizen repariert den verwalteten Gaming-Stack …"
|
||
autopilot_maintain || true
|
||
backend_game_repair
|
||
wine_doctor
|
||
trap - ERR
|
||
echo "Reparatur abgeschlossen."
|
||
notify "Citizen Launcher" "Gaming-Stack wurde repariert."
|
||
}
|
||
|
||
update_stack_terminal() {
|
||
set -Ee
|
||
exec > >(tee -a "$LOG_FILE") 2>&1
|
||
echo "Synchronisiere Wine, DXVK, RSI Launcher und optionale Support-Werkzeuge …"
|
||
autopilot_maintain
|
||
echo "Gaming-Stack ist aktuell."
|
||
}
|
||
|
||
system_update_terminal() {
|
||
set -Ee
|
||
exec > >(tee -a "$LOG_FILE") 2>&1
|
||
if ! command -v omarchy >/dev/null 2>&1; then
|
||
echo "Omarchy-Befehl nicht gefunden." >&2
|
||
return 1
|
||
fi
|
||
echo "Starte den offiziellen Omarchy-Systemupdate-Pfad …"
|
||
omarchy update -y
|
||
}
|
||
|
||
primary_action() {
|
||
local game health
|
||
game="$(backend_game_status 2>/dev/null || true)"
|
||
health="$(printf '%s\n' "$game" | kv_get health)"
|
||
case "$health" in
|
||
hardware-blocked) hardware_info ;;
|
||
ready|install-game) backend_game_launch ;;
|
||
repair|launcher-repair) launch_terminal_action repair-stack-terminal ;;
|
||
*) launch_terminal_action install-stack-terminal ;;
|
||
esac
|
||
}
|
||
|
||
repair_assistant() {
|
||
launch_terminal_action repair-stack-terminal
|
||
}
|
||
|
||
plugin_update_check() { backend_exec check; }
|
||
plugin_update_now() { backend_exec update; }
|
||
plugin_auto_enable() { backend_exec auto enable; }
|
||
plugin_auto_disable() { backend_exec auto disable; }
|
||
|
||
open_file() {
|
||
local path="$1"
|
||
[[ -f "$path" ]] || { notify_error "Datei noch nicht vorhanden: $path"; return 1; }
|
||
xdg-open "$path" >/dev/null 2>&1 &
|
||
}
|
||
|
||
open_debug_log() { open_file "$LOG_FILE"; }
|
||
open_updater_log() { open_file "$UPDATER_LOG"; }
|
||
open_log() { open_file "$RSI_LOG"; }
|
||
open_wiki() { xdg-open "https://wiki.starcitizen-lug.org" >/dev/null 2>&1 & }
|
||
open_ngl_page() { xdg-open "https://www.nglproject.com/de#downloads" >/dev/null 2>&1 & }
|
||
|
||
open_helper() {
|
||
if [[ -x "$MANAGED_LUG" ]]; then
|
||
nohup env APPIMAGE_EXTRACT_AND_RUN=1 "$MANAGED_LUG" >>"$LOG_FILE" 2>&1 &
|
||
else
|
||
open_wiki
|
||
fi
|
||
}
|
||
|
||
sanitize_to() {
|
||
local source="$1" target="$2"
|
||
[[ -f "$source" ]] || return 0
|
||
if command -v python3 >/dev/null 2>&1 && [[ -f "$SANITIZER" ]]; then
|
||
python3 "$SANITIZER" <"$source" >"$target"
|
||
else
|
||
sed -e "s#${HOME//\#/\\#}#~#g" "$source" >"$target"
|
||
fi
|
||
}
|
||
|
||
capture_sanitized() {
|
||
local target="$1"; shift
|
||
local tmp="$CACHE_DIR/capture-$$-$RANDOM.txt"
|
||
"$@" >"$tmp" 2>&1 || true
|
||
sanitize_to "$tmp" "$target"
|
||
rm -f "$tmp"
|
||
}
|
||
|
||
support_build() {
|
||
local stamp support_id work downloads archive game_prefix=""
|
||
stamp="$(date '+%Y%m%d-%H%M%S')"
|
||
support_id="OC-${stamp}-$(printf '%s-%s-%s' "$stamp" "$$" "$RANDOM" | sha256sum | cut -c1-6)"
|
||
downloads="$(command -v xdg-user-dir >/dev/null 2>&1 && xdg-user-dir DOWNLOAD 2>/dev/null || true)"
|
||
[[ -n "$downloads" && -d "$downloads" ]] || downloads="$HOME/Downloads"
|
||
mkdir -p "$downloads"
|
||
work="$CACHE_DIR/support-$support_id"
|
||
rm -rf "$work" && mkdir -p "$work"
|
||
|
||
cat >"$work/README_SUPPORT.txt" <<SUPPORT
|
||
Omarchy Citizen Support-Paket
|
||
Support-ID: $support_id
|
||
Plugin-Version: $PLUGIN_VERSION
|
||
Erstellt: $(date '+%Y-%m-%d %H:%M:%S %z')
|
||
|
||
Das Paket enthält technische Diagnoseinformationen. Home-Pfad, Benutzername,
|
||
Hostname, E-Mail/IP/MAC und typische Token-/Sessionwerte werden beim Export
|
||
best-effort maskiert. Keine Browserdaten, SSH-Schlüssel oder Passwortdateien.
|
||
SUPPORT
|
||
|
||
status >"$work/citizen-status.txt" 2>&1 || true
|
||
capture_sanitized "$work/backend-game-status.txt" backend_exec game-status
|
||
capture_sanitized "$work/backend-status.txt" backend_exec status
|
||
capture_sanitized "$work/wine-doctor.txt" backend_exec doctor
|
||
|
||
if command -v omarchy >/dev/null 2>&1; then
|
||
capture_sanitized "$work/plugin-validation.txt" omarchy plugin validate "$PLUGIN_DIR"
|
||
if omarchy debug --no-sudo --print >"$CACHE_DIR/omarchy-debug-$$.txt" 2>&1; then
|
||
sanitize_to "$CACHE_DIR/omarchy-debug-$$.txt" "$work/omarchy-debug.txt"
|
||
else
|
||
{ omarchy version 2>/dev/null || true; omarchy commands --all 2>/dev/null || true; } >"$CACHE_DIR/omarchy-debug-$$.txt"
|
||
sanitize_to "$CACHE_DIR/omarchy-debug-$$.txt" "$work/omarchy-debug.txt"
|
||
fi
|
||
rm -f "$CACHE_DIR/omarchy-debug-$$.txt"
|
||
fi
|
||
|
||
{
|
||
echo "=== kernel ==="; uname -rmo 2>/dev/null || true
|
||
echo "=== memory ==="; free -h 2>/dev/null || true
|
||
echo "=== filesystems ==="; df -hT / "$HOME" 2>/dev/null || true
|
||
echo "=== gpu ==="; lspci -nnk 2>/dev/null | grep -A5 -Ei 'VGA|3D|Display' || true
|
||
echo "=== vulkan ==="; command -v vulkaninfo >/dev/null 2>&1 && vulkaninfo --summary 2>&1 || true
|
||
echo "=== limits ==="; sysctl vm.max_map_count 2>/dev/null || true; ulimit -Hn 2>/dev/null || true
|
||
} >"$CACHE_DIR/system-$$.txt"
|
||
sanitize_to "$CACHE_DIR/system-$$.txt" "$work/system.txt"
|
||
rm -f "$CACHE_DIR/system-$$.txt"
|
||
|
||
for pair in "$LOG_FILE:omarchy-citizen.log" "$UPDATER_LOG:updater.log" "$RSI_LOG:rsi-launcher.log"; do
|
||
local src="${pair%%:*}" dst="${pair#*:}"
|
||
if [[ -f "$src" ]]; then
|
||
tail -n 1800 "$src" >"$CACHE_DIR/log-$$.txt"
|
||
sanitize_to "$CACHE_DIR/log-$$.txt" "$work/$dst"
|
||
rm -f "$CACHE_DIR/log-$$.txt"
|
||
fi
|
||
done
|
||
|
||
game_prefix="$(backend_game_status 2>/dev/null | kv_get prefix || true)"
|
||
if [[ -n "$game_prefix" ]]; then
|
||
printf 'prefix=%s\n' "$game_prefix" >"$CACHE_DIR/prefix-$$.txt"
|
||
sanitize_to "$CACHE_DIR/prefix-$$.txt" "$work/prefix.txt"
|
||
rm -f "$CACHE_DIR/prefix-$$.txt"
|
||
fi
|
||
|
||
archive="$downloads/Omarchy-Citizen-Support-$support_id.tar.gz"
|
||
tar -C "$work" -czf "$archive" .
|
||
rm -rf "$work"
|
||
notify "Citizen Launcher" "Support-Paket erstellt: $(basename "$archive")"
|
||
command -v xdg-open >/dev/null 2>&1 && xdg-open "$downloads" >/dev/null 2>&1 &
|
||
printf '%s\n' "$archive"
|
||
}
|
||
|
||
ngl_info() {
|
||
local msg="NGL ist ein optionaler Community-Mod für den RSI Launcher. Omarchy Citizen installiert ihn nur nach deiner ausdrücklichen Dateiauswahl in den verwalteten Wine-Prefix."
|
||
if command -v zenity >/dev/null 2>&1; then
|
||
zenity --info --width=540 --title="Omarchy Citizen – NGL" --text="$msg" >/dev/null 2>&1 || true
|
||
else
|
||
printf '%s\n' "$msg"
|
||
fi
|
||
}
|
||
|
||
ngl_install() {
|
||
local game prefix selected exe workdir wine
|
||
command -v zenity >/dev/null 2>&1 || { notify_error "Für die NGL-Dateiauswahl wird zenity benötigt."; return 1; }
|
||
game="$(backend_game_status)"
|
||
prefix="$(printf '%s\n' "$game" | kv_get prefix)"
|
||
[[ -n "$prefix" && -d "$prefix/drive_c" ]] || { notify_error "Star Citizen muss zuerst eingerichtet werden."; return 1; }
|
||
wine="$(readlink -f "$MANAGED_WINE")/bin/wine"
|
||
[[ -x "$wine" ]] || { notify_error "Der verwaltete Wine-Runner fehlt."; return 1; }
|
||
|
||
selected="$(zenity --file-selection --title="NGL Installer auswählen" --filename="$HOME/Downloads/" \
|
||
--file-filter="NGL Installer | *.zip *.ZIP *.exe *.EXE" --file-filter="Alle Dateien | *" 2>/dev/null)" || return 0
|
||
[[ -f "$selected" ]] || return 1
|
||
exe="$selected"
|
||
if [[ "${selected,,}" == *.zip ]]; then
|
||
workdir="$CACHE_DIR/ngl-installer"
|
||
rm -rf "$workdir" && mkdir -p "$workdir"
|
||
unzip -q "$selected" -d "$workdir" || { notify_error "NGL-ZIP konnte nicht entpackt werden."; return 1; }
|
||
exe="$(find "$workdir" -type f -iname '*.exe' -print -quit)"
|
||
fi
|
||
[[ -n "$exe" && -f "$exe" ]] || { notify_error "Kein Windows-Installer gefunden."; return 1; }
|
||
zenity --question --width=560 --title="NGL experimentell installieren?" \
|
||
--ok-label="Installer starten" --cancel-label="Abbrechen" \
|
||
--text="NGL ist Community-Code und läuft im selben Wine-Prefix wie der RSI Launcher. Bitte nur Downloads von nglproject.com verwenden." 2>/dev/null || return 0
|
||
nohup env WINEPREFIX="$prefix" WINEDEBUG=-all "$wine" "$exe" >>"$LOG_FILE" 2>&1 &
|
||
}
|
||
|
||
case "$ACTION" in
|
||
status) status ;;
|
||
hardware-info) hardware_info ;;
|
||
primary) primary_action ;;
|
||
setup|install-stack) launch_terminal_action install-stack-terminal ;;
|
||
install-stack-terminal) install_stack_terminal ;;
|
||
repair|repair-interactive|recover-prefix) repair_assistant ;;
|
||
repair-stack-terminal|recover-prefix-terminal) repair_stack_terminal ;;
|
||
support|support-build) support_build ;;
|
||
debug-log) open_debug_log ;;
|
||
log) open_log ;;
|
||
updater-log) open_updater_log ;;
|
||
plugin-update-check|check-update) plugin_update_check ;;
|
||
plugin-update-now) plugin_update_now ;;
|
||
plugin-auto-enable) plugin_auto_enable ;;
|
||
plugin-auto-disable) plugin_auto_disable ;;
|
||
autopilot-enable) autopilot_enable ;;
|
||
autopilot-maintain|update-helper) launch_terminal_action update-stack-terminal ;;
|
||
update-stack-terminal|update-helper-terminal) update_stack_terminal ;;
|
||
wine-doctor) launch_terminal_action wine-doctor-terminal ;;
|
||
wine-doctor-terminal) set -e; wine_doctor ;;
|
||
system-update) launch_terminal_action system-update-terminal ;;
|
||
system-update-terminal) system_update_terminal ;;
|
||
launch) backend_game_launch ;;
|
||
helper) open_helper ;;
|
||
preflight) open_helper ;;
|
||
runners|dxvk) launch_terminal_action update-stack-terminal ;;
|
||
repair-launch|repair-rsi) launch_terminal_action repair-stack-terminal ;;
|
||
dirs) ( xdg-open "$DATA_DIR" >/dev/null 2>&1 & ) ;;
|
||
wiki) open_wiki ;;
|
||
ngl-page) open_ngl_page ;;
|
||
ngl-info) ngl_info ;;
|
||
ngl-install|ngl-install-interactive) ngl_install ;;
|
||
*) notify_error "Unbekannte Omarchy-Citizen-Aktion: $ACTION"; exit 2 ;;
|
||
esac
|