mirror of
https://github.com/arthur-pbty/arch-custom-iso.git
synced 2026-08-01 20:28:05 +02:00
Compare commits
21
Commits
37e27c3a81
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
8a2fe1b8dd | ||
|
|
fb37dc8888 | ||
|
|
19fec9ca14 | ||
|
|
316328c1ef | ||
|
|
dd0a59f294 | ||
|
|
293d7b0ee4 | ||
|
|
3c03bbf848 | ||
|
|
3b64dbe5f8 | ||
|
|
c77747ef7b | ||
|
|
5f51ee7a63 | ||
|
|
7c1a06fdd2 | ||
|
|
f553441c26 | ||
|
|
fa63045ec0 | ||
|
|
f6b54a765b | ||
|
|
298e8a2e9b | ||
|
|
186d190b14 | ||
|
|
83feb61872 | ||
|
|
ce86966355 | ||
|
|
8410019d78 | ||
|
|
c492e21337 | ||
|
|
2f33d9f69b |
@@ -0,0 +1,50 @@
|
||||
name: Build and Test Custom Arch ISO
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ "main" ]
|
||||
pull_request:
|
||||
branches: [ "main" ]
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
build-iso:
|
||||
runs-on: ubuntu-latest
|
||||
container:
|
||||
image: archlinux:latest
|
||||
options: --privileged
|
||||
steps:
|
||||
- name: Checkout repository
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Install build dependencies
|
||||
run: |
|
||||
pacman -Syu --noconfirm
|
||||
pacman -S --noconfirm archiso git sudo base-devel fakeroot
|
||||
|
||||
- name: Create builder user
|
||||
run: |
|
||||
useradd -m -G wheel -s /bin/bash builder
|
||||
echo "builder ALL=(ALL) NOPASSWD: ALL" >> /etc/sudoers
|
||||
|
||||
- name: Run ISO build script
|
||||
run: |
|
||||
chown -R builder:builder .
|
||||
sudo -u builder bash ./build.sh
|
||||
|
||||
- name: Verify ISO creation
|
||||
run: |
|
||||
if [ -f out/*.iso ]; then
|
||||
echo "ISO successfully built!"
|
||||
ls -lh out/*.iso
|
||||
else
|
||||
echo "ISO build failed: No ISO file found in out/ directory."
|
||||
exit 1
|
||||
fi
|
||||
|
||||
- name: Upload ISO artifact
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: arch-custom-iso
|
||||
path: out/*.iso
|
||||
retention-days: 7
|
||||
@@ -13,6 +13,15 @@ work/
|
||||
*.img
|
||||
*.fs
|
||||
|
||||
# --- AJOUTS POUR LE HORS-LIGNE ---
|
||||
# Dossiers temporaires de compilation (créés par build.sh)
|
||||
offline_cache/
|
||||
aur_build/
|
||||
|
||||
# Le cache des paquets générés dans l'arborescence de l'ISO (GROS FICHIERS)
|
||||
airootfs/root/offline_cache/
|
||||
# ---------------------------------
|
||||
|
||||
# Editor
|
||||
.vscode/
|
||||
.idea/
|
||||
|
||||
@@ -13,6 +13,7 @@ This project allows you to generate a fully customized Arch Linux installation I
|
||||
- Automated install scripts
|
||||
- Custom configs (dotfiles, system settings)
|
||||
- Reproducible builds
|
||||
- Support for your own packages built from source
|
||||
|
||||
---
|
||||
|
||||
@@ -39,7 +40,7 @@ Run build script:
|
||||
|
||||
```bash
|
||||
chmod +x build.sh
|
||||
sudo ./build.sh
|
||||
./build.sh
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
@@ -0,0 +1,343 @@
|
||||
#? Config file for btop v.1.4.6
|
||||
|
||||
#* Name of a btop++/bpytop/bashtop formatted ".theme" file, "Default" and "TTY" for builtin themes.
|
||||
#* Themes should be placed in "../share/btop/themes" relative to binary or "$HOME/.config/btop/themes"
|
||||
color_theme = "current"
|
||||
|
||||
#* If the theme set background should be shown, set to False if you want terminal background transparency.
|
||||
theme_background = true
|
||||
|
||||
#* Sets if 24-bit truecolor should be used, will convert 24-bit colors to 256 color (6x6x6 color cube) if false.
|
||||
truecolor = true
|
||||
|
||||
#* Set to true to force tty mode regardless if a real tty has been detected or not.
|
||||
#* Will force 16-color mode and TTY theme, set all graph symbols to "tty" and swap out other non tty friendly symbols.
|
||||
force_tty = false
|
||||
|
||||
#* Define presets for the layout of the boxes. Preset 0 is always all boxes shown with default settings. Max 9 presets.
|
||||
#* Format: "box_name:P:G,box_name:P:G" P=(0 or 1) for alternate positions, G=graph symbol to use for box.
|
||||
#* Use whitespace " " as separator between different presets.
|
||||
#* Example: "cpu:0:default,mem:0:tty,proc:1:default cpu:0:braille,proc:0:tty"
|
||||
presets = "cpu:1:default,proc:0:default cpu:0:default,mem:0:default,net:0:default cpu:0:block,net:0:tty"
|
||||
|
||||
#* Set to True to enable "h,j,k,l,g,G" keys for directional control in lists.
|
||||
#* Conflicting keys for h:"help" and k:"kill" is accessible while holding shift.
|
||||
vim_keys = true
|
||||
|
||||
#* Rounded corners on boxes, is ignored if TTY mode is ON.
|
||||
rounded_corners = true
|
||||
|
||||
#* Use terminal synchronized output sequences to reduce flickering on supported terminals.
|
||||
terminal_sync = true
|
||||
|
||||
#* Default symbols to use for graph creation, "braille", "block" or "tty".
|
||||
#* "braille" offers the highest resolution but might not be included in all fonts.
|
||||
#* "block" has half the resolution of braille but uses more common characters.
|
||||
#* "tty" uses only 3 different symbols but will work with most fonts and should work in a real TTY.
|
||||
#* Note that "tty" only has half the horizontal resolution of the other two, so will show a shorter historical view.
|
||||
graph_symbol = "braille"
|
||||
|
||||
# Graph symbol to use for graphs in cpu box, "default", "braille", "block" or "tty".
|
||||
graph_symbol_cpu = "default"
|
||||
|
||||
# Graph symbol to use for graphs in gpu box, "default", "braille", "block" or "tty".
|
||||
graph_symbol_gpu = "default"
|
||||
|
||||
# Graph symbol to use for graphs in cpu box, "default", "braille", "block" or "tty".
|
||||
graph_symbol_mem = "default"
|
||||
|
||||
# Graph symbol to use for graphs in cpu box, "default", "braille", "block" or "tty".
|
||||
graph_symbol_net = "default"
|
||||
|
||||
# Graph symbol to use for graphs in cpu box, "default", "braille", "block" or "tty".
|
||||
graph_symbol_proc = "default"
|
||||
|
||||
#* Manually set which boxes to show. Available values are "cpu mem net proc" and "gpu0" through "gpu5", separate values with whitespace.
|
||||
shown_boxes = "cpu mem net proc"
|
||||
|
||||
#* Update time in milliseconds, recommended 2000 ms or above for better sample times for graphs.
|
||||
update_ms = 2000
|
||||
|
||||
#* Processes sorting, "pid" "program" "arguments" "threads" "user" "memory" "cpu lazy" "cpu direct",
|
||||
#* "cpu lazy" sorts top process over time (easier to follow), "cpu direct" updates top process directly.
|
||||
proc_sorting = "cpu lazy"
|
||||
|
||||
#* Reverse sorting order, True or False.
|
||||
proc_reversed = false
|
||||
|
||||
#* Show processes as a tree.
|
||||
proc_tree = false
|
||||
|
||||
#* Use the cpu graph colors in the process list.
|
||||
proc_colors = true
|
||||
|
||||
#* Use a darkening gradient in the process list.
|
||||
proc_gradient = true
|
||||
|
||||
#* If process cpu usage should be of the core it's running on or usage of the total available cpu power.
|
||||
proc_per_core = false
|
||||
|
||||
#* Show process memory as bytes instead of percent.
|
||||
proc_mem_bytes = true
|
||||
|
||||
#* Show cpu graph for each process.
|
||||
proc_cpu_graphs = true
|
||||
|
||||
#* Use /proc/[pid]/smaps for memory information in the process info box (very slow but more accurate)
|
||||
proc_info_smaps = false
|
||||
|
||||
#* Show proc box on left side of screen instead of right.
|
||||
proc_left = false
|
||||
|
||||
#* (Linux) Filter processes tied to the Linux kernel(similar behavior to htop).
|
||||
proc_filter_kernel = false
|
||||
|
||||
#* In tree-view, always accumulate child process resources in the parent process.
|
||||
proc_aggregate = false
|
||||
|
||||
#* Should cpu and memory usage display be preserved for dead processes when paused.
|
||||
keep_dead_proc_usage = false
|
||||
|
||||
#* Sets the CPU stat shown in upper half of the CPU graph, "total" is always available.
|
||||
#* Select from a list of detected attributes from the options menu.
|
||||
cpu_graph_upper = "Auto"
|
||||
|
||||
#* Sets the CPU stat shown in lower half of the CPU graph, "total" is always available.
|
||||
#* Select from a list of detected attributes from the options menu.
|
||||
cpu_graph_lower = "Auto"
|
||||
|
||||
#* If gpu info should be shown in the cpu box. Available values = "Auto", "On" and "Off".
|
||||
show_gpu_info = "Auto"
|
||||
|
||||
#* Toggles if the lower CPU graph should be inverted.
|
||||
cpu_invert_lower = true
|
||||
|
||||
#* Set to True to completely disable the lower CPU graph.
|
||||
cpu_single_graph = false
|
||||
|
||||
#* Show cpu box at bottom of screen instead of top.
|
||||
cpu_bottom = false
|
||||
|
||||
#* Shows the system uptime in the CPU box.
|
||||
show_uptime = true
|
||||
|
||||
#* Shows the CPU package current power consumption in watts. Requires running `make setcap` or `make setuid` or running with sudo.
|
||||
show_cpu_watts = true
|
||||
|
||||
#* Show cpu temperature.
|
||||
check_temp = true
|
||||
|
||||
#* Which sensor to use for cpu temperature, use options menu to select from list of available sensors.
|
||||
cpu_sensor = "Auto"
|
||||
|
||||
#* Show temperatures for cpu cores also if check_temp is True and sensors has been found.
|
||||
show_coretemp = true
|
||||
|
||||
#* Set a custom mapping between core and coretemp, can be needed on certain cpus to get correct temperature for correct core.
|
||||
#* Use lm-sensors or similar to see which cores are reporting temperatures on your machine.
|
||||
#* Format "x:y" x=core with wrong temp, y=core with correct temp, use space as separator between multiple entries.
|
||||
#* Example: "4:0 5:1 6:3"
|
||||
cpu_core_map = ""
|
||||
|
||||
#* Which temperature scale to use, available values: "celsius", "fahrenheit", "kelvin" and "rankine".
|
||||
temp_scale = "celsius"
|
||||
|
||||
#* Use base 10 for bits/bytes sizes, KB = 1000 instead of KiB = 1024.
|
||||
base_10_sizes = false
|
||||
|
||||
#* Show CPU frequency.
|
||||
show_cpu_freq = true
|
||||
|
||||
#* How to calculate CPU frequency, available values: "first", "range", "lowest", "highest" and "average".
|
||||
freq_mode = "first"
|
||||
|
||||
#* Draw a clock at top of screen, formatting according to strftime, empty string to disable.
|
||||
#* Special formatting: /host = hostname | /user = username | /uptime = system uptime
|
||||
clock_format = "%X"
|
||||
|
||||
#* Update main ui in background when menus are showing, set this to false if the menus is flickering too much for comfort.
|
||||
background_update = true
|
||||
|
||||
#* Custom cpu model name, empty string to disable.
|
||||
custom_cpu_name = ""
|
||||
|
||||
#* Optional filter for shown disks, should be full path of a mountpoint, separate multiple values with whitespace " ".
|
||||
#* Only disks matching the filter will be shown. Prepend exclude= to only show disks not matching the filter. Examples: disk_filter="/boot /home/user", disks_filter="exclude=/boot /home/user"
|
||||
disks_filter = ""
|
||||
|
||||
#* Show graphs instead of meters for memory values.
|
||||
mem_graphs = true
|
||||
|
||||
#* Show mem box below net box instead of above.
|
||||
mem_below_net = false
|
||||
|
||||
#* Count ZFS ARC in cached and available memory.
|
||||
zfs_arc_cached = true
|
||||
|
||||
#* If swap memory should be shown in memory box.
|
||||
show_swap = true
|
||||
|
||||
#* Show swap as a disk, ignores show_swap value above, inserts itself after first disk.
|
||||
swap_disk = true
|
||||
|
||||
#* If mem box should be split to also show disks info.
|
||||
show_disks = true
|
||||
|
||||
#* Filter out non physical disks. Set this to False to include network disks, RAM disks and similar.
|
||||
only_physical = true
|
||||
|
||||
#* Read disks list from /etc/fstab. This also disables only_physical.
|
||||
use_fstab = true
|
||||
|
||||
#* Setting this to True will hide all datasets, and only show ZFS pools. (IO stats will be calculated per-pool)
|
||||
zfs_hide_datasets = false
|
||||
|
||||
#* Set to true to show available disk space for privileged users.
|
||||
disk_free_priv = false
|
||||
|
||||
#* Toggles if io activity % (disk busy time) should be shown in regular disk usage view.
|
||||
show_io_stat = true
|
||||
|
||||
#* Toggles io mode for disks, showing big graphs for disk read/write speeds.
|
||||
io_mode = false
|
||||
|
||||
#* Set to True to show combined read/write io graphs in io mode.
|
||||
io_graph_combined = false
|
||||
|
||||
#* Set the top speed for the io graphs in MiB/s (100 by default), use format "mountpoint:speed" separate disks with whitespace " ".
|
||||
#* Example: "/mnt/media:100 /:20 /boot:1".
|
||||
io_graph_speeds = ""
|
||||
|
||||
#* Set fixed values for network graphs in Mebibits. Is only used if net_auto is also set to False.
|
||||
net_download = 100
|
||||
|
||||
net_upload = 100
|
||||
|
||||
#* Use network graphs auto rescaling mode, ignores any values set above and rescales down to 10 Kibibytes at the lowest.
|
||||
net_auto = true
|
||||
|
||||
#* Sync the auto scaling for download and upload to whichever currently has the highest scale.
|
||||
net_sync = true
|
||||
|
||||
#* Starts with the Network Interface specified here.
|
||||
net_iface = ""
|
||||
|
||||
#* "True" shows bitrates in base 10 (Kbps, Mbps). "False" shows bitrates in binary sizes (Kibps, Mibps, etc.). "Auto" uses base_10_sizes.
|
||||
base_10_bitrate = "Auto"
|
||||
|
||||
#* Show battery stats in top right if battery is present.
|
||||
show_battery = true
|
||||
|
||||
#* Which battery to use if multiple are present. "Auto" for auto detection.
|
||||
selected_battery = "Auto"
|
||||
|
||||
#* Show power stats of battery next to charge indicator.
|
||||
show_battery_watts = true
|
||||
|
||||
#* Set loglevel for "~/.local/state/btop.log" levels are: "ERROR" "WARNING" "INFO" "DEBUG".
|
||||
#* The level set includes all lower levels, i.e. "DEBUG" will show all logging info.
|
||||
log_level = "WARNING"
|
||||
|
||||
#* Automatically save current settings to config file on exit.
|
||||
save_config_on_exit = true
|
||||
|
||||
#* Measure PCIe throughput on NVIDIA cards, may impact performance on certain cards.
|
||||
nvml_measure_pcie_speeds = true
|
||||
|
||||
#* Measure PCIe throughput on AMD cards, may impact performance on certain cards.
|
||||
rsmi_measure_pcie_speeds = true
|
||||
|
||||
#* Horizontally mirror the GPU graph.
|
||||
gpu_mirror_graph = true
|
||||
|
||||
#* Set which GPU vendors to show. Available values are "nvidia amd intel"
|
||||
shown_gpus = "nvidia amd intel"
|
||||
|
||||
#* Custom gpu0 model name, empty string to disable.
|
||||
custom_gpu_name0 = ""
|
||||
|
||||
#* Custom gpu1 model name, empty string to disable.
|
||||
custom_gpu_name1 = ""
|
||||
|
||||
#* Custom gpu2 model name, empty string to disable.
|
||||
custom_gpu_name2 = ""
|
||||
|
||||
#* Custom gpu3 model name, empty string to disable.
|
||||
custom_gpu_name3 = ""
|
||||
|
||||
#* Custom gpu4 model name, empty string to disable.
|
||||
custom_gpu_name4 = ""
|
||||
|
||||
#* Custom gpu5 model name, empty string to disable.
|
||||
custom_gpu_name5 = ""
|
||||
|
||||
|
||||
# ────────────────────────────────────────────────────────────
|
||||
# BTOP THEME — Rainy Night City (matches your wallpaper)
|
||||
# ────────────────────────────────────────────────────────────
|
||||
|
||||
# Transparent / dark night background
|
||||
theme[main_bg]="#1e2030"
|
||||
|
||||
# Main text – soft grey-blue (city lights)
|
||||
theme[main_fg]="#cdd3e1"
|
||||
|
||||
# Titles – light blue highlight (lamp glow)
|
||||
theme[title]="#d6e7ff"
|
||||
|
||||
# Highlight text – muted light grey-blue
|
||||
theme[hi_fg]="#bfc6d4"
|
||||
|
||||
# Selected row – deeper night shade
|
||||
theme[selected_bg]="#14151f"
|
||||
|
||||
# Selected row text – bright white-blue
|
||||
theme[selected_fg]="#e8f1ff"
|
||||
|
||||
# Inactive/dim text – distant-building grey
|
||||
theme[inactive_fg]="#7d8291"
|
||||
|
||||
# Misc text – light city grey
|
||||
theme[proc_misc]="#bfc6d4"
|
||||
|
||||
# Box outlines – subtle bluish-grey (window frame color)
|
||||
theme[cpu_box]="#292b3b"
|
||||
theme[mem_box]="#292b3b"
|
||||
theme[net_box]="#292b3b"
|
||||
theme[proc_box]="#292b3b"
|
||||
|
||||
# Divider lines – same subtle outline tone
|
||||
theme[div_line]="#292b3b"
|
||||
|
||||
# Graph gradients – smooth blue-grey (rain & neon reflections)
|
||||
theme[temp_start]="#4a4f65"
|
||||
theme[temp_mid]="#8c92a3"
|
||||
theme[temp_end]="#d6e7ff"
|
||||
|
||||
theme[cpu_start]="#4a4f65"
|
||||
theme[cpu_mid]="#8c92a3"
|
||||
theme[cpu_end]="#d6e7ff"
|
||||
|
||||
theme[free_start]="#4a4f65"
|
||||
theme[free_mid]="#8c92a3"
|
||||
theme[free_end]="#d6e7ff"
|
||||
|
||||
theme[cached_start]="#4a4f65"
|
||||
theme[cached_mid]="#8c92a3"
|
||||
theme[cached_end]="#d6e7ff"
|
||||
|
||||
theme[available_start]="#4a4f65"
|
||||
theme[available_mid]="#8c92a3"
|
||||
theme[available_end]="#d6e7ff"
|
||||
|
||||
theme[used_start]="#4a4f65"
|
||||
theme[used_mid]="#8c92a3"
|
||||
theme[used_end]="#d6e7ff"
|
||||
|
||||
theme[download_start]="#4a4f65"
|
||||
theme[download_mid]="#8c92a3"
|
||||
theme[download_end]="#d6e7ff"
|
||||
|
||||
theme[upload_start]="#4a4f65"
|
||||
theme[upload_mid]="#8c92a3"
|
||||
theme[upload_end]="#d6e7ff"
|
||||
@@ -0,0 +1,331 @@
|
||||
## Configuration file for CAVA.
|
||||
# Remove the ; to change parameters.
|
||||
|
||||
|
||||
[general]
|
||||
|
||||
# Auto reload config if the configuration file has changed. 1 = on, 0 = off.
|
||||
; live-config = 0
|
||||
|
||||
# Smoothing mode. Can be 'normal', 'scientific' or 'waves'. DEPRECATED as of 0.6.0
|
||||
; mode = normal
|
||||
|
||||
# Accepts only non-negative values.
|
||||
; framerate = 60
|
||||
|
||||
# 'autosens' will attempt to decrease sensitivity if the bars peak. 1 = on, 0 = off
|
||||
# new as of 0.6.0 autosens of low values (dynamic range)
|
||||
# 'overshoot' allows bars to overshoot (in % of terminal height) without initiating autosens. DEPRECATED as of 0.6.0
|
||||
; autosens = 1
|
||||
; overshoot = 20
|
||||
|
||||
# Manual sensitivity in %. If autosens is enabled, this will only be the initial value.
|
||||
# 200 means double height. Accepts only non-negative values.
|
||||
; sensitivity = 100
|
||||
|
||||
# The number of bars (0-512). 0 sets it to auto (fill up console).
|
||||
# Bars' width and space between bars in number of characters.
|
||||
; bars = 0
|
||||
; bar_width = 2
|
||||
; bar_spacing = 1
|
||||
# bar_height is only used for output in "noritake" format
|
||||
; bar_height = 32
|
||||
|
||||
# For SDL width and space between bars is in pixels, defaults are:
|
||||
; bar_width = 20
|
||||
; bar_spacing = 5
|
||||
|
||||
# sdl_glsl have these default values, they are only used to calculate max number of bars.
|
||||
; bar_width = 1
|
||||
; bar_spacing = 0
|
||||
|
||||
# ceter bars in terminal, if there is space.
|
||||
; center_align = 1
|
||||
|
||||
# max height of bars in terminal, in percent of terminal height.
|
||||
; max_height = 100
|
||||
|
||||
|
||||
# Lower and higher cutoff frequencies for lowest and highest bars
|
||||
# the bandwidth of the visualizer.
|
||||
# Note: there is a minimum total bandwidth of 43Mhz x number of bars.
|
||||
# Cava will automatically increase the higher cutoff frequency if needed to satisfy the minimum bandwidth.
|
||||
; lower_cutoff_freq = 50
|
||||
; higher_cutoff_freq = 10000
|
||||
|
||||
|
||||
# Seconds with no input before cava goes to sleep mode. Cava will not perform FFT or drawing and
|
||||
# only check for input once per second. Cava will wake up once input is detected. 0 = disable.
|
||||
; sleep_timer = 0
|
||||
|
||||
|
||||
[input]
|
||||
|
||||
# Audio capturing method. Possible methods are: 'fifo', 'portaudio', 'pipewire', 'alsa', 'pulse', 'sndio', 'oss', 'jack' or 'shmem'
|
||||
# Defaults to 'oss', 'pipewire', 'sndio', 'jack', 'pulse', 'alsa', 'portaudio' or 'fifo', in that order, dependent on what support cava was built with.
|
||||
# On Mac it defaults to 'portaudio' or 'fifo'
|
||||
# On windows this is automatic and no input settings are needed.
|
||||
#
|
||||
# All input methods uses the same config variable 'source'
|
||||
# to define where it should get the audio.
|
||||
#
|
||||
# For pulseaudio and pipewire 'source' will be the source. Default: 'auto', which uses the monitor source of the default sink
|
||||
# (all pulseaudio sinks(outputs) have 'monitor' sources(inputs) associated with them).
|
||||
#
|
||||
# For pipewire 'source' will be the object name or object.serial of the device to capture from.
|
||||
# Both input and output devices are supported. To capture the monitor source of a sink node, append '.monitor' to the sink's object name.
|
||||
#
|
||||
# For alsa 'source' will be the capture device.
|
||||
# For fifo 'source' will be the path to fifo-file.
|
||||
# For shmem 'source' will be /squeezelite-AA:BB:CC:DD:EE:FF where 'AA:BB:CC:DD:EE:FF' will be squeezelite's MAC address
|
||||
#
|
||||
# For sndio 'source' will be a raw recording audio descriptor or a monitoring sub-device, e.g. 'rsnd/2' or 'snd/1'. Default: 'default'.
|
||||
# README.md contains further information on how to setup CAVA for sndio.
|
||||
#
|
||||
# For oss 'source' will be the path to a audio device, e.g. '/dev/dsp2'. Default: '/dev/dsp', i.e. the default audio device.
|
||||
# README.md contains further information on how to setup CAVA for OSS on FreeBSD.
|
||||
#
|
||||
# For jack 'source' will be the name of the JACK server to connect to, e.g. 'foobar'. Default: 'default'.
|
||||
# README.md contains further information on how to setup CAVA for JACK.
|
||||
#
|
||||
; method = pulse
|
||||
; source = auto
|
||||
|
||||
; method = pipewire
|
||||
; source = auto
|
||||
|
||||
; method = alsa
|
||||
; source = hw:Loopback,1
|
||||
|
||||
; method = fifo
|
||||
; source = /tmp/mpd.fifo
|
||||
|
||||
; method = shmem
|
||||
; source = /squeezelite-AA:BB:CC:DD:EE:FF
|
||||
|
||||
; method = portaudio
|
||||
; source = auto
|
||||
|
||||
; method = sndio
|
||||
; source = default
|
||||
|
||||
; method = oss
|
||||
; source = /dev/dsp
|
||||
|
||||
; method = jack
|
||||
; source = default
|
||||
|
||||
# The options 'sample_rate', 'sample_bits', 'channels' and 'autoconnect' can be configured for some input methods:
|
||||
# sample_rate: fifo, pipewire, sndio, oss
|
||||
# sample_bits: fifo, pipewire, sndio, oss
|
||||
# channels: sndio, oss, jack
|
||||
# autoconnect: jack
|
||||
# Other methods ignore these settings.
|
||||
# For pipewire, sample_rate will default to 48000, for all other input methods, sample_rate will default to 44100.
|
||||
#
|
||||
# For 'sndio' and 'oss' they are only preferred values, i.e. if the values are not supported
|
||||
# by the chosen audio device, the device will use other supported values instead.
|
||||
# Example: 48000, 32 and 2, but the device only supports 44100, 16 and 1, then it
|
||||
# will use 44100, 16 and 1.
|
||||
#
|
||||
#
|
||||
# The 'pipewire' input method has three options to control linking and mixing:
|
||||
# active: Force the node to always process. Useful for monitoring sources when no other application is active.
|
||||
# remix: Allow pipewire to remix audio channels to match cava's channel count. Useful for surround sound.
|
||||
# virtual: Set the node to virtual, to avoid recording notifications from the DE.
|
||||
#
|
||||
; sample_rate = 44100
|
||||
; sample_bits = 16
|
||||
; channels = 2
|
||||
; autoconnect = 2
|
||||
; active = 1
|
||||
; remix = 1
|
||||
; virtual = 1
|
||||
|
||||
|
||||
[output]
|
||||
|
||||
# Output method. Can be 'ncurses', 'noncurses', 'raw', 'noritake', 'sdl'
|
||||
# or 'sdl_glsl'.
|
||||
# 'noncurses' (default) uses a buffer and cursor movements to only print
|
||||
# changes from frame to frame in the terminal. Uses less resources and is less
|
||||
# prone to tearing (vsync issues) than 'ncurses'.
|
||||
#
|
||||
# 'raw' is an 8 or 16 bit (configurable via the 'bit_format' option) data
|
||||
# stream of the bar heights that can be used to send to other applications.
|
||||
# 'raw' defaults to 1024 bars stereo (512 bars mono), which can be adjusted in the 'bars' option above.
|
||||
#
|
||||
# 'noritake' outputs a bitmap in the format expected by a Noritake VFD display
|
||||
# in graphic mode. It only support the 3000 series graphical VFDs for now.
|
||||
#
|
||||
# 'sdl' uses the Simple DirectMedia Layer to render in a graphical context.
|
||||
# 'sdl_glsl' uses SDL to create an OpenGL context. Write your own shaders or
|
||||
# use one of the predefined ones.
|
||||
; method = noncurses
|
||||
|
||||
# Orientation of the visualization. Can be 'bottom', 'top', 'left', 'right' or
|
||||
# 'horizontal'. Default is 'bottom'. 'left and 'right' are only supported on sdl
|
||||
# and ncruses output. 'horizontal' (bars go up and down from center) is only supported
|
||||
# on noncurses output.
|
||||
# Note: many fonts have weird or missing glyphs for characters used in orientations
|
||||
# other than 'bottom', which can make output not look right.
|
||||
; orientation = bottom
|
||||
|
||||
# Visual channels. Can be 'stereo' or 'mono'.
|
||||
# 'stereo' mirrors both channels with low frequencies in center.
|
||||
# 'mono' outputs left to right lowest to highest frequencies.
|
||||
# 'mono_option' set mono to either take input from 'left', 'right' or 'average'.
|
||||
# set 'reverse' to 1 to display frequencies the other way around.
|
||||
; channels = stereo
|
||||
; mono_option = average
|
||||
; reverse = 0
|
||||
|
||||
# Only valid if orientation is set to 'horizontal'.
|
||||
# Set 'horizontal_stereo' to 1 to have left channel bars at top and right channel at bottom.
|
||||
# Set 'left_bottom' to 0 to have right channel at top and left channel at bottom.
|
||||
; horizontal_stereo = 0
|
||||
; left_bottom = 1
|
||||
|
||||
# Raw output target.
|
||||
# On Linux, a fifo will be created if target does not exist.
|
||||
# On Windows, a named pipe will be created if target does not exist.
|
||||
; raw_target = /dev/stdout
|
||||
|
||||
# Raw data format. Can be 'binary' or 'ascii'.
|
||||
; data_format = binary
|
||||
|
||||
# Binary bit format, can be '8bit' (0-255) or '16bit' (0-65530).
|
||||
; bit_format = 16bit
|
||||
|
||||
# Ascii max value. In 'ascii' mode range will run from 0 to value specified here
|
||||
; ascii_max_range = 1000
|
||||
|
||||
# Ascii delimiters. In ascii format each bar and frame is separated by a delimiters.
|
||||
# Use decimal value in ascii table (i.e. 59 = ';' and 10 = '\n' (line feed)).
|
||||
; bar_delimiter = 59
|
||||
; frame_delimiter = 10
|
||||
|
||||
# sdl window size and position. -1,-1 is centered.
|
||||
; sdl_width = 1024
|
||||
; sdl_height = 512
|
||||
; sdl_x = -1
|
||||
; sdl_y= -1
|
||||
; sdl_full_screen = 0
|
||||
|
||||
# set label on bars on the x-axis. Can be 'frequency' or 'none'. Default: 'none'
|
||||
# 'frequency' displays the lower cut off frequency of the bar above.
|
||||
# Only supported on ncurses and noncurses output.
|
||||
; xaxis = none
|
||||
|
||||
# enable synchronized sync. 1 = on, 0 = off
|
||||
# removes flickering in alacritty terminal emulator.
|
||||
# defaults to off since the behaviour in other terminal emulators is unknown
|
||||
; synchronized_sync = 0
|
||||
|
||||
# Shaders for sdl_glsl, located in $HOME/.config/cava/shaders
|
||||
; vertex_shader = pass_through.vert
|
||||
; fragment_shader = bar_spectrum.frag
|
||||
|
||||
; for glsl output mode, keep rendering even if no audio
|
||||
; continuous_rendering = 0
|
||||
|
||||
# disable console blank (screen saver) in tty
|
||||
# (Not supported on FreeBSD)
|
||||
; disable_blanking = 0
|
||||
|
||||
# show a flat bar at the bottom of the screen when idle, 1 = on, 0 = off
|
||||
; show_idle_bar_heads = 1
|
||||
|
||||
# show waveform instead of frequency spectrum, 1 = on, 0 = off
|
||||
; waveform = 0
|
||||
|
||||
[color]
|
||||
|
||||
# Colors can be one of seven predefined: black, blue, cyan, green, magenta, red, white, yellow.
|
||||
# Or defined by hex code '#xxxxxx' (hex code must be within ''). User defined colors requires
|
||||
# a terminal that can change color definitions such as Gnome-terminal or rxvt.
|
||||
# default is to keep current terminal color
|
||||
; background = default
|
||||
; foreground = default
|
||||
|
||||
# SDL and sdl_glsl only support hex code colors, these are the default:
|
||||
; background = '#111111'
|
||||
; foreground = '#33ffff'
|
||||
|
||||
|
||||
# Gradient mode, only hex defined colors are supported,
|
||||
# background must also be defined in hex or remain commented out. 1 = on, 0 = off.
|
||||
# You can define as many as 8 different colors. They range from bottom to top of screen
|
||||
gradient = 1
|
||||
gradient_count = 8
|
||||
gradient_color_1 = '#91e3e1'
|
||||
gradient_color_2 = '#a7aaaf'
|
||||
gradient_color_3 = '#d7d8db'
|
||||
gradient_color_4 = '#e382d2'
|
||||
gradient_color_5 = '#f6cbee'
|
||||
gradient_color_6 = '#d9f7f6'
|
||||
gradient_color_7 = '#f6cbee'
|
||||
gradient_color_8 = '#91e3e1'
|
||||
|
||||
|
||||
# Horizontal is only supported on noncurses output.
|
||||
# Only one color will be calculated per bar.
|
||||
; horizontal_gradient = 0
|
||||
; horizontal_gradient_color_1 = '#c45161'
|
||||
; horizontal_gradient_color_2 = '#e094a0'
|
||||
; horizontal_gradient_color_3 = '#f2b6c0'
|
||||
; horizontal_gradient_color_4 = '#f2dde1'
|
||||
; horizontal_gradient_color_5 = '#cbc7d8'
|
||||
; horizontal_gradient_color_6 = '#8db7d2'
|
||||
; horizontal_gradient_color_7 = '#5e62a9'
|
||||
; horizontal_gradient_color_8 = '#434279'
|
||||
|
||||
|
||||
# If both vertical and horizontal gradient is enabled, vertical will be blended in this direction.
|
||||
# Can be 'up', 'down', 'left' or 'right'. 'up' means the vertical gradient will be blended in from
|
||||
# bottom to top. I.e. the bottom will be only the horizontal
|
||||
# and top will be only the color of the vertical gradient.
|
||||
; blend_direction = 'up'
|
||||
|
||||
# use theme file instead of defining colors in this file
|
||||
# themes are located in $HOME/.config/cava/themes
|
||||
; theme = 'none'
|
||||
|
||||
|
||||
[smoothing]
|
||||
|
||||
# Percentage value for integral smoothing. Takes values from 0 - 100.
|
||||
# Higher values means smoother, but less precise. 0 to disable.
|
||||
# DEPRECATED as of 0.8.0, use noise_reduction instead
|
||||
; integral = 77
|
||||
|
||||
# Disables or enables the so-called "Monstercat smoothing" with or without "waves". Set to 0 to disable.
|
||||
; monstercat = 0
|
||||
; waves = 0
|
||||
|
||||
# Set gravity percentage for "drop off". Higher values means bars will drop faster.
|
||||
# Accepts only non-negative values. 50 means half gravity, 200 means double. Set to 0 to disable "drop off".
|
||||
# DEPRECATED as of 0.8.0, use noise_reduction instead
|
||||
; gravity = 100
|
||||
|
||||
|
||||
# In bar height, bars that would have been lower that this will not be drawn.
|
||||
# DEPRECATED as of 0.8.0
|
||||
; ignore = 0
|
||||
|
||||
# Noise reduction, int 0 - 100. default 77
|
||||
# the raw visualization is very noisy, this factor adjusts the integral and gravity filters to keep the signal smooth
|
||||
# 100 will be very slow and smooth, 0 will be fast but noisy.
|
||||
; noise_reduction = 77
|
||||
|
||||
|
||||
[eq]
|
||||
|
||||
# This one is tricky. You can have as much keys as you want.
|
||||
# Remember to uncomment more than one key! More keys = more precision.
|
||||
# Look at readme.md on github for further explanations and examples.
|
||||
; 1 = 1 # bass
|
||||
; 2 = 1
|
||||
; 3 = 1 # midtone
|
||||
; 4 = 1
|
||||
; 5 = 1 # treble
|
||||
@@ -0,0 +1,73 @@
|
||||
#version 330
|
||||
|
||||
in vec2 fragCoord;
|
||||
out vec4 fragColor;
|
||||
|
||||
// bar values. defaults to left channels first (low to high), then right (high to low).
|
||||
uniform float bars[512];
|
||||
|
||||
uniform int bars_count; // number of bars (left + right) (configurable)
|
||||
uniform int bar_width; // bar width (configurable), not used here
|
||||
uniform int bar_spacing; // space between bars (configurable)
|
||||
|
||||
uniform vec3 u_resolution; // window resolution
|
||||
|
||||
// colors, configurable in cava config file (r,g,b) (0.0 - 1.0)
|
||||
uniform vec3 bg_color; // background color
|
||||
uniform vec3 fg_color; // foreground color
|
||||
|
||||
uniform int gradient_count;
|
||||
uniform vec3 gradient_colors[8]; // gradient colors
|
||||
|
||||
uniform float shader_time; // shader execution time s (not used here)
|
||||
|
||||
uniform sampler2D inputTexture; // Texture from the last render pass (not used here)
|
||||
|
||||
vec3 normalize_C(float y, vec3 col_1, vec3 col_2, float y_min, float y_max) {
|
||||
// create color based on fraction of this color and next color
|
||||
float yr = (y - y_min) / (y_max - y_min);
|
||||
return col_1 * (1.0 - yr) + col_2 * yr;
|
||||
}
|
||||
|
||||
void main() {
|
||||
// find which bar to use based on where we are on the x axis
|
||||
float x = u_resolution.x * fragCoord.x;
|
||||
int bar = int(bars_count * fragCoord.x);
|
||||
|
||||
// calculate a bar size
|
||||
float bar_size = u_resolution.x / bars_count;
|
||||
|
||||
// the y coordinate and bar values are the same
|
||||
float y = bars[bar];
|
||||
|
||||
// make sure there is a thin line at bottom
|
||||
if (y * u_resolution.y < 1.0) {
|
||||
y = 1.0 / u_resolution.y;
|
||||
}
|
||||
|
||||
// draw the bar up to current height
|
||||
if (y > fragCoord.y) {
|
||||
// make some space between bars basen on settings
|
||||
if (x > (bar + 1) * (bar_size)-bar_spacing) {
|
||||
fragColor = vec4(bg_color, 1.0);
|
||||
} else {
|
||||
if (gradient_count == 0) {
|
||||
fragColor = vec4(fg_color, 1.0);
|
||||
} else {
|
||||
// find which color in the configured gradient we are at
|
||||
int color = int((gradient_count - 1) * fragCoord.y);
|
||||
|
||||
// find where on y this and next color is supposed to be
|
||||
float y_min = color / (gradient_count - 1.0);
|
||||
float y_max = (color + 1.0) / (gradient_count - 1.0);
|
||||
|
||||
// make color
|
||||
fragColor = vec4(normalize_C(fragCoord.y, gradient_colors[color],
|
||||
gradient_colors[color + 1], y_min, y_max),
|
||||
1.0);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
fragColor = vec4(bg_color, 1.0);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,117 @@
|
||||
#version 330
|
||||
|
||||
// this shader was stolen from shadertoy user ChunderFPV
|
||||
|
||||
#define SCALE 8.0
|
||||
#define PI radians(180.0)
|
||||
#define TAU (PI * 2.0)
|
||||
#define CS(a) vec2(cos(a), sin(a))
|
||||
#define PT(u, r) smoothstep(0.0, r, r - length(u))
|
||||
|
||||
in vec2 fragCoord;
|
||||
out vec4 fragColor;
|
||||
|
||||
uniform float bars[512];
|
||||
|
||||
uniform int bars_count; // number of bars (left + right) (configurable)
|
||||
uniform float shader_time; // shader execution time s
|
||||
uniform int bar_width; // bar width (configurable), not used here
|
||||
uniform int bar_spacing; // space between bars (configurable)
|
||||
|
||||
uniform vec3 u_resolution; // window resolution
|
||||
|
||||
// colors, configurable in cava config file (r,g,b) (0.0 - 1.0)
|
||||
uniform vec3 bg_color; // background color
|
||||
uniform vec3 fg_color; // foreground color
|
||||
|
||||
uniform int gradient_count;
|
||||
uniform vec3 gradient_colors[8]; // gradient colors
|
||||
|
||||
// gradient map ( color, equation, time, width, shadow, reciprocal )
|
||||
vec3 gm(vec3 c, float n, float t, float w, float d, bool i) {
|
||||
float g = min(abs(n), 1.0 / abs(n));
|
||||
float s = abs(sin(n * PI - t));
|
||||
if (i)
|
||||
s = min(s, abs(sin(PI / n + t)));
|
||||
return (1.0 - pow(abs(s), w)) * c * pow(g, d) * 6.0;
|
||||
}
|
||||
|
||||
// denominator spiral, use 1/n for numerator
|
||||
// ( screen xy, spiral exponent, decimal, line width, hardness, rotation )
|
||||
float ds(vec2 u, float e, float n, float w, float h, float ro) {
|
||||
float ur = length(u); // unit radius
|
||||
float sr = pow(ur, e); // spiral radius
|
||||
float a = round(sr) * n * TAU; // arc
|
||||
vec2 xy = CS(a + ro) * ur; // xy coords
|
||||
float l = PT(u - xy, w); // line
|
||||
float s = mod(sr + 0.5, 1.0); // gradient smooth
|
||||
s = min(s, 1.0 - s); // darken filter
|
||||
return l * s * h;
|
||||
}
|
||||
|
||||
void main() {
|
||||
float t = shader_time / PI * 2.0;
|
||||
vec4 m = vec4(0, 0, 0, 0); // iMouse;
|
||||
m.xy = m.xy * 2.0 / u_resolution.xy - 1.0; // ±1x, ±1y
|
||||
if (m.z > 0.0)
|
||||
t += m.y * SCALE; // move time with mouse y
|
||||
float z = (m.z > 0.0) ? pow(1.0 - abs(m.y), sign(m.y)) : 1.0; // zoom (+)
|
||||
float e = (m.z > 0.0) ? pow(1.0 - abs(m.x), -sign(m.x))
|
||||
: 1.0; // screen exponent (+)
|
||||
float se = (m.z > 0.0) ? e * -sign(m.y) : 1.0; // spiral exponent
|
||||
vec3 bg = vec3(0); // black background
|
||||
|
||||
float aa = 3.0; // anti-aliasing
|
||||
|
||||
for (float j = 0.0; j < aa; j++)
|
||||
for (float k = 0.0; k < aa; k++) {
|
||||
vec3 c = vec3(0);
|
||||
vec2 o = vec2(j, k) / aa;
|
||||
vec2 uv = (fragCoord * u_resolution.xy - 0.5 * u_resolution.xy + o) /
|
||||
u_resolution.y * SCALE * z; // apply cartesian, scale and zoom
|
||||
if (m.z > 0.0)
|
||||
uv =
|
||||
exp(log(abs(uv)) * e) * sign(uv); // warp screen space with exponent
|
||||
|
||||
float px = length(fwidth(uv)); // pixel width
|
||||
float x = uv.x; // every pixel on x
|
||||
float y = uv.y; // every pixel on y
|
||||
float l = length(uv); // hypot of xy: sqrt(x*x+y*y)
|
||||
|
||||
float mc = (x * x + y * y - 1.0) / y; // metallic circle at xy
|
||||
float g = min(abs(mc), 1.0 / abs(mc)); // gradient
|
||||
vec3 gold = vec3(1.0, 0.6, 0.0) * g * l;
|
||||
vec3 blue = vec3(0.3, 0.5, 0.9) * (1.0 - g);
|
||||
vec3 rgb = max(gold, blue);
|
||||
|
||||
float w = 0.1; // line width
|
||||
float d = 0.4; // shadow depth
|
||||
c = max(c, gm(rgb, mc, -t, w * bars[0], d, false)); // metallic
|
||||
c = max(c, gm(rgb, abs(y / x) * sign(y), -t, w * bars[1], d,
|
||||
false)); // tangent
|
||||
c = max(c, gm(rgb, (x * x) / (y * y) * sign(y), -t, w * bars[2], d,
|
||||
false)); // sqrt cotangent
|
||||
c = max(c, gm(rgb, (x * x) + (y * y), t, w * bars[3], d,
|
||||
true)); // sqrt circles
|
||||
|
||||
c += rgb * ds(uv, se, t / TAU, px * 2.0 * bars[4], 2.0, 0.0); // spiral 1a
|
||||
c += rgb * ds(uv, se, t / TAU, px * 2.0 * bars[5], 2.0, PI); // spiral 1b
|
||||
c +=
|
||||
rgb * ds(uv, -se, t / TAU, px * 2.0 * bars[6], 2.0, 0.0); // spiral 2a
|
||||
c += rgb * ds(uv, -se, t / TAU, px * 2.0 * bars[7], 2.0, PI); // spiral 2b
|
||||
c = max(c, 0.0); // clear negative color
|
||||
|
||||
c += pow(max(1.0 - l, 0.0), 3.0 / z); // center glow
|
||||
|
||||
if (m.z > 0.0) // display grid on click
|
||||
{
|
||||
vec2 xyg = abs(fract(uv + 0.5) - 0.5) / px; // xy grid
|
||||
c.gb += 0.2 * (1.0 - min(min(xyg.x, xyg.y), 1.0));
|
||||
}
|
||||
bg += c;
|
||||
}
|
||||
bg /= aa * aa;
|
||||
bg *= sqrt(bg) * 1.5;
|
||||
|
||||
fragColor = vec4(bg, 1.0);
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
#version 330
|
||||
|
||||
in vec2 fragCoord;
|
||||
out vec4 fragColor;
|
||||
|
||||
// bar values. defaults to left channels first (low to high), then right (high to low).
|
||||
uniform float bars[512];
|
||||
|
||||
uniform int bars_count; // number of bars (left + right) (configurable)
|
||||
|
||||
uniform vec3 u_resolution; // window resolution, not used here
|
||||
|
||||
//colors, configurable in cava config file
|
||||
uniform vec3 bg_color; // background color(r,g,b) (0.0 - 1.0), not used here
|
||||
uniform vec3 fg_color; // foreground color, not used here
|
||||
|
||||
void main()
|
||||
{
|
||||
// find which bar to use based on where we are on the x axis
|
||||
int bar = int(bars_count * fragCoord.x);
|
||||
|
||||
float bar_y = 1.0 - abs((fragCoord.y - 0.5)) * 2.0;
|
||||
float y = (bars[bar]) * bar_y;
|
||||
|
||||
float bar_x = (fragCoord.x - float(bar) / float(bars_count)) * bars_count;
|
||||
float bar_r = 1.0 - abs((bar_x - 0.5)) * 2;
|
||||
|
||||
bar_r = bar_r * bar_r * 2;
|
||||
|
||||
// set color
|
||||
fragColor.r = fg_color.x * y * bar_r;
|
||||
fragColor.g = fg_color.y * y * bar_r;
|
||||
fragColor.b = fg_color.z * y * bar_r;
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
#version 330
|
||||
|
||||
|
||||
// Input vertex data, different for all executions of this shader.
|
||||
layout(location = 0) in vec3 vertexPosition_modelspace;
|
||||
|
||||
// Output data ; will be interpolated for each fragment.
|
||||
out vec2 fragCoord;
|
||||
|
||||
void main()
|
||||
{
|
||||
gl_Position = vec4(vertexPosition_modelspace,1);
|
||||
fragCoord = (vertexPosition_modelspace.xy+vec2(1,1))/2.0;
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
#version 330
|
||||
|
||||
in vec2 fragCoord;
|
||||
out vec4 fragColor;
|
||||
|
||||
// bar values. defaults to left channels first (low to high), then right (high
|
||||
// to low).
|
||||
uniform float bars[512];
|
||||
|
||||
uniform int bars_count; // number of bars (left + right) (configurable)
|
||||
uniform int bar_width; // bar width (configurable), not used here
|
||||
uniform int bar_spacing; // space between bars (configurable)
|
||||
|
||||
uniform vec3 u_resolution; // window resolution
|
||||
|
||||
// colors, configurable in cava config file (r,g,b) (0.0 - 1.0)
|
||||
uniform vec3 bg_color; // background color
|
||||
uniform vec3 fg_color; // foreground color
|
||||
|
||||
uniform int gradient_count;
|
||||
uniform vec3 gradient_colors[8]; // gradient colors
|
||||
|
||||
uniform sampler2D inputTexture; // Texture from the last render pass
|
||||
|
||||
vec3 normalize_C(float y, vec3 col_1, vec3 col_2, float y_min, float y_max) {
|
||||
// create color based on fraction of this color and next color
|
||||
float yr = (y - y_min) / (y_max - y_min);
|
||||
return col_1 * (1.0 - yr) + col_2 * yr;
|
||||
}
|
||||
|
||||
void main() {
|
||||
// find which bar to use based on where we are on the y axis
|
||||
int bar = int(bars_count * fragCoord.y);
|
||||
float y = bars[bar];
|
||||
float band_size = 1.0 / float(bars_count);
|
||||
float current_band_min = bar * band_size;
|
||||
float current_band_max = (bar + 1) * band_size;
|
||||
|
||||
int hist_length = 512;
|
||||
float win_size = 1.0 / hist_length;
|
||||
|
||||
if (fragCoord.x > 1.0 - win_size) {
|
||||
|
||||
if (fragCoord.y > current_band_min && fragCoord.y < current_band_max) {
|
||||
|
||||
fragColor = vec4(fg_color * y, 1.0);
|
||||
}
|
||||
} else {
|
||||
vec2 offsetCoord = fragCoord;
|
||||
offsetCoord.x += float(win_size);
|
||||
fragColor = texture(inputTexture, offsetCoord);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,112 @@
|
||||
#version 330
|
||||
|
||||
// Emulate the "line style" spectrum analyzer from Winamp 2.
|
||||
// Try this config for a demonstration:
|
||||
|
||||
/*
|
||||
[general]
|
||||
bar_width = 2
|
||||
bar_spacing = 0
|
||||
higher_cutoff_freq = 22000
|
||||
|
||||
[output]
|
||||
method = sdl_glsl
|
||||
channels = mono
|
||||
fragment_shader = winamp_line_style_spectrum.frag
|
||||
|
||||
[color]
|
||||
background = '#000000'
|
||||
gradient = 1
|
||||
gradient_color_1 = '#319C08'
|
||||
gradient_color_2 = '#29CE10'
|
||||
gradient_color_3 = '#BDDE29'
|
||||
gradient_color_4 = '#DEA518'
|
||||
gradient_color_5 = '#D66600'
|
||||
gradient_color_6 = '#CE2910'
|
||||
|
||||
[smoothing]
|
||||
noise_reduction = 10
|
||||
*/
|
||||
|
||||
in vec2 fragCoord;
|
||||
out vec4 fragColor;
|
||||
|
||||
// bar values. defaults to left channels first (low to high), then right (high to low).
|
||||
uniform float bars[512];
|
||||
|
||||
uniform int bars_count; // number of bars (left + right) (configurable)
|
||||
uniform int bar_width; // bar width (configurable), not used here
|
||||
uniform int bar_spacing; // space between bars (configurable)
|
||||
|
||||
uniform vec3 u_resolution; // window resolution
|
||||
|
||||
//colors, configurable in cava config file (r,g,b) (0.0 - 1.0)
|
||||
uniform vec3 bg_color; // background color
|
||||
uniform vec3 fg_color; // foreground color
|
||||
|
||||
uniform int gradient_count;
|
||||
uniform vec3 gradient_colors[8]; // gradient colors
|
||||
|
||||
vec3 normalize_C(float y,vec3 col_1, vec3 col_2, float y_min, float y_max)
|
||||
{
|
||||
//create color based on fraction of this color and next color
|
||||
float yr = (y - y_min) / (y_max - y_min);
|
||||
return col_1 * (1.0 - yr) + col_2 * yr;
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
// find which bar to use based on where we are on the x axis
|
||||
float x = u_resolution.x * fragCoord.x;
|
||||
int bar = int(bars_count * fragCoord.x);
|
||||
|
||||
//calculate a bar size
|
||||
float bar_size = u_resolution.x / bars_count;
|
||||
|
||||
//the y coordinate is stretched by 4X to resemble Winamp
|
||||
float y = min(bars[bar] * 4.0, 1.0);
|
||||
|
||||
// make sure there is a thin line at bottom
|
||||
if (y * u_resolution.y < 1.0)
|
||||
{
|
||||
y = 1.0 / u_resolution.y;
|
||||
}
|
||||
|
||||
vec4 bar_color;
|
||||
|
||||
if (gradient_count == 0)
|
||||
{
|
||||
bar_color = vec4(fg_color,1.0);
|
||||
}
|
||||
else
|
||||
{
|
||||
//find color in the configured gradient for the top of the bar
|
||||
int color = int((gradient_count - 1) * y);
|
||||
|
||||
//find where on y this and next color is supposed to be
|
||||
float y_min = float(color) / (gradient_count - 1.0);
|
||||
float y_max = float(color + 1) / (gradient_count - 1.0);
|
||||
|
||||
//make a solid color for the entire bar
|
||||
bar_color = vec4(normalize_C(y, gradient_colors[color], gradient_colors[color + 1], y_min, y_max), 1.0);
|
||||
}
|
||||
|
||||
|
||||
//draw the bar up to current height
|
||||
if (y > fragCoord.y)
|
||||
{
|
||||
//make some space between bars based on settings
|
||||
if (x > (bar + 1) * (bar_size) - bar_spacing)
|
||||
{
|
||||
fragColor = vec4(bg_color,1.0);
|
||||
}
|
||||
else
|
||||
{
|
||||
fragColor = bar_color;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
fragColor = vec4(bg_color,1.0);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
[color]
|
||||
background = '#001e26'
|
||||
foreground = '#708183'
|
||||
|
||||
gradient = 1
|
||||
gradient_color_1 = '#268bd2'
|
||||
gradient_color_2 = '#6c71c4'
|
||||
gradient_color_3 = '#cb4b16'
|
||||
|
||||
horizontal_gradient = 1
|
||||
horizontal_gradient_color_1 = '#586e75'
|
||||
horizontal_gradient_color_2 = '#b58900'
|
||||
horizontal_gradient_color_3 = '#839496'
|
||||
|
||||
blend_direction = 'up'
|
||||
@@ -0,0 +1,10 @@
|
||||
[color]
|
||||
horizontal_gradient = 1
|
||||
horizontal_gradient_color_1 = '#c45161'
|
||||
horizontal_gradient_color_2 = '#e094a0'
|
||||
horizontal_gradient_color_3 = '#f2b6c0'
|
||||
horizontal_gradient_color_4 = '#f2dde1'
|
||||
horizontal_gradient_color_5 = '#cbc7d8'
|
||||
horizontal_gradient_color_6 = '#8db7d2'
|
||||
horizontal_gradient_color_7 = '#5e62a9'
|
||||
horizontal_gradient_color_8 = '#434279'
|
||||
@@ -0,0 +1,19 @@
|
||||
-`
|
||||
.o+`
|
||||
`ooo/
|
||||
`+oooo:
|
||||
`+oooooo:
|
||||
-+oooooo+:
|
||||
`/:-:++oooo+:
|
||||
`/++++/+++++++:
|
||||
`/++++++++++++++:
|
||||
`/+++ooooooooooooo/`
|
||||
./ooosssso++osssssso+`
|
||||
.oossssso-````/ossssss+`
|
||||
-osssssso. :ssssssso.
|
||||
:osssssss/ osssso+++.
|
||||
/ossssssss/ +ssssooo/-
|
||||
`/ossssso+/:- -:/+osssso+-
|
||||
`+sso+:-` `.-/+oso:
|
||||
`++:. `-/+/
|
||||
.` `
|
||||
@@ -0,0 +1,147 @@
|
||||
{
|
||||
"$schema": "https://github.com/fastfetch-cli/fastfetch/raw/dev/doc/json_schema.json",
|
||||
"logo": {
|
||||
"type": "file",
|
||||
"source": "~/.config/fastfetch/about.txt",
|
||||
"color": { "1": "blue" },
|
||||
"padding": {
|
||||
"top": 2,
|
||||
"right": 6,
|
||||
"left": 2
|
||||
}
|
||||
},
|
||||
"modules": [
|
||||
"break",
|
||||
{
|
||||
"type": "custom",
|
||||
"format": "\u001b[90m┌──────────────────────Hardware──────────────────────┐"
|
||||
},
|
||||
{
|
||||
"type": "host",
|
||||
"key": " PC",
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "cpu",
|
||||
"key": "│ ├",
|
||||
"showPeCoreCount": true,
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "gpu",
|
||||
"key": "│ ├",
|
||||
"detectionMethod": "pci",
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "display",
|
||||
"key": "│ ├",
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "disk",
|
||||
"key": "│ ├",
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "memory",
|
||||
"key": "│ ├",
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "swap",
|
||||
"key": "└ └",
|
||||
"keyColor": "green"
|
||||
},
|
||||
{
|
||||
"type": "custom",
|
||||
"format": "\u001b[90m└────────────────────────────────────────────────────┘"
|
||||
},
|
||||
|
||||
"break",
|
||||
|
||||
{
|
||||
"type": "custom",
|
||||
"format": "\u001b[90m┌──────────────────────Software──────────────────────┐"
|
||||
},
|
||||
{
|
||||
"type": "os",
|
||||
"key": " OS",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "kernel",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "wm",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "shell",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "terminal",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "packages",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "wmtheme",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "theme",
|
||||
"key": "│ ├",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "terminalfont",
|
||||
"key": "└ └",
|
||||
"keyColor": "blue"
|
||||
},
|
||||
{
|
||||
"type": "custom",
|
||||
"format": "\u001b[90m└────────────────────────────────────────────────────┘"
|
||||
},
|
||||
|
||||
"break",
|
||||
|
||||
{
|
||||
"type": "custom",
|
||||
"format": "\u001b[90m┌────────────────Age / Uptime / Update───────────────┐"
|
||||
},
|
||||
{
|
||||
"type": "command",
|
||||
"key": " OS Age",
|
||||
"keyColor": "magenta",
|
||||
"text": "echo $(( ($(date +%s) - $(stat -c %W /)) / 86400 )) days"
|
||||
},
|
||||
{
|
||||
"type": "uptime",
|
||||
"key": " Uptime",
|
||||
"keyColor": "magenta"
|
||||
},
|
||||
{
|
||||
"type": "command",
|
||||
"key": " Updates",
|
||||
"keyColor": "magenta",
|
||||
"text": "checkupdates 2>/dev/null | wc -l"
|
||||
},
|
||||
{
|
||||
"type": "custom",
|
||||
"format": "\u001b[90m└────────────────────────────────────────────────────┘"
|
||||
},
|
||||
|
||||
"break"
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,58 @@
|
||||
# Background and foreground colors
|
||||
background = #1e1e2e
|
||||
foreground = #cdd6f4
|
||||
|
||||
# Standard colors
|
||||
palette = 0=#45475a
|
||||
palette = 1=#f38ba8
|
||||
palette = 2=#a6e3a1
|
||||
palette = 3=#f9e2af
|
||||
palette = 4=#89b4fa
|
||||
palette = 5=#cba6f7
|
||||
palette = 6=#94e2d5
|
||||
palette = 7=#bac2de
|
||||
|
||||
# Bright colors
|
||||
palette = 8=#585b70
|
||||
palette = 9=#f38ba8
|
||||
palette = 10=#a6e3a1
|
||||
palette = 11=#f9e2af
|
||||
palette = 12=#89b4fa
|
||||
palette = 13=#cba6f7
|
||||
palette = 14=#94e2d5
|
||||
palette = 15=#cdd6f4
|
||||
|
||||
# Font
|
||||
font-family = "JetBrainsMono Nerd Font"
|
||||
font-style = Regular
|
||||
font-size = 9
|
||||
|
||||
# Window
|
||||
window-theme = ghostty
|
||||
window-padding-x = 14
|
||||
window-padding-y = 14
|
||||
confirm-close-surface=false
|
||||
resize-overlay = never
|
||||
gtk-toolbar-style = flat
|
||||
|
||||
# Cursor styling
|
||||
cursor-style = "block"
|
||||
cursor-style-blink = false
|
||||
|
||||
# Cursor styling + SSH session terminfo
|
||||
# (all shell integration options must be passed together)
|
||||
shell-integration-features = no-cursor,ssh-env
|
||||
|
||||
# Keyboard bindings
|
||||
keybind = shift+insert=paste_from_clipboard
|
||||
keybind = control+insert=copy_to_clipboard
|
||||
keybind = super+control+shift+alt+arrow_down=resize_split:down,100
|
||||
keybind = super+control+shift+alt+arrow_up=resize_split:up,100
|
||||
keybind = super+control+shift+alt+arrow_left=resize_split:left,100
|
||||
keybind = super+control+shift+alt+arrow_right=resize_split:right,100
|
||||
|
||||
# Slowdown mouse scrolling
|
||||
mouse-scroll-multiplier = 0.95
|
||||
|
||||
# Fix general slowness on hyprland (https://github.com/ghostty-org/ghostty/discussions/3224)
|
||||
async-backend = epoll
|
||||
@@ -0,0 +1,358 @@
|
||||
-- Refer to the wiki for more information.
|
||||
-- https://wiki.hypr.land/Configuring/Start/
|
||||
|
||||
-- Please note not all available settings / options are set here.
|
||||
-- For a full list, see the wiki
|
||||
|
||||
-- You can (and should!!) split this configuration into multiple files
|
||||
-- Create your files separately and then require them like this:
|
||||
-- require("myColors")
|
||||
|
||||
|
||||
------------------
|
||||
---- MONITORS ----
|
||||
------------------
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Basics/Monitors/
|
||||
hl.monitor({
|
||||
output = "",
|
||||
mode = "preferred",
|
||||
position = "auto",
|
||||
scale = "auto",
|
||||
})
|
||||
|
||||
|
||||
---------------------
|
||||
---- MY PROGRAMS ----
|
||||
---------------------
|
||||
|
||||
-- Set programs that you use
|
||||
local terminal = "ghostty"
|
||||
local fileManager = "yazi"
|
||||
local menu = "rofi -show drun"
|
||||
|
||||
|
||||
-------------------
|
||||
---- AUTOSTART ----
|
||||
-------------------
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Basics/Autostart/
|
||||
|
||||
-- Autostart necessary processes (like notifications daemons, status bars, etc.)
|
||||
-- Or execute your favorite apps at launch like this:
|
||||
--
|
||||
hl.on("hyprland.start", function ()
|
||||
--hl.exec_cmd("hyprpaper")
|
||||
hl.exec_cmd("waybar")
|
||||
end)
|
||||
|
||||
|
||||
-------------------------------
|
||||
---- ENVIRONMENT VARIABLES ----
|
||||
-------------------------------
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Advanced-and-Cool/Environment-variables/
|
||||
|
||||
hl.env("XCURSOR_SIZE", "24")
|
||||
hl.env("HYPRCURSOR_SIZE", "24")
|
||||
|
||||
|
||||
-----------------------
|
||||
----- PERMISSIONS -----
|
||||
-----------------------
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Advanced-and-Cool/Permissions/
|
||||
-- Please note permission changes here require a Hyprland restart and are not applied on-the-fly
|
||||
-- for security reasons
|
||||
|
||||
-- hl.config({
|
||||
-- ecosystem = {
|
||||
-- enforce_permissions = true,
|
||||
-- },
|
||||
-- })
|
||||
|
||||
-- hl.permission("/usr/(bin|local/bin)/grim", "screencopy", "allow")
|
||||
-- hl.permission("/usr/(lib|libexec|lib64)/xdg-desktop-portal-hyprland", "screencopy", "allow")
|
||||
-- hl.permission("/usr/(bin|local/bin)/hyprpm", "plugin", "allow")
|
||||
|
||||
|
||||
-----------------------
|
||||
---- LOOK AND FEEL ----
|
||||
-----------------------
|
||||
|
||||
-- Refer to https://wiki.hypr.land/Configuring/Basics/Variables/
|
||||
hl.config({
|
||||
general = {
|
||||
gaps_in = 2,
|
||||
gaps_out = 4,
|
||||
|
||||
border_size = 2,
|
||||
|
||||
col = {
|
||||
active_border = "rgb(303463)",
|
||||
inactive_border = "rgb(1a1b26)",
|
||||
},
|
||||
|
||||
-- Set to true to enable resizing windows by clicking and dragging on borders and gaps
|
||||
resize_on_border = false,
|
||||
|
||||
-- Please see https://wiki.hypr.land/Configuring/Advanced-and-Cool/Tearing/ before you turn this on
|
||||
allow_tearing = false,
|
||||
|
||||
layout = "dwindle",
|
||||
},
|
||||
|
||||
decoration = {
|
||||
rounding = 14,
|
||||
rounding_power = 5,
|
||||
|
||||
-- Change transparency of focused and unfocused windows
|
||||
active_opacity = 0.93,
|
||||
inactive_opacity = 0.92,
|
||||
fullscreen_opacity = 1.0,
|
||||
|
||||
shadow = {
|
||||
enabled = false,
|
||||
range = 15,
|
||||
render_power = 5,
|
||||
color = 0xee1a1a1a,
|
||||
},
|
||||
|
||||
blur = {
|
||||
enabled = true,
|
||||
size = 1,
|
||||
passes = 4,
|
||||
vibrancy = 0.2,
|
||||
},
|
||||
},
|
||||
|
||||
animations = {
|
||||
enabled = true,
|
||||
},
|
||||
})
|
||||
|
||||
-- Default curves and animations, see https://wiki.hypr.land/Configuring/Advanced-and-Cool/Animations/
|
||||
hl.curve("easeOutQuint", { type = "bezier", points = { {0.23, 1}, {0.32, 1} } })
|
||||
hl.curve("easeInOutCubic", { type = "bezier", points = { {0.65, 0.05}, {0.36, 1} } })
|
||||
hl.curve("linear", { type = "bezier", points = { {0, 0}, {1, 1} } })
|
||||
hl.curve("almostLinear", { type = "bezier", points = { {0.5, 0.5}, {0.75, 1} } })
|
||||
hl.curve("quick", { type = "bezier", points = { {0.15, 0}, {0.1, 1} } })
|
||||
|
||||
-- Default springs
|
||||
hl.curve("easy", { type = "spring", mass = 1, stiffness = 71.2633, dampening = 15.8273644 })
|
||||
|
||||
hl.animation({ leaf = "global", enabled = true, speed = 10, bezier = "default" })
|
||||
hl.animation({ leaf = "border", enabled = true, speed = 5.39, bezier = "easeOutQuint" })
|
||||
hl.animation({ leaf = "windows", enabled = true, speed = 4.79, spring = "easy" })
|
||||
hl.animation({ leaf = "windowsIn", enabled = true, speed = 4.1, spring = "easy", style = "popin 87%" })
|
||||
hl.animation({ leaf = "windowsOut", enabled = true, speed = 1.49, bezier = "linear", style = "popin 87%" })
|
||||
hl.animation({ leaf = "fadeIn", enabled = true, speed = 1.73, bezier = "almostLinear" })
|
||||
hl.animation({ leaf = "fadeOut", enabled = true, speed = 1.46, bezier = "almostLinear" })
|
||||
hl.animation({ leaf = "fade", enabled = true, speed = 3.03, bezier = "quick" })
|
||||
hl.animation({ leaf = "layers", enabled = true, speed = 3.81, bezier = "easeOutQuint" })
|
||||
hl.animation({ leaf = "layersIn", enabled = true, speed = 4, bezier = "easeOutQuint", style = "fade" })
|
||||
hl.animation({ leaf = "layersOut", enabled = true, speed = 1.5, bezier = "linear", style = "fade" })
|
||||
hl.animation({ leaf = "fadeLayersIn", enabled = true, speed = 1.79, bezier = "almostLinear" })
|
||||
hl.animation({ leaf = "fadeLayersOut", enabled = true, speed = 1.39, bezier = "almostLinear" })
|
||||
hl.animation({ leaf = "workspaces", enabled = true, speed = 1.94, bezier = "almostLinear", style = "fade" })
|
||||
hl.animation({ leaf = "workspacesIn", enabled = true, speed = 1.21, bezier = "almostLinear", style = "fade" })
|
||||
hl.animation({ leaf = "workspacesOut", enabled = true, speed = 1.94, bezier = "almostLinear", style = "fade" })
|
||||
hl.animation({ leaf = "zoomFactor", enabled = true, speed = 7, bezier = "quick" })
|
||||
|
||||
-- Ref https://wiki.hypr.land/Configuring/Basics/Workspace-Rules/
|
||||
-- "Smart gaps" / "No gaps when only"
|
||||
-- uncomment all if you wish to use that.
|
||||
-- hl.workspace_rule({ workspace = "w[tv1]", gaps_out = 0, gaps_in = 0 })
|
||||
-- hl.workspace_rule({ workspace = "f[1]", gaps_out = 0, gaps_in = 0 })
|
||||
-- hl.window_rule({
|
||||
-- name = "no-gaps-wtv1",
|
||||
-- match = { float = false, workspace = "w[tv1]" },
|
||||
-- border_size = 0,
|
||||
-- rounding = 0,
|
||||
-- })
|
||||
-- hl.window_rule({
|
||||
-- name = "no-gaps-f1",
|
||||
-- match = { float = false, workspace = "f[1]" },
|
||||
-- border_size = 0,
|
||||
-- rounding = 0,
|
||||
-- })
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Layouts/Dwindle-Layout/ for more
|
||||
hl.config({
|
||||
dwindle = {
|
||||
preserve_split = true, -- You probably want this
|
||||
},
|
||||
})
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Layouts/Master-Layout/ for more
|
||||
hl.config({
|
||||
master = {
|
||||
new_status = "master",
|
||||
},
|
||||
})
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Layouts/Scrolling-Layout/ for more
|
||||
hl.config({
|
||||
scrolling = {
|
||||
fullscreen_on_one_column = true,
|
||||
},
|
||||
})
|
||||
|
||||
----------------
|
||||
---- MISC ----
|
||||
----------------
|
||||
|
||||
hl.config({
|
||||
misc = {
|
||||
force_default_wallpaper = -1, -- Set to 0 or 1 to disable the anime mascot wallpapers
|
||||
disable_hyprland_logo = false, -- If true disables the random hyprland logo / anime girl background. :(
|
||||
},
|
||||
})
|
||||
|
||||
|
||||
---------------
|
||||
---- INPUT ----
|
||||
---------------
|
||||
|
||||
hl.config({
|
||||
input = {
|
||||
kb_layout = "__KB_LAYOUT__", -- MARQUEUR REMPLACÉ PAR LE SCRIPT BASH
|
||||
kb_variant = "",
|
||||
kb_model = "",
|
||||
kb_options = "",
|
||||
kb_rules = "",
|
||||
|
||||
follow_mouse = 1,
|
||||
|
||||
sensitivity = 0, -- -1.0 - 1.0, 0 means no modification.
|
||||
|
||||
touchpad = {
|
||||
natural_scroll = false,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
hl.gesture({
|
||||
fingers = 3,
|
||||
direction = "horizontal",
|
||||
action = "workspace"
|
||||
})
|
||||
|
||||
-- Example per-device config
|
||||
-- See https://wiki.hypr.land/Configuring/Advanced-and-Cool/Devices/ for more
|
||||
hl.device({
|
||||
name = "epic-mouse-v1",
|
||||
sensitivity = -0.5,
|
||||
})
|
||||
|
||||
|
||||
---------------------
|
||||
---- KEYBINDINGS ----
|
||||
---------------------
|
||||
|
||||
local mainMod = "SUPER" -- Sets "Windows" key as main modifier
|
||||
|
||||
-- Example binds, see https://wiki.hypr.land/Configuring/Basics/Binds/ for more
|
||||
hl.bind(mainMod .. " + Return", hl.dsp.exec_cmd(terminal))
|
||||
local closeWindowBind = hl.bind(mainMod .. " + W", hl.dsp.window.close())
|
||||
-- closeWindowBind:set_enabled(false)
|
||||
hl.bind(mainMod .. " + M", hl.dsp.exec_cmd("command -v hyprshutdown >/dev/null 2>&1 && hyprshutdown || hyprctl dispatch exit"))
|
||||
hl.bind(mainMod .. " + F", hl.dsp.exec_cmd(fileManager))
|
||||
hl.bind(mainMod .. " + T", hl.dsp.window.float({ action = "toggle" }))
|
||||
hl.bind(mainMod .. " + SPACE", hl.dsp.exec_cmd(menu))
|
||||
hl.bind(mainMod .. " + P", hl.dsp.window.pseudo())
|
||||
hl.bind(mainMod .. " + J", hl.dsp.layout("togglesplit")) -- dwindle only
|
||||
|
||||
-- Move focus with mainMod + arrow keys
|
||||
hl.bind(mainMod .. " + left", hl.dsp.focus({ direction = "left" }))
|
||||
hl.bind(mainMod .. " + right", hl.dsp.focus({ direction = "right" }))
|
||||
hl.bind(mainMod .. " + up", hl.dsp.focus({ direction = "up" }))
|
||||
hl.bind(mainMod .. " + down", hl.dsp.focus({ direction = "down" }))
|
||||
|
||||
-- Switch workspaces with mainMod + [0-9]
|
||||
-- Move active window to a workspace with mainMod + SHIFT + [0-9]
|
||||
-- CORRECTION : Utilisation des keycodes (code:10 à code:19) pour que ça marche sur AZERTY/QWERTY
|
||||
for i = 1, 10 do
|
||||
local keycode = 9 + i -- 10=1, 11=2, 12=3 ... 18=9, 19=0
|
||||
local key_str = "code:" .. keycode
|
||||
|
||||
hl.bind(mainMod .. " + " .. key_str, hl.dsp.exec_cmd("hyprctl dispatch workspace " .. i))
|
||||
hl.bind(mainMod .. " + SHIFT + " .. key_str, hl.dsp.exec_cmd("hyprctl dispatch movetoworkspace " .. i))
|
||||
end
|
||||
|
||||
-- Example special workspace (scratchpad)
|
||||
hl.bind(mainMod .. " + S", hl.dsp.workspace.toggle_special("magic"))
|
||||
hl.bind(mainMod .. " + SHIFT + S", hl.dsp.window.move({ workspace = "special:magic" }))
|
||||
|
||||
-- Scroll through existing workspaces with mainMod + scroll
|
||||
hl.bind(mainMod .. " + mouse_down", hl.dsp.focus({ workspace = "e+1" }))
|
||||
hl.bind(mainMod .. " + mouse_up", hl.dsp.focus({ workspace = "e-1" }))
|
||||
|
||||
-- Move/resize windows with mainMod + LMB/RMB and dragging
|
||||
hl.bind(mainMod .. " + mouse:272", hl.dsp.window.drag(), { mouse = true })
|
||||
hl.bind(mainMod .. " + mouse:273", hl.dsp.window.resize(), { mouse = true })
|
||||
|
||||
-- Laptop multimedia keys for volume and LCD brightness
|
||||
hl.bind("XF86AudioRaiseVolume", hl.dsp.exec_cmd("wpctl set-volume -l 1 @DEFAULT_AUDIO_SINK@ 5%+"), { locked = true, repeating = true })
|
||||
hl.bind("XF86AudioLowerVolume", hl.dsp.exec_cmd("wpctl set-volume @DEFAULT_AUDIO_SINK@ 5%-"), { locked = true, repeating = true })
|
||||
hl.bind("XF86AudioMute", hl.dsp.exec_cmd("wpctl set-mute @DEFAULT_AUDIO_SINK@ toggle"), { locked = true, repeating = true })
|
||||
hl.bind("XF86AudioMicMute", hl.dsp.exec_cmd("wpctl set-mute @DEFAULT_AUDIO_SOURCE@ toggle"), { locked = true, repeating = true })
|
||||
hl.bind("XF86MonBrightnessUp", hl.dsp.exec_cmd("brightnessctl -e4 -n2 set 5%+"), { locked = true, repeating = true })
|
||||
hl.bind("XF86MonBrightnessDown",hl.dsp.exec_cmd("brightnessctl -e4 -n2 set 5%-"), { locked = true, repeating = true })
|
||||
|
||||
-- Requires playerctl
|
||||
hl.bind("XF86AudioNext", hl.dsp.exec_cmd("playerctl next"), { locked = true })
|
||||
hl.bind("XF86AudioPause", hl.dsp.exec_cmd("playerctl play-pause"), { locked = true })
|
||||
hl.bind("XF86AudioPlay", hl.dsp.exec_cmd("playerctl play-pause"), { locked = true })
|
||||
hl.bind("XF86AudioPrev", hl.dsp.exec_cmd("playerctl previous"), { locked = true })
|
||||
|
||||
|
||||
--------------------------------
|
||||
---- WINDOWS AND WORKSPACES ----
|
||||
--------------------------------
|
||||
|
||||
-- See https://wiki.hypr.land/Configuring/Basics/Window-Rules/
|
||||
-- and https://wiki.hypr.land/Configuring/Basics/Workspace-Rules/
|
||||
|
||||
-- Example window rules that are useful
|
||||
|
||||
local suppressMaximizeRule = hl.window_rule({
|
||||
-- Ignore maximize requests from all apps. You'll probably like this.
|
||||
name = "suppress-maximize-events",
|
||||
match = { class = ".*" },
|
||||
|
||||
suppress_event = "maximize",
|
||||
})
|
||||
-- suppressMaximizeRule:set_enabled(false)
|
||||
|
||||
hl.window_rule({
|
||||
-- Fix some dragging issues with XWayland
|
||||
name = "fix-xwayland-drags",
|
||||
match = {
|
||||
class = "^$",
|
||||
title = "^$",
|
||||
xwayland = true,
|
||||
float = true,
|
||||
fullscreen = false,
|
||||
pin = false,
|
||||
},
|
||||
|
||||
no_focus = true,
|
||||
})
|
||||
|
||||
-- Layer rules also return a handle.
|
||||
-- local overlayLayerRule = hl.layer_rule({
|
||||
-- name = "no-anim-overlay",
|
||||
-- match = { namespace = "^my-overlay$" },
|
||||
-- no_anim = true,
|
||||
-- })
|
||||
-- overlayLayerRule:set_enabled(false)
|
||||
|
||||
-- Hyprland-run windowrule
|
||||
hl.window_rule({
|
||||
name = "move-hyprland-run",
|
||||
match = { class = "hyprland-run" },
|
||||
|
||||
move = "20 monitor_h-120",
|
||||
float = true,
|
||||
})
|
||||
@@ -0,0 +1,99 @@
|
||||
/* Theme for Obsidian */
|
||||
|
||||
.theme-dark, .theme-light {
|
||||
/* Core colors */
|
||||
--background-primary: #1e1e2e;
|
||||
--background-primary-alt: #1e1e2e;
|
||||
--background-secondary: #1e1e2e;
|
||||
--background-secondary-alt: #1e1e2e;
|
||||
--text-normal: #cdd6f4;
|
||||
|
||||
/* Selection colors */
|
||||
--text-selection: #292b3b;
|
||||
|
||||
/* Border color */
|
||||
--background-modifier-border: #585b70;
|
||||
|
||||
/* Semantic heading colors */
|
||||
--text-title-h1: #f38ba8;
|
||||
--text-title-h2: #a6e3a1;
|
||||
--text-title-h3: #f9e2af;
|
||||
--text-title-h4: #89b4fa;
|
||||
--text-title-h5: #cba6f7;
|
||||
--text-title-h6: #cba6f7;
|
||||
|
||||
/* Links and accents */
|
||||
--text-link: #89b4fa;
|
||||
--text-accent: #89b4fa;
|
||||
--text-accent-hover: #89b4fa;
|
||||
--interactive-accent: #89b4fa;
|
||||
--interactive-accent-hover: #89b4fa;
|
||||
|
||||
/* Muted text */
|
||||
--text-muted: color-mix(in srgb, #cdd6f4 70%, transparent);
|
||||
--text-faint: color-mix(in srgb, #cdd6f4 55%, transparent);
|
||||
|
||||
/* Code */
|
||||
--code-normal: #94e2d5;
|
||||
|
||||
/* Errors and success */
|
||||
--text-error: #f38ba8;
|
||||
--text-error-hover: #f38ba8;
|
||||
--text-success: #a6e3a1;
|
||||
|
||||
/* Tags */
|
||||
--tag-color: #94e2d5;
|
||||
--tag-background: #585b70;
|
||||
|
||||
/* Graph */
|
||||
--graph-line: #585b70;
|
||||
--graph-node: #89b4fa;
|
||||
--graph-node-focused: #89b4fa;
|
||||
--graph-node-tag: #94e2d5;
|
||||
--graph-node-attachment: #a6e3a1;
|
||||
}
|
||||
|
||||
/* Headers */
|
||||
.cm-header-1, .markdown-rendered h1 { color: var(--text-title-h1); }
|
||||
.cm-header-2, .markdown-rendered h2 { color: var(--text-title-h2); }
|
||||
.cm-header-3, .markdown-rendered h3 { color: var(--text-title-h3); }
|
||||
.cm-header-4, .markdown-rendered h4 { color: var(--text-title-h4); }
|
||||
.cm-header-5, .markdown-rendered h5 { color: var(--text-title-h5); }
|
||||
.cm-header-6, .markdown-rendered h6 { color: var(--text-title-h6); }
|
||||
|
||||
/* Code blocks */
|
||||
.markdown-rendered code {
|
||||
color: #94e2d5;
|
||||
}
|
||||
|
||||
/* Syntax highlighting */
|
||||
.cm-s-obsidian span.cm-keyword { color: #f38ba8; }
|
||||
.cm-s-obsidian span.cm-string { color: #a6e3a1; }
|
||||
.cm-s-obsidian span.cm-number { color: #f9e2af; }
|
||||
.cm-s-obsidian span.cm-comment { color: #585b70; }
|
||||
.cm-s-obsidian span.cm-operator { color: #89b4fa; }
|
||||
.cm-s-obsidian span.cm-def { color: #89b4fa; }
|
||||
|
||||
/* Links */
|
||||
.markdown-rendered a {
|
||||
color: var(--text-link);
|
||||
}
|
||||
|
||||
/* Blockquotes */
|
||||
.markdown-rendered blockquote {
|
||||
border-left-color: #89b4fa;
|
||||
}
|
||||
|
||||
/* Active elements */
|
||||
.workspace-leaf.mod-active .workspace-leaf-header-title {
|
||||
color: var(--interactive-accent);
|
||||
}
|
||||
|
||||
.nav-file-title.is-active {
|
||||
color: var(--interactive-accent);
|
||||
}
|
||||
|
||||
/* Search results */
|
||||
.search-result-file-title {
|
||||
color: var(--interactive-accent);
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
# Obsidian reads this file through the Arch package wrapper.
|
||||
-disable-gpu
|
||||
--enable-wayland-ime
|
||||
@@ -0,0 +1,38 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
print_status() {
|
||||
time=$(date +"%H:%M")
|
||||
date=$(date +"%d/%m")
|
||||
|
||||
# tooltip complet
|
||||
full_date=$(date +"%A %d %B %Y %H:%M:%S")
|
||||
calendar=$(cal -m)
|
||||
esc_calendar=$(sed 's/&/&/g; s/</</g; s/>/>/g' <<< "$calendar")
|
||||
|
||||
text="$time
|
||||
$date"
|
||||
|
||||
tooltip="$full_date
|
||||
|
||||
$esc_calendar"
|
||||
|
||||
jq -nc \
|
||||
--arg text "$text" \
|
||||
--arg tooltip "$tooltip" \
|
||||
'{ text: $text, tooltip: $tooltip }'
|
||||
}
|
||||
|
||||
print_status
|
||||
|
||||
last=""
|
||||
|
||||
while true; do
|
||||
current=$(date +"%H%M%S%Y%m%d")
|
||||
|
||||
if [[ "$current" != "$last" ]]; then
|
||||
print_status
|
||||
last="$current"
|
||||
fi
|
||||
|
||||
sleep 1
|
||||
done
|
||||
@@ -0,0 +1,139 @@
|
||||
{
|
||||
"reload_style_on_change": true,
|
||||
"layer": "top",
|
||||
"position": "left",
|
||||
"spacing": 0,
|
||||
"width": 35,
|
||||
"modules-left": ["custom/clock", "cpu", "memory", "custom/media"],
|
||||
"modules-center": ["hyprland/workspaces"],
|
||||
"modules-right": ["group/tray-expander", "pulseaudio", "bluetooth", "network", "battery"],
|
||||
"hyprland/workspaces": {
|
||||
"on-click": "activate",
|
||||
"format": "{icon}",
|
||||
"format-icons": {
|
||||
"default": "",
|
||||
"1": "1",
|
||||
"2": "2",
|
||||
"3": "3",
|
||||
"4": "4",
|
||||
"5": "5",
|
||||
"6": "6",
|
||||
"7": "7",
|
||||
"8": "8",
|
||||
"9": "9",
|
||||
"10": "0",
|
||||
"active": ""
|
||||
},
|
||||
"persistent-workspaces": {
|
||||
"1": [],
|
||||
"2": [],
|
||||
"3": [],
|
||||
"4": [],
|
||||
"5": [],
|
||||
"6": [],
|
||||
"7": [],
|
||||
"8": [],
|
||||
"9": [],
|
||||
"10": []
|
||||
}
|
||||
},
|
||||
"cpu": {
|
||||
"interval": 2,
|
||||
"format": "{icon} ",
|
||||
"format-icons": ["", "", "", "", "", "", "", ""],
|
||||
"on-click": "btop"
|
||||
},
|
||||
"memory": {
|
||||
"interval": 2,
|
||||
"format": "{icon} ",
|
||||
"format-icons": ["", "", "", "", "", "", "", ""],
|
||||
"on-click": "btop"
|
||||
},
|
||||
"custom/clock": {
|
||||
"exec": "~/.config/waybar/clock.sh",
|
||||
"return-type": "json",
|
||||
"tooltip": true
|
||||
},
|
||||
"custom/media": {
|
||||
"exec": "~/.config/waybar/media.sh",
|
||||
"return-type": "json",
|
||||
"interval": 1,
|
||||
"on-click": "~/.config/waybar/media_click.sh",
|
||||
"on-click-right": "playerctl -p subtui next",
|
||||
"on-click-middle": "playerctl -p subtui previous",
|
||||
"tooltip": true
|
||||
},
|
||||
"network": {
|
||||
"format-icons": ["", "", "", "", ""],
|
||||
"format": "{icon}",
|
||||
"format-wifi": "{icon}",
|
||||
"format-ethernet": "",
|
||||
"format-disconnected": "",
|
||||
"tooltip-format-wifi": "{essid} ({frequency} GHz)",
|
||||
"tooltip-format-ethernet": "Connected",
|
||||
"tooltip-format-disconnected": "Disconnected",
|
||||
"interval": 3,
|
||||
"spacing": 1,
|
||||
"on-click": "impala"
|
||||
},
|
||||
"battery": {
|
||||
"format": "{capacity}% {icon}",
|
||||
"format-discharging": "{icon}",
|
||||
"format-charging": "{icon}",
|
||||
"format-plugged": "",
|
||||
"format-icons": {
|
||||
"charging": ["", "", "", "", "", "", "", "", "", ""],
|
||||
"default": ["", "", "", "", "", "", "", "", "", ""]
|
||||
},
|
||||
"format-full": "",
|
||||
"tooltip-format-discharging": "{power:>1.0f}W↓ {capacity}%",
|
||||
"tooltip-format-charging": "{power:>1.0f}W↑ {capacity}%",
|
||||
"interval": 5,
|
||||
"states": {
|
||||
"warning": 20,
|
||||
"critical": 10
|
||||
}
|
||||
},
|
||||
"bluetooth": {
|
||||
"format": "",
|
||||
"format-off": "",
|
||||
"format-disabled": "",
|
||||
"format-connected": "",
|
||||
"format-no-controller": "",
|
||||
"tooltip-format": "Devices connected: {num_connections}",
|
||||
"on-click": "bluetui"
|
||||
},
|
||||
"pulseaudio": {
|
||||
"format": "{icon}",
|
||||
"on-click": "wiremix",
|
||||
"on-click-right": "pamixer -t",
|
||||
"tooltip-format": "Playing at {volume}%",
|
||||
"scroll-step": 5,
|
||||
"format-muted": "",
|
||||
"format-icons": {
|
||||
"headphone": "",
|
||||
"headset": "",
|
||||
"default": ["", "", ""]
|
||||
}
|
||||
},
|
||||
"group/tray-expander": {
|
||||
"orientation": "inherit",
|
||||
"drawer": {
|
||||
"transition-duration": 600,
|
||||
"children-class": "tray-group-item"
|
||||
},
|
||||
"modules": ["custom/expand-icon", "tray"]
|
||||
},
|
||||
"custom/expand-icon": {
|
||||
"format": "",
|
||||
"tooltip": false,
|
||||
"on-scroll-up": "",
|
||||
"on-scroll-down": "",
|
||||
"on-scroll-left": "",
|
||||
"on-scroll-right": ""
|
||||
},
|
||||
"tray": {
|
||||
"icon-size": 12,
|
||||
"spacing": 17
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
#!/bin/bash
|
||||
|
||||
PLAYER="subtui"
|
||||
|
||||
# Vérifie si Subtui est lancé
|
||||
if ! playerctl -l 2>/dev/null | grep -q "^${PLAYER}$"; then
|
||||
echo '{"text":"","tooltip":"Subtui non lancé"}'
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Métadonnées
|
||||
title=$(playerctl -p "$PLAYER" metadata title 2>/dev/null)
|
||||
artist=$(playerctl -p "$PLAYER" metadata artist 2>/dev/null)
|
||||
album=$(playerctl -p "$PLAYER" metadata album 2>/dev/null)
|
||||
status=$(playerctl -p "$PLAYER" status 2>/dev/null)
|
||||
|
||||
# Valeurs par défaut
|
||||
[ -z "$title" ] && title="Titre inconnu"
|
||||
[ -z "$artist" ] && artist="Artiste inconnu"
|
||||
[ -z "$album" ] && album="Album inconnu"
|
||||
|
||||
# Position actuelle (secondes)
|
||||
position=$(playerctl -p "$PLAYER" position 2>/dev/null)
|
||||
[ -z "$position" ] && position=0
|
||||
|
||||
# Durée totale (microsecondes)
|
||||
length=$(playerctl -p "$PLAYER" metadata mpris:length 2>/dev/null)
|
||||
[ -z "$length" ] && length=0
|
||||
|
||||
# Conversion sûre
|
||||
position_sec=$(awk -v p="$position" 'BEGIN { printf("%d", p+0.5) }')
|
||||
length_sec=$((length / 1000000))
|
||||
|
||||
# Format temps
|
||||
elapsed=$(printf "%02d:%02d" $((position_sec/60)) $((position_sec%60)))
|
||||
|
||||
if [ "$length_sec" -gt 0 ]; then
|
||||
duration=$(printf "%02d:%02d" $((length_sec/60)) $((length_sec%60)))
|
||||
else
|
||||
duration="--:--"
|
||||
fi
|
||||
|
||||
# Icône
|
||||
if [ "$status" = "Playing" ]; then
|
||||
icon=""
|
||||
else
|
||||
icon=""
|
||||
fi
|
||||
|
||||
# Échapper les guillemets pour JSON
|
||||
title=${title//\"/\\\"}
|
||||
artist=${artist//\"/\\\"}
|
||||
album=${album//\"/\\\"}
|
||||
|
||||
# Tooltip
|
||||
tooltip="$artist
|
||||
$title
|
||||
|
||||
Album : $album
|
||||
|
||||
$elapsed / $duration
|
||||
|
||||
Clic gauche : Lecture/Pause
|
||||
Clic droit : Suivant
|
||||
Clic milieu : Précédent"
|
||||
|
||||
# Convertir les retours à la ligne pour JSON
|
||||
tooltip=$(echo "$tooltip" | sed ':a;N;$!ba;s/\n/\\n/g')
|
||||
|
||||
# JSON final
|
||||
printf '{"text":"%s","tooltip":"%s"}\n' "$icon" "$tooltip"
|
||||
@@ -0,0 +1,9 @@
|
||||
#!/bin/bash
|
||||
|
||||
PLAYER="subtui"
|
||||
|
||||
if playerctl -l 2>/dev/null | grep -q "^${PLAYER}$"; then
|
||||
playerctl -p "$PLAYER" play-pause
|
||||
else
|
||||
ghostty -e subtui &
|
||||
fi
|
||||
@@ -0,0 +1,109 @@
|
||||
* {
|
||||
background-color: black;
|
||||
color: white;
|
||||
border: none;
|
||||
border-radius: 0;
|
||||
min-height: 0;
|
||||
font-family: 'JetBrainsMono Nerd Font';
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.modules-left {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.modules-right {
|
||||
margin-top: 8px;
|
||||
}
|
||||
|
||||
#workspaces button {
|
||||
all: initial;
|
||||
padding: 6px 0;
|
||||
margin: 1.5px 0;
|
||||
min-height: 9px;
|
||||
}
|
||||
|
||||
#workspaces button.empty {
|
||||
opacity: 0.5;
|
||||
}
|
||||
|
||||
#cpu,
|
||||
#memory,
|
||||
#custom-media,
|
||||
#battery,
|
||||
#pulseaudio,
|
||||
#custom-update {
|
||||
min-height: 12px;
|
||||
margin: 7.5px 0;
|
||||
}
|
||||
|
||||
#tray {
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
#bluetooth {
|
||||
margin-top: 17px;
|
||||
}
|
||||
|
||||
#network {
|
||||
margin-top: 13px;
|
||||
}
|
||||
|
||||
#custom-expand-icon {
|
||||
margin-top: 18px;
|
||||
}
|
||||
|
||||
tooltip {
|
||||
padding: 2px;
|
||||
}
|
||||
|
||||
#custom-update {
|
||||
font-size: 10px;
|
||||
}
|
||||
|
||||
#custom-clock {
|
||||
margin-bottom: 8.75px;
|
||||
}
|
||||
|
||||
#custom-weather {
|
||||
margin-bottom: 7.5px;
|
||||
margin-top: 7.5px;
|
||||
}
|
||||
|
||||
#custom-weather.unavailable {
|
||||
min-height: 0;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.hidden {
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
#custom-screenrecording-indicator,
|
||||
#custom-idle-indicator,
|
||||
#custom-notification-silencing-indicator {
|
||||
min-height: 12px;
|
||||
margin-bottom: 5px;
|
||||
margin-top: 0;
|
||||
font-size: 10px;
|
||||
padding-right: 1px;
|
||||
}
|
||||
|
||||
#custom-screenrecording-indicator.active {
|
||||
color: #a55555;
|
||||
}
|
||||
|
||||
#custom-idle-indicator.active,
|
||||
#custom-notification-silencing-indicator.active {
|
||||
color: #a55555;
|
||||
}
|
||||
|
||||
#custom-voxtype {
|
||||
min-height: 12px;
|
||||
margin: 0 0 7.5px 0;
|
||||
}
|
||||
|
||||
#custom-voxtype.recording {
|
||||
color: #a55555;
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
# overwrites default wiremix configuration
|
||||
# defaults: https://github.com/tsowell/wiremix/blob/main/wiremix.toml
|
||||
|
||||
[char_sets.default]
|
||||
default_device = "⮞"
|
||||
+480
-107
@@ -1,144 +1,517 @@
|
||||
#!/bin/bash
|
||||
set -e
|
||||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
clear
|
||||
echo "========================"
|
||||
echo " Arch Custom Installer"
|
||||
echo "========================"
|
||||
# ==========================================
|
||||
# UI SYSTEM
|
||||
# ==========================================
|
||||
declare -A GRID_DATA
|
||||
GRID_NUM_PAGES=0
|
||||
|
||||
# =========================
|
||||
# 1. KEYBOARD
|
||||
# =========================
|
||||
echo "Clavier (fr / us / uk / de / es) :"
|
||||
read -r KEYMAP
|
||||
loadkeys "$KEYMAP"
|
||||
grid_menu() {
|
||||
local -n items=$1
|
||||
local page=$2
|
||||
local max_cols=$3
|
||||
local max_rows=$4
|
||||
local data_page=0
|
||||
local item_number=0
|
||||
local max_cols_data
|
||||
local line
|
||||
|
||||
# =========================
|
||||
# 2. NETWORK (AUTO + WIFI MANUEL)
|
||||
# =========================
|
||||
if ! ping -c 1 archlinux.org &>/dev/null; then
|
||||
echo "Pas d'internet détecté."
|
||||
GRID_DATA=()
|
||||
GRID_NUM_PAGES=0
|
||||
|
||||
iwctl device list
|
||||
echo "Device Wi-Fi (ex: wlan0) :"
|
||||
read -r DEVICE
|
||||
while (( item_number < ${#items[@]} )); do
|
||||
max_cols_data=1
|
||||
for (( line=0; line<max_rows; line++ )); do
|
||||
if (( item_number >= ${#items[@]} )); then break; fi
|
||||
local key="P${data_page}L${line}"
|
||||
if [[ ! -v GRID_DATA[$key] ]]; then GRID_DATA[$key]=""; fi
|
||||
|
||||
iwctl station "$DEVICE" scan
|
||||
sleep 3
|
||||
local index=$(( item_number + max_rows - line ))
|
||||
if (( index >= ${#items[@]} )); then index=$(( ${#items[@]} - 1 ))
|
||||
elif (( index < 0 )); then index=$(( ${#items[@]} + index ))
|
||||
(( index < 0 )) && index=0
|
||||
fi
|
||||
|
||||
iwctl station "$DEVICE" get-networks
|
||||
local index_str; printf -v index_str "%d" "$index"
|
||||
local item_num_plus1=$(( item_number + 1 ))
|
||||
local item_num_str; printf -v item_num_str "%d" "$item_num_plus1"
|
||||
local spaces_needed=$(( ${#index_str} - ${#item_num_str} ))
|
||||
if (( spaces_needed < 0 )); then spaces_needed=0; fi
|
||||
local spaces; printf -v spaces "%*s" "$spaces_needed" ""
|
||||
local item="${items[$item_number]}"
|
||||
local add="${spaces}${item_num_plus1}) ${item}"
|
||||
|
||||
echo "SSID :"
|
||||
read -r SSID
|
||||
local current_line="${GRID_DATA[$key]}"
|
||||
if (( ${#current_line} + ${#add} > max_cols )); then
|
||||
data_page=$(( data_page + 1 ))
|
||||
break
|
||||
fi
|
||||
GRID_DATA[$key]="${current_line}${add}"
|
||||
local len_item_plus2=$(( ${#item} + 2 ))
|
||||
max_cols_data=$(( max_cols_data > len_item_plus2 ? max_cols_data : len_item_plus2 ))
|
||||
item_number=$(( item_number + 1 ))
|
||||
done
|
||||
|
||||
echo "Password Wi-Fi :"
|
||||
read -rs PASS
|
||||
echo
|
||||
for (( line=0; line<max_rows; line++ )); do
|
||||
local key="P${data_page}L${line}"
|
||||
if [[ ! -v GRID_DATA[$key] ]]; then continue; fi
|
||||
local idx=$(( item_number - (max_rows - line) ))
|
||||
if (( idx < 0 )); then idx=$(( ${#items[@]} + idx ))
|
||||
(( idx < 0 )) && idx=0
|
||||
elif (( idx >= ${#items[@]} )); then idx=$(( ${#items[@]} - 1 ))
|
||||
fi
|
||||
local item="${items[$idx]}"
|
||||
local pad=$(( max_cols_data - ${#item} ))
|
||||
if (( pad < 0 )); then pad=0; fi
|
||||
local spaces_pad; printf -v spaces_pad "%*s" "$pad" ""
|
||||
GRID_DATA[$key]="${GRID_DATA[$key]}${spaces_pad}"
|
||||
done
|
||||
done
|
||||
GRID_NUM_PAGES=$(( data_page + 1 ))
|
||||
}
|
||||
|
||||
iwctl station "$DEVICE" connect "$SSID" --passphrase "$PASS"
|
||||
print_grid_menu() {
|
||||
local page=$1
|
||||
local found=0
|
||||
local key
|
||||
for key in "${!GRID_DATA[@]}"; do
|
||||
if [[ $key == P${page}L* ]]; then found=1; break; fi
|
||||
done
|
||||
if (( found == 0 )); then echo "Page $(( page + 1 )) does not exist."; return; fi
|
||||
|
||||
sleep 5
|
||||
fi
|
||||
echo ""
|
||||
echo "Page $(( page + 1 )) of $GRID_NUM_PAGES"
|
||||
echo ""
|
||||
for key in $(printf "%s\n" "${!GRID_DATA[@]}" | grep "^P${page}L" | sort -t 'L' -k2 -n); do
|
||||
echo "${GRID_DATA[$key]}"
|
||||
done
|
||||
}
|
||||
|
||||
# =========================
|
||||
# 3. TIMEZONE
|
||||
# =========================
|
||||
echo "Fuseau horaire (ex: Europe/Paris) :"
|
||||
read -r TIMEZONE
|
||||
json_escape() {
|
||||
local s="$1"
|
||||
s="${s//\\/\\\\}"
|
||||
s="${s//\"/\\\"}"
|
||||
s="${s//$'\n'/\\n}"
|
||||
s="${s//$'\r'/\\r}"
|
||||
s="${s//$'\t'/\\t}"
|
||||
printf '%s' "$s"
|
||||
}
|
||||
|
||||
# =========================
|
||||
# 4. LOCALE
|
||||
# =========================
|
||||
echo "Langue système (fr_FR.UTF-8 / en_US.UTF-8 / etc) :"
|
||||
read -r LOCALE
|
||||
# ==========================================
|
||||
# SYSTEM LOGIC
|
||||
# ==========================================
|
||||
|
||||
# =========================
|
||||
# 5. USER
|
||||
# =========================
|
||||
DEFAULT_USER="user"
|
||||
echo "Nom utilisateur [$DEFAULT_USER] :"
|
||||
read -r USERNAME
|
||||
USERNAME=${USERNAME:-$DEFAULT_USER}
|
||||
cleanup_install_disk() {
|
||||
local disk="$1"
|
||||
[[ -z "$disk" || ! -b "$disk" ]] && return 1
|
||||
echo "Cleaning up disk: $disk"
|
||||
findmnt -R /mnt >/dev/null && umount -R /mnt || true
|
||||
while read -r dev; do
|
||||
[[ -b "$dev" ]] || continue
|
||||
swapoff "$dev" 2>/dev/null || true
|
||||
while read -r target; do [[ -n "$target" ]] && umount "$target" 2>/dev/null; done < <(findmnt -rn -S "$dev" -o TARGET 2>/dev/null)
|
||||
done < <(lsblk -rnpo PATH "$disk" 2>/dev/null)
|
||||
while read -r dev type; do
|
||||
[[ "$type" == "disk" || "$type" == "part" || "$type" == "crypt" ]] || continue
|
||||
while read -r vg; do [[ -n "$vg" ]] && vgchange -an "$vg" 2>/dev/null; done < <(pvs --noheadings -o vg_name "$dev" 2>/dev/null | awk '{$1=$1; print}' | sort -u)
|
||||
done < <(lsblk -rnpo PATH,TYPE "$disk" 2>/dev/null)
|
||||
while read -r dev type; do [[ "$type" == "crypt" ]] && cryptsetup close "$dev" 2>/dev/null; done < <(lsblk -rnpo PATH,TYPE "$disk" 2>/dev/null)
|
||||
blockdev --flushbufs "$disk" 2>/dev/null || true
|
||||
partprobe "$disk" 2>/dev/null || true
|
||||
udevadm settle 2>/dev/null || true
|
||||
}
|
||||
|
||||
echo "Mot de passe utilisateur :"
|
||||
read -rs USERPASS
|
||||
echo
|
||||
install_base_system() {
|
||||
pacman-key --init
|
||||
pacman-key --populate archlinux
|
||||
pacman -Sy --noconfirm
|
||||
|
||||
# =========================
|
||||
# 6. HOSTNAME
|
||||
# =========================
|
||||
DEFAULT_HOST="archbox"
|
||||
echo "Hostname [$DEFAULT_HOST] :"
|
||||
read -r HOSTNAME
|
||||
HOSTNAME=${HOSTNAME:-$DEFAULT_HOST}
|
||||
local disk
|
||||
disk=$(grep -o '"device": *"[^"]*"' user_configuration.json | head -1 | cut -d'"' -f4)
|
||||
cleanup_install_disk "$disk"
|
||||
|
||||
# =========================
|
||||
# 7. DISK
|
||||
# =========================
|
||||
lsblk -dpno NAME,SIZE,MODEL
|
||||
archinstall --config user_configuration.json --creds user_credentials.json --silent --skip-ntp --skip-wkd --skip-wifi-check
|
||||
|
||||
echo "Disque (ex: /dev/sda ou /dev/nvme0n1) :"
|
||||
read -r DISK
|
||||
mkdir -p /mnt/etc/sudoers.d
|
||||
echo "%wheel ALL=(ALL:ALL) NOPASSWD: ALL" > /mnt/etc/sudoers.d/99-installer
|
||||
chmod 440 /mnt/etc/sudoers.d/99-installer
|
||||
}
|
||||
|
||||
echo "⚠️ TOUT SERA EFFACÉ SUR $DISK"
|
||||
echo "Taper YES pour confirmer :"
|
||||
read -r CONFIRM
|
||||
[[ "$CONFIRM" != "YES" ]] && exit 1
|
||||
# ==========================================
|
||||
# CONFIGURATOR
|
||||
# ==========================================
|
||||
|
||||
# =========================
|
||||
# 8. PARTITIONING
|
||||
# =========================
|
||||
sgdisk --zap-all "$DISK"
|
||||
run_configurator() {
|
||||
# --- 1. KEYBOARD ---
|
||||
KB_LAYOUT=("us" "fr" "de" "uk" "es" "it" "pt-latin1" "br-abnt2" "dvorak" "colemak" "ru" "jp106")
|
||||
PAGE=1
|
||||
COLS=$(( $(tput cols) - 10 ))
|
||||
ROWS=$(( $(tput lines) - 10 ))
|
||||
|
||||
sgdisk -n 1:0:+512M -t 1:ef00 -c 1:"EFI" "$DISK"
|
||||
sgdisk -n 2:0:0 -t 2:8300 -c 2:"ROOT" "$DISK"
|
||||
grid_menu KB_LAYOUT "$PAGE" "$COLS" "$ROWS"
|
||||
|
||||
EFI="${DISK}1"
|
||||
ROOT="${DISK}2"
|
||||
while true; do
|
||||
clear
|
||||
echo "=== SELECT KEYBOARD LAYOUT ==="
|
||||
print_grid_menu $(( PAGE - 1 ))
|
||||
echo -e "\n[n] Next | [p] Prev | [q] Quit"
|
||||
read -rp "Entrée (n/p ou nombre) : " input
|
||||
|
||||
mkfs.fat -F32 "$EFI"
|
||||
mkfs.ext4 -F "$ROOT"
|
||||
if [[ "$input" == "q" ]]; then exit 1; fi
|
||||
if [[ "$input" =~ ^[0-9]+$ ]]; then
|
||||
PAGE="$input"
|
||||
break
|
||||
elif [[ "$input" == "n" ]]; then
|
||||
if (( PAGE < GRID_NUM_PAGES )); then PAGE=$(( PAGE + 1 )); fi
|
||||
elif [[ "$input" == "p" ]]; then
|
||||
if (( PAGE > 1 )); then PAGE=$(( PAGE - 1 )); fi
|
||||
fi
|
||||
done
|
||||
keyboard="${KB_LAYOUT[$((PAGE - 1))]}"
|
||||
[[ $(tty 2>/dev/null) == "/dev/tty"* ]] && loadkeys "$keyboard" 2>/dev/null || true
|
||||
|
||||
mount "$ROOT" /mnt
|
||||
mount --mkdir "$EFI" /mnt/boot
|
||||
# --- 2. USER ---
|
||||
while true; do
|
||||
clear; read -rp "Username: " username
|
||||
[[ "$username" =~ ^[a-z_][a-z0-9_-]*[$]?$ ]] && break
|
||||
done
|
||||
while true; do
|
||||
clear; read -rsp "Password: " password; echo
|
||||
read -rsp "Confirm: " password_confirmation; echo
|
||||
[[ -n "$password" && "$password" == "$password_confirmation" ]] && break
|
||||
done
|
||||
password_hash=$(printf '%s' "$password" | openssl passwd -6 -stdin)
|
||||
clear; read -rp "Hostname [archlinux]: " hostname
|
||||
[[ -z "$hostname" ]] && hostname="archlinux"
|
||||
|
||||
# =========================
|
||||
# 9. BASE INSTALL
|
||||
# =========================
|
||||
pacstrap -K /mnt \
|
||||
base linux linux-firmware \
|
||||
sudo networkmanager iwd
|
||||
# --- 3. TIMEZONE ---
|
||||
clear; echo "Loading timezones..."
|
||||
mapfile -t TIMEZONES < <(timedatectl list-timezones)
|
||||
PAGE=1
|
||||
COLS=$(( $(tput cols) - 10 ))
|
||||
ROWS=$(( $(tput lines) - 10 ))
|
||||
|
||||
genfstab -U /mnt >> /mnt/etc/fstab
|
||||
grid_menu TIMEZONES "$PAGE" "$COLS" "$ROWS"
|
||||
|
||||
# =========================
|
||||
# 10. CHROOT
|
||||
# =========================
|
||||
arch-chroot /mnt /bin/bash <<EOF
|
||||
while true; do
|
||||
clear
|
||||
echo "=== SELECT TIMEZONE ==="
|
||||
print_grid_menu $(( PAGE - 1 ))
|
||||
echo -e "\n[n] Next | [p] Prev | [q] Quit"
|
||||
read -rp "Entrée (n/p ou nombre) : " input
|
||||
|
||||
set -e
|
||||
if [[ "$input" == "q" ]]; then exit 1; fi
|
||||
if [[ "$input" =~ ^[0-9]+$ ]]; then
|
||||
PAGE="$input"
|
||||
break
|
||||
elif [[ "$input" == "n" ]]; then
|
||||
if (( PAGE < GRID_NUM_PAGES )); then PAGE=$(( PAGE + 1 )); fi
|
||||
elif [[ "$input" == "p" ]]; then
|
||||
if (( PAGE > 1 )); then PAGE=$(( PAGE - 1 )); fi
|
||||
fi
|
||||
done
|
||||
timezone="${TIMEZONES[$((PAGE - 1))]}"
|
||||
|
||||
ln -sf "/usr/share/zoneinfo/$TIMEZONE" /etc/localtime
|
||||
hwclock --systohc
|
||||
# --- 4. DISK ---
|
||||
clear
|
||||
local boot_source exclude_disk
|
||||
boot_source=$(findmnt -no SOURCE /run/archiso/bootmnt 2>/dev/null || true)
|
||||
local device_b
|
||||
device_b=$(readlink -f "$boot_source" 2>/dev/null || echo "")
|
||||
while [[ -n "$device_b" ]]; do
|
||||
local parent_b
|
||||
parent_b=$(lsblk -dno PKNAME "$device_b" 2>/dev/null | tail -n1)
|
||||
[[ -z "$parent_b" ]] && break; device_b="/dev/$parent_b"
|
||||
done
|
||||
[[ $(lsblk -dno TYPE "$device_b" 2>/dev/null) == "disk" ]] && exclude_disk="$device_b"
|
||||
|
||||
echo "KEYMAP=$KEYMAP" > /etc/vconsole.conf
|
||||
DISKS=()
|
||||
mapfile -t available_disks < <(lsblk -dpno NAME,TYPE | awk '$2=="disk"{print $1}' | grep -E '/dev/(sd|hd|vd|nvme|mmcblk|xv)' | { [[ -n "${exclude_disk:-}" ]] && grep -Fvx "$exclude_disk" || cat; })
|
||||
for dev in "${available_disks[@]}"; do
|
||||
local size; size=$(lsblk -dno SIZE "$dev" 2>/dev/null) || true
|
||||
local model; model=$(lsblk -dno MODEL "$dev" 2>/dev/null | sed 's/ *$//') || true
|
||||
DISKS+=("$dev ($size) - $model")
|
||||
done
|
||||
|
||||
echo "$LOCALE UTF-8" >> /etc/locale.gen
|
||||
locale-gen
|
||||
echo "LANG=$LOCALE" > /etc/locale.conf
|
||||
PAGE=1
|
||||
COLS=$(( $(tput cols) - 10 ))
|
||||
ROWS=$(( $(tput lines) - 10 ))
|
||||
|
||||
echo "$HOSTNAME" > /etc/hostname
|
||||
grid_menu DISKS "$PAGE" "$COLS" "$ROWS"
|
||||
|
||||
useradd -m -G wheel -s /bin/bash "$USERNAME"
|
||||
echo "$USERNAME:$USERPASS" | chpasswd
|
||||
while true; do
|
||||
clear
|
||||
echo "=== SELECT INSTALLATION DISK ==="
|
||||
print_grid_menu $(( PAGE - 1 ))
|
||||
echo -e "\n[n] Next | [p] Prev | [q] Quit"
|
||||
read -rp "Entrée (n/p ou nombre) : " input
|
||||
|
||||
echo "%wheel ALL=(ALL:ALL) ALL" > /etc/sudoers.d/wheel
|
||||
if [[ "$input" == "q" ]]; then exit 1; fi
|
||||
if [[ "$input" =~ ^[0-9]+$ ]]; then
|
||||
PAGE="$input"
|
||||
break
|
||||
elif [[ "$input" == "n" ]]; then
|
||||
if (( PAGE < GRID_NUM_PAGES )); then PAGE=$(( PAGE + 1 )); fi
|
||||
elif [[ "$input" == "p" ]]; then
|
||||
if (( PAGE > 1 )); then PAGE=$(( PAGE - 1 )); fi
|
||||
fi
|
||||
done
|
||||
disk=$(echo "${DISKS[$((PAGE - 1))]}" | awk '{print $1}')
|
||||
|
||||
systemctl enable NetworkManager
|
||||
# --- 5. JSON GENERATION ---
|
||||
local pw_esc="\"$(json_escape "$password")\""
|
||||
local hash_esc="\"$(json_escape "$password_hash")\""
|
||||
local user_esc="\"$(json_escape "$username")\""
|
||||
local host_esc="\"$(json_escape "$hostname")\""
|
||||
local tz_esc="\"$(json_escape "$timezone")\""
|
||||
local kb_esc="\"$(json_escape "$keyboard")\""
|
||||
local disk_esc="\"$(json_escape "$disk")\""
|
||||
|
||||
credentials_encryption_line=" \"encryption_password\": $pw_esc,"
|
||||
|
||||
cat <<_EOF_ >user_credentials.json
|
||||
{
|
||||
$credentials_encryption_line
|
||||
"root_enc_password": $hash_esc,
|
||||
"users": [
|
||||
{
|
||||
"enc_password": $hash_esc,
|
||||
"groups": [],
|
||||
"sudo": true,
|
||||
"username": $user_esc
|
||||
}
|
||||
]
|
||||
}
|
||||
_EOF_
|
||||
|
||||
local disk_size; disk_size=$(lsblk -bdno SIZE "$disk" 2>/dev/null) || true
|
||||
local mib=$((1024*1024))
|
||||
local gib=$((mib*1024))
|
||||
local disk_size_in_mib=$((disk_size / mib * mib))
|
||||
local boot_size=$((2 * gib))
|
||||
local main_start=$((boot_size + mib))
|
||||
local main_size=$((disk_size_in_mib - main_start - mib))
|
||||
|
||||
disk_encryption_config=$(cat <<_EOF_
|
||||
,
|
||||
"disk_encryption": {
|
||||
"encryption_type": "luks",
|
||||
"lvm_volumes": [],
|
||||
"iter_time": 2000,
|
||||
"partitions": [ "8c2c2b92-1070-455d-b76a-56263bab24aa" ],
|
||||
"encryption_password": $pw_esc
|
||||
}
|
||||
_EOF_
|
||||
)
|
||||
|
||||
cat <<_EOF_ >user_configuration.json
|
||||
{
|
||||
"archinstall-language": "English",
|
||||
"audio_config": { "audio": "pipewire" },
|
||||
"bootloader": "grub",
|
||||
"disk_config": {
|
||||
"btrfs_options": { "snapshot_config": { "type": "Snapper" } },
|
||||
"config_type": "default_layout",
|
||||
"device_modifications": [
|
||||
{
|
||||
"device": $disk_esc,
|
||||
"partitions": [
|
||||
{
|
||||
"btrfs": [],
|
||||
"dev_path": null,
|
||||
"flags": [ "boot", "esp" ],
|
||||
"fs_type": "fat32",
|
||||
"mount_options": [],
|
||||
"mountpoint": "/boot",
|
||||
"obj_id": "ea21d3f2-82bb-49cc-ab5d-6f81ae94e18d",
|
||||
"size": {
|
||||
"sector_size": { "unit": "B", "value": 512 },
|
||||
"unit": "B",
|
||||
"value": $boot_size
|
||||
},
|
||||
"start": {
|
||||
"sector_size": { "unit": "B", "value": 512 },
|
||||
"unit": "B",
|
||||
"value": $mib
|
||||
},
|
||||
"status": "create",
|
||||
"type": "primary"
|
||||
},
|
||||
{
|
||||
"btrfs": [
|
||||
{ "mountpoint": "/", "name": "@" },
|
||||
{ "mountpoint": "/home", "name": "@home" },
|
||||
{ "mountpoint": "/var/log", "name": "@log" },
|
||||
{ "mountpoint": "/var/cache/pacman/pkg", "name": "@pkg" }
|
||||
],
|
||||
"dev_path": null,
|
||||
"flags": [],
|
||||
"fs_type": "btrfs",
|
||||
"mount_options": [ "compress=zstd" ],
|
||||
"mountpoint": null,
|
||||
"obj_id": "8c2c2b92-1070-455d-b76a-56263bab24aa",
|
||||
"size": {
|
||||
"sector_size": { "unit": "B", "value": 512 },
|
||||
"unit": "B",
|
||||
"value": $main_size
|
||||
},
|
||||
"start": {
|
||||
"sector_size": { "unit": "B", "value": 512 },
|
||||
"unit": "B",
|
||||
"value": $main_start
|
||||
},
|
||||
"status": "create",
|
||||
"type": "primary"
|
||||
}
|
||||
],
|
||||
"wipe": true
|
||||
}
|
||||
]$disk_encryption_config
|
||||
},
|
||||
"hostname": $host_esc,
|
||||
"kernels": [ "linux" ],
|
||||
"network_config": { "type": "iso" },
|
||||
"ntp": true,
|
||||
"parallel_downloads": 8,
|
||||
"swap": true,
|
||||
"timezone": $tz_esc,
|
||||
"locale_config": {
|
||||
"kb_layout": $kb_esc,
|
||||
"sys_enc": "UTF-8",
|
||||
"sys_lang": "fr_FR.UTF-8"
|
||||
},
|
||||
"mirror_config": {
|
||||
"custom_servers": [
|
||||
{"url": "https://geo.mirror.pkgbuild.com/\$repo/os/\$arch"},
|
||||
{"url": "https://mirror.rackspace.com/archlinux/\$repo/os/\$arch"}
|
||||
]
|
||||
},
|
||||
"packages": [
|
||||
"base-devel",
|
||||
"git",
|
||||
"snapper"
|
||||
],
|
||||
"profile_config": {
|
||||
"gfx_driver": null,
|
||||
"greeter": null,
|
||||
"profile": {}
|
||||
},
|
||||
"version": "3.0.9"
|
||||
}
|
||||
_EOF_
|
||||
}
|
||||
|
||||
# ==========================================
|
||||
# MAIN
|
||||
# ==========================================
|
||||
|
||||
if [[ $(tty) == "/dev/tty1" ]]; then
|
||||
run_configurator
|
||||
clear
|
||||
echo "Installing base system..."
|
||||
install_base_system
|
||||
|
||||
# --- 0. CONFIGURATION HORS-LIGNE ---
|
||||
ISO_CACHE="/root/offline_cache"
|
||||
# On monte le cache dans un dossier à part pour ne pas saturer la RAM
|
||||
CHROOT_OFFLINE_DIR="/mnt/opt/offline_cache"
|
||||
|
||||
if [[ -d "$ISO_CACHE" && -n "$(ls -A $ISO_CACHE/*.pkg.tar.zst 2>/dev/null)" ]]; then
|
||||
echo ">>> Mode HORS-LIGNE activé : Utilisation du cache de l'ISO"
|
||||
mkdir -p "$CHROOT_OFFLINE_DIR"
|
||||
mount --bind "$ISO_CACHE" "$CHROOT_OFFLINE_DIR"
|
||||
else
|
||||
echo ">>> Mode EN-LIGNE : Cache de l'ISO non trouvé, téléchargement depuis internet."
|
||||
fi
|
||||
|
||||
# --- 1. INSTALLATION PACKAGES OFFICIELS ---
|
||||
clear
|
||||
echo "Installing packages (Offline or Online)..."
|
||||
|
||||
EXTRA_PACKAGES=(
|
||||
"neovim" "ghostty" "hyprland" "xdg-desktop-portal-hyprland"
|
||||
"git" "yazi" "dolphin" "rofi" "waybar" "wiremix" "impala"
|
||||
"bluetui" "btop" "cava" "fastfetch" "obsidian" "obs-studio"
|
||||
"lazygit" "docker" "docker-buildx" "docker-compose" "lazydocker"
|
||||
"mpv" "prismlauncher" "rust" "chromium" "bat" "base-devel"
|
||||
"cmake" "nodejs" "npm" "pnpm" "python" "python-pip"
|
||||
"curl" "wget" "unzip"
|
||||
)
|
||||
|
||||
# On dit à pacman d'utiliser le disque dur pour écrire, et le dossier /opt/offline_cache pour LIRE les paquets pré-téléchargés
|
||||
if [[ -d "$CHROOT_OFFLINE_DIR" ]]; then
|
||||
arch-chroot /mnt pacman -S --noconfirm --cachedir /var/cache/pacman/pkg --cachedir /opt/offline_cache "${EXTRA_PACKAGES[@]}"
|
||||
else
|
||||
arch-chroot /mnt pacman -S --noconfirm "${EXTRA_PACKAGES[@]}"
|
||||
fi
|
||||
|
||||
# --- 2. INSTALLATION PACKAGES AUR (HORS-LIGNE) ---
|
||||
clear
|
||||
echo "Installing pre-compiled AUR packages..."
|
||||
for pkg in visual-studio-code-bin subtui-bin localsend-bin; do
|
||||
# On cherche le nom exact du fichier depuis l'hôte
|
||||
PKG_PATH=$(ls ${CHROOT_OFFLINE_DIR}/${pkg}*.pkg.tar.zst 2>/dev/null | head -n 1)
|
||||
|
||||
if [[ -n "$PKG_PATH" ]]; then
|
||||
echo ">>> Installation de $pkg"
|
||||
# On enlève "/mnt" du chemin pour que ça corresponde au point de vue du chroot
|
||||
CHROOT_PKG_PATH="${PKG_PATH#/mnt}"
|
||||
|
||||
# On passe le chemin exact (sans étoile) à pacman
|
||||
arch-chroot /mnt pacman -U --noconfirm "$CHROOT_PKG_PATH"
|
||||
else
|
||||
echo ">>> $pkg non trouvé, ignoré."
|
||||
fi
|
||||
done
|
||||
|
||||
# --- 3. CONFIGURATION TTY AUTO-LOGIN ---
|
||||
echo "Configuring TTY auto-login for $username..."
|
||||
|
||||
mkdir -p /mnt/etc/systemd/system/getty@tty1.service.d
|
||||
cat > /mnt/etc/systemd/system/getty@tty1.service.d/override.conf << EOF
|
||||
[Service]
|
||||
ExecStart=
|
||||
ExecStart=-/sbin/agetty --autologin $username --noclear %I \$TERM
|
||||
EOF
|
||||
|
||||
# --- 4. LANCEMENT AUTOMATIQUE DE HYPRLAND ---
|
||||
echo "Configuring auto-start Hyprland..."
|
||||
cat > "/mnt/home/$username/.bash_profile" << 'EOF'
|
||||
if [ -f /.arch-chroot ] || [ -n "$INSTALLING" ]; then
|
||||
return 0 2>/dev/null || exit 0
|
||||
fi
|
||||
if [ -z "${DISPLAY:-}" ] && [ "$(tty 2>/dev/null)" = "/dev/tty1" ]; then
|
||||
exec Hyprland
|
||||
fi
|
||||
EOF
|
||||
chown 1000:1000 "/mnt/home/$username/.bash_profile"
|
||||
|
||||
echo "========================"
|
||||
echo " Installation terminée"
|
||||
echo "========================"
|
||||
reboot
|
||||
# --- 5. COPIE DES DOTFILES & INJECTION CLAVIER ---
|
||||
clear
|
||||
echo "Copying custom .config files..."
|
||||
if [[ -d ".config" ]]; then
|
||||
cp -r .config "/mnt/home/$username/"
|
||||
|
||||
# On cherche dynamiquement le fichier .lua contenant le marqueur dans tout le dossier hypr
|
||||
HYPRLAND_CONF=$(grep -rl "__KB_LAYOUT__" "/mnt/home/$username/.config/hypr/" 2>/dev/null | head -n 1)
|
||||
|
||||
if [[ -n "$HYPRLAND_CONF" ]]; then
|
||||
# Utilisation de | comme délimiteur pour sed pour éviter les erreurs de parsing
|
||||
sed -i "s|__KB_LAYOUT__|${keyboard}|g" "$HYPRLAND_CONF"
|
||||
echo "Hyprland keyboard set to: $keyboard in $HYPRLAND_CONF"
|
||||
else
|
||||
echo "ERREUR: Marqueur __KB_LAYOUT__ introuvable dans les configs Hyprland !"
|
||||
fi
|
||||
|
||||
chown -R 1000:1000 "/mnt/home/$username/.config"
|
||||
echo "Dotfiles configured successfully!"
|
||||
else
|
||||
echo "No .config folder found, skipping."
|
||||
fi
|
||||
|
||||
# --- REBOOT ---
|
||||
echo "Installation finished! Rebooting in 3 seconds..."
|
||||
sleep 3
|
||||
reboot
|
||||
fi
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 46 KiB |
@@ -1,37 +1,137 @@
|
||||
#!/bin/bash
|
||||
|
||||
# Si l'utilisateur a oublié de mettre sudo, on redémarre le script avec sudo
|
||||
if [ "$EUID" -ne 0 ]; then
|
||||
echo "Le build nécessite les droits administrateur (sudo). Redémarrage..."
|
||||
exec sudo bash "$0" "$@"
|
||||
fi
|
||||
|
||||
set -e
|
||||
|
||||
ISO_NAME="arch-custom-iso"
|
||||
# On récupère le nom de l'utilisateur normal (pas root) pour makepkg
|
||||
BUILD_USER="${SUDO_USER:-root}"
|
||||
CUSTOM_PKGS_DIR="$PWD/custom-pkgs"
|
||||
|
||||
# ==============================================================================
|
||||
# LES LISTES DE PAQUETS
|
||||
# ==============================================================================
|
||||
EXTRA_PACKAGES=(
|
||||
"neovim" "ghostty" "hyprland" "xdg-desktop-portal-hyprland"
|
||||
"git" "yazi" "dolphin" "rofi" "waybar" "wiremix" "impala"
|
||||
"bluetui" "btop" "cava" "fastfetch" "obsidian" "obs-studio"
|
||||
"lazygit" "docker" "docker-buildx" "docker-compose" "lazydocker"
|
||||
"mpv" "prismlauncher" "rust" "chromium" "bat" "base-devel"
|
||||
"cmake" "nodejs" "npm" "pnpm" "python" "python-pip"
|
||||
"curl" "wget" "unzip"
|
||||
)
|
||||
|
||||
AUR_PACKAGES=(
|
||||
"visual-studio-code-bin"
|
||||
"subtui-bin"
|
||||
"localsend-bin"
|
||||
)
|
||||
|
||||
# ==============================================================================
|
||||
# PROCESSUS DE BUILD
|
||||
# ==============================================================================
|
||||
|
||||
echo "====================================="
|
||||
echo " Building Arch Linux ISO"
|
||||
echo " Project: $ISO_NAME"
|
||||
echo " Build lancé par l'utilisateur: $BUILD_USER"
|
||||
echo "====================================="
|
||||
|
||||
# Check archiso
|
||||
if ! command -v mkarchiso &> /dev/null; then
|
||||
echo "[ERROR] archiso is not installed"
|
||||
echo "Run: sudo pacman -S archiso"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Clean previous build
|
||||
echo "[1/3] Cleaning previous build..."
|
||||
rm -rf work out
|
||||
echo "[1/5] Cleaning previous build..."
|
||||
rm -rf work out offline_cache
|
||||
|
||||
# Build ISO
|
||||
echo "[2/3] Building ISO..."
|
||||
# --- TÉLÉCHARGEMENT DES PAQUETS OFFICIELS ---
|
||||
echo "[2/6] Downloading Official Packages for offline cache..."
|
||||
# On utilise /tmp pour éviter tout problème de permissions dans le Home
|
||||
TMP_CACHE="/tmp/archiso_cache_$$"
|
||||
mkdir -p "$TMP_CACHE"
|
||||
sudo pacman -Sy --noconfirm
|
||||
|
||||
# On télécharge (-w) sans installer, dans le dossier temporaire
|
||||
sudo pacman -Sw --noconfirm --cachedir "$TMP_CACHE" "${EXTRA_PACKAGES[@]}" || true
|
||||
|
||||
# On crée le vrai dossier de cache et on déplace les paquets
|
||||
mkdir -p offline_cache
|
||||
cp "$TMP_CACHE"/*.pkg.tar.zst offline_cache/ 2>/dev/null || true
|
||||
rm -rf "$TMP_CACHE"
|
||||
|
||||
# --- COMPILATION DES PAQUETS PERSONNALISÉS ---
|
||||
echo "[3/6] Building custom packages from custom-pkgs/..."
|
||||
mkdir -p custom_pkg_build
|
||||
for pkg_dir in "$CUSTOM_PKGS_DIR"/*; do
|
||||
[ -d "$pkg_dir" ] || continue
|
||||
[ -f "$pkg_dir/PKGBUILD" ] || continue
|
||||
|
||||
pkg_name=$(basename "$pkg_dir")
|
||||
echo " -> Building custom package: $pkg_name"
|
||||
rm -rf "custom_pkg_build/$pkg_name"
|
||||
cp -a "$pkg_dir" "custom_pkg_build/$pkg_name"
|
||||
chown -R "$BUILD_USER":"$BUILD_USER" "custom_pkg_build/$pkg_name"
|
||||
sudo -u "$BUILD_USER" bash -lc "cd '$PWD/custom_pkg_build/$pkg_name' && makepkg -f --noconfirm --needed"
|
||||
mv "custom_pkg_build/$pkg_name"/*.pkg.tar.zst offline_cache/ 2>/dev/null || true
|
||||
done
|
||||
rm -rf custom_pkg_build
|
||||
|
||||
# --- COMPILATION DES PAQUETS AUR ---
|
||||
echo "[4/6] Building AUR Packages for offline cache..."
|
||||
mkdir -p aur_build
|
||||
|
||||
for pkg in "${AUR_PACKAGES[@]}"; do
|
||||
echo " -> Building AUR package: $pkg"
|
||||
cd aur_build
|
||||
rm -rf "$pkg"
|
||||
git clone "https://aur.archlinux.org/${pkg}.git" --depth 1
|
||||
|
||||
# CRUCIAL : On donne les droits à l'utilisateur NORMAL pour que makepkg accepte de tourner
|
||||
chown -R "$BUILD_USER":"$BUILD_USER" "$pkg"
|
||||
cd "$pkg"
|
||||
|
||||
# CRUCIAL : On lance makepkg EN TANT QU'UTILISATEUR NORMAL (pas de -s pour éviter de reboucler sur sudo)
|
||||
sudo -u "$BUILD_USER" makepkg -d -f --noconfirm --needed
|
||||
|
||||
# On déplace le paquet compilé dans notre cache
|
||||
mv *.pkg.tar.zst ../../offline_cache/
|
||||
cd ../..
|
||||
done
|
||||
rm -rf aur_build
|
||||
|
||||
# --- INJECTION DANS L'ISO ---
|
||||
echo "[5/6] Injecting offline cache into ISO skeleton..."
|
||||
mkdir -p airootfs/root/offline_cache
|
||||
cp offline_cache/*.pkg.tar.zst airootfs/root/offline_cache/
|
||||
rm -rf offline_cache
|
||||
|
||||
# Copier les scripts personnalisés dans la racine du live system si nécessaire
|
||||
mkdir -p airootfs/usr/local/bin
|
||||
for script in custom-pkgs/*/*.sh; do
|
||||
[ -f "$script" ] || continue
|
||||
script_name="$(basename "$script")"
|
||||
target_name="${script_name%.sh}"
|
||||
install -Dm0755 "$script" "airootfs/usr/local/bin/$target_name"
|
||||
done
|
||||
|
||||
# --- CRÉATION DE L'ISO ---
|
||||
echo "[6/6] Building ISO (this will take a while)..."
|
||||
sudo mkarchiso -v .
|
||||
|
||||
# Check result
|
||||
if [ -f out/*.iso ]; then
|
||||
echo "[3/3] Build successful!"
|
||||
echo "ISO located in: out/"
|
||||
echo ""
|
||||
echo "====================================="
|
||||
echo " Build successful!"
|
||||
echo " ISO located in: out/"
|
||||
echo "====================================="
|
||||
else
|
||||
echo "[ERROR] ISO not found in out/"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
echo "====================================="
|
||||
echo "Done."
|
||||
echo "====================================="
|
||||
fi
|
||||
@@ -0,0 +1,18 @@
|
||||
# Paquets personnalisés
|
||||
|
||||
Place ici les sources de tes applications personnelles.
|
||||
|
||||
Structure recommandée :
|
||||
|
||||
- custom-pkgs/my-app/
|
||||
- PKGBUILD
|
||||
- .SRCINFO (généré automatiquement)
|
||||
- src/
|
||||
|
||||
Exemple rapide :
|
||||
|
||||
- une application en C/C++/Rust/Go/Python
|
||||
- un script shell autonome
|
||||
- un binaire déjà compilé
|
||||
|
||||
Pour une application non disponible sur pacman/AUR, la méthode la plus propre est de la packager avec un PKGBUILD puis de la construire dans le build ISO.
|
||||
@@ -0,0 +1,18 @@
|
||||
# Maintainer: Ton Nom <ton@email>
|
||||
|
||||
pkgname=optifetch
|
||||
pkgver=1.0
|
||||
pkgrel=1
|
||||
pkgdesc="Version personnalisée de fastfetch intégrée dans l'ISO"
|
||||
arch=('x86_64')
|
||||
url='https://example.com/ton-projet'
|
||||
license=('MIT')
|
||||
depends=('gcc' 'make')
|
||||
source=("optifetch::git+https://github.com/arthur-pbty/optifetch.git")
|
||||
sha256sums=('SKIP')
|
||||
|
||||
package() {
|
||||
cd "$srcdir/optifetch"
|
||||
make
|
||||
install -Dm0755 optifetch "$pkgdir/usr/bin/optifetch"
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
# Ce script est exécuté dans l'environnement du live ISO
|
||||
# Il peut installer/mettre en place des éléments personnalisés.
|
||||
|
||||
echo "[custom] Configuration personnalisée de l'ISO"
|
||||
|
||||
# Exemple: créer un dossier pour tes applis perso
|
||||
mkdir -p /usr/local/bin /usr/local/share/my-apps
|
||||
|
||||
# Si tu as déjà un binaire compilé, tu peux l'ajouter ici.
|
||||
# Exemple:
|
||||
# install -Dm0755 /root/custom-app /usr/local/bin/custom-app
|
||||
|
||||
# Si tu veux rendre un script disponible globalement:
|
||||
# install -Dm0755 /root/custom-scripts/hello.sh /usr/local/bin/hello.sh
|
||||
Reference in New Issue
Block a user