Wing Commander II
Reconstructed Win32 source (1996)
Loading...
Searching...
No Matches
fields.c
Go to the documentation of this file.
1/*
2 * Asteroid and mine hazard fields.
3 *
4 * Retail object 0x417610-0x41876F (link order; see docs/ORDER.md).
5 */
6#include "game.h"
7
8short g_nHazardReferenceSpeed = 0; /* 0x00492e58 */
9short g_nActiveHazards = 0; /* 0x00492e5c */
10
11/* The cockpit layout packs the hazard pitch range into the two bytes of
12 * field_f7: the low byte is the minimum, the high byte the maximum. */
13#define g_acHazardPitchRange \
14 ((const signed char *)&g_nHazardPitchRange)
15
16void make_shard(short asteroid, FixedVector direction);
17void init_hazard(short obj, FixedVector position, short moving);
18short try_far_spot(FixedVector *spot, short *moving);
19void manage_hazard(short obj, short slot);
20void extra_hazard(short obj);
21void add_hazard_field(short type, FixedVector center, short radius,
22 short density);
23
24/* Function start: 0x417610 */
25short easy2see(short obj)
26{
27 short bounds[4];
28 short x;
29 short y;
30
31 if (g_asObjectScreenX[obj] == (short)0x8001) {
32 return 0;
33 } else {
35 y = (short)(g_asObjectScreenY[obj] + g_37_nViewCenterY);
41 g_asObjectFlip[obj], bounds);
42 }
43}
44
45/* Function start: 0x4176D2 */
46void make_shard(short asteroid, FixedVector direction)
47{
48 short fragment;
49
50 fragment = find_vacant_3d_object();
51 if (fragment != -1) {
52 set_objects_data(fragment, OBJECT_DATA_ROCK_CHUNK, asteroid, 0);
53 g_asObjectCounter[fragment] = 40;
54 g_acObjectOwner[fragment] = (signed char)asteroid;
56 (unsigned int *)&direction,
57 (short)(g_asObjectCollisionRadius[asteroid] >> 1));
58 AddFixedVectors(&g_aShipPosition[asteroid], &direction,
59 &g_aShipPosition[fragment]);
60 g_aShipForwardVector[fragment] = direction;
61 fix_objects_ijk(fragment);
62 alter_yaw(signed_random(20), fragment);
63 alter_pitch(signed_random(20), fragment);
64 g_aShipVelocity[fragment] =
65 g_aShipForwardVector[fragment];
67 (unsigned int *)&g_aShipVelocity[fragment],
68 (short)(real_velocity(asteroid) + RandomInRange(0, 5)));
70 }
71}
72
73/* Function start: 0x417838 */
74void remove_hazard(signed char hazard)
75{
76 remove_object((short)hazard);
78 MaxShort(0, (short)(g_nActiveHazards - 1));
79 RecordCannedSceneObjectEvent((short)hazard, 1);
80}
81
82/* Function start: 0x41787A */
84{
85 short slot;
86
87 for (slot = 0; slot < 20; slot++) {
88 if (g_abHazardObjects[slot] != -1) {
90 g_abHazardObjects[slot] = -1;
91 }
92 }
94}
95
96#pragma function(abs)
97/* Function start: 0x4178E5 */
98short difficulty(void)
99{
100 return (short)(abs(25 - (int)g_nHazardReferenceSpeed) * 2);
101}
102
103/* Function start: 0x417916 */
105{
106 return MinShort(20, (short)(RandomBelowOrEqual(7) + 10));
107}
108
109/* Function start: 0x417941 */
110void skew_randomly(short obj, short allowReverse)
111{
112 FixedVector saved;
113
114 if (RandomBelow(100) < 50) {
115 saved = g_aShipRightVector[obj];
116 g_aShipRightVector[obj] =
119 g_aShipUpVector[obj];
120 g_aShipUpVector[obj] = saved;
121 } else {
122 saved = g_aShipUpVector[obj];
123 g_aShipUpVector[obj] =
127 g_aShipRightVector[obj] = saved;
128 }
129 if (allowReverse != 0 && RandomBelow(100) < 50)
131}
132
133/* Function start: 0x417AD7 */
134void align(int *value, short quantum)
135{
136 *value -= *value % quantum;
137}
138
139/* Function start: 0x417AF9 */
140void init_hazard(short obj, FixedVector position, short moving)
141{
142 short hazardType;
143 FixedVector aimPoint;
144 short moves;
145 short travelTime;
146 short velocity;
147
148 moves = moving;
151 hazardType = (short)(OBJECT_DATA_ASTEROID1 +
153 } else {
154 hazardType = OBJECT_DATA_SPACE_MINE;
155 }
156 set_objects_data(obj, hazardType, -1, 0);
157 g_aShipPosition[obj] = position;
158
159 if (hazardType == OBJECT_DATA_SPACE_MINE) {
160 moves = 0;
161 point_at(obj, g_aShipPosition[0]);
162 skew_randomly(obj, 1);
163 velocity = 2;
164 moves = (short)(velocity == 0);
165 } else if (moves != 0) {
166 travelTime = (short)(RandomBelowOrEqual(15) +
169 travelTime = MaxShort(
170 45, (short)(travelTime -
172 } else {
173 travelTime = MaxShort(
174 7, (short)(travelTime -
176 }
178 (int)travelTime << 8, &aimPoint);
179 AddFixedVectors(&g_aShipPosition[0], &aimPoint, &aimPoint);
180 point_at(obj, aimPoint);
181 velocity = (short)(distance_between_points(
182 &aimPoint, &g_aShipPosition[obj]) /
183 MaxShort(3, (short)(travelTime - RandomBelow(5))));
184 } else {
186 skew_randomly(obj, 1);
187 if (RandomBelow(100) < 20)
188 velocity = 0;
189 else
190 velocity = asteroid_velocity();
191 }
192 if (kilrathi_near(0, 16000) != 0)
193 velocity = 0;
195 (int)velocity << 8, &g_aShipVelocity[obj]);
196
197 if (moves == 0) {
198 int separation;
199
200 if (hazardType == OBJECT_DATA_ASTEROID_FIELD)
201 separation = 1500;
202 else
203 separation = RandomBelowOrEqual(1000) << 8;
205 separation, &aimPoint);
206 SubtractFixedVectors(&g_aShipPosition[obj], &aimPoint,
207 &g_aShipPosition[obj]);
208 }
209 if (hazardType == OBJECT_DATA_SPACE_MINE) {
210 align(&g_aShipPosition[obj].x, 200);
211 align(&g_aShipPosition[obj].y, 200);
212 align(&g_aShipPosition[obj].z, 200);
213 }
215 g_asObjectCounter[obj] = 0;
217}
218
219/* Function start: 0x417EA4 */
220short near_field(const HazardField *field, const FixedVector *point)
221{
222 return IsPointWithinRange((FixedVector *)&field->center,
223 (FixedVector *)point,
224 (short)(field->innerRadius + 4300));
225}
226
227/* Function start: 0x417ED4 */
228short within_field(const HazardField *field, const FixedVector *point)
229{
230 return IsPointWithinRange((FixedVector *)&field->center,
231 (FixedVector *)point, field->innerRadius);
232}
233
234/* Function start: 0x417EFF */
235short try_far_spot(FixedVector *spot, short *moving)
236{
237 short yawDelta;
238 short pitchDelta;
239 short usable;
240
244 pitchDelta = signed_random(20);
245 yawDelta = signed_random(35);
246 if (g_nCurrentView == 0) {
247 if (g_acHazardPitchRange[0] < pitchDelta &&
248 g_acHazardPitchRange[1] > pitchDelta &&
249 abs(yawDelta) < 19 &&
250 RandomBelow(100) < 60)
251 *moving = 1;
252 else
253 *moving = 0;
254 } else {
255 if (abs(pitchDelta) > 5 && abs(pitchDelta) < 20 &&
256 abs(yawDelta) > 5 && abs(yawDelta) < 20 && RandomBelow(100) < 30)
257 *moving = 1;
258 else
259 *moving = 0;
260 }
261 pitchDelta = (short)(pitchDelta + find_ratio(
262 -15, 15, g_anObjectPitchRotation[0], -150, 150));
263 yawDelta = (short)(yawDelta + find_ratio(
264 -15, 15, g_anObjectYawRotation[0], -150, 150));
265 rotate_about_j(yawDelta,
268 rotate_about_i(pitchDelta,
272 usable = !IsPointWithinRange(&g_aShipPosition[0], spot, 3000);
273 usable = usable != 0 &&
275 return usable;
276}
277
278/* Function start: 0x418175 */
279short rear_sphere(void)
280{
281 return find_ratio(0, 20, (short)g_nHazardReferenceSpeed,
282 4300, 3100);
283}
284
285/* Function start: 0x4181A2 */
286short ok_hazard_spot(short obj)
287{
288 int range;
289 short result;
290
291 if (g_asObjectScreenX[obj] == (short)0x8001)
292 range = rear_sphere();
293 else
294 range = 4300;
296 &g_aShipPosition[obj],
297 (short)range);
298 return result;
299}
300
301/* Function start: 0x41820B */
302short make_hazard(void)
303{
304 FixedVector spot;
305 short isMoving;
306 short obj = find_vacant_3d_object();
307
308 if (obj != -1 && try_far_spot(&spot, &isMoving) != 0) {
309 init_hazard(obj, spot, isMoving);
311 } else
312 obj = -1;
313 return obj;
314}
315
316/* Function start: 0x418288 */
317void extra_hazard(short obj)
318{
321}
322
323/* Function start: 0x4182B6 */
324void approach(short obj)
325{
326 FixedVector vector;
327
328 ScaleFixedVector(&g_aShipVelocity[0], 20 << 8, &vector);
329 AddFixedVectors(&g_aShipPosition[0], &vector, &vector);
330 point_at(obj, vector);
332 &vector);
333 AddFixedVectors(&g_aShipVelocity[obj], &vector,
334 &g_aShipVelocity[obj]);
335 if (g_nCannedSceneMode == 0)
337}
338
339/* Function start: 0x41836E */
340void manage_hazard(short obj, short slot)
341{
342 if (g_nRenderedSpaceFrame % 20 == slot) {
343 if (ok_hazard_spot(obj) == 0) {
344 remove_hazard((signed char)obj);
345 return;
346 }
348 g_asObjectScreenX[obj] != (short)0x8001 &&
349 (unsigned short)g_asObjectDistance[obj] > 1500 &&
350 real_velocity(obj) < 20)
351 approach(obj);
352 }
353}
354
355/* Function start: 0x418426 */
373
374/* Function start: 0x4184F6 */
376{
377 short freeSlot;
378 short slot;
379
380 freeSlot = -1;
381
384 else
386 for (slot = 0; slot < 20; slot++) {
387 if (g_abHazardObjects[slot] != -1)
388 manage_hazard((short)g_abHazardObjects[slot], slot);
389 else
390 freeSlot = slot;
391 }
392 if (freeSlot != -1 &&
393 RandomBelowOrEqual(215) <
394 (short)g_nHazardReferenceSpeed + 30)
395 g_abHazardObjects[freeSlot] = (signed char)make_hazard();
396}
397
398/* Function start: 0x4185CC */
399void start_hazard_field(short region)
400{
401 short slot;
402
403 slot = 0;
406 while (slot++ < 3)
407 g_abHazardObjects[slot] = (signed char)make_hazard();
408}
409
410/* Function start: 0x418626 */
411void add_hazard_field(short type, FixedVector center,
412 short radius, short density)
413{
414 HazardField *field;
415
416 if (g_nHazardFieldCount < 7) {
418 field->type = type;
419 field->center = center;
420 field->outerRadius = radius;
421 field->innerRadius = radius;
422 field->density = density;
424 }
425}
426
427/* Function start: 0x4186A4 */
429{
430 HazardField *field;
431 short region;
432
434 return;
435 if (g_pActiveHazardField == 0) {
436 field = g_aHazardFields;
437 for (region = 0; g_nHazardFieldCount > region;
438 region++, field++) {
439 if (field != g_pActiveHazardField &&
440 near_field(field, &g_aShipPosition[0]) != 0) {
441 start_hazard_field(region);
442 break;
443 }
444 }
446 &g_aShipPosition[0]) == 0) {
448 }
449}
#define g_acHazardPitchRange
Definition fields.c:13
void SetVectorFixedPoint(unsigned int *p, short v)
Definition geom.c:754
void remove_hazard(signed char hazard)
Definition fields.c:74
short kilrathi_near(short obj, short range)
Definition cockpt.c:395
void make_shard(short asteroid, FixedVector direction)
Definition fields.c:46
short MaxShort(short a, short b)
Definition disk.c:36
short distance_between_points(const FixedVector *from, const FixedVector *to)
Definition geom.c:528
void fix_objects_ijk(short obj)
Definition geom.c:481
void match_ship_to_eye(void)
Definition fields.c:356
void rotate_about_i(short angle, FixedVector *j, FixedVector *k)
Definition geom.c:393
short GetTransformedShapeBounds(Viewport *viewport, short x, short y, unsigned char *shape, short frame, short angle, short scale, short flip, short *bounds)
Definition gr.c:1518
void remove_object(short obj)
Definition geom.c:858
void align(int *value, short quantum)
Definition fields.c:134
void alter_pitch(short angle, short obj)
Definition geom.c:504
void add_hazard_field(short type, FixedVector center, short radius, short density)
Definition fields.c:411
void AddFixedVectors(const FixedVector *left, const FixedVector *right, FixedVector *sum)
Definition geom.c:211
short easy2see(short obj)
Definition fields.c:25
void position_relative_ijk(FixedVector *position, short obj, short right, short up, short forward)
Definition geom.c:112
void ScaleFixedVector(FixedVector *vector, int scale, FixedVector *result)
Definition geom.c:237
short MinShort(short a, short b)
Definition disk.c:27
short find_ratio(short inputMinimum, short inputMaximum, short input, short outputMinimum, short outputMaximum)
Definition logic.c:1013
short ok_hazard_spot(short obj)
Definition fields.c:286
void extra_hazard(short obj)
Definition fields.c:317
void copy_frame(short source, short destination)
Definition geom.c:470
short signed_random(short range)
Definition logic.c:19
void alter_yaw(short angle, short obj)
Definition geom.c:512
void init_hazard(short obj, FixedVector position, short moving)
Definition fields.c:140
void SubtractFixedVectors(FixedVector *left, FixedVector *right, FixedVector *difference)
Definition geom.c:220
short real_velocity(short obj)
Definition ship.c:705
void start_hazard_field(short region)
Definition fields.c:399
short within_field(const HazardField *field, const FixedVector *point)
Definition fields.c:228
void approach(short obj)
Definition fields.c:324
short RandomBelow(short n)
Definition eventmgr.c:12
short find_vacant_3d_object(void)
Definition geom.c:841
short near_field(const HazardField *field, const FixedVector *point)
Definition fields.c:220
short make_hazard(void)
Definition fields.c:302
void point_at(short obj, FixedVector point)
Definition geom.c:84
short difficulty(void)
Definition fields.c:98
void RecordCannedSceneObjectEvent(short obj, int event)
Definition taperec.c:176
short asteroid_velocity(void)
Definition fields.c:104
short try_far_spot(FixedVector *spot, short *moving)
Definition fields.c:235
short IsPointWithinRange(FixedVector *from, FixedVector *to, short range)
Definition geom.c:760
void manage_hazard(short obj, short slot)
Definition fields.c:340
short rear_sphere(void)
Definition fields.c:279
unsigned short RandomInRange(unsigned short lo, unsigned short hi)
Definition eventmgr.c:31
void set_objects_data(short obj, short type, short owner, short matchObjectClass)
Definition ship.c:347
void update_hazards(void)
Definition fields.c:375
void remove_all_hazards(void)
Definition fields.c:83
short RandomBelowOrEqual(short n)
Definition eventmgr.c:43
void skew_randomly(short obj, short allowReverse)
Definition fields.c:110
void check_hazards(void)
Definition fields.c:428
void negate_vector(FixedVector *vector)
Definition geom.c:203
void rotate_about_j(short angle, FixedVector *i, FixedVector *k)
Definition geom.c:413
Shared Win32 declarations, types and library interfaces.
@ OBJECT_DATA_ASTEROID_FIELD
Definition game_data.h:449
@ OBJECT_DATA_SPACE_MINE
Definition game_data.h:450
#define SCRATCH_VIEW_OBJECT
Definition game_data.h:1581
#define OBJECT_DATA_ROCK_CHUNK
Definition game_data.h:1622
#define EYE_OBJECT
Definition game_data.h:1580
#define OBJECT_DATA_PORCUPINE_MINE
Definition game_data.h:1615
#define OBJECT_DATA_ASTEROID1
Definition game_data.h:1616
@ OBJECT_CLASS_DUST
Definition game_data.h:41
@ OBJECT_CLASS_NULL
Definition game_data.h:37
short g_asObjectScreenAngle[SPACE_OBJECT_COUNT]
Definition viewrect.c:97
HazardField g_aHazardFields[8]
Definition viewrect.c:59
short g_nActiveHazards
Definition fields.c:9
HazardField * g_pActiveHazardField
Definition viewrect.c:60
short g_asObjectCollisionRadius[SPACE_OBJECT_COUNT]
Definition viewrect.c:120
unsigned char * g_apObjectShape[SPACE_OBJECT_COUNT]
Definition viewrect.c:100
short g_asObjectDistance[SPACE_OBJECT_COUNT]
Definition viewrect.c:104
signed char g_abHazardObjects[0x14]
Definition viewrect.c:62
int g_nCurrentView
Definition spc.c:11
short g_aeObjectClass[SPACE_OBJECT_COUNT]
Definition viewrect.c:125
short g_anObjectYawRotation[SPACE_OBJECT_COUNT]
Definition viewrect.c:118
short g_asObjectType[SPACE_OBJECT_COUNT]
Definition viewrect.c:124
short g_asObjectFlip[SPACE_OBJECT_COUNT]
Definition viewrect.c:102
short g_bUseEyePositionForHazards
Definition viewrect.c:61
FixedVector g_aShipForwardVector[SPACE_OBJECT_COUNT]
Definition viewrect.c:107
short g_asObjectScreenX[SPACE_OBJECT_COUNT]
Definition viewrect.c:95
short g_nHazardReferenceSpeed
Definition fields.c:8
FixedVector g_aShipRightVector[SPACE_OBJECT_COUNT]
Definition viewrect.c:105
signed char g_acObjectOwner[SPACE_OBJECT_COUNT]
Definition viewrect.c:122
short g_asObjectScreenScale[SPACE_OBJECT_COUNT]
Definition viewrect.c:103
short g_anObjectPitchRotation[SPACE_OBJECT_COUNT]
Definition viewrect.c:117
short g_nRenderedSpaceFrame
Definition viewrect.c:33
signed char g_acObjectCollisionGraceTicks[SPACE_OBJECT_COUNT]
Definition viewrect.c:114
short g_37_nViewCenterY
Definition eventmgr.c:2502
Viewport g_27_stViewScratchInfo
Definition cockpt.c:3841
FixedVector g_aShipPosition[SPACE_OBJECT_COUNT]
Definition viewrect.c:108
FixedVector g_aShipUpVector[SPACE_OBJECT_COUNT]
Definition viewrect.c:106
FixedVector g_aShipVelocity[SPACE_OBJECT_COUNT]
Definition viewrect.c:109
short g_15_nStoredScreenViewCentreX
Definition eventmgr.c:2501
signed char g_cHazardBaseTravelTime
Definition cockpt.c:26
short g_asObjectScreenY[SPACE_OBJECT_COUNT]
Definition viewrect.c:96
short g_asObjectCounter[SPACE_OBJECT_COUNT]
Definition viewrect.c:110
short g_nCannedSceneMode
Definition taperec.c:14
short g_asObjectViewFrame[SPACE_OBJECT_COUNT]
Definition viewrect.c:94
short g_nHazardFieldCount
Definition viewrect.c:58
short outerRadius
Definition game_data.h:1236
short innerRadius
Definition game_data.h:1235
FixedVector center
Definition game_data.h:1234
short density
Definition game_data.h:1237