// A string localized into multiple locales. export type string = [](locale, str); // Selects the most appropriate localized version of a [[string]] given a // [[locale]]. The matching algorithm used is the one specified by the // XDG Desktop Entry Specification, ยง5. Memory is borrowed from the input. export fn string_resolve(strin: string, local: locale) (str | void) = { // The matching is done as follows. If LC_MESSAGES is of the form // lang_COUNTRY.ENCODING@MODIFIER, then it will match a key of the form // lang_COUNTRY@MODIFIER. If such a key does not exist, it will attempt // to match lang_COUNTRY followed by lang@MODIFIER. Then, a match // against lang by itself will be attempted. Finally, if no matching key // is found the required key without a locale specified is used. The // encoding from the LC_MESSAGES value is ignored when matching. // // If LC_MESSAGES does not have a MODIFIER field, then no key with a // modifier will be matched. Similarly, if LC_MESSAGES does not have a // COUNTRY field, then no key with a country specified will be matched. // If LC_MESSAGES just has a lang field, then it will do a straight // match to a key with a similar value. let lang_country_modifier = local; lang_country_modifier.encoding = ""; match (string_resolve_exact(strin, lang_country_modifier)) { case let index: size => return index; case => void; }; let lang_country = local; lang_country.modifier = ""; match (string_resolve_exact(strin, lang_country)) { case let index: size => return index; case => void; }; let lang_modifier = lang_country_modifier; lang_modifier.country = ""; match (string_resolve_exact(strin, lang_modifier)) { case let index: size => return index; case => void; }; let lang = lang_modifier; lang.modifier = ""; match (string_resolve_exact(strin, lang)) { case let index: size => return index; case => void; }; return void; }; fn string_resolve_exact(strin: string, local: locale) (size | void) = { let index = 0z; for (let pair .. strn) { if(equal(pair.1, local)) return index; index += 1; }; };