Ҷаҳиш ба мӯҳтаво

Модул:PamirTranslit

Аз Wiktionary
(Тағйири масир аз Модул:PmTranslit)

Documentation for this module may be created at Модул:PamirTranslit/doc

local p = {}

-- Коды языков
local lang_codes = {
    ['isk'] = 'ишкошимӣ',
    ['sgh'] = 'шуғнонӣ', 
    ['sgh-ro'] = 'рошорвӣ',
    ['sgh-ru'] = 'рӯшонӣ',
    ['sgh-ba'] = 'бартангӣ',
    ['yah'] = 'язғуломӣ',
    ['wbl'] = 'вахонӣ',
    ['srh'] = 'сарикӯлӣ'
}

-- Таблица соответствий латиница -> кириллица
local lat_to_cyr_map = {
    -- Основные буквы
    ['a'] = 'а', ['A'] = 'А',
    ['b'] = 'б', ['B'] = 'Б', 
    ['c'] = 'ц', ['C'] = 'Ц',
    ['d'] = 'д', ['D'] = 'Д',
    ['e'] = 'е', ['E'] = 'Е',
    ['f'] = 'ф', ['F'] = 'Ф',
    ['g'] = 'г', ['G'] = 'Г', 
    ['h'] = 'ҳ', ['H'] = 'Ҳ',
    ['i'] = 'и', ['I'] = 'И',
    ['j'] = 'ҷ', ['J'] = 'Ҷ',
    ['k'] = 'к', ['K'] = 'К',
    ['l'] = 'л', ['L'] = 'Л',
    ['m'] = 'м', ['M'] = 'М',
    ['n'] = 'н', ['N'] = 'Н',
    ['o'] = 'о', ['O'] = 'О',
    ['p'] = 'п', ['P'] = 'П',
    ['q'] = 'қ', ['Q'] = 'Қ',
    ['r'] = 'р', ['R'] = 'Р',
    ['s'] = 'с', ['S'] = 'С',
    ['t'] = 'т', ['T'] = 'Т',
    ['u'] = 'у', ['U'] = 'У',
    ['v'] = 'в', ['V'] = 'В',
    ['w'] = 'в̌', ['W'] = 'В̌', -- в с гачеком
    ['x'] = 'х', ['X'] = 'Х',
    ['y'] = 'й', ['Y'] = 'Й',
    ['z'] = 'з', ['Z'] = 'З',
    
    -- Диакритические знаки
    ['ī'] = 'ӣ', ['Ī'] = 'Ӣ',
    ['ū'] = 'ӯ', ['Ū'] = 'Ӯ',
    ['ů'] = 'у̊', ['Ů'] = 'У̊', -- у с кольцом
    ['x̊'] = 'х̊', ['X̊'] = 'Х̊', -- х с кольцом
    ['ǰ'] = 'ҷ', ['J̌'] = 'Ҷ',
    ['ɣ'] = 'ғ', ['Ɣ'] = 'Ғ',
    ['ɣ̌'] = 'г̌', ['Ɣ̌'] = 'Г̌', -- ɣ с гачеком -> г с гачеком всегда
    ['ə'] = 'ә', ['Ə'] = 'Ә',
    ['ē'] = 'е̄', ['Ē'] = 'Е̄',
    ['ō'] = 'о̄', ['Ō'] = 'О̄',
    ['ā'] = 'а̄', ['Ā'] = 'А̄',
    ['θ'] = 'т̌', ['Θ'] = 'Т̌', -- тета для т с гачеком
    ['ǵ'] = 'ѓ', ['Ǵ'] = 'Ѓ', -- g с ударением
    ['ḱ'] = 'ќ', ['Ḱ'] = 'Ќ', -- k с ударением  
    ['ʒ'] = 'з̌', ['Ʒ'] = 'З̌', -- З с гачеком
    ['š'] = 'ш', ['Š'] = 'Ш',
    ['č'] = 'ч', ['Č'] = 'Ч',
    ['ž'] = 'ж', ['Ž'] = 'Ж',
    ['ś'] = 'с̌', ['Ś'] = 'С̌', -- с с гачеком = т с гачеком
    ['č̌'] = 'ц̌', ['Č̌'] = 'Ц̌', -- ц с гачеком
    
    -- С точкой внизу
    ['ḍ'] = 'д̣', ['Ḍ'] = 'Д̣',
    ['ẓ̌'] = 'ж̣', ['Ẓ̌'] = 'Ж̣', -- ž с точкой внизу
    ['ṣ̌'] = 'ш̣', ['Ṣ̌'] = 'Ш̣', -- š с точкой внизу
    ['ṭ'] = 'т̣', ['Ṭ'] = 'Т̣',
    ['č̣'] = 'ч̣', ['Č̣'] = 'Ч̣', -- č с точкой внизу
    ['j̇'] = 'ҷ̣', ['J̇'] = 'Ҷ̣', -- ǰ с точкой
    
    -- С умлаутом (кроме ü)
    ['ü'] = 'ӱ', ['Ü'] = 'Ӱ',
    ['d̈'] = 'д̈', ['D̈'] = 'Д̈',
    ['ẗ'] = 'т̈', ['T̈'] = 'Т̈',
    
    -- Специальные для язгулямского (с кольцом рядом)
    ['k̥'] = 'к̊', ['K̥'] = 'К̊', -- к с кольцом рядом
    ['q̊'] = 'қ̊', ['Q̊'] = 'Қ̊', -- қ с кольцом рядом
    ['x̥'] = 'х̊', ['X̥'] = 'Х̊', -- х с кольцом рядом
    ['x̌̊'] = 'х̌̊', ['X̌̊'] = 'Х̌̊', -- х с гачеком и кольцом
    ['ɣ̊'] = 'ғ̊', ['Ɣ̊'] = 'Ғ̊', -- ғ с кольцом рядом
    ['g̊'] = 'г̊', ['G̊'] = 'Г̊', -- г с кольцом рядом
    
    -- Диграфы
    ['yu'] = 'йу', ['Yu'] = 'Йу', ['YU'] = 'ЙУ',
    ['ya'] = 'йа', ['Ya'] = 'Йа', ['YA'] = 'ЙА',
    ['ye'] = 'йе', ['Ye'] = 'Йе', ['YE'] = 'ЙЕ',
    
    -- Остаются как есть
    ['ы'] = 'ы', ['Ы'] = 'Ы',
    ['ь'] = 'ь', ['Ь'] = 'Ь',
}

