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

Comparing deliantra/server/server/spell_attack.C (file contents):
Revision 1.15 by root, Sat Sep 16 22:24:13 2006 UTC vs.
Revision 1.18 by root, Wed Dec 13 00:42:04 2006 UTC

140 140
141 if (OB_TYPE_MOVE_BLOCK (tmp, GET_MAP_MOVE_BLOCK (m, sx, sy))) 141 if (OB_TYPE_MOVE_BLOCK (tmp, GET_MAP_MOVE_BLOCK (m, sx, sy)))
142 return; 142 return;
143 143
144 /* OK, we made a fork */ 144 /* OK, we made a fork */
145 new_bolt = get_object (); 145 new_bolt = tmp->clone ();
146 copy_object (tmp, new_bolt);
147 146
148 /* reduce chances of subsequent forking */ 147 /* reduce chances of subsequent forking */
149 new_bolt->stats.Dex -= 10; 148 new_bolt->stats.Dex -= 10;
150 tmp->stats.Dex -= 10; /* less forks from main bolt too */ 149 tmp->stats.Dex -= 10; /* less forks from main bolt too */
151 new_bolt->stats.Con += 25 * new_dir; /* adjust the left bias */ 150 new_bolt->stats.Con += 25 * new_dir; /* adjust the left bias */
174 sint16 x, y; 173 sint16 x, y;
175 maptile *m; 174 maptile *m;
176 175
177 if (--(op->duration) < 0) 176 if (--(op->duration) < 0)
178 { 177 {
179 remove_ob (op); 178 op->destroy ();
180 free_object (op);
181 return; 179 return;
182 } 180 }
183 181
184 hit_map (op, 0, op->attacktype, 1); 182 hit_map (op, 0, op->attacktype, 1);
185 183
250 update_turn_face (op); /* A bolt *must* be IS_TURNABLE */ 248 update_turn_face (op); /* A bolt *must* be IS_TURNABLE */
251 return; 249 return;
252 } 250 }
253 else 251 else
254 { /* Create a copy of this object and put it ahead */ 252 { /* Create a copy of this object and put it ahead */
255 tmp = get_object (); 253 tmp = op->clone ();
256 copy_object (op, tmp); 254
257 tmp->speed_left = -0.1; 255 tmp->speed_left = -0.1;
258 tmp->x += DIRX (tmp), tmp->y += DIRY (tmp); 256 tmp->x += DIRX (tmp), tmp->y += DIRY (tmp);
259 tmp = insert_ob_in_map (tmp, op->map, op, 0); 257 tmp = insert_ob_in_map (tmp, op->map, op, 0);
260 /* To make up for the decrease at the top of the function */ 258 /* To make up for the decrease at the top of the function */
261 tmp->duration++; 259 tmp->duration++;
320 tmp->map = op->map; 318 tmp->map = op->map;
321 319
322 mflags = get_map_flags (tmp->map, &tmp->map, tmp->x, tmp->y, &tmp->x, &tmp->y); 320 mflags = get_map_flags (tmp->map, &tmp->map, tmp->x, tmp->y, &tmp->x, &tmp->y);
323 if (mflags & P_OUT_OF_MAP) 321 if (mflags & P_OUT_OF_MAP)
324 { 322 {
325 free_object (tmp); 323 tmp->destroy ();
326 return 0; 324 return 0;
327 } 325 }
326
328 if (OB_TYPE_MOVE_BLOCK (tmp, GET_MAP_MOVE_BLOCK (tmp->map, tmp->x, tmp->y))) 327 if (OB_TYPE_MOVE_BLOCK (tmp, GET_MAP_MOVE_BLOCK (tmp->map, tmp->x, tmp->y)))
329 { 328 {
330 if (!QUERY_FLAG (tmp, FLAG_REFLECTING)) 329 if (!QUERY_FLAG (tmp, FLAG_REFLECTING))
331 { 330 {
332 free_object (tmp); 331 tmp->destroy ();
333 return 0; 332 return 0;
334 } 333 }
334
335 tmp->x = op->x; 335 tmp->x = op->x;
336 tmp->y = op->y; 336 tmp->y = op->y;
337 tmp->direction = absdir (tmp->direction + 4); 337 tmp->direction = absdir (tmp->direction + 4);
338 tmp->map = op->map; 338 tmp->map = op->map;
339 } 339 }
340
340 if ((tmp = insert_ob_in_map (tmp, tmp->map, op, 0)) != NULL) 341 if ((tmp = insert_ob_in_map (tmp, tmp->map, op, 0)) != NULL)
341 move_bolt (tmp); 342 move_bolt (tmp);
343
342 return 1; 344 return 1;
343} 345}
344 346
345 347
346 348
361 maptile *m = op->map; 363 maptile *m = op->map;
362 int i; 364 int i;
363 365
364 if (--(op->duration) < 0) 366 if (--(op->duration) < 0)
365 { 367 {
366 remove_ob (op); 368 op->destroy ();
367 free_object (op);
368 return; 369 return;
369 } 370 }
371
370 hit_map (op, 0, op->attacktype, 0); 372 hit_map (op, 0, op->attacktype, 0);
371 373
372 if (op->range > 0) 374 if (op->range > 0)
373 { 375 {
374 for (i = 1; i < 9; i++) 376 for (i = 1; i < 9; i++)
380 /* ok_to_put_more already does things like checks for walls, 382 /* ok_to_put_more already does things like checks for walls,
381 * out of map, etc. 383 * out of map, etc.
382 */ 384 */
383 if (ok_to_put_more (op->map, dx, dy, op, op->attacktype)) 385 if (ok_to_put_more (op->map, dx, dy, op, op->attacktype))
384 { 386 {
385 tmp = get_object (); 387 tmp = op->clone ();
386 copy_object (op, tmp);
387 tmp->state = 0; 388 tmp->state = 0;
388 tmp->speed_left = -0.21; 389 tmp->speed_left = -0.21;
389 tmp->range--; 390 tmp->range--;
390 tmp->value = 0; 391 tmp->value = 0;
391 tmp->x = dx; 392 tmp->x = dx;
407 object *tmp, *owner; 408 object *tmp, *owner;
408 409
409 if (op->other_arch == NULL) 410 if (op->other_arch == NULL)
410 { 411 {
411 LOG (llevError, "BUG: explode_bullet(): op without other_arch\n"); 412 LOG (llevError, "BUG: explode_bullet(): op without other_arch\n");
412 remove_ob (op); 413 op->destroy ();
413 free_object (op);
414 return; 414 return;
415 } 415 }
416 416
417 if (op->env) 417 if (op->env)
418 { 418 {
420 420
421 env = object_get_env_recursive (op); 421 env = object_get_env_recursive (op);
422 if (env->map == NULL || out_of_map (env->map, env->x, env->y)) 422 if (env->map == NULL || out_of_map (env->map, env->x, env->y))
423 { 423 {
424 LOG (llevError, "BUG: explode_bullet(): env out of map\n"); 424 LOG (llevError, "BUG: explode_bullet(): env out of map\n");
425 remove_ob (op); 425 op->destroy ();
426 free_object (op);
427 return; 426 return;
428 } 427 }
428
429 remove_ob (op); 429 op->remove ();
430 op->x = env->x; 430 op->x = env->x;
431 op->y = env->y; 431 op->y = env->y;
432 insert_ob_in_map (op, env->map, op, INS_NO_MERGE | INS_NO_WALK_ON); 432 insert_ob_in_map (op, env->map, op, INS_NO_MERGE | INS_NO_WALK_ON);
433 } 433 }
434 else if (out_of_map (op->map, op->x, op->y)) 434 else if (out_of_map (op->map, op->x, op->y))
435 { 435 {
436 LOG (llevError, "BUG: explode_bullet(): op out of map\n"); 436 LOG (llevError, "BUG: explode_bullet(): op out of map\n");
437 remove_ob (op); 437 op->destroy ();
438 free_object (op);
439 return; 438 return;
440 } 439 }
441 440
442 // elmex Tue Aug 15 17:46:51 CEST 2006: Prevent explosions of any kind on safe maps 441 // elmex Tue Aug 15 17:46:51 CEST 2006: Prevent explosions of any kind on safe maps
443 // NOTE: If this breaks something important: remove this. I can't think of anything 442 // NOTE: If this breaks something important: remove this. I can't think of anything
444 // bad at the moment that might happen from this. 443 // bad at the moment that might happen from this.
445 if (get_map_flags (op->map, NULL, op->x, op->y, NULL, NULL) & P_SAFE) 444 if (get_map_flags (op->map, NULL, op->x, op->y, NULL, NULL) & P_SAFE)
446 { 445 {
447 remove_ob (op); 446 op->destroy ();
448 free_object (op);
449 return; 447 return;
450 } 448 }
451 449
452 if (op->attacktype) 450 if (op->attacktype)
453 { 451 {
464 462
465 owner = get_owner (op); 463 owner = get_owner (op);
466 464
467 if ((tmp->attacktype & AT_HOLYWORD || tmp->attacktype & AT_GODPOWER) && owner && !tailor_god_spell (tmp, owner)) 465 if ((tmp->attacktype & AT_HOLYWORD || tmp->attacktype & AT_GODPOWER) && owner && !tailor_god_spell (tmp, owner))
468 { 466 {
469 remove_ob (op); 467 op->destroy ();
470 free_object (op);
471 return; 468 return;
472 } 469 }
473 470
474 tmp->x = op->x; 471 tmp->x = op->x;
475 tmp->y = op->y; 472 tmp->y = op->y;
505 502
506 insert_ob_in_map (tmp, op->map, op, 0); 503 insert_ob_in_map (tmp, op->map, op, 0);
507 /* remove the firebullet */ 504 /* remove the firebullet */
508 if (!op->destroyed ()) 505 if (!op->destroyed ())
509 { 506 {
510 remove_ob (op); 507 op->destroy ();
511 free_object (op);
512 } 508 }
513} 509}
514 510
515 511
516 512
549 dam = hit_player (tmp, op->stats.dam, op, op->attacktype, 1); 545 dam = hit_player (tmp, op->stats.dam, op, op->attacktype, 1);
550 if (op->destroyed () || !tmp->destroyed () || (op->stats.dam -= dam) < 0) 546 if (op->destroyed () || !tmp->destroyed () || (op->stats.dam -= dam) < 0)
551 { 547 {
552 if (!QUERY_FLAG (op, FLAG_REMOVED)) 548 if (!QUERY_FLAG (op, FLAG_REMOVED))
553 { 549 {
554 remove_ob (op); 550 op->destroy ();
555 free_object (op);
556 return; 551 return;
557 } 552 }
558 } 553 }
559 } 554 }
560 } 555 }
589 584
590 /* Reached the end of its life - remove it */ 585 /* Reached the end of its life - remove it */
591 if (--op->range <= 0) 586 if (--op->range <= 0)
592 { 587 {
593 if (op->other_arch) 588 if (op->other_arch)
594 {
595 explode_bullet (op); 589 explode_bullet (op);
596 }
597 else 590 else
598 { 591 op->destroy ();
599 remove_ob (op); 592
600 free_object (op);
601 }
602 return; 593 return;
603 } 594 }
604 595
605 new_x = op->x + DIRX (op); 596 new_x = op->x + DIRX (op);
606 new_y = op->y + DIRY (op); 597 new_y = op->y + DIRY (op);
607 m = op->map; 598 m = op->map;
608 mflags = get_map_flags (m, &m, new_x, new_y, &new_x, &new_y); 599 mflags = get_map_flags (m, &m, new_x, new_y, &new_x, &new_y);
609 600
610 if (mflags & P_OUT_OF_MAP) 601 if (mflags & P_OUT_OF_MAP)
611 { 602 {
612 remove_ob (op); 603 op->destroy ();
613 free_object (op);
614 return; 604 return;
615 } 605 }
616 606
617 if (!op->direction || OB_TYPE_MOVE_BLOCK (op, GET_MAP_MOVE_BLOCK (m, new_x, new_y))) 607 if (!op->direction || OB_TYPE_MOVE_BLOCK (op, GET_MAP_MOVE_BLOCK (m, new_x, new_y)))
618 { 608 {
619 if (op->other_arch) 609 if (op->other_arch)
620 {
621 explode_bullet (op); 610 explode_bullet (op);
622 }
623 else 611 else
624 { 612 op->destroy ();
625 remove_ob (op); 613
626 free_object (op);
627 }
628 return; 614 return;
629 } 615 }
630 616
631 remove_ob (op); 617 op->remove ();
632 op->x = new_x; 618 op->x = new_x;
633 op->y = new_y; 619 op->y = new_y;
634 if ((op = insert_ob_in_map (op, m, op, 0)) == NULL) 620 if ((op = insert_ob_in_map (op, m, op, 0)) == NULL)
635 return; 621 return;
636 622
695 tmp->map = op->map; 681 tmp->map = op->map;
696 682
697 mflags = get_map_flags (tmp->map, &tmp->map, tmp->x, tmp->y, &tmp->x, &tmp->y); 683 mflags = get_map_flags (tmp->map, &tmp->map, tmp->x, tmp->y, &tmp->x, &tmp->y);
698 if (mflags & P_OUT_OF_MAP) 684 if (mflags & P_OUT_OF_MAP)
699 { 685 {
700 free_object (tmp); 686 tmp->destroy ();
701 return 0; 687 return 0;
702 } 688 }
689
703 if (OB_TYPE_MOVE_BLOCK (tmp, GET_MAP_MOVE_BLOCK (tmp->map, tmp->x, tmp->y))) 690 if (OB_TYPE_MOVE_BLOCK (tmp, GET_MAP_MOVE_BLOCK (tmp->map, tmp->x, tmp->y)))
704 { 691 {
705 if (!QUERY_FLAG (tmp, FLAG_REFLECTING)) 692 if (!QUERY_FLAG (tmp, FLAG_REFLECTING))
706 { 693 {
707 free_object (tmp); 694 tmp->destroy ();
708 return 0; 695 return 0;
709 } 696 }
697
710 tmp->x = op->x; 698 tmp->x = op->x;
711 tmp->y = op->y; 699 tmp->y = op->y;
712 tmp->direction = absdir (tmp->direction + 4); 700 tmp->direction = absdir (tmp->direction + 4);
713 tmp->map = op->map; 701 tmp->map = op->map;
714 } 702 }
703
715 if ((tmp = insert_ob_in_map (tmp, tmp->map, op, 0)) != NULL) 704 if ((tmp = insert_ob_in_map (tmp, tmp->map, op, 0)) != NULL)
716 {
717 check_bullet (tmp); 705 check_bullet (tmp);
718 } 706
719 return 1; 707 return 1;
720} 708}
721 709
722 710
723 711
777 * when their cone dies when they die. 765 * when their cone dies when they die.
778 */ 766 */
779 /* If no owner left, the spell dies out. */ 767 /* If no owner left, the spell dies out. */
780 if (get_owner (op) == NULL) 768 if (get_owner (op) == NULL)
781 { 769 {
782 remove_ob (op); 770 op->destroy ();
783 free_object (op);
784 return; 771 return;
785 } 772 }
786#endif 773#endif
787 774
788 hit_map (op, 0, op->attacktype, 0); 775 hit_map (op, 0, op->attacktype, 0);
797 if (op->destroyed ()) 784 if (op->destroyed ())
798 return; 785 return;
799 786
800 if ((op->duration--) < 0) 787 if ((op->duration--) < 0)
801 { 788 {
802 remove_ob (op); 789 op->destroy ();
803 free_object (op);
804 return; 790 return;
805 } 791 }
806 /* Object has hit maximum range, so don't have it move 792 /* Object has hit maximum range, so don't have it move
807 * any further. When the duration above expires, 793 * any further. When the duration above expires,
808 * then the object will get removed. 794 * then the object will get removed.
817 { 803 {
818 sint16 x = op->x + freearr_x[absdir (op->stats.sp + i)], y = op->y + freearr_y[absdir (op->stats.sp + i)]; 804 sint16 x = op->x + freearr_x[absdir (op->stats.sp + i)], y = op->y + freearr_y[absdir (op->stats.sp + i)];
819 805
820 if (ok_to_put_more (op->map, x, y, op, op->attacktype)) 806 if (ok_to_put_more (op->map, x, y, op, op->attacktype))
821 { 807 {
822 object *tmp = get_object (); 808 object *tmp = op->clone ();
823 809
824 copy_object (op, tmp);
825 tmp->x = x; 810 tmp->x = x;
826 tmp->y = y; 811 tmp->y = y;
827 812
828 tmp->duration = op->duration + 1; 813 tmp->duration = op->duration + 1;
829 814
1012 return; 997 return;
1013 998
1014 if (env->type == PLAYER) 999 if (env->type == PLAYER)
1015 esrv_del_item (env->contr, op->count); 1000 esrv_del_item (env->contr, op->count);
1016 1001
1017 remove_ob (op); 1002 op->remove ();
1018 op->x = env->x; 1003 op->x = env->x;
1019 op->y = env->y; 1004 op->y = env->y;
1020 if ((op = insert_ob_in_map (op, env->map, op, 0)) == NULL) 1005 if ((op = insert_ob_in_map (op, env->map, op, 0)) == NULL)
1021 return; 1006 return;
1022 } 1007 }
1024 // elmex Tue Aug 15 17:46:51 CEST 2006: Prevent bomb from exploding 1009 // elmex Tue Aug 15 17:46:51 CEST 2006: Prevent bomb from exploding
1025 // on a safe map. I don't like this special casing, but it seems to be neccessary 1010 // on a safe map. I don't like this special casing, but it seems to be neccessary
1026 // as bombs can be carried. 1011 // as bombs can be carried.
1027 if (get_map_flags (op->map, NULL, op->x, op->y, NULL, NULL) & P_SAFE) 1012 if (get_map_flags (op->map, NULL, op->x, op->y, NULL, NULL) & P_SAFE)
1028 { 1013 {
1029 remove_ob (op); 1014 op->destroy ();
1030 free_object (op);
1031 return; 1015 return;
1032 } 1016 }
1033 1017
1034 /* This copies a lot of the code from the fire bullet, 1018 /* This copies a lot of the code from the fire bullet,
1035 * but using the cast_bullet isn't really feasible, 1019 * but using the cast_bullet isn't really feasible,
1229 } 1213 }
1230 else 1214 else
1231 { 1215 {
1232 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s looks stronger!", query_name (target)); 1216 new_draw_info_format (NDI_UNIQUE, 0, op, "The %s looks stronger!", query_name (target));
1233 target->stats.hp = target->stats.maxhp * 2; 1217 target->stats.hp = target->stats.maxhp * 2;
1234 free_object (effect); 1218 effect->destroy ();
1235 return 0; 1219 return 0;
1236 } 1220 }
1237 } 1221 }
1238 } 1222 }
1239 else 1223 else
1270 sint16 new_x, new_y; 1254 sint16 new_x, new_y;
1271 maptile *m; 1255 maptile *m;
1272 1256
1273 if (op->range-- <= 0) 1257 if (op->range-- <= 0)
1274 { 1258 {
1275 remove_ob (op); 1259 op->destroy ();
1276 free_object (op);
1277 return; 1260 return;
1278 } 1261 }
1279 1262
1280 owner = get_owner (op); 1263 owner = get_owner (op);
1281#if 0 1264#if 0
1282 /* It'd make things nastier if this wasn't here - spells cast by 1265 /* It'd make things nastier if this wasn't here - spells cast by
1283 * monster that are then killed would continue to survive 1266 * monster that are then killed would continue to survive
1284 */ 1267 */
1285 if (owner == NULL) 1268 if (owner == NULL)
1286 { 1269 {
1287 remove_ob (op); 1270 op->destroy ();
1288 free_object (op);
1289 return; 1271 return;
1290 } 1272 }
1291#endif 1273#endif
1292 1274
1293 new_x = op->x + DIRX (op); 1275 new_x = op->x + DIRX (op);
1300 hit_map (op, op->direction, AT_MAGIC, 1); 1282 hit_map (op, op->direction, AT_MAGIC, 1);
1301 /* Basically, missile only hits one thing then goes away. 1283 /* Basically, missile only hits one thing then goes away.
1302 * we need to remove it if someone hasn't already done so. 1284 * we need to remove it if someone hasn't already done so.
1303 */ 1285 */
1304 if (!op->destroyed ()) 1286 if (!op->destroyed ())
1305 free_object (op); 1287 op->destroy ();
1306 1288
1307 return; 1289 return;
1308 } 1290 }
1309 1291
1310 remove_ob (op); 1292 op->remove ();
1311 1293
1312 if (!op->direction || (mflags & P_OUT_OF_MAP)) 1294 if (!op->direction || (mflags & P_OUT_OF_MAP))
1313 { 1295 {
1314 free_object (op); 1296 op->destroy ();
1315 return; 1297 return;
1316 } 1298 }
1317 1299
1318 op->x = new_x; 1300 op->x = new_x;
1319 op->y = new_y; 1301 op->y = new_y;
1785 nx = op->x; 1767 nx = op->x;
1786 ny = op->y; 1768 ny = op->y;
1787 m = op->map; 1769 m = op->map;
1788 } 1770 }
1789 1771
1790 remove_ob (op); 1772 op->remove ();
1791 op->y = ny; 1773 op->y = ny;
1792 op->x = nx; 1774 op->x = nx;
1793 insert_ob_in_map (op, m, op, 0); 1775 insert_ob_in_map (op, m, op, 0);
1794 1776
1795 dam_save = op->stats.dam; /* save the original dam: we do halfdam on 1777 dam_save = op->stats.dam; /* save the original dam: we do halfdam on
1874 object *owner; 1856 object *owner;
1875 1857
1876 owner = get_owner (op); 1858 owner = get_owner (op);
1877 if (op->duration == 0 || owner == NULL) 1859 if (op->duration == 0 || owner == NULL)
1878 { 1860 {
1879 remove_ob (op); 1861 op->destroy ();
1880 free_object (op);
1881 return; 1862 return;
1882 } 1863 }
1864
1883 op->duration--; 1865 op->duration--;
1884 1866
1885 basedir = op->direction; 1867 basedir = op->direction;
1886 if (basedir == 0) 1868 if (basedir == 0)
1887 { 1869 {
2199 { 2181 {
2200 object *flash; /* visual effect for inflicting disease */ 2182 object *flash; /* visual effect for inflicting disease */
2201 2183
2202 new_draw_info_format (NDI_UNIQUE, 0, op, "You inflict %s on %s!", &disease->name, &walk->name); 2184 new_draw_info_format (NDI_UNIQUE, 0, op, "You inflict %s on %s!", &disease->name, &walk->name);
2203 2185
2204 free_object (disease); /* don't need this one anymore */ 2186 disease->destroy (); /* don't need this one anymore */
2205 flash = get_archetype (ARCH_DETECT_MAGIC); 2187 flash = get_archetype (ARCH_DETECT_MAGIC);
2206 flash->x = x; 2188 flash->x = x;
2207 flash->y = y; 2189 flash->y = y;
2208 flash->map = walk->map; 2190 flash->map = walk->map;
2209 insert_ob_in_map (flash, walk->map, op, 0); 2191 insert_ob_in_map (flash, walk->map, op, 0);
2210 return 1; 2192 return 1;
2211 } 2193 }
2212 free_object (disease); 2194
2195 disease->destroy ();
2213 } 2196 }
2214 } /* if living creature */ 2197 } /* if living creature */
2215 } /* for range of spaces */ 2198 } /* for range of spaces */
2216 new_draw_info (NDI_UNIQUE, 0, op, "No one caught anything!"); 2199 new_draw_info (NDI_UNIQUE, 0, op, "No one caught anything!");
2217 return 1; 2200 return 1;

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines