Filtering a list of strings based on user locale

被刻印的时光 ゝ 提交于 2019-12-05 01:07:58

I'd go about getting the user's locale directly from the browser via navigator (src), an object representing the user agent:

var language = navigator.language;

This will assign language the locale code of the user's browser, in my case en-US. I found this site helpful for finding locale code's to test other regions of the world.

My strFromLocale function is comparable to your removeDiacritics function:

function strFromLocale(str) {
    function match(letter) {
        function letterMatch(letter, normalizedLetter) {
            var location = new Intl.Collator(language, {usage: 'search', sensitivity: 'base' }).compare(letter, normalizedLetter);
            return (location == 0)
        }
        normalizedLetter = letter.normalize('NFD').replace(/[\u0300-\u036f]/gi, "")
        if ( letterMatch(letter, normalizedLetter) ) {
            return normalizedLetter;
        } else {
            return letter;
        }
    }
    return str.replace(/[^\u0000-\u007E]/g, match);
}

Note the line with Intl.Collator (src). This line compares the diacritic with the normalized letter of the diacritic and checks the given language's alphabet for positional differences. Therefore:

/* English */
new Intl.Collator('en-US', {usage: 'search', sensitivity: 'base' }).compare('u', 'ü');
>>> 0

/* Swedish */
new Intl.Collator('sv', {usage: 'search', sensitivity: 'base' }).compare('u', 'ü');
>>> -1

/* German */
new Intl.Collator('de', {usage: 'search', sensitivity: 'base' }).compare('u', 'ü');
>>> -1

As you can see in the letterMatch function, it returns true if and only if the result of Intl.Collator is 0, indicating that there are no positional differences of the letter within the alphabet of that language meaning it is safe to replace.

With that, here are some tests of the strFromLocale function:

var language = navigator.language; // en-US
strFromLocale("cigüeña");
>>> ciguena

var language = 'sv' // Swedish
strFromLocale("cigüeña");
>>> cigüena

var language = 'de' // German
strFromLocale("cigüeña");
>>> cigüena

var language = 'es-mx' // Spanish - Mexico
strFromLocale("cigüeña");
>>> cigueña

You are probably looking for the ECMA 6 Intl library. This will allow you to adjust sort order based on locale e.g.:

// in German, ä sorts with a
console.log(new Intl.Collator('de').compare('ä', 'z'));
// → a negative value

// in Swedish, ä sorts after z
console.log(new Intl.Collator('sv').compare('ä', 'z'));
// → a positive value

The sensitivity: 'base' option will automatically sort with/without diacritics.

// in German, ä has a as the base letter
console.log(new Intl.Collator('de', { sensitivity: 'base' }).compare('ä', 'a'));
// → 0

// in Swedish, ä and a are separate base letters
console.log(new Intl.Collator('sv', { sensitivity: 'base' }).compare('ä', 'a'));
// → a positive value

You can then sort your list into the correct order prior to populating your UI Widget.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!