ONATIONB.cpp 63 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355
  1. /*
  2. * Seven Kingdoms: Ancient Adversaries
  3. *
  4. * Copyright 1997,1998 Enlight Software Ltd.
  5. *
  6. * This program is free software: you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation, either version 2 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * This program is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. * GNU General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  18. *
  19. */
  20. //Filename : ONATION.CPP
  21. //Description : Object Nation - part 1
  22. #include <OSTR.h>
  23. #include <OSYS.h>
  24. #include <ODATE.h>
  25. #include <OBOX.h>
  26. #include <OVGA.h>
  27. #include <OFONT.h>
  28. #include <ONEWS.h>
  29. #include <OWORLD.h>
  30. #include <OFIRM.h>
  31. #include <OGAME.h>
  32. #include <OPOWER.h>
  33. #include <OREGIONS.h>
  34. #include <ORACERES.h>
  35. #include <OTALKRES.h>
  36. #include <OMONSRES.h>
  37. #include <OGODRES.h>
  38. #include <OTOWN.h>
  39. #include <OSPY.h>
  40. #include <OF_MARK.h>
  41. #include <OF_BASE.h>
  42. #include <OF_MONS.h>
  43. #include <OTECHRES.h>
  44. #include <ONATION.h>
  45. #include <OREBEL.h>
  46. #include <OREMOTE.h>
  47. //-------- Define static variables --------//
  48. char* NationRelation::relation_status_str_array[5] =
  49. {
  50. "War", "Tense", "Neutral", "Friendly", "Alliance"
  51. };
  52. //--------- Define static functions -------//
  53. static int succeed_king_loyalty_change(int thisRaceId, int newKingRaceId, int oldKingRaceId);
  54. //--------- Begin of function NationBase::Nation --------//
  55. NationBase::NationBase()
  56. {
  57. memset( this, 0, sizeof(NationBase) );
  58. }
  59. //---------- End of function NationBase::Nation --------//
  60. //--------- Begin of function NationBase::~Nation --------//
  61. NationBase::~NationBase()
  62. {
  63. #ifdef DEBUG
  64. err_when( nation_recno ); // deinit() must be called first before this destructor is called
  65. for( int i=0 ; i<MAX_RACE ; i++ )
  66. err_when( base_count_array[i] > 0 ); // it should be all zeros
  67. #endif
  68. }
  69. //---------- End of function NationBase::~Nation --------//
  70. //--------- Begin of function NationBase::init --------//
  71. //
  72. // This function will be called directly by
  73. //
  74. // <int> nationType = the nation type (NATION_???)
  75. // <int> raceId = id. of the race
  76. // <int> colorSchemeId = color scheme id. of the nation
  77. // [DWORD] playerId = an unique player id. (for multiplayer game)
  78. //
  79. void NationBase::init(int nationType, int raceId, int colorSchemeId, DWORD playerId)
  80. {
  81. //------------- set vars ---------------//
  82. nation_type = nationType;
  83. race_id = raceId;
  84. color_scheme_id = colorSchemeId;
  85. player_id = playerId;
  86. colorSchemeId = min( colorSchemeId, MAX_COLOR_SCHEME );
  87. nation_color = game.color_remap_array[colorSchemeId].main_color;
  88. last_war_date = info.game_date;
  89. //------- if this is the local player's nation -------//
  90. if( nation_type==NATION_OWN )
  91. nation_array.player_recno = nation_recno;
  92. //---------- init game vars ------------//
  93. static int start_up_cash_array[] = { 4000, 7000, 12000, 20000 };
  94. if( is_ai() )
  95. cash = (float) start_up_cash_array[config.ai_start_up_cash-1];
  96. else
  97. cash = (float) start_up_cash_array[config.start_up_cash-1];
  98. food = (float) 5000; // startup food is 5000 for all nations in all settings
  99. //---- initialize this nation's relation on other nations ----//
  100. for( int i=nation_array.size() ; i>0 ; i-- )
  101. {
  102. if( nation_array.is_deleted(i) )
  103. continue;
  104. init_relation(i);
  105. nation_array[i]->init_relation(nation_recno);
  106. }
  107. //--------- init technology ----------//
  108. tech_res.init_nation_tech(nation_recno);
  109. //------- reset all god knowledge --------//
  110. god_res.init_nation_know(nation_recno);
  111. //### begin alex 23/9 ###//
  112. if(remote.is_enable() && nation_recno && !is_ai() && m.is_file_exist("TECHGOD.SYS"))
  113. {
  114. tech_res.inc_all_tech_level(nation_recno);
  115. tech_res.inc_all_tech_level(nation_recno);
  116. tech_res.inc_all_tech_level(nation_recno);
  117. god_res.enable_know_all(nation_recno);
  118. }
  119. //#### end alex 23/9 ####//
  120. }
  121. //----------- End of function NationBase::init ---------//
  122. //--------- Begin of function NationBase::deinit --------//
  123. //
  124. // When a nation is to be deleted, NationBase::deinit() must
  125. // be called first from nation_array before calling its
  126. // destructor as when it deinitalizes units, some functions
  127. // will need to access the nation_array[].
  128. //
  129. void NationBase::deinit()
  130. {
  131. if( nation_recno==0 ) // has been deinitialized
  132. return;
  133. //---- delete all talk messages to/from this nation ----//
  134. talk_res.del_all_nation_msg(nation_recno);
  135. //------- close down all firms --------//
  136. close_all_firm();
  137. //---- neutralize all towns belong to this nation ----//
  138. Town* townPtr;
  139. int i;
  140. for( i=town_array.size() ; i>0 ; i-- )
  141. {
  142. if( town_array.is_deleted(i) )
  143. continue;
  144. townPtr = town_array[i];
  145. if( townPtr->nation_recno == nation_recno )
  146. townPtr->set_nation(0);
  147. }
  148. //------------- deinit our spies -------------//
  149. for( i=spy_array.size() ; i>0 ; i-- )
  150. {
  151. if( spy_array.is_deleted(i) )
  152. continue;
  153. Spy* spyPtr = spy_array[i];
  154. //-----------------------------------------------------//
  155. // Convert all of spies of this nation to normal units,
  156. // so there will be no more spies of this nation.
  157. //-----------------------------------------------------//
  158. if( spyPtr->true_nation_recno == nation_recno ) // drop spy identities of spies in towns, firms and mobile ones
  159. spyPtr->drop_spy_identity();
  160. //-----------------------------------------------------//
  161. // For spies of other nation cloaked as this nation,
  162. // their will uncover their cloak and change back
  163. // to their original nation.
  164. //-----------------------------------------------------//
  165. else if( spyPtr->cloaked_nation_recno == nation_recno )
  166. spyPtr->change_cloaked_nation(spyPtr->true_nation_recno);
  167. err_when( spyPtr->true_nation_recno == nation_recno || // there should be no more spies associated with this nation
  168. spyPtr->cloaked_nation_recno == nation_recno );
  169. }
  170. //----- deinit all units belonging to this nation -----//
  171. deinit_all_unit();
  172. //-------- if the viewing nation is this nation -------//
  173. if( !sys.signal_exit_flag )
  174. {
  175. if( info.default_viewing_nation_recno == nation_recno )
  176. {
  177. info.default_viewing_nation_recno = nation_array.player_recno;
  178. sys.set_view_mode(MODE_NORMAL);
  179. }
  180. else if( info.viewing_nation_recno == nation_recno )
  181. sys.set_view_mode(MODE_NORMAL); // it will set viewing_nation_recno to default_viewing_nation_recno
  182. // ##### begin Gilbert 22/10 #######//
  183. // if deleting own nation, darken view mode buttons
  184. if( nation_recno == nation_array.player_recno )
  185. {
  186. sys.disp_view_mode(1);
  187. }
  188. // ##### end Gilbert 22/10 #######//
  189. }
  190. nation_recno = 0;
  191. }
  192. //----------- End of function NationBase::deinit ---------//
  193. //--------- Begin of function NationBase::init_relation --------//
  194. //
  195. // Initialize the relation vars with the given nation.
  196. //
  197. // <int> relationNationRecno - recno of the NationRelation to set.
  198. //
  199. void NationBase::init_relation(int relationNationRecno)
  200. {
  201. NationRelation* nationRelation = relation_array+relationNationRecno-1;
  202. memset( nationRelation, 0, sizeof(NationRelation) );
  203. set_relation_should_attack(relationNationRecno, relationNationRecno!=nation_recno, COMMAND_AUTO);
  204. if( is_ai() && nation_array[relationNationRecno]->is_ai() ) // AI has contact with each other in the beginning of the game.
  205. nationRelation->has_contact = 1;
  206. else
  207. nationRelation->has_contact = relationNationRecno==nation_recno || config.explore_whole_map; // if the map is blackened out, no contact in the beginning
  208. nationRelation->trade_treaty = relationNationRecno==nation_recno;
  209. nationRelation->status = NATION_NEUTRAL;
  210. nationRelation->ai_relation_level = NATION_NEUTRAL * RELATION_LEVEL_PER_STATUS;
  211. nationRelation->last_change_status_date = info.game_date;
  212. if( relationNationRecno == nation_recno ) // own nation
  213. relation_status_array[relationNationRecno-1] = NATION_ALLIANCE; // for facilitating searching
  214. else
  215. relation_status_array[relationNationRecno-1] = NATION_NEUTRAL;
  216. set_relation_passable(relationNationRecno, NATION_FRIENDLY);
  217. is_allied_with_player = 0;
  218. }
  219. //----------- End of function NationBase::init_relation ---------//
  220. //--------- Begin of function NationBase::close_all_firm --------//
  221. //
  222. // Close down all firms under this nation.
  223. //
  224. void NationBase::close_all_firm()
  225. {
  226. int i;
  227. for( i=firm_array.size() ; i>0 ; i-- )
  228. {
  229. if( !firm_array.is_deleted(i) &&
  230. firm_array[i]->nation_recno == nation_recno )
  231. {
  232. firm_array.del_firm(i);
  233. }
  234. }
  235. }
  236. //----------- End of function NationBase::close_all_firm ---------//
  237. //--------- Begin of function NationBase::deinit_all_unit --------//
  238. //
  239. // Deinit all units belonging to this nation when this nation is deinitialized.
  240. //
  241. void NationBase::deinit_all_unit()
  242. {
  243. //--- update total_human_unit so the numbers will be correct ---//
  244. #ifndef DEBUG // only do this in release version to on-fly fix bug
  245. nation_array.update_statistic();
  246. #endif
  247. //--------------------------------------//
  248. int i;
  249. Unit* unitPtr;
  250. for( i=unit_array.size() ; i>0 ; i-- )
  251. {
  252. if( unit_array.is_deleted(i) )
  253. {
  254. unitPtr = (Unit*) unit_array.get_ptr(i); // this unit is dying, so is_deleted() return 1;
  255. if( !unitPtr )
  256. continue;
  257. if( unitPtr->nation_recno == nation_recno )
  258. unit_array.del(i);
  259. continue;
  260. }
  261. //--------------------------------------------//
  262. unitPtr = unit_array[i];
  263. if( unitPtr->nation_recno != nation_recno )
  264. continue;
  265. //----- only human units will betray -----//
  266. if( unitPtr->race_id )
  267. {
  268. unitPtr->loyalty = 0; // force it to detray
  269. if( unitPtr->think_betray() )
  270. continue;
  271. }
  272. //--- if the unit has not changed nation, the unit will disappear ---//
  273. if( unit_array.get_ptr(i) )
  274. unit_array.del(i);
  275. }
  276. //------------ debug code -------------//
  277. for( i=unit_array.size() ; i>0 ; i-- )
  278. {
  279. if( unit_array.is_deleted(i) )
  280. continue;
  281. unitPtr = unit_array[i];
  282. err_when( unitPtr->nation_recno == nation_recno ); // they should have been all deleted.
  283. }
  284. }
  285. //----------- End of function NationBase::deinit_all_unit ---------//
  286. //--------- Begin of function NationBase::hand_over_to --------//
  287. //
  288. // <int> handoverNationRecno - hand over the entire nation to this nation.
  289. //
  290. void NationBase::hand_over_to(int handoverNationRecno)
  291. {
  292. rebel_array.stop_attack_nation(nation_recno);
  293. town_array.stop_attack_nation(nation_recno);
  294. unit_array.stop_all_war(nation_recno);
  295. monster_res.stop_attack_nation(nation_recno);
  296. nation_hand_over_flag = nation_recno;
  297. //--- hand over units (should hand over units first as you cannot change a firm's nation without changing the nation of the overseer there ---//
  298. Unit* unitPtr;
  299. int i;
  300. for( i=unit_array.size() ; i>0 ; i-- )
  301. {
  302. if( unit_array.is_deleted(i) )
  303. {
  304. //-- If the unit is dying and isn't truly deleted yet, delete it now --//
  305. if( !unit_array.is_truly_deleted(i) &&
  306. unit_array[i]->nation_recno == nation_recno )
  307. {
  308. unit_array.die(i);
  309. }
  310. continue;
  311. }
  312. //---------------------------------------//
  313. unitPtr = unit_array[i];
  314. if( unitPtr->nation_recno != nation_recno )
  315. continue;
  316. //----- if it is a god, resign it -------//
  317. if( god_res.is_god_unit(unitPtr->unit_id) )
  318. {
  319. unitPtr->resign(COMMAND_AUTO);
  320. continue;
  321. }
  322. //----- if it is a spy cloaked as this nation -------//
  323. //
  324. // If the unit is a overseer of a Camp or Base,
  325. // the Camp or Base will change nation as a result.
  326. //
  327. //---------------------------------------------------//
  328. if( unitPtr->spy_recno )
  329. unitPtr->spy_change_nation(handoverNationRecno, COMMAND_AUTO);
  330. else
  331. unitPtr->change_nation(handoverNationRecno);
  332. }
  333. //------- hand over firms ---------//
  334. for( i=firm_array.size() ; i>0 ; i-- )
  335. {
  336. if( !firm_array.is_deleted(i) &&
  337. firm_array[i]->nation_recno == nation_recno )
  338. {
  339. firm_array[i]->change_nation(handoverNationRecno);
  340. }
  341. }
  342. //------- hand over towns ---------//
  343. for( i=town_array.size() ; i>0 ; i-- )
  344. {
  345. if( !town_array.is_deleted(i) &&
  346. town_array[i]->nation_recno == nation_recno )
  347. {
  348. town_array[i]->set_nation(handoverNationRecno);
  349. }
  350. }
  351. //-------------------------------------------------//
  352. //
  353. // For the spies of this nation cloaked into other nations,
  354. // we need to update their true_nation_recno.
  355. //
  356. //-------------------------------------------------//
  357. Spy* spyPtr;
  358. for( i=spy_array.size() ; i>0 ; i-- )
  359. {
  360. if( spy_array.is_deleted(i) )
  361. continue;
  362. spyPtr = spy_array[i];
  363. err_when( spyPtr->cloaked_nation_recno == nation_recno ); // there should be no units in this nation after the above deinitialization
  364. if( spyPtr->true_nation_recno == nation_recno )
  365. spyPtr->change_true_nation(handoverNationRecno);
  366. }
  367. //------- delete this nation from nation_array -------//
  368. nation_array.del_nation(nation_recno);
  369. nation_hand_over_flag = 0;
  370. }
  371. //----------- End of function NationBase::hand_over_to ---------//
  372. //--------- Begin of function NationBase::set_king --------//
  373. //
  374. // Set the king unit recno.
  375. //
  376. // <int> kingUnitRecno - unit recno of the king
  377. // <int> firstKing - whether this is the first king of the nation.
  378. //
  379. void NationBase::set_king(int kingUnitRecno, int firstKing)
  380. {
  381. king_unit_recno = kingUnitRecno;
  382. Unit* kingUnit = unit_array[king_unit_recno];
  383. //--- if this unit currently has not have leadership ---//
  384. if( kingUnit->skill.skill_id != SKILL_LEADING )
  385. {
  386. kingUnit->skill.skill_id = SKILL_LEADING;
  387. kingUnit->skill.skill_level = 0;
  388. }
  389. kingUnit->set_rank(RANK_KING);
  390. kingUnit->stop2(); // clear the existing order, as there might be an assigning to firm/town order. But kings cannot be assigned to towns or firms as workers.
  391. //---------- king related vars ----------//
  392. if( nation_type == NATION_AI || !firstKing ) // for succession, no longer use the original player name
  393. nation_name_id = kingUnit->name_id;
  394. else
  395. nation_name_id = -nation_recno; // for human players, the name is retrieved from NationArray::human_name_array
  396. race_id = kingUnit->race_id;
  397. king_leadership = kingUnit->skill.skill_level;
  398. err_when( !nation_name_id );
  399. err_when( !race_id );
  400. }
  401. //----------- End of function NationBase::set_king ---------//
  402. //--------- Begin of function NationBase::nation_name --------//
  403. //
  404. char* NationBase::nation_name()
  405. {
  406. #if(defined(SPANISH))
  407. strncpy( nation_name_str, "Reino de ", NATION_NAME_LEN );
  408. nation_name_str[NATION_NAME_LEN]=NULL;
  409. strncat( nation_name_str, king_name(1), NATION_NAME_LEN ); // 1-get the first word of the name only
  410. nation_name_str[NATION_NAME_LEN]=NULL;
  411. #elif(defined(FRENCH))
  412. strncpy( nation_name_str, "Royaume de ", NATION_NAME_LEN );
  413. nation_name_str[NATION_NAME_LEN]=NULL;
  414. strncat( nation_name_str, king_name(1), NATION_NAME_LEN ); // 1-get the first word of the name only
  415. nation_name_str[NATION_NAME_LEN]=NULL;
  416. #else
  417. // German and US
  418. strncpy( nation_name_str, king_name(1), NATION_NAME_LEN ); // 1-get the first word of the name only
  419. nation_name_str[NATION_NAME_LEN]=NULL;
  420. strncat( nation_name_str, "'s ", NATION_NAME_LEN ); // 1-get the first word of the name only
  421. nation_name_str[NATION_NAME_LEN]=NULL;
  422. strncat( nation_name_str, translate.process("Kingdom"), NATION_NAME_LEN );
  423. nation_name_str[NATION_NAME_LEN]=NULL;
  424. #endif
  425. return nation_name_str; // each name needs to have its own var as multiple nation names will be displayed at the same time in diplomatic talk choices
  426. }
  427. //----------- End of function NationBase::nation_name ---------//
  428. //--------- Begin of function NationBase::king_name --------//
  429. //
  430. // [int] firstWordOnly - whether only get the first word of the name.
  431. // (default: 0)
  432. //
  433. char* NationBase::king_name(int firstWordOnly)
  434. {
  435. if( nation_name_id < 0 ) // human player custom names
  436. {
  437. return nation_array.get_human_name(nation_name_id, firstWordOnly);
  438. }
  439. else
  440. {
  441. if( firstWordOnly )
  442. return race_res[race_id]->get_single_name( (WORD) nation_name_id );
  443. else
  444. return race_res[race_id]->get_name( (WORD) nation_name_id );
  445. }
  446. }
  447. //----------- End of function NationBase::king_name ---------//
  448. //------- Begin of function NationBase::cash_str ------//
  449. //
  450. // Return a text string with the current nation treasure and profit
  451. // in the past 30 days.
  452. //
  453. char* NationBase::cash_str()
  454. {
  455. static String str;
  456. if( cash >= 0 )
  457. {
  458. str = m.format( (int)cash, 4 ); // format type 4 - no thousand separators
  459. }
  460. else
  461. {
  462. str = "-";
  463. str += m.format( (int)-cash, 4 ); // format type 4 - no thousand separators
  464. }
  465. //--------------------------------------//
  466. int curProfit = (int) profit_365days();
  467. if( curProfit )
  468. {
  469. str += " (";
  470. if( curProfit > 0 )
  471. str += "+";
  472. else
  473. str += "-";
  474. str += m.format( abs(curProfit), 4 ); // format type 4 - no thousand separators
  475. str += ")";
  476. }
  477. return str;
  478. }
  479. //------- End of function NationBase::cash_str -------//
  480. //------- Begin of function NationBase::food_str ------//
  481. //
  482. // Return a text string with the current nation treasure and profit
  483. // in the past 30 days.
  484. //
  485. char* NationBase::food_str()
  486. {
  487. static String str;
  488. if( food >= 0 )
  489. {
  490. str = m.format( (int)food, 4 ); // format type 4 - no thousand separators
  491. }
  492. else
  493. {
  494. str = "-";
  495. str += m.format( (int)-food, 4 ); // format type 4 - no thousand separators
  496. }
  497. //--------------------------------------//
  498. int foodChange = (int) food_change_365days();
  499. if( foodChange )
  500. {
  501. str += " (";
  502. if( foodChange > 0 )
  503. str += "+";
  504. else
  505. str += "-";
  506. str += m.format( abs(foodChange), 4 ); // format type 4 - no thousand separators
  507. str += ")";
  508. }
  509. return str;
  510. }
  511. //------- End of function NationBase::food_str -------//
  512. //---------- Begin of function NationBase::next_day --------//
  513. //
  514. // This function is called every day.
  515. //
  516. void NationBase::next_day()
  517. {
  518. //------ post is at war flag -------/
  519. if( is_at_war_today )
  520. last_war_date = info.game_date;
  521. is_at_war_yesterday = is_at_war_today;
  522. is_at_war_today = 0;
  523. //--- if the king is dead, and now looking for a successor ---//
  524. if( !king_unit_recno )
  525. {
  526. if( info.game_date%3 == nation_recno%3 ) // decrease 1 loyalty point every 3 days
  527. change_all_people_loyalty(-1);
  528. }
  529. //---------- debug code ------------//
  530. #ifdef DEBUG
  531. //---------- check king -----------//
  532. if( king_unit_recno )
  533. {
  534. Unit* unitPtr = unit_array[king_unit_recno];
  535. err_when( unitPtr->rank_id != RANK_KING );
  536. err_when( unitPtr->nation_recno != nation_recno );
  537. }
  538. //---------- check relation -----------//
  539. err_when( get_relation_status(nation_recno) != NATION_ALLIANCE ); // relation to own nation must be alliance
  540. #endif
  541. //------ check if this nation has won the game -----//
  542. check_win();
  543. //-- if the player still hasn't selected a unit to succeed the died king, declare defeated if the all units are killed --//
  544. if( !king_unit_recno )
  545. check_lose();
  546. //---------- debug code --------------//
  547. /*
  548. #ifdef DEBUG
  549. int totalHumanCount=0;
  550. for( int i=unit_array.size() ; i>0 ; i-- )
  551. {
  552. Unit* unitPtr = (Unit*) unit_array.get_ptr(i);
  553. if( unitPtr &&
  554. unitPtr->nation_recno == nation_recno &&
  555. unitPtr->race_id &&
  556. unitPtr->rank_id != RANK_KING )
  557. {
  558. totalHumanCount++;
  559. }
  560. }
  561. for( i=firm_array.size() ; i>0 ; i-- )
  562. {
  563. if( firm_array.is_deleted(i) )
  564. continue;
  565. Firm* firmPtr = firm_array[i];
  566. if( firmPtr->nation_recno != nation_recno )
  567. continue;
  568. if( firmPtr->firm_id == FIRM_CAMP ||
  569. firmPtr->firm_id == FIRM_BASE )
  570. {
  571. totalHumanCount += firmPtr->worker_count;
  572. }
  573. }
  574. err_when( total_human_count != totalHumanCount );
  575. #endif
  576. */
  577. }
  578. //----------- End of function NationBase::next_day ---------//
  579. //---------- Begin of function NationBase::next_month --------//
  580. //
  581. // This function is called every month.
  582. //
  583. void NationBase::next_month()
  584. {
  585. //--------------------------------------------------//
  586. // When the two nations, whose relationship is Tense,
  587. // do not have new conflicts for 3 years, their
  588. // relationship automatically becomes Neutral.
  589. //--------------------------------------------------//
  590. NationRelation* nationRelation;
  591. for( int i=1 ; i<=nation_array.size() ; i++ )
  592. {
  593. if( nation_array.is_deleted(i) )
  594. continue;
  595. nationRelation = get_relation(i);
  596. if( nationRelation->status == NATION_TENSE &&
  597. info.game_date >= nationRelation->last_change_status_date + 365*3 )
  598. {
  599. set_relation_status(i, NATION_NEUTRAL);
  600. }
  601. //--- update good_relation_duration_rating ---//
  602. else if( nationRelation->status == NATION_FRIENDLY )
  603. nationRelation->good_relation_duration_rating += (float) 0.2; // this is the monthly increase
  604. else if( nationRelation->status == NATION_ALLIANCE )
  605. nationRelation->good_relation_duration_rating += (float) 0.4;
  606. }
  607. //----- increase reputation gradually -----//
  608. if( reputation < 100 )
  609. change_reputation((float)0.5);
  610. }
  611. //---------- End of function NationBase::next_month --------//
  612. //---------- Begin of function NationBase::next_year --------//
  613. //
  614. // This function is called every year
  615. //
  616. void NationBase::next_year()
  617. {
  618. //------ post financial data --------//
  619. last_year_income = cur_year_income;
  620. cur_year_income = (float) 0;
  621. last_year_expense = cur_year_expense;
  622. cur_year_expense = (float) 0;
  623. last_year_fixed_income = cur_year_fixed_income;
  624. cur_year_fixed_income = (float) 0;
  625. last_year_fixed_expense = cur_year_fixed_expense;
  626. cur_year_fixed_expense = (float) 0;
  627. last_year_profit = cur_year_profit;
  628. cur_year_profit = (float) 0;
  629. last_year_cheat = cur_year_cheat;
  630. cur_year_cheat = (float) 0;
  631. //------ post income & expense breakdown ------//
  632. int i;
  633. for( i=0 ; i<INCOME_TYPE_COUNT ; i++ )
  634. {
  635. last_year_income_array[i] = cur_year_income_array[i];
  636. cur_year_income_array[i] = (float) 0;
  637. }
  638. for( i=0 ; i<EXPENSE_TYPE_COUNT ; i++ )
  639. {
  640. last_year_expense_array[i] = cur_year_expense_array[i];
  641. cur_year_expense_array[i] = (float) 0;
  642. }
  643. //------ post good change data ------//
  644. last_year_food_in = cur_year_food_in;
  645. cur_year_food_in = (float) 0;
  646. last_year_food_out = cur_year_food_out;
  647. cur_year_food_out = (float) 0;
  648. last_year_food_change = cur_year_food_change;
  649. cur_year_food_change = (float) 0;
  650. //---------- post imports ----------//
  651. NationRelation* nationRelation = relation_array;
  652. for( i=0; i<MAX_NATION ; i++, nationRelation++ )
  653. {
  654. for( int j=0 ; j<IMPORT_TYPE_COUNT ; j++ )
  655. {
  656. nationRelation->last_year_import[j] = nationRelation->cur_year_import[j];
  657. nationRelation->cur_year_import[j] = (float) 0;
  658. }
  659. }
  660. //--------- post reputation ----------//
  661. last_year_reputation_change = cur_year_reputation_change;
  662. cur_year_reputation_change = (float) 0;
  663. }
  664. //---------- End of function NationBase::next_year --------//
  665. //---------- Begin of function NationBase::add_income --------//
  666. //
  667. // <int> incomeType - the income type
  668. // <float> incomeAmt - the amount of the income.
  669. // [int] fixedIncome - whether this is a fixed income, or
  670. // a variable income. (default: 0)
  671. //
  672. void NationBase::add_income(int incomeType, float incomeAmt, int fixedIncome)
  673. {
  674. err_when( incomeType < 0 || incomeType >= INCOME_TYPE_COUNT );
  675. cash += incomeAmt;
  676. cur_year_income_array[incomeType] += incomeAmt;
  677. cur_year_income += incomeAmt;
  678. cur_year_profit += incomeAmt;
  679. if( fixedIncome )
  680. cur_year_fixed_income += incomeAmt;
  681. }
  682. //---------- End of function NationBase::add_income --------//
  683. //---------- Begin of function NationBase::add_expense --------//
  684. //
  685. // <int> expenseType - the expense type
  686. // <float> incomeAmt - the amount of the income.
  687. // <int> fixedExpense - whether this is a fixed expense, or
  688. // a variable income. (default: 0)
  689. //
  690. void NationBase::add_expense(int expenseType, float expenseAmt, int fixedExpense)
  691. {
  692. err_when( expenseType < 0 || expenseType >= EXPENSE_TYPE_COUNT );
  693. cash -= expenseAmt;
  694. cur_year_expense_array[expenseType] += expenseAmt;
  695. cur_year_expense += expenseAmt;
  696. cur_year_profit -= expenseAmt;
  697. if( fixedExpense )
  698. cur_year_fixed_expense += expenseAmt;
  699. }
  700. //---------- End of function NationBase::add_expense --------//
  701. //---------- Begin of function NationBase::add_cheat --------//
  702. //
  703. // <float> cheatAmount - the cheating amount.
  704. //
  705. void NationBase::add_cheat(float cheatAmount)
  706. {
  707. if( sys.testing_session || nation_type == NATION_OWN )
  708. {
  709. add_income(INCOME_CHEAT, cheatAmount);
  710. }
  711. else // cheat less obviously, randomly add to one of the account at a random amount //
  712. {
  713. add_income( m.random(INCOME_TYPE_COUNT-1)+1, cheatAmount );
  714. cur_year_cheat += cheatAmount;
  715. }
  716. }
  717. //---------- End of function NationBase::add_cheat --------//
  718. //---------- Begin of function NationBase::import_goods --------//
  719. //
  720. // This function is called when the current nation imports
  721. // goods from a specific nation.
  722. //
  723. // <int> importType - type of goods imported.
  724. //
  725. // <int> importNationRecno - recno of the nation from which this
  726. // nation imports.
  727. //
  728. // <float> importAmt - the import amount
  729. //
  730. void NationBase::import_goods(int importType, int importNationRecno, float importAmt)
  731. {
  732. if( importNationRecno == nation_recno )
  733. return;
  734. NationRelation* nationRelation = get_relation(importNationRecno);
  735. nationRelation->cur_year_import[importType] += importAmt;
  736. nationRelation->cur_year_import[IMPORT_TOTAL] += importAmt;
  737. add_expense(EXPENSE_IMPORTS, importAmt, 1);
  738. nation_array[importNationRecno]->add_income(INCOME_EXPORTS, importAmt, 1);
  739. }
  740. //---------- End of function NationBase::import_goods --------//
  741. //---------- Begin of function NationBase::add_food --------//
  742. //
  743. // <float> foodToAdd - quantity of food to be added
  744. //
  745. void NationBase::add_food(float foodToAdd)
  746. {
  747. food += foodToAdd;
  748. cur_year_food_in += foodToAdd;
  749. cur_year_food_change += foodToAdd;
  750. }
  751. //----------- End of function NationBase::add_food ---------//
  752. //---------- Begin of function NationBase::consume_food --------//
  753. //
  754. // <float> foodConsumed - quantity of food consumed
  755. //
  756. void NationBase::consume_food(float foodConsumed)
  757. {
  758. food -= foodConsumed;
  759. cur_year_food_out += foodConsumed;
  760. cur_year_food_change -= foodConsumed;
  761. }
  762. //----------- End of function NationBase::consume_food ---------//
  763. //---------- Begin of function NationBase::change_reputation --------//
  764. //
  765. // <float> changeLevel - level of reputation to be changed.
  766. //
  767. void NationBase::change_reputation(float changeLevel)
  768. {
  769. //--- reputation increase more slowly when it is close to 100 ----//
  770. if( changeLevel > 0 && reputation > 0 )
  771. changeLevel = changeLevel * (150-reputation) / 150;
  772. //-----------------------------------------------//
  773. reputation += changeLevel;
  774. if( reputation > 100 )
  775. reputation = (float) 100;
  776. if( reputation < -100 )
  777. reputation = (float) -100;
  778. //------ update cur_year_reputation_change ------//
  779. cur_year_reputation_change += changeLevel;
  780. }
  781. //---------- End of function NationBase::change_reputation --------//
  782. //---------- Begin of function NationBase::change_ai_relation_level --------//
  783. //
  784. // Change this AI nation's subjectively relation levels towards the others,
  785. // the opposite nation's relation level is not the same as this.
  786. //
  787. // ai_relation_level is for AI only and will only be reviewed by AI functions.
  788. //
  789. // <short> nationRecno - the nation recno of the relation
  790. // <int> levelChange - the amount of change to the relation level
  791. //
  792. void NationBase::change_ai_relation_level(short nationRecno, int levelChange)
  793. {
  794. NationRelation* nationRelation = get_relation(nationRecno);
  795. int newLevel = nationRelation->ai_relation_level + levelChange;
  796. newLevel = min(newLevel, 100);
  797. newLevel = max(newLevel, 0 );
  798. nationRelation->ai_relation_level = newLevel;
  799. }
  800. //----------- End of function NationBase::change_ai_relation_level -----------//
  801. //---------- Begin of function NationBase::set_relation_status --------//
  802. //
  803. // <short> nationRecno - the nation recno of the relation
  804. // <char> newStatus - the new relationship status
  805. // [char] recursiveCall - whether this is a recursive call from itself
  806. // (default: 0)
  807. //
  808. void NationBase::set_relation_status(short nationRecno, char newStatus, char recursiveCall)
  809. {
  810. if( nationRecno == nation_recno ) // cannot set relation to itself
  811. return;
  812. NationRelation* nationRelation = get_relation(nationRecno);
  813. //--------- debug code --------// BUGHERE
  814. /*
  815. #ifdef DEBUG
  816. if( nation_array[nationRecno]->is_ai() && is_ai() ) // AI must terminate the treaty first before declaring war
  817. {
  818. err_when( nationRelation->status >= NATION_FRIENDLY &&
  819. newStatus == NATION_HOSTILE );
  820. }
  821. #endif
  822. */
  823. //-------------------------------------------------//
  824. //
  825. // When two nations agree to a cease-fire, there may
  826. // still be some bullets on their ways, and those
  827. // will set the status back to War status, so we need
  828. // the following code to handle this case.
  829. //
  830. //-------------------------------------------------//
  831. if( !recursiveCall &&
  832. nationRelation->status == NATION_TENSE &&
  833. newStatus == NATION_HOSTILE &&
  834. info.game_date < nationRelation->last_change_status_date + 5 ) // 5 days after the cease-fire, the nation will remain cease-fire
  835. {
  836. return;
  837. }
  838. //-------------------------------------------------//
  839. //
  840. // If the nation cease fire or form a friendly/alliance
  841. // treaty with a nation. And this nation current
  842. // has plan to attack that nation, then cancel the plan.
  843. //
  844. //-------------------------------------------------//
  845. if( is_ai() )
  846. {
  847. if( newStatus==NATION_TENSE || // cease fire
  848. newStatus>=NATION_FRIENDLY ) // new friendly/alliance treaty
  849. {
  850. if( ((Nation*)this)->ai_attack_target_nation_recno == nationRecno )
  851. ((Nation*)this)->reset_ai_attack_target();
  852. }
  853. }
  854. //------------------------------------------------//
  855. relation_status_array[nationRecno-1] = newStatus;
  856. nationRelation->status = newStatus;
  857. nationRelation->last_change_status_date = info.game_date;
  858. int newRelationLevel = newStatus * RELATION_LEVEL_PER_STATUS;
  859. if( newRelationLevel < nationRelation->ai_relation_level ) // only set it when the new value is lower than the current value
  860. nationRelation->ai_relation_level = newRelationLevel;
  861. set_relation_passable(nationRecno, NATION_FRIENDLY);
  862. //---------- set should_attack -------//
  863. if( newStatus==NATION_ALLIANCE || newStatus==NATION_FRIENDLY ||
  864. newStatus==NATION_TENSE )
  865. {
  866. set_relation_should_attack(nationRecno, 0, COMMAND_AUTO);
  867. }
  868. else if( newStatus==NATION_HOSTILE )
  869. {
  870. set_relation_should_attack(nationRecno, 1, COMMAND_AUTO);
  871. }
  872. //----- share the nation contact with each other -----//
  873. /*
  874. // these segment code will cause multiplayer sync problem
  875. if( newStatus == NATION_ALLIANCE )
  876. {
  877. Nation* withNation = nation_array[nationRecno];
  878. for( i=nation_array.size() ; i>0 ; i-- )
  879. {
  880. if( i==nation_recno || i==nationRecno )
  881. continue;
  882. if( nation_array.is_deleted(i) )
  883. continue;
  884. //-- if we have contact with this nation and our ally doesn't, share the contact with it --//
  885. if( get_relation(i)->has_contact &&
  886. withNation->get_relation(i)->has_contact==0 )
  887. {
  888. withNation->establish_contact(i);
  889. }
  890. }
  891. }
  892. */
  893. //--- if this is a call from a client function, not a recursive call ---//
  894. if( !recursiveCall )
  895. {
  896. nation_array[nationRecno]->set_relation_status(nation_recno, newStatus, 1);
  897. //-- auto terminate their trade treaty if two nations go into a war --//
  898. if( newStatus == NATION_HOSTILE )
  899. set_trade_treaty(nationRecno, 0);
  900. }
  901. }
  902. //----------- End of function NationBase::set_relation_status -----------//
  903. //---------- Begin of function NationBase::get_relation_status --------//
  904. char NationBase::get_relation_status(short nationRecno)
  905. {
  906. return relation_status_array[nationRecno-1];
  907. }
  908. //----------- End of function NationBase::get_relation_status -----------//
  909. //---------- Begin of function NationBase::set_relation_passable --------//
  910. void NationBase::set_relation_passable(short nationRecno, char status)
  911. {
  912. relation_passable_array[nationRecno-1] = (relation_status_array[nationRecno-1] >= status);
  913. }
  914. //----------- End of function NationBase::set_relation_passable -----------//
  915. //---------- Begin of function NationBase::get_relation_passable --------//
  916. char NationBase::get_relation_passable(short nationRecno)
  917. {
  918. return relation_passable_array[nationRecno-1];
  919. }
  920. //----------- End of function NationBase::get_relation_passable -----------//
  921. #ifdef DEBUG
  922. //---------- Begin of function NationBase::get_relation --------//
  923. //
  924. NationRelation* NationBase::get_relation(int nationRecno)
  925. {
  926. if( nationRecno<1 || nationRecno>MAX_NATION )
  927. err.run( "NationBase::get_relation()" );
  928. return relation_array+nationRecno-1;
  929. }
  930. //---------- End of function NationBase::get_relation --------//
  931. #endif
  932. //---------- Begin of function NationBase::set_relation_should_attack --------//
  933. void NationBase::set_relation_should_attack(short nationRecno, char newValue, char remoteAction)
  934. {
  935. if( !remoteAction && remote.is_enable() )
  936. {
  937. short *shortPtr = (short *) remote.new_send_queue_msg(MSG_NATION_SET_SHOULD_ATTACK, 3*sizeof(short));
  938. *shortPtr = nation_recno;
  939. shortPtr[1] = nationRecno;
  940. shortPtr[2] = newValue;
  941. }
  942. else
  943. {
  944. relation_should_attack_array[nationRecno-1] = newValue;
  945. get_relation(nationRecno)->should_attack = newValue;
  946. }
  947. }
  948. //---------- End of function NationBase::set_relation_should_attack --------//
  949. //---------- Begin of function NationBase::get_relation_should_attack --------//
  950. char NationBase::get_relation_should_attack(short nationRecno)
  951. {
  952. // ###### begin Gilbert 3/9 #######//
  953. // always can attack independent unit
  954. return nationRecno == 0 || relation_should_attack_array[nationRecno-1];
  955. // ###### end Gilbert 3/9 #######//
  956. }
  957. //---------- End of function NationBase::get_relation_should_attack --------//
  958. //------- Begin of function NationBase::form_friendly_treaty ------//
  959. //
  960. // <int> nationRecno - recno of the nation with which this nation
  961. // will form treaty.
  962. //
  963. void NationBase::form_friendly_treaty(int nationRecno)
  964. {
  965. err_when( nationRecno == nation_recno );
  966. err_when( nation_array.is_deleted(nationRecno) );
  967. set_relation_status(nationRecno, NATION_FRIENDLY);
  968. }
  969. //------- End of function NationBase::form_friendly_treaty -------//
  970. //------- Begin of function NationBase::form_alliance_treaty ------//
  971. //
  972. // <int> nationRecno - recno of the nation with which this nation
  973. // will form treaty.
  974. //
  975. void NationBase::form_alliance_treaty(int nationRecno)
  976. {
  977. err_when( nationRecno == nation_recno );
  978. err_when( nation_array.is_deleted(nationRecno) );
  979. set_relation_status(nationRecno, NATION_ALLIANCE);
  980. //--- allied nations are oblied to trade with each other ---//
  981. set_trade_treaty(nationRecno, 1);
  982. //------ set is_allied_with_player -------//
  983. if( nationRecno == nation_array.player_recno )
  984. is_allied_with_player = 1;
  985. if( nation_recno == nation_array.player_recno )
  986. nation_array[nationRecno]->is_allied_with_player = 1;
  987. }
  988. //------- End of function NationBase::form_alliance_treaty -------//
  989. //------- Begin of function NationBase::end_treaty ------//
  990. //
  991. // <int> withNationRecno - recno of the nation which ends treaty
  992. // with this nation. If it's an alliance treaty,
  993. // allied nations with break treaty with
  994. // this nation.
  995. //
  996. // <int> newStatus - the new status after breaking the treaty.
  997. //
  998. void NationBase::end_treaty(int withNationRecno,int newStatus)
  999. {
  1000. //----- decrease reputation when terminating a treaty -----//
  1001. Nation* withNation = nation_array[withNationRecno];
  1002. if( withNation->reputation > 0 )
  1003. {
  1004. int curStatus = get_relation_status(withNationRecno);
  1005. if( curStatus == TALK_END_FRIENDLY_TREATY )
  1006. change_reputation( -withNation->reputation * 10 / 100 );
  1007. else
  1008. change_reputation( -withNation->reputation * 20 / 100 );
  1009. }
  1010. //------- reset good_relation_duration_rating -----//
  1011. if( newStatus <= NATION_NEUTRAL )
  1012. {
  1013. get_relation(withNationRecno)->good_relation_duration_rating = (float) 0;
  1014. withNation->get_relation(nation_recno)->good_relation_duration_rating = (float) 0;
  1015. }
  1016. //------- set new relation status --------//
  1017. set_relation_status(withNationRecno, newStatus);
  1018. //------ set is_allied_with_player -------//
  1019. if( withNationRecno == nation_array.player_recno )
  1020. is_allied_with_player = 0;
  1021. if( nation_recno == nation_array.player_recno )
  1022. nation_array[withNationRecno]->is_allied_with_player = 0;
  1023. }
  1024. //------- End of function NationBase::end_treaty -------//
  1025. //------- Begin of function NationBase::set_trade_treaty ------//
  1026. //
  1027. // <int> nationRecno - recno of the nation to change the trade allow flag
  1028. //
  1029. void NationBase::set_trade_treaty(int nationRecno, char treatyFlag)
  1030. {
  1031. err_when( nation_recno==nationRecno ); // cannot set trade treaty with oneself
  1032. get_relation(nationRecno)->trade_treaty = treatyFlag;
  1033. nation_array[nationRecno]->get_relation(nation_recno)->trade_treaty = treatyFlag;
  1034. }
  1035. //------- End of function NationBase::set_trade_treaty -------//
  1036. //------- Begin of function NationBase::establish_contact ------//
  1037. //
  1038. // <int> nationRecno - recno of the nation to establish contact with
  1039. //
  1040. void NationBase::establish_contact(int nationRecno)
  1041. {
  1042. get_relation(nationRecno)->has_contact = 1;
  1043. nation_array[nationRecno]->get_relation(nation_recno)->has_contact = 1;
  1044. }
  1045. //------- End of function NationBase::establish_contact -------//
  1046. //------- Begin of function NationBase::being_attacked ------//
  1047. //
  1048. // <int> attackNationRecno - recno of the nation that does the attack.
  1049. //
  1050. void NationBase::being_attacked(int attackNationRecno)
  1051. {
  1052. if( nation_array.is_deleted(attackNationRecno) || attackNationRecno==nation_recno )
  1053. return;
  1054. //--- if it is an accidential attack (e.g. bullets attack with spreading damages) ---//
  1055. Nation* attackNation = nation_array[attackNationRecno];
  1056. if( attackNation->get_relation(nation_recno)->should_attack==0 )
  1057. return;
  1058. //--- check if there a treaty between these two nations ---//
  1059. NationRelation* nationRelation = get_relation(attackNationRecno);
  1060. if( nationRelation->status != NATION_HOSTILE )
  1061. {
  1062. //--- if this nation (the one being attacked) has a higher than 0 reputation, the attacker's reputation will decrease ---//
  1063. if( reputation > 0 )
  1064. attackNation->change_reputation( -reputation * 40 / 100 );
  1065. nationRelation->started_war_on_us_count++; // how many times this nation has started a war with us, the more the times the worse this nation is.
  1066. if( nationRelation->status == NATION_ALLIANCE ||
  1067. nationRelation->status == NATION_FRIENDLY )
  1068. {
  1069. attackNation->end_treaty(nation_recno, NATION_HOSTILE); // the attacking nation abruptly terminates the treaty with us, not we terminate the treaty with them, so attackNation->end_treaty() should be called instead of end_treaty()
  1070. }
  1071. else
  1072. {
  1073. set_relation_status(attackNationRecno, NATION_HOSTILE);
  1074. }
  1075. }
  1076. //---- reset the inter-national peace days counter ----//
  1077. nation_array.nation_peace_days = 0;
  1078. }
  1079. //------- End of function NationBase::being_attacked -------//
  1080. //------- Begin of function NationBase::disp_nation_color ------//
  1081. //
  1082. // Display the color of the nation in a rectangular box.
  1083. //
  1084. void NationBase::disp_nation_color(int x, int y)
  1085. {
  1086. vga.active_buf->bar( x, y-2, x+12, y+10, nation_color );
  1087. vga.active_buf->rect( x, y-2, x+12, y+10, 1, nation_color+2 );
  1088. }
  1089. //------- End of function NationBase::disp_nation_color -------//
  1090. //------- Begin of function NationBase::trade_rating ------//
  1091. //
  1092. // Return a rating from 0 to 100 telling the significance of
  1093. // trading with the specific nation in this nation's regard.
  1094. //
  1095. int NationBase::trade_rating(int nationRecno)
  1096. {
  1097. // use an absolute value 5000 as the divider.
  1098. int tradeRating1 = 100 * (int) total_year_trade(nationRecno) / 5000;
  1099. int tradeRating2 = 50 * (int) nation_array[nationRecno]->get_relation(nation_recno)->last_year_import[IMPORT_TOTAL] / (int) (last_year_income+1) +
  1100. 50 * (int) get_relation(nationRecno)->last_year_import[IMPORT_TOTAL] / (int) (last_year_expense+1);
  1101. return max(tradeRating1, tradeRating2);
  1102. }
  1103. //------- End of function NationBase::trade_rating -------//
  1104. //------- Begin of function NationBase::revealed_by_phoenix ------//
  1105. //
  1106. // Whether the area is revealed by phoenix of the nation or not.
  1107. //
  1108. // <int> xLoc, yLoc - the location
  1109. //
  1110. int NationBase::revealed_by_phoenix(int xLoc, int yLoc)
  1111. {
  1112. Unit* unitPtr;
  1113. int effectiveRange = unit_res[UNIT_PHOENIX]->visual_range;
  1114. for( int i=unit_array.size() ; i>0 ; i-- )
  1115. {
  1116. if( unit_array.is_deleted(i) )
  1117. continue;
  1118. unitPtr = unit_array[i];
  1119. if( unitPtr->unit_id == UNIT_PHOENIX &&
  1120. unitPtr->nation_recno == nation_recno )
  1121. {
  1122. if( m.points_distance( xLoc, yLoc,
  1123. unitPtr->next_x_loc(), unitPtr->next_y_loc() ) <= effectiveRange )
  1124. {
  1125. return 1;
  1126. }
  1127. }
  1128. }
  1129. return 0;
  1130. }
  1131. //------- End of function NationBase::revealed_by_phoenix -------//
  1132. //------- Begin of function NationBase::total_tech_level -------//
  1133. //
  1134. // The sum of the tech levels of weapons that this nation possesses.
  1135. //
  1136. // [int] unitClass - only calculate total tech levels of this
  1137. // unit class. (default: 0, any classes)
  1138. //
  1139. int NationBase::total_tech_level(int unitClass)
  1140. {
  1141. TechInfo* techInfo;
  1142. int techLevel, totalTechLevel=0;
  1143. for( int i=1 ; i<=tech_res.tech_count ; i++ )
  1144. {
  1145. techInfo = tech_res[i];
  1146. techLevel = techInfo->get_nation_tech_level(nation_recno);
  1147. if( techLevel > 0 )
  1148. {
  1149. if( !unitClass ||
  1150. (unit_res[techInfo->unit_id]->unit_class == unitClass) )
  1151. {
  1152. totalTechLevel += techLevel;
  1153. }
  1154. }
  1155. }
  1156. return totalTechLevel;
  1157. }
  1158. //-------- End of function NationBase::total_tech_level -------//
  1159. //---------- Begin of function NationBase::civilian_killed --------//
  1160. //
  1161. // This function is called when civilian units are killed and this
  1162. // nation either killed the civilian units or this nation's civilian
  1163. // units are killed.
  1164. //
  1165. // <int> civilianRaceId - the race id. of the civilian unit killed
  1166. // 0 - all races, when a Caravan is killed, 0 will
  1167. // be passed, the loyalty of all races will be decreased.
  1168. //
  1169. // <int> isAttacker - 1 if the nation is the offensive attacker.
  1170. // 0 if the nation that suffers the atttack.
  1171. //
  1172. void NationBase::civilian_killed(int civilianRaceId, int isAttacker)
  1173. {
  1174. if( isAttacker )
  1175. {
  1176. change_all_people_loyalty(-3, civilianRaceId);
  1177. if( civilianRaceId==0 ) // a caravan
  1178. change_reputation(-(float)10);
  1179. else
  1180. change_reputation(-(float)1);
  1181. }
  1182. else
  1183. {
  1184. change_all_people_loyalty(-1, civilianRaceId);
  1185. if( civilianRaceId==0 ) // a caravan
  1186. change_reputation(-(float)3);
  1187. else
  1188. change_reputation(-(float)0.3);
  1189. }
  1190. }
  1191. //----------- End of function NationBase::civilian_killed ---------//
  1192. //--------- Begin of function NationBase::succeed_king --------//
  1193. //
  1194. // Appoint a unit to succeed the king who has died.
  1195. //
  1196. // The loyalty of the people in the natino may change due
  1197. // to the succession.
  1198. //
  1199. void NationBase::succeed_king(int kingUnitRecno)
  1200. {
  1201. Unit* newKing = unit_array[kingUnitRecno];
  1202. err_when( newKing->skill.combat_level <= 0 );
  1203. int newKingLeadership=0;
  1204. if( newKing->skill.skill_id == SKILL_LEADING )
  1205. newKingLeadership = newKing->skill.skill_level;
  1206. newKingLeadership = max( 20, newKingLeadership ); // give the king a minimum level of leadership
  1207. //----- set the common loyalty change for all races ------//
  1208. int loyaltyChange=0;
  1209. if( newKingLeadership < king_leadership )
  1210. loyaltyChange = (newKingLeadership-king_leadership)/2;
  1211. if( newKing->rank_id != RANK_GENERAL )
  1212. loyaltyChange -= 20;
  1213. //---- update loyalty of units in this nation ----//
  1214. Unit* unitPtr;
  1215. int i;
  1216. for( i=unit_array.size() ; i>0 ; i-- )
  1217. {
  1218. if( unit_array.is_deleted(i) )
  1219. continue;
  1220. if( i==king_unit_recno || i==kingUnitRecno )
  1221. continue;
  1222. unitPtr = unit_array[i];
  1223. if( unitPtr->nation_recno != nation_recno )
  1224. continue;
  1225. //--------- update loyalty change ----------//
  1226. unitPtr->change_loyalty( loyaltyChange +
  1227. succeed_king_loyalty_change(unitPtr->race_id, newKing->race_id, race_id) );
  1228. }
  1229. //---- update loyalty of units in camps ----//
  1230. Firm* firmPtr;
  1231. for( i=firm_array.size() ; i>0 ; i-- )
  1232. {
  1233. if( firm_array.is_deleted(i) )
  1234. continue;
  1235. firmPtr = firm_array[i];
  1236. if( firmPtr->nation_recno != nation_recno )
  1237. continue;
  1238. //------ process military camps and seat of power -------//
  1239. if( firmPtr->firm_id == FIRM_CAMP || firmPtr->firm_id == FIRM_BASE )
  1240. {
  1241. Worker* workerPtr = firmPtr->worker_array;
  1242. for(int j=firmPtr->worker_count-1 ; j>=0 ; j--, workerPtr++ )
  1243. {
  1244. //--------- update loyalty change ----------//
  1245. workerPtr->change_loyalty( loyaltyChange +
  1246. succeed_king_loyalty_change(workerPtr->race_id, newKing->race_id, race_id ) );
  1247. }
  1248. }
  1249. }
  1250. //---- update loyalty of town people ----//
  1251. Town* townPtr;
  1252. for( i=town_array.size() ; i>0 ; i-- )
  1253. {
  1254. if( town_array.is_deleted(i) )
  1255. continue;
  1256. townPtr = town_array[i];
  1257. if( townPtr->nation_recno != nation_recno )
  1258. continue;
  1259. for(int raceId=1 ; raceId<=MAX_RACE ; raceId++ )
  1260. {
  1261. if( townPtr->race_pop_array[raceId-1]==0 )
  1262. continue;
  1263. //------ update loyalty now ------//
  1264. townPtr->change_loyalty(raceId, (float) loyaltyChange +
  1265. succeed_king_loyalty_change( raceId, newKing->race_id, race_id ) );
  1266. }
  1267. }
  1268. //------- add news --------//
  1269. news_array.new_king(nation_recno, kingUnitRecno);
  1270. //-------- set the new king now ------//
  1271. set_king(kingUnitRecno, 0); // 0-not the first king, it is a succession
  1272. //------ if the new king is a spy -------//
  1273. if( newKing->spy_recno )
  1274. {
  1275. Spy* spyPtr = spy_array[newKing->spy_recno];
  1276. if( newKing->true_nation_recno() == nation_recno ) // if this is your spy
  1277. spyPtr->drop_spy_identity();
  1278. else
  1279. spyPtr->think_become_king();
  1280. err_when( newKing->rank_id==RANK_KING && newKing->spy_recno ); // it can't still be a spy when it asscends as the king
  1281. }
  1282. }
  1283. //----------- End of function NationBase::succeed_king ---------//
  1284. //------ Begin of static function succeed_king_loyalty_change -----//
  1285. //
  1286. // Return the amount of loyalty should be changed.
  1287. //
  1288. static int succeed_king_loyalty_change(int thisRaceId, int newKingRaceId, int oldKingRaceId)
  1289. {
  1290. #define SAME_RACE_LOYALTY_INC 20
  1291. #define DIFFERENT_RACE_LOYALTY_DEC 30
  1292. //----- the races of the new and old kings are different ----//
  1293. if( newKingRaceId != oldKingRaceId )
  1294. {
  1295. //--- if this unit's race is the same as the new king ---//
  1296. if( thisRaceId == newKingRaceId )
  1297. return SAME_RACE_LOYALTY_INC;
  1298. //--- if this unit's race is the same as the old king ---//
  1299. else if( thisRaceId == oldKingRaceId )
  1300. return DIFFERENT_RACE_LOYALTY_DEC;
  1301. }
  1302. return 0;
  1303. }
  1304. //-------- End of static function succeed_king_loyalty_change ------//
  1305. //--------- Begin of function NationBase::has_people --------//
  1306. //
  1307. // Whether the nation has any people (but not counting the king).
  1308. // If no, then the nation is going to end.
  1309. //
  1310. int NationBase::has_people()
  1311. {
  1312. return all_population() > 0;
  1313. }
  1314. //----------- End of function NationBase::has_people ---------//
  1315. //--------- Begin of function NationBase::surrender --------//
  1316. //
  1317. // This nation surrenders.
  1318. //
  1319. // <int> toNationRecno - the recno of the nation this nation
  1320. // surrenders to.
  1321. //
  1322. void NationBase::surrender(int toNationRecno)
  1323. {
  1324. news_array.nation_surrender(nation_recno, toNationRecno);
  1325. //---- the king demote himself to General first ----//
  1326. if( king_unit_recno )
  1327. {
  1328. unit_array[king_unit_recno]->set_rank(RANK_GENERAL);
  1329. king_unit_recno = 0;
  1330. }
  1331. //------- if the player surrenders --------//
  1332. if( nation_recno==nation_array.player_recno )
  1333. game.game_end(0, 1, toNationRecno);
  1334. //--- hand over the entire nation to another nation ---//
  1335. hand_over_to(toNationRecno);
  1336. }
  1337. //----------- End of function NationBase::surrender ---------//
  1338. //--------- Begin of function NationBase::defeated --------//
  1339. //
  1340. // This nation is defeated.
  1341. //
  1342. void NationBase::defeated()
  1343. {
  1344. //---- if the defeated nation is the player's nation ----//
  1345. if( nation_recno == nation_array.player_recno )
  1346. {
  1347. game.game_end(0, 1); // the player lost the game
  1348. }
  1349. else // AI and remote players
  1350. {
  1351. news_array.nation_destroyed(nation_recno);
  1352. }
  1353. //---- delete this nation from nation_array ----//
  1354. nation_array.del_nation(nation_recno);
  1355. }
  1356. //----------- End of function NationBase::defeated ---------//
  1357. //------- Begin of function NationBase::change_all_people_loyalty ------//
  1358. //
  1359. // Change the loyalty of all the people in your nation.
  1360. //
  1361. // <int> loyaltyChange - degree of loyalty change
  1362. // [int] raceId - if this is given, then only people of this race
  1363. // will be affected. (default: 0)
  1364. //
  1365. void NationBase::change_all_people_loyalty(int loyaltyChange, int raceId)
  1366. {
  1367. //---- update loyalty of units in this nation ----//
  1368. Unit* unitPtr;
  1369. int i;
  1370. for( i=unit_array.size() ; i>0 ; i-- )
  1371. {
  1372. if( unit_array.is_deleted(i) )
  1373. continue;
  1374. if( i==king_unit_recno )
  1375. continue;
  1376. unitPtr = unit_array[i];
  1377. if( unitPtr->nation_recno != nation_recno )
  1378. continue;
  1379. //--------- update loyalty change ----------//
  1380. if( !raceId || unitPtr->race_id == raceId )
  1381. unitPtr->change_loyalty(loyaltyChange);
  1382. }
  1383. //---- update loyalty of units in camps ----//
  1384. Firm* firmPtr;
  1385. for( i=firm_array.size() ; i>0 ; i-- )
  1386. {
  1387. if( firm_array.is_deleted(i) )
  1388. continue;
  1389. firmPtr = firm_array[i];
  1390. if( firmPtr->nation_recno != nation_recno )
  1391. continue;
  1392. //------ process military camps and seat of power -------//
  1393. if( firmPtr->firm_id == FIRM_CAMP || firmPtr->firm_id == FIRM_BASE )
  1394. {
  1395. Worker* workerPtr = firmPtr->worker_array;
  1396. for(int j=firmPtr->worker_count-1 ; j>=0 ; j--, workerPtr++ )
  1397. {
  1398. if( !raceId || workerPtr->race_id == raceId )
  1399. workerPtr->change_loyalty(loyaltyChange);
  1400. }
  1401. }
  1402. }
  1403. //---- update loyalty of town people ----//
  1404. Town* townPtr;
  1405. for( i=town_array.size() ; i>0 ; i-- )
  1406. {
  1407. if( town_array.is_deleted(i) )
  1408. continue;
  1409. townPtr = town_array[i];
  1410. if( townPtr->nation_recno != nation_recno )
  1411. continue;
  1412. //--------------------------------------//
  1413. if( raceId ) // decrease loyalty of a specific race
  1414. {
  1415. if( townPtr->race_pop_array[raceId-1] > 0 )
  1416. townPtr->change_loyalty(raceId, (float) loyaltyChange);
  1417. }
  1418. else // decrease loyalty of all races
  1419. {
  1420. for(int j=0 ; j<MAX_RACE ; j++ )
  1421. {
  1422. if( townPtr->race_pop_array[j]==0 )
  1423. continue;
  1424. townPtr->change_loyalty(j+1, (float) loyaltyChange);
  1425. }
  1426. }
  1427. }
  1428. }
  1429. //------- End of function NationBase::change_all_people_loyalty -------//
  1430. //------- Begin of function NationBase::total_year_trade ------//
  1431. //
  1432. // Return the total trade (import + export) with the specific
  1433. // trade in the last year.
  1434. //
  1435. float NationBase::total_year_trade(int nationRecno)
  1436. {
  1437. return get_relation(nationRecno)->last_year_import[IMPORT_TOTAL] +
  1438. nation_array[nationRecno]->get_relation(nation_recno)->last_year_import[IMPORT_TOTAL];
  1439. }
  1440. //------- End of function NationBase::total_year_trade -------//
  1441. //---------- Begin of function NationBase::check_win --------//
  1442. //
  1443. // Check if the player has won the game.
  1444. //
  1445. void NationBase::check_win()
  1446. {
  1447. int hasWon = goal_destroy_nation_achieved() ||
  1448. goal_destroy_monster_achieved() ||
  1449. goal_population_achieved() ||
  1450. goal_economic_score_achieved() ||
  1451. goal_total_score_achieved();
  1452. if( !hasWon )
  1453. return;
  1454. //--------------------------------------//
  1455. game.game_end(nation_recno, 0); // if the player achieves the goal, the player wins, if one of the other kingdoms achieves the goal, it wins.
  1456. }
  1457. //----------- End of function NationBase::check_win ---------//
  1458. //---------- Begin of function NationBase::check_lose --------//
  1459. //
  1460. // Check if the player has lost the game.
  1461. //
  1462. // If the player still hasn't selected a unit to succeed the
  1463. // died king, declare defeated if the all units are killed.
  1464. //
  1465. void NationBase::check_lose()
  1466. {
  1467. //---- if the king of this nation is dead and it has no people left ----//
  1468. if( !king_unit_recno && !has_people() )
  1469. defeated();
  1470. }
  1471. //----------- End of function NationBase::check_lose ---------//
  1472. //---------- Begin of function NationBase::give_tribute --------//
  1473. //
  1474. // Give tribute or aid to a nation.
  1475. //
  1476. // <int> toNationRecno - give tribute to this nation
  1477. // <int> tributeAmt - the amount of the tribute
  1478. //
  1479. void NationBase::give_tribute(int toNationRecno, int tributeAmt)
  1480. {
  1481. Nation* toNation = nation_array[toNationRecno];
  1482. add_expense( EXPENSE_TRIBUTE, (float) tributeAmt );
  1483. toNation->add_income( INCOME_TRIBUTE, (float) tributeAmt );
  1484. NationRelation* nationRelation = get_relation(toNationRecno);
  1485. nationRelation->last_give_gift_date = info.game_date;
  1486. nationRelation->total_given_gift_amount += tributeAmt;
  1487. //---- set the last rejected date so it won't request or give again soon ----//
  1488. nationRelation->last_talk_reject_date_array[TALK_GIVE_AID-1] = 0;
  1489. nationRelation->last_talk_reject_date_array[TALK_DEMAND_AID-1] = 0;
  1490. nationRelation->last_talk_reject_date_array[TALK_GIVE_TRIBUTE-1] = 0;
  1491. nationRelation->last_talk_reject_date_array[TALK_DEMAND_TRIBUTE-1] = 0;
  1492. NationRelation* nationRelation2 = toNation->get_relation(nation_recno);
  1493. nationRelation2->last_talk_reject_date_array[TALK_GIVE_AID-1] = 0;
  1494. nationRelation2->last_talk_reject_date_array[TALK_DEMAND_AID-1] = 0;
  1495. nationRelation2->last_talk_reject_date_array[TALK_GIVE_TRIBUTE-1] = 0;
  1496. nationRelation2->last_talk_reject_date_array[TALK_DEMAND_TRIBUTE-1] = 0;
  1497. }
  1498. //----------- End of function NationBase::give_tribute ---------//
  1499. //---------- Begin of function NationBase::give_tech --------//
  1500. //
  1501. // Give tribute or aid to a nation.
  1502. //
  1503. // <int> toNationRecno - give tribute to this nation
  1504. // <int> techId - id. of the technology
  1505. // <int> techVersion - version of the technology
  1506. //
  1507. void NationBase::give_tech(int toNationRecno, int techId, int techVersion)
  1508. {
  1509. Nation* toNation = nation_array[toNationRecno];
  1510. int curVersion = tech_res[techId]->get_nation_tech_level(toNationRecno);
  1511. if( curVersion < techVersion )
  1512. tech_res[techId]->set_nation_tech_level( toNationRecno, techVersion );
  1513. NationRelation* nationRelation = get_relation(toNationRecno);
  1514. nationRelation->last_give_gift_date = info.game_date;
  1515. nationRelation->total_given_gift_amount += (techVersion-curVersion) * 500; // one version level is worth $500
  1516. //---- set the last rejected date so it won't request or give again soon ----//
  1517. nationRelation->last_talk_reject_date_array[TALK_GIVE_TECH-1] = 0;
  1518. nationRelation->last_talk_reject_date_array[TALK_DEMAND_TECH-1] = 0;
  1519. NationRelation* nationRelation2 = toNation->get_relation(nation_recno);
  1520. nationRelation2->last_talk_reject_date_array[TALK_GIVE_TECH-1] = 0;
  1521. nationRelation2->last_talk_reject_date_array[TALK_DEMAND_TECH-1] = 0;
  1522. }
  1523. //----------- End of function NationBase::give_tech ---------//
  1524. //----- Begin of function NationBase::base_town_count_in_region -----//
  1525. //
  1526. // Return the number of base towns in the given region.
  1527. //
  1528. int NationBase::base_town_count_in_region(int regionId)
  1529. {
  1530. // ###### patch begin Gilbert 16/3 #######//
  1531. // regionStatId may be zero
  1532. int regionStatId = region_array[regionId]->region_stat_id;
  1533. if( regionStatId )
  1534. {
  1535. return region_array.get_region_stat2(regionStatId)->
  1536. base_town_nation_count_array[nation_recno-1];
  1537. }
  1538. else if( region_array[regionId]->region_size < STD_TOWN_LOC_WIDTH*STD_TOWN_LOC_HEIGHT)
  1539. {
  1540. return 0; // not enough to build any town
  1541. }
  1542. else
  1543. {
  1544. int townCount = 0;
  1545. for( int townRecno = town_array.size(); townRecno > 0; --townRecno )
  1546. {
  1547. if( town_array.is_deleted(townRecno) )
  1548. continue;
  1549. Town *townPtr = town_array[townRecno];
  1550. if( townPtr->region_id == regionId && townPtr->nation_recno == nation_recno )
  1551. townCount++;
  1552. }
  1553. return townCount == 0;
  1554. }
  1555. // ###### patch end Gilbert 16/3 #######//
  1556. }
  1557. //------ End of function NationBase::base_town_count_in_region -----//
  1558. //----- Begin of function NationBase::peace_duration_str -----//
  1559. //
  1560. char* NationBase::peace_duration_str()
  1561. {
  1562. int peaceDays = peaceful_days();
  1563. int peaceYear = peaceDays / 365;
  1564. int peaceMonth = (peaceDays - peaceYear * 365) / 30;
  1565. static String str;
  1566. str = "";
  1567. if( peaceYear > 0 )
  1568. {
  1569. str += peaceYear;
  1570. str += translate.process( peaceYear>1 ? (char*)" years" : (char*)" year" );
  1571. str += translate.process( (char*)" and " );
  1572. }
  1573. str += peaceMonth;
  1574. str += translate.process( peaceMonth>1 ? (char*)" months" : (char*)" month" );
  1575. return str;
  1576. }
  1577. //------ End of function NationBase::peace_duration_str -----//
  1578. //----- Begin of function NationBase::true_income_365days -----//
  1579. //
  1580. // Return the total income of the nation, excluding cheats.
  1581. //
  1582. float NationBase::true_income_365days()
  1583. {
  1584. float curYearIncome=(float)0, lastYearIncome=(float)0;
  1585. for( int i=0 ; i<INCOME_TYPE_COUNT-1 ; i++ ) // -1 to exclude cheat
  1586. {
  1587. curYearIncome += cur_year_income_array[i];
  1588. lastYearIncome += last_year_income_array[i];
  1589. }
  1590. return lastYearIncome * (365-info.year_day) / 365 + curYearIncome;
  1591. }
  1592. //------ End of function NationBase::true_income_365days -----//
  1593. //----- Begin of function NationBase::update_nation_rating -----//
  1594. //
  1595. void NationBase::update_nation_rating()
  1596. {
  1597. population_rating = get_population_rating();
  1598. economic_rating = get_economic_rating();
  1599. overall_rating = get_overall_rating();
  1600. }
  1601. //------ End of function NationBase::update_nation_rating -----//
  1602. //----- Begin of function NationBase::get_population_rating -----//
  1603. //
  1604. int NationBase::get_population_rating()
  1605. {
  1606. return all_population();
  1607. }
  1608. //------ End of function NationBase::get_population_rating -----//
  1609. //----- Begin of function NationBase::get_economic_rating -----//
  1610. //
  1611. int NationBase::get_economic_rating()
  1612. {
  1613. return (int) cash / 300 +
  1614. (int) true_income_365days()/2 +
  1615. (int) true_profit_365days();
  1616. }
  1617. //------ End of function NationBase::get_economic_rating -----//
  1618. //----- Begin of function NationBase::get_overall_rating -----//
  1619. //
  1620. int NationBase::get_overall_rating()
  1621. {
  1622. return 33*population_rating/500+
  1623. 33*military_rating/200+
  1624. 33*economic_rating/10000;
  1625. }
  1626. //------ End of function NationBase::get_overall_rating -----//
  1627. //----- Begin of function NationBase::population_rank_rating -----//
  1628. //
  1629. int NationBase::population_rank_rating()
  1630. {
  1631. if( nation_array.max_population_rating==0 )
  1632. return 0;
  1633. return 100 * population_rating / nation_array.max_population_rating;
  1634. }
  1635. //------ End of function NationBase::population_rank_rating -----//
  1636. //----- Begin of function NationBase::military_rank_rating -----//
  1637. //
  1638. int NationBase::military_rank_rating()
  1639. {
  1640. if( nation_array.max_military_rating==0 )
  1641. return 0;
  1642. return 100 * military_rating / nation_array.max_military_rating;
  1643. }
  1644. //------ End of function NationBase::military_rank_rating -----//
  1645. //----- Begin of function NationBase::economic_rank_rating -----//
  1646. //
  1647. int NationBase::economic_rank_rating()
  1648. {
  1649. if( nation_array.max_economic_rating==0 )
  1650. return 0;
  1651. return 100 * economic_rating / nation_array.max_economic_rating;
  1652. }
  1653. //------ End of function NationBase::economic_rank_rating -----//
  1654. //----- Begin of function NationBase::reputation_rank_rating -----//
  1655. //
  1656. int NationBase::reputation_rank_rating()
  1657. {
  1658. if( nation_array.max_reputation==0 )
  1659. return 0;
  1660. return 100 * (int) reputation / nation_array.max_reputation;
  1661. }
  1662. //------ End of function NationBase::reputation_rank_rating -----//
  1663. //----- Begin of function NationBase::kill_monster_rank_rating -----//
  1664. //
  1665. int NationBase::kill_monster_rank_rating()
  1666. {
  1667. if( nation_array.max_kill_monster_score==0 )
  1668. return 0;
  1669. if( config.monster_type == OPTION_MONSTER_NONE )
  1670. return 0;
  1671. return 100 * (int) kill_monster_score / nation_array.max_kill_monster_score;
  1672. }
  1673. //------ End of function NationBase::kill_monster_rank_rating -----//
  1674. //----- Begin of function NationBase::overall_rank_rating -----//
  1675. //
  1676. int NationBase::overall_rank_rating()
  1677. {
  1678. if( nation_array.max_overall_rating==0 )
  1679. return 0;
  1680. return 100 * overall_rating / nation_array.max_overall_rating;
  1681. }
  1682. //------ End of function NationBase::overall_rank_rating -----//
  1683. //------- Begin of function NationBase::goal_destroy_nation_achieved --------//
  1684. int NationBase::goal_destroy_nation_achieved()
  1685. {
  1686. return nation_array.nation_count==1;
  1687. }
  1688. //------- End of function NationBase::goal_destroy_nation_achieved --------//
  1689. //------- Begin of function NationBase::goal_destroy_monster_achieved --------//
  1690. int NationBase::goal_destroy_monster_achieved()
  1691. {
  1692. if( !config.goal_destroy_monster ) // this is not one of the required goals.
  1693. return 0;
  1694. if( config.monster_type == OPTION_MONSTER_NONE )
  1695. return 0;
  1696. //------- when all monsters have been killed -------//
  1697. if( firm_res[FIRM_MONSTER]->total_firm_count == 0 &&
  1698. unit_res.mobile_monster_count == 0 )
  1699. {
  1700. Nation* nationPtr;
  1701. float maxScore=(float)0;
  1702. for( int i=nation_array.size() ; i>0 ; i-- )
  1703. {
  1704. if( nation_array.is_deleted(i) )
  1705. continue;
  1706. nationPtr = nation_array[i];
  1707. if( nationPtr->kill_monster_score > maxScore )
  1708. maxScore = nationPtr->kill_monster_score;
  1709. }
  1710. //-- if this nation is the one that has destroyed most monsters, it wins, otherwise it loses --//
  1711. return maxScore == kill_monster_score;
  1712. }
  1713. return 0;
  1714. }
  1715. //------- End of function NationBase::goal_destroy_monster_achieved --------//
  1716. //------- Begin of function NationBase::goal_population_achieved --------//
  1717. int NationBase::goal_population_achieved()
  1718. {
  1719. if( !config.goal_population_flag ) // this is not one of the required goals.
  1720. return 0;
  1721. return all_population() >= config.goal_population;
  1722. }
  1723. //------- End of function NationBase::goal_population_achieved --------//
  1724. //------ Begin of function NationBase::goal_economic_score_achieved ------//
  1725. int NationBase::goal_economic_score_achieved()
  1726. {
  1727. if( !config.goal_economic_score_flag )
  1728. return 0;
  1729. info.set_rank_data(0); // 0-set all nations, not just those that have contact with us
  1730. return info.get_rank_score(3,nation_recno) >= config.goal_economic_score;
  1731. }
  1732. //------- End of function NationBase::goal_economic_score_achieved -------//
  1733. //------ Begin of function NationBase::goal_total_score_achieved -------//
  1734. int NationBase::goal_total_score_achieved()
  1735. {
  1736. if( !config.goal_total_score_flag )
  1737. return 0;
  1738. info.set_rank_data(0); // 0-set all nations, not just those that have contact with us
  1739. return info.get_total_score(nation_recno) >= config.goal_total_score;
  1740. }
  1741. //------- End of function NationBase::goal_total_score_achieved --------//
  1742. //----- Begin of function NationBase::set_auto_collect_tax_loyalty -----//
  1743. //
  1744. void NationBase::set_auto_collect_tax_loyalty(int loyaltyLevel)
  1745. {
  1746. auto_collect_tax_loyalty = loyaltyLevel;
  1747. if( loyaltyLevel && auto_grant_loyalty >= auto_collect_tax_loyalty )
  1748. {
  1749. auto_grant_loyalty = auto_collect_tax_loyalty-10;
  1750. }
  1751. }
  1752. //------ End of function NationBase::set_auto_collect_tax_loyalty -----//
  1753. //----- Begin of function NationBase::set_auto_grant_loyalty -----//
  1754. //
  1755. void NationBase::set_auto_grant_loyalty(int loyaltyLevel)
  1756. {
  1757. auto_grant_loyalty = loyaltyLevel;
  1758. if( loyaltyLevel && auto_grant_loyalty >= auto_collect_tax_loyalty )
  1759. {
  1760. auto_collect_tax_loyalty = auto_grant_loyalty+10;
  1761. if( auto_collect_tax_loyalty > 100 )
  1762. auto_collect_tax_loyalty = 0; // disable auto collect tax if it's over 100
  1763. }
  1764. }
  1765. //------ End of function NationBase::set_auto_grant_loyalty -----//
  1766. //----- Begin of function NationRelation::status_duration_str -----//
  1767. //
  1768. char* NationRelation::status_duration_str()
  1769. {
  1770. int statusDays = info.game_date - last_change_status_date;
  1771. int statusYear = statusDays / 365;
  1772. int statusMonth = (statusDays - statusYear * 365) / 30;
  1773. static String str;
  1774. str = "";
  1775. if( statusYear > 0 )
  1776. {
  1777. str += statusYear;
  1778. str += translate.process( statusYear>1 ? (char*)" years" : (char*)" year" );
  1779. str += translate.process( (char*)" and " );
  1780. }
  1781. str += statusMonth;
  1782. str += translate.process( statusMonth>1 ? (char*)" months" : (char*)" month" );
  1783. return str;
  1784. }
  1785. //------ End of function NationRelation::status_duration_str -----//