xref: /original-bsd/games/trek/klmove.c (revision 65ba69af)
1 /*
2  * Copyright (c) 1980 Regents of the University of California.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms are permitted
6  * provided that the above copyright notice and this paragraph are
7  * duplicated in all such forms and that any documentation,
8  * advertising materials, and other materials related to such
9  * distribution and use acknowledge that the software was developed
10  * by the University of California, Berkeley.  The name of the
11  * University may not be used to endorse or promote products derived
12  * from this software without specific prior written permission.
13  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
14  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
15  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
16  */
17 
18 #ifndef lint
19 static char sccsid[] = "@(#)klmove.c	5.3 (Berkeley) 06/18/88";
20 #endif /* not lint */
21 
22 # include	"trek.h"
23 
24 /*
25 **  Move Klingons Around
26 **
27 **	This is a largely incomprehensible block of code that moves
28 **	Klingons around in a quadrant.  It was written in a very
29 **	"program as you go" fashion, and is a prime candidate for
30 **	rewriting.
31 **
32 **	The flag `fl' is zero before an attack, one after an attack,
33 **	and two if you are leaving a quadrant.  This serves to
34 **	change the probability and distance that it moves.
35 **
36 **	Basically, what it will try to do is to move a certain number
37 **	of steps either toward you or away from you.  It will avoid
38 **	stars whenever possible.  Nextx and nexty are the next
39 **	sector to move to on a per-Klingon basis; they are roughly
40 **	equivalent to Ship.sectx and Ship.secty for the starship.  Lookx and
41 **	looky are the sector that you are going to look at to see
42 **	if you can move their.  Dx and dy are the increment.  Fudgex
43 **	and fudgey are the things you change around to change your
44 **	course around stars.
45 */
46 
47 klmove(fl)
48 int	fl;
49 {
50 	int			n;
51 	register struct kling	*k;
52 	double			dx, dy;
53 	int			nextx, nexty;
54 	register int		lookx, looky;
55 	int			motion;
56 	int			fudgex, fudgey;
57 	int			qx, qy;
58 	double			bigger;
59 	int			i;
60 
61 #	ifdef xTRACE
62 	if (Trace)
63 		printf("klmove: fl = %d, Etc.nkling = %d\n", fl, Etc.nkling);
64 #	endif
65 	for (n = 0; n < Etc.nkling; k && n++)
66 	{
67 		k = &Etc.klingon[n];
68 		i = 100;
69 		if (fl)
70 			i = 100.0 * k->power / Param.klingpwr;
71 		if (ranf(i) >= Param.moveprob[2 * Move.newquad + fl])
72 			continue;
73 		/* compute distance to move */
74 		motion = ranf(75) - 25;
75 		motion *= k->avgdist * Param.movefac[2 * Move.newquad + fl];
76 		/* compute direction */
77 		dx = Ship.sectx - k->x + ranf(3) - 1;
78 		dy = Ship.secty - k->y + ranf(3) - 1;
79 		bigger = dx;
80 		if (dy > bigger)
81 			bigger = dy;
82 		if (bigger == 0.0)
83 			bigger = 1.0;
84 		dx = dx / bigger + 0.5;
85 		dy = dy / bigger + 0.5;
86 		if (motion < 0)
87 		{
88 			motion = -motion;
89 			dx = -dx;
90 			dy = -dy;
91 		}
92 		fudgex = fudgey = 1;
93 		/* try to move the klingon */
94 		nextx = k->x;
95 		nexty = k->y;
96 		for (; motion > 0; motion--)
97 		{
98 			lookx = nextx + dx;
99 			looky = nexty + dy;
100 			if (lookx < 0 || lookx >= NSECTS || looky < 0 || looky >= NSECTS)
101 			{
102 				/* new quadrant */
103 				qx = Ship.quadx;
104 				qy = Ship.quady;
105 				if (lookx < 0)
106 					qx -= 1;
107 				else
108 					if (lookx >= NSECTS)
109 						qx += 1;
110 				if (looky < 0)
111 					qy -= 1;
112 				else
113 					if (looky >= NSECTS)
114 						qy += 1;
115 				if (qx < 0 || qx >= NQUADS || qy < 0 || qy >= NQUADS ||
116 						Quad[qx][qy].stars < 0 || Quad[qx][qy].klings > MAXKLQUAD - 1)
117 					break;
118 				if (!damaged(SRSCAN))
119 				{
120 					printf("Klingon at %d,%d escapes to quadrant %d,%d\n",
121 						k->x, k->y, qx, qy);
122 					motion = Quad[qx][qy].scanned;
123 					if (motion >= 0 && motion < 1000)
124 						Quad[qx][qy].scanned += 100;
125 					motion = Quad[Ship.quadx][Ship.quady].scanned;
126 					if (motion >= 0 && motion < 1000)
127 						Quad[Ship.quadx][Ship.quady].scanned -= 100;
128 				}
129 				Sect[k->x][k->y] = EMPTY;
130 				Quad[qx][qy].klings += 1;
131 				Etc.nkling -= 1;
132 				bmove(&Etc.klingon[Etc.nkling], k, sizeof *k);
133 				Quad[Ship.quadx][Ship.quady].klings -= 1;
134 				k = 0;
135 				break;
136 			}
137 			if (Sect[lookx][looky] != EMPTY)
138 			{
139 				lookx = nextx + fudgex;
140 				if (lookx < 0 || lookx >= NSECTS)
141 					lookx = nextx + dx;
142 				if (Sect[lookx][looky] != EMPTY)
143 				{
144 					fudgex = -fudgex;
145 					looky = nexty + fudgey;
146 					if (looky < 0 || looky >= NSECTS || Sect[lookx][looky] != EMPTY)
147 					{
148 						fudgey = -fudgey;
149 						break;
150 					}
151 				}
152 			}
153 			nextx = lookx;
154 			nexty = looky;
155 		}
156 		if (k && (k->x != nextx || k->y != nexty))
157 		{
158 			if (!damaged(SRSCAN))
159 				printf("Klingon at %d,%d moves to %d,%d\n",
160 					k->x, k->y, nextx, nexty);
161 			Sect[k->x][k->y] = EMPTY;
162 			Sect[k->x = nextx][k->y = nexty] = KLINGON;
163 		}
164 	}
165 	compkldist(0);
166 }
167