ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/deliantra/server/server/pets.C
(Generate patch)

Comparing deliantra/server/server/pets.C (file contents):
Revision 1.49 by root, Mon Dec 29 07:43:36 2008 UTC vs.
Revision 1.62 by root, Fri Mar 26 01:04:45 2010 UTC

1/* 1/*
2 * This file is part of Deliantra, the Roguelike Realtime MMORPG. 2 * This file is part of Deliantra, the Roguelike Realtime MMORPG.
3 * 3 *
4 * Copyright (©) 2005,2006,2007,2008 Marc Alexander Lehmann / Robin Redeker / the Deliantra team 4 * Copyright (©) 2005,2006,2007,2008,2009,2010 Marc Alexander Lehmann / Robin Redeker / the Deliantra team
5 * Copyright (©) 2002,2007 Mark Wedel & Crossfire Development Team 5 * Copyright (©) 2002 Mark Wedel & Crossfire Development Team
6 * Copyright (©) 1992,2007 Frank Tore Johansen 6 * Copyright (©) 1992 Frank Tore Johansen
7 * 7 *
8 * Deliantra is free software: you can redistribute it and/or modify 8 * Deliantra is free software: you can redistribute it and/or modify it under
9 * it under the terms of the GNU General Public License as published by 9 * the terms of the Affero GNU General Public License as published by the
10 * the Free Software Foundation, either version 3 of the License, or 10 * Free Software Foundation, either version 3 of the License, or (at your
11 * (at your option) any later version. 11 * option) any later version.
12 * 12 *
13 * This program is distributed in the hope that it will be useful, 13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details. 16 * GNU General Public License for more details.
17 * 17 *
18 * You should have received a copy of the GNU General Public License 18 * You should have received a copy of the Affero GNU General Public License
19 * along with this program. If not, see <http://www.gnu.org/licenses/>. 19 * and the GNU General Public License along with this program. If not, see
20 * <http://www.gnu.org/licenses/>.
20 * 21 *
21 * The authors can be reached via e-mail to <support@deliantra.net> 22 * The authors can be reached via e-mail to <support@deliantra.net>
22 */ 23 */
23 24
24#include <global.h> 25#include <global.h>
338 if (!on_same_map (ob, owner) && !owner->flag [FLAG_REMOVED]) 339 if (!on_same_map (ob, owner) && !owner->flag [FLAG_REMOVED])
339 { 340 {
340 follow_owner (ob, owner); 341 follow_owner (ob, owner);
341 return; 342 return;
342 } 343 }
344
343 /* Calculate Direction */ 345 /* Calculate Direction */
344 if (owner->type == PLAYER && owner->contr->petmode == pet_sad) 346 if (owner->type == PLAYER && owner->contr->petmode == pet_sad)
345 { 347 {
346 /* in S&D mode, if we have no enemy, run randomly about. */ 348 /* in S&D mode, if we have no enemy, run randomly about. */
347 for (i = 0; i < 15; i++) 349 for (i = 0; i < 15; i++)
363 struct rv_vector rv; 365 struct rv_vector rv;
364 366
365 get_rangevector (ob, ob->owner, &rv, 0); 367 get_rangevector (ob, ob->owner, &rv, 0);
366 dir = rv.direction; 368 dir = rv.direction;
367 } 369 }
370
368 ob->direction = dir; 371 ob->direction = dir;
369 372
370 /* move_ob returns 0 if the object couldn't move. If that is the 373 /* move_ob returns 0 if the object couldn't move. If that is the
371 * case, lets do some other work. 374 * case, lets do some other work.
372 */ 375 */
373 if (!(move_ob (ob, dir, ob))) 376 if (!(ob->move (dir)))
374 { 377 {
375 object *part; 378 object *part;
376 379
377 /* the failed move_ob above may destroy the pet, so check here */ 380 /* the failed move_ob above may destroy the pet, so check here */
378 if (ob->destroyed ()) 381 if (ob->destroyed ())
389 for (ob2 = GET_MAP_OB (m, dx, dy); ob2 != NULL; ob2 = ob2->above) 392 for (ob2 = GET_MAP_OB (m, dx, dy); ob2 != NULL; ob2 = ob2->above)
390 { 393 {
391 object *new_ob; 394 object *new_ob;
392 395
393 new_ob = ob2->head ? ob2->head : ob2; 396 new_ob = ob2->head ? ob2->head : ob2;
397
394 if (new_ob == ob) 398 if (new_ob == ob)
395 break; 399 break;
400
396 if (new_ob == ob->owner) 401 if (new_ob == ob->owner)
397 return; 402 return;
403
398 if (new_ob->owner == ob->owner) 404 if (new_ob->owner == ob->owner)
399 break; 405 break;
400 406
401 /* Hmm. Did we try to move into an enemy monster? If so, 407 /* Hmm. Did we try to move into an enemy monster? If so,
402 * make it our enemy. 408 * make it our enemy.
417 } 423 }
418 } 424 }
419 } 425 }
420 /* Try a different course */ 426 /* Try a different course */
421 dir = absdir (dir + 4 - (rndm (5)) - (rndm (5))); 427 dir = absdir (dir + 4 - (rndm (5)) - (rndm (5)));
422 (void) move_ob (ob, dir, ob); 428 ob->move (dir);
423 } 429 }
424 return;
425} 430}
426 431
427/**************************************************************************** 432/****************************************************************************
428 * 433 *
429 * GOLEM SPELL CODE 434 * GOLEM SPELL CODE
434 * proper for map insertion. 439 * proper for map insertion.
435 * at is the archetype, op is the caster of the spell, dir is the 440 * at is the archetype, op is the caster of the spell, dir is the
436 * direction the monster should be placed in. 441 * direction the monster should be placed in.
437 * is_golem is to note that this is a golem spell. 442 * is_golem is to note that this is a golem spell.
438 */ 443 */
439object * 444static object *
440fix_summon_pet (archetype *at, object *op, int dir, int is_golem) 445fix_summon_pet (archetype *at, object *op, int dir, int is_golem)
441{ 446{
442 object *tmp = NULL, *prev = NULL, *head = NULL; 447 object *tmp = NULL, *prev = NULL, *head = NULL;
443 448
444 for (archetype *atmp = at; atmp; atmp = (archetype *)atmp->more) 449 for (archetype *atmp = at; atmp; atmp = (archetype *)atmp->more)
445 { 450 {
446 tmp = arch_to_object (atmp); 451 tmp = atmp->instance ();
447 452
448 if (atmp == at) 453 if (atmp == at)
449 { 454 {
450 if (!is_golem) 455 if (!is_golem)
451 SET_FLAG (tmp, FLAG_MONSTER); 456 SET_FLAG (tmp, FLAG_MONSTER);
553 return; 558 return;
554 } 559 }
555 560
556 /* Do golem attacks/movement for single & multisq golems. 561 /* Do golem attacks/movement for single & multisq golems.
557 * Assuming here that op is the 'head' object. Pass only op to 562 * Assuming here that op is the 'head' object. Pass only op to
558 * move_ob (makes recursive calls to other parts) 563 * ->move (makes recursive calls to other parts)
559 * move_ob returns 0 if the creature was not able to move. 564 * move_ob returns 0 if the creature was not able to move.
560 */ 565 */
561 if (move_ob (op, op->direction, op)) 566 if (op->move (op->direction, op))
562 return; 567 return;
563 568
564 if (op->destroyed ()) 569 if (op->destroyed ())
565 return; 570 return;
566 571
592 { 597 {
593 /* for golems with race fields, we don't attack 598 /* for golems with race fields, we don't attack
594 * aligned races 599 * aligned races
595 */ 600 */
596 601
597 if (victim->race && op->race && strstr (op->race, victim->race)) 602 if (victim->race && op->race && op->race.contains (victim->race))
598 { 603 {
599 if (op->owner) 604 if (op->owner)
600 new_draw_info_format (NDI_UNIQUE, 0, op->owner, "%s avoids damaging %s.", &op->name, &victim->name); 605 new_draw_info_format (NDI_UNIQUE, 0, op->owner, "%s avoids damaging %s.", &op->name, &victim->name);
601 } 606 }
602 else if (victim == op->owner) 607 else if (victim == op->owner)
636int 641int
637summon_golem (object *op, object *caster, int dir, object *spob) 642summon_golem (object *op, object *caster, int dir, object *spob)
638{ 643{
639 object *tmp, *god = NULL; 644 object *tmp, *god = NULL;
640 archetype *at; 645 archetype *at;
641 char buf[MAX_BUF];
642 646
643 /* Because there can be different golem spells, player may want to 647 /* Because there can be different golem spells, player may want to
644 * 'lose' their old golem. 648 * 'lose' their old golem.
645 */ 649 */
646 if (op->type == PLAYER && op->contr->golem) 650 if (op->type == PLAYER && op->contr->golem)
699 op->contr->golem = tmp; 703 op->contr->golem = tmp;
700 /* give the player control of the golem */ 704 /* give the player control of the golem */
701 set_spell_skill (op, caster, spob, tmp); 705 set_spell_skill (op, caster, spob, tmp);
702 } 706 }
703 707
704 /* make the speed positive. */
705 tmp->speed = fabs (tmp->speed);
706
707 /* This sets the level dependencies on dam and hp for monsters */ 708 /* This sets the level dependencies on dam and hp for monsters */
708 /* players can't cope with too strong summonings. */ 709 /* players can't cope with too strong summonings. */
709 /* but monsters can. reserve these for players. */ 710 /* but monsters can. reserve these for players. */
710 if (op->type == PLAYER) 711 if (op->type == PLAYER)
711 { 712 {
712 tmp->stats.hp += spob->duration + SP_level_duration_adjust (caster, spob); 713 tmp->stats.hp += spob->duration + SP_level_duration_adjust (caster, spob);
736 tmp->direction = dir; 737 tmp->direction = dir;
737 738
738 /* Holy spell - some additional tailoring */ 739 /* Holy spell - some additional tailoring */
739 if (god) 740 if (god)
740 { 741 {
741 object *tmp2;
742
743 sprintf (buf, "%s of %s", &spob->name, &god->name); 742 char *buf = format ("%s of %s", &spob->name, &god->name);
744 buf[0] = toupper (buf[0]); 743 buf[0] = toupper (buf[0]);
745 744
746 for (tmp2 = tmp; tmp2; tmp2 = tmp2->more) 745 for (object *tmp2 = tmp; tmp2; tmp2 = tmp2->more)
747 tmp2->name = buf; 746 tmp2->name = buf;
748 747
749 tmp->attacktype |= god->attacktype; 748 tmp->attacktype |= god->attacktype;
750 memcpy (tmp->resist, god->resist, sizeof (tmp->resist)); 749 memcpy (tmp->resist, god->resist, sizeof (tmp->resist));
751 tmp->race = god->race; 750 tmp->race = god->race;
771/* Returns a monster (chosen at random) that this particular player (and his 770/* Returns a monster (chosen at random) that this particular player (and his
772 * god) find acceptable. This checks level, races allowed by god, etc 771 * god) find acceptable. This checks level, races allowed by god, etc
773 * to determine what is acceptable. 772 * to determine what is acceptable.
774 * This returns NULL if no match was found. 773 * This returns NULL if no match was found.
775 */ 774 */
776object * 775static object *
777choose_cult_monster (object *pl, object *god, int summon_level) 776choose_cult_monster (object *pl, object *god, int summon_level)
778{ 777{
779 char buf[MAX_BUF]; 778 char buf[MAX_BUF];
780 const char *race; 779 const char *race;
781 int racenr, mon_nr, i; 780 int racenr, mon_nr, i;
854} 853}
855 854
856int 855int
857summon_object (object *op, object *caster, object *spell_ob, int dir, const char *stringarg) 856summon_object (object *op, object *caster, object *spell_ob, int dir, const char *stringarg)
858{ 857{
859 sint16 x, y, nrof = 1, i; 858 int nrof = 1;
860 archetype *summon_arch; 859 archetype *summon_arch;
861 int ndir; 860 int ndir;
862 861
863 if (spell_ob->other_arch) 862 if (spell_ob->other_arch)
864 summon_arch = spell_ob->other_arch; 863 summon_arch = spell_ob->other_arch;
895 } 894 }
896 895
897 summon_arch = lasttr->item; 896 summon_arch = lasttr->item;
898 nrof = lasttr->nrof; 897 nrof = lasttr->nrof;
899 } 898 }
900 else if (spell_ob->race && !strcmp (spell_ob->race, "GODCULTMON")) 899 else if (spell_ob->race == shstr_GODCULTMON)
901 { 900 {
902 object *god = find_god (determine_god (op)), *mon, *owner; 901 object *god = find_god (determine_god (op)), *mon, *owner;
903 int summon_level, tries; 902 int summon_level, tries;
904 903
905 if (!god && ((owner = op->owner) != NULL)) 904 if (!god && ((owner = op->owner) != NULL))
964 { 963 {
965 new_draw_info (NDI_UNIQUE, 0, op, "There is no monsters available for summoning."); 964 new_draw_info (NDI_UNIQUE, 0, op, "There is no monsters available for summoning.");
966 return 0; 965 return 0;
967 } 966 }
968 967
969 for (i = 1; i <= nrof; i++) 968 for (int i = 1; i <= nrof; i++)
970 { 969 {
971 object *prev = NULL, *head = NULL, *tmp; 970 object *prev = NULL, *head = NULL, *tmp;
972 971
973 if (dir) 972 if (dir)
974 { 973 {
976 dir = absdir (dir + 1); 975 dir = absdir (dir + 1);
977 } 976 }
978 else 977 else
979 ndir = find_free_spot (summon_arch, op->map, op->x, op->y, 1, SIZEOFFREE); 978 ndir = find_free_spot (summon_arch, op->map, op->x, op->y, 1, SIZEOFFREE);
980 979
981 if (ndir > 0)
982 {
983 x = freearr_x[ndir]; 980 sint16 x = freearr_x [ndir];
984 y = freearr_y[ndir]; 981 sint16 y = freearr_y [ndir];
985 }
986 982
987 if (ndir < 0 || summon_arch->blocked (op->map, op->x + x, op->y + y)) 983 if (ndir < 0 || summon_arch->blocked (op->map, op->x + x, op->y + y))
988 { 984 {
989 new_draw_info (NDI_UNIQUE, 0, op, "There is something in the way."); 985 new_draw_info (NDI_UNIQUE, 0, op, "There is something in the way.");
990 if (nrof > 1) 986 if (nrof > 1)
991 new_draw_info (NDI_UNIQUE, 0, op, "No more pets for this casting."); 987 new_draw_info (NDI_UNIQUE, 0, op, "No more pets for this casting.");
992 988
993 return nrof > 1; 989 return nrof > 1;
994 } 990 }
995 991
996 for (archetype *atmp = summon_arch; atmp != NULL; atmp = (archetype *)atmp->more) 992 for (archetype *atmp = summon_arch; atmp; atmp = (archetype *)atmp->more)
997 { 993 {
998 tmp = arch_to_object (atmp); 994 tmp = atmp->instance ();
999 if (atmp == summon_arch) 995 if (atmp == summon_arch)
1000 { 996 {
1001 if (QUERY_FLAG (tmp, FLAG_MONSTER)) 997 if (QUERY_FLAG (tmp, FLAG_MONSTER))
1002 { 998 {
1003 tmp->set_owner (op); 999 tmp->set_owner (op);

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines