
Weapon Spell Special Procedures
dkoepke@california.com


--introduction

This little patch spawns from my personal aid to someone with making
weapons cast spells in the heat of combat. This patch is rather small
and the code is fairly simply, but it works and is flexible. This
little document should explain how to add the patch and how to add
more weapon spell spec-procs.

This patch comes with three example spec-procs: blind_weapon,
fireball_weapon, and curse_weapon (each named after the spell they
cast). They are *offensive* spells. It's possible to make defensive
spells which are cast on the wielder of the magical weapon or on one
of their group-members. These three spec-procs are assigned to objects
#15, #16, and #17 (respectfully), which do not exist in stock Circle.
They were used as test objects [and the db enteries for these objects
are shown later in this document, too].

Oh, also, this is my new document format for READMEs and things. I
like this more than the older format you can see with my other patches.
I still need to update those older patches, as of this writing, I just
keep forgetting to do it.


--about the author

Daniel Koepke is a person. He uses a computer. He's connected to the
internet via his ISP, california.com, which will also be hosting his
mud (in lowercase). It is uncertain whether he will put up a CircleMud
to start with, or just wait until he finishes his mud from scratch.
You'll just have to wait and see.

Presently, he belongs to the CircleMud Mailing List, and the Moderated
CircleMud Mailing List. He regularly contributes to the first, and has
yet to say a damn thing on the second (<grin>). He's not a fake person.
If he is pissed off, he says it, he's not on the mailing lists for a
popularity contest. He doesn't presently have a mud up, he doesn't have
a cure for cancer (not yet, anyway), and, no, he won't help you Riddler.


--what is availible by me?

Presently, I have a healthy selection of patches availible that can help
you get a few features into your mud without any or much coding
involved. The 'mount' patch serves as a starting point for coding a
complete mount system, it does not include things like tethering,
horse-back combat, etc. It is left up to you to do that.

  Query ANSI Patch: qansi.diff.gz, qansi.diff.README
    Adds a CON_ state that prompts a player if they have ANSI or not.
    You can then add your own code to have a colorized login screen, 
    character creation process, MOTD, etc. No reported bugs.

  Base Mount System Patch: mount.diff.gz, mount.diff.README
    Adds a few skills and commands for supporting mounts. There may
    be a few bugs in movement, but the only reported bug is a typo
    or two in do_buck() [damaging the wrong person] and perhaps sending
    a message to the wrong person. To add OasisOLC support for the
    MOB_MOUNTABLE flag increase the NUM_MOB_FLAGS by one. Note that
    the skill numbers used for the mounting and riding skills may need
    to be changed if you have added more skills or if you used my
    multi-hit patch.

  Multiple Hits Per Round Patch: multi-hit.diff.gz, multi-hit.diff.README
    Adds two skills for characters doing two or three attacks per
    round. Very small and simple patch. It most likely won't fit in
    smoothly because it adds new skill defines , but manually patching 
    this one in is very trivial. No reported bugs.

  New do_who Patch: do_who.diff.gz, do_who.diff.README
    A new 'who' command that seperates immortals and mortals and provides
    individual counts for each of them, as well as a wiz-title (eg.,
    [Implementor] instead of level and class). Also includes the highest
    number of players for a single reboot. No reported bugs with the
    second revision.

  Improved Prompt Patch: new_prompt.diff.gz, new_prompt.diff.README
    Includes premade prompts and the ability for players to create their
    own unique prompts using % codes and color codes. Includes my
    on-the-fly color system (I posted a revision to the color parser
    on the unmoderated list a time back which I plan to incorperate into
    this patch sooner or later). No bugs have been reported.

I think that's all (I'm not exactly sure...:)). Also, there are snippets
by Brian Williams on Alex's snippet page that are based upon my code.
I also HTML'ized the CircleMUD Role-Playing Proposal, written by Claywar 
(I forget where it is, ask claywar@cetlink.net) and contributed a few
things to it. Furthermore, I've contributed to the CircleMUD FAQ which
is maintained by Alex Fletcher (Furry) [*read it before posting to the
mailing list god dammit*]. Done a little of this and a little of that.


--patching in this one

To patch in wspell.diff (under UNIX, I dunno about DOS/Windows/etc.),
do:

  % patch < wspell.diff

The '%' being the UNIX prompt. If you get rejections you'll have to
manually patch in stuff from the .rej files that are created. A '+' is
an addition, a '-' is a removal, and a '!' means change the line(s) 
marked with it to the matching line(s) below the '---xxx,xxx---'
seperator.


--the test objects

As said in the introduction, the three existing weapon spell special
procedures are assigned to three test objects, #15, #16, and #17. You
may either delete the ASSIGNOBJ() calls that assign the spec-procs
to the objects or create the test objects. Here is the database
enteries for the three test objects that I placed in lib/world/obj/0.obj

  #15
  mace nightbringer~
  Nightbringer~
  A mace with the word 'Nightbringer' etched into the shaft lies here.~
  ~
  5 cd 8193
  0 15 15 5
  40 0 50000
  #16
  sword firecaster~
  Firecaster~
  A sword with the word 'Firecaster' etched into the hilt lies here.~
  ~
  5 cd 8193
  0 15 15 5
  40 0 50000
  #17
  flail unholy~
  Unholy~
  A flail with the word 'Unholy' etched into the shaft lies here.~
  ~
  5 cd 8193
  0 15 15 5
  40 0 50000

These were placed after the waybread and before the scythe of death.
They are meant to be for immortals only, thus are too heavy for anyone
but those with maximum (25/100) strength can wield.


--damaging weapon spells

Three damaging weapon spells are included in the patch by default. You
can examine them for yourself to see how things are done. For those of
you that might need a little more help, here is the blind_weapon
special procedure shown below and disected:

  SPECIAL(blind_weapon)
  {
    struct char_data *vict = FIGHTING(ch);
  
    if (cmd || !vict || number(0, 9))
      return 0;
    if (IS_AFFECTED(vict, AFF_BLIND) || MOB_FLAGGED(vict, MOB_NOBLIND))
      return 0;
    
    weapon_spell("You scream, \"MIDNIGHT!\" at $N.",
                 "$n screams, \"Midnight!\" at you.",
                 "$n screams, \"Midnight!\" at $N.",
                 ch, vict, (struct obj_data *) me, SPELL_BLINDNESS);
    return 1;
  }

The line 'struct char_data *vict = FIGHTING(ch);' sets the target of
the spell to whomever the caster is fighting. This is required for the
damaging weapon spells (you don't want to cast it on anyone else, do
you?).

The 'if (cmd || !vict || number(0, 9))' line done three different
things. First it checks if 'cmd != 0' [the != 0 is implied]. If cmd
is non-zero we return 0 and the rest of the spec-proc is ignored. If
cmd is zero, then we check if victim is null (zero, unset). If that
is true, we return 0 because there is no-one to cast the spell on.
Then we check if a random number between zero and nine isn't zero
and if so, we return without executing the spec-proc. The purpose this
last one serves is to make the casting of the weapon spells rare, so
that they don't always occur. Changing the higher number will increase
or decrease the chances the spell is cast (eg., number(0, 1) is a 50/50
chance, number(0, 3) is a 25/75 chance).

Next we check if the victim is already blind or if the victim is a
mobile and can't be blinded. If either one or both is true, the
spec-proc returns zero, making the character take a swing instead.

