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

Comparing deliantra/server/server/spell_effect.C (file contents):
Revision 1.107 by elmex, Thu Sep 17 16:53:15 2009 UTC vs.
Revision 1.121 by elmex, Mon Mar 29 17:30:46 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>
71 if (!(random_roll (0, 3, op, PREFER_HIGH))) 72 if (!(random_roll (0, 3, op, PREFER_HIGH)))
72 { 73 {
73 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s vibrates violently, then explodes!", query_name (wand)); 74 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s vibrates violently, then explodes!", query_name (wand));
74 op->play_sound (sound_find ("ob_explode")); 75 op->play_sound (sound_find ("ob_explode"));
75 wand->destroy (); 76 wand->destroy ();
76 tmp = get_archetype ("fireball"); 77 tmp = get_archetype (shstr_fireball);
77 tmp->stats.dam = (spell_ob->stats.dam + SP_level_dam_adjust (caster, spell_ob)) / 10; 78 tmp->stats.dam = (spell_ob->stats.dam + SP_level_dam_adjust (caster, spell_ob)) / 10;
78 79
79 if (!tmp->stats.dam) 80 if (!tmp->stats.dam)
80 tmp->stats.dam = 1; 81 tmp->stats.dam = 1;
81 82
261 new_draw_info (NDI_UNIQUE, 0, op, "You don't have enough experience to create any food."); 262 new_draw_info (NDI_UNIQUE, 0, op, "You don't have enough experience to create any food.");
262 return 0; 263 return 0;
263 } 264 }
264 265
265 food_value /= at->stats.food; 266 food_value /= at->stats.food;
266 new_op = arch_to_object (at); 267 new_op = at->instance ();
267 new_op->nrof = food_value; 268 new_op->nrof = food_value;
268 269
269 new_op->value = 0; 270 new_op->value = 0;
270 if (new_op->nrof < 1) 271 if (new_op->nrof < 1)
271 new_op->nrof = 1; 272 new_op->nrof = 1;
564 565
565int 566int
566perceive_self (object *op) 567perceive_self (object *op)
567{ 568{
568 const char *cp = describe_item (op, op); 569 const char *cp = describe_item (op, op);
569 archetype *at = archetype::find (ARCH_DEPLETION); 570 archetype *at = archetype::find (shstr_depletion);
570 571
571 dynbuf_text &buf = msg_dynbuf; buf.clear (); 572 dynbuf_text &buf = msg_dynbuf; buf.clear ();
572 573
573 if (!op->is_player ()) 574 if (!op->is_player ())
574 return 0; 575 return 0;
593 for (int i = 0; i < NUM_STATS; i++) 594 for (int i = 0; i < NUM_STATS; i++)
594 if (tmp->stats.stat (i) < 0) 595 if (tmp->stats.stat (i) < 0)
595 buf.printf (" - Your %s is depleted by %d.\n", statname[i], -tmp->stats.stat (i)); 596 buf.printf (" - Your %s is depleted by %d.\n", statname[i], -tmp->stats.stat (i));
596 } 597 }
597 598
598 if (is_dragon_pl (op)) 599 if (op->is_dragon ())
599 /* now grab the 'dragon_ability'-force from the player's inventory */ 600 /* now grab the 'dragon_ability'-force from the player's inventory */
600 for (tmp = op->inv; tmp; tmp = tmp->below) 601 for (tmp = op->inv; tmp; tmp = tmp->below)
601 { 602 {
602 if (tmp->type == FORCE && tmp->arch->archname == shstr_dragon_ability_force) 603 if (tmp->type == FORCE && tmp->arch->archname == shstr_dragon_ability_force)
603 { 604 {
649 new_draw_info (NDI_UNIQUE, 0, op, "Something is in the way."); 650 new_draw_info (NDI_UNIQUE, 0, op, "Something is in the way.");
650 return 0; 651 return 0;
651 } 652 }
652 653
653 if (spell_ob->other_arch) 654 if (spell_ob->other_arch)
654 tmp = arch_to_object (spell_ob->other_arch); 655 tmp = spell_ob->other_arch->instance ();
655 else if (spell_ob->race) 656 else if (spell_ob->race)
656 { 657 {
657 char buf1[MAX_BUF]; 658 char buf1[MAX_BUF];
658 659
659 sprintf (buf1, spell_ob->race, dir); 660 sprintf (buf1, spell_ob->race, dir);
663 LOG (llevError, "summon_wall: Unable to find archetype %s\n", buf1); 664 LOG (llevError, "summon_wall: Unable to find archetype %s\n", buf1);
664 new_draw_info (NDI_UNIQUE, 0, op, "This spell is broken."); 665 new_draw_info (NDI_UNIQUE, 0, op, "This spell is broken.");
665 return 0; 666 return 0;
666 } 667 }
667 668
668 tmp = arch_to_object (at); 669 tmp = at->instance ();
669 } 670 }
670 else 671 else
671 { 672 {
672 LOG (llevError, "magic_wall: spell %s lacks other_arch\n", &spell_ob->name); 673 LOG (llevError, "magic_wall: spell %s lacks other_arch\n", &spell_ob->name);
673 return 0; 674 return 0;
717 return 0; 718 return 0;
718 } 719 }
719 720
720 /* If this is a spellcasting wall, need to insert the spell object */ 721 /* If this is a spellcasting wall, need to insert the spell object */
721 if (tmp->other_arch && tmp->other_arch->type == SPELL) 722 if (tmp->other_arch && tmp->other_arch->type == SPELL)
722 insert_ob_in_ob (arch_to_object (tmp->other_arch), tmp); 723 insert_ob_in_ob (tmp->other_arch->instance (), tmp);
723 724
724 /* This code causes the wall to extend some distance in 725 /* This code causes the wall to extend some distance in
725 * each direction, or until an obstruction is encountered. 726 * each direction, or until an obstruction is encountered.
726 * posblocked and negblocked help determine how far the 727 * posblocked and negblocked help determine how far the
727 * created wall can extend, it won't go extend through 728 * created wall can extend, it won't go extend through
747 object *tmp2 = tmp->clone (); 748 object *tmp2 = tmp->clone ();
748 m->insert (tmp2, x, y, op); 749 m->insert (tmp2, x, y, op);
749 750
750 /* If this is a spellcasting wall, need to insert the spell object */ 751 /* If this is a spellcasting wall, need to insert the spell object */
751 if (tmp2->other_arch && tmp2->other_arch->type == SPELL) 752 if (tmp2->other_arch && tmp2->other_arch->type == SPELL)
752 tmp2->insert (arch_to_object (tmp2->other_arch)); 753 tmp2->insert (tmp2->other_arch->instance ());
753 754
754 } 755 }
755 else 756 else
756 posblocked = 1; 757 posblocked = 1;
757 758
764 { 765 {
765 object *tmp2 = tmp->clone (); 766 object *tmp2 = tmp->clone ();
766 m->insert (tmp2, x, y, op); 767 m->insert (tmp2, x, y, op);
767 768
768 if (tmp2->other_arch && tmp2->other_arch->type == SPELL) 769 if (tmp2->other_arch && tmp2->other_arch->type == SPELL)
769 tmp2->insert (arch_to_object (tmp2->other_arch)); 770 tmp2->insert (tmp2->other_arch->instance ());
770 } 771 }
771 else 772 else
772 negblocked = 1; 773 negblocked = 1;
773 } 774 }
774 775
884 885
885 /* Actually move the player now */ 886 /* Actually move the player now */
886 if (!(op = op->map->insert (op, op->x + freearr_x[dir] * dist, op->y + freearr_y[dir] * dist, op))) 887 if (!(op = op->map->insert (op, op->x + freearr_x[dir] * dist, op->y + freearr_y[dir] * dist, op)))
887 return 1; 888 return 1;
888 889
889 op->speed_left = -FABS (op->speed) * 5; /* Freeze them for a short while */ 890 op->speed_left = -5. * op->speed; /* Freeze them for a short while */
891
890 return 1; 892 return 1;
891} 893}
892 894
893/* cast_heal: Heals something. 895/* cast_heal: Heals something.
894 * op is the caster. 896 * op is the caster.
949 if (cure_disease (tmp, op, spell)) 951 if (cure_disease (tmp, op, spell))
950 success = 1; 952 success = 1;
951 953
952 if (spell->attacktype & AT_POISON) 954 if (spell->attacktype & AT_POISON)
953 { 955 {
954 at = archetype::find ("poisoning"); 956 at = archetype::find (shstr_poisoning);
955 poison = present_arch_in_ob (at, tmp); 957 poison = present_arch_in_ob (at, tmp);
956 if (poison) 958 if (poison)
957 { 959 {
958 success = 1; 960 success = 1;
959 new_draw_info (NDI_UNIQUE, 0, tmp, "Your body feels cleansed"); 961 new_draw_info (NDI_UNIQUE, 0, tmp, "Your body feels cleansed");
961 } 963 }
962 } 964 }
963 965
964 if (spell->attacktype & AT_CONFUSION) 966 if (spell->attacktype & AT_CONFUSION)
965 { 967 {
966 poison = present_in_ob_by_name (FORCE, "confusion", tmp); 968 poison = present_in_ob_by_name (FORCE, shstr_confusion, tmp);
967 if (poison) 969 if (poison)
968 { 970 {
969 success = 1; 971 success = 1;
970 new_draw_info (NDI_UNIQUE, 0, tmp, "Your mind feels clearer"); 972 new_draw_info (NDI_UNIQUE, 0, tmp, "Your mind feels clearer");
971 poison->duration = 1; 973 poison->duration = 1;
972 } 974 }
973 } 975 }
974 976
975 if (spell->attacktype & AT_BLIND) 977 if (spell->attacktype & AT_BLIND)
976 { 978 {
977 at = archetype::find ("blindness"); 979 at = archetype::find (shstr_blindness);
978 poison = present_arch_in_ob (at, tmp); 980 poison = present_arch_in_ob (at, tmp);
979 if (poison) 981 if (poison)
980 { 982 {
981 success = 1; 983 success = 1;
982 new_draw_info (NDI_UNIQUE, 0, tmp, "Your vision begins to return."); 984 new_draw_info (NDI_UNIQUE, 0, tmp, "Your vision begins to return.");
1062 break; 1064 break;
1063 } 1065 }
1064 else if (spell_ob->race && spell_ob->race == tmp2->name) 1066 else if (spell_ob->race && spell_ob->race == tmp2->name)
1065 { 1067 {
1066 if (!silent) 1068 if (!silent)
1067 new_draw_info_format (NDI_UNIQUE, 0, op, "You can not cast %s while %s is in effect", &spell_ob->name, &tmp2->name_pl); 1069 new_draw_info_format (NDI_UNIQUE, 0, op,
1070 "You can not cast %s while %s is in effect",
1071 &spell_ob->name, &tmp2->name_pl);
1068 1072
1069 return 0; 1073 return 0;
1070 } 1074 }
1071 } 1075 }
1072 } 1076 }
1073 1077
1074 if (!force)
1075 {
1076 force = get_archetype (FORCE_NAME);
1077 force->subtype = FORCE_CHANGE_ABILITY;
1078
1079 if (spell_ob->race)
1080 force->name = spell_ob->race;
1081 else
1082 force->name = spell_ob->name;
1083
1084 force->name_pl = spell_ob->name;
1085 new_draw_info (NDI_UNIQUE, 0, op, "You create an aura of magical force.");
1086
1087 }
1088 else
1089 {
1090 int duration = change_ability_duration (spell_ob, caster); 1078 int duration = change_ability_duration (spell_ob, caster);
1091 1079
1080 if (force)
1081 {
1092 if (duration > force->duration) 1082 if (duration > force->duration)
1093 { 1083 {
1094 force->duration = duration; 1084 force->duration = duration;
1095 new_draw_info (NDI_UNIQUE, 0, op, "You recast the spell while in effect."); 1085 new_draw_info (NDI_UNIQUE, 0, op, "You recast the spell while in effect.");
1096 } 1086 }
1098 new_draw_info (NDI_UNIQUE, 0, op, "Recasting the spell had no effect."); 1088 new_draw_info (NDI_UNIQUE, 0, op, "Recasting the spell had no effect.");
1099 1089
1100 return 1; 1090 return 1;
1101 } 1091 }
1102 1092
1103 force->duration = spell_ob->duration + SP_level_duration_adjust (caster, spell_ob) * 50; 1093 new_draw_info_format (NDI_UNIQUE, 0, op,
1094 "You create an aura of magical force. H<The effect will last for about %.10g seconds.>",
1095 TICK2TIME (duration));
1096
1097 force = get_archetype (FORCE_NAME);
1098 force->subtype = FORCE_CHANGE_ABILITY;
1099 force->duration = duration;
1100
1101 if (spell_ob->race)
1102 force->name = spell_ob->race;
1103 else
1104 force->name = spell_ob->name;
1105
1106 force->name_pl = spell_ob->name;
1107
1104 force->speed = 1.0; 1108 force->speed = 1.0;
1105 force->speed_left = -1.0; 1109 force->speed_left = -1.0;
1106 SET_FLAG (force, FLAG_APPLIED); 1110 SET_FLAG (force, FLAG_APPLIED);
1107 1111
1108 /* Now start processing the effects. First, protections */ 1112 /* Now start processing the effects. First, protections */
1246 } 1250 }
1247 else 1251 else
1248 { 1252 {
1249 /* Only give out good benefits, and put a max on it */ 1253 /* Only give out good benefits, and put a max on it */
1250 for (i = 0; i < NROFATTACKS; i++) 1254 for (i = 0; i < NROFATTACKS; i++)
1251 {
1252 if (god->resist[i] > 0) 1255 if (god->resist[i] > 0)
1253 {
1254 force->resist[i] = MIN (god->resist[i], spell_ob->resist[ATNR_GODPOWER]); 1256 force->resist[i] = min (god->resist[i], spell_ob->resist[ATNR_GODPOWER]);
1255 } 1257
1256 }
1257 force->path_attuned |= god->path_attuned; 1258 force->path_attuned |= god->path_attuned;
1258 1259
1259 if (spell_ob->attacktype) 1260 if (spell_ob->attacktype)
1260 force->slaying = god->slaying; 1261 force->slaying = god->slaying;
1261 1262
1326 if (op->type != PLAYER) 1327 if (op->type != PLAYER)
1327 return 0; 1328 return 0;
1328 1329
1329 archetype *nugget[3]; 1330 archetype *nugget[3];
1330 1331
1331 nugget[0] = archetype::find ("pyrite3"); 1332 nugget[0] = archetype::find (shstr_pyrite3);
1332 nugget[1] = archetype::find ("pyrite2"); 1333 nugget[1] = archetype::find (shstr_pyrite2);
1333 nugget[2] = archetype::find ("pyrite"); 1334 nugget[2] = archetype::find (shstr_pyrite);
1334 1335
1335 /* Put a maximum weight of items that can be alchemised. Limits the power 1336 /* Put a maximum weight of items that can be alchemised. Limits the power
1336 * some, and also prevents people from alchemising every table/chair/clock 1337 * some, and also prevents people from alchemising every table/chair/clock
1337 * in sight 1338 * in sight
1338 */ 1339 */
1398 for (int i = 0; i < sizeof (nugget) / sizeof (nugget [0]); ++i) 1399 for (int i = 0; i < sizeof (nugget) / sizeof (nugget [0]); ++i)
1399 if (int nrof = value / nugget [i]->value) 1400 if (int nrof = value / nugget [i]->value)
1400 { 1401 {
1401 value -= nrof * nugget[i]->value; 1402 value -= nrof * nugget[i]->value;
1402 1403
1403 object *tmp = arch_to_object (nugget[i]); 1404 object *tmp = nugget[i]->instance ();
1404 tmp->nrof = nrof; 1405 tmp->nrof = nrof;
1405 tmp->flag [FLAG_IDENTIFIED] = true; 1406 tmp->flag [FLAG_IDENTIFIED] = true;
1406 op->map->insert (tmp, x, y, op, 0); 1407 op->map->insert (tmp, x, y, op, 0);
1407 } 1408 }
1408 1409
1544 range = spell->range + SP_level_range_adjust (caster, spell); 1545 range = spell->range + SP_level_range_adjust (caster, spell);
1545 1546
1546 if (!skill) 1547 if (!skill)
1547 skill = caster; 1548 skill = caster;
1548 1549
1550 dynbuf buf;
1549 unordered_mapwalk (op, -range, -range, range, range) 1551 unordered_mapwalk (buf, op, -range, -range, range, range)
1550 { 1552 {
1551 /* For most of the detections, we only detect objects above the 1553 /* For most of the detections, we only detect objects above the
1552 * floor. But this is not true for show invisible. 1554 * floor. But this is not true for show invisible.
1553 * Basically, we just go and find the top object and work 1555 * Basically, we just go and find the top object and work
1554 * down - that is easier than working up. 1556 * down - that is easier than working up.
1567 floor = 0; 1569 floor = 0;
1568 detect = NULL; 1570 detect = NULL;
1569 for (tmp = last; tmp; tmp = tmp->below) 1571 for (tmp = last; tmp; tmp = tmp->below)
1570 { 1572 {
1571 /* show invisible */ 1573 /* show invisible */
1572 if (QUERY_FLAG (spell, FLAG_MAKE_INVIS) && 1574 if (QUERY_FLAG (spell, FLAG_MAKE_INVIS)
1573 /* Might there be other objects that we can make visible? */ 1575 /* Might there be other objects that we can make visible? */
1574 (tmp->invisible && (QUERY_FLAG (tmp, FLAG_MONSTER) 1576 && (tmp->invisible && (QUERY_FLAG (tmp, FLAG_MONSTER)
1575 || (tmp->type == PLAYER && !QUERY_FLAG (tmp, FLAG_WIZ)) 1577 || (tmp->type == PLAYER && !QUERY_FLAG (tmp, FLAG_WIZ))
1576 || tmp->type == CF_HANDLE 1578 || tmp->type == T_HANDLE
1577 || tmp->type == TRAPDOOR 1579 || tmp->type == TRAPDOOR
1578 || tmp->type == EXIT 1580 || tmp->type == EXIT
1579 || tmp->type == HOLE 1581 || tmp->type == HOLE
1580 || tmp->type == BUTTON 1582 || tmp->type == BUTTON
1581 || tmp->type == TELEPORTER 1583 || tmp->type == TELEPORTER
1582 || tmp->type == GATE 1584 || tmp->type == GATE
1583 || tmp->type == LOCKED_DOOR 1585 || tmp->type == LOCKED_DOOR
1584 || tmp->type == WEAPON 1586 || tmp->type == WEAPON
1585 || tmp->type == ALTAR 1587 || tmp->type == ALTAR
1586 || tmp->type == SIGN 1588 || tmp->type == SIGN
1587 || tmp->type == TRIGGER_PEDESTAL 1589 || tmp->type == TRIGGER_PEDESTAL
1588 || tmp->type == SPECIAL_KEY 1590 || tmp->type == SPECIAL_KEY
1589 || tmp->type == TREASURE 1591 || tmp->type == TREASURE
1590 || tmp->type == BOOK 1592 || tmp->type == BOOK
1591 || tmp->type == HOLY_ALTAR 1593 || tmp->type == HOLY_ALTAR
1592 || tmp->type == CONTAINER))) 1594 || tmp->type == CONTAINER)))
1593 { 1595 {
1594 if (random_roll (0, skill->level - 1, op, PREFER_HIGH) > level / 4) 1596 if (random_roll (0, skill->level - 1, op, PREFER_HIGH) > level / 4)
1595 { 1597 {
1596 tmp->invisible = 0; 1598 tmp->invisible = 0;
1597 done_one = 1; 1599 done_one = 1;
1619 /* detect magic */ 1621 /* detect magic */
1620 if (QUERY_FLAG (spell, FLAG_KNOWN_MAGICAL) && 1622 if (QUERY_FLAG (spell, FLAG_KNOWN_MAGICAL) &&
1621 !QUERY_FLAG (tmp, FLAG_KNOWN_MAGICAL) && !QUERY_FLAG (tmp, FLAG_IDENTIFIED) && is_magical (tmp)) 1623 !QUERY_FLAG (tmp, FLAG_KNOWN_MAGICAL) && !QUERY_FLAG (tmp, FLAG_IDENTIFIED) && is_magical (tmp))
1622 { 1624 {
1623 SET_FLAG (tmp, FLAG_KNOWN_MAGICAL); 1625 SET_FLAG (tmp, FLAG_KNOWN_MAGICAL);
1624 /* make runes more visibile */ 1626 /* make runes more visible */
1625 if (tmp->type == RUNE && tmp->attacktype & AT_MAGIC) 1627 if (tmp->type == RUNE && tmp->attacktype & AT_MAGIC)
1626 tmp->stats.Cha /= 4; 1628 tmp->stats.Cha /= 4;
1627 1629
1628 done_one = 1; 1630 done_one = 1;
1629 } 1631 }
1655 (QUERY_FLAG (tmp, FLAG_CURSED) || QUERY_FLAG (tmp, FLAG_DAMNED))) 1657 (QUERY_FLAG (tmp, FLAG_CURSED) || QUERY_FLAG (tmp, FLAG_DAMNED)))
1656 { 1658 {
1657 SET_FLAG (tmp, FLAG_KNOWN_CURSED); 1659 SET_FLAG (tmp, FLAG_KNOWN_CURSED);
1658 done_one = 1; 1660 done_one = 1;
1659 } 1661 }
1662
1663 // Do mining detection spell:
1664 if (spell->last_sp == 1) // 1 - detect any vein
1665 {
1666 if (tmp->type == VEIN)
1667 {
1668 if (tmp->other_arch)
1669 {
1670 if (!detect)
1671 detect = tmp->other_arch;
1672 done_one = 2;
1673 }
1674 else
1675 done_one = 1;
1676 }
1677 }
1660 } /* for stack of objects on this space */ 1678 } /* for stack of objects on this space */
1661 1679
1662 /* Code here puts an effect of the spell on the space, so you can see 1680 /* Code here puts an effect of the spell on the space, so you can see
1663 * where the magic is. 1681 * where the magic is.
1664 */ 1682 */
1665 if (done_one) 1683 if (done_one)
1666 { 1684 {
1667 object *detect_ob = arch_to_object (spell->other_arch); 1685 object *detect_ob = spell->other_arch->instance ();
1668 1686
1669 /* if this is set, we want to copy the face */ 1687 /* if this is set, we want to copy the face */
1670 if (done_one == 2 && detect) 1688 if (done_one == 2 && detect)
1671 { 1689 {
1672 detect_ob->face = detect->face; 1690 detect_ob->face = detect->face;
1676 /* by default, the detect_ob is already animated */ 1694 /* by default, the detect_ob is already animated */
1677 if (!QUERY_FLAG (detect, FLAG_ANIMATE)) 1695 if (!QUERY_FLAG (detect, FLAG_ANIMATE))
1678 CLEAR_FLAG (detect_ob, FLAG_ANIMATE); 1696 CLEAR_FLAG (detect_ob, FLAG_ANIMATE);
1679 } 1697 }
1680 1698
1681 m->insert (detect_ob, nx, ny, op); 1699 m->insert (detect_ob, nx, ny, op, INS_ON_TOP);
1682 } 1700 }
1683 } /* for processing the surrounding spaces */ 1701 } /* for processing the surrounding spaces */
1684 1702
1685 1703
1686 /* Now process objects in the players inventory if detect curse or magic */ 1704 /* Now process objects in the players inventory if detect curse or magic */
2029 } 2047 }
2030 2048
2031 weapon = weapon->split (); 2049 weapon = weapon->split ();
2032 2050
2033 /* create the golem object */ 2051 /* create the golem object */
2034 tmp = arch_to_object (spell->other_arch); 2052 tmp = spell->other_arch->instance ();
2035 2053
2036 /* if animated by a player, give the player control of the golem */ 2054 /* if animated by a player, give the player control of the golem */
2037 CLEAR_FLAG (tmp, FLAG_MONSTER); 2055 CLEAR_FLAG (tmp, FLAG_MONSTER);
2038 tmp->stats.exp = 0; 2056 tmp->stats.exp = 0;
2039 add_friendly_object (tmp); 2057 add_friendly_object (tmp);
2084 2102
2085 /* attacktype */ 2103 /* attacktype */
2086 if (!tmp->attacktype) 2104 if (!tmp->attacktype)
2087 tmp->attacktype = AT_PHYSICAL; 2105 tmp->attacktype = AT_PHYSICAL;
2088 2106
2089 if (materialtype_t *mt = name_to_material (op->materialname))
2090 {
2091 for (i = 0; i < NROFATTACKS; i++) 2107 for (i = 0; i < NROFATTACKS; i++)
2092 tmp->resist[i] = 50 - (mt->save[i] * 5); 2108 tmp->resist[i] = 50 - (op->material->save[i] * 5);
2093 a = mt->save[0]; 2109
2094 } 2110 a = op->material->save[0];
2095 else
2096 {
2097 for (i = 0; i < NROFATTACKS; i++)
2098 tmp->resist[i] = 5;
2099 a = 10;
2100 }
2101 2111
2102 /* Set weapon's immunity */ 2112 /* Set weapon's immunity */
2103 tmp->resist[ATNR_CONFUSION] = 100; 2113 tmp->resist[ATNR_CONFUSION] = 100;
2104 tmp->resist[ATNR_POISON] = 100; 2114 tmp->resist[ATNR_POISON] = 100;
2105 tmp->resist[ATNR_SLOW] = 100; 2115 tmp->resist[ATNR_SLOW] = 100;
2132 tmp->state = weapon->state; 2142 tmp->state = weapon->state;
2133 tmp->flag [FLAG_ANIMATE] = weapon->flag [FLAG_ANIMATE]; 2143 tmp->flag [FLAG_ANIMATE] = weapon->flag [FLAG_ANIMATE];
2134 } 2144 }
2135 2145
2136 /* make experience increase in proportion to the strength of the summoned creature. */ 2146 /* make experience increase in proportion to the strength of the summoned creature. */
2137 tmp->stats.exp *= 1 + (MAX (spell->stats.maxgrace, spell->stats.sp) / casting_level (caster, spell)); 2147 tmp->stats.exp *= 1 + (max (spell->stats.maxgrace, spell->stats.sp) / casting_level (caster, spell));
2138 2148
2139 tmp->speed_left = -1; 2149 tmp->speed_left = -1;
2140 tmp->direction = dir; 2150 tmp->direction = dir;
2141 2151
2142 m->insert (tmp, x, y, op); 2152 m->insert (tmp, x, y, op);
2181 2191
2182 new_aura = present_arch_in_ob (spell->other_arch, op); 2192 new_aura = present_arch_in_ob (spell->other_arch, op);
2183 if (new_aura) 2193 if (new_aura)
2184 refresh = 1; 2194 refresh = 1;
2185 else 2195 else
2186 new_aura = arch_to_object (spell->other_arch); 2196 new_aura = spell->other_arch->instance ();
2187 2197
2188 new_aura->duration = spell->duration + 10 * SP_level_duration_adjust (caster, spell); 2198 new_aura->duration = spell->duration + 10 * SP_level_duration_adjust (caster, spell);
2189 2199
2190 new_aura->stats.dam = spell->stats.dam + SP_level_dam_adjust (caster, spell); 2200 new_aura->stats.dam = spell->stats.dam + SP_level_dam_adjust (caster, spell);
2191 2201
2256 if (pos.normalise () && !(OB_TYPE_MOVE_BLOCK (env, pos->move_block))) 2266 if (pos.normalise () && !(OB_TYPE_MOVE_BLOCK (env, pos->move_block)))
2257 { 2267 {
2258 hit_map (aura, i, aura->attacktype, 0); 2268 hit_map (aura, i, aura->attacktype, 0);
2259 2269
2260 if (aura->other_arch) 2270 if (aura->other_arch)
2261 pos.insert (arch_to_object (aura->other_arch), aura); 2271 pos.insert (aura->other_arch->instance (), aura);
2262 } 2272 }
2263 } 2273 }
2264 2274
2265 /* put the aura back in the player's inventory */ 2275 /* put the aura back in the player's inventory */
2266 env->insert (aura); 2276 env->insert (aura);
2285 continue; 2295 continue;
2286 2296
2287 if (victim->stats.exp == 0) 2297 if (victim->stats.exp == 0)
2288 continue; 2298 continue;
2289 2299
2290 def_lev = MAX (1, victim->level); 2300 def_lev = max (1, victim->level);
2291 atk_lev = MAX (1, op->level); 2301 atk_lev = max (1, op->level);
2292 2302
2293 if (rndm (0, atk_lev - 1) > def_lev) 2303 if (rndm (0, atk_lev - 1) > def_lev)
2294 { 2304 {
2295 /* make this sucker peaceful. */ 2305 /* make this sucker peaceful. */
2296 2306
2328 { 2338 {
2329 new_draw_info (NDI_UNIQUE, 0, op, "Write what?"); 2339 new_draw_info (NDI_UNIQUE, 0, op, "Write what?");
2330 return 0; 2340 return 0;
2331 } 2341 }
2332 2342
2333 if (strcasestr_local (msg, "endmsg")) 2343 if (!msg_is_safe (msg))
2334 { 2344 {
2335 new_draw_info (NDI_UNIQUE, 0, op, "Trying to cheat are we?"); 2345 new_draw_info (NDI_UNIQUE, 0, op, "Trying to cheat are we?");
2336 LOG (llevInfo, "write_rune: player %s tried to write bogus rune %s\n", &op->name, msg); 2346 LOG (llevInfo, "write_mark: player %s tried to write bogus rune %s\n", &op->name, msg);
2337 return 0; 2347 return 0;
2338 } 2348 }
2339 2349
2340 if (!spell->other_arch) 2350 if (!spell->other_arch)
2341 return 0; 2351 return 0;
2342 2352
2343 object *tmp = arch_to_object (spell->other_arch); 2353 object *tmp = spell->other_arch->instance ();
2344 2354
2345 tmp->race = op->name; /*Save the owner of the rune */ 2355 tmp->race = op->name; /*Save the owner of the rune */
2346 tmp->msg = msg; 2356 tmp->msg = msg;
2347 2357
2348 tmp->insert_at (op, op, INS_BELOW_ORIGINATOR); 2358 tmp->insert_at (op, op, INS_BELOW_ORIGINATOR);

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines