#!/bin/bash
# Screen settings script with multi-monitor support
# Usage:
#   screensetting                                    # Apply saved settings (boot restore)
#   screensetting HDMI-1 1920x1080 60 normal         # Legacy single monitor
#   screensetting apply '<JSON>'                     # Multi-monitor JSON config
#   screensetting save                               # Save current xrandr state
#
# JSON format for 'apply':
# {"monitors":[
#   {"name":"HDMI-A-0","mode":"1920x1080","rate":"60","rotation":"normal","primary":true,"enabled":true},
#   {"name":"VGA-1","mode":"1920x1080","rate":"60","rotation":"normal","primary":false,"enabled":true,
#    "placement":"right-of","relative_to":"HDMI-A-0"}
# ]}

CONFIG_FILE="$HOME/.screensetting"

# Check for jq
has_jq() {
    command -v jq >/dev/null 2>&1
}

# ============================================================================
# Legacy single-monitor functions (backward compatible)
# ============================================================================

setting_simple() {
    local size=$1
    if ! xrandr -s $size -r 60; then
        echo "Error: Failed to set resolution" >&2
        exit 1
    fi
    echo "$size" > "$CONFIG_FILE"
    feh --bg-scale /usr/share/bizhi.jpg 2>/dev/null
    exit 0
}

setting_monitor() {
    local output=$1
    local resolution=$2
    local rate=${3:-60}
    local rotation=${4:-normal}

    if ! xrandr --output "$output" --mode "$resolution" --rate "$rate" --rotate "$rotation"; then
        echo "Error: Failed to apply xrandr settings" >&2
        exit 1
    fi

    echo "OUTPUT=$output" > "$CONFIG_FILE"
    echo "RESOLUTION=$resolution" >> "$CONFIG_FILE"
    echo "RATE=$rate" >> "$CONFIG_FILE"
    echo "ROTATION=$rotation" >> "$CONFIG_FILE"

    feh --bg-scale /usr/share/bizhi.jpg 2>/dev/null
    exit 0
}

# ============================================================================
# Multi-monitor JSON apply
# ============================================================================

apply_json() {
    local json="$1"

    if ! has_jq; then
        echo "Error: jq is required for multi-monitor config" >&2
        exit 1
    fi

    # Validate JSON
    if ! echo "$json" | jq . >/dev/null 2>&1; then
        echo "Error: Invalid JSON" >&2
        exit 1
    fi

    local monitor_count
    monitor_count=$(echo "$json" | jq '.monitors | length')

    if [ "$monitor_count" -eq 0 ] 2>/dev/null; then
        echo "Error: No monitors in config" >&2
        exit 1
    fi

    # Apply each monitor separately to avoid one failure blocking all
    local i=0
    local has_error=0
    local error_msgs=""

    while [ $i -lt "$monitor_count" ]; do
        local name enabled mode rate rotation primary placement relative_to
        local xrandr_cmd="xrandr"

        name=$(echo "$json" | jq -r ".monitors[$i].name")
        enabled=$(echo "$json" | jq -r ".monitors[$i].enabled")

        xrandr_cmd="$xrandr_cmd --output $name"

        if [ "$enabled" = "true" ]; then
            mode=$(echo "$json" | jq -r ".monitors[$i].mode")
            rate=$(echo "$json" | jq -r ".monitors[$i].rate // \"60\"")
            rotation=$(echo "$json" | jq -r ".monitors[$i].rotation // \"normal\"")
            primary=$(echo "$json" | jq -r ".monitors[$i].primary")
            placement=$(echo "$json" | jq -r ".monitors[$i].placement // empty")
            relative_to=$(echo "$json" | jq -r ".monitors[$i].relative_to // empty")

            xrandr_cmd="$xrandr_cmd --mode $mode --rate $rate --rotate $rotation"

            if [ "$primary" = "true" ]; then
                xrandr_cmd="$xrandr_cmd --primary"
            fi

            if [ -n "$placement" ] && [ -n "$relative_to" ]; then
                xrandr_cmd="$xrandr_cmd --$placement $relative_to"
            fi
        else
            xrandr_cmd="$xrandr_cmd --off"
        fi

        echo "Executing: $xrandr_cmd"

        if ! eval "$xrandr_cmd" 2>&1; then
            echo "Warning: Failed to configure $name" >&2
            error_msgs="${error_msgs}${name}: configure failed\n"
            has_error=1
        fi

        i=$((i + 1))
    done

    if [ "$has_error" -eq 1 ]; then
        echo -e "Error: Some monitors failed to configure:\n$error_msgs" >&2
        exit 1
    fi

    # Save as JSON v2 format
    echo "$json" > "$CONFIG_FILE"

    feh --bg-scale /usr/share/bizhi.jpg 2>/dev/null
    echo "Settings applied and saved"
    exit 0
}

# ============================================================================
# Save current settings
# ============================================================================

save_current() {
    local primary_output
    primary_output=$(xrandr | grep " connected primary" | awk '{print $1}')
    if [ -z "$primary_output" ]; then
        primary_output=$(xrandr | grep " connected" | head -1 | awk '{print $1}')
    fi

    if [ -z "$primary_output" ]; then
        echo "Error: No connected display found"
        exit 1
    fi

    local current_mode current_rate
    current_mode=$(xrandr | grep -A1 "^$primary_output" | grep '\*' | awk '{print $1}')
    current_rate=$(xrandr | grep -A1 "^$primary_output" | grep '\*' | awk '{print $2}' | tr -d '*+')

    echo "OUTPUT=$primary_output" > "$CONFIG_FILE"
    echo "RESOLUTION=$current_mode" >> "$CONFIG_FILE"
    echo "RATE=$current_rate" >> "$CONFIG_FILE"
    echo "ROTATION=normal" >> "$CONFIG_FILE"

    echo "Saved: $primary_output @ $current_mode ${current_rate}Hz"
}

# ============================================================================
# Load and apply saved settings (boot restore)
# ============================================================================

load_settings() {
    if [ ! -e "$CONFIG_FILE" ]; then
        echo "No saved settings found"
        exit 0
    fi

    local first_char
    first_char=$(head -c1 "$CONFIG_FILE")

    if [ "$first_char" = "{" ]; then
        # JSON v2 format
        echo "Restoring JSON config..."
        apply_json "$(cat "$CONFIG_FILE")"
    else
        # Legacy format
        # shellcheck disable=SC1090
        source "$CONFIG_FILE"

        if [ -n "$OUTPUT" ] && [ -n "$RESOLUTION" ]; then
            echo "Applying saved settings: $OUTPUT @ $RESOLUTION ${RATE}Hz (${ROTATION})"
            setting_monitor "$OUTPUT" "$RESOLUTION" "$RATE" "$ROTATION"
        else
            local size
            size=$(cat "$CONFIG_FILE")
            echo "Applying legacy settings: $size"
            setting_simple "$size"
        fi
    fi
}

# ============================================================================
# Main entry
# ============================================================================

case "$1" in
    "")
        load_settings
        ;;
    "apply")
        if [ -z "$2" ]; then
            echo "Error: apply requires JSON argument" >&2
            exit 1
        fi
        apply_json "$2"
        ;;
    "save")
        save_current
        ;;
    *)
        if [ $# -eq 1 ]; then
            setting_simple "$1"
        elif [ $# -ge 2 ]; then
            setting_monitor "$1" "$2" "${3:-60}" "${4:-normal}"
        fi
        ;;
esac