-- Обратная таблица кириллица -> латиница
local cyr_to_lat_map = {}
for lat, cyr in pairs(lat_to_cyr_map) do
    cyr_to_lat_map[cyr] = lat
end

-- Дополнительные обратные соответствия
local additional_cyr_to_lat = {
    ['ю'] = 'yu', ['Ю'] = 'Yu',
    ['я'] = 'ya', ['Я'] = 'Ya',
    ['ғ̌'] = 'ɣ̌', ['Ғ̌'] = 'Ɣ̌', -- ғ с гачеком тоже переводим в ɣ̌
}
for cyr, lat in pairs(additional_cyr_to_lat) do
    cyr_to_lat_map[cyr] = lat
end

-- Функция определения письменности
function p.detect_script(frame)
    local text
    if type(frame) == 'table' and frame.args then
        text = frame.args[1] or ''
    else
        text = frame or ''
    end

    if text == '' then
        return 'latin'
    end

    if mw.ustring.find(text, '[а-яё]') or mw.ustring.find(text, '[А-ЯЁ]') or 
       mw.ustring.find(text, '[ғқўҳҷӯәӣ]') or mw.ustring.find(text, '[ҒҚЎҲҶӮӘӢ]') then
        return 'cyrillic'
    else
        return 'latin'
    end
end

