mirror of
https://github.com/OpenDriver2/REDRIVER2.git
synced 2024-11-23 10:52:36 +01:00
- significantly reduce code with use of GetSurfaceRoadInfo
- refactoring progress on GetNextRoadInfo
This commit is contained in:
parent
b24df3aae9
commit
ebce60cba6
@ -621,6 +621,8 @@ int GetNextRoadInfo(_CAR_DATA* cp, int randomExit, int* turnAngle, int* startDis
|
||||
{
|
||||
int currentLaneDir;
|
||||
int widthInLanes;
|
||||
int laneNo;
|
||||
int count;
|
||||
|
||||
_st = GET_STRAIGHT(currentRoadId);
|
||||
|
||||
@ -636,34 +638,34 @@ int GetNextRoadInfo(_CAR_DATA* cp, int randomExit, int* turnAngle, int* startDis
|
||||
else
|
||||
tmpNewRoad[1] = _st->ConnectIdx[1];
|
||||
|
||||
uVar9 = widthInLanes; // counter
|
||||
uVar29 = widthInLanes; // bestLane
|
||||
count = widthInLanes; // counter
|
||||
laneNo = widthInLanes; // bestLane
|
||||
|
||||
do
|
||||
{
|
||||
uVar9--;
|
||||
if(ROAD_IS_AI_LANE(_st, uVar9) && !ROAD_IS_PARKING_ALLOWED_AT(_st, uVar9))
|
||||
count--;
|
||||
if(ROAD_IS_AI_LANE(_st, count) && !ROAD_IS_PARKING_ALLOWED_AT(_st, count))
|
||||
{
|
||||
test42 = ROAD_LANE_DIR(_st, uVar9);
|
||||
uVar29 = uVar9;
|
||||
test42 = ROAD_LANE_DIR(_st, count);
|
||||
laneNo = count;
|
||||
}
|
||||
} while (uVar9 >= 0);
|
||||
} while (count >= 0);
|
||||
|
||||
if (currentLaneDir == 0)
|
||||
leftLane = uVar29 & 0xff;
|
||||
leftLane = laneNo & 0xff;
|
||||
else
|
||||
rightLane = uVar29 & 0xff;
|
||||
rightLane = laneNo & 0xff;
|
||||
|
||||
|
||||
uVar17 = ROAD_HAS_FAST_LANES(_st); // counter
|
||||
uVar29 = widthInLanes; // bestLane
|
||||
// if speed lane, use other first lane. WTF idk why
|
||||
count = ROAD_HAS_FAST_LANES(_st); // counter
|
||||
laneNo = widthInLanes; // bestLane
|
||||
|
||||
while (uVar17 < widthInLanes)
|
||||
while (count < widthInLanes)
|
||||
{
|
||||
if(ROAD_IS_AI_LANE(_st, uVar17) && !ROAD_IS_PARKING_ALLOWED_AT(_st, uVar17))
|
||||
if(ROAD_IS_AI_LANE(_st, count) && !ROAD_IS_PARKING_ALLOWED_AT(_st, count))
|
||||
{
|
||||
test555 = ROAD_LANE_DIR(_st, uVar17) ^ 1;
|
||||
uVar29 = uVar17;
|
||||
test555 = ROAD_LANE_DIR(_st, count) ^ 1;
|
||||
laneNo = count;
|
||||
|
||||
if (test555 == 0)
|
||||
{
|
||||
@ -676,133 +678,84 @@ int GetNextRoadInfo(_CAR_DATA* cp, int randomExit, int* turnAngle, int* startDis
|
||||
break;
|
||||
}
|
||||
}
|
||||
uVar29 = widthInLanes;
|
||||
uVar17++;
|
||||
laneNo = widthInLanes;
|
||||
count++;
|
||||
}
|
||||
|
||||
if (currentLaneDir != 0)
|
||||
leftLane = uVar29 & 0xff;
|
||||
leftLane = laneNo & 0xff;
|
||||
else
|
||||
rightLane = uVar29 & 0xff;
|
||||
rightLane = laneNo & 0xff;
|
||||
}
|
||||
else if(IS_CURVED_SURFACE(currentRoadId))
|
||||
{
|
||||
int currentLaneDir;
|
||||
int widthInLanes;
|
||||
int laneNo;
|
||||
int count;
|
||||
|
||||
____cv = GET_CURVE(currentRoadId);
|
||||
|
||||
if (*(short*)&____cv->NumLanes == -0xff)
|
||||
{
|
||||
uVar9 = (uint)cp->ai.c.currentLane;
|
||||
}
|
||||
widthInLanes = ROAD_WIDTH_IN_LANES(____cv);
|
||||
|
||||
currentLaneDir = ROAD_LANE_DIR(____cv, cp->ai.c.currentLane);
|
||||
oldOppDir = currentLaneDir << 0xb;
|
||||
|
||||
tmpNewRoad[0] = ____cv->ConnectIdx[currentLaneDir * 2];
|
||||
|
||||
if (currentLaneDir != 0)
|
||||
tmpNewRoad[1] = ____cv->ConnectIdx[3];
|
||||
else
|
||||
tmpNewRoad[1] = ____cv->ConnectIdx[1];
|
||||
|
||||
count = widthInLanes; // counter
|
||||
laneNo = widthInLanes; // bestLane
|
||||
|
||||
do
|
||||
{
|
||||
uVar9 = (int)(u_char)____cv->LaneDirs >> ((uint)(cp->ai.c.currentLane >> 1) & 0x1f);
|
||||
}
|
||||
|
||||
uVar9 = uVar9 & 1;
|
||||
oldOppDir = uVar9 << 0xb;
|
||||
|
||||
if (*(short*)&____cv->NumLanes == -0xff)
|
||||
{
|
||||
uVar29 = (uint)cp->ai.c.currentLane;
|
||||
}
|
||||
else
|
||||
{
|
||||
uVar29 = (int)(u_char)____cv->LaneDirs >> ((uint)(cp->ai.c.currentLane >> 1) & 0x1f);
|
||||
}
|
||||
|
||||
tmpNewRoad[0] = (int)____cv->ConnectIdx[(uVar29 & 1) * 2];
|
||||
|
||||
if (*(short*)&____cv->NumLanes == -0xff)
|
||||
{
|
||||
uVar29 = (uint)cp->ai.c.currentLane;
|
||||
}
|
||||
else
|
||||
{
|
||||
uVar29 = (int)(u_char)____cv->LaneDirs >> ((uint)(cp->ai.c.currentLane >> 1) & 0x1f);
|
||||
}
|
||||
|
||||
iVar22 = 2;
|
||||
|
||||
if ((uVar29 & 1) != 0)
|
||||
iVar22 = 6;
|
||||
|
||||
tmpNewRoad[1] = (int)*(short*)((int)____cv->ConnectIdx + iVar22);
|
||||
uVar25 = ((u_char)____cv->NumLanes & 0xf) * 2;
|
||||
uVar29 = uVar25;
|
||||
|
||||
do {
|
||||
do {
|
||||
uVar29 = uVar29 - 1;
|
||||
uVar16 = uVar25;
|
||||
|
||||
if ((int)uVar29 < 0)
|
||||
{
|
||||
goto LAB_000245c0_break;
|
||||
}
|
||||
|
||||
} while (((int)(u_char)____cv->AILanes >> ((int)uVar29 / 2 & 0x1fU) & 1U) == 0 ||
|
||||
uVar29 == 0 && (____cv->NumLanes & 0x40U) != 0 ||
|
||||
((u_char)____cv->NumLanes & 0xffffff0f) * 2 - 1 == uVar29 &&
|
||||
(____cv->NumLanes & 0x80U) != 0);
|
||||
|
||||
uVar16 = uVar29;
|
||||
|
||||
if (*(short*)&____cv->NumLanes != -0xff)
|
||||
count--;
|
||||
if(ROAD_IS_AI_LANE(____cv, count) && !ROAD_IS_PARKING_ALLOWED_AT(____cv, count))
|
||||
{
|
||||
uVar16 = (int)(u_char)____cv->LaneDirs >> ((int)uVar29 / 2 & 0x1fU);
|
||||
test42 = ROAD_LANE_DIR(____cv, count);
|
||||
laneNo = count;
|
||||
}
|
||||
} while (count >= 0);
|
||||
|
||||
test42 = (uVar16 ^ 1) & 1;
|
||||
uVar16 = uVar29;
|
||||
} while (uVar9 == 0);
|
||||
LAB_000245c0_break:
|
||||
|
||||
if (uVar9 == 0)
|
||||
leftLane = uVar16 & 0xff;
|
||||
if (currentLaneDir == 0)
|
||||
leftLane = laneNo & 0xff;
|
||||
else
|
||||
rightLane = uVar16 & 0xff;
|
||||
rightLane = laneNo & 0xff;
|
||||
|
||||
uVar25 = (u_char)____cv->NumLanes;
|
||||
uVar20 = (uVar25 & 0xf) << 1;
|
||||
uVar16 = (u_char)(____cv->NumLanes >> 6) & 1;
|
||||
uVar29 = uVar20;
|
||||
// if speed lane, use other first lane. WTF idk why
|
||||
count = ROAD_HAS_FAST_LANES(____cv); // counter
|
||||
laneNo = widthInLanes; // bestLane
|
||||
|
||||
if (uVar16 < uVar20)
|
||||
while (count < widthInLanes)
|
||||
{
|
||||
do {
|
||||
if (((int)(u_char)____cv->AILanes >> ((int)uVar16 / 2 & 0x1fU) & 1U) != 0 && (uVar16 != 0 || (____cv->NumLanes & 0x40U) == 0) &&
|
||||
((uVar25 & 0xffffff0f) * 2 - 1 != uVar16 || (uVar25 & 0x80) == 0))
|
||||
if(ROAD_IS_AI_LANE(____cv, count) && !ROAD_IS_PARKING_ALLOWED_AT(____cv, count))
|
||||
{
|
||||
test555 = ROAD_LANE_DIR(____cv, count) ^ 1;
|
||||
laneNo = count;
|
||||
|
||||
if (test555 == 0)
|
||||
{
|
||||
uVar29 = uVar16;
|
||||
|
||||
if (*(short*)&____cv->NumLanes != -0xff)
|
||||
{
|
||||
uVar29 = (int)(u_char)____cv->LaneDirs >> ((int)uVar16 / 2 & 0x1fU);
|
||||
}
|
||||
|
||||
test555 = (uVar29 ^ 1) & 1;
|
||||
uVar29 = uVar16;
|
||||
if (test555 == 0)
|
||||
{
|
||||
if (uVar9 != 0)
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (uVar9 == 0)
|
||||
break;
|
||||
}
|
||||
if (currentLaneDir != 0)
|
||||
break;
|
||||
}
|
||||
uVar25 = (u_char)____cv->NumLanes;
|
||||
uVar16 = uVar16 + 1;
|
||||
uVar29 = uVar20;
|
||||
} while ((int)uVar16 < (int)((uVar25 & 0xffffff0f) << 1));
|
||||
else
|
||||
{
|
||||
if (currentLaneDir == 0)
|
||||
break;
|
||||
}
|
||||
}
|
||||
laneNo = widthInLanes;
|
||||
count++;
|
||||
}
|
||||
|
||||
if (uVar9 == 0)
|
||||
rightLane = uVar29 & 0xff;
|
||||
if (currentLaneDir != 0)
|
||||
leftLane = laneNo & 0xff;
|
||||
else
|
||||
leftLane = uVar29 & 0xff;
|
||||
rightLane = laneNo & 0xff;
|
||||
}
|
||||
|
||||
iVar22 = tmpNewRoad[0];
|
||||
@ -3430,10 +3383,6 @@ int CreateNewNode(_CAR_DATA * cp)
|
||||
// [D] [T]
|
||||
int InitCivState(_CAR_DATA * cp, EXTRA_CIV_DATA * extraData)
|
||||
{
|
||||
int uVar1;
|
||||
long lVar2;
|
||||
int iVar3;
|
||||
|
||||
CIV_STATE* cs = &cp->ai.c;
|
||||
|
||||
cp->controlType = CONTROL_TYPE_CIV_AI;
|
||||
@ -3462,27 +3411,17 @@ int InitCivState(_CAR_DATA * cp, EXTRA_CIV_DATA * extraData)
|
||||
// init road and nodes
|
||||
if (cs->currentRoad > -1)
|
||||
{
|
||||
DRIVER2_CURVE* crv;
|
||||
DRIVER2_STRAIGHT* str;
|
||||
DRIVER2_ROAD_INFO roadInfo;
|
||||
|
||||
cp->ai.c.currentNode = 0;
|
||||
cp->ai.c.pnode = NULL;
|
||||
cp->ai.c.ctrlNode = NULL;
|
||||
cp->ai.c.turnNode = -1;
|
||||
|
||||
if (IS_CURVED_SURFACE(cs->currentRoad) || IS_STRAIGHT_SURFACE(cs->currentRoad))
|
||||
if(GetSurfaceRoadInfo(&roadInfo, cs->currentRoad))
|
||||
{
|
||||
if (IS_STRAIGHT_SURFACE(cs->currentRoad))
|
||||
{
|
||||
str = GET_STRAIGHT(cs->currentRoad);
|
||||
cp->ai.c.maxSpeed = speedLimits[ROAD_SPEED_LIMIT(str)];
|
||||
}
|
||||
else
|
||||
{
|
||||
crv = GET_CURVE(cs->currentRoad);
|
||||
cp->ai.c.maxSpeed = speedLimits[ROAD_SPEED_LIMIT(crv)];
|
||||
}
|
||||
|
||||
cp->ai.c.maxSpeed = speedLimits[ROAD_SPEED_LIMIT(&roadInfo)];
|
||||
|
||||
InitNodeList(cp, extraData);
|
||||
|
||||
cp->ai.c.pnode = &cp->ai.c.targetRoute[0];
|
||||
@ -4344,8 +4283,12 @@ int PingInCivCar(int minPingInDist)
|
||||
int model;
|
||||
_CAR_DATA* carCnt;
|
||||
_CAR_DATA* newCar;
|
||||
DRIVER2_CURVE* curve;
|
||||
DRIVER2_STRAIGHT* straight;
|
||||
|
||||
//DRIVER2_CURVE* curve;
|
||||
//DRIVER2_STRAIGHT* straight;
|
||||
|
||||
DRIVER2_ROAD_INFO roadInfo;
|
||||
|
||||
_EXTRA_CIV_DATA civDat;
|
||||
unsigned char possibleLanes[12];
|
||||
// carDistLanes removed as it's unused
|
||||
@ -4361,10 +4304,11 @@ int PingInCivCar(int minPingInDist)
|
||||
int oldCookieCount;
|
||||
uint retDistSq;
|
||||
|
||||
//straight = NULL;
|
||||
//curve = NULL;
|
||||
|
||||
civDat.distAlongSegment = -5;
|
||||
lane = -1;
|
||||
straight = NULL;
|
||||
curve = NULL;
|
||||
dir = 0xffffff;
|
||||
|
||||
tryPingInParkedCars = 0;
|
||||
@ -4517,31 +4461,27 @@ int PingInCivCar(int minPingInDist)
|
||||
|
||||
roadSeg = RoadInCell(&randomLoc);
|
||||
}
|
||||
|
||||
|
||||
// wtf there were before? car wasn't set to 'confused' state
|
||||
if (!IS_STRAIGHT_SURFACE(roadSeg) && !IS_CURVED_SURFACE(roadSeg))
|
||||
if (!GetSurfaceRoadInfo(&roadInfo, roadSeg))
|
||||
{
|
||||
civPingTest.OffRoad++;
|
||||
CIV_STATE_SET_CONFUSED(newCar);
|
||||
return 0;
|
||||
}
|
||||
|
||||
// I wonder if next code was sort of a BIG-BIG inline or MACRO also used in other functions
|
||||
if (IS_STRAIGHT_SURFACE(roadSeg))
|
||||
{
|
||||
int numPossibleLanes;
|
||||
int numLanes;
|
||||
int allowedToPark;
|
||||
|
||||
straight = GET_STRAIGHT(roadSeg);
|
||||
|
||||
if (ROAD_LANES_COUNT(straight) == 0) // BAD ROAD
|
||||
|
||||
if (ROAD_LANES_COUNT(&roadInfo) == 0) // BAD ROAD
|
||||
{
|
||||
CIV_STATE_SET_CONFUSED(newCar);
|
||||
return 0;
|
||||
}
|
||||
|
||||
numLanes = ROAD_WIDTH_IN_LANES(straight);
|
||||
numLanes = ROAD_WIDTH_IN_LANES(&roadInfo);
|
||||
|
||||
numPossibleLanes = 0;
|
||||
|
||||
@ -4556,7 +4496,7 @@ int PingInCivCar(int minPingInDist)
|
||||
while (i < numLanes)
|
||||
{
|
||||
// collect the lanes.
|
||||
allowedToPark = ROAD_IS_PARKING_ALLOWED_AT(straight, i);
|
||||
allowedToPark = ROAD_IS_PARKING_ALLOWED_AT(&roadInfo, i);
|
||||
|
||||
// this is closest to OG decompiled. Works different!
|
||||
//if ((
|
||||
@ -4564,7 +4504,7 @@ int PingInCivCar(int minPingInDist)
|
||||
// ((ROAD_IS_AI_LANE(straight, i) && (((i != 0 || ((straight->NumLanes & 0x40U) == 0)) && (((straight->NumLanes & 0xffffff0f) * 2 - 1 != i || ((straight->NumLanes & 0x80U) == 0))))))))
|
||||
|
||||
// pick only non-parkable driveable lanes if parked cars not requested
|
||||
if (tryPingInParkedCars && allowedToPark || ROAD_IS_AI_LANE(straight, i) && !allowedToPark)
|
||||
if (tryPingInParkedCars && allowedToPark || ROAD_IS_AI_LANE(&roadInfo, i) && !allowedToPark)
|
||||
possibleLanes[numPossibleLanes++] = i;
|
||||
|
||||
i++;
|
||||
@ -4577,89 +4517,19 @@ int PingInCivCar(int minPingInDist)
|
||||
}
|
||||
|
||||
// check if need to make a parked car
|
||||
if (ROAD_IS_PARKING_ALLOWED_AT(straight, lane))
|
||||
if (ROAD_IS_PARKING_ALLOWED_AT(&roadInfo, lane))
|
||||
{
|
||||
civDat.thrustState = 3;
|
||||
civDat.ctrlState = 7;
|
||||
|
||||
// set to drive off
|
||||
if (ROAD_IS_AI_LANE(straight, lane))
|
||||
if (ROAD_IS_AI_LANE(&roadInfo, lane))
|
||||
civDat.ctrlState = 5;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Car is not active. Permanently parked
|
||||
if (ROAD_IS_AI_LANE(straight, lane) == 0)
|
||||
{
|
||||
civPingTest.NotDrivable++;
|
||||
return 0;
|
||||
}
|
||||
|
||||
civDat.thrustState = 0;
|
||||
civDat.ctrlState = 0;
|
||||
}
|
||||
}
|
||||
else if (IS_CURVED_SURFACE(roadSeg))
|
||||
{
|
||||
int numPossibleLanes;
|
||||
int numLanes;
|
||||
int allowedToPark;
|
||||
|
||||
curve = GET_CURVE(roadSeg);
|
||||
|
||||
if (ROAD_LANES_COUNT(curve) == 0) // BAD ROAD
|
||||
{
|
||||
CIV_STATE_SET_CONFUSED(newCar);
|
||||
return 0;
|
||||
}
|
||||
|
||||
numLanes = ROAD_WIDTH_IN_LANES(curve);
|
||||
|
||||
numPossibleLanes = 0;
|
||||
|
||||
i = 0;
|
||||
while (i < numLanes)
|
||||
{
|
||||
// collect the lanes.
|
||||
allowedToPark = ROAD_IS_PARKING_ALLOWED_AT(curve, i);
|
||||
|
||||
// this is closest to OG decompiled. Works different!
|
||||
//if ((
|
||||
// ((tryPingInParkedCars && allowedToPark))) ||
|
||||
// ((ROAD_IS_AI_LANE(curve, i) && (((i != 0 || ((curve->NumLanes & 0x40U) == 0)) && (((curve->NumLanes & 0xffffff0f) * 2 - 1 != i || ((curve->NumLanes & 0x80U) == 0))))))))
|
||||
|
||||
// pick only non-parkable driveable lanes if parked cars not requested
|
||||
if (tryPingInParkedCars && allowedToPark || ROAD_IS_AI_LANE(curve, i) && !allowedToPark)
|
||||
possibleLanes[numPossibleLanes++] = i;
|
||||
|
||||
i++;
|
||||
}
|
||||
|
||||
if (numPossibleLanes == 0)
|
||||
return 0;
|
||||
|
||||
lane = possibleLanes[(Random2(0) >> 8) % numPossibleLanes];
|
||||
|
||||
if (lane > ROAD_WIDTH_IN_LANES(curve))
|
||||
{
|
||||
CIV_STATE_SET_CONFUSED(newCar);
|
||||
return 0;
|
||||
}
|
||||
|
||||
// check if need to make a parked car
|
||||
if (ROAD_IS_PARKING_ALLOWED_AT(curve, lane))
|
||||
{
|
||||
civDat.thrustState = 3;
|
||||
civDat.ctrlState = 7;
|
||||
|
||||
// set to drive off
|
||||
if (ROAD_IS_AI_LANE(curve, lane))
|
||||
civDat.ctrlState = 5;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Car is not active. Permanently parked
|
||||
if (ROAD_IS_AI_LANE(curve, lane) == 0)
|
||||
if (ROAD_IS_AI_LANE(&roadInfo, lane) == 0)
|
||||
{
|
||||
civPingTest.NotDrivable++;
|
||||
return 0;
|
||||
@ -4773,69 +4643,69 @@ int PingInCivCar(int minPingInDist)
|
||||
minDistAlong = 0;
|
||||
}
|
||||
|
||||
if (straight->length <= (scDist + lbody) * 2) // don't spawn outside straight
|
||||
if (roadInfo.straight->length <= (scDist + lbody) * 2) // don't spawn outside straight
|
||||
return 0;
|
||||
|
||||
dx = randomLoc.vx - straight->Midx;
|
||||
dz = randomLoc.vz - straight->Midz;
|
||||
dx = randomLoc.vx - roadInfo.straight->Midx;
|
||||
dz = randomLoc.vz - roadInfo.straight->Midz;
|
||||
|
||||
theta = (straight->angle - ratan2(dx, dz) & 0xfffU);
|
||||
theta = (roadInfo.straight->angle - ratan2(dx, dz) & 0xfffU);
|
||||
|
||||
civDat.distAlongSegment = (straight->length / 2) + FIXEDH(rcossin_tbl[theta * 2 + 1] * SquareRoot0(dx * dx + dz * dz));
|
||||
civDat.distAlongSegment = (roadInfo.straight->length / 2) + FIXEDH(rcossin_tbl[theta * 2 + 1] * SquareRoot0(dx * dx + dz * dz));
|
||||
|
||||
if (requestCopCar == 0)
|
||||
{
|
||||
if (civDat.distAlongSegment < minDistAlong)
|
||||
civDat.distAlongSegment = minDistAlong;
|
||||
|
||||
if (straight->length - civDat.distAlongSegment < minDistAlong)
|
||||
civDat.distAlongSegment = straight->length - minDistAlong;
|
||||
if (roadInfo.straight->length - civDat.distAlongSegment < minDistAlong)
|
||||
civDat.distAlongSegment = roadInfo.straight->length - minDistAlong;
|
||||
}
|
||||
|
||||
if (ROAD_LANE_DIR(straight, lane) == 0)
|
||||
dir = straight->angle;
|
||||
if (ROAD_LANE_DIR(roadInfo.straight, lane) == 0)
|
||||
dir = roadInfo.straight->angle;
|
||||
else
|
||||
dir = straight->angle + 0x800U & 0xfff;
|
||||
dir = roadInfo.straight->angle + 0x800U & 0xfff;
|
||||
}
|
||||
else if (IS_CURVED_SURFACE(roadSeg))
|
||||
{
|
||||
int minDistAlong;
|
||||
int segmentLen;
|
||||
|
||||
currentAngle = ratan2(randomLoc.vx - curve->Midx, randomLoc.vz - curve->Midz);
|
||||
currentAngle = ratan2(randomLoc.vx - roadInfo.curve->Midx, randomLoc.vz - roadInfo.curve->Midz);
|
||||
minDistAlong = 0;
|
||||
|
||||
if (requestCopCar == 0)
|
||||
{
|
||||
if (curve->inside > 9)
|
||||
if (roadInfo.curve->inside > 9)
|
||||
minDistAlong = 32;
|
||||
else if (curve->inside < 20)
|
||||
else if (roadInfo.curve->inside < 20)
|
||||
minDistAlong = 64;
|
||||
else
|
||||
minDistAlong = 128;
|
||||
}
|
||||
|
||||
if (curve->inside > 9)
|
||||
civDat.distAlongSegment = (currentAngle & 0xfffU) - curve->start & 0xfe0;
|
||||
else if (curve->inside < 20)
|
||||
civDat.distAlongSegment = (currentAngle & 0xfffU) - curve->start & 0xfc0;
|
||||
if (roadInfo.curve->inside > 9)
|
||||
civDat.distAlongSegment = (currentAngle & 0xfffU) - roadInfo.curve->start & 0xfe0;
|
||||
else if (roadInfo.curve->inside < 20)
|
||||
civDat.distAlongSegment = (currentAngle & 0xfffU) - roadInfo.curve->start & 0xfc0;
|
||||
else
|
||||
civDat.distAlongSegment = (currentAngle & 0xfffU) - curve->start & 0xf80;
|
||||
civDat.distAlongSegment = (currentAngle & 0xfffU) - roadInfo.curve->start & 0xf80;
|
||||
|
||||
if (civDat.distAlongSegment <= minDistAlong)
|
||||
civDat.distAlongSegment = minDistAlong;
|
||||
|
||||
segmentLen = (curve->end - curve->start) - segmentLen & 0xfff;
|
||||
segmentLen = (roadInfo.curve->end - roadInfo.curve->start) - segmentLen & 0xfff;
|
||||
|
||||
if (civDat.distAlongSegment >= segmentLen)
|
||||
civDat.distAlongSegment = segmentLen;
|
||||
|
||||
if (ROAD_LANE_DIR(curve, lane) == 0)
|
||||
dir = civDat.distAlongSegment + curve->start + 0x400;
|
||||
if (ROAD_LANE_DIR(roadInfo.curve, lane) == 0)
|
||||
dir = civDat.distAlongSegment + roadInfo.curve->start + 0x400;
|
||||
else
|
||||
dir = civDat.distAlongSegment + curve->start - 0x400;
|
||||
dir = civDat.distAlongSegment + roadInfo.curve->start - 0x400;
|
||||
|
||||
curveLength = ((curve->end - curve->start & 0xfffU) * curve->inside * 11) / 7;
|
||||
curveLength = ((roadInfo.curve->end - roadInfo.curve->start & 0xfffU) * roadInfo.curve->inside * 11) / 7;
|
||||
|
||||
if (lbody * 6 > curveLength) // don't spawn outside curve
|
||||
return 0;
|
||||
@ -4853,7 +4723,7 @@ int PingInCivCar(int minPingInDist)
|
||||
return 0;
|
||||
}
|
||||
|
||||
GetNodePos(straight, NULL, curve, civDat.distAlongSegment, newCar, &newCar->ai.c.targetRoute[0].x, &newCar->ai.c.targetRoute[0].z, lane);
|
||||
GetNodePos(roadInfo.straight, NULL, roadInfo.curve, civDat.distAlongSegment, newCar, &newCar->ai.c.targetRoute[0].x, &newCar->ai.c.targetRoute[0].z, lane);
|
||||
|
||||
retDistSq = 0x7fffffff; // INT_MAX
|
||||
pos[0] = newCar->ai.c.targetRoute[0].x;
|
||||
@ -4983,29 +4853,17 @@ int PingInCivCar(int minPingInDist)
|
||||
void AttemptUnPark(_CAR_DATA * cp)
|
||||
{
|
||||
unsigned char oldLane;
|
||||
int curRoad;
|
||||
DRIVER2_STRAIGHT* straight;
|
||||
DRIVER2_CURVE* curve;
|
||||
DRIVER2_ROAD_INFO roadInfo;
|
||||
|
||||
straight = NULL;
|
||||
curve = NULL;
|
||||
InitCivState(cp, NULL);
|
||||
curRoad = cp->ai.c.currentRoad;
|
||||
|
||||
if (IS_STRAIGHT_SURFACE(curRoad))
|
||||
straight = GET_STRAIGHT(curRoad);
|
||||
else // actually there might be a bug - it might need additional IS_CURVED_SURFACE check
|
||||
curve = GET_CURVE(curRoad);
|
||||
|
||||
oldLane = cp->ai.c.currentLane;
|
||||
|
||||
if (straight && curve)
|
||||
|
||||
if(GetSurfaceRoadInfo(&roadInfo, cp->ai.c.currentRoad))
|
||||
{
|
||||
cp->ai.c.currentLane = CheckChangeLanes(straight, curve, cp->ai.c.targetRoute[0].distAlongSegment, cp, 0);
|
||||
cp->ai.c.currentLane = CheckChangeLanes(roadInfo.straight, roadInfo.curve, cp->ai.c.targetRoute[0].distAlongSegment, cp, 0);
|
||||
|
||||
if (oldLane == cp->ai.c.currentLane ||
|
||||
(straight != NULL && ROAD_IS_AI_LANE(straight, cp->ai.c.currentLane) == 0) ||
|
||||
(curve != NULL && ROAD_IS_AI_LANE(curve, cp->ai.c.currentLane) == 0))
|
||||
if (oldLane == cp->ai.c.currentLane || ROAD_IS_AI_LANE(&roadInfo, cp->ai.c.currentLane) == 0)
|
||||
{
|
||||
// shut off. Unknown intention
|
||||
CIV_STATE_SET_CONFUSED(cp);
|
||||
@ -6890,10 +6748,13 @@ void CreateRoadblock(void)
|
||||
CAR_COSMETICS* car_cos;
|
||||
_CAR_DATA* cp;
|
||||
int distAlongSegment;
|
||||
|
||||
DRIVER2_CURVE* crv;
|
||||
DRIVER2_STRAIGHT* str;
|
||||
|
||||
VECTOR startPos;
|
||||
VECTOR endPos;
|
||||
DRIVER2_STRAIGHT* str;
|
||||
|
||||
VECTOR currentPos;
|
||||
int numLanes;
|
||||
int externalCopModel;
|
||||
|
@ -28,7 +28,7 @@
|
||||
|
||||
|
||||
#define ROAD_LANE_DIR(rd, lane) \
|
||||
(((u_char)rd->LaneDirs == 0xFF && rd->NumLanes == 1) ? (lane & 1) : ROAD_LANE_DIRECTION_BIT(rd, lane))
|
||||
(((u_char)(rd)->LaneDirs == 0xFF && (rd)->NumLanes == 1) ? ((lane) & 1) : ROAD_LANE_DIRECTION_BIT(rd, lane))
|
||||
|
||||
#define ROAD_IS_PARKING_ALLOWED_AT(rd, lane)\
|
||||
((ROAD_IS_LEFTMOST_LANE_PARKING(rd) && (lane) == 0) || (ROAD_IS_RIGHTMOST_LANE_PARKING(rd) && (lane) == ROAD_WIDTH_IN_LANES(rd) - 1))
|
||||
|
@ -569,14 +569,10 @@ void CheckPlayerMiscFelonies(void)
|
||||
int exitId;
|
||||
int _exitId;
|
||||
VECTOR *carPos;
|
||||
DRIVER2_CURVE *cv;
|
||||
DRIVER2_STRAIGHT *st;
|
||||
DRIVER2_ROAD_INFO roadInfo;
|
||||
DRIVER2_JUNCTION *jn;
|
||||
_CAR_DATA* cp;
|
||||
|
||||
cv = NULL;
|
||||
st = NULL;
|
||||
|
||||
if (player[0].playerType == 2 || player[0].playerCarId < 0 || FelonyBar.active == 0)
|
||||
return;
|
||||
|
||||
@ -613,36 +609,50 @@ void CheckPlayerMiscFelonies(void)
|
||||
playerLastRoad = surfInd;
|
||||
goingWrongWay = false;
|
||||
|
||||
// straight or curve
|
||||
if (IS_STRAIGHT_SURFACE(surfInd))
|
||||
if(GetSurfaceRoadInfo(&roadInfo, surfInd))
|
||||
{
|
||||
int lane_count;
|
||||
int lane; // $s0
|
||||
int dx; // $v1
|
||||
int dz; // $a0
|
||||
int lane;
|
||||
int dx;
|
||||
int dz;
|
||||
int crd;
|
||||
|
||||
st = GET_STRAIGHT(surfInd);
|
||||
lane_count = ROAD_WIDTH_IN_LANES(&roadInfo);
|
||||
|
||||
dx = carPos->vx - st->Midx;
|
||||
dz = carPos->vz - st->Midz;
|
||||
|
||||
lane = ROAD_LANES_COUNT(st) - (FIXEDH(dx * rcossin_tbl[(st->angle & 0xfff) * 2 + 1] - dz * rcossin_tbl[(st->angle & 0xfff) * 2]) + 512 >> 9);
|
||||
|
||||
lane_count = ROAD_WIDTH_IN_LANES(st);
|
||||
|
||||
if (lane < 0)
|
||||
lane = 0;
|
||||
|
||||
if (lane_count <= lane)
|
||||
lane = lane_count - 1;
|
||||
|
||||
// check if on correct lane
|
||||
if (ROAD_IS_AI_LANE(st, lane))
|
||||
if(roadInfo.straight)
|
||||
{
|
||||
int crd;
|
||||
crd = (st->angle - cp->hd.direction) + 0x400U >> 0xb & 1;
|
||||
dx = carPos->vx - roadInfo.straight->Midx;
|
||||
dz = carPos->vz - roadInfo.straight->Midz;
|
||||
|
||||
if (ROAD_LANE_DIR(st, lane) == 0)
|
||||
lane = ROAD_LANES_COUNT(&roadInfo) - (FIXEDH(dx * rcossin_tbl[(roadInfo.straight->angle & 0xfff) * 2 + 1] - dz * rcossin_tbl[(roadInfo.straight->angle & 0xfff) * 2]) + 512 >> 9);
|
||||
|
||||
if (lane < 0)
|
||||
lane = 0;
|
||||
|
||||
if (lane_count <= lane)
|
||||
lane = lane_count - 1;
|
||||
|
||||
crd = (roadInfo.straight->angle - cp->hd.direction) + 0x400U >> 0xb & 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
dx = carPos->vx - roadInfo.curve->Midx;
|
||||
dz = carPos->vz - roadInfo.curve->Midz;
|
||||
|
||||
lane = (SquareRoot0(dx * dx + dz * dz) >> 9) - roadInfo.curve->inside * 2;
|
||||
if (lane < 0)
|
||||
lane = 0;
|
||||
|
||||
if (lane >= lane_count)
|
||||
lane = lane_count - 1;
|
||||
|
||||
crd = NotTravellingAlongCurve(carPos->vx, carPos->vz, cp->hd.direction, roadInfo.curve);
|
||||
}
|
||||
|
||||
// check if on correct lane
|
||||
if (ROAD_IS_AI_LANE(&roadInfo, lane))
|
||||
{
|
||||
if (ROAD_LANE_DIR(&roadInfo, lane) == 0)
|
||||
{
|
||||
if (crd == 1)
|
||||
goingWrongWay = true;
|
||||
@ -654,72 +664,26 @@ void CheckPlayerMiscFelonies(void)
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
printInfo("str lane: %d / %d (%d). AI drive: %d, flg: %d%d%d, dir: %d, spd: %d (wrong way: %d)\n",
|
||||
#if 1
|
||||
printInfo("ROAD lane: %d / %d, (%d). AI drive: %d, flg: %d%d%d, dir: %d, spd: %d (wrong way: %d)\n",
|
||||
lane + 1,
|
||||
((u_char)st->NumLanes & 0xF) * 2, // lane count. * 2 for both sides as roads are symmetric
|
||||
IS_NARROW_ROAD(st),
|
||||
((u_char)st->AILanes >> (lane / 2) & 1U), // lane AI driveable flag
|
||||
(st->NumLanes & 0x20) > 0, // flag 0 - first lane?
|
||||
(st->NumLanes & 0x40) > 0, // flag 1 - leftmost park
|
||||
(st->NumLanes & 0x80) > 0, // flag 2 - rightmost park
|
||||
((u_char)st->LaneDirs >> (lane / 2) & 1U), // direction bit
|
||||
((u_char)st->NumLanes >> 4) & 3, // speed limit id
|
||||
((u_char)roadInfo.NumLanes & 0xF) * 2, // lane count. * 2 for both sides as roads are symmetric
|
||||
IS_NARROW_ROAD(&roadInfo),
|
||||
((u_char)roadInfo.AILanes >> (lane / 2) & 1U), // lane AI driveable flag
|
||||
(roadInfo.NumLanes & 0x20) > 0, // flag 0 - first lane?
|
||||
(roadInfo.NumLanes & 0x40) > 0, // flag 1 - leftmost park
|
||||
(roadInfo.NumLanes & 0x80) > 0, // flag 2 - rightmost park
|
||||
((u_char)roadInfo.LaneDirs >> (lane / 2) & 1U), // direction bit
|
||||
((u_char)roadInfo.NumLanes >> 4) & 3, // speed limit id
|
||||
goingWrongWay);
|
||||
#endif
|
||||
|
||||
// get road speed limit
|
||||
maxSpeed = speedLimits[ROAD_SPEED_LIMIT(&roadInfo)];
|
||||
}
|
||||
else if(IS_CURVED_SURFACE(surfInd))
|
||||
else
|
||||
{
|
||||
int lane_count;
|
||||
int lane; // $s0
|
||||
int dx; // $v1
|
||||
int dz; // $a0
|
||||
|
||||
cv = GET_CURVE(surfInd);
|
||||
dx = carPos->vx - cv->Midx;
|
||||
dz = carPos->vz - cv->Midz;
|
||||
|
||||
lane = (SquareRoot0(dx * dx + dz * dz) >> 9) - cv->inside * 2;
|
||||
if (lane < 0)
|
||||
lane = 0;
|
||||
|
||||
lane_count = ROAD_WIDTH_IN_LANES(cv);
|
||||
|
||||
if (lane >= lane_count)
|
||||
lane = lane_count - 1;
|
||||
|
||||
// check if on correct lane
|
||||
if (ROAD_IS_AI_LANE(cv, lane))
|
||||
{
|
||||
int crd;
|
||||
|
||||
crd = NotTravellingAlongCurve(carPos->vx, carPos->vz, cp->hd.direction, cv);
|
||||
|
||||
if (ROAD_LANE_DIR(cv, lane) == 0)
|
||||
{
|
||||
if (crd != 0)
|
||||
goingWrongWay = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (crd == 0)
|
||||
goingWrongWay = true;
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
printInfo("crv lane: %d / %d, (%d). AI drive: %d, flg: %d%d%d, dir: %d, spd: %d (wrong way: %d)\n",
|
||||
lane + 1,
|
||||
((u_char)cv->NumLanes & 0xF) * 2, // lane count. * 2 for both sides as roads are symmetric
|
||||
IS_NARROW_ROAD(cv),
|
||||
((u_char)cv->AILanes >> (lane / 2) & 1U), // lane AI driveable flag
|
||||
(cv->NumLanes & 0x20) > 0, // flag 0 - first lane?
|
||||
(cv->NumLanes & 0x40) > 0, // flag 1 - leftmost park
|
||||
(cv->NumLanes & 0x80) > 0, // flag 2 - rightmost park
|
||||
((u_char)cv->LaneDirs >> (lane / 2) & 1U), // direction bit
|
||||
((u_char)cv->NumLanes >> 4) & 3, // speed limit id
|
||||
goingWrongWay);
|
||||
#endif
|
||||
maxSpeed = speedLimits[2];
|
||||
}
|
||||
|
||||
// wrong way
|
||||
@ -751,13 +715,6 @@ void CheckPlayerMiscFelonies(void)
|
||||
NoteFelony(&felonyData, 10, 0x1000);
|
||||
|
||||
// check the speed limit
|
||||
if (st != NULL)
|
||||
maxSpeed = speedLimits[ROAD_SPEED_LIMIT(st)];
|
||||
else if (cv != NULL)
|
||||
maxSpeed = speedLimits[ROAD_SPEED_LIMIT(cv)];
|
||||
else
|
||||
maxSpeed = speedLimits[2];
|
||||
|
||||
if (speedLimits[2] == maxSpeed)
|
||||
limit = (maxSpeed * 19) >> 4;
|
||||
else
|
||||
|
Loading…
Reference in New Issue
Block a user