001package com.fs.starfarer.api.impl.campaign.abilities.ai; 002 003import org.lwjgl.util.vector.Vector2f; 004 005import com.fs.starfarer.api.campaign.CampaignFleetAPI; 006import com.fs.starfarer.api.campaign.ai.FleetAIFlags; 007import com.fs.starfarer.api.campaign.econ.MarketAPI; 008import com.fs.starfarer.api.campaign.rules.MemoryAPI; 009import com.fs.starfarer.api.impl.campaign.abilities.GoDarkAbility; 010import com.fs.starfarer.api.impl.campaign.events.BaseEventPlugin.MarketFilter; 011import com.fs.starfarer.api.impl.campaign.ids.MemFlags; 012import com.fs.starfarer.api.util.IntervalUtil; 013import com.fs.starfarer.api.util.Misc; 014 015public class GoDarkAbilityAI extends BaseAbilityAI { 016 017 private IntervalUtil interval = new IntervalUtil(0.05f, 0.15f); 018 019// public GoDarkAbilityAI(AbilityPlugin ability, ModularFleetAIAPI ai) { 020// super(ability, ai); 021// } 022 023 public void advance(float days) { 024 interval.advance(days * EmergencyBurnAbilityAI.AI_FREQUENCY_MULT); 025 if (!interval.intervalElapsed()) return; 026 027 028 MemoryAPI mem = fleet.getMemoryWithoutUpdate(); 029 030 031 if (ability.isActiveOrInProgress()) { 032 mem.set(FleetAIFlags.HAS_SPEED_PENALTY, true, 0.2f); 033 mem.set(FleetAIFlags.HAS_LOWER_DETECTABILITY, true, 0.2f); 034 } 035 036 CampaignFleetAPI pursueTarget = mem.getFleet(FleetAIFlags.PURSUIT_TARGET); 037 CampaignFleetAPI fleeingFrom = mem.getFleet(FleetAIFlags.NEAREST_FLEEING_FROM); 038 Vector2f travelDest = mem.getVector2f(FleetAIFlags.TRAVEL_DEST); 039 boolean wantsTransponderOn = mem.getBoolean(FleetAIFlags.WANTS_TRANSPONDER_ON); 040 041// if (pursueTarget != null && pursueTarget.isPlayerFleet() && fleeingFrom != null) { 042// System.out.println("dfsdfwefwe"); 043// } 044 045 // if being pursued 046 if (fleeingFrom != null) { 047 float dist = Misc.getDistance(fleet.getLocation(), fleeingFrom.getLocation()) - fleet.getRadius() - fleeingFrom.getRadius(); 048 if (dist < 0) return; 049 float detRange = fleeingFrom.getMaxSensorRangeToDetect(fleet); 050 float ourSpeed = fleet.getFleetData().getBurnLevel(); 051 float theirSpeed = fleeingFrom.getFleetData().getBurnLevel(); 052 // slower than closest pursuer, but could hide using go dark: do it 053 if (!ability.isActiveOrInProgress()) { 054 if (dist > detRange * GoDarkAbility.DETECTABILITY_MULT + 100f && ourSpeed < theirSpeed && 055 dist > detRange && dist < detRange + 300f) { 056 ability.activate(); 057 } 058 } else { // already seen by them, or faster than them with "go dark" off 059 //if (dist < detRange || ourSpeed / GoDarkAbility.MAX_BURN_MULT > theirSpeed) { 060 // since going dark means "slow moving", ourSpeed doesn't actually include that, so it's still 061 // as if go dark was turned off 062 if (dist < detRange || ourSpeed > theirSpeed) { 063 ability.deactivate(); 064 } 065 } 066 return; 067 } 068 069 // if wants to use transponder & not being pursued, don't do it 070 //if (wantsTransponderOn) { 071 if (fleet.isTransponderOn()) { 072 return; 073 } 074 075// if (pursueTarget != null && pursueTarget.isPlayerFleet()) { 076// System.out.println("dfsdfwefwe"); 077// } 078 079 // if ok with using it, and not being pursued 080 // if pursuing, target can't see us, and we're gaining: leave on 081 // if pursuing, target can see us or we're losing groung: turn off 082 if (pursueTarget != null) { 083 float closingSpeed = Misc.getClosingSpeed(fleet.getLocation(), pursueTarget.getLocation(), 084 fleet.getVelocity(),pursueTarget.getVelocity()); 085 if (closingSpeed <= 1 && ability.isActiveOrInProgress()) { 086 ability.deactivate(); 087 } 088 return; 089 } 090 091 // is the destination nearby? turn on 092 boolean smuggler = mem.getBoolean(MemFlags.MEMORY_KEY_SMUGGLER); 093 boolean pirate = mem.getBoolean(MemFlags.MEMORY_KEY_PIRATE); 094 // don't use for general pirates; too grief-y 095 pirate = false; 096 097 boolean nearestMarketHostile = false; 098 MarketAPI nearestMarket = Misc.findNearestLocalMarket(fleet, 2000, new MarketFilter() { 099 public boolean acceptMarket(MarketAPI market) { 100 return true; 101 } 102 }); 103 if (nearestMarket != null && nearestMarket.getFaction().isHostileTo(fleet.getFaction())) { 104 nearestMarketHostile = true; 105 } 106 107 if ((smuggler || pirate || nearestMarketHostile) && !ability.isActiveOrInProgress() && travelDest != null) { 108 float dist = Misc.getDistance(fleet.getLocation(), travelDest); 109 if (dist < 1500) { 110 ability.activate(); 111 } 112 return; 113 } 114 } 115} 116 117 118 119 120 121