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.54 by root, Mon May 28 21:28:36 2007 UTC vs.
Revision 1.71 by root, Wed Aug 29 20:40:25 2007 UTC

3 * 3 *
4 * Copyright (©) 2005,2006,2007 Marc Alexander Lehmann / Robin Redeker / the Crossfire TRT team 4 * Copyright (©) 2005,2006,2007 Marc Alexander Lehmann / Robin Redeker / the Crossfire TRT team
5 * Copyright (©) 2002,2007 Mark Wedel & Crossfire Development Team 5 * Copyright (©) 2002,2007 Mark Wedel & Crossfire Development Team
6 * Copyright (©) 1992,2007 Frank Tore Johansen 6 * Copyright (©) 1992,2007 Frank Tore Johansen
7 * 7 *
8 * Crossfire TRT is free software; you can redistribute it and/or modify it 8 * Crossfire TRT is free software: you can redistribute it and/or modify
9 * under the terms of the GNU General Public License as published by the Free 9 * it under the terms of the GNU General Public License as published by
10 * Software Foundation; either version 2 of the License, or (at your option) 10 * the Free Software Foundation, either version 3 of the License, or
11 * any later version. 11 * (at your option) any later version.
12 * 12 *
13 * This program is distributed in the hope that it will be useful, but 13 * This program is distributed in the hope that it will be useful,
14 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * 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 along 18 * You should have received a copy of the GNU General Public License
19 * with Crossfire TRT; if not, write to the Free Software Foundation, Inc. 51 19 * along with this program. If not, see <http://www.gnu.org/licenses/>.
20 * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 * 20 *
22 * The authors can be reached via e-mail to <crossfire@schmorp.de> 21 * The authors can be reached via e-mail to <crossfire@schmorp.de>
23 */ 22 */
24 23
25#include <global.h> 24#include <global.h>
70 return 0; 69 return 0;
71 } 70 }
72 if (!(random_roll (0, 3, op, PREFER_HIGH))) 71 if (!(random_roll (0, 3, op, PREFER_HIGH)))
73 { 72 {
74 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s vibrates violently, then explodes!", query_name (wand)); 73 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s vibrates violently, then explodes!", query_name (wand));
75 play_sound_map (op->map, op->x, op->y, SOUND_OB_EXPLODE); 74 op->play_sound (sound_find ("ob_explode"));
76 esrv_del_item (op->contr, wand->count); 75 esrv_del_item (op->contr, wand->count);
77 wand->destroy (); 76 wand->destroy ();
78 tmp = get_archetype ("fireball"); 77 tmp = get_archetype ("fireball");
79 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;
80 79
104 ncharges = 1; 103 ncharges = 1;
105 104
106 wand->stats.food += ncharges; 105 wand->stats.food += ncharges;
107 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s glows with power.", query_name (wand)); 106 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s glows with power.", query_name (wand));
108 107
109 if (wand->arch && QUERY_FLAG (&wand->arch->clone, FLAG_ANIMATE)) 108 if (wand->arch && QUERY_FLAG (wand->arch, FLAG_ANIMATE))
110 { 109 {
111 SET_FLAG (wand, FLAG_ANIMATE); 110 SET_FLAG (wand, FLAG_ANIMATE);
112 wand->set_speed (wand->arch->clone.speed); 111 wand->set_speed (wand->arch->speed);
113 } 112 }
114 113
115 return 1; 114 return 1;
116} 115}
117 116
123 * great a plus, the default is used. 122 * great a plus, the default is used.
124 * The # of arrows created also goes up with level, so if a 30th level mage 123 * The # of arrows created also goes up with level, so if a 30th level mage
125 * wants LOTS of arrows, and doesn't care what the plus is he could 124 * wants LOTS of arrows, and doesn't care what the plus is he could
126 * create nonnmagic arrows, or even -1, etc... 125 * create nonnmagic arrows, or even -1, etc...
127 */ 126 */
128
129int 127int
130cast_create_missile (object *op, object *caster, object *spell, int dir, const char *stringarg) 128cast_create_missile (object *op, object *caster, object *spell, int dir, const char *stringarg)
131{ 129{
132 int missile_plus = 0, bonus_plus = 0; 130 int missile_plus = 0, bonus_plus = 0;
133 const char *missile_name; 131 const char *missile_name;
224 if (stringarg) 222 if (stringarg)
225 { 223 {
226 at = find_archetype_by_object_type_name (FOOD, stringarg); 224 at = find_archetype_by_object_type_name (FOOD, stringarg);
227 if (at == NULL) 225 if (at == NULL)
228 at = find_archetype_by_object_type_name (DRINK, stringarg); 226 at = find_archetype_by_object_type_name (DRINK, stringarg);
229 if (at == NULL || at->clone.stats.food > food_value) 227 if (at == NULL || at->stats.food > food_value)
230 stringarg = NULL; 228 stringarg = NULL;
231 } 229 }
232 230
233 if (!stringarg) 231 if (!stringarg)
234 { 232 {
240 * We don't use flesh types because the weight values of those need 238 * We don't use flesh types because the weight values of those need
241 * to be altered from the donor. 239 * to be altered from the donor.
242 */ 240 */
243 241
244 /* We assume the food items don't have multiple parts */ 242 /* We assume the food items don't have multiple parts */
245 for (at_tmp = first_archetype; at_tmp != NULL; at_tmp = at_tmp->next) 243 for_all_archetypes (at_tmp)
246 { 244 {
247 if (at_tmp->clone.type == FOOD || at_tmp->clone.type == DRINK) 245 if (at_tmp->type == FOOD || at_tmp->type == DRINK)
248 { 246 {
249 /* Basically, if the food value is something that is creatable 247 /* Basically, if the food value is something that is creatable
250 * under the limits of the spell and it is higher than 248 * under the limits of the spell and it is higher than
251 * the item we have now, take it instead. 249 * the item we have now, take it instead.
252 */ 250 */
253 if (at_tmp->clone.stats.food <= food_value && (!at || at_tmp->clone.stats.food > at->clone.stats.food)) 251 if (at_tmp->stats.food <= food_value
252 && (!at
253 || at_tmp->stats.food > at->stats.food
254 || (at_tmp->stats.food == at->stats.food
255 && at_tmp->weight < at->weight)))
254 at = at_tmp; 256 at = at_tmp;
255 } 257 }
256 } 258 }
257 } 259 }
260
258 /* Pretty unlikely (there are some very low food items), but you never 261 /* Pretty unlikely (there are some very low food items), but you never
259 * know 262 * know
260 */ 263 */
261 if (!at) 264 if (!at)
262 { 265 {
263 new_draw_info (NDI_UNIQUE, 0, op, "You don't have enough experience to create any food."); 266 new_draw_info (NDI_UNIQUE, 0, op, "You don't have enough experience to create any food.");
264 return 0; 267 return 0;
265 } 268 }
266 269
267 food_value /= at->clone.stats.food; 270 food_value /= at->stats.food;
268 new_op = arch_to_object (at); 271 new_op = arch_to_object (at);
269 new_op->nrof = food_value; 272 new_op->nrof = food_value;
270 273
271 new_op->value = 0; 274 new_op->value = 0;
272 if (new_op->nrof < 1) 275 if (new_op->nrof < 1)
287 if (!dir) 290 if (!dir)
288 { 291 {
289 examine_monster (op, op); 292 examine_monster (op, op);
290 return 1; 293 return 1;
291 } 294 }
295
292 maxrange = spell_ob->range + SP_level_range_adjust (caster, spell_ob); 296 maxrange = spell_ob->range + SP_level_range_adjust (caster, spell_ob);
293 for (r = 1; r < maxrange; r++) 297 for (r = 1; r < maxrange; r++)
294 { 298 {
295 sint16 x = op->x + r * freearr_x[dir], y = op->y + r * freearr_y[dir]; 299 sint16 x = op->x + r * freearr_x[dir], y = op->y + r * freearr_y[dir];
296 300
316 examine_monster (op, tmp); 320 examine_monster (op, tmp);
317 return 1; 321 return 1;
318 } 322 }
319 } 323 }
320 } 324 }
325
321 new_draw_info (NDI_UNIQUE, 0, op, "You detect nothing."); 326 new_draw_info (NDI_UNIQUE, 0, op, "You detect nothing.");
322 return 1; 327 return 1;
323} 328}
324
325 329
326/* This checks to see if 'pl' is invisible to 'mon'. 330/* This checks to see if 'pl' is invisible to 'mon'.
327 * does race check, undead check, etc 331 * does race check, undead check, etc
328 * Returns TRUE if mon can't see pl, false 332 * Returns TRUE if mon can't see pl, false
329 * otherwise. This doesn't check range, walls, etc. It 333 * otherwise. This doesn't check range, walls, etc. It
331 * pl is invisible. 335 * pl is invisible.
332 */ 336 */
333int 337int
334makes_invisible_to (object *pl, object *mon) 338makes_invisible_to (object *pl, object *mon)
335{ 339{
336
337 if (!pl->invisible) 340 if (!pl->invisible)
338 return 0; 341 return 0;
342
339 if (pl->type == PLAYER) 343 if (pl->type == PLAYER)
340 { 344 {
341 /* If race isn't set, then invisible unless it is undead */ 345 /* If race isn't set, then invisible unless it is undead */
342 if (!pl->contr->invis_race) 346 if (!pl->contr->invis_race)
343 { 347 {
344 if (QUERY_FLAG (mon, FLAG_UNDEAD)) 348 if (QUERY_FLAG (mon, FLAG_UNDEAD))
345 return 0; 349 return 0;
350
346 return 1; 351 return 1;
347 } 352 }
353
348 /* invis_race is set if we get here */ 354 /* invis_race is set if we get here */
349 if (!strcmp (pl->contr->invis_race, "undead") && is_true_undead (mon)) 355 if (!strcmp (pl->contr->invis_race, "undead") && is_true_undead (mon))
350 return 1; 356 return 1;
357
351 /* No race, can't be invisible to it */ 358 /* No race, can't be invisible to it */
352 if (!mon->race) 359 if (!mon->race)
353 return 0; 360 return 0;
361
354 if (strstr (mon->race, pl->contr->invis_race)) 362 if (strstr (mon->race, pl->contr->invis_race))
355 return 1; 363 return 1;
364
356 /* Nothing matched above, return 0 */ 365 /* Nothing matched above, return 0 */
357 return 0; 366 return 0;
358 } 367 }
359 else 368 else
360 { 369 {
565} 574}
566 575
567int 576int
568perceive_self (object *op) 577perceive_self (object *op)
569{ 578{
570 char buf[MAX_BUF];
571 const char *cp = describe_item (op, op); 579 const char *cp = describe_item (op, op);
572 archetype *at = archetype::find (ARCH_DEPLETION); 580 archetype *at = archetype::find (ARCH_DEPLETION);
573 object *tmp;
574 int i;
575 581
582 dynbuf_text buf;
583
584 if (player *pl = op->contr)
585 if (object *race = archetype::find (op->race))
586 buf << "You are a " << (pl->gender ? "female" : "male") << " " << &race->name << ".\n";
587
576 tmp = find_god (determine_god (op)); 588 if (object *god = find_god (determine_god (op)))
577 if (tmp) 589 buf << "You worship " << &god->name << ".\n";
578 new_draw_info_format (NDI_UNIQUE, 0, op, "You worship %s", &tmp->name);
579 else 590 else
580 new_draw_info (NDI_UNIQUE, 0, op, "You worship no god"); 591 buf << "You worship no god.\n";
581 592
582 tmp = present_arch_in_ob (at, op); 593 object *tmp = present_arch_in_ob (at, op);
583 594
584 if (*cp == '\0' && tmp == NULL) 595 if (*cp == '\0' && tmp == NULL)
585 new_draw_info (NDI_UNIQUE, 0, op, "You feel very mundane"); 596 buf << "You feel very mundane. ";
586 else 597 else
587 { 598 {
588 new_draw_info (NDI_UNIQUE, 0, op, "You have:"); 599 buf << "You have: " << cp << ".\n";
589 new_draw_info (NDI_UNIQUE, 0, op, cp);
590 600
591 if (tmp) 601 if (tmp)
592 for (i = 0; i < NUM_STATS; i++) 602 for (int i = 0; i < NUM_STATS; i++)
593 if (tmp->stats.stat (i) < 0) 603 if (tmp->stats.stat (i) < 0)
594 new_draw_info_format (NDI_UNIQUE, 0, op, "Your %s is depleted by %d", statname[i], -tmp->stats.stat (i)); 604 buf.printf ("Your %s is depleted by %d.\n", statname[i], -tmp->stats.stat (i));
595 } 605 }
596 606
597 if (is_dragon_pl (op)) 607 if (is_dragon_pl (op))
598 {
599 /* now grab the 'dragon_ability'-force from the player's inventory */ 608 /* now grab the 'dragon_ability'-force from the player's inventory */
600 for (tmp = op->inv; tmp != NULL; tmp = tmp->below) 609 for (tmp = op->inv; tmp; tmp = tmp->below)
601 { 610 {
602 if (tmp->type == FORCE && !strcmp (tmp->arch->name, "dragon_ability_force")) 611 if (tmp->type == FORCE && tmp->arch->archname == shstr_dragon_ability_force)
603 { 612 {
604 if (tmp->stats.exp == 0) 613 if (tmp->stats.exp == 0)
605 sprintf (buf, "Your metabolism isn't focused on anything."); 614 buf << "Your metabolism isn't focused on anything.\n";
606 else 615 else
607 sprintf (buf, "Your metabolism is focused on %s.", change_resist_msg[tmp->stats.exp]); 616 buf << "Your metabolism is focused on " << change_resist_msg[tmp->stats.exp] << ".\n";
608 617
609 new_draw_info (NDI_UNIQUE, 0, op, buf);
610 break; 618 break;
611 } 619 }
612 } 620 }
613 } 621
622 buf << '\0'; // zero-terminate
623
624 new_draw_info (NDI_UNIQUE, 0, op, buf.linearise ());
614 625
615 return 1; 626 return 1;
616} 627}
617 628
618/* This creates magic walls. Really, it can create most any object, 629/* This creates magic walls. Really, it can create most any object,
716 new_draw_info_format (NDI_UNIQUE, 0, op, "Something destroys your %s", name); 727 new_draw_info_format (NDI_UNIQUE, 0, op, "Something destroys your %s", name);
717 return 0; 728 return 0;
718 } 729 }
719 730
720 /* If this is a spellcasting wall, need to insert the spell object */ 731 /* If this is a spellcasting wall, need to insert the spell object */
721 if (tmp->other_arch && tmp->other_arch->clone.type == SPELL) 732 if (tmp->other_arch && tmp->other_arch->type == SPELL)
722 insert_ob_in_ob (arch_to_object (tmp->other_arch), tmp); 733 insert_ob_in_ob (arch_to_object (tmp->other_arch), tmp);
723 734
724 /* This code causes the wall to extend some distance in 735 /* This code causes the wall to extend some distance in
725 * each direction, or until an obstruction is encountered. 736 * each direction, or until an obstruction is encountered.
726 * posblocked and negblocked help determine how far the 737 * posblocked and negblocked help determine how far the
746 { 757 {
747 object *tmp2 = tmp->clone (); 758 object *tmp2 = tmp->clone ();
748 m->insert (tmp2, x, y, op); 759 m->insert (tmp2, x, y, op);
749 760
750 /* If this is a spellcasting wall, need to insert the spell object */ 761 /* If this is a spellcasting wall, need to insert the spell object */
751 if (tmp2->other_arch && tmp2->other_arch->clone.type == SPELL) 762 if (tmp2->other_arch && tmp2->other_arch->type == SPELL)
752 tmp2->insert (arch_to_object (tmp2->other_arch)); 763 tmp2->insert (arch_to_object (tmp2->other_arch));
753 764
754 } 765 }
755 else 766 else
756 posblocked = 1; 767 posblocked = 1;
763 ((spell_ob->move_block & GET_MAP_MOVE_BLOCK (m, x, y)) != spell_ob->move_block) && !negblocked) 774 ((spell_ob->move_block & GET_MAP_MOVE_BLOCK (m, x, y)) != spell_ob->move_block) && !negblocked)
764 { 775 {
765 object *tmp2 = tmp->clone (); 776 object *tmp2 = tmp->clone ();
766 m->insert (tmp2, x, y, op); 777 m->insert (tmp2, x, y, op);
767 778
768 if (tmp2->other_arch && tmp2->other_arch->clone.type == SPELL) 779 if (tmp2->other_arch && tmp2->other_arch->type == SPELL)
769 tmp2->insert (arch_to_object (tmp2->other_arch)); 780 tmp2->insert (arch_to_object (tmp2->other_arch));
770 } 781 }
771 else 782 else
772 negblocked = 1; 783 negblocked = 1;
773 } 784 }
889 900
890 op->speed_left = -FABS (op->speed) * 5; /* Freeze them for a short while */ 901 op->speed_left = -FABS (op->speed) * 5; /* Freeze them for a short while */
891 return 1; 902 return 1;
892} 903}
893 904
894
895/* cast_heal: Heals something. 905/* cast_heal: Heals something.
896 * op is the caster. 906 * op is the caster.
897 * dir is the direction he is casting it in. 907 * dir is the direction he is casting it in.
898 * spell is the spell object. 908 * spell is the spell object.
899 */ 909 */
925 { 935 {
926 /* See how many points we actually heal. Instead of messages 936 /* See how many points we actually heal. Instead of messages
927 * based on type of spell, we instead do messages based 937 * based on type of spell, we instead do messages based
928 * on amount of damage healed. 938 * on amount of damage healed.
929 */ 939 */
930 if (heal > (tmp->stats.maxhp - tmp->stats.hp)) 940 if (heal > tmp->stats.maxhp - tmp->stats.hp)
931 heal = tmp->stats.maxhp - tmp->stats.hp; 941 heal = tmp->stats.maxhp - tmp->stats.hp;
942
932 tmp->stats.hp += heal; 943 tmp->stats.hp += heal;
933 944
934 if (tmp->stats.hp >= tmp->stats.maxhp) 945 if (tmp->stats.hp >= tmp->stats.maxhp)
935 new_draw_info (NDI_UNIQUE, 0, tmp, "You feel just fine!"); 946 new_draw_info (NDI_UNIQUE, 0, tmp, "You feel just fine!");
936 else if (heal > 50) 947 else if (heal > 50)
945 success = 1; 956 success = 1;
946 } 957 }
947 } 958 }
948 959
949 if (spell->attacktype & AT_DISEASE) 960 if (spell->attacktype & AT_DISEASE)
950 if (cure_disease (tmp, op)) 961 if (cure_disease (tmp, op, spell))
951 success = 1; 962 success = 1;
952 963
953 if (spell->attacktype & AT_POISON) 964 if (spell->attacktype & AT_POISON)
954 { 965 {
955 at = archetype::find ("poisoning"); 966 at = archetype::find ("poisoning");
1004 } 1015 }
1005 1016
1006 if (spell->stats.food && tmp->stats.food < 999) 1017 if (spell->stats.food && tmp->stats.food < 999)
1007 { 1018 {
1008 tmp->stats.food += spell->stats.food; 1019 tmp->stats.food += spell->stats.food;
1020
1009 if (tmp->stats.food > 999) 1021 if (tmp->stats.food > 999)
1010 tmp->stats.food = 999; 1022 tmp->stats.food = 999;
1023
1011 success = 1; 1024 success = 1;
1012 /* We could do something a bit better like the messages for healing above */ 1025 /* We could do something a bit better like the messages for healing above */
1013 new_draw_info (NDI_UNIQUE, 0, tmp, "You feel your belly fill with food"); 1026 new_draw_info (NDI_UNIQUE, 0, tmp, "You feel your belly fill with food");
1014 } 1027 }
1015 1028
1016 return success; 1029 return success;
1017} 1030}
1018
1019 1031
1020/* This is used for the spells that gain stats. There are no spells 1032/* This is used for the spells that gain stats. There are no spells
1021 * right now that icnrease wis/int/pow on a temp basis, so no 1033 * right now that icnrease wis/int/pow on a temp basis, so no
1022 * good comments for those. 1034 * good comments for those.
1023 */ 1035 */
1024static const char *const no_gain_msgs[NUM_STATS] = { 1036static const char *const no_gain_msgs[NUM_STATS] = {
1025 "You grow no stronger.", 1037 "You grow no stronger.",
1026 "You grow no more agile.", 1038 "You grow no more agile.",
1027 "You don't feel any healthier.", 1039 "You don't feel any healthier.",
1028 "no wis", 1040 "You didn't grow any more intelligent.",
1041 "You do not feel any wiser.",
1042 "You don't feel any more powerful."
1029 "You are no easier to look at.", 1043 "You are no easier to look at.",
1030 "no int",
1031 "no pow"
1032}; 1044};
1033 1045
1034int 1046int
1035cast_change_ability (object *op, object *caster, object *spell_ob, int dir, int silent) 1047cast_change_ability (object *op, object *caster, object *spell_ob, int dir, int silent)
1036{ 1048{
1087 } 1099 }
1088 else 1100 else
1089 { 1101 {
1090 new_draw_info (NDI_UNIQUE, 0, op, "Recasting the spell had no effect."); 1102 new_draw_info (NDI_UNIQUE, 0, op, "Recasting the spell had no effect.");
1091 } 1103 }
1104
1092 return 1; 1105 return 1;
1093 } 1106 }
1107
1094 force->duration = spell_ob->duration + SP_level_duration_adjust (caster, spell_ob) * 50; 1108 force->duration = spell_ob->duration + SP_level_duration_adjust (caster, spell_ob) * 50;
1095 force->speed = 1.0; 1109 force->speed = 1.0;
1096 force->speed_left = -1.0; 1110 force->speed_left = -1.0;
1097 SET_FLAG (force, FLAG_APPLIED); 1111 SET_FLAG (force, FLAG_APPLIED);
1098 1112
1104 force->resist[i] = spell_ob->resist[i] + SP_level_dam_adjust (caster, spell_ob); 1118 force->resist[i] = spell_ob->resist[i] + SP_level_dam_adjust (caster, spell_ob);
1105 if (force->resist[i] > 100) 1119 if (force->resist[i] > 100)
1106 force->resist[i] = 100; 1120 force->resist[i] = 100;
1107 } 1121 }
1108 } 1122 }
1123
1109 if (spell_ob->stats.hp) 1124 if (spell_ob->stats.hp)
1110 force->stats.hp = spell_ob->stats.hp + SP_level_dam_adjust (caster, spell_ob); 1125 force->stats.hp = spell_ob->stats.hp + SP_level_dam_adjust (caster, spell_ob);
1111 1126
1112 if (tmp->type == PLAYER) 1127 if (tmp->type == PLAYER)
1113 { 1128 {
1153 force->attacktype = spell_ob->attacktype; 1168 force->attacktype = spell_ob->attacktype;
1154 1169
1155 insert_ob_in_ob (force, tmp); 1170 insert_ob_in_ob (force, tmp);
1156 change_abil (tmp, force); /* Mostly to display any messages */ 1171 change_abil (tmp, force); /* Mostly to display any messages */
1157 tmp->update_stats (); 1172 tmp->update_stats ();
1173
1158 return 1; 1174 return 1;
1159} 1175}
1160 1176
1161/* This used to be part of cast_change_ability, but it really didn't make 1177/* This used to be part of cast_change_ability, but it really didn't make
1162 * a lot of sense, since most of the values it derives are from the god 1178 * a lot of sense, since most of the values it derives are from the god
1163 * of the caster. 1179 * of the caster.
1164 */ 1180 */
1165
1166int 1181int
1167cast_bless (object *op, object *caster, object *spell_ob, int dir) 1182cast_bless (object *op, object *caster, object *spell_ob, int dir)
1168{ 1183{
1169 int i; 1184 int i;
1170 object *god = find_god (determine_god (op)), *tmp2, *force = NULL, *tmp; 1185 object *god = find_god (determine_god (op)), *tmp2, *force = NULL, *tmp;
1268} 1283}
1269 1284
1270/* Alchemy code by Mark Wedel 1285/* Alchemy code by Mark Wedel
1271 * 1286 *
1272 * This code adds a new spell, called alchemy. Alchemy will turn 1287 * This code adds a new spell, called alchemy. Alchemy will turn
1273 * objects to gold nuggets, the value of the gold nuggets being 1288 * objects to pyrite ("false gold"), henceforth called gold nuggets.
1274 * about 90% of that of the item itself. It uses the value of the
1275 * object before charisma adjustments, because the nuggets themselves
1276 * will be will be adjusted by charisma when sold.
1277 * 1289 *
1278 * Large nuggets are worth 25 gp each (base). You will always get 1290 * The value of the gold nuggets being about 90% of that of the item
1279 * the maximum number of large nuggets you could get. 1291 * itself. It uses the value of the object before charisma adjustments,
1280 * Small nuggets are worth 1 gp each (base). You will get from 0 1292 * because the nuggets themselves will be will be adjusted by charisma
1281 * to the max amount of small nuggets as you could get. 1293 * when sold.
1282 *
1283 * For example, if an item is worth 110 gold, you will get
1284 * 4 large nuggets, and from 0-10 small nuggets.
1285 * 1294 *
1286 * There is also a chance (1:30) that you will get nothing at all 1295 * There is also a chance (1:30) that you will get nothing at all
1287 * for the object. There is also a maximum weight that will be 1296 * for the object. There is also a maximum weight that will be
1288 * alchemised. 1297 * alchemised.
1289 */ 1298 */
1312 total_weight += obj->total_weight (); 1321 total_weight += obj->total_weight ();
1313 1322
1314 obj->destroy (); 1323 obj->destroy ();
1315} 1324}
1316 1325
1317static void
1318update_map (object *op, maptile *m, int small_nuggets, object *small, int large_nuggets, object *large, int x, int y)
1319{
1320 int flag = 0;
1321
1322 /* Put any nuggets below the player, but we can only pass this
1323 * flag if we are on the same space as the player
1324 */
1325 if (x == op->x && y == op->y && op->map == m)
1326 flag = INS_BELOW_ORIGINATOR;
1327
1328 if (small_nuggets)
1329 {
1330 object *tmp = small->clone ();
1331 tmp->nrof = small_nuggets;
1332 m->insert (tmp, x, y, op, flag);
1333 }
1334
1335 if (large_nuggets)
1336 {
1337 object *tmp = large->clone ();
1338 tmp->nrof = large_nuggets;
1339 m->insert (tmp, x, y, op, flag);
1340 }
1341
1342 if (object *pl = m->at (x, y).player ())
1343 if (pl->contr->ns)
1344 pl->contr->ns->look_position = 0;
1345}
1346
1347int 1326int
1348alchemy (object *op, object *caster, object *spell_ob) 1327alchemy (object *op, object *caster, object *spell_ob)
1349{ 1328{
1350 if (op->type != PLAYER) 1329 if (op->type != PLAYER)
1351 return 0; 1330 return 0;
1352 1331
1353 object *large = get_archetype ("largenugget"); 1332 archetype *nugget[3];
1354 object *small = get_archetype ("smallnugget"); 1333
1334 nugget[0] = archetype::find ("pyrite3");
1335 nugget[1] = archetype::find ("pyrite2");
1336 nugget[2] = archetype::find ("pyrite");
1355 1337
1356 /* Put a maximum weight of items that can be alchemised. Limits the power 1338 /* Put a maximum weight of items that can be alchemised. Limits the power
1357 * some, and also prevents people from alchemising every table/chair/clock 1339 * some, and also prevents people from alchemising every table/chair/clock
1358 * in sight 1340 * in sight
1359 */ 1341 */
1411 if (weight > weight_max) 1393 if (weight > weight_max)
1412 break; 1394 break;
1413 } 1395 }
1414 } 1396 }
1415 1397
1398 value -= rndm (value >> 4);
1416 value = min (value, value_max); 1399 value = min (value, value_max);
1417 1400
1418 uint64 count = value / large->value; 1401 for (int i = 0; i < sizeof (nugget) / sizeof (nugget [0]); ++i)
1419 int large_nuggets = count; 1402 if (int nrof = value / nugget [i]->value)
1420 value -= count * large->value;
1421
1422 count = value / small->value;
1423 int small_nuggets = count;
1424
1425 /* Insert all the nuggets at one time. This probably saves time, but
1426 * it also prevents us from alcheming nuggets that were just created
1427 * with this spell.
1428 */ 1403 {
1429 update_map (op, mp, small_nuggets, small, large_nuggets, large, nx, ny); 1404 value -= nrof * nugget[i]->value;
1405
1406 object *tmp = arch_to_object (nugget[i]);
1407 tmp->nrof = nrof;
1408 tmp->flag [FLAG_IDENTIFIED] = true;
1409 op->map->insert (tmp, x, y, op, 0);
1410 }
1430 1411
1431 if (weight > weight_max) 1412 if (weight > weight_max)
1432 goto bailout; 1413 goto bailout;
1433 } 1414 }
1434 } 1415 }
1435 1416
1436bailout: 1417bailout:
1437 large->destroy ();
1438 small->destroy ();
1439 return 1; 1418 return 1;
1440} 1419}
1441 1420
1442 1421
1443/* This function removes the cursed/damned status on equipped 1422/* This function removes the cursed/damned status on equipped
1991 object *weapon, *tmp; 1970 object *weapon, *tmp;
1992 char buf[MAX_BUF]; 1971 char buf[MAX_BUF];
1993 int a, i; 1972 int a, i;
1994 sint16 x, y; 1973 sint16 x, y;
1995 maptile *m; 1974 maptile *m;
1996 materialtype_t *mt;
1997 1975
1998 if (!spell->other_arch) 1976 if (!spell->other_arch)
1999 { 1977 {
2000 new_draw_info (NDI_UNIQUE, 0, op, "Oops, program error!"); 1978 new_draw_info (NDI_UNIQUE, 0, op, "Oops, program error!");
2001 LOG (llevError, "animate_weapon failed: spell %s missing other_arch!\n", &spell->name); 1979 LOG (llevError, "animate_weapon failed: spell %s missing other_arch!\n", &spell->name);
2020 x = op->x + freearr_x[dir]; 1998 x = op->x + freearr_x[dir];
2021 y = op->y + freearr_y[dir]; 1999 y = op->y + freearr_y[dir];
2022 2000
2023 /* if there's no place to put the golem, abort */ 2001 /* if there's no place to put the golem, abort */
2024 if ((dir == -1) || (get_map_flags (m, &m, x, y, &x, &y) & P_OUT_OF_MAP) || 2002 if ((dir == -1) || (get_map_flags (m, &m, x, y, &x, &y) & P_OUT_OF_MAP) ||
2025 ((spell->other_arch->clone.move_type & GET_MAP_MOVE_BLOCK (m, x, y)) == spell->other_arch->clone.move_type)) 2003 ((spell->other_arch->move_type & GET_MAP_MOVE_BLOCK (m, x, y)) == spell->other_arch->move_type))
2026 { 2004 {
2027 new_draw_info (NDI_UNIQUE, 0, op, "There is something in the way."); 2005 new_draw_info (NDI_UNIQUE, 0, op, "There is something in the way.");
2028 return 0; 2006 return 0;
2029 } 2007 }
2030 2008
2034 if (!weapon) 2012 if (!weapon)
2035 { 2013 {
2036 new_draw_info (NDI_BLACK, 0, op, "You must mark a weapon to use with this spell!"); 2014 new_draw_info (NDI_BLACK, 0, op, "You must mark a weapon to use with this spell!");
2037 return 0; 2015 return 0;
2038 } 2016 }
2039 if (spell->race && strcmp (weapon->arch->name, spell->race)) 2017 if (spell->race && strcmp (weapon->arch->archname, spell->race))
2040 { 2018 {
2041 new_draw_info (NDI_UNIQUE, 0, op, "The spell fails to transform your weapon."); 2019 new_draw_info (NDI_UNIQUE, 0, op, "The spell fails to transform your weapon.");
2042 return 0; 2020 return 0;
2043 } 2021 }
2044 if (weapon->type != WEAPON) 2022 if (weapon->type != WEAPON)
2113 2091
2114 /* attacktype */ 2092 /* attacktype */
2115 if (!tmp->attacktype) 2093 if (!tmp->attacktype)
2116 tmp->attacktype = AT_PHYSICAL; 2094 tmp->attacktype = AT_PHYSICAL;
2117 2095
2118 mt = NULL;
2119 if (op->materialname != NULL)
2120 mt = name_to_material (op->materialname); 2096 if (materialtype_t *mt = name_to_material (op->materialname))
2121 if (mt != NULL)
2122 { 2097 {
2123 for (i = 0; i < NROFATTACKS; i++) 2098 for (i = 0; i < NROFATTACKS; i++)
2124 tmp->resist[i] = 50 - (mt->save[i] * 5); 2099 tmp->resist[i] = 50 - (mt->save[i] * 5);
2125 a = mt->save[0]; 2100 a = mt->save[0];
2126 } 2101 }
2128 { 2103 {
2129 for (i = 0; i < NROFATTACKS; i++) 2104 for (i = 0; i < NROFATTACKS; i++)
2130 tmp->resist[i] = 5; 2105 tmp->resist[i] = 5;
2131 a = 10; 2106 a = 10;
2132 } 2107 }
2108
2133 /* Set weapon's immunity */ 2109 /* Set weapon's immunity */
2134 tmp->resist[ATNR_CONFUSION] = 100; 2110 tmp->resist[ATNR_CONFUSION] = 100;
2135 tmp->resist[ATNR_POISON] = 100; 2111 tmp->resist[ATNR_POISON] = 100;
2136 tmp->resist[ATNR_SLOW] = 100; 2112 tmp->resist[ATNR_SLOW] = 100;
2137 tmp->resist[ATNR_PARALYZE] = 100; 2113 tmp->resist[ATNR_PARALYZE] = 100;
2143 2119
2144 /* Improve weapon's armour value according to best save vs. physical of its material */ 2120 /* Improve weapon's armour value according to best save vs. physical of its material */
2145 2121
2146 if (a > 14) 2122 if (a > 14)
2147 a = 14; 2123 a = 14;
2124
2148 tmp->resist[ATNR_PHYSICAL] = 100 - (int) ((100.0 - (float) tmp->resist[ATNR_PHYSICAL]) / (30.0 - 2.0 * a)); 2125 tmp->resist[ATNR_PHYSICAL] = 100 - (int) ((100.0 - (float) tmp->resist[ATNR_PHYSICAL]) / (30.0 - 2.0 * a));
2149 2126
2150 /* Determine golem's speed */ 2127 /* Determine golem's speed */
2151 tmp->set_speed (min (3.33, 0.4 + 0.1 * SP_level_range_adjust (caster, spell))); 2128 tmp->set_speed (min (3.33, 0.4 + 0.1 * SP_level_range_adjust (caster, spell)));
2152 2129
2197 new_draw_info (NDI_UNIQUE, 0, op, "It can be no darker here."); 2174 new_draw_info (NDI_UNIQUE, 0, op, "It can be no darker here.");
2198 } 2175 }
2199 return success; 2176 return success;
2200} 2177}
2201 2178
2202
2203
2204
2205
2206/* create an aura spell object and put it in the player's inventory. 2179/* create an aura spell object and put it in the player's inventory.
2207 * as usual, op is player, caster is the object casting the spell, 2180 * as usual, op is player, caster is the object casting the spell,
2208 * spell is the spell object itself. 2181 * spell is the spell object itself.
2209 */ 2182 */
2210int 2183int
2221 2194
2222 new_aura->duration = spell->duration + 10 * SP_level_duration_adjust (caster, spell); 2195 new_aura->duration = spell->duration + 10 * SP_level_duration_adjust (caster, spell);
2223 2196
2224 new_aura->stats.dam = spell->stats.dam + SP_level_dam_adjust (caster, spell); 2197 new_aura->stats.dam = spell->stats.dam + SP_level_dam_adjust (caster, spell);
2225 2198
2226 new_aura->set_owner (op);
2227 set_spell_skill (op, caster, spell, new_aura); 2199 set_spell_skill (op, caster, spell, new_aura);
2228 new_aura->attacktype = spell->attacktype; 2200 new_aura->attacktype = spell->attacktype;
2229 2201
2230 new_aura->level = caster_level (caster, spell); 2202 new_aura->level = caster_level (caster, spell);
2203
2231 if (refresh) 2204 if (refresh)
2232 new_draw_info (NDI_UNIQUE, 0, op, "You recast the spell while in effect."); 2205 new_draw_info (NDI_UNIQUE, 0, op, "You recast the spell while in effect.");
2233 else 2206 else
2234 new_draw_info (NDI_UNIQUE, 0, op, "You create an aura of magical force."); 2207 new_draw_info (NDI_UNIQUE, 0, op, "You create an aura of magical force.");
2208
2235 insert_ob_in_ob (new_aura, op); 2209 insert_ob_in_ob (new_aura, op);
2210 new_aura->set_owner (op);
2211
2236 return 1; 2212 return 1;
2237} 2213}
2238 2214
2239 2215
2240/* move aura function. An aura is a part of someone's inventory, 2216/* move aura function. An aura is a part of someone's inventory,
2307} 2283}
2308 2284
2309/* moves the peacemaker spell. 2285/* moves the peacemaker spell.
2310 * op is the piece object. 2286 * op is the piece object.
2311 */ 2287 */
2312
2313void 2288void
2314move_peacemaker (object *op) 2289move_peacemaker (object *op)
2315{ 2290{
2316 object *tmp; 2291 object *tmp;
2317 2292

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines