1package com.fs.starfarer.api.impl.combat;
3import java.util.ArrayList;
4import java.util.Arrays;
6import java.util.Random;
10import org.lwjgl.util.vector.Vector2f;
12import com.fs.starfarer.api.Global;
13import com.fs.starfarer.api.campaign.BattleCreationPlugin;
14import com.fs.starfarer.api.campaign.CampaignFleetAPI;
15import com.fs.starfarer.api.campaign.CampaignTerrainAPI;
16import com.fs.starfarer.api.campaign.CustomCampaignEntityAPI;
17import com.fs.starfarer.api.campaign.LocationAPI;
18import com.fs.starfarer.api.campaign.PlanetAPI;
19import com.fs.starfarer.api.campaign.SectorEntityToken;
20import com.fs.starfarer.api.campaign.StarSystemAPI;
21import com.fs.starfarer.api.combat.BaseEveryFrameCombatPlugin;
22import com.fs.starfarer.api.combat.BattleCreationContext;
23import com.fs.starfarer.api.combat.CombatEngineAPI;
24import com.fs.starfarer.api.combat.MissileAPI;
25import com.fs.starfarer.api.combat.ShipAPI;
26import com.fs.starfarer.api.fleet.FleetGoal;
27import com.fs.starfarer.api.fleet.FleetMemberAPI;
28import com.fs.starfarer.api.impl.campaign.ids.Planets;
29import com.fs.starfarer.api.impl.campaign.ids.Tags;
30import com.fs.starfarer.api.impl.campaign.ids.Terrain;
31import com.fs.starfarer.api.impl.campaign.terrain.HyperspaceAbyssPluginImpl;
32import com.fs.starfarer.api.impl.campaign.terrain.PulsarBeamTerrainPlugin;
33import com.fs.starfarer.api.impl.campaign.terrain.StarCoronaTerrainPlugin;
34import com.fs.starfarer.api.input.InputEventAPI;
35import com.fs.starfarer.api.mission.FleetSide;
36import com.fs.starfarer.api.mission.MissionDefinitionAPI;
37import com.fs.starfarer.api.util.Misc;
38import com.fs.starfarer.api.util.WeightedRandomPicker;
55 protected float xPad = 2000;
56 protected float yPad = 2000;
58 protected List<String>
objs =
null;
91 if (member.canBeDeployedForCombat() || playerGoal ==
FleetGoal.
ESCAPE) {
92 fpOne += member.getUnmodifiedDeploymentPointsCost();
96 if (member.canBeDeployedForCombat() || playerGoal ==
FleetGoal.
ESCAPE) {
97 fpTwo += member.getUnmodifiedDeploymentPointsCost();
101 int smaller = Math.min(fpOne, fpTwo);
103 boolean withObjectives = smaller > maxFP;
106 withObjectives =
false;
108 withObjectives =
true;
111 int numObjectives = 0;
112 if (withObjectives) {
119 if (fpOne + fpTwo > maxFP + 70) {
123 numObjectives = 3 + random.nextInt(2);
129 if (numObjectives > 4) {
166 }
else if (withObjectives) {
168 if (numObjectives == 2) {
197 if (withObjectives) {
210 String name =
"Corona";
214 final String name2 = name;
219 final Object key1 =
new Object();
220 final Object key2 =
new Object();
224 public void advance(
float amount, List<InputEventAPI> events) {
243 final Object key1 =
new Object();
244 final Object key2 =
new Object();
246 final String name =
"Abyssal hyperspace";
249 public void advance(
float amount, List<InputEventAPI> events) {
255 String modId =
"abyssal";
261 if (curr.isHulk())
continue;
263 curr.getEngineController().fadeToOtherColor(
this, Color.black,
null, 1f,
abyssalDepth * 0.4f);
264 curr.getEngineController().extendFlame(
this, modL, modW, modG);
266 curr.getMutableStats().getMaxSpeed().modifyMult(modId,
268 curr.getMutableStats().getMissileWeaponRangeBonus().modifyMult(modId,
270 curr.getMutableStats().getMissileMaxSpeedBonus().modifyMult(modId,
275 missile.getEngineController().fadeToOtherColor(
this, Color.black,
null, 1f,
abyssalDepth * 0.4f);
276 missile.getEngineController().extendFlame(
this, modL, modW, 0f);
294 String nebulaTex =
null;
295 String nebulaMapTex =
null;
296 boolean inNebula =
false;
298 boolean protectedFromCorona =
false;
301 protectedFromCorona =
true;
310 Color coronaColor =
null;
315 if (terrain.getPlugin().containsEntity(playerFleet)) {
323 if (nebulaTex ==
null) {
337 intensity = 0.4f + 0.6f * intensity;
338 int alpha = (int)(80f * intensity);
340 if (coronaColor ==
null || coronaColor.getAlpha() < alpha) {
352 intensity = 0.4f + 0.6f * intensity;
353 int alpha = (int)(80f * intensity);
355 if (coronaColor ==
null || coronaColor.getAlpha() < alpha) {
362 }
else if (terrain.getType().equals(
Terrain.
RING)) {
363 if (terrain.getPlugin().containsEntity(playerFleet)) {
368 if (nebulaTex !=
null) {
373 if (coronaColor !=
null) {
385 for (
int i = 0; i < numNebula; i++) {
386 float x = random.nextFloat() *
width -
width/2;
388 float radius = 100f + random.nextFloat() * 400f;
390 radius += 100f + 500f * random.nextFloat();
398 int numAsteroids = Math.min(400, (
int)((numAsteroidsWithinRange + 1f) * 20f));
401 20f, 70f, numAsteroids);
404 int numRingAsteroids = (int) (numRings * 300 + (numRings * 600f) * random.nextFloat());
406 if (numRingAsteroids > 1500) {
407 numRingAsteroids = 1500;
410 100f, 200f, numRingAsteroids);
430 float bgWidth = 2048f;
431 float bgHeight = 2048f;
434 if (planet ==
null)
return;
437 if (dist < 0) dist = 0;
439 float scaleFactor = 1.5f;
440 float maxRadius = 500f;
441 float minRadius = 100f;
449 if (maxDist < 1) maxDist = 1;
452 boolean playerHasStation =
false;
453 boolean enemyHasStation =
false;
456 if (curr.isStation()) {
457 playerHasStation =
true;
463 if (curr.isStation()) {
464 enemyHasStation =
true;
469 float planetYOffset = 0;
471 if (playerHasStation) {
472 planetYOffset = -bgHeight / 2f * 0.5f;
474 if (enemyHasStation) {
475 planetYOffset = bgHeight / 2f * 0.5f;
479 float f = (maxDist - dist) / maxDist * 0.65f + 0.35f;
480 float radius = baseRadius * f * scaleFactor;
481 if (radius > maxRadius) radius = maxRadius;
482 if (radius < minRadius) radius = minRadius;
488 float bgWidth = 2048f;
489 float bgHeight = 2048f;
494 if (!planets.isEmpty()) {
496 for (NearbyPlanetData data : planets) {
498 float baseRadius = data.planet.getRadius();
499 float scaleFactor = 1.5f;
500 float maxRadius = 500f;
502 if (data.planet.isStar()) {
509 float f = (maxDist - dist) / maxDist * 0.65f + 0.35f;
510 float radius = baseRadius * f * scaleFactor;
511 if (radius > maxRadius) radius = maxRadius;
515 radius, data.planet.getTypeId(), 0f,
true);
524 String [] bgs =
new String [] {
525 "graphics/backgrounds/background1.jpg",
526 "graphics/backgrounds/background2.jpg",
527 "graphics/backgrounds/background3.jpg",
528 "graphics/backgrounds/background4.jpg"
530 String pick = bgs[Math.min(bgs.length - 1, (
int)(random.nextDouble() * bgs.length))];
534 protected static String
COMM =
"comm_relay";
535 protected static String
SENSOR =
"sensor_array";
536 protected static String
NAV =
"nav_buoy";
541 objs =
new ArrayList<String>(Arrays.asList(
new String [] {
551 objs =
new ArrayList<String>(Arrays.asList(
new String [] {
560 }
else if (num == 3) {
561 float r = random.nextFloat();
566 }
else if (r < 0.67f) {
571 if (random.nextFloat() < 0.5f) {
581 }
else if (num == 4) {
582 float r = random.nextFloat();
584 String [] maybeRelays =
pickCommRelays(2, 2,
false,
true,
true,
false, random);
589 }
else if (r < 0.67f) {
590 String [] maybeRelays =
pickCommRelays(1, 2,
true,
false,
true,
false, random);
596 if (random.nextFloat() < 0.5f) {
597 String [] maybeRelays =
pickCommRelays(1, 2,
true,
false,
true,
false, random);
603 String [] maybeRelays =
pickCommRelays(1, 2,
false,
true,
false,
true, random);
613 protected String []
pickCommRelays(
int min,
int max,
boolean comm1,
boolean comm2,
boolean comm3,
boolean comm4, Random random) {
614 String [] result =
new String [4];
617 if (comm1) picker.
add(0);
618 if (comm2) picker.
add(1);
619 if (comm3) picker.
add(2);
620 if (comm4) picker.
add(3);
622 int num = min + random.nextInt(max - min + 1);
624 for (
int i = 0; i < num && !picker.
isEmpty(); i++) {
632 objs =
new ArrayList<String>(Arrays.asList(
new String [] {
641 float r = random.nextFloat();
645 }
else if (r < 0.67f) {
652 }
else if (num == 3) {
653 float r = random.nextFloat();
658 }
else if (r < 0.67f) {
667 }
else if (num == 4) {
668 float r = random.nextFloat();
674 }
else if (r < 0.67f) {
688 protected void addObjectiveAt(
float xMult,
float yMult,
float xOff,
float yOff, Random random) {
691 protected void addObjectiveAt(
float xMult,
float yMult,
float xOff,
float yOff, String type, Random random) {
695 if (
objs !=
null &&
objs.size() > 0) {
696 int index = (int) (random.nextDouble() *
objs.size());
697 type =
objs.remove(index);
704 float x = (
width -
xPad * 2f) * xMult + minX;
705 float y = (
height -
yPad * 2f) * yMult + minY;
707 x = ((int) x / 1000) * 1000f;
708 y = ((int) y / 1000) * 1000f;
710 float offsetX = Math.round((random.nextFloat() - 0.5f) * xOff * 1f) * 1000f;
711 float offsetY = Math.round((random.nextFloat() - 0.5f) * yOff * 1f) * 1000f;
716 float xDir = (float) Math.signum(offsetX);
717 float yDir = (float) Math.signum(offsetY);
721 offsetX = Math.abs(offsetX) * -
prevXDir;
726 offsetY = Math.abs(offsetY) * -
prevYDir;
738 float nebulaSize = random.nextFloat() * 1500f + 500f;
744 float r = random.nextFloat();
745 if (r < 0.33f)
return "nav_buoy";
746 else if (r < 0.67f)
return "sensor_array";
747 else return "comm_relay";
751 float numAsteroidsWithinRange = 0;
755 List<SectorEntityToken> asteroids = system.
getAsteroids();
757 float range = Vector2f.sub(playerFleet.
getLocation(), asteroid.getLocation(),
new Vector2f()).length();
758 if (range < 300) numAsteroidsWithinRange ++;
761 return numAsteroidsWithinRange;
764 protected static class NearbyPlanetData {
765 protected Vector2f offset;
767 public NearbyPlanetData(Vector2f offset,
PlanetAPI planet) {
768 this.offset = offset;
769 this.planet = planet;
781 List<NearbyPlanetData> result =
new ArrayList<NearbyPlanetData>();
784 List<PlanetAPI> planets = system.
getPlanets();
786 float diffX = planet.getLocation().x - playerFleet.
getLocation().x;
787 float diffY = planet.getLocation().y - playerFleet.
getLocation().y;
790 result.add(
new NearbyPlanetData(
new Vector2f(diffX, diffY), planet));
800 float minDist = Float.MAX_VALUE;
803 List<PlanetAPI> planets = system.
getPlanets();
805 if (planet.isStar())
continue;
808 if (planet.getSpec().isDoNotShowInCombat())
continue;
static SettingsAPI getSettings()
static SectorAPI getSector()
void setInitialDeploymentBurnDuration(float initialDeploymentBurnDuration)
void setNormalDeploymentBurnDuration(float normalDeploymentBurnDuration)
CampaignFleetAPI getOtherFleet()
boolean objectivesAllowed
FleetGoal getPlayerGoal()
boolean forceObjectivesOnMap
int getPlayerCommandPoints()
void setEscapeDeploymentBurnDuration(float escapeDeploymentBurnDuration)
void setStandoffRange(float standoffRange)
CampaignFleetAPI getPlayerFleet()
void setInitialEscapeRange(float initialEscapeRange)
void setFlankDeploymentDistance(float sideDeploymentDistance)
static final String PLANET_LAVA_MINOR
static final String PLANET_LAVA
boolean containsEntity(SectorEntityToken other)
static float DEPTH_THRESHOLD_FOR_NO_DUST_PARTICLES_IN_COMBAT
float getIntensityAtPoint(Vector2f point)
Color getPulsarColorForAngle(float angle)
float getIntensityAtPoint(Vector2f point)
Color getAuroraColorForAngle(float angle)
static float PLANET_AREA_WIDTH
List< NearbyPlanetData > getNearbyPlanets(CampaignFleetAPI playerFleet)
void afterDefinitionLoad(final CombatEngineAPI engine)
PulsarBeamTerrainPlugin pulsar
static float PLANET_AREA_HEIGHT
void addEscapeObjectives(MissionDefinitionAPI loader, int num, Random random)
void addObjectiveAt(float xMult, float yMult, float xOff, float yOff, String type, Random random)
void addObjectives(MissionDefinitionAPI loader, int num, Random random)
void addObjectiveAt(float xMult, float yMult, float xOff, float yOff, Random random)
static float ABYSS_SHIP_SPEED_PENALTY
MissionDefinitionAPI loader
void createMap(Random random)
static float SINGLE_PLANET_MAX_DIST
StarCoronaTerrainPlugin corona
float countNearbyAsteroids(CampaignFleetAPI playerFleet)
static float PLANET_MAX_DIST
String[] pickCommRelays(int min, int max, boolean comm1, boolean comm2, boolean comm3, boolean comm4, Random random)
static float ABYSS_MISSILE_SPEED_PENALTY
PlanetAPI getClosestPlanet(CampaignFleetAPI playerFleet)
void initBattle(final BattleCreationContext context, MissionDefinitionAPI loader)
static float ABYSS_OVERLAY_ALPHA
void addMultiplePlanets()
BattleCreationContext context
String pickAny(Random random)
void setRandomBackground(MissionDefinitionAPI loader, Random random)
static Random getRandom(long seed, int level)
static Color setAlpha(Color color, int alpha)
static float getDistance(SectorEntityToken from, SectorEntityToken to)
static long getSalvageSeed(SectorEntityToken entity)
static Color scaleAlpha(Color color, float factor)
static float getAbyssalDepth(Vector2f loc)
static float getAngleInDegreesStrict(Vector2f v)
static float getAngleInDegrees(Vector2f v)
static Color scaleColor(Color color, float factor)
String getSpriteName(String category, String id)
float getFloat(String key)
LocationAPI getContainingLocation()
FleetDataAPI getFleetData()
MutableCharacterStatsAPI getCommanderStats()
List< FleetMemberAPI > getCombatReadyMembersListCopy()
List< FleetMemberAPI > getMembersListCopy()
List< PlanetAPI > getPlanets()
List< CustomCampaignEntityAPI > getCustomEntitiesWithTag(String tag)
List< CampaignTerrainAPI > getTerrainCopy()
List< SectorEntityToken > getAsteroids()
String getBackgroundTextureFilename()
CampaignFleetAPI getPlayerFleet()
LocationAPI getHyperspace()
MutableStat getCommandPoints()
void maintainStatusForPlayerShip(Object key, String spriteName, String title, String data, boolean isDebuff)
List< MissileAPI > getMissiles()
void setBackgroundGlowColor(Color backgroundGlowColor)
void addPlugin(EveryFrameCombatPlugin plugin)
void setBackgroundColor(Color backgroundColor)
void setRenderStarfield(boolean renderStarfield)
List< ShipAPI > getShips()
void setBackgroundGlowColorNonAdditive(boolean backgroundGlowColorNonAdditive)
void setBackgroundGlowColor(Color backgroundGlowColor)
void setNebulaTex(String nebulaTex)
void addObjective(float x, float y, String type, BattleObjectiveAPI.Importance importance)
void setBackgroundSpriteName(String background)
void setHyperspaceMode(boolean hyperspaceMode)
void addRingAsteroids(float x, float y, float angle, float width, float minSpeed, float maxSpeed, int quantity)
void setPlanetBgSize(float bgWidth, float bgHeight)
void addPlanet(float x, float y, float radius, String type, float gravity)
void addAsteroidField(float x, float y, float angle, float width, float minSpeed, float maxSpeed, int quantity)
void addFleetMember(FleetSide side, FleetMemberAPI member)
void initMap(float minX, float maxX, float minY, float maxY)
void initFleet(FleetSide side, String shipNamePrefix, FleetGoal goal, boolean useDefaultAI)
void addPlugin(EveryFrameCombatPlugin plugin)
void setNebulaMapTex(String nebulaMapTex)
void addNebula(float x, float y, float radius)