forked from github/server
world generation algorithm for E3
This commit is contained in:
parent
27d8628084
commit
fa2072b6e0
|
@ -1,6 +1,6 @@
|
|||
/* vi: set ts=2:
|
||||
*
|
||||
* Eressea PB(E)M host Copyright (C) 1998-2003
|
||||
* Eressea PB(E)M host Copyright (C) 1998-2003
|
||||
* Christian Schlittchen (corwin@amber.kn-bremen.de)
|
||||
* Katja Zedel (katze@felidae.kn-bremen.de)
|
||||
* Henning Peters (faroul@beyond.kn-bremen.de)
|
||||
|
@ -72,9 +72,9 @@ struct unit_list;
|
|||
struct weapon_type;
|
||||
|
||||
typedef struct ursprung {
|
||||
struct ursprung *next;
|
||||
int id;
|
||||
short x, y;
|
||||
struct ursprung *next;
|
||||
int id;
|
||||
short x, y;
|
||||
} ursprung;
|
||||
|
||||
/* ----------------- Befehle ----------------------------------- */
|
||||
|
@ -169,80 +169,80 @@ enum {
|
|||
|
||||
typedef unsigned char param_t;
|
||||
enum {
|
||||
P_LOCALE,
|
||||
P_LOCALE,
|
||||
P_ANY,
|
||||
P_EACH,
|
||||
P_PEASANT,
|
||||
P_BUILDING,
|
||||
P_UNIT,
|
||||
P_PRIVAT,
|
||||
P_BEHIND,
|
||||
P_CONTROL,
|
||||
P_HERBS,
|
||||
P_NOT,
|
||||
P_NEXT,
|
||||
P_FACTION,
|
||||
P_GAMENAME,
|
||||
P_PERSON,
|
||||
P_REGION,
|
||||
P_SHIP,
|
||||
P_MONEY,
|
||||
P_ROAD,
|
||||
P_TEMP,
|
||||
P_FLEE,
|
||||
P_GEBAEUDE,
|
||||
P_GIVE,
|
||||
P_FIGHT,
|
||||
P_PEASANT,
|
||||
P_BUILDING,
|
||||
P_UNIT,
|
||||
P_PRIVAT,
|
||||
P_BEHIND,
|
||||
P_CONTROL,
|
||||
P_HERBS,
|
||||
P_NOT,
|
||||
P_NEXT,
|
||||
P_FACTION,
|
||||
P_GAMENAME,
|
||||
P_PERSON,
|
||||
P_REGION,
|
||||
P_SHIP,
|
||||
P_MONEY,
|
||||
P_ROAD,
|
||||
P_TEMP,
|
||||
P_FLEE,
|
||||
P_GEBAEUDE,
|
||||
P_GIVE,
|
||||
P_FIGHT,
|
||||
P_TRAVEL,
|
||||
P_GUARD,
|
||||
P_ZAUBER,
|
||||
P_PAUSE,
|
||||
P_VORNE,
|
||||
P_AGGRO,
|
||||
P_CHICKEN,
|
||||
P_LEVEL,
|
||||
P_HELP,
|
||||
P_FOREIGN,
|
||||
P_AURA,
|
||||
P_FOR,
|
||||
P_AID,
|
||||
P_MERCY,
|
||||
P_AFTER,
|
||||
P_BEFORE,
|
||||
P_NUMBER,
|
||||
P_ITEMS,
|
||||
P_POTIONS,
|
||||
P_GROUP,
|
||||
P_FACTIONSTEALTH,
|
||||
P_TREES,
|
||||
P_XEPOTION,
|
||||
P_XEBALLOON,
|
||||
P_XELAEN,
|
||||
MAXPARAMS,
|
||||
NOPARAM = (param_t) - 1
|
||||
P_GUARD,
|
||||
P_ZAUBER,
|
||||
P_PAUSE,
|
||||
P_VORNE,
|
||||
P_AGGRO,
|
||||
P_CHICKEN,
|
||||
P_LEVEL,
|
||||
P_HELP,
|
||||
P_FOREIGN,
|
||||
P_AURA,
|
||||
P_FOR,
|
||||
P_AID,
|
||||
P_MERCY,
|
||||
P_AFTER,
|
||||
P_BEFORE,
|
||||
P_NUMBER,
|
||||
P_ITEMS,
|
||||
P_POTIONS,
|
||||
P_GROUP,
|
||||
P_FACTIONSTEALTH,
|
||||
P_TREES,
|
||||
P_XEPOTION,
|
||||
P_XEBALLOON,
|
||||
P_XELAEN,
|
||||
MAXPARAMS,
|
||||
NOPARAM = (param_t) - 1
|
||||
};
|
||||
|
||||
typedef enum { /* Fehler und Meldungen im Report */
|
||||
MSG_BATTLE,
|
||||
MSG_EVENT,
|
||||
MSG_MOVE,
|
||||
MSG_INCOME,
|
||||
MSG_COMMERCE,
|
||||
MSG_PRODUCE,
|
||||
MSG_ORCVERMEHRUNG,
|
||||
MSG_MESSAGE,
|
||||
MSG_COMMENT,
|
||||
MSG_MAGIC,
|
||||
MAX_MSG
|
||||
typedef enum { /* Fehler und Meldungen im Report */
|
||||
MSG_BATTLE,
|
||||
MSG_EVENT,
|
||||
MSG_MOVE,
|
||||
MSG_INCOME,
|
||||
MSG_COMMERCE,
|
||||
MSG_PRODUCE,
|
||||
MSG_ORCVERMEHRUNG,
|
||||
MSG_MESSAGE,
|
||||
MSG_COMMENT,
|
||||
MSG_MAGIC,
|
||||
MAX_MSG
|
||||
} msg_t;
|
||||
|
||||
enum { /* Message-Level */
|
||||
ML_IMPORTANT, /* Sachen, die IMO erscheinen _muessen_ */
|
||||
ML_DEBUG,
|
||||
ML_MISTAKE,
|
||||
ML_WARN,
|
||||
ML_INFO,
|
||||
ML_MAX
|
||||
enum { /* Message-Level */
|
||||
ML_IMPORTANT, /* Sachen, die IMO erscheinen _muessen_ */
|
||||
ML_DEBUG,
|
||||
ML_MISTAKE,
|
||||
ML_WARN,
|
||||
ML_INFO,
|
||||
ML_MAX
|
||||
};
|
||||
|
||||
extern const char *parameters[MAXPARAMS];
|
||||
|
@ -250,147 +250,147 @@ extern const char *parameters[MAXPARAMS];
|
|||
/* --------------- Reports Typen ------------------------------- */
|
||||
|
||||
enum {
|
||||
O_REPORT, /* 1 */
|
||||
O_COMPUTER, /* 2 */
|
||||
O_ZUGVORLAGE, /* 4 */
|
||||
O_REPORT, /* 1 */
|
||||
O_COMPUTER, /* 2 */
|
||||
O_ZUGVORLAGE, /* 4 */
|
||||
O_UNUSED_3,
|
||||
O_STATISTICS, /* 16 */
|
||||
O_DEBUG, /* 32 */
|
||||
O_COMPRESS, /* 64 */
|
||||
O_NEWS, /* 128 */
|
||||
O_STATISTICS, /* 16 */
|
||||
O_DEBUG, /* 32 */
|
||||
O_COMPRESS, /* 64 */
|
||||
O_NEWS, /* 128 */
|
||||
O_UNUSED_8,
|
||||
O_ADRESSEN, /* 512 */
|
||||
O_BZIP2, /* 1024 - compress as bzip2 */
|
||||
O_SCORE, /* 2048 - punkte anzeigen? */
|
||||
O_SHOWSKCHANGE, /* 4096 - Skillveränderungen anzeigen? */
|
||||
O_XML, /* 8192 - XML report versenden */
|
||||
O_ADRESSEN, /* 512 */
|
||||
O_BZIP2, /* 1024 - compress as bzip2 */
|
||||
O_SCORE, /* 2048 - punkte anzeigen? */
|
||||
O_SHOWSKCHANGE, /* 4096 - Skillveränderungen anzeigen? */
|
||||
O_XML, /* 8192 - XML report versenden */
|
||||
MAXOPTIONS
|
||||
};
|
||||
|
||||
/* ------------------ Talente ---------------------------------- */
|
||||
|
||||
enum {
|
||||
SK_ALCHEMY,
|
||||
SK_CROSSBOW,
|
||||
SK_MINING,
|
||||
SK_LONGBOW,
|
||||
SK_BUILDING,
|
||||
SK_TRADE,
|
||||
SK_LUMBERJACK,
|
||||
SK_CATAPULT,
|
||||
SK_HERBALISM,
|
||||
SK_MAGIC,
|
||||
SK_HORSE_TRAINING, /* 10 */
|
||||
SK_RIDING,
|
||||
SK_ARMORER,
|
||||
SK_SHIPBUILDING,
|
||||
SK_MELEE,
|
||||
SK_SAILING,
|
||||
SK_SPEAR,
|
||||
SK_SPY,
|
||||
SK_QUARRYING,
|
||||
SK_ROAD_BUILDING,
|
||||
SK_TACTICS, /* 20 */
|
||||
SK_STEALTH,
|
||||
SK_ENTERTAINMENT,
|
||||
SK_WEAPONSMITH,
|
||||
SK_CARTMAKER,
|
||||
SK_PERCEPTION,
|
||||
SK_TAXING,
|
||||
SK_STAMINA,
|
||||
SK_WEAPONLESS,
|
||||
MAXSKILLS,
|
||||
NOSKILL = (skill_t) -1
|
||||
SK_ALCHEMY,
|
||||
SK_CROSSBOW,
|
||||
SK_MINING,
|
||||
SK_LONGBOW,
|
||||
SK_BUILDING,
|
||||
SK_TRADE,
|
||||
SK_LUMBERJACK,
|
||||
SK_CATAPULT,
|
||||
SK_HERBALISM,
|
||||
SK_MAGIC,
|
||||
SK_HORSE_TRAINING, /* 10 */
|
||||
SK_RIDING,
|
||||
SK_ARMORER,
|
||||
SK_SHIPBUILDING,
|
||||
SK_MELEE,
|
||||
SK_SAILING,
|
||||
SK_SPEAR,
|
||||
SK_SPY,
|
||||
SK_QUARRYING,
|
||||
SK_ROAD_BUILDING,
|
||||
SK_TACTICS, /* 20 */
|
||||
SK_STEALTH,
|
||||
SK_ENTERTAINMENT,
|
||||
SK_WEAPONSMITH,
|
||||
SK_CARTMAKER,
|
||||
SK_PERCEPTION,
|
||||
SK_TAXING,
|
||||
SK_STAMINA,
|
||||
SK_WEAPONLESS,
|
||||
MAXSKILLS,
|
||||
NOSKILL = (skill_t) -1
|
||||
};
|
||||
|
||||
/* ------------- Typ von Einheiten ----------------------------- */
|
||||
|
||||
enum {
|
||||
RC_DWARF, /* 0 - Zwerg */
|
||||
RC_ELF,
|
||||
RC_ORC,
|
||||
RC_GOBLIN,
|
||||
RC_HUMAN,
|
||||
RC_DWARF, /* 0 - Zwerg */
|
||||
RC_ELF,
|
||||
RC_ORC,
|
||||
RC_GOBLIN,
|
||||
RC_HUMAN,
|
||||
|
||||
RC_TROLL,
|
||||
RC_DAEMON,
|
||||
RC_INSECT,
|
||||
RC_HALFLING,
|
||||
RC_CAT,
|
||||
RC_INSECT,
|
||||
RC_HALFLING,
|
||||
RC_CAT,
|
||||
|
||||
RC_AQUARIAN,
|
||||
RC_URUK,
|
||||
RC_SNOTLING,
|
||||
RC_UNDEAD,
|
||||
RC_ILLUSION,
|
||||
RC_SNOTLING,
|
||||
RC_UNDEAD,
|
||||
RC_ILLUSION,
|
||||
|
||||
RC_FIREDRAGON,
|
||||
RC_DRAGON,
|
||||
RC_WYRM,
|
||||
RC_TREEMAN,
|
||||
RC_BIRTHDAYDRAGON,
|
||||
RC_WYRM,
|
||||
RC_TREEMAN,
|
||||
RC_BIRTHDAYDRAGON,
|
||||
|
||||
RC_DRACOID,
|
||||
RC_SPECIAL,
|
||||
RC_SPELL,
|
||||
RC_IRONGOLEM,
|
||||
RC_STONEGOLEM,
|
||||
RC_SPECIAL,
|
||||
RC_SPELL,
|
||||
RC_IRONGOLEM,
|
||||
RC_STONEGOLEM,
|
||||
|
||||
RC_SHADOW,
|
||||
RC_SHADOWLORD,
|
||||
RC_IRONKEEPER,
|
||||
RC_ALP,
|
||||
RC_TOAD,
|
||||
RC_IRONKEEPER,
|
||||
RC_ALP,
|
||||
RC_TOAD,
|
||||
|
||||
RC_HIRNTOETER,
|
||||
RC_PEASANT,
|
||||
RC_WOLF = 32,
|
||||
RC_PEASANT,
|
||||
RC_WOLF = 32,
|
||||
|
||||
RC_SONGDRAGON = 37,
|
||||
RC_SONGDRAGON = 37,
|
||||
|
||||
RC_SEASERPENT = 51,
|
||||
RC_SHADOWKNIGHT,
|
||||
RC_CENTAUR,
|
||||
RC_SKELETON,
|
||||
RC_SHADOWKNIGHT,
|
||||
RC_CENTAUR,
|
||||
RC_SKELETON,
|
||||
|
||||
RC_SKELETON_LORD,
|
||||
RC_ZOMBIE,
|
||||
RC_ZOMBIE_LORD,
|
||||
RC_GHOUL,
|
||||
RC_GHOUL_LORD,
|
||||
RC_ZOMBIE,
|
||||
RC_ZOMBIE_LORD,
|
||||
RC_GHOUL,
|
||||
RC_GHOUL_LORD,
|
||||
|
||||
RC_MUS_SPIRIT,
|
||||
RC_GNOME,
|
||||
RC_TEMPLATE,
|
||||
RC_CLONE,
|
||||
RC_MUS_SPIRIT,
|
||||
RC_GNOME,
|
||||
RC_TEMPLATE,
|
||||
RC_CLONE,
|
||||
|
||||
MAXRACES,
|
||||
NORACE = (race_t) - 1
|
||||
MAXRACES,
|
||||
NORACE = (race_t) - 1
|
||||
};
|
||||
|
||||
/* Richtungen */
|
||||
enum {
|
||||
D_NORTHWEST,
|
||||
D_NORTHEAST,
|
||||
D_EAST,
|
||||
D_SOUTHEAST,
|
||||
D_SOUTHWEST,
|
||||
D_WEST,
|
||||
MAXDIRECTIONS,
|
||||
D_PAUSE,
|
||||
D_NORTHWEST,
|
||||
D_NORTHEAST,
|
||||
D_EAST,
|
||||
D_SOUTHEAST,
|
||||
D_SOUTHWEST,
|
||||
D_WEST,
|
||||
MAXDIRECTIONS,
|
||||
D_PAUSE,
|
||||
D_SPECIAL,
|
||||
NODIRECTION = (direction_t) - 1
|
||||
NODIRECTION = (direction_t) - 1
|
||||
};
|
||||
|
||||
#define DONT_HELP 0
|
||||
#define HELP_MONEY 1 /* Mitversorgen von Einheiten */
|
||||
#define HELP_FIGHT 2 /* Bei Verteidigung mithelfen */
|
||||
#define HELP_OBSERVE 4 /* Bei Wahrnehmung mithelfen */
|
||||
#define HELP_GIVE 8 /* Dinge annehmen ohne KONTAKTIERE */
|
||||
#define HELP_GUARD 16 /* Laesst Steuern eintreiben etc. */
|
||||
#define HELP_FSTEALTH 32 /* Parteitarnung anzeigen. */
|
||||
#define HELP_TRAVEL 64 /* Laesst Regionen betreten. */
|
||||
#define HELP_ALL (127-HELP_TRAVEL-HELP_OBSERVE) /* Alle "positiven" HELPs zusammen */
|
||||
#define HELP_MONEY 1 /* Mitversorgen von Einheiten */
|
||||
#define HELP_FIGHT 2 /* Bei Verteidigung mithelfen */
|
||||
#define HELP_OBSERVE 4 /* Bei Wahrnehmung mithelfen */
|
||||
#define HELP_GIVE 8 /* Dinge annehmen ohne KONTAKTIERE */
|
||||
#define HELP_GUARD 16 /* Laesst Steuern eintreiben etc. */
|
||||
#define HELP_FSTEALTH 32 /* Parteitarnung anzeigen. */
|
||||
#define HELP_TRAVEL 64 /* Laesst Regionen betreten. */
|
||||
#define HELP_ALL (127-HELP_TRAVEL-HELP_OBSERVE) /* Alle "positiven" HELPs zusammen */
|
||||
/* HELP_OBSERVE deaktiviert */
|
||||
/* ------------------------------------------------------------- */
|
||||
/* Prototypen */
|
||||
|
|
|
@ -49,23 +49,30 @@
|
|||
#include <assert.h>
|
||||
|
||||
const terrain_type *
|
||||
random_terrain(boolean distribution)
|
||||
random_terrain(const terrain_type * terrains[], int distribution[], int size)
|
||||
{
|
||||
static int nterrains;
|
||||
static int ndistribution;
|
||||
int ndistribution = size;
|
||||
const terrain_type * terrain;
|
||||
int n;
|
||||
if (nterrains==0) {
|
||||
for (terrain=terrains();terrain;terrain=terrain->next) {
|
||||
ndistribution += terrain->distribution;
|
||||
++nterrains;
|
||||
|
||||
if (distribution) {
|
||||
ndistribution = 0;
|
||||
for (n=0;n!=size;++n) {
|
||||
ndistribution += distribution[n];
|
||||
}
|
||||
}
|
||||
|
||||
n = rng_int() % (distribution?ndistribution:nterrains);
|
||||
for (terrain=terrains();terrain;terrain=terrain->next) {
|
||||
n -= distribution?terrain->distribution:1;
|
||||
if (n<0) break;
|
||||
n = rng_int() % ndistribution;
|
||||
if (distribution) {
|
||||
int i;
|
||||
for (i=0;i!=size;++i) {
|
||||
n -= distribution[i];
|
||||
if (n<0) break;
|
||||
}
|
||||
assert(i<size);
|
||||
terrain = terrains[i];
|
||||
} else {
|
||||
terrain = terrains[n];
|
||||
}
|
||||
return terrain;
|
||||
}
|
||||
|
@ -412,9 +419,7 @@ free_newfaction(newfaction * nf)
|
|||
free(nf->password);
|
||||
free(nf);
|
||||
}
|
||||
/** create new island with up to nsize players
|
||||
* returns the number of players placed on the new island.
|
||||
*/
|
||||
|
||||
static void
|
||||
frame_regions(int age, const terrain_type * terrain)
|
||||
{
|
||||
|
@ -435,6 +440,7 @@ frame_regions(int age, const terrain_type * terrain)
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
prepare_starting_region(region * r)
|
||||
{
|
||||
|
@ -467,6 +473,9 @@ prepare_starting_region(region * r)
|
|||
fix_demand(r);
|
||||
}
|
||||
|
||||
/** create new island with up to nsize players
|
||||
* returns the number of players placed on the new island.
|
||||
*/
|
||||
int
|
||||
autoseed(newfaction ** players, int nsize, int max_agediff)
|
||||
{
|
||||
|
@ -477,7 +486,27 @@ autoseed(newfaction ** players, int nsize, int max_agediff)
|
|||
int isize = REGIONS_PER_FACTION; /* target size for the island */
|
||||
int psize = 0; /* players on this island */
|
||||
const terrain_type * volcano_terrain = get_terrain("volcano");
|
||||
static int nterrains = -1;
|
||||
static const terrain_type ** terrainarr = 0;
|
||||
static int * distribution;
|
||||
|
||||
if (nterrains<0) {
|
||||
int n = 0;
|
||||
const terrain_type * terrain = terrains();
|
||||
for (nterrains=0;terrain;terrain=terrain->next) {
|
||||
if (terrain->distribution) {
|
||||
++nterrains;
|
||||
}
|
||||
}
|
||||
terrainarr = malloc(sizeof(terrain_type *) * nterrains);
|
||||
distribution = malloc(sizeof(int) * nterrains);
|
||||
for (terrain = terrains();terrain;terrain = terrain->next) {
|
||||
if (terrain->distribution) {
|
||||
terrainarr[n] = terrain;
|
||||
distribution[n++] = terrain->distribution;
|
||||
}
|
||||
}
|
||||
}
|
||||
frame_regions(16, newterrain(T_FIREWALL));
|
||||
|
||||
if (listlen(*players)<MINFACTIONS) return 0;
|
||||
|
@ -633,7 +662,7 @@ autoseed(newfaction ** players, int nsize, int max_agediff)
|
|||
--isize;
|
||||
if (psize>=PLAYERS_PER_ISLAND) break;
|
||||
} else {
|
||||
terraform_region(r, random_terrain(true));
|
||||
terraform_region(r, random_terrain(terrainarr, distribution, nterrains));
|
||||
--isize;
|
||||
}
|
||||
}
|
||||
|
@ -664,7 +693,7 @@ autoseed(newfaction ** players, int nsize, int max_agediff)
|
|||
const struct terrain_type * terrain = newterrain(T_OCEAN);
|
||||
rn = new_region(r->x + delta_x[d], r->y + delta_y[d], 0);
|
||||
if (rng_int() % SPECIALCHANCE < special) {
|
||||
terrain = random_terrain(true);
|
||||
terrain = random_terrain(terrainarr, distribution, nterrains);
|
||||
special = SPECIALCHANCE / 3; /* 33% chance auf noch eines */
|
||||
} else {
|
||||
special = 1;
|
||||
|
@ -706,3 +735,157 @@ autoseed(newfaction ** players, int nsize, int max_agediff)
|
|||
}
|
||||
return tsize;
|
||||
}
|
||||
|
||||
static void get_neighbours(const region * r, region ** list)
|
||||
{
|
||||
direction_t dir;
|
||||
for (dir=0;dir!=MAXDIRECTIONS;++dir) {
|
||||
list[dir] = rconnect(r, dir);
|
||||
}
|
||||
}
|
||||
|
||||
region_list * regionqueue_push(region_list ** rlist, region * r)
|
||||
{
|
||||
region_list * rnew = malloc(sizeof(region_list));
|
||||
rnew->data = r;
|
||||
rnew->next = 0;
|
||||
while (*rlist) { rlist = &(*rlist)->next; }
|
||||
*rlist = rnew;
|
||||
return rnew;
|
||||
}
|
||||
|
||||
region * regionqueue_pop(region_list ** rlist)
|
||||
{
|
||||
if (*rlist) {
|
||||
region * r = (*rlist)->data;
|
||||
region_list * rpop = *rlist;
|
||||
*rlist = rpop->next;
|
||||
free(rpop);
|
||||
return r;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define GEOMAX 8
|
||||
static struct geo {
|
||||
int distribution;
|
||||
terrain_t type;
|
||||
} geography_e3[GEOMAX] = {
|
||||
{ 8, T_OCEAN },
|
||||
{ 3, T_SWAMP },
|
||||
{ 1, T_VOLCANO },
|
||||
{ 3, T_DESERT },
|
||||
{ 3, T_HIGHLAND },
|
||||
{ 3, T_MOUNTAIN },
|
||||
{ 2, T_GLACIER },
|
||||
{ 1, T_PLAIN }
|
||||
};
|
||||
|
||||
const terrain_type * random_terrain_e3(direction_t dir)
|
||||
{
|
||||
static const terrain_type ** terrainarr = 0;
|
||||
static int * distribution = 0;
|
||||
|
||||
if (!distribution) {
|
||||
int n = 0;
|
||||
|
||||
terrainarr = malloc(GEOMAX * sizeof(const terrain_type *));
|
||||
distribution = malloc(GEOMAX * sizeof(int));
|
||||
for (n=0;n!=GEOMAX;++n) {
|
||||
terrainarr[n] = newterrain(geography_e3[n].type);
|
||||
distribution[n] = geography_e3[n].distribution;
|
||||
}
|
||||
}
|
||||
return random_terrain(terrainarr, distribution, GEOMAX);
|
||||
}
|
||||
|
||||
int
|
||||
random_neighbours(region * r, region_list ** rlist, const terrain_type *(*terraformer)(direction_t))
|
||||
{
|
||||
int nsize = 0;
|
||||
direction_t dir;
|
||||
for (dir=0;dir!=MAXDIRECTIONS;++dir) {
|
||||
region * rn = rconnect(r, dir);
|
||||
if (rn==NULL) {
|
||||
const terrain_type * terrain = terraformer(dir);
|
||||
rn = new_region(r->x+delta_x[dir], r->y+delta_y[dir], 0);
|
||||
terraform_region(rn, terrain);
|
||||
if (rn->land) {
|
||||
regionqueue_push(rlist, rn);
|
||||
++nsize;
|
||||
}
|
||||
}
|
||||
}
|
||||
return nsize;
|
||||
}
|
||||
|
||||
const terrain_type * get_ocean(direction_t dir)
|
||||
{
|
||||
return newterrain(T_OCEAN);
|
||||
}
|
||||
|
||||
int region_quality(const region * r)
|
||||
{
|
||||
region * rn[MAXDIRECTIONS];
|
||||
int n, result = 0;
|
||||
get_neighbours(r, rn);
|
||||
for (n=0;n!=MAXDIRECTIONS;++n) {
|
||||
if (rn[n] && rn[n]->land) {
|
||||
result += rn[n]->land->peasants;
|
||||
}
|
||||
}
|
||||
// result += r->land->peasants * 2;
|
||||
return result;
|
||||
}
|
||||
|
||||
/* E3A island generation */
|
||||
int
|
||||
build_island_e3(short x, short y, int numfactions, int minsize)
|
||||
{
|
||||
int nfactions = 0;
|
||||
region_list * rlist = NULL;
|
||||
region_list * island = NULL;
|
||||
region * r = new_region(x, y, 0);
|
||||
int nsize = 1;
|
||||
int q, maxq = INT_MIN, minq = INT_MAX;
|
||||
|
||||
terraform_region(r, random_terrain_e3(NODIRECTION));
|
||||
|
||||
while (r) {
|
||||
if (r->land) {
|
||||
fset(r, RF_MARK);
|
||||
regionqueue_push(&island, r);
|
||||
}
|
||||
if (nsize<minsize) {
|
||||
nsize += random_neighbours(r, &rlist, &random_terrain_e3);
|
||||
} else {
|
||||
nsize += random_neighbours(r, &rlist, &get_ocean);
|
||||
}
|
||||
r = regionqueue_pop(&rlist);
|
||||
}
|
||||
for (rlist=island;rlist;rlist=rlist->next) {
|
||||
r = rlist->data;
|
||||
if (fval(r, RF_MARK)) {
|
||||
region *rn[MAXDIRECTIONS];
|
||||
int n;
|
||||
unit * u;
|
||||
|
||||
freset(r, RF_MARK);
|
||||
get_neighbours(r, rn);
|
||||
for (n=0;n!=MAXDIRECTIONS;++n) {
|
||||
freset(rn[n], RF_MARK);
|
||||
}
|
||||
q = region_quality(r);
|
||||
if (q>1500 && nfactions<numfactions) {
|
||||
terraform_region(r, newterrain(T_PLAIN));
|
||||
minq = MIN(minq, q);
|
||||
maxq = MAX(maxq, q);
|
||||
prepare_starting_region(r);
|
||||
u = addplayer(r, addfaction("enno@eressea.de", itoa36(rng_int()), races,
|
||||
default_locale, 0));
|
||||
++nfactions;
|
||||
}
|
||||
}
|
||||
}
|
||||
return nfactions;
|
||||
}
|
||||
|
|
|
@ -39,9 +39,10 @@ extern int autoseed(newfaction ** players, int nsize, int max_agediff);
|
|||
extern newfaction * read_newfactions(const char * filename);
|
||||
extern void get_island(struct region * root, struct region_list ** rlist);
|
||||
extern int fix_demand(struct region *r);
|
||||
extern const struct terrain_type * random_terrain(boolean use_distribution);
|
||||
extern const struct terrain_type * random_terrain(const struct terrain_type * terrains[], int distribution[], int size);
|
||||
|
||||
extern int seed_adamantium(struct region * r, int base);
|
||||
extern int build_island_e3(short x, short y, int numfactions, int minsize);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
|
|
@ -28,6 +28,7 @@
|
|||
#include <modules/arena.h>
|
||||
#endif
|
||||
#include <modules/wormhole.h>
|
||||
#include <modules/autoseed.h>
|
||||
#if DUNGEON_MODULE
|
||||
#include <modules/dungeon.h>
|
||||
#endif
|
||||
|
@ -56,6 +57,7 @@
|
|||
#include <items/itemtypes.h>
|
||||
|
||||
#include <util/log.h>
|
||||
#include <util/rng.h>
|
||||
#include <util/base36.h>
|
||||
#include <util/storage.h>
|
||||
|
||||
|
@ -727,6 +729,7 @@ handlekey(state * st, int c)
|
|||
region *r;
|
||||
char sbuffer[80];
|
||||
static char kbuffer[80];
|
||||
int n;
|
||||
|
||||
switch(c) {
|
||||
case FAST_RIGHT:
|
||||
|
@ -785,7 +788,11 @@ handlekey(state * st, int c)
|
|||
}
|
||||
break;
|
||||
case 'B':
|
||||
/*
|
||||
make_block((short)st->cursor.x, (short)st->cursor.y, 6, select_terrain(st, NULL));
|
||||
*/
|
||||
n = rng_int() % 8 + 8;
|
||||
build_island_e3((short)st->cursor.x, (short)st->cursor.y, n, n*4);
|
||||
st->modified = 1;
|
||||
st->wnd_info->update |= 1;
|
||||
st->wnd_status->update |= 1;
|
||||
|
|
Loading…
Reference in New Issue