summaryrefslogtreecommitdiff
path: root/src/map/itemdb.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/map/itemdb.cpp')
-rw-r--r--src/map/itemdb.cpp173
1 files changed, 72 insertions, 101 deletions
diff --git a/src/map/itemdb.cpp b/src/map/itemdb.cpp
index 50cc5c4..7dd725e 100644
--- a/src/map/itemdb.cpp
+++ b/src/map/itemdb.cpp
@@ -29,20 +29,24 @@
#include "../generic/db.hpp"
#include "../io/cxxstdio.hpp"
-#include "../io/read.hpp"
+#include "../io/extract.hpp"
+#include "../io/line.hpp"
#include "../mmo/config_parse.hpp"
-#include "../mmo/extract.hpp"
#include "../mmo/extract_enums.hpp"
+#include "../ast/item.hpp"
+
+#include "globals.hpp"
+#include "script-parse.hpp"
+
#include "../poison.hpp"
namespace tmwa
{
-static
-Map<ItemNameId, struct item_data> item_db;
-
+namespace map
+{
// Function declarations
/*==========================================
@@ -51,24 +55,24 @@ Map<ItemNameId, struct item_data> item_db;
*/
// name = item alias, so we should find items aliases first. if not found then look for "jname" (full name)
static
-void itemdb_searchname_sub(struct item_data *item, ItemName str, struct item_data **dst)
+void itemdb_searchname_sub(Borrowed<struct item_data> item, ItemName str, Borrowed<Option<Borrowed<struct item_data>>> dst)
{
if (item->name == str)
- *dst = item;
+ *dst = Some(item);
}
/*==========================================
* 名前で検索
*------------------------------------------
*/
-struct item_data *itemdb_searchname(XString str_)
+Option<Borrowed<struct item_data>> itemdb_searchname(XString str_)
{
ItemName str = stringish<ItemName>(str_);
if (XString(str) != str_)
- return nullptr;
- struct item_data *item = nullptr;
+ return None;
+ Option<P<struct item_data>> item = None;
for (auto& pair : item_db)
- itemdb_searchname_sub(&pair.second, str, &item);
+ itemdb_searchname_sub(borrow(pair.second), str, borrow(item));
return item;
}
@@ -76,7 +80,7 @@ struct item_data *itemdb_searchname(XString str_)
* DBの存在確認
*------------------------------------------
*/
-struct item_data *itemdb_exists(ItemNameId nameid)
+Option<Borrowed<struct item_data>> itemdb_exists(ItemNameId nameid)
{
return item_db.search(nameid);
}
@@ -85,13 +89,16 @@ struct item_data *itemdb_exists(ItemNameId nameid)
* DBの検索
*------------------------------------------
*/
-struct item_data *itemdb_search(ItemNameId nameid)
+Borrowed<struct item_data> itemdb_search(ItemNameId nameid)
{
- struct item_data *id = item_db.search(nameid);
- if (id)
+ Option<P<struct item_data>> id_ = item_db.search(nameid);
+ OMATCH_BEGIN_SOME (id, id_)
+ {
return id;
+ }
+ OMATCH_END ();
- id = item_db.init(nameid);
+ P<struct item_data> id = item_db.init(nameid);
id->nameid = nameid;
id->value_buy = 10;
@@ -123,10 +130,8 @@ int itemdb_isequip(ItemNameId nameid)
*
*------------------------------------------
*/
-int itemdb_isequip2(struct item_data *data)
+bool itemdb_isequip2(Borrowed<struct item_data> data)
{
- if (!data)
- return false;
ItemType type = data->type;
return !(type == ItemType::USE
|| type == ItemType::_2
@@ -149,99 +154,64 @@ int itemdb_isequip3(ItemNameId nameid)
bool itemdb_readdb(ZString filename)
{
- bool rv = true;
-
- int ln = 0, lines = 0;
+ io::LineCharReader in(filename);
+ if (!in.is_open())
{
- io::ReadFile in(filename);
-
- if (!in.is_open())
- {
- PRINTF("can't read %s\n"_fmt, filename);
- return false;
- }
+ PRINTF("can't read %s\n"_fmt, filename);
+ return false;
+ }
- lines = 0;
+ int ln = 0;
- AString line;
- while (in.getline(line))
+ while (true)
+ {
+ auto res = TRY_UNWRAP(ast::item::parse_item(in),
+ {
+ PRINTF("read %s done (count=%d)\n"_fmt, filename, ln);
+ return true;
+ });
+ if (res.get_failure())
+ PRINTF("%s\n"_fmt, res.get_failure());
+ ast::item::ItemOrComment ioc = TRY_UNWRAP(std::move(res.get_success()), return false);
+
+ MATCH_BEGIN (ioc)
{
- lines++;
- if (is_comment(line))
- continue;
- // a line is 17 normal fields followed by 2 {} fields
- // the fields are separated by ", *", but there may be ,
- // in the {}.
-
- auto it = std::find(line.begin(), line.end(), '{');
- XString main_part = line.xislice_h(it).rstrip();
- // According to the code, tail_part may be empty. See later.
- ZString tail_part = line.xislice_t(it);
-
- XString unused_slot_count;
- item_data idv {};
- if (!extract(
- main_part, record<','>(
- &idv.nameid,
- lstripping(&idv.name),
- lstripping(&idv.jname),
- lstripping(&idv.type),
- lstripping(&idv.value_buy),
- lstripping(&idv.value_sell),
- lstripping(&idv.weight),
- lstripping(&idv.atk),
- lstripping(&idv.def),
- lstripping(&idv.range),
- lstripping(&idv.magic_bonus),
- lstripping(&unused_slot_count),
- lstripping(&idv.sex),
- lstripping(&idv.equip),
- lstripping(&idv.wlv),
- lstripping(&idv.elv),
- lstripping(&idv.look)
- )
- )
- )
- {
- PRINTF("%s:%d: error: bad item line: %s\n"_fmt,
- filename, lines, line);
- rv = false;
- continue;
- }
-
- ln++;
-
- struct item_data *id = itemdb_search(idv.nameid);
- *id = std::move(idv);
- if (id->value_buy == 0 && id->value_sell == 0)
+ MATCH_CASE (const ast::item::Comment&, c)
{
+ (void)c;
}
- else if (id->value_buy == 0)
+ MATCH_CASE (const ast::item::Item&, item)
{
- id->value_buy = id->value_sell * 2;
+ ln++;
+
+ item_data idv {};
+ idv.nameid = item.id.data;
+ idv.name = item.name.data;
+ idv.jname = item.jname.data;
+ idv.type = item.type.data;
+ idv.value_buy = item.buy_price.data ?: item.sell_price.data * 2;
+ idv.value_sell = item.sell_price.data ?: item.buy_price.data / 2;
+ idv.weight = item.weight.data;
+ idv.atk = item.atk.data;
+ idv.def = item.def.data;
+ idv.range = item.range.data;
+ idv.magic_bonus = item.magic_bonus.data;
+ idv.sex = item.gender.data;
+ idv.equip = item.loc.data;
+ idv.wlv = item.wlv.data;
+ idv.elv = item.elv.data;
+ idv.look = item.view.data;
+
+ idv.use_script = compile_script(STRPRINTF("use script %d"_fmt, idv.nameid), item.use_script, true);
+ idv.equip_script = compile_script(STRPRINTF("equip script %d"_fmt, idv.nameid), item.equip_script, true);
+
+ Borrowed<struct item_data> id = itemdb_search(idv.nameid);
+ *id = std::move(idv);
}
- else if (id->value_sell == 0)
- {
- id->value_sell = id->value_buy / 2;
- }
-
- id->use_script = nullptr;
- id->equip_script = nullptr;
-
- if (!tail_part)
- continue;
- id->use_script = parse_script(tail_part, lines, true);
-
- tail_part = tail_part.xislice_t(std::find(tail_part.begin() + 1, tail_part.end(), '{'));
- if (!tail_part)
- continue;
- id->equip_script = parse_script(tail_part, lines, true);
}
- PRINTF("read %s done (count=%d)\n"_fmt, filename, ln);
+ MATCH_END ();
}
-
- return rv;
}
/*==========================================
@@ -265,4 +235,5 @@ void do_final_itemdb(void)
itemdb_final(&pair.second);
item_db.clear();
}
+} // namespace map
} // namespace tmwa