hypr-helper 0.1.1

Hyprland Utilities such as adjusting gaps, getting windowname and workspace information
use crate::{
    args::GapsVariant,
    utils::{exec, get_pwd},
};

use serde_json::Value;

/// Given GapsVariant executes respective function.
///
/// # Usage
///
/// Just pass in the `GapsVariant` request that you want to handle
/// ```rust
/// handle_gaps_command(GapsVariant::Increase);
/// ```
pub fn handle_gaps_command(variant: GapsVariant) {
    match variant {
        GapsVariant::Increase => increase_gaps(),
        GapsVariant::Decrease => decrease_gaps(),
        GapsVariant::Reset => reset_gaps(),
    }
}

/// Increases the current outer gap size by 5.
///
/// Changes the inner gap size based on the following
/// | Outer gap | Inner gap |
/// |-----------|-----------|
/// |      > 0  |         2 |
/// |      > 20 |         5 |
fn increase_gaps() {
    let target_gap = get_current_gap_size() + 5;

    match target_gap {
        x if x > 20 => set_inner_gap(5),
        x if x > 0 => set_inner_gap(2),
        _ => set_inner_gap(0),
    }

    set_outer_gap(target_gap);
}

/// Decreases current outer gap size by 5.
///
/// Changes the inner gap size based on the following
/// | Outer gap | Inner gap |
/// |-----------|-----------|
/// |      > 0  |         2 |
/// |      > 20 |         5 |
fn decrease_gaps() {
    let target_gap = get_current_gap_size() - 5;

    if target_gap < 0 {
        return;
    }

    match target_gap {
        x if x > 20 => set_inner_gap(5),
        x if x > 0 => set_inner_gap(2),
        _ => set_inner_gap(0),
    }

    set_outer_gap(target_gap);
}

/// Sets Inner and Outer gaps to 0
fn reset_gaps() {
    set_inner_gap(0);
    set_outer_gap(0);
}

/// Gets the current gap size.
fn get_current_gap_size() -> i8 {
    match exec(
        "hyprctl getoption general:gaps_out -j",
        get_pwd(None).as_path(),
    ) {
        Ok(o) => {
            let output = match String::from_utf8(o.stdout) {
                Ok(output) => output,
                Err(err) => {
                    println!("Error parsing hyprctl output: {err}");
                    std::process::exit(1);
                }
            };

            let json_value: Value = serde_json::from_str(&output).unwrap();
            let value: i8 = json_value["int"]
                .as_i64()
                .unwrap()
                .try_into()
                .unwrap_or_default();

            return value;
        }
        Err(err) => {
            println!("Error executing hyprctl: {err}");
            std::process::exit(1);
        }
    }
}

/// Sets inner gap to given `target_gap`
///
/// # Usage
///
/// Setting inner gaps to 10
/// ```rust
/// set_inner_gap(10);
fn set_inner_gap(target_gap: i8) {
    let command = format!("hyprctl keyword general:gaps_in {target_gap}");

    match exec(command.as_str(), get_pwd(None).as_path()) {
        Ok(_) => {
            println!("ok");
        }
        Err(err) => {
            println!("Failed to set gaps: {err}");
            std::process::exit(1);
        }
    }
}

/// Sets outer gap to given `target_gap`
///
/// # Usage
///
/// Setting outer gaps to 10
/// ```rust
/// set_outer_gap(10);
/// ```
fn set_outer_gap(target_gap: i8) {
    let command = format!("hyprctl keyword general:gaps_out {target_gap}");

    match exec(command.as_str(), get_pwd(None).as_path()) {
        Ok(_) => {
            println!("ok");
        }
        Err(err) => {
            println!("Failed to set gaps: {err}");
            std::process::exit(1);
        }
    }
}