forked from github/server
unit::lastorder entfernt. Das Konzept eines einzelnen langen Befehles hat ausgedient, spätestens seit @ existiert.
This commit is contained in:
parent
9b0daeced4
commit
092b249060
27 changed files with 695 additions and 622 deletions
|
@ -38,7 +38,6 @@
|
|||
# include "option.h"
|
||||
#endif
|
||||
#include "moved.h"
|
||||
#include "aggressive.h"
|
||||
#include "variable.h"
|
||||
|
||||
/* util includes */
|
||||
|
@ -74,6 +73,5 @@ init_attributes(void)
|
|||
#ifdef USE_UGROUPS
|
||||
init_ugroup();
|
||||
#endif
|
||||
init_aggressive();
|
||||
init_variable();
|
||||
}
|
||||
|
|
|
@ -173,9 +173,6 @@
|
|||
<Filter
|
||||
Name="Header"
|
||||
Filter="*.h">
|
||||
<File
|
||||
RelativePath=".\aggressive.h">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\attributes.h">
|
||||
</File>
|
||||
|
@ -246,9 +243,6 @@
|
|||
RelativePath=".\viewrange.h">
|
||||
</File>
|
||||
</Filter>
|
||||
<File
|
||||
RelativePath=".\aggressive.c">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\at_movement.c">
|
||||
</File>
|
||||
|
|
|
@ -760,12 +760,17 @@ cr_output_unit(FILE * F, const region * r,
|
|||
}
|
||||
/* default commands */
|
||||
fprintf(F, "COMMANDS\n");
|
||||
#ifdef LASTORDER
|
||||
if (u->lastorder) {
|
||||
fwriteorder(F, u->lastorder, f->locale);
|
||||
fputc('\n', F);
|
||||
}
|
||||
#endif
|
||||
for (ord = u->orders; ord; ord = ord->next) {
|
||||
if (is_persistent(ord) && ord!=u->lastorder) {
|
||||
#ifdef LASTORDER
|
||||
if (ord==u->lastorder) continue;
|
||||
#endif
|
||||
if (is_persistent(ord)) {
|
||||
fwriteorder(F, ord, f->locale);
|
||||
fputc('\n', F);
|
||||
}
|
||||
|
|
|
@ -1534,21 +1534,21 @@ make_cmd(unit * u, struct order * ord)
|
|||
if (p == P_ROAD) {
|
||||
direction_t d;
|
||||
if(r->planep && fval(r->planep, PFL_NOBUILD)) {
|
||||
cmistake(u, u->thisorder, 275, MSG_PRODUCE);
|
||||
cmistake(u, ord, 275, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
d = finddirection(getstrtoken(), u->faction->locale);
|
||||
if (d!=NODIRECTION) {
|
||||
if(r->planep && fval(r->planep, PFL_NOBUILD)) {
|
||||
cmistake(u, u->thisorder, 94, MSG_PRODUCE);
|
||||
cmistake(u, ord, 94, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
build_road(r, u, m, d);
|
||||
} else cmistake(u, u->thisorder, 71, MSG_PRODUCE);
|
||||
} else cmistake(u, ord, 71, MSG_PRODUCE);
|
||||
return;
|
||||
} else if (p == P_SHIP) {
|
||||
if(r->planep && fval(r->planep, PFL_NOBUILD)) {
|
||||
cmistake(u, u->thisorder, 276, MSG_PRODUCE);
|
||||
cmistake(u, ord, 276, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
continue_ship(r, u, m);
|
||||
|
@ -1592,19 +1592,19 @@ make_cmd(unit * u, struct order * ord)
|
|||
|
||||
if (stype != NOSHIP) {
|
||||
if(r->planep && fval(r->planep, PFL_NOBUILD)) {
|
||||
cmistake(u, u->thisorder, 276, MSG_PRODUCE);
|
||||
cmistake(u, ord, 276, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
create_ship(r, u, stype, m);
|
||||
create_ship(r, u, stype, m, ord);
|
||||
return;
|
||||
}
|
||||
|
||||
if (btype != NOBUILDING) {
|
||||
if(r->planep && fval(r->planep, PFL_NOBUILD)) {
|
||||
cmistake(u, u->thisorder, 94, MSG_PRODUCE);
|
||||
cmistake(u, ord, 94, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
build_building(u, btype, m);
|
||||
build_building(u, btype, m, ord);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1613,7 +1613,7 @@ make_cmd(unit * u, struct order * ord)
|
|||
return;
|
||||
}
|
||||
|
||||
cmistake(u, u->thisorder, 125, MSG_PRODUCE);
|
||||
cmistake(u, ord, 125, MSG_PRODUCE);
|
||||
}
|
||||
/* ------------------------------------------------------------- */
|
||||
|
||||
|
|
|
@ -139,7 +139,9 @@ restart_race(unit *u, const race * rc)
|
|||
*ordp = ord->next;
|
||||
ord->next = NULL;
|
||||
if (u->thisorder == ord) set_order(&u->thisorder, NULL);
|
||||
#ifdef LASTORDER
|
||||
if (u->lastorder == ord) set_order(&u->lastorder, NULL);
|
||||
#endif
|
||||
} else {
|
||||
ordp = &ord->next;
|
||||
}
|
||||
|
@ -2662,6 +2664,7 @@ instant_orders(void)
|
|||
unit * u;
|
||||
for (u = r->units; u; u = u->next) {
|
||||
order * ord;
|
||||
freset(u, UFL_MOVED);
|
||||
for (ord = u->orders; ord; ord = ord->next) {
|
||||
switch (get_keyword(ord)) {
|
||||
case K_URSPRUNG:
|
||||
|
@ -3413,86 +3416,48 @@ setdefaults (void)
|
|||
set_order(&u->thisorder, default_order(u->faction->locale));
|
||||
continue;
|
||||
}
|
||||
|
||||
#ifdef LASTORDER
|
||||
/* by default the default long order becomes the new long order. */
|
||||
u->thisorder = copy_order(u->lastorder);
|
||||
|
||||
u->thisorder = duplicate_order(u->lastorder);
|
||||
#endif
|
||||
/* check all orders for a potential new long order this round: */
|
||||
for (ord = u->orders; ord; ord = ord->next) {
|
||||
keyword_t keyword = get_keyword(ord);
|
||||
|
||||
switch (keyword) {
|
||||
/* Wenn gehandelt wird, darf kein langer Befehl ausgeführt
|
||||
* werden. Da Handel erst nach anderen langen Befehlen kommt,
|
||||
* muß das vorher abgefangen werden. Wir merken uns also
|
||||
* hier, ob die Einheit handelt. */
|
||||
case K_BUY:
|
||||
case K_SELL:
|
||||
/* Wenn die Einheit handelt, muß der Default-Befehl gelöscht
|
||||
* werden. */
|
||||
trade = true;
|
||||
break;
|
||||
|
||||
case K_CAST:
|
||||
/* dient dazu, das neben Zaubern kein weiterer Befehl
|
||||
* ausgeführt werden kann, Zaubern ist ein kurzer Befehl */
|
||||
set_order(&u->thisorder, NULL);
|
||||
break;
|
||||
|
||||
case K_MAKE:
|
||||
/* Falls wir MACHE TEMP haben, ignorieren wir es. Alle anderen
|
||||
* Arten von MACHE zaehlen aber als neue defaults und werden
|
||||
* behandelt wie die anderen (deswegen kein break nach case
|
||||
* K_MAKE) - und in thisorder (der aktuelle 30-Tage Befehl)
|
||||
* abgespeichert). */
|
||||
init_tokens(ord); /* initialize token-parser */
|
||||
skip_token();
|
||||
if (getparam(u->faction->locale) == P_TEMP) break;
|
||||
/* else fall through */
|
||||
|
||||
#if GROWING_TREES
|
||||
case K_PFLANZE:
|
||||
#endif
|
||||
case K_BESIEGE:
|
||||
case K_ENTERTAIN:
|
||||
case K_TAX:
|
||||
case K_RESEARCH:
|
||||
case K_SPY:
|
||||
case K_STEAL:
|
||||
case K_SABOTAGE:
|
||||
case K_STUDY:
|
||||
case K_TEACH:
|
||||
case K_ZUECHTE:
|
||||
case K_BIETE:
|
||||
case K_PIRACY:
|
||||
/* Über dieser Zeile nur Befehle, die auch eine idle Faction machen darf */
|
||||
if (idle (u->faction)) {
|
||||
set_order(&u->thisorder, default_order(u->faction->locale));
|
||||
} else {
|
||||
set_order(&u->thisorder, ord);
|
||||
}
|
||||
break;
|
||||
|
||||
case K_FOLLOW:
|
||||
/* FOLLOW is only a long order if we are following a ship. */
|
||||
init_tokens(ord);
|
||||
skip_token();
|
||||
if (getparam(u->faction->locale) == P_SHIP) {
|
||||
set_order(&u->thisorder, ord);
|
||||
}
|
||||
break;
|
||||
|
||||
case K_ROUTE:
|
||||
case K_WORK:
|
||||
case K_DRIVE:
|
||||
case K_MOVE:
|
||||
case K_WEREWOLF:
|
||||
if (is_exclusive(ord)) {
|
||||
/* Über dieser Zeile nur Befehle, die auch eine idle Faction machen darf */
|
||||
if (idle(u->faction)) {
|
||||
set_order(&u->thisorder, default_order(u->faction->locale));
|
||||
} else {
|
||||
set_order(&u->thisorder, ord);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
} else {
|
||||
keyword_t keyword = get_keyword(ord);
|
||||
switch (keyword) {
|
||||
/* Wenn gehandelt wird, darf kein langer Befehl ausgeführt
|
||||
* werden. Da Handel erst nach anderen langen Befehlen kommt,
|
||||
* muß das vorher abgefangen werden. Wir merken uns also
|
||||
* hier, ob die Einheit handelt. */
|
||||
case K_BUY:
|
||||
case K_SELL:
|
||||
/* Wenn die Einheit handelt, muß der Default-Befehl gelöscht
|
||||
* werden. */
|
||||
trade = true;
|
||||
break;
|
||||
|
||||
/* Wird je diese Ausschliesslichkeit aufgehoben, muss man aufpassen
|
||||
* mit der Reihenfolge von Kaufen, Verkaufen etc., damit es Spielern
|
||||
* nicht moeglich ist, Schulden zu machen. */
|
||||
case K_CAST:
|
||||
/* dient dazu, das neben Zaubern kein weiterer Befehl
|
||||
* ausgeführt werden kann, Zaubern ist ein kurzer Befehl */
|
||||
set_order(&u->thisorder, NULL);
|
||||
break;
|
||||
|
||||
case K_WEREWOLF:
|
||||
set_order(&u->thisorder, ord);
|
||||
break;
|
||||
|
||||
/* Wird je diese Ausschliesslichkeit aufgehoben, muss man aufpassen
|
||||
* mit der Reihenfolge von Kaufen, Verkaufen etc., damit es Spielern
|
||||
* nicht moeglich ist, Schulden zu machen. */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3512,21 +3477,19 @@ setdefaults (void)
|
|||
* die Einheitsnummer ungueltig). Auch Attackiere sollte nie in
|
||||
* den Default übernommen werden */
|
||||
|
||||
#ifdef LASTORDER
|
||||
switch (get_keyword(u->thisorder)) {
|
||||
case K_MOVE:
|
||||
case K_BIETE:
|
||||
case K_ATTACK:
|
||||
case K_WEREWOLF:
|
||||
case NOKEYWORD:
|
||||
/* these can never be default orders */
|
||||
break;
|
||||
|
||||
default:
|
||||
set_order(&u->lastorder, u->thisorder);
|
||||
/* Attackiere sollte niemals Default werden */
|
||||
if (get_keyword(u->lastorder) == K_ATTACK) {
|
||||
set_order(&u->lastorder, default_order(u->faction->locale));
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -3648,6 +3611,7 @@ monthly_healing(void)
|
|||
}
|
||||
}
|
||||
|
||||
#ifdef LASTORDER
|
||||
static void
|
||||
defaultorders (void)
|
||||
{
|
||||
|
@ -3675,6 +3639,7 @@ defaultorders (void)
|
|||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/* ************************************************************ */
|
||||
/* GANZ WICHTIG! ALLE GEÄNDERTEN SPRÜCHE NEU ANZEIGEN */
|
||||
|
@ -3900,8 +3865,10 @@ processorders (void)
|
|||
monthly_healing();
|
||||
regeneration_magiepunkte();
|
||||
|
||||
#ifdef LASTORDER
|
||||
puts(" - Defaults setzen");
|
||||
defaultorders();
|
||||
#endif
|
||||
|
||||
puts(" - Unterhaltskosten, Nachfrage, Seuchen, Wachstum, Auswanderung");
|
||||
demographics();
|
||||
|
|
|
@ -32,7 +32,6 @@
|
|||
/* attributes includes */
|
||||
#include <attributes/targetregion.h>
|
||||
#include <attributes/hate.h>
|
||||
#include <attributes/aggressive.h>
|
||||
|
||||
/* spezialmonster */
|
||||
#include <spells/alp.h>
|
||||
|
@ -74,87 +73,69 @@
|
|||
static boolean
|
||||
is_waiting(const unit * u)
|
||||
{
|
||||
if (fval(u, UFL_ISNEW)) return true;
|
||||
if (get_keyword(u->lastorder)==K_WAIT) return true;
|
||||
|
||||
return false;
|
||||
if (fval(u, UFL_ISNEW|UFL_MOVED)) return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
static boolean
|
||||
static order *
|
||||
monster_attack(unit * u, const unit * target)
|
||||
{
|
||||
char zText[20];
|
||||
|
||||
if (u->region!=target->region) return false;
|
||||
if (!cansee(u->faction, u->region, target, 0)) return false;
|
||||
if (is_waiting(u)) return false;
|
||||
if (u->region!=target->region) return NULL;
|
||||
if (u->faction==target->faction) return NULL;
|
||||
if (!cansee(u->faction, u->region, target, 0)) return NULL;
|
||||
if (is_waiting(u)) return NULL;
|
||||
|
||||
sprintf(zText, "%s %s",
|
||||
locale_string(u->faction->locale, keywords[K_ATTACK]), unitid(target));
|
||||
addlist(&u->orders, parse_order(zText, u->faction->locale));
|
||||
return true;
|
||||
return parse_order(zText, u->faction->locale);
|
||||
}
|
||||
|
||||
void
|
||||
taxed_by_monster(unit * u)
|
||||
{
|
||||
const char * zText = locale_string(u->faction->locale, keywords[K_TAX]);
|
||||
addlist(&u->orders, parse_order(zText, u->faction->locale));
|
||||
}
|
||||
|
||||
static boolean
|
||||
static order *
|
||||
get_money_for_dragon(region * r, unit * u, int wanted)
|
||||
{
|
||||
unit *u2;
|
||||
int n;
|
||||
|
||||
/* attackiere bewachende einheiten */
|
||||
for (u2 = r->units; u2; u2 = u2->next) {
|
||||
if (u2 != u && getguard(u2)&GUARD_TAX) {
|
||||
order * ord = monster_attack(u, u2);
|
||||
if (ord) addlist(&u->orders, ord);
|
||||
}
|
||||
}
|
||||
|
||||
for (u2 = r->units; u2; u2 = u2->next)
|
||||
if (u2 != u && getguard(u2)&GUARD_TAX)
|
||||
monster_attack(u, u2);
|
||||
|
||||
/* treibe steuern bei den bauern ein */
|
||||
|
||||
taxed_by_monster(u);
|
||||
|
||||
/* falls das genug geld ist, bleibt das monster hier */
|
||||
|
||||
if (rmoney(r) >= wanted)
|
||||
return true;
|
||||
|
||||
/* attackiere so lange die fremden, alteingesessenen einheiten mit geld
|
||||
* (einfach die reihenfolge der einheiten), bis das geld da ist. n
|
||||
* zaehlt das so erhaltene geld. */
|
||||
/* falls genug geld in der region ist, treiben wir steuern ein. */
|
||||
if (rmoney(r) >= wanted) {
|
||||
/* 5% chance, dass der drache aus einer laune raus attackiert */
|
||||
if (chance(0.95)) return parse_order(keywords[K_TAX], default_locale);
|
||||
}
|
||||
|
||||
/* falls der drache launisch ist, oder das regionssilber knapp, greift er alle an */
|
||||
n = 0;
|
||||
for (u2 = r->units; u2; u2 = u2->next)
|
||||
if (u2->faction != u->faction && get_money(u2)) {
|
||||
if (monster_attack(u, u2)) {
|
||||
n += get_money(u2);
|
||||
for (u2 = r->units; u2; u2 = u2->next) {
|
||||
if (u2->faction != u->faction && get_money(u2)) {
|
||||
if (getguard(u2) & GUARD_TAX) continue;
|
||||
else {
|
||||
order * ord = monster_attack(u, u2);
|
||||
if (ord) {
|
||||
addlist(&u->orders, ord);
|
||||
n += get_money(u2);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (n > wanted)
|
||||
break;
|
||||
}
|
||||
}
|
||||
/* falls die einnahmen erreicht werden, bleibt das monster noch eine
|
||||
/* falls die einnahmen erreicht werden, bleibt das monster noch eine
|
||||
* runde hier. */
|
||||
if (n + rmoney(r) >= wanted) {
|
||||
return parse_order(keywords[K_TAX], default_locale);
|
||||
}
|
||||
|
||||
if (n + rmoney(r) >= wanted)
|
||||
return true;
|
||||
|
||||
/* falls das geld, das wir haben, und das der angriffe zum leben
|
||||
* reicht, koennen wir uns fortbewegen. deswegen duerfen wir
|
||||
* steuereinnahmen nicht beruecksichtigen - wir bewegen uns ja fort. */
|
||||
|
||||
if (get_money(u) + n >= MAINTENANCE)
|
||||
return false;
|
||||
|
||||
/* falls wir auch mit angriffe nicht genug geld zum wandern haben,
|
||||
* muessen wir wohl oder uebel hier bleiben. vielleicht wurden ja genug
|
||||
* steuern eingetrieben */
|
||||
|
||||
return true;
|
||||
/* wenn wir NULL zurückliefern, macht der drache was anderes, z.b. weggehen */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static int
|
||||
|
@ -314,8 +295,8 @@ treeman_neighbour(region * r)
|
|||
return NODIRECTION;
|
||||
}
|
||||
|
||||
static void
|
||||
move_monster(region * r, unit * u)
|
||||
static order *
|
||||
monster_move(region * r, unit * u)
|
||||
{
|
||||
direction_t d = NODIRECTION;
|
||||
|
||||
|
@ -337,11 +318,11 @@ move_monster(region * r, unit * u)
|
|||
* den ozean */
|
||||
|
||||
if (d == NODIRECTION)
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
sprintf(buf, "%s %s", locale_string(u->faction->locale, keywords[K_MOVE]), locale_string(u->faction->locale, directions[d]));
|
||||
|
||||
addlist(&u->orders, parse_order(buf, u->faction->locale));
|
||||
return parse_order(buf, u->faction->locale);
|
||||
}
|
||||
|
||||
/* Wir machen das mal autoconf-style: */
|
||||
|
@ -412,8 +393,8 @@ set_new_dragon_target(unit * u, region * r, int range)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static boolean
|
||||
set_movement_order(unit * u, const region * target, int moves, boolean (*allowed)(const region *, const region *))
|
||||
static order *
|
||||
make_movement_order(unit * u, const region * target, int moves, boolean (*allowed)(const region *, const region *))
|
||||
{
|
||||
region * r = u->region;
|
||||
region ** plan = path_find(r, target, DRAGON_RANGE*5, allowed);
|
||||
|
@ -421,7 +402,7 @@ set_movement_order(unit * u, const region * target, int moves, boolean (*allowed
|
|||
char * c;
|
||||
|
||||
if (plan==NULL) {
|
||||
return false;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
strcpy(buf, locale_string(u->faction->locale, keywords[K_MOVE]));
|
||||
|
@ -437,12 +418,10 @@ set_movement_order(unit * u, const region * target, int moves, boolean (*allowed
|
|||
c += strlen(c);
|
||||
}
|
||||
|
||||
set_order(&u->lastorder, parse_order(buf, u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have both increased the refcount */
|
||||
return true;
|
||||
return parse_order(buf, u->faction->locale);
|
||||
}
|
||||
|
||||
static void
|
||||
static order *
|
||||
monster_seeks_target(region *r, unit *u)
|
||||
{
|
||||
direction_t d;
|
||||
|
@ -465,7 +444,10 @@ monster_seeks_target(region *r, unit *u)
|
|||
}
|
||||
|
||||
/* TODO: prüfen, ob target überhaupt noch existiert... */
|
||||
if(!target) return; /* this is a bug workaround! remove!! */
|
||||
if (!target) {
|
||||
log_error(("Monster '%s' hat kein Ziel!\n", unitname(u)));
|
||||
return NULL; /* this is a bug workaround! remove!! */
|
||||
}
|
||||
|
||||
if(r == target->region ) { /* Wir haben ihn! */
|
||||
if (u->race == new_race[RC_ALP]) {
|
||||
|
@ -474,7 +456,7 @@ monster_seeks_target(region *r, unit *u)
|
|||
else {
|
||||
assert(!"Seeker-Monster hat keine Aktion fuer Ziel");
|
||||
}
|
||||
return;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Simpler Ansatz: Nachbarregion mit gerinster Distanz suchen.
|
||||
|
@ -500,9 +482,9 @@ monster_seeks_target(region *r, unit *u)
|
|||
}
|
||||
|
||||
if( d == NODIRECTION )
|
||||
return;
|
||||
return NULL;
|
||||
sprintf(buf, "%s %s", locale_string(u->faction->locale, keywords[K_MOVE]), locale_string(u->faction->locale, directions[d]));
|
||||
addlist(&u->orders, parse_order(buf, u->faction->locale));
|
||||
return parse_order(buf, u->faction->locale);
|
||||
}
|
||||
|
||||
unit *
|
||||
|
@ -535,61 +517,18 @@ random_unit(const region * r)
|
|||
return u;
|
||||
}
|
||||
|
||||
static boolean
|
||||
random_attack_by_monster(const region * r, unit * u)
|
||||
static void
|
||||
monster_attacks(unit * u)
|
||||
{
|
||||
boolean success = false;
|
||||
unit *target;
|
||||
int kill, max;
|
||||
int tries = 0;
|
||||
int attacked = 0;
|
||||
region * r = u->region;
|
||||
unit * u2;
|
||||
|
||||
switch (old_race(u->race)) {
|
||||
case RC_FIREDRAGON:
|
||||
kill = 25;
|
||||
max = 50;
|
||||
break;
|
||||
case RC_DRAGON:
|
||||
kill = 100;
|
||||
max = 200;
|
||||
break;
|
||||
case RC_WYRM:
|
||||
kill = 400;
|
||||
max = 800;
|
||||
break;
|
||||
default:
|
||||
kill = 1;
|
||||
max = 1;
|
||||
}
|
||||
|
||||
kill *= u->number;
|
||||
max *= u->number;
|
||||
|
||||
do {
|
||||
tries++;
|
||||
target = random_unit(r);
|
||||
if (target
|
||||
&& target != u
|
||||
&& humanoidrace(target->race)
|
||||
&& !illusionaryrace(target->race)
|
||||
&& target->number <= max)
|
||||
{
|
||||
if (monster_attack(u, target)) {
|
||||
unit * u2;
|
||||
success = true;
|
||||
for (u2 = r->units; u2; u2 = u2->next) {
|
||||
if (u2->faction->no == MONSTER_FACTION
|
||||
&& rand() % 100 < 75)
|
||||
{
|
||||
monster_attack(u2, target);
|
||||
}
|
||||
}
|
||||
attacked += target->number;
|
||||
}
|
||||
}
|
||||
}
|
||||
while (attacked < kill && tries < 10);
|
||||
return success;
|
||||
for (u2=r->units;u2;u2=u2->next) {
|
||||
if (chance(0.75)) {
|
||||
order * ord = monster_attack(u, u2);
|
||||
if (ord) addlist(&u->orders, ord);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -741,12 +680,13 @@ random_growl(void)
|
|||
|
||||
extern attrib_type at_direction;
|
||||
|
||||
static void
|
||||
learn_monster(unit *u)
|
||||
static order *
|
||||
monster_learn(unit *u)
|
||||
{
|
||||
int c = 0;
|
||||
int n;
|
||||
skill * sv;
|
||||
const struct locale * lang = u->faction->locale;
|
||||
|
||||
/* Monster lernt ein zufälliges Talent aus allen, in denen es schon
|
||||
* Lerntage hat. */
|
||||
|
@ -755,7 +695,7 @@ learn_monster(unit *u)
|
|||
if (sv->level>0) ++c;
|
||||
}
|
||||
|
||||
if(c == 0) return;
|
||||
if(c == 0) return NULL;
|
||||
|
||||
n = rand()%c + 1;
|
||||
c = 0;
|
||||
|
@ -763,14 +703,13 @@ learn_monster(unit *u)
|
|||
for (sv = u->skills; sv != u->skills + u->skill_size; ++sv) {
|
||||
if (sv->level>0) {
|
||||
if (++c == n) {
|
||||
sprintf(buf, "%s %s", locale_string(u->faction->locale, keywords[K_STUDY]),
|
||||
skillname(sv->id, u->faction->locale));
|
||||
set_order(&u->thisorder, parse_order(buf, u->faction->locale));
|
||||
free_order(u->thisorder); /* parse_order & set_order have both increased the refcount */
|
||||
break;
|
||||
sprintf(buf, "%s %s", locale_string(lang, keywords[K_STUDY]),
|
||||
skillname(sv->id, lang));
|
||||
return parse_order(buf, lang);
|
||||
}
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -810,6 +749,47 @@ check_overpopulated(unit *u)
|
|||
}
|
||||
|
||||
static void
|
||||
recruit_dracoids(unit * dragon, int size)
|
||||
{
|
||||
faction * f = dragon->faction;
|
||||
region * r = dragon->region;
|
||||
const struct item_type * weapon = NULL;
|
||||
order * new_order;
|
||||
unit *un = createunit(r, f, size, new_race[RC_DRACOID]);
|
||||
|
||||
name_unit(un);
|
||||
change_money(dragon, -un->number * 50);
|
||||
|
||||
set_level(un, SK_SPEAR, (3 + rand() % 4));
|
||||
set_level(un, SK_SWORD, (3 + rand() % 4));
|
||||
set_level(un, SK_LONGBOW, (2 + rand() % 3));
|
||||
|
||||
switch (rand() % 3) {
|
||||
case 0:
|
||||
weapon = olditemtype[I_LONGBOW];
|
||||
break;
|
||||
case 1:
|
||||
weapon = olditemtype[I_SWORD];
|
||||
break;
|
||||
default:
|
||||
weapon = olditemtype[I_SPEAR];
|
||||
break;
|
||||
}
|
||||
i_change(&un->items, weapon, un->number);
|
||||
if (weapon->rtype->wtype->flags & WTF_MISSILE) un->status = ST_BEHIND;
|
||||
else un->status = ST_FIGHT;
|
||||
|
||||
sprintf(buf, "%s \"%s\"", keywords[K_STUDY], skillname(weapon->rtype->wtype->skill, f->locale));
|
||||
new_order = parse_order(buf, default_locale);
|
||||
#ifdef LASTORDER
|
||||
set_order(&un->lastorder, new_order);
|
||||
free_order(new_order);
|
||||
#else
|
||||
addlist(&un->orders, new_order);
|
||||
#endif
|
||||
}
|
||||
|
||||
static order *
|
||||
plan_dragon(unit * u)
|
||||
{
|
||||
attrib * ta = a_find(u->attribs, &at_targetregion);
|
||||
|
@ -819,6 +799,7 @@ plan_dragon(unit * u)
|
|||
int capacity = walkingcapacity(u);
|
||||
item ** itmp = &u->items;
|
||||
boolean move = false;
|
||||
order * long_order = NULL;
|
||||
|
||||
if (horses > 0) {
|
||||
change_resource(u, R_HORSE, - min(horses,(u->number*2)));
|
||||
|
@ -853,15 +834,16 @@ plan_dragon(unit * u)
|
|||
}
|
||||
}
|
||||
if (tr!=NULL) {
|
||||
assert(long_order==NULL);
|
||||
switch(old_race(u->race)) {
|
||||
case RC_FIREDRAGON:
|
||||
set_movement_order(u, tr, 4, allowed_dragon);
|
||||
long_order = make_movement_order(u, tr, 4, allowed_dragon);
|
||||
break;
|
||||
case RC_DRAGON:
|
||||
set_movement_order(u, tr, 3, allowed_dragon);
|
||||
long_order = make_movement_order(u, tr, 3, allowed_dragon);
|
||||
break;
|
||||
case RC_WYRM:
|
||||
set_movement_order(u, tr, 1, allowed_dragon);
|
||||
long_order = make_movement_order(u, tr, 1, allowed_dragon);
|
||||
break;
|
||||
}
|
||||
if (rand()%100 < 15) {
|
||||
|
@ -875,49 +857,28 @@ plan_dragon(unit * u)
|
|||
}
|
||||
}
|
||||
} else {
|
||||
if (!get_money_for_dragon(u->region, u, income(u))) {
|
||||
/* money is gone */
|
||||
/* we have no target. do we like it here, then? */
|
||||
long_order = get_money_for_dragon(u->region, u, income(u));
|
||||
if (long_order==NULL) {
|
||||
/* money is gone, need a new target */
|
||||
set_new_dragon_target(u, u->region, DRAGON_RANGE);
|
||||
}
|
||||
else if (u->race != new_race[RC_FIREDRAGON] && u->region->terrain!=T_OCEAN
|
||||
&& !(terrain[rterrain(u->region)].flags & FORBIDDEN_LAND)) {
|
||||
else if (u->race != new_race[RC_FIREDRAGON]) {
|
||||
/* neue dracoiden! */
|
||||
terrain_t t = rterrain(r);
|
||||
if (r->land && !(terrain[t].flags & FORBIDDEN_LAND)) {
|
||||
int ra = 20 + rand() % 100;
|
||||
if (get_money(u) > ra * 50 + 100 && rand() % 100 < 50)
|
||||
{
|
||||
const struct item_type * weapon = NULL;
|
||||
unit *un;
|
||||
un = createunit(u->region, findfaction(MONSTER_FACTION), ra, new_race[RC_DRACOID]);
|
||||
name_unit(un);
|
||||
change_money(u, -un->number * 50);
|
||||
|
||||
set_level(un, SK_SPEAR, (3 + rand() % 4));
|
||||
set_level(un, SK_SWORD, (3 + rand() % 4));
|
||||
set_level(un, SK_LONGBOW, (2 + rand() % 3));
|
||||
|
||||
switch (rand() % 3) {
|
||||
case 0:
|
||||
weapon = olditemtype[I_LONGBOW];
|
||||
break;
|
||||
case 1:
|
||||
weapon = olditemtype[I_SWORD];
|
||||
break;
|
||||
default:
|
||||
weapon = olditemtype[I_SPEAR];
|
||||
break;
|
||||
}
|
||||
i_change(&un->items, weapon, un->number);
|
||||
if (weapon->rtype->wtype->flags & WTF_MISSILE) un->status = ST_BEHIND;
|
||||
else un->status = ST_FIGHT;
|
||||
sprintf(buf, "%s \"%s\"", keywords[K_STUDY], skillname(weapon->rtype->wtype->skill, u->faction->locale));
|
||||
set_order(&un->lastorder, parse_order(buf, default_locale));
|
||||
}
|
||||
if (is_waiting(u)) {
|
||||
sprintf(buf, "%s \"%s\"", keywords[K_STUDY], skillname(SK_OBSERVATION, u->faction->locale));
|
||||
set_order(&u->thisorder, parse_order(buf, default_locale));
|
||||
set_order(&u->lastorder, u->thisorder);
|
||||
if (get_money(u) > ra * 50 + 100 && rand() % 100 < 50) {
|
||||
recruit_dracoids(u, ra);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (long_order==NULL) {
|
||||
sprintf(buf, "%s \"%s\"", keywords[K_STUDY], skillname(SK_OBSERVATION, u->faction->locale));
|
||||
long_order = parse_order(buf, default_locale);
|
||||
}
|
||||
return long_order;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -931,30 +892,32 @@ plan_monsters(void)
|
|||
|
||||
for (r = regions; r; r = r->next) {
|
||||
unit *u;
|
||||
double attack_chance = MONSTERATTACK;
|
||||
boolean attacking = false;
|
||||
|
||||
for (u = r->units; u; u = u->next) {
|
||||
boolean is_moving = false;
|
||||
attrib * ta;
|
||||
order * long_order = NULL;
|
||||
|
||||
/* Ab hier nur noch Befehle für NPC-Einheiten. */
|
||||
if (u->faction->no != MONSTER_FACTION) continue;
|
||||
|
||||
if (attack_chance>0.0) {
|
||||
if (chance(attack_chance)) attacking = true;
|
||||
attack_chance = 0.0;
|
||||
}
|
||||
|
||||
if (u->status>ST_BEHIND) u->status = ST_FIGHT; /* all monsters fight */
|
||||
/* Monster bekommen jede Runde ein paar Tage Wahrnehmung dazu */
|
||||
produceexp(u, SK_OBSERVATION, u->number);
|
||||
|
||||
/* Haben Drachen ihr Ziel erreicht? */
|
||||
ta = a_find(u->attribs, &at_targetregion);
|
||||
if (ta) {
|
||||
if (u->region == (region*)ta->data.v) {
|
||||
a_remove(&u->attribs, ta);
|
||||
set_order(&u->lastorder, parse_order(keywords[K_WAIT], u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
}
|
||||
else {
|
||||
is_moving = true;
|
||||
}
|
||||
}
|
||||
/* Befehle müssen jede Runde neu gegeben werden: */
|
||||
free_orders(&u->orders);
|
||||
|
||||
if (attacking) {
|
||||
monster_attacks(u);
|
||||
}
|
||||
/* units with a plan to kill get ATTACK orders: */
|
||||
ta = a_find(u->attribs, &at_hate);
|
||||
if (ta && !is_waiting(u)) {
|
||||
unit * tu = (unit *)ta->data.v;
|
||||
|
@ -963,62 +926,63 @@ plan_monsters(void)
|
|||
addlist(&u->orders, parse_order(buf, u->faction->locale));
|
||||
} else if (tu) {
|
||||
tu = findunitg(ta->data.i, NULL);
|
||||
if (tu) set_movement_order(u, tu->region, 2, allowed_walk);
|
||||
if (tu!=NULL) {
|
||||
long_order = make_movement_order(u, tu->region, 2, allowed_walk);
|
||||
}
|
||||
}
|
||||
else a_remove(&u->attribs, ta);
|
||||
}
|
||||
|
||||
if (!(fval(u, UFL_ISNEW)) && r->terrain != T_OCEAN) { /* Monster bewachen immer */
|
||||
/* All monsters guard the region: */
|
||||
if (!is_waiting(u) && r->land) {
|
||||
const char * cmd = locale_string(u->faction->locale, keywords[K_GUARD]);
|
||||
addlist(&u->orders, parse_order(cmd, u->faction->locale));
|
||||
}
|
||||
|
||||
/* Diese Verkettung ist krank und sollte durch eine 'vernünftige KI'
|
||||
* ersetzt werden. */
|
||||
|
||||
if( (u->race->flags & RCF_MOVERANDOM)
|
||||
&& (rand()%100<MOVECHANCE || check_overpopulated(u))) {
|
||||
move_monster(r, u);
|
||||
} else {
|
||||
boolean done = false;
|
||||
if((u->race->flags & RCF_ATTACKRANDOM) && is_moving == false)
|
||||
{
|
||||
double probability;
|
||||
attrib *a = a_find(u->attribs, &at_aggressive);
|
||||
|
||||
if (a) {
|
||||
probability = a->data.flt;
|
||||
} else {
|
||||
probability = MONSTERATTACK;
|
||||
}
|
||||
|
||||
if(chance(probability)) {
|
||||
done = random_attack_by_monster(r, u);
|
||||
}
|
||||
/* Einheiten mit Bewegungsplan kriegen ein NACH: */
|
||||
if (long_order==NULL) {
|
||||
attrib * ta = a_find(u->attribs, &at_targetregion);
|
||||
if (ta) {
|
||||
if (u->region == (region*)ta->data.v) {
|
||||
a_remove(&u->attribs, ta);
|
||||
}
|
||||
if (!done) {
|
||||
if(u->race == new_race[RC_SEASERPENT]) {
|
||||
set_order(&u->thisorder, parse_order(keywords[K_PIRACY], default_locale));
|
||||
set_order(&u->lastorder, u->thisorder);
|
||||
free_order(u->lastorder); /* parse_order & set_order have both increased the refcount */
|
||||
} else if(u->race->flags & RCF_LEARN) {
|
||||
learn_monster(u);
|
||||
}
|
||||
} else if (u->race->flags & RCF_MOVERANDOM) {
|
||||
if (rand()%100<MOVECHANCE || check_overpopulated(u)) {
|
||||
long_order = monster_move(r, u);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
if (long_order==NULL) {
|
||||
/* Ab hier noch nicht generalisierte Spezialbehandlungen. */
|
||||
|
||||
switch (old_race(u->race)) {
|
||||
case RC_ALP:
|
||||
monster_seeks_target(r, u);
|
||||
break;
|
||||
case RC_FIREDRAGON:
|
||||
case RC_DRAGON:
|
||||
case RC_WYRM:
|
||||
plan_dragon(u);
|
||||
break;
|
||||
case RC_SEASERPENT:
|
||||
long_order = parse_order(keywords[K_PIRACY], default_locale);
|
||||
break;
|
||||
case RC_ALP:
|
||||
long_order = monster_seeks_target(r, u);
|
||||
break;
|
||||
case RC_FIREDRAGON:
|
||||
case RC_DRAGON:
|
||||
case RC_WYRM:
|
||||
long_order = plan_dragon(u);
|
||||
break;
|
||||
default:
|
||||
if (u->race->flags & RCF_LEARN) {
|
||||
long_order = monster_learn(u);
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (long_order) {
|
||||
set_order(&u->thisorder, long_order);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, long_order);
|
||||
free_order(new_order); /* parse_order & set_order have both increased the refcount */
|
||||
#else
|
||||
addlist(&u->orders, long_order);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -308,9 +308,9 @@ get_unit(region * r, unit * u)
|
|||
addmessage(r, u->faction, buf, MSG_EVENT, ML_IMPORTANT);
|
||||
|
||||
newunit = createunit(r, u->faction, rand() % 20 + 3, u->faction->race);
|
||||
fset(newunit, UFL_ISNEW|UFL_MOVED);
|
||||
set_string(&newunit->name, "Dorfbewohner");
|
||||
set_money(newunit, (rand() % 26 + 10) * newunit->number);
|
||||
fset(newunit, UFL_ISNEW);
|
||||
if (fval(u, UFL_PARTEITARNUNG)) fset(newunit, UFL_PARTEITARNUNG);
|
||||
switch (rand() % 4) {
|
||||
case 0:
|
||||
|
@ -576,7 +576,7 @@ chaos(region * r)
|
|||
break;
|
||||
}
|
||||
if (mfac) set_money(u, u->number * (rand() % mfac));
|
||||
guard(u, GUARD_ALL);
|
||||
fset(u, UFL_ISNEW|UFL_MOVED);
|
||||
}
|
||||
case 2: /* Terrainveränderung */
|
||||
if (!(terrain[rterrain(r)].flags & FORBIDDEN_LAND)) {
|
||||
|
@ -1101,7 +1101,7 @@ godcurse(void)
|
|||
}
|
||||
}
|
||||
|
||||
static void
|
||||
static unit *
|
||||
split_unit(region * r, unit *u)
|
||||
{
|
||||
unit *u2 = createunit(r, u->faction, 0, u->race);
|
||||
|
@ -1109,11 +1109,8 @@ split_unit(region * r, unit *u)
|
|||
|
||||
set_string(&u2->name, u->name);
|
||||
set_string(&u2->display, u->display);
|
||||
set_order(&u2->thisorder, parse_order(keywords[K_WAIT], u->faction->locale));
|
||||
set_order(&u2->lastorder, u2->thisorder);
|
||||
free_order(u2->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
|
||||
transfermen(u, u2, newsize);
|
||||
return u2;
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -1126,7 +1123,8 @@ check_split(void)
|
|||
for(u=r->units;u;u=u->next) {
|
||||
if(u->faction->no == MONSTER_FACTION) {
|
||||
if(u->number > u->race->splitsize) {
|
||||
split_unit(r, u);
|
||||
unit * u2 = split_unit(r, u);
|
||||
fset(u2, UFL_ISNEW|UFL_MOVED);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1386,6 +1384,7 @@ randomevents(void)
|
|||
message * msg;
|
||||
if (rterrain(r) == T_OCEAN && rand()%10000 < 1) {
|
||||
u = createunit(r, findfaction(MONSTER_FACTION), 1, new_race[RC_SEASERPENT]);
|
||||
fset(u, UFL_ISNEW|UFL_MOVED);
|
||||
set_level(u, SK_MAGIC, 4);
|
||||
set_level(u, SK_OBSERVATION, 3);
|
||||
set_level(u, SK_STEALTH, 2);
|
||||
|
@ -1393,25 +1392,14 @@ randomevents(void)
|
|||
set_string(&u->name, "Seeschlange");
|
||||
}
|
||||
|
||||
if ((rterrain(r) == T_GLACIER
|
||||
|| rterrain(r) == T_SWAMP || rterrain(r) == T_DESERT)
|
||||
&& rand() % 10000 < (5 + 100 * chaosfactor(r))) {
|
||||
|
||||
switch (rand() % 10) {
|
||||
case 0:
|
||||
case 1:
|
||||
case 2:
|
||||
case 3:
|
||||
case 4:
|
||||
case 5:
|
||||
case 6:
|
||||
case 7:
|
||||
if ((rterrain(r) == T_GLACIER || rterrain(r) == T_SWAMP || rterrain(r) == T_DESERT) && rand() % 10000 < (5 + 100 * chaosfactor(r)))
|
||||
{
|
||||
if (chance(0.80)) {
|
||||
u = createunit(r, findfaction(MONSTER_FACTION), nrand(60, 20) + 1, new_race[RC_FIREDRAGON]);
|
||||
break;
|
||||
default:
|
||||
u = createunit(r, findfaction(MONSTER_FACTION), nrand(30, 20) + 1, new_race[RC_DRAGON]);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
u = createunit(r, findfaction(MONSTER_FACTION), nrand(30, 20) + 1, new_race[RC_DRAGON]);
|
||||
}
|
||||
fset(u, UFL_ISNEW|UFL_MOVED);
|
||||
|
||||
set_money(u, u->number * (rand() % 500 + 100));
|
||||
set_level(u, SK_MAGIC, 4);
|
||||
|
@ -1422,8 +1410,6 @@ randomevents(void)
|
|||
LOC(default_locale, rc_name(u->race, u->number!=1)), regionname(r, NULL));
|
||||
|
||||
name_unit(u);
|
||||
set_order(&u->lastorder, parse_order(keywords[K_WAIT], u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
|
||||
/* add message to the region */
|
||||
ADDMSG(&r->msgs,
|
||||
|
@ -1472,6 +1458,7 @@ randomevents(void)
|
|||
}
|
||||
|
||||
u = createunit(r, findfaction(MONSTER_FACTION), undead, rc);
|
||||
fset(u, UFL_ISNEW|UFL_MOVED);
|
||||
if ((rc == new_race[RC_SKELETON] || rc == new_race[RC_ZOMBIE]) && rand()%10 < 4) {
|
||||
set_item(u, I_RUSTY_SWORD, undead);
|
||||
if (rand()%10 < 3) {
|
||||
|
@ -1490,14 +1477,12 @@ randomevents(void)
|
|||
u->hp = unit_max_hp(u) * u->number;
|
||||
|
||||
deathcounts(r, -undead);
|
||||
set_order(&u->lastorder, parse_order(keywords[K_WAIT], u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
name_unit(u);
|
||||
name_unit(u);
|
||||
|
||||
log_printf("%d %s in %s.\n", u->number,
|
||||
LOC(default_locale, rc_name(u->race, u->number!=1)), regionname(r, NULL));
|
||||
log_printf("%d %s in %s.\n", u->number,
|
||||
LOC(default_locale, rc_name(u->race, u->number!=1)), regionname(r, NULL));
|
||||
|
||||
{
|
||||
{
|
||||
message * msg = msg_message("undeadrise", "region", r);
|
||||
add_message(&r->msgs, msg);
|
||||
for (u=r->units;u;u=u->next) freset(u->faction, FL_DH);
|
||||
|
@ -1566,9 +1551,7 @@ randomevents(void)
|
|||
rsettrees(r, trees);
|
||||
#endif
|
||||
u = createunit(r, findfaction(MONSTER_FACTION),treemen, new_race[RC_TREEMAN]);
|
||||
set_order(&u->lastorder, parse_order(keywords[K_WAIT], u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
/* guard(u, GUARD_ALL); kein auto-guard! erst in monster.c! */
|
||||
fset(u, UFL_ISNEW|UFL_MOVED);
|
||||
|
||||
set_level(u, SK_OBSERVATION, 2);
|
||||
if (u->number == 1)
|
||||
|
|
|
@ -1676,12 +1676,14 @@ order_template(FILE * F, faction * f)
|
|||
|
||||
/* If the lastorder begins with an @ it should have
|
||||
* been printed in the loop before. */
|
||||
#ifdef LASTORDER
|
||||
if (u->lastorder && !is_persistent(u->lastorder)) {
|
||||
strcpy(buf, " ");
|
||||
write_order(u->lastorder, u->faction->locale, buf+2, sizeof(buf)-2);
|
||||
rps_nowrap(F, buf);
|
||||
rnl(F);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
rps_nowrap(F, "");
|
||||
|
@ -3776,7 +3778,7 @@ report_init(void)
|
|||
add_function("spell", &eval_spell);
|
||||
|
||||
register_argtype("string", free, (void*(*)(void*))strdup);
|
||||
register_argtype("order", (void(*)(void*))free_order, (void*(*)(void*))copy_order);
|
||||
register_argtype("order", (void(*)(void*))free_order, (void*(*)(void*))duplicate_order);
|
||||
register_function((pf_generic)view_neighbours, "view_neighbours");
|
||||
register_function((pf_generic)view_regatta, "view_regatta");
|
||||
}
|
||||
|
|
|
@ -241,213 +241,215 @@ static void
|
|||
teach(unit * u, struct order * ord)
|
||||
{
|
||||
region * r = u->region;
|
||||
static char order[BUFSIZE];
|
||||
int teaching, i, j, count, academy=0;
|
||||
unit *u2;
|
||||
const char *s;
|
||||
skill_t sk;
|
||||
int teaching, i, j, count, academy=0;
|
||||
unit *u2;
|
||||
const char *s;
|
||||
skill_t sk = NOSKILL;
|
||||
|
||||
if ((u->race->flags & RCF_NOTEACH) || fval(u, UFL_WERE)) {
|
||||
cmistake(u, u->thisorder, 274, MSG_EVENT);
|
||||
return;
|
||||
}
|
||||
if ((u->race->flags & RCF_NOTEACH) || fval(u, UFL_WERE)) {
|
||||
cmistake(u, ord, 274, MSG_EVENT);
|
||||
return;
|
||||
}
|
||||
|
||||
if (r->planep && fval(r->planep, PFL_NOTEACH)) {
|
||||
cmistake(u, u->thisorder, 273, MSG_EVENT);
|
||||
return;
|
||||
}
|
||||
if (r->planep && fval(r->planep, PFL_NOTEACH)) {
|
||||
cmistake(u, ord, 273, MSG_EVENT);
|
||||
return;
|
||||
}
|
||||
|
||||
teaching = u->number * 30 * TEACHNUMBER;
|
||||
teaching = u->number * 30 * TEACHNUMBER;
|
||||
|
||||
if ((i = get_effect(u, oldpotiontype[P_FOOL])) > 0) { /* Trank "Dumpfbackenbrot" */
|
||||
i = min(i, u->number * TEACHNUMBER);
|
||||
/* Trank wirkt pro Schüler, nicht pro Lehrer */
|
||||
teaching -= i * 30;
|
||||
change_effect(u, oldpotiontype[P_FOOL], -i);
|
||||
j = teaching / 30;
|
||||
add_message(&u->faction->msgs, msg_message("teachdumb",
|
||||
"teacher amount", u, j));
|
||||
}
|
||||
if (teaching == 0) return;
|
||||
if ((i = get_effect(u, oldpotiontype[P_FOOL])) > 0) { /* Trank "Dumpfbackenbrot" */
|
||||
i = min(i, u->number * TEACHNUMBER);
|
||||
/* Trank wirkt pro Schüler, nicht pro Lehrer */
|
||||
teaching -= i * 30;
|
||||
change_effect(u, oldpotiontype[P_FOOL], -i);
|
||||
j = teaching / 30;
|
||||
add_message(&u->faction->msgs, msg_message("teachdumb",
|
||||
"teacher amount", u, j));
|
||||
}
|
||||
if (teaching == 0) return;
|
||||
|
||||
strcpy(order, locale_string(u->faction->locale, keywords[K_TEACH]));
|
||||
|
||||
u2 = 0;
|
||||
count = 0;
|
||||
u2 = 0;
|
||||
count = 0;
|
||||
|
||||
init_tokens(ord);
|
||||
skip_token();
|
||||
|
||||
#if TEACH_ALL
|
||||
if (getparam(u->faction->locale)==P_ANY) {
|
||||
unit * student = r->units;
|
||||
skill_t teachskill[MAXSKILLS];
|
||||
int i = 0;
|
||||
do {
|
||||
sk = getskill(u->faction->locale);
|
||||
teachskill[i++]=sk;
|
||||
} while (sk!=NOSKILL);
|
||||
while (teaching && student) {
|
||||
if (student->faction == u->faction) {
|
||||
if (getparam(u->faction->locale)==P_ANY) {
|
||||
unit * student = r->units;
|
||||
skill_t teachskill[MAXSKILLS];
|
||||
int i = 0;
|
||||
do {
|
||||
sk = getskill(u->faction->locale);
|
||||
teachskill[i++]=sk;
|
||||
} while (sk!=NOSKILL);
|
||||
while (teaching && student) {
|
||||
if (student->faction == u->faction) {
|
||||
#ifdef NEW_DAEMONHUNGER_RULE
|
||||
if (LongHunger(student)) continue;
|
||||
#else
|
||||
if (fval(student, UFL_HUNGER)) continue;
|
||||
#endif
|
||||
if (get_keyword(student->thisorder) == K_STUDY) {
|
||||
/* Input ist nun von student->thisorder !! */
|
||||
init_tokens(student->thisorder);
|
||||
skip_token();
|
||||
sk = getskill(student->faction->locale);
|
||||
if (sk!=NOSKILL && teachskill[0]!=NOSKILL) {
|
||||
for (i=0;teachskill[i]!=NOSKILL;++i) if (sk==teachskill[i]) break;
|
||||
sk = teachskill[i];
|
||||
}
|
||||
if (sk != NOSKILL && eff_skill_study(u, sk, r)-TEACHDIFFERENCE > eff_skill_study(student, sk, r)) {
|
||||
teaching -= teach_unit(u, student, teaching, sk, true, &academy);
|
||||
}
|
||||
}
|
||||
}
|
||||
student = student->next;
|
||||
}
|
||||
#ifdef TEACH_FRIENDS
|
||||
while (teaching && student) {
|
||||
if (student->faction != u->faction && alliedunit(u, student->faction, HELP_GUARD)) {
|
||||
#ifdef NEW_DAEMONHUNGER_RULE
|
||||
if (LongHunger(student)) continue;
|
||||
if (LongHunger(student)) continue;
|
||||
#else
|
||||
if (fval(student, UFL_HUNGER)) continue;
|
||||
#endif
|
||||
if (get_keyword(student->thisorder) == K_STUDY) {
|
||||
/* Input ist nun von student->thisorder !! */
|
||||
if (get_keyword(student->thisorder) == K_STUDY) {
|
||||
/* Input ist nun von student->thisorder !! */
|
||||
init_tokens(student->thisorder);
|
||||
skip_token();
|
||||
sk = getskill(student->faction->locale);
|
||||
if (sk != NOSKILL && eff_skill_study(u, sk, r)-TEACHDIFFERENCE >= eff_skill(student, sk, r)) {
|
||||
teaching -= teach_unit(u, student, teaching, sk, true, &academy);
|
||||
}
|
||||
}
|
||||
}
|
||||
student = student->next;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else
|
||||
#endif
|
||||
for (;;) {
|
||||
/* Da später tokens aus (u2->thisorder) verwendet werden,
|
||||
* muß hier wieder von vorne gelesen werden. Also merken wir uns, an
|
||||
* welcher Stelle wir hier waren...
|
||||
* TODO: Optimierung wäre hier wirklich sinnvoll
|
||||
*
|
||||
* Beispiel count = 1: LEHRE 101 102 103
|
||||
*
|
||||
* LEHRE und 101 wird gelesen (und ignoriert), und dann wird
|
||||
* getunit die einheit 102 zurück liefern. */
|
||||
|
||||
init_tokens(u->thisorder);
|
||||
skip_token();
|
||||
for (j = count; j; j--) getstrtoken();
|
||||
|
||||
u2 = getunit(r, u->faction);
|
||||
|
||||
/* Falls keine Unit gefunden, abbrechen - außer es gibt überhaupt keine
|
||||
* Unit, dann gibt es zusätzlich noch einen Fehler */
|
||||
|
||||
if (!u2) {
|
||||
|
||||
/* Finde den string, der den Fehler verursacht hat */
|
||||
|
||||
init_tokens(u->thisorder);
|
||||
skip_token();
|
||||
for (j = count; j; j--) getstrtoken();
|
||||
|
||||
s = getstrtoken();
|
||||
|
||||
/* Falls es keinen String gibt, ist die Liste der Einheiten zuende */
|
||||
|
||||
if (!s[0])
|
||||
return;
|
||||
|
||||
/* Beginne die Fehlermeldung */
|
||||
|
||||
strcpy(buf, "Die Einheit '");
|
||||
|
||||
if (findparam(s, u->faction->locale) == P_TEMP) {
|
||||
/* Für: "Die Einheit 'TEMP ZET' wurde nicht gefunden" oder "Die Einheit
|
||||
* 'TEMP' wurde nicht gefunden" */
|
||||
|
||||
scat(s);
|
||||
s = getstrtoken();
|
||||
if (s[0])
|
||||
scat(" ");
|
||||
|
||||
/* Um nachher weiter einlesen zu koennen */
|
||||
count++;
|
||||
}
|
||||
scat(s);
|
||||
scat("' wurde nicht gefunden");
|
||||
mistake(u, u->thisorder, buf, MSG_EVENT);
|
||||
|
||||
count++;
|
||||
continue;
|
||||
}
|
||||
/* Defaultorder zusammenbauen. TEMP-Einheiten werden automatisch in
|
||||
* ihre neuen Nummern übersetzt. */
|
||||
strcat(order, " ");
|
||||
strcat(order, unitid(u2));
|
||||
set_order(&u->lastorder, parse_order(order, u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
|
||||
/* Wir müssen nun hochzählen, wieviele Einheiten wir schon abgearbeitet
|
||||
* haben, damit mit getstrtoken() die richtige Einheit geholt werden kann.
|
||||
* Falls u2 ein Alias hat, ist sie neu, und es wurde ein TEMP verwendet, um
|
||||
* sie zu beschreiben. */
|
||||
|
||||
count++;
|
||||
if (ualias(u2))
|
||||
count++;
|
||||
|
||||
if (get_keyword(u2->thisorder) != K_STUDY) {
|
||||
add_message(&u->faction->msgs,
|
||||
msg_feedback(u, u->thisorder, "teach_nolearn", "student", u2));
|
||||
continue;
|
||||
}
|
||||
/* Input ist nun von u2->thisorder !! */
|
||||
init_tokens(u2->thisorder);
|
||||
skip_token();
|
||||
sk = getskill(u2->faction->locale);
|
||||
if (sk == NOSKILL) {
|
||||
add_message(&u->faction->msgs,
|
||||
msg_feedback(u, u->thisorder, "teach_nolearn", "student", u2));
|
||||
continue;
|
||||
}
|
||||
|
||||
/* u is teacher, u2 is student */
|
||||
if (eff_skill_study(u2, sk, r) > eff_skill_study(u, sk, r)-TEACHDIFFERENCE) {
|
||||
add_message(&u->faction->msgs,
|
||||
msg_feedback(u, u->thisorder, "teach_asgood", "student", u2));
|
||||
continue;
|
||||
}
|
||||
if (sk == SK_MAGIC) {
|
||||
/* ist der Magier schon spezialisiert, so versteht er nur noch
|
||||
* Lehrer seines Gebietes */
|
||||
if (find_magetype(u2) != 0
|
||||
&& find_magetype(u) != find_magetype(u2))
|
||||
{
|
||||
sprintf(buf, "%s versteht unsere Art von Magie nicht", unitname(u2));
|
||||
mistake(u, u->thisorder, buf, MSG_EVENT);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
teaching -= teach_unit(u, u2, teaching, sk, false, &academy);
|
||||
|
||||
sk = getskill(student->faction->locale);
|
||||
if (sk!=NOSKILL && teachskill[0]!=NOSKILL) {
|
||||
for (i=0;teachskill[i]!=NOSKILL;++i) if (sk==teachskill[i]) break;
|
||||
sk = teachskill[i];
|
||||
}
|
||||
if (academy) {
|
||||
academy = academy/30;
|
||||
learn_skill(u, sk, academy/30.0/TEACHNUMBER);
|
||||
}
|
||||
if (sk != NOSKILL && eff_skill_study(u, sk, r)-TEACHDIFFERENCE > eff_skill_study(student, sk, r)) {
|
||||
teaching -= teach_unit(u, student, teaching, sk, true, &academy);
|
||||
}
|
||||
}
|
||||
}
|
||||
student = student->next;
|
||||
}
|
||||
#ifdef TEACH_FRIENDS
|
||||
while (teaching && student) {
|
||||
if (student->faction != u->faction && alliedunit(u, student->faction, HELP_GUARD)) {
|
||||
#ifdef NEW_DAEMONHUNGER_RULE
|
||||
if (LongHunger(student)) continue;
|
||||
#else
|
||||
if (fval(student, UFL_HUNGER)) continue;
|
||||
#endif
|
||||
if (get_keyword(student->thisorder) == K_STUDY) {
|
||||
/* Input ist nun von student->thisorder !! */
|
||||
init_tokens(student->thisorder);
|
||||
skip_token();
|
||||
sk = getskill(student->faction->locale);
|
||||
if (sk != NOSKILL && eff_skill_study(u, sk, r)-TEACHDIFFERENCE >= eff_skill(student, sk, r)) {
|
||||
teaching -= teach_unit(u, student, teaching, sk, true, &academy);
|
||||
}
|
||||
}
|
||||
}
|
||||
student = student->next;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
static char zOrder[BUFSIZE];
|
||||
order * new_order;
|
||||
|
||||
strcpy(zOrder, locale_string(u->faction->locale, keywords[K_TEACH]));
|
||||
init_tokens(ord);
|
||||
skip_token();
|
||||
for (;;) {
|
||||
|
||||
u2 = getunit(r, u->faction);
|
||||
|
||||
/* Falls keine Unit gefunden, abbrechen - außer es gibt überhaupt keine
|
||||
* Unit, dann gibt es zusätzlich noch einen Fehler */
|
||||
|
||||
if (!u2) {
|
||||
|
||||
/* Finde den string, der den Fehler verursacht hat */
|
||||
parser_pushstate();
|
||||
init_tokens(ord);
|
||||
skip_token();
|
||||
for (j = count; j; j--) {
|
||||
/* skip over the first 'count' units */
|
||||
getunit(r, u->faction);
|
||||
}
|
||||
|
||||
s = getstrtoken();
|
||||
|
||||
if (!s[0]) {
|
||||
/* Falls es keinen String gibt, ist einfach nur die Liste der Einheiten
|
||||
* zu ende. dann raus hier */
|
||||
parser_popstate();
|
||||
break;
|
||||
}
|
||||
|
||||
/* Beginne die Fehlermeldung */
|
||||
|
||||
strcpy(buf, "Die Einheit '");
|
||||
|
||||
if (findparam(s, u->faction->locale) == P_TEMP) {
|
||||
/* Für: "Die Einheit 'TEMP ZET' wurde nicht gefunden" oder "Die Einheit
|
||||
* 'TEMP' wurde nicht gefunden" */
|
||||
|
||||
scat(s);
|
||||
s = getstrtoken();
|
||||
if (s[0])
|
||||
scat(" ");
|
||||
|
||||
/* count++; -- unnötig/alt? Um nachher weiter einlesen zu koennen */
|
||||
|
||||
}
|
||||
scat(s);
|
||||
scat("' wurde nicht gefunden");
|
||||
mistake(u, ord, buf, MSG_EVENT);
|
||||
|
||||
count++;
|
||||
parser_popstate();
|
||||
continue;
|
||||
}
|
||||
/* Defaultorder zusammenbauen. TEMP-Einheiten werden automatisch in
|
||||
* ihre neuen Nummern übersetzt. */
|
||||
strcat(zOrder, " ");
|
||||
strcat(zOrder, unitid(u2));
|
||||
|
||||
/* Wir müssen nun hochzählen, wieviele Einheiten wir schon abgearbeitet
|
||||
* haben, damit mit getstrtoken() die richtige Einheit geholt werden kann.
|
||||
* Falls u2 ein Alias hat, ist sie neu, und es wurde ein TEMP verwendet, um
|
||||
* sie zu beschreiben. */
|
||||
|
||||
count++;
|
||||
|
||||
if (get_keyword(u2->thisorder) != K_STUDY) {
|
||||
add_message(&u->faction->msgs,
|
||||
msg_feedback(u, ord, "teach_nolearn", "student", u2));
|
||||
continue;
|
||||
}
|
||||
/* Input ist nun von u2->thisorder !! */
|
||||
init_tokens(u2->thisorder);
|
||||
skip_token();
|
||||
sk = getskill(u2->faction->locale);
|
||||
if (sk == NOSKILL) {
|
||||
add_message(&u->faction->msgs,
|
||||
msg_feedback(u, ord, "teach_nolearn", "student", u2));
|
||||
continue;
|
||||
}
|
||||
|
||||
/* u is teacher, u2 is student */
|
||||
if (eff_skill_study(u2, sk, r) > eff_skill_study(u, sk, r)-TEACHDIFFERENCE) {
|
||||
add_message(&u->faction->msgs,
|
||||
msg_feedback(u, ord, "teach_asgood", "student", u2));
|
||||
continue;
|
||||
}
|
||||
if (sk == SK_MAGIC) {
|
||||
/* ist der Magier schon spezialisiert, so versteht er nur noch
|
||||
* Lehrer seines Gebietes */
|
||||
if (find_magetype(u2) != 0
|
||||
&& find_magetype(u) != find_magetype(u2))
|
||||
{
|
||||
sprintf(buf, "%s versteht unsere Art von Magie nicht", unitname(u2));
|
||||
mistake(u, ord, buf, MSG_EVENT);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
teaching -= teach_unit(u, u2, teaching, sk, false, &academy);
|
||||
|
||||
}
|
||||
new_order = parse_order(zOrder, u->faction->locale);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, new_order);
|
||||
#else
|
||||
copy_order(ord, new_order);
|
||||
#endif
|
||||
free_order(new_order); /* parse_order & set_order have each increased the refcount */
|
||||
}
|
||||
if (academy && sk!=NOSKILL) {
|
||||
academy = academy/30; /* anzahl gelehrter wochen, max. 10 */
|
||||
learn_skill(u, sk, academy/30.0/TEACHNUMBER);
|
||||
}
|
||||
}
|
||||
/* ------------------------------------------------------------- */
|
||||
|
||||
|
|
|
@ -795,7 +795,7 @@ maxbuild(const unit * u, const construction * cons)
|
|||
/** old build routines */
|
||||
|
||||
void
|
||||
build_building(unit * u, const building_type * btype, int want)
|
||||
build_building(unit * u, const building_type * btype, int want, order * ord)
|
||||
{
|
||||
region * r = u->region;
|
||||
boolean newbuilding = false;
|
||||
|
@ -804,9 +804,10 @@ build_building(unit * u, const building_type * btype, int want)
|
|||
/* einmalige Korrektur */
|
||||
static char buffer[8 + IDSIZE + 1 + NAMESIZE + 1];
|
||||
const char *string2;
|
||||
order * new_order;
|
||||
|
||||
if (eff_skill(u, SK_BUILDING, r) == 0) {
|
||||
cmistake(u, u->thisorder, 101, MSG_PRODUCE);
|
||||
cmistake(u, ord, 101, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -825,7 +826,7 @@ build_building(unit * u, const building_type * btype, int want)
|
|||
b = u->building;
|
||||
} else {
|
||||
/* keine neue Burg anfangen wenn eine Nummer angegeben war */
|
||||
cmistake(u, u->thisorder, 6, MSG_PRODUCE);
|
||||
cmistake(u, ord, 6, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -835,17 +836,17 @@ build_building(unit * u, const building_type * btype, int want)
|
|||
|
||||
if (b && fval(btype, BTF_UNIQUE) && buildingtype_exists(r, btype)) {
|
||||
/* only one of these per region */
|
||||
cmistake(u, u->thisorder, 93, MSG_PRODUCE);
|
||||
cmistake(u, ord, 93, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
if (besieged(u)) {
|
||||
/* units under siege can not build */
|
||||
cmistake(u, u->thisorder, 60, MSG_PRODUCE);
|
||||
cmistake(u, ord, 60, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
if (btype->flags & BTF_NOBUILD) {
|
||||
/* special building, cannot be built */
|
||||
cmistake(u, u->thisorder, 221, MSG_PRODUCE);
|
||||
cmistake(u, ord, 221, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -870,7 +871,7 @@ build_building(unit * u, const building_type * btype, int want)
|
|||
switch (built) {
|
||||
case ECOMPLETE:
|
||||
/* the building is already complete */
|
||||
cmistake(u, u->thisorder, 4, MSG_PRODUCE);
|
||||
cmistake(u, ord, 4, MSG_PRODUCE);
|
||||
return;
|
||||
case ENOMATERIALS: {
|
||||
/* something missing from the list of materials */
|
||||
|
@ -887,14 +888,14 @@ build_building(unit * u, const building_type * btype, int want)
|
|||
);
|
||||
ch = ch+strlen(ch);
|
||||
}
|
||||
ADDMSG(&u->faction->msgs, msg_feedback(u, u->thisorder, "build_required",
|
||||
ADDMSG(&u->faction->msgs, msg_feedback(u, ord, "build_required",
|
||||
"required", buf));
|
||||
return;
|
||||
}
|
||||
case ELOWSKILL:
|
||||
case ENEEDSKILL:
|
||||
/* no skill, or not enough skill points to build */
|
||||
cmistake(u, u->thisorder, 50, MSG_PRODUCE);
|
||||
cmistake(u, ord, 50, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -928,8 +929,14 @@ build_building(unit * u, const building_type * btype, int want)
|
|||
strcpy(buffer, locale_string(u->faction->locale, "defaultorder"));
|
||||
else
|
||||
sprintf(buffer, "%s %d %s %s", locale_string(u->faction->locale, keywords[K_MAKE]), want-built, string2, buildingid(b));
|
||||
set_order(&u->lastorder, parse_order(buffer, u->faction->locale));
|
||||
free_order(u->lastorder);
|
||||
|
||||
new_order = parse_order(buffer, u->faction->locale);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, new_order);
|
||||
#else
|
||||
copy_order(ord, new_order);
|
||||
#endif
|
||||
free_order(new_order);
|
||||
|
||||
b->size += built;
|
||||
update_lighthouse(b);
|
||||
|
@ -976,19 +983,20 @@ build_ship(unit * u, ship * sh, int want)
|
|||
}
|
||||
|
||||
void
|
||||
create_ship(region * r, unit * u, const struct ship_type * newtype, int want)
|
||||
create_ship(region * r, unit * u, const struct ship_type * newtype, int want, order * ord)
|
||||
{
|
||||
static char buffer[IDSIZE + 2 * KEYWORDSIZE + 3];
|
||||
ship *sh;
|
||||
int msize;
|
||||
const construction * cons = newtype->construction;
|
||||
order * new_order;
|
||||
|
||||
if (!eff_skill(u, SK_SHIPBUILDING, r)) {
|
||||
cmistake(u, u->thisorder, 100, MSG_PRODUCE);
|
||||
cmistake(u, ord, 100, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
if (besieged(u)) {
|
||||
cmistake(u, u->thisorder, 60, MSG_PRODUCE);
|
||||
cmistake(u, ord, 60, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -996,13 +1004,13 @@ create_ship(region * r, unit * u, const struct ship_type * newtype, int want)
|
|||
if (eff_skill(u, cons->skill, r) < cons->minskill) {
|
||||
sprintf(buf, "Um %s zu bauen, braucht man ein Talent von "
|
||||
"mindestens %d.", newtype->name[1], cons->minskill);
|
||||
mistake(u, u->thisorder, buf, MSG_PRODUCE);
|
||||
mistake(u, ord, buf, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
|
||||
msize = maxbuild(u, cons);
|
||||
if (msize==0) {
|
||||
cmistake(u, u->thisorder, 88, MSG_PRODUCE);
|
||||
cmistake(u, ord, 88, MSG_PRODUCE);
|
||||
return;
|
||||
}
|
||||
if (want>0) want = min(want, msize);
|
||||
|
@ -1015,8 +1023,14 @@ create_ship(region * r, unit * u, const struct ship_type * newtype, int want)
|
|||
fset(u, UFL_OWNER);
|
||||
sprintf(buffer, "%s %s %s",
|
||||
locale_string(u->faction->locale, keywords[K_MAKE]), locale_string(u->faction->locale, parameters[P_SHIP]), shipid(sh));
|
||||
set_order(&u->lastorder, parse_order(buffer, u->faction->locale));
|
||||
free_order(u->lastorder);
|
||||
|
||||
new_order = parse_order(buffer, u->faction->locale);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, new_order);
|
||||
#else
|
||||
copy_order(ord, new_order);
|
||||
#endif
|
||||
free_order(new_order);
|
||||
|
||||
build_ship(u, sh, want);
|
||||
}
|
||||
|
|
|
@ -68,7 +68,7 @@ extern boolean can_contact(const struct region *r, const struct unit *u, const s
|
|||
|
||||
void do_siege(void);
|
||||
void build_road(struct region * r, struct unit * u, int size, direction_t d);
|
||||
void create_ship(struct region * r, struct unit * u, const struct ship_type * newtype, int size);
|
||||
void create_ship(struct region * r, struct unit * u, const struct ship_type * newtype, int size, struct order * ord);
|
||||
void continue_ship(struct region * r, struct unit * u, int size);
|
||||
|
||||
struct building * getbuilding(const struct region * r);
|
||||
|
|
|
@ -112,7 +112,7 @@ extern const char * buildingtype(const struct building * b, int bsize);
|
|||
extern const char * buildingname(const struct building * b);
|
||||
extern int buildingcapacity(const struct building * b);
|
||||
extern struct building *new_building(const struct building_type * typ, struct region * r, const struct locale * lang);
|
||||
void build_building(struct unit * u, const struct building_type * typ, int size);
|
||||
void build_building(struct unit * u, const struct building_type * typ, int size, struct order * ord);
|
||||
|
||||
/* Alte Gebäudetypen: */
|
||||
|
||||
|
|
|
@ -344,7 +344,6 @@ const char *keywords[MAXKEYWORDS] =
|
|||
"BANNER",
|
||||
"ARBEITEN",
|
||||
"ATTACKIEREN",
|
||||
"BIETEN",
|
||||
"BEKLAUEN",
|
||||
"BELAGERE",
|
||||
"BENENNEN",
|
||||
|
@ -398,7 +397,6 @@ const char *keywords[MAXKEYWORDS] =
|
|||
"MAGIEGEBIET",
|
||||
"PIRATERIE",
|
||||
"NEUSTART",
|
||||
"WARTEN",
|
||||
"GRUPPE",
|
||||
"OPFERE",
|
||||
"BETEN",
|
||||
|
@ -1259,21 +1257,50 @@ count_maxmigrants(const faction * f)
|
|||
/* GET STR, I zur Eingabe von Daten liest diese aus dem Buffer, der beim ersten
|
||||
* Aufruf inititialisiert wird? */
|
||||
|
||||
static const unsigned char *current_token;
|
||||
typedef struct parser_state {
|
||||
const unsigned char *current_token;
|
||||
char * current_cmd;
|
||||
struct parser_state * next;
|
||||
} parser_state;
|
||||
|
||||
static parser_state * state;
|
||||
|
||||
void
|
||||
init_tokens_str(const char * initstr)
|
||||
{
|
||||
current_token = (const unsigned char *)initstr;
|
||||
if (state==NULL) {
|
||||
state = malloc(sizeof(parser_state));
|
||||
state->current_cmd = NULL;
|
||||
}
|
||||
state->current_token = (const unsigned char *)initstr;
|
||||
}
|
||||
|
||||
void
|
||||
init_tokens(const struct order * ord)
|
||||
{
|
||||
static char * cmd = NULL;
|
||||
if (cmd!=NULL) free(cmd);
|
||||
cmd = getcommand(ord);
|
||||
init_tokens_str(cmd);
|
||||
if (state==NULL) state = malloc(sizeof(parser_state));
|
||||
else if (state->current_cmd!=NULL) free(state->current_cmd);
|
||||
state->current_cmd = getcommand(ord);
|
||||
init_tokens_str(state->current_cmd);
|
||||
}
|
||||
|
||||
void
|
||||
parser_pushstate(void)
|
||||
{
|
||||
parser_state * new_state = malloc(sizeof(parser_state));
|
||||
new_state->current_cmd = NULL;
|
||||
new_state->current_token = NULL;
|
||||
new_state->next = state;
|
||||
state = new_state;
|
||||
}
|
||||
|
||||
void
|
||||
parser_popstate(void)
|
||||
{
|
||||
parser_state * new_state = state->next;
|
||||
if (state->current_cmd!=NULL) free(state->current_cmd);
|
||||
free(state);
|
||||
state = new_state;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1281,23 +1308,23 @@ skip_token(void)
|
|||
{
|
||||
char quotechar = 0;
|
||||
|
||||
while (isspace(*current_token)) ++current_token;
|
||||
while (*current_token) {
|
||||
if (isspace(*current_token) && quotechar==0) {
|
||||
while (isspace(*state->current_token)) ++state->current_token;
|
||||
while (*state->current_token) {
|
||||
if (isspace(*state->current_token) && quotechar==0) {
|
||||
return;
|
||||
} else {
|
||||
switch(*current_token) {
|
||||
switch(*state->current_token) {
|
||||
case '"':
|
||||
case '\'':
|
||||
if (*current_token==quotechar) return;
|
||||
quotechar = *current_token;
|
||||
if (*state->current_token==quotechar) return;
|
||||
quotechar = *state->current_token;
|
||||
break;
|
||||
case ESCAPE_CHAR:
|
||||
++current_token;
|
||||
++state->current_token;
|
||||
break;
|
||||
}
|
||||
}
|
||||
++current_token;
|
||||
++state->current_token;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1377,13 +1404,13 @@ igetstrtoken(const char * initstr)
|
|||
init_tokens_str(initstr);
|
||||
}
|
||||
|
||||
return parse_token((const char**)¤t_token);
|
||||
return parse_token((const char**)&state->current_token);
|
||||
}
|
||||
|
||||
const char *
|
||||
getstrtoken(void)
|
||||
{
|
||||
return parse_token((const char**)¤t_token);
|
||||
return parse_token((const char**)&state->current_token);
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -1870,12 +1897,17 @@ unit *
|
|||
create_unit(region * r, faction * f, int number, const struct race *urace, int id, const char * dname, unit *creator)
|
||||
{
|
||||
unit * u = calloc(1, sizeof(unit));
|
||||
order * deford = default_order(f->locale);
|
||||
|
||||
assert(urace);
|
||||
assert(f->alive);
|
||||
u_setfaction(u, f);
|
||||
set_order(&u->thisorder, NULL);
|
||||
set_order(&u->lastorder, default_order(f->locale));
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, deford);
|
||||
#else
|
||||
addlist(&u->orders, deford);
|
||||
#endif
|
||||
u_seteffstealth(u, -1);
|
||||
u->race = urace;
|
||||
u->irace = urace;
|
||||
|
@ -2600,7 +2632,10 @@ init_used_faction_ids(void)
|
|||
void
|
||||
make_undead_unit(unit * u)
|
||||
{
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, NULL);
|
||||
#endif
|
||||
free_orders(&u->orders);
|
||||
name_unit(u);
|
||||
fset(u, UFL_ISNEW);
|
||||
}
|
||||
|
|
|
@ -161,6 +161,7 @@ struct building_type;
|
|||
#define SAVEALLIANCE_VERSION 317
|
||||
#define CLAIM_VERSION 318
|
||||
#define BACTION_VERSION 319 /* building action gets a param string */
|
||||
#define NOLASTORDER_VERSION 320 /* do not use lastorder */
|
||||
|
||||
#define MIN_VERSION ALLIANCES_VERSION
|
||||
#define REGIONOWNERS_VERSION 400
|
||||
|
@ -168,8 +169,10 @@ struct building_type;
|
|||
|
||||
#ifdef REGIONOWNERS
|
||||
# define RELEASE_VERSION REGIONOWNERS_VERSION
|
||||
#else
|
||||
#elif defined(LASTORDER)
|
||||
# define RELEASE_VERSION BACTION_VERSION
|
||||
#else
|
||||
# define RELEASE_VERSION NOLASTORDER_VERSION
|
||||
#endif
|
||||
|
||||
#if RESOURCE_CONVERSION
|
||||
|
@ -377,7 +380,6 @@ enum {
|
|||
K_BANNER,
|
||||
K_WORK,
|
||||
K_ATTACK,
|
||||
K_BIETE,
|
||||
K_STEAL,
|
||||
K_BESIEGE,
|
||||
K_NAME,
|
||||
|
@ -431,7 +433,6 @@ enum {
|
|||
K_MAGIEGEBIET,
|
||||
K_PIRACY,
|
||||
K_RESTART,
|
||||
K_WAIT,
|
||||
K_GROUP,
|
||||
K_SACRIFICE,
|
||||
K_PRAY,
|
||||
|
@ -944,6 +945,8 @@ extern void init_tokens_str(const char * initstr); /* initialize token parsing *
|
|||
extern void init_tokens(const struct order * ord); /* initialize token parsing */
|
||||
extern void skip_token(void);
|
||||
extern const char * parse_token(const char ** str);
|
||||
extern void parser_pushstate(void);
|
||||
extern void parser_popstate(void);
|
||||
|
||||
extern skill_t findskill(const char *s, const struct locale * lang);
|
||||
|
||||
|
|
|
@ -14,6 +14,7 @@
|
|||
/* TODO: enum auf fst_ umstellen. Pointer auf Display-Routine */
|
||||
#include <config.h>
|
||||
#include "eressea.h"
|
||||
|
||||
#include "karma.h"
|
||||
|
||||
/* kernel includes */
|
||||
|
|
|
@ -2004,7 +2004,7 @@ new_castorder(void *u, unit *u2, spell *sp, region *r, int lev,
|
|||
corder->force = force;
|
||||
corder->rt = r;
|
||||
corder->distance = range;
|
||||
corder->order = copy_order(ord);
|
||||
corder->order = duplicate_order(ord);
|
||||
corder->par = p;
|
||||
|
||||
return corder;
|
||||
|
|
|
@ -332,7 +332,7 @@ mistake(const unit * u, struct order * ord, const char *comment, int mtype)
|
|||
if (u->faction->no != MONSTER_FACTION) {
|
||||
char * cmt = strdup(comment);
|
||||
ADDMSG(&u->faction->msgs, msg_message("mistake",
|
||||
"command error unit region", copy_order(ord), cmt, u, u->region));
|
||||
"command error unit region", duplicate_order(ord), cmt, u, u->region));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -345,7 +345,7 @@ cmistake(const unit * u, struct order *ord, int mno, int mtype)
|
|||
if (u->faction->no == MONSTER_FACTION) return;
|
||||
sprintf(ebuf, "error%d", mno);
|
||||
ADDMSG(&u->faction->msgs, msg_message(ebuf,
|
||||
"command unit region", copy_order(ord), u, u->region));
|
||||
"command unit region", duplicate_order(ord), u, u->region));
|
||||
}
|
||||
|
||||
extern unsigned int new_hashstring(const char* s);
|
||||
|
|
|
@ -860,7 +860,7 @@ static const char *shortdirections[MAXDIRECTIONS] =
|
|||
};
|
||||
|
||||
static void
|
||||
cycle_route(unit *u, int gereist)
|
||||
cycle_route(order * ord, unit *u, int gereist)
|
||||
{
|
||||
int cm = 0;
|
||||
char tail[1024];
|
||||
|
@ -869,13 +869,14 @@ cycle_route(unit *u, int gereist)
|
|||
direction_t d = NODIRECTION;
|
||||
boolean paused = false;
|
||||
boolean pause;
|
||||
order * norder;
|
||||
|
||||
if (get_keyword(u->thisorder) != K_ROUTE) return;
|
||||
if (get_keyword(ord) != K_ROUTE) return;
|
||||
tail[0] = '\0';
|
||||
|
||||
strcpy(neworder, locale_string(u->faction->locale, keywords[K_ROUTE]));
|
||||
|
||||
init_tokens(u->thisorder);
|
||||
init_tokens(ord);
|
||||
skip_token();
|
||||
|
||||
for (cm=0;;++cm) {
|
||||
|
@ -909,8 +910,13 @@ cycle_route(unit *u, int gereist)
|
|||
}
|
||||
|
||||
strcat(neworder, tail);
|
||||
set_order(&u->lastorder, parse_order(neworder, u->faction->locale));
|
||||
free_order(u->lastorder); /* parse_order & set_order have each increased the refcount */
|
||||
norder = parse_order(neworder, u->faction->locale);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, norder);
|
||||
#else
|
||||
copy_order(ord, norder);
|
||||
#endif
|
||||
free_order(norder);
|
||||
}
|
||||
|
||||
static boolean
|
||||
|
@ -1311,7 +1317,7 @@ travel_route(unit * u, region_list * route_begin, region_list * route_end, order
|
|||
region * next = r;
|
||||
|
||||
setguard(u, GUARD_NONE);
|
||||
cycle_route(u, steps);
|
||||
cycle_route(ord, u, steps);
|
||||
|
||||
if (mode==TRAVEL_RUNNING) {
|
||||
walkmode = 0;
|
||||
|
@ -1659,7 +1665,7 @@ sail(unit * u, order * ord, boolean move_on_land, region_list **routep)
|
|||
unit * hafenmeister;
|
||||
/* nachdem alle Richtungen abgearbeitet wurden, und alle Einheiten
|
||||
* transferiert wurden, kann der aktuelle Befehl gelöscht werden. */
|
||||
cycle_route(u, step);
|
||||
cycle_route(ord, u, step);
|
||||
set_order(&u->thisorder, NULL);
|
||||
set_coast(sh, last_point, current_point);
|
||||
|
||||
|
|
|
@ -26,6 +26,16 @@ static int nlocales = 0;
|
|||
|
||||
#undef SHORT_STRINGS
|
||||
|
||||
void
|
||||
copy_order(order * dst, const order * src)
|
||||
{
|
||||
if (dst->_str) free(dst->_str);
|
||||
dst->_str = strdup(src->_str);
|
||||
dst->_keyword = src->_keyword;
|
||||
dst->_lindex = src->_lindex;
|
||||
dst->_persistent = src->_persistent;
|
||||
}
|
||||
|
||||
keyword_t
|
||||
get_keyword(const order * ord)
|
||||
{
|
||||
|
@ -70,7 +80,7 @@ free_order(order * ord)
|
|||
}
|
||||
|
||||
order *
|
||||
copy_order(order * ord)
|
||||
duplicate_order(order * ord)
|
||||
{
|
||||
if (ord!=NULL) ++ord->_refcount;
|
||||
return ord;
|
||||
|
@ -81,7 +91,7 @@ set_order(struct order ** destp, struct order * src)
|
|||
{
|
||||
if (*destp==src) return;
|
||||
free_order(*destp);
|
||||
*destp = copy_order(src);
|
||||
*destp = duplicate_order(src);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -156,19 +166,82 @@ parse_order(const char * s, const struct locale * lang)
|
|||
}
|
||||
|
||||
boolean
|
||||
is_persistent(const order * cmd)
|
||||
is_exclusive(const order * ord)
|
||||
{
|
||||
switch (cmd->_keyword) {
|
||||
const struct locale * lang = locale_array[ord->_lindex];
|
||||
param_t param;
|
||||
|
||||
switch (ord->_keyword) {
|
||||
case K_MOVE:
|
||||
case K_WEREWOLF:
|
||||
/* these should not become persistent */
|
||||
case K_ROUTE:
|
||||
case K_DRIVE:
|
||||
case K_WORK:
|
||||
case K_BESIEGE:
|
||||
case K_ENTERTAIN:
|
||||
case K_TAX:
|
||||
case K_RESEARCH:
|
||||
case K_SPY:
|
||||
case K_STEAL:
|
||||
case K_SABOTAGE:
|
||||
case K_STUDY:
|
||||
case K_TEACH:
|
||||
case K_ZUECHTE:
|
||||
case K_PIRACY:
|
||||
return true;
|
||||
|
||||
#if GROWING_TREES
|
||||
case K_PFLANZE:
|
||||
return true;
|
||||
#endif
|
||||
|
||||
case K_FOLLOW:
|
||||
/* FOLLOW is only a long order if we are following a ship. */
|
||||
parser_pushstate();
|
||||
init_tokens(ord);
|
||||
skip_token();
|
||||
param = getparam(lang);
|
||||
parser_popstate();
|
||||
|
||||
if (param == P_SHIP) return true;
|
||||
break;
|
||||
|
||||
case K_MAKE:
|
||||
/* Falls wir MACHE TEMP haben, ignorieren wir es. Alle anderen
|
||||
* Arten von MACHE zaehlen aber als neue defaults und werden
|
||||
* behandelt wie die anderen (deswegen kein break nach case
|
||||
* K_MAKE) - und in thisorder (der aktuelle 30-Tage Befehl)
|
||||
* abgespeichert). */
|
||||
parser_pushstate();
|
||||
init_tokens(ord); /* initialize token-parser */
|
||||
skip_token();
|
||||
param = getparam(lang);
|
||||
parser_popstate();
|
||||
|
||||
if (param != P_TEMP) return true;
|
||||
break;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
boolean
|
||||
is_persistent(const order * ord)
|
||||
{
|
||||
boolean persist = ord->_persistent!=0;
|
||||
switch (ord->_keyword) {
|
||||
case K_MOVE:
|
||||
case K_WEREWOLF:
|
||||
case NOKEYWORD:
|
||||
/* lang, aber niemals persistent! */
|
||||
return false;
|
||||
|
||||
case K_KOMMENTAR:
|
||||
case K_LIEFERE:
|
||||
return true;
|
||||
}
|
||||
#ifdef AT_PERSISTENT
|
||||
if (cmd->_persistent) return true;
|
||||
#endif /* Nur kurze Befehle! */
|
||||
return false;
|
||||
|
||||
return persist || is_exclusive(ord);
|
||||
}
|
||||
|
||||
char *
|
||||
|
|
|
@ -37,9 +37,10 @@ typedef struct order {
|
|||
|
||||
/* constructor */
|
||||
extern struct order * parse_order(const char * s, const struct locale * lang);
|
||||
extern void copy_order(order * dst, const order * src);
|
||||
|
||||
/* reference counted copies of orders: */
|
||||
extern struct order * copy_order(struct order * ord);
|
||||
extern struct order * duplicate_order(struct order * ord);
|
||||
extern void free_order(struct order * ord);
|
||||
extern void free_orders(struct order ** olist);
|
||||
|
||||
|
@ -48,6 +49,7 @@ extern keyword_t get_keyword(const struct order * ord);
|
|||
extern void set_order(struct order ** destp, struct order * src);
|
||||
extern char * getcommand(const struct order * ord);
|
||||
extern boolean is_persistent(const struct order *ord);
|
||||
extern boolean is_exclusive(const struct order *ord);
|
||||
extern char * write_order(const struct order * ord, const struct locale * lang, char * buffer, size_t size);
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
|
|
@ -111,7 +111,7 @@ regions_in_range(struct region * start, int maxdist, boolean (*allowed)(const st
|
|||
region * rn = rconnect(r, d);
|
||||
if (rn==NULL) continue;
|
||||
if (fval(rn, FL_MARK)) continue; /* already been there */
|
||||
if (!allowed(r, rn)) continue; /* can't go there */
|
||||
if (allowed && !allowed(r, rn)) continue; /* can't go there */
|
||||
|
||||
/* add the region to the list of available ones. */
|
||||
add_regionlist(&rlist, rn);
|
||||
|
|
|
@ -414,6 +414,7 @@ bufunit(const faction * f, const unit * u, int indent, int mode)
|
|||
}
|
||||
}
|
||||
}
|
||||
#ifdef LASTORDER
|
||||
if (!isbattle && u->lastorder) {
|
||||
char * cmd = getcommand(u->lastorder);
|
||||
scat(", \"");
|
||||
|
@ -421,6 +422,7 @@ bufunit(const faction * f, const unit * u, int indent, int mode)
|
|||
scat("\"");
|
||||
free(cmd);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
i = 0;
|
||||
|
||||
|
|
|
@ -1101,7 +1101,7 @@ readunit(FILE * F)
|
|||
}
|
||||
} else
|
||||
u->flags = ri(F) & ~UFL_DEBUG;
|
||||
/* Kurze persistente Befehle einlesen */
|
||||
/* Persistente Befehle einlesen */
|
||||
free_orders(&u->orders);
|
||||
freadstr(F, buf, sizeof(buf));
|
||||
while (*buf != 0) {
|
||||
|
@ -1109,8 +1109,19 @@ readunit(FILE * F)
|
|||
if (ord!=NULL) addlist(&u->orders, ord);
|
||||
freadstr(F, buf, sizeof(buf));
|
||||
}
|
||||
freadstr(F, buf, sizeof(buf));
|
||||
u->lastorder = parse_order(buf, u->faction->locale);
|
||||
if (global.data_version<NOLASTORDER_VERSION) {
|
||||
order * ord;
|
||||
freadstr(F, buf, sizeof(buf));
|
||||
ord = parse_order(buf, u->faction->locale);
|
||||
if (ord!=NULL) {
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, ord);
|
||||
free_order(ord);
|
||||
#else
|
||||
addlist(&u->orders, ord);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
set_order(&u->thisorder, NULL);
|
||||
|
||||
assert(u->number >= 0);
|
||||
|
@ -1219,9 +1230,11 @@ writeunit(FILE * F, const unit * u)
|
|||
/* write an empty string to terminate the list */
|
||||
fwriteorder(F, NULL, u->faction->locale);
|
||||
wnl(F);
|
||||
#if RELEASE_VERSION<NOLASTORDER_VERSION
|
||||
/* the current default order */
|
||||
fwriteorder(F, u->lastorder, u->faction->locale);
|
||||
wnl(F);
|
||||
#endif
|
||||
|
||||
assert(u->number >= 0);
|
||||
assert(u->race);
|
||||
|
|
|
@ -814,7 +814,9 @@ u_setfaction(unit * u, faction * f)
|
|||
join_group(u, NULL);
|
||||
free_orders(&u->orders);
|
||||
set_order(&u->thisorder, NULL);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, NULL);
|
||||
#endif
|
||||
}
|
||||
if (u->prevF) u->prevF->nextF = u->nextF;
|
||||
else if (u->faction) {
|
||||
|
|
|
@ -55,9 +55,9 @@ struct skill;
|
|||
|
||||
/* Flags, die gespeichert werden sollen: */
|
||||
#ifndef HEROES
|
||||
# define UFL_SAVEMASK (UFL_NOAID | UFL_OWNER | UFL_PARTEITARNUNG | UFL_LOCKED | UFL_HUNGER | FFL_NOIDLEOUT | UFL_TAKEALL)
|
||||
# define UFL_SAVEMASK (UFL_MOVED | UFL_NOAID | UFL_OWNER | UFL_PARTEITARNUNG | UFL_LOCKED | UFL_HUNGER | FFL_NOIDLEOUT | UFL_TAKEALL)
|
||||
#else
|
||||
# define UFL_SAVEMASK (UFL_NOAID | UFL_OWNER | UFL_PARTEITARNUNG | UFL_LOCKED | UFL_HUNGER | FFL_NOIDLEOUT | UFL_TAKEALL | UFL_HERO)
|
||||
# define UFL_SAVEMASK (UFL_MOVED | UFL_NOAID | UFL_OWNER | UFL_PARTEITARNUNG | UFL_LOCKED | UFL_HUNGER | FFL_NOIDLEOUT | UFL_TAKEALL | UFL_HERO)
|
||||
#endif
|
||||
|
||||
#ifdef HEROES
|
||||
|
@ -94,7 +94,9 @@ typedef struct unit {
|
|||
/* orders */
|
||||
struct order *orders;
|
||||
struct order * thisorder;
|
||||
#ifdef LASTORDER
|
||||
struct order * lastorder;
|
||||
#endif
|
||||
|
||||
/* race and illusionary race */
|
||||
const struct race * race;
|
||||
|
|
|
@ -376,8 +376,10 @@ guardian_faction(plane * pl, int id)
|
|||
u = createunit(r, f, 1, new_race[RC_GOBLIN]);
|
||||
set_string(&u->name, "Igjarjuks Auge");
|
||||
set_item(u, I_RING_OF_INVISIBILITY, 1);
|
||||
u->thisorder = calloc(1, sizeof(char));
|
||||
u->lastorder = calloc(1, sizeof(char));
|
||||
set_order(&u->thisorder, NULL);
|
||||
#ifdef LASTORDER
|
||||
set_order(&u->lastorder, NULL);
|
||||
#endif
|
||||
fset(u, UFL_PARTEITARNUNG);
|
||||
set_money(u, 1000);
|
||||
}
|
||||
|
|
|
@ -114,6 +114,7 @@ extern "C" {
|
|||
extern char * g_resourcedir;
|
||||
|
||||
extern boolean nonr;
|
||||
extern boolean nosh;
|
||||
extern boolean nocr;
|
||||
extern boolean noreports;
|
||||
extern boolean nomer;
|
||||
|
@ -471,6 +472,7 @@ usage(const char * prog, const char * arg)
|
|||
"--debug : schreibt Debug-Ausgaben in die Datei debug\n"
|
||||
"--nocr : keine CRs\n"
|
||||
"--nonr : keine Reports\n"
|
||||
"--nosh : keine Mail-Skripte\n"
|
||||
"--crabsolute : absolute Koordinaten im CR\n"
|
||||
"--help : help\n", prog);
|
||||
return -1;
|
||||
|
@ -509,6 +511,7 @@ read_args(int argc, char **argv, lua_State * luaState)
|
|||
else if (strcmp(argv[i]+2, "xml")==0) xmlfile = argv[++i];
|
||||
else if (strcmp(argv[i]+2, "dirtyload")==0) dirtyload = true;
|
||||
else if (strcmp(argv[i]+2, "nonr")==0) nonr = true;
|
||||
else if (strcmp(argv[i]+2, "nosh")==0) nosh = true;
|
||||
else if (strcmp(argv[i]+2, "lomem")==0) lomem = true;
|
||||
else if (strcmp(argv[i]+2, "nobattle")==0) nobattle = true;
|
||||
else if (strcmp(argv[i]+2, "nomonsters")==0) nomonsters = true;
|
||||
|
|
Loading…
Reference in a new issue