예제 #1
0
/** Open a new exit.
 * \verbatim
 * This is the top-level function for @open. It calls do_real_open()
 * to do the real work of opening both the exit forward and the exit back.
 * \endverbatim
 * \param player the enactor.
 * \param direction name of the exit forward.
 * \param links 1-based array, possibly containing name of destination, name of exit back,
 * and room to open initial exit from.
 * \param pe_info the pe_info to use for any lock checks
 */
void
do_open(dbref player, const char *direction, char **links, NEW_PE_INFO *pe_info)
{
  dbref forward;
  dbref source = NOTHING;

  if (links[3]) {
    source =
      match_result(player, links[3], TYPE_ROOM,
                   MAT_HERE | MAT_ABSOLUTE | MAT_TYPE);
    if (!GoodObject(source)) {
      notify(player, T("Open from where?"));
      return;
    }
  }

  if (links[5]) {
    if (!make_first_free_wrapper(player, links[5]))
      return;
  }
  if (links[4]) {
    if (!make_first_free_wrapper(player, links[4]))
      return;
  }

  forward = do_real_open(player, direction, links[1], source, pe_info);
  if (links[2] && *links[2] && GoodObject(forward)
      && GoodObject(Location(forward))) {
    char sourcestr[SBUF_LEN];   /* SBUF_LEN is the size used by unparse_dbref */
    if (!GoodObject(source)) {
      source = speech_loc(player);
    }
    strcpy(sourcestr, unparse_dbref(source));
    do_real_open(player, links[2], sourcestr, Location(forward), pe_info);
  }
}
예제 #2
0
파일: create.c 프로젝트: tkrajcar/pypenn
/** Clone an object.
 * \verbatim
 * This is the top-level function for @clone, which creates a duplicate
 * of a (non-player) object.
 * \endverbatim
 * \param player the enactor.
 * \param name the name of the object to clone.
 * \param newname the name to give the duplicate.
 * \param preserve if 1, preserve ownership and privileges on duplicate.
 * \paran newdbref the (unparsed) dbref to give the object, or NULL to use the next free
 * \return dbref of the duplicate, or NOTHING.
 */
dbref
do_clone(dbref player, char *name, char *newname, int preserve, char *newdbref)
{
  dbref clone, thing;
  char dbnum[BUFFER_LEN];

  thing = noisy_match_result(player, name, NOTYPE, MAT_EVERYTHING);
  if ((thing == NOTHING))
    return NOTHING;

  if (newname && *newname && !ok_name(newname, IsExit(thing))) {
    notify(player, T("That is not a reasonable name."));
    return NOTHING;
  }

  if (!controls(player, thing) || IsPlayer(thing) ||
      (IsRoom(thing) && !command_check_byname(player, "@dig")) ||
      (IsExit(thing) && !command_check_byname(player, "@open")) ||
      (IsThing(thing) && !command_check_byname(player, "@create"))) {
    notify(player, T("Permission denied."));
    return NOTHING;
  }
  /* don't allow cloning of destructed things */
  if (IsGarbage(thing)) {
    notify(player, T("There's nothing left of it to clone!"));
    return NOTHING;
  }
  if (preserve && !Wizard(player)) {
    notify(player, T("You cannot @CLONE/PRESERVE. Use normal @CLONE instead."));
    return NOTHING;
  }

  if (!make_first_free_wrapper(player, newdbref)) {
    return NOTHING;
  }

  /* make sure owner can afford it */
  switch (Typeof(thing)) {
  case TYPE_THING:
    if (can_pay_fees(player, Pennies(thing))) {
      clone = clone_object(player, thing, newname, preserve);
      notify_format(player, T("Cloned: Object %s."), unparse_dbref(clone));
      if (IsRoom(player))
        moveto(clone, player, player, "cloned");
      else
        moveto(clone, Location(player), player, "cloned");
      current_state.things++;
      local_data_clone(clone, thing);
      real_did_it(player, clone, NULL, NULL, NULL, NULL, "ACLONE", NOTHING,
                  global_eval_context.wenv, 0);
      return clone;
    }
    return NOTHING;
    break;
  case TYPE_ROOM:
    if (can_pay_fees(player, ROOM_COST)) {
      clone = clone_object(player, thing, newname, preserve);
      Exits(clone) = NOTHING;
      notify_format(player, T("Cloned: Room #%d."), clone);
      current_state.rooms++;
      local_data_clone(clone, thing);
      real_did_it(player, clone, NULL, NULL, NULL, NULL, "ACLONE", NOTHING,
                  global_eval_context.wenv, 0);
      return clone;
    }
    return NOTHING;
    break;
  case TYPE_EXIT:
    /* For exits, we don't want people to be able to link it to
       a location they can't with @open. So, all this stuff.
     */
    switch (Location(thing)) {
    case NOTHING:
      strcpy(dbnum, "#-1");
      break;
    case HOME:
      strcpy(dbnum, "home");
      break;
    case AMBIGUOUS:
      strcpy(dbnum, "variable");
      break;
    default:
      strcpy(dbnum, unparse_dbref(Location(thing)));
    }
    if (newname && *newname)
      clone = do_real_open(player, newname, dbnum, NOTHING);
    else
      clone = do_real_open(player, Name(thing), dbnum, NOTHING);
    if (!GoodObject(clone)) {
      return NOTHING;
    } else {
      atr_cpy(clone, thing);
      clone_locks(player, thing, clone);
      Zone(clone) = Zone(thing);
      Parent(clone) = Parent(thing);
      Flags(clone) = clone_flag_bitmask("FLAG", Flags(thing));
      if (!preserve) {
        clear_flag_internal(clone, "WIZARD");
        clear_flag_internal(clone, "ROYALTY");
        Warnings(clone) = 0;    /* zap warnings */
        Powers(clone) = new_flag_bitmask("POWER");      /* zap powers */
      } else {
        Warnings(clone) = Warnings(thing);
        Powers(clone) = clone_flag_bitmask("POWER", Powers(thing));
      }
      if (Wizard(clone) || Royalty(clone) || Warnings(clone) ||
          !null_flagmask("POWER", Powers(clone)))
        notify(player,
               T
               ("Warning: @CLONE/PRESERVE on an object with WIZ, ROY, @powers, or @warnings."));
      notify_format(player, T("Cloned: Exit #%d."), clone);
      local_data_clone(clone, thing);
      return clone;
    }
  }
  return NOTHING;

}
예제 #3
0
파일: create.c 프로젝트: tkrajcar/pypenn
/** Create a thing.
 * \verbatim
 * This is the top-level function for @create.
 * \endverbatim
 * \param player the enactor.
 * \param name name of thing to create.
 * \param cost pennies spent in creation.
 * \paran newdbref the (unparsed) dbref to give the object, or NULL to use the next free
 * \return dbref of new thing, or NOTHING.
 */