-- Функция транслитерации латиницы в кириллицу
function p.lat_to_cyr(frame)
    local text
    if type(frame) == 'table' and frame.args then
        text = frame.args[1] or ''
    else
        text = frame or ''
    end

    if text == '' then
        return ''
    end

    local result = text
    
    -- Сначала обрабатываем длинные последовательности
    for lat, cyr in pairs(lat_to_cyr_map) do
        if mw.ustring.len(lat) > 1 then
            result = mw.ustring.gsub(result, lat, cyr)
        end
    end
    
    -- Затем одиночные символы
    for lat, cyr in pairs(lat_to_cyr_map) do
        if mw.ustring.len(lat) == 1 then
            result = mw.ustring.gsub(result, lat, cyr)
        end
    end
    
    return result
end

-- Функция транслитерации кириллицы в латиницу
function p.cyr_to_lat(frame)
    local text
    if type(frame) == 'table' and frame.args then
        text = frame.args[1] or ''
    else
        text = frame or ''
    end

    if text == '' then
        return ''
    end

    local result = text
    
    -- Сначала длинные последовательности
    for cyr, lat in pairs(cyr_to_lat_map) do
        if mw.ustring.len(cyr) > 1 then
            result = mw.ustring.gsub(result, cyr, lat)
        end
    end
    
    -- Затем одиночные символы
    for cyr, lat in pairs(cyr_to_lat_map) do
        if mw.ustring.len(cyr) == 1 then
            result = mw.ustring.gsub(result, cyr, lat)
        end
    end
    
    return result
end

-- Функция получения названия языка
function p.get_lang_name(frame)
    local code
    if type(frame) == 'table' and frame.args then
        code = frame.args[1] or ''
    else
        code = frame or ''
    end
    return lang_codes[code] or code
end

-- Функция получения альтернативной письменности с языком
function p.get_alt_script(frame)
    local word, lang_code
    if type(frame) == 'table' and frame.args then
        word = frame.args[1] or ''
        lang_code = frame.args[2] or ''
    else
        word = frame or ''
        lang_code = ''
    end

    if word == '' then
        return ''
    end

    local lang_name = lang_codes[lang_code] or lang_code
    local script_type = p.detect_script(word)

    if script_type == 'latin' then
        local cyr_word = p.lat_to_cyr(word)
        return string.format('(навишти кириллӣ: [[%s#%s|%s]])', cyr_word, lang_name, cyr_word)
    else
        local lat_word = p.cyr_to_lat(word)
        return string.format('(навишти лотинӣ: [[%s#%s|%s]])', lat_word, lang_name, lat_word)
    end
end

-- Функция определения окончания множественного числа
function p.get_plural_suffix(frame)
    local word
    if type(frame) == 'table' and frame.args then
        word = frame.args[1] or ''
    else
        word = frame or ''
    end

    if word == '' then
        return 'en' -- По умолчанию для латиницы
    end

    local last_char = mw.ustring.sub(word, -1)
    local vowels_cyr = 'аеиоуыэюяӯәӣ'
    local vowels_lat = 'aeiouāēīōūə'
    local script_type = p.detect_script(word)
    local suffix_cyr, suffix_lat

    -- Определяем окончание в зависимости от последнего символа
    for i = 1, mw.ustring.len(vowels_cyr) do
        if last_char == mw.ustring.sub(vowels_cyr, i, i) then
            suffix_cyr = 'йен'
            suffix_lat = 'yen'
            break
        end
    end

    for i = 1, mw.ustring.len(vowels_lat) do
        if last_char == mw.ustring.sub(vowels_lat, i, i) then
            suffix_cyr = 'йен'
            suffix_lat = 'yen'
            break
        end
    end

    -- Если окончание не установлено, используем по умолчанию
    if not suffix_cyr then
        suffix_cyr = 'ен'
        suffix_lat = 'en'
    end

    -- Возвращаем окончание в зависимости от письменности слова
    return script_type == 'latin' and suffix_lat or suffix_cyr
end

return p