ghostShipIcon.py (14029B)
1 #Embedded file name: C:\BuildAgent\work\20d73f1b24eed06e\eve\release\V24.01\eve\client\script\ui\shared\fittingScreen\ghostShipIcon.py 2 import carbonui.const as uiconst 3 import carbonui.fontconst 4 import evetypes 5 import inventorycommon 6 import log 7 import trinity 8 import uthread2 9 from carbon.client.script.environment.AudioUtil import PlaySound 10 from carbonui.primitives.container import Container 11 from carbonui.primitives.fill import Fill 12 from carbonui.primitives.frame import Frame 13 from carbonui.primitives.sprite import Sprite 14 from carbonui.primitives.transform import Transform 15 from carbonui.uicore import uicore 16 from carbonui.control.buttonIcon import ButtonIcon 17 from eve.client.script.ui.control.themeColored import LabelThemeColored 18 from eve.client.script.ui.services.menuSvcExtras import openFunctions 19 from eve.client.script.ui.shared.fitting.fittingUtil import GetTypeIDForController 20 from eve.client.script.ui.shared.fittingScreen.simulationModeTooltip import LoadSimulationIconTooltip 21 from eve.client.script.ui.shared.fittingScreen.tryFit import GhostFitShip 22 from eve.common.script.sys.eveCfg import GetActiveShip 23 from eve.common.script.sys.idCheckers import IsStructure 24 from localization import GetByLabel 25 from menu import MenuLabel 26 from menucheckers import SessionChecker, ItemChecker 27 from utillib import KeyVal 28 COLOR_BG = (0.0259, 0.0491, 0.075, 1.0) 29 OPACITY_NORMAL = 1.0 30 OPACITY_MOUSEOVER = 2.0 31 OPACITY_NORMAL_FRAME = 0.25 32 OPACITY_MOUSEOVER_FRAME = 0.45 33 OPACITY_NORMAL_ACTIVE_FRAME = 0.0 34 OPACITY_MOUSEOVER_ACTIVE_FRAME = 0.25 35 36 class GhostShipIcon(Container): 37 default_name = 'GhostShipIcon' 38 default_align = uiconst.TOPRIGHT 39 default_state = uiconst.UI_NORMAL 40 isDragObject = True 41 42 def ApplyAttributes(self, attributes): 43 Container.ApplyAttributes(self, attributes) 44 self.controller = attributes.controller 45 self.fittingSvc = sm.GetService('fittingSvc') 46 self.enableButtonThread = None 47 self.ConstructEnterSimulationCont() 48 self.ConstructExitSimulationCont() 49 self.iconSprite, self.iconTransform = AddIconAndIconTransform(self, self.width) 50 self.bgActiveFrame = AddBackground(self) 51 self.SetShipTypeID() 52 53 def ConstructEnterSimulationCont(self): 54 self.enterSimulationCont = Container(name='enterSimulationCont', parent=self) 55 self.simulateLabel = LabelThemeColored(name='simulateLabel', fontStyle=carbonui.fontconst.STYLE_HEADER, parent=self.enterSimulationCont, fontsize=12, align=uiconst.CENTERBOTTOM, uppercase=True, text=GetByLabel('UI/Fitting/FittingWindow/Simulate'), opacity=0.75, top=-20) 56 57 def ConstructExitSimulationCont(self): 58 self.exitSimulationCont = Container(name='exitSimulationCont', parent=self) 59 Fill(bgParent=self.exitSimulationCont, color=(0, 0, 0, 0.7)) 60 self.exitButtonIcon = ButtonIcon(parent=self.exitSimulationCont, texturePath='res:/UI/Texture/classes/Fitting/simExitOverlay.png', pos=(0, 0, 64, 64), align=uiconst.CENTER, iconSize=64, state=uiconst.UI_DISABLED) 61 self.label = LabelThemeColored(fontStyle=carbonui.fontconst.STYLE_HEADER, parent=self.exitSimulationCont, fontsize=10, text='<center>%s' % GetByLabel('UI/Fitting/FittingWindow/ExitSimulation'), align=uiconst.CENTER, width=64, uppercase=True) 62 63 def SetShipTypeID(self): 64 if self.destroyed or not self.controller: 65 return 66 isSimulated = self.controller.IsSimulated() 67 if isSimulated: 68 self.typeID = GetTypeIDForController(session.shipid) 69 self.iconSprite.blendMode = trinity.TR2_SBM_BLEND 70 sm.GetService('photo').GetIconByType(self.iconSprite, self.typeID) 71 self.exitSimulationCont.display = True 72 self.enterSimulationCont.display = False 73 self.ResetIcon() 74 else: 75 self.exitSimulationCont.display = False 76 self.enterSimulationCont.display = True 77 try: 78 shipID = session.shipid 79 self.typeID = GetTypeIDForController(shipID) 80 self.iconSprite.blendMode = trinity.TR2_SBM_ADD 81 texturePath = inventorycommon.typeHelpers.GetHoloIconPath(self.typeID) 82 except AttributeError as e: 83 texturePath = None 84 log.LogException(e) 85 finally: 86 self.iconSprite.SetTexturePath(texturePath) 87 88 def ResetIcon(self): 89 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, 1.0, duration=0.1, loops=1) 90 self.iconTransform.StopAnimations() 91 self.iconTransform.scale = (1.0, 1.0) 92 93 def _GetSimulatedShipID(self): 94 return sm.GetService('clientDogmaIM').GetFittingDogmaLocation().shipID 95 96 def OnMouseEnter(self, *args): 97 PlaySound(uiconst.SOUND_BUTTON_HOVER) 98 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, OPACITY_MOUSEOVER, duration=1.0, loops=1) 99 uicore.animations.FadeTo(self.bgActiveFrame, self.bgActiveFrame.opacity, OPACITY_MOUSEOVER_ACTIVE_FRAME, duration=0.25, loops=1, curveType=uiconst.ANIM_OVERSHOT) 100 if self.controller.IsSimulated(): 101 self.exitButtonIcon.OnMouseEnter() 102 uicore.animations.MorphScalar(self.label, 'opacity', self.label.opacity, 1.5, duration=0.2) 103 else: 104 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, OPACITY_MOUSEOVER, duration=1.0, loops=1) 105 uicore.animations.Tr2DScaleTo(self.iconTransform, self.iconTransform.scale, (1.05, 1.05), duration=0.3) 106 uicore.animations.MorphScalar(self.simulateLabel, 'opacity', self.simulateLabel.opacity, 1.5, duration=0.2) 107 108 def OnMouseExit(self, *args): 109 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, OPACITY_NORMAL, duration=1.3) 110 uicore.animations.FadeTo(self.bgActiveFrame, self.bgActiveFrame.opacity, OPACITY_NORMAL_ACTIVE_FRAME, duration=0.25, loops=1) 111 uicore.animations.Tr2DScaleTo(self.iconTransform, self.iconTransform.scale, (1.0, 1.0), duration=0.3) 112 self.exitButtonIcon.OnMouseExit() 113 uicore.animations.MorphScalar(self.label, 'opacity', self.label.opacity, 0.75, duration=0.2) 114 uicore.animations.MorphScalar(self.simulateLabel, 'opacity', self.simulateLabel.opacity, 0.75, duration=0.2) 115 116 def LoadTooltipPanel(self, tooltipPanel, *args): 117 LoadSimulationIconTooltip(tooltipPanel, self.controller.IsSimulated()) 118 119 def GetMenu(self, *args): 120 m = [] 121 if self.controller.IsSimulated(): 122 m += [(MenuLabel('UI/Fitting/FittingWindow/SimulateMyShip', {'typeID': self.typeID}), sm.GetService('ghostFittingSvc').LoadCurrentShip, ())] 123 m += [(MenuLabel('UI/Fitting/FittingWindow/ExitSimulationMode'), self.OnClick, ())] 124 else: 125 myActualShipTypeID = sm.GetService('clientDogmaIM').GetDogmaLocation().GetShip().typeID 126 m += [(MenuLabel('UI/Fitting/FittingWindow/SimulateMyShip', {'typeID': myActualShipTypeID}), sm.GetService('ghostFittingSvc').LoadCurrentShip, ())] 127 m += [(MenuLabel('UI/Fitting/FittingWindow/EnterSimulationMode'), self.OnClick, ())] 128 return m 129 130 def OnClick(self, *args): 131 PlaySound(uiconst.SOUND_BUTTON_CLICK) 132 self.ToggleGhostFitting() 133 134 def Close(self): 135 self.controller = None 136 Container.Close(self) 137 138 def ToggleGhostFitting(self, *args): 139 ghostFittingSvc = sm.GetService('ghostFittingSvc') 140 if self.enableButtonThread: 141 self.enableButtonThread.kill() 142 self.enableButtonThread = None 143 self.state = uiconst.UI_DISABLED 144 try: 145 ghostFittingSvc.ToggleGhostFitting() 146 finally: 147 self.EnableButtonWithDelay() 148 149 def EnableButtonWithDelay(self): 150 if self.enableButtonThread: 151 self.enableButtonThread.kill() 152 self.enableButtonThread = uthread2.call_after_wallclocktime_delay(self.EnableButton, 0.5) 153 154 def EnableButton(self): 155 self.state = uiconst.UI_NORMAL 156 self.enableButtonThread = None 157 158 def GetDragData(self): 159 fitting = KeyVal() 160 fitting.shipTypeID, fitting.fitData, _ = self.GetFittingDictForOtherState() 161 fitting.isCurrentShip = self.controller.IsSimulated() or self._GetSimulatedShipID() is None 162 fitting.fittingID = None 163 fitting.description = '' 164 shipName = cfg.evelocations.Get(GetActiveShip()).locationName 165 fitting.name = shipName 166 entry = KeyVal() 167 entry.fitting = fitting 168 entry.label = fitting.name 169 entry.displayText = fitting.name 170 entry.__guid__ = 'listentry.FittingEntry' 171 return [entry] 172 173 def GetFittingDictForOtherState(self): 174 fittingSvc = sm.GetService('fittingSvc') 175 return fittingSvc.GetFittingDictForActiveShip() 176 177 178 class GhostShipIconSimple(Container): 179 default_name = 'GhostShipIconSimple' 180 default_align = uiconst.TOPRIGHT 181 default_state = uiconst.UI_NORMAL 182 isDragObject = True 183 184 def ApplyAttributes(self, attributes): 185 Container.ApplyAttributes(self, attributes) 186 self.itemID = attributes.itemID 187 self.typeID = attributes.typeID 188 self.invItem = attributes.invItem 189 self.enableButtonThread = None 190 self.iconSprite, self.iconTransform = AddIconAndIconTransform(self, self.width) 191 self.iconSprite.blendMode = trinity.TR2_SBM_ADD 192 self.bgActiveFrame = AddBackground(self) 193 self.SetShipTypeID(self.typeID) 194 195 def SetShipTypeID(self, typeID): 196 texturePath = inventorycommon.typeHelpers.GetHoloIconPath(typeID) 197 self.iconSprite.SetTexturePath(texturePath) 198 199 def OnClick(self, *args): 200 PlaySound(uiconst.SOUND_BUTTON_CLICK) 201 self.SimulateShip() 202 203 def SimulateShip(self, *args): 204 if self.enableButtonThread: 205 self.enableButtonThread.kill() 206 self.enableButtonThread = None 207 self.Disable() 208 uicore.animations.MorphScalar(self, 'opacity', startVal=1.0, endVal=1.2, curveType=uiconst.ANIM_BOUNCE) 209 try: 210 if self.itemID == session.shipid: 211 sm.GetService('ghostFittingSvc').LoadCurrentShipExternal() 212 elif self.invItem: 213 GhostFitShip(self.invItem) 214 else: 215 openFunctions.SimulateFitting(KeyVal(shipTypeID=self.typeID, fitData=[])) 216 finally: 217 self.EnableButtonWithDelay() 218 219 def EnableButtonWithDelay(self): 220 if self.enableButtonThread: 221 self.enableButtonThread.kill() 222 self.enableButtonThread = uthread2.call_after_wallclocktime_delay(self.EnableButton, 0.5) 223 224 def EnableButton(self): 225 self.Enable() 226 self.enableButtonThread = None 227 228 def LoadTooltipPanel(self, tooltipPanel, *args): 229 wrapWidth = 250 230 tooltipPanel.LoadGeneric2ColumnTemplate() 231 tooltipPanel.cellSpacing = (10, 2) 232 headerText = GetByLabel(GetSimulateLabelPath(self.itemID, self.typeID, self.invItem)) 233 bodyText = GetByLabel('Tooltips/FittingWindow/SimulateShipFittingDescription') 234 tooltipPanel.AddLabelMedium(text=headerText, bold=True, colSpan=tooltipPanel.columns, wrapWidth=wrapWidth) 235 tooltipPanel.AddLabelMedium(text=bodyText, colSpan=tooltipPanel.columns, wrapWidth=wrapWidth, color=(0.6, 0.6, 0.6, 1)) 236 237 def OnMouseEnter(self, *args): 238 PlaySound(uiconst.SOUND_BUTTON_HOVER) 239 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, OPACITY_MOUSEOVER, duration=1.0, loops=1) 240 uicore.animations.FadeTo(self.bgActiveFrame, self.bgActiveFrame.opacity, OPACITY_MOUSEOVER_ACTIVE_FRAME, duration=0.25, loops=1, curveType=uiconst.ANIM_OVERSHOT) 241 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, OPACITY_MOUSEOVER, duration=1.0, loops=1) 242 uicore.animations.Tr2DScaleTo(self.iconTransform, self.iconTransform.scale, (1.05, 1.05), duration=0.3) 243 244 def OnMouseExit(self, *args): 245 self.AnimateMouseExit() 246 247 def AnimateMouseExit(self): 248 uicore.animations.FadeTo(self.iconSprite, self.iconSprite.opacity, OPACITY_NORMAL, duration=1.3) 249 uicore.animations.FadeTo(self.bgActiveFrame, self.bgActiveFrame.opacity, OPACITY_NORMAL_ACTIVE_FRAME, duration=0.25, loops=1) 250 uicore.animations.Tr2DScaleTo(self.iconTransform, self.iconTransform.scale, (1.0, 1.0), duration=0.3) 251 252 def OnMouseDown(self, *args): 253 self.top = 1 254 255 def OnMouseUp(self, *args): 256 self.top = 0 257 258 259 def AddIconAndIconTransform(parent, size): 260 iconTransform = Transform(parent=parent, align=uiconst.TOALL, scalingCenter=(0.5, 0.5)) 261 iconSprite = Sprite(name='iconSprite', parent=iconTransform, align=uiconst.CENTER, state=uiconst.UI_DISABLED, blendMode=trinity.TR2_SBM_ADD, pos=(0, 262 0, 263 size, 264 size), idx=0, opacity=OPACITY_NORMAL) 265 return (iconSprite, iconTransform) 266 267 268 def AddBackground(parent): 269 bgCont = Container(name='bgCont', parent=parent, padding=-4) 270 bgActiveFrame = Frame(bgParent=bgCont, cornerSize=4, opacity=OPACITY_NORMAL_ACTIVE_FRAME, texturePath='res:/UI/Texture/classes/Fitting/simEdgeDecorationFrame.png') 271 gridOverlay = Frame(bgParent=bgCont, cornerSize=10, opacity=0.5, texturePath='res:/UI/Texture/classes/Fitting/simBoxOverlay.png', padding=1) 272 fill = Sprite(bgParent=bgCont, texturePath='res:/UI/Texture/classes/Fitting/simGridBack.png', opacity=0.75, padding=4) 273 return bgActiveFrame 274 275 276 def GetSimulateLabelPath(itemID, typeID, invItem): 277 if IsStructure(evetypes.GetCategoryID(typeID)): 278 labelPath = 'UI/Fitting/FittingWindow/SimulateStructure' 279 else: 280 labelPath = 'UI/Fitting/FittingWindow/SimulateShip' 281 if invItem: 282 sessionChecker = SessionChecker(session, sm) 283 item = ItemChecker(invItem, sessionChecker) 284 if item.OfferSimulateShipFitting(): 285 labelPath = 'UI/Fitting/FittingWindow/SimulateShipFitting' 286 elif itemID == session.shipid: 287 labelPath = 'UI/Fitting/FittingWindow/SimulateShipFitting' 288 return labelPath