-- ApiVault UI / XML / Widgets workflow panel for AppShell. Added in v1.3.1.
local addonName, ApiVault = ...

ApiVault.UIMetadataPanel = ApiVault.UIMetadataPanel or {}
local Panel = ApiVault.UIMetadataPanel

local function createText(parent, template)
    local fs = parent:CreateFontString(nil, "OVERLAY", template or "GameFontNormal")
    fs:SetJustifyH("LEFT")
    fs:SetJustifyV("TOP")
    return fs
end

local function createBackdropFrame(name, parent)
    return CreateFrame("Frame", name, parent, BackdropTemplateMixin and "BackdropTemplate" or nil)
end

local function setBackdrop(frame)
    if not frame.SetBackdrop then return end
    frame:SetBackdrop({
        bgFile = "Interface\\DialogFrame\\UI-DialogBox-Background",
        edgeFile = "Interface\\Tooltips\\UI-Tooltip-Border",
        tile = true,
        tileSize = 16,
        edgeSize = 12,
        insets = { left = 4, right = 4, top = 4, bottom = 4 },
    })
    frame:SetBackdropColor(0.02, 0.02, 0.03, 0.86)
end

function Panel:Clear(parent)
    if parent.ApiVaultUIChildren then
        for _, child in ipairs(parent.ApiVaultUIChildren) do
            if child.Hide then child:Hide() end
            if child.SetParent then child:SetParent(nil) end
        end
    end
    parent.ApiVaultUIChildren = {}
end

function Panel:Add(parent, child)
    parent.ApiVaultUIChildren = parent.ApiVaultUIChildren or {}
    table.insert(parent.ApiVaultUIChildren, child)
    return child
end

function Panel:SetOutput(text)
    if self.output then
        if ApiVault.CapOutputText then text = ApiVault:CapOutputText(text) end
        self.output:SetText(tostring(text or ""))
        self.output:SetCursorPosition(0)
    end
end

function Panel:ShowSummary()
    local lines = {}
    table.insert(lines, "ApiVault UI / XML / Widgets")
    table.insert(lines, "")
    if ApiVault.InterfaceResources and ApiVault.InterfaceResources.GetStats then
        local files, folders, modules = ApiVault.InterfaceResources:GetStats()
        table.insert(lines, "Interface Resources: files=" .. tostring(files) .. ", folders=" .. tostring(folders) .. ", modules=" .. tostring(modules))
    end
    if ApiVault.XMLCatalog and ApiVault.XMLCatalog.GetStats then
        local templates, xmlFiles, virtualTemplates, secureTemplates = ApiVault.XMLCatalog:GetStats()
        table.insert(lines, "XML Templates: templates=" .. tostring(templates) .. ", files=" .. tostring(xmlFiles) .. ", virtual=" .. tostring(virtualTemplates) .. ", secureRefs=" .. tostring(secureTemplates))
    end
    if ApiVault.LazyData then ApiVault.LazyData:Ensure("widgets") end
    if ApiVault.Widgets and ApiVault.Widgets.GetStats then
        local widgetTotal, methods, scripts, createFrames, setScripts = ApiVault.Widgets:GetStats()
        table.insert(lines, "Widgets: total=" .. tostring(widgetTotal) .. ", methods=" .. tostring(methods) .. ", scripts=" .. tostring(scripts) .. ", createFrameRefs=" .. tostring(createFrames) .. ", setScriptRefs=" .. tostring(setScripts))
    end
    if ApiVault.ModuleCatalog and ApiVault.ModuleCatalog.GetStats then
        local tocEntries, moduleEntries, tocFileRefs = ApiVault.ModuleCatalog:GetStats()
        table.insert(lines, "Modules: TOCs=" .. tostring(tocEntries) .. ", modules=" .. tostring(moduleEntries) .. ", fileRefs=" .. tostring(tocFileRefs))
    end
    table.insert(lines, "")
    table.insert(lines, "Use the buttons above to open the detailed browsers.")
    self:SetOutput(table.concat(lines, "\n"))
end

function Panel:OpenInterface()
    if ApiVault.InterfaceBrowser and ApiVault.InterfaceBrowser.Open then ApiVault.InterfaceBrowser:Open()
    elseif ApiVault.InterfaceBrowser and ApiVault.InterfaceBrowser.Toggle then ApiVault.InterfaceBrowser:Toggle()
    else self:SetOutput("Interface Browser unavailable.") end
end

function Panel:OpenXML()
    if ApiVault.XMLTemplateBrowser and ApiVault.XMLTemplateBrowser.Open then ApiVault.XMLTemplateBrowser:Open()
    elseif ApiVault.XMLTemplateBrowser and ApiVault.XMLTemplateBrowser.Toggle then ApiVault.XMLTemplateBrowser:Toggle()
    else self:SetOutput("XML Template Browser unavailable.") end
