Files
2025-09-29 00:52:08 +02:00

3887 lines
129 KiB
Scheme
Executable File

//////////////////////////////////////////////////////////////////////////////////////////
// //
// SCRIPT NAME : Towing.sch //
// AUTHOR : Steven Messinger //
// DESCRIPTION : Header for tow truck oddjob //
// //
//////////////////////////////////////////////////////////////////////////////////////////
// including the most common script headers
USING "rage_builtins.sch"
USING "globals.sch"
USING "brains.sch"
USING "script_player.sch"
USING "commands_script.sch"
USING "commands_pad.sch"
USING "commands_graphics.sch"
USING "commands_camera.sch"
USING "commands_streaming.sch"
USING "commands_interiors.sch"
USING "commands_object.sch"
USING "commands_vehicle.sch"
USING "commands_player.sch"
USING "commands_path.sch"
USING "finance_control_public.sch"
USING "player_ped_public.sch"
USING "minigame_private.sch"
USING "timer_public.sch"
USING "timer_globals.sch"
USING "minigame_uiinputs.sch"
USING "Towing_Data.sch"
USING "script_oddjob_funcs.sch"
USING "script_oddjob_queues.sch"
USING "minigame_stats_tracker_helpers.sch"
USING "chase_hint_cam.sch"
USING "minigames_helpers.sch"
USING "completionpercentage_public.sch"
USING "oddjob_aggro.sch"
USING "flow_public_game.sch"
USING "clearmissionarea.sch"
USING "commands_recording.sch"
//USING "Towing.sch"
CONST_FLOAT MIN_TIME 20.0
CONST_INT FAIL_TIME 50000 //50 seconds out of vehicle fail time
CONST_INT FAIL_TIME_TOTAL 300 // 300 seconds total fail time
CONST_INT WARN_TIME_TOTAL 180 // 180 seconds total fail time
CONST_INT MAX_NUM_CAR_NAMES 1 //only 1 broken down car at a time now that patrol has been cut
CONST_INT MAX_NUM_PED_NAMES 2
CONST_INT MAX_NUM_BYSTANDERS 3
CONST_INT MAX_NUM_BROKEN_CARS 1 //max number of current broken down cars
CONST_FLOAT MAX_COMMUTE 70.0
CONST_FLOAT DROP_DISTANCE 11.5
CONST_FLOAT TIMER_X 0.383
CONST_FLOAT TIMER_Y 0.067
CONST_FLOAT FAIL_DISTANCE 450.0
CONST_FLOAT WARN_DISTANCE 400.0
CONST_FLOAT MAX_PATROL_DIST 2500.0
CHASE_HINT_CAM_STRUCT localChaseHintCamStruct
REL_GROUP_HASH relInstructor
AGGRO_ARGS aggroArgs
EAggro aggroReason
NODE_TYPE chosenNodeType
SEQUENCE_INDEX taskSequence
CAMERA_INDEX cam01, cam02
BLIP_INDEX blipTruck
BLIP_INDEX blipTonya
VEHICLE_INDEX vehReplayVehicle
BOOL bPushedOffTrack = FALSE
FLOAT fTotalFine = 0
FLOAT fTotalPayment = 0
FLOAT fObjDist = 0
#IF NOT IS_JAPANESE_BUILD
FLOAT humpMin = 0.8
FLOAT humpMax = 1.5
FLOAT humpThrust = 0.5
structTimer shakeTimer
#ENDIF
VECTOR vDropOffPosition = <<401.5500, -1631.3087, 29.3>>
BOOL bPrintEnter = TRUE
BOOL bPrintObj = TRUE
BOOL bPedCreated = FALSE
BOOL bUpDownPrinted = FALSE
BOOL bSkipped = FALSE
//BOOL bReprintFloatingHelp = FALSE
BOOL bClearAllPrints = FALSE
BOOL bLeftVehicle = FALSE
BOOL bPlayedFirstCovno = FALSE
BOOL bPlayedSecondCovno = FALSE
BOOL bSkippedIntroCutscene = FALSE
BOOL bSkippedSecondCutscene = FALSE
BOOL bSkippedThirdCutscene = FALSE
BOOL bPlayedTruckDialogue = FALSE
BOOL bTonyaGotCarDialogue = FALSE
BOOL bFirstConvoRan = FALSE
BOOL bSecondConvoRan = FALSE
BOOL bLastConvoRan = FALSE
BOOL bPlayTonyaAccidentConvo = FALSE
BOOL bToldToReturnToTonya = FALSE
BOOL bPlayedTonyaUnhookedConvo = FALSE
BOOL bPrintedCraneHelp = FALSE
BOOL bWanted = FALSE
BOOL bPrintObjectiveToImpound = FALSE
BOOL bNoTonyaInterrupt = FALSE
BOOL bNoTonyaWayBackConvo = FALSE
BOOL bPlayShockLine = FALSE
BOOL bDropComplete = FALSE
BOOL bOutOfVehicle = FALSE
BOOL bTowHooked = FALSE
BOOL bPlayedWaitingConvo = FALSE
//STRING sLastFloatingHelpText
INT fUnhookStartTime
INT iCloseBystander
INT iTotalPayment = 0
INT iFirstCutsceneStages = 0
INT iSecondCutsceneStages = 0
INT iThirdCutsceneStages = 0
INT iTonyaStallConvoStages = 0
//INT iStageNum = 0
TEXT_LABEL_23 resumptionLabel
STRING sRootLabel
structPedsForConversation pedConvo
MODEL_NAMES missionCarName = TOWTRUCK
//TODO.. we don't need this full array of data.. We only need our node locations and after selecting a node then fill in data
ILLEGAL_NODE illegalNodes[MAX_NUM_ILLEGAL_NODES]
ACCIDENT_DATA extraData[NUM_ACCIDENT_NODES]
SCENARIO_BLOCKING_INDEX sblockingIndex
structPedsForConversation MyLocalPedStruct
structTimer stagingTimer
structTimer tIntroBufferTimer
structTimer tCutsceneTimer
structTimer tDialogueBufferTimer
structTimer tTonyaStallConvoTimer
structTimer tWaitingConvoTimer
VECTOR vVehicleStartPosition = <<-6.80809, -1465.87268, 29.45427>>
FLOAT fVehicleStartHeading = 275.5635
ENUM TUT_INTRO_CUTSCENE_STATE
TUT_INTRO_CUTSCENE_01 = 0,
TUT_INTRO_CUTSCENE_02,
TUT_INTRO_CUTSCENE_03,
TUT_INTRO_CUTSCENE_04,
TUT_INTRO_CUTSCENE_SKIP_01,
TUT_INTRO_CUTSCENE_SKIP_02
ENDENUM
FUNC BOOL VALIDATE_HINT_CAM(BOOL bCheckHooked = TRUE)
IF bOutOfVehicle OR bDropComplete
// PRINTLN("bOutOfVehicle OR bDropComplete: ", bOutOfVehicle, bDropComplete)
RETURN FALSE
ENDIF
IF bCheckHooked
IF bTowHooked
PRINTLN("bTowHooked ")
RETURN FALSE
ENDIF
ENDIF
RETURN TRUE
ENDFUNC
TUT_INTRO_CUTSCENE_STATE tutorialIntroCutsceneState = TUT_INTRO_CUTSCENE_01
STRUCT STRUCT_INTRO_CUTSCENE
// Intro Cutscene
CAMERA_INDEX camIntro
VECTOR vTutorialPedPosition
VECTOR vPlayerTutorialPosition
VECTOR vCamPosition
VECTOR vCamRotation
FLOAT fPlayerTutorialHeading
FLOAT fTutorialPedHeading
BOOL bRunIntroDialogue
BOOL bSkippedCutscene
structTimer tIntroCutsceneTimer
ENDSTRUCT
STRUCT_INTRO_CUTSCENE stIntroCutscene
ENUM TOW_TUTORIAL
TOW_TUTORIAL_VISIBLE_DIA = 0,
TOW_TUTORIAL_VISIBLE_PRINT,
TOW_TUTORIAL_LINE_UP_DIA,
TOW_TUTORIAL_LINE_UP_PRINT,
TOW_TUTORIAL_LS,
TOW_TUTORIAL_WAIT,
TOW_TUTORIAL_DROPZONE_DIA,
TOW_TUTORIAL_DROPZONE_PRINT,
TOW_TUTORIAL_DROPZONE_WAIT,
TOW_TUTORIAL_DROPZONE_OBJ,
TOW_TUTORIAL_UNHOOK,
TOW_TUTORIAL_WAITHOOK,
TOW_TUTORIAL_DONE
ENDENUM
ENUM STAGING_STATE
STAGING_STATE_INIT = 0,
STAGING_STATE_CLOSE,
STAGING_STATE_PEDS,
STAGING_STATE_TASK,
STAGING_STATE_WAIT,
STAGING_STATE_DONE
ENDENUM
STRUCT BROKEN_VEHICLE
PED_INDEX pedIndex
PED_INDEX pedIndexPass //passenger
PED_INDEX pedBystanders[MAX_NUM_BYSTANDERS]
VEHICLE_INDEX vehicleIndex
VEHICLE_INDEX blockingIndex //double use for the train
BLIP_INDEX blipIndex
BLIP_INDEX blipIndexPed
BLIP_INDEX blipIndexExtra
//INT towIndex
structTimer carTimer
FLOAT pickupTime
BOOL bDoFire
//BOOL bPedTasked
BOOL bCleared
INT speedIDA, speedIDB, SpeedIDC
ENDSTRUCT
STRUCT DECAL_STRUCT
DECAL_ID id
DECAL_RENDERSETTING_ID decal_texture_id
VECTOR pos
VECTOR direction
VECTOR side
FLOAT width
FLOAT height
FLOAT fAlpha
FLOAT life
FLOAT wash_amount
BLIP_INDEX blip
BOOL decal_removed
ENDSTRUCT
STRUCT TOW_CAM_ARGS
CAMERA_INDEX towCam
INT iCamTime
ENDSTRUCT
DECAL_STRUCT stains[2] //holds all of the blood stains
structTimer breakTimer
INT soundID = -1 //horn
INT soundID2 = -1 //breaks squeling
INT soundID3 = -1 //Car trying to start
INT soundID4 = -1 //Crossing bell
CONST_FLOAT fSlowRate 0.35
FLOAT fNewSpeed = 0
TOW_TUTORIAL curTutState = TOW_TUTORIAL_VISIBLE_DIA
//TOW_TUTORIAL nextTutState = TOW_TUTORIAL_LINE_UP
BOOL bHookPlayed = FALSE
//BOOL bUnHookPlayed = FALSE
INT myFrameCount = 0
INT illegalIdx = 0
//
//Uses TIMERA
PROC DO_FOREVER_PRINT(STRING message)//, BOOL bForever = TRUE)
// CLEAR_HELP()
SETTIMERA(0)
//PRINT_HELP_FOREVER(message)
PRINT_HELP(message)
//Reset bools
//bAboveCar = FALSE
//bAboveTow = FALSE
ENDPROC
FUNC INT GET_IDX()
PRINTLN("GET_IDX is returning: ", illegalNodes[illegalIdx].extraDataIndex)
RETURN illegalNodes[illegalIdx].extraDataIndex
ENDFUNC
PROC CLEAR_THIS_HELP(STRING sHelp)
IF IS_THIS_HELP_MESSAGE_BEING_DISPLAYED(sHelp)
CLEAR_HELP()
ENDIF
ENDPROC
PROC CLEAR_TEXT_ON_HOOKING()
CLEAR_THIS_HELP("TOW_TUT_03")
CLEAR_THIS_HELP("TOW_TUT_02")
CLEAR_THIS_HELP("TOW_TUT_01")
CLEAR_THIS_PRINT("TOWT_OBJ_03")
CLEAR_THIS_PRINT("TOWT_OBJ_03a")
CLEAR_THIS_PRINT("TOWT_OBJ_03G")
CLEAR_THIS_PRINT("TOWT_OBJ_03Ga")
CLEAR_THIS_PRINT("TOWT_OBJS_03")
ENDPROC
FUNC BOOL IS_THIS_CONVERSATION_PLAYING(STRING sRoot)
IF IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
TEXT_LABEL txtRoot = GET_CURRENTLY_PLAYING_STANDARD_CONVERSATION_ROOT()
IF ARE_STRINGS_EQUAL(sRoot, txtRoot)
RETURN TRUE
ENDIF
ENDIF
RETURN FALSE
ENDFUNC
FUNC BOOL IS_PLAYER_IN_TOW_TRUCK()
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
VEHICLE_INDEX tempVeh = GET_VEHICLE_PED_IS_IN(PLAYER_PED_ID())
IF NOT IS_ENTITY_DEAD(tempVeh)
IF (GET_PED_IN_VEHICLE_SEAT(tempVeh) = PLAYER_PED_ID())
MODEL_NAMES tempModel = GET_ENTITY_MODEL(tempVeh)
IF (tempModel = TOWTRUCK) OR (tempModel = TOWTRUCK2)
// Cool, he's in a tow truck.
PRINTLN("TOWING SCRIPT: WERE IN A TOW TRUCK - LET'S GO")
RETURN TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
RETURN FALSE
ENDFUNC
PROC TOWING_CHECK_FOR_EARLY_RELEASE(GARAGE_DATA myGarageData, VEHICLE_INDEX vehTowTruck, VEHICLE_INDEX targetCar)
VECTOR vAngledA
VECTOR vAngledB
FLOAT fWidth
IF NOT DOES_ENTITY_EXIST(vehTowTruck) OR NOT DOES_ENTITY_EXIST(targetCar)
PRINTLN("vehTowTruck OR targetCar DOES NOT EXIST")
EXIT
ENDIF
IF IS_ENTITY_DEAD(vehTowTruck) OR IS_ENTITY_DEAD(targetCar)
PRINTLN("vehTowTruck OR targetCar IS DEAD")
EXIT
ENDIF
//If this location has a process zone require the player to be in it
IF NOT IS_VECTOR_ZERO(myGarageData.vProcessZone)
vAngledA = myGarageData.vDropZoneA
vAngledB = myGarageData.vDropZoneB
fWidth = myGarageData.fDropZoneW
ELSE
vAngledA = myGarageData.vCoordinate01
vAngledB = myGarageData.vCoordinate02
fWidth = myGarageData.fWidth
ENDIF
IF NOT bClearAllPrints
IF IS_ENTITY_IN_ANGLED_AREA(targetCar, vAngledA, vAngledB, fWidth, FALSE, TRUE)
PRINTLN("TARGET CAR IS IN THE RIGHT SPOT")
IF NOT IS_ENTITY_DEAD(vehTowTruck) AND NOT IS_ENTITY_DEAD(targetCar)
IF NOT IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(vehTowTruck, targetCar)
PRINTLN("TARGET CAR NO LONGER ATTACHED")
CLEAR_HELP()
CLEAR_PRINTS()
curTutState = TOW_TUTORIAL_DONE
bClearAllPrints = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDPROC
PROC HANDLE_TONYA_STALL_CONVO()
SWITCH iTonyaStallConvoStages
CASE 0
IF NOT IS_TIMER_STARTED(tTonyaStallConvoTimer)
START_TIMER_NOW(tTonyaStallConvoTimer)
ELSE
IF GET_TIMER_IN_SECONDS(tTonyaStallConvoTimer) > 10.0
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TOW_SUGG2", CONV_PRIORITY_VERY_HIGH)
PRINTLN("iTonyaStallConvoStages = 1")
iTonyaStallConvoStages = 1
ENDIF
ENDIF
ENDIF
BREAK
CASE 1
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TOW_RESP", CONV_PRIORITY_VERY_HIGH)
RESTART_TIMER_NOW(tTonyaStallConvoTimer)
PRINTLN("iTonyaStallConvoStages = 2")
iTonyaStallConvoStages = 2
ENDIF
ENDIF
BREAK
CASE 2
IF IS_TIMER_STARTED(tTonyaStallConvoTimer)
IF GET_TIMER_IN_SECONDS(tTonyaStallConvoTimer) > 15.0
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TOW_WAIT", CONV_PRIORITY_VERY_HIGH)
PRINTLN("iTonyaStallConvoStages = 3")
iTonyaStallConvoStages = 3
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
CASE 3
BREAK
ENDSWITCH
ENDPROC
PROC HANDLE_TONYA_UNHOOK_CONVO()
IF NOT bPlayedTonyaUnhookedConvo
IF NOT IS_MESSAGE_BEING_DISPLAYED()
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_UNHOOK", CONV_PRIORITY_VERY_HIGH)
PRINTLN("bPlayedTonyaUnhookedConvo = TRUE")
bPlayedTonyaUnhookedConvo = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDPROC
FUNC BOOL UPDATE_TUTORIAL(VEHICLE_INDEX vehTowTruck, VEHICLE_INDEX targetCar, GARAGE_DATA myGarageData, BLIP_INDEX& myBlip,
VECTOR& vCurDestObjective[], TEXT_LABEL_63& sLastObjective, VECTOR& vDropOff, BOOL bDoTutorial, PED_INDEX& pedTutorial)
//PRINTLN("Player Distance: ", GET_DISTANCE_BETWEEN_ENTITIES(vehTowTruck, targetCar))
VECTOR vAngledA
VECTOR vAngledB
FLOAT fWidth
UNUSED_PARAMETER(vDropOff)
IF curTutState != TOW_TUTORIAL_DONE
// Need to check for an early release.
TOWING_CHECK_FOR_EARLY_RELEASE(myGarageData, vehTowTruck, targetCar)
ENDIF
IF NOT bOutOfVehicle
IF curTutState >= TOW_TUTORIAL_DROPZONE_DIA AND curTutState <= TOW_TUTORIAL_WAITHOOK
IF bDoTutorial // Only do this for the tutorial
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF IS_ENTITY_AT_COORD(PLAYER_PED_ID(), <<400.28537, -1632.59705, 28.29278>>, <<5,5,LOCATE_SIZE_HEIGHT>>, TRUE)
// Do nothing... need this for the chevron
// PRINTLN("DOING CHECK FOR COORDINATE: ", vDropOff)
ENDIF
ENDIF
ENDIF
ENDIF
SWITCH curTutState
CASE TOW_TUTORIAL_VISIBLE_DIA
IF SHOULD_TRIGGER_ENTITY(targetCar, vehTowTruck, myFrameCount, 10, 90, 100)
SET_VEHICLE_TYRES_CAN_BURST(targetCar, FALSE)
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 3, pedTutorial, "TONYA")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INS1", CONV_PRIORITY_VERY_HIGH)
curTutState = TOW_TUTORIAL_VISIBLE_PRINT
ENDIF
BREAK
CASE TOW_TUTORIAL_VISIBLE_PRINT
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
PRINT_HELP("TOW_TUT_03")
SETTIMERA(0)
//bAboveCar = TRUE
curTutState = TOW_TUTORIAL_LINE_UP_DIA
ENDIF
BREAK
CASE TOW_TUTORIAL_LINE_UP_DIA
IF bTowHooked
CLEAR_HELP()
curTutState = TOW_TUTORIAL_LS
ENDIF
IF TIMERA() > 5000
IF (TIMERA() > 12000 OR GET_DISTANCE_BETWEEN_ENTITIES(vehTowTruck, targetCar) < 15)
AND GET_DISTANCE_BETWEEN_ENTITIES(vehTowTruck, targetCar) < 30 //min dist
AND NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INS2", CONV_PRIORITY_VERY_HIGH)
curTutState = TOW_TUTORIAL_LINE_UP_PRINT
ENDIF
ENDIF
BREAK
CASE TOW_TUTORIAL_LINE_UP_PRINT
IF NOT bTowHooked
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
AND NOT IS_THIS_HELP_MESSAGE_BEING_DISPLAYED("TOW_TUT_03")
DO_FOREVER_PRINT("TOW_TUT_02")
//bAboveTow = TRUE
curTutState = TOW_TUTORIAL_LS
ENDIF
ELSE
curTutState = TOW_TUTORIAL_LS
ENDIF
BREAK
CASE TOW_TUTORIAL_LS
IF TIMERA() > 5000 OR bTowHooked//min time
IF (TIMERA() > 12000 OR GET_DISTANCE_BETWEEN_ENTITIES(vehTowTruck, targetCar) < 7.5) OR bTowHooked
AND GET_DISTANCE_BETWEEN_ENTITIES(vehTowTruck, targetCar) < 30 //min dist
bUpDownPrinted = TRUE
bUpDownPrinted = bUpDownPrinted
DO_FOREVER_PRINT("TOW_TUT_01")
curTutState = TOW_TUTORIAL_WAIT //TOW_TUTORIAL_UNHOOK
ENDIF
ENDIF
BREAK
CASE TOW_TUTORIAL_WAIT
IF TIMERA() > 8000
curTutState = TOW_TUTORIAL_DROPZONE_DIA
ENDIF
BREAK
CASE TOW_TUTORIAL_DROPZONE_DIA
//If we didn't tell the player how to move the truck up and down do it here.
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
AND NOT IS_MESSAGE_BEING_DISPLAYED()
AND TIMERA() > 12000
IF NOT bPrintedCraneHelp
PRINT_HELP("TOWT_HELP_CR")
bPrintedCraneHelp = TRUE
PRINTLN("bPrintedCraneHelp = TRUE")
ENDIF
ENDIF
// //TODO this is a bit of a hack to catch the case where CHECK_TOW_ATTACHMNENTS hasn't taken over yet
// IF NOT IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(vehTowTruck, targetCar)
// myBlip = ADD_BLIP_FOR_ENTITY(targetCar)
// SET_BLIP_COLOUR(myBlip, BLIP_COLOUR_BLUE)
// ELIF DOES_BLIP_EXIST(myBlip)
// REMOVE_BLIP(myBlip)
// ENDIF
//PRINTLN("TOW_TUTORIAL_DROPZONE_DIA")
IF IS_ENTITY_IN_ANGLED_AREA(vehTowTruck, myGarageData.vCoordinate01, myGarageData.vCoordinate02, myGarageData.fWidth, FALSE, FALSE)
//Track how long it takes player to get vehicle into processing zone
CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INS4", CONV_PRIORITY_VERY_HIGH)
IF DOES_BLIP_EXIST(myBlip)
SET_BLIP_ROUTE(myBlip, FALSE)
REMOVE_BLIP(myBlip)
ENDIF
sLastObjective = "TOW_TUT_04A"
vCurDestObjective[0] = myGarageData.vProcessZone
fObjDist = GET_PLAYER_DISTANCE_FROM_LOCATION(myGarageData.vProcessZone, FALSE)
myBlip = ADD_BLIP_FOR_COORD(myGarageData.vProcessZone)
SETTIMERB(0)
PRINTLN("TOW_TUTORIAL_DROPZONE_PRINT")
curTutState = TOW_TUTORIAL_DROPZONE_PRINT
ENDIF
BREAK
CASE TOW_TUTORIAL_DROPZONE_PRINT
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF TIMERB() > 6000
PRINTLN("TOW_TUTORIAL_DROPZONE_WAIT")
SETTIMERA(0)
PRINT_NOW("TOW_TUT_04A", DEFAULT_GOD_TEXT_TIME, 1)
curTutState = TOW_TUTORIAL_DROPZONE_OBJ
ENDIF
ENDIF
BREAK
// CASE TOW_TUTORIAL_DROPZONE_WAIT
// //TODO should be a more elegent way to handle this than a bunch of wait states.
// IF TIMERA() > 10000
// PRINTLN("TOW_TUTORIAL_DROPZONE_OBJ")
// CLEAR_HELP()
// bAboveLocation = FALSE
// curTutState = TOW_TUTORIAL_DROPZONE_OBJ
// ENDIF
// BREAK
CASE TOW_TUTORIAL_DROPZONE_OBJ
//We'll shouldn't be here until we have a car hooked
//When you enter the drop area tell the player about the drop zone
IF IS_VECTOR_ZERO(myGarageData.vProcessZone)
PRINTLN("we don't have a special process zone.. skip")
curTutState = TOW_TUTORIAL_UNHOOK
ENDIF
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF IS_ENTITY_IN_ANGLED_AREA(vehTowTruck, myGarageData.vCoordinate01, myGarageData.vCoordinate02, myGarageData.fWidth, FALSE, TRUE)
//Drop vehicle in the ~y~processing area.
fUnhookStartTime = GET_GAME_TIMER()
// PRINT_NOW("TOW_TUT_04A", DEFAULT_GOD_TEXT_TIME, 1)
// sLastObjective = "TOW_TUT_04A"
//Regualr towing missions skip ahead and don't do a full tutorial
IF bSkipped
PRINTLN("bSkipped IS TRUE")
SET_BLIP_ROUTE(myBlip, FALSE)
PRINTLN("CLEARING BLIP ROUTE - 03")
REMOVE_BLIP(myBlip)
vCurDestObjective[0] = myGarageData.vProcessZone
fObjDist = GET_PLAYER_DISTANCE_FROM_LOCATION(myGarageData.vProcessZone, FALSE)
myBlip = ADD_BLIP_FOR_COORD(myGarageData.vProcessZone)
ENDIF
//myBlip = ADD_BLIP_FOR_RADIUS(myGarageData.vProcessZone,5.0) //1.75 x 5.. no idea why
IF DOES_BLIP_EXIST(myBlip)
SET_BLIP_COLOUR(myBlip, BLIP_COLOUR_YELLOW)
ENDIF
curTutState = TOW_TUTORIAL_UNHOOK
ENDIF
ENDIF
BREAK
CASE TOW_TUTORIAL_UNHOOK
//If this location has a process zone require the player to be in it
IF NOT IS_VECTOR_ZERO(myGarageData.vProcessZone)
vAngledA = myGarageData.vDropZoneA
vAngledB = myGarageData.vDropZoneB
fWidth = myGarageData.fDropZoneW
ELSE
vAngledA = myGarageData.vCoordinate01
vAngledB = myGarageData.vCoordinate02
fWidth = myGarageData.fWidth
ENDIF
IF IS_ENTITY_IN_ANGLED_AREA(targetCar, vAngledA, vAngledB, fWidth, FALSE, TRUE)
PRINT_HELP("TOWT_HELP_UH")
// PRINTLN("PRINTING HELP 2")
HANDLE_TONYA_UNHOOK_CONVO()
IF NOT IS_ENTITY_DEAD(vehTowTruck) AND NOT IS_ENTITY_DEAD(targetCar)
IF IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(vehTowTruck, targetCar)
curTutState = TOW_TUTORIAL_WAITHOOK
ENDIF
ENDIF
ELSE
HANDLE_TONYA_STALL_CONVO()
ENDIF
BREAK
CASE TOW_TUTORIAL_WAITHOOK
//If this location has a process zone require the player to be in it
IF NOT IS_VECTOR_ZERO(myGarageData.vProcessZone)
vAngledA = myGarageData.vDropZoneA
vAngledB = myGarageData.vDropZoneB
fWidth = myGarageData.fDropZoneW
ELSE
vAngledA = myGarageData.vCoordinate01
vAngledB = myGarageData.vCoordinate02
fWidth = myGarageData.fWidth
ENDIF
IF IS_ENTITY_IN_ANGLED_AREA(targetCar, vAngledA, vAngledB, fWidth, FALSE, TRUE)
PRINT_HELP("TOWT_HELP_UH")
// PRINTLN("PRINTING HELP 3")
HANDLE_TONYA_UNHOOK_CONVO()
ENDIF
IF DOES_ENTITY_EXIST(vehTowTruck) AND DOES_ENTITY_EXIST(targetCar)
AND NOT IS_ENTITY_DEAD(vehTowTruck)
AND NOT IS_ENTITY_DEAD(targetCar)
IF NOT IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(vehTowTruck, targetCar) //OR TIMERA() > 11000
// CLEAR_THIS_PRINT("TOW_TUT_04")
CLEAR_HELP()
CLEAR_PRINTS()
KILL_CHASE_HINT_CAM(localChaseHintCamStruct)
curTutState = TOW_TUTORIAL_DONE
ENDIF
ENDIF
BREAK
CASE TOW_TUTORIAL_DONE
// PRINTLN("TOW_TUTORIAL_DONE")
BREAK
ENDSWITCH
IF bDoTutorial
//need to be able to skip ahead on unhooking as well
IF DOES_ENTITY_EXIST(vehTowTruck) AND DOES_ENTITY_EXIST(targetCar)
AND NOT IS_ENTITY_DEAD(vehTowTruck)
AND NOT IS_ENTITY_DEAD(targetCar)
IF IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(vehTowTruck, targetCar) AND NOT bHookPlayed
IF IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF IS_HELP_MESSAGE_BEING_DISPLAYED()
PRINTLN("CLEARING HELP")
CLEAR_HELP()
ENDIF
KILL_ANY_CONVERSATION()
PRINTLN("GOING TO STATE - TOW_TUTORIAL_DROPZONE_DIA")
curTutState = TOW_TUTORIAL_DROPZONE_DIA
ELSE
SCRIPT_REMOVE_BLIP_SAFE(myBlip)
SETTIMERA(0)
curTutState = TOW_TUTORIAL_DROPZONE_DIA
CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INS3", CONV_PRIORITY_VERY_HIGH)
bHookPlayed = TRUE
PRINTLN("PLAYING CONVO - TOW_TUT_INS3")
ENDIF
ENDIF
ENDIF
IF NOT bPrintObjectiveToImpound
IF bHookPlayed
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
CLEAR_HELP()
PRINT_NOW("TOWT_OBJ_06", DEFAULT_GOD_TEXT_TIME, 1)
bPrintObjectiveToImpound = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
RETURN FALSE
ENDFUNC
PROC START_BREAKING_PFX(PTFX_ID& sparksEffects[], VEHICLE_INDEX myCar)
sparksEffects[0] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<-0.771, 6.515, -1.507>>, <<0,0,-20>>, 1.15, TRUE)
sparksEffects[1] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<0.771, 6.515, -1.507>>, <<0,0,20>>, 1.15 )
sparksEffects[2] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<-0.771, 3.781, -1.507>>, <<0,0,-20>>, 1.15, TRUE)
sparksEffects[3] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<0.771, 3.781, -1.507>>, <<0,0,20>>, 1.15 )
sparksEffects[4] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<-0.771, -3.743, -1.507>>, <<0,0,-20>>, 1.15, TRUE)
sparksEffects[5] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<0.7711, -3.743, -1.507>>, <<0,0,20>>, 1.15)
sparksEffects[6] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<-0.771, -6.537, -1.507>>, <<0,0,-20>>, 1.15, TRUE )
sparksEffects[7] = START_PARTICLE_FX_LOOPED_ON_ENTITY("scr_ojtt_train_sparks", myCar, <<0.771, -6.537, -1.507>>, <<0,0,20>>, 1.15)
//DATA IS IN BUG# 243490
ENDPROC
PROC STOP_BREAKING_PFX(PTFX_ID& sparksEffects[])
INT idx
REPEAT 8 idx
IF sparksEffects[idx] <> NULL
STOP_PARTICLE_FX_LOOPED(sparksEffects[idx])
sparksEffects[idx] = NULL
ENDIF
ENDREPEAT
ENDPROC
FUNC BOOL SHOULD_WAKE_UP(VEHICLE_INDEX myVehicle, VEHICLE_INDEX targetVehicle, BOOL bSkip)
IF bSkip
RETURN FALSE
ENDIF
BOOL bShouldWakeUp = FALSE
IF IS_PLAYER_PRESSING_HORN(GET_PLAYER_INDEX()) AND GET_PLAYER_DISTANCE_FROM_ENTITY(targetVehicle) < 40
bShouldWakeUp = TRUE
ENDIF
IF IS_ENTITY_TOUCHING_ENTITY(myVehicle, targetVehicle)
bShouldWakeUp = TRUE
ENDIF
IF HAS_ENTITY_BEEN_DAMAGED_BY_ENTITY(targetVehicle, PLAYER_PED_ID())
bShouldWakeUp = TRUE
ENDIF
IF IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
IF IS_PED_IN_VEHICLE(PLAYER_PED_ID(), targetVehicle)
bShouldWakeUp = TRUE
ENDIF
ENDIF
RETURN bShouldWakeUp
ENDFUNC
FUNC VECTOR GET_GOTO_POS(ENTITY_INDEX myCar)
VECTOR vFrontPos
VECTOR vBackPos
vFrontPos = GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(myCar, <<-2,4,0>>)
vBackPos = GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(myCar, <<-2,-4,0>>)
IF GET_PLAYER_DISTANCE_FROM_LOCATION(vFrontPos, FALSE) < GET_PLAYER_DISTANCE_FROM_LOCATION(vBackPos, FALSE)
RETURN vFrontPos
ELSE
RETURN vBackPos
ENDIF
ENDFUNC
FUNC VECTOR GET_GOTO_POS_PASSENGER(ENTITY_INDEX myCar)
VECTOR vFrontPos
VECTOR vBackPos
vFrontPos = GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(myCar, <<2,4,0>>)
vBackPos = GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(myCar, <<2,-4,0>>)
IF GET_PLAYER_DISTANCE_FROM_LOCATION(vFrontPos, FALSE) < GET_PLAYER_DISTANCE_FROM_LOCATION(vBackPos, FALSE)
RETURN vFrontPos
ELSE
RETURN vBackPos
ENDIF
ENDFUNC
#IF NOT IS_JAPANESE_BUILD
FUNC BOOL SHAKE_CAR(ENTITY_INDEX myEntity, PED_INDEX ped)
IF DOES_ENTITY_EXIST(ped)
IF NOT IS_ENTITY_DEAD(ped)
IF NOT IS_PED_IN_ANY_VEHICLE(ped)
RETURN FALSE
ENDIF
ELSE
RETURN FALSE
ENDIF
ENDIF
IF NOT IS_TIMER_STARTED(shakeTimer)
RESTART_TIMER_NOW(shakeTimer)
ENDIF
IF GET_PLAYER_DISTANCE_FROM_ENTITY(myEntity, FALSE) < 15
// DEBUG_MESSAGE("hump 2")
humpMin = 0.3
humpMax = 0.5
humpThrust = 0.1
ELIF GET_PLAYER_DISTANCE_FROM_ENTITY(myEntity, FALSE) < 40
// DEBUG_MESSAGE("hump 1")
humpMin = 0.6
humpMax = 1.0
humpThrust = 0.2
ENDIF
IF TIMER_DO_WHEN_READY(shakeTimer, GET_RANDOM_FLOAT_IN_RANGE(humpMin,humpMax))
RESTART_TIMER_NOW(shakeTimer)
APPLY_FORCE_TO_ENTITY(myEntity, APPLY_TYPE_IMPULSE, <<0.0, 0.0, humpThrust>>, <<-0.0067, -0.8283, -0.2766>>, 0, TRUE, TRUE, TRUE, TRUE)
ENDIF
RETURN TRUE
ENDFUNC
#ENDIF
FUNC BOOL SIMULATE_BREAKING(VEHICLE_INDEX myVehicle)
IF NOT IS_TIMER_STARTED(breakTimer)
START_TIMER_NOW(breakTimer)
ENDIF
FLOAT fCurSpeed
IF DOES_ENTITY_EXIST(myVehicle)
IF NOT IS_ENTITY_DEAD(myVehicle)
fCurSpeed = GET_ENTITY_SPEED(myVehicle)
//PRINTLN("Current train speed: ", fCurSpeed)
ELSE
RETURN FALSE
ENDIF
ENDIF
IF TIMER_DO_WHEN_READY(breakTimer, 0.150)
fNewSpeed = fCurSpeed - fSlowRate
//4.0 min speed
IF fNewSpeed < 8.0
fNewSpeed = 8.0
ENDIF
RESTART_TIMER_NOW(breakTimer)
SET_TRAIN_CRUISE_SPEED(myVehicle, fNewSpeed)
SET_TRAIN_SPEED(myVehicle, fNewSpeed)
ENDIF
RETURN TRUE
ENDFUNC
ENUM MISSION_STATE
MISSION_STATE_CUTSCENE,
MISSION_STATE_INTRO,
MISSION_STATE_CONVERSATION,
MISSION_STATE_CHECK_DISTANCE,
MISSION_STATE_CREATE,
MISSION_STATE_PED,
MISSION_STATE_PRINTS,
MISSION_STATE_TOWING,
MISISON_STATE_PED_ENTER,
MISSION_STATE_DROPOFF,
MISSION_STATE_DROPOFF_NEXT,
MISSION_STATE_DROPOFF_TONYA,
MISSION_STATE_POST_DROPOFF,
MISSION_STATE_TONYA_PHONE_CALL,
MISSION_STATE_SPECIAL_CASE,
MISSION_STATE_ENDUI_SETUP,
MISSION_STATE_ENDUI_WAIT,
MISSION_STATE_COMPLETE
ENDENUM
ENUM INTRO_CUTSCENE
INTRO_CUTSCENE_CREATE = 0,
INTRO_CUTSCENE_DRIVE,
INTRO_CUTSCENE_TRANSITIONA,
INTRO_CUTSCENE_CUTA,
INTRO_CUTSCENE_HOOK,
INTRO_CUTSCENE_TRANSITIONB,
INTRO_CUTSCENE_CUTB,
INTRO_CUTSCENE_UNHOOK,
INTRO_CUTSCENE_CLEANUP,
INTRO_CUTSCENE_FADEIN,
INTRO_CUTSCENE_END
ENDENUM
ENUM ANGRY_PED
ANGRY_PED_INIT = 0,
ANGRY_PED_CREATE,
ANGRY_PED_EXIT,
ANGRY_PED_WAIT,
ANGRY_PED_DIALOUGE,
ANGRY_PED_CHASE,
ANGRY_PED_ENTER,
ANGRY_PED_DRIVE,
ANGRY_PED_DONE
ENDENUM
ENUM TRAIN_STATE
TRAIN_STATE_PRINT = 0,
TRAIN_STATE_WAIT,
TRAIN_STATE_START,
TRAIN_STATE_BREAK,
TRAIN_STATE_CHECKS,
TRAIN_STATE_CHECK_CLEAR,
TRAIN_STATE_STOP,
TRAIN_STATE_OBJ,
TRAIN_STATE_DONE
ENDENUM
ENUM TOW_PED_DIALOUGE
TOW_PED_BEG = 0,
TOW_PED_FACE,
TOW_PED_CHASE,
TOW_PED_END
ENDENUM
ENUM TRAIN_STATE_PED
TRAIN_STATE_PED_INIT = 0,
TRAIN_STATE_PED_FIRST,
TRAIN_STATE_PED_LOOK,
TRAIN_STATE_PED_PANIC,
TRAIN_STATE_PED_PENDING,
TRAIN_STATE_PED_ENTER_TRUCK,
TRAIN_STATE_PED_END
ENDENUM
ENUM BROKEN_STATE
BROKEN_STATE_VISIBLE = 0,
BROKEN_STATE_PED_TALK,
BROKEN_STATE_PED_ENTER,
BROKEN_STATE_DIALOUGE,
BROKEN_STATE_HOOKING,
BROKEN_STATE_TOWING
ENDENUM
CONST_INT DAMAGE_FIRST 250
CONST_INT DAMAGE_SECOND 500
CONST_INT DAMAGE_THIRD 550
CONST_INT DAMAGE_FAIL 900
CONST_INT FINE_SMALL 25
CONST_INT FINE_MEDIUM 75
CONST_INT PAYMENT_NORMAL 500
CONST_INT PAYMENT_MEDIUM 150
ENUM DAMAGE_PRINTS
DAMAGE_PRINTS_FIRST = 0,
DAMAGE_PRINTS_SECOND,
DAMAGE_PRINTS_THIRD,
DAMAGE_PRINTS_FINAL,
DAMAGE_PRINTS_FAIL
ENDENUM
ENUM PED_CONVERSATION
PED_CONVERSATION_INIT = 0,
PED_CONVERSATION_START,
PED_CONVERSATION_RUNNING,
PED_CONVERSATION_INTERRUPT,
PED_CONVERSATION_DONE
ENDENUM
PED_CONVERSATION convState = PED_CONVERSATION_INIT
ENUM INTERRUPT_TYPE
INTERRUPT_INVALID = 0,
INTERRUPT_SHOCKED,
INTERRUPT_DAMAGED,
INTERRUPT_WRONGWAY,
INTERRUPT_HARM,
INTERRUPT_LOSTCAR,
INTERRUPT_DESERT
ENDENUM
INTERRUPT_TYPE interrupt
FUNC BOOL HANDLE_INTERRUPTS(BROKEN_VEHICLE& brokenVehicles[], VEHICLE_INDEX & myVehicle)
IF GET_PLAYER_WANTED_LEVEL(PLAYER_ID()) > 0
OR IS_PED_SHOOTING(PLAYER_PED_ID())
// OR HAS_PLAYER_DAMAGED_AT_LEAST_ONE_NON_ANIMAL_PED(PLAYER_ID())
IF HAS_PLAYER_DAMAGED_AT_LEAST_ONE_NON_ANIMAL_PED(PLAYER_ID())
PRINTLN("HAS_PLAYER_DAMAGED_AT_LEAST_ONE_NON_ANIMAL_PED")
CLEAR_PLAYER_HAS_DAMAGED_AT_LEAST_ONE_NON_ANIMAL_PED(PLAYER_ID())
ENDIF
PRINTLN("interrupt = INTERRUPT_SHOCKED")
interrupt = INTERRUPT_SHOCKED
RETURN TRUE
ENDIF
IF DOES_ENTITY_EXIST(brokenVehicles[0].vehicleIndex) AND NOT IS_ENTITY_DEAD(brokenVehicles[0].vehicleIndex)
AND NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF NOT bPushedOffTrack
IF HAS_ENTITY_BEEN_DAMAGED_BY_ENTITY(brokenVehicles[0].vehicleIndex, PLAYER_PED_ID())
OR HAS_ENTITY_BEEN_DAMAGED_BY_ANY_OBJECT(brokenVehicles[0].vehicleIndex)
OR HAS_ENTITY_BEEN_DAMAGED_BY_ANY_PED(brokenVehicles[0].vehicleIndex)
PRINTLN("interrupt = INTERRUPT_DAMAGED")
interrupt = INTERRUPT_DAMAGED
RETURN TRUE
ENDIF
ENDIF
ENDIF
IF DOES_ENTITY_EXIST(brokenVehicles[0].pedIndex) AND NOT IS_ENTITY_DEAD(brokenVehicles[0].pedIndex)
AND NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF HAS_ENTITY_BEEN_DAMAGED_BY_ENTITY(PLAYER_PED_ID(), brokenVehicles[0].pedIndex)
PRINTLN("interrupt = INTERRUPT_HARM")
interrupt = INTERRUPT_HARM
RETURN TRUE
ENDIF
ENDIF
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myVehicle)
IF NOT IS_PED_IN_VEHICLE(PLAYER_PED_ID(), myVehicle)
PRINTLN("interrupt = INTERRUPT_DESERT")
interrupt = INTERRUPT_DESERT
RETURN TRUE
ENDIF
ENDIF
RETURN FALSE
ENDFUNC
PROC HANDLE_INTERRUPTS_CONVERSATION(structPedsForConversation PedStruct, BROKEN_VEHICLE& brokenVehicles[])
SWITCH interrupt
CASE INTERRUPT_SHOCKED
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Towing")) = 0)
IF chosenNodeType = NODE_TYPE_TRAIN
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_SHOCK", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("bPlayShockLine = TRUE - 01")
CLEAR_PLAYER_HAS_DAMAGED_AT_LEAST_ONE_NON_ANIMAL_PED(PLAYER_ID())
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_SHOCK2", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("bPlayShockLine = TRUE - 02")
CLEAR_PLAYER_HAS_DAMAGED_AT_LEAST_ONE_NON_ANIMAL_PED(PLAYER_ID())
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELSE
IF chosenNodeType = NODE_TYPE_TRAIN
IF g_savedGlobals.sTowingData.iTrainCompleted = 0
OR g_savedGlobals.sTowingData.iTrainCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWTRAINF")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_SHOCKGEN", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 01")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iTrainCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWILLEGALMAN2")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_GENSHOCK", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 02")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF g_savedGlobals.sTowingData.iBreakDownCompleted = 0
OR g_savedGlobals.sTowingData.iBreakDownCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWBREAKM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_SHK", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 03")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iBreakDownCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWBREAKHIPM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_SHK2", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 04")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
CASE INTERRUPT_DAMAGED
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Towing")) = 0)
IF chosenNodeType = NODE_TYPE_TRAIN
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_DAMAGE", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("bPlayShockLine = TRUE - 03")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_DAMAGE2", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("bPlayShockLine = TRUE - 04")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELSE
IF chosenNodeType = NODE_TYPE_TRAIN
IF g_savedGlobals.sTowingData.iTrainCompleted = 0
OR g_savedGlobals.sTowingData.iTrainCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWTRAINF")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_DAMCAR", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 05")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iTrainCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWILLEGALMAN2")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_CARDAM", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 06")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF g_savedGlobals.sTowingData.iBreakDownCompleted = 0
OR g_savedGlobals.sTowingData.iBreakDownCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWBREAKM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_DMG", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 07")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iBreakDownCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWBREAKHIPM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_DMG2", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 08")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
CASE INTERRUPT_HARM
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Towing")) = 0)
IF chosenNodeType = NODE_TYPE_TRAIN
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_HARM", CONV_PRIORITY_MEDIUM)
PRINTLN("bPlayShockLine = TRUE")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_HARM_PED", CONV_PRIORITY_MEDIUM)
PRINTLN("bPlayShockLine = TRUE")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELSE
IF chosenNodeType = NODE_TYPE_TRAIN
IF g_savedGlobals.sTowingData.iTrainCompleted = 0
OR g_savedGlobals.sTowingData.iTrainCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWTRAINF")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_HARMED", CONV_PRIORITY_MEDIUM)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 09")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iTrainCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWILLEGALMAN2")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_HARM2", CONV_PRIORITY_MEDIUM)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 10")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF g_savedGlobals.sTowingData.iBreakDownCompleted = 0
OR g_savedGlobals.sTowingData.iBreakDownCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWBREAKM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_HRM", CONV_PRIORITY_MEDIUM)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 11")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iBreakDownCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWBREAKHIPM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_HRM2", CONV_PRIORITY_MEDIUM)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 12")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
CASE INTERRUPT_DESERT
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Towing")) = 0)
IF chosenNodeType = NODE_TYPE_TRAIN
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_DESERT", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("bPlayShockLine = TRUE - 05")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_DESERT2", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("bPlayShockLine = TRUE - 06")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELSE
IF chosenNodeType = NODE_TYPE_TRAIN
IF g_savedGlobals.sTowingData.iTrainCompleted = 0
OR g_savedGlobals.sTowingData.iTrainCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWTRAINF")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_DESERTED", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 13")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iTrainCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWILLEGALMAN2")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_DESERTD2", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 14")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF g_savedGlobals.sTowingData.iBreakDownCompleted = 0
OR g_savedGlobals.sTowingData.iBreakDownCompleted = 1
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 5, brokenVehicles[0].pedIndex, "TOWBREAKM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_DSRT", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 15")
bPlayShockLine = TRUE
ENDIF
ENDIF
ELIF g_savedGlobals.sTowingData.iBreakDownCompleted = 2
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 6, brokenVehicles[0].pedIndex, "TOWBREAKHIPM")
IF NOT bPlayShockLine
IF CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_BRK_DESR", CONV_PRIORITY_MEDIUM, DO_NOT_DISPLAY_SUBTITLES)
PRINTLN("PROCEDURAL: bPlayShockLine = TRUE - 16")
bPlayShockLine = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
ENDSWITCH
ENDPROC
FUNC BOOL HANDLE_RESET(VEHICLE_INDEX & myVehicle)
SWITCH interrupt
CASE INTERRUPT_SHOCKED
IF GET_PLAYER_WANTED_LEVEL(PLAYER_ID()) = 0
AND NOT IS_PED_SHOOTING(PLAYER_PED_ID())
// PRINTLN("RESET - INTERRUPT_SHOCKED")
bPlayShockLine = FALSE
RETURN TRUE
ENDIF
BREAK
CASE INTERRUPT_DAMAGED
BREAK
CASE INTERRUPT_HARM
BREAK
CASE INTERRUPT_DESERT
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myVehicle)
IF IS_PED_IN_VEHICLE(PLAYER_PED_ID(), myVehicle)
// PRINTLN("RESET - INTERRUPT_DESERT")
bPlayShockLine = FALSE
RETURN TRUE
ENDIF
ENDIF
BREAK
ENDSWITCH
RETURN FALSE
ENDFUNC
PROC HANDLE_POST_REPEATABLE_CONVO_TRAIN(structPedsForConversation PedStruct, BROKEN_VEHICLE& brokenVehicles[])
ADD_PED_FOR_DIALOGUE(PedStruct, 3, brokenVehicles[0].pedIndex, "TOWPEDC")
PRINTLN("g_savedGlobals.sTowingData.iTrainCompleted = ", g_savedGlobals.sTowingData.iTrainCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_GEN_MCH2", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_GEN_MCH2"
ENDPROC
PROC HANDLE_POST_REPEATABLE_CONVO_DYNAMIC(structPedsForConversation PedStruct, BROKEN_VEHICLE& brokenVehicles[])
INT iRand
iRand = GET_RANDOM_INT_IN_RANGE() % 4
IF iRand = 0
ADD_PED_FOR_DIALOGUE(PedStruct, 3, brokenVehicles[0].pedIndex, "TOWPEDA")
PRINTLN("SHOULD BE POST REPEATABLE - TOWPEDA, iRand = ", iRand)
PRINTLN("g_savedGlobals.sTowingData.iBreakDownCompleted = ", g_savedGlobals.sTowingData.iBreakDownCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_GEN_MCH", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_GEN_MCH"
ELIF iRand = 1
ADD_PED_FOR_DIALOGUE(PedStruct, 3, brokenVehicles[0].pedIndex, "TOWPEDB")
PRINTLN("SHOULD BE POST REPEATABLE - TOWPEDB, iRand = ", iRand)
PRINTLN("g_savedGlobals.sTowingData.iBreakDownCompleted = ", g_savedGlobals.sTowingData.iBreakDownCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_GEN_MCH1", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_GEN_MCH1"
ELIF iRand = 2
ADD_PED_FOR_DIALOGUE(PedStruct, 3, brokenVehicles[0].pedIndex, "TOWPEDD")
PRINTLN("SHOULD BE POST REPEATABLE - TOWPEDD, iRand = ", iRand)
PRINTLN("g_savedGlobals.sTowingData.iBreakDownCompleted = ", g_savedGlobals.sTowingData.iBreakDownCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_GEN_MCH3", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_GEN_MCH3"
ELIF iRand = 3
ADD_PED_FOR_DIALOGUE(PedStruct, 3, brokenVehicles[0].pedIndex, "TOWPEDE")
PRINTLN("SHOULD BE POST REPEATABLE - TOWPEDE, iRand = ", iRand)
PRINTLN("g_savedGlobals.sTowingData.iBreakDownCompleted = ", g_savedGlobals.sTowingData.iBreakDownCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD", "TOW_GEN_MCH4", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_GEN_MCH4"
ENDIF
ENDPROC
PROC MANAGE_PED_CONVERSATION(structPedsForConversation PedStruct, BROKEN_VEHICLE& brokenVehicles[], VEHICLE_INDEX & myVehicle)
// PRINTLN("INSIDE - MANAGE_PED_CONVERSATION")
IF NOT bNoTonyaInterrupt
// PRINTLN("bNoTonyaInterrupt IS FALSE")
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF convState > PED_CONVERSATION_START
IF HANDLE_INTERRUPTS(brokenVehicles, myVehicle)
IF IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
resumptionLabel = GET_STANDARD_CONVERSATION_LABEL_FOR_FUTURE_RESUMPTION()
PRINTLN("KILLING ANY CONVERSATION THAT MIGHT BE ONGOING")
KILL_FACE_TO_FACE_CONVERSATION()
bNoTonyaInterrupt = TRUE
PRINTLN("bNoTonyaInterrupt = TRUE")
convState = PED_CONVERSATION_INTERRUPT
ELSE
bNoTonyaInterrupt = TRUE
PRINTLN("bNoTonyaInterrupt = TRUE - 01")
convState = PED_CONVERSATION_INTERRUPT
ENDIF
ELSE
// PRINTLN("HANDLE_INTERRUPTS IS FALSE")
ENDIF
ENDIF
ENDIF
ELSE
// PRINTLN("bNoTonyaInterrupt IS TRUE")
ENDIF
SWITCH convState
CASE PED_CONVERSATION_INIT
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
SETTIMERA(0)
PRINTLN("GOING TO STATE - PED_CONVERSATION_START")
convState = PED_CONVERSATION_START
ENDIF
BREAK
CASE PED_CONVERSATION_START
IF TIMERA() > 3000
AND bTowHooked
AND NOT IS_THIS_PRINT_BEING_DISPLAYED("TOWT_OBJ_04")
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
ADD_PED_FOR_DIALOGUE(PedStruct, 1, PLAYER_PED_ID(), "FRANKLIN")
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya3")) = 1)
OR (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya4")) = 1)
IF chosenNodeType = NODE_TYPE_TRAIN
CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_TRN_C1", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_TRN_C1"
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_BRK_C", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_BRK_C"
PRINTLN("CALLING CONVERSATION - TOW_BRK_C")
ENDIF
bNoTonyaWayBackConvo = TRUE
ELSE
IF chosenNodeType = NODE_TYPE_TRAIN
IF g_savedGlobals.sTowingData.iTrainCompleted = 0
OR g_savedGlobals.sTowingData.iTrainCompleted = 1
ADD_PED_FOR_DIALOGUE(PedStruct, 5, brokenVehicles[0].pedIndex, "TOWTRAINF")
PRINTLN("g_savedGlobals.sTowingData.iTrainCompleted = ", g_savedGlobals.sTowingData.iTrainCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_MECH", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_MECH"
ELIF g_savedGlobals.sTowingData.iTrainCompleted = 2
ADD_PED_FOR_DIALOGUE(PedStruct, 6, brokenVehicles[0].pedIndex, "TOWILLEGALMAN2")
PRINTLN("g_savedGlobals.sTowingData.iTrainCompleted = ", g_savedGlobals.sTowingData.iTrainCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_MECH2", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_MECH2"
ELSE
HANDLE_POST_REPEATABLE_CONVO_TRAIN(PedStruct, brokenVehicles)
ENDIF
bNoTonyaWayBackConvo = TRUE
ELIF chosenNodeType = NODE_TYPE_DYNAMIC
IF g_savedGlobals.sTowingData.iBreakDownCompleted = 0
OR g_savedGlobals.sTowingData.iBreakDownCompleted = 1
ADD_PED_FOR_DIALOGUE(PedStruct, 5, brokenVehicles[0].pedIndex, "TOWBREAKM")
PRINTLN("g_savedGlobals.sTowingData.iBreakDownCompleted = ", g_savedGlobals.sTowingData.iBreakDownCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_BRK_CONV", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_BRK_CONV"
ELIF g_savedGlobals.sTowingData.iBreakDownCompleted = 2
ADD_PED_FOR_DIALOGUE(PedStruct, 6, brokenVehicles[0].pedIndex, "TOWBREAKHIPM")
PRINTLN("g_savedGlobals.sTowingData.iBreakDownCompleted = ", g_savedGlobals.sTowingData.iBreakDownCompleted)
CREATE_CONVERSATION(PedStruct, "TOWAUD","TOW_BRK_CON2", CONV_PRIORITY_MEDIUM)
sRootLabel = "TOW_BRK_CON2"
ELSE
HANDLE_POST_REPEATABLE_CONVO_DYNAMIC(PedStruct, brokenVehicles)
ENDIF
bNoTonyaWayBackConvo = TRUE
ENDIF
ENDIF
ELSE
IF IS_THIS_CONVERSATION_PLAYING(sRootLabel)
PRINTLN("CONVERSATION HAS STARTED - GOING TO STATE: PED_CONVERSATION_RUNNING")
convState = PED_CONVERSATION_RUNNING
ENDIF
ENDIF
ENDIF
BREAK
CASE PED_CONVERSATION_INTERRUPT
PRINTLN("PED_CONVERSATION_INTERRUPT")
HANDLE_INTERRUPTS_CONVERSATION(PedStruct, brokenVehicles)
IF bPlayShockLine
PRINTLN("CONVERSATION HAS STARTED - GOING TO STATE: PED_CONVERSATION_RUNNING")
convState = PED_CONVERSATION_RUNNING
ENDIF
BREAK
CASE PED_CONVERSATION_RUNNING
IF HANDLE_RESET(myVehicle)
IF bNoTonyaWayBackConvo // To check if we've started the long conversation
IF bNoTonyaInterrupt
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF CREATE_CONVERSATION_FROM_SPECIFIC_LINE(MyLocalPedStruct, "TOWAUD", sRootLabel, resumptionLabel, CONV_PRIORITY_HIGH)
PRINTLN("TRYING TO RESUME INTERRUPTED LINE")
bNoTonyaInterrupt = FALSE
PRINTLN("GOING TO STATE - PED_CONVERSATION_DONE VIA INTERRUPT")
convState = PED_CONVERSATION_DONE
ENDIF
ELSE
PRINTLN("CONVERSATION IS ONGOING OR QUEUED")
ENDIF
ELSE
PRINTLN("PED_CONVERSATION_RUNNING: bNoTonyaInterrupt IS FALSE")
ENDIF
ELSE
PRINTLN("bNoTonyaWayBackConvo IS FALSE")
ENDIF
ELSE
PRINTLN("HANDLE_RESET IS FALSE - 01")
ENDIF
BREAK
CASE PED_CONVERSATION_DONE
HANDLE_RESET(myVehicle)
BREAK
ENDSWITCH
ENDPROC
PROC INIT_DAMAGE_TRACKING(VEHICLE_INDEX myCar, INT& iLastHealth, INT& iInitialHealth)
IF DOES_ENTITY_EXIST(myCar)
iLastHealth = GET_ENTITY_HEALTH(myCar)
iInitialHealth = iLastHealth
ENDIF
ENDPROC
//TODO it would be nice to merge this with UPDATE_DAMAGE_TRACKING and just modify the data / variables...
FUNC BOOL UPDATE_TOWTRUCK_DAMAGE_TRACKING(DAMAGE_PRINTS& printState, VEHICLE_INDEX myTowTruck, INT& iLastHealth, INT& iHealthDelta, BOOL bPostTonya)
// INT iTemp
INT curDelta
IF DOES_ENTITY_EXIST(myTowTruck)
curDelta = iLastHealth - GET_ENTITY_HEALTH(myTowTruck)
ENDIF
//fix for release compile
IF fTotalFine = 0
ENDIF
IF curDelta > 0
//Can we properly blame this damage on the player?
IF DOES_ENTITY_EXIST(myTowTruck)
IF NOT IS_ENTITY_DEAD( myTowTruck)
IF (IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID()) AND IS_PED_IN_VEHICLE(PLAYER_PED_ID(), myTowTruck))
OR HAS_ENTITY_BEEN_DAMAGED_BY_ENTITY(myTowTruck, PLAYER_PED_ID())
iHealthDelta += curDelta
ELSE
IF DOES_ENTITY_EXIST(myTowTruck)
iLastHealth = GET_ENTITY_HEALTH(myTowTruck)
curDelta = 0
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
// iTemp = GET_ENTITY_HEALTH(myTowTruck)
// PRINTLN("TOW TRUCK HEALTH = ", iTemp)
SWITCH printState
CASE DAMAGE_PRINTS_FIRST
IF iHealthDelta > DAMAGE_FIRST
//PRINT_HELP_WITH_NUMBER("TOW_DMG_01", FINE_SMALL)
IF bPostTonya
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DMA", CONV_PRIORITY_HIGH)
PRINTLN("GIVING PLAYER POST TONYA WARNING - TOW_DISP_DMA")
printState = DAMAGE_PRINTS_SECOND
ENDIF
ELSE
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DMT", CONV_PRIORITY_HIGH)
PRINTLN("TONYA WARNING PLAYER ON DAMAGING TRUCK - TOW_DISP_DMT")
printState = DAMAGE_PRINTS_SECOND
ENDIF
ENDIF
IF bPostTonya
//DEBIT_BANK_ACCOUNT(GET_CURRENT_PLAYER_PED_ENUM(), BAAC_UNLOGGED_SMALL_ACTION, FINE_SMALL)
fTotalFine += FINE_SMALL
PRINTLN("DAMAGE TRACKING FIRST: fTotalFine = ", fTotalFine)
ENDIF
ENDIF
BREAK
CASE DAMAGE_PRINTS_SECOND
IF iHealthDelta > DAMAGE_SECOND
//PRINT_HELP_WITH_NUMBER("TOW_DMG_01", FINE_SMALL)
IF bPostTonya
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DMA", CONV_PRIORITY_HIGH)
PRINTLN("GIVING PLAYER POST TONYA WARNING - TOW_DISP_DMA")
printState = DAMAGE_PRINTS_THIRD
ENDIF
ELSE
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DT2", CONV_PRIORITY_HIGH)
PRINTLN("TONYA WARNING PLAYER ON DAMAGING TRUCK - TOW_DISP_DT2")
printState = DAMAGE_PRINTS_THIRD
ENDIF
ENDIF
IF bPostTonya
//DEBIT_BANK_ACCOUNT(GET_CURRENT_PLAYER_PED_ENUM(), BAAC_UNLOGGED_SMALL_ACTION, FINE_SMALL)
fTotalFine += FINE_SMALL
PRINTLN("DAMAGE TRACKING FIRST: fTotalFine = ", fTotalFine)
ENDIF
ENDIF
BREAK
CASE DAMAGE_PRINTS_THIRD
IF iHealthDelta > DAMAGE_FAIL
//PRINT_HELP_WITH_NUMBER("TOW_DMG_01", FINE_MEDIUM)
IF bPostTonya
CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DMB", CONV_PRIORITY_HIGH)
PRINTLN("GIVING PLAYER SECOND WARNING POST TONYA - TOW_DISP_DMB")
printState = DAMAGE_PRINTS_FINAL
ELSE
CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DT2", CONV_PRIORITY_HIGH)
PRINTLN("GIVING PLAYER SECOND WARNING POST TONYA - TOW_DISP_DT2")
printState = DAMAGE_PRINTS_FINAL
ENDIF
IF bPostTonya
//DEBIT_BANK_ACCOUNT(GET_CURRENT_PLAYER_PED_ENUM(), BAAC_UNLOGGED_SMALL_ACTION, FINE_MEDIUM)
fTotalFine += FINE_MEDIUM
PRINTLN("DAMAGE TRACKING SECOND: fTotalFine = ", fTotalFine)
ENDIF
ENDIF
BREAK
CASE DAMAGE_PRINTS_FINAL
BREAK
ENDSWITCH
IF DOES_ENTITY_EXIST(myTowTruck)
iLastHealth = GET_ENTITY_HEALTH(myTowTruck)
ENDIF
RETURN FALSE
ENDFUNC
FUNC BOOL UPDATE_DAMAGE_TRACKING(DAMAGE_PRINTS& printState, VEHICLE_INDEX myCar, VEHICLE_INDEX myTowTruck, INT& iLastHealth,
INT& iHealthDelta, BOOL bPostTonya)
INT curDelta
IF DOES_ENTITY_EXIST(myCar)
curDelta = iLastHealth - GET_ENTITY_HEALTH(myCar)
ENDIF
IF bPostTonya
IF curDelta > 0
//Can we properly blame this damage on the player?
IF DOES_ENTITY_EXIST(myCar) AND DOES_ENTITY_EXIST(myTowTruck)
IF NOT IS_ENTITY_DEAD(myCar) AND NOT IS_ENTITY_DEAD( myTowTruck)
IF IS_ENTITY_TOUCHING_ENTITY(myCar, myTowTruck) OR IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(myTowTruck, myCar)
OR HAS_ENTITY_BEEN_DAMAGED_BY_ENTITY(myCar, PLAYER_PED_ID())
iHealthDelta += curDelta
ELSE
IF DOES_ENTITY_EXIST(myCar)
iLastHealth = GET_ENTITY_HEALTH(myCar)
curDelta = 0
ENDIF
ENDIF
ENDIF
ENDIF
ELSE
//do nothing
ENDIF
SWITCH printState
CASE DAMAGE_PRINTS_FIRST
IF iHealthDelta > DAMAGE_FIRST
printState = DAMAGE_PRINTS_SECOND
PRINT_HELP_WITH_NUMBER("TOW_DMG_01", FINE_SMALL)
// CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DM1", CONV_PRIORITY_HIGH)
DEBIT_BANK_ACCOUNT(GET_CURRENT_PLAYER_PED_ENUM(), BAAC_UNLOGGED_SMALL_ACTION, FINE_SMALL)
fTotalFine += FINE_SMALL
PRINTLN("FIRST OFFENSE: fTotalFine = ", fTotalFine)
ENDIF
BREAK
CASE DAMAGE_PRINTS_SECOND
IF iHealthDelta > DAMAGE_SECOND
printState = DAMAGE_PRINTS_THIRD
PRINT_HELP_WITH_NUMBER("TOW_DMG_01", FINE_MEDIUM)
// CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DM2", CONV_PRIORITY_HIGH)
DEBIT_BANK_ACCOUNT(GET_CURRENT_PLAYER_PED_ENUM(), BAAC_UNLOGGED_SMALL_ACTION, FINE_MEDIUM)
fTotalFine += FINE_MEDIUM
PRINTLN("SECOND OFFENSE: fTotalFine = ", fTotalFine)
ENDIF
BREAK
CASE DAMAGE_PRINTS_THIRD
IF iHealthDelta > DAMAGE_THIRD
printState = DAMAGE_PRINTS_FINAL
PRINT_HELP("TOW_DMG_03")
// CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_DISP_DM3", CONV_PRIORITY_HIGH)
//no fine for now..
ENDIF
BREAK
CASE DAMAGE_PRINTS_FINAL
IF iHealthDelta > DAMAGE_FAIL
RETURN FALSE
ENDIF
BREAK
ENDSWITCH
ENDIF
IF DOES_ENTITY_EXIST(myCar)
iLastHealth = GET_ENTITY_HEALTH(myCar)
ENDIF
RETURN TRUE
ENDFUNC
FUNC INT FIND_FIRST_OPEN(BROKEN_VEHICLE& brokenVehicles[])
INT idx
REPEAT MAX_NUM_BROKEN_CARS idx
IF brokenVehicles[idx].vehicleIndex = NULL
RETURN idx
ENDIF
ENDREPEAT
RETURN -1
ENDFUNC
FUNC BOOL GET_POINT(VECTOR& returnVec, FLOAT& returnHeading, VECTOR& vExtra1, VECTOR& vExtra2)
PRINTLN("Get_Point")
VECTOR vOffset
UNUSED_PARAMETER(vExtra2)
// Get num of lanes, required with using NATIVE function below
INT iNumLanes, iNode
// Return by ref values
VECTOR vNodePos
//Four Directions
FLOAT fXoffset = 0
FLOAT fYoffset = 0
INT rand
rand = GET_RANDOM_INT_IN_RANGE(0,3999) / 1000
IF rand = 0
//left
fXoffset = -GET_RANDOM_FLOAT_IN_RANGE(450, 700)
fYoffset = GET_RANDOM_FLOAT_IN_RANGE(-100, 100)
ELIF rand = 1
//for now no right
fXoffset = GET_RANDOM_FLOAT_IN_RANGE(450, 700)
fYoffset = GET_RANDOM_FLOAT_IN_RANGE(100, 100)
ELIF rand = 2
//in front
fYoffset = GET_RANDOM_FLOAT_IN_RANGE(450, 700)
fXoffset = GET_RANDOM_FLOAT_IN_RANGE(-100, 100)
ELSE
//behind
fYoffset = -GET_RANDOM_FLOAT_IN_RANGE(450, 700)
fXoffset = GET_RANDOM_FLOAT_IN_RANGE(-100, 100)
ENDIF
vOffset = GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(PLAYER_PED_ID(), <<fXoffset, fYOffset, 0>>)
// Once the node has been returned and perhaps sent to a client the coordinates to spawn a car can be found using GET_SPAWN_COORDINATES_FOR_CAR_NODE
//PARAM NOTES:
//PURPOSE: Will return a random node to satisfy the specified conditions. More info..
IF NOT GET_RANDOM_VEHICLE_NODE( vOffset, 10.0, 1, TRUE, TRUE, vNodePos, iNode)
RETURN FALSE
ENDIF
GET_NTH_CLOSEST_VEHICLE_NODE_WITH_HEADING(vNodePos, 2, vExtra1, returnHeading, iNumLanes)
// Grab vehicle note position/orientation based on an offset from the direction the player is facing
//GET_NTH_CLOSEST_VEHICLE_NODE_WITH_HEADING(vOffset, 2, vNodePos, returnHeading, iNumLanes)
//GET_NTH_CLOSEST_VEHICLE_NODE_WITH_HEADING(vOffset, 3, vExtra2, returnHeading, iNumLanes)
//GET_CLOSEST_VEHICLE_NODE_WITH_HEADING(<< -67.7994, -1344.1205, 28.2917 >>, vNodePos, returnHeading )
//Run some tests on vNodePos
returnVec = vNodePos
// Override if we're doing Tonya mission.
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya4")) = 1)
PRINTLN("OVERRIDING DYNAMIC SPAWN LOCATION USED IN TONYA MISSION")
returnVec = <<-476.1537, 132.6556, 62.9586>>
returnHeading = 87.9510
ENDIF
// Check against a zero vector, i.e. empty node
IF ARE_VECTORS_EQUAL(returnVec, <<0,0,0>>)
PRINTSTRING("VECTOR IS ZERO, RETURNING FALSE!!!")
RETURN FALSE
ENDIF
RETURN TRUE
ENDFUNC
#IF IS_DEBUG_BUILD
PROC DEBUG_DARW_BLIPS()
INT idx
BLIP_INDEX tempBlip
REPEAT MAX_NUM_ILLEGAL_NODES idx
tempBlip = ADD_BLIP_FOR_COORD(illegalNodes[idx].vCarPos)
SWITCH illegalNodes[idx].myType
CASE NODE_TYPE_ABANDON
SET_BLIP_COLOUR(tempBlip, BLIP_COLOUR_GREEN)
SET_BLIP_NAME_FROM_ASCII(tempBlip, "Abandonded Car")
BREAK
CASE NODE_TYPE_HANDI
SET_BLIP_COLOUR(tempBlip, BLIP_COLOUR_BLUE)
SET_BLIP_NAME_FROM_ASCII(tempBlip, "Handicap Spot")
BREAK
CASE NODE_TYPE_TRAIN
SET_BLIP_COLOUR(tempBlip, BLIP_COLOUR_RED)
SET_BLIP_NAME_FROM_ASCII(tempBlip, "Train Clearing")
BREAK
ENDSWITCH
ENDREPEAT
tempBlip = ADD_BLIP_FOR_COORD(vImpound[0])
SET_BLIP_COLOUR(tempBlip, BLIP_COLOUR_WHITE)
SET_BLIP_NAME_FROM_ASCII(tempBlip, "Impound")
ENDPROC
#ENDIF
FUNC BOOL GET_FORWARD_POINT(VECTOR &vSpawnPos, FLOAT &fSpawnOri, FLOAT iNodeOffsetToCheck = 200.0)
// If the player is not in a vehicle, exit early.
IF NOT IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
RETURN FALSE
ENDIF
// Players Initial Position/Orientation - WITHOUT DIRECTION
VECTOR tempPlayerPos
FLOAT tempPlayerRot
// Vehicle Node Position/Orientation - WITHOUT DIRECTION
VECTOR vNodePos
FLOAT fNodeOri
// Constructed vectors - WITH DIRECTION
VECTOR vPlayerDir, vNodeDirAlt
// Get num of lanes, required with using NATIVE function below
INT iNumLanes
// Get the player position and heading
tempPlayerPos = GET_ENTITY_COORDS(PLAYER_PED_ID())
tempPlayerRot = GET_ENTITY_HEADING(PLAYER_PED_ID())
// Grab vehicle note position/orientation based on an offset from the direction the player is facing
GET_NTH_CLOSEST_VEHICLE_NODE_WITH_HEADING(GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(PLAYER_PED_ID(), <<0, iNodeOffsetToCheck, 0>>), 1, vNodePos, fNodeOri, iNumLanes)
// ====================================== CONSTRUCT VECTORS FROM HEADINGS ======================================
// Formulate vector based on player's heading
vPlayerDir = <<-SIN(tempPlayerRot), COS(tempPlayerRot), 0>>
// Formulate vector based on spawn coordinates given from vehicle node functions
vNodeDirAlt = vNodePos - tempPlayerPos
// If the node is almost 180 degrees, just turn it around... useful for going against one-way streets.
IF COS(ABSF(fNodeOri - tempPlayerRot)) <= -0.98
fNodeOri += 180
ENDIF
// ============================================ RUN TESTS ======================================================
BOOL bPointIsGood
bPointIsGood = TRUE
// Check the orientations of the points used are roughly pointing in the same direction... 0.867 equates roughly to 30 degrees.
IF COS(ABSF(fNodeOri - tempPlayerRot)) <= 0.867
PRINTSTRING("ORIENTATION BETWEEN HEADINGS ARE TOO GREAT, RETURNING FALSE!!!")
bPointIsGood = FALSE
ENDIF
// Check the z values to make sure the points are not too high, e.g. on an overpass, etc.
IF ABSF(vNodePos.z - tempPlayerPos.z) > 3.0
PRINTSTRING("GET_FORWARD_POINT: Z VALUE IS TOO HIGH, RETURNING FALSE!!!")
bPointIsGood = FALSE
ENDIF
// Check against a zero vector, i.e. empty node
IF ARE_VECTORS_EQUAL(vNodePos, <<0,0,0>>)
PRINTSTRING("GET_FORWARD_POINT: VECTOR IS ZERO, RETURNING FALSE!!!")
bPointIsGood = FALSE
ENDIF
// Check to make sure point is in front of the player.
IF DOT_PRODUCT(vPlayerDir, vNodeDirAlt) <= 0
bPointIsGood = FALSE
ENDIF
IF bPointIsGood
vSpawnPos = vNodePos
fSpawnOri = fNodeOri+90
PRINTSTRING("GET_FORWARD_POINT: GOT A VALID POINT!!!")
RETURN TRUE
ELSE
RETURN FALSE
ENDIF
ENDFUNC
PROC SETUP_PED_FOR_COMBAT(PED_INDEX myPed)//, BOOL bKeepTask = TRUE)
IF DOES_ENTITY_EXIST(myPed)
IF NOT IS_ENTITY_DEAD(myPed)
SET_PED_COMBAT_ABILITY(myPed, CAL_AVERAGE)
SET_PED_COMBAT_RANGE(myPed, CR_MEDIUM)
//SET_PED_COMBAT_ATTRIBUTES(myPed, CA_DO_DRIVEBYS, TRUE)
SET_PED_COMBAT_ATTRIBUTES(myPed, CA_REQUIRES_LOS_TO_SHOOT, FALSE)
SET_PED_COMBAT_MOVEMENT(myPed, CM_WILLADVANCE)
GIVE_WEAPON_TO_PED(myPed, WEAPONTYPE_MICROSMG, 1000, TRUE)
SET_PED_SHOOT_RATE(myPed, 500)
//TASK_SHOOT_AT_ENTITY()
ENDIF
//SET_PED_ACCURACY(myPed, 5)
ENDIF
ENDPROC
PROC HANDLE_TOW_SUCCESS()
g_savedGlobals.sTowingData.iTowingJobsCompleted++
g_savedGlobals.sTowingData.lastNodeType = chosenNodeType
SWITCH chosenNodeType
CASE NODE_TYPE_ABANDON
g_savedGlobals.sTowingData.iAbandonCompleted++
// Commenting out as this is handled in the main Tonya mission scripts
// and was the cause of B*1466468 due to an early autosave request.
/*
IF g_savedGlobals.sTowingData.iAbandonCompleted = 1
PRINTLN("CP_OJ_TOW1")
REGISTER_SCRIPT_IN_COMPLETION_PERCENTAGE_TOTAL(CP_OJ_TOW1)
ENDIF
*/
BREAK
CASE NODE_TYPE_DYNAMIC
g_savedGlobals.sTowingData.iBreakDownCompleted++
/*
IF g_savedGlobals.sTowingData.iBreakDownCompleted = 1
PRINTLN("CP_OJ_TOW4")
REGISTER_SCRIPT_IN_COMPLETION_PERCENTAGE_TOTAL(CP_OJ_TOW4)
ENDIF
*/
BREAK
CASE NODE_TYPE_HANDI
g_savedGlobals.sTowingData.iHandiCompleted++
/*
IF g_savedGlobals.sTowingData.iHandiCompleted= 1
PRINTLN("CP_OJ_TOW2")
REGISTER_SCRIPT_IN_COMPLETION_PERCENTAGE_TOTAL(CP_OJ_TOW2)
ENDIF
*/
BREAK
CASE NODE_TYPE_TRAIN
g_savedGlobals.sTowingData.iTrainCompleted++
/*
IF g_savedGlobals.sTowingData.iTrainCompleted = 1
PRINTLN("CP_OJ_TOW3")
REGISTER_SCRIPT_IN_COMPLETION_PERCENTAGE_TOTAL(CP_OJ_TOW3)
ENDIF
*/
BREAK
CASE NODE_TYPE_ACCIDENT
g_savedGlobals.sTowingData.iAccidentCompleted++
/*
IF g_savedGlobals.sTowingData.iAccidentCompleted = 1
PRINTLN("CP_OJ_TOW5")
REGISTER_SCRIPT_IN_COMPLETION_PERCENTAGE_TOTAL(CP_OJ_TOW5)
ENDIF
*/
BREAK
ENDSWITCH
ENDPROC
//TODO.. improve selection logic so we populate a list of valid locations and randomly pick one
FUNC INT FIND_VALID_NODE(FLOAT maxDist, NODE_TYPE myType = NODE_TYPE_NONE, INT iLastNodeIndex = 0)
FLOAT minDist = 500
int chosenIdx = -1
FLOAT fDistance
INT validIndex[MAX_NUM_ILLEGAL_NODES]
INT validCount = 0
INT idx
//for now we're not going to consider the last 2 becaue they're bugged.
REPEAT MAX_NUM_ILLEGAL_NODES idx
fDistance = GET_PLAYER_DISTANCE_FROM_LOCATION(illegalNodes[idx].vCarPos)
IF NOT IS_VECTOR_ZERO(illegalNodes[idx].vCarPos)
IF fDistance < maxDist AND fDistance > minDist AND idx <> iLastNodeIndex
PRINTLN("fDistance = ", fDistance)
IF myType = NODE_TYPE_NONE
validIndex[validCount] = idx
validCount++
ELIF illegalNodes[idx].myType = myType //if there is a specific type ensure types match
validIndex[validCount] = idx
validCount++
ENDIF
ENDIF
ENDIF
ENDREPEAT
PRINTLN("Valid count: ", validCount, " Secleted node: ", chosenIdx)
IF validCount > 1
chosenIdx = validIndex[GET_RANDOM_INT_IN_RANGE(0,validCount-1)]
ELIF validCount = 1
chosenIdx = validIndex[0]
ELSE
PRINTLN("FIND_VALID_NODE FAILED.. returning 0")
RETURN 0
ENDIF
//Can return -1
RETURN chosenIdx
ENDFUNC
FUNC BOOL GET_BACKWARD_POINT(VECTOR &vSpawnPos, FLOAT &fSpawnOri, FLOAT iNodeOffsetToCheck = -100.0)
// If the player is not in a vehicle, exit early.
IF NOT IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
RETURN FALSE
ENDIF
// Players Initial Position/Orientation - WITHOUT DIRECTION
VECTOR tempPlayerPos
FLOAT tempPlayerRot
// Vehicle Node Position/Orientation - WITHOUT DIRECTION
VECTOR vNodePos
FLOAT fNodeOri
// Constructed vectors - WITH DIRECTION
VECTOR vPlayerDir
// VECTOR vNodeDir
VECTOR vNodeDirAlt
// Get num of lanes, required with using NATIVE function below
INT iNumLanes
// Get the player position and heading
tempPlayerPos = GET_ENTITY_COORDS(PLAYER_PED_ID())
tempPlayerRot = GET_ENTITY_HEADING(PLAYER_PED_ID())
// Grab vehicle note position/orientation based on an offset from the direction the player is facing
GET_NTH_CLOSEST_VEHICLE_NODE_WITH_HEADING(GET_OFFSET_FROM_ENTITY_IN_WORLD_COORDS(PLAYER_PED_ID(), <<0, iNodeOffsetToCheck, 0>>), 1, vNodePos, fNodeOri, iNumLanes)
// ====================================== CONSTRUCT VECTORS FROM HEADINGS ======================================
// Formulate vector based on player's heading
vPlayerDir = <<-SIN(tempPlayerRot), COS(tempPlayerRot), 0>>
// Formulate vector of node based on node's heading
// vNodeDir = <<-SIN(fNodeOri), COS(fNodeOri), 0>>
// Formulate vector based on spawn coordinates given from vehicle node functions
vNodeDirAlt = vNodePos - tempPlayerPos
// If the node is almost 180 degrees, just turn it around... useful for going against one-way streets.
IF COS(ABSF(fNodeOri - tempPlayerRot)) <= -0.98
fNodeOri += 180
ENDIF
// ============================================ RUN TESTS ======================================================
BOOL bPointIsGood
bPointIsGood = TRUE
// Check the orientations of the points used are roughly pointing in the same direction... 0.867 equates roughly to 30 degrees.
IF COS(ABSF(fNodeOri - tempPlayerRot)) <= 0.867
PRINTSTRING("ORIENTATION BETWEEN HEADINGS ARE TOO GREAT, RETURNING FALSE!!!")
bPointIsGood = FALSE
ENDIF
// Check the z values to make sure the points are not too high, e.g. on an overpass, etc.
IF ABSF(vNodePos.z - tempPlayerPos.z) > 3.0
PRINTSTRING("Z VALUE IS TOO HIGH, RETURNING FALSE!!!")
bPointIsGood = FALSE
ENDIF
// Check against a zero vector, i.e. empty node
IF ARE_VECTORS_EQUAL(vNodePos, <<0,0,0>>)
PRINTSTRING("VECTOR IS ZERO, RETURNING FALSE!!!")
bPointIsGood = FALSE
ENDIF
// Check point to see if it's sufficiently behind the player.
IF DOT_PRODUCT(vPlayerDir, vNodeDirAlt) >= 0
bPointIsGood = FALSE
ENDIF
IF bPointIsGood
vSpawnPos = vNodePos
fSpawnOri = fNodeOri
PRINTSTRING("GOT A VALID POINT!!!")
RETURN TRUE
ELSE
RETURN FALSE
ENDIF
ENDFUNC
FUNC BOOL IS_PLAYER_IN_VALID_VEHICLE(VEHICLE_INDEX& myVehicle)
IF DOES_ENTITY_EXIST(PLAYER_PED_ID())
IF NOT IS_PED_INJURED(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
IF GET_VEHICLE_PED_IS_IN(PLAYER_PED_ID()) <> myVehicle
RETURN FALSE
ENDIF
ELSE
RETURN FALSE
ENDIF
ENDIF
ENDIF
RETURN TRUE
ENDFUNC
PROC ADD_BLOOD(VECTOR& vBloodPos[])
INT i
REPEAT 1 i
stains[i].pos = vBloodPos[i]
stains[i].direction = <<0.0,0.0,-1>>
IF i = 0
stains[i].side = normalise_vector(<< GET_RANDOM_FLOAT_IN_RANGE(), GET_RANDOM_FLOAT_IN_RANGE(), 0.0>>) //heading
ELSE
stains[i].side = normalise_vector(<<0.5, 1.0, 0.0>>) //heading
ENDIF
stains[i].width = 2
stains[i].height = 1
stains[i].fAlpha = 1
stains[i].life = -1
stains[i].wash_amount = 0.1
stains[i].decal_removed = false
stains[i].decal_texture_id = DECAL_RSID_BLOOD_SPLATTER
stains[i].id = ADD_DECAL(stains[i].decal_texture_id,stains[i].pos,stains[i].direction,stains[i].side,stains[i].width,stains[i].height, 0.196, 0, 0, 1.0, -1)
ENDREPEAT
ENDPROC
//Function to handle updating of any staging.. ie ambulance or bystanders
PROC UPDATE_STAGING(STAGING_STATE& myStage, VEHICLE_INDEX veAmbulance, PED_INDEX myPed, VEHICLE_INDEX myTowTruck, PED_INDEX& pedBystanders[],
INT iNumPeds, STRING specialAnimDict, STRING& SpecialAnims[], PED_INDEX& pedTonya, BOOL bPostTonya, VEHICLE_INDEX & vehBrokenDownCar)
INT idx
pedBystanders[0] = pedBystanders[0]
iNumPeds = iNumPeds
idx = idx
bPostTonya = bPostTonya
REPEAT iNumPeds idx
IF DOES_ENTITY_EXIST(pedBystanders[idx])
IF NOT IS_ENTITY_DEAD(pedBystanders[idx]) AND NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF DO_AGGRO_CHECK(pedBystanders[idx], NULL, aggroArgs, aggroReason)
TASK_SMART_FLEE_PED(pedBystanders[idx], PLAYER_PED_ID(), 1000, -1)
PRINTLN("TASKING BYSTANDER TO FLEE: ", idx)
ENDIF
ENDIF
ENDIF
ENDREPEAT
SWITCH myStage
CASE STAGING_STATE_INIT
IF SHOULD_TRIGGER_ENTITY(veAmbulance, myTowTruck, myFrameCount, 20, 70, 65)
myFrameCount = 0
PRINTLN("GOING TO STATE - STAGING_STATE_CLOSE")
myStage = STAGING_STATE_CLOSE
ENDIF
BREAK
CASE STAGING_STATE_CLOSE
IF DOES_ENTITY_EXIST(myPed)
//might want to trigger some dialouge here as well
IF NOT IS_ENTITY_DEAD(veAmbulance) AND NOT IS_ENTITY_DEAD(myPed)
TASK_VEHICLE_DRIVE_WANDER(myPed, veAmbulance, 50.0, DRIVINGMODE_AVOIDCARS)
SET_PED_KEEP_TASK(myPed, TRUE)
SET_PED_AS_NO_LONGER_NEEDED(myPed)
SET_VEHICLE_AS_NO_LONGER_NEEDED(veAmbulance)
ENDIF
PRINTLN("GOING TO STATE - STAGING_STATE_PEDS")
myStage = STAGING_STATE_PEDS
ENDIF
BREAK
CASE STAGING_STATE_PEDS
//if we've hooked up we can have them walk off.
IF bTowHooked
RESTART_TIMER_NOW(stagingTimer)
myStage = STAGING_STATE_TASK
ENDIF
REPEAT iNumPeds idx
IF DOES_ENTITY_EXIST(pedBystanders[idx])
IF NOT IS_ENTITY_DEAD(pedBystanders[idx])
IF GET_PLAYER_DISTANCE_FROM_ENTITY(pedBystanders[idx]) < 55.0
iCloseBystander = idx
iCloseBystander = iCloseBystander
RESTART_TIMER_NOW(stagingTimer)
PRINTLN("GOING TO STATE - STAGING_STATE_TASK")
myStage = STAGING_STATE_TASK
ENDIF
ELSE
PRINTLN("BYSTANDERS ARE DEAD: ", idx)
ENDIF
ELSE
PRINTLN("BYSTANDERS DO NOT EXIST: ", idx)
ENDIF
ENDREPEAT
BREAK
CASE STAGING_STATE_TASK
IF NOT IS_VECTOR_ZERO(extraData[GET_IDX()].vMin)
ALLOW_PEDS_TO_BE_IN_AREA(sblockingIndex, extraData[GET_IDX()].vMin, extraData[GET_IDX()].vMax)
ENDIF
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya5")) = 1)
IF NOT bPlayTonyaAccidentConvo
ADD_PED_FOR_DIALOGUE(pedConvo, 3, pedTonya, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TOW_ACC_TNYA", CONV_PRIORITY_VERY_HIGH)
PRINTLN("bPlayTonyAccidentConvo = TRUE")
bPlayTonyaAccidentConvo = TRUE
ENDIF
ENDIF
ENDIF
REPEAT iNumPeds idx
IF NOT IS_ENTITY_DEAD(pedBystanders[idx])
OPEN_SEQUENCE_TASK(taskSequence)
TASK_PLAY_ANIM(NULL, specialAnimDict, SpecialAnims[idx], SLOW_BLEND_IN, SLOW_BLEND_OUT, GET_RANDOM_INT_IN_RANGE(10000,20000))
PRINTLN("TASKING BYSTANDERS TO PLAN ANIMS")
TASK_WANDER_STANDARD(NULL)
CLOSE_SEQUENCE_TASK(taskSequence)
TASK_PERFORM_SEQUENCE(pedBystanders[idx], taskSequence)
CLEAR_SEQUENCE_TASK(taskSequence)
ENDIF
ENDREPEAT
myStage = STAGING_STATE_DONE
BREAK
CASE STAGING_STATE_WAIT
//Peds might walk away at this point
BREAK
CASE STAGING_STATE_DONE
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya5")) = 1)
IF NOT bPlayTonyaAccidentConvo
ADD_PED_FOR_DIALOGUE(pedConvo, 3, pedTonya, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TOW_ACC_TNYA", CONV_PRIORITY_VERY_HIGH)
PRINTLN("bPlayTonyAccidentConvo = TRUE")
bPlayTonyaAccidentConvo = TRUE
ENDIF
ENDIF
IF NOT bPlayedWaitingConvo
IF NOT IS_ENTITY_DEAD(myTowTruck) AND NOT IS_ENTITY_DEAD(vehBrokenDownCar)
IF NOT IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(myTowTruck, vehBrokenDownCar)
IF NOT IS_TIMER_STARTED(tWaitingConvoTimer)
START_TIMER_NOW(tWaitingConvoTimer)
PRINTLN("STARTING TIMER - tWaitingConvoTimer")
ELSE
IF GET_TIMER_IN_SECONDS(tWaitingConvoTimer) > 20.0
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TOW_WAITING2", CONV_PRIORITY_VERY_HIGH)
PRINTLN("bPlayedWaitingConvo = TRUE")
bPlayedWaitingConvo = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
ENDSWITCH
ENDPROC
//Special function to spawn ped once bounds have been loaded
FUNC BOOL SPAWN_PED(VECTOR& vGroundPedPos[], VECTOR& vBloodPos[], VECTOR vCarPos, PED_INDEX& myActor, PED_INDEX& myActors[], MODEL_NAMES& modelNames[], FLOAT fOrient, STRING specialAnimDict, STRING& SpecialAnims[], INT iNumPeds)
FLOAT fGroundZ//, fTemp
PED_INDEX tempActor
INT idx
VECTOR vTemp
SEQUENCE_INDEX iSeq
vTemp = vGroundPedPos[0]
vTemp.z += 1
PRINTLN("INSIDE - SPAWN_PED")
IF GET_GROUND_Z_FOR_3D_COORD(vTemp, fGroundZ) OR GET_PLAYER_DISTANCE_FROM_LOCATION(vGroundPedPos[0], FALSE) < 60
ADD_BLOOD(vBloodPos)
CLEAR_AREA_OF_PEDS(vCarPos, 28.0)
vGroundPedPos[0].z = fGroundZ
REPEAT iNumPeds idx
IF fOrient = -1.0
fOrient = GET_HEADING_BETWEEN_VECTORS(vGroundPedPos[idx], vCarPos)
PRINTLN("Car Pos: ", vCarPos, " Ped Pos: ", vGroundPedPos[idx], " fOrient: ", fOrient)
ELSE
fOrient += 180
ENDIF
//This little hack makes this funciton play nice with all variations of towing.
IF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya4")) = 1)
tempActor = CREATE_PED(PEDTYPE_CIVMALE, A_M_M_TOURIST_01, vGroundPedPos[idx], fOrient) //%2 is a bit of a hack.. only stream 2 enums currently
PRINTLN("TONYA 4 - PED CREATION")
SET_PED_COMPONENT_VARIATION(tempActor, INT_TO_ENUM(PED_COMPONENT,0), 0, 1, 0) //(head)
SET_PED_COMPONENT_VARIATION(tempActor, INT_TO_ENUM(PED_COMPONENT,2), 0, 0, 0) //(hair)
SET_PED_COMPONENT_VARIATION(tempActor, INT_TO_ENUM(PED_COMPONENT,3), 0, 2, 0) //(uppr)
SET_PED_COMPONENT_VARIATION(tempActor, INT_TO_ENUM(PED_COMPONENT,4), 1, 2, 0) //(lowr)
SET_PED_COMPONENT_VARIATION(tempActor, INT_TO_ENUM(PED_COMPONENT,8), 0, 0, 0) //(accs)
SET_PED_COMPONENT_VARIATION(tempActor, INT_TO_ENUM(PED_COMPONENT,10), 1, 1, 0) //(decl)
SET_MODEL_AS_NO_LONGER_NEEDED(A_M_M_TOURIST_01)
ELIF (GET_NUMBER_OF_THREADS_RUNNING_THE_SCRIPT_WITH_THIS_HASH(HASH("Tonya5")) = 1)
IF idx = 0
tempActor = CREATE_PED(PEDTYPE_CIVMALE, A_M_Y_GENSTREET_02, vGroundPedPos[idx], fOrient) //%2 is a bit of a hack.. only stream 2 enums currently
PRINTLN("TONYA 5 - PED CREATION")
SET_MODEL_AS_NO_LONGER_NEEDED(A_M_Y_GENSTREET_02)
ELSE
tempActor = CREATE_PED(PEDTYPE_CIVMALE, A_M_M_BEVHILLS_02, vGroundPedPos[idx], fOrient) //%2 is a bit of a hack.. only stream 2 enums currently
PRINTLN("TONYA 5 - PED CREATION")
SET_MODEL_AS_NO_LONGER_NEEDED(A_M_M_BEVHILLS_02)
ENDIF
ELSE
tempActor = CREATE_PED(PEDTYPE_CIVMALE, modelNames[idx%2], vGroundPedPos[idx], fOrient) //%2 is a bit of a hack.. only stream 2 enums currently
PRINTLN("PROCEDURAL - PED CREATION")
ENDIF
SET_ENTITY_LOAD_COLLISION_FLAG(tempActor, TRUE)
fOrient = -1
IF iNumPeds > 1
myActors[idx] = tempActor
ELSE
myActor = tempActor
ENDIF
specialAnimDict = specialAnimDict
SpecialAnims[idx] = SpecialAnims[idx]
SET_BLOCKING_OF_NON_TEMPORARY_EVENTS(tempActor, TRUE)
SET_PED_CONFIG_FLAG(tempActor, PCF_DontInfluenceWantedLevel, TRUE)
SET_PED_MOVEMENT_CLIPSET(tempActor, "move_m@JOG@")
SET_PED_RESET_FLAG(tempActor, PRF_IsInStationaryScenario, TRUE)
IF chosenNodeType = NODE_TYPE_DYNAMIC
CLEAR_SEQUENCE_TASK(iSeq)
OPEN_SEQUENCE_TASK(iSeq)
TASK_PLAY_ANIM(NULL, "oddjobs@towingcome_here", "come_here_idle_a", SLOW_BLEND_IN, SLOW_BLEND_OUT, -1, AF_SECONDARY | AF_UPPERBODY | AF_LOOPING)
TASK_TURN_PED_TO_FACE_ENTITY(NULL, PLAYER_PED_ID(), -1)
CLOSE_SEQUENCE_TASK(iSeq)
IF NOT IS_ENTITY_DEAD(tempActor)
TASK_PERFORM_SEQUENCE(tempActor, iSeq)
ENDIF
CLEAR_SEQUENCE_TASK(iSeq)
ENDIF
ENDREPEAT
bPedCreated = TRUE
DEBUG_MESSAGE("bounds loaded.. spawning ped")
RETURN TRUE
ELSE
//just spawn the little bastards even if bounds aren't loaded!
IF GET_PLAYER_DISTANCE_FROM_LOCATION(vGroundPedPos[0], FALSE) < 70
SCRIPT_ASSERT("Bounds havn't loaded but the player is getting close. Failsafe spawn!")
ENDIF
PRINTLN("Waiting for bounds to load around2: ", vGroundPedPos[0])
ENDIF
RETURN FALSE
ENDFUNC
//TODO do a better champ with passing in blips/bools (bInRangeForPerfect) based on variation.
PROC UPDATE_MISSION_CAR(VEHICLE_INDEX& myVehicle, BLIP_INDEX& myVehicleBlip, BROKEN_VEHICLE& brokenVehicles[], VECTOR& vCurDestObjective[],
TEXT_LABEL_63& sLastObjective, INT& outOfVehicleTime, INT iClosestIdx, BOOL bSuppressBlips, BOOL& bGpsActive,
BOOL bInCombat, BOOL bUnlockDoors, BOOL bWantedLevel, MISSION_STATE curStage, BOOL bPrintWarning = TRUE)
INT idx
bUnlockDoors = bUnlockDoors
//If we're in combat don't blip or bother the player bInCombat
//TODO what if we already have blip and then combat happens?
// IF bOutOfVehicle
// PRINTLN("bOutOfVehicle IS TRUE")
// ELSE
// PRINTLN("bOutOfVehicle IS FALSE")
// ENDIF
//
// PRINTLN("outOfVehicleTime = ", outOfVehicleTime)
// PRINTLN("GET_GAME_TIMER = ", GET_GAME_TIMER())
IF bWantedLevel
IF DOES_BLIP_EXIST(myVehicleBlip)
REMOVE_BLIP(myVehicleBlip)
PRINTLN("REMOVING BLIP - myVehicleBlip VIA bWanted SET TO TRUE")
ENDIF
outOfVehicleTime = GET_GAME_TIMER()
bOutOfVehicle = NOT IS_PLAYER_IN_VALID_VEHICLE(myVehicle)
EXIT
ELSE
// if you lose wanted and you're out of the vehicle, blip the vehicle
IF NOT DOES_BLIP_EXIST(myVehicleBlip)
AND bOutOfVehicle
myVehicleBlip = ADD_BLIP_FOR_ENTITY(myVehicle)
SET_BLIP_COLOUR(myVehicleBlip, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(myVehicleBlip, TRUE)
PRINTLN("ADDING BLIP - myVehicleBlip")
ENDIF
ENDIF
IF NOT bInCombat// AND NOT IS_PLAYER_IN_VALID_VEHICLE(myVehicle)
IF NOT bOutOfVehicle
IF NOT IS_PLAYER_IN_VALID_VEHICLE(myVehicle)
PRINTLN("UPDATE_MISSION_CAR 1")
//Need to clear current objecetives
CLEAR_SMALL_PRINTS()
// Record time for abandoned car check
outOfVehicleTime = GET_GAME_TIMER()
IF bPrintWarning
IF bPrintEnter
PRINT_NOW("DTRSHRD_03",DEFAULT_GOD_TEXT_TIME,1)
bPrintEnter = FALSE
ENDIF
IF NOT DOES_BLIP_EXIST(myVehicleBlip)
myVehicleBlip = ADD_BLIP_FOR_ENTITY(myVehicle)
SET_BLIP_COLOUR(myVehicleBlip, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(myVehicleBlip, TRUE)
PRINTLN("ADDING BLIP - myVehicleBlip")
ENDIF
ENDIF
REPEAT MAX_NUM_BROKEN_CARS idx
// IF NOT IS_ENTITY_DEAD(brokenVehicles[idx].vehicleIndex)
IF DOES_BLIP_EXIST(brokenVehicles[idx].blipIndex)
SET_BLIP_ROUTE(brokenVehicles[idx].blipIndex, FALSE)
PRINTLN("CLEARING BLIP ROUTE - 04")
REMOVE_BLIP(brokenVehicles[idx].blipIndex)
PRINTLN("REMOVING BLIP - brokenVehicles[idx].blipIndex ", idx)
bGpsActive = FALSE
ENDIF
// ENDIF
ENDREPEAT
IF DOES_BLIP_EXIST(brokenVehicles[0].blipIndexPed)
REMOVE_BLIP(brokenVehicles[0].blipIndexPed)
PRINTLN("REMOVING BLIP - brokenVehicles[0].blipIndexPed IN UPDATE MISSION CAR")
ENDIF
bOutOfVehicle = TRUE
ENDIF
ELSE
IF IS_PLAYER_IN_VALID_VEHICLE(myVehicle)
PRINTLN("UPDATE_MISSION_CAR 2")
//bDisplayTimer = FALSE
IF DOES_BLIP_EXIST(myVehicleBlip)
REMOVE_BLIP(myVehicleBlip)
PRINTLN("REMOVING BLIP - myVehicleBlip")
ENDIF
IF NOT IS_PED_INJURED(brokenVehicles[0].pedIndex)
IF NOT IS_PED_IN_VEHICLE(brokenVehicles[0].pedIndex, myVehicle) AND NOT IS_PED_IN_VEHICLE(brokenVehicles[0].pedIndex, brokenVehicles[iClosestIdx].vehicleIndex)
IF NOT DOES_BLIP_EXIST(brokenVehicles[0].blipIndexPed)
brokenVehicles[0].blipIndexPed = ADD_BLIP_FOR_ENTITY(brokenVehicles[idx].pedIndex)
SET_BLIP_COLOUR(brokenVehicles[0].blipIndexPed, BLIP_COLOUR_BLUE)
SET_BLIP_SCALE(brokenVehicles[0].blipIndexPed, BLIP_SIZE_PED)
PRINTLN("ADDING BLIP - brokenVehicles[0].blipIndexPed")
ENDIF
ENDIF
ENDIF
IF bPrintObj
PRINT_NOW(sLastObjective,DEFAULT_GOD_TEXT_TIME,1)
PRINTLN("PRINTING sLastObjective VIA UPDATE_MISSION_CAR")
bPrintObj = FALSE
ENDIF
//either re-blip the cars or destination
//If we have a valid destination reblip it.
IF NOT IS_VECTOR_ZERO(vCurDestObjective[0]) AND curStage = MISSION_STATE_DROPOFF
IF NOT DOES_BLIP_EXIST(brokenVehicles[0].blipIndex )
brokenVehicles[0].blipIndex = ADD_BLIP_FOR_COORD(vCurDestObjective[0])
SET_BLIP_ROUTE(brokenVehicles[0].blipIndex, TRUE)
PRINTLN("ADDING BLIP - brokenVehicles[0].blipIndex")
ENDIF
ELSE
IF bSuppressBlips
IF NOT IS_ENTITY_DEAD(brokenVehicles[iClosestIdx].vehicleIndex)
IF NOT DOES_BLIP_EXIST(brokenVehicles[iClosestIdx].blipIndex)
brokenVehicles[iClosestIdx].blipIndex = ADD_BLIP_FOR_ENTITY(brokenVehicles[iClosestIdx].vehicleIndex)
SET_BLIP_COLOUR(brokenVehicles[iClosestIdx].blipIndex, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(brokenVehicles[0].blipIndex, TRUE)
PRINTLN("ADDING BLIP - brokenVehicles[iClosestIdx].blipIndex ", iClosestIdx)
ENDIF
ELSE
IF chosenNodeType = NODE_TYPE_DYNAMIC
illegalNodes[illegalIdx].vCarPos = <<-476.1537, 132.6556, 62.9586>>
// PRINTLN("OVERRIDING CAR POSITION FOR TONYA 4")
ENDIF
IF NOT DOES_BLIP_EXIST(brokenVehicles[0].blipIndex)
brokenVehicles[0].blipIndex = ADD_BLIP_FOR_COORD(illegalNodes[illegalIdx].vCarPos)
SET_BLIP_COLOUR(brokenVehicles[0].blipIndex, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(brokenVehicles[0].blipIndex, TRUE)
PRINTLN("CREATING TOWING BLIP - 03")
ENDIF
ENDIF
ELSE
REPEAT MAX_NUM_BROKEN_CARS idx
IF NOT IS_ENTITY_DEAD(brokenVehicles[idx].vehicleIndex)
IF NOT DOES_BLIP_EXIST(brokenVehicles[idx].blipIndex)
brokenVehicles[idx].blipIndex = ADD_BLIP_FOR_ENTITY(brokenVehicles[idx].vehicleIndex)
SET_BLIP_COLOUR(brokenVehicles[idx].blipIndex, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(brokenVehicles[idx].blipIndex, TRUE)
PRINTLN("ADDING BLIP - brokenVehicles[idx].blipIndex ", idx)
ENDIF
ELSE
IF chosenNodeType = NODE_TYPE_DYNAMIC
illegalNodes[illegalIdx].vCarPos = <<-476.1537, 132.6556, 62.9586>>
// PRINTLN("OVERRIDING CAR POSITION FOR TONYA 4")
ENDIF
IF NOT DOES_BLIP_EXIST(brokenVehicles[0].blipIndex)
brokenVehicles[0].blipIndex = ADD_BLIP_FOR_COORD(illegalNodes[illegalIdx].vCarPos)
SET_BLIP_COLOUR(brokenVehicles[0].blipIndex, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(brokenVehicles[0].blipIndex, TRUE)
PRINTLN("CREATING TOWING BLIP - 04")
ENDIF
ENDIF
ENDREPEAT
ENDIF
ENDIF
outOfVehicleTime = 0
bOutOfVehicle = FALSE
ELSE
// PRINTLN("UPDATE_MISSION_CAR 3")
//still not in vehicle
ENDIF
ENDIF
ENDIF
ENDPROC
FUNC BOOL VALIDATE_NODE_TYPE(NODE_TYPE myNodeType)
illegalIdx = FIND_VALID_NODE(1300, myNodeType, g_savedGlobals.sTowingData.iLastNodeIndex)
IF illegalIdx = -1
PRINTLN("Selected node type was not validated: ", myNodeType)
RETURN FALSE
ELSE
RETURN TRUE
ENDIF
ENDFUNC
FUNC NODE_TYPE GET_LEAST_COMPLETED_MODE(NODE_TYPE notThis)
INT min = 2000000
NODE_TYPE returnType = NODE_TYPE_ABANDON
IF notTHis <> NODE_TYPE_ABANDON
IF g_savedGlobals.sTowingData.iAbandonCompleted < min
min = g_savedGlobals.sTowingData.iAbandonCompleted
returnType = NODE_TYPE_ABANDON
ENDIF
ENDIF
IF notTHis <> NODE_TYPE_HANDI
IF g_savedGlobals.sTowingData.iHandiCompleted < min
min = g_savedGlobals.sTowingData.iHandiCompleted
returnType = NODE_TYPE_HANDI
ENDIF
ENDIF
IF notTHis <> NODE_TYPE_TRAIN
IF g_savedGlobals.sTowingData.iTrainCompleted < min
min = g_savedGlobals.sTowingData.iTrainCompleted
returnType = NODE_TYPE_TRAIN
ENDIF
ENDIF
IF notTHis <> NODE_TYPE_DYNAMIC
IF g_savedGlobals.sTowingData.iBreakDownCompleted < min
min = g_savedGlobals.sTowingData.iBreakDownCompleted
returnType = NODE_TYPE_DYNAMIC
ENDIF
ENDIF
IF notTHis <> NODE_TYPE_ACCIDENT
IF g_savedGlobals.sTowingData.iAccidentCompleted< min
min = g_savedGlobals.sTowingData.iAccidentCompleted
returnType = NODE_TYPE_ACCIDENT
ENDIF
ENDIF
RETURN returnType
ENDFUNC
PROC SELECTION_LOGIC()
chosenNodeType = GET_LEAST_COMPLETED_MODE(g_savedGlobals.sTowingData.lastNodeType)
IF NOT VALIDATE_NODE_TYPE(chosenNodeType)
//Our chosen node can't be validated. Revert to our "safe" choice of dynamic
chosenNodeType = NODE_TYPE_DYNAMIC
ELSE
PRINTLN("CHECK: illegalIdx = ", illegalIdx)
ENDIF
// IF bDoTutorial
// chosenNodeType = NODE_TYPE_ABANDON
// ENDIF
IF chosenNodeType = NODE_TYPE_DYNAMIC
DEBUG_MESSAGE("Dynamic mode was chosen")
ELSE
illegalIdx = FIND_VALID_NODE(1300, chosenNodeType, g_savedGlobals.sTowingData.iLastNodeIndex)
PRINTLN("CHECK 01: illegalIdx = ", illegalIdx)
g_savedGlobals.sTowingData.iLastNodeIndex = illegalIdx
PRINTLN("g_savedGlobals.sTowingData.iLastNodeIndex = ", g_savedGlobals.sTowingData.iLastNodeIndex)
ENDIF
//this shouldn't be needed anymore with the addition of VALIDATE_NODE_TYPE
IF illegalIdx = 0
DEBUG_MESSAGE("Could not find a tow node for our desired type. Defaulting to dynamic.")
chosenNodeType = NODE_TYPE_DYNAMIC
ENDIF
PRINTLN("Seleciton logic has chosen: ", chosenNodeType)
g_savedGlobals.sTowingData.lastNodeType = chosenNodeType
PRINTLN("g_savedGlobals.sTowingData.lastNodeType = ", chosenNodeType)
ENDPROC
ENUM TUT_PED
TUT_PED_CREATE = 0,
TUT_PED_CUTSCENE,
TUT_PED_TRAVEL,
TUT_PED_ARRIVE,
TUT_PED_PLAYER,
TUT_PED_ENTER
ENDENUM
TUT_PED tutorialPedState = TUT_PED_CREATE
PROC INIT_INTRO_CUTSCENE()
stIntroCutscene.vTutorialPedPosition = <<410.7697, -1630.0444, 28.2928>> //<< 412.9097, -1622.8549, 28.2928 >>
stIntroCutscene.fTutorialPedHeading = 287.8853 //115.7309
stIntroCutscene.vPlayerTutorialPosition = <<413.0471, -1630.4077, 28.2928>>
stIntroCutscene.fPlayerTutorialHeading = 80.5853
stIntroCutscene.vCamPosition = <<414.0333, -1630.1799, 29.9957>>
stIntroCutscene.vCamRotation = <<-3.5835, -0.0000, 80.2614>>
ENDPROC
PROC TUTORIAL_INTRO_CUTSCENE_CLEANUP(BLIP_INDEX& towBlip, VEHICLE_INDEX & myVehicle)
CLEAR_THIS_PRINT("TOWT_OBJ_01E")
SCRIPT_REMOVE_BLIP_SAFE(towBlip)
SET_VEHICLE_DOORS_LOCKED(myVehicle, VEHICLELOCK_UNLOCKED)
DISPLAY_RADAR(TRUE)
DISPLAY_HUD(TRUE)
IF DOES_CAM_EXIST(stIntroCutscene.camIntro)
SET_CAM_ACTIVE(stIntroCutscene.camIntro, FALSE)
ENDIF
RENDER_SCRIPT_CAMS(FALSE, FALSE)
SET_GAMEPLAY_CAM_RELATIVE_HEADING()
SET_GAMEPLAY_CAM_RELATIVE_PITCH()
SET_PLAYER_CONTROL(PLAYER_ID(), TRUE)
ENDPROC
FUNC BOOL RUN_TOWING_INTRODUCTORY_CUTSCENE(VEHICLE_INDEX & myVehicle, PED_INDEX myPed, BLIP_INDEX& towBlip)
VECTOR vPlayerPos
SEQUENCE_INDEX iSeq
//------------------------------------------SKIP CUTSCENE------------------------------------------
IF NOT stIntroCutscene.bSkippedCutscene
IF IS_TIMER_STARTED(stIntroCutscene.tIntroCutsceneTimer)
IF GET_TIMER_IN_SECONDS(stIntroCutscene.tIntroCutsceneTimer) > 1.0
IF IS_CUTSCENE_SKIP_BUTTON_JUST_PRESSED()
DO_SCREEN_FADE_OUT(500)
WHILE NOT IS_SCREEN_FADED_OUT()
WAIT(0)
ENDWHILE
CLEAR_PRINTS()
HANG_UP_AND_PUT_AWAY_PHONE()
STOP_SCRIPTED_CONVERSATION(FALSE)
PRINTLN("INTRO CUTSCENE HAS BEEN SKIPPED")
PRINTLN("GOING TO STATE - TUT_INTRO_CUTSCENE_SKIP_01")
tutorialIntroCutsceneState = TUT_INTRO_CUTSCENE_SKIP_01
stIntroCutscene.bSkippedCutscene = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
SWITCH tutorialIntroCutsceneState
CASE TUT_INTRO_CUTSCENE_01
INIT_INTRO_CUTSCENE()
REQUEST_ANIM_DICT("oddjobs@towingcome_here")
IF HAS_ANIM_DICT_LOADED("oddjobs@towingcome_here")
PRINTLN("GOING TO STATE - TUT_INTRO_CUTSCENE_02")
tutorialIntroCutsceneState = TUT_INTRO_CUTSCENE_02
ENDIF
BREAK
//----------------------------------------------------------------------------------------------------------------
CASE TUT_INTRO_CUTSCENE_02
IF NOT IS_PED_INJURED(PLAYER_PED_ID())
vPlayerPos = GET_ENTITY_COORDS(PLAYER_PED_ID())
ENDIF
IF (VDIST2(vPlayerPos, stIntroCutscene.vTutorialPedPosition) < 16
AND stIntroCutscene.bRunIntroDialogue)
OR (bLeftVehicle AND IS_TIMER_STARTED(tIntroBufferTimer) AND GET_TIMER_IN_SECONDS(tIntroBufferTimer) > 1.5)
IF NOT IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
stIntroCutscene.camIntro = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, stIntroCutscene.vCamPosition,
stIntroCutscene.vCamRotation, 30.0, TRUE)
KILL_ANY_CONVERSATION()
SET_CAM_NEAR_DOF(stIntroCutscene.camIntro, 0.25)
SET_CAM_FAR_DOF(stIntroCutscene.camIntro, 7.0)
SET_CAM_DOF_STRENGTH(stIntroCutscene.camIntro, 1.0)
SET_USE_HI_DOF()
FORCE_PED_AI_AND_ANIMATION_UPDATE(PLAYER_PED_ID())
SET_ENTITY_COORDS(PLAYER_PED_ID(), stIntroCutscene.vPlayerTutorialPosition)
SET_ENTITY_HEADING(PLAYER_PED_ID(), stIntroCutscene.fPlayerTutorialHeading)
SET_ENTITY_COORDS(myPed, stIntroCutscene.vTutorialPedPosition)
SET_ENTITY_HEADING(myPed, stIntroCutscene.fTutorialPedHeading)
DISPLAY_RADAR(FALSE)
DISPLAY_HUD(FALSE)
SET_PLAYER_CONTROL(PLAYER_ID(), FALSE, SPC_REMOVE_FIRES | SPC_REMOVE_EXPLOSIONS | SPC_REMOVE_PROJECTILES)
RENDER_SCRIPT_CAMS(TRUE, FALSE)
CLEAR_PED_TASKS(myPed)
TASK_CLEAR_LOOK_AT(myPed)
CLEAR_SEQUENCE_TASK(iSeq)
OPEN_SEQUENCE_TASK(iSeq)
TASK_TURN_PED_TO_FACE_ENTITY(NULL, PLAYER_PED_ID())
TASK_PLAY_ANIM(NULL, "oddjobs@towing", "thanks_male_04", SLOW_BLEND_IN,SLOW_BLEND_OUT, -1, AF_SECONDARY | AF_UPPERBODY | AF_LOOPING)
CLOSE_SEQUENCE_TASK(iSeq)
IF NOT IS_ENTITY_DEAD(myPed)
TASK_PERFORM_SEQUENCE(myPed, iSeq)
ENDIF
CLEAR_SEQUENCE_TASK(iSeq)
IF NOT bPlayedFirstCovno
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INTB", CONV_PRIORITY_VERY_HIGH)
PRINTLN("bPlayedFirstCovno = TRUE 01")
bPlayedFirstCovno = TRUE
ENDIF
ENDIF
IF NOT IS_TIMER_STARTED(stIntroCutscene.tIntroCutsceneTimer)
START_TIMER_NOW(stIntroCutscene.tIntroCutsceneTimer)
PRINTLN("STARTING TIMER - stIntroCutscene.tIntroCutsceneTimer")
ENDIF
PRINTLN("GOING TO STATE - TUT_INTRO_CUTSCENE_03")
tutorialIntroCutsceneState = TUT_INTRO_CUTSCENE_03
ELSE
TASK_LEAVE_ANY_VEHICLE(PLAYER_PED_ID())
bLeftVehicle = TRUE
PRINTLN("bLeftVehicle = TRUE")
IF NOT IS_TIMER_STARTED(tIntroBufferTimer)
START_TIMER_NOW(tIntroBufferTimer)
ENDIF
ENDIF
ELSE
IF NOT stIntroCutscene.bRunIntroDialogue
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 3, myPed, "TOWDISPATCH")
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 0, PLAYER_PED_ID(), "FRANKLIN")
towBlip = ADD_BLIP_FOR_ENTITY(myPed)
SET_BLIP_COLOUR(towBlip, BLIP_COLOUR_BLUE)
SET_BLIP_SCALE(towBlip, BLIP_SIZE_PED)
IF NOT bPlayedSecondCovno
IF IS_ENTITY_PLAYING_ANIM(myPed, "oddjobs@towingcome_here", "come_here_idle_c")
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INTA", CONV_PRIORITY_VERY_HIGH, DO_NOT_DISPLAY_SUBTITLES)
bPlayedSecondCovno = TRUE
PRINTLN("bPlayedSecondCovno = TRUE 01")
ENDIF
ENDIF
ENDIF
CLEAR_SEQUENCE_TASK(iSeq)
OPEN_SEQUENCE_TASK(iSeq)
TASK_PLAY_ANIM(NULL, "oddjobs@towingcome_here", "come_here_idle_c", NORMAL_BLEND_IN,SLOW_BLEND_OUT, -1, AF_SECONDARY | AF_UPPERBODY | AF_LOOPING)
TASK_TURN_PED_TO_FACE_ENTITY(NULL, PLAYER_PED_ID(), -1)
CLOSE_SEQUENCE_TASK(iSeq)
IF NOT IS_ENTITY_DEAD(myPed)
TASK_PERFORM_SEQUENCE(myPed, iSeq)
ENDIF
CLEAR_SEQUENCE_TASK(iSeq)
PRINTLN("PLAYER ISN'T CLOSE ENOUGH")
stIntroCutscene.bRunIntroDialogue = TRUE
ENDIF
IF NOT bPlayedSecondCovno
IF IS_ENTITY_PLAYING_ANIM(myPed, "oddjobs@towingcome_here", "come_here_idle_c")
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INTA", CONV_PRIORITY_VERY_HIGH, DO_NOT_DISPLAY_SUBTITLES)
bPlayedSecondCovno = TRUE
PRINTLN("bPlayedSecondCovno = TRUE 02")
ENDIF
ENDIF
ENDIF
ENDIF
BREAK
//----------------------------------------------------------------------------------------------------------------
CASE TUT_INTRO_CUTSCENE_03
SET_USE_HI_DOF()
IF NOT bPlayedFirstCovno
IF CREATE_CONVERSATION(MyLocalPedStruct, "TOWAUD", "TOW_TUT_INTB", CONV_PRIORITY_VERY_HIGH)
PRINTLN("bPlayedFirstCovno = TRUE 02")
bPlayedFirstCovno = TRUE
ENDIF
ENDIF
IF IS_TIMER_STARTED(stIntroCutscene.tIntroCutsceneTimer)
IF GET_TIMER_IN_SECONDS(stIntroCutscene.tIntroCutsceneTimer) > 9.0
AND NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
SET_ENTITY_COORDS(PLAYER_PED_ID(), << 406.2195, -1625.8931, 28.3117 >>)
SET_ENTITY_HEADING(PLAYER_PED_ID(), 156.5446)
IF NOT IS_PED_INJURED(myPed)
CLEAR_PED_TASKS(myPed)
TASK_ENTER_VEHICLE(myPed, myVehicle, DEFAULT_TIME_BEFORE_WARP, VS_FRONT_RIGHT, PEDMOVEBLENDRATIO_WALK, ECF_WARP_ENTRY_POINT)
PRINTLN("TASKING GUY TO ENTER VEHICLE")
ENDIF
IF NOT IS_PED_INJURED(PLAYER_PED_ID())
TASK_ENTER_VEHICLE(PLAYER_PED_ID(), myVehicle, DEFAULT_TIME_BEFORE_WARP, VS_DRIVER, PEDMOVEBLENDRATIO_WALK, ECF_WARP_ENTRY_POINT)
PRINTLN("TASKING PLAYER TO ENTER VEHICLE")
ENDIF
SET_CAM_COORD(stIntroCutscene.camIntro, << 402.1656, -1624.6968, 31.0961 >>)
SET_CAM_ROT(stIntroCutscene.camIntro, << -11.8470, -0.0000, -118.9643 >>)
PRINTLN("GOING TO STATE - TUT_INTRO_CUTSCENE_04")
tutorialIntroCutsceneState = TUT_INTRO_CUTSCENE_04
ENDIF
ENDIF
BREAK
//----------------------------------------------------------------------------------------------------------------
CASE TUT_INTRO_CUTSCENE_04
IF IS_PED_IN_VEHICLE(PLAYER_PED_ID(), myVehicle) AND IS_PED_IN_VEHICLE(myPed, myVehicle)
TUTORIAL_INTRO_CUTSCENE_CLEANUP(towBlip, myVehicle)
RETURN TRUE
ENDIF
BREAK
//----------------------------------------------------------------------------------------------------------------
CASE TUT_INTRO_CUTSCENE_SKIP_01
DESTROY_CAM(stIntroCutscene.camIntro)
RENDER_SCRIPT_CAMS(FALSE, FALSE)
IF NOT IS_PED_INJURED(PLAYER_PED_ID()) AND IS_VEHICLE_DRIVEABLE(myVehicle)
SET_PED_INTO_VEHICLE(PLAYER_PED_ID(), myVehicle)
ENDIF
IF NOT IS_PED_INJURED(myPed) AND IS_VEHICLE_DRIVEABLE(myVehicle)
SET_PED_INTO_VEHICLE(myPed, myVehicle, VS_FRONT_RIGHT)
ENDIF
TUTORIAL_INTRO_CUTSCENE_CLEANUP(towBlip, myVehicle)
PRINTLN("GOING TO STATE - TUT_INTRO_CUTSCENE_SKIP_02")
tutorialIntroCutsceneState = TUT_INTRO_CUTSCENE_SKIP_02
BREAK
//----------------------------------------------------------------------------------------------------------------
CASE TUT_INTRO_CUTSCENE_SKIP_02
DO_SCREEN_FADE_IN(1000)
WHILE NOT IS_SCREEN_FADED_IN()
WAIT(0)
ENDWHILE
RETURN TRUE
BREAK
ENDSWITCH
RETURN FALSE
ENDFUNC
PROC TONYA_FIRST_CUTSCENE_CLEANUP(PED_INDEX myPed)
DISPLAY_RADAR(TRUE)
DISPLAY_HUD(TRUE)
DISABLE_CELLPHONE(FALSE)
SET_PLAYER_CONTROL(PLAYER_ID(), TRUE)
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
CLEAR_PED_TASKS(PLAYER_PED_ID())
TASK_CLEAR_LOOK_AT(PLAYER_PED_ID())
ENDIF
IF NOT IS_ENTITY_DEAD(myPed)
CLEAR_PED_TASKS(myPed)
ENDIF
RENDER_SCRIPT_CAMS(FALSE, FALSE)
SET_GAMEPLAY_CAM_RELATIVE_HEADING()
SET_GAMEPLAY_CAM_RELATIVE_PITCH()
IF DOES_CAM_EXIST(cam01)
DESTROY_CAM(cam01)
ENDIF
IF DOES_CAM_EXIST(cam02)
DESTROY_CAM(cam02)
ENDIF
bSkippedIntroCutscene = FALSE
PRINTLN("RUNNING CUTSCENE CLEANUP")
ENDPROC
FUNC BOOL RUN_FIRST_TONYA_CUTSCENE(PED_INDEX myPed)
IF NOT bSkippedIntroCutscene
IF IS_TIMER_STARTED(tCutsceneTimer)
IF GET_TIMER_IN_SECONDS(tCutsceneTimer) > 1.0
IF IS_CUTSCENE_SKIP_BUTTON_JUST_PRESSED()
DO_SCREEN_FADE_OUT(500)
WHILE NOT IS_SCREEN_FADED_OUT()
WAIT(0)
ENDWHILE
CLEAR_PRINTS()
CLEAR_HELP()
HANG_UP_AND_PUT_AWAY_PHONE()
STOP_SCRIPTED_CONVERSATION(FALSE)
PRINTLN("TOWING: FIRST CUTSCENE HAS BEEN SKIPPED")
PRINTLN("iFirstCutsceneStages = 3")
iFirstCutsceneStages = 3
bSkippedIntroCutscene = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
SWITCH iFirstCutsceneStages
CASE 0
cam01 = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, <<-12.2070, -1472.5962, 31.2021>>, <<-5.2325, -0.0000, 96.5678>>, 35.0, TRUE)
cam02 = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, <<-12.2642, -1472.0994, 31.2021>>, <<-5.2325, -0.0000, 96.5678>>, 35.0, FALSE)
CLEAR_PRINTS()
CLEAR_HELP()
DISPLAY_RADAR(FALSE)
DISPLAY_HUD(FALSE)
DISABLE_CELLPHONE(TRUE)
WAIT(0)
SET_PLAYER_CONTROL(PLAYER_ID(), FALSE, SPC_REMOVE_EXPLOSIONS | SPC_REMOVE_FIRES | SPC_REMOVE_PROJECTILES)
PRINTLN("TURNING OFF PLAYER CONTROL")
RENDER_SCRIPT_CAMS(TRUE, FALSE)
RESOLVE_VEHICLES_INSIDE_ANGLED_AREA(<<-11.207333,-1475.108398,29.046181>>, <<-17.081156,-1469.945068,33.362968>>, 6.250000, vVehicleStartPosition, fVehicleStartHeading)
SET_CAM_ACTIVE_WITH_INTERP(cam02, cam01, 12000)
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myPed)
SET_ENTITY_COORDS(PLAYER_PED_ID(), <<-13.3596, -1471.8689, 29.5836>>)
SET_ENTITY_HEADING(PLAYER_PED_ID(), 137.1648)
FORCE_PED_AI_AND_ANIMATION_UPDATE(PLAYER_PED_ID(), TRUE)
TASK_LOOK_AT_ENTITY(PLAYER_PED_ID(), myPed, -1)
TASK_LOOK_AT_ENTITY(myPed, PLAYER_PED_ID(), -1)
ENDIF
ADD_PED_FOR_DIALOGUE(pedConvo, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(pedConvo, 3, myPed, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_TOW_1", CONV_PRIORITY_VERY_HIGH)
bFirstConvoRan = TRUE
ENDIF
IF NOT IS_TIMER_STARTED(tCutsceneTimer)
START_TIMER_NOW(tCutsceneTimer)
PRINTLN("STATING TIMER - tCutsceneTimer")
ENDIF
PRINTLN("iFirstCutsceneStages = 1")
iFirstCutsceneStages = 1
BREAK
//------------------------------------------------------------------------------------------------
CASE 1
IF NOT bFirstConvoRan
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_TOW_1", CONV_PRIORITY_VERY_HIGH)
bFirstConvoRan = TRUE
ENDIF
ENDIF
IF IS_TIMER_STARTED(tCutsceneTimer)
IF GET_TIMER_IN_SECONDS(tCutsceneTimer) > 12.0
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
PRINTLN("iFirstCutsceneStages = 2")
iFirstCutsceneStages = 2
ELSE
// PRINTLN("CONVERSATION IS STILL GOING")
ENDIF
ENDIF
ENDIF
BREAK
//------------------------------------------------------------------------------------------------
CASE 2
RETURN TRUE
BREAK
//------------------------------------------------------------------------------------------------
CASE 3
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
PRINTLN("iFirstCutsceneStages = 4")
iFirstCutsceneStages = 4
BREAK
//------------------------------------------------------------------------------------------------
CASE 4
PRINTLN("SKIPPING CUTSCENE: iFirstCutsceneStages = 4")
DO_SCREEN_FADE_IN(1000)
WHILE NOT IS_SCREEN_FADED_IN()
WAIT(0)
ENDWHILE
RETURN TRUE
BREAK
//------------------------------------------------------------------------------------------------
ENDSWITCH
RETURN FALSE
ENDFUNC
//FUNC BOOL RUN_FIRST_TONYA_CUTSCENE(PED_INDEX myPed)
// SWITCH iStageNum
// CASE 0
// REQUEST_CUTSCENE("tonya_mcs_1")
//
// iStageNum ++
// PRINTLN("RUN_FIRST_TONYA_CUTSCENE, iStageNum = ", iStageNum)
// BREAK
// //----------------------------------------------------------------------------------------------------------------------
// CASE 1
// IF HAS_CUTSCENE_LOADED()
//
// iStageNum ++
// PRINTLN("RUN_FIRST_TONYA_CUTSCENE, iStageNum = ", iStageNum)
// ENDIF
// BREAK
// //----------------------------------------------------------------------------------------------------------------------
// CASE 2
// SET_SCRIPTS_SAFE_FOR_CUTSCENE(TRUE)
//
// IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
// REGISTER_ENTITY_FOR_CUTSCENE(PLAYER_PED_ID(), "Franklin", CU_ANIMATE_EXISTING_SCRIPT_ENTITY) //, PLAYER_ONE)
// ENDIF
// IF NOT IS_ENTITY_DEAD(myPed)
// REGISTER_ENTITY_FOR_CUTSCENE(myPed, "Tonya", CU_ANIMATE_EXISTING_SCRIPT_ENTITY) //, PLAYER_ONE)
// PRINTLN("REGISTERING TONYA FOR CUTSCENE")
// ENDIF
//
// START_CUTSCENE()
//
// iStageNum ++
// PRINTLN("RUN_FIRST_TONYA_CUTSCENE, iStageNum = ", iStageNum)
// BREAK
// //----------------------------------------------------------------------------------------------------------------------
// CASE 3
// IF IS_CUTSCENE_PLAYING()
// // Do stuff here
//// RESOLVE_VEHICLES_AT_MISSION_TRIGGER(<<-1520.4059, -924.5485, 9.1222>>, 48.0063)
// ENDIF
//
// IF CAN_SET_EXIT_STATE_FOR_REGISTERED_ENTITY("Franklin")
// // Do other stuff here
// ENDIF
//
// IF HAS_CUTSCENE_FINISHED()
// SET_SCRIPTS_SAFE_FOR_CUTSCENE(FALSE)
//
// DESTROY_ALL_CAMS()
// RENDER_SCRIPT_CAMS(FALSE, FALSE)
//
// SET_GAMEPLAY_CAM_RELATIVE_HEADING()
// SET_GAMEPLAY_CAM_RELATIVE_PITCH()
//
// IF IS_SCREEN_FADED_OUT()
// WAIT(0)
// DO_SCREEN_FADE_IN(500)
// ENDIF
//
// PRINTLN("RETURNING TRUE ON FIRST TONYA CUTSCENE")
// RETURN TRUE
// ENDIF
// BREAK
// ENDSWITCH
//
// RETURN FALSE
//ENDFUNC
FUNC BOOL RUN_SECOND_TONYA_CUTSCENE(PED_INDEX myPed)
IF NOT bSkippedSecondCutscene
IF IS_TIMER_STARTED(tCutsceneTimer)
IF GET_TIMER_IN_SECONDS(tCutsceneTimer) > 1.0
IF IS_CUTSCENE_SKIP_BUTTON_JUST_PRESSED()
DO_SCREEN_FADE_OUT(500)
WHILE NOT IS_SCREEN_FADED_OUT()
WAIT(0)
ENDWHILE
CLEAR_PRINTS()
CLEAR_HELP()
HANG_UP_AND_PUT_AWAY_PHONE()
STOP_SCRIPTED_CONVERSATION(FALSE)
PRINTLN("TOWING: SECOND CUTSCENE HAS BEEN SKIPPED")
PRINTLN("iSecondCutsceneStages = 3")
iSecondCutsceneStages = 3
bSkippedSecondCutscene = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
SWITCH iSecondCutsceneStages
CASE 0
cam01 = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, <<-12.2070, -1472.5962, 31.2021>>, <<-5.2325, -0.0000, 96.5678>>, 35.0, TRUE)
cam02 = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, <<-12.2642, -1472.0994, 31.2021>>, <<-5.2325, -0.0000, 96.5678>>, 35.0, FALSE)
CLEAR_PRINTS()
CLEAR_HELP()
DISPLAY_RADAR(FALSE)
DISPLAY_HUD(FALSE)
DISABLE_CELLPHONE(TRUE)
WAIT(0)
SET_PLAYER_CONTROL(PLAYER_ID(), FALSE, SPC_REMOVE_EXPLOSIONS | SPC_REMOVE_FIRES | SPC_REMOVE_PROJECTILES)
RENDER_SCRIPT_CAMS(TRUE, FALSE)
RESOLVE_VEHICLES_INSIDE_ANGLED_AREA(<<-11.207333,-1475.108398,29.046181>>, <<-17.081156,-1469.945068,33.362968>>, 6.250000, vVehicleStartPosition, fVehicleStartHeading)
SET_CAM_ACTIVE_WITH_INTERP(cam02, cam01, 12000)
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myPed)
SET_ENTITY_COORDS(PLAYER_PED_ID(), <<-13.3596, -1471.8689, 29.5836>>)
SET_ENTITY_HEADING(PLAYER_PED_ID(), 137.1648)
FORCE_PED_AI_AND_ANIMATION_UPDATE(PLAYER_PED_ID(), TRUE)
TASK_LOOK_AT_ENTITY(PLAYER_PED_ID(), myPed, -1)
TASK_LOOK_AT_ENTITY(myPed, PLAYER_PED_ID(), -1)
ENDIF
ADD_PED_FOR_DIALOGUE(pedConvo, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(pedConvo, 3, myPed, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_TOW_2", CONV_PRIORITY_VERY_HIGH)
bSecondConvoRan = TRUE
ENDIF
IF NOT IS_TIMER_STARTED(tCutsceneTimer)
START_TIMER_NOW(tCutsceneTimer)
PRINTLN("STARTING TIMER - tCutsceneTimer")
ELSE
RESTART_TIMER_NOW(tCutsceneTimer)
PRINTLN("RESTARTING TIMER - tCutsceneTimer")
ENDIF
PRINTLN("iSecondCutsceneStages = 1")
iSecondCutsceneStages = 1
BREAK
//------------------------------------------------------------------------------------------------
CASE 1
IF NOT bSecondConvoRan
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_TOW_2", CONV_PRIORITY_VERY_HIGH)
bSecondConvoRan = TRUE
ENDIF
ENDIF
IF IS_TIMER_STARTED(tCutsceneTimer)
IF GET_TIMER_IN_SECONDS(tCutsceneTimer) > 12.0
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
PRINTLN("iSecondCutsceneStages = 2")
iSecondCutsceneStages = 2
ELSE
// PRINTLN("CONVERSATION IS STILL GOING")
ENDIF
ENDIF
ENDIF
BREAK
//------------------------------------------------------------------------------------------------
CASE 2
RETURN TRUE
BREAK
//------------------------------------------------------------------------------------------------
CASE 3
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
PRINTLN("iSecondCutsceneStages = 4")
iSecondCutsceneStages = 4
BREAK
//------------------------------------------------------------------------------------------------
CASE 4
PRINTLN("SKIPPING CUTSCENE: iSecondCutsceneStages = 4")
DO_SCREEN_FADE_IN(1000)
WHILE NOT IS_SCREEN_FADED_IN()
WAIT(0)
ENDWHILE
RETURN TRUE
BREAK
//------------------------------------------------------------------------------------------------
ENDSWITCH
RETURN FALSE
ENDFUNC
FUNC BOOL RUN_LAST_TONYA_CUTSCENE(PED_INDEX myPed)
IF NOT bSkippedThirdCutscene
IF IS_TIMER_STARTED(tCutsceneTimer)
IF GET_TIMER_IN_SECONDS(tCutsceneTimer) > 1.0
IF IS_CUTSCENE_SKIP_BUTTON_JUST_PRESSED()
DO_SCREEN_FADE_OUT(500)
WHILE NOT IS_SCREEN_FADED_OUT()
WAIT(0)
ENDWHILE
CLEAR_PRINTS()
CLEAR_HELP()
HANG_UP_AND_PUT_AWAY_PHONE()
STOP_SCRIPTED_CONVERSATION(FALSE)
PRINTLN("TOWING: LAST CUTSCENE HAS BEEN SKIPPED")
PRINTLN("iThirdCutsceneStages = 3")
iThirdCutsceneStages = 3
bSkippedThirdCutscene = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
SWITCH iThirdCutsceneStages
CASE 0
cam01 = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, <<-12.2070, -1472.5962, 31.2021>>, <<-5.2325, -0.0000, 96.5678>>, 35.0, TRUE)
cam02 = CREATE_CAMERA_WITH_PARAMS(CAMTYPE_SCRIPTED, <<-12.2642, -1472.0994, 31.2021>>, <<-5.2325, -0.0000, 96.5678>>, 35.0, FALSE)
CLEAR_PRINTS()
CLEAR_HELP()
DISPLAY_RADAR(FALSE)
DISPLAY_HUD(FALSE)
DISABLE_CELLPHONE(TRUE)
WAIT(0)
SET_PLAYER_CONTROL(PLAYER_ID(), FALSE, SPC_REMOVE_EXPLOSIONS | SPC_REMOVE_FIRES | SPC_REMOVE_PROJECTILES)
RENDER_SCRIPT_CAMS(TRUE, FALSE)
RESOLVE_VEHICLES_INSIDE_ANGLED_AREA(<<-11.207333,-1475.108398,29.046181>>, <<-17.081156,-1469.945068,33.362968>>, 6.250000, vVehicleStartPosition, fVehicleStartHeading)
SET_CAM_ACTIVE_WITH_INTERP(cam02, cam01, 12000)
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myPed)
SET_ENTITY_COORDS(PLAYER_PED_ID(), <<-13.3596, -1471.8689, 29.5836>>)
SET_ENTITY_HEADING(PLAYER_PED_ID(), 137.1648)
FORCE_PED_AI_AND_ANIMATION_UPDATE(PLAYER_PED_ID(), TRUE)
TASK_LOOK_AT_ENTITY(PLAYER_PED_ID(), myPed, -1)
TASK_LOOK_AT_ENTITY(myPed, PLAYER_PED_ID(), -1)
ENDIF
ADD_PED_FOR_DIALOGUE(pedConvo, 1, PLAYER_PED_ID(), "FRANKLIN")
ADD_PED_FOR_DIALOGUE(pedConvo, 3, myPed, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_TOW_5", CONV_PRIORITY_VERY_HIGH)
bLastConvoRan = TRUE
ENDIF
IF NOT IS_TIMER_STARTED(tCutsceneTimer)
START_TIMER_NOW(tCutsceneTimer)
PRINTLN("STATING TIMER - tCutsceneTimer")
ENDIF
PRINTLN("iThirdCutsceneStages = 1")
iThirdCutsceneStages = 1
BREAK
//------------------------------------------------------------------------------------------------
CASE 1
IF NOT bLastConvoRan
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_TOW_5", CONV_PRIORITY_VERY_HIGH)
bLastConvoRan = TRUE
ENDIF
ENDIF
IF IS_TIMER_STARTED(tCutsceneTimer)
IF GET_TIMER_IN_SECONDS(tCutsceneTimer) > 12.0
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
PRINTLN("iThirdCutsceneStages = 2")
iThirdCutsceneStages = 2
ELSE
// PRINTLN("CONVERSATION IS STILL GOING")
ENDIF
ENDIF
ENDIF
BREAK
//------------------------------------------------------------------------------------------------
CASE 2
RETURN TRUE
BREAK
//------------------------------------------------------------------------------------------------
CASE 3
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
PRINTLN("iThirdCutsceneStages = 4")
iThirdCutsceneStages = 4
BREAK
//------------------------------------------------------------------------------------------------
CASE 4
PRINTLN("SKIPPING CUTSCENE: iThirdCutsceneStages = 4")
DO_SCREEN_FADE_IN(1000)
WHILE NOT IS_SCREEN_FADED_IN()
WAIT(0)
ENDWHILE
RETURN TRUE
BREAK
//------------------------------------------------------------------------------------------------
ENDSWITCH
RETURN FALSE
ENDFUNC
FUNC BOOL IS_FRANKLIN_IN_ANY_TOW_TRUCK(VEHICLE_INDEX& myVehicle, BOOL bCheckTonya = FALSE, PED_INDEX pedTonya = NULL)
IF DOES_ENTITY_EXIST(PLAYER_PED_ID())
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
// PRINTLN("PLAYER IS IN A TOW TRUCK ALREADY - 02")
VEHICLE_INDEX vehTemp
vehTemp = GET_VEHICLE_PED_IS_IN(PLAYER_PED_ID())
IF DOES_ENTITY_EXIST(vehTemp) AND NOT IS_ENTITY_DEAD(vehTemp)
IF GET_ENTITY_MODEL(vehTemp) = TOWTRUCK
OR GET_ENTITY_MODEL(vehTemp) = TOWTRUCK2
IF bCheckTonya
IF DOES_ENTITY_EXIST(pedTonya) AND NOT IS_ENTITY_DEAD(pedTonya) AND NOT IS_ENTITY_DEAD(vehTemp)
IF IS_PED_IN_VEHICLE(pedTonya, vehTemp) AND IS_PED_IN_VEHICLE(PLAYER_PED_ID(), vehTemp)
IF DOES_ENTITY_EXIST(myVehicle)
IF IS_ENTITY_OCCLUDED(myVehicle)
DELETE_VEHICLE(myVehicle)
PRINTLN("DELETING TOW TRUCK - BECAUSE PLAYER HOPPED IN ONE ALREADY")
ELSE
SET_VEHICLE_AS_NO_LONGER_NEEDED(myVehicle)
PRINTLN("SETTING TOW TRUCK AS NO LONGER NEEDED - BECAUSE PLAYER HOPPED IN ONE ALREADY")
ENDIF
ENDIF
myVehicle = vehTemp
PRINTLN("VEHICLE ASSIGNMENT IN PLACE VIA UPDATE TUTORIAL PED - 01")
RETURN TRUE
ENDIF
ENDIF
ELSE
IF DOES_ENTITY_EXIST(myVehicle)
IF IS_ENTITY_OCCLUDED(myVehicle)
DELETE_VEHICLE(myVehicle)
PRINTLN("DELETING TOW TRUCK - BECAUSE PLAYER HOPPED IN ONE ALREADY")
ELSE
SET_VEHICLE_AS_NO_LONGER_NEEDED(myVehicle)
PRINTLN("SETTING TOW TRUCK AS NO LONGER NEEDED - BECAUSE PLAYER HOPPED IN ONE ALREADY")
ENDIF
ENDIF
myVehicle = vehTemp
PRINTLN("VEHICLE ASSIGNMENT IN PLACE VIA UPDATE TUTORIAL PED - 02")
RETURN TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
RETURN FALSE
ENDFUNC
PROC UPDATE_LAW(BROKEN_VEHICLE& brokenVehicles[], BOOL bVehicleHooked, VECTOR& vCurDestObjective[], BLIP_INDEX& truckBlip,
BLIP_INDEX& blipImpound, VEHICLE_INDEX& myVehicle, MISSION_STATE curStage, PED_INDEX pedToShout = NULL)
bVehicleHooked = bVehicleHooked
IF NOT bWanted
IF IS_PLAYER_WANTED_LEVEL_GREATER(GET_PLAYER_INDEX(), 0)
IF IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
KILL_FACE_TO_FACE_CONVERSATION_DO_NOT_FINISH_LAST_LINE()
ENDIF
IF pedToShout <> NULL
IF NOT IS_ENTITY_DEAD(pedToShout)
PLAY_PED_AMBIENT_SPEECH_WITH_VOICE(pedToShout, "GET_WANTED_LEVEL", "TONYA", SPEECH_PARAMS_SHOUTED)
PRINTLN("PLAYING PED AMBIENT SPEECH")
ENDIF
ENDIF
IF DOES_BLIP_EXIST(brokenVehicles[0].blipIndex)
REMOVE_BLIP(brokenVehicles[0].blipIndex)
PRINTLN("REMOVING BLIP - brokenVehicles[0].blipIndex")
ENDIF
IF DOES_BLIP_EXIST(brokenVehicles[0].blipIndexPed)
REMOVE_BLIP(brokenVehicles[0].blipIndexPed)
PRINTLN("REMOVING BLIP - brokenVehicles[0].blipIndexPed")
ENDIF
IF DOES_BLIP_EXIST(truckBlip)
REMOVE_BLIP(truckBlip)
PRINTLN("REMOVING BLIP - truckBlip")
ENDIF
IF DOES_BLIP_EXIST(blipImpound)
REMOVE_BLIP(blipImpound)
PRINTLN("REMOVING BLIP - blipImpound")
ENDIF
bWanted = TRUE
PRINT_NOW("TOW_OBJ_06", DEFAULT_GOD_TEXT_TIME,1)
PRINTLN("TOWING: PLAYER WANTED")
ENDIF
ELSE
IF NOT IS_PLAYER_WANTED_LEVEL_GREATER(GET_PLAYER_INDEX(), 0) AND bWanted
IF IS_THIS_PRINT_BEING_DISPLAYED("TOW_OBJ_06")
CLEAR_PRINTS()
ENDIF
IF NOT DOES_BLIP_EXIST(brokenVehicles[0].blipIndex)
//Are we at the tow truck yet?
IF curStage > MISSION_STATE_INTRO
IF bOutOfVehicle
truckBlip = ADD_BLIP_FOR_ENTITY(myVehicle)
SET_BLIP_COLOUR(truckBlip, BLIP_COLOUR_BLUE)
EXIT
ENDIF
//We are headed back to the drop off. Need to make sure the car is hooked.
IF curStage >= MISSION_STATE_DROPOFF AND curStage < MISSION_STATE_DROPOFF_TONYA
IF NOT IS_ENTITY_DEAD(myVehicle) AND NOT IS_ENTITY_DEAD(brokenVehicles[0].vehicleIndex)
AND IS_VEHICLE_ATTACHED_TO_TOW_TRUCK(myVehicle, brokenVehicles[0].vehicleIndex)
SCRIPT_REMOVE_BLIP_SAFE(blipImpound)
blipImpound = ADD_BLIP_FOR_COORD(vCurDestObjective[0])
SET_BLIP_COLOUR(blipImpound, BLIP_COLOUR_YELLOW)
SET_BLIP_ROUTE(blipImpound, TRUE)
ELSE
brokenVehicles[0].blipIndex = ADD_BLIP_FOR_ENTITY(brokenVehicles[0].vehicleIndex)
SET_BLIP_COLOUR(brokenVehicles[0].blipIndex, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(brokenVehicles[0].blipIndex, TRUE)
ENDIF
ELIF curStage < MISSION_STATE_DROPOFF_TONYA
brokenVehicles[0].blipIndex = ADD_BLIP_FOR_COORD(vCurDestObjective[0])
SET_BLIP_COLOUR(brokenVehicles[0].blipIndex, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(brokenVehicles[0].blipIndex, TRUE)
ENDIF
ELIF NOT DOES_BLIP_EXIST(truckBlip)
truckBlip = ADD_BLIP_FOR_ENTITY(myVehicle)
SET_BLIP_COLOUR(truckBlip, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(truckBlip, TRUE)
PRINTLN("WANTED CHECK: ADDING BACK IN truckBlip")
ENDIF
ENDIF
fObjDist = GET_PLAYER_DISTANCE_FROM_LOCATION(vCurDestObjective[0], FALSE)
PRINTLN("UPDATE_LAW - fObjDist = ", fObjDist)
bWanted = FALSE
PRINTLN("TOWING: PLAYER NO LONGER WANTED")
ENDIF
ENDIF
ENDPROC
//This is for the ped waiting for you at the first tow truck
FUNC BOOL UPDATE_TUTORIAL_PED(VEHICLE_INDEX& myVehicle, PED_INDEX myPed, BLIP_INDEX& towBlip, BOOL& bCleanUp,
BOOL& bAggroedTonya, BOOL& bAbandonedTonya, BOOL& bRunningThreeOrFour, BOOL& bSkipTutorial, BOOL& bReplaying)
IF bSkipTutorial
PRINTLN("WE SKIPPED THE TUTORIAL FUNCTION - RETURNING TRUE")
RETURN TRUE
ENDIF
IF DOES_ENTITY_EXIST(myPed) AND DOES_ENTITY_EXIST(myVehicle)
IF IS_ENTITY_DEAD(myPed) OR IS_ENTITY_DEAD(myVehicle)
IF NOT bRunningThreeOrFour
SET_BITMASK_AS_ENUM(g_savedGlobals.sTowingData.iBools, TOW_GLOBAL_MAX_DELAY)
bCleanUp = TRUE
bAggroedTonya = TRUE
PRINTLN("bCleanUp = TRUE - 01")
ENDIF
ELIF GET_PLAYER_DISTANCE_FROM_ENTITY(myPed) > 50 OR GET_PLAYER_WANTED_LEVEL(PLAYER_ID()) > 0
IF NOT bRunningThreeOrFour
IF NOT bToldToReturnToTonya
PRINT("TOW_TUT_RETONYA", DEFAULT_GOD_TEXT_TIME, 1)
PRINTLN("PRINTING LINE TO RETURN TO TONYA")
bToldToReturnToTonya = TRUE
IF DOES_BLIP_EXIST(blipTruck)
REMOVE_BLIP(blipTruck)
PRINTLN("REMOVING BLIP - blipTruck")
ENDIF
IF GET_PLAYER_WANTED_LEVEL(PLAYER_ID()) = 0
IF NOT DOES_BLIP_EXIST(blipTonya)
blipTonya = ADD_BLIP_FOR_ENTITY(myPed)
SET_BLIP_COLOUR(blipTonya, BLIP_COLOUR_BLUE)
SET_BLIP_SCALE(blipTonya, 0.5)
PRINTLN("ADDING BLIP - blipTonya")
ENDIF
ENDIF
ENDIF
IF GET_PLAYER_DISTANCE_FROM_ENTITY(myPed) > 150 OR GET_PLAYER_WANTED_LEVEL(PLAYER_ID()) > 0
SET_BITMASK_AS_ENUM(g_savedGlobals.sTowingData.iBools, TOW_GLOBAL_10_DELAY)
bCleanUp = TRUE
bAbandonedTonya = TRUE
PRINTLN("bCleanUp = TRUE - 02")
ENDIF
ENDIF
ELIF DO_AGGRO_CHECK(myPed, NULL, aggroArgs, aggroReason, FALSE, TRUE, FALSE, TRUE, FALSE)
SET_BITMASK_AS_ENUM(g_savedGlobals.sTowingData.iBools, TOW_GLOBAL_MAX_DELAY)
bCleanUp = TRUE
bAggroedTonya = TRUE
PRINTLN("bCleanUp = TRUE - 03")
ELSE
IF GET_PLAYER_WANTED_LEVEL(PLAYER_ID()) = 0
IF GET_PLAYER_DISTANCE_FROM_ENTITY(myPed) < 50
IF bToldToReturnToTonya
bToldToReturnToTonya = FALSE
PRINTLN("bToldToReturnToTonya = FALSE")
IF NOT DOES_BLIP_EXIST(blipTruck)
blipTruck = ADD_BLIP_FOR_ENTITY(myVehicle)
SET_BLIP_COLOUR(blipTruck, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(blipTruck, TRUE)
PRINTLN("ADDING BACK IN TOW TRUCK BLIP")
ENDIF
IF DOES_BLIP_EXIST(blipTonya)
REMOVE_BLIP(blipTonya)
PRINTLN("REMOVING BLIP - blipTonya")
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
// FLOAT fTempDistance = GET_PLAYER_DISTANCE_FROM_ENTITY(myPed)
// PRINTLN("PLAYER DISTANCE FROM DUDE: ", fTempDistance)
IF bCleanUp
STOP_SCRIPTED_CONVERSATION(FALSE)
IF NOT IS_PED_INJURED(myPed)
IF IS_ENTITY_PLAYING_ANIM(myPed, "oddjobs@towing", "thanks_male_04")
STOP_ANIM_TASK(myPed, "oddjobs@towings", "thanks_male_04")
PRINTLN("STOPPING ANIMATION ON TUTORIAL PED")
ENDIF
CLEAR_PED_TASKS(myPed)
SET_PED_KEEP_TASK(myPed, TRUE)
TASK_SMART_FLEE_PED(myPed, PLAYER_PED_ID(), 1000, -1)
ENDIF
PRINTLN("Shutting down towing")
SCRIPT_REMOVE_BLIP_SAFE(towBlip)
IF tutorialPedState > TUT_PED_CREATE
TONYA_FIRST_CUTSCENE_CLEANUP(myPed)
ENDIF
RETURN TRUE
ENDIF
SWITCH tutorialPedState
CASE TUT_PED_CREATE
// bPedCreated = TRUE
// PRINTLN("bPedCreated = TRUE - TUT_PED_CREATE")
IF DOES_ENTITY_EXIST(myPed)
IF NOT IS_ENTITY_DEAD(myPed)
SET_ENTITY_AS_MISSION_ENTITY(myPed, TRUE, TRUE)
ADD_RELATIONSHIP_GROUP("instructorRelGroup", relInstructor)
SET_PED_RELATIONSHIP_GROUP_HASH(myPed, relInstructor)
SET_RELATIONSHIP_BETWEEN_GROUPS(ACQUAINTANCE_TYPE_PED_RESPECT, relInstructor, RELGROUPHASH_PLAYER)
ENDIF
ENDIF
PRINTLN("GOING TO STATE - TUT_PED_CUTSCENE")
tutorialPedState = TUT_PED_CUTSCENE
BREAK
//------------------------------------------------------------------------------------------------------------------------------
CASE TUT_PED_CUTSCENE
IF GET_RANDOM_BOOL()
IF g_savedGlobals.sTowingData.iTowingJobsCompleted = 1
IF RUN_SECOND_TONYA_CUTSCENE(myPed)
// Unlock Tonya as a contact.
ADD_CONTACT_TO_PHONEBOOK(CHAR_TOW_TONYA, FRANKLIN_BOOK)
SET_REPLAY_MID_MISSION_STAGE_WITH_NAME(0, "towing_tonya_franklin_travel")
PRINTLN("FIRST CUTSCENE IF FINISHED - GOING TO STATE - TUT_PED_TRAVEL - 01")
tutorialPedState = TUT_PED_TRAVEL
ENDIF
ELIF g_savedGlobals.sTowingData.iTowingJobsCompleted = 4
IF RUN_LAST_TONYA_CUTSCENE(myPed)
SET_REPLAY_MID_MISSION_STAGE_WITH_NAME(0, "towing_tonya_franklin_travel")
PRINTLN("LAST CUTSCENE IF FINISHED - GOING TO STATE - TUT_PED_TRAVEL - 02")
tutorialPedState = TUT_PED_TRAVEL
ENDIF
ENDIF
ELIF bRunningThreeOrFour
PRINTLN("RUNNING THREE OR FOUR - GOING TO STATE - TUT_PED_TRAVEL")
tutorialPedState = TUT_PED_TRAVEL
ELSE
IF RUN_FIRST_TONYA_CUTSCENE(myPed)
// Unlock Tonya as a contact.
ADD_CONTACT_TO_PHONEBOOK(CHAR_TOW_TONYA, FRANKLIN_BOOK)
SET_REPLAY_MID_MISSION_STAGE_WITH_NAME(0, "towing_tonya_franklin_travel")
PRINTLN("FIRST CUTSCENE IF FINISHED - GOING TO STATE - TUT_PED_TRAVEL - 03")
tutorialPedState = TUT_PED_TRAVEL
ENDIF
ENDIF
BREAK
//------------------------------------------------------------------------------------------------------------------------------
CASE TUT_PED_TRAVEL
IF NOT bRunningThreeOrFour
PRINTLN("MUST BE RUNNING TOWING 1")
IF NOT IS_ENTITY_DEAD(myPed)
// Print an objective.
IF (g_savedGlobals.sTowingData.iTowingJobsCompleted = 0)
OR (g_savedGlobals.sTowingData.iTowingJobsCompleted = 1)
OR (g_savedGlobals.sTowingData.iTowingJobsCompleted = 4)
IF IS_ENTITY_PLAYING_ANIM(myPed, "amb@world_human_smoking@male@male_a@base", "base")
STOP_ANIM_TASK(myPed, "amb@world_human_smoking@male@male_a@base", "base")
ENDIF
SET_PED_AS_GROUP_MEMBER(myPed, PLAYER_GROUP_ID())
SET_PED_NEVER_LEAVES_GROUP(myPed, TRUE)
SET_PED_GROUP_MEMBER_PASSENGER_INDEX(myPed, VS_FRONT_RIGHT)
SET_GROUP_FORMATION(PLAYER_GROUP_ID(), FORMATION_LOOSE)
SET_PED_CONFIG_FLAG(myPed, PCF_ForcedToUseSpecificGroupSeatIndex, TRUE)
PRINTLN("PLACING TONYA IN OUR GROUP")
ENDIF
ENDIF
ENDIF
IF NOT IS_TIMER_STARTED(tDialogueBufferTimer)
START_TIMER_NOW(tDialogueBufferTimer)
PRINTLN("STARTING TIMER - tDialogueBufferTimer")
ELSE
RESTART_TIMER_NOW(tDialogueBufferTimer)
PRINTLN("RESTARTING TIMER - tDialogueBufferTimer")
ENDIF
IF NOT IS_PLAYER_IN_TOW_TRUCK()
// Objective
PRINT("TOW_TUT_INTRUCK", DEFAULT_GOD_TEXT_TIME, 1)
// Blip
IF NOT DOES_BLIP_EXIST(blipTruck)
blipTruck = ADD_BLIP_FOR_ENTITY(myVehicle)
SET_BLIP_COLOUR(blipTruck, BLIP_COLOUR_BLUE)
SET_BLIP_ROUTE(blipTruck, TRUE)
SET_GPS_FLAGS(GPS_FLAG_CUSTOM_PROXIMITY, 0)
PRINTLN("SETTING BLIP ROUTE - blipTruck")
ENDIF
ELSE
PRINTLN("RETURNING TRUE ON UPDATE_TUTORIAL_PED - PLAYER IS ALREADY IN A TOW TRUCK")
RETURN TRUE
ENDIF
PRINTLN("CUTSCENE IF FINISHED - GOING TO STATE - TUT_PED_ARRIVE")
tutorialPedState = TUT_PED_ARRIVE
BREAK
//------------------------------------------------------------------------------------------------------------------------------
CASE TUT_PED_ARRIVE
IF NOT DOES_ENTITY_EXIST(vehReplayVehicle)
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
vehReplayVehicle = GET_VEHICLE_PED_IS_IN(PLAYER_PED_ID())
PRINTLN("FOUND REPLAY VEHICLE")
IF DOES_ENTITY_EXIST(vehReplayVehicle) AND NOT IS_ENTITY_DEAD(vehReplayVehicle)
OVERRIDE_REPLAY_CHECKPOINT_VEHICLE(vehReplayVehicle)
ENDIF
ENDIF
ENDIF
ENDIF
IF NOT bReplaying
IF NOT bRunningThreeOrFour
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myPed)
IF IS_ENTITY_IN_ANGLED_AREA(PLAYER_PED_ID(), <<423.742371,-1652.842163,27.268002>>, <<397.839600,-1630.331665,40.292778>>, 42.000000)
AND IS_ENTITY_IN_ANGLED_AREA(myPed, <<423.742371,-1652.842163,27.268002>>, <<397.839600,-1630.331665,40.292778>>, 42.000000)
IF NOT IS_ANY_CONVERSATION_ONGOING_OR_QUEUED()
IF NOT bPlayedTruckDialogue
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 3, myPed, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_AT_TRK", CONV_PRIORITY_HIGH)
PRINTLN("PLAYING ACKNOWLEDGE TRUCK CONVO")
bPlayedTruckDialogue = TRUE
ENDIF
ENDIF
ENDIF
ELSE
IF NOT bTonyaGotCarDialogue
IF IS_TIMER_STARTED(tDialogueBufferTimer)
IF GET_TIMER_IN_SECONDS(tDialogueBufferTimer) > 5.0
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())AND NOT IS_ENTITY_DEAD(myPed)
IF NOT IS_PED_IN_ANY_VEHICLE(PLAYER_PED_ID())
ADD_PED_FOR_DIALOGUE(MyLocalPedStruct, 3, myPed, "TONYA")
IF CREATE_CONVERSATION(pedConvo, "TOWAUD", "TONYA_CAR", CONV_PRIORITY_HIGH)
PRINTLN("TONYA - GOT CAR CONVO")
bTonyaGotCarDialogue = TRUE
ENDIF
ELSE
PRINTLN("WE'VE BEEN A CAR AT SOME POINT")
bTonyaGotCarDialogue = TRUE
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
ENDIF
IF bRunningThreeOrFour
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID())
IF IS_PED_IN_VEHICLE(PLAYER_PED_ID(), myVehicle) OR IS_FRANKLIN_IN_ANY_TOW_TRUCK(myVehicle)
IF DOES_BLIP_EXIST(blipTruck)
REMOVE_BLIP(blipTruck)
PRINTLN("REMOVING BLIP - blipTruck - 01")
ENDIF
PRINTLN("RETURNING TRUE ON UPDATE_TUTORIAL_PED - 01")
RETURN TRUE
ELSE
// PRINTLN("WAITING ON THEM TO ENTER TOW TRUCK")
ENDIF
ENDIF
ELSE
IF NOT IS_ENTITY_DEAD(PLAYER_PED_ID()) AND NOT IS_ENTITY_DEAD(myPed)
IF IS_PED_IN_VEHICLE(PLAYER_PED_ID(), myVehicle) AND IS_PED_IN_VEHICLE(myPed, myVehicle)
OR IS_FRANKLIN_IN_ANY_TOW_TRUCK(myVehicle, TRUE, myPed)
IF DOES_BLIP_EXIST(blipTruck)
REMOVE_BLIP(blipTruck)
PRINTLN("REMOVING BLIP - blipTruck - 02")
ENDIF
IF DOES_BLIP_EXIST(blipTonya)
REMOVE_BLIP(blipTonya)
PRINTLN("REMOVING BLIP - blipTonya")
ENDIF
SET_REPLAY_MID_MISSION_STAGE_WITH_NAME(1, "towing_tonya_franklin_towing")
OVERRIDE_REPLAY_CHECKPOINT_VEHICLE(vehReplayVehicle)
PRINTLN("RETURNING TRUE ON UPDATE_TUTORIAL_PED - 02")
RETURN TRUE
ELSE
// PRINTLN("WAITING ON THEM TO ENTER TOW TRUCK")
ENDIF
ENDIF
ENDIF
BREAK
ENDSWITCH
//Towtruck posiiton: 405.8, -1628, 29.93
//Ped position: 417.7, -1662.5, 33.64 275.1529
RETURN FALSE
ENDFUNC