Oil spills (#171)
* Simplify FindFacesInBox * Simplify FindFacesInBox * Simplify ActorBoxPick * Implement oil spills * Simplify DRScenePick2D
This commit is contained in:
parent
6061fd1d5f
commit
31afabce90
|
|
@ -4,6 +4,7 @@
|
|||
#include "car.h"
|
||||
#include "globvars.h"
|
||||
#include "harness/trace.h"
|
||||
#include "raycast.h"
|
||||
#include "world.h"
|
||||
#include <math.h>
|
||||
#include <stdlib.h>
|
||||
|
|
@ -419,12 +420,13 @@ void CheckSingleFace(tFace_ref* pFace, br_vector3* ray_pos, br_vector3* ray_dir,
|
|||
|
||||
this_material = pFace->material;
|
||||
*rt = 100.0;
|
||||
|
||||
d = pFace->normal.v[1] * ray_dir->v[1] + ray_dir->v[2] * pFace->normal.v[2] + ray_dir->v[0] * pFace->normal.v[0];
|
||||
if ((!this_material || (this_material->flags & 0x1800) != 0 || d <= 0.0)
|
||||
if ((this_material == NULL || (this_material->flags & (BR_MATF_TWO_SIDED | BR_MATF_ALWAYS_VISIBLE )) != 0 || d <= 0.0)
|
||||
&& (!this_material || !this_material->identifier || *this_material->identifier != '!' || !gPling_materials)
|
||||
&& fabs(d) >= 0.00000023841858) {
|
||||
BrVector3Sub(&p, ray_pos, &pFace->v[0]);
|
||||
numerator = pFace->normal.v[1] * p.v[1] + pFace->normal.v[2] * p.v[2] + pFace->normal.v[0] * p.v[0];
|
||||
numerator = BrVector3Dot(&pFace->normal, &p);
|
||||
if (!BadDiv__finteray(numerator, d)) {
|
||||
if (d > 0.0) {
|
||||
if (-numerator < -0.001 || -numerator > d + 0.003) {
|
||||
|
|
@ -437,12 +439,8 @@ void CheckSingleFace(tFace_ref* pFace, br_vector3* ray_pos, br_vector3* ray_dir,
|
|||
if (t > 1.0) {
|
||||
t = 1.0;
|
||||
}
|
||||
tv.v[0] = ray_dir->v[0] * t;
|
||||
tv.v[1] = ray_dir->v[1] * t;
|
||||
tv.v[2] = ray_dir->v[2] * t;
|
||||
tv.v[0] = ray_pos->v[0] + tv.v[0];
|
||||
tv.v[1] = ray_pos->v[1] + tv.v[1];
|
||||
tv.v[2] = ray_pos->v[2] + tv.v[2];
|
||||
BrVector3Scale(&tv, ray_dir, t);
|
||||
BrVector3Accumulate(&tv, ray_pos);
|
||||
axis_m = fabs(pFace->normal.v[0]) < fabs(pFace->normal.v[1]);
|
||||
if (fabs(pFace->normal.v[2]) > fabs(pFace->normal.v[axis_m])) {
|
||||
axis_m = 2;
|
||||
|
|
@ -481,9 +479,7 @@ void CheckSingleFace(tFace_ref* pFace, br_vector3* ray_pos, br_vector3* ray_dir,
|
|||
*rt = t;
|
||||
*normal = pFace->normal;
|
||||
if (d > 0.0) {
|
||||
normal->v[0] = -normal->v[0];
|
||||
normal->v[1] = -normal->v[1];
|
||||
normal->v[2] = -normal->v[2];
|
||||
BrVector3Negate(normal, normal);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -663,61 +659,53 @@ int FindFacesInBox(tBounds* bnds, tFace_ref* face_list, int max_face) {
|
|||
|
||||
j = 0;
|
||||
track_spec = &gProgram_state.track_spec;
|
||||
a.v[0] = bnds->original_bounds.min.v[0] + bnds->original_bounds.max.v[0];
|
||||
a.v[1] = bnds->original_bounds.min.v[1] + bnds->original_bounds.max.v[1];
|
||||
a.v[2] = bnds->original_bounds.min.v[2] + bnds->original_bounds.max.v[2];
|
||||
b.v[0] = a.v[0] * 0.5;
|
||||
b.v[1] = a.v[1] * 0.5;
|
||||
b.v[2] = a.v[2] * 0.5;
|
||||
BrMatrix34ApplyP(&bnds->box_centre, &b, bnds->mat);
|
||||
b.v[0] = bnds->original_bounds.max.v[0] - bnds->original_bounds.min.v[0];
|
||||
b.v[1] = bnds->original_bounds.max.v[1] - bnds->original_bounds.min.v[1];
|
||||
b.v[2] = bnds->original_bounds.max.v[2] - bnds->original_bounds.min.v[2];
|
||||
bnds->radius = sqrt(b.v[1] * b.v[1] + b.v[2] * b.v[2] + b.v[0] * b.v[0]) / 2.0;
|
||||
BrVector3Add(&a, &bnds->original_bounds.min, &bnds->original_bounds.max);
|
||||
BrVector3Scale(&a, &a, 0.5f);
|
||||
BrMatrix34ApplyP(&bnds->box_centre, &a, bnds->mat);
|
||||
BrVector3Sub(&b, &bnds->original_bounds.max, &bnds->original_bounds.min);
|
||||
bnds->radius = BrVector3Length(&b) / 2.f;
|
||||
BrMatrix34ApplyP(&bnds->real_bounds.min, &bnds->original_bounds.min, bnds->mat);
|
||||
bnds->real_bounds.max = bnds->real_bounds.min;
|
||||
BrVector3Copy(&bnds->real_bounds.max, &bnds->real_bounds.min);
|
||||
for (i = 0; i < 3; ++i) {
|
||||
c[i].v[0] = bnds->mat->m[i][0] * b.v[i];
|
||||
c[i].v[1] = bnds->mat->m[i][1] * b.v[i];
|
||||
c[i].v[2] = bnds->mat->m[i][2] * b.v[i];
|
||||
}
|
||||
for (i = 0; i < 3; ++i) {
|
||||
bnds->real_bounds.min.v[i] = (double)(c[2].v[i] < 0.0) * c[2].v[i]
|
||||
+ (double)(c[1].v[i] < 0.0) * c[1].v[i]
|
||||
+ (double)(c[0].v[i] < 0.0) * c[0].v[i]
|
||||
+ bnds->real_bounds.min.v[i];
|
||||
bnds->real_bounds.max.v[i] = (double)(c[2].v[i] > 0.0) * c[2].v[i]
|
||||
+ (double)(c[1].v[i] > 0.0) * c[1].v[i]
|
||||
+ (double)(c[0].v[i] > 0.0) * c[0].v[i]
|
||||
+ bnds->real_bounds.max.v[i];
|
||||
bnds->real_bounds.min.v[i] += MIN(c[0].v[i], 0.f)
|
||||
+ MIN(c[1].v[i], 0.f)
|
||||
+ MIN(c[2].v[i], 0.f);
|
||||
bnds->real_bounds.max.v[i] += MAX(c[0].v[i], 0.f)
|
||||
+ MAX(c[1].v[i], 0.f)
|
||||
+ MAX(c[2].v[i], 0.f);
|
||||
}
|
||||
XZToColumnXZ(&cx_min, &cz_min, bnds->real_bounds.min.v[0], bnds->real_bounds.min.v[2], track_spec);
|
||||
XZToColumnXZ(&cx_max, &cz_max, bnds->real_bounds.max.v[0], bnds->real_bounds.max.v[2], track_spec);
|
||||
if (cx_min) {
|
||||
if (cx_min != 0) {
|
||||
cx_min--;
|
||||
}
|
||||
if (cz_min) {
|
||||
if (cz_min != 0) {
|
||||
cz_min--;
|
||||
}
|
||||
if (track_spec->ncolumns_x > cx_max + 1) {
|
||||
if (cx_max + 1 < track_spec->ncolumns_x) {
|
||||
cx_max++;
|
||||
}
|
||||
if (track_spec->ncolumns_z > cz_max + 1) {
|
||||
if (cz_max + 1 < track_spec->ncolumns_z) {
|
||||
cz_max++;
|
||||
}
|
||||
for (x = cx_min; cx_max >= x; ++x) {
|
||||
for (z = cz_min; cz_max >= z; ++z) {
|
||||
if (track_spec->columns[z][x]) {
|
||||
if (track_spec->blends[z][x]) {
|
||||
for (x = cx_min; x <= cx_max; x++) {
|
||||
for (z = cz_min; z <= cz_max; z++) {
|
||||
if (track_spec->columns[z][x] != NULL) {
|
||||
if (track_spec->blends[z][x] != NULL) {
|
||||
track_spec->blends[z][x]->render_style = BR_RSTYLE_FACES;
|
||||
}
|
||||
j = max_face - ActorBoxPick(bnds, track_spec->columns[z][x], NULL, NULL, &face_list[j], max_face - j, 0);
|
||||
if (track_spec->blends[z][x]) {
|
||||
j = max_face - ActorBoxPick(bnds, track_spec->columns[z][x], model_unk1, material_unk1, &face_list[j], max_face - j, NULL);
|
||||
if (track_spec->blends[z][x] != NULL) {
|
||||
track_spec->blends[z][x]->render_style = BR_RSTYLE_NONE;
|
||||
}
|
||||
}
|
||||
if (track_spec->lollipops[z][x]) {
|
||||
j = max_face - ActorBoxPick(bnds, track_spec->lollipops[z][x], NULL, NULL, &face_list[j], max_face - j, 0);
|
||||
if (track_spec->lollipops[z][x] != NULL) {
|
||||
j = max_face - ActorBoxPick(bnds, track_spec->lollipops[z][x], model_unk1, material_unk1, &face_list[j], max_face - j, NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -754,25 +742,29 @@ int ActorBoxPick(tBounds* bnds, br_actor* ap, br_model* model, br_material* mate
|
|||
|
||||
i = 0;
|
||||
test_children = 1;
|
||||
if (ap->model) {
|
||||
if (ap->model != NULL) {
|
||||
this_model = ap->model;
|
||||
} else {
|
||||
this_model = model;
|
||||
}
|
||||
if (ap->material) {
|
||||
if (ap->material != NULL) {
|
||||
this_material = ap->material;
|
||||
} else {
|
||||
this_material = material;
|
||||
}
|
||||
if (ap->render_style == 1) {
|
||||
if (ap->render_style == BR_RSTYLE_NONE) {
|
||||
return max_face;
|
||||
}
|
||||
if (ap->identifier && *ap->identifier == '&') {
|
||||
if (!ap->children
|
||||
&& (ap->type != BR_ACTOR_MODEL || !BoundsTransformTest(&this_model->bounds, &bnds->real_bounds, &ap->t.t.mat))) {
|
||||
return max_face;
|
||||
if (ap->identifier != NULL && ap->identifier[0] == '&') {
|
||||
if (ap->children == NULL) {
|
||||
if (ap->type != BR_ACTOR_MODEL) {
|
||||
return max_face;
|
||||
}
|
||||
if (!BoundsTransformTest(&this_model->bounds, &bnds->real_bounds, &ap->t.t.mat)) {
|
||||
return max_face;
|
||||
}
|
||||
}
|
||||
if (pMat) {
|
||||
if (pMat != NULL) {
|
||||
BrMatrix34Mul(&mat, &ap->t.t.mat, pMat);
|
||||
pMat = &mat;
|
||||
} else {
|
||||
|
|
@ -781,7 +773,8 @@ int ActorBoxPick(tBounds* bnds, br_actor* ap, br_model* model, br_material* mate
|
|||
BrMatrix34LPInverse(&invmat, &ap->t.t.mat);
|
||||
BrMatrix34Mul(&mat2, bnds->mat, &invmat);
|
||||
new_bounds.mat = &mat2;
|
||||
new_bounds.original_bounds = bnds->original_bounds;
|
||||
BrVector3Copy(&new_bounds.original_bounds.min, &bnds->original_bounds.min);
|
||||
BrVector3Copy(&new_bounds.original_bounds.max, &bnds->original_bounds.max);
|
||||
BrMatrix34ApplyP(&new_bounds.box_centre, &bnds->box_centre, &invmat);
|
||||
new_bounds.radius = bnds->radius;
|
||||
GetNewBoundingBox(&new_bounds.real_bounds, &new_bounds.original_bounds, new_bounds.mat);
|
||||
|
|
@ -810,11 +803,11 @@ int ActorBoxPick(tBounds* bnds, br_actor* ap, br_model* model, br_material* mate
|
|||
i += max_face - n;
|
||||
max_face = n;
|
||||
}
|
||||
} else if (ap->type >= 5u && ap->type <= 6u) {
|
||||
} else if (ap->type == BR_ACTOR_BOUNDS || ap->type == BR_ACTOR_BOUNDS_CORRECT) {
|
||||
test_children = BoundsOverlapTest__finteray(&bnds->real_bounds, (br_bounds*)ap->type_data);
|
||||
}
|
||||
if (test_children) {
|
||||
for (a = ap->children; a; a = next_a) {
|
||||
for (a = ap->children; a != NULL; a = next_a) {
|
||||
next_a = a->next;
|
||||
n = ActorBoxPick(bnds, a, this_model, this_material, &face_list[i], max_face, pMat);
|
||||
i += max_face - n;
|
||||
|
|
|
|||
|
|
@ -1,14 +1,18 @@
|
|||
#include "oil.h"
|
||||
#include "brender/brender.h"
|
||||
#include "finteray.h"
|
||||
#include "globvars.h"
|
||||
#include "globvrpb.h"
|
||||
#include "harness/trace.h"
|
||||
#include "loading.h"
|
||||
#include "network.h"
|
||||
#include "piping.h"
|
||||
#include "utility.h"
|
||||
#include <math.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
char* gOil_pixie_names[1] = { "OIL.PIX" };
|
||||
int gNext_oil_pixie;
|
||||
int gNext_oil_pixie = 0;
|
||||
br_scalar gZ_buffer_diff;
|
||||
br_scalar gMin_z_diff;
|
||||
br_pixelmap* gOil_pixies[1];
|
||||
|
|
@ -32,11 +36,11 @@ void InitOilSpills() {
|
|||
the_material->ka = 0.99f;
|
||||
the_material->kd = 0.0f;
|
||||
the_material->ks = 0.0f;
|
||||
the_material->power = 0.0;
|
||||
the_material->power = 0.0f;
|
||||
the_material->index_base = 0;
|
||||
the_material->flags |= BR_MATF_LIGHT;
|
||||
the_material->flags |= BR_MATF_PERSPECTIVE;
|
||||
the_material->flags |= 0x00000004;
|
||||
the_material->flags |= BR_MATF_SMOOTH;
|
||||
the_material->index_range = 0;
|
||||
the_material->colour_map = NULL;
|
||||
BrMatrix23Identity(&the_material->map_transform);
|
||||
|
|
@ -45,36 +49,24 @@ void InitOilSpills() {
|
|||
the_model = BrModelAllocate(NULL, 4, 2);
|
||||
the_model->flags |= BR_MODF_KEEP_ORIGINAL;
|
||||
|
||||
the_model->faces->vertices[0] = 2;
|
||||
the_model->faces->vertices[1] = 1;
|
||||
the_model->faces->vertices[2] = 0;
|
||||
the_model->faces->material = NULL;
|
||||
the_model->faces->smoothing = 1;
|
||||
the_model->faces[0].vertices[0] = 2;
|
||||
the_model->faces[0].vertices[1] = 1;
|
||||
the_model->faces[0].vertices[2] = 0;
|
||||
the_model->faces[0].material = NULL;
|
||||
the_model->faces[0].smoothing = 1;
|
||||
the_model->faces[1].vertices[0] = 3;
|
||||
the_model->faces[1].vertices[1] = 2;
|
||||
the_model->faces[1].vertices[2] = 0;
|
||||
the_model->faces[1].material = NULL;
|
||||
the_model->faces[1].smoothing = 1;
|
||||
the_model->vertices[0].p.v[0] = -1.0f;
|
||||
the_model->vertices[0].p.v[1] = 0.0f;
|
||||
the_model->vertices[0].p.v[2] = -1.0f;
|
||||
the_model->vertices->map.v[0] = 0.0f;
|
||||
the_model->vertices->map.v[1] = 1.0f;
|
||||
the_model->vertices[1].p.v[0] = 1.0f;
|
||||
the_model->vertices[1].p.v[1] = 0.0f;
|
||||
the_model->vertices[1].p.v[2] = 1.0f;
|
||||
the_model->vertices[1].map.v[0] = 0.0f;
|
||||
the_model->vertices[1].map.v[1] = 0.0f;
|
||||
the_model->vertices[2].p.v[0] = 1.0f;
|
||||
the_model->vertices[2].p.v[1] = 0.0f;
|
||||
the_model->vertices[2].p.v[2] = -1.0f;
|
||||
the_model->vertices[2].map.v[0] = 1.0f;
|
||||
the_model->vertices[2].map.v[1] = 0.0f;
|
||||
the_model->vertices[3].p.v[0] = -1.0f;
|
||||
the_model->vertices[3].p.v[1] = 0.0f;
|
||||
the_model->vertices[3].p.v[2] = 1.0f;
|
||||
the_model->vertices[3].map.v[0] = 1.0f;
|
||||
the_model->vertices[3].map.v[1] = 1.0f;
|
||||
BrVector3Set(&the_model->vertices[0].p, -1.f, 0.f, -1.f);
|
||||
BrVector2Set(&the_model->vertices[0].map, 0.f, 1.f);
|
||||
BrVector3Set(&the_model->vertices[1].p, 1.f, 0.f, 1.f);
|
||||
BrVector2Set(&the_model->vertices[1].map, 0.f, 0.f);
|
||||
BrVector3Set(&the_model->vertices[2].p, 1.f, 0.f, -1.f);
|
||||
BrVector2Set(&the_model->vertices[2].map, 1.f, 0.f);
|
||||
BrVector3Set(&the_model->vertices[3].p, -1.f, 0.f, 1.f);
|
||||
BrVector2Set(&the_model->vertices[3].map, 1.f, 1.f);
|
||||
gOily_spills[i].actor = BrActorAllocate(BR_ACTOR_MODEL, NULL);
|
||||
gOily_spills[i].actor->model = the_model;
|
||||
gOily_spills[i].actor->render_style = BR_RSTYLE_NONE;
|
||||
|
|
@ -110,7 +102,7 @@ void QueueOilSpill(tCar_spec* pCar) {
|
|||
oldest_time = GetTotalTime();
|
||||
|
||||
for (i = 0; i < COUNT_OF(gOily_spills); i++) {
|
||||
if (gOily_spills[i].car == pCar && the_time < (gOily_spills[i].spill_time + 5000)) {
|
||||
if (gOily_spills[i].car == pCar && the_time < gOily_spills[i].spill_time + 5000) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
|
@ -132,7 +124,7 @@ void QueueOilSpill(tCar_spec* pCar) {
|
|||
gOily_spills[oily_index].car = pCar;
|
||||
gOily_spills[oily_index].spill_time = the_time + 500;
|
||||
gOily_spills[oily_index].full_size = SRandomBetween(.35f, .6f);
|
||||
gOily_spills[oily_index].grow_rate = SRandomBetween(30e-4f, 1e-4f);
|
||||
gOily_spills[oily_index].grow_rate = SRandomBetween(3e-5f, 10e-5f);
|
||||
gOily_spills[oily_index].current_size = .1f;
|
||||
gOily_spills[oily_index].actor->render_style = BR_RSTYLE_NONE;
|
||||
}
|
||||
|
|
@ -156,7 +148,56 @@ int OKToSpillOil(tOil_spill_info* pOil) {
|
|||
tFace_ref the_list[10];
|
||||
tFace_ref* face_ref;
|
||||
LOG_TRACE("(%p)", pOil);
|
||||
NOT_IMPLEMENTED();
|
||||
|
||||
car = pOil->car;
|
||||
if (car->driver >= eDriver_net_human && car->damage_units[eDamage_engine].damage_level <= 98 && car->damage_units[eDamage_transmission].damage_level <= 98) {
|
||||
return 0;
|
||||
}
|
||||
angle_to_rotate_by = IRandomBetween(0, 0xffff);
|
||||
kev_bounds.original_bounds.min.v[0] = -pOil->full_size;
|
||||
kev_bounds.original_bounds.min.v[1] = 1.5f * car->car_model_actors[car->principal_car_actor].actor->model->bounds.min.v[1];
|
||||
kev_bounds.original_bounds.min.v[2] = -pOil->full_size;
|
||||
kev_bounds.original_bounds.max.v[0] = pOil->full_size;
|
||||
kev_bounds.original_bounds.max.v[1] = car->car_model_actors[car->principal_car_actor].actor->model->bounds.max.v[1];
|
||||
kev_bounds.original_bounds.max.v[2] = pOil->full_size;
|
||||
BrMatrix34PreRotateY(&pOil->actor->t.t.mat, angle_to_rotate_by);
|
||||
kev_bounds.mat = &car->car_master_actor->t.t.mat;
|
||||
face_count = FindFacesInBox(&kev_bounds, the_list, COUNT_OF(the_list));
|
||||
BrVector3Set(&v, .0f, .2f, .0f);
|
||||
BrMatrix34ApplyP(&ray_pos, &v, &car->car_master_actor->t.t.mat);
|
||||
BrVector3Set(&ray_dir, 0.f, kev_bounds.original_bounds.min.v[1] - kev_bounds.original_bounds.max.v[1], 0.f);\
|
||||
if (face_count == 0) {
|
||||
return 0;
|
||||
}
|
||||
found_one = 0;
|
||||
for (i = 0; i < face_count; i++) {
|
||||
face_ref = &the_list[i];
|
||||
if (!found_one) {
|
||||
CheckSingleFace(face_ref, &ray_pos, &ray_dir, &normal, &distance);
|
||||
if (distance < 100.f) {
|
||||
found_one = 1;
|
||||
BrVector3Copy((br_vector3*)pOil->actor->t.t.mat.m[1], &normal);
|
||||
BrVector3Set(&v, 0.f, 0.f, 1.f);
|
||||
BrVector3Cross((br_vector3*)pOil->actor->t.t.mat.m[0], &normal, &v);
|
||||
BrVector3Set(&v, 1.f, 0.f, 0.f);
|
||||
BrVector3Cross((br_vector3*)pOil->actor->t.t.mat.m[2], &normal, &v);
|
||||
BrVector3Scale(&v, &ray_dir, distance);
|
||||
BrVector3Add(&pOil->pos, &ray_pos, &v);
|
||||
BrMatrix34PreRotateY(&pOil->actor->t.t.mat, angle_to_rotate_by);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!found_one || normal.v[1] < .97f) {
|
||||
return 0;
|
||||
}
|
||||
for (i = 0; i < face_count; i++) {
|
||||
face_ref = &the_list[i];
|
||||
mr_dotty = BrVector3Dot(&face_ref->normal, &normal);
|
||||
if (mr_dotty < .98f && (mr_dotty > .8f || !NormalSideOfPlane(&pOil->actor->t.t.translate.t, &face_ref->normal, face_ref->d))) {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
// IDA: void __usercall Vector3Interpolate(br_vector3 *pDst@<EAX>, br_vector3 *pFrom@<EDX>, br_vector3 *pTo@<EBX>, br_scalar pP)
|
||||
|
|
@ -182,7 +223,7 @@ void EnsureGroundDetailVisible(br_vector3* pNew_pos, br_vector3* pGround_normal,
|
|||
dist = BrVector3Length(&to_camera);
|
||||
if (dist > BR_SCALAR_EPSILON) {
|
||||
factor = BrVector3Dot(pGround_normal, &to_camera) / dist;
|
||||
if (fabs(factor) <= 0.01f) {
|
||||
if (fabsf(factor) <= 0.01f) {
|
||||
s = 0.01f;
|
||||
} else {
|
||||
s = 0.01f / factor;
|
||||
|
|
@ -236,7 +277,97 @@ void ProcessOilSpills(tU32 pFrame_period) {
|
|||
br_vector3 v;
|
||||
tNet_message* message;
|
||||
LOG_TRACE("(%d)", pFrame_period);
|
||||
STUB_ONCE();
|
||||
|
||||
time = GetTotalTime();
|
||||
for (i = 0; i < COUNT_OF(gOily_spills); i++) {
|
||||
if (gOily_spills[i].car == NULL) {
|
||||
gOily_spills[i].actor->render_style = BR_RSTYLE_NONE;
|
||||
} else {
|
||||
the_model = gOily_spills[i].actor->model;
|
||||
if (gOily_spills[i].actor->render_style == BR_RSTYLE_NONE &&
|
||||
gOily_spills[i].spill_time <= time &&
|
||||
fabsf(gOily_spills[i].car->v.v[0]) < .01f &&
|
||||
fabsf(gOily_spills[i].car->v.v[1]) < .01f &&
|
||||
fabsf(gOily_spills[i].car->v.v[2]) < .01f) {
|
||||
if (gAction_replay_mode) {
|
||||
SetInitialOilStuff(&gOily_spills[i], the_model);
|
||||
} else {
|
||||
if (!OKToSpillOil(&gOily_spills[i])) {
|
||||
gOily_spills[i].car = NULL;
|
||||
} else {
|
||||
gOily_spills[i].spill_time = time;
|
||||
gOily_spills[i].actor->material->colour_map = gOil_pixies[gNext_oil_pixie];
|
||||
gNext_oil_pixie++;
|
||||
if (gNext_oil_pixie >= COUNT_OF(gOil_pixies)) {
|
||||
gNext_oil_pixie = 0;
|
||||
}
|
||||
BrVector3Copy(&gOily_spills[i].original_pos, &gOily_spills[i].car->pos);
|
||||
PipeSingleOilSpill(i,
|
||||
&gOily_spills[i].actor->t.t.mat,
|
||||
gOily_spills[i].full_size,
|
||||
gOily_spills[i].grow_rate,
|
||||
gOily_spills[i].spill_time,
|
||||
gOily_spills[i].stop_time,
|
||||
gOily_spills[i].car,
|
||||
&gOily_spills[i].original_pos,
|
||||
gOily_spills[i].actor->material->colour_map);
|
||||
gOily_spills[i].stop_time = 0;
|
||||
SetInitialOilStuff(&gOily_spills[i], the_model);
|
||||
if (gNet_mode != eNet_mode_none) {
|
||||
message = NetBuildMessage(30, 0);
|
||||
message->contents.data.oil_spill.player = NetPlayerFromCar(gOily_spills[i].car)->ID;
|
||||
message->contents.data.oil_spill.full_size = gOily_spills[i].full_size;
|
||||
message->contents.data.oil_spill.grow_rate = gOily_spills[i].grow_rate;
|
||||
message->contents.data.oil_spill.current_size = gOily_spills[i].current_size;
|
||||
NetGuaranteedSendMessageToAllPlayers(gCurrent_net_game, message, NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (gOily_spills[i].actor->render_style == BR_RSTYLE_FACES &&
|
||||
(gOily_spills[i].stop_time == 0 || time < gOily_spills[i].stop_time)) {
|
||||
BrVector3Sub(&v, &gOily_spills[i].original_pos, &gOily_spills[i].car->pos);
|
||||
grow_amount = BrVector3LengthSquared(&v);
|
||||
if (gOily_spills[i].stop_time != 0 || grow_amount <= 0.2f) {
|
||||
this_size = 0.1f + (time - gOily_spills[i].spill_time) * gOily_spills[i].grow_rate;
|
||||
if (this_size >= 0.1f) {
|
||||
gOily_spills[i].actor->render_style = BR_RSTYLE_FACES;
|
||||
if (this_size <= gOily_spills[i].full_size) {
|
||||
the_model->vertices[0].p.v[0] = -this_size;
|
||||
the_model->vertices[0].p.v[2] = -this_size;
|
||||
the_model->vertices[1].p.v[0] = this_size;
|
||||
the_model->vertices[1].p.v[2] = -this_size;
|
||||
the_model->vertices[2].p.v[0] = this_size;
|
||||
the_model->vertices[2].p.v[2] = this_size;
|
||||
the_model->vertices[3].p.v[0] = -this_size;
|
||||
the_model->vertices[3].p.v[2] = this_size;
|
||||
gOily_spills[i].current_size = this_size;
|
||||
} else {
|
||||
the_model->vertices[0].p.v[0] = -gOily_spills[i].full_size;
|
||||
the_model->vertices[0].p.v[2] = -gOily_spills[i].full_size;
|
||||
the_model->vertices[1].p.v[0] = gOily_spills[i].full_size;
|
||||
the_model->vertices[1].p.v[2] = -gOily_spills[i].full_size;
|
||||
the_model->vertices[2].p.v[0] = gOily_spills[i].full_size;
|
||||
the_model->vertices[2].p.v[2] = gOily_spills[i].full_size;
|
||||
the_model->vertices[3].p.v[0] = -gOily_spills[i].full_size;
|
||||
the_model->vertices[3].p.v[2] = gOily_spills[i].full_size;
|
||||
gOily_spills[i].current_size = gOily_spills[i].full_size;
|
||||
}
|
||||
BrModelUpdate(the_model, BR_MODU_ALL);
|
||||
} else {
|
||||
gOily_spills[i].actor->render_style = BR_RSTYLE_NONE;
|
||||
}
|
||||
} else {
|
||||
gOily_spills[i].stop_time = time;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (gOily_spills[i].actor->render_style == BR_RSTYLE_FACES) {
|
||||
MungeOilsHeightAboveGround(&gOily_spills[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// IDA: int __cdecl GetOilSpillCount()
|
||||
|
|
@ -254,17 +385,19 @@ void GetOilSpillDetails(int pIndex, br_actor** pActor, br_scalar* pSize) {
|
|||
*pActor = gOily_spills[pIndex].actor;
|
||||
*pSize = gOily_spills[pIndex].full_size;
|
||||
} else {
|
||||
*pActor = 0;
|
||||
*pActor = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
#define SQR(V) ((V)*(V))
|
||||
|
||||
// IDA: int __usercall PointInSpill@<EAX>(br_vector3 *pV@<EAX>, int pSpill@<EDX>)
|
||||
int PointInSpill(br_vector3* pV, int pSpill) {
|
||||
LOG_TRACE("(%p, %d)", pV, pSpill);
|
||||
|
||||
return gOily_spills[pSpill].current_size * gOily_spills[pSpill].current_size * 0.8f > (pV->v[0] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.mat.m[3][0]) * (pV->v[0] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.mat.m[3][0])
|
||||
&& gOily_spills[pSpill].current_size * gOily_spills[pSpill].current_size * 0.8f > (pV->v[2] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.mat.m[3][2]) * (pV->v[2] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.mat.m[3][2])
|
||||
&& fabs(pV->v[1] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.mat.m[3][1]) < 0.1f;
|
||||
return gOily_spills[pSpill].current_size * gOily_spills[pSpill].current_size * 0.8f > SQR(pV->v[0] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.translate.t.v[0])
|
||||
&& gOily_spills[pSpill].current_size * gOily_spills[pSpill].current_size * 0.8f > SQR(pV->v[2] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.translate.t.v[2])
|
||||
&& fabsf(pV->v[1] / WORLD_SCALE - gOily_spills[pSpill].actor->t.t.translate.t.v[1]) < 0.1f;
|
||||
}
|
||||
|
||||
// IDA: void __usercall GetOilFrictionFactors(tCar_spec *pCar@<EAX>, br_scalar *pFl_factor@<EDX>, br_scalar *pFr_factor@<EBX>, br_scalar *pRl_factor@<ECX>, br_scalar *pRr_factor)
|
||||
|
|
@ -273,10 +406,10 @@ void GetOilFrictionFactors(tCar_spec* pCar, br_scalar* pFl_factor, br_scalar* pF
|
|||
br_vector3 wheel_world;
|
||||
LOG_TRACE("(%p, %p, %p, %p, %p)", pCar, pFl_factor, pFr_factor, pRl_factor, pRr_factor);
|
||||
|
||||
*pFl_factor = 1.0;
|
||||
*pFr_factor = 1.0;
|
||||
*pRl_factor = 1.0;
|
||||
*pRr_factor = 1.0;
|
||||
*pFl_factor = 1.0f;
|
||||
*pFr_factor = 1.0f;
|
||||
*pRl_factor = 1.0f;
|
||||
*pRr_factor = 1.0f;
|
||||
switch (pCar->driver) {
|
||||
case eDriver_non_car_unused_slot:
|
||||
case eDriver_non_car:
|
||||
|
|
@ -286,7 +419,7 @@ void GetOilFrictionFactors(tCar_spec* pCar, br_scalar* pFl_factor, br_scalar* pF
|
|||
}
|
||||
if (pCar->shadow_intersection_flags != 0) {
|
||||
for (i = 0; i < COUNT_OF(gOily_spills); i++) {
|
||||
if (((1 << i) & pCar->shadow_intersection_flags) != 0 && gOily_spills[i].car) {
|
||||
if (((1 << i) & pCar->shadow_intersection_flags) != 0 && gOily_spills[i].car != NULL) {
|
||||
BrMatrix34ApplyP(&wheel_world, &pCar->wpos[2], &pCar->car_master_actor->t.t.mat);
|
||||
if (PointInSpill(&wheel_world, i)) {
|
||||
pCar->oil_remaining[2] = SRandomBetween(1.5f, 2.5f);
|
||||
|
|
@ -323,7 +456,16 @@ void GetOilFrictionFactors(tCar_spec* pCar, br_scalar* pFl_factor, br_scalar* pF
|
|||
// IDA: void __usercall AdjustOilSpill(int pIndex@<EAX>, br_matrix34 *pMat@<EDX>, br_scalar pFull_size, br_scalar pGrow_rate, tU32 pSpill_time, tU32 pStop_time, tCar_spec *pCar, br_vector3 *pOriginal_pos, br_pixelmap *pPixelmap)
|
||||
void AdjustOilSpill(int pIndex, br_matrix34* pMat, br_scalar pFull_size, br_scalar pGrow_rate, tU32 pSpill_time, tU32 pStop_time, tCar_spec* pCar, br_vector3* pOriginal_pos, br_pixelmap* pPixelmap) {
|
||||
LOG_TRACE("(%d, %p, %f, %f, %d, %d, %p, %p, %p)", pIndex, pMat, pFull_size, pGrow_rate, pSpill_time, pStop_time, pCar, pOriginal_pos, pPixelmap);
|
||||
NOT_IMPLEMENTED();
|
||||
|
||||
BrMatrix34Copy(&gOily_spills[pIndex].actor->t.t.mat, pMat);
|
||||
gOily_spills[pIndex].full_size = pFull_size;
|
||||
gOily_spills[pIndex].grow_rate = pGrow_rate;
|
||||
gOily_spills[pIndex].spill_time = pSpill_time;
|
||||
gOily_spills[pIndex].stop_time = pStop_time;
|
||||
gOily_spills[pIndex].car = pCar;
|
||||
BrVector3Copy(&gOily_spills[pIndex].original_pos, pOriginal_pos);
|
||||
gOily_spills[pIndex].actor->material->colour_map = pPixelmap;
|
||||
gOily_spills[pIndex].actor->render_style = BR_RSTYLE_NONE;
|
||||
}
|
||||
|
||||
// IDA: void __usercall ReceivedOilSpill(tNet_contents *pContents@<EAX>)
|
||||
|
|
@ -335,5 +477,37 @@ void ReceivedOilSpill(tNet_contents* pContents) {
|
|||
tU32 oldest_time;
|
||||
tCar_spec* car;
|
||||
LOG_TRACE("(%p)", pContents);
|
||||
NOT_IMPLEMENTED();
|
||||
|
||||
oldest_one = 0;
|
||||
car = NetCarFromPlayerID(pContents->data.oil_spill.player);
|
||||
if (car == NULL) {
|
||||
return;
|
||||
}
|
||||
oily_index = -1;
|
||||
the_time = GetTotalTime();
|
||||
oldest_time = GetTotalTime();
|
||||
for (i = 0; i < COUNT_OF(gOily_spills); i++) {
|
||||
if (gOily_spills[i].car == car && the_time < gOily_spills[i].spill_time + 5000) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
for (i = 0; i < COUNT_OF(gOily_spills); i++) {
|
||||
if (gOily_spills[i].car == NULL) {
|
||||
oily_index = i;
|
||||
break;
|
||||
}
|
||||
if (gOily_spills[i].spill_time < oldest_time) {
|
||||
oldest_time = gOily_spills[i].spill_time;
|
||||
oldest_one = i;
|
||||
}
|
||||
}
|
||||
if (oily_index < 0) {
|
||||
oily_index = oldest_one;
|
||||
}
|
||||
gOily_spills[oily_index].car = car;
|
||||
gOily_spills[oily_index].spill_time = the_time;
|
||||
gOily_spills[oily_index].full_size = pContents->data.oil_spill.full_size;
|
||||
gOily_spills[oily_index].grow_rate = pContents->data.oil_spill.grow_rate;
|
||||
gOily_spills[oily_index].current_size = pContents->data.oil_spill.current_size;
|
||||
gOily_spills[oily_index].actor->render_style = BR_RSTYLE_NONE;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -252,8 +252,7 @@ int DRScenePick2D(br_actor* world, br_actor* camera, dr_pick2d_cbfn* callback, v
|
|||
camera_data = (br_camera*)camera->type_data;
|
||||
DRActorToRoot(camera, world, &camera_tfm);
|
||||
BrMatrix34Inverse(&gPick_model_to_view__raycast, &camera_tfm);
|
||||
scale = cos(BrAngleToRadian(camera_data->field_of_view / 2));
|
||||
scale = scale / sin(BrAngleToRadian(camera_data->field_of_view / 2));
|
||||
scale = cosf(BrAngleToRadian(camera_data->field_of_view / 2)) / sinf(BrAngleToRadian(camera_data->field_of_view / 2));
|
||||
|
||||
BrMatrix34PostScale(&gPick_model_to_view__raycast, scale / camera_data->aspect, scale, 1.0f);
|
||||
return ActorPick2D(world, model_unk1, material_unk1, callback, arg);
|
||||
|
|
|
|||
|
|
@ -14,6 +14,10 @@ extern br_scalar gHighest_y_below;
|
|||
extern br_actor* gY_picking_camera;
|
||||
extern br_scalar gLowest_y_above;
|
||||
|
||||
// Added, probably can be replaced with NULL
|
||||
extern br_model* model_unk1;
|
||||
extern br_material* material_unk1;
|
||||
|
||||
int DRActorToRoot(br_actor* a, br_actor* world, br_matrix34* m);
|
||||
|
||||
void InitRayCasting();
|
||||
|
|
|
|||
Loading…
Reference in New Issue