end

function Panel:OpenWidgets(mode)
    if ApiVault.LazyData then ApiVault.LazyData:Ensure("widgets") end
    if ApiVault.WidgetMethodBrowser and ApiVault.WidgetMethodBrowser.Open then ApiVault.WidgetMethodBrowser:Open(mode or "All")
    elseif ApiVault.WidgetMethodBrowser and ApiVault.WidgetMethodBrowser.Toggle then ApiVault.WidgetMethodBrowser:Toggle()
    else self:SetOutput("Widget Browser unavailable.") end
end

function Panel:OpenModules()
    if ApiVault.ModuleBrowser and ApiVault.ModuleBrowser.Open then ApiVault.ModuleBrowser:Open()
    elseif ApiVault.ModuleBrowser and ApiVault.ModuleBrowser.Toggle then ApiVault.ModuleBrowser:Toggle()
    else self:SetOutput("Module Browser unavailable.") end
end

function Panel:Render(parent)
    self:Clear(parent)

    local title = self:Add(parent, createText(parent, "GameFontHighlightLarge"))
    title:SetPoint("TOPLEFT", parent, "TOPLEFT", 20, -18)
    title:SetText("UI / XML / Widgets")

    local sub = self:Add(parent, createText(parent, "GameFontDisable"))
    sub:SetPoint("TOPLEFT", title, "BOTTOMLEFT", 0, -8)
    sub:SetPoint("RIGHT", parent, "RIGHT", -20, 0)
    sub:SetText("Browse Interface resources, XML templates, widget methods, CreateFrame references and module metadata.")

    local interface = self:Add(parent, CreateFrame("Button", nil, parent, "UIPanelButtonTemplate"))
    interface:SetSize(132, 22)
    interface:SetPoint("TOPLEFT", parent, "TOPLEFT", 20, -78)
    interface:SetText("Interface Files")
    interface:SetScript("OnClick", function() Panel:OpenInterface() end)

    local xml = self:Add(parent, CreateFrame("Button", nil, parent, "UIPanelButtonTemplate"))
    xml:SetSize(118, 22)
    xml:SetPoint("LEFT", interface, "RIGHT", 6, 0)
    xml:SetText("XML Templates")
    xml:SetScript("OnClick", function() Panel:OpenXML() end)

    local widgets = self:Add(parent, CreateFrame("Button", nil, parent, "UIPanelButtonTemplate"))
    widgets:SetSize(96, 22)
    widgets:SetPoint("LEFT", xml, "RIGHT", 6, 0)
    widgets:SetText("Widgets")
    widgets:SetScript("OnClick", function() Panel:OpenWidgets("All") end)

    local createFrame = self:Add(parent, CreateFrame("Button", nil, parent, "UIPanelButtonTemplate"))
    createFrame:SetSize(112, 22)
    createFrame:SetPoint("LEFT", widgets, "RIGHT", 6, 0)
    createFrame:SetText("CreateFrame")
    createFrame:SetScript("OnClick", function() Panel:OpenWidgets("CreateFrame") end)

    local modules = self:Add(parent, CreateFrame("Button", nil, parent, "UIPanelButtonTemplate"))
    modules:SetSize(90, 22)
    modules:SetPoint("LEFT", createFrame, "RIGHT", 6, 0)
    modules:SetText("Modules")
    modules:SetScript("OnClick", function() Panel:OpenModules() end)

    local bg = self:Add(parent, createBackdropFrame(nil, parent))
    bg:SetPoint("TOPLEFT", parent, "TOPLEFT", 20, -118)
    bg:SetPoint("BOTTOMRIGHT", parent, "BOTTOMRIGHT", -20, 20)
    setBackdrop(bg)

    local scroll = self:Add(parent, CreateFrame("ScrollFrame", nil, bg, "UIPanelScrollFrameTemplate"))
    scroll:SetPoint("TOPLEFT", bg, "TOPLEFT", 12, -12)
    scroll:SetPoint("BOTTOMRIGHT", bg, "BOTTOMRIGHT", -30, 12)

    local output = self:Add(parent, CreateFrame("EditBox", nil, scroll))
    self.output = output
    output:SetMultiLine(true)
    output:SetAutoFocus(false)
    output:SetFontObject(ChatFontNormal)
    output:SetWidth(720)
    output:SetText("")
    output:SetScript("OnEscapePressed", function(box) box:ClearFocus() end)
    scroll:SetScrollChild(output)

    parent:SetScript("OnSizeChanged", function()
        if output and bg then output:SetWidth(math.max(520, bg:GetWidth() - 50)) end
    end)

    self:ShowSummary()
end
