new object $command_lib: $libraries;
var $command_lib arg_types = ["this", "any", "any:*", "object", "object:*", "user", "user:*", "descendant of *", "descendant of *:*", "number", "number:*", "objref", "objref:*"];
var $root created_on = 796268969;
var $root flags = ['methods, 'code, 'variables, 'core];
var $root inited = 1;
var $root managed = [$command_lib];
var $root manager = $command_lib;
public method ._parse_option_templates() {
arg opt;
var reg, out;
out = [];
opt = strsed(opt, "^ *", "");
while (opt) {
if ((reg = regexp(opt, "^[\+-]([^= ]*)=([^ ]+) *(.*)"))) {
opt = reg[3];
out += [delete(reg, 3)];
} else if ((reg = regexp(opt, "^[\+-]([^ ]+) *(.*)"))) {
opt = reg[2];
out += [[reg[1]]];
} else {
throw(~invopt, "Option templates must begin with '+' or '-'");
}
opt = strsed(opt, "^ *", "");
}
return out;
};
public method .arg_types() {
return arg_types;
};
public method .break_cards() {
arg str;
var card, reg, i, x, cards, out, s;
out = (cards = []);
while ((reg = match_regexp(str, "(%[0-9]+)"))) {
if (((reg[2])[1]) != 1)
out += [@.break_wildcards(str.subrange(1, ((reg[2])[1]) - 1))];
card = substr(str, @reg[2]);
str = substr(str, (reg[2]).sum());
if (!((card[2]).is_numeric()))
throw(~invcard, "Argument cards must be numeric.");
card = toint(substr(card, 2));
cards += [card];
out += [card];
}
if (str)
out += [str];
return [out, cards];
};
public method .break_wildcards() {
arg str;
var out, i, s;
out = [];
while ((i = "*" in str)) {
out += [substr(str, 1, i - 1), ""];
str = str.subrange(i + 1);
}
if (str)
out += [str];
return out;
};
public method .format_commands_long() {
arg cmds, type, clen;
var def, name, c, cdef, line, o, cs, dname;
o = [];
for def in (cmds.keys()) {
o += [((type + " commands on ") + (def.name())) + ":"];
for cdef in (cmds[def]) {
for c in (cdef[2])
o += [(((" " + (toliteral(c[3]).left(clen))) + ".") + tostr(c[4])) + "()"];
}
}
return o;
};
public method .format_commands_short() {
arg cmds, type, len;
var def, name, c, cdef, line, o, cs, dname;
o = [];
for def in (cmds.keys()) {
o += [((type + " commands on ") + (def.name())) + ":"];
cs = [];
for cdef in (cmds[def]) {
for c in (cdef[2])
cs += [("\"" + (c[3])) + "\""];
}
o += ((cs.sort()).lcolumnize(len - 2, " ")).prefix(" ");
}
return o;
};
public method .format_relation() {
arg relation;
var x, str;
str = "";
for x in (relation) {
if (type(x) == 'integer)
str = (str + "%") + tostr(x);
else
str += x;
}
return str;
};
public method .get_argument_type() {
arg type;
var a, m, opts, o, result, is_list;
o = $object_lib;
is_list = 0;
if ((m = type.match_template("list *"))) {
type = m[2];
is_list = 1;
}
for a in (arg_types) {
m = match_pattern(type, a);
if (type(m) == 'list) {
switch (a) {
case "descendant of *":
result = ['descendant, [(> o.to_dbref(m[1]) <)]];
case "descendant of *:*":
opts = ._parse_option_templates(m[2]);
result = ['descendant, [(> o.to_dbref(m[1]) <)] + opts];
case "number:*", "objref:*", "any:*", "object:*", "user:*":
opts = ._parse_option_templates(m[1]);
result = [tosym(((a.explode(":"))[1]) + "_opt"), opts];
default:
result = [tosym(a), []];
}
return is_list ? ['list, result] : result;
}
}
throw(~command, ("Invalid argument type \"" + type) + "\"");
};
public method .handle_shortcut_fields() {
arg subs, fields;
var subbed_list, elem;
subbed_list = [];
for elem in (subs) {
if (type(elem) == 'string)
subbed_list += [elem];
else if (type(elem) == 'integer)
subbed_list += [(> fields[elem] <)];
else
throw(~type, "Substitution element is of wrong type.");
}
return subbed_list;
};
public method .parse_relation() {
arg left, right;
var x, str, out;
left = .break_cards(left);
right = .break_cards(right);
if ((((left[2]).length()) != ((right[2]).length())) || (!((left[2]).set_equal(right[2]))))
throw(~invrel, "Left side cards are not equal to the right side.");
str = "";
for x in (left[1]) {
if (type(x) == 'string)
str += x;
else if (str && ((str[strlen(str)]) == "*"))
str += " *";
else
str += "*";
}
out = [str, @left];
str = "";
for x in (right[1]) {
if (type(x) == 'string)
str += x;
else
str += "*";
}
return [out, [str, @right]];
};
public method .unparse_shortcut() {
arg s;
var part, line, short, method, args;
line = "";
[short, [method, args]] = s;
for part in (args) {
if (type(part) == 'string)
line += part;
else
line += "%" + part;
}
return ((((("\"" + (s[1])) + "\"").left(10)) + " => \"") + line) + "\"";
};
public method .unparse_shortcut_full() {
arg s;
var part, out, short, method, args;
[short, [method, args]] = s;
out = "";
for part in (args) {
if (type(part) == 'string)
out += ((out ? ", \"" : "\"") + part) + "\"";
else
out += ((out ? ", " : "") + "%") + part;
}
out = ((("." + method) + "(") + out) + ")";
return (((("\"" + short) + "\"").left(10)) + " => ") + out;
};
public method .validate_command_template() {
arg str;
var cmd, tmp, loc, types, part, relations;
[tmp, types] = str.explode_delimited("<", ">");
loc = [];
cmd = [];
relations = #[];
for part in (tmp) {
if (type(part) == 'string)
cmd += part.explode();
else
cmd += [part];
}
// clean
for part in [1 .. cmd.length()] {
if (type(cmd[part]) == 'string) {
cmd = cmd.replace(part, (cmd[part]).trim());
} else {
relations = relations.add(part - 1, (> .get_argument_type(types[cmd[part]]) <));
cmd = cmd.replace(part, "*");
}
}
cmd = [cmd[1], (cmd.subrange(2)).join()];
return [cmd, relations];
};