Changeset 465

Show
Ignore:
Timestamp:
08/07/07 19:44:53 (1 year ago)
Author:
takkaria
Message:

Move running code into pathfind.c. Also, give CJS the credit and copyright date he deserves. (part of #65)

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/src/cmd1.c

    r433 r465  
    10541054        } 
    10551055} 
    1056  
    1057  
    1058 /* 
    1059  * Hack -- Check for a "known wall" (see below) 
    1060  */ 
    1061 static int see_wall(int dir, int y, int x) 
    1062 { 
    1063         /* Get the new location */ 
    1064         y += ddy[dir]; 
    1065         x += ddx[dir]; 
    1066  
    1067         /* Illegal grids are not known walls XXX XXX XXX */ 
    1068         if (!in_bounds(y, x)) return (FALSE); 
    1069  
    1070         /* Non-wall grids are not known walls */ 
    1071         if (cave_feat[y][x] < FEAT_SECRET) return (FALSE); 
    1072  
    1073         /* Unknown walls are not known walls */ 
    1074         if (!(cave_info[y][x] & (CAVE_MARK))) return (FALSE); 
    1075  
    1076         /* Default */ 
    1077         return (TRUE); 
    1078 } 
    1079  
    1080  
    1081  
    1082  
    1083 /* 
    1084  * The running algorithm  -CJS- 
    1085  * 
    1086  * Basically, once you start running, you keep moving until something 
    1087  * interesting happens.  In an enclosed space, you run straight, but 
    1088  * you follow corners as needed (i.e. hallways).  In an open space, 
    1089  * you run straight, but you stop before entering an enclosed space 
    1090  * (i.e. a room with a doorway).  In a semi-open space (with walls on 
    1091  * one side only), you run straight, but you stop before entering an 
    1092  * enclosed space or an open space (i.e. running along side a wall). 
    1093  * 
    1094  * All discussions below refer to what the player can see, that is, 
    1095  * an unknown wall is just like a normal floor.  This means that we 
    1096  * must be careful when dealing with "illegal" grids. 
    1097  * 
    1098  * No assumptions are made about the layout of the dungeon, so this 
    1099  * algorithm works in hallways, rooms, town, destroyed areas, etc. 
    1100  * 
    1101  * In the diagrams below, the player has just arrived in the grid 
    1102  * marked as '@', and he has just come from a grid marked as 'o', 
    1103  * and he is about to enter the grid marked as 'x'. 
    1104  * 
    1105  * Running while confused is not allowed, and so running into a wall 
    1106  * is only possible when the wall is not seen by the player.  This 
    1107  * will take a turn and stop the running. 
    1108  * 
    1109  * Several conditions are tracked by the running variables. 
    1110  * 
    1111  *   p_ptr->run_open_area (in the open on at least one side) 
    1112  *   p_ptr->run_break_left (wall on the left, stop if it opens) 
    1113  *   p_ptr->run_break_right (wall on the right, stop if it opens) 
    1114  * 
    1115  * When running begins, these conditions are initialized by examining 
    1116  * the grids adjacent to the requested destination grid (marked 'x'), 
    1117  * two on each side (marked 'L' and 'R').  If either one of the two 
    1118  * grids on a given side is a wall, then that side is considered to 
    1119  * be "closed".  Both sides enclosed yields a hallway. 
    1120  * 
    1121  *    LL                     @L 
    1122  *    @x      (normal)       RxL   (diagonal) 
    1123  *    RR      (east)          R    (south-east) 
    1124  * 
    1125  * In the diagram below, in which the player is running east along a 
    1126  * hallway, he will stop as indicated before attempting to enter the 
    1127  * intersection (marked 'x').  Starting a new run in any direction 
    1128  * will begin a new hallway run. 
    1129  * 
    1130  * #.# 
    1131  * ##.## 
    1132  * o@x.. 
    1133  * ##.## 
    1134  * #.# 
    1135  * 
    1136  * Note that a minor hack is inserted to make the angled corridor 
    1137  * entry (with one side blocked near and the other side blocked 
    1138  * further away from the runner) work correctly. The runner moves 
    1139  * diagonally, but then saves the previous direction as being 
    1140  * straight into the gap. Otherwise, the tail end of the other 
    1141  * entry would be perceived as an alternative on the next move. 
    1142  * 
    1143  * In the diagram below, the player is running east down a hallway, 
    1144  * and will stop in the grid (marked '1') before the intersection. 
    1145  * Continuing the run to the south-east would result in a long run 
    1146  * stopping at the end of the hallway (marked '2'). 
    1147  * 
    1148  * ################## 
    1149  * o@x       1 
    1150  * ########### ###### 
    1151  * #2          # 
    1152  * ############# 
    1153  * 
    1154  * After each step, the surroundings are examined to determine if 
    1155  * the running should stop, and to determine if the running should 
    1156  * change direction.  We examine the new current player location 
    1157  * (at which the runner has just arrived) and the direction from 
    1158  * which the runner is considered to have come. 
    1159  * 
    1160  * Moving one grid in some direction places you adjacent to three 
    1161  * or five new grids (for straight and diagonal moves respectively) 
    1162  * to which you were not previously adjacent (marked as '!'). 
    1163  * 
    1164  *   ...!              ... 
    1165  *   .o@!  (normal)    .o.!  (diagonal) 
    1166  *   ...!  (east)      ..@!  (south east) 
    1167  *                      !!! 
    1168  * 
    1169  * If any of the newly adjacent grids are "interesting" (monsters, 
    1170  * objects, some terrain features) then running stops. 
    1171  * 
    1172  * If any of the newly adjacent grids seem to be open, and you are 
    1173  * looking for a break on that side, then running stops. 
    1174  * 
    1175  * If any of the newly adjacent grids do not seem to be open, and 
    1176  * you are in an open area, and the non-open side was previously 
    1177  * entirely open, then running stops. 
    1178  * 
    1179  * If you are in a hallway, then the algorithm must determine if 
    1180  * the running should continue, turn, or stop.  If only one of the 
    1181  * newly adjacent grids appears to be open, then running continues 
    1182  * in that direction, turning if necessary.  If there are more than 
    1183  * two possible choices, then running stops.  If there are exactly 
    1184  * two possible choices, separated by a grid which does not seem 
    1185  * to be open, then running stops.  Otherwise, as shown below, the 
    1186  * player has probably reached a "corner". 
    1187  * 
    1188  *    ###             o## 
    1189  *    o@x  (normal)   #@!   (diagonal) 
    1190  *    ##!  (east)     ##x   (south east) 
    1191  * 
    1192  * In this situation, there will be two newly adjacent open grids, 
    1193  * one touching the player on a diagonal, and one directly adjacent. 
    1194  * We must consider the two "option" grids further out (marked '?'). 
    1195  * We assign "option" to the straight-on grid, and "option2" to the 
    1196  * diagonal grid.  For some unknown reason, we assign "check_dir" to 
    1197  * the grid marked 's', which may be incorrectly labelled. 
    1198  * 
    1199  *    ###s 
    1200  *    o@x?   (may be incorrect diagram!) 
    1201  *    ##!? 
    1202  * 
    1203  * If both "option" grids are closed, then there is no reason to enter 
    1204  * the corner, and so we can cut the corner, by moving into the other 
    1205  * grid (diagonally).  If we choose not to cut the corner, then we may 
    1206  * go straight, but we pretend that we got there by moving diagonally. 
    1207  * Below, we avoid the obvious grid (marked 'x') and cut the corner 
    1208  * instead (marked 'n'). 
    1209  * 
    1210  *    ###:               o## 
    1211  *    o@x#   (normal)    #@n    (maybe?) 
    1212  *    ##n#   (east)      ##x# 
    1213  *                       #### 
    1214  * 
    1215  * If one of the "option" grids is open, then we may have a choice, so 
    1216  * we check to see whether it is a potential corner or an intersection 
    1217  * (or room entrance).  If the grid two spaces straight ahead, and the 
    1218  * space marked with 's' are both open, then it is a potential corner 
    1219  * and we enter it if requested.  Otherwise, we stop, because it is 
    1220  * not a corner, and is instead an intersection or a room entrance. 
    1221  * 
    1222  *    ### 
    1223  *    o@x 
    1224  *    ##!# 
    1225  * 
    1226  * I do not think this documentation is correct. 
    1227  */ 
    1228  
    1229  
    1230  
    1231  
    1232 /* 
    1233  * Hack -- allow quick "cycling" through the legal directions 
    1234  */ 
    1235 static const byte cycle[] = 
    1236 { 1, 2, 3, 6, 9, 8, 7, 4, 1, 2, 3, 6, 9, 8, 7, 4, 1 }; 
    1237  
    1238 /* 
    1239  * Hack -- map each direction into the "middle" of the "cycle[]" array 
    1240  */ 
    1241 static const byte chome[] = 
    1242 { 0, 8, 9, 10, 7, 0, 11, 6, 5, 4 }; 
    1243  
    1244  
    1245  
    1246 /* 
    1247  * Initialize the running algorithm for a new direction. 
    1248  * 
    1249  * Diagonal Corridor -- allow diaginal entry into corridors. 
    1250  * 
    1251  * Blunt Corridor -- If there is a wall two spaces ahead and 
    1252  * we seem to be in a corridor, then force a turn into the side 
    1253  * corridor, must be moving straight into a corridor here. (?) 
    1254  * 
    1255  * Diagonal Corridor    Blunt Corridor (?) 
    1256  *       # #                  # 
    1257  *       #x#                 @x# 
    1258  *       @p.                  p 
    1259  */ 
    1260 static void run_init(int dir) 
    1261 { 
    1262         int py = p_ptr->py; 
    1263         int px = p_ptr->px; 
    1264  
    1265         int i, row, col; 
    1266  
    1267         bool deepleft, deepright; 
    1268         bool shortleft, shortright; 
    1269  
    1270  
    1271         /* Save the direction */ 
    1272         p_ptr->run_cur_dir = dir; 
    1273  
    1274         /* Assume running straight */ 
    1275         p_ptr->run_old_dir = dir; 
    1276  
    1277         /* Assume looking for open area */ 
    1278         p_ptr->run_open_area = TRUE; 
    1279  
    1280         /* Assume not looking for breaks */ 
    1281         p_ptr->run_break_right = FALSE; 
    1282         p_ptr->run_break_left = FALSE; 
    1283  
    1284         /* Assume no nearby walls */ 
    1285         deepleft = deepright = FALSE; 
    1286         shortright = shortleft = FALSE; 
    1287  
    1288         /* Find the destination grid */ 
    1289         row = py + ddy[dir]; 
    1290         col = px + ddx[dir]; 
    1291  
    1292         /* Extract cycle index */ 
    1293         i = chome[dir]; 
    1294  
    1295         /* Check for nearby wall */ 
    1296         if (see_wall(cycle[i+1], py, px)) 
    1297         { 
    1298                 p_ptr->run_break_left = TRUE; 
    1299                 shortleft = TRUE; 
    1300         } 
    1301  
    1302         /* Check for distant wall */ 
    1303         else if (see_wall(cycle[i+1], row, col)) 
    1304         { 
    1305                 p_ptr->run_break_left = TRUE; 
    1306                 deepleft = TRUE; 
    1307         } 
    1308  
    1309         /* Check for nearby wall */ 
    1310         if (see_wall(cycle[i-1], py, px)) 
    1311         { 
    1312                 p_ptr->run_break_right = TRUE; 
    1313                 shortright = TRUE; 
    1314         } 
    1315  
    1316         /* Check for distant wall */ 
    1317         else if (see_wall(cycle[i-1], row, col)) 
    1318         { 
    1319                 p_ptr->run_break_right = TRUE; 
    1320                 deepright = TRUE; 
    1321         } 
    1322  
    1323         /* Looking for a break */ 
    1324         if (p_ptr->run_break_left && p_ptr->run_break_right) 
    1325         { 
    1326                 /* Not looking for open area */ 
    1327                 p_ptr->run_open_area = FALSE; 
    1328  
    1329                 /* Hack -- allow angled corridor entry */ 
    1330                 if (dir & 0x01) 
    1331                 { 
    1332                         if (deepleft && !deepright) 
    1333                         { 
    1334                                 p_ptr->run_old_dir = cycle[i - 1]; 
    1335                         } 
    1336                         else if (deepright && !deepleft) 
    1337                         { 
    1338                                 p_ptr->run_old_dir = cycle[i + 1]; 
    1339                         } 
    1340                 } 
    1341  
    1342                 /* Hack -- allow blunt corridor entry */ 
    1343                 else if (see_wall(cycle[i], row, col)) 
    1344                 { 
    1345                         if (shortleft && !shortright) 
    1346                         { 
    1347                                 p_ptr->run_old_dir = cycle[i - 2]; 
    1348                         } 
    1349                         else if (shortright && !shortleft) 
    1350                         { 
    1351                                 p_ptr->run_old_dir = cycle[i + 2]; 
    1352                         } 
    1353                 } 
    1354         } 
    1355 } 
    1356  
    1357  
    1358 /* 
    1359  * Update the current "run" path 
    1360  * 
    1361  * Return TRUE if the running should be stopped 
    1362  */ 
    1363 static bool run_test(void) 
    1364 { 
    1365         int py = p_ptr->py; 
    1366         int px = p_ptr->px; 
    1367  
    1368         int prev_dir; 
    1369         int new_dir; 
    1370         int check_dir = 0; 
    1371  
    1372         int row, col; 
    1373         int i, max, inv; 
    1374         int option, option2; 
    1375  
    1376  
    1377         /* No options yet */ 
    1378         option = 0; 
    1379         option2 = 0; 
    1380  
    1381         /* Where we came from */ 
    1382         prev_dir = p_ptr->run_old_dir; 
    1383  
    1384  
    1385         /* Range of newly adjacent grids */ 
    1386         max = (prev_dir & 0x01) + 1; 
    1387  
    1388  
    1389         /* Look at every newly adjacent square. */ 
    1390         for (i = -max; i <= max; i++) 
    1391         { 
    1392                 object_type *o_ptr; 
    1393  
    1394  
    1395                 /* New direction */ 
    1396                 new_dir = cycle[chome[prev_dir] + i]; 
    1397  
    1398                 /* New location */ 
    1399                 row = py + ddy[new_dir]; 
    1400                 col = px + ddx[new_dir]; 
    1401  
    1402  
    1403                 /* Visible monsters abort running */ 
    1404                 if (cave_m_idx[row][col] > 0) 
    1405                 { 
    1406                         monster_type *m_ptr = &mon_list[cave_m_idx[row][col]]; 
    1407  
    1408                         /* Visible monster */ 
    1409                         if (m_ptr->ml) return (TRUE); 
    1410                 } 
    1411  
    1412                 /* Visible objects abort running */ 
    1413                 for (o_ptr = get_first_object(row, col); o_ptr; o_ptr = get_next_object(o_ptr)) 
    1414                 { 
    1415                         /* Visible object */ 
    1416                         if (o_ptr->marked && !squelch_hide_item(o_ptr)) return (TRUE); 
    1417                 } 
    1418  
    1419  
    1420                 /* Assume unknown */ 
    1421                 inv = TRUE; 
    1422  
    1423                 /* Check memorized grids */ 
    1424                 if (cave_info[row][col] & (CAVE_MARK)) 
    1425                 { 
    1426                         bool notice = TRUE; 
    1427  
    1428                         /* Examine the terrain */ 
    1429                         switch (cave_feat[row][col]) 
    1430                         { 
    1431                                 /* Floors */ 
    1432                                 case FEAT_FLOOR: 
    1433  
    1434                                 /* Invis traps */ 
    1435                                 case FEAT_INVIS: 
    1436  
    1437                                 /* Secret doors */ 
    1438                                 case FEAT_SECRET: 
    1439  
    1440                                 /* Normal veins */ 
    1441                                 case FEAT_MAGMA: 
    1442                                 case FEAT_QUARTZ: 
    1443  
    1444                                 /* Hidden treasure */ 
    1445                                 case FEAT_MAGMA_H: 
    1446                                 case FEAT_QUARTZ_H: 
    1447  
    1448                                 /* Walls */ 
    1449                                 case FEAT_WALL_EXTRA: 
    1450                                 case FEAT_WALL_INNER: 
    1451                                 case FEAT_WALL_OUTER: 
    1452                                 case FEAT_WALL_SOLID: 
    1453                                 case FEAT_PERM_EXTRA: 
    1454                                 case FEAT_PERM_INNER: 
    1455                                 case FEAT_PERM_OUTER: 
    1456                                 case FEAT_PERM_SOLID: 
    1457                                 { 
    1458                                         /* Ignore */ 
    1459                                         notice = FALSE; 
    1460  
    1461                                         /* Done */ 
    1462                                         break; 
    1463                                 } 
    1464                         } 
    1465  
    1466                         /* Interesting feature */ 
    1467                         if (notice) return (TRUE); 
    1468  
    1469                         /* The grid is "visible" */ 
    1470                         inv = FALSE; 
    1471                 } 
    1472  
    1473                 /* Analyze unknown grids and floors */ 
    1474                 if (inv || cave_floor_bold(row, col)) 
    1475                 { 
    1476                         /* Looking for open area */ 
    1477                         if (p_ptr->run_open_area) 
    1478                         { 
    1479                                 /* Nothing */ 
    1480                         } 
    1481  
    1482                         /* The first new direction. */ 
    1483                         else if (!option) 
    1484                         { 
    1485                                 option = new_dir; 
    1486                         } 
    1487  
    1488                         /* Three new directions. Stop running. */ 
    1489                         else if (option2) 
    1490                         { 
    1491                                 return (TRUE); 
    1492                         } 
    1493  
    1494                         /* Two non-adjacent new directions.  Stop running. */ 
    1495                         else if (option != cycle[chome[prev_dir] + i - 1]) 
    1496                         { 
    1497                                 return (TRUE); 
    1498                         } 
    1499  
    1500                         /* Two new (adjacent) directions (case 1) */ 
    1501                         else if (new_dir & 0x01) 
    1502                         { 
    1503                                 check_dir = cycle[chome[prev_dir] + i - 2]; 
    1504                                 option2 = new_dir; 
    1505                         } 
    1506  
    1507                         /* Two new (adjacent) directions (case 2) */ 
    1508                         else 
    1509                         { 
    1510                                 check_dir = cycle[chome[prev_dir] + i + 1]; 
    1511                                 option2 = option; 
    1512                                 option = new_dir; 
    1513                         } 
    1514                 } 
    1515  
    1516                 /* Obstacle, while looking for open area */ 
    1517                 else 
    1518                 { 
    1519                         if (p_ptr->run_open_area) 
    1520                         { 
    1521                                 if (i < 0) 
    1522                                 { 
    1523                                         /* Break to the right */ 
    1524                                         p_ptr->run_break_right = TRUE; 
    1525                                 } 
    1526  
    1527                                 else if (i > 0) 
    1528                                 { 
    1529                                         /* Break to the left */ 
    1530                                         p_ptr->run_break_left = TRUE; 
    1531                                 } 
    1532                         } 
    1533                 } 
    1534         } 
    1535  
    1536  
    1537         /* Looking for open area */ 
    1538         if (p_ptr->run_open_area) 
    1539         { 
    1540                 /* Hack -- look again */ 
    1541                 for (i = -max; i < 0; i++) 
    1542                 { 
    1543                         new_dir = cycle[chome[prev_dir] + i]; 
    1544  
    1545                         row = py + ddy[new_dir]; 
    1546                         col = px + ddx[new_dir]; 
    1547  
    1548                         /* Unknown grid or non-wall */ 
    1549                         /* Was: cave_floor_bold(row, col) */ 
    1550                         if (!(cave_info[row][col] & (CAVE_MARK)) || 
    1551                             (cave_feat[row][col] < FEAT_SECRET)) 
    1552                         { 
    1553                                 /* Looking to break right */ 
    1554                                 if (p_ptr->run_break_right) 
    1555                                 { 
    1556                                         return (TRUE); 
    1557                                 } 
    1558                         } 
    1559  
    1560                         /* Obstacle */ 
    1561                         else 
    1562                         { 
    1563                                 /* Looking to break left */ 
    1564                                 if (p_ptr->run_break_left) 
    1565                                 { 
    1566                                         return (TRUE); 
    1567                                 } 
    1568                         } 
    1569                 } 
    1570  
    1571                 /* Hack -- look again */ 
    1572                 for (i = max; i > 0; i--) 
    1573                 { 
    1574                         new_dir = cycle[chome[prev_dir] + i]; 
    1575  
    1576                         row = py + ddy[new_dir]; 
    1577                         col = px + ddx[new_dir]; 
    1578  
    1579                         /* Unknown grid or non-wall */ 
    1580                         /* Was: cave_floor_bold(row, col) */ 
    1581                         if (!(cave_info[row][col] & (CAVE_MARK)) || 
    1582                             (cave_feat[row][col] < FEAT_SECRET)) 
    1583                         { 
    1584                                 /* Looking to break left */ 
    1585                                 if (p_ptr->run_break_left) 
    1586                                 { 
    1587                                         return (TRUE); 
    1588                                 } 
    1589                         } 
    1590  
    1591                         /* Obstacle */ 
    1592                         else 
    1593                         { 
    1594                                 /* Looking to break right */ 
    1595                                 if (p_ptr->run_break_right) 
    1596                                 { 
    1597                                         return (TRUE); 
    1598                                 } 
    1599                         } 
    1600                 } 
    1601         } 
    1602  
    1603  
    1604         /* Not looking for open area */ 
    1605         else 
    1606         { 
    1607                 /* No options */ 
    1608                 if (!option) 
    1609                 { 
    1610                         return (TRUE); 
    1611                 } 
    1612  
    1613                 /* One option */ 
    1614                 else if (!option2) 
    1615                 { 
    1616                         /* Primary option */ 
    1617                         p_ptr->run_cur_dir = option; 
    1618  
    1619                         /* No other options */ 
    1620                         p_ptr->run_old_dir = option; 
    1621                 } 
    1622  
    1623                 /* Two options, examining corners */ 
    1624                 else 
    1625                 { 
    1626                         /* Primary option */ 
    1627                         p_ptr->run_cur_dir = option; 
    1628  
    1629                         /* Hack -- allow curving */ 
    1630                         p_ptr->run_old_dir = option2; 
    1631                 } 
    1632         } 
    1633  
    1634  
    1635         /* About to hit a known wall, stop */ 
    1636         if (see_wall(p_ptr->run_cur_dir, py, px)) 
    1637         { 
    1638                 return (TRUE); 
    1639         } 
    1640  
    1641  
    1642         /* Failure */ 
    1643         return (FALSE); 
    1644 } 
    1645  
    1646  
    1647  
    1648 /* 
    1649  * Take one step along the current "run" path 
    1650  * 
    1651  * Called with a real direction to begin a new run, and with zero 
    1652  * to continue a run in progress. 
    1653  */ 
    1654 void run_step(int dir) 
    1655 { 
    1656         int x, y; 
    1657  
    1658         /* Start run */ 
    1659         if (dir) 
    1660         { 
    1661                 /* Initialize */ 
    1662                 run_init(dir); 
    1663  
    1664                 /* Hack -- Set the run counter */ 
    1665                 p_ptr->running = (p_ptr->command_arg ? p_ptr->command_arg : 1000); 
    1666  
    1667                 /* Calculate torch radius */ 
    1668                 p_ptr->update |= (PU_TORCH); 
    1669         } 
    1670  
    1671         /* Continue run */ 
    1672         else 
    1673         { 
    1674                 if (!p_ptr->running_withpathfind) 
    1675                 { 
    1676                         /* Update run */ 
    1677                         if (run_test()) 
    1678                         { 
    1679                                 /* Disturb */ 
    1680                                 disturb(0, 0); 
    1681          
    1682                                 /* Done */ 
    1683                                 return; 
    1684                         } 
    1685                 } 
    1686                 else 
    1687                 { 
    1688                         /* Abort if we have finished */ 
    1689                         if (pf_result_index < 0) 
    1690                         { 
    1691                                 disturb(0, 0); 
    1692                                 p_ptr->running_withpathfind = FALSE; 
    1693                                 return; 
    1694                         } 
    1695                         /* Abort if we would hit a wall */ 
    1696                         else if (pf_result_index == 0) 
    1697                         { 
    1698                                 /* Get next step */ 
    1699                                 y = p_ptr->py + ddy[pf_result[pf_result_index] - '0']; 
    1700                                 x = p_ptr->px + ddx[pf_result[pf_result_index] - '0']; 
    1701  
    1702                                 /* Known wall */ 
    1703                                 if ((cave_info[y][x] & (CAVE_MARK)) && !cave_floor_bold(y, x)) 
    1704                                 { 
    1705                                         disturb(0,0); 
    1706                                         p_ptr->running_withpathfind = FALSE; 
    1707                                         return; 
    1708                                 } 
    1709                         } 
    1710                         /* Hack -- walking stick lookahead. 
    1711                          * 
    1712                          * If the player has computed a path that is going to end up in a wall, 
    1713                          * we notice this and convert to a normal run. This allows us to click 
    1714                          * on unknown areas to explore the map. 
    1715                          * 
    1716                          * We have to look ahead two, otherwise we don't know which is the last 
    1717                          * direction moved and don't initialise the run properly. 
    1718                          */ 
    1719                         else if (pf_result_index > 0) 
    1720                         { 
    1721                                 /* Get next step */ 
    1722                                 y = p_ptr->py + ddy[pf_result[pf_result_index] - '0']; 
    1723                                 x = p_ptr->px + ddx[pf_result[pf_result_index] - '0']; 
    1724  
    1725                                 /* Known wall */ 
    1726                                 if ((cave_info[y][x] & (CAVE_MARK)) && !cave_floor_bold(y, x)) 
    1727                                 { 
    1728                                         disturb(0,0); 
    1729                                         p_ptr->running_withpathfind = FALSE; 
    1730                                         return; 
    1731                                 } 
    1732  
    1733                                 /* Get step after */ 
    1734                                 y = y + ddy[pf_result[pf_result_index-1] - '0']; 
    1735                                 x = x + ddx[pf_result[pf_result_index-1] - '0']; 
    1736  
    1737                                 /* Known wall */ 
    1738                                 if ((cave_info[y][x] & (CAVE_MARK)) && !cave_floor_bold(y, x)) 
    1739                                 { 
    1740                                         p_ptr->running_withpathfind = FALSE; 
    1741  
    1742                                         run_init(pf_result[pf_result_index] - '0'); 
    1743                                 } 
    1744                         } 
    1745  
    1746                         p_ptr->run_cur_dir = pf_result[pf_result_index--] - '0'; 
    1747  
    1748                         /* Hack -- allow easy_alter */ 
    1749                         p_ptr->command_dir = p_ptr->run_cur_dir; 
    1750                 } 
    1751         } 
    1752  
    1753  
    1754         /* Decrease counter */ 
    1755         p_ptr->running--; 
    1756  
    1757         /* Take time */ 
    1758         p_ptr->energy_use = 100; 
    1759  
    1760         /* Move the player.  Never pick up objects */ 
    1761         p_ptr->auto_pickup_okay = FALSE; 
    1762         move_player(p_ptr->run_cur_dir); 
    1763 } 
  • trunk/src/cmd2.c

    r457 r465  
    19971997 * Determine if a given grid may be "walked" 
    19981998 */ 
    1999 bool do_cmd_walk_test(int y, int x) 
     1999static bool do_cmd_walk_test(int y, int x) 
    20002000{ 
    20012001        /* Hack -- walking obtains knowledge XXX XXX */ 
  • trunk/src/externs.h

    r463 r465  
    305305extern void hit_trap(int y, int x); 
    306306extern void move_player(int dir); 
    307 extern void run_step(int dir); 
    308 bool do_cmd_walk_test(int y, int x); 
    309307 
    310308/* dungeon.c */ 
     
    479477extern void get_grid_using_angle(int angle, int y0, int x0, 
    480478        int *ty, int *tx); 
     479extern void run_step(int dir); 
    481480 
    482481/* randart.c */ 
  • trunk/src/pathfind.c

    r224 r465  
    11/* 
    22 * File: pathfind.c 
    3  * Purpose: Pathfinding algorithm 
    4  * 
    5  * Copyright (c) 2004 Christophe Cavalaria, Leon Marrick 
     3 * Purpose: Pathfinding and running code. 
     4 * 
     5 * Copyright (c) 1988 Christopher J Stuart (running code) 
     6 * Copyright (c) 2004-2007 Christophe Cavalaria, Leon Marrick (pathfinding) 
    67 * 
    78 * This work is free software; you can redistribute it and/or modify it 
     
    1920 
    2021 
    21 /*** Constants ***/ 
     22/****** Pathfinding code ******/ 
    2223 
    2324/* Maximum size around the player to consider in the pathfinder */ 
     
    2728#define MAX_PF_LENGTH 250 
    2829 
    29  
    30 /*** Globals ***/ 
    3130 
    3231static int terrain[MAX_PF_RADIUS][MAX_PF_RADIUS]; 
     
    3736 
    3837 
    39 /*** Pathfinding code ***/ 
    4038 
    4139static bool is_valid_pf(int y, int x) 
     
    400398} 
    401399 
     400 
     401/****** Running code ******/ 
     402 
     403/* 
     404 * Basically, once you start running, you keep moving until something 
     405 * interesting happens.  In an enclosed space, you run straight, but 
     406 * you follow corners as needed (i.e. hallways).  In an open space, 
     407 * you run straight, but you stop before entering an enclosed space 
     408 * (i.e. a room with a doorway).  In a semi-open space (with walls on 
     409 * one side only), you run straight, but you stop before entering an 
     410 * enclosed space or an open space (i.e. running along side a wall). 
     411 * 
     412 * All discussions below refer to what the player can see, that is, 
     413 * an unknown wall is just like a normal floor.  This means that we 
     414 * must be careful when dealing with "illegal" grids. 
     415 * 
     416 * No assumptions are made about the layout of the dungeon, so this 
     417 * algorithm works in hallways, rooms, town, destroyed areas, etc. 
     418 * 
     419 * In the diagrams below, the player has just arrived in the grid 
     420 * marked as '@', and he has just come from a grid marked as 'o', 
     421 * and he is about to enter the grid marked as 'x'. 
     422 * 
     423 * Running while confused is not allowed, and so running into a wall 
     424 * is only possible when the wall is not seen by the player.  This 
     425 * will take a turn and stop the running. 
     426 * 
     427 * Several conditions are tracked by the running variables. 
     428 * 
     429 *   p_ptr->run_open_area (in the open on at least one side) 
     430 *   p_ptr->run_break_left (wall on the left, stop if it opens) 
     431 *   p_ptr->run_break_right (wall on the right, stop if it opens) 
     432 * 
     433 * When running begins, these conditions are initialized by examining 
     434 * the grids adjacent to the requested destination grid (marked 'x'), 
     435 * two on each side (marked 'L' and 'R').  If either one of the two 
     436 * grids on a given side is a wall, then that side is considered to 
     437 * be "closed".  Both sides enclosed yields a hallway. 
     438 * 
     439 *    LL                     @L 
     440 *    @x      (normal)       RxL   (diagonal) 
     441 *    RR      (east)          R    (south-east) 
     442 * 
     443 * In the diagram below, in which the player is running east along a 
     444 * hallway, he will stop as indicated before attempting to enter the 
     445 * intersection (marked 'x').  Starting a new run in any direction 
     446 * will begin a new hallway run. 
     447 * 
     448 * #.# 
     449 * ##.## 
     450 * o@x.. 
     451 * ##.## 
     452 * #.# 
     453 * 
     454 * Note that a minor hack is inserted to make the angled corridor 
     455 * entry (with one side blocked near and the other side blocked 
     456 * further away from the runner) work correctly. The runner moves 
     457 * diagonally, but then saves the previous direction as being 
     458 * straight into the gap. Otherwise, the tail end of the other 
     459 * entry would be perceived as an alternative on the next move. 
     460 * 
     461 * In the diagram below, the player is running east down a hallway, 
     462 * and will stop in the grid (marked '1') before the intersection. 
     463 * Continuing the run to the south-east would result in a long run 
     464 * stopping at the end of the hallway (marked '2'). 
     465 * 
     466 * ################## 
     467 * o@x       1 
     468 * ########### ###### 
     469 * #2          # 
     470 * ############# 
     471 * 
     472 * After each step, the surroundings are examined to determine if 
     473 * the running should stop, and to determine if the running should 
     474 * change direction.  We examine the new current player location 
     475 * (at which the runner has just arrived) and the direction from 
     476 * which the runner is considered to have come. 
     477 * 
     478 * Moving one grid in some direction places you adjacent to three 
     479 * or five new grids (for straight and diagonal moves respectively) 
     480 * to which you were not previously adjacent (marked as '!'). 
     481 * 
     482 *   ...!              ... 
     483 *   .o@!  (normal)    .o.!  (diagonal) 
     484 *   ...!  (east)      ..@!  (south east) 
     485 *                      !!! 
     486 * 
     487 * If any of the newly adjacent grids are "interesting" (monsters, 
     488 * objects, some terrain features) then running stops. 
     489 * 
     490 * If any of the newly adjacent grids seem to be open, and you are 
     491 * looking for a break on that side, then running stops. 
     492 * 
     493 * If any of the newly adjacent grids do not seem to be open, and 
     494 * you are in an open area, and the non-open side was previously 
     495 * entirely open, then running stops. 
     496 * 
     497 * If you are in a hallway, then the algorithm must determine if 
     498 * the running should continue, turn, or stop.  If only one of the 
     499 * newly adjacent grids appears to be open, then running continues 
     500 * in that direction, turning if necessary.  If there are more than 
     501 * two possible choices, then running stops.  If there are exactly 
     502 * two possible choices, separated by a grid which does not seem 
     503 * to be open, then running stops.  Otherwise, as shown below, the 
     504 * player has probably reached a "corner". 
     505 * 
     506 *    ###             o## 
     507 *    o@x  (normal)   #@!   (diagonal) 
     508 *    ##!  (east)     ##x   (south east) 
     509 * 
     510 * In this situation, there will be two newly adjacent open grids, 
     511 * one touching the player on a diagonal, and one directly adjacent. 
     512 * We must consider the two "option" grids further out (marked '?'). 
     513 * We assign "option" to the straight-on grid, and "option2" to the 
     514 * diagonal grid.  For some unknown reason, we assign "check_dir" to 
     515 * the grid marked 's', which may be incorrectly labelled. 
     516 * 
     517 *    ###s 
     518 *    o@x?   (may be incorrect diagram!) 
     519 *    ##!? 
     520 * 
     521 * If both "option" grids are closed, then there is no reason to enter 
     522 * the corner, and so we can cut the corner, by moving into the other 
     523 * grid (diagonally).  If we choose not to cut the corner, then we may 
     524 * go straight, but we pretend that we got there by moving diagonally. 
     525 * Below, we avoid the obvious grid (marked 'x') and cut the corner 
     526 * instead (marked 'n'). 
     527 * 
     528 *    ###:               o## 
     529 *    o@x#   (normal)    #@n    (maybe?) 
     530 *    ##n#   (east)      ##x# 
     531 *                       #### 
     532 * 
     533 * If one of the "option" grids is open, then we may have a choice, so 
     534 * we check to see whether it is a potential corner or an intersection 
     535 * (or room entrance).  If the grid two spaces straight ahead, and the 
     536 * space marked with 's' are both open, then it is a potential corner 
     537 * and we enter it if requested.  Otherwise, we stop, because it is 
     538 * not a