diff --git a/eos/db/saveddata/targetProfile.py b/eos/db/saveddata/targetProfile.py index 0f1ba836c..b0fd9fc76 100644 --- a/eos/db/saveddata/targetProfile.py +++ b/eos/db/saveddata/targetProfile.py @@ -39,4 +39,8 @@ targetProfiles_table = Table("targetResists", saveddata_meta, Column("modified", DateTime, nullable=True, onupdate=datetime.datetime.now) ) -mapper(TargetProfile, targetProfiles_table) +mapper(TargetProfile, targetProfiles_table, + properties={ + "_maxVelocity": targetProfiles_table.c.maxVelocity, + "_signatureRadius": targetProfiles_table.c.signatureRadius, + "_radius": targetProfiles_table.c.radius}) diff --git a/eos/saveddata/targetProfile.py b/eos/saveddata/targetProfile.py index 5e13b2ffe..8b9e6a4f7 100644 --- a/eos/saveddata/targetProfile.py +++ b/eos/saveddata/targetProfile.py @@ -17,10 +17,14 @@ # along with eos. If not, see . # =============================================================================== +import math import re + from logbook import Logger + import eos.db + pyfalog = Logger(__name__) @@ -36,9 +40,51 @@ class TargetProfile: self.thermalAmount = thermalAmount self.kineticAmount = kineticAmount self.explosiveAmount = explosiveAmount - self.maxVelocity = maxVelocity - self.signatureRadius = signatureRadius - self.radius = radius + self._maxVelocity = maxVelocity + self._signatureRadius = signatureRadius + self._radius = radius + + _idealTarget = None + + @classmethod + def getIdeal(cls): + if cls._idealTarget is None: + cls._idealTarget = cls( + emAmount=0, + thermalAmount=0, + kineticAmount=0, + explosiveAmount=0, + maxVelocity=0, + signatureRadius=None, + radius=0) + cls._idealTarget.name = 'Ideal Target' + return cls._idealTarget + + @property + def maxVelocity(self): + return self._maxVelocity or 0 + + @maxVelocity.setter + def maxVelocity(self, val): + self._maxVelocity = val + + @property + def signatureRadius(self): + if self._signatureRadius is None or self._signatureRadius == -1: + return math.inf + return self._signatureRadius + + @signatureRadius.setter + def signatureRadius(self, val): + self._signatureRadius = val + + @property + def radius(self): + return self._radius or 0 + + @radius.setter + def radius(self, val): + self._radius = val @classmethod def importPatterns(cls, text): @@ -116,6 +162,6 @@ class TargetProfile: def __deepcopy__(self, memo): p = TargetProfile( self.emAmount, self.thermalAmount, self.kineticAmount, self.explosiveAmount, - self.maxVelocity, self.signatureRadius, self.radius) + self._maxVelocity, self._signatureRadius, self._radius) p.name = "%s copy" % self.name return p diff --git a/gui/builtinViewColumns/attributeDisplayGraph.py b/gui/builtinViewColumns/attributeDisplayGraph.py index 1f204bbe9..93c40f052 100644 --- a/gui/builtinViewColumns/attributeDisplayGraph.py +++ b/gui/builtinViewColumns/attributeDisplayGraph.py @@ -17,7 +17,6 @@ # along with pyfa. If not, see . # ============================================================================= - from abc import ABCMeta, abstractmethod # noinspection PyPackageRequirements @@ -26,6 +25,7 @@ import wx import eos.config import gui.mainFrame from eos.saveddata.fit import Fit +from eos.saveddata.targetProfile import TargetProfile from eos.utils.spoolSupport import SpoolOptions, SpoolType from gui.bitmap_loader import BitmapLoader from gui.viewColumn import ViewColumn @@ -47,7 +47,7 @@ class GraphColumn(ViewColumn, metaclass=ABCMeta): raise NotImplementedError def getText(self, stuff): - if isinstance(stuff, Fit): + if isinstance(stuff, (Fit, TargetProfile)): val, unit = self._getValue(stuff) if val is None: return '' @@ -107,8 +107,14 @@ class SpeedColumn(GraphColumn): def __init__(self, fittingView, params): super().__init__(fittingView, 1389) - def _getValue(self, fit): - return fit.ship.getModifiedItemAttr('maxVelocity'), 'm/s' + def _getValue(self, stuff): + if isinstance(stuff, Fit): + speed = stuff.ship.getModifiedItemAttr('maxVelocity') + elif isinstance(stuff, TargetProfile): + speed = stuff.maxVelocity + else: + speed = 0 + return speed, 'm/s' def _getFitTooltip(self): return 'Maximum speed' @@ -141,8 +147,14 @@ class RadiusColumn(GraphColumn): def __init__(self, fittingView, params): super().__init__(fittingView, 3266) - def _getValue(self, fit): - return fit.ship.getModifiedItemAttr('radius'), 'm' + def _getValue(self, stuff): + if isinstance(stuff, Fit): + radius = stuff.ship.getModifiedItemAttr('radius') + elif isinstance(stuff, TargetProfile): + radius = stuff.radius + else: + radius = 0 + return radius, 'm' def _getFitTooltip(self): return 'Radius' @@ -158,8 +170,14 @@ class SignatureRadiusColumn(GraphColumn): def __init__(self, fittingView, params): super().__init__(fittingView, 1390) - def _getValue(self, fit): - return fit.ship.getModifiedItemAttr('signatureRadius'), 'm' + def _getValue(self, stuff): + if isinstance(stuff, Fit): + sigRadius = stuff.ship.getModifiedItemAttr('signatureRadius') + elif isinstance(stuff, TargetProfile): + sigRadius = stuff.signatureRadius + else: + sigRadius = 0 + return sigRadius, 'm' def _getFitTooltip(self): return 'Signature radius' diff --git a/gui/builtinViewColumns/baseIcon.py b/gui/builtinViewColumns/baseIcon.py index e5cbd62f2..11d79689b 100644 --- a/gui/builtinViewColumns/baseIcon.py +++ b/gui/builtinViewColumns/baseIcon.py @@ -4,6 +4,7 @@ from eos.saveddata.implant import Implant from eos.saveddata.drone import Drone from eos.saveddata.module import Module, Rack from eos.saveddata.fit import Fit +from eos.saveddata.targetProfile import TargetProfile from eos.const import FittingSlot from gui.viewColumn import ViewColumn @@ -37,6 +38,8 @@ class BaseIcon(ViewColumn): "gui") else: return self.loadIconFile(stuff.item.iconID or "") + elif isinstance(stuff, TargetProfile): + return self.fittingView.imageList.GetImageIndex("target_small", "gui") item = getattr(stuff, "item", stuff) return self.loadIconFile(item.iconID) diff --git a/gui/builtinViewColumns/baseName.py b/gui/builtinViewColumns/baseName.py index 00fae9abd..c18518122 100644 --- a/gui/builtinViewColumns/baseName.py +++ b/gui/builtinViewColumns/baseName.py @@ -27,6 +27,7 @@ from eos.saveddata.drone import Drone from eos.saveddata.fighter import Fighter from eos.saveddata.module import Module, Rack from eos.saveddata.fit import Fit +from eos.saveddata.targetProfile import TargetProfile from eos.const import FittingSlot from service.fit import Fit as FitSvc from service.market import Market @@ -94,6 +95,8 @@ class BaseName(ViewColumn): return stuff.item.name elif isinstance(stuff, Implant): return stuff.item.name + elif isinstance(stuff, TargetProfile): + return stuff.name else: item = getattr(stuff, "item", stuff) diff --git a/gui/graphFrame/lists.py b/gui/graphFrame/lists.py index e4567231d..85b7ec239 100644 --- a/gui/graphFrame/lists.py +++ b/gui/graphFrame/lists.py @@ -23,6 +23,7 @@ import wx import gui.display import gui.globalEvents as GE +from eos.saveddata.targetProfile import TargetProfile from gui.builtinShipBrowser.events import EVT_FIT_RENAMED from service.const import GraphCacheCleanupReason from service.fit import Fit @@ -107,7 +108,10 @@ class BaseList(gui.display.Display): self.removeColumn(col) for colSpec in extraColSpecs: self.appendColumnBySpec(colSpec) - self.refresh(self.fits) + self.refreshView() + + def refreshView(self): + raise NotImplementedError def OnFitRenamed(self, event): event.Skip() @@ -191,9 +195,19 @@ class FitList(BaseList): self.fits.append(fit) self.update(self.fits) + def refreshView(self): + self.refresh(self.fits) + class TargetList(BaseList): def __init__(self, graphFrame, parent): super().__init__(graphFrame, parent) - self.update(self.fits) + self.profiles = [] + self.profiles.append(TargetProfile.getIdeal()) + stuff = self.fits + self.profiles + self.update(stuff) + + def refreshView(self): + stuff = self.fits + self.profiles + self.refresh(stuff) diff --git a/gui/utils/numberFormatter.py b/gui/utils/numberFormatter.py index bd93c0625..12d53a564 100644 --- a/gui/utils/numberFormatter.py +++ b/gui/utils/numberFormatter.py @@ -16,6 +16,8 @@ def formatAmount(val, prec=3, lowest=0, highest=0, currency=False, forceSign=Fal """ if val is None: return "" + if val == math.inf: + return "\u221e" if unitName is None else "\u221e {}".format(unitName) # Define suffix maps posSuffixMap = {3: "k", 6: "M", 9: "B" if currency is True else "G"} negSuffixMap = {-6: '\u03bc', -3: "m"}