#!/usr/bin/perl # Copyright (C) 2010-2012 Trizen . # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # #------------------------------------------------------- # Appname: alsi # Created on: 04 October 2010 # Latest edit on: 13 April 2012 # Website: http://trizen.googlecode.com #------------------------------------------------------- # use strict; # use warnings; my (%CONFIG, $appname, $version, $config_file, $colors_file); sub help { print <<"HELP"; Usage: $0 [options]\n Main options: -a --archey : archey's logo -n --screenfetch : screenfetch's logo -f --file-logo=file : use logo from file -u --usage-colors : use colors for RAM and HDD usage -ub or --usage-bold-colors for bold colors -t --text-color : use NC (color1) for text values -l --list : output logo + values as a list -c1=COLOR_NAME : set normal color (ex: red) -c2=COLOR_NAME : set bold color (ex: black) - : set color1 and color2 at the same color. Available colors are: black, red, green yellow, blue, purple, cyan and white Other options: -update-config : update the configuration file -noconfig : don't load the configuration file -s --screenshot : take a screenshot -h --help : print help and exit -v --version : print version and exit Logo file: special variables : \$c1, \$c2, \$z * escaped characters : \\t, \\e, \\x * Note: the variables are also valid as \${var_name} when are followed by a word character ** Config file : $config_file ** Colors file : $CONFIG{COLORS_FILE} ** Output file : $CONFIG{OUTPUT_FILE} ** Logo file : $CONFIG{LOGO_FILE} ** WManagers : $CONFIG{WM_FILE} ** DEnvironments : $CONFIG{DE_FILE}\n HELP exit 0; } sub version { print "$appname $version\n"; exit 0; } my $colors = do $CONFIG{COLORS_FILE}; unless (ref $colors eq 'HASH') { die "[!] There is a problem with the COLORS_FILE '$CONFIG{COLORS_FILE}': " . ($! || q{doesn't return a HASH ref}) . "\n"; } # argv options my %opt; # Save hash config to file sub write_config_to_file { Config::save_hash($config_file, \%CONFIG); return 1; } # Set config file to %CONFIG sub apply_configuration { my $config_ref = do $config_file; if (ref $config_ref eq 'HASH') { while (my ($key, $value) = each %$config_ref) { $CONFIG{$key} = $value; } } else { write_config_to_file(); } if ($CONFIG{ALSI_VERSION} ne $version) { $CONFIG{ALSI_VERSION} = $version; $opt{update_config} = 1; } } sub parse_arguments { require Getopt::Long; Getopt::Long::GetOptions( # Main options 'help|h|?' => \&help, 'version|v' => \&version, # Colors 'normal|color1|c1=s' => \$CONFIG{DEFAULT_COLOR_NORMAL}, 'bold|color2|c2=s' => \$CONFIG{DEFAULT_COLOR_BOLD}, 'default|d' => sub { ($opt{default_color}) = @_ }, 'blue' => sub { ($opt{default_color}) = @_ }, 'red|r' => sub { ($opt{default_color}) = @_ }, 'green|g' => sub { ($opt{default_color}) = @_ }, 'yellow|y' => sub { ($opt{default_color}) = @_ }, 'black|b' => sub { ($opt{default_color}) = @_ }, 'purple|p' => sub { ($opt{default_color}) = @_ }, 'cyan|c' => sub { ($opt{default_color}) = @_ }, 'white|w' => sub { ($opt{default_color}) = @_ }, # Others 'usage-colors|u!' => \$CONFIG{USAGE_COLORS}, 'usage-bold-colors|ub!' => \$CONFIG{USAGE_COLORS_BOLD}, 'text-color|t!' => \$CONFIG{USE_VALUES_COLOR}, 'list|l' => \$opt{as_a_list}, 'file-logo|logo-from-file|f:s' => \$opt{logo_from_file}, 'noconfig!' => \$opt{noconfig}, 'screenfetch|n' => \$opt{screenfetch_logo}, 'archey|a' => \$opt{archey_logo}, 'screenshot|s' => \$opt{take_screenshot}, 'update-config|reconfigure!' => \$opt{update_config}, ); } # Parsing arguments if (@ARGV) { parse_arguments(); } $colors->{default}{normal} = $colors->{$CONFIG{DEFAULT_COLOR_NORMAL}}{normal}; $colors->{default}{bold} = $colors->{$CONFIG{DEFAULT_COLOR_BOLD}}{bold}; if (defined $opt{default_color}) { $colors->{default} = $colors->{$opt{default_color}}; } if ($CONFIG{USE_VALUES_COLOR}) { $colors->{reset} = $colors->{default}{normal}; } my ($c1, $c2, $z) = ($colors->{default}{normal}, $colors->{default}{bold}, $colors->{reset}); my $wm = do $CONFIG{WM_FILE}; my $de = do $CONFIG{DE_FILE}; #------ Getting system informations -------# sub count_packages { opendir(my $dir_h, $CONFIG{PACKAGES_PATH}) or return; my $x = () = readdir $dir_h; closedir $dir_h; $x - 2; } sub get_usage_color { my ($percent) = @_; return $colors->{green}{$CONFIG{USAGE_COLORS_BOLD} ? 'bold' : 'normal'} if $percent <= $CONFIG{USAGE_PRECENT_GREEN}; return $colors->{yellow}{$CONFIG{USAGE_COLORS_BOLD} ? 'bold' : 'normal'} if $percent <= $CONFIG{USAGE_PRECENT_YELLOW}; return $colors->{red}{$CONFIG{USAGE_COLORS_BOLD} ? 'bold' : 'normal'} if $percent <= $CONFIG{USAGE_PRECENT_RED}; } sub get_total_size_color { my $bold = $c1; $bold =~ s/0/1/; return $CONFIG{USE_VALUES_COLOR} ? $CONFIG{USAGE_COLORS_BOLD} ? $bold : $c1 : ''; } sub get_cpu_load_average { my $load_average; open my $fh, '<', '/proc/loadavg' or return; sysread $fh, $load_average, 14; close $fh; return $load_average; } sub get_init_mode { my $init_mode; open my $fh, '<', '/etc/inittab' or return; while (defined(my $line = <$fh>)) { ($init_mode) = $line =~ /^id:(\d):initdefault/ and last; } close $fh; return $init_mode; } # Hostname my $hostname; if (open my $hostname_fh, '<', '/proc/sys/kernel/hostname') { $hostname = <$hostname_fh>; close $hostname_fh; } else { $hostname = `uname -n`; } # Kernel my $kernel; if (open my $osrelease_fh, '<', '/proc/sys/kernel/osrelease') { $kernel = <$osrelease_fh>; close $osrelease_fh; } else { $kernel = `uname -r`; } # Arch my $arch = `uname -m`; # OS my $os = -e '/etc/arch-release' ? "Arch Linux $arch" : substr(`uname -o`, 0, -1) . " $arch"; # Packages my $packages = count_packages() || 'Unknown'; $packages .= "\n"; # Finding Window Manager or Desktop Environment my $wm_de = ['Window Manager', "unknown\n"]; open my $ps_pipe, '-|', $CONFIG{PS_COMMAND}; while (defined(my $process = <$ps_pipe>)) { $process = (split(' ', $process))[-1]; if (exists $de->{$process}) { $wm_de = ['Desktop Environment', "$de->{$process}\n"]; last; } elsif ( exists $wm->{$process} or ( substr($process, -8) eq '-session' and exists $wm->{ do { $process =~ s/-session$//; $process } } ) ) { $wm_de = ['Window Manager', "$wm->{$process}\n"]; last; } } close $ps_pipe; # CPU my $cpu; if (open my $cpu_fh, '<', '/proc/cpuinfo') { while (defined(my $cpu_line = <$cpu_fh>)) { if (substr($cpu_line, 0, 10) eq 'model name') { ($cpu) = $cpu_line =~ /^model name\t: (.+)/s; last; } } close $cpu_fh; } $cpu //= `uname -p`; $cpu = join(' ', split(' ', $cpu)) . "\n"; # RAM my $freeram = 0; my $totalram = 0; my $match_ram = qr/:\s+?(\d+)/; open my $ram_fh, '<', '/proc/meminfo'; while (defined(my $ram_line = <$ram_fh>)) { $totalram = int $1 / 1024 if $. == 1 and $ram_line =~ /$match_ram/o; $freeram += int $1 / 1024 if $. ~~ [2, 3, 4] and $ram_line =~ /$match_ram/o; last if $. == 4; } close $ram_fh; my $usedram = $totalram - $freeram; my $usedpercent = int $usedram / $totalram * 100; if ($CONFIG{USAGE_COLORS} or $CONFIG{USAGE_COLORS_BOLD}) { my $ram_usage_color = get_usage_color($usedpercent); $usedram = $ram_usage_color . "${usedram}M" . $z; $usedpercent = $ram_usage_color . $usedpercent . '%' . $z; $totalram = get_total_size_color() . "${totalram}M" . $z; } $usedpercent .= '%' unless $usedpercent =~ /%/; # Uptime open my $uptime_fh, '<', '/proc/uptime'; my $uptime = <$uptime_fh>; close $uptime_fh; ($uptime) = $uptime =~ /^(.+?) /; my $day = int $uptime / 86400; $uptime %= 86400; my $hours = int $uptime / 3600; $uptime %= 3600; my $min = sprintf('%02d', int $uptime / 60); my $sec = $uptime % 60; $uptime = ''; $uptime = "$day day, " if $day == 1; $uptime = "$day days, " if $day > 1; $uptime .= $hours ? "${hours}:$min" : "$min min"; $uptime .= ", $sec sec" unless $day; $uptime .= "\n"; # Partitions my %partitions; my $tmp_clr = ''; my $tmp_gcl = ''; my $match_device = qr"^/.+?\s+(\w+)\s+([\w.,]+)\s+([\w.,]+)\s+[\w.,]+\s+(\d+)%\s+/(.*)"; open my $df_pipe, '-|', $CONFIG{DF_COMMAND}; while (defined(my $line = <$df_pipe>)) { my ($type, $totalsize, $used, $used_percent, $mountpoint) = $line =~ /$match_device/o or next; $mountpoint = length $mountpoint ? $mountpoint =~ m{.+/} ? ucfirst substr($mountpoint, $+[0]) : ucfirst $mountpoint : 'Root'; if ($CONFIG{USAGE_COLORS} or $CONFIG{USAGE_COLORS_BOLD}) { $tmp_clr = get_usage_color($used_percent); $tmp_gcl = get_total_size_color(); } $partitions{"$c2${mountpoint}:$z $tmp_clr$used$z / $tmp_gcl$totalsize$z ($tmp_clr$used_percent%$z) ($type)\n"} = (); } close $df_pipe; # Getting GTK informations my %GTKRC; sub get_gtkrc_info { my ($name, $version) = @_; $version ||= 2; if (exists $GTKRC{$name}) { return $GTKRC{$name}; } my $gtkrc_content; my $file = $version == 3 ? $CONFIG{GTK3_RC_FILE} : $CONFIG{GTK2_RC_FILE}; open my $fh, '<', $file or return; sysread $fh, $gtkrc_content, -s $file; close $fh; ($GTKRC{"GTK${version}_THEME"}) = $gtkrc_content =~ /^\s*gtk-theme-name\s*=\s*['"]?([^"'\n]+)/m; ($GTKRC{"GTK${version}_ICON_THEME"}) = $gtkrc_content =~ /^\s*gtk-icon-theme-name\s*=\s*['"]?([^"'\n]+)/m; ($GTKRC{"GTK${version}_FONT_NAME"}) = $gtkrc_content =~ /^\s*gtk-font-name\s*=\s*['"]?([^"'\n]+)/m; return $GTKRC{$name}; } # Logos if (defined $opt{logo_from_file} or $CONFIG{USE_LOGO_FROM_FILE}) { unless (-r $CONFIG{LOGO_FILE}) { warn "[!] Unable to read '$CONFIG{LOGO_FILE}': $!\n"; undef $opt{logo_from_file}; } } my $arch_logo; if (defined $opt{logo_from_file} or $CONFIG{USE_LOGO_FROM_FILE}) { open my $logo_fh, '<', (-f $opt{logo_from_file} ? $opt{logo_from_file} : $CONFIG{LOGO_FILE}); while (defined(my $line = <$logo_fh>)) { $line =~ s/(? < $c2/$c1##,-,##$c2\\$c1 \\__,_|_| \\___|_| |_|_|_|_| |_|\\__,_/_/\\_\\ $c2/$c1##( )##$c2\\$c1 $c2/$c1#.-- --.#$c2\\\e[1;37m A simple, elegant GNU/Linux distribution. $c2/$c1` `$c2\\$z LOGO } else { $arch_logo = <<"LOGO" $c1##$z\t\t\t $c1#$c2##$c1#$z\t\t\t $c1#$c2####$c1#$z\t\t\t $c1#$c2######$c1#$z\t\t\t $c1#$c2########$c1#$z\t\t $c1#$c2##########$c1#$z\t\t $c1#$c2############$c1#$z\t\t $c1#$c2##############$c1#$z\t\t $c1#$c2################$c1#$z\t\t $c1#$c2##################$c1#$z\t\t $c1#$c2#######$c1######$c2#######$c1#$z\t\t $c1#$c2#######$c1#$z $c1#$z$c2#######$c1#$z\t\t $c1#$c2########$c1#$z $c1#$z$c2########$c1#$z\t $c1#$c2#########$c1#$z $c1#$z$c2#########$c1#$z\t $c1#$c2######$c1###$z $c1###$c2######$c1#$z\t $c1#$c2####$c1##$z $c1##$c2####$c1#$z\t $c1#$c2##$c1#$z $c1#$c2##$c1#$z\t $c1#$c2#$c1#$z $c1#$c2#$c1#$z\t LOGO } my (@arch_logo) = split(/\n/, $arch_logo); #--- OUTPUT AREA my $config_array = do $CONFIG{OUTPUT_FILE}; sub print_logo_line { if ($opt{as_a_list} and @arch_logo) { print join "\n", @arch_logo, "\n", "${c1}> "; @arch_logo = (); return 1; } elsif (@arch_logo) { print shift @arch_logo; return 1; } return $opt{as_a_list} ? print "${c1}> " : 0; } if (ref $config_array eq 'ARRAY') { print "\n"; foreach my $item (@$config_array) { if (exists $item->{OS}) { print_logo_line() or last; printf $item->{OS}, $c2, $z, $os; } elsif (exists $item->{CPU}) { print_logo_line() or last; printf $item->{CPU}, $c2, $z, $cpu; } elsif (exists $item->{RAM}) { print_logo_line() or last; printf $item->{RAM}, $c2, $z, "$usedram / $totalram ($usedpercent)\n"; } elsif (exists $item->{WM_DE}) { print_logo_line() or last; printf $item->{WM_DE}, $c2, $wm_de->[0], $z, $wm_de->[1]; } elsif (exists $item->{UPTIME}) { print_logo_line() or last; printf $item->{UPTIME}, $c2, $z, $uptime; } elsif (exists $item->{KERNEL}) { print_logo_line() or last; printf $item->{KERNEL}, $c2, $z, $kernel; } elsif (exists $item->{HOSTNAME}) { print_logo_line() or last; printf $item->{HOSTNAME}, $c2, $z, $hostname; } elsif (exists $item->{PACKAGES}) { print_logo_line() or last; printf $item->{PACKAGES}, $c2, $z, $packages; } elsif (exists $item->{SHELL}) { print_logo_line() or last; printf $item->{SHELL}, $c2, $z, ($ENV{SHELL} || (getpwuid($<))[-1] || 'Unknown') . "\n"; } elsif (exists $item->{GTK2_THEME}) { my $gtk2_theme = get_gtkrc_info('GTK2_THEME', 2) // next; print_logo_line() or last; printf $item->{GTK2_THEME}, $c2, $z, "$gtk2_theme\n"; } elsif (exists $item->{GTK2_ICON_THEME}) { my $gtk2_icon_theme = get_gtkrc_info('GTK2_ICON_THEME', 2) // next; print_logo_line() or last; printf $item->{GTK2_ICON_THEME}, $c2, $z, "$gtk2_icon_theme\n"; } elsif (exists $item->{GTK2_FONT_NAME}) { my $gtk2_font_name = get_gtkrc_info('GTK2_FONT_NAME', 2) // next; print_logo_line() or last; printf $item->{GTK2_FONT_NAME}, $c2, $z, "$gtk2_font_name\n"; } elsif (exists $item->{GTK3_THEME}) { my $gtk3_theme = get_gtkrc_info('GTK3_THEME', 3) // next; print_logo_line() or last; printf $item->{GTK3_THEME}, $c2, $z, "$gtk3_theme\n"; } elsif (exists $item->{GTK3_ICON_THEME}) { my $gtk3_icon_theme = get_gtkrc_info('GTK3_ICON_THEME', 3) // next; print_logo_line() or last; printf $item->{GTK3_ICON_THEME}, $c2, $z, "$gtk3_icon_theme\n"; } elsif (exists $item->{GTK3_FONT_NAME}) { my $gtk3_font_name = get_gtkrc_info('GTK3_FONT_NAME', 3) // next; print_logo_line() or last; printf $item->{GTK3_FONT_NAME}, $c2, $z, "$gtk3_font_name\n"; } elsif (exists $item->{PARTITIONS}) { foreach my $partition (sort keys %partitions) { print_logo_line() or last; print $partition; } } elsif (exists $item->{OTHER}) { print_logo_line() or last; printf $item->{OTHER} . ($item->{OTHER} =~ /\n\z/ ? '' : "\n"), $c2, $z; } elsif (exists $item->{HARDCODED}) { print_logo_line() or last; print $item->{HARDCODED} . ($item->{HARDCODED} =~ /\n\z/ ? '' : "\n"); } elsif (exists $item->{CPU_LOAD}) { my $cpu_load_average = get_cpu_load_average() // next; print_logo_line() or last; printf $item->{CPU_LOAD}, $c2, $z, "$cpu_load_average\n"; } elsif (exists $item->{USERNAME}) { print_logo_line() or last; printf $item->{USERNAME}, $c2, $z, ($ENV{USERNAME} // $ENV{LOGNAME} // getlogin // (getpwuid($<))[0] // 'unknown') . "\n"; } elsif (exists $item->{INIT_MODE}) { my $init_mode = get_init_mode() // next; print_logo_line() or last; printf $item->{INIT_MODE}, $c2, $z, "$init_mode\n"; } elsif (exists $item->{COMMAND} and ref $item->{COMMAND} eq 'ARRAY') { print_logo_line() or last; printf $item->{COMMAND}[0], $c2, $z, `$item->{COMMAND}[1]`; } } } else { die "[!] There is a problem with the OUTPUT_FILE '$CONFIG{OUTPUT_FILE}': " . ($! || q{doesn't return an ARRAY ref}) . "\n"; } while (@arch_logo) { print_logo_line(); print "\n"; } print "\n"; print "\e[0m" if $CONFIG{USE_VALUES_COLOR}; Config::save_hash($config_file, \%CONFIG) if $opt{update_config}; exec $CONFIG{SCREENSHOT_COMMAND} if $opt{take_screenshot}; sub INIT { $appname = 'alsi'; $version = '0.4.3'; my $home_dir = $ENV{HOME} || $ENV{LOGDIR} || (getpwuid($<))[7] || `echo -n ~`; my $config_dir = $ENV{XDG_CONFIG_HOME} || "$home_dir/.config"; my $alsi_config_dir = "$config_dir/$appname"; $config_file = $alsi_config_dir . "/$appname.conf"; %CONFIG = ( ALSI_VERSION => $version, USE_VALUES_COLOR => 0, USE_LOGO_FROM_FILE => 0, USAGE_COLORS => 0, USAGE_COLORS_BOLD => 0, USAGE_PRECENT_RED => 100, USAGE_PRECENT_YELLOW => 85, USAGE_PRECENT_GREEN => 50, DEFAULT_COLOR_NORMAL => 'blue', DEFAULT_COLOR_BOLD => 'blue', PS_COMMAND => 'ps xc', DF_COMMAND => 'df -Th -x sys -x tmpfs -x devtmpfs', SCREENSHOT_COMMAND => 'scrot -cd 5', GTK2_RC_FILE => "$home_dir/.gtkrc-2.0", GTK3_RC_FILE => "$config_dir/gtk-3.0/settings.ini", LOGO_FILE => "$alsi_config_dir/alsi.logo", COLORS_FILE => "$alsi_config_dir/$appname.colors", OUTPUT_FILE => "$alsi_config_dir/alsi.output", WM_FILE => "$alsi_config_dir/alsi.wm", DE_FILE => "$alsi_config_dir/alsi.de", PACKAGES_PATH => '/var/lib/pacman/local/', ); # Creating config unless it exists if (not -e $config_file or not -e $alsi_config_dir) { require File::Path; File::Path::make_path($alsi_config_dir); write_config_to_file(); } apply_configuration() unless '-noconfig' ~~ \@ARGV; unless (-e $CONFIG{COLORS_FILE}) { Config::save_plain($CONFIG{COLORS_FILE}, <<'COLORS'); #!/usr/bin/perl # Colors for alsi scalar { black => {normal => "\e[0;30m", bold => "\e[1;30m"}, red => {normal => "\e[0;31m", bold => "\e[1;31m"}, green => {normal => "\e[0;32m", bold => "\e[1;32m"}, yellow => {normal => "\e[0;33m", bold => "\e[1;33m"}, default => {normal => "\e[0;34m", bold => "\e[1;34m"}, blue => {normal => "\e[0;34m", bold => "\e[1;34m"}, purple => {normal => "\e[0;35m", bold => "\e[1;35m"}, cyan => {normal => "\e[0;36m", bold => "\e[1;36m"}, white => {normal => "\e[0;37m", bold => "\e[1;37m"}, reset => "\e[0m", } COLORS } unless (-e $CONFIG{OUTPUT_FILE}) { Config::save_plain($CONFIG{OUTPUT_FILE}, <<'OUTPUT_FILE'); #!/usr/bin/perl # '%sTitle:%s %s' # | \ \ ` Value # \ \ `-- End of BC (or start of NC) # BC ` Label # NC = normal color (color1) # BC = bold color (color2) #-- Other valid options are: # USERNAME - ex: {USERNAME => '%sUsername:%s %s'}, # CPU_LOAD - ex: {CPU_LOAD => '%sCPU load average:%s %s'}, # INIT_MODE - ex: {INIT_MODE => '%sInit mode:%s %s'}, # OTHER - ex: {OTHER => '%sResolution:%s 1024x768'}, # COMMAND - ex: {COMMAND => ['%sBinaries:%s %s', 'ls /usr/bin | wc -l']}, # HARDCODED - ex: {HARDCODED => "\e[1;37m\e[41mTHIS IS ALSI\e[0m"}, # GTK3_THEME - ex: {GTK3_THEME => '%sGTK3 theme:%s %s'}, # GTK3_ICON_THEME - ex: {GTK3_ICON_THEME => '%sGTK3 icon theme:%s %s'}, # GTK3_FONT_NAME - ex: {GTK3_FONT_NAME => '%sGTK3 font name:%s %s'}, [ {OS => '%sOS:%s %s'}, # Operating system {HOSTNAME => '%sHostname:%s %s'}, # Hostname {UPTIME => '%sUptime:%s %s'}, # Uptime {KERNEL => '%sKernel:%s %s'}, # Kernel version {SHELL => '%sShell:%s %s'}, # Shell {PACKAGES => '%sPackages:%s %s'}, # Number of installed packages {WM_DE => '%s%s:%s %s'}, # Window Manager or Desktop Environment {GTK2_THEME => '%sGTK2 theme:%s %s'}, # Gtk2 theme {GTK2_ICON_THEME => '%sGTK2 icon theme:%s %s'}, # Gtk2 icon theme {GTK2_FONT_NAME => '%sGTK2 font name:%s %s'}, # Gtk2 font name {RAM => '%sRAM:%s %s'}, # RAM usage {CPU => '%sCPU:%s %s'}, # CPU name {PARTITIONS => '...'}, # Partitions goes here ] OUTPUT_FILE } unless (-e $CONFIG{WM_FILE}) { Config::save_plain($CONFIG{WM_FILE}, <<'WM_FILE'); #!/usr/bin/perl # PROCESS_NAME => WINDOW_MANAGER_NAME scalar { '2wm' => '2wm', '9wm' => '9wm', 'afterstep' => 'AfterStep', 'antiwm' => 'AntiWM', 'awesome' => 'Awesome', 'barewm' => 'Bare WM', 'beryl' => 'Beryl', 'blackbox' => 'Blackbox', 'clfswm' => 'CLFS WM', 'compiz' => 'Compiz', 'ctwm' => 'CTWM', 'cwm' => 'CWM', 'dswm' => 'DSWM', 'dwm' => 'DWM', 'echinus' => 'Echinus', 'enlightenment' => 'Enlightenment', 'euclid' => 'Euclid', 'evil-wm' => 'EvilWM', 'evilpoison' => 'EviL Poison', 'fluxbox' => 'Fluxbox', 'flwm' => 'FLWM', 'fvwm' => 'FVWM', 'hackedbox' => 'Hackedbox', 'hildon-desktop' => 'Matchbox', 'i3' => 'i3', 'icewm' => 'IceWM', 'ion-3' => 'Ion3', 'ion3' => 'Ion3', 'jwm' => 'JWM', 'karmen' => 'Karmen', 'kwin' => 'Kwin', 'larswm' => 'Lars WM', 'lewm' => 'LEWM', 'lwm' => 'LWM', 'matwm2' => 'matWM2', 'metacity' => 'Metacity', 'musca' => 'Musca', 'notion' => 'Notion', 'openbox' => 'Openbox', 'openbox-gnome-session' => 'Openbox (GNOME session)', 'openbox-kde-session' => 'Openbox (KDE session)', 'pawm' => 'PAWM', 'pekwm' => 'PekWM', 'qlwm' => 'qLWM', 'qtile' => 'qTile', 'quarkwm' => 'QuarkWM', 'ratpoison' => 'ratpoison', 'sawfish' => 'Sawfish', 'scrot-wm' => 'ScrotWM', 'scrotwm' => 'ScrotWM', 'sithwm' => 'SithWM', 'stumpwm' => 'StumpWM', 'subtle' => 'Subtle', 'swm' => 'SWM', 'tinywm' => 'TinyWM', 'tritium' => 'Tritium', 'twm' => 'twm', 'velox' => 'Velox', 'vtwm' => 'VtWM', 'vwm' => 'VWM', 'w9wm' => 'w9wm', 'weewm' => 'WeeWM', 'windowmaker' => 'WindowMaker', 'windwm' => 'WindWM', 'wmaker' => 'WindowMaker', 'wmfs' => 'Wmfs', 'WMFS' => 'WMFS', 'wmii' => 'wmii', 'wmii36' => 'wmii36', 'xmonad' => 'xmonad', 'yeahwm' => 'YeahWM', } WM_FILE } unless (-e $CONFIG{DE_FILE}) { Config::save_plain($CONFIG{DE_FILE}, <<'DE_FILE'); #!/usr/bin/perl # PROCESS_NAME => DESKTOP_ENVIRONMENT_NAME scalar { 'gnome-session' => 'GNOME', 'kdm' => 'KDE', 'ksmserver' => 'KDE', 'lxsession' => 'LXDE', 'xfce4-session' => 'XFCE4', 'xfwm4' => 'XFCE4', } DE_FILE } unless (-e $CONFIG{LOGO_FILE}) { Config::save_plain($CONFIG{LOGO_FILE}, <<'LOGO'); $c1 Y\ /Y\t\t $c1 | \ _ / |\t\t $c1 _____ | =(_)= |\t\t $c1 ,-~" "~-. ,-~\/^ ^\/~-.\t\t $c1 ,^ ___ ___ ^. ,^ ___ ___ ^.\t $c1 / .^ ^. .^ ^. \ / .^ ^. .^ ^. \\\t $c1 Y l O! l O! Y Y lo ! lo ! Y\t $c1 l_ `.___.' `.___.' _[ l_ `.___.' `.___.' _[\t $c1 l^~"-------------"~^I l^~"-------------"~^I\t $c1 !\, ,/! ! !\t $c1 \ ~-.,_______,.-~ / \ /\t $c1 ^. .^ ^. .^\t $c1 "-.._____.,-" "-.._____.,-"\t\t \t\t\t\t\t\t\t $c2 WHY DOES THE LOGO FOR GENTOO LINUX\t\t \t\t\t\t\t\t\t $c2 LOOK LIKE A RETARDED PAC-MAN?\t\t$z LOGO } } package Config; sub _dump { require Data::Dumper; return Data::Dumper::Dumper(shift); } sub _sort_items { my ($data) = @_; my ($items) = $data =~ /\{(.+?)\s*\};?\s*\z/s; $items .= ','; $data = "#!/usr/bin/perl\n\nscalar {" . join( "\n", ( sort { lc $a cmp lc $b } split(/\n/, $items, 0) ) ) . "\n};\n"; $data =~ s{=>\s*'(\d+)',\s*$} {=> $1,}gm; $data =~ s{(.+?)\s*=>\s*(.+)}{ sprintf '%s%*s', $1, 40 - length($1) + length($2), ' => ' . $2; }egm; return $data; } sub save_hash { my ($file, $config) = @_; return unless ref $config eq 'HASH'; open(my $fh, '>', $file) or return; print {$fh} _sort_items(_dump($config)); close $fh; return 1; } sub save_plain { my $file = shift; open(my $fh, '>', $file) or return; print {$fh} @_; close $fh; return 1; }