diff --git a/scripts/tests/common.lua b/scripts/tests/common.lua index 03ae5db85..b8156a777 100644 --- a/scripts/tests/common.lua +++ b/scripts/tests/common.lua @@ -5,6 +5,10 @@ local function _test_create_ship(r) return s end +local function create_faction(race) + return faction.create(race .. '@eressea.de', race, "de") +end + local function one_unit(r, f) local u = unit.create(f, r, 1) u:add_item("money", u.number * 100) @@ -17,8 +21,8 @@ local function two_units(r, f1, f2) end local function two_factions() - local f1 = faction.create("one@eressea.de", "human", "de") - local f2 = faction.create("two@eressea.de", "elf", "de") + local f1 = create_faction('human') + local f2 = create_faction('elf') return f1, f2 end @@ -44,7 +48,7 @@ end function test_flags() local r = region.create(0, 0, "plain") - local f = faction.create("flags@eressea.de", "halfling", "de") + local f = create_faction('halfling') local u = unit.create(f, r, 1) local no = itoa36(f.id) local flags = 50332673 @@ -62,7 +66,7 @@ function test_elvenhorse_requires_riding_5() local r = region.create(0, 0, "plain") region.create(1, 0, "plain") local goal = region.create(2, 0, "plain") - local f = faction.create("riding@eressea.de", "halfling", "de") + local f = create_faction('halfling') local u = unit.create(f, r, 1) u:add_item("elvenhorse", 1) u:set_skill("riding", 6)-- halfling has -1 modifier @@ -76,7 +80,7 @@ function test_cannot_ride_elvenhorse_without_enough_skill() local r = region.create(0, 0, "plain") local goal = region.create(1, 0, "plain") region.create(2, 0, "plain") - local f = faction.create("elvenhorse@eressea.de", "halfling", "de") + local f = create_faction('halfling') local u = unit.create(f, r, 1) u:add_item("elvenhorse", 1) u:set_skill("riding", 5) -- halfling has -1 modifier @@ -96,7 +100,7 @@ end function test_demon_food() local r = region.create(0, 0, "plain") - local f = faction.create("demonfood@eressea.de", "demon", "de") + local f = create_faction('demon') local u = unit.create(f, r, 1) local p = r:get_resource("peasant") r:set_resource("peasant", 2000) @@ -136,7 +140,7 @@ function test_plane() local nx, ny = plane.normalize(pl, 4, 4) assert_equal(nx, -3, "normalization failed") assert_equal(ny, -3, "normalization failed") - local f = faction.create("plan@eressea.de", "human", "de") + local f = create_faction('human') f.id = atoi36("tpla") local r, x, y for x = -3, 3 do for y = -3, 3 do @@ -155,7 +159,7 @@ end function test_read_write() local r = region.create(0, 0, "plain") - local f = faction.create("readwrite@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r) u.number = 2 local fno = f.id @@ -184,7 +188,7 @@ end function test_descriptions() local info = "Descriptions can be very long. Bug 1984 behauptet, dass es Probleme gibt mit Beschreibungen die laenger als 120 Zeichen sind. This description is longer than 120 characters." local r = region.create(0, 0, "plain") - local f = faction.create("descriptions@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) local s = _test_create_ship(r) local b = building.create(r, "castle") @@ -236,7 +240,7 @@ end function test_faction() local r = region.create(0, 0, "plain") - local f = faction.create("testfaction@eressea.de", "human", "de") + local f = create_faction('human') assert(f) f.info = "Spazz" assert(f.info=="Spazz") @@ -259,7 +263,7 @@ end function test_unit() local r = region.create(0, 0, "plain") - local f = faction.create("testunit@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r) u.number = 20 u.name = "Enno" @@ -292,7 +296,7 @@ end function test_building() local u - local f = faction.create("testbuilding@eressea.de", "human", "de") + local f = create_faction('human') local r = region.create(0, 0, "plain") local b = building.create(r, "castle") u = unit.create(f, r) @@ -318,7 +322,7 @@ end function test_message() local r = region.create(0, 0, "plain") - local f = faction.create("testmessage@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r) local msg = message.create("item_create_spell") msg:set_unit("mage", u) @@ -346,7 +350,7 @@ function test_events() plain = region.create(0, 0, "plain") skill = 8 - f = faction.create("noreply2@eressea.de", "elf", "de") + f = create_faction('elf') f.age = 20 u = unit.create(f, plain) @@ -356,7 +360,7 @@ function test_events() u:add_order("NUMMER PARTEI test") u:add_handler("message", msg_handler) msg = "BOTSCHAFT EINHEIT " .. itoa36(u.id) .. " Du~Elf~stinken" - f = faction.create("noreply3@eressea.de", "elf", "de") + f = create_faction('elf') f.age = 20 u = unit.create(f, plain) @@ -371,7 +375,7 @@ end function test_renumber_ship() local r = region.create(0, 0, "plain") - local f = faction.create("noreply4@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r) local s = ship.create(r, config.ships[1]) u.ship = s @@ -386,7 +390,7 @@ end function test_recruit2() local r = region.create(0, 0, "plain") - local f = faction.create("noreply4@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r) u.number = 1 u:add_item("money", 2000) @@ -401,7 +405,7 @@ end function test_guard() region.create(1, 0, "plain") local r = region.create(0, 0, "plain") - local f1 = faction.create("noreply5@eressea.de", "human", "de") + local f1 = create_faction('human') f1.age = 20 local u1 = unit.create(f1, r, 10) u1:add_item("sword", 10) @@ -411,7 +415,7 @@ function test_guard() u1:add_order("NACH O") u1.name="Kalle Pimp" - local f2 = faction.create("noreply6@eressea.de", "human", "de") + local f2 = create_faction('human') f2.age = 20 local u2 = unit.create(f2, r, 1) local u3 = unit.create(f2, r, 1) @@ -429,7 +433,7 @@ end function test_recruit() local r = region.create(0, 0, "plain") - local f = faction.create("noreply7@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r) u.number = 1 local n = 3 @@ -445,7 +449,7 @@ end function test_produce() local r = region.create(0, 0, "plain") - local f = faction.create("noreply8@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) u:clear_orders() local sword = config.get_resource('sword') @@ -460,7 +464,7 @@ end function test_work() local r = region.create(0, 0, "plain") - local f = faction.create("noreply9@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) u:add_item("money", u.number * 10) -- humans cost 10 u:set_skill("herbalism", 5) @@ -473,7 +477,7 @@ end function test_upkeep() eressea.settings.set("rules.food.flags", "0") local r = region.create(0, 0, "plain") - local f = faction.create("noreply10@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 5) u:add_item("money", u.number * 11) u:clear_orders() @@ -485,7 +489,7 @@ end function test_id() local r = region.create(0, 0, "plain") - local f = faction.create("noreply11@eressea.de", "human", "de") + local f = create_faction('human') f.id = atoi36("42") assert_not_equal(f, get_faction(42)) assert_equal(f, get_faction("42")) @@ -521,7 +525,7 @@ function test_mallorn() m:set_resource("tree", 100) assert_equal(100, m:get_resource("tree")) - local f = faction.create("noreply13@eressea.de", "human", "de") + local f = create_faction('human') local u1 = unit.create(f, r, 1) u1:add_item("money", u1.number * 100) @@ -558,7 +562,7 @@ function test_coordinate_translation() local pl = plane.create(1, 500, 500, 1001, 1001) -- astralraum local pe = plane.create(1, -8761, 3620, 23, 23) -- eternath local r = region.create(1000, 1000, "plain") - local f = faction.create("noreply14@eressea.de", "human", "de") + local f = create_faction('human') assert_not_equal(nil, r) assert_equal(r.x, 1000) assert_equal(r.y, 1000) @@ -604,8 +608,8 @@ end function test_building_other() local r = region.create(0,0, "plain") - local f1 = faction.create("noreply17@eressea.de", "human", "de") - local f2 = faction.create("noreply18@eressea.de", "human", "de") + local f1 = create_faction('human') + local f2 = create_faction('human') local b = building.create(r, "castle") b.size = 10 local u1 = unit.create(f1, r, 3) @@ -632,7 +636,7 @@ end local function _test_create_laen() eressea.settings.set("rules.terraform.all", "1") local r = region.create(0,0, "mountain") - local f1 = faction.create("noreply19@eressea.de", "human", "de") + local f1 = create_faction('human') local u1 = unit.create(f1, r, 1) r:set_resource("laen", 50) return r, u1 @@ -671,7 +675,7 @@ end function test_mine() local r = region.create(0,0, "mountain") - local f1 = faction.create("noreply20@eressea.de", "human", "de") + local f1 = create_faction('human') local u1 = unit.create(f1, r, 1) u1:add_item("money", 1000) @@ -692,9 +696,9 @@ end function test_guard_resources() -- this is not quite http://bugs.eressea.de/view.php?id=1756 local r = region.create(0,0, "mountain") - local f1 = faction.create("noreply21@eressea.de", "human", "de") + local f1 = create_faction('human') f1.age=20 - local f2 = faction.create("noreply22@eressea.de", "human", "de") + local f2 = create_faction('human') f2.age=20 local u1 = unit.create(f1, r, 1) u1:add_item("money", 100) @@ -722,7 +726,7 @@ end function test_hero_hero_transfer() local r = region.create(0,0, "mountain") - local f = faction.create("noreply23@eressea.de", "human", "de") + local f = create_faction('human') f.age=20 local UFL_HERO = 128 @@ -743,7 +747,7 @@ end function test_hero_normal_transfer() local r = region.create(0,0, "mountain") - local f = faction.create("noreply24@eressea.de", "human", "de") + local f = create_faction('human') f.age=20 local UFL_HERO = 128 @@ -762,7 +766,7 @@ end function test_expensive_skills_cost_money() local r = region.create(0,0, "mountain") - local f = faction.create("noreply25@eressea.de", "elf", "de") + local f = create_faction('elf') local u = unit.create(f, r, 1) u:add_item("money", 10000) u:clear_orders() @@ -775,7 +779,7 @@ end function test_food_is_consumed() local r = region.create(0, 0, "plain") - local f = faction.create("noreply26@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) u:add_item("money", 100) u:clear_orders() @@ -787,7 +791,7 @@ end function test_food_can_override() local r = region.create(0, 0, "plain") - local f = faction.create("noreply27@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) u:add_item("money", 100) u:clear_orders() @@ -799,7 +803,7 @@ end function test_swim_and_survive() local r = region.create(0, 0, "plain") - local f = faction.create("noreply28@eressea.de", "human", "de") + local f = create_faction('human') f.nam = "chaos" local u = unit.create(f, r, 1) process_orders() @@ -813,7 +817,7 @@ end function test_swim_and_die() local r = region.create(0, 0, "plain") - local f = faction.create("noreply29@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) local uid = u.id process_orders() @@ -828,7 +832,7 @@ function test_ride_with_horse() region.create(1, 0, "plain") region.create(2, 0, "plain") local r = region.create(0, 0, "plain") - local f = faction.create("noreply30@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) u:add_item("horse", 1) local horse_cfg = config.get_resource("horse") @@ -851,7 +855,7 @@ function test_ride_with_horses_and_cart() region.create(1, 0, "plain") region.create(2, 0, "plain") local r = region.create(0, 0, "plain") - local f = faction.create("noreply31@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) local horse_cfg = config.get_resource("horse") local cart_cfg = config.get_resource("cart") @@ -904,7 +908,7 @@ function test_walk_and_carry_the_cart() region.create(1, 0, "plain") local r = region.create(2, 0, "plain") local r = region.create(0, 0, "plain") - local f = faction.create("noreply32@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 10) u:add_item("cart", 1) @@ -925,7 +929,7 @@ end function test_bug_1795_limit() local r = region.create(0, 0, "plain") - local f = faction.create("noreply@eressea.de", "human", "de") + local f = create_faction('human') local u1 = one_unit(r,f) u1:add_item("money", 100000000) u1:add_order("REKRUTIEREN 9999") @@ -940,7 +944,7 @@ end function test_bug_1795_demons() local r = region.create(0, 0, "plain") - local f = faction.create("noreply@eressea.de", "demon", "de") + local f = create_faction('demon') local u1 = one_unit(r,f) r:set_resource("peasant", 2000) local peasants = r:get_resource("peasant") @@ -966,7 +970,7 @@ end function test_parser() local r = region.create(0, 0, "mountain") - local f = faction.create("noreply@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) local filename = "orders.txt" @@ -991,7 +995,7 @@ end function test_prefix() local r0 = region.create(0, 0, "plain") - local f1 = faction.create("noreply@eressea.de", "human", "de") + local f1 = create_faction('human') local u1 = unit.create(f1, r0, 1) set_order(u1, "PRAEFIX See") @@ -1018,7 +1022,7 @@ end function test_recruit() local r = region.create(0, 0, "plain") - local f = faction.create("noreply@eressea.de", "human", "de") + local f = create_faction('human') local u = unit.create(f, r, 1) u:add_item("money", 1000) diff --git a/scripts/tests/e2/adamantium.lua b/scripts/tests/e2/adamantium.lua new file mode 100644 index 000000000..2818db4e8 --- /dev/null +++ b/scripts/tests/e2/adamantium.lua @@ -0,0 +1,56 @@ +require "lunit" + +module("tests.e2.adamantium", package.seeall, lunit.testcase ) + +function setup() + eressea.free_game() + eressea.settings.set("nmr.timeout", "0") + eressea.settings.set("rules.food.flags", "4") + eressea.settings.set("rules.ship.storms", "0") + eressea.settings.set("rules.encounters", "0") +end + +local function create_faction(race) + return faction.create(race .. '@eressea.de', race, "de") +end + +local function _test_create_adamantium() + eressea.settings.set("rules.terraform.all", "1") + local r = region.create(0,0, "mountain") + local f1 = create_faction('human') + local u1 = unit.create(f1, r, 1) + r:set_resource("adamantium", 50) + assert_equal(50, r:get_resource("adamantium")) + return r, u1 +end + +function test_adamantium1() + local r, u1 = _test_create_adamantium() + + u1:add_item("money", 1000) + u1:set_skill("mining", 14) + u1:clear_orders() + u1:add_order("MACHEN Adamantium") + + process_orders() + assert_equal(0, u1:get_item("adamantium")) +end + +function test_adamantium2() + local r, u1 = _test_create_adamantium() + + u1:add_item("money", 1000) + u1:set_skill("mining", 15) + u1:clear_orders() + u1:add_order("MACHEN Adamantium") + + local b = building.create(r, "mine") + b.size = 10 + u1.building = b + local adamantium = r:get_resource("adamantium") + + process_orders() + assert_equal(1, u1:get_item("adamantium")) + assert_equal(adamantium - 1, r:get_resource("adamantium")) +end + diff --git a/scripts/tests/e2/init.lua b/scripts/tests/e2/init.lua index 25e21f3e5..991014287 100644 --- a/scripts/tests/e2/init.lua +++ b/scripts/tests/e2/init.lua @@ -1,3 +1,4 @@ +require 'tests.e2.adamantium' require 'tests.e2.undead' require 'tests.e2.shiplanding' require 'tests.e2.e2features' diff --git a/src/bind_region.c b/src/bind_region.c index 51a5bedd4..f0c2ba87b 100644 --- a/src/bind_region.c +++ b/src/bind_region.c @@ -330,7 +330,7 @@ static int tolua_region_get_resourcelevel(lua_State * L) if (rtype != NULL) { const rawmaterial *rm; for (rm = r->resources; rm; rm = rm->next) { - if (rm->type->rtype == rtype) { + if (rm->rtype == rtype) { lua_pushinteger(L, rm->level); return 1; } diff --git a/src/economy.c b/src/economy.c index 248344e47..c210ee643 100644 --- a/src/economy.c +++ b/src/economy.c @@ -1091,7 +1091,7 @@ leveled_allocation(const resource_type * rtype, region * r, allocation * alist) avail = MIN(avail, nreq); if (need > 0) { int use = 0; - for (al = alist; al; al = al->next) + for (al = alist; al; al = al->next) { if (!fval(al, AFL_DONE)) { if (avail > 0) { int want = required(al->want - al->get, al->save); @@ -1106,9 +1106,13 @@ leveled_allocation(const resource_type * rtype, region * r, allocation * alist) al->get = MIN(al->want, al->get + x * al->save.sa[1] / al->save.sa[0]); } } + } if (use) { - assert(use <= rm->amount); - rm->type->use(rm, r, use); + rawmaterial_type *raw = rmt_get(rm->rtype); + if (raw && raw->use) { + assert(use <= rm->amount); + raw->use(rm, r, use); + } } assert(avail == 0 || nreq == 0); } diff --git a/src/economy.test.c b/src/economy.test.c index 7534afe7e..b77c69a86 100644 --- a/src/economy.test.c +++ b/src/economy.test.c @@ -382,13 +382,13 @@ static void test_make_item(CuTest *tc) { rmt_create(rtype); rdata = rtype->limit = calloc(1, sizeof(resource_limit)); add_resource(u->region, 1, 300, 150, rtype); - u->region->resources->amount = 300; /* there are 300 stones at level 1 */ + CuAssertIntEquals(tc, 300, region_getresource(u->region, rtype)); set_level(u, SK_ALCHEMY, 10); make_item(u, itype, 10); split_allocations(u->region); CuAssertIntEquals(tc, 11, get_item(u, itype)); - CuAssertIntEquals(tc, 290, u->region->resources->amount); /* used 10 stones to make 10 stones */ + CuAssertIntEquals(tc, 290, region_getresource(u->region, rtype)); /* used 10 stones to make 10 stones */ rdata->modifiers = calloc(2, sizeof(resource_mod)); rdata->modifiers[0].flags = RMF_SAVEMATERIAL; @@ -398,18 +398,18 @@ static void test_make_item(CuTest *tc) { make_item(u, itype, 10); split_allocations(u->region); CuAssertIntEquals(tc, 21, get_item(u, itype)); - CuAssertIntEquals(tc, 284, u->region->resources->amount); /* 60% saving = 6 stones make 10 stones */ + CuAssertIntEquals(tc, 284, region_getresource(u->region, rtype)); /* 60% saving = 6 stones make 10 stones */ make_item(u, itype, 1); split_allocations(u->region); CuAssertIntEquals(tc, 22, get_item(u, itype)); - CuAssertIntEquals(tc, 283, u->region->resources->amount); /* no free lunches */ + CuAssertIntEquals(tc, 283, region_getresource(u->region, rtype)); /* no free lunches */ rdata->modifiers[0].value = frac_make(1, 2); make_item(u, itype, 6); split_allocations(u->region); CuAssertIntEquals(tc, 28, get_item(u, itype)); - CuAssertIntEquals(tc, 280, u->region->resources->amount); /* 50% saving = 3 stones make 6 stones */ + CuAssertIntEquals(tc, 280, region_getresource(u->region, rtype)); /* 50% saving = 3 stones make 6 stones */ rdata->modifiers[0].flags = RMF_REQUIREDBUILDING; rdata->modifiers[0].race = NULL; diff --git a/src/kernel/region.c b/src/kernel/region.c index aefffa875..5223d8bf8 100644 --- a/src/kernel/region.c +++ b/src/kernel/region.c @@ -823,7 +823,7 @@ void region_setresource(region * r, const resource_type * rtype, int value) { rawmaterial *rm = r->resources; while (rm) { - if (rm->type->rtype == rtype) { + if (rm->rtype == rtype) { rm->amount = value; break; } @@ -837,14 +837,27 @@ void region_setresource(region * r, const resource_type * rtype, int value) else if (rtype == get_resourcetype(R_HORSE)) rsethorses(r, value); else { - int i; - for (i = 0; r->terrain->production[i].type; ++i) { - const terrain_production *production = r->terrain->production + i; - if (production->type == rtype) { - add_resource(r, 1, value, dice_rand(production->divisor), rtype); - break; + rawmaterial *rm; + if (r->terrain->production) { + int i; + for (i = 0; r->terrain->production[i].type; ++i) { + const terrain_production *production = r->terrain->production + i; + if (production->type == rtype) { + add_resource(r, 1, value, dice_rand(production->divisor), rtype); + return; + } } } + /* adamantium etc are not usually terraformed: */ + for (rm = r->resources; rm; rm = rm->next) { + if (rm->rtype == rtype) { + rm->amount = value; + return; + } + } + if (!rm) { + add_resource(r, 1, value, 150, rtype); + } } } } @@ -853,7 +866,7 @@ int region_getresource(const region * r, const resource_type * rtype) { const rawmaterial *rm; for (rm = r->resources; rm; rm = rm->next) { - if (rm->type->rtype == rtype) { + if (rm->rtype == rtype) { return rm->amount; } } @@ -1044,8 +1057,8 @@ void terraform_region(region * r, const terrain_type * terrain) if (terrain->production != NULL) { int i; for (i = 0; terrain->production[i].type; ++i) { - if (rm->type->rtype == terrain->production[i].type) { - rtype = rm->type->rtype; + if (rm->rtype == terrain->production[i].type) { + rtype = rm->rtype; break; } } diff --git a/src/kernel/region.test.c b/src/kernel/region.test.c index 892b37a8e..879faad50 100644 --- a/src/kernel/region.test.c +++ b/src/kernel/region.test.c @@ -1,6 +1,7 @@ #include #include "region.h" +#include "resources.h" #include "building.h" #include "unit.h" #include "terrain.h" @@ -52,10 +53,36 @@ static void test_region_get_owner(CuTest *tc) { test_cleanup(); } +static void test_region_getset_resource(CuTest *tc) { + region *r; + item_type *itype; + + test_setup(); + init_resources(); + itype = test_create_itemtype("iron"); + itype->construction = calloc(1, sizeof(construction)); + rmt_create(itype->rtype); + r = test_create_region(0, 0, NULL); + + region_setresource(r, itype->rtype, 50); + CuAssertIntEquals(tc, 50, region_getresource(r, itype->rtype)); + + region_setresource(r, get_resourcetype(R_HORSE), 10); + CuAssertIntEquals(tc, 10, region_getresource(r, get_resourcetype(R_HORSE))); + CuAssertIntEquals(tc, 10, rhorses(r)); + + region_setresource(r, get_resourcetype(R_PEASANT), 10); + CuAssertIntEquals(tc, 10, region_getresource(r, get_resourcetype(R_PEASANT))); + CuAssertIntEquals(tc, 10, rpeasants(r)); + + test_cleanup(); +} + CuSuite *get_region_suite(void) { CuSuite *suite = CuSuiteNew(); SUITE_ADD_TEST(suite, test_terraform); + SUITE_ADD_TEST(suite, test_region_getset_resource); SUITE_ADD_TEST(suite, test_region_get_owner); return suite; } diff --git a/src/kernel/resources.c b/src/kernel/resources.c index a3f86aac6..8945e34c2 100644 --- a/src/kernel/resources.c +++ b/src/kernel/resources.c @@ -36,8 +36,10 @@ void update_resources(region * r) { struct rawmaterial *res = r->resources; while (res) { - if (res->type->update) - res->type->update(res, r); + struct rawmaterial_type *raw = rmt_get(res->rtype); + if (raw && raw->update) { + raw->update(res, r); + } res = res->next; } } @@ -55,7 +57,7 @@ static void update_resource(struct rawmaterial *res, double modifier) assert(res->amount > 0); } -void +struct rawmaterial * add_resource(region * r, int level, int base, int divisor, const resource_type * rtype) { @@ -66,11 +68,11 @@ const resource_type * rtype) rm->level = level; rm->startlevel = level; rm->base = base; + rm->amount = base; rm->divisor = divisor; rm->flags = 0; - rm->type = rmt_get(rtype); - update_resource(rm, 1.0); - rm->type->terraform(rm, r); + rm->rtype = rtype; + return rm; } void terraform_resources(region * r) @@ -87,7 +89,7 @@ void terraform_resources(region * r) const resource_type *rtype = production->type; for (rm = r->resources; rm; rm = rm->next) { - if (rm->type->rtype == rtype) + if (rm->rtype == rtype) break; } if (rm) { @@ -95,9 +97,16 @@ void terraform_resources(region * r) } if (terraform_all || chance(production->chance)) { - add_resource(r, dice_rand(production->startlevel), + rawmaterial *rm; + rawmaterial_type *raw; + rm = add_resource(r, dice_rand(production->startlevel), dice_rand(production->base), dice_rand(production->divisor), production->type); + update_resource(rm, 1.0); + raw = rmt_get(rm->rtype); + if (raw && raw->terraform) { + raw->terraform(rm, r); + } } } } @@ -142,7 +151,7 @@ static int visible_default(const rawmaterial * res, int skilllevel) /* resources are visible, if skill equals minimum skill to mine them * plus current level of difficulty */ { - const struct item_type *itype = res->type->rtype->itype; + const struct item_type *itype = res->rtype->itype; if (res->level <= 1 && res->level + itype->construction->minskill <= skilllevel + 1) { assert(res->amount > 0); @@ -166,7 +175,7 @@ static void use_default(rawmaterial * res, const region * r, int amount) int i; for (i = 0; r->terrain->production[i].type; ++i) { - if (res->type->rtype == r->terrain->production[i].type) + if (res->rtype == r->terrain->production[i].type) break; } @@ -178,8 +187,9 @@ static void use_default(rawmaterial * res, const region * r, int amount) struct rawmaterial *rm_get(region * r, const struct resource_type *rtype) { struct rawmaterial *rm = r->resources; - while (rm && rm->type->rtype != rtype) + while (rm && rm->rtype != rtype) { rm = rm->next; + } return rm; } diff --git a/src/kernel/resources.h b/src/kernel/resources.h index d7c0e5bfd..04e122f76 100644 --- a/src/kernel/resources.h +++ b/src/kernel/resources.h @@ -24,7 +24,7 @@ extern "C" { }; typedef struct rawmaterial { - const struct rawmaterial_type *type; + const struct resource_type *rtype; #ifdef LOMEM int amount:16; int level:8; @@ -79,8 +79,8 @@ extern "C" { struct rawmaterial_type *rmt_find(const char *str); struct rawmaterial_type *rmt_get(const struct resource_type *); - void add_resource(struct region *r, int level, int base, int divisor, - const struct resource_type *rtype); + struct rawmaterial *add_resource(struct region *r, int level, + int base, int divisor, const struct resource_type *rtype); struct rawmaterial_type *rmt_create(struct resource_type *rtype); #ifdef __cplusplus diff --git a/src/kernel/save.c b/src/kernel/save.c index 8316121f3..e1d6178fb 100644 --- a/src/kernel/save.c +++ b/src/kernel/save.c @@ -955,11 +955,11 @@ static region *readregion(struct gamedata *data, int x, int y) if (strcmp(name, "end") == 0) break; res = malloc(sizeof(rawmaterial)); - res->type = rmt_find(name); - if (res->type == NULL) { + res->rtype = rt_find(name); + if (!res->rtype || !res->rtype->raw) { log_error("invalid resourcetype %s in data.", name); } - assert(res->type != NULL); + assert(res->rtype); READ_INT(data->store, &n); res->level = n; READ_INT(data->store, &n); @@ -1068,7 +1068,7 @@ void writeregion(struct gamedata *data, const region * r) WRITE_INT(data->store, rhorses(r)); while (res) { - WRITE_TOK(data->store, res->type->rtype->_name); + WRITE_TOK(data->store, res->rtype->_name); WRITE_INT(data->store, res->level); WRITE_INT(data->store, res->amount); WRITE_INT(data->store, res->startlevel); diff --git a/src/modules/autoseed.c b/src/modules/autoseed.c index 1e2d2d23f..ffab4ca46 100644 --- a/src/modules/autoseed.c +++ b/src/modules/autoseed.c @@ -81,20 +81,6 @@ const terrain_type *random_terrain(const terrain_type * terrains[], return terrain; } -int seed_adamantium(region * r, int base) -{ - const resource_type *rtype = rt_find("adamantium"); - rawmaterial *rm; - for (rm = r->resources; rm; rm = rm->next) { - if (rm->type->rtype == rtype) - break; - } - if (!rm) { - add_resource(r, 1, base, 150, rtype); - } - return 0; -} - static int count_demand(const region * r) { struct demand *dmd; diff --git a/src/report.test.c b/src/report.test.c index 3c6a09ae1..2bdbebb7c 100644 --- a/src/report.test.c +++ b/src/report.test.c @@ -95,8 +95,7 @@ static void test_report_region(CuTest *tc) { mstream_init(&out); r = test_create_region(0, 0, 0); - add_resource(r, 1, 100, 10, rt_stone); - r->resources->amount = 135; + add_resource(r, 1, 135, 10, rt_stone); CuAssertIntEquals(tc, 1, r->resources->level); r->land->peasants = 5; r->land->horses = 7; diff --git a/src/reports.c b/src/reports.c index c23809a32..fe1f59775 100644 --- a/src/reports.c +++ b/src/reports.c @@ -448,12 +448,13 @@ const faction * viewer, bool see_unit) rawmaterial *res = r->resources; while (res) { int maxskill = 0; - const item_type *itype = resource2item(res->type->rtype); + const item_type *itype = resource2item(res->rtype); int minskill = itype->construction->minskill; skill_t skill = itype->construction->skill; int level = res->level + minskill - 1; int visible = -1; - if (res->type->visible == NULL) { + rawmaterial_type *raw = rmt_get(res->rtype); + if (raw->visible == NULL) { visible = res->amount; level = res->level + minskill - 1; } @@ -464,7 +465,7 @@ const faction * viewer, bool see_unit) int s = effskill(u, skill, 0); if (s > maxskill) { maxskill = s; - visible = res->type->visible(res, maxskill); + visible = raw->visible(res, maxskill); } } } @@ -472,7 +473,7 @@ const faction * viewer, bool see_unit) if (level >= 0 && visible >= 0) { if (n >= size) return -1; - report_resource(result + n, res->type->rtype, visible, level); + report_resource(result + n, res->rtype, visible, level); n++; } res = res->next;