1#!/bin/sh 2#--------------------------------------------- 3# xdg-icon-resource 4# 5# Utility script to install icons on a Linux desktop. 6# 7# Refer to the usage() function below for usage. 8# 9# Copyright 2009-2010, Fathi Boudra <fabo@freedesktop.org> 10# Copyright 2009-2010, Rex Dieter <rdieter@fedoraproject.org> 11# Copyright 2006, Kevin Krammer <kevin.krammer@gmx.at> 12# Copyright 2006, Jeremy White <jwhite@codeweavers.com> 13# 14# LICENSE: 15# 16#--------------------------------------------- 17 18manualpage() 19{ 20cat << _MANUALPAGE 21_MANUALPAGE 22} 23 24usage() 25{ 26cat << _USAGE 27_USAGE 28} 29 30#@xdg-utils-common@ 31 32# Set GTK_UPDATE_ICON_CACHE to gtk-update-icon-cache executable path or 33# to "-" if not found. 34GTK_UPDATE_ICON_CACHE= 35find_gtk_update_icon_cache() 36{ 37 [ -n "$GTK_UPDATE_ICON_CACHE" ] && return; 38 39 GTK_UPDATE_ICON_CACHE="-" 40 for x in `echo "$PATH:/opt/gnome/bin" | sed 's/:/ /g'`; do 41 DEBUG 3 "Checking $x for gtk-update-icon-cache" 42 if [ -x "$x/gtk-update-icon-cache" ] ; then 43 DEBUG 1 "Found $x/gtk-update-icon-cache" 44 GTK_UPDATE_ICON_CACHE="$x/gtk-update-icon-cache" 45 return 46 fi 47 done 48} 49 50# Start GNOME legacy workaround section 51need_dot_icon_path() 52{ 53 # GTK < 2.6 uses ~/.icons but not XDG_DATA_HOME/icons 54 # The availability of gtk-update-icon-cache is used as indication 55 # of whether the system is using GTK 2.6 or later 56 find_gtk_update_icon_cache 57 [ "$GTK_UPDATE_ICON_CACHE" != "-" ] && return 1; 58 return 0; 59} 60 61update_icon_database() 62{ 63 # Touch me, I'm dirty 64 touch "$1/.@NAME@-dummy" 65 rm -f "$1/.@NAME@-dummy" 66 67 # Don't create a cache if there wan't one already 68 if [ -f "$1/icon-theme.cache" ] ; then 69 find_gtk_update_icon_cache 70 if [ "$GTK_UPDATE_ICON_CACHE" != "-" ] ; then 71 DEBUG 1 "Running $GTK_UPDATE_ICON_CACHE -f -t \"$1\"" 72 eval '$GTK_UPDATE_ICON_CACHE -f -t "$1"'$xdg_redirect_output 73 return 74 fi 75 fi 76} 77 78[ x"$1" != x"" ] || exit_failure_syntax 79 80mode= 81action= 82update=yes 83size= 84theme=hicolor 85context=apps 86icon_file= 87icon_name= 88 89case $1 in 90 install) 91 action=install 92 ;; 93 94 uninstall) 95 action=uninstall 96 ;; 97 98 forceupdate) 99 action=forceupdate 100 ;; 101 102 *) 103 exit_failure_syntax "unknown command '$1'" 104 ;; 105esac 106 107shift 108 109vendor=true 110while [ $# -gt 0 ] ; do 111 parm="$1" 112 shift 113 114 case $parm in 115 --noupdate) 116 update=no 117 ;; 118 119 --mode) 120 if [ -z "$1" ] ; then 121 exit_failure_syntax "mode argument missing for --mode" 122 fi 123 case "$1" in 124 user) 125 mode="user" 126 ;; 127 128 system) 129 mode="system" 130 ;; 131 132 *) 133 exit_failure_syntax "unknown mode '$1'" 134 ;; 135 esac 136 shift 137 ;; 138 139 --theme) 140 if [ -z "$1" ] ; then 141 exit_failure_syntax "theme argument missing for --theme" 142 fi 143 theme="$1" 144 shift 145 ;; 146 147 --size) 148 if [ -z "$1" ] ; then 149 exit_failure_syntax "size argument missing for --size" 150 fi 151 if echo "$1" | grep '[^0-9]' > /dev/null 2> /dev/null; then 152 exit_failure_syntax "size argument must be numeric" 153 fi 154 size="$1" 155 shift 156 ;; 157 158 --context) 159 if [ -z "$1" ] ; then 160 exit_failure_syntax "context argument missing for --context" 161 fi 162 context="$1" 163 shift 164 ;; 165 166 --novendor) 167 vendor=false 168 ;; 169 170 -*) 171 exit_failure_syntax "unexpected option '$parm'" 172 ;; 173 174 *) 175 if [ -n "$icon_name" ] ; then 176 exit_failure_syntax "unexpected argument '$parm'" 177 elif [ -n "$icon_file" ] ; then 178 icon_name="$parm" 179 else 180 if [ "$action" = "install" ] ; then 181 check_input_file "$parm" 182 fi 183 icon_file="$parm" 184 fi 185 ;; 186 esac 187done 188 189# Shouldn't happen 190if [ -z "$action" ] ; then 191 exit_failure_syntax "command argument missing" 192fi 193 194# Shouldn't happen 195if [ -z "$context" ] ; then 196 exit_failure_syntax "context argument missing" 197fi 198 199if [ -n "$XDG_UTILS_INSTALL_MODE" ] ; then 200 if [ "$XDG_UTILS_INSTALL_MODE" = "system" ] ; then 201 mode="system" 202 elif [ "$XDG_UTILS_INSTALL_MODE" = "user" ] ; then 203 mode="user" 204 fi 205fi 206 207if [ -z "$mode" ] ; then 208 if [ `whoami` = "root" ] ; then 209 mode="system" 210 else 211 mode="user" 212 fi 213fi 214 215xdg_dir_name="icons/$theme" 216 217xdg_user_dir="$XDG_DATA_HOME" 218[ -n "$xdg_user_dir" ] || xdg_user_dir="$HOME/.local/share" 219xdg_user_prefix="$xdg_user_dir/icons" 220xdg_user_dir="$xdg_user_dir/$xdg_dir_name" 221 222xdg_global_dir= 223xdg_global_prefix= 224xdg_system_dirs="$XDG_DATA_DIRS" 225[ -n "$xdg_system_dirs" ] || xdg_system_dirs="/usr/local/share/:/usr/share/" 226for x in `echo "$xdg_system_dirs" | sed 's/:/ /g'`; do 227 if [ -w $x/$xdg_dir_name ] ; then 228 xdg_global_prefix="$x/icons" 229 xdg_global_dir="$x/$xdg_dir_name" 230 break 231 fi 232done 233[ -w $xdg_global_dir ] || xdg_global_dir= 234 235dot_icon_dir= 236dot_base_dir= 237if [ x"$mode" = x"user" ] ; then 238 xdg_base_dir="$xdg_user_dir" 239 #Gnome 2.8 supports ~/.icons but not XDG_DATA_HOME 240 if need_dot_icon_path ; then 241 dot_icon_dir="$HOME/.icons" 242 dot_base_dir="$dot_icon_dir/$theme" 243 fi 244else 245 xdg_base_dir="$xdg_global_dir" 246 if [ -z "$xdg_base_dir" ] ; then 247 exit_failure_operation_impossible "No writable system icon directory found." 248 fi 249fi 250 251if [ x"$action" = x"forceupdate" ] ; then 252 if [ -n "$icon_file" ] ; then 253 exit_failure_syntax "unexpected argument '$icon_file'" 254 fi 255 update_icon_database $xdg_base_dir 256 if [ -n "$dot_icon_dir" ] ; then 257 if [ -d "$dot_icon_dir/" -a ! -L "$dot_icon_dir" ] ; then 258 update_icon_database $dot_base_dir 259 fi 260 fi 261 exit_success 262fi 263 264if [ -z "$icon_file" ] ; then 265 if [ x"$action" = x"install" ] ; then 266 exit_failure_syntax "icon-file argument missing" 267 else 268 exit_failure_syntax "icon-name argument missing" 269 fi 270fi 271 272xdg_size_name= 273extension= 274 275if [ -z "$size" ] ; then 276 exit_failure_syntax "the icon size must be specified with --size" 277fi 278xdg_size_name="${size}x${size}" 279 280if [ x"$action" = x"install" ] ; then 281 case $icon_file in 282 *.xpm) 283 extension="xpm" 284 ;; 285 *.png) 286 extension="png" 287 ;; 288 *) 289 exit_failure_syntax "icon file to install must be a *.png or *.xpm file" 290 ;; 291 esac 292fi 293 294if [ -n "$icon_name" ] ; then 295 case $icon_name in 296 *.png) 297 exit_failure_syntax "icon name should not include an extension" 298 ;; 299 *.xpm) 300 exit_failure_syntax "icon name should not include an extension" 301 ;; 302 esac 303fi 304 305# Start KDE legacy workaround section 306need_kde_icon_path() 307{ 308 local path 309 path=`readlink -f "$1" 2> /dev/null` # Normalize path 310 DEBUG 2 "need_kde_icon_path $path" 311 if [ -z "$path" ] ; then 312 DEBUG 2 "need_kde_icon_path RETURN 1 (not needed, no xdg icon dir)" 313 return 1; # Not needed 314 fi 315 316 # if kde-config not found... return 0 317 kde_icon_dirs=`kde${KDE_SESSION_VERSION}-config --path icon 2> /dev/null |sed 's/:/ /g'` 318 DEBUG 3 "kde_icon_dirs: $kde_icon_dirs" 319 if [ -z "$kde_icon_dirs" ] ; then 320 DEBUG 3 "no result from kde${KDE_SESSION_VERSION}-config --path icon" 321 DEBUG 2 "need_kde_icon_path RETURN 1 (not needed, no kde icon path)" 322 return 1; # Not needed 323 fi 324 needed=0 # Needed 325 for y in $kde_icon_dirs ; do 326 x=`readlink -f "$y"` # Normalize path 327 DEBUG 3 "Normalize $y --> $x" 328 if [ -n "$x" ] ; then 329 if [ "$x" = "$path" ] ; then 330 needed=1 # Not needed 331 fi 332 if [ -w "$x" ] ; then 333 kde_global_prefix="$x" 334 # Take last writable dir 335 fi 336 fi 337 done 338 DEBUG 2 "kde_global_prefix: $kde_global_prefix" 339 [ $needed -eq "1" ] && DEBUG 2 "need_kde_icon_path RETURN $needed (not needed)" 340 [ $needed -eq "0" ] && DEBUG 2 "need_kde_icon_path RETURN $needed (needed)" 341 return $needed 342} 343 344kde_dir= 345if [ x"$mode" = x"user" ] ; then 346 xdg_dir="$xdg_base_dir/$xdg_size_name/$context" 347 #KDE 3.x doesn't support XDG_DATA_HOME for icons 348 #Check if xdg_dir prefix is listed by kde-config --path icon 349 #If not, install additional symlink to kdedir 350 if need_kde_icon_path "$xdg_user_prefix" ; then 351 kde_user_icon_dir=`kde${KDE_SESSION_VERSION}-config --path icon | cut -d ':' -f 1` 352 kde_user_dir="$kde_user_icon_dir/$theme" 353 kde_dir="$kde_user_dir/$xdg_size_name/$context" 354 fi 355 #Gnome 2.8 supports ~/.icons but not XDG_DATA_HOME 356 if [ -n "$dot_icon_dir" ] ; then 357 if [ -L "$dot_icon_dir" ] ; then 358 # Don't do anything 359 dot_icon_dir= 360 elif [ ! -d "$dot_icon_dir/" ] ; then 361 # Symlink if it doesn't exist 362 eval 'ln -s ".local/share/icons" "$dot_icon_dir"'$xdg_redirect_output 363 dot_icon_dir= 364 else 365 dot_icon_dir="$dot_icon_dir/$theme/$xdg_size_name/$context" 366 fi 367 fi 368 my_umask=077 369else 370 xdg_dir="$xdg_base_dir/$xdg_size_name/$context" 371 #KDE 3.x doesn't support XDG_DATA_DIRS for icons 372 #Check if xdg_dir prefix is listed by kde-config --path icon 373 #If not, install additional symlink to kdedir 374 if need_kde_icon_path "$xdg_global_prefix" ; then 375 kde_global_dir="$kde_global_prefix/$theme" 376 kde_dir="$kde_global_dir/$xdg_size_name/$context" 377 fi 378 my_umask=022 379fi 380# End KDE legacy workaround section 381 382# Start GNOME legacy workaround section 383need_gnome_mime= 384[ $context = "mimetypes" ] && need_gnome_mime=true 385# End GNOME legacy workaround section 386 387[ -n "$icon_name" ] || icon_name=`basename "$icon_file" | sed 's/\.[a-z][a-z][a-z]$//'` 388 389if [ "$vendor" = "true" -a "$action" = "install" -a "$context" = "apps" ] ; then 390 check_vendor_prefix "$icon_name" "icon name" 391fi 392 393icon_icon_file=`echo "$icon_file" | sed 's/\.[a-z][a-z][a-z]$/.icon/'` 394icon_icon_name="$icon_name.icon" 395 396DEBUG 1 "$action icon in $xdg_dir" 397[ $action = "install" -a -f $icon_icon_file ] && DEBUG 1 "install $icon_icon_name meta file in $xdg_dir" 398[ -n "$kde_dir" ] && DEBUG 1 "$action symlink in $kde_dir (KDE 3.x support)" 399[ -n "$need_gnome_mime" ] && DEBUG 1 "$action gnome-mime-$icon_name symlink (GNOME 2.x support)" 400[ $action = "install" -a -n "$dot_icon_dir" ] && DEBUG 1 "$action ~/.icons symlink (GNOME 2.8 support)" 401 402case $action in 403 install) 404 save_umask=`umask` 405 umask $my_umask 406 407 for icon_dir in $xdg_dir $dot_icon_dir; do 408 mkdir -p $icon_dir 409 eval 'cp "$icon_file" "$icon_dir/$icon_name.$extension"'$xdg_redirect_output 410 if [ -f "$icon_icon_file" ] ; then 411 eval 'cp "$icon_icon_file" "$icon_dir/$icon_icon_name"'$xdg_redirect_output 412 fi 413 if [ -n "$need_gnome_mime" ] ; then 414 eval 'ln -s "$icon_name.$extension" "$icon_dir/gnome-mime-$icon_name.$extension"'$xdg_redirect_output 415 fi 416 done 417 if [ -n "$kde_dir" ] ; then 418 mkdir -p $kde_dir 419 eval 'ln -s "$xdg_dir/$icon_name.$extension" "$kde_dir/$icon_name.$extension"'$xdg_redirect_output 420 fi 421 422 umask $save_umask 423 ;; 424 425 uninstall) 426 for icon_dir in $xdg_dir $dot_icon_dir; do 427 rm -f "$icon_dir/$icon_name.xpm" "$icon_dir/$icon_name.png" 428 rm -f "$icon_dir/$icon_icon_name" 429 if [ -n "$need_gnome_mime" ] ; then 430 rm -f "$icon_dir/gnome-mime-$icon_name.xpm" 431 rm -f "$icon_dir/gnome-mime-$icon_name.png" 432 fi 433 done 434 if [ -n "$kde_dir" ] ; then 435 rm -f "$kde_dir/$icon_name.xpm" "$kde_dir/$icon_name.png" 436 fi 437 438 ;; 439esac 440 441if [ x"$update" = x"yes" ] ; then 442 update_icon_database "$xdg_base_dir" 443 if [ -n "$dot_icon_dir" ] ; then 444 if [ -d "$dot_icon_dir/" -a ! -L "$dot_icon_dir" ] ; then 445 update_icon_database $dot_base_dir 446 fi 447 fi 448fi 449 450exit_success 451