diff options
Diffstat (limited to 'perl-install/lang.pm')
-rw-r--r-- | perl-install/lang.pm | 742 |
1 files changed, 530 insertions, 212 deletions
diff --git a/perl-install/lang.pm b/perl-install/lang.pm index 73e4a76d5..a3c8aa7ea 100644 --- a/perl-install/lang.pm +++ b/perl-install/lang.pm @@ -1,4 +1,4 @@ -package lang; # $Id$ +package lang; use diagnostics; use strict; @@ -6,25 +6,70 @@ use common; use utf8; use log; -#- key: lang name (locale name for some (~5) special cases needing -#- extra distinctions) -#- [0]: lang name in english -#- [1]: transliterated locale name in the locale name (used for sorting) -#- [2]: default locale name to use for that language if there is not -#- an existing locale for the combination language+country choosen -#- [3]: geographic groups that this language belongs to (for displaying -#- in the menu grouped in smaller lists), 1=Europe, 2=Asia, 3=Africa, -#- 4=Oceania&Pacific, 5=America (if you wonder, it's the order -#- used in the olympic flag) -#- [4]: special value for LANGUAGE variable (if different of the default -#- of 'll_CC:ll_DD:ll' (ll_CC: locale (if exist) resulting of the -#- combination of chosen lang (ll) and country (CC), ll_DD: the -#- default locale shown here (field [2]) and ll: the language (the key)) +=head1 SYNOPSYS + +B<lang> enables to manipulate the system or the user locale settings. + +=head1 Data structures & functions + +=head2 Languages + +=over + +=item our %lang + +The key is the lang name (locale name for some (~5) special cases needing +extra distinctions) + +The fields are: + +=over 4 + +=item 0 lang name in English + +=item 1 transliterated locale name in the locale name (used for sorting) + +=item 2 default locale name to use for that language if there is not +an existing locale for the combination language+country chosen + +=item 3 geographic groups that this language belongs to (for displaying +in the menu grouped in smaller lists): + +=over 4 + +=item 1=Europe, + +=item 2=Asia, + +=item 3=Africa, + +=item 4=Oceania & Pacific, + +=item 5=America + +=back + +If you wonder, it's the order used in the Olympic flag... + +=item 4 special value for LANGUAGE variable (if different of the default +of 'll_CC:ll_DD:ll' (ll_CC: locale (if exist) resulting of the +combination of chosen lang (ll) and country (CC), ll_DD: the +default locale shown here (field [2]) and ll: the language (the key)) + +=back + +Example: + + C<< 'fr' => [ 'French', 'Francais', 'fr_FR', '1 345', 'iso-8859-15' ], >> + +=cut + our %langs = ( 'af' => [ 'Afrikaans', 'Afrikaans', 'af_ZA', ' 3 ', 'iso-8859-1' ], 'am' => [ 'Amharic', 'ZZ emarNa', 'am_ET', ' 3 ', 'utf_ethi' ], 'ar' => [ 'Arabic', 'AA Arabic', 'ar_EG', ' 23 ', 'utf_ar' ], 'as' => [ 'Assamese', 'ZZ Assamese', 'as_IN', ' 2 ', 'utf_beng' ], +'ast' => [ 'Asturian', 'Asturianu', 'ast_ES', ' 1 ', 'unicode' ], 'az' => [ 'Azeri (Latin)', 'Azerbaycanca', 'az_AZ', ' 2 ', 'utf_az' ], 'be' => [ 'Belarussian', 'Belaruskaya', 'be_BY', '1 ', 'utf_cyr1' ], 'ber' => [ 'Berber', 'ZZ Tamazight', 'ber_MA', ' 3 ', 'utf_tfng', 'ber_MA:ber:fr' ], @@ -47,6 +92,7 @@ our %langs = ( 'en_GB' => [ 'English', 'English', 'en_GB', '123 5', 'iso-8859-15' ], 'en_IE' => [ 'English (Ireland)', 'English (Ireland)', 'en_IE', '1 ', 'iso-8859-15', 'en_IE:en_GB:en' ], 'en_NZ' => [ 'English (New-Zealand)', 'English (NZ)', 'en_NZ', ' 4 ', 'iso-8859-1', 'en_NZ:en_AU:en_GB:en' ], +'en_ZA' => [ 'English (South Africa)', 'English (ZA)', 'en_ZA', ' 3 ', 'iso-8859-1', 'en_ZA:en_GB:en' ], 'en_US' => [ 'English (American)', 'English (American)', 'en_US', ' 5', 'C' ], 'eo' => [ 'Esperanto', 'Esperanto', 'eo_XX', '12345', 'unicode' ], 'es' => [ 'Spanish', 'Espanol', 'es_ES', '1 3 5', 'iso-8859-15' ], @@ -111,13 +157,13 @@ our %langs = ( 'ms' => [ 'Malay', 'Bahasa Melayu', 'ms_MY', ' 2 ', 'utf_lat1' ], 'mt' => [ 'Maltese', 'Maltin', 'mt_MT', '1 3 ', 'unicode' ], #- "my_MM" not yet done, using "en_US" for now -'my' => [ 'Burmese', 'ZZ Bamaca', 'en_US', ' 2 ', 'utf_mymr', 'my_MM:my' ], +'my' => [ 'Burmese', 'ZZ Bamaca', 'my', ' 2 ', 'utf_mymr', 'my_MM:my' ], 'nb' => [ 'Norwegian Bokmaal', 'Norsk, Bokmal', 'nb_NO', '1 ', 'iso-8859-15', 'nb:no' ], 'nds' => [ 'Low Saxon', 'Platduutsch', 'nds_DE', '1 ', 'utf_lat1', 'nds_DE:nds' ], 'ne' => [ 'Nepali', 'ZZ Nepali', 'ne_NP', ' 2 ', 'utf_deva' ], 'nl' => [ 'Dutch', 'Nederlands', 'nl_NL', '1 ', 'iso-8859-15' ], 'nn' => [ 'Norwegian Nynorsk', 'Norsk, Nynorsk', 'nn_NO', '1 ', 'iso-8859-15', 'nn:no@nynorsk:no_NY:no:nb' ], -'nr' => [ 'Ndebele', 'IsiNdebele', 'nr_ZA', ' 3 ', 'utf_lat1', 'nr:en_ZA' ], +'nr' => [ 'Ndebele', 'Ndebele', 'nr_ZA', ' 3 ', 'utf_lat1', 'nr:en_ZA' ], 'nso' => [ 'Northern Sotho', 'Sesotho sa Leboa', 'nso_ZA', ' 3 ', 'utf_lat1', 'st:nso:en_ZA' ], 'oc' => [ 'Occitan', 'Occitan', 'oc_FR', '1 ', 'utf_lat1', 'oc:fr_FR:fr' ], 'pa_IN' => [ 'Punjabi (gurmukhi)', 'ZZ Punjabi', 'pa_IN', ' 2 ', 'utf_guru' ], @@ -137,7 +183,7 @@ our %langs = ( 'sq' => [ 'Albanian', 'Shqip', 'sq_AL', '1 ', 'iso-8859-1' ], 'sr' => [ 'Serbian Cyrillic', 'Srpska', 'sr_CS', '1 ', 'utf_cyr1', 'sp:sr' ], #- "sh" comes first, because otherwise, due to the way glibc does language -#- fallback, if "sr@Latn" is not there but a "sr" (whichs uses cyrillic) +#- fallback, if "sr@Latn" is not there but a "sr" (which uses cyrillic) #- is there, "sh" will never be used. 'sr@Latn' => [ 'Serbian Latin', 'Srpska', 'sr_CS', '1 ', 'unicode', 'sh:sr@Latn' ], 'ss' => [ 'Swati', 'SiSwati', 'ss_ZA', ' 3 ', 'utf_lat1', 'ss:en_ZA' ], @@ -163,12 +209,12 @@ our %langs = ( #- locale "wen_DE" not done yet, using "de_DE" instead #- wen disabled until we have a perl-install/pixmaps/langs/lang-wen.png for it #'wen' => [ 'Sorbian', 'Sorbian', 'de_DE', '1 ', 'utf_lat1', 'wen' ], -'xh' => [ 'Xhosa', 'IsiXhosa', 'xh_ZA', ' 3 ', 'utf_lat1', 'xh:en_ZA' ], +'xh' => [ 'Xhosa', 'Xhosa', 'xh_ZA', ' 3 ', 'utf_lat1', 'xh:en_ZA' ], 'yi' => [ 'Yiddish', 'AA Yidish', 'yi_US', '1 ', 'utf_he' ], 'yo' => [ 'Yoruba', 'Yoruba', 'yo_NG', ' 3 ', 'utf_yo', 'yo:en_NG' ], 'zh_CN' => [ 'Chinese Simplified', 'ZZ ZhongWen', 'zh_CN', ' 2 ', 'gb2312', 'zh_CN.GBK:zh_CN.GB2312:zh_CN:zh' ], 'zh_TW' => [ 'Chinese Traditional', 'ZZ ZhongWen', 'zh_TW', ' 2 ', 'Big5', 'zh_TW.Big5:zh_TW:zh_HK:zh' ], -'zu' => [ 'Zulu', 'IsiZulu', 'zu_ZA', ' 3 ', 'utf_lat1', 'xh:en_ZA' ], +'zu' => [ 'Zulu', 'Zulu', 'zu_ZA', ' 3 ', 'utf_lat1', 'xh:en_ZA' ], ); sub l2name { exists $langs{$_[0]} && $langs{$_[0]}[0] } sub l2transliterated { exists $langs{$_[0]} && $langs{$_[0]}[1] } @@ -180,10 +226,18 @@ sub l2location { } sub l2charset { exists $langs{$_[0]} && $langs{$_[0]}[4] } sub l2language { exists $langs{$_[0]} && $langs{$_[0]}[5] } + +sub is_locale_installed { + my ($locale) = @_; + my @ctypes = glob "/usr/share/locale/" . $locale . "{,.*}/LC_CTYPE"; + foreach my $ctype (@ctypes) { -e $ctype && return 1 } + 0; +} + sub list_langs { my (%options) = @_; my @l = keys %langs; - $options{exclude_non_installed} ? grep { -e "/usr/share/locale/" . l2locale($_) . "/LC_CTYPE" } @l : @l; + $options{exclude_non_installed} ? grep { is_locale_installed(l2locale($_)) } @l : @l; } sub text_direction_rtl() { @@ -193,19 +247,56 @@ sub text_direction_rtl() { N("default:LTR") eq "default:RTL"; } +=back + +=head2 Countries + +=over + +=item my %countries; + +The key is the ISO 639-1 country name code (that should be YY in xx_YY locale). + +The fields are: + +=over 4 + +=item 0: country name in natural language + +=item 1: default locale for that country + +=item 2: geographic groups that this country belongs to (for displaying +in the menu grouped in smaller lists): + +=over 4 + +=item *1=Europe, + +=item *2=Asia, + +=item *3=Africa, + +=item 4=Oceania & Pacific, + +=item 5=America + +=back + +If you wonder, it's the order used in the Olympic flag. + +=back + +Note: for countries for which a glibc locale do not exist (yet) I tried to +put a locale that makes sense; and a '#' at the end of the line to show +the locale is not the "correct" one. 'en_US' is used when no good choice +is available. + +Example: + + C<< 'FR' => [ N_("France"), 'fr_FR', '1' ], >> + +=cut -#- key: country name (that should be YY in xx_YY locale) -#- [0]: country name in natural language -#- [1]: default locale for that country -#- [2]: geographic groups that this country belongs to (for displaying -#- in the menu grouped in smaller lists), 1=Europe, 2=Asia, 3=Africa, -#- 4=Oceania&Pacific, 5=America (if you wonder, it's the order -#- used in the olympic flag) -#- -#- Note: for countries for which a glibc locale do not exist (yet) I tried to -#- put a locale that makes sense; and a '#' at the end of the line to show -#- the locale is not the "correct" one. 'en_US' is used when no good choice -#- is available. my %countries = ( 'AD' => [ N_("Andorra"), 'ca_AD', '1' ], 'AE' => [ N_("United Arab Emirates"), 'ar_AE', '2' ], @@ -446,17 +537,52 @@ my %countries = ( 'ZM' => [ N_("Zambia"), 'en_US', '3' ], # 'ZW' => [ N_("Zimbabwe"), 'en_ZW', '5' ], ); + +=item c2name($country_code) + +Returns the translated name for $country_code. + +=cut + sub c2name { exists $countries{$_[0]} && translate($countries{$_[0]}[0]) } + +=item c2locale($country_code) + +Returns default locale for that $country_code. + +=cut + sub c2locale { exists $countries{$_[0]} && $countries{$_[0]}[1] } -sub list_countries { - my (%_options) = @_; + +=item list_countries() + +Returns the full list of countries. + +=cut + +sub list_countries() { keys %countries; } -#- this list is built with the following command on the compile cluster: -#- rpm -qpl /cooker/RPMS/release/locales-* | grep LC_CTYPE | grep '\.UTF-8' | cut -d'/' -f5 | sed 's/.UTF-8//' | sort | tr '\n' ' ' ; echo -our @locales = qw(aa_DJ aa_ER aa_ER@saaho aa_ET af_ZA am_ET an_ES ar_AE ar_BH ar_DZ ar_EG ar_IN ar_IQ ar_JO ar_KW ar_LB ar_LY ar_MA ar_OM ar_QA ar_SA ar_SD ar_SY ar_TN ar_YE as_IN az_AZ be_BY ber_DZ ber_MA bg_BG bn_BD bn_IN br_FR bs_BA byn_ER ca_AD ca_ES ca_FR ca_IT cs_CZ cy_GB da_DK de_AT de_BE de_CH de_DE de_LU dz_BT el_CY el_GR en_AU en_BE en_BW en_CA en_DK en_GB en_HK en_IE en_IN en_NG en_NZ en_PH en_SG en_US en_ZA en_ZW eo_XX es_AR es_BO es_CL es_CO es_CR es_DO es_EC es_ES es_GT es_HN es_MX es_NI es_PA es_PE es_PR es_PY es_SV es_US es_UY es_VE et_EE eu_ES fa_IR fi_FI fil_PH fo_FO fr_BE fr_CA fr_CH fr_FR fr_LU fur_IT fy_DE fy_NL ga_IE gd_GB gez_ER gez_ER@abegede gez_ET gez_ET@abegede gl_ES gu_IN gv_GB ha_NG he_IL hi_IN hr_HR hsb_DE hu_HU hy_AM id_ID ig_NG ik_CA is_IS it_CH it_IT iu_CA ja_JP ka_GE kk_KZ kl_GL km_KH kn_IN ko_KR ku_TR kw_GB ky_KG lg_UG li_BE li_NL lo_LA lt_LT lv_LV mg_MG mi_NZ mk_MK ml_IN mn_MN mr_IN ms_MY mt_MT nb_NO nds_DE@traditional ne_NP nl_BE nl_NL nn_NO no_NO nr_ZA nso_ZA oc_FR om_ET om_KE pa_IN pap_AN pa_PK ph_PH pl_PL pt_BR pt_PT ro_RO ru_RU ru_UA rw_RW sc_IT se_NO sid_ET si_LK sk_SK sl_SI so_DJ so_ET so_KE so_SO sq_AL sr_ME sr_RS sr_RS@latin ss_ZA st_ZA sv_FI sv_SE sw_XX ta_IN te_IN tg_TJ th_TH ti_ER ti_ET tig_ER tk_TM tl_PH tn_ZA tr_CY tr_TR ts_ZA tt_RU ug_CN uk_UA ur_PK uz_UZ uz_UZ@cyrillic ve_ZA vi_VN wa_BE wal_ET xh_ZA yi_US yo_NG zh_CN zh_HK zh_SG zh_TW zu_ZA); - +=back + +=head2 Locales + +=over + +=item our @locales; + +The list of locales supported by glibc. + +=cut + +#- this list is built with the following command: +#- urpmf LC_CTYPE | grep -E '/usr/share/locale/[a-z]' | cut -d'/' -f5 | sed 's/\.\(UTF-8\|ARM\|EUC\|GB.\|ISO\|KOI\|TCVN\).*\|\@\(euro\|iqtelif.*\)//' | sort -u | tr '\n' ' ';echo +our @locales = qw(aa_DJ aa_ER aa_ER@saaho aa_ET af_ZA ak_GH am_ET an_ES anp_IN ar_AE ar_BH ar_DZ ar_EG ar_IN ar_IQ ar_JO ar_KW ar_LB ar_LY ar_MA ar_OM ar_QA ar_SA ar_SD ar_SS ar_SY ar_TN ar_YE as_IN ast_ES ayc_PE az_AZ be_BY be_BY@latin bem_ZM ber_DZ ber_MA bg_BG bho_IN bn_BD bn_IN bo_CN bo_IN br_FR brx_IN bs_BA byn_ER ca_AD ca_ES ca_FR ca_IT cmn_TW crh_UA csb_PL cs_CZ cv_RU cy_GB da_DK de_AT de_BE de_CH de_DE de_LU doi_IN dv_MV dz_BT el_CY el_GR en_AG en_AU en_BE en_BW en_CA en_DK en_GB en_HK en_IE en_IN en_NG en_NZ en_PH en_SG en_US en_ZA en_ZM en_ZW eo_XX es_AR es_BO es_CL es_CO es_CR es_CU es_DO es_EC es_ES es_GT es_HN es_MX es_NI es_PA es_PE es_PR es_PY es_SV es@tradicional es_US es_UY es_VE et_EE eu_ES fa_IR ff_SN fi_FI fil_PH fo_FO fr_BE fr_CA fr_CH fr_FR fr_LU fur_IT fy_DE fy_NL ga_IE gd_GB gez_ER gez_ER@abegede gez_ET gez_ET@abegede gl_ES gu_IN gv_GB hak_TW ha_NG he_IL hi_IN hne_IN hr_HR hsb_DE ht_HT hu_HU hy_AM ia_FR id_ID ig_NG ik_CA is_IS it_CH it_IT iu_CA iw_IL ja_JP ka_GE kk_KZ kl_GL km_KH kn_IN kok_IN ko_KR ks_IN ks_IN@devanagari ku_TR kw_GB ky_KG lb_LU lg_UG li_BE lij_IT li_NL lo_LA lt_LT lv_LV lzh_TW mag_IN mai_IN mg_MG mhr_RU mi_NZ mk_MK ml_IN mni_IN mn_MN mr_IN ms_MY mt_MT my_MM nan_TW nan_TW@latin nb_NO nds_DE nds_DE@traditional nds_NL ne_NP nhn_MX niu_NU niu_NZ nl_AW nl_BE nl_NL nn_NO nr_ZA nso_ZA oc_FR om_ET om_KE or_IN os_RU pa_IN pap_AN pap_AW pap_CW pa_PK pl_PL ps_AF pt_BR pt_PT quz_PE ro_RO ru_RU ru_UA rw_RW sa_IN sat_IN sc_IT sd_IN sd_IN@devanagari se_NO shs_CA sid_ET si_LK sk_SK sl_SI so_DJ so_ET so_KE so_SO sq_AL sq_MK sr_ME sr_RS sr_RS@latin ss_ZA st_ZA sv_FI sv_SE sw_KE sw_TZ sw_XX szl_PL ta_IN ta_LK te_IN tg_TJ the_NP th_TH ti_ER ti_ET tig_ER tk_TM tl_PH tn_ZA tr_CY tr_TR ts_ZA tt_RU ug_CN uk_UA unm_US ur_IN ur_PK uz_UZ uz_UZ@cyrillic ve_ZA vi_VN wa_BE wae_CH wal_ET wo_SN xh_ZA yi_US yo_NG yue_HK zh_CN zh_HK zh_SG zh_TW zu_ZA); + +# (cg) Taken from systemd/src/locale/localed.c +my @locale_conf_fields = qw(LANG LANGUAGE LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT LC_IDENTIFICATION); + sub standard_locale { my ($lang, $country, $prefer_lang) = @_; @@ -484,6 +610,13 @@ sub force_lang_charset { analysed_to_lang($h); } +=item analysed_to_lang($h) + +The reverse of analyse_locale_name($lang), it takes a hash ref and returns +the standard ll_CC.cc@VV + +=cut + sub analysed_to_lang { my ($h) = @_; $h->{main} . '_' . $h->{country} . @@ -491,12 +624,40 @@ sub analysed_to_lang { ($h->{variant} ? '@' . $h->{variant} : ''); } +=item analyse_locale_name($lang) + +Analyse a ll_CC.cc@VV locale and return a hash ref containing: + +=over 4 + +=item * main (langage code) + +=item * country code + +=item * charset + +=item * variant + +=back + +=cut + sub analyse_locale_name { my ($lang) = @_; $lang =~ /^(.*?) (?:_(.*?))? (?:\.(.*?))? (?:\@(.*?))? $/x && { main => $1, country => $2, charset => $3, variant => $4 }; } +=item locale_to_main_locale($lang) + +=cut + +=item locale_to_main_locale($lang) + +Returns the locale code from a ll_LL representation. + +=cut + sub locale_to_main_locale { my ($lang) = @_; lc(analyse_locale_name($lang)->{main}); @@ -526,7 +687,7 @@ sub countries_to_locales { my $may_add = sub { my ($locale, $country) = @_; if ($options{exclude_non_installed}) { - -e "/usr/share/locale/$locale/LC_CTYPE" or return; + is_locale_installed($locale) or return; } my $h = analyse_locale_name($locale) or internal_error(); push @{$country2locales{$country || $h->{country}}}, $h; @@ -544,56 +705,105 @@ sub countries_to_locales { } #------------------------------------------------------------- -# -# IM configuration hash tables -# -# in order to configure an IM, one has to: -# - put generic configuration in %IM_config - - -# This set generic IM fields. -my @IM_i18n_fields = ( - 'XMODIFIERS', -#- is the environnement variable used by the X11 XIM protocol -#- it is of the form XIMODIFIERS="@im=foo" - 'XIM', -#- is used by some programs, it usually is the like XIMODIFIERS -#- with the "@im=" part stripped - 'GTK_IM_MODULE', -#- the module to use for Gtk programs ("xim" to use an X11 -#- XIM server; or a a native gtk module if exists) - 'XIM_PROGRAM', -#- the XIM program to run (usually the same as XIM value, but -#- in some cases different, particularly if parameters are needed; - 'QT_IM_MODULE', -#- the module to use for Qt programs ("xim" to use an X11 -#- XIM server; or a Qt plugin if exists) -); +=back + +=head2 Input Methods (IM) + +Various hash tables enables to configure IMs. + +=over + +=item my @IM_i18n_fields; + +This set generic IM fields: + +=over 4 + +=item * B<XMODIFIERS>: is the environnement variable used by the X11 XIM protocol +it is of the form XIMODIFIERS="@im=foo" + +=item * B<XIM>: is used by some programs, it usually is the like XIMODIFIERS +with the "@im=" part stripped + +=item * B<GTK_IM_MODULE>: the module to use for Gtk programs ("xim" to use an X11 +XIM server; or a a native gtk module if exists) + +=item * B<XIM_PROGRAM>: the XIM program to run (usually the same as XIM value, but +in some cases different, particularly if parameters are needed; + +=item * B<QT_IM_MODULE>: the module to use for Qt programs ("xim" to use an X11 +XIM server; or a Qt plugin if exists) + +=back + +=cut + +my @IM_i18n_fields = qw(XMODIFIERS XIM GTK_IM_MODULE XIM_PROGRAM QT_IM_MODULE); + +my $is_plasma; + +=item my %IM_config; + +In order to configure an IM, one has to put generic configuration here. +Fields are : + +=over 4 + +=item * B<GTK_IM_MODULE>: the Gtk+ IM module to use + +=item * B<QT_IM_MODULE>: the Qt IM module to use + +=item * B<XIM>: + +=item * B<XIM_PROGRAM>: the XIM program to use + +=item * B<XMODIFIERS>: the X Modifiers (see X11 config), eg: C<'@im=gcin'>, + +See above for those 5 parameters. + +=item * B<default_for_lang>: the language codes for which it's the default IM +=item * B<langs>: 'zh', + +=item * B<packages:> a hash ref that contains subroutine references: + +=over 4 + +=item * B<generic>: packages that must be installed for all languages + +=item * B<common>: packages that are shared between per language & generic packages -my ($is_kde3, $is_kde4); +=item * eventually several B<code_lang> returning per language packages + +=back + +The I<packages> field must be kept in sync with meta-task's C<rpmsrate-raw>, especially for the per language package selection! + +The actual packages list will consist of: + +=over 4 + +=item * either per language package list or I<generic> list + +=item * plus the packages returned by I<common> + +=back + +=back + +=cut -# keep the 'packages' field in sync with share/rpmsrate: my %IM_config = ( - chinput => { - GTK_IM_MODULE => 'xim', - XIM => 'chinput', - XMODIFIERS => '@im=Chinput', - XIM_PROGRAM => { - 'zh_CN' => 'chinput -gb', - 'en_SG' => 'chinput -gb', - 'zh_HK' => 'chinput -big5', - 'zh_TW' => 'chinput -big5', - }, - langs => 'zh', - packages => { generic => sub { 'miniChinput' } }, - }, fcitx => { - GTK_IM_MODULE => 'xim', + GTK_IM_MODULE => 'fcitx', XIM => 'fcitx', XIM_PROGRAM => 'fcitx', XMODIFIERS => '@im=fcitx', langs => 'zh', + packages => { + common => sub { if_($is_plasma, 'fcitx-qt5') }, + generic => sub { qw(fcitx) }, + }, }, gcin => { GTK_IM_MODULE => 'gcin', @@ -602,10 +812,21 @@ my %IM_config = XMODIFIERS => '@im=gcin', langs => 'zh', packages => { - common => sub { if_($is_kde3, 'gcin-qt3'), if_($is_kde4, 'gcin-qt4') }, + common => sub { if_($is_plasma, 'gcin-qt5') }, generic => sub { qw(gcin) }, }, }, + hime => { + GTK_IM_MODULE => 'hime', + XIM => 'hime', + XIM_PROGRAM => 'hime', + XMODIFIERS => '@im=hime', + langs => 'zh', + packages => { + common => sub { if_($is_plasma, 'hime-qt5') }, + generic => sub { qw(hime) }, + }, + }, 'im-ja' => { GTK_IM_MODULE => 'im-ja', QT_IM_MODULE => 'xim', @@ -615,14 +836,6 @@ my %IM_config = langs => 'ja', }, - kinput2 => { - GTK_IM_MODULE => 'xim', - XIM => 'kinput2', - XIM_PROGRAM => 'kinput2', - XMODIFIERS => '@im=kinput2', - langs => 'ja', - packages => { generic => sub { 'kinput2-wnn' } }, - }, nabi => { GTK_IM_MODULE => 'xim', XIM => 'nabi', @@ -631,58 +844,49 @@ my %IM_config = langs => 'ko', }, - oxim => { - GTK_IM_MODULE => 'oxim', - XIM => 'oxim', - XIM_PROGRAM => 'oxim', - XMODIFIERS => '@im=oxim', # '@im=SCIM' is broken for now - langs => 'zh_TW', - packages => { generic => sub { 'oxim' } }, - }, 'scim' => { GTK_IM_MODULE => 'scim', + QT_IM_MODULE => 'xim', XIM_PROGRAM => 'scim -d', XMODIFIERS => '@im=SCIM', packages => { - common => sub { if_($is_kde3, 'scim-qtimm') }, generic => sub { qw(scim-m17n scim-tables) }, am => sub { qw(scim-tables) }, - ja => sub { qw(scim-anthy scim-input-pad scim-tomoe) }, - ko => sub { qw(scim-hangul) }, + ja => sub { qw(scim-anthy) }, + ko => sub { qw(scim-hangul) }, + th => sub { qw(scim-thai) }, vi => sub { qw(scim-m17n) }, - zh => sub { qw(scim-pinyin scim-tables scim-chewing) }, + zh => sub { qw(scim-tables-zh scim-chewing) }, }, }, 'scim-bridge' => { GTK_IM_MODULE => 'scim-bridge', - XIM_PROGRAM => 'scim -d', + XIM_PROGRAM => 'scim-bridge', XMODIFIERS => '@im=SCIM', - default_for_lang => 'am ja ko vi zh_CN zh_TW', packages => { - common => sub { if_($is_kde3, 'scim-bridge-qt3'), if_($is_kde4, 'scim-bridge-qt4') }, generic => sub { qw(scim-m17n scim-tables) }, am => sub { qw(scim-tables) }, - ja => sub { qw(scim-anthy scim-input-pad scim-tomoe) }, - ko => sub { qw(scim-hangul) }, + ja => sub { qw(scim-anthy) }, + ko => sub { qw(scim-hangul) }, + th => sub { qw(scim-thai) }, vi => sub { qw(scim-m17n) }, - zh => sub { qw(scim-pinyin scim-tables scim-chewing) }, + zh => sub { qw(scim-tables-zh scim-chewing) }, }, }, - skim => { - GTK_IM_MODULE => 'scim', - XIM_PROGRAM => 'skim -d', - XMODIFIERS => '@im=SCIM', - packages => { - common => sub { if_($is_kde3, 'scim-qtimm') }, - generic => sub { qw(skim-scim-tables scim-m17n) }, - am => sub { qw(skim-scim-tables) }, - ja => sub { qw(skim-scim-anthy scim-input-pad scim-tomoe) }, - ko => sub { qw(scim-hangul-skim) }, - vi => sub { qw(skim scim-m17n) }, - zh => sub { qw(skim-scim-pinyin skim-scim-tables scim-chewing) }, - }, - }, + 'ibus' => { + GTK_IM_MODULE => 'ibus', + QT_IM_MODULE => 'ibus', + XIM_PROGRAM => 'ibus-daemon -d -x', + XMODIFIERS => '@im=ibus', + default_for_lang => 'am ja ko th vi zh_CN zh_TW', + packages => { + generic => sub { qw(ibus-table ibus-m17n) }, + ja => sub { qw(ibus-mozc) }, + zh => sub { qw(ibus-libpinyin ibus-chewing) }, + ko => sub { qw(ibus-hangul) }, + }, + }, uim => { GTK_IM_MODULE => 'uim', XIM => 'uim', @@ -690,17 +894,9 @@ my %IM_config = XMODIFIERS => '@im=uim', langs => 'ja', packages => { - common => sub { if_($is_kde3, 'uim-qtimmodule'), if_($is_kde4, 'uim-qt4immodule') }, generic => sub { qw(uim-gtk uim) }, }, }, - xcin => { - XIM => 'xcin', - XIM_PROGRAM => 'xcin', - XMODIFIERS => '@im=xcin-zh_TW', - GTK_IM_MODULE => 'xim', - langs => 'zh', - }, 'x-unikey' => { GTK_IM_MODULE => 'xim', XMODIFIERS => '@im=unikey', @@ -734,6 +930,12 @@ my %IM_locale_specific_config = ( ); +=item get_ims ($lang) + +Returns the IMs that are usable for $lang. + +=cut + sub get_ims { my ($lang) = @_; my $main_lang = analyse_locale_name($lang)->{main}; @@ -745,6 +947,12 @@ sub get_ims { } keys %IM_config; } +=item get_default_im ($lang) + +Returns the default IM to use for $lang. + +=cut + sub get_default_im { my ($lang) = @_; find { @@ -752,13 +960,18 @@ sub get_default_im { } keys %IM_config; } +=item IM2packages ($locale) + +Returns the packages to use for $locale if it's set to use an IM + +=cut + sub IM2packages { my ($locale) = @_; if ($locale->{IM}) { require any; my @sessions = any::sessions(); - $is_kde3 = member('KDE', @sessions); - $is_kde4 = member('KDE4', @sessions); + $is_plasma = any { /plasma/ } @sessions; my $per_lang = $IM_config{$locale->{IM}}{packages} || {}; my $main_lang = analyse_locale_name($locale->{lang})->{main}; my $packages = $per_lang->{$main_lang} || $per_lang->{generic}; @@ -768,11 +981,32 @@ sub IM2packages { } else { () } } -#- [0]: console font name -#- [1]: unused -#- [2]: console map (none if utf8) -#- [3]: iocharset param for mount (utf8 if utf8) -#- [4]: codepage parameter for mount (none if utf8) +=back + +=head2 Charsets + +=over + +=item my %charsets; + +Key is encoding. Fields are: + +=over 4 + +=item 0: console font name + +=item 1: unused + +=item 2: console map (none if utf8) + +=item 3: iocharset param for mount (utf8 if utf8) + +=item 4: codepage parameter for mount (none if utf8) + +=back + +=cut + my %charsets = ( #- chinese needs special console driver for text mode "Big5" => [ undef, undef, undef, "big5", "950" ], @@ -803,7 +1037,7 @@ my %charsets = ( "utf_cyr1" => [ "UniCyr_8x16", undef, undef, "utf8", undef ], "utf_cyr2" => [ "koi8-k", undef, undef, "utf8", undef ], "utf_deva" => [ undef, undef, undef, "utf8", undef ], -"utf_ethi" => [ "Agafari-16", undef, undef, "utf8", undef ], +"utf_ethi" => [ undef, undef, undef, "utf8", undef ], "utf_geor" => [ "t_geors", undef, undef, "utf8", undef ], "utf_guru" => [ undef, undef, undef, "utf8", undef ], "utf_he" => [ undef, undef, undef, "utf8", undef ], @@ -827,7 +1061,12 @@ my %charsets = ( "unicode" => [ "LatArCyrHeb-16", undef, undef, "utf8", undef ], ); -#- for special cases not handled magically +=item my %charset2kde_charset; + +For special cases not handled magically + +=cut + my %charset2kde_charset = ( gb2312 => 'gb2312.1980-0', gbk => 'gb2312.1980-0', @@ -841,6 +1080,12 @@ my %charset2kde_charset = ( #- ------------------- +=item l2console_font ($locale, $during_install) + +Returns console font name & console map (none if utf8 and if not during install); + +=cut + sub l2console_font { my ($locale, $during_install) = @_; my $c = $charsets{l2charset($locale->{lang}) || return} or return; @@ -900,8 +1145,15 @@ sub charset2kde_charset { $r || $o_default || 'iso10646-1'; } -#- font+size for different charsets; the field [0] is the default, -#- others are overrridens for fixed(1), toolbar(2), menu(3) and taskbar(4) +=item my %charset2kde_font; + +Font+size for different charsets; the field [0] is the default, +others are overrridens for fixed(1), toolbar(2), menu(3) and taskbar(4) + +This is needed because KDE historically doesn't use fontconfig... + +=cut + my %charset2kde_font = ( 'C' => [ "Sans,10", "Monospace,10" ], 'iso-8859-1' => [ "Sans,10", "Monospace,10" ], @@ -958,9 +1210,14 @@ sub charset2kde_font { "$r,-1,5,0,0,0,0,0,0"; } -# this define pango name fonts (like "NimbusSans L") depending -# on the "charset" defined by language array. This allows to selecting -# an appropriate font for each language for the installer only. +=item my %charset2pango_font; + +This define pango name fonts (like "NimbusSans L") depending +on the "charset" defined by language array. This allows to selecting +an appropriate font for each language for the installer only. + +=cut + my %charset2pango_font = ( 'utf_geor' => "Sans 14", 'utf_taml' => "TSCu_Paranar 14", @@ -970,10 +1227,30 @@ my %charset2pango_font = ( 'default' => "DejaVu Sans 12" ); +=item charset2pango_font ($charset) + +Returns the font to use with $charset or the default one if non is set + +=cut + sub charset2pango_font { my ($charset) = @_; - $charset2pango_font{exists $charset2pango_font{$charset} ? $charset : 'default'}; + $charset2pango_font{$charset} || $charset2pango_font{default}; +} + +=item charset2css_font ($charset) + +Returns the font to use with $charset or the default one if non is set + +=cut + +sub charset2css_font { + my ($charset) = @_; + + my $font = $charset2pango_font{$charset} || $charset2pango_font{default}; + my ($familly, $size) = $font =~ /(.*) (\d+)$/; + return "font-family: $familly; font-size: ${size}pt;"; } sub l2pango_font { @@ -986,6 +1263,24 @@ sub l2pango_font { return $font; } +sub l2css_font { + my ($lang) = @_; + + my $charset = l2charset($lang) or log::l("no charset found for lang $lang!"), return; + my $font = charset2css_font($charset); + log::l("lang:$lang charset:$charset font:$font consolefont:$charsets{$charset}[0]"); + + return $font; +} + +=back + +=head1 Other functions + +=over + +=cut + sub set { my ($locale, $b_translate_for_console) = @_; @@ -1026,7 +1321,7 @@ sub pack_langs { } sub system_locales_to_ourlocale { - my ($locale_lang, $locale_country) = @_; + my ($locale_lang, $locale_country, $o_country) = @_; my $locale = {}; my $h = analyse_locale_name($locale_lang); my $locale_lang_no_encoding = join('_', $h->{main}, if_($h->{country}, $h->{country})); @@ -1034,7 +1329,7 @@ sub system_locales_to_ourlocale { $locale_lang_no_encoding : #- special lang's such as en_US pt_BR $h->{main}; $locale->{lang} .= '@' . $h->{variant} if $h->{variant}; - $locale->{country} = analyse_locale_name($locale_country)->{country}; + $locale->{country} = $o_country || analyse_locale_name($locale_country)->{country}; $locale->{utf8} = $h->{charset} && $h->{charset} eq 'UTF-8'; #- safe fallbacks @@ -1061,20 +1356,30 @@ sub lang_changed { $locale->{IM} = get_default_im($locale->{lang}); } +=item read($b_user_only) + +Read locale settings from files. +If $b_user_only is set, reads the user config, else read the system config. + +=cut + sub read { my ($b_user_only) = @_; - my ($f1, $f2) = ("$::prefix$ENV{HOME}/.i18n", "$::prefix/etc/sysconfig/i18n"); + my $f1 = "$::prefix$ENV{HOME}/.i18n"; + my $f2 = "$::prefix/etc/locale.conf"; + # (cg) Only use the 'legacy' config name when the new one doesn't exist + $f2 = "$::prefix/etc/sysconfig/i18n" if ! -e $f2 && -e "$::prefix/etc/sysconfig/i18n"; my %h = getVarsFromSh($b_user_only && -e $f1 ? $f1 : $f2); - my $locale = system_locales_to_ourlocale($h{LC_MESSAGES} || 'en_US', $h{LC_MONETARY} || 'en_US'); + # Fill in defaults (from LANG= variable) + $h{$_} ||= $h{LANG} || 'en_US' foreach @locale_conf_fields; + my $locale = system_locales_to_ourlocale($h{LC_MESSAGES}, $h{LC_MONETARY}, $h{COUNTRY}); if (find { $h{$_} } @IM_i18n_fields) { - my @l = grep { !/^scim/ || /\(default\)/ } keys %IM_config; - foreach my $field ('XMODIFIERS', 'XIM_PROGRAM') { - $h{$field} or next; - my @m = grep { $h{$field} eq $IM_config{$_}{$field} } @l or last; - @l = @m; - } - $locale->{IM} = $l[0] if @l; + my $current_IM = find { + my $i = $IM_config{$_}; + every { !defined $i->{$_} || $h{$_} eq $i->{$_} } ('GTK_IM_MODULE', 'XMODIFIERS', 'XIM_PROGRAM'); + } keys %IM_config; + $locale->{IM} = $current_IM if $current_IM; } $locale; } @@ -1096,6 +1401,7 @@ sub i18n_env { my $h = { XKB_IN_USE => '', + COUNTRY => $locale->{country}, (map { $_ => $locale_lang } qw(LANG LC_COLLATE LC_CTYPE LC_MESSAGES LC_TIME)), LANGUAGE => getLANGUAGE($locale->{lang}, $locale->{country}, $locale->{utf8}), (map { $_ => $locale_country } qw(LC_NUMERIC LC_MONETARY LC_ADDRESS LC_MEASUREMENT LC_NAME LC_PAPER LC_IDENTIFICATION LC_TELEPHONE)) @@ -1117,6 +1423,12 @@ sub write_and_install { &write($locale, $b_user_only, $b_dont_touch_kde_files); } +=item write ($locale, $b_user_only, $b_dont_touch_kde_files) + +Save locale settings, either system ones or per user ones (if $b_user_only is set). + +=cut + sub write { my ($locale, $b_user_only, $b_dont_touch_kde_files) = @_; @@ -1176,7 +1488,25 @@ sub write { log::explanations(qq(Setting l10n configuration in "$file")); setVarsInShMode($::prefix . $file, 0644, $h); - configure_hal($locale) if !$b_user_only; + if (!$b_user_only) { + $file = '/etc/locale.conf'; + log::explanations(qq(Setting locale configuration in "$file")); + # Only include valid fields and ommit any that are the same as LANG to make it cleaner + # (cleanup logic copied from systemd) + my @filtered_keys = grep { exists $h->{$_} && ($_ eq 'LANG' || !exists $h->{LANG} || $h->{$_} ne $h->{LANG}) } @locale_conf_fields; + my @filtered_input = grep { exists $h->{$_} } @IM_i18n_fields; + push @filtered_keys, @filtered_input; + push @filtered_keys, 'COUNTRY' if exists $h->{COUNTRY}; + my $h2 = { map { $_ => $h->{$_} } @filtered_keys }; + setVarsInShMode($::prefix . $file, 0644, $h2); + + if ($h->{SYSFONT}) { + $file = '/etc/vconsole.conf'; + $h2 = { 'FONT' => $h->{SYSFONT} }; + $h2->{FONT_UNIMAP} = $h->{SYSFONTACM} if $h->{SYSFONTACM}; + addVarsInShMode($::prefix . $file, 0644, $h2); + } + } run_program::rooted($::prefix, 'grub-gfxmenu', '--quiet', '--lang', $locale->{lang}) if !$b_user_only; @@ -1191,7 +1521,7 @@ sub write { my $kderc = $::prefix ? common::expand_symlinks_with_absolute_symlinks_in_prefix($::prefix, '/etc/kderc') : '/etc/kderc'; log::l("reading $kderc"); my %dir_defaults = read_gnomekderc($kderc, 'Directories-default'); - first(split(',', $dir_defaults{prefixes})) || "/etc/kde" + first(split(',', $dir_defaults{prefixes})) || "/etc/kde"; }) . '/share/config'; -d $confdir or die 'not configuring kde config files since it is not installed/used'; @@ -1207,7 +1537,7 @@ sub write { if (!$b_user_only) { my $kde_charset = charset2kde_charset(l2charset($locale->{lang})); my $welcome = common::to_utf8(N("Welcome to %s", '%n')); - log::explanations(qq(Configuring KDM/MdkKDM)); + log::explanations(qq(Configuring KDM)); substInFile { s/^(GreetString)=.*/$1=$welcome/; s/^(Language)=.*/$1=$locale->{lang}/; @@ -1235,58 +1565,6 @@ sub write { } } -sub configure_hal { - my ($locale) = @_; - my $option = sub { - my ($cat, $val) = @_; - qq(\t\t<merge key="$cat.policy.mount_option.$val" type="bool">true</merge>); - }; - my %options = (fs_options($locale), utf8 => 1); - my %known_options = ( - auto => [ 'iocharset', 'codepage' ], - vfat => [ 'iocharset', 'codepage' ], - msdos => [ 'iocharset', 'codepage' ], - ntfs => [ 'iocharset', 'utf8' ], - cdrom => [ 'iocharset', 'codepage', 'utf8' ], - ); - my $options = sub { - my ($cat, $name) = @_; - join("\n", map { - $option->($cat, $_ eq 'utf8' ? $_ : "$_=$options{$_}"); - } grep { $options{$_} } @{$known_options{$name}}); - }; - my $options_per_fs = join('', map { - my $s = $options->('volume', $_); - $s && sprintf(<<'EOF', $_, $s); - <match key="volume.fstype" string="%s"> -%s - </match> -EOF - } 'auto', 'vfat', 'msdos', 'ntfs'); - - output_p("$::prefix/usr/share/hal/fdi/30osvendor/locale-policy.fdi", - sprintf(<<'EOF', $options_per_fs, $options->('storage', 'cdrom'))); -<?xml version="1.0" encoding="UTF-8"?> <!-- -*- SGML -*- --> - -<deviceinfo version="0.2"> - - <device> - <match key="block.is_volume" bool="true"> - <match key="volume.fsusage" string="filesystem"> - -%s - </match> - </match> - - <match key="storage.drive_type" string="cdrom"> -%s - </match> - </device> - -</deviceinfo> -EOF -} - sub configure_kdeglobals { my ($locale, $confdir) = @_; my $kdeglobals = "$confdir/kdeglobals"; @@ -1323,6 +1601,12 @@ sub configure_kdeglobals { )); } +=item bindtextdomain() + +Binds the translation domains with the proper encoding (UTF-8). + +=cut + sub bindtextdomain() { #- if $::prefix is set, search for libDrakX.mo in locale_special #- NB: not using $::isInstall to make it work more easily at install and standalone @@ -1337,6 +1621,13 @@ sub bindtextdomain() { $localedir; } +=item load_mo ($o_lang) + +Used by the installer: returns the firste existing .mo file to load according to $o_lang. +If it's not set, we rely on environment variables. + +=cut + sub load_mo { my ($o_lang) = @_; @@ -1353,13 +1644,24 @@ sub load_mo { } -#- used in share/list.xml during "make get_needed_files" +=item console_font_files() + +Used in share/list.xml during "make get_needed_files" + +=cut + sub console_font_files() { map { -e $_ ? $_ : "$_.gz" } (map { my $p = "/usr/lib/kbd/consolefonts/$_"; -e "$p.psfu" || -e "$p.psfu.gz" ? "$p.psfu" : "$p.psf" } uniq grep { $_ } map { $_->[0] } values %charsets), (map { "/usr/lib/kbd/consoletrans/${_}_to_uni.trans" } uniq grep { $_ } map { $_->[2] } values %charsets); } +=item load_console_font($locale) + +Loads the console font... + +=cut + sub load_console_font { my ($locale) = @_; return if $::local_install; @@ -1370,6 +1672,12 @@ sub load_console_font { run_program::run('setfont', '-v', $name || 'lat0-16', if_($acm, '-m', $acm)); } +=item fs_options($locale) + +Returns the options suitable for filesystems mounting according to $locale. + +=cut + sub fs_options { my ($locale) = @_; if ($locale->{utf8}) { @@ -1381,6 +1689,12 @@ sub fs_options { } } +=item check() + +Used by 'make check_full'. + +=cut + sub check() { $^W = 0; my ($warnings, $errors) = (0, 0); @@ -1432,4 +1746,8 @@ sub check() { exit($errors ? 1 : 0); } +=back + +=cut + 1; |