Модуль:Автоматическая статистика: различия между версиями

Нет описания правки
Нет описания правки
 
(не показаны 3 промежуточные версии 2 участников)
Строка 1: Строка 1:
-- ==========================================
-- ==========================================
-- Модуль:Автоматическая статистика 6.0
-- Модуль:Автоматическая статистика
-- (Pure UI Render для PlayerStats)
-- (Pure UI Render для PlayerStats JSON)
-- ==========================================
-- ==========================================


Строка 132: Строка 132:
                     td:cssText(style .. Config.styles.header)  
                     td:cssText(style .. Config.styles.header)  
                 else
                 else
                     local m_data = compiled_data.metrics[row.id].years[year]
                     local m_data = compiled_data.metrics[row.id] and compiled_data.metrics[row.id].years[year] or { val=0, num=0, den=0, color="" }
                     if m_data.color ~= "" then style = style .. m_data.color end
                     if m_data.color and m_data.color ~= "" then style = style .. m_data.color end
                     td:cssText(style)
                     td:cssText(style)
                      
                      
Строка 154: Строка 154:
                 td_tot:cssText(style_tot):wikitext("—")  
                 td_tot:cssText(style_tot):wikitext("—")  
             else
             else
                 local m_tot = compiled_data.metrics[row.id]
                 local m_tot = compiled_data.metrics[row.id] or { total_val=0, total_num=0, total_den=0, color="" }
                 if m_tot.color and m_tot.color ~= "" then style_tot = style_tot .. m_tot.color end
                 if m_tot.color and m_tot.color ~= "" then style_tot = style_tot .. m_tot.color end
                 td_tot:cssText(style_tot)
                 td_tot:cssText(style_tot)