dbref
do_create(dbref player, char *name, int cost, char *newdbref)
{
  dbref loc;
  dbref thing;
  char *flaglist, *flagname;
  char flagbuff[BUFFER_LEN];

  if (*name == '\0') {
    notify(player, T("Create what?"));
    return NOTHING;
  } else if (!ok_name(name, 0)) {
    notify(player, T("That's a silly name for a thing!"));
    return NOTHING;
  } else if (cost < OBJECT_COST) {
    cost = OBJECT_COST;
  }

  if (!make_first_free_wrapper(player, newdbref)) {
    return NOTHING;
  }

  if (can_pay_fees(player, cost)) {
    /* create the object */
    thing = new_object();

    /* initialize everything */
    set_name(thing, name);
    if (!IsExit(player))        /* Exits shouldn't have contents! */
      Location(thing) = player;
    else
      Location(thing) = Source(player);
    Owner(thing) = Owner(player);
    Zone(thing) = Zone(player);
    s_Pennies(thing, cost);
    Type(thing) = TYPE_THING;
    Flags(thing) = new_flag_bitmask("FLAG");
    strcpy(flagbuff, options.thing_flags);
    flaglist = trim_space_sep(flagbuff, ' ');
    if (*flaglist != '\0') {
      while (flaglist) {
        flagname = split_token(&flaglist, ' ');
        twiddle_flag_internal("FLAG", thing, flagname, 0);
      }
    }


    /* home is here (if we can link to it) or player's home */
    if ((loc = Location(player)) != NOTHING &&
        (controls(player, loc) || Abode(loc))) {
      Home(thing) = loc;        /* home */
    } else {
      Home(thing) = Home(player);       /* home */
    }

    /* link it in */
    if (!IsExit(player))
      PUSH(thing, Contents(player));
    else
      PUSH(thing, Contents(Source(player)));

    /* and we're done */
    notify_format(player, T("Created: Object %s."), unparse_dbref(thing));
    current_state.things++;
    local_data_create(thing);

    queue_event(player, "OBJECT`CREATE", "%s", unparse_objid(thing));

    return thing;
  }
  return NOTHING;
}
예제 #4
0
파일: create.c 프로젝트: tkrajcar/pypenn
/** Create a room.
 * \verbatim
 * This is the top-level interface for @dig.
 * \endverbatim
 * \param player the enactor.
 * \param name the name of the room to create.
 * \param argv array of additional arguments to command
 *             (exit forward,exit back,newdbref)
 * \param tport if 1, teleport the player to the new room.
 * \return dbref of new room, or NOTHING.
 */
dbref
do_dig(dbref player, const char *name, char **argv, int tport)
{
  dbref room;
  char *flaglist, *flagname;
  char flagbuff[BUFFER_LEN];
  char *newdbref = NULL;

  if (argv[3] && *argv[3]) {
    newdbref = argv[3];
  }

  /* we don't need to know player's location!  hooray! */
  if (*name == '\0') {
    notify(player, T("Dig what?"));
  } else if (!ok_name(name, 0)) {
    notify(player, T("That's a silly name for a room!"));
  } else if (can_pay_fees(player, ROOM_COST)) {
    if (!make_first_free_wrapper(player, newdbref)) {
      return NOTHING;
    }

    room = new_object();

    /* Initialize everything */
    set_name(room, name);
    Owner(room) = Owner(player);
    Zone(room) = Zone(player);
    Type(room) = TYPE_ROOM;
    Flags(room) = new_flag_bitmask("FLAG");
    strcpy(flagbuff, options.room_flags);
    flaglist = trim_space_sep(flagbuff, ' ');
    if (*flaglist != '\0') {
      while (flaglist) {
        flagname = split_token(&flaglist, ' ');
        twiddle_flag_internal("FLAG", room, flagname, 0);
      }
    }

    notify_format(player, T("%s created with room number %d."), name, room);
    if (argv[1] && *argv[1]) {
      char nbuff[MAX_COMMAND_LEN];
      sprintf(nbuff, "#%d", room);
      do_real_open(player, argv[1], nbuff, NOTHING);
    }
    if (argv[2] && *argv[2]) {
      do_real_open(player, argv[2], "here", room);
    }
    current_state.rooms++;
    local_data_create(room);
    if (tport) {
      /* We need to use the full command, because we need NO_TEL
       * and Z_TEL checking */
      char roomstr[MAX_COMMAND_LEN];
      sprintf(roomstr, "#%d", room);
      do_teleport(player, "me", roomstr, 0, 0); /* if flag, move the player */
    }
    queue_event(player, "OBJECT`CREATE", "%s", unparse_objid(room));
    return room;
  }
  return NOTHING;
}