110 lines
4.6 KiB
Ruby
110 lines
4.6 KiB
Ruby
# encoding: utf-8
|
||
# frozen_string_literal: true
|
||
|
||
module I18n
|
||
module Backend
|
||
module Transliterator
|
||
DEFAULT_REPLACEMENT_CHAR = "?"
|
||
|
||
# Given a locale and a UTF-8 string, return the locale's ASCII
|
||
# approximation for the string.
|
||
def transliterate(locale, string, replacement = nil)
|
||
@transliterators ||= {}
|
||
@transliterators[locale] ||= Transliterator.get I18n.t(:'i18n.transliterate.rule',
|
||
:locale => locale, :resolve => false, :default => {})
|
||
@transliterators[locale].transliterate(string, replacement)
|
||
end
|
||
|
||
# Get a transliterator instance.
|
||
def self.get(rule = nil)
|
||
if !rule || rule.kind_of?(Hash)
|
||
HashTransliterator.new(rule)
|
||
elsif rule.kind_of? Proc
|
||
ProcTransliterator.new(rule)
|
||
else
|
||
raise I18n::ArgumentError, "Transliteration rule must be a proc or a hash."
|
||
end
|
||
end
|
||
|
||
# A transliterator which accepts a Proc as its transliteration rule.
|
||
class ProcTransliterator
|
||
def initialize(rule)
|
||
@rule = rule
|
||
end
|
||
|
||
def transliterate(string, replacement = nil)
|
||
@rule.call(string)
|
||
end
|
||
end
|
||
|
||
# A transliterator which accepts a Hash of characters as its translation
|
||
# rule.
|
||
class HashTransliterator
|
||
DEFAULT_APPROXIMATIONS = {
|
||
"À"=>"A", "Á"=>"A", "Â"=>"A", "Ã"=>"A", "Ä"=>"A", "Å"=>"A", "Æ"=>"AE",
|
||
"Ç"=>"C", "È"=>"E", "É"=>"E", "Ê"=>"E", "Ë"=>"E", "Ì"=>"I", "Í"=>"I",
|
||
"Î"=>"I", "Ï"=>"I", "Ð"=>"D", "Ñ"=>"N", "Ò"=>"O", "Ó"=>"O", "Ô"=>"O",
|
||
"Õ"=>"O", "Ö"=>"O", "×"=>"x", "Ø"=>"O", "Ù"=>"U", "Ú"=>"U", "Û"=>"U",
|
||
"Ü"=>"U", "Ý"=>"Y", "Þ"=>"Th", "ß"=>"ss", "ẞ"=>"SS", "à"=>"a",
|
||
"á"=>"a", "â"=>"a", "ã"=>"a", "ä"=>"a", "å"=>"a", "æ"=>"ae", "ç"=>"c",
|
||
"è"=>"e", "é"=>"e", "ê"=>"e", "ë"=>"e", "ì"=>"i", "í"=>"i", "î"=>"i",
|
||
"ï"=>"i", "ð"=>"d", "ñ"=>"n", "ò"=>"o", "ó"=>"o", "ô"=>"o", "õ"=>"o",
|
||
"ö"=>"o", "ø"=>"o", "ù"=>"u", "ú"=>"u", "û"=>"u", "ü"=>"u", "ý"=>"y",
|
||
"þ"=>"th", "ÿ"=>"y", "Ā"=>"A", "ā"=>"a", "Ă"=>"A", "ă"=>"a", "Ą"=>"A",
|
||
"ą"=>"a", "Ć"=>"C", "ć"=>"c", "Ĉ"=>"C", "ĉ"=>"c", "Ċ"=>"C", "ċ"=>"c",
|
||
"Č"=>"C", "č"=>"c", "Ď"=>"D", "ď"=>"d", "Đ"=>"D", "đ"=>"d", "Ē"=>"E",
|
||
"ē"=>"e", "Ĕ"=>"E", "ĕ"=>"e", "Ė"=>"E", "ė"=>"e", "Ę"=>"E", "ę"=>"e",
|
||
"Ě"=>"E", "ě"=>"e", "Ĝ"=>"G", "ĝ"=>"g", "Ğ"=>"G", "ğ"=>"g", "Ġ"=>"G",
|
||
"ġ"=>"g", "Ģ"=>"G", "ģ"=>"g", "Ĥ"=>"H", "ĥ"=>"h", "Ħ"=>"H", "ħ"=>"h",
|
||
"Ĩ"=>"I", "ĩ"=>"i", "Ī"=>"I", "ī"=>"i", "Ĭ"=>"I", "ĭ"=>"i", "Į"=>"I",
|
||
"į"=>"i", "İ"=>"I", "ı"=>"i", "IJ"=>"IJ", "ij"=>"ij", "Ĵ"=>"J", "ĵ"=>"j",
|
||
"Ķ"=>"K", "ķ"=>"k", "ĸ"=>"k", "Ĺ"=>"L", "ĺ"=>"l", "Ļ"=>"L", "ļ"=>"l",
|
||
"Ľ"=>"L", "ľ"=>"l", "Ŀ"=>"L", "ŀ"=>"l", "Ł"=>"L", "ł"=>"l", "Ń"=>"N",
|
||
"ń"=>"n", "Ņ"=>"N", "ņ"=>"n", "Ň"=>"N", "ň"=>"n", "ʼn"=>"'n", "Ŋ"=>"NG",
|
||
"ŋ"=>"ng", "Ō"=>"O", "ō"=>"o", "Ŏ"=>"O", "ŏ"=>"o", "Ő"=>"O", "ő"=>"o",
|
||
"Œ"=>"OE", "œ"=>"oe", "Ŕ"=>"R", "ŕ"=>"r", "Ŗ"=>"R", "ŗ"=>"r", "Ř"=>"R",
|
||
"ř"=>"r", "Ś"=>"S", "ś"=>"s", "Ŝ"=>"S", "ŝ"=>"s", "Ş"=>"S", "ş"=>"s",
|
||
"Š"=>"S", "š"=>"s", "Ţ"=>"T", "ţ"=>"t", "Ť"=>"T", "ť"=>"t", "Ŧ"=>"T",
|
||
"ŧ"=>"t", "Ũ"=>"U", "ũ"=>"u", "Ū"=>"U", "ū"=>"u", "Ŭ"=>"U", "ŭ"=>"u",
|
||
"Ů"=>"U", "ů"=>"u", "Ű"=>"U", "ű"=>"u", "Ų"=>"U", "ų"=>"u", "Ŵ"=>"W",
|
||
"ŵ"=>"w", "Ŷ"=>"Y", "ŷ"=>"y", "Ÿ"=>"Y", "Ź"=>"Z", "ź"=>"z", "Ż"=>"Z",
|
||
"ż"=>"z", "Ž"=>"Z", "ž"=>"z", "Ǫ"=>"O", "ǫ"=>"o", "Ǭ"=>"O",
|
||
"ǭ"=>"o"
|
||
}.freeze
|
||
|
||
def initialize(rule = nil)
|
||
@rule = rule
|
||
add_default_approximations
|
||
add rule if rule
|
||
end
|
||
|
||
def transliterate(string, replacement = nil)
|
||
replacement ||= DEFAULT_REPLACEMENT_CHAR
|
||
string.gsub(/[^\x00-\x7f]/u) do |char|
|
||
approximations[char] || (replacement == :none ? char : replacement)
|
||
end
|
||
end
|
||
|
||
private
|
||
|
||
def approximations
|
||
@approximations ||= {}
|
||
end
|
||
|
||
def add_default_approximations
|
||
DEFAULT_APPROXIMATIONS.each do |key, value|
|
||
approximations[key] = value
|
||
end
|
||
end
|
||
|
||
# Add transliteration rules to the approximations hash.
|
||
def add(hash)
|
||
hash.each do |key, value|
|
||
approximations[key.to_s] = value.to_s
|
||
end
|
||
end
|
||
end
|
||
end
|
||
end
|
||
end
|