001package com.fs.starfarer.api.impl.campaign.fleets.misc;
002
003import java.util.Random;
004
005import com.fs.starfarer.api.Global;
006import com.fs.starfarer.api.campaign.BattleAPI;
007import com.fs.starfarer.api.campaign.CampaignFleetAPI;
008import com.fs.starfarer.api.campaign.SectorEntityToken;
009import com.fs.starfarer.api.campaign.StarSystemAPI;
010import com.fs.starfarer.api.campaign.econ.MarketAPI;
011import com.fs.starfarer.api.impl.campaign.fleets.RouteManager;
012import com.fs.starfarer.api.impl.campaign.fleets.RouteManager.RouteData;
013import com.fs.starfarer.api.impl.campaign.fleets.RouteManager.RouteSegment;
014import com.fs.starfarer.api.impl.campaign.fleets.misc.MiscFleetRouteManager.MiscRouteData;
015import com.fs.starfarer.api.impl.campaign.ids.Factions;
016import com.fs.starfarer.api.impl.campaign.ids.FleetTypes;
017import com.fs.starfarer.api.impl.campaign.ids.MemFlags;
018import com.fs.starfarer.api.impl.campaign.ids.Tags;
019import com.fs.starfarer.api.impl.campaign.missions.FleetCreatorMission;
020import com.fs.starfarer.api.impl.campaign.missions.hub.HubMissionWithTriggers.FleetQuality;
021import com.fs.starfarer.api.impl.campaign.missions.hub.HubMissionWithTriggers.FleetSize;
022import com.fs.starfarer.api.impl.campaign.missions.hub.HubMissionWithTriggers.OfficerNum;
023import com.fs.starfarer.api.impl.campaign.missions.hub.HubMissionWithTriggers.OfficerQuality;
024import com.fs.starfarer.api.impl.campaign.missions.hub.MissionFleetAutoDespawn;
025import com.fs.starfarer.api.impl.campaign.shared.SharedData;
026import com.fs.starfarer.api.util.Misc;
027import com.fs.starfarer.api.util.WeightedRandomPicker;
028
029public class MiscAcademyFleetCreator extends BaseMiscFleetCreatorPlugin {
030
031        public static String ACADEMY_FLEET_TYPE = "$academyFleetType";
032        
033        @Override
034        public float getFrequency() {
035                return Global.getSettings().getFloat("miscFleetAcademyFrequency");
036        }
037
038        @Override
039        public int getMaxFleetsForThisCreator() {
040                return Global.getSettings().getInt("miscFleetAcademyMaxFleets");
041        }
042
043        public static SectorEntityToken getAcademy() {
044                StarSystemAPI system = Global.getSector().getStarSystem("Galatia");
045                return system.getEntityById("station_galatia_academy");
046        }
047
048        
049        @Override
050        public MiscRouteData createRouteParams(MiscFleetRouteManager manager, Random random) {
051                MarketAPI from = pickSourceMarket(manager);
052                SectorEntityToken to = getAcademy();
053                
054                if (to == null || to.getContainingLocation().hasTag(Tags.SYSTEM_CUT_OFF_FROM_HYPER)) return null;
055                
056                
057//              from = Global.getSector().getEconomy().getMarket("chalcedon");
058//              to = Global.getSector().getEconomy().getMarket("eochu_bres").getPrimaryEntity();
059//              to = Global.getSector().getEntityById("beholder_station");
060                
061                MiscRouteData result = createData(from, to);
062                
063                return result;
064        }
065        
066
067        @Override
068        public CampaignFleetAPI createFleet(MiscFleetRouteManager manager, RouteData route, Random random) {
069                MiscRouteData data = (MiscRouteData) route.getCustom();
070
071                FleetCreatorMission m = new FleetCreatorMission(random);
072                m.beginFleet();
073                
074                
075                m.triggerCreateFleet(FleetSize.MEDIUM, FleetQuality.LOWER, data.factionId, 
076                                                         FleetTypes.ACADEMY_FLEET, data.from.getLocationInHyperspace());
077                m.triggerSetFleetOfficers(OfficerNum.FC_ONLY, OfficerQuality.LOWER);
078                m.triggerSetFleetSizeFraction(data.size * 0.5f * (0.5f + random.nextFloat() * 0.5f));
079                m.triggerFleetSetNoFactionInName();
080                m.triggerSetTraderFleet();
081                m.triggerSetFleetComposition(0f, 0f, 0f, 1f, 0f);
082                m.triggerSetFleetMemoryValue(MemFlags.MEMORY_KEY_SOURCE_MARKET, data.from);
083                //m.triggerSetFleetMemoryValue("$destShrine", data.to.getId());
084                m.triggerSetFleetMemoryValue(MemFlags.ACADEMY_FLEET, true);
085
086                WeightedRandomPicker<String> types = new WeightedRandomPicker<String>(random);
087                types.add("supplies");
088                types.add("students");
089                types.add("visitors");
090                m.triggerSetFleetMemoryValue(ACADEMY_FLEET_TYPE, types.pick());
091                
092                
093                CampaignFleetAPI fleet = m.createFleet();
094                fleet.removeScriptsOfClass(MissionFleetAutoDespawn.class);
095                
096                return fleet;
097        }
098
099        
100        public MiscRouteData createData(MarketAPI from, SectorEntityToken to) {
101                MiscRouteData data = new MiscRouteData(getId());
102                data.from = from;
103                data.to = to;
104                
105                if (from.getFaction().isHostileTo(Factions.INDEPENDENT)) {
106                        data.factionId = from.getFactionId();
107                } else {
108                        data.factionId = Factions.INDEPENDENT;
109                }
110                
111                // in case the source colony is hostile to the Hegemony (which has Ancyra in the system)
112                data.smuggling = true;
113                
114                float sizeBasis = from.getSize() / 8f;
115                sizeBasis *= 0.25f;
116                if (sizeBasis < 0.05f) sizeBasis = 0.05f;
117                if (sizeBasis > 0.25f) sizeBasis = 0.25f;
118                data.size = sizeBasis;
119                
120                return data;
121        }
122        
123        public MarketAPI pickSourceMarket(MiscFleetRouteManager manager) {
124                WeightedRandomPicker<MarketAPI> markets = new WeightedRandomPicker<MarketAPI>(manager.getRandom());
125                for (MarketAPI market : Global.getSector().getEconomy().getMarketsCopy()) {
126                        if (market.isHidden()) continue;
127                        if (!market.hasSpaceport()) continue; // markets w/o spaceports don't launch fleets
128                        if (market.getContainingLocation().hasTag(Tags.SYSTEM_CUT_OFF_FROM_HYPER)) continue;
129                        
130                        if (manager.getTimeout(getId()).contains(market.getId())) continue;
131                        
132                        // use this for academy fleets also
133                        if (SharedData.getData().getMarketsWithoutTradeFleetSpawn().contains(market.getId())) continue;
134                        
135                        float distLY = Misc.getDistanceToPlayerLY(market.getPrimaryEntity());
136                        float mult = 1f - Math.min(0.99f, distLY / 10f);
137                        
138                        if (market.getFaction().isHostileTo(Factions.INDEPENDENT)) {
139                                mult *= 0.2f;
140                        }
141                        
142                        markets.add(market, market.getSize() * mult);
143                }
144                return markets.pick();
145        }
146        
147        @Override
148        public void reportBattleOccurred(MiscFleetRouteManager manager, CampaignFleetAPI fleet, CampaignFleetAPI primaryWinner, BattleAPI battle) {
149                RouteData route = RouteManager.getInstance().getRoute(manager.getRouteSourceId(), fleet);
150                if (route == null || !(route.getCustom() instanceof MiscRouteData)) return;
151                
152                if (route.isExpired()) return;
153                if (!battle.isPlayerInvolved()) return;
154
155                // player was involved, no the opposite side of the pilgrim fleet
156                if (battle.getNonPlayerSideSnapshot().contains(fleet)) {
157                        MiscRouteData data = (MiscRouteData) route.getCustom();
158                        
159                        // possible TODO: some kind of response, depending?
160                }
161        }
162        
163        
164        public String getStartingActionText(CampaignFleetAPI fleet, RouteSegment segment, MiscRouteData data) {
165                String type = fleet.getMemoryWithoutUpdate().getString(ACADEMY_FLEET_TYPE);
166                return "preparing for voyage to Galatia Academy";
167        }
168
169        public String getEndingActionText(CampaignFleetAPI fleet, RouteSegment segment, MiscRouteData data) {
170                //return "orbiting " + data.from.getName();
171                return "returned from voyage to Galatia Academy";
172        }
173
174        public String getTravelToDestActionText(CampaignFleetAPI fleet, RouteSegment segment, MiscRouteData data) {
175                return "traveling to Galatia Academy";
176        }
177
178        public String getTravelReturnActionText(CampaignFleetAPI fleet, RouteSegment segment, MiscRouteData data) {
179                return "traveling to " + data.from.getName();
180        }
181
182        public String getAtDestUnloadActionText(CampaignFleetAPI fleet, RouteSegment segment, MiscRouteData data) {
183                return "orbiting Galatia Academy";
184        }
185
186        public String getAtDestLoadActionText(CampaignFleetAPI fleet, RouteSegment segment, MiscRouteData data) {
187                return "orbiting Galatia Academy";
188        }
189        
190}