The list of alliance members is now also a quicklist, and the lua binding for faction_list iteration can disappear.

This commit is contained in:
Enno Rehling 2011-02-25 07:23:02 -08:00
parent d2994d816a
commit efca8cee43
9 changed files with 79 additions and 73 deletions

View File

@ -26,6 +26,7 @@ without prior permission by the authors of Eressea.
#include <util/language.h>
#include <util/log.h>
#include <util/quicklist.h>
#include <lua.h>
#include <tolua.h>
@ -43,18 +44,6 @@ int tolua_factionlist_next(lua_State *L)
else return 0; /* no more values to return */
}
int tolua_factionlist_iter(lua_State *L)
{
faction_list** faction_ptr = (faction_list **)lua_touserdata(L, lua_upvalueindex(1));
faction_list* flist = *faction_ptr;
if (flist != NULL) {
tolua_pushusertype(L, (void*)flist->data, TOLUA_CAST "faction");
*faction_ptr = flist->next;
return 1;
}
else return 0; /* no more values to return */
}
static int tolua_faction_get_units(lua_State* L)
{
faction * self = (faction *)tolua_tousertype(L, 1, 0);

View File

@ -16,7 +16,6 @@ extern "C" {
struct lua_State;
int tolua_factionlist_next(struct lua_State *L);
int tolua_factionlist_iter(struct lua_State *L);
void tolua_faction_open(struct lua_State *L);
#ifdef __cplusplus

View File

@ -55,6 +55,7 @@ without prior permission by the authors of Eressea.
#include <util/language.h>
#include <util/lists.h>
#include <util/log.h>
#include <util/quicklist.h>
#include <util/rand.h>
#include <util/rng.h>
#include <util/storage.h>
@ -91,6 +92,24 @@ int tolua_orderlist_next(lua_State *L)
else return 0; /* no more values to return */
}
int tolua_quicklist_iter(lua_State *L)
{
quicklist** qlp = (quicklist **)lua_touserdata(L, lua_upvalueindex(1));
quicklist* ql = *qlp;
if (ql != NULL) {
int index = lua_tointeger(L, lua_upvalueindex(2));
const char * type = lua_tostring(L, lua_upvalueindex(3));
void * data = ql_get(ql, index);
tolua_pushusertype(L, data, TOLUA_CAST type);
ql_advance(qlp, &index, 1);
tolua_pushnumber(L, index);
lua_replace(L, lua_upvalueindex(2));
return 1;
}
else return 0; /* no more values to return */
}
int tolua_spelllist_next(lua_State *L)
{
spell_list** spell_ptr = (spell_list **)lua_touserdata(L, lua_upvalueindex(1));
@ -728,14 +747,17 @@ static int
tolua_get_alliance_factions(lua_State* L)
{
alliance * self = (alliance *)tolua_tousertype(L, 1, 0);
faction_list ** faction_ptr = (faction_list**)lua_newuserdata(L, sizeof(faction_list *));
quicklist ** faction_ptr = (quicklist**)lua_newuserdata(L, sizeof(quicklist *));
luaL_getmetatable(L, "faction_list");
lua_setmetatable(L, -2);
lua_pushnumber(L, 0);
*faction_ptr = self->members;
lua_pushcclosure(L, tolua_factionlist_iter, 1);
lua_pushstring(L, "faction");
lua_pushcclosure(L, tolua_quicklist_iter, 3); /* OBS: this closure has multiple upvalues (list, index, type_name) */
return 1;
}
@ -1052,6 +1074,7 @@ tolua_eressea_open(lua_State* L)
tolua_usertype(L, TOLUA_CAST "item");
tolua_usertype(L, TOLUA_CAST "alliance");
tolua_usertype(L, TOLUA_CAST "event");
tolua_usertype(L, TOLUA_CAST "faction_list");
tolua_module(L, NULL, 0);
tolua_beginmodule(L, NULL);

View File

@ -33,6 +33,7 @@ without prior permission by the authors of Eressea.
#include <util/base36.h>
#include <util/language.h>
#include <util/parser.h>
#include <util/quicklist.h>
#include <util/rng.h>
#include <util/umlaut.h>
@ -49,11 +50,7 @@ void
free_alliance(alliance * al)
{
free(al->name);
while (al->members) {
faction_list * m = al->members;
al->members = m->next;
free(m);
}
if (al->members) ql_free(al->members);
free(al);
}
@ -111,7 +108,7 @@ alliance_get_leader(alliance * al)
{
if (!al->_leader) {
if (al->members) {
al->_leader = al->members->data;
al->_leader = (faction *)ql_get(al->members, 0);
}
}
return al->_leader;
@ -120,7 +117,7 @@ alliance_get_leader(alliance * al)
static void
create_transaction(int type, unit * u, order * ord)
{
alliance_transaction * tr = calloc(1, sizeof(alliance_transaction));
alliance_transaction * tr = (alliance_transaction *)calloc(1, sizeof(alliance_transaction));
tr->ord = ord;
tr->u = u;
tr->next = transactions[type];
@ -372,24 +369,24 @@ alliancejoin(void)
}
void
setalliance(struct faction * f, alliance * al)
setalliance(faction * f, alliance * al)
{
faction_list * flist = NULL;
if (f->alliance==al) return;
if (f->alliance!=NULL) {
faction_list ** flistp = &f->alliance->members;
while (*flistp) {
faction_list * flist = *flistp;
if ((*flistp)->data==f) {
*flistp = flist->next;
int qi;
quicklist ** flistp = &f->alliance->members;
for (qi=0;*flistp;ql_advance(flistp, &qi, 1)) {
faction * data = (faction *)ql_get(*flistp, qi);
if (data==f) {
ql_delete(flistp, qi);
break;
}
flistp = &flist->next;
}
if (f->alliance->_leader==f) {
if (f->alliance->members) {
f->alliance->_leader = f->alliance->members->data;
f->alliance->_leader = (faction *)ql_get(f->alliance->members, 0);
} else {
f->alliance->_leader = NULL;
}
@ -398,22 +395,11 @@ setalliance(struct faction * f, alliance * al)
f->alliance = al;
f->alliance_joindate = turn;
if (al!=NULL) {
faction_list ** flistp = &al->members;
while (*flistp) {
flistp = &(*flistp)->next;
}
if (flist==NULL) {
flist = malloc(sizeof(faction_list));
flist->data = f;
}
*flistp = flist;
flist->next = NULL;
ql_push(&al->members, f);
if (al->_leader==NULL) {
al->_leader = f;
}
flist = NULL;
}
free(flist);
}
const char *
@ -456,15 +442,15 @@ alliancevictory(void)
}
while (al!=NULL) {
if (!fval(al, FFL_MARK)) {
faction_list * flist = al->members;
while (flist!=0) {
faction * f = flist->data;
int qi;
quicklist * flist = al->members;
for (qi=0;flist;ql_advance(&flist, &qi, 1)) {
faction * f = (faction *)ql_get(flist, qi);
if (f->alliance==al) {
ADDMSG(&f->msgs, msg_message("alliance::lost",
"alliance", al));
destroyfaction(f);
}
flist = flist->next;
}
} else {
freset(al, FFL_MARK);
@ -478,18 +464,20 @@ victorycondition(const alliance * al, const char * name)
{
const char * gems[] = { "opal", "diamond", "zaphire", "topaz", "beryl", "agate", "garnet", "emerald", NULL };
if (strcmp(name, "gems")==0) {
const char ** igem = gems;
const char ** igem;
for (;*igem;++igem) {
for (igem=gems;*igem;++igem) {
const struct item_type * itype = it_find(*igem);
faction_list * flist = al->members;
quicklist * flist = al->members;
int qi;
boolean found = false;
assert(itype!=NULL);
for (;flist && !found;flist=flist->next) {
unit * u = flist->data->units;
for (qi=0;flist && !found;ql_advance(&flist, &qi, 1)) {
faction * f = (faction *)ql_get(flist, 0);
unit * u;
for (;u;u=u->nextF) {
for (u=f->units;u;u=u->nextF) {
if (i_get(u->items, itype)>0) {
found = true;
break;
@ -501,9 +489,11 @@ victorycondition(const alliance * al, const char * name)
return 1;
} else if (strcmp(name, "phoenix")==0) {
faction_list * flist = al->members;
for (;flist;flist=flist->next) {
faction * f = flist->data;
quicklist * flist = al->members;
int qi;
for (qi=0;flist;ql_advance(&flist, &qi, 1)) {
faction * f = (faction *)ql_get(flist, qi);
if (find_key(f->attribs, atoi36("phnx"))) {
return 1;
}
@ -527,9 +517,11 @@ victorycondition(const alliance * al, const char * name)
* }
*/
faction_list * flist = al->members;
for (;flist;flist=flist->next) {
faction * f = flist->data;
quicklist * flist = al->members;
int qi;
for (qi=0;flist;ql_advance(&flist, &qi, 1)) {
faction * f = (faction *)ql_get(flist, qi);
if (find_key(f->attribs, atoi36("pyra"))) {
return 1;
}

View File

@ -44,7 +44,7 @@ enum {
typedef struct alliance {
struct alliance * next;
struct faction * _leader;
struct faction_list * members;
struct quicklist * members;
unsigned int flags;
int id;
char * name;

View File

@ -53,6 +53,7 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
/* util includes */
#include <util/attrib.h>
#include <util/base36.h>
#include <util/bsdstring.h>
#include <util/crmessage.h>
#include <util/event.h>
#include <util/functions.h>
@ -60,14 +61,14 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
#include <util/log.h>
#include <util/lists.h>
#include <util/parser.h>
#include <util/quicklist.h>
#include <util/rand.h>
#include <util/rng.h>
#include <util/sql.h>
#include <util/translation.h>
#include <util/unicode.h>
#include <util/umlaut.h>
#include <util/xml.h>
#include <util/bsdstring.h>
#include <util/unicode.h>
/* libxml includes */
#include <libxml/tree.h>
@ -507,10 +508,12 @@ allied_skillcount(const faction * f, skill_t sk)
{
int num = 0;
alliance * a = f_get_alliance(f);
faction_list * members = a->members;
while (members!=NULL) {
num += count_skill(members->data, sk);
members=members->next;
quicklist * members = a->members;
int qi;
for (qi=0;members;ql_advance(&members, &qi, 1)) {
faction * m = (faction *)ql_get(members, qi);
num += count_skill(m, sk);
}
return num;
}

View File

@ -924,9 +924,10 @@ get_addresses(report_context * ctx)
ql_push(&flist, ctx->f);
if (f_get_alliance(ctx->f)) {
faction_list * member = ctx->f->alliance->members;
for (;member;member=member->next) {
ql_set_insert(&flist, member->data);
quicklist * ql = ctx->f->alliance->members;
int qi;
for (qi=0;ql;ql_advance(&ql, &qi, 1)) {
ql_set_insert(&flist, ql_get(ql, qi));
}
}

View File

@ -62,6 +62,7 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
#include <util/lists.h>
#include <util/log.h>
#include <util/parser.h>
#include <util/quicklist.h>
#include <util/rand.h>
#include <util/resolve.h>
#include <util/rng.h>
@ -1178,13 +1179,10 @@ readfaction(struct storage * store)
if (allianceid>0) f->alliance = findalliance(allianceid);
if (f->alliance) {
alliance * al = f->alliance;
faction_list * flist = (faction_list *)malloc(sizeof(faction_list));
if (al->flags&ALF_NON_ALLIED) {
assert(!al->members || !"non-allied dummy-alliance has more than one member");
}
flist->data = f;
flist->next = al->members;
al->members = flist;
ql_push(&al->members, f);
} else if (rule_region_owners()){
/* compat fix for non-allied factions */
alliance * al = makealliance(0, NULL);

View File

@ -142,6 +142,7 @@ int ql_advance(struct quicklist ** iterator, int * index, int stride)
void ql_free(struct quicklist * ql)
{
if (!ql) return;
if (ql->next) ql_free(ql->next);
free(ql);
}