Localizar sus scripts en BASH, parte 2

Esta es una continuación del artículo Cómo localizar sus scripts en BASH . En él, utilizando matrices y referencias indirectas, aprendimos cómo agregar idiomas adicionales a nuestros scripts y cambiar entre ellos.





En este artículo, compilaremos una lista de idiomas integrados y estableceremos la elección del idioma a través del menú, creando un menú de varios niveles para esto. Para evitar que el artículo se convierta en un gran fragmento de código con una descripción de cada línea, publicaré el código en sí con comentarios detallados a continuación, y aquí tocaré solo algunos puntos principales.





Creación de menú

En el último artículo, usamos un bucle for



y un operador de selección para mostrar un menú en la pantalla y seleccionar el elemento requerido case



. Obviamente, para crear un menú de varios niveles, estos pasos deberán repetirse varias veces, es decir, para cada submenú. En este caso, tendrá que volver a crear el encabezado del menú, la apariencia, etc.





Una buena manera de evitarlo: hacer for



, case



y read



en una función separada (llamarlo prints



), y luego simplemente lo pasaremos a los parámetros requeridos. Todos los scripts que se ejecutarán cuando se seleccionen ciertos elementos del menú también se transferirán a las funciones correspondientes.





Entonces, para agregar una nueva acción al script:





  • agregar palabras y frases a la matriz de idiomas





  • en la matriz con el menú principal o adicional, inserte el elemento correspondiente y el comando para llamar a la función





  • agregar una función con el fragmento de código requerido





Primero, creemos un menú principal, que aparecerá inmediatamente en la pantalla cuando se inicie el script:





menu0=("${lng[3]};main" "${lng[4]};gitadd" "${lng[5]};gitinit" "${lng[2]};options" "${lng[1]};exit")
      
      



: , ;



- , . , . , , .





main



:





main() {
    #    
    local menu0=("${lng[3]};main" "${lng[4]};gitadd" "${lng[5]};gitinit" "${lng[2]};options" "${lng[1]};exit")

    while true ; do

        #       
        #    ,     
        prints "menu0[@]" "${msg[1]}"
    done
}

main
      
      



, options



:





options() {
    local menu1=("${lng[2]};options" "${lng[7]} [$langset];langmenu" "${lng[1]};exit")
    prints "menu1[@]" "${msg[1]}"
      
      



prints



, . , . cut



:





if [[ "$1" == "text" ]] ; then
    #     
    echo "$2" | cut -d ";" -f 1
    return
elif [[ "$1" == "command" ]] ; then
    #    
    echo "$2" | cut -d ";" -f 2
    return
fi
      
      



, , ${prints "text" "${menu[0]}"}



, - .





, : . colors



. ANSI escape ( echo -e



) 256 .





, , pwds



, . , .





, .





prints



. , :





local menu=("${!1}")
      
      



- . , , 1 :





pwds
colors "title" "---$(prints "text" "${menu[0]}")---"
      
      



for



,



, read



case



:





for (( op=1; op < "${#menu[@]}"; op++ )); do
	colors "item" "$op ) $(prints "text" "${menu[$op]}")"
done
echo ----------
read -s -n1 -p "$(colors "item" "$2: ")" item	
case $item in
	[1-$((${#menu[@]}-1))] ) 
		#      
		colors "ok" "[$item]->: $(prints "text" "${menu[$item]}")"
		#     
		$(prints "command" "${menu[$item]}") ;;
		#    [q]
		"q" ) echo; exit;;
		#          
		* ) colors "err" "[$item]->: ${msg[2]}"; sleep 2 ;;
esac
      
      



Así es como se verá este menú.

. , .





, , , . langmenu



.





, . . , sed



language_



. language_ru



ru



:





# [-r] -    
# [-n] -   ,    
local lng_sfx=($(sed -r -n "s/^\s?+language_(\w+)=.*/\1/p" "${0}"))
      
      



, , prints



. . langmenu



:





langmenu(){
    local lng_sfx=($(sed -r -n "s/^\s?+language_(\w+)=.*/\1/p" "${0}"))
    local menu2=("${lng[7]};langmenu")

    for a in ${lng_sfx[@]} ; do
        local d="language_$a[@]"; d=("${!d}")
        menu2+=("$d;languages set $a")
    done

    menu2+=("${lng[1]};exit")
    prints "menu2[@]" "${msg[6]}"
}
      
      



:









  1. . , 0



    ( ). : , ;



    , , languages



    .



    "English;languages set en"



    , set en



    - languages



    .









  2. prints



    . ,





Menú de selección de idioma

. sed



-i



-r



, -i



- () , -r



- .





: , langset=



langset=



:





sed -i -r "0,/^\s?+langset=/s/langset=[\"\']?\w*[\"\']?/langset=\"$langset\"/" "${0}"
exit
      
      



prints



. , , case



languages



, set



. languages



, . :





languages
if [ "$1" == "set" ] ; then
	#      
	langset="$2"
	local df="language_$langset"
	echo
	#       ,  
	colors "ok" "${msg[7]} ${!df}. ${msg[8]}"
	#   
	languages
	#       ,  
	colors "ok" "${msg[7]} ${lng[0]}. ${msg[8]}"
	echo
	#   langset=     
	sed -i -r "0,/^\s?+langset=/s/langset=[\"\']?\w*[\"\']?/langset=\"$langset\"/" "${0}"
	exit 
fi
      
      



Configurar el idioma

En este artículo y en el anterior , creamos una plantilla que puede utilizar para escribir sus propios scripts con la capacidad de mostrar menús y mensajes en pantalla en diferentes idiomas. En este caso, la secuencia de comandos consta de un archivo y para agregar un nuevo idioma, basta con soltar la matriz con las palabras al principio de la secuencia de comandos y agregar cualquier acción: cree una función y regístrela en el menú.





Gracias por leer hasta el final.





A continuación se adjunta todo el código con comentarios.





Todo el código
#!/bin/bash
#  
langset="ru"

#   
language_en=( "English" "Quit" "Options" "Main menu" "Git: add ALL files/commit" "Git init" "Change language" "Language selection" )
message_en=( "English" "Select item" "Wrong! This item does not exist" "Added all files" "Enter you commit" "Changes recorded" "Select a language" "The language has been changed to" "Start the program again" "Repository not found\nPlease, select Git init pepository" )

language_ru=( "" "" "" " " "Git:   /" "" "" " " )
message_ru=( "" " " "!    " "  " "  " " " " " "  " "  " "  \n,  ,  Git init" )

language_de=( "Deutsch" )
message_de=( "Deutsch" "" "" "" "" "" "" "" "Starten Sie das Programm neu" )

language_cn=( "中文" "出口" "设置" "主菜单")
message_cn=( "中文" "选择项目" "" "" "" "" "选择语言" "语言已改为" "重新启动程序" )

# Settings section

languages() {
	#        
	#      
	lng="language_$langset[@]"; lng=("${!lng}")
	msg="message_$langset[@]"; msg=("${!msg}")

	#       
	for b in ${!language_en[@]} ${!message_en[@]} ; do
	
		if [[ ! ${lng[$b]} ]] ; then
			lng[$b]=${language_en[$b]}
		fi
		if [[ ! ${msg[$b]} ]] ; then
			msg[$b]=${message_en[$b]}
		fi
	done

	#   
	if [ "$1" == "set" ] ; then
		
		#      
		langset="$2"

		local df="language_$langset"
		
		#        ,
		#   ,   
		echo
		colors "ok" "${msg[7]} ${!df}. ${msg[8]}"
		
		#   
		languages
		
		#        
		#   ,   
		colors "ok" "${msg[7]} ${lng[0]}. ${msg[8]}"
		echo
		#      
		#   langset=     
		# [-r] -    
		# [-i] -  
		# [0,] -   
		sed -i -r "0,/^\s?+langset=/s/langset=[\"\']?\w*[\"\']?/langset=\"$langset\"/" "${0}"
		exit 
	fi
}

#   
languages


colors() {
	#     .   ,
	#      ,   
	#  [48] -    , [38] - 
	# [5] - 8-   (0-255), [1] - ,
	# [22] -  , [0] -   
	case "$1" in
		# : - ()
		"tm" ) echo -e "\e[48;5;256;38;5;34;22m$2\e[0m" ;;
		# : -, :   (  )
		"pt" ) echo -e "\e[48;5;24;38;5;15;1m$2\e[0m" ;;
		# : -  ( )
		"cf" ) echo -e "\e[48;5;256;38;5;226;1m$2\e[0m" ;;
		# : -  (  )
		"ok" ) echo -e "\e[48;5;256;38;5;34;1m$2\e[0m" ;;
		# :   ( )
		"err" ) echo -e "\e[48;5;256;38;5;160;1m$2\e[0m" ;;
		# : - ( )
		"title" ) echo -e "\e[48;5;256;38;5;226;22m$2\e[0m" ;;
		# :  (    )
		"item" ) echo -e "\e[48;5;256;38;5;15;22m$2\e[0m" ;;
	esac	
}

