Add DefineDefaultResourceMaxAmounts() to define max value per resource.(default value is 0, so change it in lua).

Add "Storing" to UnitType to increase MaxResourceAmount

Patch from cybermind.
This commit is contained in:
joris 2012-02-17 15:57:11 +01:00
parent 5d4ddd2508
commit dc044a9c70
12 changed files with 198 additions and 58 deletions

View file

@ -628,7 +628,7 @@ static int MoveToDepot(CUnit &unit)
{
const ResourceInfo &resinfo = *unit.Type->ResInfo[unit.CurrentResource];
CUnit *goal = unit.CurrentOrder()->GetGoal();
CPlayer& player = *unit.Player;
Assert(goal);
switch (DoActionMove(unit)) { // reached end-point?
@ -637,7 +637,7 @@ static int MoveToDepot(CUnit &unit)
case PF_REACHED:
break;
default:
if (unit.Anim.Unbreakable || goal->IsVisibleAsGoal(*unit.Player)) {
if (unit.Anim.Unbreakable || goal->IsVisibleAsGoal(player)) {
return 0;
}
break;
@ -646,8 +646,8 @@ static int MoveToDepot(CUnit &unit)
//
// Target is dead, stop getting resources.
//
if (!goal->IsVisibleAsGoal(*unit.Player)) {
DebugPrint("%d: Worker %d report: Destroyed depot\n" _C_ unit.Player->Index _C_ unit.Slot);
if (!goal->IsVisibleAsGoal(player)) {
DebugPrint("%d: Worker %d report: Destroyed depot\n" _C_ player.Index _C_ unit.Slot);
unit.CurrentOrder()->ClearGoal();
@ -655,10 +655,10 @@ static int MoveToDepot(CUnit &unit)
if (depot) {
UnitGotoGoal(unit, depot, SUB_MOVE_TO_DEPOT);
DebugPrint("%d: Worker %d report: Going to new deposit.\n" _C_ unit.Player->Index _C_ unit.Slot);
DebugPrint("%d: Worker %d report: Going to new deposit.\n" _C_ player.Index _C_ unit.Slot);
} else {
DebugPrint("%d: Worker %d report: Can't find a new resource deposit.\n"
_C_ unit.Player->Index _C_ unit.Slot);
_C_ player.Index _C_ unit.Slot);
// FIXME: perhaps we should choose an alternative
unit.ClearAction();
@ -667,8 +667,7 @@ static int MoveToDepot(CUnit &unit)
}
// Not ready
if (unit.Player->AiEnabled && unit.CurrentOrder()->Data.Move.Cycles > 300)
{
if (player.AiEnabled && unit.CurrentOrder()->Data.Move.Cycles > 300) {
AiNewDepotRequest(unit);
}
@ -688,9 +687,13 @@ static int MoveToDepot(CUnit &unit)
}
// Update resource.
unit.Player->Resources[resinfo.FinalResource] += (unit.ResourcesHeld * unit.Player->Incomes[resinfo.FinalResource]) / 100;
unit.Player->TotalResources[resinfo.FinalResource] += (unit.ResourcesHeld * unit.Player->Incomes[resinfo.FinalResource]) / 100;
unit.ResourcesHeld = 0;
const int rindex = resinfo.FinalResource;
player.Resources[rindex] += (unit.ResourcesHeld * player.Incomes[rindex]) / 100;
if (player.MaxResources[rindex] != -1) {
player.Resources[rindex] = std::min(player.Resources[rindex], player.MaxResources[rindex]);
}
player.TotalResources[rindex] += (unit.ResourcesHeld * player.Incomes[rindex]) / 100;
unit.ResourcesHeld = 0;
if (unit.Wait) {
unit.Wait /= SpeedResourcesReturn[resinfo.ResourceId];

View file

@ -852,7 +852,7 @@ void CommandDiplomacy(int player, int state, int opponent)
*/
void CommandSetResource(int player, int resource, int value)
{
Players[player].Resources[resource] = value;
Players[player].SetResource(resource, value);
}
/**

View file

@ -133,6 +133,10 @@
** units and structures.
** @see _costs_, TimeCost, GoldCost, WoodCost, OilCost, MaxCosts.
**
** CPlayer::MaxResources[::MaxCosts]
**
** How many resources the player can store at the moment.
**
** CPlayer::Incomes[::MaxCosts]
**
** Income of the resources, when they are delivered at a store.
@ -324,6 +328,7 @@ public:
inline void SetStartView(int x, int y) { StartX = x; StartY = y; }
int Resources[MaxCosts]; /// resources in store
int MaxResources[MaxCosts]; /// max resources can be stored
int LastResources[MaxCosts]; /// last values for revenue
int Incomes[MaxCosts]; /// income of the resources
int Revenue[MaxCosts]; /// income rate of the resources

View file

@ -940,6 +940,7 @@ public:
CConstruction *Construction; /// What is shown in construction phase
int _Costs[MaxCosts]; /// How many resources needed
int _Storing[MaxCosts]; /// How many resources the unit can store
int RepairHP; /// Amount of HP per repair
int RepairCosts[MaxCosts]; /// How much it costs to repair

View file

@ -122,6 +122,11 @@ extern std::string DefaultResourceNames[MaxCosts];
*/
extern int DefaultResourceAmounts[MaxCosts];
/**
** Default max amounts for the resources.
*/
extern int DefaultResourceMaxAmounts[MaxCosts];
/**
** These are the current stats of a unit. Upgraded or downgraded.
*/

View file

@ -198,6 +198,18 @@ void SavePlayers(CFile *file)
}
file->printf("\"%s\", %d,", DefaultResourceNames[j].c_str(), p.Resources[j]);
}
// Max Resources
file->printf(" \"max-resources\", {");
for (int j = 0; j < MaxCosts; ++j) {
if (j) {
if (j == MaxCosts / 2) {
file->printf("\n ");
} else {
file->printf(" ");
}
}
file->printf("\"%s\", %d,", DefaultResourceNames[j].c_str(), p.MaxResources[j]);
}
// Last Resources
file->printf("},\n \"last-resources\", {");
for (int j = 0; j < MaxCosts; ++j) {
@ -450,6 +462,13 @@ void CreatePlayer(int type)
player.Incomes[i] = DefaultIncomes[i];
}
//
// Initial max resource amounts.
//
for (int i = 0; i < MaxCosts; ++i) {
player.MaxResources[i] = DefaultResourceMaxAmounts[i];
}
memset(player.UnitTypesCount, 0, sizeof (player.UnitTypesCount));
player.Supply = 0;
@ -512,6 +531,7 @@ void CPlayer::Clear()
StartX = 0;
StartY = 0;
memset(Resources, 0, sizeof(Resources));
memset(MaxResources, 0, sizeof(MaxResources));
memset(LastResources, 0, sizeof(LastResources));
memset(Incomes, 0, sizeof(Incomes));
memset(Revenue, 0, sizeof(Revenue));
@ -550,7 +570,11 @@ void CPlayer::Clear()
*/
void CPlayer::SetResource(int resource, int value)
{
this->Resources[resource] = value;
if (this->MaxResources[resource] != -1) {
this->Resources[resource] = std::min(value, this->MaxResources[resource]);
} else {
this->Resources[resource] = value;
}
}
/**
@ -650,7 +674,7 @@ int CPlayer::CheckUnitType(const CUnitType &type) const
void CPlayer::AddCosts(const int *costs)
{
for (int i = 1; i < MaxCosts; ++i) {
this->Resources[i] += costs[i];
SetResource(i, Resources[i] + costs[i]);
}
}
@ -674,7 +698,7 @@ void CPlayer::AddUnitType(const CUnitType &type)
void CPlayer::AddCostsFactor(const int *costs, int factor)
{
for (int i = 1; i < MaxCosts; ++i) {
this->Resources[i] += costs[i] * factor / 100;
SetResource(i, this->Resources[i] + costs[i] * factor / 100);
}
}
@ -686,7 +710,7 @@ void CPlayer::AddCostsFactor(const int *costs, int factor)
void CPlayer::SubCosts(const int *costs)
{
for (int i = 1; i < MaxCosts; ++i) {
this->Resources[i] -= costs[i];
SetResource(i, this->Resources[i] - costs[i]);
}
}
@ -709,7 +733,7 @@ void CPlayer::SubUnitType(const CUnitType &type)
void CPlayer::SubCostsFactor(const int *costs, int factor)
{
for (int i = 1; i < MaxCosts; ++i) {
this->Resources[i] -= costs[i] * 100 / factor;
SetResource(i, this->Resources[i] - costs[i] * 100 / factor);
}
}

View file

@ -2302,6 +2302,23 @@ static int CclDefineDefaultResourceAmounts(lua_State *l)
return 0;
}
/**
** Define max amounts for the resources.
**
** @param l Lua state.
*/
static int CclDefineDefaultResourceMaxAmounts(lua_State *l)
{
int args = std::min<int>(lua_gettop(l), MaxCosts);
for (int i = 0; i < args; ++i) {
DefaultResourceMaxAmounts[i] = LuaToNumber(l, i + 1);
}
for (int i = args; i < MaxCosts; ++i)
DefaultResourceMaxAmounts[i] = -1;
return 0;
}
/**
** Define default extra death types.
**
@ -2434,6 +2451,7 @@ void InitCcl()
lua_register(Lua, "DefineDefaultActions", CclDefineDefaultActions);
lua_register(Lua, "DefineDefaultResourceNames", CclDefineDefaultResourceNames);
lua_register(Lua, "DefineDefaultResourceAmounts", CclDefineDefaultResourceAmounts);
lua_register(Lua, "DefineDefaultResourceMaxAmounts", CclDefineDefaultResourceMaxAmounts);
lua_register(Lua, "DefineExtraDeathTypes", CclDefineExtraDeathTypes);
lua_register(Lua, "NoRandomPlacementMultiplayer", CclNoRandomPlacementMultiplayer);

View file

@ -199,6 +199,29 @@ static int CclPlayer(lua_State *l)
LuaError(l, "Unsupported tag: %s" _C_ value);
}
}
} else if (!strcmp(value, "max-resources")) {
if (!lua_istable(l, j + 1)) {
LuaError(l, "incorrect argument");
}
subargs = lua_objlen(l, j + 1);
for (k = 0; k < subargs; ++k) {
lua_rawgeti(l, j + 1, k + 1);
value = LuaToString(l, -1);
lua_pop(l, 1);
++k;
for (i = 0; i < MaxCosts; ++i) {
if (!strcmp(value, DefaultResourceNames[i].c_str())) {
lua_rawgeti(l, j + 1, k + 1);
player->MaxResources[i] = LuaToNumber(l, -1);
lua_pop(l, 1);
break;
}
}
if (i == MaxCosts) {
LuaError(l, "Unsupported tag: %s" _C_ value);
}
}
} else if (!strcmp(value, "last-resources")) {
if (!lua_istable(l, j + 1)) {
LuaError(l, "incorrect argument");
@ -350,10 +373,13 @@ static int CclPlayer(lua_State *l)
lua_pop(l, 1);
}
} else {
LuaError(l, "Unsupported tag: %s" _C_ value);
LuaError(l, "Unsupported tag: %s" _C_ value);
}
}
// Manage max
for (int i = 0; i < MaxCosts; ++i) {
player->SetResource(i, player->Resources[i]);
}
return 0;
}
@ -761,6 +787,18 @@ static int CclGetPlayerData(lua_State *l)
} else if (!strcmp(data, "Resources")) {
LuaCheckArgs(l, 3);
const std::string res = LuaToString(l, 3);
for (int i = 0; i < MaxCosts; ++i) {
if (res == DefaultResourceNames[i]) {
lua_pushnumber(l, p->Resources[i]);
return 1;
}
}
LuaError(l, "Invalid resource \"%s\"" _C_ res.c_str());
} else if (!strcmp(data, "MaxResources")) {
LuaCheckArgs(l, 3);
const std::string res = LuaToString(l, 3);
unsigned int i;
@ -772,7 +810,7 @@ static int CclGetPlayerData(lua_State *l)
if (i == MaxCosts) {
LuaError(l, "Invalid resource \"%s\"" _C_ res.c_str());
}
lua_pushnumber(l, p->Resources[i]);
lua_pushnumber(l, p->MaxResources[i]);
return 1;
} else if (!strcmp(data, "UnitTypesCount")) {
CUnitType *type;

View file

@ -535,31 +535,31 @@ void CContentTypeCompleteBar::Draw(const CUnit &unit, CFont *) const
//FIXME: ugly
switch (this->Color)
{
case 1:
case 1:
color = ColorRed;
break;
case 2:
case 2:
color = ColorYellow;
break;
case 3:
case 3:
color = ColorGreen;
break;
case 4:
case 4:
color = ColorGray;
break;
case 5:
case 5:
color = ColorWhite;
break;
case 6:
case 6:
color = ColorOrange;
break;
case 7:
case 7:
color = ColorBlue;
break;
case 8:
case 8:
color = ColorDarkGreen;
break;
case 9:
case 9:
color = ColorBlack;
break;
default:
@ -773,23 +773,30 @@ static void DrawUnitInfo(CUnit &unit)
*/
void DrawResources()
{
int i;
int v;
CLabel label(GetGameFont());
// Draw all icons of resource.
for (i = 0; i <= ScoreCost; ++i) {
for (int i = 0; i <= ScoreCost; ++i) {
if (UI.Resources[i].G) {
UI.Resources[i].G->DrawFrameClip(UI.Resources[i].IconFrame,
UI.Resources[i].IconX, UI.Resources[i].IconY);
}
}
for (i = 0; i < MaxCosts; ++i) {
for (int i = 0; i < MaxCosts; ++i) {
if (UI.Resources[i].TextX != -1) {
v = ThisPlayer->Resources[i];
label.SetFont(v > 99999 ? GetSmallFont() : GetGameFont());
label.Draw(UI.Resources[i].TextX,
UI.Resources[i].TextY + (v > 99999) * 3, v);
const int resourceAmount = ThisPlayer->Resources[i];
if (ThisPlayer->MaxResources[i] != -1) {
char tmp[128];
snprintf(tmp, sizeof(tmp), "%d/%d", resourceAmount, ThisPlayer->MaxResources[i]);
label.SetFont(GetSmallFont());
label.Draw(UI.Resources[i].TextX, UI.Resources[i].TextY + 3, tmp);
} else {
label.SetFont(resourceAmount > 99999 ? GetSmallFont() : GetGameFont());
label.Draw(UI.Resources[i].TextX, UI.Resources[i].TextY + (resourceAmount > 99999) * 3, resourceAmount);
}
}
}
if (UI.Resources[FoodCost].TextX != -1) {
@ -797,18 +804,16 @@ void DrawResources()
snprintf(tmp,sizeof(tmp), "%d/%d", ThisPlayer->Demand, ThisPlayer->Supply);
label.SetFont(GetGameFont());
if (ThisPlayer->Supply < ThisPlayer->Demand) {
label.DrawReverse(UI.Resources[FoodCost].TextX,
UI.Resources[FoodCost].TextY, tmp);
label.DrawReverse(UI.Resources[FoodCost].TextX, UI.Resources[FoodCost].TextY, tmp);
} else {
label.Draw(UI.Resources[FoodCost].TextX,
UI.Resources[FoodCost].TextY, tmp);
label.Draw(UI.Resources[FoodCost].TextX, UI.Resources[FoodCost].TextY, tmp);
}
}
if (UI.Resources[ScoreCost].TextX != -1) {
v = ThisPlayer->Score;
label.SetFont(v > 99999 ? GetSmallFont() : GetGameFont());
label.Draw(UI.Resources[ScoreCost].TextX,
UI.Resources[ScoreCost].TextY + (v > 99999) * 3, v);
const int score = ThisPlayer->Score;
label.SetFont(score > 99999 ? GetSmallFont() : GetGameFont());
label.Draw(UI.Resources[ScoreCost].TextX, UI.Resources[ScoreCost].TextY + (score > 99999) * 3, score);
}
}

View file

@ -532,6 +532,20 @@ static int CclDefineUnitType(lua_State *l)
type->_Costs[res] = LuaToNumber(l, -1);
lua_pop(l, 1);
}
} else if (!strcmp(value, "Storing")) {
if (!lua_istable(l, -1)) {
LuaError(l, "incorrect argument");
}
subargs = lua_objlen(l, -1);
for (k = 0; k < subargs; ++k) {
lua_rawgeti(l, -1, k + 1);
const int res = CclGetResourceByName(l);
lua_pop(l, 1);
++k;
lua_rawgeti(l, -1, k + 1);
type->_Storing[res] = LuaToNumber(l, -1);
lua_pop(l, 1);
}
} else if (!strcmp(value, "ImproveProduction")) {
if (!lua_istable(l, -1)) {
LuaError(l, "incorrect argument");
@ -656,7 +670,6 @@ static int CclDefineUnitType(lua_State *l)
} else {
LuaError(l, "Unsupported Type: %s" _C_ value);
}
} else if (!strcmp(value, "RightMouseAction")) {
value = LuaToString(l, -1);
if (!strcmp(value, "none")) {

View file

@ -488,6 +488,13 @@ CUnit *MakeUnit(CUnitType &type, CPlayer *player)
unit->AssignToPlayer(player);
}
// Increase the max resources limit
for (int i = 0; i < MaxCosts; ++i) {
if (type._Storing[i] && unit->Player->MaxResources[i] != -1) {
unit->Player->MaxResources[i] += type._Storing[i];
}
}
if (type.Building) {
//
// fancy buildings: mirror buildings (but shadows not correct)
@ -936,10 +943,8 @@ void UnitLost(CUnit &unit)
CUnit *temp;
CBuildRestrictionOnTop *b;
const CUnitType *type;
CPlayer *player;
int i;
CPlayer *player = unit.Player;
player = unit.Player;
Assert(player); // Next code didn't support no player!
//
@ -990,13 +995,21 @@ void UnitLost(CUnit &unit)
//
if (unit.CurrentAction() != UnitActionBuilt) {
player->Supply -= type->Supply;
// Decrease resource limit
for (int i = 0; i < MaxCosts; ++i) {
if (unit.Player->MaxResources[i] != -1 && type->_Storing[i]) {
const int newMaxValue = unit.Player->MaxResources[i] - type->_Storing[i];
unit.Player->MaxResources[i] = std::max(0, newMaxValue);
unit.Player->SetResource(i, unit.Player->Resources[i]);
}
}
//
// Handle income improvements, look if a player loses a building
// which have given him a better income, find the next best
// income.
//
for (i = 1; i < MaxCosts; ++i) {
for (int i = 1; i < MaxCosts; ++i) {
if (player->Incomes[i] && type->ImproveIncomes[i] == player->Incomes[i]) {
int m;
int j;
@ -1069,11 +1082,16 @@ void UpdateForNewUnit(const CUnit &unit, int upgrade)
CPlayer *player = unit.Player;
//
// Handle unit supply. (Currently only food supported.)
// Handle unit supply and max resources.
// Note an upgraded unit can't give more supply.
//
if (!upgrade) {
player->Supply += type->Supply;
for (int i = 0; i < MaxCosts; ++i) {
if (unit.Player->MaxResources[i] != -1 && type->_Storing[i]) {
unit.Player->MaxResources[i] += type->_Storing[i];
}
}
}
//
@ -1557,6 +1575,12 @@ void CUnit::ChangeOwner(CPlayer &newplayer)
}
newplayer.Demand += Type->Demand;
newplayer.Supply += Type->Supply;
// Increase resource limit
for (int i = 0; i < MaxCosts; ++i) {
if (newplayer.MaxResources[i] != -1 && Type->_Storing[i]) {
newplayer.MaxResources[i] += Type->_Storing[i];
}
}
if (Type->Building) {
newplayer.NumBuildings++;
}
@ -2392,10 +2416,9 @@ CUnit *UnitFindResource(const CUnit &unit, const Vec2i &startPos, int range, int
if (bestw < waiting) {
better = false;
} else {
if (bestw == waiting && bestd < n)
{
better = false;
}
if (bestw == waiting && bestd < n) {
better = false;
}
}
}
} else {
@ -2415,8 +2438,7 @@ CUnit *UnitFindResource(const CUnit &unit, const Vec2i &startPos, int range, int
bestw = waiting;
}
} else {
if (bestmine != NoUnitP && bestd < n)
{
if (bestmine != NoUnitP && bestd < n) {
better = false;
}
}
@ -3341,7 +3363,7 @@ void CleanUnits()
//
// Free memory for all units in unit table.
//
while(NumUnits) {
while (NumUnits) {
int count = NumUnits;
do {
CUnit *unit = Units[count - 1];

View file

@ -94,6 +94,11 @@ std::string DefaultResourceNames[MaxCosts];
*/
int DefaultResourceAmounts[MaxCosts];
/**
** Default max amounts for the resources.
*/
int DefaultResourceMaxAmounts[MaxCosts];
/**
** Default names for the resources.
*/
@ -132,6 +137,7 @@ CUnitType::CUnitType() :
memset(&Portrait, 0, sizeof(Portrait));
#endif
memset(_Costs, 0, sizeof(_Costs));
memset(_Storing, 0, sizeof(_Storing));
memset(RepairCosts, 0, sizeof(RepairCosts));
memset(CanStore, 0, sizeof(CanStore));
memset(ResInfo, 0, sizeof(ResInfo));