Merge branch 'citadel'
@@ -18,10 +18,10 @@ debug = False
|
||||
saveInRoot = False
|
||||
|
||||
# Version data
|
||||
version = "1.22.2"
|
||||
tag = "Stable"
|
||||
expansionName = "YC 118.6"
|
||||
expansionVersion = "1.0"
|
||||
version = "1.22.3"
|
||||
tag = "git"
|
||||
expansionName = "Singularity"
|
||||
expansionVersion = "1053072"
|
||||
evemonMinVersion = "4081"
|
||||
|
||||
pyfaPath = None
|
||||
|
||||
3
eos/effects/lightningweapon.py
Normal file
@@ -0,0 +1,3 @@
|
||||
type = 'active'
|
||||
def handler(fit, module, context):
|
||||
pass
|
||||
@@ -3,7 +3,7 @@
|
||||
# Used by:
|
||||
# Modules from group: Missile Guidance Enhancer (3 of 3)
|
||||
type = "passive"
|
||||
def handler(fit, container, context):
|
||||
def handler(fit, module, context):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.requiresSkill("Missile Launcher Operation"),
|
||||
"aoeCloudSize", container.getModifiedItemAttr("aoeCloudSizeBonus"),
|
||||
"aoeCloudSize", module.getModifiedItemAttr("aoeCloudSizeBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
# Used by:
|
||||
# Modules from group: Missile Guidance Enhancer (3 of 3)
|
||||
type = "passive"
|
||||
def handler(fit, container, context):
|
||||
def handler(fit, module, context):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.requiresSkill("Missile Launcher Operation"),
|
||||
"aoeVelocity", container.getModifiedItemAttr("aoeVelocityBonus"),
|
||||
"aoeVelocity", module.getModifiedItemAttr("aoeVelocityBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
# Used by:
|
||||
# Modules from group: Missile Guidance Enhancer (3 of 3)
|
||||
type = "passive"
|
||||
def handler(fit, container, context):
|
||||
def handler(fit, module, context):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.requiresSkill("Missile Launcher Operation"),
|
||||
"explosionDelay", container.getModifiedItemAttr("explosionDelayBonus"),
|
||||
"explosionDelay", module.getModifiedItemAttr("explosionDelayBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
# Used by:
|
||||
# Modules from group: Missile Guidance Enhancer (3 of 3)
|
||||
type = "passive"
|
||||
def handler(fit, container, context):
|
||||
def handler(fit, module, context):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.requiresSkill("Missile Launcher Operation"),
|
||||
"maxVelocity", container.getModifiedItemAttr("missileVelocityBonus"),
|
||||
"maxVelocity", module.getModifiedItemAttr("missileVelocityBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
7
eos/effects/pointdefense.py
Normal file
@@ -0,0 +1,7 @@
|
||||
# targetAttack
|
||||
#
|
||||
# Used by:
|
||||
# Citadel Point Defense
|
||||
type = 'active'
|
||||
def handler(fit, module, context):
|
||||
pass
|
||||
@@ -4,7 +4,7 @@
|
||||
# Variations of module: Guidance Disruptor I (6 of 6)
|
||||
type = "active", "projected"
|
||||
|
||||
def handler(fit, src, context):
|
||||
def handler(fit, module, context):
|
||||
if "projected" in context:
|
||||
for srcAttr, tgtAttr in (
|
||||
("aoeCloudSizeBonus", "aoeCloudSize"),
|
||||
@@ -13,5 +13,5 @@ def handler(fit, src, context):
|
||||
("explosionDelayBonus", "explosionDelay"),
|
||||
):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.requiresSkill("Missile Launcher Operation"),
|
||||
tgtAttr, src.getModifiedItemAttr(srcAttr),
|
||||
tgtAttr, module.getModifiedItemAttr(srcAttr),
|
||||
stackingPenalties=True, remoteResists=True)
|
||||
|
||||
4
eos/effects/skillstructuredoomsdaydurationbonus.py
Normal file
@@ -0,0 +1,4 @@
|
||||
type = "passive", "structure"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name == "Structure Doomsday Weapon",
|
||||
"duration", src.getModifiedItemAttr("durationBonus"), skill="Structure Doomsday Operation")
|
||||
@@ -0,0 +1,5 @@
|
||||
type = "passive", "structure"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure Warp Scrambler", "Structure Disruption Battery", "Structure Stasis Webifier")
|
||||
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name in groups,
|
||||
"capacitorNeed", src.getModifiedItemAttr("capNeedBonus"), skill="Structure Electronic Systems")
|
||||
@@ -0,0 +1,5 @@
|
||||
type = "passive", "structure"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure Energy Neutralizer", "Structure Area Denial Module")
|
||||
fit.modules.filteredItemBoost(lambda mod: mod.item.group.name in groups,
|
||||
"capacitorNeed", src.getModifiedItemAttr("capNeedBonus"), skill="Structure Engineering Systems")
|
||||
6
eos/effects/skillstructuremissiledamagebonus.py
Normal file
@@ -0,0 +1,6 @@
|
||||
type = "passive", "structure"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure Anti-Capital Missile", "Structure Anti-Subcapital Missile", "Structure Guided Bomb")
|
||||
for damageType in ("em", "thermal", "explosive", "kinetic"):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.group.name in groups,
|
||||
"%sDamage"%damageType, src.getModifiedItemAttr("damageMultiplierBonus"), skill="Structure Missile Systems")
|
||||
19
eos/effects/structureMissileGuidanceEnhancer.py
Normal file
@@ -0,0 +1,19 @@
|
||||
# missileAOECloudSizeBonusOnline
|
||||
#
|
||||
# Used by:
|
||||
# Modules from group: Missile Guidance Enhancer (3 of 3)
|
||||
type = "passive"
|
||||
def handler(fit, module, context):
|
||||
groups = ("Structure Anti-Capital Missile", "Structure Anti-Subcapital Missile")
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.group.name in groups,
|
||||
"aoeCloudSize", module.getModifiedItemAttr("aoeCloudSizeBonus"),
|
||||
stackingPenalties=True)
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.group.name in groups,
|
||||
"aoeVelocity", module.getModifiedItemAttr("aoeVelocityBonus"),
|
||||
stackingPenalties=True)
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.group.name in groups,
|
||||
"explosionDelay", module.getModifiedItemAttr("explosionDelayBonus"),
|
||||
stackingPenalties=True)
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.group.name in groups,
|
||||
"maxVelocity", module.getModifiedItemAttr("missileVelocityBonus"),
|
||||
stackingPenalties=True)
|
||||
13
eos/effects/structureballisticcontrolsystem.py
Normal file
@@ -0,0 +1,13 @@
|
||||
type = "passive"
|
||||
def handler(fit, module, context):
|
||||
missileGroups = ("Structure Anti-Capital Missile", "Structure Anti-Subcapital Missile")
|
||||
|
||||
for dmgType in ("em", "kinetic", "explosive", "thermal"):
|
||||
fit.modules.filteredChargeMultiply(lambda mod: mod.charge.group.name in missileGroups,
|
||||
"%sDamage" % dmgType, module.getModifiedItemAttr("missileDamageMultiplierBonus"),
|
||||
stackingPenalties = True)
|
||||
|
||||
launcherGroups = ("Structure AXL Missile Launcher", "Structure ASML Missile Launcher")
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name in launcherGroups,
|
||||
"speed", module.getModifiedItemAttr("speedMultiplier"),
|
||||
stackingPenalties=True)
|
||||
8
eos/effects/structureenergyneutralizerfalloff.py
Normal file
@@ -0,0 +1,8 @@
|
||||
from eos.types import State
|
||||
type = "active", "projected"
|
||||
def handler(fit, container, context):
|
||||
if "projected" in context and ((hasattr(container, "state") \
|
||||
and container.state >= State.ACTIVE) or hasattr(container, "amountActive")):
|
||||
amount = container.getModifiedItemAttr("energyNeutralizerAmount")
|
||||
time = container.getModifiedItemAttr("duration")
|
||||
fit.addDrain(time, amount, 0)
|
||||
7
eos/effects/structuremoduleeffectecm.py
Normal file
@@ -0,0 +1,7 @@
|
||||
type = "projected", "active"
|
||||
def handler(fit, module, context):
|
||||
if "projected" in context:
|
||||
# jam formula: 1 - (1- (jammer str/ship str))^(# of jam mods with same str))
|
||||
strModifier = 1 - module.getModifiedItemAttr("scan{0}StrengthBonus".format(fit.scanType))/fit.scanStrength
|
||||
|
||||
fit.ecmProjectedStr *= strModifier
|
||||
11
eos/effects/structuremoduleeffectremotesensordampener.py
Normal file
@@ -0,0 +1,11 @@
|
||||
|
||||
type= "projected", "active"
|
||||
def handler(fit, module, context):
|
||||
if "projected" not in context:
|
||||
return
|
||||
|
||||
fit.ship.boostItemAttr("maxTargetRange", module.getModifiedItemAttr("maxTargetRangeBonus"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
|
||||
fit.ship.boostItemAttr("scanResolution", module.getModifiedItemAttr("scanResolutionBonus"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
5
eos/effects/structuremoduleeffectstasiswebifier.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "active", "projected"
|
||||
def handler(fit, module, context):
|
||||
if "projected" not in context: return
|
||||
fit.ship.boostItemAttr("maxVelocity", module.getModifiedItemAttr("speedFactor"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
5
eos/effects/structuremoduleeffecttargetpainter.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "projected", "active"
|
||||
def handler(fit, container, context):
|
||||
if "projected" in context:
|
||||
fit.ship.boostItemAttr("signatureRadius", container.getModifiedItemAttr("signatureRadiusBonus"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
24
eos/effects/structuremoduleeffectweapondisruption.py
Normal file
@@ -0,0 +1,24 @@
|
||||
|
||||
type = "active", "projected"
|
||||
|
||||
def handler(fit, module, context):
|
||||
if "projected" in context:
|
||||
for srcAttr, tgtAttr in (
|
||||
("aoeCloudSizeBonus", "aoeCloudSize"),
|
||||
("aoeVelocityBonus", "aoeVelocity"),
|
||||
("missileVelocityBonus", "maxVelocity"),
|
||||
("explosionDelayBonus", "explosionDelay"),
|
||||
):
|
||||
fit.modules.filteredChargeBoost(lambda mod: mod.charge.requiresSkill("Missile Launcher Operation"),
|
||||
tgtAttr, module.getModifiedItemAttr(srcAttr),
|
||||
stackingPenalties=True, remoteResists=True)
|
||||
|
||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Gunnery"),
|
||||
"trackingSpeed", module.getModifiedItemAttr("trackingSpeedBonus"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Gunnery"),
|
||||
"maxRange", module.getModifiedItemAttr("maxRangeBonus"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
fit.modules.filteredItemBoost(lambda mod: mod.item.requiresSkill("Gunnery"),
|
||||
"falloff", module.getModifiedItemAttr("falloffBonus"),
|
||||
stackingPenalties = True, remoteResists=True)
|
||||
@@ -0,0 +1,7 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure Anti-Subcapital Missile", "Structure Anti-Capital Missile")
|
||||
|
||||
fit.modules.filteredChargeMultiply(lambda mod: mod.charge.group.name in groups,
|
||||
"aoeVelocity", src.getModifiedItemAttr("structureRigMissileExploVeloBonus"),
|
||||
stackingPenalties=True)
|
||||
5
eos/effects/structurerigdoomsdaydamageloss.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Doomsday Weapon",
|
||||
"lightningWeaponDamageLossTarget", src.getModifiedItemAttr("structureRigDoomsdayDamageLossTargetBonus"),
|
||||
stackingPenalties=True)
|
||||
5
eos/effects/structurerigdoomsdaytargetamountbonus.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Doomsday Weapon",
|
||||
"lightningWeaponTargetAmount", src.getModifiedItemAttr("structureRigDoomsdayTargetAmountBonus"),
|
||||
stackingPenalties=True)
|
||||
6
eos/effects/structurerigewcapacitorneed.py
Normal file
@@ -0,0 +1,6 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure ECM Battery", "Structure Disruption Battery")
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name in groups,
|
||||
"capacitorNeed", src.getModifiedItemAttr("structureRigEwarCapUseBonus"),
|
||||
stackingPenalties=True)
|
||||
15
eos/effects/structurerigewmaxrangefalloff.py
Normal file
@@ -0,0 +1,15 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure ECM Battery", "Structure Disruption Battery")
|
||||
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name in groups,
|
||||
"falloff", src.getModifiedItemAttr("structureRigEwarFalloffBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name in groups,
|
||||
"maxRange", src.getModifiedItemAttr("structureRigEwarOptimalBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name in groups,
|
||||
"falloffEffectiveness", src.getModifiedItemAttr("structureRigEwarFalloffBonus"),
|
||||
stackingPenalties=True)
|
||||
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredChargeMultiply(lambda mod: mod.charge.group.name == "Structure Guided Bomb",
|
||||
"aoeCloudSize", src.getModifiedItemAttr("structureRigMissileExplosionRadiusBonus"),
|
||||
stackingPenalties=True)
|
||||
3
eos/effects/structurerigmaxtargets.py
Normal file
@@ -0,0 +1,3 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.ship.increaseItemAttr("maxLockedTargets", src.getModifiedItemAttr("structureRigMaxTargetBonus"))
|
||||
5
eos/effects/structurerigneutralizercapacitorneed.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Energy Neutralizer",
|
||||
"capacitorNeed", src.getModifiedItemAttr("structureRigEwarCapUseBonus"),
|
||||
stackingPenalties=True)
|
||||
@@ -0,0 +1,9 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Energy Neutralizer",
|
||||
"maxRange", src.getModifiedItemAttr("structureRigEwarOptimalBonus"),
|
||||
stackingPenalties=True)
|
||||
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Energy Neutralizer",
|
||||
"falloffEffectiveness", src.getModifiedItemAttr("structureRigEwarFalloffBonus"),
|
||||
stackingPenalties=True)
|
||||
5
eos/effects/structurerigpdbcapacitorneed.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Area Denial Module",
|
||||
"capacitorNeed", src.getModifiedItemAttr("structureRigPDCapUseBonus"),
|
||||
stackingPenalties=True)
|
||||
5
eos/effects/structurerigpdbmaxrange.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredItemMultiply(lambda mod: mod.item.group.name == "Structure Area Denial Module",
|
||||
"empFieldRange", src.getModifiedItemAttr("structureRigPDRangeBonus"),
|
||||
stackingPenalties=True)
|
||||
4
eos/effects/structurerigsensorresolution.py
Normal file
@@ -0,0 +1,4 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.ship.boostItemAttr("scanResolution", src.getModifiedItemAttr("structureRigScanResBonus"),
|
||||
stackingPenalties=True)
|
||||
5
eos/effects/structurerigvelocitybonusaoemissiles.py
Normal file
@@ -0,0 +1,5 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
fit.modules.filteredChargeMultiply(lambda mod: mod.charge.group.name == "Structure Guided Bomb",
|
||||
"maxVelocity", src.getModifiedItemAttr("structureRigMissileVelocityBonus"),
|
||||
stackingPenalties=True)
|
||||
@@ -0,0 +1,6 @@
|
||||
type = "passive"
|
||||
def handler(fit, src, context):
|
||||
groups = ("Structure Anti-Subcapital Missile", "Structure Anti-Capital Missile")
|
||||
fit.modules.filteredChargeMultiply(lambda mod: mod.charge.group.name in groups,
|
||||
"maxVelocity", src.getModifiedItemAttr("structureRigMissileVelocityBonus"),
|
||||
stackingPenalties=True)
|
||||
12
eos/effects/structurewarpscrambleblockmwdwithnpceffect.py
Normal file
@@ -0,0 +1,12 @@
|
||||
runTime = "early"
|
||||
type = "projected", "active"
|
||||
|
||||
from eos.types import State
|
||||
|
||||
def handler(fit, module, context):
|
||||
if "projected" not in context:
|
||||
return
|
||||
# this is such a dirty hack
|
||||
for mod in fit.modules:
|
||||
if not mod.isEmpty and mod.item.requiresSkill("High Speed Maneuvering") and mod.state > State.ONLINE:
|
||||
mod.state = State.ONLINE
|
||||
@@ -89,7 +89,7 @@ class Effect(EqBase):
|
||||
The type of the effect, automaticly fetched from effects/<effectName>.py if the file exists.
|
||||
|
||||
Valid values are:
|
||||
"passive", "active", "projected", "gang"
|
||||
"passive", "active", "projected", "gang", "structure"
|
||||
|
||||
Each gives valuable information to eos about what type the module having
|
||||
the effect is. passive vs active gives eos clues about wether to module
|
||||
|
||||
@@ -24,6 +24,7 @@ from itertools import chain
|
||||
from eos.effectHandlerHelpers import HandledItem, HandledImplantBoosterList
|
||||
import eos.db
|
||||
import eos
|
||||
import eos.types
|
||||
import logging
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
@@ -329,7 +330,7 @@ class Skill(HandledItem):
|
||||
return
|
||||
|
||||
for effect in item.effects.itervalues():
|
||||
if effect.runTime == runTime and effect.isType("passive"):
|
||||
if effect.runTime == runTime and effect.isType("passive") and (not fit.isStructure or effect.isType("structure")):
|
||||
try:
|
||||
effect.handler(fit, self, ("skill",))
|
||||
except AttributeError:
|
||||
|
||||
42
eos/saveddata/citadel.py
Normal file
@@ -0,0 +1,42 @@
|
||||
#===============================================================================
|
||||
# Copyright (C) 2010 Diego Duclos
|
||||
#
|
||||
# This file is part of eos.
|
||||
#
|
||||
# eos is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Lesser General Public License as published by
|
||||
# the Free Software Foundation, either version 2 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# eos is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Lesser General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Lesser General Public License
|
||||
# along with eos. If not, see <http://www.gnu.org/licenses/>.
|
||||
#===============================================================================
|
||||
|
||||
from eos.modifiedAttributeDict import ModifiedAttributeDict, ItemAttrShortcut
|
||||
from eos.effectHandlerHelpers import HandledItem
|
||||
from eos.saveddata.mode import Mode
|
||||
import eos.db
|
||||
from eos.types import Ship
|
||||
import logging
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
class Citadel(Ship):
|
||||
|
||||
def validate(self, item):
|
||||
if item.category.name != "Structure":
|
||||
raise ValueError('Passed item "%s" (category: (%s)) is not under Structure category'%(item.name, item.category.name))
|
||||
|
||||
def __deepcopy__(self, memo):
|
||||
copy = Citadel(self.item)
|
||||
return copy
|
||||
|
||||
def __repr__(self):
|
||||
return "Citadel(ID={}, name={}) at {}".format(
|
||||
self.item.ID, self.item.name, hex(id(self))
|
||||
)
|
||||
@@ -35,7 +35,7 @@ class Fighter(HandledItem, HandledCharge, ItemAttrShortcut, ChargeAttrShortcut):
|
||||
def __init__(self, item):
|
||||
"""Initialize a fighter from the program"""
|
||||
self.__item = item
|
||||
print self.__item.category.name
|
||||
|
||||
if self.isInvalid:
|
||||
raise ValueError("Passed item is not a Fighter")
|
||||
|
||||
|
||||
@@ -24,7 +24,7 @@ from itertools import chain
|
||||
from eos import capSim
|
||||
from copy import deepcopy
|
||||
from math import sqrt, log, asinh
|
||||
from eos.types import Drone, Cargo, Ship, Character, State, Slot, Module, Implant, Booster, Skill
|
||||
from eos.types import Drone, Cargo, Ship, Character, State, Slot, Module, Implant, Booster, Skill, Citadel
|
||||
from eos.saveddata.module import State, Hardpoint
|
||||
from eos.saveddata.mode import Mode
|
||||
import eos.db
|
||||
@@ -92,7 +92,10 @@ class Fit(object):
|
||||
return
|
||||
|
||||
try:
|
||||
self.__ship = Ship(item, self)
|
||||
try:
|
||||
self.__ship = Ship(item, self)
|
||||
except ValueError:
|
||||
self.__ship = Citadel(item, self)
|
||||
# @todo extra attributes is now useless, however it set to be
|
||||
# the same as ship attributes for ease (so we don't have to
|
||||
# change all instances in source). Remove this at some point
|
||||
@@ -191,6 +194,10 @@ class Fit(object):
|
||||
# set fit attributes the same as ship
|
||||
self.extraAttributes = self.ship.itemModifiedAttributes
|
||||
|
||||
@property
|
||||
def isStructure(self):
|
||||
return isinstance(self.ship, Citadel)
|
||||
|
||||
@property
|
||||
def drones(self):
|
||||
return self.__drones
|
||||
@@ -331,7 +338,7 @@ class Fit(object):
|
||||
|
||||
@property
|
||||
def alignTime(self):
|
||||
agility = self.ship.getModifiedItemAttr("agility")
|
||||
agility = self.ship.getModifiedItemAttr("agility") or 0
|
||||
mass = self.ship.getModifiedItemAttr("mass")
|
||||
|
||||
return -log(0.25) * agility * mass / 1000000
|
||||
@@ -510,6 +517,11 @@ class Fit(object):
|
||||
self.boosters,
|
||||
self.appliedImplants,
|
||||
self.modules
|
||||
] if not self.isStructure else [
|
||||
# Ensure a restricted set for citadels
|
||||
(self.character, self.ship),
|
||||
self.fighters,
|
||||
self.modules
|
||||
]
|
||||
|
||||
# Items that are restricted. These items are only run on the local
|
||||
@@ -564,7 +576,7 @@ class Fit(object):
|
||||
if self.ship is None:
|
||||
return
|
||||
|
||||
for slotType in (Slot.LOW, Slot.MED, Slot.HIGH, Slot.RIG, Slot.SUBSYSTEM):
|
||||
for slotType in (Slot.LOW, Slot.MED, Slot.HIGH, Slot.RIG, Slot.SUBSYSTEM, Slot.SERVICE):
|
||||
amount = self.getSlotsFree(slotType, True)
|
||||
if amount > 0:
|
||||
for _ in xrange(int(amount)):
|
||||
@@ -639,6 +651,7 @@ class Fit(object):
|
||||
Slot.HIGH: "hiSlots",
|
||||
Slot.RIG: "rigSlots",
|
||||
Slot.SUBSYSTEM: "maxSubSystems",
|
||||
Slot.SERVICE: "serviceSlots",
|
||||
Slot.F_LIGHT: "fighterLightSlots",
|
||||
Slot.F_SUPPORT: "fighterSupportSlots",
|
||||
Slot.F_HEAVY: "fighterHeavySlots"}
|
||||
@@ -743,6 +756,10 @@ class Fit(object):
|
||||
capacity = self.ship.getModifiedItemAttr("capacitorCapacity")
|
||||
mass = self.ship.getModifiedItemAttr("mass")
|
||||
warpCapNeed = self.ship.getModifiedItemAttr("warpCapacitorNeed")
|
||||
|
||||
if not warpCapNeed:
|
||||
return 0
|
||||
|
||||
return capacity / (mass * warpCapNeed)
|
||||
|
||||
@property
|
||||
|
||||
@@ -24,6 +24,7 @@ from eos.effectHandlerHelpers import HandledItem, HandledCharge
|
||||
from eos.enum import Enum
|
||||
from eos.mathUtils import floorFloat
|
||||
import eos.db
|
||||
from eos.types import Citadel
|
||||
import logging
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
@@ -46,6 +47,8 @@ class Slot(Enum):
|
||||
# system effects. They are projected "modules" and pyfa assumes all modules
|
||||
# have a slot. In this case, make one up.
|
||||
SYSTEM = 7
|
||||
# used for citadel services
|
||||
SERVICE = 8
|
||||
# fighter 'slots'. Just easier to put them here...
|
||||
F_LIGHT = 10
|
||||
F_SUPPORT = 11
|
||||
@@ -151,7 +154,7 @@ class Module(HandledItem, HandledCharge, ItemAttrShortcut, ChargeAttrShortcut):
|
||||
def isInvalid(self):
|
||||
if self.isEmpty:
|
||||
return False
|
||||
return self.__item is None or (self.__item.category.name not in ("Module", "Subsystem") and self.__item.group.name != "Effect Beacon")
|
||||
return self.__item is None or (self.__item.category.name not in ("Module", "Subsystem", "Structure Module") and self.__item.group.name != "Effect Beacon")
|
||||
|
||||
@property
|
||||
def numCharges(self):
|
||||
@@ -393,6 +396,11 @@ class Module(HandledItem, HandledCharge, ItemAttrShortcut, ChargeAttrShortcut):
|
||||
if (len(fitsOnGroup) > 0 or len(fitsOnType) > 0) and fit.ship.item.group.ID not in fitsOnGroup and fit.ship.item.ID not in fitsOnType:
|
||||
return False
|
||||
|
||||
# AFAIK Citadel modules will always be restricted based on canFitShipType/Group. If we are fitting to a Citadel
|
||||
# and the module does not have these properties, return false to prevent regular ship modules from being used
|
||||
if isinstance(fit.ship, Citadel) and len(fitsOnGroup) == 0 and len(fitsOnType) == 0:
|
||||
return False
|
||||
|
||||
# If the mod is a subsystem, don't let two subs in the same slot fit
|
||||
if self.slot == Slot.SUBSYSTEM:
|
||||
subSlot = self.getModifiedItemAttr("subSystemSlot")
|
||||
@@ -534,7 +542,8 @@ class Module(HandledItem, HandledCharge, ItemAttrShortcut, ChargeAttrShortcut):
|
||||
"loPower" : Slot.LOW,
|
||||
"medPower" : Slot.MED,
|
||||
"hiPower" : Slot.HIGH,
|
||||
"subSystem" : Slot.SUBSYSTEM}
|
||||
"subSystem" : Slot.SUBSYSTEM,
|
||||
"serviceSlot": Slot.SERVICE}
|
||||
if item is None:
|
||||
return None
|
||||
for effectName, slot in effectSlotMap.iteritems():
|
||||
|
||||
@@ -42,9 +42,7 @@ class Ship(ItemAttrShortcut, HandledItem):
|
||||
}
|
||||
|
||||
def __init__(self, item, parent=None):
|
||||
|
||||
if item.category.name != "Ship":
|
||||
raise ValueError('Passed item "%s" (category: (%s)) is not under Ship category'%(item.name, item.category.name))
|
||||
self.validate(item)
|
||||
|
||||
self.__item = item
|
||||
self.__modeItems = self.__getModeItems()
|
||||
@@ -58,6 +56,10 @@ class Ship(ItemAttrShortcut, HandledItem):
|
||||
self.parent = parent
|
||||
self.commandBonus = 0
|
||||
|
||||
def validate(self, item):
|
||||
if item.category.name != "Ship":
|
||||
raise ValueError('Passed item "%s" (category: (%s)) is not under Ship category'%(item.name, item.category.name))
|
||||
|
||||
@property
|
||||
def item(self):
|
||||
return self.__item
|
||||
|
||||
@@ -25,6 +25,8 @@ from eos.saveddata.crestchar import CrestChar
|
||||
from eos.saveddata.damagePattern import DamagePattern
|
||||
from eos.saveddata.targetResists import TargetResists
|
||||
from eos.saveddata.character import Character, Skill
|
||||
from eos.saveddata.ship import Ship
|
||||
from eos.saveddata.citadel import Citadel
|
||||
from eos.saveddata.module import Module, State, Slot, Hardpoint, Rack
|
||||
from eos.saveddata.drone import Drone
|
||||
from eos.saveddata.fighterAbility import FighterAbility
|
||||
@@ -34,10 +36,10 @@ from eos.saveddata.implant import Implant
|
||||
from eos.saveddata.implantSet import ImplantSet
|
||||
from eos.saveddata.booster import SideEffect
|
||||
from eos.saveddata.booster import Booster
|
||||
from eos.saveddata.ship import Ship
|
||||
from eos.saveddata.fit import Fit, ImplantLocation
|
||||
from eos.saveddata.mode import Mode
|
||||
from eos.saveddata.fleet import Fleet, Wing, Squad
|
||||
from eos.saveddata.miscData import MiscData
|
||||
from eos.saveddata.override import Override
|
||||
|
||||
import eos.db
|
||||
|
||||
@@ -58,23 +58,36 @@ class AdditionsPane(TogglePanel):
|
||||
gangImg = BitmapLoader.getImage("fleet_fc_small", "gui")
|
||||
cargoImg = BitmapLoader.getImage("cargo_small", "gui")
|
||||
|
||||
self.notebook.AddPage(DroneView(self.notebook), "Drones", tabImage = droneImg, showClose = False)
|
||||
self.notebook.AddPage(FighterView(self.notebook), "Fighters", tabImage = fighterImg, showClose = False)
|
||||
self.notebook.AddPage(CargoView(self.notebook), "Cargo", tabImage = cargoImg, showClose = False)
|
||||
self.notebook.AddPage(ImplantView(self.notebook), "Implants", tabImage = implantImg, showClose = False)
|
||||
self.notebook.AddPage(BoosterView(self.notebook), "Boosters", tabImage = boosterImg, showClose = False)
|
||||
self.drone = DroneView(self.notebook)
|
||||
self.notebook.AddPage(self.drone, "Drones", tabImage = droneImg, showClose = False)
|
||||
|
||||
self.fighter = FighterView(self.notebook)
|
||||
self.notebook.AddPage(self.fighter, "Fighters", tabImage = fighterImg, showClose = False)
|
||||
|
||||
self.cargo = CargoView(self.notebook)
|
||||
self.notebook.AddPage(self.cargo, "Cargo", tabImage = cargoImg, showClose = False)
|
||||
|
||||
self.implant = ImplantView(self.notebook)
|
||||
self.notebook.AddPage(self.implant, "Implants", tabImage = implantImg, showClose = False)
|
||||
|
||||
self.booster = BoosterView(self.notebook)
|
||||
self.notebook.AddPage(self.booster, "Boosters", tabImage = boosterImg, showClose = False)
|
||||
|
||||
self.projectedPage = ProjectedView(self.notebook)
|
||||
self.notebook.AddPage(self.projectedPage, "Projected", tabImage = projectedImg, showClose = False)
|
||||
|
||||
self.gangPage = GangView(self.notebook)
|
||||
self.notebook.AddPage(self.gangPage, "Fleet", tabImage = gangImg, showClose = False)
|
||||
|
||||
self.notebook.SetSelection(0)
|
||||
|
||||
PANES = ["Drones", "Fighters", "Cargo", "Implants", "Boosters", "Projected", "Fleet"]
|
||||
def select(self, name):
|
||||
self.notebook.SetSelection(self.PANES.index(name))
|
||||
|
||||
def toggleBoosters(self, event):
|
||||
self.notebook.ToggleShown(self.booster)
|
||||
|
||||
def getName(self, idx):
|
||||
return self.PANES[idx]
|
||||
|
||||
|
||||
@@ -85,6 +85,11 @@ class BoosterView(d.Display):
|
||||
event.Skip()
|
||||
|
||||
def fitChanged(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.Parent.Parent.DisablePage(self, not fit or fit.isStructure)
|
||||
|
||||
#Clear list and get out if current fitId is None
|
||||
if event.fitID is None and self.lastFitId is not None:
|
||||
self.DeleteAllItems()
|
||||
@@ -92,9 +97,6 @@ class BoosterView(d.Display):
|
||||
event.Skip()
|
||||
return
|
||||
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.origional = fit.boosters if fit is not None else None
|
||||
self.boosters = stuff = fit.boosters[:] if fit is not None else None
|
||||
|
||||
@@ -115,6 +117,12 @@ class BoosterView(d.Display):
|
||||
def addItem(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fitID = self.mainFrame.getActiveFit()
|
||||
|
||||
fit = sFit.getFit(fitID)
|
||||
|
||||
if fit.isStructure:
|
||||
return
|
||||
|
||||
trigger = sFit.addBooster(fitID, event.itemID)
|
||||
if trigger:
|
||||
wx.PostEvent(self.mainFrame, GE.FitChanged(fitID=fitID))
|
||||
|
||||
@@ -11,8 +11,12 @@ class Cargo(ContextMenu):
|
||||
self.mainFrame = gui.mainFrame.MainFrame.getInstance()
|
||||
|
||||
def display(self, srcContext, selection):
|
||||
sFit = service.Fit.getInstance()
|
||||
fitID = self.mainFrame.getActiveFit()
|
||||
|
||||
fit = sFit.getFit(fitID)
|
||||
# Make sure context menu registers in the correct view
|
||||
if srcContext not in ("marketItemGroup", "marketItemMisc") or self.mainFrame.getActiveFit() is None:
|
||||
if srcContext not in ("marketItemGroup", "marketItemMisc") or not fit or fit.isStructure:
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
@@ -29,6 +29,9 @@ class MetaSwap(ContextMenu):
|
||||
|
||||
self.selection = selection
|
||||
|
||||
if len(self.variations) == 1:
|
||||
return False # no variations from current module
|
||||
|
||||
return True
|
||||
|
||||
def getText(self, itmContext, selection):
|
||||
@@ -38,6 +41,7 @@ class MetaSwap(ContextMenu):
|
||||
self.moduleLookup = {}
|
||||
|
||||
def get_metalevel(x):
|
||||
if "metaLevel" not in x.attributes: return 0
|
||||
return x.attributes["metaLevel"].value
|
||||
|
||||
def get_metagroup(x):
|
||||
|
||||
@@ -12,7 +12,7 @@ class ShipJump(ContextMenu):
|
||||
return srcContext == "fittingShip"
|
||||
|
||||
def getText(self, itmContext, selection):
|
||||
return "Open in Ship Browser"
|
||||
return "Open in Fitting Browser"
|
||||
|
||||
def activate(self, fullContext, selection, i):
|
||||
fitID = self.mainFrame.getActiveFit()
|
||||
|
||||
@@ -201,7 +201,7 @@ class TargetingMiscViewFull(StatsView):
|
||||
elif labelName == "labelFullAlignTime":
|
||||
alignTime = "Align:\t%.3fs"%mainValue
|
||||
mass = 'Mass:\t{:,.0f}kg'.format(fit.ship.getModifiedItemAttr("mass"))
|
||||
agility = "Agility:\t%.3fx"%fit.ship.getModifiedItemAttr("agility")
|
||||
agility = "Agility:\t%.3fx"%(fit.ship.getModifiedItemAttr("agility") or 0)
|
||||
label.SetToolTip(wx.ToolTip("%s\n%s\n%s" % (alignTime, mass, agility)))
|
||||
elif labelName == "labelFullCargo":
|
||||
tipLines = []
|
||||
|
||||
@@ -409,7 +409,7 @@ class FittingView(d.Display):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(self.activeFitID)
|
||||
|
||||
slotOrder = [Slot.SUBSYSTEM, Slot.HIGH, Slot.MED, Slot.LOW, Slot.RIG]
|
||||
slotOrder = [Slot.SUBSYSTEM, Slot.HIGH, Slot.MED, Slot.LOW, Slot.RIG, Slot.SERVICE]
|
||||
|
||||
if fit is not None:
|
||||
self.mods = fit.modules[:]
|
||||
@@ -503,7 +503,10 @@ class FittingView(d.Display):
|
||||
|
||||
sel = self.GetNextSelected(sel)
|
||||
|
||||
contexts.append(("fittingShip", "Ship"))
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(self.activeFitID)
|
||||
|
||||
contexts.append(("fittingShip", "Ship" if not fit.isStructure else "Citadel"))
|
||||
|
||||
menu = ContextMenu.getMenu(selection, *contexts)
|
||||
self.PopupMenu(menu)
|
||||
|
||||
@@ -125,6 +125,11 @@ class CargoView(d.Display):
|
||||
wx.PostEvent(self.mainFrame, GE.FitChanged(fitID=self.mainFrame.getActiveFit()))
|
||||
|
||||
def fitChanged(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.Parent.Parent.DisablePage(self, not fit or fit.isStructure)
|
||||
|
||||
#Clear list and get out if current fitId is None
|
||||
if event.fitID is None and self.lastFitId is not None:
|
||||
self.DeleteAllItems()
|
||||
@@ -132,9 +137,6 @@ class CargoView(d.Display):
|
||||
event.Skip()
|
||||
return
|
||||
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.original = fit.cargo if fit is not None else None
|
||||
self.cargo = stuff = fit.cargo if fit is not None else None
|
||||
if stuff is not None: stuff.sort(key=lambda cargo: cargo.itemID)
|
||||
|
||||
@@ -227,6 +227,18 @@ class PFNotebook(wx.Panel):
|
||||
self.activePage = tabWnd
|
||||
self.ShowActive(True)
|
||||
|
||||
def DisablePage(self, page, toggle):
|
||||
idx = self.GetPageIndex(page)
|
||||
|
||||
if toggle and page == self.activePage:
|
||||
try:
|
||||
# Set page to the first non-disabled page
|
||||
self.SetSelection(next(i for i, _ in enumerate(self.pages) if not self.tabsContainer.tabs[i].disabled))
|
||||
except StopIteration, ex:
|
||||
self.SetSelection(0)
|
||||
|
||||
self.tabsContainer.DisableTab(idx, toggle)
|
||||
|
||||
def SetSelection(self, page):
|
||||
oldsel = self.GetSelection()
|
||||
if oldsel != page:
|
||||
@@ -354,6 +366,7 @@ class PFTabRenderer:
|
||||
|
||||
self.inclination = inclination
|
||||
self.text = text
|
||||
self.disabled = False
|
||||
self.tabSize = (width, height)
|
||||
self.closeButton = closeButton
|
||||
self.selected = False
|
||||
@@ -548,7 +561,7 @@ class PFTabRenderer:
|
||||
mdc.DrawBitmap(self.tabBackBitmap, 0, 0, True)
|
||||
|
||||
if self.tabImg:
|
||||
bmp = wx.BitmapFromImage(self.tabImg)
|
||||
bmp = wx.BitmapFromImage(self.tabImg.ConvertToGreyscale() if self.disabled else self.tabImg)
|
||||
if self.contentWidth > 16: # @todo: is this conditional relevant anymore?
|
||||
# Draw tab icon
|
||||
mdc.DrawBitmap(bmp, self.leftWidth + self.padding - bmp.GetWidth()/2, (height - bmp.GetHeight())/2)
|
||||
@@ -591,6 +604,10 @@ class PFTabRenderer:
|
||||
bmp = wx.BitmapFromImage(img)
|
||||
self.tabBitmap = bmp
|
||||
|
||||
def __repr__(self):
|
||||
return "PFTabRenderer(text={}, disabled={}) at {}".format(
|
||||
self.text, self.disabled, hex(id(self))
|
||||
)
|
||||
|
||||
class PFAddRenderer:
|
||||
def __init__(self):
|
||||
@@ -848,6 +865,7 @@ class PFTabsContainer(wx.Panel):
|
||||
return True
|
||||
|
||||
if self.TabHitTest(tab, x, y):
|
||||
if tab.disabled: return
|
||||
tab.SetSelected(True)
|
||||
oldSelTab.SetSelected(False)
|
||||
|
||||
@@ -1186,6 +1204,13 @@ class PFTabsContainer(wx.Panel):
|
||||
for tab in self.tabs:
|
||||
tab.SetSelected(False)
|
||||
|
||||
def DisableTab(self, tab, disabled=True):
|
||||
tabRenderer = self.tabs[tab]
|
||||
tabRenderer.disabled = disabled
|
||||
|
||||
self.AdjustTabsSize()
|
||||
self.Refresh()
|
||||
|
||||
def DeleteTab(self, tab, external=False):
|
||||
tabRenderer = self.tabs[tab]
|
||||
wasSelected = tabRenderer.GetSelected()
|
||||
|
||||
@@ -159,6 +159,10 @@ class DroneView(d.Display):
|
||||
drone.item.name)
|
||||
|
||||
def fitChanged(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.Parent.Parent.DisablePage(self, not fit or fit.isStructure)
|
||||
|
||||
#Clear list and get out if current fitId is None
|
||||
if event.fitID is None and self.lastFitId is not None:
|
||||
@@ -167,9 +171,6 @@ class DroneView(d.Display):
|
||||
event.Skip()
|
||||
return
|
||||
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.original = fit.drones if fit is not None else None
|
||||
self.drones = stuff = fit.drones[:] if fit is not None else None
|
||||
|
||||
@@ -194,6 +195,12 @@ class DroneView(d.Display):
|
||||
def addItem(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fitID = self.mainFrame.getActiveFit()
|
||||
|
||||
fit = sFit.getFit(fitID)
|
||||
|
||||
if fit.isStructure:
|
||||
return
|
||||
|
||||
trigger = sFit.addDrone(fitID, event.itemID)
|
||||
if trigger:
|
||||
wx.PostEvent(self.mainFrame, GE.FitChanged(fitID=fitID))
|
||||
|
||||
@@ -224,6 +224,10 @@ class FighterDisplay(d.Display):
|
||||
'''
|
||||
|
||||
def fitChanged(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.Parent.Parent.Parent.DisablePage(self.Parent, not fit)
|
||||
|
||||
#Clear list and get out if current fitId is None
|
||||
if event.fitID is None and self.lastFitId is not None:
|
||||
@@ -232,9 +236,6 @@ class FighterDisplay(d.Display):
|
||||
event.Skip()
|
||||
return
|
||||
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.original = fit.fighters if fit is not None else None
|
||||
self.fighters = stuff = fit.fighters[:] if fit is not None else None
|
||||
|
||||
|
||||
@@ -26,7 +26,6 @@ import gui.globalEvents as GE
|
||||
|
||||
from gui import characterEditor as CharEditor
|
||||
|
||||
|
||||
class GangView ( ScrolledPanel ):
|
||||
|
||||
def __init__( self, parent ):
|
||||
@@ -247,6 +246,9 @@ class GangView ( ScrolledPanel ):
|
||||
activeFitID = self.mainFrame.getActiveFit()
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID or activeFitID)
|
||||
|
||||
self.Parent.Parent.DisablePage(self, not fit or fit.isStructure)
|
||||
|
||||
commanders = (None, None, None)
|
||||
|
||||
if activeFitID:
|
||||
@@ -363,8 +365,10 @@ class GangView ( ScrolledPanel ):
|
||||
#Those are drags coming from pyfa sources, NOT builtin wx drags
|
||||
self.draggedFitID = None
|
||||
if type == "fit":
|
||||
activeFit = self.mainFrame.getActiveFit()
|
||||
if activeFit:
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(self.mainFrame.getActiveFit())
|
||||
|
||||
if fit and not fit.isStructuree:
|
||||
self.draggedFitID = fitID
|
||||
|
||||
pos = wx.GetMousePosition()
|
||||
|
||||
@@ -107,6 +107,11 @@ class ImplantDisplay(d.Display):
|
||||
event.Skip()
|
||||
|
||||
def fitChanged(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.Parent.Parent.Parent.DisablePage(self.Parent, not fit or fit.isStructure)
|
||||
|
||||
#Clear list and get out if current fitId is None
|
||||
if event.fitID is None and self.lastFitId is not None:
|
||||
self.DeleteAllItems()
|
||||
@@ -114,9 +119,6 @@ class ImplantDisplay(d.Display):
|
||||
event.Skip()
|
||||
return
|
||||
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.original = fit.implants if fit is not None else None
|
||||
self.implants = stuff = fit.appliedImplants if fit is not None else None
|
||||
if stuff is not None: stuff.sort(key=lambda implant: implant.slot)
|
||||
@@ -137,6 +139,12 @@ class ImplantDisplay(d.Display):
|
||||
def addItem(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fitID = self.mainFrame.getActiveFit()
|
||||
|
||||
fit = sFit.getFit(fitID)
|
||||
|
||||
if fit.isStructure:
|
||||
return
|
||||
|
||||
trigger = sFit.addImplant(fitID, event.itemID)
|
||||
if trigger:
|
||||
wx.PostEvent(self.mainFrame, GE.FitChanged(fitID=fitID))
|
||||
|
||||
@@ -24,7 +24,7 @@ from gui.bitmapLoader import BitmapLoader
|
||||
import sys
|
||||
import wx.lib.mixins.listctrl as listmix
|
||||
import wx.html
|
||||
from eos.types import Fit, Ship, Module, Skill, Booster, Implant, Drone, Mode, Fighter
|
||||
from eos.types import Fit, Ship, Citadel, Module, Skill, Booster, Implant, Drone, Mode, Fighter
|
||||
from gui.utils.numberFormatter import formatAmount
|
||||
import service
|
||||
import config
|
||||
@@ -747,7 +747,7 @@ class ItemEffects (wx.Panel):
|
||||
|
||||
|
||||
class ItemAffectedBy (wx.Panel):
|
||||
ORDER = [Fit, Ship, Mode, Module, Drone, Fighter, Implant, Booster, Skill]
|
||||
ORDER = [Fit, Ship, Citadel, Mode, Module, Drone, Fighter, Implant, Booster, Skill]
|
||||
def __init__(self, parent, stuff, item):
|
||||
wx.Panel.__init__(self, parent)
|
||||
self.stuff = stuff
|
||||
|
||||
@@ -156,7 +156,7 @@ class MainFrame(wx.Frame):
|
||||
self.marketBrowser.splitter.SetSashPosition(self.marketHeight)
|
||||
|
||||
self.shipBrowser = ShipBrowser(self.notebookBrowsers)
|
||||
self.notebookBrowsers.AddPage(self.shipBrowser, "Ships", tabImage = shipBrowserImg, showClose = False)
|
||||
self.notebookBrowsers.AddPage(self.shipBrowser, "Fittings", tabImage = shipBrowserImg, showClose = False)
|
||||
|
||||
#=======================================================================
|
||||
# DISABLED FOR RC2 RELEASE
|
||||
|
||||
@@ -159,6 +159,11 @@ class ProjectedView(d.Display):
|
||||
return fit.name
|
||||
|
||||
def fitChanged(self, event):
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
|
||||
self.Parent.Parent.DisablePage(self, not fit or fit.isStructure)
|
||||
|
||||
#Clear list and get out if current fitId is None
|
||||
if event.fitID is None and self.lastFitId is not None:
|
||||
self.DeleteAllItems()
|
||||
@@ -166,8 +171,6 @@ class ProjectedView(d.Display):
|
||||
event.Skip()
|
||||
return
|
||||
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(event.fitID)
|
||||
stuff = []
|
||||
if fit is not None:
|
||||
self.modules = fit.projectedModules[:]
|
||||
|
||||
@@ -1538,7 +1538,10 @@ class FitItem(SFItem.SFBrowserItem):
|
||||
menu.Check(toggleItem.GetId(), self.fitBooster)
|
||||
self.Bind(wx.EVT_MENU, self.OnToggleBooster, toggleItem)
|
||||
|
||||
if self.mainFrame.getActiveFit():
|
||||
sFit = service.Fit.getInstance()
|
||||
fit = sFit.getFit(self.mainFrame.getActiveFit())
|
||||
|
||||
if fit and not fit.isStructure:
|
||||
# If there is an active fit, get menu for setting individual boosters
|
||||
menu.AppendSeparator()
|
||||
boosterMenu = self.mainFrame.additionsPane.gangPage.buildBoostermenu()
|
||||
|
||||
BIN
imgs/icons/123_10.png
Normal file
|
After Width: | Height: | Size: 894 B |
BIN
imgs/icons/123_11.png
Normal file
|
After Width: | Height: | Size: 904 B |
BIN
imgs/icons/123_5.png
Normal file
|
After Width: | Height: | Size: 861 B |
BIN
imgs/icons/123_6.png
Normal file
|
After Width: | Height: | Size: 1006 B |
BIN
imgs/icons/123_8.png
Normal file
|
After Width: | Height: | Size: 818 B |
BIN
imgs/icons/123_9.png
Normal file
|
After Width: | Height: | Size: 900 B |
BIN
imgs/icons/127_1.png
Normal file
|
After Width: | Height: | Size: 742 B |
BIN
imgs/icons/127_10.png
Normal file
|
After Width: | Height: | Size: 841 B |
BIN
imgs/icons/127_2.png
Normal file
|
After Width: | Height: | Size: 781 B |
BIN
imgs/icons/127_3.png
Normal file
|
After Width: | Height: | Size: 738 B |
BIN
imgs/icons/127_4.png
Normal file
|
After Width: | Height: | Size: 793 B |
BIN
imgs/icons/127_5.png
Normal file
|
After Width: | Height: | Size: 794 B |
BIN
imgs/icons/127_7.png
Normal file
|
After Width: | Height: | Size: 823 B |
BIN
imgs/icons/127_9.png
Normal file
|
After Width: | Height: | Size: 874 B |
BIN
imgs/icons/45_12.png
Normal file
|
After Width: | Height: | Size: 735 B |
|
Before Width: | Height: | Size: 732 B After Width: | Height: | Size: 731 B |
|
Before Width: | Height: | Size: 800 B After Width: | Height: | Size: 800 B |
BIN
imgs/renders/35832.png
Normal file
|
After Width: | Height: | Size: 1.9 KiB |
BIN
imgs/renders/35833.png
Normal file
|
After Width: | Height: | Size: 2.0 KiB |
BIN
imgs/renders/35834.png
Normal file
|
After Width: | Height: | Size: 2.0 KiB |
BIN
imgs/renders/40340.png
Normal file
|
After Width: | Height: | Size: 2.0 KiB |
@@ -38,7 +38,8 @@ ITEM_CATEGORIES = (
|
||||
16, # Skill
|
||||
18, # Drone
|
||||
20, # Implant
|
||||
32 # Subsystem
|
||||
32, # Subsystem
|
||||
66, # Structure Module
|
||||
)
|
||||
|
||||
MARKET_ROOTS = {
|
||||
@@ -48,7 +49,9 @@ MARKET_ROOTS = {
|
||||
11, # Ammo
|
||||
1112, # Subsystems
|
||||
24, # Implants & Boosters
|
||||
404 # Deployables
|
||||
404, # Deployables
|
||||
2202, # Structure Equipment
|
||||
2203 # Structure Modifications (Rigs)
|
||||
}
|
||||
|
||||
# Add children to market group list
|
||||
@@ -153,7 +156,7 @@ for fname in os.listdir(icons_dir):
|
||||
print fname,"exists"
|
||||
existing.add(fname)
|
||||
|
||||
# Get a list of all the icons currently available
|
||||
# Get a list of all the icons currently available in export
|
||||
for dir in dirs:
|
||||
for fname in os.listdir(dir):
|
||||
if not os.path.isfile(os.path.join(dir, fname)):
|
||||
@@ -164,7 +167,7 @@ for dir in dirs:
|
||||
# convention without size specification
|
||||
sizeless = re.sub('^(?P<prefix>[^_]+)_(?P<size>\d+)_(?P<suffix>[^_]+)$', r'\1_\3', stripped)
|
||||
# Often items referred to with 01_01 format,
|
||||
fnames = export.setdefault(stripped.lower(), set())
|
||||
fnames = export.setdefault(sizeless.lower(), set())
|
||||
fnames.add(fname)
|
||||
|
||||
def crop_image(img):
|
||||
|
||||
@@ -30,7 +30,7 @@ cursor = db.cursor()
|
||||
RENDER_SIZE = (32, 32)
|
||||
|
||||
|
||||
query_ships = 'select it.typeID from invtypes as it inner join invgroups as ig on it.groupID = ig.groupID where ig.categoryID = 6'
|
||||
query_ships = 'select it.typeID from invtypes as it inner join invgroups as ig on it.groupID = ig.groupID where ig.categoryID in (6, 65)'
|
||||
|
||||
|
||||
needed = set()
|
||||
|
||||
@@ -158,7 +158,10 @@ class Fit(object):
|
||||
return fit.modules[pos]
|
||||
|
||||
def newFit(self, shipID, name=None):
|
||||
ship = eos.types.Ship(eos.db.getItem(shipID))
|
||||
try:
|
||||
ship = eos.types.Ship(eos.db.getItem(shipID))
|
||||
except ValueError:
|
||||
ship = eos.types.Citadel(eos.db.getItem(shipID))
|
||||
fit = eos.types.Fit(ship)
|
||||
fit.name = name if name is not None else "New %s" % fit.ship.item.name
|
||||
fit.damagePattern = self.pattern
|
||||
@@ -361,7 +364,6 @@ class Fit(object):
|
||||
|
||||
drone.amount += 1
|
||||
elif thing.category.name == "Fighter":
|
||||
print "dskfnds"
|
||||
fighter = eos.types.Fighter(thing)
|
||||
fit.projectedFighters.append(fighter)
|
||||
elif thing.group.name == "Effect Beacon":
|
||||
|
||||
@@ -331,7 +331,7 @@ class Market():
|
||||
("faction", frozenset((4, 3))),
|
||||
("complex", frozenset((6,))),
|
||||
("officer", frozenset((5,)))])
|
||||
self.SEARCH_CATEGORIES = ("Drone", "Module", "Subsystem", "Charge", "Implant", "Deployable", "Fighter")
|
||||
self.SEARCH_CATEGORIES = ("Drone", "Module", "Subsystem", "Charge", "Implant", "Deployable", "Fighter", "Structure", "Structure Module")
|
||||
self.SEARCH_GROUPS = ("Ice Product",)
|
||||
self.ROOT_MARKET_GROUPS = (9, # Modules
|
||||
1111, # Rigs
|
||||
@@ -339,7 +339,10 @@ class Market():
|
||||
11, # Ammo
|
||||
1112, # Subsystems
|
||||
24, # Implants & Boosters
|
||||
404) # Deployables
|
||||
404, # Deployables
|
||||
2202, # Structure Equipment
|
||||
2203 # Structure Modifications
|
||||
)
|
||||
# Tell other threads that Market is at their service
|
||||
mktRdy.set()
|
||||
|
||||
@@ -666,8 +669,10 @@ class Market():
|
||||
return root
|
||||
|
||||
def getShipRoot(self):
|
||||
cat = self.getCategory("Ship")
|
||||
root = set(self.getGroupsByCategory(cat))
|
||||
cat1 = self.getCategory("Ship")
|
||||
cat2 = self.getCategory("Structure")
|
||||
root = set(self.getGroupsByCategory(cat1) | self.getGroupsByCategory(cat2))
|
||||
|
||||
return root
|
||||
|
||||
def getShipList(self, grpid):
|
||||
|
||||