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

scanResults.py (12237B)


      1 #Embedded file name: C:\BuildAgent\work\20d73f1b24eed06e\eve\release\V24.01\eve\client\script\ui\inflight\scannerFiles\scanResults.py
      2 import blue
      3 from carbon.common.script.sys.service import ROLE_QA
      4 from carbon.common.script.util.timerstuff import AutoTimer
      5 import carbonui.const as uiconst
      6 from carbonui.control.basicDynamicScroll import BasicDynamicScroll
      7 from carbonui.uianimations import animations
      8 from eve.common.script.sys.eveCfg import IsControllingStructure
      9 from eve.client.script.ui.control.entries.util import GetFromClass
     10 from eve.client.script.ui.control.scrollColumnHeader import ScrollColumnHeader
     11 from eve.client.script.ui.inflight.scannerFiles.swipeAnimation import SwipeAnimator
     12 from eve.client.script.ui.inflight.scannerListEntries import ScanResultNew
     13 from eve.client.script.ui.shared.mapView.markers.mapMarkerUtil import GetResultTexturePath
     14 from gametime import GetSimTime, GetTimeDiff
     15 from localization import GetByLabel
     16 from logging import getLogger
     17 from menu import MenuLabel
     18 from probescanning.const import probeScanGroupAnomalies
     19 from sensorsuite.overlay.controllers.probescanner import SiteDataFromScanResult
     20 from uthread2 import call_after_wallclocktime_delay
     21 from utillib import KeyVal
     22 logger = getLogger(__name__)
     23 
     24 class ScanResults(BasicDynamicScroll):
     25     __notifyevents__ = ['OnSiteSelectionChanged', 'OnCosmicAnomalyAdded', 'OnCosmicSignatureAdded']
     26 
     27     def ApplyAttributes(self, attributes):
     28         self._scan_service = None
     29         self._michelle = None
     30         super(ScanResults, self).ApplyAttributes(attributes)
     31         sm.RegisterNotify(self)
     32         self.palette = attributes.palette
     33         self.swipe_animator = SwipeAnimator(parent=self, name='scanAnimator', align=uiconst.TOLEFT_PROP, clipChildren=True)
     34         self.sort_headers = ScrollColumnHeader(parent=self, settingsID='probescannerwindow_resultScrollList', idx=0, scroll=self, entryClass=ScanResultNew, padBottom=4)
     35         for header in self.sort_headers.headers:
     36             header.OnClick = (self.on_header_clicked, header)
     37 
     38         self.highlighted_target_ids = set()
     39         self.update_timer = AutoTimer(interval=1500, method=self.update_results)
     40 
     41     def Close(self, *args):
     42         sm.UnregisterNotify(self)
     43         if self.update_timer:
     44             self.update_timer.KillTimer()
     45             self.update_timer = None
     46         super(ScanResults, self).Close(*args)
     47 
     48     @property
     49     def scan_service(self):
     50         if self._scan_service is None:
     51             self._scan_service = sm.GetService('scanSvc')
     52         return self._scan_service
     53 
     54     @property
     55     def michelle(self):
     56         if self._michelle is None:
     57             self._michelle = sm.GetService('michelle')
     58         return self._michelle
     59 
     60     def OnSelectionChange(self, *args):
     61         selected = self.GetSelected()
     62         self.scan_service.SetSelectedSites([ site.id for site in selected ])
     63 
     64     def OnSiteSelectionChanged(self):
     65         nodes = self.GetNodes()
     66         for node in nodes:
     67             if not node.panel:
     68                 continue
     69             if self.scan_service.IsSiteSelected(node.id):
     70                 node.panel.Select()
     71             else:
     72                 node.panel.Deselect()
     73 
     74     def on_system_scan_started(self):
     75         current_scan = self.scan_service.GetCurrentScan()
     76         if current_scan is None:
     77             return
     78         dilation_multiplier = 1.0 / max(blue.os.desiredSimDilation, 0.1)
     79         swipe_duration = dilation_multiplier * current_scan.duration / 1000 + 0.5
     80         self._start_animation(resultsFadeDuration=0.5, swipeDuration=swipe_duration, swipeFadeInDuration=0.5, swipeFadeOutDuration=0.5, swipeHighlightDuration=0.3)
     81 
     82     def on_system_scan_ended(self):
     83         self._end_animation(resultsFadeDuration=0.7)
     84 
     85     def OnCosmicAnomalyAdded(self, anomaly):
     86         target_id = anomaly.targetID
     87         self.highlight_entry(target_id)
     88 
     89     def OnCosmicSignatureAdded(self, target_id):
     90         self.highlight_entry(target_id)
     91 
     92     def highlight_entry(self, target_id):
     93         self._add_highlight(target_id)
     94         if self.IsVisible():
     95             self._show_quick_swipe(callback=self.palette.Refresh)
     96         else:
     97             self.palette.Refresh()
     98 
     99     def _show_quick_swipe(self, callback = None):
    100         swipe_duration = 1.0
    101         results_fade_in_duration = 0.15 * swipe_duration
    102         results_fade_out_duration = 0.21 * swipe_duration
    103         end_delay = 0.8 * swipe_duration
    104         callback_delay = 0.6 * swipe_duration
    105         self._start_animation(results_fade_in_duration, swipe_duration)
    106         call_after_wallclocktime_delay(self._end_animation, delay=end_delay, resultsFadeDuration=results_fade_out_duration)
    107         if callable(callback):
    108             call_after_wallclocktime_delay(callback, delay=callback_delay)
    109 
    110     def _start_animation(self, resultsFadeDuration, swipeDuration, swipeFadeInDuration = None, swipeFadeOutDuration = None, swipeHighlightDuration = None):
    111         animations.FadeTo(self, duration=resultsFadeDuration, startVal=1.0, endVal=0.5)
    112         self.swipe_animator.start(swipeDuration, swipeFadeInDuration, swipeHighlightDuration, swipeFadeOutDuration)
    113 
    114     def _end_animation(self, resultsFadeDuration):
    115         animations.FadeIn(self, duration=resultsFadeDuration, curveType=uiconst.ANIM_OVERSHOT5)
    116 
    117     def on_header_clicked(self, header):
    118         self.load_results()
    119         self.sort_headers.ClickHeader(header)
    120 
    121     def get_result_entry(self, columnWidths, myPos, result):
    122         displayName = self.scan_service.GetDisplayName(result)
    123         scanGroupName = self.scan_service.GetScanGroupName(result)
    124         groupName = self.scan_service.GetGroupName(result)
    125         typeName = self.scan_service.GetTypeName(result)
    126         distance = result.GetDistance(myPos)
    127         sortValues = [GetResultTexturePath(result),
    128          distance,
    129          result.id,
    130          displayName,
    131          groupName,
    132          min(1.0, result.certainty)]
    133         data = KeyVal()
    134         data.sortValues = sortValues
    135         data.columnID = 'probeResultColumn'
    136         data.displayName = displayName
    137         data.scanGroupName = scanGroupName
    138         data.groupName = groupName
    139         data.typeName = typeName
    140         data.result = result
    141         data.GetMenu = self.result_menu
    142         data.distance = distance
    143         data.newResult = True
    144         data.columnWidths = columnWidths
    145         data.itemID = result.itemID
    146         data.id = result.id
    147         data.isSelected = self.scan_service.IsSiteSelected(result.id)
    148         entry = GetFromClass(ScanResultNew, data)
    149         return entry
    150 
    151     def result_menu(self, panel, *args):
    152         result = panel.sr.node.result
    153         menu = []
    154         siteData = SiteDataFromScanResult(result)
    155         menu.extend(self.scan_service.GetScanResultMenuWithoutIgnore(siteData))
    156         nodes = self.GetSelected() or [panel.sr.node]
    157         idList = []
    158         nonAnomalyIdList = []
    159         for node in nodes:
    160             if hasattr(node.result, 'id'):
    161                 idList.append(node.result.id)
    162                 if node.result.scanGroupID != probeScanGroupAnomalies:
    163                     nonAnomalyIdList.append(node.result.id)
    164 
    165         menu.append((MenuLabel('UI/Inflight/Scanner/IngoreResult'), self.scan_service.IgnoreResult, idList))
    166         menu.append((MenuLabel('UI/Inflight/Scanner/IgnoreOtherResults'), self.scan_service.IgnoreOtherResults, idList))
    167         if session.role & ROLE_QA:
    168             menu.append(('QA', [('Scan selected sites', self.scan_service.QAScanSites, idList),
    169               None,
    170               ('Dungeon ID: {}'.format(result.dungeonID), None),
    171               ('Archetype ID: {}'.format(result.archetypeID), None)]))
    172         return menu
    173 
    174     def load_results(self):
    175         if self.destroyed:
    176             return
    177         current_scan = self.scan_service.GetCurrentScan()
    178         scanning_probes = self.scan_service.GetScanningProbes()
    179         my_position = sm.GetService('michelle').GetMyPosition()
    180         if not my_position:
    181             return
    182         results, ignored, filtered, filtered_anomalies = self.scan_service.GetResults()
    183         column_widths = self.sort_headers.GetColumnWidths()
    184         resultList = []
    185         if current_scan and GetTimeDiff(current_scan.startTime, GetSimTime()) < current_scan.duration:
    186             return
    187         if scanning_probes and session.shipid not in scanning_probes:
    188             return
    189         if results:
    190             for result in results:
    191                 entry = self.get_result_entry(column_widths, my_position, result)
    192                 resultList.append(entry)
    193 
    194         scroll_position = self.GetScrollProportion()
    195         self.Clear()
    196         sorted_results = self.get_sorted_results(resultList)
    197         if IsControllingStructure():
    198             self.ShowHint(hint=GetByLabel('UI/Inflight/Scanner/ProbeScanDisabledInStructure'))
    199         else:
    200             self.AddNodes(0, sorted_results)
    201             self._apply_highlights(sorted_results)
    202             if scroll_position:
    203                 self.ScrollToProportion(scroll_position)
    204             if sorted_results:
    205                 self.ShowHint()
    206                 self.sort_headers.Show()
    207             else:
    208                 self.sort_headers.Hide()
    209                 self.ShowHint(hint=self.get_no_scan_results_text(filtered, ignored, filtered_anomalies))
    210             self.palette.ShowFilteredAndIgnored(filtered, ignored, filtered_anomalies)
    211         self.palette.RefreshProbeResults()
    212 
    213     def _apply_highlights(self, results):
    214         for result in results:
    215             self._apply_highlight(result)
    216 
    217     def _apply_highlight(self, result):
    218         result_id = getattr(result, 'id', None)
    219         if result_id and result_id in self.highlighted_target_ids:
    220             panel = getattr(result, 'panel', None)
    221             if panel:
    222                 panel.ShowNewResultHighlight()
    223                 panel.RegisterForMouseExit(self._remove_highlight)
    224                 logger.debug('Scan result highlights: {} had highlight applied'.format(result_id))
    225 
    226     def _add_highlight(self, result_id):
    227         self.highlighted_target_ids.add(result_id)
    228         logger.debug('Scan result highlights: {} added to the list to highlight'.format(result_id))
    229 
    230     def _remove_highlight(self, panel, result_id):
    231         self.highlighted_target_ids.discard(result_id)
    232         panel.UnregisterForMouseExit(self._remove_highlight)
    233         logger.debug('Scan result highlights: {} had highlight removed'.format(result_id))
    234 
    235     def update_results(self):
    236         if not self.michelle.InWarp():
    237             return
    238         nodes = self.GetNodes()
    239         my_position = self.michelle.GetMyPosition()
    240         if not nodes or not my_position:
    241             return
    242         for node in nodes:
    243             if not node or not node.result:
    244                 continue
    245             distance = node.result.GetDistance(my_position)
    246             node.distance = distance
    247             node.sortValues[1] = distance
    248             if not node.panel:
    249                 continue
    250             node.panel.UpdateDistanceText()
    251 
    252         sorted_results = self.get_sorted_results(nodes)
    253         self.SetOrderedNodes(sorted_results)
    254 
    255     def get_sorted_results(self, results):
    256         _, column_direction = self.sort_headers.GetActiveColumnAndDirection()
    257         sorted_results = sorted(results, key=self.get_sort_value, reverse=not column_direction)
    258         return sorted_results
    259 
    260     def get_sort_value(self, node):
    261         columns = ScanResultNew.GetColumns()
    262         active_column, _ = self.sort_headers.GetActiveColumnAndDirection()
    263         active_colum_index = columns.index(active_column) if active_column else 0
    264         return node.sortValues[active_colum_index]
    265 
    266     def get_no_scan_results_text(self, filtered, ignored, filteredAnomalies):
    267         if IsControllingStructure():
    268             return GetByLabel('UI/Inflight/Scanner/ProbeScanDisabledInStructure')
    269         if ignored and (filtered or filteredAnomalies):
    270             text = GetByLabel('UI/Inflight/Scanner/FilteredAndIgnoredResults')
    271         elif ignored:
    272             text = GetByLabel('UI/Inflight/Scanner/IgnoredResults')
    273         elif filtered or filteredAnomalies:
    274             text = GetByLabel('UI/Inflight/Scanner/FilteredResults')
    275         else:
    276             text = GetByLabel('UI/Inflight/Scanner/NoScanResults')
    277         return text