LCOV - code coverage report
Current view: top level - omega-rpg-0.90-pa9 - gen1.c (source / functions) Hit Total Coverage
Test: lcov.info Lines: 23 415 5.5 %
Date: 2017-09-08 22:00:26 Functions: 1 16 6.2 %
Branches: 5 284 1.8 %

           Branch data     Line data    Source code
       1                 :            : /* omega copyright (c) 1987,1988,1989 by Laurence Raphael Brothers */
       2                 :            : /* gen1.c */
       3                 :            : /* level generator functions */
       4                 :            : 
       5                 :            : #include "glob.h"
       6                 :            : 
       7                 :            : #include <time.h>
       8                 :            : 
       9                 :            : /* Deallocate current dungeon */
      10                 :          0 : void free_dungeon(void)
      11                 :            : {
      12                 :            : #ifndef SAVE_LEVELS
      13                 :            :   plv tlv;
      14                 :            :   
      15         [ #  # ]:          0 :   while (Dungeon != NULL) {
      16                 :          0 :     tlv = Dungeon;
      17                 :          0 :     Dungeon = Dungeon->next;
      18                 :          0 :     free_level(tlv);
      19                 :            :   }
      20                 :            : #else
      21                 :            :   if (Dungeon != NULL)
      22                 :            :   {
      23                 :            :     sprintf(Str2,"om%d*.lev",Dungeon->environment);
      24                 :            :     kill_levels(Str2);
      25                 :            :   }
      26                 :            : #endif
      27                 :          0 : }
      28                 :            : 
      29                 :            : 
      30                 :            : /* erase the level w/o deallocating it*/
      31                 :          6 : void clear_level(struct level *dungeon_level)
      32                 :            : {
      33                 :            :   int i,j;
      34         [ +  - ]:          6 :   if (dungeon_level != NULL) {
      35                 :          6 :     dungeon_level->generated = FALSE;
      36                 :          6 :     dungeon_level->numrooms = 0;
      37                 :          6 :     dungeon_level->level_length = 0;
      38                 :          6 :     dungeon_level->level_width = 0;
      39                 :          6 :     dungeon_level->tunnelled = 0;
      40                 :          6 :     dungeon_level->depth = 0;
      41                 :          6 :     dungeon_level->mlist = NULL;
      42                 :          6 :     dungeon_level->next = NULL;
      43                 :          6 :     dungeon_level->last_visited = time(NULL);
      44         [ +  + ]:        774 :     for(i=0;i<MAXWIDTH;i++)
      45         [ +  + ]:      49920 :       for(j=0;j<MAXLENGTH;j++) {
      46                 :      49152 :         dungeon_level->site[i][j].locchar = WALL;
      47                 :      49152 :         dungeon_level->site[i][j].showchar = SPACE;
      48                 :      49152 :         dungeon_level->site[i][j].creature = NULL;
      49                 :      49152 :         dungeon_level->site[i][j].things = NULL;
      50                 :            :         /* PGM: clear_level is called from restore_level, before it knows anything about the current environment, which is where difficulty() gets its information! */
      51                 :      49152 :         dungeon_level->site[i][j].aux = difficulty()*20;
      52                 :      49152 :         dungeon_level->site[i][j].buildaux = 0;
      53                 :      49152 :         dungeon_level->site[i][j].p_locf = L_NO_OP;
      54                 :      49152 :         dungeon_level->site[i][j].lstatus = 0;
      55                 :      49152 :         dungeon_level->site[i][j].roomnumber = RS_WALLSPACE;
      56                 :            :       }
      57                 :            :   }
      58                 :          6 : }
      59                 :            : 
      60                 :            : 
      61                 :            : 
      62                 :            : /* Looks for level tolevel in current dungeon which is named by
      63                 :            : Dungeon, which may be NULL. If the level is found, and rewrite_level
      64                 :            : is FALSE, and the level has already been generated, nothing happens
      65                 :            : beyond Level being set correctly. Otherwise the level is recreated
      66                 :            : from scratch */
      67                 :            : 
      68                 :          0 : void change_level (char fromlevel, char tolevel, char rewrite_level)
      69                 :            : {
      70                 :          0 :   struct level * thislevel = NULL;
      71                 :          0 :   Player.sx = -1;
      72                 :          0 :   Player.sy = -1; /* sanctuary effect dispelled */
      73                 :            : 
      74                 :            : #ifndef SAVE_LEVELS
      75                 :          0 :   thislevel = findlevel(Dungeon, tolevel);
      76                 :          0 :   deepest[Current_Environment] = max(deepest[Current_Environment], tolevel);
      77         [ #  # ]:          0 :   if (!thislevel)
      78                 :            :     {
      79                 :          0 :       thislevel = checkmalloc(sizeof(levtype));
      80                 :          0 :       clear_level(thislevel);
      81                 :          0 :       Level = thislevel;
      82                 :          0 :       Level->next = Dungeon;
      83                 :          0 :       Dungeon = Level;
      84                 :            :     }
      85                 :            : #else
      86                 :            :   thislevel = msdos_changelevel(Level, Current_Environment, tolevel);
      87                 :            :   deepest[Current_Environment] = max(deepest[Current_Environment], tolevel);
      88                 :            :   if (!thislevel)
      89                 :            :     {
      90                 :            :       thislevel = &TheLevel;
      91                 :            :       clear_level(thislevel);
      92                 :            :       Level = thislevel;
      93                 :            :       Level->next = Dungeon;
      94                 :            :       Dungeon = Level;
      95                 :            :     }
      96                 :            : #endif
      97                 :            : 
      98                 :          0 :   Level = thislevel;
      99 [ #  # ][ #  # ]:          0 :   if ((!Level->generated) || rewrite_level)
     100                 :            :     {
     101                 :          0 :       initrand(Current_Environment, tolevel);
     102                 :          0 :       Level->environment = Current_Environment;
     103                 :          0 :       Level->depth = tolevel;
     104                 :          0 :       Level->generated = TRUE;
     105                 :            : 
     106   [ #  #  #  #  :          0 :       switch (Current_Environment)
                #  #  # ]
     107                 :            :         {
     108                 :            :         case E_CAVES: 
     109                 :          0 :           Level->level_width = CAVES_WIDTH;
     110                 :          0 :           Level->level_length = CAVES_LENGTH;
     111 [ #  # ][ #  # ]:          0 :           if ((0 == random_range(4)) && (tolevel < MaxDungeonLevels))
     112                 :          0 :             room_level();
     113                 :            :           else
     114                 :          0 :             cavern_level();
     115                 :          0 :           break;
     116                 :            : 
     117                 :            :         case E_SEWERS: 
     118                 :          0 :           Level->level_width = SEWERS_WIDTH;
     119                 :          0 :           Level->level_length = SEWERS_LENGTH;
     120 [ #  # ][ #  # ]:          0 :           if ((0 == random_range(4)) && (tolevel < MaxDungeonLevels))
     121                 :          0 :             room_level();
     122                 :            :           else
     123                 :          0 :             sewer_level(); 
     124                 :          0 :           break;
     125                 :            : 
     126                 :            :         case E_CASTLE:
     127                 :          0 :           Level->level_width = CASTLE_WIDTH;
     128                 :          0 :           Level->level_length = CASTLE_LENGTH;
     129                 :          0 :           room_level();
     130                 :          0 :           break;
     131                 :            : 
     132                 :            :         case E_PALACE: /* PGM TODO */
     133                 :          0 :           Level->level_width = PALACE_WIDTH;
     134                 :          0 :           Level->level_length = PALACE_LENGTH;
     135                 :          0 :           room_level();
     136                 :          0 :           break;
     137                 :            : 
     138                 :            :         case E_ASTRAL:
     139                 :          0 :           Level->level_width = ASTRAL_WIDTH;
     140                 :          0 :           Level->level_length = ASTRAL_LENGTH;
     141                 :          0 :           maze_level();
     142                 :          0 :           break;
     143                 :            : 
     144                 :            :         case E_VOLCANO:
     145                 :          0 :           Level->level_width = VOLCANO_WIDTH;
     146                 :          0 :           Level->level_length = VOLCANO_LENGTH;
     147   [ #  #  #  # ]:          0 :           switch (random_range(3))
     148                 :            :             {
     149                 :          0 :             case 0: cavern_level(); break;
     150                 :          0 :             case 1: room_level(); break;
     151                 :          0 :             case 2: maze_level(); break;
     152                 :            :             }
     153                 :          0 :           break;
     154                 :            : 
     155                 :            :         default:
     156                 :          0 :           print3("This dungeon not implemented!");
     157                 :          0 :           assert(FALSE);
     158                 :            :           break;
     159                 :            :         }
     160                 :            : 
     161                 :          0 :       install_traps();
     162                 :          0 :       install_specials();
     163                 :          0 :       make_stairs(fromlevel);
     164                 :          0 :       make_stairs(fromlevel);
     165                 :          0 :       initrand(E_RESTORE, 0);
     166                 :          0 :       populate_level(Current_Environment);
     167                 :          0 :       stock_level();
     168                 :            :     }
     169                 :            : 
     170                 :          0 :   find_stairs(fromlevel, tolevel);
     171                 :          0 :   ScreenOffset = Player.y - (ScreenLength/2);
     172                 :          0 :   show_screen();
     173                 :          0 :   screencheck(Player.x,Player.y);
     174                 :          0 :   drawvision(Player.x,Player.y);
     175                 :            : 
     176                 :            :   /* synchronize with player on level change */
     177                 :          0 :   Player.click = (Tick+1)%60;
     178                 :          0 :   roomcheck();
     179                 :          0 : }
     180                 :            : 
     181                 :            : #ifndef SAVE_LEVELS
     182                 :            : /* tries to find the level of depth levelnum in dungeon; if can't find
     183                 :            :    it returns NULL */
     184                 :          0 : plv findlevel(struct level *dungeon, char levelnum)
     185                 :            : {
     186         [ #  # ]:          0 :   if (dungeon == NULL) return(NULL);
     187                 :            :   else {
     188 [ #  # ][ #  # ]:          0 :     while((dungeon->next != NULL) && (dungeon->depth != levelnum))
     189                 :          0 :       dungeon = dungeon->next;
     190         [ #  # ]:          0 :     if (dungeon->depth == levelnum) {
     191                 :          0 :       dungeon->last_visited = time(NULL);
     192                 :          0 :       return(dungeon);
     193                 :            :     }
     194                 :          0 :     else return(NULL);
     195                 :            :   }
     196                 :            : }
     197                 :            : #endif
     198                 :            : 
     199                 :            : 
     200                 :            : 
     201                 :            : /* keep going in one orthogonal direction or another until we hit our */
     202                 :            : /* destination */
     203                 :            : 
     204                 :          0 : void straggle_corridor(int fx, int fy, int tx, int ty, Symbol loc, char rsi)
     205                 :            : {
     206                 :            :   int dx,dy;
     207 [ #  # ][ #  # ]:          0 :   while ((fx != tx) || (fy != ty)) {
     208                 :          0 :     dx = tx - fx;
     209                 :          0 :     dy = ty - fy;
     210         [ #  # ]:          0 :     if (random_range(abs(dx)+abs(dy)) < abs(dx))
     211         [ #  # ]:          0 :       corridor_crawl(&fx,&fy,sign(dx),0,random_range(abs(dx))+1,loc,rsi);
     212         [ #  # ]:          0 :     else corridor_crawl(&fx,&fy,0,sign(dy),random_range(abs(dy))+1,loc,rsi);
     213                 :            :   }
     214                 :          0 : }
     215                 :            : 
     216                 :            : 
     217                 :          0 : void makedoor(int x, int y)
     218                 :            : {
     219         [ #  # ]:          0 :   if (random_range(20) <= Level->depth/10) {
     220                 :          0 :     Level->site[x][y].locchar = FLOOR;
     221                 :          0 :     lset(x,y,SECRET);
     222                 :            :   }
     223         [ #  # ]:          0 :   else if (random_range(20)<=Level->depth/2) {
     224                 :          0 :     Level->site[x][y].locchar = CLOSED_DOOR;
     225         [ #  # ]:          0 :     if (random_range(20) <= Level->depth/10) 
     226                 :          0 :       lset(x,y,SECRET);
     227         [ #  # ]:          0 :     if (random_range(40) <= Level->depth) 
     228                 :          0 :       Level->site[x][y].aux = LOCKED;
     229                 :          0 :     else Level->site[x][y].aux = UNLOCKED;
     230                 :            :   }
     231                 :            :   else {
     232                 :          0 :     Level->site[x][y].locchar = OPEN_DOOR;
     233                 :          0 :     Level->site[x][y].aux = UNLOCKED;
     234                 :            :   }
     235         [ #  # ]:          0 :   if (! loc_statusp(x,y,SECRET)) {
     236                 :          0 :     lset(x,y+1,STOPS);
     237                 :          0 :     lset(x+1,y,STOPS);
     238                 :          0 :     lset(x-1,y,STOPS);
     239                 :          0 :     lset(x,y-1,STOPS);
     240                 :          0 :     lset(x,y,STOPS);
     241                 :            :   }
     242                 :          0 :   Level->site[x][y].p_locf = L_NO_OP; 
     243                 :            :   /* prevents water corridors from being instant death in sewers */
     244                 :          0 : }
     245                 :            : 
     246                 :            : 
     247                 :          0 : void corridor_crawl(int *fx, int *fy, int sx, int sy, int n, 
     248                 :            :                     Symbol loc, char rsi)
     249                 :            : {
     250                 :            :   int i;
     251         [ #  # ]:          0 :   for (i=0;i<n;i++) {
     252                 :          0 :     *fx += sx;
     253                 :          0 :     *fy += sy;
     254 [ #  # ][ #  # ]:          0 :     if ((*fx < Level->level_width) && 
     255         [ #  # ]:          0 :         (*fx > -1) && 
     256         [ #  # ]:          0 :         (*fy > -1) && 
     257                 :          0 :         (*fy < Level->level_length)) {
     258                 :          0 :       Level->site[*fx][*fy].locchar = loc;
     259         [ #  # ]:          0 :       if (Level->site[*fx][*fy].roomnumber == RS_WALLSPACE)
     260                 :          0 :         Level->site[*fx][*fy].roomnumber = rsi;
     261         [ #  # ]:          0 :       if (loc==WATER) 
     262                 :          0 :         Level->site[*fx][*fy].p_locf = L_WATER;
     263         [ #  # ]:          0 :       else if (loc==FLOOR) 
     264                 :          0 :         Level->site[*fx][*fy].p_locf = L_NO_OP;
     265         [ #  # ]:          0 :       else if (loc==RUBBLE)
     266                 :          0 :         Level->site[*fx][*fy].p_locf = L_RUBBLE;
     267                 :            :     }
     268                 :            :   }
     269                 :          0 : }  
     270                 :            : 
     271                 :            : 
     272                 :          0 : char *roomname(int index)
     273                 :            : {
     274   [ #  #  #  #  :          0 :   switch(index) {
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
          #  #  #  #  #  
                #  #  # ]
     275                 :          0 :   case RS_ZORCH:strcpy(Str4,"A place zorched by powerful magic.");break;
     276                 :          0 :   case RS_COURT:strcpy(Str4,"The Court of the ArchMage."); break;
     277                 :          0 :   case RS_CIRCLE:strcpy(Str4,"The Astral Demesne of the Circle of Sorcerors");
     278                 :          0 :     break;
     279                 :          0 :   case RS_MAGIC_ISLE: strcpy(Str4,"An island positively reeking of magic");
     280                 :          0 :     break;
     281                 :          0 :   case RS_STARPEAK: strcpy(Str4,"Near the oddly glowing peak of a mountain");
     282                 :          0 :     break;
     283                 :          0 :   case RS_VOLCANO: strcpy(Str4,"Deep within the bowels of the earth"); break;
     284                 :          0 :   case RS_HIGHASTRAL: strcpy(Str4,"The High Astral Plane"); break;
     285                 :          0 :   case RS_EARTHPLANE: strcpy(Str4,"The Plane of Earth"); break;
     286                 :          0 :   case RS_WATERPLANE: strcpy(Str4,"The Plane of Water"); break;
     287                 :          0 :   case RS_FIREPLANE: strcpy(Str4,"The Plane of Fire"); break;
     288                 :          0 :   case RS_AIRPLANE: strcpy(Str4,"The Plane of Air"); break;
     289                 :          0 :   case RS_KITCHEN: strcpy(Str4,"A kitchen"); break;
     290                 :          0 :   case RS_BATHROOM: strcpy(Str4,"A bathroom"); break;
     291                 :          0 :   case RS_BEDROOM: strcpy(Str4,"A bedroom"); break;
     292                 :          0 :   case RS_DININGROOM: strcpy(Str4,"A dining room"); break;
     293                 :          0 :   case RS_SECRETPASSAGE: strcpy(Str4,"A secret passage"); break;
     294                 :          0 :   case RS_CLOSET: strcpy(Str4,"A stuffy closet"); break;
     295                 :          0 :   case RS_ARENA: strcpy(Str4,"The Rampart Arena"); break;
     296                 :          0 :   case RS_DROWNED_SEWER: strcpy(Str4,"A water-filled sewer node"); break;
     297                 :          0 :   case RS_DRAINED_SEWER: strcpy(Str4,"An unused sewer node"); break;
     298                 :          0 :   case RS_SEWER_DUCT: strcpy(Str4,"A winding sewer duct"); break;
     299                 :          0 :   case RS_DESTINY: strcpy(Str4,"The Halls of Fate"); break;
     300                 :          0 :   case RS_DRUID: strcpy(Str4,"The Great Henge"); break;
     301                 :          0 :   case RS_HECATE: strcpy(Str4,"The Church of the Far Side"); break;
     302                 :          0 :   case RS_SET: strcpy(Str4,"The Temple of the Black Hand"); break;
     303                 :          0 :   case RS_ATHENA: strcpy(Str4,"The Parthenon"); break;
     304                 :          0 :   case RS_ODIN: strcpy(Str4,"The Shrine of the Noose"); break;
     305                 :          0 :   case RS_ADEPT: strcpy(Str4,"The Adept's Challenge"); break;
     306                 :          0 :   case RS_WYRM: strcpy(Str4,"The Sunken Cavern of the Great Wyrm."); break;
     307                 :          0 :   case RS_OCEAN: strcpy(Str4,"The Underground Ocean."); break;
     308                 :          0 :   case RS_PONDS: strcpy(Str4,"A series of subterranean pools and streams."); break;
     309                 :          0 :   case RS_DRAGONLORD: strcpy(Str4,"The Lair of the DragonLord."); break;
     310                 :          0 :   case RS_GOBLINKING: strcpy(Str4,"The Caves of the Goblins."); break;
     311                 :          0 :   case RS_CAVERN: strcpy(Str4,"A vast natural cavern."); break;
     312                 :          0 :   case RS_CORRIDOR: strcpy(Str4,"A dimly lit corridor."); break;
     313                 :          0 :   case RS_WALLSPACE: strcpy(Str4,"A niche hollowed out of the wall."); break;
     314                 :            :   /* following are above ROOMBASE */
     315                 :          0 :   case RS_GARDEROBE: strcpy(Str4,"An abandoned garderobe."); break;
     316                 :          0 :   case RS_CELL: strcpy(Str4,"A dungeon cell."); break;
     317                 :          0 :   case RS_TILED: strcpy(Str4,"A tiled chamber."); break;
     318                 :          0 :   case RS_CRYSTAL_CAVE: strcpy(Str4,"A crystal cavern."); break;
     319                 :          0 :   case RS_BEDROOM2: strcpy(Str4,"Someone's bedroom."); break;
     320                 :          0 :   case RS_STOREROOM: strcpy(Str4,"An old storeroom."); break;
     321                 :          0 :   case RS_CHARRED: strcpy(Str4,"A room with charred walls."); break;
     322                 :          0 :   case RS_MARBLE_HALL: strcpy(Str4,"A marble hall."); break;
     323                 :          0 :   case RS_EERIE_CAVE: strcpy(Str4,"An eerie cave."); break;
     324                 :          0 :   case RS_TREASURE: strcpy(Str4,"A ransacked treasure-chamber."); break;
     325                 :          0 :   case RS_SMOKEY: strcpy(Str4,"A smoke-filled room."); break;
     326                 :          0 :   case RS_APARTMENT: strcpy(Str4,"A well-appointed apartment."); break;
     327                 :          0 :   case RS_ANTECHAMBER: strcpy(Str4,"An antechamber."); break;
     328                 :          0 :   case RS_HAREM: strcpy(Str4,"An unoccupied harem."); break;
     329                 :          0 :   case RS_MULTIPURPOSE: strcpy(Str4,"A multi-purpose room."); break;
     330                 :          0 :   case RS_STALACTITES: strcpy(Str4,"A room filled with stalactites."); break;
     331                 :          0 :   case RS_GREENHOUSE: strcpy(Str4,"An underground greenhouse."); break;
     332                 :          0 :   case RS_WATERCLOSET: strcpy(Str4,"A water closet."); break;
     333                 :          0 :   case RS_STUDY: strcpy(Str4,"A study."); break;
     334                 :          0 :   case RS_LIVING_ROOM: strcpy(Str4,"A living room."); break;
     335                 :          0 :   case RS_DEN: strcpy(Str4,"A comfortable den."); break;
     336                 :          0 :   case RS_ABATOIR: strcpy(Str4,"An abatoir."); break;
     337                 :          0 :   case RS_BOUDOIR: strcpy(Str4,"A boudoir.");break;
     338                 :          0 :   case RS_STAR_CHAMBER: strcpy(Str4,"A star chamber.");break;
     339                 :          0 :   case RS_MANMADE_CAVE: strcpy(Str4,"A manmade cavern."); break;
     340                 :          0 :   case RS_SEWER_CONTROL: strcpy(Str4,"A sewer control room");break;
     341                 :          0 :   case RS_SHRINE: strcpy(Str4,"A shrine to High Magic"); break;
     342                 :          0 :   case RS_MAGIC_LAB: strcpy(Str4,"A magic laboratory"); break;
     343                 :          0 :   case RS_PENTAGRAM: strcpy(Str4,"A room with inscribed pentagram");break;
     344                 :          0 :   case RS_OMEGA_DAIS: strcpy(Str4,"A chamber with a blue crystal omega dais");
     345                 :          0 :     break;
     346                 :            :      /* WDT: removed period from description. */
     347                 :          0 :   default: strcpy(Str4,"A room of mystery and allure"); break;
     348                 :            :   }
     349                 :          0 :   return(Str4);
     350                 :            : }
     351                 :            : 
     352                 :            : 
     353                 :            : /* puts the player on the first set of stairs from the apt level */
     354                 :            : /* if can't find them, just drops player anywhere.... */
     355                 :          0 : void find_stairs(char fromlevel, char tolevel)
     356                 :            : {
     357                 :          0 :   int i,j,found=FALSE;
     358                 :            :   Symbol sitechar;
     359         [ #  # ]:          0 :   if (fromlevel > tolevel) sitechar = STAIRS_DOWN; else sitechar = STAIRS_UP;
     360         [ #  # ]:          0 :   for(i=0;i<Level->level_width;i++)
     361         [ #  # ]:          0 :     for(j=0;j<Level->level_length;j++) 
     362 [ #  # ][ #  # ]:          0 :       if ((Level->site[i][j].locchar == sitechar) && (! found)) { 
     363                 :          0 :         found = TRUE;
     364                 :          0 :         Player.x = i;
     365                 :          0 :         Player.y = j;
     366                 :          0 :         break;
     367                 :            :       }
     368         [ #  # ]:          0 :   if (! found) {
     369                 :          0 :     findspace(&Player.x,&Player.y,-1);
     370         [ #  # ]:          0 :     if (Level->environment != E_ASTRAL) {
     371                 :          0 :       Level->site[Player.x][Player.y].locchar = sitechar;
     372                 :          0 :       lset(Player.x, Player.y, CHANGED);
     373                 :            :     }
     374                 :            :   }
     375                 :          0 : }
     376                 :            : 
     377                 :            : 
     378                 :            : 
     379                 :          0 : void install_traps(void)
     380                 :            : {
     381                 :            :   int i,j;
     382         [ #  # ]:          0 :   for(i=0;i<Level->level_width;i++)
     383         [ #  # ]:          0 :     for(j=0;j<Level->level_length;j++)
     384 [ #  # ][ #  # ]:          0 :       if ((Level->site[i][j].locchar == FLOOR) &&
     385         [ #  # ]:          0 :           (Level->site[i][j].p_locf == L_NO_OP) &&
     386                 :          0 :           random_range(500) <= ((int)(Level->depth/6)))
     387                 :          0 :         Level->site[i][j].p_locf = TRAP_BASE+random_range(NUMTRAPS);
     388                 :          0 : }
     389                 :            : 
     390                 :            : 
     391                 :            : /* x, y, is top left corner, l is length of side, rsi is room string index */
     392                 :            : /* baux is so all rooms will have a key field. */
     393                 :          0 : void build_square_room(int x, int y, int l, char rsi, int baux)
     394                 :            : {
     395                 :            :   int i,j;
     396                 :            : 
     397         [ #  # ]:          0 :   for(i=x;i<=x+l;i++)
     398         [ #  # ]:          0 :     for(j=y;j<=y+l;j++){
     399                 :          0 :       Level->site[i][j].roomnumber = rsi;
     400                 :          0 :       Level->site[i][j].buildaux = baux;
     401                 :            :     }
     402         [ #  # ]:          0 :   for(i=x+1;i<x+l;i++)
     403         [ #  # ]:          0 :     for(j=y+1;j<y+l;j++) {
     404                 :          0 :       Level->site[i][j].locchar = FLOOR;
     405                 :          0 :       Level->site[i][j].p_locf = L_NO_OP;
     406                 :            :     }
     407                 :          0 : }
     408                 :            : 
     409                 :            : 
     410                 :          0 : void build_room(int x, int y, int l, char rsi, int baux)
     411                 :            : {
     412                 :          0 :   build_square_room(x,y,l,rsi,baux);
     413                 :          0 : }
     414                 :            : 
     415                 :          0 : void cavern_level(void)
     416                 :            : {
     417                 :            :   int i,fx,fy,tx,ty,t,l,e;
     418                 :            :   char rsi;
     419                 :            : 
     420                 :          0 :   Level->numrooms = 1;
     421                 :            : 
     422 [ #  # ][ #  # ]:          0 :   if ((Current_Dungeon == E_CAVES) && (Level->depth == CAVELEVELS))
     423                 :          0 :     rsi = RS_GOBLINKING;
     424                 :          0 :   else rsi = RS_CAVERN;
     425                 :          0 :   t = random_range((Level->level_length)/2);
     426                 :          0 :   l = random_range((Level->level_width)/2);
     427                 :          0 :   e = random_range((Level->level_width)/8)+(Level->level_width)/8;
     428                 :          0 :   build_square_room(t,l,e,rsi,0);
     429                 :            :   
     430         [ #  # ]:          0 :   for (i=0;i<16;i++) {
     431                 :          0 :     findspace(&tx,&ty,-1);
     432                 :          0 :     fx = random_range((Level->level_width)-2)+1;
     433                 :          0 :     fy = random_range((Level->level_length)-2)+1;
     434                 :          0 :     straggle_corridor(fx,fy,tx,ty,FLOOR,RS_CORRIDOR);
     435                 :            :   }
     436         [ #  # ]:          0 :   while (random_range(3)==1) {
     437                 :          0 :     findspace(&tx,&ty,-1);
     438                 :          0 :     fx = random_range((Level->level_width)-2)+1;
     439                 :          0 :     fy = random_range((Level->level_length)-2)+1;
     440                 :          0 :     straggle_corridor(fx,fy,tx,ty,WATER,RS_PONDS);
     441                 :            :   }
     442         [ #  # ]:          0 :   if (Current_Dungeon == E_CAVES) {
     443 [ #  # ][ #  # ]:          0 :     if ((Level->depth == CAVELEVELS) && (! gamestatusp(COMPLETED_CAVES))) {
     444                 :          0 :       findspace(&tx,&ty,-1);
     445                 :          0 :       Level->mlist = ((pml) checkmalloc(sizeof(mltype)));
     446                 :          0 :       Level->mlist->next = NULL;
     447                 :          0 :       Level->mlist->m = 
     448                 :          0 :         Level->site[tx][ty].creature = 
     449                 :          0 :           ((pmt) make_creature(GOBLIN_KING)); /* goblin king */
     450                 :          0 :       Level->mlist->m->x = tx;
     451                 :          0 :       Level->mlist->m->y = ty;
     452                 :            :     }
     453                 :            :   }
     454         [ #  # ]:          0 :   else if (Current_Environment == E_VOLCANO) {
     455         [ #  # ]:          0 :     if (Level->depth == VOLCANOLEVELS) {
     456                 :          0 :       findspace(&tx,&ty,-1);
     457                 :          0 :       Level->mlist = ((pml) checkmalloc(sizeof(mltype)));
     458                 :          0 :       Level->mlist->next = NULL;
     459                 :          0 :       Level->mlist->m = 
     460                 :          0 :         Level->site[tx][ty].creature = 
     461                 :          0 :           ((pmt) make_creature(DEMON_EMP)); /* The demon emp */
     462                 :          0 :       Level->mlist->m->x = tx;
     463                 :          0 :       Level->mlist->m->y = ty;
     464                 :            :     }
     465                 :            :   }
     466                 :          0 : }
     467                 :            : 
     468                 :            : 
     469                 :          0 : void sewer_level(void)
     470                 :            : {
     471                 :            :   int i,tx,ty,t,l,e;
     472                 :            :   char rsi;
     473                 :            :   Symbol lchar;
     474                 :            : 
     475                 :          0 :   Level->numrooms = random_range(3)+3;
     476                 :          0 :   rsi = RS_DRAINED_SEWER;
     477         [ #  # ]:          0 :   for (i=0;i<Level->numrooms;i++) {
     478                 :            :     do {
     479                 :          0 :       t = random_range((Level->level_length)-10)+1;
     480                 :          0 :       l = random_range((Level->level_width)-10)+1;
     481                 :          0 :       e = 4;
     482         [ #  # ]:          0 :     } while ((Level->site[l][t].roomnumber == rsi) ||
     483         [ #  # ]:          0 :              (Level->site[l+e][t].roomnumber == rsi) ||
     484         [ #  # ]:          0 :              (Level->site[l][t+e].roomnumber == rsi) ||
     485         [ #  # ]:          0 :              (Level->site[l+e][t+e].roomnumber == rsi));
     486         [ #  # ]:          0 :     if (random_range(5)) {
     487                 :          0 :       lchar = FLOOR;
     488                 :          0 :       rsi = RS_DRAINED_SEWER;
     489                 :            :     }
     490                 :            :     else {
     491                 :          0 :       lchar = WATER;
     492                 :          0 :       rsi = RS_DROWNED_SEWER;
     493                 :            :     }
     494                 :          0 :     build_room(l,t,e,rsi,i);
     495                 :          0 :     sewer_corridor(l,t,-1,-1,lchar);
     496                 :          0 :     sewer_corridor(l+e,t,1,-1,lchar);
     497                 :          0 :     sewer_corridor(l,t+e,-1,1,lchar);
     498                 :          0 :     sewer_corridor(l+e,t+e,1,1,lchar);
     499                 :            :   }
     500         [ #  # ]:          0 :   if (Current_Dungeon == E_SEWERS) {
     501 [ #  # ][ #  # ]:          0 :     if ((Level->depth == SEWERLEVELS) && (! gamestatusp(COMPLETED_SEWERS))) {
     502                 :          0 :       findspace(&tx,&ty,-1);
     503                 :          0 :       Level->mlist = ((pml) checkmalloc(sizeof(mltype)));
     504                 :          0 :       Level->mlist->next = NULL;
     505                 :          0 :       Level->mlist->m = 
     506                 :          0 :         Level->site[tx][ty].creature = 
     507                 :          0 :           ((pmt) make_creature(GREAT_WYRM)); /* The Great Wyrm */
     508                 :          0 :       Level->mlist->m->x = tx;
     509                 :          0 :       Level->mlist->m->y = ty;
     510                 :            :     }
     511                 :            :   }
     512                 :          0 : }
     513                 :            : 
     514                 :            : 
     515                 :          0 : void sewer_corridor(int x, int y, int dx, int dy, Symbol locchar)
     516                 :            : {
     517                 :          0 :   int continuing = TRUE;
     518                 :          0 :   makedoor(x,y);
     519                 :          0 :   x+=dx;
     520                 :          0 :   y+=dy;
     521         [ #  # ]:          0 :   while(continuing) {
     522                 :          0 :     Level->site[x][y].locchar = locchar;
     523         [ #  # ]:          0 :     if (locchar == WATER)
     524                 :          0 :       Level->site[x][y].p_locf = L_WATER;
     525                 :          0 :     else Level->site[x][y].p_locf = L_NO_OP;
     526                 :          0 :     Level->site[x][y].roomnumber = RS_SEWER_DUCT;
     527                 :          0 :     x+=dx;
     528                 :          0 :     y+=dy;
     529         [ #  # ]:          0 :   if (locchar == WATER)
     530 [ #  # ][ #  # ]:          0 :     continuing = (inbounds(x,y) && 
     531         [ #  # ]:          0 :                   ((Level->site[x][y].locchar == WALL) ||
     532                 :          0 :                    (Level->site[x][y].locchar == WATER)));
     533                 :            :   else
     534 [ #  # ][ #  # ]:          0 :     continuing = (inbounds(x,y) && 
     535         [ #  # ]:          0 :                   ((Level->site[x][y].roomnumber == RS_WALLSPACE) ||
     536                 :          0 :                    (Level->site[x][y].roomnumber == RS_SEWER_DUCT)));
     537                 :            :   }
     538         [ #  # ]:          0 :   if (inbounds(x,y))
     539                 :          0 :     makedoor(x,y);
     540                 :          0 : }
     541                 :            : 
     542                 :            : 
     543                 :          0 : void install_specials(void)
     544                 :            : {
     545                 :            :   int i,j,x,y;
     546                 :            : 
     547         [ #  # ]:          0 :   for(x=0;x<Level->level_width;x++)
     548         [ #  # ]:          0 :     for(y=0;y<Level->level_length;y++)
     549 [ #  # ][ #  # ]:          0 :       if ((Level->site[x][y].locchar == FLOOR) &&
     550         [ #  # ]:          0 :           (Level->site[x][y].p_locf == L_NO_OP) &&
     551                 :          0 :           (random_range(300) < difficulty())) {
     552                 :          0 :         i = random_range(100);
     553         [ #  # ]:          0 :         if (i < 10) {
     554                 :          0 :           Level->site[x][y].locchar = ALTAR;
     555                 :          0 :           Level->site[x][y].p_locf = L_ALTAR;
     556                 :          0 :           Level->site[x][y].aux = random_range(10);
     557                 :            :         }
     558         [ #  # ]:          0 :         else if (i < 20) {
     559                 :          0 :           Level->site[x][y].locchar = WATER;
     560                 :          0 :           Level->site[x][y].p_locf = L_MAGIC_POOL;
     561                 :            :         }
     562         [ #  # ]:          0 :         else if (i < 35) {
     563                 :          0 :           Level->site[x][y].locchar = RUBBLE;
     564                 :          0 :           Level->site[x][y].p_locf = L_RUBBLE;
     565                 :            :         }
     566         [ #  # ]:          0 :         else if (i < 40) {
     567                 :          0 :           Level->site[x][y].locchar = LAVA;
     568                 :          0 :           Level->site[x][y].p_locf = L_LAVA;
     569                 :            :         }
     570         [ #  # ]:          0 :         else if (i < 45) {
     571                 :          0 :           Level->site[x][y].locchar = FIRE;
     572                 :          0 :           Level->site[x][y].p_locf = L_FIRE;
     573                 :            :         }
     574 [ #  # ][ #  # ]:          0 :         else if ((i < 50) && (Current_Environment != E_ASTRAL)) {
     575                 :          0 :           Level->site[x][y].locchar = LIFT;
     576                 :          0 :           Level->site[x][y].p_locf = L_LIFT;
     577                 :            :         }
     578 [ #  # ][ #  # ]:          0 :         else if ((i < 55) && (Current_Environment != E_VOLCANO)) {
     579                 :          0 :           Level->site[x][y].locchar = HEDGE;
     580                 :          0 :           Level->site[x][y].p_locf = L_HEDGE;
     581                 :            :         }
     582         [ #  # ]:          0 :         else if (i < 57) {
     583                 :          0 :           Level->site[x][y].locchar = HEDGE;
     584                 :          0 :           Level->site[x][y].p_locf = L_TRIFID;
     585                 :            :         }
     586         [ #  # ]:          0 :         else if (i< 70) {
     587                 :          0 :           Level->site[x][y].locchar = STATUE;
     588         [ #  # ]:          0 :           if (random_range(100) < difficulty()) 
     589         [ #  # ]:          0 :             for (j=0;j<8;j++) {
     590         [ #  # ]:          0 :               if (Level->site[x+Dirs[0][j]][y+Dirs[1][j]].p_locf != L_NO_OP)
     591                 :          0 :                 Level->site[x+Dirs[0][j]][y+Dirs[1][j]].locchar = FLOOR;
     592                 :          0 :               Level->site[x+Dirs[0][j]][y+Dirs[1][j]].p_locf = 
     593                 :            :                 L_STATUE_WAKE;
     594                 :            :             }
     595                 :            :         }
     596                 :            :         else {
     597         [ #  # ]:          0 :           if (Current_Environment == E_VOLCANO) {
     598                 :          0 :             Level->site[x][y].locchar = LAVA;
     599                 :          0 :             Level->site[x][y].p_locf = L_LAVA;
     600                 :            :           }
     601         [ #  # ]:          0 :           else if (Current_Environment == E_ASTRAL) {
     602         [ #  # ]:          0 :             if (Level->depth == 1) {
     603                 :          0 :               Level->site[x][y].locchar = RUBBLE;
     604                 :          0 :               Level->site[x][y].p_locf = L_RUBBLE;
     605                 :            :             }
     606         [ #  # ]:          0 :             else if (Level->depth == 2) {
     607                 :          0 :               Level->site[x][y].locchar = FIRE;
     608                 :          0 :               Level->site[x][y].p_locf = L_FIRE;
     609                 :            :             }
     610         [ #  # ]:          0 :             else if (Level->depth == 3) {
     611                 :          0 :               Level->site[x][y].locchar = WATER;
     612                 :          0 :               Level->site[x][y].p_locf = L_WATER;
     613                 :            :             }
     614         [ #  # ]:          0 :             else if (Level->depth == 4) {
     615                 :          0 :               Level->site[x][y].locchar = ABYSS;
     616                 :          0 :               Level->site[x][y].p_locf = L_ABYSS;
     617                 :            :             }
     618                 :            :           }
     619                 :            :           else {
     620                 :          0 :             Level->site[x][y].locchar = WATER;
     621                 :          0 :             Level->site[x][y].p_locf = L_WATER;
     622                 :            :           }
     623                 :            :         }
     624                 :            :       }
     625                 :          0 : }

Generated by: LCOV version 1.11