pwds() {
	#        
	echo 
	echo ----------
	echo "$(colors 'tm' "[$(date +"%T")]") $(colors 'pt' "${PWD%/*}"/)$(colors 'cf'  "$(basename   "$PWD")")"
	echo ----------
}

prints() {
	#     
	
	#       ,    [;]
	if [[ "$1" == "text" ]] ; then
		echo "$2" | cut -d ";" -f 1
		return
	elif [[ "$1" == "command" ]] ; then
		echo "$2" | cut -d ";" -f 2
		return
	fi
	
	#    ,     
	local menu=("${!1}")
	
	#     
	pwds
		
	#     ,  
	#    1   	
	colors "title" "---$(prints "text" "${menu[0]}")---"
	
	#    
	for (( op=1; op < "${#menu[@]}"; op++ )); do
		
		#     ,  
		#      
		colors "item" "$op ) $(prints "text" "${menu[$op]}")"
	done
	
	echo ----------
	
	#   ,    
	read -s -n1 -p "$(colors "item" "$2: ")" item	
	
	#  
	case $item in
		#    1      1 (     0)
		#        
		#      
		[1-$((${#menu[@]}-1))] ) colors "ok" "[$item]->: $(prints "text" "${menu[$item]}")"
		
		#     ,   
		#      
		$(prints "command" "${menu[$item]}") ;;
		
		#    [q]
		"q" ) echo; exit;;
		
		#          
		* ) colors "err" "[$item]->: ${msg[2]}"; sleep 2 ;;
	esac	
}


# Application section

gitinit() {
	#  :    [git init]
	git init
}

gitadd() {
	#  :    [git add] -   
	git add .
	#  .       [0]
	#          
	if [[ "$?" != "0" ]] ; then
		colors "err" "${msg[9]}" 
		sleep 1
		return 1 
	fi
	
	echo "${msg[3]} ..."
	#    
	read -p "$(colors "item" "${msg[4]}: ")" comm
	git commit -m "$comm"
	#      
	colors "ok" "${msg[5]}"
}


# Menu section

langmenu() {
	#    
	#    ,    
	#    [language_*]      
	# [-r] -    
	# [-n] -   ,    
	local lng_sfx=($(sed -r -n "s/^\s?+language_(\w+)=.*/\1/p" "${0}"))
	
	#     	
	local menu2=("${lng[7]};langmenu")
	
	#       ,      ,
	#    0     (   )
	for a in ${lng_sfx[@]} ; do
		local d="language_$a[@]"; d=("${!d}")
		
		#       
		#         ,  
		#  [;],   ,    
		# [languages]       .   
		#  ["English;languages set en"],  [set en] -    [languages]
		menu2+=("$d;languages set $a")
	done
	#     
	menu2+=("${lng[1]};exit")
	
	#           
	#    ,     
	prints "menu2[@]" "${msg[6]}"
}

options() {
	#     
	#           ,
	#    [;],   ,     
	local menu1=("${lng[2]};options" "${lng[7]} [$langset];langmenu" "${lng[1]};exit")
	
	#       
	#    ,     
	prints "menu1[@]" "${msg[1]}"
}

main() {
	#    
	#           ,
	#    [;],   ,     
	#     ,  ,   -       
	#   ,              
	local menu0=("${lng[3]};main" "${lng[4]};gitadd" "${lng[5]};gitinit" "${lng[2]};options" "${lng[1]};exit")

	
	while true ; do
		#       
		#    ,     
		prints "menu0[@]" "${msg[1]}"
	done
}

main

exit 0
      
      










All Articles