diff --git a/dat/missions/cargo.lua b/dat/missions/cargo.lua index 84dcbb0..61ac2a9 100644 --- a/dat/missions/cargo.lua +++ b/dat/missions/cargo.lua @@ -31,7 +31,7 @@ function create() until planet ~= space.landName() or i > 10 -- Protect agains inf loop. if i > 10 then - misn.finish() + misn.finish(false) end -- Missions generic. @@ -67,7 +67,7 @@ function land() if player.rmCargo(carg_id) then player.pay(reward) tk.msg(finish_title, string.format(finish_msg, carg_type)) - misn_finish() + misn_finish(true) else tk.msg(miss_title, string.format(miss_msg, carg_mass, carg_type)) end diff --git a/dat/missions/empire00.lua b/dat/missions/empire00.lua index f74e1ed..3f5be6f 100644 --- a/dat/missions/empire00.lua +++ b/dat/missions/empire00.lua @@ -46,7 +46,7 @@ function land() player.pay(reward) -- More flavour text :) tk.msg(title[3], string.format(text[4], dest)) - misn.finish() + misn.finish(true) end end end diff --git a/src/misn_lua.c b/src/misn_lua.c index abbe76c..7e9323c 100644 --- a/src/misn_lua.c +++ b/src/misn_lua.c @@ -10,6 +10,7 @@ #include "space.h" #include "toolkit.h" #include "land.h" +#include "player.h" #include "misn_lua.h" // FUCK LUA!!! @@ -215,8 +216,19 @@ static int misn_accept(lua_State* L) { } static int misn_finish(lua_State* L) { + int b; + + if(lua_isboolean(L, -1)) b = lua_toboolean(L, -1); + else { + DEBUG("Mission '%s' trying to finish without specifying if mission is complete", + cur_mission->data->name); + return 0; + } misn_delete = 1; + if(b && mis_isFlag(cur_mission->data, MISSION_UNIQUE)) + player_missionFinished(mission_getID(cur_mission->data)); + lua_pushstring(L, "Mission Finished"); lua_error(L); // Should not return.. diff --git a/src/mission.c b/src/mission.c index 7f34d1f..19b7623 100644 --- a/src/mission.c +++ b/src/mission.c @@ -43,6 +43,17 @@ static int mission_matchFaction(MissionData* misn, int faction); static int mission_location(char* loc); static MissionData* mission_parse(const xmlNodePtr parent); +// Gets the ID of a MissionData. +int mission_getID(MissionData* misn) { + int i; + for(i = 0; i < mission_nstack; i++) + if(misn == &mission_stack[i]) + return i; + + DEBUG("Mission '%s' not found in stack", misn->name); + return -1; +} + // Initialize a mission. static int mission_init(Mission* mission, MissionData* misn) { char* buf; @@ -103,6 +114,8 @@ void missions_bar(int faction, char* planet, char* system) { (((misn->avail.planet && strcmp(misn->avail.planet, planet)==0)) || (misn->avail.system && (strcmp(misn->avail.system, system)==0)) || mission_matchFaction(misn, faction))) { + + if(player_missionAlreadyDone(i)) continue; // Already done the mission. chance = (double)(misn->avail.chance % 100)/100.; diff --git a/src/mission.h b/src/mission.h index add1471..2d0aed7 100644 --- a/src/mission.h +++ b/src/mission.h @@ -65,6 +65,9 @@ Mission* missions_computer(int* n, int faction, char* planet, char* system); void mission_accept(Mission* mission); void mission_bar(int faction, char* planet, char* system); +// Misc. +int mission_getID(MissionData* misn); + // Cargo stuff. void mission_linkCargo(Mission* misn, unsigned int cargo_id); void mission_unlinkCargo(Mission* misn, unsigned int cargo_id); diff --git a/src/player.c b/src/player.c index 0d31f7c..78a1265 100644 --- a/src/player.c +++ b/src/player.c @@ -15,6 +15,7 @@ #include "pause.h" #include "menu.h" #include "toolkit.h" +#include "mission.h" #include "player.h" #define XML_GUI_ID "GUIs" // XML section identifier. @@ -52,6 +53,10 @@ int hyperspace_target = -1; // Target hyperspace route. static unsigned int player_timer = 0; static Vec2 player_cam; +static int* missions_done = NULL; // Saves position. +static int missions_mdone = 0; +static int missions_ndone = 0; + // Pilot stuff for GUI. extern Pilot** pilot_stack; extern int pilots; @@ -310,6 +315,12 @@ void player_cleanup(void) { // Nothing left. player_nstack = 0; } + if(missions_done) { + free(missions_done); + missions_done = NULL; + missions_ndone = 0; + missions_mdone = 0; + } } void player_message(const char* fmt, ...) { @@ -1369,3 +1380,24 @@ void player_setLoc(char* shipname, char* loc) { WARN("Player ship '%s' not found in stack", shipname); } +// Marks a mission as completed. +void player_missionFinished(int id) { + missions_ndone++; + if(missions_ndone > missions_mdone) { + // Need to grow. + missions_mdone += 25; + missions_done = realloc(missions_done, sizeof(int) * missions_mdone); + } + missions_done[missions_ndone-1] = id; +} + +// has player already completed a mission? +int player_missionAlreadyDone(int id) { + int i; + + for(i = 0; i < missions_ndone; i++) + if(missions_done[i] == id) + return 1; + return 0; +} + diff --git a/src/player.h b/src/player.h index d985c0d..6bfbc36 100644 --- a/src/player.h +++ b/src/player.h @@ -58,6 +58,10 @@ char* player_getLoc(char* shipname); void player_setLoc(char* shipname, char* loc); void player_swapShip(char* shipname); +// Player missions. +void player_missionFinished(int id); +int player_missionAlreadyDone(int id); + // Keybind actions. void player_setRadarRel(int mod); void player_secondaryNext(void);