initial commit, lordsawar source, slightly modified
[lordsawar] / src / CreateScenarioRandomize.cpp
1 //  Copyright (C) 2008, 2009 Ben Asselstine
2 //
3 //  This program is free software; you can redistribute it and/or modify
4 //  it under the terms of the GNU General Public License as published by
5 //  the Free Software Foundation; either version 3 of the License, or
6 //  (at your option) any later version.
7 //
8 //  This program is distributed in the hope that it will be useful,
9 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
10 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 //  GNU Library General Public License for more details.
12 //
13 //  You should have received a copy of the GNU General Public License
14 //  along with this program; if not, write to the Free Software
15 //  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 
16 //  02110-1301, USA.
17
18 #include <sstream>
19 #include <iostream>
20 #include <fstream>
21 #include "ucompose.hpp"
22
23 #include "CreateScenarioRandomize.h"
24
25 #include "File.h"
26 #include "citylist.h"
27 #include "city.h"
28 #include "ruin.h"
29 #include "temple.h"
30 #include "signpost.h"
31 #include "armysetlist.h"
32 #include "playerlist.h"
33 #include "reward.h"
34
35 using namespace std;
36
37 #define debug(x) {cerr<<__FILE__<<": "<<__LINE__<<": "<<x<<endl<<flush;}
38 //#define debug(x)
39
40 CreateScenarioRandomize::CreateScenarioRandomize()
41 {
42     // Fill the namelists 
43     bool success = true;
44     
45     d_citynames = new NameList("citynames.xml", "city");
46     d_templenames = new NameList("templenames.xml", "temple");
47     d_ruinnames = new NameList("ruinnames.xml", "ruin");
48     d_signposts = new NameList("signposts.xml", "signpost");
49
50     if (!success)
51     {
52         std::cerr <<"CreateScenarioRandomize: Didn't succeed in reading object names. Aborting!\n";
53         exit(-1);
54     }
55 }
56
57 CreateScenarioRandomize::~CreateScenarioRandomize()
58 {
59     debug("CreateScenarioRandomize::~CreateScenarioRandomize")
60 }
61
62 std::string CreateScenarioRandomize::popRandomCityName()
63 {
64   std::string name = d_citynames->popRandomName().c_str();
65   if (name == "")
66     return City::getDefaultName();
67   return name;
68 }
69
70 void CreateScenarioRandomize::pushRandomCityName(std::string name)
71 {
72   d_citynames->push_back(name);
73 }
74
75 std::string CreateScenarioRandomize::popRandomRuinName()
76 {
77   std::string name = d_ruinnames->popRandomName().c_str();
78   if (name == "")
79     return Ruin::getDefaultName();
80   return name;
81 }
82
83 void CreateScenarioRandomize::pushRandomRuinName(std::string name)
84 {
85   d_ruinnames->push_back(name);
86 }
87
88 std::string CreateScenarioRandomize::popRandomTempleName()
89 {
90   std::string name = d_templenames->popRandomName().c_str();
91   if (name == "")
92     return Temple::getDefaultName();
93   return name;
94 }
95
96 void CreateScenarioRandomize::pushRandomTempleName(std::string name)
97 {
98   d_templenames->push_back(name);
99 }
100
101 std::string CreateScenarioRandomize::popRandomSignpost()
102 {
103   return d_signposts->popRandomName().c_str();
104 }
105
106 void CreateScenarioRandomize::pushRandomSignpost(std::string name)
107 {
108   d_signposts->push_back(name);
109 }
110
111 guint32 CreateScenarioRandomize::getRandomCityIncome(bool capital)
112 {
113   if (capital)
114     return 33 + (rand() % 8);
115   else
116     return 15 + (rand() % 12);
117 }
118
119 Army * CreateScenarioRandomize::getRandomRuinKeeper(Player *p)
120 {
121   Armysetlist *al = Armysetlist::getInstance();
122   const ArmyProto *a= al->getArmyset(p->getArmyset())->getRandomRuinKeeper();
123   if (a)
124     return (new Army(*a, p));
125
126   return NULL;
127 }
128
129 std::string CreateScenarioRandomize::getDynamicSignpost(Signpost *signpost)
130 {
131   char *dir = NULL;
132   int xdir, ydir;
133   Vector<int> signpostPos = signpost->getPos();
134   City *nearCity = Citylist::getInstance()->getNearestCity(signpostPos);
135   if (nearCity == NULL)
136     return "nowhere";
137
138   Vector<int> cityPos = nearCity->getPos();
139   xdir = cityPos.x - signpostPos.x;
140   ydir = cityPos.y - signpostPos.y;
141   if (xdir >= 1 && ydir >= 1)
142     dir = _("southeast");
143   else if (xdir >= 1 && ydir == 0)
144     dir = _("east");
145   else if (xdir >= 1 && ydir <= -1)
146     dir = _("northeast");
147   else if (xdir == 0 && ydir >= 1)
148     dir = _("south");
149   else if (xdir == 0 && ydir <= -1)
150     dir = _("north");
151   else if (xdir <= -1 && ydir >= 1)
152     dir = _("southwest");
153   else if (xdir <= -1 && ydir == 0)
154     dir = _("west");
155   else if (xdir <= -1 && ydir <= -1)
156     dir = _("northwest");
157   return String::ucompose("%1 lies to the %2", nearCity->getName(), dir);
158 }
159   
160 Reward *CreateScenarioRandomize::getNewRandomReward(bool hidden_ruins)
161 {
162   int max_reward_types = 5;
163   if (!hidden_ruins)
164     max_reward_types--;
165   int num = rand() % max_reward_types;
166   Reward *reward = 0;
167
168   switch (num)
169     {
170     case 0: //Gold
171       reward = new Reward_Gold(Reward_Gold::getRandomGoldPieces());
172       break;
173     case 1: //Item
174       reward = new Reward_Item(Reward_Item::getRandomItem());
175       break;
176     case 2: //Allies
177         {
178           const ArmyProto *a = Reward_Allies::randomArmyAlly();
179           if (a)
180             reward = new Reward_Allies 
181               (a, Reward_Allies::getRandomAmountOfAllies());
182           else
183             reward = new Reward_Gold(Reward_Gold::getRandomGoldPieces());
184         }
185       break;
186     case 3: //Map
187         {
188           int x, y, width, height;
189           Reward_Map::getRandomMap(&x, &y, &width, &height);
190           reward = new Reward_Map (Vector<int>(x, y), "", height, width);
191           reward->setName(reward->getDescription());
192         }
193       break;
194     case 4: //Hidden Ruin
195         {
196           Ruin *r = Reward_Ruin::getRandomHiddenRuin();
197           reward = new Reward_Ruin (r);
198           reward->setName(reward->getDescription());
199         }
200       break;
201     }
202       
203   if (reward)
204     reward->setName(reward->getDescription());
205   return reward;
206 }
207
208 int CreateScenarioRandomize::adjustBaseGold (int base_gold)
209 {
210   int gold = base_gold + ((rand() % 7) - 4);
211   if (gold < 0)
212     gold = 0;
213   return gold;
214 }
215
216 void CreateScenarioRandomize::getBaseGold (int difficulty, int *base_gold)
217 {
218   if (difficulty < 50)
219     *base_gold = 131;
220   else if (difficulty < 60)
221     *base_gold = 129;
222   else if (difficulty < 70)
223     *base_gold = 127;
224   else if (difficulty < 80)
225     *base_gold = 125;
226   else if (difficulty < 90)
227     *base_gold = 123;
228   else
229     *base_gold = 121;
230 }
231
232 std::string CreateScenarioRandomize::getPlayerName(Shield::Colour id)
233 {
234   std::string name = "";
235   switch (id)
236     {
237     case Shield::WHITE: 
238       name = _("The Sirians");
239       break;
240     case Shield::GREEN: 
241       name = _("Elvallie");
242       break;
243     case Shield::YELLOW: 
244       name = _("Storm Giants");
245       break;
246     case Shield::LIGHT_BLUE: 
247       name = _("The Selentines");
248       break;
249     case Shield::ORANGE: 
250       name = _("Grey Dwarves");
251       break;
252     case Shield::DARK_BLUE: 
253       name = _("Horse Lords");
254       break;
255     case Shield::RED:
256       name = _("Orcs of Kor");
257       break;
258     case Shield::BLACK:
259       name = _("Lord Bane");
260       break;
261     case Shield::NEUTRAL:
262       name = _("Neutrals");
263       break;
264     }
265   return name;
266 }