Fix testpaint

This commit is contained in:
Ted John 2017-09-02 17:33:12 +01:00
parent b314cc4d74
commit 4ea9ac2d07
4 changed files with 69 additions and 34 deletions

View File

@ -26,6 +26,8 @@ extern "C" {
#include <openrct2/sprites.h>
}
paint_session gPaintSession;
static bool _woodenSupports = false;
static uint8 _callCount = 0;
static function_call _calls[256] = {0};
@ -42,9 +44,9 @@ namespace PaintIntercept {
static uint8 InterceptPaint9C(registers *regs);
static uint8 InterceptPaintFull(uint8 function, registers *regs);
bool PaintMetalSupports(uint8 function, int supportType, uint8 segment, int special, int height, uint32 imageColourFlags);
bool PaintWoodenSupports(uint8 function, int supportType, int special, int height, uint32 imageColourFlags, bool *underground);
static void CheckSegmentSupportHeight();
bool PaintMetalSupports(uint8 function, int supportType, uint8 segment, int special, int height, uint32 imageColourFlags, const support_height * supportSegments);
bool PaintWoodenSupports(uint8 function, int supportType, int special, int height, uint32 imageColourFlags, bool *underground, const paint_struct * prependTo);
static void CheckSegmentSupportHeight(const support_height * supportSegments);
void InitHooks() {
addhook(0x006629BC, InterceptWoodenASupports);
@ -74,7 +76,7 @@ namespace PaintIntercept {
addhook(0x00687902, InterceptPaint9C);
}
bool PaintWoodenSupports(uint8 function, int supportType, int special, int height, uint32 imageColourFlags, bool *underground) {
bool PaintWoodenSupports(uint8 function, int supportType, int special, int height, uint32 imageColourFlags, bool *underground, const paint_struct * prependTo) {
function_call * call = &_calls[_callCount];
call->function = function;
call->supports.type = supportType;
@ -83,11 +85,11 @@ namespace PaintIntercept {
call->supports.colour_flags = imageColourFlags;
call->supports.prepend_to = SPR_NONE;
if (gWoodenSupportsPrependTo != nullptr)
if (prependTo != nullptr)
{
for (int i = 0; i < _callCount; i++)
{
if (&_calls[i].paint.output_struct == gWoodenSupportsPrependTo)
if (&_calls[i].paint.output_struct == prependTo)
{
call->supports.prepend_to = _calls[i].paint.image_id;
break;
@ -100,8 +102,8 @@ namespace PaintIntercept {
return _woodenSupports;
}
bool PaintMetalSupports(uint8 function, int supportType, uint8 segment, int special, int height, uint32 imageColourFlags) {
CheckSegmentSupportHeight();
bool PaintMetalSupports(uint8 function, int supportType, uint8 segment, int special, int height, uint32 imageColourFlags, const support_height * supportSegments) {
CheckSegmentSupportHeight(supportSegments);
function_call * call = &_calls[_callCount];
call->function = function;
@ -175,23 +177,23 @@ namespace PaintIntercept {
static uint8 InterceptMetalASupports(registers *regs)
{
bool output = PaintMetalSupports(SUPPORTS_METAL_A, regs->edi, regs->ebx, (sint16) regs->ax, regs->dx, regs->ebp);
bool output = PaintMetalSupports(SUPPORTS_METAL_A, regs->edi, regs->ebx, (sint16) regs->ax, regs->dx, regs->ebp, gSupportSegments);
return output ? X86_FLAG_CARRY : 0;
}
static uint8 InterceptMetalBSupports(registers *regs)
{
bool output = PaintMetalSupports(SUPPORTS_METAL_B, regs->edi, regs->ebx, (sint16) regs->ax, regs->dx, regs->ebp);
bool output = PaintMetalSupports(SUPPORTS_METAL_B, regs->edi, regs->ebx, (sint16) regs->ax, regs->dx, regs->ebp, gSupportSegments);
return output ? X86_FLAG_CARRY : 0;
}
static void CheckSegmentSupportHeight() {
static void CheckSegmentSupportHeight(const support_height * supportSegments) {
bool hasChanged = false;
for (int i = 0; i < 9; i++) {
if (gSupportSegments[i].height != 0) hasChanged = true;
if (gSupportSegments[i].slope != 0xFF) hasChanged = true;
if (supportSegments[i].height != 0) hasChanged = true;
if (supportSegments[i].slope != 0xFF) hasChanged = true;
}
if (!hasChanged) {
@ -208,7 +210,7 @@ namespace PaintIntercept {
static uint8 InterceptWoodenASupports(registers *regs)
{
bool cf = false;
regs->al = PaintWoodenSupports(SUPPORTS_WOOD_A, regs->edi, regs->ax, regs->dx, regs->ebp, &cf);
regs->al = PaintWoodenSupports(SUPPORTS_WOOD_A, regs->edi, regs->ax, regs->dx, regs->ebp, &cf, gWoodenSupportsPrependTo);
if (cf)
{
@ -221,7 +223,7 @@ namespace PaintIntercept {
static uint8 InterceptWoodenBSupports(registers *regs)
{
bool cf = false;
regs->al = PaintWoodenSupports(SUPPORTS_WOOD_B, regs->edi, regs->ax, regs->dx, regs->ebp, &cf);
regs->al = PaintWoodenSupports(SUPPORTS_WOOD_B, regs->edi, regs->ax, regs->dx, regs->ebp, &cf, gWoodenSupportsPrependTo);
if (cf)
{
@ -307,19 +309,19 @@ namespace PaintIntercept {
extern "C" {
bool wooden_a_supports_paint_setup(int supportType, int special, int height, uint32 imageColourFlags, bool *underground) {
return PaintIntercept::PaintWoodenSupports(SUPPORTS_WOOD_A, supportType, special, height, imageColourFlags, underground);
return PaintIntercept::PaintWoodenSupports(SUPPORTS_WOOD_A, supportType, special, height, imageColourFlags, underground, gPaintSession.WoodenSupportsPrependTo);
}
bool wooden_b_supports_paint_setup(int supportType, int special, int height, uint32 imageColourFlags, bool *underground) {
return PaintIntercept::PaintWoodenSupports(SUPPORTS_WOOD_B, supportType, special, height, imageColourFlags, underground);
return PaintIntercept::PaintWoodenSupports(SUPPORTS_WOOD_B, supportType, special, height, imageColourFlags, underground, gPaintSession.WoodenSupportsPrependTo);
}
bool metal_a_supports_paint_setup(uint8 supportType, uint8 segment, int special, int height, uint32 imageColourFlags) {
return PaintIntercept::PaintMetalSupports(SUPPORTS_METAL_A, supportType, segment, special, height, imageColourFlags);
return PaintIntercept::PaintMetalSupports(SUPPORTS_METAL_A, supportType, segment, special, height, imageColourFlags, gPaintSession.SupportSegments);
}
bool metal_b_supports_paint_setup(uint8 supportType, uint8 segment, int special, int height, uint32 imageColourFlags) {
return PaintIntercept::PaintMetalSupports(SUPPORTS_METAL_B, supportType, segment, special, height, imageColourFlags);
return PaintIntercept::PaintMetalSupports(SUPPORTS_METAL_B, supportType, segment, special, height, imageColourFlags, gPaintSession.SupportSegments);
}
paint_struct *sub_98196C(uint32 image_id, sint8 x_offset, sint8 y_offset, sint16 bound_box_length_x, sint16 bound_box_length_y, sint8 bound_box_length_z, sint16 z_offset, uint32 rotation) {

View File

@ -19,7 +19,7 @@
#include <openrct2/common.h>
extern "C" {
#include <openrct2/paint/map_element/map_element.h>
#include <openrct2/paint/paint.h>
}
enum {

View File

@ -35,6 +35,8 @@ namespace TestPaint
{
void ResetEnvironment() {
gPaintInteractionType = VIEWPORT_INTERACTION_ITEM_RIDE;
gPaintSession.InteractionType = VIEWPORT_INTERACTION_ITEM_RIDE;
gTrackColours[SCHEME_TRACK] = DEFAULT_SCHEME_TRACK;
gTrackColours[SCHEME_SUPPORTS] = DEFAULT_SCHEME_SUPPORTS;
gTrackColours[SCHEME_MISC] = DEFAULT_SCHEME_MISC;
@ -43,6 +45,7 @@ namespace TestPaint
rct_drawpixelinfo dpi = { 0 };
dpi.zoom_level = 1;
unk_140E9A8 = &dpi;
gPaintSession.Unk140E9A8 = &dpi;
rct_ride ride = {0};
ride.entrance_style = RIDE_ENTRANCE_STYLE_PLAIN;
@ -56,23 +59,34 @@ namespace TestPaint
gRideEntries[0] = &rideEntry;
g141E9DB = G141E9DB_FLAG_1 | G141E9DB_FLAG_2;
gPaintSession.Unk141E9DB = G141E9DB_FLAG_1 | G141E9DB_FLAG_2;
}
void ResetTunnels() {
gLeftTunnelCount = 0;
gRightTunnelCount = 0;
gPaintSession.LeftTunnelCount = 0;
gPaintSession.RightTunnelCount = 0;
for (int i = 0; i < TUNNEL_MAX_COUNT; i++) {
gLeftTunnels[i].height = 0;
gLeftTunnels[i].type = 0;
gRightTunnels[i].height = 0;
gRightTunnels[i].type = 0;
gPaintSession.LeftTunnels[i].height = 0;
gPaintSession.LeftTunnels[i].type = 0;
gPaintSession.RightTunnels[i].height = 0;
gPaintSession.RightTunnels[i].type = 0;
}
gLeftTunnels[0].height = 0xFF;
gLeftTunnels[0].type = 0xFF;
gRightTunnels[0].height = 0xFF;
gRightTunnels[0].type = 0xFF;
gPaintSession.LeftTunnels[0].height = 0xFF;
gPaintSession.LeftTunnels[0].type = 0xFF;
gPaintSession.RightTunnels[0].height = 0xFF;
gPaintSession.RightTunnels[0].type = 0xFF;
}
void ResetSupportHeights() {
@ -80,10 +94,14 @@ namespace TestPaint
{
gSupportSegments[s].height = 0;
gSupportSegments[s].slope = 0xFF;
gPaintSession.SupportSegments[s].height = 0;
gPaintSession.SupportSegments[s].slope = 0xFF;
}
gSupport.height = 0;
gSupport.slope = 0xFF;
gPaintSession.Support.height = 0;
gPaintSession.Support.slope = 0xFF;
}
struct IgnoredEntry

View File

@ -272,6 +272,10 @@ static uint8 TestTrackElementPaintCalls(uint8 rideType, uint8 trackType, uint8 t
gSurfaceElement = &surfaceElement;
gDidPassSurface = true;
gPaintSession.CurrentlyDrawnItem = &mapElement;
gPaintSession.SurfaceElement = &surfaceElement;
gPaintSession.DidPassSurface = true;
TestPaint::ResetEnvironment();
TestPaint::ResetTunnels();
@ -359,7 +363,7 @@ static uint8 TestTrackElementPaintCalls(uint8 rideType, uint8 trackType, uint8 t
PaintIntercept::ClearCalls();
testpaint_clear_ignore();
TestPaint::ResetSupportHeights();
gWoodenSupportsPrependTo = nullptr;
gPaintSession.WoodenSupportsPrependTo = nullptr;
CallNew(rideType, trackType, direction, trackSequence, height, &mapElement);
@ -407,13 +411,17 @@ static uint8 TestTrackElementSegmentSupportHeight(uint8 rideType, uint8 trackTyp
mapElement.properties.track.type = trackType;
mapElement.base_height = height / 16;
g_currently_drawn_item = &mapElement;
rct_map_element surfaceElement = {0};
surfaceElement.type = MAP_ELEMENT_TYPE_SURFACE;
surfaceElement.base_height = 2;
gSurfaceElement = &surfaceElement;
gDidPassSurface = true;
gPaintSession.CurrentlyDrawnItem = &mapElement;
gPaintSession.SurfaceElement = &surfaceElement;
gPaintSession.DidPassSurface = true;
TestPaint::ResetEnvironment();
TestPaint::ResetTunnels();
@ -456,8 +464,7 @@ static uint8 TestTrackElementSegmentSupportHeight(uint8 rideType, uint8 trackTyp
continue;
}
std::vector<SegmentSupportCall> newCalls = SegmentSupportHeightCall::getSegmentCalls(gSupportSegments,
direction);
std::vector<SegmentSupportCall> newCalls = SegmentSupportHeightCall::getSegmentCalls(gPaintSession.SupportSegments, direction);
if (!SegmentSupportHeightCall::CallsEqual(referenceCalls, newCalls)) {
*error += String::Format(
"Segment support heights didn't match. [direction:%d] %s\n",
@ -490,6 +497,10 @@ static uint8 TestTrackElementGeneralSupportHeight(uint8 rideType, uint8 trackTyp
gSurfaceElement = &surfaceElement;
gDidPassSurface = true;
gPaintSession.CurrentlyDrawnItem = &mapElement;
gPaintSession.SurfaceElement = &surfaceElement;
gPaintSession.DidPassSurface = true;
TestPaint::ResetEnvironment();
TestPaint::ResetTunnels();
@ -539,11 +550,11 @@ static uint8 TestTrackElementGeneralSupportHeight(uint8 rideType, uint8 trackTyp
if (referenceCall.height != -1) {
if (gSupport.height != referenceCall.height) {
if (gPaintSession.Support.height != referenceCall.height) {
*error += String::Format(
"General support heights didn't match. (expected height + %d, actual: height + %d) [direction:%d] %s\n",
referenceCall.height - height,
gSupport.height - height,
gPaintSession.Support.height - height,
direction,
state.c_str()
);
@ -551,11 +562,11 @@ static uint8 TestTrackElementGeneralSupportHeight(uint8 rideType, uint8 trackTyp
}
}
if (referenceCall.slope != -1) {
if (gSupport.slope != referenceCall.slope) {
if (gPaintSession.Support.slope != referenceCall.slope) {
*error += String::Format(
"General support slopes didn't match. (expected 0x%02X, actual: 0x%02X) [direction:%d] %s\n",
referenceCall.slope,
gSupport.slope,
gPaintSession.Support.slope,
direction,
state.c_str()
);
@ -582,6 +593,10 @@ static uint8 TestTrackElementSideTunnels(uint8 rideType, uint8 trackType, uint8
gSurfaceElement = &surfaceElement;
gDidPassSurface = true;
gPaintSession.CurrentlyDrawnItem = &mapElement;
gPaintSession.SurfaceElement = &surfaceElement;
gPaintSession.DidPassSurface = true;
TestPaint::ResetEnvironment();
TestPaint::ResetTunnels();
@ -635,12 +650,8 @@ static uint8 TestTrackElementSideTunnels(uint8 rideType, uint8 trackType, uint8
}
bool err = false;
newTileTunnelCalls[direction][rightIndex] = SideTunnelCall::ExtractTunnelCalls(gRightTunnels, gRightTunnelCount, height,
&err);
newTileTunnelCalls[direction][leftIndex] = SideTunnelCall::ExtractTunnelCalls(gLeftTunnels, gLeftTunnelCount, height,
&err);
newTileTunnelCalls[direction][rightIndex] = SideTunnelCall::ExtractTunnelCalls(gPaintSession.RightTunnels, gPaintSession.RightTunnelCount, height, &err);
newTileTunnelCalls[direction][leftIndex] = SideTunnelCall::ExtractTunnelCalls(gPaintSession.LeftTunnels, gPaintSession.LeftTunnelCount, height, &err);
if (err) {
*error += "Multiple tunnels on one side aren't supported.\n";
return TEST_FAILED;
@ -698,6 +709,10 @@ static uint8 TestTrackElementVerticalTunnels(uint8 rideType, uint8 trackType, ui
gSurfaceElement = &surfaceElement;
gDidPassSurface = true;
gPaintSession.CurrentlyDrawnItem = &mapElement;
gPaintSession.SurfaceElement = &surfaceElement;
gPaintSession.DidPassSurface = true;
TestPaint::ResetEnvironment();
TestPaint::ResetTunnels();