diff options
Diffstat (limited to 'src/map/script-fun.cpp')
-rw-r--r-- | src/map/script-fun.cpp | 272 |
1 files changed, 236 insertions, 36 deletions
diff --git a/src/map/script-fun.cpp b/src/map/script-fun.cpp index 4ef6499..f215d73 100644 --- a/src/map/script-fun.cpp +++ b/src/map/script-fun.cpp @@ -780,7 +780,7 @@ void builtin_foreach(ScriptState *st) *---------------------------------------- */ static -void builtin_destroypuppet(ScriptState *st) +void builtin_destroy(ScriptState *st) { BlockId id; if (HARG(0)) @@ -909,37 +909,116 @@ void builtin_puppet(ScriptState *st) static void builtin_set(ScriptState *st) { - dumb_ptr<map_session_data> sd = nullptr; + BlockId id; + dumb_ptr<block_list> bl = nullptr; if (auto *u = AARG(0).get_if<ScriptDataParam>()) { SIR reg = u->reg; - sd = script_rid2sd(st); + if(HARG(2)) + { + struct script_data *sdata = &AARG(2); + get_val(st, sdata); + CharName name; + if (sdata->is<ScriptDataStr>()) + { + name = stringish<CharName>(ZString(conv_str(st, sdata))); + if (name.to__actual()) + bl = map_nick2sd(name); + } + else + { + id = wrap<BlockId>(conv_num(st, sdata)); + bl = map_id2bl(id); + } + } + + else + bl = script_rid2sd(st)->is_player(); + if (bl == nullptr) + return; int val = conv_num(st, &AARG(1)); - set_reg(sd, VariableCode::PARAM, reg, val); + set_reg(bl, VariableCode::PARAM, reg, val); return; } SIR reg = AARG(0).get_if<ScriptDataVariable>()->reg; ZString name = variable_names.outtern(reg.base()); - char prefix = name.front(); - char postfix = name.back(); + VarName name_ = stringish<VarName>(name); + char prefix = name_.front(); + char postfix = name_.back(); if (prefix != '$') - sd = script_rid2sd(st); + { + if(HARG(2)) + { + struct script_data *sdata = &AARG(2); + get_val(st, sdata); + if(prefix == '.') + { + if (name_[1] == '@') + { + PRINTF("builtin_set: illegal scope!\n"_fmt); + return; + } + NpcName n_name; + if (sdata->is<ScriptDataStr>()) + { + n_name = stringish<NpcName>(ZString(conv_str(st, sdata))); + bl = npc_name2id(n_name); + } + else + { + id = wrap<BlockId>(conv_num(st, sdata)); + bl = map_id2bl(id); + } + } + else + { + CharName c_name; + if (sdata->is<ScriptDataStr>()) + { + c_name = stringish<CharName>(ZString(conv_str(st, sdata))); + if (c_name.to__actual()) + bl = map_nick2sd(c_name); + } + else + { + id = wrap<BlockId>(conv_num(st, sdata)); + bl = map_id2bl(id); + } + } + } + else + { + if(prefix == '.') + { + if (name_[1] == '@') + { + set_scope_reg(st, reg, AARG(1)); + return; + } + bl = map_id2bl(st->oid)->is_npc(); + } + else + bl = map_id2bl(st->rid)->is_player(); + } + if (bl == nullptr) + return; + } if (postfix == '$') { // 文字列 RString str = conv_str(st, &AARG(1)); - set_reg(sd, VariableCode::VARIABLE, reg, str); + set_reg(bl, VariableCode::VARIABLE, reg, str); } else { // 数値 int val = conv_num(st, &AARG(1)); - set_reg(sd, VariableCode::VARIABLE, reg, val); + set_reg(bl, VariableCode::VARIABLE, reg, val); } } @@ -951,26 +1030,30 @@ void builtin_set(ScriptState *st) static void builtin_setarray(ScriptState *st) { - dumb_ptr<map_session_data> sd = nullptr; + dumb_ptr<block_list> bl = nullptr; SIR reg = AARG(0).get_if<ScriptDataVariable>()->reg; ZString name = variable_names.outtern(reg.base()); char prefix = name.front(); char postfix = name.back(); - if (prefix != '$' && prefix != '@') + if (prefix != '$' && prefix != '@' && prefix != '.') { PRINTF("builtin_setarray: illegal scope!\n"_fmt); return; } - if (prefix != '$') - sd = script_rid2sd(st); + if (prefix == '.' && name[1] != '@') + bl = map_id2bl(st->oid)->is_npc(); + else if (prefix != '$') + bl = map_id2bl(st->rid)->is_player(); for (int j = 0, i = 1; i < st->end - st->start - 2 && j < 256; i++, j++) { - if (postfix == '$') - set_reg(sd, VariableCode::VARIABLE, reg.iplus(j), conv_str(st, &AARG(i))); + if (prefix == '.' && name[1] == '@') + set_scope_reg(st, reg.iplus(j), AARG(i)); + else if (postfix == '$') + set_reg(bl, VariableCode::VARIABLE, reg.iplus(j), conv_str(st, &AARG(i))); else - set_reg(sd, VariableCode::VARIABLE, reg.iplus(j), conv_num(st, &AARG(i))); + set_reg(bl, VariableCode::VARIABLE, reg.iplus(j), conv_num(st, &AARG(i))); } } @@ -981,27 +1064,31 @@ void builtin_setarray(ScriptState *st) static void builtin_cleararray(ScriptState *st) { - dumb_ptr<map_session_data> sd = nullptr; + dumb_ptr<block_list> bl = nullptr; SIR reg = AARG(0).get_if<ScriptDataVariable>()->reg; ZString name = variable_names.outtern(reg.base()); char prefix = name.front(); char postfix = name.back(); int sz = conv_num(st, &AARG(2)); - if (prefix != '$' && prefix != '@') + if (prefix != '$' && prefix != '@' && prefix != '.') { PRINTF("builtin_cleararray: illegal scope!\n"_fmt); return; } - if (prefix != '$') - sd = script_rid2sd(st); + if (prefix == '.' && name[1] != '@') + bl = map_id2bl(st->oid)->is_npc(); + else if (prefix != '$') + bl = map_id2bl(st->rid)->is_player(); for (int i = 0; i < sz; i++) { - if (postfix == '$') - set_reg(sd, VariableCode::VARIABLE, reg.iplus(i), conv_str(st, &AARG(1))); + if (prefix == '.' && name[1] == '@') + set_scope_reg(st, reg.iplus(i), AARG(i)); + else if (postfix == '$') + set_reg(bl, VariableCode::VARIABLE, reg.iplus(i), conv_str(st, &AARG(1))); else - set_reg(sd, VariableCode::VARIABLE, reg.iplus(i), conv_num(st, &AARG(1))); + set_reg(bl, VariableCode::VARIABLE, reg.iplus(i), conv_num(st, &AARG(1))); } } @@ -1045,7 +1132,7 @@ void builtin_getarraysize(ScriptState *st) ZString name = variable_names.outtern(reg.base()); char prefix = name.front(); - if (prefix != '$' && prefix != '@') + if (prefix != '$' && prefix != '@' && prefix != '.') { PRINTF("builtin_copyarray: illegal scope!\n"_fmt); return; @@ -2908,7 +2995,7 @@ void builtin_getpartnerid2(ScriptState *st) static void builtin_explode(ScriptState *st) { - dumb_ptr<map_session_data> sd = nullptr; + dumb_ptr<block_list> bl = nullptr; SIR reg = AARG(0).get_if<ScriptDataVariable>()->reg; ZString name = variable_names.outtern(reg.base()); const char separator = conv_str(st, &AARG(2))[0]; @@ -2917,33 +3004,49 @@ void builtin_explode(ScriptState *st) char prefix = name.front(); char postfix = name.back(); - if (prefix != '$' && prefix != '@') + if (prefix != '$' && prefix != '@' && prefix != '.') { PRINTF("builtin_explode: illegal scope!\n"_fmt); return; } - if (prefix != '$') - sd = script_rid2sd(st); + if (prefix == '.' && name[1] != '@') + bl = map_id2bl(st->oid)->is_npc(); + else if (prefix != '$' && prefix != '.') + bl = map_id2bl(st->rid)->is_player(); for (int j = 0; j < 256; j++) { auto find = std::find(str.begin(), str.end(), separator); if (find == str.end()) { - if (postfix == '$') - set_reg(sd, VariableCode::VARIABLE, reg.iplus(j), str); + if (prefix == '.' && name[1] == '@') + { + struct script_data vd = script_data(ScriptDataInt{atoi(str.c_str())}); + if (postfix == '$') + vd = script_data(ScriptDataStr{str}); + set_scope_reg(st, reg.iplus(j), &vd); + } + else if (postfix == '$') + set_reg(bl, VariableCode::VARIABLE, reg.iplus(j), str); else - set_reg(sd, VariableCode::VARIABLE, reg.iplus(j), atoi(str.c_str())); + set_reg(bl, VariableCode::VARIABLE, reg.iplus(j), atoi(str.c_str())); break; } { val = str.xislice_h(find); str = str.xislice_t(find + 1); - if (postfix == '$') - set_reg(sd, VariableCode::VARIABLE, reg.iplus(j), val); + if (prefix == '.' && name[1] == '@') + { + struct script_data vd = script_data(ScriptDataInt{atoi(val.c_str())}); + if (postfix == '$') + vd = script_data(ScriptDataStr{val}); + set_scope_reg(st, reg.iplus(j), &vd); + } + else if (postfix == '$') + set_reg(bl, VariableCode::VARIABLE, reg.iplus(j), val); else - set_reg(sd, VariableCode::VARIABLE, reg.iplus(j), atoi(val.c_str())); + set_reg(bl, VariableCode::VARIABLE, reg.iplus(j), atoi(val.c_str())); } } } @@ -3149,6 +3252,102 @@ void builtin_specialeffect2(ScriptState *st) } +static +void builtin_get(ScriptState *st) +{ + BlockId id; + dumb_ptr<block_list> bl = nullptr; + if (auto *u = AARG(0).get_if<ScriptDataParam>()) + { + SIR reg = u->reg; + struct script_data *sdata = &AARG(1); + get_val(st, sdata); + CharName name; + if (sdata->is<ScriptDataStr>()) + { + name = stringish<CharName>(ZString(conv_str(st, sdata))); + if (name.to__actual()) + bl = map_nick2sd(name); + } + else + { + id = wrap<BlockId>(conv_num(st, sdata)); + bl = map_id2bl(id); + } + + if (bl == nullptr) + return; + int var = pc_readparam(bl->is_player(), reg.sp()); + push_int<ScriptDataInt>(st->stack, var); + return; + } + + struct script_data *sdata = &AARG(1); + get_val(st, sdata); + + SIR reg = AARG(0).get_if<ScriptDataVariable>()->reg; + ZString name_ = variable_names.outtern(reg.base()); + char prefix = name_.front(); + char postfix = name_.back(); + + if(prefix == '.') + { + if (name_[1] == '@') + { + PRINTF("builtin_get: illegal scope!\n"_fmt); + return; + } + NpcName name; + if (sdata->is<ScriptDataStr>()) + { + name = stringish<NpcName>(ZString(conv_str(st, sdata))); + bl = npc_name2id(name); + } + else + { + id = wrap<BlockId>(conv_num(st, sdata)); + bl = map_id2bl(id); + } + } + else if(prefix != '$') + { + CharName name; + if (sdata->is<ScriptDataStr>()) + { + name = stringish<CharName>(ZString(conv_str(st, sdata))); + if (name.to__actual()) + bl = map_nick2sd(name); + } + else + { + id = wrap<BlockId>(conv_num(st, sdata)); + bl = map_id2bl(id); + } + } + else + { + PRINTF("builtin_get: illegal scope !\n"_fmt); + return; + } + + if (!bl) + { + PRINTF("builtin_get: no block list attached !\n"_fmt); + return; + } + + if (postfix == '$') + { + ZString var = pc_readregstr(bl, reg); + push_str<ScriptDataStr>(st->stack, var); + } + else + { + int var = pc_readreg(bl, reg); + push_int<ScriptDataInt>(st->stack, var); + } +} + /*========================================== * Nude [Valaris] *------------------------------------------ @@ -3859,7 +4058,8 @@ BuiltinFunction builtin_functions[] = BUILTIN(if, "iF*"_s, '\0'), BUILTIN(elif, "iF*"_s, '\0'), BUILTIN(else, "F*"_s, '\0'), - BUILTIN(set, "Ne"_s, '\0'), + BUILTIN(set, "Ne?"_s, '\0'), + BUILTIN(get, "Ne"_s, '.'), BUILTIN(setarray, "Ne*"_s, '\0'), BUILTIN(cleararray, "Nei"_s, '\0'), BUILTIN(getarraysize, "N"_s, 'i'), @@ -3968,7 +4168,7 @@ BuiltinFunction builtin_functions[] = BUILTIN(aggravate, "Mxyxyi"_s, '\0'), BUILTIN(fakenpcname, "ssi"_s, '\0'), BUILTIN(puppet, "mxysi"_s, 'i'), - BUILTIN(destroypuppet, "?"_s, '\0'), + BUILTIN(destroy, "?"_s, '\0'), BUILTIN(getx, ""_s, 'i'), BUILTIN(gety, ""_s, 'i'), BUILTIN(getnpcx, "?"_s, 'i'), |