1*da121b33Sdholland /* $NetBSD: help.c,v 1.13 2009/08/12 08:54:54 dholland Exp $ */
2887dd216Scgd
361f28255Scgd /*
4887dd216Scgd * Copyright (c) 1980, 1993
5887dd216Scgd * The Regents of the University of California. All rights reserved.
661f28255Scgd *
761f28255Scgd * Redistribution and use in source and binary forms, with or without
861f28255Scgd * modification, are permitted provided that the following conditions
961f28255Scgd * are met:
1061f28255Scgd * 1. Redistributions of source code must retain the above copyright
1161f28255Scgd * notice, this list of conditions and the following disclaimer.
1261f28255Scgd * 2. Redistributions in binary form must reproduce the above copyright
1361f28255Scgd * notice, this list of conditions and the following disclaimer in the
1461f28255Scgd * documentation and/or other materials provided with the distribution.
15e5aeb4eaSagc * 3. Neither the name of the University nor the names of its contributors
1661f28255Scgd * may be used to endorse or promote products derived from this software
1761f28255Scgd * without specific prior written permission.
1861f28255Scgd *
1961f28255Scgd * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
2061f28255Scgd * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
2161f28255Scgd * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
2261f28255Scgd * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
2361f28255Scgd * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
2461f28255Scgd * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
2561f28255Scgd * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
2661f28255Scgd * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
2761f28255Scgd * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
2861f28255Scgd * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
2961f28255Scgd * SUCH DAMAGE.
3061f28255Scgd */
3161f28255Scgd
32ef383c95Schristos #include <sys/cdefs.h>
3361f28255Scgd #ifndef lint
34887dd216Scgd #if 0
35887dd216Scgd static char sccsid[] = "@(#)help.c 8.1 (Berkeley) 5/31/93";
36887dd216Scgd #else
37*da121b33Sdholland __RCSID("$NetBSD: help.c,v 1.13 2009/08/12 08:54:54 dholland Exp $");
38887dd216Scgd #endif
3961f28255Scgd #endif /* not lint */
4061f28255Scgd
41ef383c95Schristos #include <stdio.h>
42ef383c95Schristos #include <math.h>
43ef383c95Schristos #include <unistd.h>
446fb30065Schristos #include <limits.h>
4561f28255Scgd #include "trek.h"
4661f28255Scgd
4761f28255Scgd /*
4861f28255Scgd ** call starbase for help
4961f28255Scgd **
5061f28255Scgd ** First, the closest starbase is selected. If there is a
5161f28255Scgd ** a starbase in your own quadrant, you are in good shape.
5261f28255Scgd ** This distance takes quadrant distances into account only.
5361f28255Scgd **
5461f28255Scgd ** A magic number is computed based on the distance which acts
5561f28255Scgd ** as the probability that you will be rematerialized. You
5661f28255Scgd ** get three tries.
5761f28255Scgd **
5861f28255Scgd ** When it is determined that you should be able to be remater-
5961f28255Scgd ** ialized (i.e., when the probability thing mentioned above
6061f28255Scgd ** comes up positive), you are put into that quadrant (anywhere).
6161f28255Scgd ** Then, we try to see if there is a spot adjacent to the star-
6261f28255Scgd ** base. If not, you can't be rematerialized!!! Otherwise,
6361f28255Scgd ** it drops you there. It only tries five times to find a spot
6461f28255Scgd ** to drop you. After that, it's your problem.
6561f28255Scgd */
6661f28255Scgd
67*da121b33Sdholland static const char *const Cntvect[3] = {
6850b862e2Sdholland "first", "second", "third"
6950b862e2Sdholland };
7061f28255Scgd
71ef383c95Schristos /*ARGSUSED*/
72ef383c95Schristos void
help(int v __unused)73bf0917b6Sdholland help(int v __unused)
7461f28255Scgd {
75ef383c95Schristos int i;
7661f28255Scgd double dist, x;
77ef383c95Schristos int dx = 0, dy = 0;
78ef383c95Schristos int j, l = 0;
7961f28255Scgd
8061f28255Scgd /* check to see if calling for help is reasonable ... */
81ef383c95Schristos if (Ship.cond == DOCKED) {
82ef383c95Schristos printf("Uhura: But Captain, we're already docked\n");
83ef383c95Schristos return;
84ef383c95Schristos }
8561f28255Scgd
8661f28255Scgd /* or possible */
87ef383c95Schristos if (damaged(SSRADIO)) {
88ef383c95Schristos out(SSRADIO);
89ef383c95Schristos return;
90ef383c95Schristos }
91ef383c95Schristos if (Now.bases <= 0) {
92ef383c95Schristos printf("Uhura: I'm not getting any response from starbase\n");
93ef383c95Schristos return;
94ef383c95Schristos }
9561f28255Scgd
9661f28255Scgd /* tut tut, there goes the score */
9761f28255Scgd Game.helps += 1;
9861f28255Scgd
9961f28255Scgd /* find the closest base */
1006fb30065Schristos dist = TOOLARGE;
10150b862e2Sdholland if (Quad[Ship.quadx][Ship.quady].bases <= 0) {
10261f28255Scgd /* there isn't one in this quadrant */
10350b862e2Sdholland for (i = 0; i < Now.bases; i++) {
10461f28255Scgd /* compute distance */
10561f28255Scgd dx = Now.base[i].x - Ship.quadx;
10661f28255Scgd dy = Now.base[i].y - Ship.quady;
10761f28255Scgd x = dx * dx + dy * dy;
10861f28255Scgd x = sqrt(x);
10961f28255Scgd
11061f28255Scgd /* see if better than what we already have */
11150b862e2Sdholland if (x < dist) {
11261f28255Scgd dist = x;
11361f28255Scgd l = i;
11461f28255Scgd }
11561f28255Scgd }
11661f28255Scgd
11761f28255Scgd /* go to that quadrant */
11861f28255Scgd Ship.quadx = Now.base[l].x;
11961f28255Scgd Ship.quady = Now.base[l].y;
12061f28255Scgd initquad(1);
12150b862e2Sdholland } else {
12261f28255Scgd dist = 0.0;
12361f28255Scgd }
12461f28255Scgd
12561f28255Scgd /* dematerialize the Enterprise */
12661f28255Scgd Sect[Ship.sectx][Ship.secty] = EMPTY;
12761f28255Scgd printf("Starbase in %d,%d responds\n", Ship.quadx, Ship.quady);
12861f28255Scgd
12961f28255Scgd /* this next thing acts as a probability that it will work */
13061f28255Scgd x = pow(1.0 - pow(0.94, dist), 0.3333333);
13161f28255Scgd
13261f28255Scgd /* attempt to rematerialize */
13350b862e2Sdholland for (i = 0; i < 3; i++) {
13461f28255Scgd sleep(2);
13561f28255Scgd printf("%s attempt to rematerialize ", Cntvect[i]);
13650b862e2Sdholland if (franf() > x) {
13761f28255Scgd /* ok, that's good. let's see if we can set her down */
13850b862e2Sdholland for (j = 0; j < 5; j++) {
13961f28255Scgd dx = Etc.starbase.x + ranf(3) - 1;
14061f28255Scgd if (dx < 0 || dx >= NSECTS)
14161f28255Scgd continue;
14261f28255Scgd dy = Etc.starbase.y + ranf(3) - 1;
14361357867Sdholland if (dy < 0 || dy >= NSECTS ||
14461357867Sdholland Sect[dx][dy] != EMPTY)
14561f28255Scgd continue;
14661f28255Scgd break;
14761f28255Scgd }
14850b862e2Sdholland if (j < 5) {
14961f28255Scgd /* found an empty spot */
15061f28255Scgd printf("succeeds\n");
15161f28255Scgd Ship.sectx = dx;
15261f28255Scgd Ship.secty = dy;
15361f28255Scgd Sect[dx][dy] = Ship.ship;
154ef383c95Schristos dock(0);
15561f28255Scgd compkldist(0);
15661f28255Scgd return;
15761f28255Scgd }
15861f28255Scgd /* the starbase must have been surrounded */
15961f28255Scgd }
16061f28255Scgd printf("fails\n");
16161f28255Scgd }
16261f28255Scgd
16361f28255Scgd /* one, two, three strikes, you're out */
16461f28255Scgd lose(L_NOHELP);
16561f28255Scgd }
166