Merge remote-tracking branch 'upstream/master'
updated from upstream
This commit is contained in:
12
README.md
12
README.md
@@ -1,5 +1,7 @@
|
|||||||
# pyfa
|
# pyfa
|
||||||
|
|
||||||
|
[](https://gitter.im/pyfa-org/Pyfa?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
## What is it?
|
## What is it?
|
||||||
@@ -12,7 +14,7 @@ The latest version along with release notes can always be found on the projects
|
|||||||
## Installing
|
## Installing
|
||||||
Windows and OS X users are supplied self-contained builds of pyfa that can be run without additional software. An `.exe` installer is also available for the Windows builds. There is no self-contained package for Linux users, which are expected to run pyfa through their distributions Python interpreter. However, there are a number of third-party packages available that handle the dependencies and updates for pyfa (for example, [pyfa for Arch Linux](https://aur.archlinux.org/packages/pyfa/)). Please check your distributions repositories.
|
Windows and OS X users are supplied self-contained builds of pyfa that can be run without additional software. An `.exe` installer is also available for the Windows builds. There is no self-contained package for Linux users, which are expected to run pyfa through their distributions Python interpreter. However, there are a number of third-party packages available that handle the dependencies and updates for pyfa (for example, [pyfa for Arch Linux](https://aur.archlinux.org/packages/pyfa/)). Please check your distributions repositories.
|
||||||
|
|
||||||
## Requirements
|
### Requirements
|
||||||
If you wish to help with development or simply need to run pyfa through a Python interpreter, the following software is required:
|
If you wish to help with development or simply need to run pyfa through a Python interpreter, the following software is required:
|
||||||
|
|
||||||
* Python 2.7
|
* Python 2.7
|
||||||
@@ -22,6 +24,14 @@ If you wish to help with development or simply need to run pyfa through a Python
|
|||||||
* `matplotlib` (for some Linux distributions, you may need to install separate wxPython bindings, such as `python-matplotlib-wx`)
|
* `matplotlib` (for some Linux distributions, you may need to install separate wxPython bindings, such as `python-matplotlib-wx`)
|
||||||
* `requests`
|
* `requests`
|
||||||
|
|
||||||
|
### Linux Distro-specific Packages
|
||||||
|
The following is a list of pyfa packages available for certain distros. Please note that these packages are maintained by third-parties and are not evaluated by the pyfa developers.
|
||||||
|
|
||||||
|
* Debian/Ubuntu/derivitives: https://github.com/AdamMajer/Pyfa/releases
|
||||||
|
* Arch: https://aur.archlinux.org/packages/pyfa/
|
||||||
|
* openSUSE: https://build.opensuse.org/package/show/home:rmk2/pyfa
|
||||||
|
* FreeBSD: http://www.freshports.org/games/pyfa/ (see #484 for instructions)
|
||||||
|
|
||||||
## Bug Reporting
|
## Bug Reporting
|
||||||
The preferred method of reporting bugs is through the projects GitHub Issues interface. Alternatively, posting a report in the pyfa thread on the official EVE Online forums is acceptable. Guidelines for bug reporting can be found on [this wiki page](https://github.com/DarkFenX/Pyfa/wiki/Bug-Reporting).
|
The preferred method of reporting bugs is through the projects GitHub Issues interface. Alternatively, posting a report in the pyfa thread on the official EVE Online forums is acceptable. Guidelines for bug reporting can be found on [this wiki page](https://github.com/DarkFenX/Pyfa/wiki/Bug-Reporting).
|
||||||
|
|
||||||
|
|||||||
@@ -18,10 +18,10 @@ debug = False
|
|||||||
saveInRoot = False
|
saveInRoot = False
|
||||||
|
|
||||||
# Version data
|
# Version data
|
||||||
version = "1.18.0"
|
version = "1.19.1"
|
||||||
tag = "Stable"
|
tag = "Stable"
|
||||||
expansionName = "YC 118.1"
|
expansionName = "February 2016"
|
||||||
expansionVersion = "1.0"
|
expansionVersion = "1.1"
|
||||||
evemonMinVersion = "4081"
|
evemonMinVersion = "4081"
|
||||||
|
|
||||||
pyfaPath = None
|
pyfaPath = None
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
gangBonus = "commandBonusECM"
|
gangBonus = "commandBonusECM"
|
||||||
gangBoost = "ewarStrECM"
|
gangBoost = "ewarStrECM"
|
||||||
type = "active", "gang"
|
type = "active", "gang"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
for scanType in ("Magnetometric", "Radar", "Ladar", "Gravimetric"):
|
for scanType in ("Magnetometric", "Radar", "Ladar", "Gravimetric"):
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
gangBonus = "commandBonusRSD"
|
gangBonus = "commandBonusRSD"
|
||||||
gangBoost = "ewarStrRSD"
|
gangBoost = "ewarStrRSD"
|
||||||
type = "active", "gang"
|
type = "active", "gang"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Sensor Linking"),
|
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Sensor Linking"),
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
gangBonus = "commandBonusTD"
|
gangBonus = "commandBonusTD"
|
||||||
gangBoost = "ewarStrTD"
|
gangBoost = "ewarStrTD"
|
||||||
type = "active", "gang"
|
type = "active", "gang"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
for bonus in (
|
for bonus in (
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
gangBonus = "commandBonusTP"
|
gangBonus = "commandBonusTP"
|
||||||
gangBoost = "ewarStrTP"
|
gangBoost = "ewarStrTP"
|
||||||
type = "active", "gang"
|
type = "active", "gang"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Target Painting"),
|
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Target Painting"),
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
# droneDmgBonus
|
# droneDmgBonus
|
||||||
#
|
#
|
||||||
# Used by:
|
# Used by:
|
||||||
# Skills from group: Drones (8 of 21)
|
# Skills from group: Drones (8 of 23)
|
||||||
# Skills named like: Drone Specialization (4 of 4)
|
# Skills named like: Drone Specialization (4 of 4)
|
||||||
type = "passive"
|
type = "passive"
|
||||||
def handler(fit, skill, context):
|
def handler(fit, skill, context):
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
# energyDestabilizationNew
|
# energyDestabilizationNew
|
||||||
#
|
#
|
||||||
# Used by:
|
# Used by:
|
||||||
# Drones from group: Cap Drain Drone (3 of 3)
|
# Drones from group: Energy Neutralizer Drone (3 of 3)
|
||||||
from eos.types import State
|
from eos.types import State
|
||||||
type = "active", "projected"
|
type = "active", "projected"
|
||||||
def handler(fit, container, context):
|
def handler(fit, container, context):
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Skirmish Warfare Link - Rapid Deployment I (2 of 2)
|
# Variations of module: Skirmish Warfare Link - Rapid Deployment I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "speedFactor"
|
gangBoost = "speedFactor"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name == "Propulsion Module",
|
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name == "Propulsion Module",
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Armored Warfare Link - Passive Defense I (2 of 2)
|
# Variations of module: Armored Warfare Link - Passive Defense I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "armorResistance"
|
gangBoost = "armorResistance"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
for damageType in ("Em", "Thermal", "Explosive", "Kinetic"):
|
for damageType in ("Em", "Thermal", "Explosive", "Kinetic"):
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Armored Warfare Link - Damage Control I (2 of 2)
|
# Variations of module: Armored Warfare Link - Damage Control I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "armorRepairCapacitorNeed"
|
gangBoost = "armorRepairCapacitorNeed"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Repair Systems") or mod.item.requiresSkill("Remote Armor Repair Systems"),
|
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Repair Systems") or mod.item.requiresSkill("Remote Armor Repair Systems"),
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Armored Warfare Link - Rapid Repair I (2 of 2)
|
# Variations of module: Armored Warfare Link - Rapid Repair I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "armorRepairDuration"
|
gangBoost = "armorRepairDuration"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Repair Systems") or mod.item.requiresSkill("Remote Armor Repair Systems"),
|
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Repair Systems") or mod.item.requiresSkill("Remote Armor Repair Systems"),
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Skirmish Warfare Link - Evasive Maneuvers I (2 of 2)
|
# Variations of module: Skirmish Warfare Link - Evasive Maneuvers I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "signatureRadius"
|
gangBoost = "signatureRadius"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.ship.boostItemAttr("signatureRadius", module.getModifiedItemAttr("commandBonus"),
|
fit.ship.boostItemAttr("signatureRadius", module.getModifiedItemAttr("commandBonus"),
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Information Warfare Link - Recon Operation I (2 of 2)
|
# Variations of module: Information Warfare Link - Recon Operation I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "electronicMaxRange"
|
gangBoost = "electronicMaxRange"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
groups = ("Target Painter", "Weapon Disruptor", "Remote Sensor Damper", "ECM", "ECM Burst")
|
groups = ("Target Painter", "Weapon Disruptor", "Remote Sensor Damper", "ECM", "ECM Burst")
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
# Used by:
|
# Used by:
|
||||||
# Variations of module: Information Warfare Link - Electronic Superiority I (2 of 2)
|
# Variations of module: Information Warfare Link - Electronic Superiority I (2 of 2)
|
||||||
type = "active"
|
type = "active"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
module.multiplyItemAttr("commandBonusTD", module.getModifiedItemAttr("commandBonusHidden"))
|
module.multiplyItemAttr("commandBonusTD", module.getModifiedItemAttr("commandBonusHidden"))
|
||||||
module.multiplyItemAttr("commandBonusECM", module.getModifiedItemAttr("commandBonusHidden"))
|
module.multiplyItemAttr("commandBonusECM", module.getModifiedItemAttr("commandBonusHidden"))
|
||||||
|
|||||||
@@ -4,9 +4,11 @@
|
|||||||
# Variations of module: Skirmish Warfare Link - Interdiction Maneuvers I (2 of 2)
|
# Variations of module: Skirmish Warfare Link - Interdiction Maneuvers I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "interdictionMaxRange"
|
gangBoost = "interdictionMaxRange"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
groups = ("Stasis Web","Warp Scrambler")
|
groups = ("Stasis Web", "Warp Scrambler")
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name in groups,
|
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name in groups,
|
||||||
"maxRange", module.getModifiedItemAttr("commandBonus"),
|
"maxRange", module.getModifiedItemAttr("commandBonus"),
|
||||||
stackingPenalties = True)
|
stackingPenalties = True)
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "maxTargetRange"
|
gangBoost = "maxTargetRange"
|
||||||
gangBonus = "commandBonus"
|
gangBonus = "commandBonus"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.ship.boostItemAttr("maxTargetRange", module.getModifiedItemAttr("commandBonus"),
|
fit.ship.boostItemAttr("maxTargetRange", module.getModifiedItemAttr("commandBonus"),
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Siege Warfare Link - Shield Efficiency I (2 of 2)
|
# Variations of module: Siege Warfare Link - Shield Efficiency I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "shieldRepairCapacitorNeed"
|
gangBoost = "shieldRepairCapacitorNeed"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Shield Operation") or mod.item.requiresSkill("Shield Emission Systems"),
|
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Shield Operation") or mod.item.requiresSkill("Shield Emission Systems"),
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Siege Warfare Link - Active Shielding I (2 of 2)
|
# Variations of module: Siege Warfare Link - Active Shielding I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "shieldRepairDuration"
|
gangBoost = "shieldRepairDuration"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Shield Operation") or mod.item.requiresSkill("Shield Emission Systems"),
|
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Shield Operation") or mod.item.requiresSkill("Shield Emission Systems"),
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
# Variations of module: Siege Warfare Link - Shield Harmonizing I (2 of 2)
|
# Variations of module: Siege Warfare Link - Shield Harmonizing I (2 of 2)
|
||||||
type = "gang", "active"
|
type = "gang", "active"
|
||||||
gangBoost = "shieldResistance"
|
gangBoost = "shieldResistance"
|
||||||
|
runTime = "late"
|
||||||
|
|
||||||
def handler(fit, module, context):
|
def handler(fit, module, context):
|
||||||
if "gang" not in context: return
|
if "gang" not in context: return
|
||||||
for damageType in ("Em", "Explosive", "Thermal", "Kinetic"):
|
for damageType in ("Em", "Explosive", "Thermal", "Kinetic"):
|
||||||
|
|||||||
@@ -6,4 +6,4 @@ type = "gang"
|
|||||||
gangBoost = "scanResolution"
|
gangBoost = "scanResolution"
|
||||||
gangBonus = "scanResolutionBonus"
|
gangBonus = "scanResolutionBonus"
|
||||||
def handler(fit, skill, context):
|
def handler(fit, skill, context):
|
||||||
fit.ship.boostItemAttr(gangBoost, skill.getModifiedItemAttr(gangBonus) * skill.level)
|
fit.ship.boostItemAttr(gangBoost, skill.getModifiedItemAttr(gangBonus) * skill.level, stackingPenalties = True)
|
||||||
|
|||||||
@@ -7,4 +7,4 @@ gangBoost = "maxTargetRange"
|
|||||||
gangBonus = "maxTargetRangeBonus"
|
gangBonus = "maxTargetRangeBonus"
|
||||||
def handler(fit, container, context):
|
def handler(fit, container, context):
|
||||||
level = container.level if "skill" in context else 1
|
level = container.level if "skill" in context else 1
|
||||||
fit.ship.boostItemAttr(gangBoost, container.getModifiedItemAttr(gangBonus) * level)
|
fit.ship.boostItemAttr(gangBoost, container.getModifiedItemAttr(gangBonus) * level, stackingPenalties = True )
|
||||||
|
|||||||
@@ -7,4 +7,4 @@ gangBoost = "agility"
|
|||||||
gangBonus = "agilityBonus"
|
gangBonus = "agilityBonus"
|
||||||
def handler(fit, container, context):
|
def handler(fit, container, context):
|
||||||
level = container.level if "skill" in context else 1
|
level = container.level if "skill" in context else 1
|
||||||
fit.ship.boostItemAttr(gangBoost, container.getModifiedItemAttr(gangBonus) * level)
|
fit.ship.boostItemAttr(gangBoost, container.getModifiedItemAttr(gangBonus) * level, stackingPenalties = True)
|
||||||
|
|||||||
@@ -476,9 +476,6 @@ class Fit(object):
|
|||||||
logger.debug("Fit has already been calculated and is not projected, returning: %r", self)
|
logger.debug("Fit has already been calculated and is not projected, returning: %r", self)
|
||||||
return
|
return
|
||||||
|
|
||||||
# Mark fit as calculated
|
|
||||||
self.__calculated = True
|
|
||||||
|
|
||||||
for runTime in ("early", "normal", "late"):
|
for runTime in ("early", "normal", "late"):
|
||||||
# Items that are unrestricted. These items are run on the local fit
|
# Items that are unrestricted. These items are run on the local fit
|
||||||
# first and then projected onto the target fit it one is designated
|
# first and then projected onto the target fit it one is designated
|
||||||
@@ -505,9 +502,10 @@ class Fit(object):
|
|||||||
# Registering the item about to affect the fit allows us to
|
# Registering the item about to affect the fit allows us to
|
||||||
# track "Affected By" relations correctly
|
# track "Affected By" relations correctly
|
||||||
if item is not None:
|
if item is not None:
|
||||||
# apply effects locally
|
if not self.__calculated:
|
||||||
self.register(item)
|
# apply effects locally if this is first time running them on fit
|
||||||
item.calculateModifiedAttributes(self, runTime, False)
|
self.register(item)
|
||||||
|
item.calculateModifiedAttributes(self, runTime, False)
|
||||||
|
|
||||||
if projected is True and item not in chain.from_iterable(r):
|
if projected is True and item not in chain.from_iterable(r):
|
||||||
# apply effects onto target fit
|
# apply effects onto target fit
|
||||||
@@ -517,6 +515,9 @@ class Fit(object):
|
|||||||
|
|
||||||
timer.checkpoint('Done with runtime: %s'%runTime)
|
timer.checkpoint('Done with runtime: %s'%runTime)
|
||||||
|
|
||||||
|
# Mark fit as calculated
|
||||||
|
self.__calculated = True
|
||||||
|
|
||||||
# Only apply projected fits if fit it not projected itself.
|
# Only apply projected fits if fit it not projected itself.
|
||||||
if not projected:
|
if not projected:
|
||||||
for fit in self.projectedFits:
|
for fit in self.projectedFits:
|
||||||
|
|||||||
@@ -374,7 +374,7 @@ class Module(HandledItem, HandledCharge, ItemAttrShortcut, ChargeAttrShortcut):
|
|||||||
if shipType is not None:
|
if shipType is not None:
|
||||||
fitsOnType.add(shipType)
|
fitsOnType.add(shipType)
|
||||||
|
|
||||||
for i in xrange(1, 6):
|
for i in xrange(1, 10):
|
||||||
shipType = self.getModifiedItemAttr("canFitShipType%d" % i)
|
shipType = self.getModifiedItemAttr("canFitShipType%d" % i)
|
||||||
if shipType is not None:
|
if shipType is not None:
|
||||||
fitsOnType.add(shipType)
|
fitsOnType.add(shipType)
|
||||||
|
|||||||
@@ -25,8 +25,16 @@ licenses = (
|
|||||||
"Silk Icons Set by famfamfam.com - Creative Commons Attribution 2.5 License",
|
"Silk Icons Set by famfamfam.com - Creative Commons Attribution 2.5 License",
|
||||||
"Fat Cow Icons by fatcow.com - Creative Commons Attribution 3.0 License"
|
"Fat Cow Icons by fatcow.com - Creative Commons Attribution 3.0 License"
|
||||||
)
|
)
|
||||||
developers = ("blitzmann \t(Sable Blitzmann)", "cncfanatics \t(Sakari Orisi) (founder)" , "DarkPhoenix \t(Kadesh Priestess) (project lead)", "Darriele \t(Darriele)")
|
developers = (
|
||||||
credits = ("Entity (Entity) \t\tCapacitor calculations / EVEAPI python lib / Reverence", "Aurora \t\t\tMaths", "Corollax (Aamrr) \tVarious EOS / pyfa improvements")
|
"blitzmann \t(Sable Blitzmann) (maintainer)",
|
||||||
|
"cncfanatics \t(Sakari Orisi)" ,
|
||||||
|
"DarkPhoenix \t(Kadesh Priestess)",
|
||||||
|
"Darriele \t\t(Darriele)")
|
||||||
|
credits = (
|
||||||
|
"Entity (Entity) \tCapacitor calculations / EVEAPI python lib / Reverence",
|
||||||
|
"Aurora \t\tMaths",
|
||||||
|
"Corollax (Aamrr) \tVarious EOS / pyfa improvements",
|
||||||
|
"Dreae (Dreae)\tPyCrest")
|
||||||
description = (
|
description = (
|
||||||
"Pyfa (the Python Fitting Assistant) is an open-source standalone application able to "
|
"Pyfa (the Python Fitting Assistant) is an open-source standalone application able to "
|
||||||
"create and simulate fittings for EVE-Online SciFi MMORPG with a very high degree of "
|
"create and simulate fittings for EVE-Online SciFi MMORPG with a very high degree of "
|
||||||
|
|||||||
@@ -97,8 +97,8 @@ class PFCrestPref ( PreferenceView):
|
|||||||
service.Crest.restartService()
|
service.Crest.restartService()
|
||||||
|
|
||||||
def OnBtnApply(self, event):
|
def OnBtnApply(self, event):
|
||||||
self.settings.set('clientID', self.inputClientID.GetValue())
|
self.settings.set('clientID', self.inputClientID.GetValue().strip())
|
||||||
self.settings.set('clientSecret', self.inputClientSecret.GetValue())
|
self.settings.set('clientSecret', self.inputClientSecret.GetValue().strip())
|
||||||
sCrest = service.Crest.getInstance()
|
sCrest = service.Crest.getInstance()
|
||||||
sCrest.delAllCharacters()
|
sCrest.delAllCharacters()
|
||||||
|
|
||||||
|
|||||||
@@ -62,6 +62,8 @@ class PFGeneralPref ( PreferenceView):
|
|||||||
self.cbGaugeAnimation = wx.CheckBox( panel, wx.ID_ANY, u"Animate gauges", wx.DefaultPosition, wx.DefaultSize, 0 )
|
self.cbGaugeAnimation = wx.CheckBox( panel, wx.ID_ANY, u"Animate gauges", wx.DefaultPosition, wx.DefaultSize, 0 )
|
||||||
mainSizer.Add( self.cbGaugeAnimation, 0, wx.ALL|wx.EXPAND, 5 )
|
mainSizer.Add( self.cbGaugeAnimation, 0, wx.ALL|wx.EXPAND, 5 )
|
||||||
|
|
||||||
|
self.cbExportCharges = wx.CheckBox( panel, wx.ID_ANY, u"Export loaded charges", wx.DefaultPosition, wx.DefaultSize, 0 )
|
||||||
|
mainSizer.Add( self.cbExportCharges, 0, wx.ALL|wx.EXPAND, 5 )
|
||||||
|
|
||||||
defCharSizer = wx.BoxSizer( wx.HORIZONTAL )
|
defCharSizer = wx.BoxSizer( wx.HORIZONTAL )
|
||||||
|
|
||||||
@@ -78,6 +80,7 @@ class PFGeneralPref ( PreferenceView):
|
|||||||
self.cbShowTooltip.SetValue(self.sFit.serviceFittingOptions["showTooltip"] or False)
|
self.cbShowTooltip.SetValue(self.sFit.serviceFittingOptions["showTooltip"] or False)
|
||||||
self.cbMarketShortcuts.SetValue(self.sFit.serviceFittingOptions["showMarketShortcuts"] or False)
|
self.cbMarketShortcuts.SetValue(self.sFit.serviceFittingOptions["showMarketShortcuts"] or False)
|
||||||
self.cbGaugeAnimation.SetValue(self.sFit.serviceFittingOptions["enableGaugeAnimation"])
|
self.cbGaugeAnimation.SetValue(self.sFit.serviceFittingOptions["enableGaugeAnimation"])
|
||||||
|
self.cbExportCharges.SetValue(self.sFit.serviceFittingOptions["exportCharges"])
|
||||||
|
|
||||||
self.cbGlobalChar.Bind(wx.EVT_CHECKBOX, self.OnCBGlobalCharStateChange)
|
self.cbGlobalChar.Bind(wx.EVT_CHECKBOX, self.OnCBGlobalCharStateChange)
|
||||||
self.cbGlobalDmgPattern.Bind(wx.EVT_CHECKBOX, self.OnCBGlobalDmgPatternStateChange)
|
self.cbGlobalDmgPattern.Bind(wx.EVT_CHECKBOX, self.OnCBGlobalDmgPatternStateChange)
|
||||||
@@ -90,6 +93,7 @@ class PFGeneralPref ( PreferenceView):
|
|||||||
self.cbShowTooltip.Bind(wx.EVT_CHECKBOX, self.onCBShowTooltip)
|
self.cbShowTooltip.Bind(wx.EVT_CHECKBOX, self.onCBShowTooltip)
|
||||||
self.cbMarketShortcuts.Bind(wx.EVT_CHECKBOX, self.onCBShowShortcuts)
|
self.cbMarketShortcuts.Bind(wx.EVT_CHECKBOX, self.onCBShowShortcuts)
|
||||||
self.cbGaugeAnimation.Bind(wx.EVT_CHECKBOX, self.onCBGaugeAnimation)
|
self.cbGaugeAnimation.Bind(wx.EVT_CHECKBOX, self.onCBGaugeAnimation)
|
||||||
|
self.cbExportCharges.Bind(wx.EVT_CHECKBOX, self.onCBExportCharges)
|
||||||
|
|
||||||
self.cbRackLabels.Enable(self.sFit.serviceFittingOptions["rackSlots"] or False)
|
self.cbRackLabels.Enable(self.sFit.serviceFittingOptions["rackSlots"] or False)
|
||||||
|
|
||||||
@@ -152,6 +156,9 @@ class PFGeneralPref ( PreferenceView):
|
|||||||
def onCBGaugeAnimation(self, event):
|
def onCBGaugeAnimation(self, event):
|
||||||
self.sFit.serviceFittingOptions["enableGaugeAnimation"] = self.cbGaugeAnimation.GetValue()
|
self.sFit.serviceFittingOptions["enableGaugeAnimation"] = self.cbGaugeAnimation.GetValue()
|
||||||
|
|
||||||
|
def onCBExportCharges(self, event):
|
||||||
|
self.sFit.serviceFittingOptions["exportCharges"] = self.cbExportCharges.GetValue()
|
||||||
|
|
||||||
def getImage(self):
|
def getImage(self):
|
||||||
return BitmapLoader.getBitmap("prefs_settings", "gui")
|
return BitmapLoader.getBitmap("prefs_settings", "gui")
|
||||||
|
|
||||||
|
|||||||
@@ -96,7 +96,7 @@ class PFUpdatePref (PreferenceView):
|
|||||||
self.resetButton.Hide()
|
self.resetButton.Hide()
|
||||||
|
|
||||||
def OnDownload(self, event):
|
def OnDownload(self, event):
|
||||||
wx.LaunchDefaultBrowser('https://github.com/DarkFenX/Pyfa/releases/tag/'+self.UpdateSettings.get('version'))
|
wx.LaunchDefaultBrowser('https://github.com/pyfa-org/Pyfa/releases/tag/'+self.UpdateSettings.get('version'))
|
||||||
|
|
||||||
def getImage(self):
|
def getImage(self):
|
||||||
return BitmapLoader.getBitmap("prefs_update", "gui")
|
return BitmapLoader.getBitmap("prefs_update", "gui")
|
||||||
|
|||||||
@@ -426,7 +426,7 @@ class Miscellanea(ViewColumn):
|
|||||||
ttEntries.append("shield")
|
ttEntries.append("shield")
|
||||||
tooltip = "{0} repaired per second".format(formatList(ttEntries)).capitalize()
|
tooltip = "{0} repaired per second".format(formatList(ttEntries)).capitalize()
|
||||||
return text, tooltip
|
return text, tooltip
|
||||||
elif itemGroup == "Cap Drain Drone":
|
elif itemGroup == "Energy Neutralizer Drone":
|
||||||
neutAmount = stuff.getModifiedItemAttr("energyDestabilizationAmount")
|
neutAmount = stuff.getModifiedItemAttr("energyDestabilizationAmount")
|
||||||
cycleTime = stuff.getModifiedItemAttr("duration")
|
cycleTime = stuff.getModifiedItemAttr("duration")
|
||||||
if not neutAmount or not cycleTime:
|
if not neutAmount or not cycleTime:
|
||||||
|
|||||||
@@ -32,7 +32,7 @@ import gui.globalEvents as GE
|
|||||||
class CharacterEditor(wx.Frame):
|
class CharacterEditor(wx.Frame):
|
||||||
def __init__(self, parent):
|
def __init__(self, parent):
|
||||||
wx.Frame.__init__ (self, parent, id=wx.ID_ANY, title=u"pyfa: Character Editor", pos=wx.DefaultPosition,
|
wx.Frame.__init__ (self, parent, id=wx.ID_ANY, title=u"pyfa: Character Editor", pos=wx.DefaultPosition,
|
||||||
size=wx.Size(641, 600), style=wx.DEFAULT_FRAME_STYLE|wx.FRAME_FLOAT_ON_PARENT|wx.TAB_TRAVERSAL)
|
size=wx.Size(640, 600), style=wx.DEFAULT_FRAME_STYLE ^ wx.RESIZE_BORDER)
|
||||||
|
|
||||||
i = wx.IconFromBitmap(BitmapLoader.getBitmap("character_small", "gui"))
|
i = wx.IconFromBitmap(BitmapLoader.getBitmap("character_small", "gui"))
|
||||||
self.SetIcon(i)
|
self.SetIcon(i)
|
||||||
@@ -40,7 +40,6 @@ class CharacterEditor(wx.Frame):
|
|||||||
self.mainFrame = parent
|
self.mainFrame = parent
|
||||||
|
|
||||||
#self.disableWin = wx.WindowDisabler(self)
|
#self.disableWin = wx.WindowDisabler(self)
|
||||||
self.SetSizeHintsSz(wx.Size(640, 600), wx.DefaultSize)
|
|
||||||
self.SetBackgroundColour( wx.SystemSettings.GetColour( wx.SYS_COLOUR_BTNFACE ) )
|
self.SetBackgroundColour( wx.SystemSettings.GetColour( wx.SYS_COLOUR_BTNFACE ) )
|
||||||
|
|
||||||
mainSizer = wx.BoxSizer(wx.VERTICAL)
|
mainSizer = wx.BoxSizer(wx.VERTICAL)
|
||||||
|
|||||||
@@ -326,6 +326,7 @@ class MainFrame(wx.Frame):
|
|||||||
|
|
||||||
def ShowAboutBox(self, evt):
|
def ShowAboutBox(self, evt):
|
||||||
import eos.config
|
import eos.config
|
||||||
|
v = sys.version_info
|
||||||
info = wx.AboutDialogInfo()
|
info = wx.AboutDialogInfo()
|
||||||
info.Name = "pyfa"
|
info.Name = "pyfa"
|
||||||
info.Version = gui.aboutData.versionString
|
info.Version = gui.aboutData.versionString
|
||||||
@@ -336,14 +337,14 @@ class MainFrame(wx.Frame):
|
|||||||
"\n\nLicenses:\n\t" +
|
"\n\nLicenses:\n\t" +
|
||||||
"\n\t".join(gui.aboutData.licenses) +
|
"\n\t".join(gui.aboutData.licenses) +
|
||||||
"\n\nEVE Data: \t" + eos.config.gamedata_version +
|
"\n\nEVE Data: \t" + eos.config.gamedata_version +
|
||||||
"\nPython: \t" + sys.version +
|
"\nPython: \t\t" + '{}.{}.{}'.format(v.major, v.minor, v.micro) +
|
||||||
"\nwxPython: \t" + wx.__version__ +
|
"\nwxPython: \t" + wx.__version__ +
|
||||||
"\nSQLAlchemy: \t" + sqlalchemy.__version__,
|
"\nSQLAlchemy: \t" + sqlalchemy.__version__,
|
||||||
700, wx.ClientDC(self))
|
500, wx.ClientDC(self))
|
||||||
if "__WXGTK__" in wx.PlatformInfo:
|
if "__WXGTK__" in wx.PlatformInfo:
|
||||||
forumUrl = "http://forums.eveonline.com/default.aspx?g=posts&t=247609"
|
forumUrl = "http://forums.eveonline.com/default.aspx?g=posts&t=466425"
|
||||||
else:
|
else:
|
||||||
forumUrl = "http://forums.eveonline.com/default.aspx?g=posts&t=247609"
|
forumUrl = "http://forums.eveonline.com/default.aspx?g=posts&t=466425"
|
||||||
info.WebSite = (forumUrl, "pyfa thread at EVE Online forum")
|
info.WebSite = (forumUrl, "pyfa thread at EVE Online forum")
|
||||||
wx.AboutBox(info)
|
wx.AboutBox(info)
|
||||||
|
|
||||||
@@ -397,10 +398,10 @@ class MainFrame(wx.Frame):
|
|||||||
dlg.ShowModal()
|
dlg.ShowModal()
|
||||||
|
|
||||||
def goWiki(self, event):
|
def goWiki(self, event):
|
||||||
webbrowser.open('https://github.com/DarkFenX/Pyfa/wiki')
|
webbrowser.open('https://github.com/pyfa-org/Pyfa/wiki')
|
||||||
|
|
||||||
def goForums(self, event):
|
def goForums(self, event):
|
||||||
webbrowser.open('https://forums.eveonline.com/default.aspx?g=posts&t=247609')
|
webbrowser.open('https://forums.eveonline.com/default.aspx?g=posts&t=466425')
|
||||||
|
|
||||||
def registerMenu(self):
|
def registerMenu(self):
|
||||||
menuBar = self.GetMenuBar()
|
menuBar = self.GetMenuBar()
|
||||||
|
|||||||
@@ -108,7 +108,8 @@ class MainMenuBar(wx.MenuBar):
|
|||||||
graphFrameItem.SetBitmap(BitmapLoader.getBitmap("graphs_small", "gui"))
|
graphFrameItem.SetBitmap(BitmapLoader.getBitmap("graphs_small", "gui"))
|
||||||
windowMenu.AppendItem(graphFrameItem)
|
windowMenu.AppendItem(graphFrameItem)
|
||||||
|
|
||||||
preferencesItem = wx.MenuItem(windowMenu, wx.ID_PREFERENCES, "Preferences\tCTRL+P")
|
preferencesShortCut = "CTRL+," if 'wxMac' in wx.PlatformInfo else "CTRL+P"
|
||||||
|
preferencesItem = wx.MenuItem(windowMenu, wx.ID_PREFERENCES, "Preferences\t"+preferencesShortCut)
|
||||||
preferencesItem.SetBitmap(BitmapLoader.getBitmap("preferences_small", "gui"))
|
preferencesItem.SetBitmap(BitmapLoader.getBitmap("preferences_small", "gui"))
|
||||||
windowMenu.AppendItem(preferencesItem)
|
windowMenu.AppendItem(preferencesItem)
|
||||||
|
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
##
|
##
|
||||||
## Author: Darriele - HomeWorld
|
## Author: Darriele - HomeWorld
|
||||||
##
|
##
|
||||||
## Project home: http://github.com/DarkFenX/Pyfa - pyfa project
|
## Project home: https://github.com/pyfa-org/Pyfa - pyfa project
|
||||||
## Some portions of code are based on
|
## Some portions of code are based on
|
||||||
## AGW:pycollapsiblepane generic implementation of wx.CollapsiblePane
|
## AGW:pycollapsiblepane generic implementation of wx.CollapsiblePane
|
||||||
## AGW:pycollapsiblepane credits ( from the original source file used ):
|
## AGW:pycollapsiblepane credits ( from the original source file used ):
|
||||||
|
|||||||
@@ -116,5 +116,5 @@ class UpdateDialog(wx.Dialog):
|
|||||||
self.UpdateSettings.set('version', None)
|
self.UpdateSettings.set('version', None)
|
||||||
|
|
||||||
def OnDownload(self, e):
|
def OnDownload(self, e):
|
||||||
wx.LaunchDefaultBrowser('https://github.com/DarkFenX/Pyfa/releases/tag/'+self.releaseInfo['tag_name'])
|
wx.LaunchDefaultBrowser('https://github.com/pyfa-org/Pyfa/releases/tag/'+self.releaseInfo['tag_name'])
|
||||||
self.OnClose(e)
|
self.OnClose(e)
|
||||||
|
|||||||
@@ -15,7 +15,7 @@
|
|||||||
|
|
||||||
#define MyAppName "pyfa"
|
#define MyAppName "pyfa"
|
||||||
#define MyAppPublisher "pyfa"
|
#define MyAppPublisher "pyfa"
|
||||||
#define MyAppURL "https://forums.eveonline.com/default.aspx?g=posts&t=247609&p=1"
|
#define MyAppURL "https://forums.eveonline.com/default.aspx?g=posts&t=466425&p=1"
|
||||||
#define MyAppExeName "pyfa.exe"
|
#define MyAppExeName "pyfa.exe"
|
||||||
|
|
||||||
; What version starts with the new structure (1.x.0). This is used to determine if we run directory structure cleanup
|
; What version starts with the new structure (1.x.0). This is used to determine if we run directory structure cleanup
|
||||||
@@ -53,7 +53,7 @@ SetupIconFile={#MyAppDir}\pyfa.ico
|
|||||||
Compression=lzma
|
Compression=lzma
|
||||||
SolidCompression=yes
|
SolidCompression=yes
|
||||||
CloseApplications=yes
|
CloseApplications=yes
|
||||||
AppReadmeFile=https://github.com/DarkFenX/Pyfa/blob/v{#MyAppVersion}/readme.txt
|
AppReadmeFile=https://github.com/pyfa-org/Pyfa/blob/v{#MyAppVersion}/readme.txt
|
||||||
|
|
||||||
[Languages]
|
[Languages]
|
||||||
Name: "english"; MessagesFile: "compiler:Default.isl"
|
Name: "english"; MessagesFile: "compiler:Default.isl"
|
||||||
|
|||||||
10
service/conversions/releaseFeb2016.py
Normal file
10
service/conversions/releaseFeb2016.py
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
"""
|
||||||
|
Conversion pack for January 2016 (YC118.1) release
|
||||||
|
"""
|
||||||
|
|
||||||
|
CONVERSIONS = {
|
||||||
|
# Renamed items
|
||||||
|
"Capital Coaxial Remote Armor Repairer Blueprint": "CONCORD Capital Remote Armor Repairer Blueprint",
|
||||||
|
"Capital Murky Remote Shield Booster Blueprint": "CONCORD Capital Remote Shield Booster Blueprint",
|
||||||
|
}
|
||||||
|
|
||||||
@@ -104,7 +104,8 @@ class Fit(object):
|
|||||||
"compactSkills": True,
|
"compactSkills": True,
|
||||||
"showTooltip": True,
|
"showTooltip": True,
|
||||||
"showMarketShortcuts": False,
|
"showMarketShortcuts": False,
|
||||||
"enableGaugeAnimation": True}
|
"enableGaugeAnimation": True,
|
||||||
|
"exportCharges": True}
|
||||||
|
|
||||||
self.serviceFittingOptions = SettingsProvider.getInstance().getSettings(
|
self.serviceFittingOptions = SettingsProvider.getInstance().getSettings(
|
||||||
"pyfaServiceFittingOptions", serviceFittingDefaultOptions)
|
"pyfaServiceFittingOptions", serviceFittingDefaultOptions)
|
||||||
|
|||||||
@@ -551,12 +551,13 @@ class Port(object):
|
|||||||
offineSuffix = " /OFFLINE"
|
offineSuffix = " /OFFLINE"
|
||||||
export = "[%s, %s]\n" % (fit.ship.item.name, fit.name)
|
export = "[%s, %s]\n" % (fit.ship.item.name, fit.name)
|
||||||
stuff = {}
|
stuff = {}
|
||||||
|
sFit = service.Fit.getInstance()
|
||||||
for module in fit.modules:
|
for module in fit.modules:
|
||||||
slot = module.slot
|
slot = module.slot
|
||||||
if not slot in stuff:
|
if not slot in stuff:
|
||||||
stuff[slot] = []
|
stuff[slot] = []
|
||||||
curr = module.item.name if module.item else ("[Empty %s slot]" % Slot.getName(slot).capitalize() if slot is not None else "")
|
curr = module.item.name if module.item else ("[Empty %s slot]" % Slot.getName(slot).capitalize() if slot is not None else "")
|
||||||
if module.charge:
|
if module.charge and sFit.serviceFittingOptions["exportCharges"]:
|
||||||
curr += ", %s" % module.charge.name
|
curr += ", %s" % module.charge.name
|
||||||
if module.state == State.OFFLINE:
|
if module.state == State.OFFLINE:
|
||||||
curr += offineSuffix
|
curr += offineSuffix
|
||||||
@@ -664,6 +665,8 @@ class Port(object):
|
|||||||
doc = xml.dom.minidom.Document()
|
doc = xml.dom.minidom.Document()
|
||||||
fittings = doc.createElement("fittings")
|
fittings = doc.createElement("fittings")
|
||||||
doc.appendChild(fittings)
|
doc.appendChild(fittings)
|
||||||
|
sFit = service.Fit.getInstance()
|
||||||
|
|
||||||
for i, fit in enumerate(fits):
|
for i, fit in enumerate(fits):
|
||||||
try:
|
try:
|
||||||
fitting = doc.createElement("fitting")
|
fitting = doc.createElement("fitting")
|
||||||
@@ -701,7 +704,7 @@ class Port(object):
|
|||||||
hardware.setAttribute("slot", "%s slot %d" % (slotName, slotId))
|
hardware.setAttribute("slot", "%s slot %d" % (slotName, slotId))
|
||||||
fitting.appendChild(hardware)
|
fitting.appendChild(hardware)
|
||||||
|
|
||||||
if module.charge:
|
if module.charge and sFit.serviceFittingOptions["exportCharges"]:
|
||||||
if not module.charge.name in charges:
|
if not module.charge.name in charges:
|
||||||
charges[module.charge.name] = 0
|
charges[module.charge.name] = 0
|
||||||
# `or 1` because some charges (ie scripts) are without qty
|
# `or 1` because some charges (ie scripts) are without qty
|
||||||
|
|||||||
@@ -37,7 +37,7 @@ class CheckUpdateThread(threading.Thread):
|
|||||||
network = service.Network.getInstance()
|
network = service.Network.getInstance()
|
||||||
|
|
||||||
try:
|
try:
|
||||||
response = network.request('https://api.github.com/repos/DarkFenX/Pyfa/releases', network.UPDATE)
|
response = network.request('https://api.github.com/repos/pyfa-org/Pyfa/releases', network.UPDATE)
|
||||||
jsonResponse = json.loads(response.read())
|
jsonResponse = json.loads(response.read())
|
||||||
jsonResponse.sort(key=lambda x: calendar.timegm(dateutil.parser.parse(x['published_at']).utctimetuple()), reverse=True)
|
jsonResponse.sort(key=lambda x: calendar.timegm(dateutil.parser.parse(x['published_at']).utctimetuple()), reverse=True)
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user