Finally, we come to our weapon_spell() call. The weapon_spell()
function accepts seven arguments. The message sent to the wielder
of the weapon when the spell is *attempted* (note that the spell
can still fail), the message sent to the victim of the weapon when
the spell is *attempted* (the spell can still fail), and the message
sent to the room when the spell is *attmempted* (spell can still
fail). After these three, there is another group of three arguments.
These should almost always stay the same. The first is the wielder
of the weapon (who is always 'ch'), the second is the victim (who is
always 'vict'), and the third is the weapon itself (which is always
'(struct obj_data *) me'. The last argument is the spell to cast,
in this case SPELL_BLINDNESS.

To create a new weapon spell spec-proc, just copy an old one, change
or remove the second 'if' statement as necessary. You don't need to
change the chance of success, but you might want to. After that, you
only need to change the messages and the spell to cast. The rest is
done automatically.


--helpful spells

You can also have it cast helpful spells on people. For instance,
the heal spell can be cast on the wielder. This is easily accomplished
using the above instructions for damage spells, save changing the
'struct char_data *vict = FIGHTING(ch);' line to simply 'struct
char_data *vict = ch;'.


--random targets

There is two times in which you'd want to use a random target. First
if you wanted to hit someone that you weren't hitting. This is
accomplished by going through the room and picking a pseudo-random
person that has FIGHTING(vict) == ch and is shown below:

  struct char_data *vict; /* was: struct char_data *vict = FIGHTING(ch); */

  if (cmd || number(0, 11)) /* note that the !vict is moved below */
    return 0;

  /* add the below */
  for (vict = world[ch->in_room].people; vict; vict = vict->next_in_room)
    if (vict != FIGHTING(ch) && FIGHTING(vict) == ch && !number(0, 2))
      break;

  if (!vict)
    if (!(vict = FIGHTING(ch))
      return 0;


There's still a likelihood that you'll strike the person you're fighting,
but there's also a good chance it will be someone else that is fighting
you.

The other time you'd want to pick a random target is if you wanted to
cast a defensive/healing spell on someone in the same group as you. This 
is accomplished by:

  struct char_data *vict; /* was: struct char_data *vict = FIGHTING(ch); */
  struct char_data *j;
  struct follow_type *f;

  /* !vict check moved below the 'for' */
  if (cmd || !IS_AFFECTED(ch, AFF_GROUP) || number(0, 11))
    return 0;

  j = (ch->master ? ch->master : ch);

  /* add the below */
  for (f = j->followers; f; f = f->next)
    if (!number(0, 2) && IS_AFFECTED((vict = j->follower), AFF_GROUP))
      break;

  if (!vict)
    if (!(vict = j))
      return 0;

Good luck with your endeavors!


--credits

Documentation and patch written by Daniel Koepke <dkoepke@california.com>.
Thanks to Jeremy Elson for all of his work on CircleMUD and in providing
CircleMUD. Also thanks to Alex Fletcher for maintaining the CircleMUD
Mailing List, the CircleMUD FAQ, the world of CircleMUD, the DIKUMUD FAQ,
the non-circlemud.org Circle WWW site (including the Snippets page, and
Alex, I didn't call it unofficial this time :)).

Everyone else who deserves thanks...well, I haven't forgotten you and
I do care, just not enough to spend the time and trouble thanking each
one of you individually. :)~

Oh, yes, and for all of those that have flamed me for being egotistical,
I'd like to extend a second, third, and fourth thanks out to me, myself,
and I. Not because I've got a large ego, but because I know it pisses
you off.


--circlemud resources

ftp.circlemud.org
  Maintainer: Alex Fletcher (furry) (and...?) <fletcher@cspo.queensu.ca>
  Desc      : The ftp site (duh)
http://www.circlemud.org/
  Maintainer: Jeremy Elson <jelson@-so-many-places-no-one-knows-for-sure>
  Desc      : Jeremy Elson's main CircleMUD homepage thingy
http://cspo.queensu.ca/~fletcher/Circle/
  Maintainer: <deja-vu!> Alex Fletcher (furry) <fletcher@cspo.queensu.ca>
  Desc      : Alex's Circle-ish place
majordomo@cspo.queensu.ca [errmm, I think this is it]
  Maintainer: <wow, deja-vu...AGAIN!> Alex Fletcher (furry)..blah,blah,blah
  Desc      : Mailing list subscription address...and before you post to
              the list (circle@cpso.queensu.ca): READ THE FUCKING FAQ!!


--
Daniel Koepke
dkoepke@california.com
Forgive me father, for I am sin.
Mass Cult Suicide? Just do it. 