Строка 171: Строка 171:
     end
     end


     if show_matches and #compiled_data.player_matches_list > 0 then
     if show_matches and compiled_data.player_matches_list then
         local pml = compiled_data.player_matches_list
        -- 1. СНАЧАЛА копируем Read-Only прокси-массив в чистую Lua-таблицу
        table.sort(pml, function(a, b) return a.num_hist < b.num_hist end)
        -- ipairs работает с JSON-прокси безупречно
         local pml = {}
        for _, m in ipairs(compiled_data.player_matches_list) do
            table.insert(pml, m)  
        end
          
          
         local url_matches = "https://thirdworldcup.ru/index.php?title=%D0%9F%D0%BE%D0%B4%D1%81%D1%82%D1%80%D0%B0%D0%BD%D0%B8%D1%86%D0%B0:%D0%A0%D0%B0%D0%B7%D0%B2%D1%91%D1%80%D1%82%D0%BA%D0%B0_%D1%88%D0%B0%D0%B1%D0%BB%D0%BE%D0%BD%D0%BE%D0%B2/%D0%A1%D0%BF%D0%B8%D1%81%D0%BE%D0%BA_%D0%BC%D0%B0%D1%82%D1%87%D0%B5%D0%B9&action=edit"
         -- 2. ТЕПЕРЬ проверяем длину чистого массива pml, а не сломанного JSON-объекта
        local match_gear = " [[Файл:Gear icon.svg|12px|link=" .. url_matches .. "]] "
        if #pml > 0 then
       
            table.sort(pml, function(a, b) return a.num_hist < b.num_hist end)
        local t_list = mw.html.create('table'):addClass('wikitable mw-collapsible mw-collapsed')
           
        t_list:tag('tr'):tag('th'):attr('colspan', '9'):wikitext((compiled_data.played_before_2022 and "Полный список матчей начиная с ЧТМ-2022" or "Полный список матчей") .. match_gear)
            local url_matches = "https://thirdworldcup.ru/index.php?title=%D0%9F%D0%BE%D0%B4%D1%81%D1%82%D1%80%D0%B0%D0%BD%D0%B8%D1%86%D0%B0:%D0%A0%D0%B0%D0%B7%D0%B2%D1%91%D1%80%D1%82%D0%BA%D0%B0_%D1%88%D0%B0%D0%B1%D0%BB%D0%BE%D0%BD%D0%BE%D0%B2/%D0%A1%D0%BF%D0%B8%D1%81%D0%BE%D0%BA_%D0%BC%D0%B0%D1%82%D1%87%D0%B5%D0%B9&action=edit"
       
            local match_gear = " [[Файл:Gear icon.svg|12px|link=" .. url_matches .. "]] "
        local h_tr = t_list:tag('tr')
           
        local cols = {"№", "Настоящая<br>дата", "ЧТМ<br>(№ матча)", "Раунд", "Команда", "Соперник", "Счёт", "Статистика", "Дополнительно"}
            local list_classes = 'wikitable mw-collapsible'
        for _, col in ipairs(cols) do h_tr:tag('th'):attr('scope', 'col'):cssText(Config.styles.header):wikitext(col) end
            if show_main then list_classes = list_classes .. ' mw-collapsed' end
           
            local t_list = mw.html.create('table'):addClass(list_classes)
            t_list:tag('tr'):tag('th'):attr('colspan', '9'):wikitext((compiled_data.played_before_2022 and "Полный список матчей начиная с ЧТМ-2022" or "Полный список матчей") .. match_gear)
           
            local h_tr = t_list:tag('tr')
            local cols = {"№", "Настоящая<br>дата", "ЧТМ<br>(№ матча)", "Раунд", "Команда", "Соперник", "Счёт", "Статистика", "Дополнительно"}
            for _, col in ipairs(cols) do h_tr:tag('th'):attr('scope', 'col'):cssText(Config.styles.header):wikitext(col) end
 
            local counter = 1
            for _, m in ipairs(pml) do
                local tr = t_list:tag('tr')
                local bg_color = get_match_color(m)
                local style_td = "white-space:nowrap;text-align:center;" .. (bg_color ~= "" and ("background-color:" .. bg_color .. ";") or "")


        local counter = 1
                tr:tag('td'):cssText(style_td):wikitext(m.is_official and tostring(counter) or ""); if m.is_official then counter = counter + 1 end
        for _, m in ipairs(pml) do
                tr:tag('td'):cssText(style_td):wikitext(m.is_official and (m.date ~= "" and (m.date:sub(9,10).."."..m.date:sub(6,7).."."..m.date:sub(1,4)) or "") or "")
            local tr = t_list:tag('tr')
                tr:tag('td'):cssText(style_td):wikitext("[[" .. m.year .. "]] (" .. m.match_num_id .. ")")
            local bg_color = get_match_color(m)
                tr:tag('td'):cssText(style_td):wikitext(format_stage(m.stage, m.letter))
            local style_td = "white-space:nowrap;text-align:center;" .. (bg_color ~= "" and ("background-color:" .. bg_color .. ";") or "")


            tr:tag('td'):cssText(style_td):wikitext(m.is_official and tostring(counter) or ""); if m.is_official then counter = counter + 1 end
                local score_txt = format_score(m); if m.wikilink then score_txt = "'''[[" .. m.wikilink .. "|" .. score_txt .. "]]'''" end
            tr:tag('td'):cssText(style_td):wikitext(m.is_official and (m.date ~= "" and (m.date:sub(9,10).."."..m.date:sub(6,7).."."..m.date:sub(1,4)) or "") or "")
            tr:tag('td'):cssText(style_td):wikitext("[[" .. m.year .. "]] (" .. m.match_num_id .. ")")
            tr:tag('td'):cssText(style_td):wikitext(format_stage(m.stage, m.letter))


            local score_txt = format_score(m); if m.wikilink then score_txt = "'''[[" .. m.wikilink .. "|" .. score_txt .. "]]'''" end
                if m.role_team == 0 then
                    tr:tag('td'):attr('colspan', '3'):cssText(style_td):wikitext("Вратарь ([[" .. Teams.getName(m.team1, 'short') .. "]] - [[" .. Teams.getName(m.team2, 'short') .. "]] - " .. score_txt .. ")")
                else
                    tr:tag('td'):cssText(style_td):wikitext("[[" .. Teams.getName((m.role_team == 1) and m.team1 or m.team2, 'short') .. "]]")
                    tr:tag('td'):cssText(style_td):wikitext("[[" .. Teams.getName((m.role_team == 1) and m.team2 or m.team1, 'short') .. "]]")
                    tr:tag('td'):cssText(style_td):wikitext(score_txt)
                end


            if m.role_team == 0 then
                local s_arr = {}
                tr:tag('td'):attr('colspan', '3'):cssText(style_td):wikitext("Вратарь ([[" .. Teams.getName(m.team1, 'short') .. "]] - [[" .. Teams.getName(m.team2, 'short') .. "]] - " .. score_txt .. ")")
                if m.goals > 0 then table.insert(s_arr, "'''" .. (m.goals > 1 and m.goals or "") .. "Г'''") end
            else
                if m.assists > 0 then table.insert(s_arr, "'''" .. (m.assists > 1 and m.assists or "") .. "П'''") end
                 tr:tag('td'):cssText(style_td):wikitext("[[" .. Teams.getName((m.role_team == 1) and m.team1 or m.team2, 'short') .. "]]")
                if m.is_mvp then table.insert(s_arr, "'''<u>MVP</u>'''") end
                 tr:tag('td'):cssText(style_td):wikitext("[[" .. Teams.getName((m.role_team == 1) and m.team2 or m.team1, 'short') .. "]]")
                 tr:tag('td'):cssText(style_td):wikitext(table.concat(s_arr, ",&nbsp;"))
                tr:tag('td'):cssText(style_td):wikitext(score_txt)
               
                -- 3. РАСПАКОВЫВАЕМ m.events, чтобы корректно работали оператор длины (#) и table.concat
                local safe_events = {}
                if m.events then
                    for _, ev in ipairs(m.events) do table.insert(safe_events, ev) end
                end
               
                 tr:tag('td'):cssText(style_td):wikitext(#safe_events > 0 and ("<small>" .. table.concat(safe_events, "<br>") .. "</small>") or "<small></small>")
             end
             end
 
             html_list = tostring(t_list)
             local s_arr = {}
            if m.goals > 0 then table.insert(s_arr, "'''" .. (m.goals > 1 and m.goals or "") .. "Г'''") end
            if m.assists > 0 then table.insert(s_arr, "'''" .. (m.assists > 1 and m.assists or "") .. "П'''") end
            if m.is_mvp then table.insert(s_arr, "'''<u>MVP</u>'''") end
            tr:tag('td'):cssText(style_td):wikitext(table.concat(s_arr, ",&nbsp;"))
            tr:tag('td'):cssText(style_td):wikitext(#m.events > 0 and ("<small>" .. table.concat(m.events, "<br>") .. "</small>") or "<small></small>")
         end
         end
        html_list = tostring(t_list)
     end
     end


Строка 220: Строка 239:
          
          
         local show_nav = {
         local show_nav = {
             champs = (N.champ_counts[player_name] or 0) > 0, superchamps = false, zshar = false, zbashmak = false, elnur = false,
             champs = (N.champ_counts and N.champ_counts[player_name] or 0) > 0, superchamps = false, zshar = false, zbashmak = false, elnur = false,
             final_goals = (N.final_goals[player_name] or 0) > 0, final_assists = (N.final_assists[player_name] or 0) > 0,
             final_goals = (N.final_goals and N.final_goals[player_name] or 0) > 0, final_assists = (N.final_assists and N.final_assists[player_name] or 0) > 0,
             club100 = (N.global_goals[player_name] or 0) >= 100, loyalty = false,
             club100 = (N.global_goals and N.global_goals[player_name] or 0) >= 100, loyalty = false,
             org = (player_name == "Диман" or player_name == "Антон" or player_name == "Геныч")
             org = (player_name == "Диман" or player_name == "Антон" or player_name == "Геныч")
         }
         }
Строка 231: Строка 250:
             local icon_td = args.noIcon and '<td style="vertical-align:middle; text-align:left; padding:0; display:none;"></td>'  
             local icon_td = args.noIcon and '<td style="vertical-align:middle; text-align:left; padding:0; display:none;"></td>'  
                 or string.format('<td style="vertical-align:middle; text-align:left; padding:0; width:%s;">%s</td>', args.iconW or '30px', args.icon)
                 or string.format('<td style="vertical-align:middle; text-align:left; padding:0; width:%s;">%s</td>', args.iconW or '30px', args.icon)
           
             local full_edit = mw.uri.encode("Шаблон:" .. args.editName, "PATH")
             local full_edit = mw.uri.encode("Шаблон:" .. args.editName, "PATH")
             local url_edit = "https://thirdworldcup.ru/index.php?title=" .. full_edit .. "&action=edit"
             local url_edit = "https://thirdworldcup.ru/index.php?title=" .. full_edit .. "&action=edit"
             local url_view = "https://thirdworldcup.ru/index.php/" .. full_edit
             local url_view = "https://thirdworldcup.ru/index.php/" .. full_edit
           
             local gear_img = "[[Файл:Gear icon.svg|12px|link=" .. url_view .. "]]"
             local gear_img = "[[Файл:Gear icon.svg|12px|link=" .. url_view .. "]]"
             local edit_link = "[" .. url_edit .. ' <span title="Редактировать">&nbsp;' .. gear_img .. '&nbsp;</span>]'
             local edit_link = "[" .. url_edit .. ' <span title="Редактировать">&nbsp;' .. gear_img .. '&nbsp;</span>]'
Строка 257: Строка 274:
             for y, _ in pairs(N.champs) do table.insert(v_years, y) end
             for y, _ in pairs(N.champs) do table.insert(v_years, y) end
             table.sort(v_years)
             table.sort(v_years)
           
             local running_counts = {}
             local running_counts = {}
             for i, y in ipairs(v_years) do
             for i, y in ipairs(v_years) do
                 local p_list = N.champs[y]; table.sort(p_list)
                -- КОПИРУЕМ СПИСОК ПЕРЕД СОРТИРОВКОЙ
                 local p_list = {}
                for _, p_n in ipairs(N.champs[y]) do table.insert(p_list, p_n) end
                table.sort(p_list)
               
                 local fps = {}
                 local fps = {}
                 for _, p_name in ipairs(p_list) do
                 for _, p_name in ipairs(p_list) do
Строка 279: Строка 299:
         if show_nav.superchamps then add_nav({bg='DarkGray', icon='[[Файл:Суперчемпион.png|30px|]]', editName='Суперчемпионы', title='[[Суперчемпион]]ы', cat='[[Категория:Суперчемпионы]]', content=flat_chron(N.superchamps)}) end
         if show_nav.superchamps then add_nav({bg='DarkGray', icon='[[Файл:Суперчемпион.png|30px|]]', editName='Суперчемпионы', title='[[Суперчемпион]]ы', cat='[[Категория:Суперчемпионы]]', content=flat_chron(N.superchamps)}) end
         if show_nav.zshar then add_nav({bg='PaleGreen', icon='[[Файл:ЗШар.png|30px|]]', editName='Лучшие игроки ЧТМ', title='[[Золотой Шар|Лучшие игроки ЧТМ]]', cat='[[Категория:Обладатели Золотого Шара]]', content=flat_chron(N.zshar)}) end
         if show_nav.zshar then add_nav({bg='PaleGreen', icon='[[Файл:ЗШар.png|30px|]]', editName='Лучшие игроки ЧТМ', title='[[Золотой Шар|Лучшие игроки ЧТМ]]', cat='[[Категория:Обладатели Золотого Шара]]', content=flat_chron(N.zshar)}) end
         if show_nav.zbashmak then
         if show_nav.zbashmak then
             local grp, sy, parts = {}, {}, {}
             local grp, sy, parts = {}, {}, {}
Строка 312: Строка 331:


         if show_nav.loyalty then
         if show_nav.loyalty then
             table.sort(N.loyalty, function(a,b) if a[1] ~= b[1] then return a[1] < b[1] end return a[2] < b[2] end); local pts = {}
            -- КОПИРУЕМ МАССИВ ПЕРЕД СОРТИРОВКОЙ
             for _, i in ipairs(N.loyalty) do table.insert(pts, "[["..i[1].."]] — [["..i[2].."]] (''[["..(Teams.getName(i[3], 'short') or i[3]).."]]'')") end
            local loy = {}
            for _, i in ipairs(N.loyalty) do table.insert(loy, i) end
             table.sort(loy, function(a,b) if a[1] ~= b[1] then return a[1] < b[1] end return a[2] < b[2] end)
           
            local pts = {}
             for _, i in ipairs(loy) do table.insert(pts, "[["..i[1].."]] — [["..i[2].."]] (''[["..(Teams.getName(i[3], 'short') or i[3]).."]]'')") end
             add_nav({bg='MediumAquamarine', noIcon=true, editName='Верность команде', title='Обладатели приза «[[Верность команде]]»', cat='[[Категория:Обладатели приза «Верность команде»]]', content='<span style="font-size:120%;">'..table.concat(pts, "&nbsp;&bull; ")..'</span>'})
             add_nav({bg='MediumAquamarine', noIcon=true, editName='Верность команде', title='Обладатели приза «[[Верность команде]]»', cat='[[Категория:Обладатели приза «Верность команде»]]', content='<span style="font-size:120%;">'..table.concat(pts, "&nbsp;&bull; ")..'</span>'})
         end
         end
Строка 348: Строка 372:
     local out_str = Config.styles.wiki_templates
     local out_str = Config.styles.wiki_templates
      
      
    -- Добавляем заголовок "== Статистика ==" только если выводится главная таблица
     if show_main then out_str = out_str .. "== Статистика ==\n" .. html_main .. "\n" end
     if show_main then  
        out_str = out_str .. "== Статистика ==\n" .. html_main .. "\n"  
    end
      
      
     if show_matches then
     if show_matches then
        if not show_main then out_str = out_str .. "== Список матчей ==\n" end
         out_str = out_str .. html_list .. "\n"
         out_str = out_str .. html_list .. "\n"
     else
     else