local GenericFooter = ZO_Object:Subclass() ZO_GAMEPAD_FOOTER_CONTROLS = { DATA1 = 1, DATA1HEADER = 2, DATA1LOADINGICON = 3, DATA2 = 4, DATA2HEADER = 5, DATA2LOADINGICON = 6, DATA3 = 7, DATA3HEADER = 8, DATA3LOADINGICON = 9, } local EMPTY_TABLE = {} -- Alias the control names to make the code less verbose and more readable. local DATA1 = ZO_GAMEPAD_FOOTER_CONTROLS.DATA1 local DATA1HEADER = ZO_GAMEPAD_FOOTER_CONTROLS.DATA1HEADER local DATA1LOADINGICON = ZO_GAMEPAD_FOOTER_CONTROLS.DATA1LOADINGICON local DATA2 = ZO_GAMEPAD_FOOTER_CONTROLS.DATA2 local DATA2HEADER = ZO_GAMEPAD_FOOTER_CONTROLS.DATA2HEADER local DATA2LOADINGICON = ZO_GAMEPAD_FOOTER_CONTROLS.DATA2LOADINGICON local DATA3 = ZO_GAMEPAD_FOOTER_CONTROLS.DATA3 local DATA3HEADER = ZO_GAMEPAD_FOOTER_CONTROLS.DATA3HEADER local DATA3LOADINGICON = ZO_GAMEPAD_FOOTER_CONTROLS.DATA3LOADINGICON function GenericFooter:New(...) local object = ZO_Object.New(self) object:Initialize(...) return object end function GenericFooter:Initialize(control) self.control = control self.controls = { [DATA1] = control:GetNamedChild("Data1"), [DATA1HEADER] = control:GetNamedChild("Data1Header"), [DATA1LOADINGICON] = control:GetNamedChild("Data1LoadingIcon"), [DATA2] = control:GetNamedChild("Data2"), [DATA2HEADER] = control:GetNamedChild("Data2Header"), [DATA2LOADINGICON] = control:GetNamedChild("Data2LoadingIcon"), [DATA3] = control:GetNamedChild("Data3"), [DATA3HEADER] = control:GetNamedChild("Data3Header"), [DATA3LOADINGICON] = control:GetNamedChild("Data3LoadingIcon"), } control.OnHidden = function() self:Refresh(EMPTY_TABLE) end end local function ProcessData(control, textData, anchorToBaselineControl, anchorToBaselineOffsetX, overrideColor) if control == nil then return false end if type(textData) == "function" then textData = textData(control) end if type(textData) == "string" or type(textData) == "number" then if overrideColor then textData = overrideColor:Colorize(textData) end control:SetText(textData) end control:SetHidden(not textData) if anchorToBaselineControl then control:ClearAnchorToBaseline(anchorToBaselineControl) if textData then control:AnchorToBaseline(anchorToBaselineControl, anchorToBaselineOffsetX, LEFT) else -- This is to make sure there is no gap when a control is missing. control:AnchorToBaseline(anchorToBaselineControl, 0, LEFT) end end control:SetHidden(not textData) return textData ~= nil end local function GetProcessedNarrationText(control, data) if control == nil or data == nil then return "" end if type(data) == "function" then data = data(control) end if type(data) == "string" then return data elseif type(data) == "number" then return tostring(data) else internalassert(false, "Unsupported data type. A custom narration function will need to be set for this control that returns a string or number.") end return "" end function GenericFooter:Refresh(data) local controls = self.controls local loadingIcon1Offset = data.data1ShowLoading and ZO_GAMEPAD_LOADING_ICON_FOOTER_SIZE or 0 controls[DATA1LOADINGICON]:SetHidden(not data.data1ShowLoading) local loadingIcon2Offset = data.data2ShowLoading and ZO_GAMEPAD_LOADING_ICON_FOOTER_SIZE or 0 controls[DATA2LOADINGICON]:SetHidden(not data.data2ShowLoading) local loadingIcon3Offset = data.data3ShowLoading and ZO_GAMEPAD_LOADING_ICON_FOOTER_SIZE or 0 controls[DATA3LOADINGICON]:SetHidden(not data.data3ShowLoading) ProcessData(controls[DATA1], data.data1Text, nil, nil, data.data1Color) ProcessData(controls[DATA1HEADER], data.data1HeaderText, controls[DATA1], -ZO_GAMEPAD_DEFAULT_HEADER_DATA_PADDING - loadingIcon1Offset, data.data1HeaderColor) ProcessData(controls[DATA2], data.data2Text, controls[DATA1HEADER], -ZO_GAMEPAD_CONTENT_INSET_X, data.data2Color) ProcessData(controls[DATA2HEADER], data.data2HeaderText, controls[DATA2], -ZO_GAMEPAD_DEFAULT_HEADER_DATA_PADDING - loadingIcon2Offset, data.data2HeaderColor) ProcessData(controls[DATA3], data.data3Text, controls[DATA2HEADER], -ZO_GAMEPAD_CONTENT_INSET_X, data.data3Color) ProcessData(controls[DATA3HEADER], data.data3HeaderText, controls[DATA3], -ZO_GAMEPAD_DEFAULT_HEADER_DATA_PADDING - loadingIcon3Offset, data.data3HeaderColor) end function GenericFooter:GetChildControl(index) if self.controls then return self.controls[index] end return nil end function GenericFooter:GetNarrationText(data) local narration = SCREEN_NARRATION_MANAGER:CreateNarratableObject() local controls = self.controls -- We narrate these in reverse numerical order because they're laid out from right to left narration:AddNarrationText(GetProcessedNarrationText(controls[DATA3HEADER], data.data3HeaderTextNarration or data.data3HeaderText)) narration:AddNarrationText(GetProcessedNarrationText(controls[DATA3], data.data3TextNarration or data.data3Text)) narration:AddNarrationText(GetProcessedNarrationText(controls[DATA2HEADER], data.data2HeaderTextNarration or data.data2HeaderText)) narration:AddNarrationText(GetProcessedNarrationText(controls[DATA2], data.data2TextNarration or data.data2Text)) narration:AddNarrationText(GetProcessedNarrationText(controls[DATA1HEADER], data.data1HeaderTextNarration or data.data1HeaderText)) narration:AddNarrationText(GetProcessedNarrationText(controls[DATA1], data.data1TextNarration or data.data1Text)) return narration end function ZO_GenericFooter_Gamepad_OnInitialized(self) GAMEPAD_GENERIC_FOOTER = GenericFooter:New(self) end function ZO_GenericFooter_Gamepad_OnHidden(self) self.OnHidden() end