diff options
| -rw-r--r-- | CHANGELOG.md | 1 | ||||
| -rwxr-xr-x | config/hypr/scripts/ZshChangeTheme.sh | 82 | ||||
| -rwxr-xr-x | copy.sh | 1 | ||||
| -rw-r--r-- | scripts/lib_apps.sh | 58 |
4 files changed, 140 insertions, 2 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md index e0012e2b..c6fafaf9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -39,6 +39,7 @@ ## Fixed: +- `OMZ`themes changed. `copy.sh` checks and downloads them - `copy.sh` didn't replace LUA system files when already in LUA workflow - Duplicate waybars on Debian Forky+ - `Float-all-windows.sh` in LUA mode no toggles float/tiled diff --git a/config/hypr/scripts/ZshChangeTheme.sh b/config/hypr/scripts/ZshChangeTheme.sh index 08162485..17888f5a 100755 --- a/config/hypr/scripts/ZshChangeTheme.sh +++ b/config/hypr/scripts/ZshChangeTheme.sh @@ -19,11 +19,85 @@ if [ -n "$(grep -i nixos < /etc/os-release)" ]; then exit 1 fi -themes_dir="$HOME/.oh-my-zsh/themes" file_extension=".zsh-theme" +# Locate the active zshrc (honoring ZDOTDIR when set) +zsh_path="${ZDOTDIR:-$HOME}/.zshrc" +if [ ! -f "$zsh_path" ] && [ -f "$HOME/.zshrc" ]; then + zsh_path="$HOME/.zshrc" +fi + +# Locate Oh My Zsh. Search order: +# 1. $ZSH env var (if exported in user environment) +# 2. Parsed `export ZSH="..."` or `ZSH="..."` line directly from .zshrc +# 3. Parsed `source .../oh-my-zsh.sh` line from .zshrc (directory containing the script) +# 4. Standard conventional paths (~/.oh-my-zsh, $ZDOTDIR/.oh-my-zsh, XDG data home, /usr/share, /opt) +omz_root="" +omz_from_zshrc="" +if [ -f "$zsh_path" ]; then + omz_from_zshrc=$(grep -E '^[[:space:]]*(export[[:space:]]+)?ZSH=' "$zsh_path" | head -n1 | sed -E 's/^[[:space:]]*(export[[:space:]]+)?ZSH=["'"'"']?([^"'"'"'[:space:]]+)["'"'"']?.*/\2/' || true) + # Expand $HOME / ~ if present in the parsed path + omz_from_zshrc="${omz_from_zshrc/#\~/$HOME}" + omz_from_zshrc="${omz_from_zshrc//\$HOME/$HOME}" + if [ -z "$omz_from_zshrc" ]; then + # Fall back to checking where oh-my-zsh.sh is sourced from in .zshrc + omz_source_line=$(grep -E '^[[:space:]]*(source|\.)[[:space:]]+.*oh-my-zsh\.sh' "$zsh_path" | head -n1 || true) + if [ -n "$omz_source_line" ]; then + omz_from_zshrc=$(echo "$omz_source_line" | sed -E 's/^[[:space:]]*(source|\.)[[:space:]]+["'"'"']?([^"'"'"'[:space:]]+)\/oh-my-zsh\.sh["'"'"']?.*/\2/' || true) + omz_from_zshrc="${omz_from_zshrc/#\~/$HOME}" + omz_from_zshrc="${omz_from_zshrc//\$HOME/$HOME}" + fi + fi +fi + +for candidate in \ + "${ZSH:-}" \ + "$omz_from_zshrc" \ + "$HOME/.oh-my-zsh" \ + "${ZDOTDIR:-$HOME}/.oh-my-zsh" \ + "${XDG_DATA_HOME:-$HOME/.local/share}/oh-my-zsh" \ + "/usr/share/oh-my-zsh" \ + "/usr/share/ohmyzsh" \ + "/opt/oh-my-zsh" \ + "/opt/ohmyzsh"; do + if [ -n "$candidate" ] && [ -d "$candidate" ]; then + omz_root="$candidate" + break + fi +done + +# Collect theme files from both built-in themes/ and custom themes/ ($ZSH_CUSTOM/themes) +themes_array=() +if [ -n "$omz_root" ]; then + # 1. Core themes directory + if [ -d "$omz_root/themes" ]; then + while IFS= read -r theme_file; do + [ -n "$theme_file" ] && themes_array+=("$theme_file") + done < <(find -L "$omz_root/themes" -maxdepth 1 -type f -name "*$file_extension" -exec basename {} \; 2>/dev/null | sed -e "s/$file_extension//" | sort -u) + fi -themes_array=($(find -L "$themes_dir" -type f -name "*$file_extension" -exec basename {} \; | sed -e "s/$file_extension//")) + # 2. Custom themes directory ($ZSH_CUSTOM/themes or $omz_root/custom/themes) + custom_themes_dir="${ZSH_CUSTOM:-$omz_root/custom}/themes" + if [ -d "$custom_themes_dir" ]; then + while IFS= read -r theme_file; do + [ -n "$theme_file" ] && themes_array+=("$theme_file") + done < <(find -L "$custom_themes_dir" -maxdepth 1 -type f -name "*$file_extension" -exec basename {} \; 2>/dev/null | sed -e "s/$file_extension//" | sort -u) + fi +fi + +# Sort and deduplicate all found themes +if [ "${#themes_array[@]}" -gt 0 ]; then + mapfile -t themes_array < <(printf "%s\n" "${themes_array[@]}" | sort -u) +fi + +# If no themes were found, show diagnostic info in the notification +if [ "${#themes_array[@]}" -eq 0 ]; then + if [ -z "$omz_root" ]; then + notify-send -i "$iDIR/error.png" "Oh My Zsh not found" "Checked ~/.oh-my-zsh, .zshrc ZSH=, and system paths. Install Oh My Zsh or set ZSH in .zshrc." + else + notify-send -i "$iDIR/error.png" "No themes found" "Found Oh My Zsh at $omz_root, but themes/ directory is empty or missing." + fi +fi # Add "Random" option to the beginning of the array themes_array=("Random" "${themes_array[@]}") @@ -49,6 +123,10 @@ main() { var_name="ZSH_THEME" if [[ "$choice" == "Random" ]]; then + if [ "${#themes_array[@]}" -le 1 ]; then + notify-send -i "$iDIR/error.png" "No themes available" "Oh My Zsh was not found; nothing to randomize." + exit 1 + fi # Pick a random theme from the original themes_array (excluding "Random") random_theme=${themes_array[$((RANDOM % (${#themes_array[@]} - 1) + 1))]} theme_to_set="$random_theme" @@ -620,6 +620,7 @@ if is_nixos; then else install_waybar_weather "$LOG" fi +ensure_oh_my_zsh "$LOG" printf "\n%.0s" {1..1} choose_default_editor "$LOG" diff --git a/scripts/lib_apps.sh b/scripts/lib_apps.sh index 55c457d5..379db801 100644 --- a/scripts/lib_apps.sh +++ b/scripts/lib_apps.sh @@ -348,3 +348,61 @@ install_waybar_weather() { install_waybar_weather_binary "$log" fi } + +# Install Oh My Zsh (and bundled theme templates) when zsh is used and OMZ is missing. +# Uses --unattended --keep-zshrc so it never blocks the script, doesn't hijack the user's +# shell immediately, and preserves the existing .zshrc. +ensure_oh_my_zsh() { + local log="${1:-/dev/null}" + local user_shell + user_shell="$(basename "${SHELL:-}")" + + # Only trigger if the user's shell is zsh or zsh is installed + if [ "$user_shell" != "zsh" ] && ! command -v zsh >/dev/null 2>&1; then + return 0 + fi + + # Skip if Oh My Zsh is already installed in any standard location + local candidate + for candidate in \ + "${ZSH:-}" \ + "$HOME/.oh-my-zsh" \ + "${ZDOTDIR:-$HOME}/.oh-my-zsh" \ + "${XDG_DATA_HOME:-$HOME/.local/share}/oh-my-zsh" \ + "/usr/share/oh-my-zsh" \ + "/usr/share/ohmyzsh" \ + "/opt/oh-my-zsh"; do + if [ -n "$candidate" ] && [ -d "$candidate/themes" ]; then + echo "${INFO:-[INFO]} Oh My Zsh themes already present at $candidate" 2>&1 | tee -a "$log" + return 0 + fi + done + + # Verify network / download tools before attempting install + if ! command -v curl >/dev/null 2>&1 && ! command -v wget >/dev/null 2>&1; then + echo "${WARN:-[WARN]} curl/wget not found; cannot install Oh My Zsh theme templates." 2>&1 | tee -a "$log" + return 1 + fi + if ! command -v git >/dev/null 2>&1; then + echo "${WARN:-[WARN]} git not found; cannot install Oh My Zsh theme templates." 2>&1 | tee -a "$log" + return 1 + fi + + echo "${INFO:-[INFO]} Oh My Zsh not found - installing theme templates to ~/.oh-my-zsh..." 2>&1 | tee -a "$log" + + local install_cmd + if command -v curl >/dev/null 2>&1; then + install_cmd='curl -fsSL https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh' + else + install_cmd='wget -qO- https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh' + fi + + # Run unattended without changing the default shell or overwriting .zshrc + if sh -c "$($install_cmd)" "" --unattended --keep-zshrc 2>&1 | tee -a "$log"; then + echo "${OK:-[OK]} Oh My Zsh theme templates installed successfully." 2>&1 | tee -a "$log" + return 0 + else + echo "${WARN:-[WARN]} Oh My Zsh installation failed; theme switcher may only show 'Random'." 2>&1 | tee -a "$log" + return 1 + fi +} |
