mercDenWnd.py (18308B)
1 #Embedded file name: C:\BuildAgent\work\20d73f1b24eed06e\eve\release\V24.01\eve\client\script\ui\shared\planet\mecDen\mercDenWnd.py 2 import appConst 3 import carbonui.text.styles 4 import eveicon 5 import uthread2 6 from ballparkCommon.parkhelpers.warpSubjects import WarpSubjects 7 from carbon.common.script.sys.serviceConst import ROLE_PROGRAMMER 8 from carbon.common.script.util.format import FmtAmt 9 from carbon.common.script.util.timerstuff import AutoTimer 10 from carbonui import Align, ButtonStyle, TextColor, TextAlign, ButtonFrameType 11 from carbonui.control.button import Button 12 from carbonui.control.contextMenu.menuData import MenuData 13 from carbonui.control.contextMenu.menuEntryData import MenuEntryData 14 from carbonui.control.scroll import Scroll 15 from carbonui.control.window import Window 16 from carbonui.decorative.panelUnderlay import PanelUnderlay 17 from carbonui.primitives.container import Container 18 from carbonui.primitives.containerAutoSize import ContainerAutoSize 19 from eve.client.script.ui import eveColor 20 from eve.client.script.ui.control.loadingContainer import LoadingContainer 21 from eve.client.script.ui.control.scrollUtil import TabFinder 22 from eve.client.script.ui.control.statefulButton import StatefulButton 23 from eve.client.script.ui.shared.agencyNew.contentGroups.contentGroupConst import contentGroupMercDens 24 from eve.client.script.ui.shared.agencyNew.ui.agencyWnd import AgencyWndNew 25 from eve.client.script.ui.shared.cloneGrade import ORGIN_MY_MERCDENS 26 from eve.client.script.ui.shared.planet.mecDen.btnController import MercDenButtonController 27 from eve.client.script.ui.shared.planet.mecDen.mercDenEntry import MerDenEntry, GetMercDenEntry, GetEmptySlotEntry, MerDenEmptySlotEntry, GetMercDenEntryData, BaseMerDenEntry 28 from eve.client.script.ui.shared.planet.mecDen.mercDenUiController import MercDenUiController 29 from eve.client.script.ui.shared.sov.threadedLoader import ThreadedLoader 30 from eveexceptions import ExceptionEater 31 from eveservices.menu import GetMenuService 32 from inventorycommon.const import typeMercenaryDenManagementSkill 33 from localization import GetByLabel 34 import carbonui 35 from menu import MenuLabel 36 from signals.signalUtil import ChangeSignalConnect 37 from sovereignty.mercenaryden.client.mercenary_den_signals import on_mercenary_den_removed, on_mercenary_den_added, on_mercenary_den_changed 38 from sovereignty.mercenaryden.client.ui.containers.management import ManagementContainerWithTabs 39 from sovereignty.mercenaryden.client.ui.containers.summary import SummaryContainer 40 from sovereignty.mercenaryden.client.ui.controller import MercenaryDenController 41 from carbonui.uicore import uicore 42 RIGHT_WIDTH = 416 43 44 class MyMercDensWnd(Window): 45 __notifyevents__ = ['OnSkillsChanged', 'OnSubscriptionChanged_Local'] 46 default_width = 900 47 default_height = 572 48 default_minSize = (650, 572) 49 default_windowID = 'myMercDensWnd' 50 default_captionLabelPath = 'UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/MyMercenaryDens' 51 default_descriptionLabelPath = 'UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/MyMercenaryDensDesc' 52 default_iconNum = eveicon.mercenary_den_product_icon 53 54 def DebugReload(self, *args): 55 self.Reload(self) 56 57 def GetMenuMoreOptions(self): 58 menu_data = super(MyMercDensWnd, self).GetMenuMoreOptions() 59 if session.role & ROLE_PROGRAMMER: 60 menu_data.AddEntry('QA Reload', self.DebugReload) 61 return menu_data 62 63 def ApplyAttributes(self, attributes): 64 self.threadedLoader = ThreadedLoader() 65 self.statefulBtn = None 66 self._btnUpdateThread = None 67 self._selectedMercDenController = None 68 super(MyMercDensWnd, self).ApplyAttributes(attributes) 69 self.uiController = MercDenUiController() 70 self.ConstructUI() 71 self.LoadWindow() 72 self.ChangeSignalConnection(connect=True) 73 sm.RegisterNotify(self) 74 75 def ChangeSignalConnection(self, connect = True): 76 signalAndCallback = [(on_mercenary_den_removed, self.OnMercenaryDenAddedOrRemoved), (on_mercenary_den_added, self.OnMercenaryDenAddedOrRemoved), (on_mercenary_den_changed, self.OnMercenaryDenChanged)] 77 ChangeSignalConnect(signalAndCallback, connect) 78 79 def ConstructUI(self): 80 self.rightCont = Container(name='rightCont', parent=self.content, align=Align.TORIGHT, width=RIGHT_WIDTH, padLeft=16) 81 self.loadingCont = LoadingContainer(parent=self.content, failureStateMessage=GetByLabel('UI/Sovereignty/SovHub/HubWnd/FailedToFetchData'), retryBtnLabel=GetByLabel('UI/Personalization/PaintTool/ErrorRetry')) 82 self.leftCont = Container(name='leftCont', parent=self.loadingCont) 83 self.ConstructLeft() 84 self.ConstructRight() 85 86 def ConstructLeft(self): 87 bgColor = eveColor.WHITE[:3] + (0.05,) 88 deployedCont = ContainerAutoSize(parent=self.leftCont, align=Align.TOTOP, bgColor=bgColor, alignMode=Align.CENTERLEFT, top=16) 89 self.noDeployedContainer = ContainerAutoSize(parent=self.leftCont, align=Align.TOTOP, alignMode=Align.TOTOP, top=16) 90 self.noDeployedLabel = carbonui.text.styles.TextBody(parent=self.noDeployedContainer, text=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/NoDensMessage'), padding=8, align=Align.TOTOP, textAlign=TextAlign.CENTER) 91 buttonCont = ContainerAutoSize(parent=self.noDeployedContainer, align=Align.TOTOP, alignMode=Align.CENTERTOP) 92 self.noDeployedButton = Button(parent=buttonCont, align=Align.CENTERTOP, label=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/OpenAgencyButton'), func=lambda *args: self.OpenAgency(), frame_type=ButtonFrameType.CUT_BOTTOM_LEFT_RIGHT, texturePath='res:/UI/Texture/classes/agency/icons/agency.png') 93 self.noDeployedContainer.display = False 94 self.skillCont = Container(name='skillCont', parent=self.leftCont, align=Align.TOBOTTOM, top=8) 95 self.skillBntCont = Container(name='skillBntCont', parent=self.skillCont, align=Align.TORIGHT) 96 self.skillTextCont = Container(name='skillTextCont', parent=self.skillCont, align=Align.TOALL, clipChildren=True, padLeft=8) 97 textPadding = 8 98 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/DeployedDens') 99 carbonui.text.styles.TextBody(parent=deployedCont, text=text, padding=textPadding, align=Align.CENTERLEFT) 100 self.numDensLabel = carbonui.text.styles.TextBody(parent=deployedCont, text='', padding=textPadding, align=Align.CENTERRIGHT, pickState=carbonui.PickState.ON) 101 self.numDensLabel.LoadTooltipPanel = self.LoadNumDensTooltipPanel 102 self.scroll = Scroll(parent=self.leftCont, top=16, id='myMercDenScroll') 103 self.scroll.GetTabStops = self.GetTabStops 104 105 def ConstructRight(self): 106 PanelUnderlay(bgParent=self.rightCont) 107 self.buttonCont = Container(name='buttonCont', parent=self.rightCont, align=Align.TOBOTTOM, height=50) 108 self.summaryParentCont = ContainerAutoSize(name='summaryParentCont', parent=self.rightCont, align=Align.TOTOP) 109 self.mgmtParentCont = ContainerAutoSize(name='mgmtParentCont', parent=self.rightCont, align=Align.TOTOP, padding=(16, 16, 16, 0)) 110 111 def LoadWindow(self): 112 self.loadingCont.LoadContent(loadCallback=self.LoadLeftSide) 113 114 def OnMercenaryDenAddedOrRemoved(self, mercDenID): 115 delaySec = 3 116 uthread2.call_after_wallclocktime_delay(self.LoadLeftSide, delaySec) 117 118 def OnMercenaryDenChanged(self, mercDenID): 119 selectedNodes = self.scroll.GetSelected() 120 if selectedNodes: 121 mercDenEntryInfo = selectedNodes[0].mercDenEntryInfo 122 if mercDenEntryInfo and mercDenEntryInfo.item_id == mercDenID: 123 self.LoadRightSide(mercDenEntryInfo) 124 125 def LoadLeftSide(self): 126 if self.destroyed: 127 return 128 myMercDens = self.uiController.GetEntryInfosForMyMercDens() 129 myMaxDens = self.uiController.myMaxDenNum 130 scrollList = [] 131 selectedItemID = self.uiController.GetSelectedItemID() 132 denIDs = {x.item_id for x in myMercDens} 133 if not selectedItemID or selectedItemID not in denIDs: 134 if myMercDens: 135 selectedItemID = myMercDens[0].item_id 136 for eachDen in myMercDens: 137 isSelected = eachDen.item_id == selectedItemID 138 entry = GetMercDenEntry(self, eachDen, isSelected) 139 scrollList.append(entry) 140 141 numMercDens = len(myMercDens) 142 if numMercDens == 0: 143 self.noDeployedContainer.display = True 144 if myMaxDens is not None and myMaxDens > numMercDens and numMercDens > 0: 145 for x in xrange(myMaxDens - numMercDens): 146 entry = GetEmptySlotEntry() 147 scrollList.append(entry) 148 149 self.threadedLoader.StartLoading(self.UpdateDenNum, self) 150 self.threadedLoader.StartLoading(self.LoadSkillsCont, self) 151 headers = MerDenEntry.GetHeaders() 152 self.scroll.Load(contentList=scrollList, headers=headers) 153 self.UpdateHeaderHints() 154 if myMercDens: 155 self.rightCont.Show() 156 self.LoadRightSideFromScrollSelection() 157 else: 158 self.rightCont.Hide() 159 160 def UpdateHeaderHints(self): 161 for i, eachHeaderChild in enumerate(self.scroll.GetHeadersChildren()): 162 eachHeaderChild.GetHint = lambda idx = i: self.GetHeaderHint(idx) 163 164 def GetHeaderHint(self, idx, *args): 165 hint = None 166 headerHint = BaseMerDenEntry.GetHeadersHint(idx) 167 if headerHint: 168 hint = headerHint 169 if hint: 170 from carbonui.uicore import uicore 171 uicore.uilib.auxiliaryTooltip = None 172 return hint 173 174 def GetTabStops(self, headertabs, idx = None): 175 return TabFinder().GetTabStops(self.scroll.sr.nodes, headertabs, BaseMerDenEntry, idx=idx) 176 177 def OnMercDenClicked(self, entry): 178 node = entry.sr.node 179 mercDenEntryInfo = node.mercDenEntryInfo 180 self.uiController.SelectEntry(mercDenEntryInfo.item_id) 181 self.LoadRightSide(mercDenEntryInfo) 182 183 def GetMercDenMenu(self, entry): 184 node = entry.sr.node 185 m = MenuData() 186 if not node.mercDenEntryInfo.has_complete_info: 187 m = MenuData() 188 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/ReloadData') 189 m.AddEntry(text, func=lambda : self.ReloadEntry(entry)) 190 return m 191 itemID = node.mercDenEntryInfo.item_id 192 typeID = node.mercDenEntryInfo.type_id 193 solarSystemID = node.mercDenEntryInfo.solar_system_id 194 m.append(MenuEntryData(MenuLabel('UI/Common/Location'), subMenuData=GetMenuService().CelestialMenu(solarSystemID, typeID=appConst.groupSolarSystem))) 195 m += GetMenuService().GetMenuFromItemIDTypeID(itemID, typeID) 196 return m 197 198 def LoadMotTooltipPanel(self, tooltipPanel, node, *args): 199 numStarted = len({x for x in node.mercDenEntryInfo.activities if x.is_started}) 200 numActivities = len(node.mercDenEntryInfo.activities) 201 tooltipPanel.LoadStandardSpacing() 202 tooltipPanel.columns = 2 203 tooltipPanel.AddTextBodyLabel(text=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/AvailableMtoTooltip'), colSpan=tooltipPanel.columns, wrapWidth=200, color=TextColor.SECONDARY) 204 tooltipPanel.AddTextBodyLabel(text=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/StartedActivities')) 205 tooltipPanel.AddTextBodyLabel(text=FmtAmt(numStarted), align=Align.CENTERRIGHT) 206 tooltipPanel.AddTextBodyLabel(text=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/AvailableActivities')) 207 tooltipPanel.AddTextBodyLabel(text=numActivities, align=Align.CENTERRIGHT) 208 209 def ReloadEntry(self, entry): 210 node = entry.sr.node 211 isSelected = node.isSelected 212 mercDenEntryInfo = self.uiController.GetMercDenEntryInfo(node.mercDenEntryInfo.item_id) 213 newNode = GetMercDenEntryData(self, mercDenEntryInfo, isSelected) 214 node.update(newNode) 215 entry.Load(node) 216 self.scroll.UpdateTabStops() 217 218 def UpdateDenNum(self): 219 numDens = len([ x for x in self.scroll.GetNodes() if x.decoClass != MerDenEmptySlotEntry ]) 220 self.numDensLabel.text = self.uiController.GetDeployedDensText(numDens) 221 222 def LoadNumDensTooltipPanel(self, tooltipPanel, *args): 223 numDens = len([ x for x in self.scroll.GetNodes() if x.decoClass != MerDenEmptySlotEntry ]) 224 tooltipPanel.LoadStandardSpacing() 225 tooltipPanel.columns = 2 226 tooltipPanel.AddTextBodyLabel(text=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/DeployedDens')) 227 tooltipPanel.AddTextBodyLabel(text=numDens, align=Align.CENTERRIGHT) 228 myMax = self.uiController.myMaxDenNum 229 absoluteMax = self.uiController.absoluteMaxDenNum 230 if myMax is not None: 231 tooltipPanel.AddTextBodyLabel(text=GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/MyMaxDeployable')) 232 tooltipPanel.AddTextBodyLabel(text=myMax, align=Align.CENTERRIGHT) 233 if self.uiController.IsAlpha(): 234 if numDens: 235 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/AlphaMaxWithDensDeployed') 236 else: 237 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/AlphaMaxWithoutDensDeployed') 238 tooltipPanel.AddTextDetailsLabel(text=text, colSpan=tooltipPanel.columns, color=eveColor.OMEGA_YELLOW, wrapWidth=200) 239 elif myMax < absoluteMax: 240 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/MaxDeployedWithFullSkills', numDens=absoluteMax) 241 tooltipPanel.AddTextDetailsLabel(text=text, colSpan=tooltipPanel.columns, color=TextColor.SECONDARY, wrapWidth=200) 242 243 def LoadSkillsCont(self): 244 self.skillBntCont.Flush() 245 self.skillTextCont.Flush() 246 if self.uiController.IsAlpha(): 247 btn = Button(parent=self.skillBntCont, label=GetByLabel('Tooltips/SkillPlanner/UpgradeToOmega'), texturePath=eveicon.omega, style=ButtonStyle.MONETIZATION, func=self.OnOmegaBtnClicked, align=Align.CENTERRIGHT) 248 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/OmegaText') 249 elif self.uiController.CanTrainMoreSkills(): 250 btn = Button(name='skillTrainingBtn', parent=self.skillBntCont, texturePath=eveicon.skill_book, label=GetByLabel('UI/Agency/MercDen/OpenSkillTraining'), func=self.OpenSkillTraining, align=Align.CENTERRIGHT) 251 text = GetByLabel('UI/Sovereignty/MercenaryDen/MyMercenaryDensWindow/UnlockSlotsWithTraining') 252 else: 253 return 254 self.skillCont.height = btn.height 255 self.skillBntCont.width = btn.width 256 carbonui.text.styles.TextDetail(parent=self.skillTextCont, text=text, align=Align.CENTERLEFT, color=TextColor.SECONDARY, pickState=carbonui.PickState.ON, autoFadeSides=16) 257 258 def OnOmegaBtnClicked(self, *args): 259 uicore.cmd.OpenCloneUpgradeWindow(origin=ORGIN_MY_MERCDENS) 260 261 def OpenSkillTraining(self, *args): 262 uicore.cmd.OpenSkillsWindow() 263 264 def OpenAgency(self, *args): 265 AgencyWndNew.OpenAndShowContentGroup(contentGroupMercDens) 266 267 def LoadRightSideFromScrollSelection(self): 268 selectedNodes = self.scroll.GetSelected() 269 if selectedNodes: 270 mercDenEntryInfo = selectedNodes[0].mercDenEntryInfo 271 else: 272 mercDenEntryInfo = None 273 self.LoadRightSide(mercDenEntryInfo) 274 275 def LoadRightSide(self, denEntryInfo): 276 self.summaryParentCont.Flush() 277 self.mgmtParentCont.Flush() 278 self.buttonCont.Flush() 279 if denEntryInfo is None or not denEntryInfo.has_complete_info: 280 return 281 denTypeID = denEntryInfo.type_id 282 self.ClearSelectedMercDenController() 283 self._selectedMercDenController = MercenaryDenController(denEntryInfo.item_id, denTypeID, denEntryInfo.mercenary_den_info) 284 summary_header_container = SummaryContainer(name='summary_header_container', parent=self.summaryParentCont, align=Align.TOTOP, controller=self._selectedMercDenController, should_show_owner=True, should_show_skyhook_owner=True, should_show_infomorphs_collected=False, should_show_workforce_cost=True, should_show_bg=False) 285 summary_header_container.load_controller(self._selectedMercDenController) 286 mgmtCont = ManagementContainerWithTabs(name='mgmtCont', parent=self.mgmtParentCont, align=Align.TOTOP, controller=self._selectedMercDenController) 287 mgmtCont.load_controller(self._selectedMercDenController) 288 mgmtCont.set_width(RIGHT_WIDTH - self.mgmtParentCont.padLeft) 289 locationBtnController = MercDenButtonController(dockabeLocationID=None, solarSystemID=denEntryInfo.solar_system_id, typeID=denEntryInfo.type_id, itemID=denEntryInfo.item_id, warpSubject=WarpSubjects.MERCENARY_DEN) 290 self.statefulBtn = StatefulButton(name='stationButton', parent=self.buttonCont, align=Align.BOTTOMRIGHT, iconAlign=Align.TORIGHT, controller=locationBtnController, pos=(8, 8, 0, 0)) 291 self._btnUpdateThread = AutoTimer(1000, self.UpdateBtn_thread) 292 293 def ClearSelectedMercDenController(self): 294 if self._selectedMercDenController: 295 self._selectedMercDenController.clear() 296 297 def UpdateBtn_thread(self): 298 if self.statefulBtn is None or self.statefulBtn.destroyed or self.destroyed: 299 self._btnUpdateThread = None 300 return 301 if not self.statefulBtn.controller.IsInCurrentSolarSystem(): 302 return 303 if session.stationid or session.structureid: 304 return 305 self.statefulBtn.UpdateState() 306 307 def OnSkillsChanged(self, skills): 308 if typeMercenaryDenManagementSkill in skills: 309 self._UpdateOnChangedNumbers() 310 311 def OnSubscriptionChanged_Local(self): 312 self._UpdateOnChangedNumbers() 313 314 def _UpdateOnChangedNumbers(self): 315 self.uiController.ClearMyMaxDens() 316 self.LoadLeftSide() 317 318 def Close(self, *args, **kwds): 319 with ExceptionEater('Closing MyMercDenWnd'): 320 self.ChangeSignalConnection(connect=False) 321 self.ClearSelectedMercDenController() 322 self.uiController = None 323 super(MyMercDensWnd, self).Close(*args, **kwds)