NovaBryan/EVE_Dump
Log | Files | 📦 下载最新源码 (.zip) | Refs | README

empireBanner.py (26025B)


      1 #Embedded file name: C:\BuildAgent\work\20d73f1b24eed06e\eve\release\V24.01\eve\client\script\ui\login\charcreation\empireui\empireBanner.py
      2 import carbonui.const as uiconst
      3 from eve.client.script.ui import eveColor
      4 from carbonui.fontconst import STYLE_HEADER
      5 from carbonui.primitives.container import Container
      6 from carbonui.primitives.frame import Frame
      7 from carbonui.primitives.gradientSprite import GradientSprite
      8 from carbonui.primitives.sprite import Sprite, StreamingVideoSprite
      9 from carbonui.uianimations import animations
     10 from carbonui.uicore import uicore
     11 from charactercreator.client.empireSelectionData import GetEmpireLogo, GetEmpireSeal, GetEmpireQuote
     12 import charactercreator.client.scalingUtils as ccScalingUtils
     13 import charactercreator.const as ccConst
     14 from eve.client.script.ui.login.charcreation.empireui.empireThemedButtons import FLARE_VIDEO_BY_RACE, CURVED_GRADIENT_TEXTURE_BY_RACE, HIGHLIGHT_TINT_BY_RACE
     15 from eve.client.script.ui.login.charcreation.label import CCLabel
     16 from eve.client.script.ui.login.charcreation.technologyViewUtils import LineDecoration
     17 from eve.client.script.ui.shared.agencyNew.ui.controls.warningContainer import WarningContainer
     18 from eve.client.script.ui.util.uix import GetTextHeight
     19 from eve.common.lib.appConst import raceAmarr, raceCaldari, raceGallente, raceMinmatar
     20 from localization import GetByMessageID, GetByLabel
     21 import math
     22 import trinity
     23 from uthread2 import call_after_wallclocktime_delay
     24 EMPIRE_BANNERS_OPACITY = 0.3
     25 EMPIRE_QUOTE_FADE_IN_DELAY = 0.25
     26 EMPIRE_QUOTE_FADE_IN_DURATION = 0.7
     27 EMPIRE_QUOTE_TEXT_FADE_IN_DELAY = 0.25
     28 EMPIRE_QUOTE_TEXT_FADE_IN_DURATION = 0.5
     29 EMPIRE_QUOTE_TEXT_FADE_OUT_DURATION = 0.3
     30 EMPIRE_QUOTE_FADE_OUT_DELAY = 0.0
     31 EMPIRE_QUOTE_FADE_OUT_DURATION = 0.3
     32 EMPIRE_LOGOS_TOP = -16
     33 RACE_SPRITE_BG_OPACITY = 0.3
     34 EMPIRE_QUOTE_FONTSIZE = 12
     35 EMPIRE_QUOTE_LINESPACING = 0.25
     36 EMPIRE_QUOTE_WIDTH = 166
     37 EMPIRE_QUOTE_TOP = 40
     38 EMPIRE_QUOTE_BOTTOM_MIN = 25
     39 EMPIRE_QUOTE_PHRASE_OPACITY = 0.75
     40 EMPIRE_QUOTE_ATTRIBUTION_OPACITY = 1.0
     41 EMPIRE_QUOTE_TINT_BY_RACE = {raceAmarr: (1.0, 0.94, 0.84),
     42  raceCaldari: (0.85, 0.95, 1.0),
     43  raceGallente: (0.75, 1.0, 1.0),
     44  raceMinmatar: (1.0, 0.85, 0.8)}
     45 UPPER_HEIGHT = 182
     46 LOWER_HEIGHT = 164
     47 FLARE_WIDTH = 284
     48 FLARE_HEIGHT = 160
     49 BANNER_TEXT_FONTSIZE = 14
     50 EXTRA_FRAME_TITLE_PADDING = 12
     51 CURVED_GRADIENT_OPACITY = 0.5
     52 LINE_HEIGHT = 4
     53 LINE_DECO_WIDTH_MIN_RES = 41
     54 LINE_CURVED_GRADIENT_WIDTH = 156
     55 LINE_CURVED_GRADIENT_HEIGHT = 22
     56 CURVED_GRADIENT_TEXTURE_BASE = 'res:/UI/Texture/Classes/EmpireSelection/curvedGradientBase.png'
     57 HEADER_BACKGROUND_OPACITY = 0.75
     58 
     59 class BannerContents(Container):
     60 
     61     def ApplyAttributes(self, attributes):
     62         super(BannerContents, self).ApplyAttributes(attributes)
     63         self.raceID = attributes.raceID
     64         self.audioSvc = sm.GetService('audio')
     65         self.raceSprite = None
     66         self.raceSpriteBg = None
     67         self.isHovered = False
     68         self.CalculateSizes()
     69         self._ShowRaceIcon()
     70         self._ShowEmpireQuote()
     71         self._ShowFlare()
     72         self._ShowEmpireQuoteBackground()
     73         self._ShowCurvedGradient()
     74 
     75     def CalculateSizes(self):
     76         scaleFactor = ccScalingUtils.GetScaleFactor()
     77         self.upperHeight = UPPER_HEIGHT * scaleFactor
     78         self.lowerHeight = LOWER_HEIGHT * scaleFactor
     79         self.raceIconsTop = EMPIRE_LOGOS_TOP * scaleFactor
     80         self.raceIconBgTop = ccConst.RACE_ICON_BG_TOP * scaleFactor
     81         self.raceIconSize = ccConst.RACE_ICON_SIZE * scaleFactor
     82         self.raceIconSizeHover = ccConst.RACE_ICON_HOVER_SIZE * scaleFactor
     83         self.flareWidth = FLARE_WIDTH * scaleFactor
     84         self.flareHeight = FLARE_HEIGHT * scaleFactor
     85         self.CalculateEmpireQuoteSizes(scaleFactor)
     86 
     87     def CalculateEmpireQuoteSizes(self, scaleFactor):
     88         self.quoteFontsize = EMPIRE_QUOTE_FONTSIZE * scaleFactor
     89         self.quoteTop = EMPIRE_QUOTE_TOP * scaleFactor
     90         self.quoteWidth = EMPIRE_QUOTE_WIDTH * scaleFactor
     91         phrase, attribution = self.GetEmpireQuoteBreakdown()
     92         self.quoteHeightPhrase = self.CalculateEmpireQuoteTextHeight(phrase)
     93         self.quoteHeightAttribution = self.CalculateEmpireQuoteTextHeight(attribution)
     94 
     95     def GetEmpireQuoteBreakdown(self):
     96         empireText = GetByMessageID(GetEmpireQuote(self.raceID))
     97         quoteBreakdown = empireText.split('<br/><br/>')
     98         attribution = quoteBreakdown[-1]
     99         phrase = empireText.replace(attribution, '')
    100         return (phrase, attribution)
    101 
    102     def CalculateEmpireQuoteTextHeight(self, text):
    103         textHeight = 0
    104         for line in text.split('<br/><br/>'):
    105             lineHeight = GetTextHeight(strng=line or '0', width=self.quoteWidth, fontsize=self.quoteFontsize, fontStyle=STYLE_HEADER)
    106             textHeight += lineHeight + lineHeight * EMPIRE_QUOTE_LINESPACING
    107 
    108         return textHeight
    109 
    110     def _ShowRaceIcon(self):
    111         self.raceSprite = Sprite(name='raceSprite', parent=self, align=uiconst.CENTERTOP, texturePath='', width=self.raceIconSize, height=self.raceIconSize, state=uiconst.UI_DISABLED, top=self.raceIconsTop)
    112         self.raceSpriteBg = Sprite(name='raceSpriteBg', parent=self, align=uiconst.CENTERTOP, texturePath='', width=self.raceIconSize, height=self.raceIconSize, state=uiconst.UI_DISABLED, top=self.raceIconBgTop + self.raceIconsTop)
    113         spritePath = GetEmpireLogo(self.raceID)
    114         bgSpritePath = GetEmpireSeal(self.raceID)
    115         self.raceSprite.SetTexturePath(spritePath)
    116         self.raceSpriteBg.SetTexturePath(bgSpritePath)
    117         self.raceSpriteBg.SetAlpha(0.0)
    118 
    119     def DesaturateRaceIcon(self):
    120         self.raceSprite.spriteEffect = trinity.TR2_SFX_SOFTLIGHT
    121         self.raceSprite.opacity = 0.5
    122         self.raceSprite.saturation = 0.0
    123 
    124     def _ShowCurvedGradient(self):
    125         bannerWidth = ccScalingUtils.GetBannerWidth()
    126         self.curvedGradientContainer = Container(name='curvedGradientContainer', parent=self, align=uiconst.TOTOP_NOPUSH, width=bannerWidth, height=self.upperHeight, state=uiconst.UI_DISABLED, opacity=0.0)
    127         self.curvedGradient = Sprite(name='curvedGradient', parent=self.curvedGradientContainer, align=uiconst.TOLEFT, texturePath=CURVED_GRADIENT_TEXTURE_BY_RACE[self.raceID], width=bannerWidth, height=self.upperHeight, opacity=CURVED_GRADIENT_OPACITY)
    128 
    129     def _ShowEmpireQuote(self):
    130         self.textCont = Container(name='empireQuoteContainer', parent=self, align=uiconst.TOTOP_NOPUSH, width=self.quoteWidth, height=self.quoteHeightPhrase + self.quoteHeightAttribution, top=self.upperHeight + self.quoteTop, opacity=0.0)
    131         self.textWrapper = Container(name='empireQuoteWrapper', parent=self.textCont, align=uiconst.CENTER, width=self.quoteWidth, height=self.quoteHeightPhrase + self.quoteHeightAttribution)
    132         phrase, attribution = self.GetEmpireQuoteBreakdown()
    133         self.empireQuotePhrase = CCLabel(name='empireQuotePhrase', parent=self.textWrapper, text='<center>%s</center>' % phrase, align=uiconst.TOTOP, width=self.quoteWidth, height=self.quoteHeightPhrase, color=EMPIRE_QUOTE_TINT_BY_RACE[self.raceID], fontsize=self.quoteFontsize, fontStyle=STYLE_HEADER, bold=False, letterspace=0, lineSpacing=EMPIRE_QUOTE_LINESPACING, opacity=EMPIRE_QUOTE_PHRASE_OPACITY)
    134         self.empireQuoteAttribution = CCLabel(name='empireQuoteAttribution', parent=self.textWrapper, text='<center>%s</center>' % attribution, align=uiconst.TOTOP, width=self.quoteWidth, height=self.quoteHeightAttribution, color=EMPIRE_QUOTE_TINT_BY_RACE[self.raceID], fontsize=self.quoteFontsize, fontStyle=STYLE_HEADER, bold=True, letterspace=0, lineSpacing=EMPIRE_QUOTE_LINESPACING, opacity=EMPIRE_QUOTE_ATTRIBUTION_OPACITY)
    135 
    136     def _ShowEmpireQuoteBackground(self):
    137         bannerWidth = ccScalingUtils.GetBannerWidth()
    138         scaleFactor = ccScalingUtils.GetScaleFactor()
    139         bottomMin = EMPIRE_QUOTE_BOTTOM_MIN * scaleFactor
    140         height = max(self.lowerHeight, self.quoteTop + self.quoteHeightPhrase + self.quoteHeightAttribution + bottomMin)
    141         self.empireQuoteBackgroundContainer = Container(name='empireQuoteBackgroundContainer', parent=self, align=uiconst.TOTOP_NOPUSH, width=bannerWidth, height=height, top=self.upperHeight, opacity=0.0)
    142         GradientSprite(name='empireQuoteBackgroundGradient', bgParent=self.empireQuoteBackgroundContainer, rgbData=[(0, (0.0, 0.0, 0.0))], alphaData=[(0, 0.0),
    143          (0.4, 0.5),
    144          (0.6, 0.5),
    145          (1.0, 0.0)])
    146         self.lineDecoration = LineDecoration(name='empireQuoteLineDecoration', parent=self.empireQuoteBackgroundContainer, align=uiconst.TOBOTTOM_NOPUSH, width=bannerWidth, height=LINE_HEIGHT, lineWidth=bannerWidth, lineDecorationWidth=LINE_DECO_WIDTH_MIN_RES * scaleFactor, invert=True, lineColor=HIGHLIGHT_TINT_BY_RACE[self.raceID])
    147         self.lineDecorationCurvedGradientContainer = Container(name='lineDecorationCurvedGradientContainer', parent=self.empireQuoteBackgroundContainer, align=uiconst.TOBOTTOM_NOPUSH, width=LINE_CURVED_GRADIENT_WIDTH * scaleFactor, height=LINE_CURVED_GRADIENT_HEIGHT * scaleFactor, state=uiconst.UI_DISABLED)
    148         self.lineDecorationCurvedGradient = Sprite(name='lineDecorationCurvedGradient', parent=self.lineDecorationCurvedGradientContainer, align=uiconst.CENTERTOP, texturePath=CURVED_GRADIENT_TEXTURE_BY_RACE[self.raceID], width=LINE_CURVED_GRADIENT_WIDTH * scaleFactor, height=LINE_CURVED_GRADIENT_HEIGHT * scaleFactor, opacity=CURVED_GRADIENT_OPACITY)
    149 
    150     def _ShowFlare(self):
    151         bannerWidth = ccScalingUtils.GetBannerWidth()
    152         self.flareContainer = Container(name='flareContainer', parent=self, align=uiconst.TOTOP_NOPUSH, width=self.flareWidth, height=self.flareHeight, top=self.upperHeight - self.flareHeight / 2, left=-(self.flareWidth - bannerWidth) / 2, opacity=0.0)
    153         self.flareWrapper = Container(name='flareWrapper', parent=self.flareContainer, align=uiconst.TOLEFT, width=self.flareWidth, height=self.flareHeight)
    154         self.flare = StreamingVideoSprite(name='flare', parent=self.flareWrapper, align=uiconst.TOALL, videoPath=FLARE_VIDEO_BY_RACE[self.raceID], state=uiconst.UI_DISABLED, blendMode=trinity.TR2_SBM_BLEND, spriteEffect=trinity.TR2_SFX_COPY, videoLoop=True, disableAudio=True)
    155 
    156     def AnimateEntered(self):
    157         self.isHovered = True
    158         quoteDuration = EMPIRE_QUOTE_FADE_IN_DURATION
    159         quoteOffset = EMPIRE_QUOTE_FADE_IN_DELAY
    160         quoteTextDuration = EMPIRE_QUOTE_TEXT_FADE_IN_DURATION
    161         quoteTextOffset = quoteOffset + EMPIRE_QUOTE_TEXT_FADE_IN_DELAY
    162         self.raceSpriteBg.width = self.raceIconSizeHover
    163         self.raceSpriteBg.height = self.raceIconSizeHover
    164         animation = animations.FadeIn
    165         animation(self.raceSpriteBg, duration=quoteDuration, timeOffset=quoteOffset, endVal=RACE_SPRITE_BG_OPACITY)
    166         animation(self.curvedGradientContainer, duration=quoteDuration, timeOffset=quoteOffset)
    167         animation(self.flareContainer, duration=quoteDuration, timeOffset=quoteOffset)
    168         animation(self.empireQuoteBackgroundContainer, duration=quoteDuration, timeOffset=quoteOffset)
    169         animation(self.textCont, duration=quoteTextDuration, timeOffset=quoteTextOffset)
    170 
    171     def AnimateExited(self):
    172         self.isHovered = False
    173         quoteTextDuration = EMPIRE_QUOTE_TEXT_FADE_OUT_DURATION
    174         quoteDuration = EMPIRE_QUOTE_FADE_OUT_DURATION
    175         quoteOffset = EMPIRE_QUOTE_FADE_OUT_DELAY
    176         animation = animations.FadeOut
    177         animation(self.textCont, duration=quoteTextDuration)
    178         animation(self.curvedGradientContainer, duration=quoteDuration, timeOffset=quoteOffset)
    179         animation(self.raceSpriteBg, duration=quoteDuration, timeOffset=quoteOffset)
    180         animation(self.flareContainer, duration=quoteDuration, timeOffset=quoteOffset)
    181         animation(self.empireQuoteBackgroundContainer, duration=quoteDuration, timeOffset=quoteOffset)
    182 
    183     def AdjustTextSize(self):
    184         self.textCont.width = self.quoteWidth
    185         self.textCont.height = self.quoteHeightPhrase + self.quoteHeightAttribution
    186         self.textCont.top = self.upperHeight + self.quoteTop
    187         self.textWrapper.width = self.quoteWidth
    188         self.textWrapper.height = self.quoteHeightPhrase + self.quoteHeightAttribution
    189         self.empireQuotePhrase.width = self.quoteWidth
    190         self.empireQuotePhrase.height = self.quoteHeightPhrase
    191         self.empireQuotePhrase.fontsize = self.quoteFontsize
    192         self.empireQuoteAttribution.width = self.quoteWidth
    193         self.empireQuoteAttribution.height = self.quoteHeightAttribution
    194         self.empireQuoteAttribution.fontsize = self.quoteFontsize
    195 
    196     def AdjustLogoSize(self):
    197         if self.raceSprite:
    198             self.raceSprite.width = self.raceIconSize
    199             self.raceSprite.height = self.raceIconSize
    200             self.raceSprite.top = self.raceIconsTop
    201         if self.raceSpriteBg:
    202             spriteSize = self.raceIconSizeHover if self.isHovered else self.raceIconSize
    203             self.raceSpriteBg.width = spriteSize
    204             self.raceSpriteBg.height = spriteSize
    205             self.raceSpriteBg.top = self.raceIconBgTop + self.raceIconsTop
    206 
    207     def AdjustFlareSize(self):
    208         bannerWidth = ccScalingUtils.GetBannerWidth()
    209         self.flareContainer.width = self.flareWidth
    210         self.flareContainer.height = self.flareHeight
    211         self.flareContainer.top = self.upperHeight - self.flareHeight / 2
    212         self.flareContainer.left = -(self.flareWidth - bannerWidth) / 2
    213         self.flareWrapper.width = self.flareWidth
    214         self.flareWrapper.height = self.flareHeight
    215 
    216     def AdjustCurvedGradientSize(self):
    217         bannerWidth = ccScalingUtils.GetBannerWidth()
    218         self.curvedGradientContainer.width = bannerWidth
    219         self.curvedGradientContainer.height = self.upperHeight
    220         self.curvedGradient.width = bannerWidth
    221         self.curvedGradient.height = self.upperHeight
    222 
    223     def AdjustEmpireQuoteBackgroundSize(self):
    224         bannerWidth = ccScalingUtils.GetBannerWidth()
    225         scaleFactor = ccScalingUtils.GetScaleFactor()
    226         bottomMin = EMPIRE_QUOTE_BOTTOM_MIN * scaleFactor
    227         height = max(self.lowerHeight, self.quoteTop + self.quoteHeightPhrase + self.quoteHeightAttribution + bottomMin)
    228         self.empireQuoteBackgroundContainer.width = bannerWidth
    229         self.empireQuoteBackgroundContainer.height = height
    230         self.empireQuoteBackgroundContainer.top = self.upperHeight
    231         lineWidth = bannerWidth
    232         lineDecorationWidth = LINE_DECO_WIDTH_MIN_RES * scaleFactor
    233         self.lineDecoration.ResizeContents(lineWidth, lineDecorationWidth)
    234         self.lineDecorationCurvedGradientContainer.width = LINE_CURVED_GRADIENT_WIDTH * scaleFactor
    235         self.lineDecorationCurvedGradientContainer.height = LINE_CURVED_GRADIENT_HEIGHT * scaleFactor
    236         self.lineDecorationCurvedGradient.width = LINE_CURVED_GRADIENT_WIDTH * scaleFactor
    237         self.lineDecorationCurvedGradient.height = LINE_CURVED_GRADIENT_HEIGHT * scaleFactor
    238 
    239     def Resize(self):
    240         self.CalculateSizes()
    241         self.AdjustLogoSize()
    242         self.AdjustTextSize()
    243         self.AdjustFlareSize()
    244         self.AdjustCurvedGradientSize()
    245         self.AdjustEmpireQuoteBackgroundSize()
    246 
    247 
    248 class EmpireBanner(Container):
    249     default_state = uiconst.UI_NORMAL
    250     default_left = 0
    251     default_top = 0
    252     default_width = ccScalingUtils.BANNER_WIDTH
    253     default_height = ccScalingUtils.BANNER_HEIGHT
    254     STATE_PICK = 1
    255     STATE_PARENT = 2
    256     RACIAL_MUSIC_ON_CLICK = {raceAmarr: 'ui_es_banner_mouse_down_amarr_play',
    257      raceCaldari: 'ui_es_banner_mouse_down_caldari_play',
    258      raceGallente: 'ui_es_banner_mouse_down_gallente_play',
    259      raceMinmatar: 'ui_es_banner_mouse_down_minmatar_play'}
    260     RACIAL_MUSIC_ON_HOVER = {raceAmarr: 'music_switch_race_amarr',
    261      raceCaldari: 'music_switch_race_caldari',
    262      raceGallente: 'music_switch_race_gallente',
    263      raceMinmatar: 'music_switch_race_minmatar'}
    264     SOUND_ON_HOVER = 'ui_es_banner_mouse_over_play'
    265 
    266     def ApplyAttributes(self, attributes):
    267         self.raceID = attributes.raceID
    268         self.isHovered = False
    269         Container.ApplyAttributes(self, attributes)
    270         self.audioSvc = sm.GetService('audio')
    271         self.bannerState = attributes.Get('bannerState', EmpireBanner.STATE_PICK)
    272         self.isDisabled = attributes.Get('isDisabled', False)
    273         self.contents = None
    274         self.headerText = ''
    275         self.animationEnder = attributes.Get('animationEnder', None)
    276         self.bannerEnterer = attributes.Get('bannerEnterer', None)
    277         self.bannerExiter = attributes.Get('bannerExiter', None)
    278         self.bannerClicker = attributes.Get('bannerClicker', None)
    279         self.AddPanelCaps()
    280         self.AddTopBlackGradient()
    281         if self.bannerState == EmpireBanner.STATE_PICK:
    282             self.contents = BannerContents(parent=self, align=uiconst.TOALL, raceID=attributes.raceID)
    283         else:
    284             self.Expand()
    285         if self.isDisabled:
    286             self.Disable()
    287             WarningContainer(parent=self.contents, align=uiconst.CENTER, color=eveColor.WARNING_ORANGE, text=GetByLabel('UI/CharacterCreation/FactionDisabled'), width=250)
    288             self.contents.DesaturateRaceIcon()
    289 
    290     def ResizeContents(self, width, height):
    291         if self.contents and not self.contents.destroyed:
    292             self.contents.Resize()
    293 
    294     def OnClick(self, *args):
    295         if self.isDisabled:
    296             return
    297         if self.bannerClicker and self.bannerState == EmpireBanner.STATE_PICK:
    298             self.bannerClicker(self.raceID)
    299         if self.contents is not None and hasattr(self.contents, 'OnClick'):
    300             self.contents.OnClick(*args)
    301         sound = self.RACIAL_MUSIC_ON_CLICK[self.raceID]
    302         self.audioSvc.SendUIEvent(sound)
    303 
    304     def OnDblClick(self, *args):
    305         activeStep = uicore.layer.charactercreation.controller.stepID
    306         selectedRace = uicore.layer.charactercreation.controller.raceID
    307         if activeStep == ccConst.TECHNOLOGYSTEP and self.raceID == selectedRace:
    308             uicore.layer.charactercreation.controller.Approve()
    309 
    310     def OnMouseEnter(self, *args):
    311         if self.isDisabled:
    312             return
    313         Container.OnMouseEnter(self, args)
    314         if self.bannerEnterer:
    315             self.bannerEnterer(self.raceID)
    316 
    317     def OnMouseExit(self, *args):
    318         if self.isDisabled:
    319             return
    320         Container.OnMouseExit(self, args)
    321         if self.bannerExiter:
    322             self.bannerExiter()
    323 
    324     def PlaySoundsOnEntered(self):
    325         self.audioSvc.SendUIEvent(self.SOUND_ON_HOVER)
    326         self.audioSvc.SendUIEvent(self.RACIAL_MUSIC_ON_HOVER[self.raceID])
    327 
    328     def AdjustTextSize(self):
    329         self.contents.AdjustTextSize()
    330 
    331     def AnimateEntered(self):
    332         if self.bannerState != EmpireBanner.STATE_PICK:
    333             return
    334         self.isHovered = True
    335         self.AdjustTextSize()
    336         self.contents.AnimateEntered()
    337         quoteTime = EMPIRE_QUOTE_FADE_IN_DELAY + EMPIRE_QUOTE_FADE_IN_DURATION
    338         textTime = EMPIRE_QUOTE_FADE_IN_DELAY + EMPIRE_QUOTE_TEXT_FADE_IN_DELAY + EMPIRE_QUOTE_TEXT_FADE_IN_DURATION
    339         timeToEnd = max(quoteTime, textTime)
    340         call_after_wallclocktime_delay(self.NotifyOfAnimationEnd, timeToEnd)
    341 
    342     def AnimateExited(self):
    343         if self.bannerState != EmpireBanner.STATE_PICK:
    344             return
    345         self.isHovered = False
    346         self.contents.AnimateExited()
    347         textTime = EMPIRE_QUOTE_TEXT_FADE_OUT_DURATION
    348         quoteTime = EMPIRE_QUOTE_FADE_OUT_DELAY + EMPIRE_QUOTE_FADE_OUT_DURATION
    349         timeToEnd = max(quoteTime, textTime)
    350         call_after_wallclocktime_delay(self.NotifyOfAnimationEnd, timeToEnd)
    351 
    352     def NotifyOfAnimationEnd(self):
    353         if self.animationEnder:
    354             self.animationEnder(self.raceID)
    355 
    356     def ConstructHeader(self, text = None):
    357         if text is not None:
    358             self.headerText = text
    359         if hasattr(self, 'header'):
    360             self.header.Close()
    361         headerHeight = ccScalingUtils.GetBannerHeaderHeight()
    362         self.header = BannerHeader(name='bannerHeader', parent=self, align=uiconst.TOTOP, width=self.width, height=headerHeight, text=self.headerText)
    363         self.header.SetOrder(0)
    364 
    365     def Resize(self, width, height):
    366         self.width = width
    367         self.height = height
    368         self.ConstructHeader()
    369         self.ResizePanelCaps()
    370         self.ResizeTopBlackGradient()
    371 
    372     def ResizePanelCaps(self):
    373         width = ccScalingUtils.GetMainPanelWidth()
    374         height = ccScalingUtils.GetBannerHeaderHeight()
    375         self.topPanelCap.width = width
    376         self.topPanelCap.height = height
    377         self.topPanelCap.top = -height
    378         self.bottomPanelCap.width = width
    379         self.bottomPanelCap.height = height
    380 
    381     def ResizeTopBlackGradient(self):
    382         width = ccScalingUtils.GetMainPanelWidth()
    383         height = ccScalingUtils.GetBannerHeaderHeight()
    384         self.topBlackGradient.width = width
    385         self.topBlackGradient.height = height
    386         self.topBlackGradient.top = -height
    387 
    388     def Expand(self):
    389         self.isHovered = False
    390         self.state = uiconst.UI_DISABLED
    391         if self.contents is not None:
    392             self.contents.Close()
    393         self.bannerState = EmpireBanner.STATE_PARENT
    394         height = ccScalingUtils.GetMainPanelHeight()
    395         width = ccScalingUtils.GetMainPanelWidth()
    396         self.Resize(width, height)
    397         self.state = uiconst.UI_DISABLED
    398         self.ShowBottomPanelCap()
    399 
    400     def AddPanelCaps(self):
    401         width = ccScalingUtils.GetMainPanelWidth()
    402         height = ccScalingUtils.GetBannerHeaderHeight()
    403         texturePath = CURVED_GRADIENT_TEXTURE_BY_RACE[self.raceID] if self.raceID else CURVED_GRADIENT_TEXTURE_BASE
    404         self.topPanelCap = Sprite(name='topPanelCap', parent=self, align=uiconst.TOTOP_NOPUSH, texturePath=texturePath, state=uiconst.UI_DISABLED, width=width, height=height, top=-height, rotation=math.pi, opacity=0.0)
    405         self.bottomPanelCap = Sprite(name='bottomPanelCap', parent=self, align=uiconst.TOBOTTOM_NOPUSH, texturePath=texturePath, state=uiconst.UI_DISABLED, width=width, height=height, rotation=0.0, opacity=0.0)
    406 
    407     def AddTopBlackGradient(self):
    408         width = ccScalingUtils.GetMainPanelWidth()
    409         height = ccScalingUtils.GetBannerHeaderHeight()
    410         self.topBlackGradient = GradientSprite(name='topBlackGradient', parent=self, align=uiconst.TOTOP_NOPUSH, width=width, height=height, top=-height, rgbData=[(0, (0.0, 0.0, 0.0))], alphaData=[(0, 0.0),
    411          (0.4, 0.5),
    412          (0.6, 0.5),
    413          (1.0, 0.0)], opacity=0.0)
    414 
    415     def ShowTopPanelCap(self):
    416         self.topPanelCap.opacity = CURVED_GRADIENT_OPACITY
    417 
    418     def ShowBottomPanelCap(self):
    419         self.bottomPanelCap.opacity = CURVED_GRADIENT_OPACITY
    420 
    421     def HideTopPanelCap(self):
    422         self.topPanelCap.opacity = 0.0
    423 
    424     def HideBottomPanelCap(self):
    425         self.bottomPanelCap.opacity = 0.0
    426 
    427     def ShowTopBlackGradient(self):
    428         self.topBlackGradient.opacity = HEADER_BACKGROUND_OPACITY
    429 
    430     def HideTopBlackGradient(self):
    431         self.topBlackGradient.opacity = 0.0
    432 
    433 
    434 class BannerHeader(Container):
    435     default_align = uiconst.CENTERTOP
    436 
    437     def ApplyAttributes(self, attributes):
    438         self.headerSpotlight = None
    439         Container.ApplyAttributes(self, attributes)
    440         text = attributes.text
    441         self._AddText(text)
    442 
    443     def _AddText(self, text):
    444         scaleFactor = ccScalingUtils.GetScaleFactor()
    445         self.headerTextBox = Container(name='headerTextBox', parent=self, height=self.height, align=uiconst.TOTOP_NOPUSH)
    446         self.header = CCLabel(text=text, name='headerLabel', parent=self.headerTextBox, align=uiconst.CENTER, uppercase=1, color=(0.9, 0.9, 0.9, 0.8), fontsize=BANNER_TEXT_FONTSIZE * scaleFactor, bold=True, letterspace=0)
    447 
    448     def ResizeContent(self):
    449         self.headerTextBox.height = self.height
    450         scaleFactor = ccScalingUtils.GetScaleFactor()
    451         self.header.fontsize = BANNER_TEXT_FONTSIZE * scaleFactor
    452 
    453 
    454 class MinimalEmpireBanner(Container):
    455     frameDecorationWidthFactor = 1.35
    456     frameDecorationHeightFactor = 0.23
    457     frameDecorationTopFactor = 0.685
    458     frameDecoration = 'res:/UI/Texture/classes/EmpireSelection/factionBannerTop.png'
    459 
    460     def ApplyAttributes(self, attributes):
    461         logo = attributes.logo
    462         logoSize = attributes.logoSize
    463         iconView = attributes.Get('iconView', None)
    464         iconText = attributes.Get('iconText', '')
    465         iconTextFontsize = attributes.Get('iconTextFontsize', None)
    466         iconColor = attributes.Get('iconColor', None)
    467         Container.ApplyAttributes(self, attributes)
    468         self.AddLogo(logo, logoSize)
    469         self.AddBanner(iconView, iconText, iconTextFontsize, iconColor)
    470 
    471     def AddLogo(self, logo, logoSize):
    472         Sprite(name='empireLogo', parent=self, align=uiconst.CENTERTOP, texturePath=logo, width=logoSize, height=logoSize, top=self.height * self.frameDecorationHeightFactor * self.frameDecorationTopFactor / 2)
    473 
    474     def AddBanner(self, iconView, iconText, iconTextFontsize, iconColor):
    475         if not iconView:
    476             return
    477         decorationWidth = self.width * self.frameDecorationWidthFactor
    478         decorationHeight = self.height * self.frameDecorationHeightFactor
    479         frameDecorationTitle = CCLabel(parent=self, name='frameDecorationTitle', align=uiconst.TOLEFT_NOPUSH, text=iconText, bold=True, fontsize=iconTextFontsize, letterspace=0)
    480         frameDecorationTitleWidth = frameDecorationTitle.width
    481         frameDecorationTitleHeight = GetTextHeight(strng=iconText, width=frameDecorationTitleWidth, fontsize=iconTextFontsize, hspace=0)
    482         frameDecorationTitle.top = -frameDecorationTitleHeight / 2 - EXTRA_FRAME_TITLE_PADDING
    483         frameDecorationTitle.left = (self.width - frameDecorationTitleWidth) / 2
    484         Frame(parent=self, name='iconView', align=uiconst.TOALL, texturePath=iconView, color=iconColor)
    485         Frame(parent=self, name='frameDecoration', align=uiconst.ANCH_CENTERTOP, texturePath=self.frameDecoration, width=decorationWidth, height=decorationHeight, top=-decorationHeight * self.frameDecorationTopFactor, left=-(decorationWidth - self.width) / 2)