diff -r 000000000000 -r cc66ad6b0d75 commands.lua --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/commands.lua Sat Mar 27 17:43:08 2010 +0000 @@ -0,0 +1,153 @@ +-- Here we process special commands, for example, those with more than one object specified + +commands = {}; + +function commands:_parse(person, command) + if person.group.perm_edit and command:match("^@.*$") then + local verb, param = command:match("^@(%a+)%s?(.*)$"); + end + local verb, object = command:match("^(%a+%s%a+)%s(.+)$"); + if verb and object and #verb > 0 and #object > 0 and person.room:_findobject(object) then + return verb, object; + end + verb, object = command:match("^(%a+)%s?(.*)$"); + if verb and object and #verb > 0 and #object > 0 then + return verb, object; + end + if verb and ((not object) or (object == "")) then return verb, nil; end +end + +function commands:_handle(person, action, object) + -- if not (person and action) then print("Invalid parameters!"); return; end + function callobjectmethod(object) + local o = person.room._objects:findobject(object) or person._contents["in"]:findobject(object); + if o and o[action] then o[action](o, {room = person.room, person = person, nick = person.nick }); return true; end + return false; + end + + if commands[action] then commands[action](person, action, object); + elseif object and object ~= "" and callobjectmethod(object) then return true; + elseif occupant[action] then occupant[action](person, { room = person.room, person = person }); return true; + elseif action and type(person.room[action]) == "function" then person.room[action](person.room, { room = person.room, person = person, jid = person.jid, nick = person.nick, param = object }); return true; + else return false; -- Unable to understand command + end +end + +function commands.get(person, action, param) + -- Decide if we are taking it from a container + obj1, obj2 = param:match("^([%a%s]+)%sfrom%s([%a%s]+)$"); + if obj1 and obj2 then -- We are taking from a container + local container = person:_findobject(obj2) or person.room:_findobject(obj2); + if not container then person:_tell(string.format("I don't see any '%s' here.", obj2 or "")); return; end + if not (container._contents and container._contents["in"]) then person:_tell(string.format("The %s is not a container.", obj2 or "")); return; end + object = container:_findobject(obj1); + if not object then + if object == false then person:_tell(string.format("Sorry, the %s is locked.", obj2)); + else person:_tell(string.format("I can't find any %s in there.", obj1)); end + return; + end + if person:_get({ object = object, container = container, name = obj1 }) then + person:_say(string.format("/me gets %s from %s", object._properties.longname or object._properties.name or "something", container._properties.longname or container._properties.name or "something")); + else + person:_tell("You can't get that"); + end + return; + end + obj1 = param:match("^([%a%s]+)$"); + if not obj1 then person:_tell("uh?"); return; end + -- So we are getting an object just in the room + local container = person.room; + local object = container:_findobject(obj1); + if not object then person:_tell(string.format("I can't find any %s in here.", obj1)); return; end + if person:_get({ object = object, container = container, name = obj1}) then + person:_say(string.format("/me picks up %s", object._properties.longname or object._properties.name or "something")); + else + person:_tell("You can't get that"); + end +end + +function commands.put(person, action, param) + obj1, obj2 = param:match("^([%a%s]+)%sin%s([%a%s]+)$"); + if not (obj1 and obj2) then return end + local oldcontainer = person; -- Where the object currently is + local object = person:_findobject(obj1); + if not object then object = person.room:_findobject(obj1); oldcontainer = person.room; end + if not object then person:_tell(string.format("Sorry, I can't find the '%s'.", obj1)); return; end + local newcontainer = person.room:_findobject(obj2); + if not newcontainer then person:_tell(string.format("I don't see any '%s' here.", obj2 or "")); return; end + if not (newcontainer._contents and newcontainer._contents["in"]) then person:_tell(string.format("The %s is not a container.", obj2 or "")); return; end + + if newcontainer:_get({ object = object, container = oldcontainer }) then + person:_say(string.format("/me puts %s in %s", object._properties.longname or object._properties.name or "something", newcontainer._properties.longname or newcontainer._properties.name or "something")); + else + person:_tell("You can't put that in there"); + end +end + +function commands.drop(person, action, param) + local o = person:_findobject(param); + if not o then person:_tell("You don't seem to have any "..param); return false; end + if person.room:_get({ object = o, container = person }) then + person:_say("/me drops "..(o._properties.longname or o._properties.name)); + end +end + +function commands.give(person, action, param) + if not param then person:_tell("Give what to whom?"); return; end + local objname, tonick = param:match("([%a%s]-)%s* to (.*)"); + if not objname or not tonick then person:_tell("Give what to whom?"); return; end + local o = person:_findobject(objname); + if not o then person:_tell("You don't seem to have any "..objname); return false; end + if not person.room.people[tonick] then person:_tell("Sorry, I can't find "..(tonick or "that person").."in this room..."); return; end + if person.room.people[tonick]:_get({object = o, container = person}) then + person:_action("gives "..(o._properties.longname or ((o._properties.prepend or "the").." "..o._properties.name)).." to "..param); + end +end + +function commands.help(person, action, param) + +end + +function commands.loadclass(person, action, param) + local subenv = { classes = { } } + local classdefinition = loadfile("objects/"..param..".lua"); + setfenv(classdefinition, subenv); + local success, message = pcall(classdefinition); + if not success then person:_tell(string.format("Error loading %s: %s", param, message)); + else + for k, v in pairs(classes[param]) do classes[param][k] = nil; end -- Clear current class + for k, v in pairs(subenv.classes[param]) do classes[param][k] = v; end -- Fill with data from new definition + person:_tell("Loaded"); + end +end + +function commands.dump(person, action, param) + table.print(param, person.room:_findobject(param) or person:_findobject(param) or classes.default or {}); +end + +function commands.dumproom(person, action, param) + table.print(person.room.name or "room", person.room); +end + +function commands.loadroom(person, action, param) + if not rooms[param] then person:_tell("You should go into the room, it has not even been created yet."); end + local oldpeople = rooms[param].people; + rooms[param]:_create{ room = param, server = GetJIDParts(person.occjid).server} + rooms[param].people = oldpeople; +end + +commands["@create"] = function (person, action, param) + local chunk = loadstring(param); + if not chunk then person:_tell("There was an error in your syntax. Please read the manual"); return; end + setfenv(chunk, 1); + local success, message = pcall(chunk); + if not success then person:_tell(message.."\nThere was an error processing the command"); return; end + local t = message; + local newobj = classes[t.class]:_create(t); + if newobj then + person._contents["in"]:add(newobj); + person:_action("waves his hands, and conjures something from thin air!"); + else + person:_tell("For some reason, the object was not created"); + end +end \ No newline at end of file