/** * @brief Gets time at index raising an error if isn't a time. * * @param L Lua state to get time from. * @param ind Index position to find the time. * @return Time found at the index in the state. */ ntime_t* luaL_checktime( lua_State *L, int ind ) { if (lua_istime(L,ind)) return lua_totime(L,ind); luaL_typerror(L, ind, TIME_METATABLE); return NULL; }
/** * @brief Adds an article. * @usage news.add(faction,title,body,[date_to_rm, [date]]) * * @usage s = news.add( "Empire", "Hello world!", "The Empire wishes to say hello!", 0 ) -- Adds an Empire specific article, with date 0. * * @luaparam faction faction of the article, "Generic" for non-factional * @luaparam title Title of the article * @luaparam content What's in the article * @luaparam date_to_rm date to remove the article * @luaparam date What time to put, defaults to current date, use 0 to not use a date * @luareturn The article matching name or nil if error. * @luafunc add( s ) */ int newsL_add( lua_State *L ) { news_t *n_article; char *title, *content, *faction; ntime_t date, date_to_rm; title = NULL; content = NULL; faction = NULL; date = ntime_get(); date_to_rm = 50000000000000; /* If a table is passed in. ugly hack */ if (lua_istable(L, 1)) { lua_pushnil(L); /* traverse table */ while (lua_next(L, -2)) { /* traverse sub table */ if (lua_istable(L, -1)) { lua_pushnil(L); while (lua_next(L, -2)) { if (lua_isnumber(L, -1)) { if (date_to_rm) date_to_rm = lua_tonumber(L, -1); else date = lua_tonumber(L, -1); } else if (lua_istime(L, -1)) { if (date_to_rm) date_to_rm = luaL_validtime(L, -1); else date = luaL_validtime(L, -1); } else if (lua_isstring(L, -1)) { if (!faction) faction = strdup(lua_tostring(L, -1)); else if (!title) title = strdup(lua_tostring(L, -1)); else if (!content) content = strdup(lua_tostring(L, -1)); } lua_pop(L, 1); } if (title && content && faction) new_article(title, content, faction, date, date_to_rm); else WARN("Bad arguments"); free(faction); free(title); free(content); faction = NULL; title = NULL; content = NULL; date = ntime_get(); date_to_rm = 50000000000000; } lua_pop(L, 1); } lua_pop(L, 1); /* If we're landed, we should regenerate the news buffer. */ if (landed) { generate_news(faction_name(land_planet->faction)); if (land_loaded) bar_regen(); } return 0; } if (!(lua_isstring(L, 1) && lua_isstring(L, 2) && lua_isstring(L, 3))) { WARN("\nBad arguments, use " "addArticle(\"Faction\",\"Title\",\"Content\",[date,[date_to_rm]])"); return 0; } faction = strdup(lua_tostring(L, 1)); title = strdup(lua_tostring(L, 2)); content = strdup(lua_tostring(L, 3)); /* get date and date to remove, or leave at defaults*/ if (lua_isnumber(L, 4) || lua_istime(L, 4)) { if (lua_istime(L, 4)) date_to_rm = luaL_validtime(L, 4); else date_to_rm = lua_tonumber(L, 4); } if (lua_isnumber(L, 5) || lua_istime(L, 5)) { if (lua_istime(L, 5)) date = luaL_validtime(L, 5); else date = lua_tonumber(L, 5); } if (title && content && faction) n_article = new_article(title, content, faction, date, date_to_rm); else WARN("Bad arguments"); lua_pusharticle(L, n_article->id); free(title); free(content); free(faction); /* If we're landed, we should regenerate the news buffer. */ if (landed) { generate_news(faction_name(land_planet->faction)); if (land_loaded) bar_regen(); } return 1; }
/** * @brief Persists the node on the top of the stack and pops it. * * @param L Lua state with node to persist on top of the stack. * @param writer XML Writer to use. * @param Are we parsing a node in a table? Avoids checking for extra __save. * @return 0 on success. */ static int nxml_persistDataNode( lua_State *L, xmlTextWriterPtr writer, int intable ) { int ret, b; LuaPlanet *p; LuaSystem *s; LuaFaction *f; LuaShip *sh; LuaTime *lt; Planet *pnt; StarSystem *ss; char buf[PATH_MAX]; const char *name, *str; int keynum; /* Default values. */ ret = 0; /* key, value */ /* Handle different types of keys. */ switch (lua_type(L, -2)) { case LUA_TSTRING: /* Can just tostring directly. */ name = lua_tostring(L,-2); /* Isn't a number key. */ keynum = 0; break; case LUA_TNUMBER: /* Can't tostring directly. */ lua_pushvalue(L,-2); name = lua_tostring(L,-1); lua_pop(L,1); /* Is a number key. */ keynum = 1; break; /* We only handle string or number keys, so ignore the rest. */ default: lua_pop(L,1); /* key */ return 0; } /* key, value */ /* Now handle the value. */ switch (lua_type(L, -1)) { /* Recursive for tables. */ case LUA_TTABLE: /* Check if should save -- only if not in table.. */ if (!intable) { lua_getfield(L, -1, "__save"); b = lua_toboolean(L,-1); lua_pop(L,1); if (!b) /* No need to save. */ break; } /* Start the table. */ xmlw_startElem(writer,"data"); xmlw_attr(writer,"type","table"); xmlw_attr(writer,"name","%s",name); if (keynum) xmlw_attr(writer,"keynum","1"); lua_pushnil(L); /* key, value, nil */ /* key, value, nil */ while (lua_next(L, -2) != 0) { /* key, value, key, value */ ret = nxml_persistDataNode( L, writer, 1 ); /* key, value, key */ } /* key, value */ xmlw_endElem(writer); /* "table" */ break; /* Normal number. */ case LUA_TNUMBER: nxml_saveData( writer, "number", name, lua_tostring(L,-1), keynum ); /* key, value */ break; /* Boolean is either 1 or 0. */ case LUA_TBOOLEAN: /* lua_tostring doesn't work on booleans. */ if (lua_toboolean(L,-1)) buf[0] = '1'; else buf[0] = '0'; buf[1] = '\0'; nxml_saveData( writer, "bool", name, buf, keynum ); /* key, value */ break; /* String is saved normally. */ case LUA_TSTRING: nxml_saveData( writer, "string", name, lua_tostring(L,-1), keynum ); /* key, value */ break; /* User data must be handled here. */ case LUA_TUSERDATA: if (lua_isplanet(L,-1)) { p = lua_toplanet(L,-1); pnt = planet_getIndex( p->id ); if (pnt != NULL) nxml_saveData( writer, "planet", name, pnt->name, keynum ); else WARN("Failed to save invalid planet."); /* key, value */ break; } else if (lua_issystem(L,-1)) { s = lua_tosystem(L,-1); ss = system_getIndex( s->id ); if (ss != NULL) nxml_saveData( writer, "system", name, ss->name, keynum ); else WARN("Failed to save invalid system."); /* key, value */ break; } else if (lua_isfaction(L,-1)) { f = lua_tofaction(L,-1); str = faction_name( f->f ); if (str == NULL) break; nxml_saveData( writer, "faction", name, str, keynum ); /* key, value */ break; } else if (lua_isship(L,-1)) { sh = lua_toship(L,-1); str = sh->ship->name; if (str == NULL) break; nxml_saveData( writer, "ship", name, str, keynum ); /* key, value */ break; } else if (lua_istime(L,-1)) { lt = lua_totime(L,-1); snprintf( buf, sizeof(buf), "%"PRId64, lt->t ); nxml_saveData( writer, "time", name, buf, keynum ); break; } /* Rest gets ignored, like functions, etc... */ default: /* key, value */ break; } lua_pop(L,1); /* key */ return ret; }