Files
gtav-src/script/dev_ng/singleplayer/include/public/script_heist.sch
T
2025-09-29 00:52:08 +02:00

2074 lines
90 KiB
XML
Executable File

//╒═════════════════════════════════════════════════════════════════════════════╕
//│ Author: Ben Rollinson Date: 15/03/10 │
//╞═════════════════════════════════════════════════════════════════════════════╡
//│ │
//│ Heist Public Script Header │
//│ │
//│ Contains all public procedures and functions that are required │
//│ when scriping heist missions. │
//│ │
//╘═════════════════════════════════════════════════════════════════════════════╛
USING "rage_builtins.sch"
USING "globals.sch"
USING "commands_ped.sch"
USING "commands_streaming.sch"
USING "commands_misc.sch"
USING "commands_camera.sch"
USING "script_player.sch"
USING "heist_private.sch"
USING "flow_public_core_override.sch"
USING "cellphone_public.sch"
USING "Screen_placements.sch"
USING "hud_drawing.sch"
USING "commands_network.sch"
ENUM HeistCrewOutfit
CREW_OUTFIT_DEFAULT,
CREW_OUTFIT_PEST_CONTROL,
CREW_OUTFIT_SCUBA,
CREW_OUTFIT_SCUBA_LAND,
CREW_OUTFIT_MIME,
CREW_OUTFIT_CLOWN,
CREW_OUTFIT_HEAVY_ARMOR,
CREW_OUTFIT_FIRE_FIGHTING,
CREW_OUTFIT_STEALTH,
CREW_OUTFIT_SECURITY,
CREW_OUTFIT_SUIT
ENDENUM
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞════════════════════════╡ Heist Debug String Lookup ╞════════════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
#IF IS_DEBUG_BUILD
FUNC STRING GET_HEIST_INDEX_DEBUG_STRING(INT paramHeistIndex)
SWITCH paramHeistIndex
CASE HEIST_JEWEL
RETURN "HEIST_JEWEL"
BREAK
CASE HEIST_DOCKS
RETURN "HEIST_DOCKS"
BREAK
CASE HEIST_RURAL_BANK
RETURN "HEIST_RURAL_BANK"
BREAK
CASE HEIST_AGENCY
RETURN "HEIST_AGENCY"
BREAK
CASE HEIST_FINALE
RETURN "HEIST_FINALE"
BREAK
ENDSWITCH
SCRIPT_ASSERT("GET_HEIST_INDEX_DEBUG_STRING: The INT passed was not a valid heist index.")
RETURN "INVALID!"
ENDFUNC
FUNC STRING GET_HEIST_CREW_OUTFIT_DEBUG_STRING(HeistCrewOutfit paramCrewOutfit)
SWITCH paramCrewOutfit
CASE CREW_OUTFIT_DEFAULT
RETURN "DEFAULT"
BREAK
CASE CREW_OUTFIT_PEST_CONTROL
RETURN "PEST_CONTROL"
BREAK
CASE CREW_OUTFIT_SCUBA
RETURN "SCUBA"
BREAK
CASE CREW_OUTFIT_SCUBA_LAND
RETURN "SCUBA_LAND"
BREAK
CASE CREW_OUTFIT_MIME
RETURN "MIME"
BREAK
CASE CREW_OUTFIT_CLOWN
RETURN "CLOWN"
BREAK
CASE CREW_OUTFIT_HEAVY_ARMOR
RETURN "HEAVY_ARMOR"
BREAK
CASE CREW_OUTFIT_FIRE_FIGHTING
RETURN "FIRE_FIGHTING"
BREAK
CASE CREW_OUTFIT_STEALTH
RETURN "STEALTH"
BREAK
CASE CREW_OUTFIT_SECURITY
RETURN "SECURITY"
BREAK
CASE CREW_OUTFIT_SUIT
RETURN "SUIT"
BREAK
ENDSWITCH
SCRIPT_ASSERT("GET_HEIST_CREW_OUTFIT_DEBUG_STRING: The crew outfit ENUM passed did not have a debug string configured. Bug BenR.")
RETURN "INVALID!"
ENDFUNC
FUNC STRING GET_HEIST_CREW_TYPE_DEBUG_STRING(CrewMemberType type)
SWITCH type
CASE CMT_EMPTY
RETURN "EMPTY"
BREAK
CASE CMT_GUNMAN
RETURN "GUNMAN"
BREAK
CASE CMT_HACKER
RETURN "HACKER"
BREAK
CASE CMT_DRIVER
RETURN "DRIVER"
BREAK
ENDSWITCH
RETURN "ERROR"
ENDFUNC
FUNC STRING GET_HEIST_CREW_STATUS_DEBUG_STRING(CrewMemberStatus status)
SWITCH status
CASE CMST_FINE
RETURN "FINE"
BREAK
CASE CMST_INJURED
RETURN "INJURED"
BREAK
CASE CMST_KILLED
RETURN "KILLED"
BREAK
CASE CMST_NOT_SET
RETURN "NOT SET"
BREAK
ENDSWITCH
RETURN "ERROR"
ENDFUNC
#ENDIF
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞═══════════════════╡ Heist Planning Location Information ╞═══════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the planning location associated with a specified heist.
FUNC PlanningLocationName GET_HEIST_PLANNING_LOCATION_ENUM(INT heistIndex)
SWITCH heistIndex
CASE HEIST_JEWEL
RETURN PLN_SWEATSHOP
BREAK
CASE HEIST_DOCKS
RETURN PLN_TREV_CITY
BREAK
CASE HEIST_RURAL_BANK
RETURN PLN_METH_LAB
BREAK
CASE HEIST_AGENCY
RETURN PLN_SWEATSHOP
BREAK
CASE HEIST_FINALE
RETURN PLN_STRIPCLUB
BREAK
ENDSWITCH
SCRIPT_ASSERT("GET_HEIST_PLANNING_LOCATION_ENUM: Invalid heist index passed.")
RETURN PLN_ERROR
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the position of the planning location associated with a specified heist.
FUNC VECTOR GET_HEIST_PLANNING_LOCATION(INT heistIndex)
PlanningLocationName ePlanningLoc = GET_HEIST_PLANNING_LOCATION_ENUM(heistIndex)
IF ePlanningLoc != PLN_ERROR
RETURN g_sPlanningLocationData[ePlanningLoc].vPlanningLocation
ENDIF
SCRIPT_ASSERT("GET_HEIST_PLANNING_LOCATION: Invalid heist index passed.")
RETURN <<0,0,0>>
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the position of the board in a planning location associated with a specified heist.
FUNC VECTOR GET_HEIST_PLANNING_BOARD_LOCATION(INT heistIndex)
PlanningLocationName ePlanningLoc = GET_HEIST_PLANNING_LOCATION_ENUM(heistIndex)
IF ePlanningLoc != PLN_ERROR
RETURN g_sPlanningLocationData[ePlanningLoc].vPlanningLocationBoard
ENDIF
SCRIPT_ASSERT("GET_HEIST_PLANNING_BOARD_LOCATION: Invalid heist index passed.")
RETURN <<0,0,0>>
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the heading of the board in a planning location associated with a specified heist.
FUNC FLOAT GET_HEIST_PLANNING_LOCATION_BOARD_HEADING(INT heistIndex)
PlanningLocationName ePlanningLoc = GET_HEIST_PLANNING_LOCATION_ENUM(heistIndex)
IF ePlanningLoc != PLN_ERROR
RETURN g_sPlanningLocationData[ePlanningLoc].fPlanningLocationBoardHeading
ENDIF
SCRIPT_ASSERT("GET_HEIST_PLANNING_LOCATION_BOARD_HEADING: Invalid heist index passed.")
RETURN 0.00
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the room name of the planning location interior associated with a specified heist.
FUNC TEXT_LABEL_31 GET_HEIST_PLANNING_LOCATION_ROOM_NAME(INT heistIndex)
PlanningLocationName ePlanningLoc = GET_HEIST_PLANNING_LOCATION_ENUM(heistIndex)
IF ePlanningLoc != PLN_ERROR
RETURN g_sPlanningLocationData[ePlanningLoc].tPlanningLocationRoomName
ENDIF
SCRIPT_ASSERT("GET_HEIST_PLANNING_LOCATION_ROOM_NAME: Invalid heist index passed.")
TEXT_LABEL_31 tEmpty = ""
RETURN tEmpty
ENDFUNC
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞═════════════════════╡ Crew Member Information Access ╞══════════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose name is to be retrieved.
//PURPOSE: Returns a text label that contains a string of the crew member's name.
FUNC STRING GET_CREW_MEMBER_NAME_LABEL(CrewMember crewMem)
RETURN PRIVATE_Get_Crew_Member_Name_Label(crewMem)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose name is to be retrieved.
//PURPOSE: Returns a text label that contains a string of the crew member's first name.
FUNC STRING GET_CREW_MEMBER_FIRST_NAME_LABEL(CrewMember crewMem)
RETURN PRIVATE_Get_Crew_Member_First_Name_Label(crewMem)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose type is to be retrieved.
//PURPOSE: Returns the type of a specified crew member.
FUNC CrewMemberType GET_CREW_MEMBER_TYPE(CrewMember crewMem)
RETURN g_sCrewMemberStaticData[crewMem].type
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose type is to be retrieved.
//PURPOSE: Returns a text label that contains a string representing the crew member's type.
FUNC STRING GET_CREW_MEMBER_TYPE_LABEL(CrewMember crewMem)
SWITCH g_sCrewMemberStaticData[crewMem].type
CASE CMT_GUNMAN
RETURN "HC_TYPE_G"
BREAK
CASE CMT_HACKER
RETURN "HC_TYPE_H"
BREAK
CASE CMT_DRIVER
RETURN "HC_TYPE_D"
BREAK
ENDSWITCH
SCRIPT_ASSERT("GET_CREW_MEMBER_TYPE_LABEL: Crew member has an invalid type set. Bug Ben R.")
RETURN "ERROR!"
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose type is to be retrieved.
//PURPOSE: Returns the type of a specified crew member.
FUNC CrewMemberSkill GET_CREW_MEMBER_SKILL(CrewMember crewMem)
RETURN g_savedGlobals.sHeistData.sCrewActiveData[crewMem].skill
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose type is to be retrieved.
//PURPOSE: Returns a text label that contains a string representing the crew member's skill level.
FUNC STRING GET_CREW_MEMBER_SKILL_LABEL(CrewMember crewMem)
SWITCH GET_CREW_MEMBER_SKILL(crewMem)
CASE CMSK_GOOD
RETURN "HC_SK_G"
BREAK
CASE CMSK_MEDIUM
RETURN "HC_SK_M"
BREAK
CASE CMSK_BAD
RETURN "HC_SK_B"
BREAK
ENDSWITCH
SCRIPT_ASSERT("GET_CREW_MEMBER_SKILL_LABEL: Crew member has an invalid skill set. Bug Ben R.")
RETURN "ERROR!"
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose character model is to be retrieved.
//PURPOSE: Returns the character model of a specified crew member.
FUNC MODEL_NAMES GET_CREW_MEMBER_MODEL(CrewMember crewMem)
RETURN g_sCrewMemberStaticData[crewMem].model
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose cut percentage is to be retrieved.
//PURPOSE: Returns the percentage of a heist's takings that the specified crew member will take as payment.
FUNC INT GET_CREW_MEMBER_JOB_CUT(CrewMember crewMem)
RETURN g_sCrewMemberStaticData[crewMem].jobCut
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to a gunman whose stat value we want to retrieve.
// stat - The gunman stat enum we want to retrieve a value for.
//PURPOSE: Returns a stat value for a specific gunman and a specific gunman stat.
FUNC INT GET_CREW_MEMBER_GUNMAN_STAT(CrewMember crewMem, CrewGunmanStat stat)
IF GET_CREW_MEMBER_TYPE(crewMem) != CMT_GUNMAN
SCRIPT_ASSERT("GET_CREW_MEMBER_GUNMAN_STAT: Crew member was not a gunman. Could not retrieve a valid stat value.")
RETURN -1
ENDIF
RETURN PRIVATE_Get_Crew_Member_Stat_At_Index(crewMem, ENUM_TO_INT(stat))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to a hacker whose stat value we want to retrieve.
// stat - The hacker stat enum we want to retrieve a value for.
//PURPOSE: Returns a stat value for a specific hacker and a specific hacker stat.
FUNC INT GET_CREW_MEMBER_HACKER_STAT(CrewMember crewMem, CrewHackerStat stat)
IF GET_CREW_MEMBER_TYPE(crewMem) != CMT_HACKER
SCRIPT_ASSERT("GET_CREW_MEMBER_HACKER_STAT: Crew member was not a hacker. Could not retrieve a valid stat value.")
RETURN -1
ENDIF
RETURN PRIVATE_Get_Crew_Member_Stat_At_Index(crewMem, ENUM_TO_INT(stat))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to a driver whose stat value we want to retrieve.
// stat - The driver stat enum we want to retrieve a value for.
//PURPOSE: Returns a stat value for a specific driver and a specific driver stat.
FUNC INT GET_CREW_MEMBER_DRIVER_STAT(CrewMember crewMem, CrewDriverStat stat)
IF GET_CREW_MEMBER_TYPE(crewMem) != CMT_DRIVER
SCRIPT_ASSERT("GET_CREW_MEMBER_DRIVER_STAT: Crew member was not a driver. Could not retrieve a valid stat value.")
RETURN -1
ENDIF
RETURN PRIVATE_Get_Crew_Member_Stat_At_Index(crewMem, ENUM_TO_INT(stat))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to a gunman whose stat value we want to retrieve.
// stat - The gunman stat enum we want to retrieve a value for.
//PURPOSE: Returns a stat value as a percentage of the highest value that the stat can have, for a
// specific gunman and a specific gunman stat.
FUNC INT GET_CREW_MEMBER_GUNMAN_STAT_AS_PERCENTAGE(CrewMember crewMem, CrewGunmanStat stat)
RETURN ROUND(TO_FLOAT(GET_CREW_MEMBER_GUNMAN_STAT(crewMem, stat)) / TO_FLOAT(PRIVATE_Get_Gunman_Stat_Max_Value(stat)) * 100.0)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to a hacker whose stat value we want to retrieve.
// stat - The hacekr stat enum we want to retrieve a value for.
//PURPOSE: Returns a stat value as a percentage of the highest value that the stat can have, for a
// specific hacker and a specific hacker stat.
FUNC INT GET_CREW_MEMBER_HACKER_STAT_AS_PERCENTAGE(CrewMember crewMem, CrewHackerStat stat)
RETURN ROUND(TO_FLOAT(GET_CREW_MEMBER_HACKER_STAT(crewMem, stat)) / TO_FLOAT(PRIVATE_Get_Hacker_Stat_Max_Value(stat)) * 100.0)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to a driver whose stat value we want to retrieve.
// stat - The driver stat enum we want to retrieve a value for.
//PURPOSE: Returns a stat value as a percentage of the highest value that the stat can have, for a
// specific driver and a specific driver stat.
FUNC INT GET_CREW_MEMBER_DRIVER_STAT_AS_PERCENTAGE(CrewMember crewMem, CrewDriverStat stat)
RETURN ROUND(TO_FLOAT(GET_CREW_MEMBER_DRIVER_STAT(crewMem, stat)) / TO_FLOAT(PRIVATE_Get_Driver_Stat_Max_Value(stat)) * 100.0)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// stat - The gunman stat enum we want to retrieve a name label for.
//PURPOSE: Returns a stat name label for a specific gunman stat.
FUNC STRING GET_GUNMAN_STAT_NAME_LABEL(CrewGunmanStat stat)
RETURN PRIVATE_Get_Crew_Type_Stat_Name_Label_At_Index(CMT_GUNMAN, ENUM_TO_INT(stat))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// stat - The hacker stat enum we want to retrieve a name label for.
//PURPOSE: Returns a stat name label for a specific hacker stat.
FUNC STRING GET_HACKER_STAT_NAME_LABEL(CrewHackerStat stat)
RETURN PRIVATE_Get_Crew_Type_Stat_Name_Label_At_Index(CMT_HACKER, ENUM_TO_INT(stat))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// stat - The driver stat enum we want to retrieve a name label for.
//PURPOSE: Returns a stat name label for a specific driver stat.
FUNC STRING GET_DRIVER_STAT_NAME_LABEL(CrewDriverStat stat)
RETURN PRIVATE_Get_Crew_Type_Stat_Name_Label_At_Index(CMT_DRIVER, ENUM_TO_INT(stat))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heist - The ID of the heist in progress as the stats are being increased.
// crewMem - The gunman crew member whose stats to increment.
//PURPOSE: Permanently adds a certain value to a gunman's crew stats.
PROC INCREMENT_GUNMAN_STATS_DURING_HEIST(INT heist, CrewMember crewMem, BOOL feedMessage = TRUE)
SCRIPT_ASSERT("INCREMENT_GUNMAN_STATS_DURING_HEIST is depricated. Please use INCREMENT_ALL_CREW_MEMBER_STATS_DURING_HEIST instead.")
UNUSED_PARAMETER(heist)
UNUSED_PARAMETER(crewMem)
UNUSED_PARAMETER(feedMessage)
// IF NOT IS_REPEAT_PLAY_ACTIVE()
// #IF IS_DEBUG_BUILD
// TEXT_LABEL_63 txtCrewName = GET_STRING_FROM_TEXT_FILE(PRIVATE_Get_Crew_Member_First_Name_Label(crewMem))
// CPRINTLN(DEBUG_HEIST, "<CREWSTAT> ", GET_THIS_SCRIPT_NAME(), " is incrementing ", txtCrewName, "'s stats.")
// #ENDIF
//
// IF g_sCrewMemberStaticData[crewMem].type != CMT_GUNMAN
// SCRIPT_ASSERT("INCREMENT_GUNMAN_STATS_DURING_HEIST: Crew member was not a gunman. Could not increment stat value.")
// EXIT
// ENDIF
//
// //Find the crew member's index in the heist's selected crew.
// FLOW_INT_IDS eFlowChoice = Get_Heist_Choice_FlowInt_For_Heist(heist)
// INT iHeistChoice
// INT iCrewIndex = -1
// IF eFlowChoice = MAX_FLOW_INT_IDS OR eFlowChoice = FLOWINT_NONE
// SCRIPT_ASSERT("INCREMENT_GUNMAN_STATS_DURING_HEIST: Failed to find a valid heist choice selection for passed heist.")
// EXIT
// ELSE
// iHeistChoice = g_savedGlobals.sFlow.controls.intIDs[eFlowChoice]
// INT iTempIndex
// REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize iTempIndex
// IF g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iTempIndex] = crewMem
// CDEBUG1LN(DEBUG_HEIST, "<CREWSTAT> Found crew member stored in index ", iTempIndex, ".")
// iCrewIndex = iTempIndex
// ENDIF
// ENDREPEAT
// IF iCrewIndex = -1
// SCRIPT_ASSERT("INCREMENT_GUNMAN_STATS_DURING_HEIST: Crew member was not part of the crew for the specified heist.")
// EXIT
// ENDIF
// ENDIF
//
// //Only increment stats for each crew member once per heist playthrough.
// IF NOT g_sHeistTempStats[iCrewIndex].statsIncreased
// //Increment each gunman stat one at a time.
// INT iStatIndex
// REPEAT 4 iStatIndex
// PRIVATE_Increment_Single_Gunman_Stat_During_Heist(iCrewIndex, INT_TO_ENUM(CrewGunmanStat, iStatIndex))
// ENDREPEAT
// g_sHeistTempStats[iCrewIndex].statsIncreased = TRUE
//
// //Display a feed message if requested.
// IF feedMessage
// PRIVATE_Display_Feed_For_Gunman_Stat_Increases(crewMem, iCrewIndex)
// ENDIF
//#IF IS_DEBUG_BUILD
// ELSE
// CPRINTLN(DEBUG_HEIST, "<CREWSTAT> Stats already increased this heist attempt. Blocking second increment.")
//#ENDIF
// ENDIF
// ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heist - The ID of the heist in progress as the stats are being increased.
// crewMem - The hacker crew member whose stats to increment.
//PURPOSE: Permanently adds a certain value to a hacker's crew stats.
PROC INCREMENT_HACKER_STATS_DURING_HEIST(INT heist, CrewMember crewMem, BOOL feedMessage = TRUE)
SCRIPT_ASSERT("INCREMENT_HACKER_STATS_DURING_HEIST is depricated. Please use INCREMENT_ALL_CREW_MEMBER_STATS_DURING_HEIST instead.")
UNUSED_PARAMETER(heist)
UNUSED_PARAMETER(crewMem)
UNUSED_PARAMETER(feedMessage)
// IF NOT IS_REPEAT_PLAY_ACTIVE()
// #IF IS_DEBUG_BUILD
// TEXT_LABEL_63 txtCrewName = GET_STRING_FROM_TEXT_FILE(PRIVATE_Get_Crew_Member_First_Name_Label(crewMem))
// CPRINTLN(DEBUG_HEIST, "<CREWSTAT> ", GET_THIS_SCRIPT_NAME(), " is incrementing ", txtCrewName, "'s stats.")
// #ENDIF
//
// IF g_sCrewMemberStaticData[crewMem].type != CMT_HACKER
// SCRIPT_ASSERT("INCREMENT_HACKER_STATS_DURING_HEIST: Crew member was not a hacker. Could not increment stat value.")
// EXIT
// ENDIF
//
// //Find the crew member's index in the heist's selected crew.
// FLOW_INT_IDS eFlowChoice = Get_Heist_Choice_FlowInt_For_Heist(heist)
// INT iHeistChoice
// INT iCrewIndex = -1
// IF eFlowChoice = MAX_FLOW_INT_IDS OR eFlowChoice = FLOWINT_NONE
// SCRIPT_ASSERT("INCREMENT_HACKER_STATS_DURING_HEIST: Failed to find a valid heist choice selection for passed heist.")
// EXIT
// ELSE
// iHeistChoice = g_savedGlobals.sFlow.controls.intIDs[eFlowChoice]
// INT iTempIndex
// REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize iTempIndex
// IF g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iTempIndex] = crewMem
// CDEBUG1LN(DEBUG_HEIST, "<CREWSTAT> Found crew member stored in index ", iTempIndex, ".")
// iCrewIndex = iTempIndex
// ENDIF
// ENDREPEAT
// IF iCrewIndex = -1
// SCRIPT_ASSERT("INCREMENT_HACKER_STATS_DURING_HEIST: Crew member was not part of the crew for the specified heist.")
// EXIT
// ENDIF
// ENDIF
//
// //Only increment stats for each crew member once per heist playthrough.
// IF NOT g_sHeistTempStats[iCrewIndex].statsIncreased
// //Increment each hacker stat one at a time.
// INT iStatIndex
// REPEAT 3 iStatIndex
// PRIVATE_Increment_Single_Hacker_Stat_During_Heist(iCrewIndex, INT_TO_ENUM(CrewHackerStat, iStatIndex))
// ENDREPEAT
// g_sHeistTempStats[iCrewIndex].statsIncreased = TRUE
//
// //Display a feed message if requested.
// IF feedMessage
// PRIVATE_Display_Feed_For_Hacker_Stat_Increases(crewMem, iCrewIndex)
// ENDIF
//#IF IS_DEBUG_BUILD
// ELSE
// CPRINTLN(DEBUG_HEIST, "<CREWSTAT> Stats already increased this heist attempt. Blocking second increment.")
//#ENDIF
// ENDIF
// ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heist - The ID of the heist in progress as the stats are being increased.
// crewMem - The driver crew member whose stats to increment.
//PURPOSE: Permanently adds a certain value to a driver's crew stats.
PROC INCREMENT_DRIVER_STATS_DURING_HEIST(INT heist, CrewMember crewMem, BOOL feedMessage = TRUE)
SCRIPT_ASSERT("INCREMENT_DRIVER_STATS_DURING_HEIST is depricated. Please use INCREMENT_ALL_CREW_MEMBER_STATS_DURING_HEIST instead.")
UNUSED_PARAMETER(heist)
UNUSED_PARAMETER(crewMem)
UNUSED_PARAMETER(feedMessage)
// IF NOT IS_REPEAT_PLAY_ACTIVE()
// #IF IS_DEBUG_BUILD
// TEXT_LABEL_63 txtCrewName = GET_STRING_FROM_TEXT_FILE(PRIVATE_Get_Crew_Member_First_Name_Label(crewMem))
// CPRINTLN(DEBUG_HEIST, "<CREWSTAT> ", GET_THIS_SCRIPT_NAME(), " is incrementing ", txtCrewName, "'s stats.")
// #ENDIF
//
// IF g_sCrewMemberStaticData[crewMem].type != CMT_DRIVER
// SCRIPT_ASSERT("INCREMENT_DRIVER_STATS_DURING_HEIST: Crew member was not a driver. Could not increment stat value.")
// EXIT
// ENDIF
//
// //Find the crew member's index in the heist's selected crew.
// FLOW_INT_IDS eFlowChoice = Get_Heist_Choice_FlowInt_For_Heist(heist)
// INT iHeistChoice
// INT iCrewIndex = -1
// IF eFlowChoice = MAX_FLOW_INT_IDS OR eFlowChoice = FLOWINT_NONE
// SCRIPT_ASSERT("INCREMENT_DRIVER_STATS_DURING_HEIST: Failed to find a valid heist choice selection for passed heist.")
// EXIT
// ELSE
// iHeistChoice = g_savedGlobals.sFlow.controls.intIDs[eFlowChoice]
// INT iTempIndex
// REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize iTempIndex
// IF g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iTempIndex] = crewMem
// CDEBUG1LN(DEBUG_HEIST, "<CREWSTAT> Found crew member stored in index ", iTempIndex, ".")
// iCrewIndex = iTempIndex
// ENDIF
// ENDREPEAT
// IF iCrewIndex = -1
// SCRIPT_ASSERT("INCREMENT_DRIVER_STATS_DURING_HEIST: Crew member was not part of the crew for the specified heist.")
// EXIT
// ENDIF
// ENDIF
//
// //Only increment stats for each crew member once per heist playthrough.
// IF NOT g_sHeistTempStats[iCrewIndex].statsIncreased
// //Increment each gunman stat one at a time.
// INT iStatIndex
// REPEAT 3 iStatIndex
// PRIVATE_Increment_Single_Driver_Stat_During_Heist(iCrewIndex, INT_TO_ENUM(CrewDriverStat, iStatIndex))
// ENDREPEAT
// g_sHeistTempStats[iCrewIndex].statsIncreased = TRUE
//
// //Display a feed message if requested.
// IF feedMessage
// PRIVATE_Display_Feed_For_Driver_Stat_Increases(crewMem, iCrewIndex)
// ENDIF
//#IF IS_DEBUG_BUILD
// ELSE
// CPRINTLN(DEBUG_HEIST, "<CREWSTAT> Stats already increased this heist attempt. Blocking second increment.")
//#ENDIF
// ENDIF
// ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heist - The ID of the heist in progress as the stats are being increased.
//PURPOSE: Permanently adds a 25% to all crew member stats for a particular heist.
PROC INCREMENT_ALL_CREW_MEMBER_STATS_DURING_HEIST(INT heist, BOOL feedMessage)
IF NOT IS_REPEAT_PLAY_ACTIVE()
INT iHeistChoice = GET_MISSION_FLOW_INT_VALUE(Get_Heist_Choice_FlowInt_For_Heist(heist))
INT iCrewIndex
INT iAliveCrewCount = 0
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize iCrewIndex
CrewMember crewMem = g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iCrewIndex]
IF NOT IS_BIT_SET(g_savedGlobals.sHeistData.iCrewDeadBitset, ENUM_TO_INT(crewMem))
iAliveCrewCount++
#IF IS_DEBUG_BUILD
TEXT_LABEL_63 txtCrewName = GET_STRING_FROM_TEXT_FILE(PRIVATE_Get_Crew_Member_First_Name_Label(crewMem))
CPRINTLN(DEBUG_HEIST, "<CREWSTAT> ", GET_THIS_SCRIPT_NAME(), " is incrementing ", txtCrewName, "'s stats.")
#ENDIF
//Only increment stats for each crew member once per heist playthrough.
IF NOT g_sHeistTempStats[iCrewIndex].statsIncreased
INT iStatIndex
SWITCH g_sCrewMemberStaticData[crewMem].type
CASE CMT_GUNMAN
REPEAT 4 iStatIndex
PRIVATE_Increment_Single_Gunman_Stat_During_Heist(iCrewIndex, INT_TO_ENUM(CrewGunmanStat, iStatIndex))
ENDREPEAT
BREAK
CASE CMT_DRIVER
REPEAT 3 iStatIndex
PRIVATE_Increment_Single_Driver_Stat_During_Heist(iCrewIndex, INT_TO_ENUM(CrewDriverStat, iStatIndex))
ENDREPEAT
BREAK
CASE CMT_HACKER
REPEAT 3 iStatIndex
PRIVATE_Increment_Single_Hacker_Stat_During_Heist(iCrewIndex, INT_TO_ENUM(CrewHackerStat, iStatIndex))
ENDREPEAT
BREAK
ENDSWITCH
g_sHeistTempStats[iCrewIndex].statsIncreased = TRUE
#IF IS_DEBUG_BUILD
ELSE
CPRINTLN(DEBUG_HEIST, "<CREWSTAT> Stats already increased this heist attempt. Blocking second increment.")
#ENDIF
ENDIF
ENDIF
ENDREPEAT
//Display a feed message if requested.
IF feedMessage
PRIVATE_Display_Feed_For_All_Crew_Member_Stat_Increases(iHeistChoice, iAliveCrewCount)
ENDIF
ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose max health value is to be retrieved.
//PURPOSE: Returns the max health of the queried crew member.
FUNC INT GET_CREW_MEMBER_MAX_HEALTH(CrewMember crewMem)
IF GET_CREW_MEMBER_TYPE(crewMem) = CMT_GUNMAN
RETURN GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_MAX_HEALTH)
ENDIF
//Drivers and hackers all share a default max health.
RETURN 100
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose accuracy value is to be retrieved.
//PURPOSE: Returns the weapon accuracy of the queried crew member.
FUNC INT GET_CREW_MEMBER_ACCURACY(CrewMember crewMem)
IF GET_CREW_MEMBER_TYPE(crewMem) = CMT_GUNMAN
RETURN GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_ACCURACY)
ENDIF
//Drivers and hackers all share a default accuracy.
RETURN 25
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member whose max shoot rate is to be retrieved.
//PURPOSE: Returns the shoot rate of the queried crew member.
FUNC INT GET_CREW_MEMBER_SHOOT_RATE(CrewMember crewMem)
IF GET_CREW_MEMBER_TYPE(crewMem) = CMT_GUNMAN
RETURN GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_SHOOT_RATE)
ENDIF
//Drivers and hackers all share a default shoot rate.
RETURN 40
ENDFUNC
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞══════════════════════════╡ Heist Crew Management ╞══════════════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the HEIST_CHOICE index that has been chosen for a given heist.
FUNC INT GET_HEIST_GAMEPLAY_CHOICE(INT heistIndex)
RETURN Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns whether or not the player has selected a crew for this heist yet.
FUNC BOOL HAS_HEIST_CREW_BEEN_SELECTED(INT heistIndex)
#IF IS_DEBUG_BUILD
TEXT_LABEL_63 tError
#ENDIF
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
IF iHeistChoice < 0
#IF IS_DEBUG_BUILD
tError = "HAS_HEIST_CREW_BEEN_SELECTED - iHeistChoice invalid:"
tError += iHeistChoice
tError += " < 0"
SCRIPT_ASSERT(tError)
#ENDIF
RETURN FALSE
ELIF iHeistChoice >= MAX_HEIST_CHOICES
#IF IS_DEBUG_BUILD
tError = "HAS_HEIST_CREW_BEEN_SELECTED - iHeistChoice invalid:"
tError += iHeistChoice
tError += " >= NO_HEISTS"
SCRIPT_ASSERT(tError)
#ENDIF
RETURN FALSE
ELSE
//Scan through all crew member slots. Check if any are still empty.
INT index
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize index
IF g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][index] = CM_EMPTY
//Empty slot found. The crew has not been selected.
RETURN FALSE
ENDIF
ENDREPEAT
//No empty slots found. The crew has been selected.
RETURN TRUE
ENDIF
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAMS NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Returns the number of crew members that are available on a specified heist.
FUNC INT GET_HEIST_CREW_SIZE(INT heistIndex)
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
RETURN g_sHeistChoiceData[iHeistChoice].iCrewSize
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
// slotIndex - An index that references the slot that the crew member is saved in.
//PURPOSE: Returns the crew member currently saved in a specified heist crew slot index.
FUNC CrewMember GET_HEIST_CREW_MEMBER_AT_INDEX(INT heistIndex,INT slotIndex)
#IF IS_DEBUG_BUILD
TEXT_LABEL_63 tError
#ENDIF // IS_DEBUG_BUILD
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
IF iHeistChoice < 0
#IF IS_DEBUG_BUILD
tError = "GET_HEIST_CREW_MEMBER_AT_INDEX - iHeistChoice invalid:"
tError += iHeistChoice
tError += " < 0"
SCRIPT_ASSERT(tError)
#ENDIF // IS_DEBUG_BUILD
RETURN CM_ERROR
ELIF iHeistChoice >= MAX_HEIST_CHOICES
#IF IS_DEBUG_BUILD
tError = "GET_HEIST_CREW_MEMBER_AT_INDEX - iHeistChoice invalid:"
tError += iHeistChoice
tError += " >= NO_HEISTS"
SCRIPT_ASSERT(tError)
#ENDIF // IS_DEBUG_BUILD
RETURN CM_ERROR
ELSE
RETURN g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][slotIndex]
ENDIF
ENDFUNC
//INFO: Author - Ross Wallaceson
//PARAM NOTES:
// thisPed - sets the components on this ped unless you supply a string for the SceneHandle which will set up a cutscene ped.
//PURPOSE: Sets a peds Heist outfit.
PROC SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(PED_INDEX pedCrew, STRING SceneHandle, PED_COMPONENT Component, INT Drawable, INT TextureID, INT NewPaletteNumber = 0)
IF (pedCrew <> NULL)
SET_PED_COMPONENT_VARIATION(pedCrew, Component, Drawable, TextureID, NewPaletteNumber)
ENDIF
SET_CUTSCENE_PED_COMPONENT_VARIATION(SceneHandle, Component, Drawable, TextureID)
ENDPROC
//INFO: Author - Ben Rollinson / Ross Wallaceson
//PARAM NOTES:
// pedCrew - A CrewMember enum that references the crew member that is to be created.
// outfit - An enum used to select the outfit the crew member will be wearing when created.
//PURPOSE: Sets a peds Heist outfit.
PROC SET_HEIST_CREW_MEMBER_OUTFIT_EXTRA_PARAMS(PED_INDEX pedCrew, STRING sceneHandle, CrewMember crewMem, HeistCrewOutfit outfit = CREW_OUTFIT_DEFAULT, BOOL withHeadset = TRUE)
CrewMemberType thisCrewMemberType = GET_CREW_MEMBER_TYPE(crewMem)
#IF IS_DEBUG_BUILD
IF pedCrew <> NULL
CPRINTLN(DEBUG_HEIST, "Setting outfit for ",
GET_HEIST_CREW_TYPE_DEBUG_STRING(thisCrewMemberType), " ",
GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem)), ". Model:",
GET_MODEL_NAME_FOR_DEBUG(GET_ENTITY_MODEL(pedCrew)), " Outfit:",
GET_HEIST_CREW_OUTFIT_DEBUG_STRING(outfit), ".")
ELSE
CPRINTLN(DEBUG_HEIST, "Setting cutscene outfit for ",
GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem)), ". Handle:",
sceneHandle, " Outfit:",
GET_HEIST_CREW_OUTFIT_DEBUG_STRING(outfit), ".")
ENDIF
#ENDIF
//Configure based on crew member
SWITCH thisCrewMemberType
CASE CMT_GUNMAN
SWITCH outfit
CASE CREW_OUTFIT_DEFAULT
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 6, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 6, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
IF pedCrew <> NULL
CLEAR_PED_PROP(pedCrew, ANCHOR_HEAD)
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ENDIF
BREAK
CASE CREW_OUTFIT_PEST_CONTROL
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_SCUBA
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 3, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 3, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 3, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 3, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_SCUBA_LAND
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 3, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 8, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 3, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_MIME
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 1)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 4, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 4, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_CLOWN
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 2)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 5, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 5, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 5, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_HEAVY_ARMOR
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 1, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 1, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 2, 1)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 1, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
// SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
//SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,0), 5, 0, 0) //(head)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,1), 1, 0, 0) //(berd)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,2), 1, 0, 0) //(hair)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,3), 1, 0, 0) //(uppr)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,4), 1, 0, 0) //(lowr)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,6), 4, 0, 0) //(feet)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,8), 0, 0, 0) //(accs)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,9), 1, 0, 0) //(task)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, INT_TO_ENUM(PED_COMPONENT,10), 1, 0, 0) //(decl)
//SET_PED_PROP_INDEX(PedIndex, INT_TO_ENUM(PED_PROP_POSITION,2), 1, 0)
//SET_PED_PROP_INDEX(PedIndex, INT_TO_ENUM(PED_PROP_POSITION,0), 5, 0)
IF pedCrew <> NULL
SET_PED_PROP_INDEX(pedCrew, INT_TO_ENUM(PED_PROP_POSITION,0), 5, 0) //Helmet prop.
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ELSE
SET_CUTSCENE_PED_PROP_VARIATION(sceneHandle, INT_TO_ENUM(PED_PROP_POSITION,0), 5, 0)
ENDIF
BREAK
CASE CREW_OUTFIT_FIRE_FIGHTING
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 4, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
IF pedCrew <> NULL
SET_PED_PROP_INDEX(pedCrew, ANCHOR_HEAD, 1, 0) //Helmet prop.
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ELSE
SET_CUTSCENE_PED_PROP_VARIATION(sceneHandle, ANCHOR_HEAD, 1, 0)
ENDIF
BREAK
CASE CREW_OUTFIT_STEALTH
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 0, 0) // old value (1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 8, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 8, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 7, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_SECURITY
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 7, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 7, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 6, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd) //Turn off harness
BREAK
CASE CREW_OUTFIT_SUIT
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0, 0) //(hair)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 5, 0, 0) //(uppr)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 5, 0, 0) //(lowr)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 1, 0, 0) //(feet)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0, 0) //(accs)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL2, 0, 0, 0) //(task)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0, 0) //(decl)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_BERD, 1, 0, 0) //(berd)
BREAK
ENDSWITCH
//Glasses prop for Chef.
IF crewMem = CM_GUNMAN_G_CHEF_UNLOCK
SWITCH outfit
CASE CREW_OUTFIT_DEFAULT
CASE CREW_OUTFIT_FIRE_FIGHTING
CASE CREW_OUTFIT_STEALTH
CASE CREW_OUTFIT_SECURITY
IF pedCrew <> NULL
SET_PED_PROP_INDEX(pedCrew, ANCHOR_EARS, 1, 0) //Glasses prop.
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ELSE
SET_CUTSCENE_PED_PROP_VARIATION(sceneHandle, ANCHOR_EARS, 1, 0)
ENDIF
BREAK
ENDSWITCH
ENDIF
BREAK
CASE CMT_HACKER
SWITCH outfit
CASE CREW_OUTFIT_DEFAULT
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation, 0) //Using outfit var on purpose. Stops Rickie having a balaclava on.
IF crewMem = CM_HACKER_G_PAIGE
OR crewMem = CM_HACKER_M_CHRIS
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAND, 0, 0)
ELSE
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAND, 2, 0)
ENDIF
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0)
IF pedCrew <> NULL
CLEAR_PED_PROP(pedCrew, ANCHOR_HEAD)
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ENDIF
BREAK
CASE CREW_OUTFIT_STEALTH
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAND, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 1, 0)
BREAK
DEFAULT
SCRIPT_ASSERT("SET_HEIST_CREW_MEMBER_OUTFIT: Tried to configure a hacker with an invalid outfit. Hackers can only use CREW_OUTFIT_DEFAULT or CREW_OUTFIT_STEALTH.")
EXIT
BREAK
ENDSWITCH
BREAK
CASE CMT_DRIVER
SWITCH outfit
CASE CREW_OUTFIT_DEFAULT
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 3, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation)
IF crewMem = CM_DRIVER_G_TALINA_UNLOCK
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 2, 0)
ELSE
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 2, g_sCrewMemberStaticData[crewMem].defaultOutfitVariation)
ENDIF
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
IF pedCrew <> NULL
CLEAR_PED_PROP(pedCrew, ANCHOR_HEAD)
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ENDIF
BREAK
CASE CREW_OUTFIT_SECURITY
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 5, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 4, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
BREAK
CASE CREW_OUTFIT_SUIT
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
//SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 4, 2)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 3, 2)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
BREAK
CASE CREW_OUTFIT_PEST_CONTROL
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
//SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 0, 0)
BREAK
CASE CREW_OUTFIT_STEALTH
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HEAD, g_sCrewMemberStaticData[crewMem].headVariation, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_HAIR, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_TORSO, 2, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_LEG, 3, 2)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_FEET, 0, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_SPECIAL, 1, 0)
SET_PED_OR_CUTSCENE_HANDLE_COMPONENT_VARIATION(pedCrew, sceneHandle, PED_COMP_DECL, 1, 0)
BREAK
DEFAULT
SCRIPT_ASSERT("SET_HEIST_CREW_MEMBER_OUTFIT: Tried to configure a driver with an invalid outfit. Drivers can only use CREW_OUTFIT_DEFAULT, CREW_OUTFIT_SECURITY, CREW_OUTFIT_PEST_CONTROL or CREW_OUTFIT_SUIT.")
EXIT
BREAK
ENDSWITCH
BREAK
ENDSWITCH
//Setup props.
IF pedCrew <> NULL //Until we work out what to do with props in cutscenes
//Add a bluetooth headset prop if requested.
IF withHeadSet
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, "Giving ", GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem)), " a headset.")
#ENDIF
SET_PED_PROP_INDEX(pedCrew, ANCHOR_EARS, 0, 0)
ELSE
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, "Not giving ", GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem)), " a headset.")
#ENDIF
CLEAR_PED_PROP(pedCrew, ANCHOR_EARS)
ENDIF
SET_CUTSCENE_PED_COMPONENT_VARIATION_FROM_PED(sceneHandle, pedCrew)
ENDIF
ENDPROC
PROC SET_HEIST_CREW_MEMBER_OUTFIT_FOR_CUTSCENE(STRING sceneHandle, CrewMember crewMem, HeistCrewOutfit outfit = CREW_OUTFIT_DEFAULT, BOOL withHeadset = TRUE)
SET_HEIST_CREW_MEMBER_OUTFIT_EXTRA_PARAMS(NULL, sceneHandle, crewMem, outfit, withHeadset)
ENDPROC
PROC SET_HEIST_CREW_MEMBER_OUTFIT(PED_INDEX pedCrew, CrewMember crewMem, HeistCrewOutfit outfit = CREW_OUTFIT_DEFAULT, BOOL withHeadset = TRUE)
SET_HEIST_CREW_MEMBER_OUTFIT_EXTRA_PARAMS(pedCrew, "", crewMem, outfit, withHeadset)
ENDPROC
//INFO: Author - Ben Rollinson. Modifed by Ross Wallace
//PARAM NOTES:
// crewMem - A CrewMember enum that references the crew member that is to be created.
// position - The VECTOR position at which the crew member will be created.
// heading - A FLOAT value that determines the heading the crew member will be facing when created.
// outfit - An enum used to select the outfit the crew member will be wearing when created.
// withHeadset - Should the crew member be created wearing a bluetooth headset. Defaults to TRUE.
//PURPOSE: Creates and configures a ped based on a specified CrewMember enum.
FUNC PED_INDEX CREATE_HEIST_CREW_MEMBER(CrewMember crewMem, VECTOR position, FLOAT heading, HeistCrewOutfit outfit = CREW_OUTFIT_DEFAULT, BOOL withHeadset = TRUE)
PED_INDEX pedCrew
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, "Creating crew member ", GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem)),".")
#ENDIF
//Create crew member with correct model.
pedCrew = CREATE_PED(PEDTYPE_MISSION, g_sCrewMemberStaticData[crewMem].model, position,heading)
//Configure based on crew member
SET_HEIST_CREW_MEMBER_OUTFIT(pedCrew, crewMem, outfit, withHeadset)
SET_ENTITY_AS_MISSION_ENTITY(pedCrew)
SET_PED_SUFFERS_CRITICAL_HITS(pedCrew, FALSE)
//If this is a gunman set up their combat attributes.
IF GET_CREW_MEMBER_TYPE(crewMem) = CMT_GUNMAN
SET_PED_MAX_HEALTH(pedCrew, GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_MAX_HEALTH))
SET_PED_ACCURACY(pedCrew, GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_ACCURACY))
SET_PED_SHOOT_RATE(pedCrew, GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_SHOOT_RATE))
ELSE
SET_PED_MAX_HEALTH(pedCrew, 100)
SET_PED_ACCURACY(pedCrew, 25)
SET_PED_SHOOT_RATE(pedCrew, 40)
ENDIF
RETURN pedCrew
ENDFUNC
//INFO: Author - Ben Rollinson.
//PARAM NOTES:
// crewMem - A CrewMember enum that references the crew member that is to be created.
// vehicle - The vehicle to create the crew member in.
// seat - The vehicle seat to place the crew memeber in.
// outfit - An enum used to select the outfit the crew member will be wearing when created.
// withHeadset - Should the crew member be created wearing a bluetooth headset. Defaults to TRUE.
//PURPOSE: Creates and configures a ped based on a specified CrewMember enum and places them in a vehicle.
FUNC PED_INDEX CREATE_HEIST_CREW_MEMEBER_IN_VEHICLE(CrewMember crewMem, VEHICLE_INDEX vehicle, VEHICLE_SEAT seat = VS_DRIVER, HeistCrewOutfit outfit = CREW_OUTFIT_DEFAULT, BOOL withHeadset = TRUE)
PED_INDEX pedCrew
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, "Creating crew member ", GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem))," in a vehicle.")
#ENDIF
//Create crew member with correct model.
pedCrew = CREATE_PED_INSIDE_VEHICLE(vehicle, PEDTYPE_MISSION, g_sCrewMemberStaticData[crewMem].model, seat)
//Configure based on crew member
SET_HEIST_CREW_MEMBER_OUTFIT(pedCrew, crewMem, outfit, withHeadset)
SET_ENTITY_AS_MISSION_ENTITY(pedCrew)
//If this is a gunman set up their combat attributes.
IF GET_CREW_MEMBER_TYPE(crewMem) = CMT_GUNMAN
SET_PED_MAX_HEALTH(pedCrew, GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_MAX_HEALTH))
SET_PED_ACCURACY(pedCrew, GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_ACCURACY))
SET_PED_SHOOT_RATE(pedCrew, GET_CREW_MEMBER_GUNMAN_STAT(crewMem, CGS_SHOOT_RATE))
ELSE
SET_PED_MAX_HEALTH(pedCrew, 100)
SET_PED_ACCURACY(pedCrew, 25)
SET_PED_SHOOT_RATE(pedCrew, 40)
ENDIF
RETURN pedCrew
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
// slotIndex - An index that references the slot that the crew member is saved in.
// position - The VECTOR position at which the crew member will be created.
// heading - A FLOAT value that determines the heading the crew member will be facing when created.
// outfit - An enum used to select the outfit the crew member will be wearing when created.
// withHeadset - Should the crew member be created wearing a bluetooth headset. Defaults to TRUE.
//PURPOSE: Creates and configures a ped based on the information found in a specified heist crew slot.
FUNC PED_INDEX CREATE_HEIST_CREW_MEMBER_AT_INDEX(INT heistIndex, INT slotIndex, VECTOR position, FLOAT heading, HeistCrewOutfit outfit = CREW_OUTFIT_DEFAULT, BOOL withHeadset = TRUE)
#IF IS_DEBUG_BUILD
TEXT_LABEL_63 tError
#ENDIF // IS_DEBUG_BUILD
IF heistIndex < 0
#IF IS_DEBUG_BUILD
tError = "CREATE_HEIST_CREW_MEMBER_AT_INDEX - heistIndex invalid:"
tError += heistIndex
tError += " < 0"
SCRIPT_ASSERT(tError)
#ENDIF // IS_DEBUG_BUILD
RETURN NULL
ELIF heistIndex >= NO_HEISTS
#IF IS_DEBUG_BUILD
tError = "CREATE_HEIST_CREW_MEMBER_AT_INDEX - heistIndex invalid:"
tError += heistIndex
tError += " >= NO_HEISTS"
SCRIPT_ASSERT(tError)
#ENDIF // IS_DEBUG_BUILD
RETURN NULL
ELSE
CrewMember selectedCrew = GET_HEIST_CREW_MEMBER_AT_INDEX(heistIndex, slotIndex)
IF selectedCrew = CM_EMPTY
OR selectedCrew = CM_ERROR
OR selectedCrew = CM_MAX_CREW_MEMBERS
RETURN NULL
ELSE
RETURN CREATE_HEIST_CREW_MEMBER(selectedCrew, position, heading, outfit, withHeadset)
ENDIF
ENDIF
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Requests the models are loaded for all crew members saved in the crew slots of a specified heist.
PROC REQUEST_MODELS_FOR_HEIST_CREW(INT heistIndex)
CrewMember tempCrew
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
INT index
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize index
tempCrew = GET_HEIST_CREW_MEMBER_AT_INDEX(heistIndex, index)
IF tempCrew <> CM_EMPTY OR tempCrew <> CM_ERROR
REQUEST_MODEL(g_sCrewMemberStaticData[tempCrew].model)
ENDIF
ENDREPEAT
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Checks whether or not all crew models are loaded for the crew members saved in the crew slots of a specified heist.
FUNC BOOL HAVE_MODELS_LOADED_FOR_HEIST_CREW(INT heistIndex)
CrewMember tempCrew
BOOL bLoaded = TRUE
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
INT index
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize index
tempCrew = GET_HEIST_CREW_MEMBER_AT_INDEX(heistIndex, index)
IF tempCrew <> CM_EMPTY OR tempCrew <> CM_ERROR
IF NOT HAS_MODEL_LOADED(g_sCrewMemberStaticData[tempCrew].model)
bLoaded = FALSE
ENDIF
ENDIF
ENDREPEAT
RETURN bLoaded
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a heist gameplay variation. This should be a constant starting HEIST_CHOICE_*
//PURPOSE: Sets models as no longer needed for all the crew members saved in the crew slots of a specified heist.
PROC SET_MODELS_FOR_HEIST_CREW_AS_NO_LONGER_NEEDED(INT heistIndex)
CrewMember tempCrew
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
INT index
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize index
tempCrew = GET_HEIST_CREW_MEMBER_AT_INDEX(heistIndex, index)
IF tempCrew <> CM_EMPTY OR tempCrew <> CM_ERROR
SET_MODEL_AS_NO_LONGER_NEEDED(g_sCrewMemberStaticData[tempCrew].model)
ENDIF
ENDREPEAT
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that references the crew member whose model is to be streamed in.
//PURPOSE: Requests that a crew member's model is loaded.
PROC REQUEST_MODEL_FOR_CREW_MEMBER(CrewMember crewMem)
REQUEST_MODEL(g_sCrewMemberStaticData[crewMem].model)
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that references the crew member who will have their model load state checked.
//PURPOSE: Checks whether or not a crew member's model is loaded.
FUNC BOOL HAS_MODEL_LOADED_FOR_CREW_MEMBER(CrewMember crewMem)
RETURN HAS_MODEL_LOADED(g_sCrewMemberStaticData[crewMem].model)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that references the crew member whose model will be flagged as no longer needed.
//PURPOSE: Sets a crew member's model as no longer needed.
PROC SET_MODEL_FOR_CREW_MEMBER_AS_NO_LONGER_NEEDED(CrewMember crewMem)
SET_MODEL_AS_NO_LONGER_NEEDED(g_sCrewMemberStaticData[crewMem].model)
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that references the crew member whose hire count we want to query.
//PURPOSE: Returns the number of times a specific crew member has been used by the player on completed heists.
FUNC INT GET_NUMBER_OF_TIMES_CREW_MEMBER_HIRED(CrewMember crewMem)
IF crewMem = CM_EMPTY
OR crewMem = CM_MAX_CREW_MEMBERS
OR crewMem = CM_ERROR
SCRIPT_ASSERT("GET_NUMBER_OF_TIMES_CREW_MEMBER_HIRED: Command called with an invalid crew member ENUM. Returning 0.")
RETURN 0
ENDIF
INT iHireCount = 0
#IF NOT USE_SP_DLC
INT iChoiceIndex
INT iCrewIndex
REPEAT MAX_HEIST_CHOICES iChoiceIndex
REPEAT g_sHeistChoiceData[iChoiceIndex].iCrewSize iCrewIndex
BOOL bCompleted = FALSE
SWITCH iChoiceIndex
CASE HEIST_CHOICE_JEWEL_STEALTH
CASE HEIST_CHOICE_JEWEL_HIGH_IMPACT
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_JEWELRY_2)
BREAK
CASE HEIST_CHOICE_DOCKS_BLOW_UP_BOAT
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_DOCKS_2A)
BREAK
CASE HEIST_CHOICE_DOCKS_DEEP_SEA
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_DOCKS_2B)
BREAK
CASE HEIST_CHOICE_RURAL_NO_TANK
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_RURAL_2)
BREAK
CASE HEIST_CHOICE_AGENCY_FIRETRUCK
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_AGENCY_3A)
BREAK
CASE HEIST_CHOICE_AGENCY_HELICOPTER
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_AGENCY_3B)
BREAK
CASE HEIST_CHOICE_FINALE_TRAFFCONT
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_FINALE_2A)
BREAK
CASE HEIST_CHOICE_FINALE_HELI
bCompleted = GET_MISSION_COMPLETE_STATE(SP_HEIST_FINALE_2B)
BREAK
ENDSWITCH
IF bCompleted
AND g_savedGlobals.sHeistData.eSelectedCrew[iChoiceIndex][iCrewIndex] = crewMem
iHireCount++
ENDIF
ENDREPEAT
ENDREPEAT
#ENDIF
RETURN iHireCount
ENDFUNC
/// INFO: Author - Michael Wadelin
/// PURPOSE:
/// Appends the a crew members initials to the end of the conversation root label.
/// PARAMS:
/// eCrewMember - The crew member who will be speaking
/// rootLabel - the conversation root to append to
/// RETURNS:
/// Returns a new root label which corresponds to that particular crew members line of dialogue in D*
FUNC TEXT_LABEL_15 APPEND_CREW_ID_TO_CONV_ROOT(CrewMember eCrewMember, STRING rootLabel, BOOL bAppendSkillID = FALSE)
TEXT_LABEL_15 result = rootLabel
SWITCH eCrewMember
// GUNMEN
CASE CM_GUNMAN_B_DARYL
result += "_DJ"
BREAK
CASE CM_GUNMAN_B_NORM
result += "_NR"
BREAK
CASE CM_GUNMAN_M_HUGH
result += "_HW"
BREAK
CASE CM_GUNMAN_G_GUSTAV
result += "_GM"
BREAK
CASE CM_GUNMAN_G_KARL
result += "_KA"
BREAK
CASE CM_GUNMAN_G_CHEF_UNLOCK
result += "_C"
BREAK
CASE CM_GUNMAN_G_PACKIE_UNLOCK
result += "_PM"
BREAK
// DRIVERS
CASE CM_DRIVER_B_KARIM
result += "_KD"
BREAK
CASE CM_DRIVER_G_EDDIE
result += "_ET"
BREAK
CASE CM_DRIVER_G_TALINA_UNLOCK
result += "_TM"
BREAK
// HACKERS
CASE CM_HACKER_G_PAIGE
result += "_PH"
BREAK
CASE CM_HACKER_M_CHRIS
result += "_CF"
BREAK
CASE CM_HACKER_B_RICKIE_UNLOCK
result += "_RL"
BREAK
ENDSWITCH
// Append skill level to the end if required
IF bAppendSkillID
SWITCH GET_CREW_MEMBER_SKILL(eCrewMember)
CASE CMSK_BAD result += "B" BREAK
CASE CMSK_MEDIUM result += "M" BREAK
CASE CMSK_GOOD result += "G" BREAK
ENDSWITCH
ENDIF
CDEBUG1LN(DEBUG_MISSION, "APPEND_CREW_ID_TO_CONV_ROOT() conveted passed rootLabel from \"", rootLabel, "\" to \"", result, "\".")
RETURN result
ENDFUNC
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞═══════════════════════╡ Heist Crew Unlocking/Killing ╞══════════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member we want to check is unlocked.
//PURPOSE: Returns if the specified crew member has been unlocked in the current playthrough.
FUNC BOOL IS_HEIST_CREW_MEMBER_UNLOCKED(CrewMember crewMem)
RETURN IS_BIT_SET(g_savedGlobals.sHeistData.iCrewUnlockedBitset, ENUM_TO_INT(crewMem))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - The CrewMember who is to be unlocked for selection.
//PURPOSE: Sets a heist crew member to be available for selection on subsequent heist missions.
PROC SET_HEIST_CREW_MEMBER_UNLOCKED(CrewMember crewMem, BOOL noFeedMessage = FALSE)
SET_BIT(g_savedGlobals.sHeistData.iCrewUnlockedBitset, ENUM_TO_INT(crewMem))
#IF IS_DEBUG_BUILD
IF g_flowUnsaved.bUpdatingGameflow
noFeedMessage = TRUE
ENDIF
#ENDIF
//Flag the dialogue bit to so the player mentions they met them on the next board interaction.
SWITCH crewMem
CASE CM_GUNMAN_G_PACKIE_UNLOCK
SET_BIT(g_savedGlobals.sHeistData.iCrewDialogueBitset, ENUM_TO_INT(CRDS_MET_PACKIE))
BREAK
CASE CM_DRIVER_G_TALINA_UNLOCK
SET_BIT(g_savedGlobals.sHeistData.iCrewDialogueBitset, ENUM_TO_INT(CRDS_MET_TALINA))
BREAK
CASE CM_HACKER_B_RICKIE_UNLOCK
SET_BIT(g_savedGlobals.sHeistData.iCrewDialogueBitset, ENUM_TO_INT(CRDS_MET_RICKIE))
BREAK
CASE CM_GUNMAN_G_CHEF_UNLOCK
SET_BIT(g_savedGlobals.sHeistData.iCrewDialogueBitset, ENUM_TO_INT(CRDS_MET_CHEF))
BREAK
ENDSWITCH
IF NOT noFeedMessage
//Display on screen signifier.
FEED_TEXT_ICON eIcon = TEXT_ICON_BLANK
SWITCH GET_CREW_MEMBER_TYPE(crewMem)
CASE CMT_GUNMAN
eIcon = TEXT_ICON_SHOOTER
BREAK
CASE CMT_DRIVER
eIcon = TEXT_ICON_DRIVER
BREAK
CASE CMT_HACKER
eIcon = TEXT_ICON_HACKER
BREAK
ENDSWITCH
STRING strCrewName = GET_CREW_MEMBER_NAME_LABEL(crewMem)
//Display feed message.
BEGIN_TEXT_COMMAND_THEFEED_POST("FEED_CREW_U")
ADD_TEXT_COMPONENT_SUBSTRING_TEXT_LABEL (GET_CREW_MEMBER_NAME_LABEL(crewMem)) //Need to extract this from the stat enum somehow.
END_TEXT_COMMAND_THEFEED_POST_MESSAGETEXT(strCrewName, strCrewName, FALSE, eIcon, "")
//Display help text if it hasn't displayed before. Attempt to display
//for 20 seconds the give up and wait till next time.
#IF NOT USE_CLF_DLC
#IF NOT USE_NRM_DLC
IF NOT HAS_ONE_TIME_HELP_DISPLAYED(FHM_HEIST_CREW_UNLOCKED)
ADD_HELP_TO_FLOW_QUEUE("AM_H_CREWU", FHP_HIGH, 0, 20000, DEFAULT_HELP_TEXT_TIME, GET_CURRENT_PLAYER_PED_BIT(), CID_BLANK, CID_HEIST_CREW_UNLOCKED_HELP_SEEN)
ENDIF
#ENDIF
#ENDIF
ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - A CrewMember enum that points to the crew member we want to check is dead.
//PURPOSE: Returns if the specified crew member has been killed in the current playthrough.
FUNC BOOL IS_HEIST_CREW_MEMBER_DEAD(CrewMember crewMem)
RETURN IS_BIT_SET(g_savedGlobals.sHeistData.iCrewDeadBitset, ENUM_TO_INT(crewMem))
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// crewMem - The CrewMember who is to be set as dead for the rest of the playthrough.
//PURPOSE: Sets a heist crew member to be dead and unavailable for selection on subsequent heist missions.
PROC SET_HEIST_CREW_MEMBER_DEAD(CrewMember crewMem)
CPRINTLN(DEBUG_HEIST, "Heist crew memeber ", GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(crewMem)), " was flagged as dead.")
SET_BIT(g_savedGlobals.sHeistData.iCrewDeadBitset, ENUM_TO_INT(crewMem))
ENDPROC
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞═══════════════════════════╡ Debug Crew Control ╞════════════════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
#IF IS_DEBUG_BUILD
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
// index - An INT that references the crew member index.
// crewMem - A CrewMember enum that points to the crew member to be saved in the heist crew index.
//PURPOSE: Debug function to set which crew member is saved in a specific heist crew index.
PROC DEBUG_SET_HEIST_CREW_MEMBER_AT_INDEX(INT heistIndex, INT index, CrewMember crewMem)
IF crewMem <> CM_ERROR AND crewMem <> CM_MAX_CREW_MEMBERS
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
IF index < g_sHeistChoiceData[iHeistChoice].iCrewSize
IF g_sCrewMemberStaticData[crewMem].type = g_sHeistChoiceData[iHeistChoice].eCrewType[index]
g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][index] = crewMem
ELSE
TEXT_LABEL_63 tError = "ERROR - Tried to set crew member at index "
tError += index
tError += " to a member who is the incorrect type."
SCRIPT_ASSERT(tError)
ENDIF
ELSE
SCRIPT_ASSERT("ERROR - Tried to set a heist crew member at an index that was out of range.")
ENDIF
ELSE
SCRIPT_ASSERT("ERROR - Tried to set a heist crew member to an invalid enum (CM_ERROR or CM_MAX_CREW_MEMBERS).")
ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Debug function to randomly fill a heist's selected crew with crew members of the correct type.
PROC DEBUG_SET_RANDOM_CREW_FOR_HEIST(INT heistIndex)
//Get which heist variation was chosen.
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
CPRINTLN(DEBUG_HEIST, "")
CPRINTLN(DEBUG_HEIST, "----Generating debug crew for ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), "----")
INT index
INT index2
CrewMember eCrewRandom
CrewMember eCrewUsed[MAX_CREW_SIZE]
INT iCrewSize = g_sHeistChoiceData[iHeistChoice].iCrewSize
//Iterate through each heist crew slot.
IF iCrewSize <> 0
REPEAT iCrewSize index
//Search for a random crew member of the correct type to fill this slot.
BOOL bFoundMatch = FALSE
WHILE NOT bFoundMatch
eCrewRandom = INT_TO_ENUM(CrewMember,GET_RANDOM_INT_IN_RANGE(1,ENUM_TO_INT(CM_MAX_CREW_MEMBERS)))
bFoundMatch = TRUE
//Is this random crew member the correct type?
IF g_sCrewMemberStaticData[eCrewRandom].type != g_sHeistChoiceData[iHeistChoice].eCrewType[index]
bFoundMatch = FALSE
ENDIF
//Is this crew member unlocked?
IF NOT IS_BIT_SET(g_savedGlobals.sHeistData.iCrewUnlockedBitset, ENUM_TO_INT(eCrewRandom))
bFoundMatch = FALSE
ENDIF
//Is this crew member dead?
IF IS_BIT_SET(g_savedGlobals.sHeistData.iCrewDeadBitset, ENUM_TO_INT(eCrewRandom))
bFoundMatch = FALSE
ENDIF
//Special case. Block using Chef on the Agency Heist.
IF eCrewRandom = CM_GUNMAN_G_CHEF_UNLOCK AND heistIndex = HEIST_AGENCY
bFoundMatch = FALSE
ENDIF
//Is this random crew member already used?
REPEAT index index2
IF eCrewRandom = eCrewUsed[index2]
bFoundMatch = FALSE
ENDIF
ENDREPEAT
ENDWHILE
CPRINTLN(DEBUG_HEIST, GET_HEIST_CREW_TYPE_DEBUG_STRING(g_sHeistChoiceData[iHeistChoice].eCrewType[index]), " for index ",
index, ": ", GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(eCrewRandom)), ".")
//Save selected crew member into relevant slot.
g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][index] = eCrewRandom
//Flag the selected crew member as already used.
eCrewUsed[index] = eCrewRandom
ENDREPEAT
ELSE
CPRINTLN(DEBUG_HEIST, "No crew required for this heist choice.")
ENDIF
CPRINTLN(DEBUG_HEIST, "------------------Finished-------------------")
CPRINTLN(DEBUG_HEIST, "")
PRIVATE_Update_Crew_Used_Flags_For_Heist(heistIndex)
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Debug function to bring up a heist selection screen that will allow a developer to pick a crew for a
// specific heist. NB. This procedure will hang the script that calls it until a crew selection has been
// made.
PROC DEBUG_DO_CREW_SELECTION_FOR_HEIST(INT heistIndex)
CPRINTLN(DEBUG_HEIST, "Running debug crew selector.")
IF IS_SCREEN_FADED_OUT()
DO_SCREEN_FADE_IN(0)
WAIT(0)
ENDIF
DebugCrewSelector selector
selector.iLinkedHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
IF IS_PLAYER_PLAYING(PLAYER_ID())
SET_PLAYER_CONTROL(PLAYER_ID(), FALSE)
ENDIF
CLEAR_HELP()
PRINT_HELP_FOREVER("CRW_SEL_H")
WHILE NOT selector.bFinalised
WAIT(0)
PRIVATE_Draw_Crew_Selector_Background(selector)
PRIVATE_Draw_Crew_Selector_Foreground(heistIndex, selector)
PRIVATE_Manage_Crew_Selector_Input(selector)
ENDWHILE
DO_SCREEN_FADE_OUT(0)
CLEAR_HELP()
PRIVATE_Update_Crew_Used_Flags_For_Heist(heistIndex)
IF IS_PLAYER_PLAYING(PLAYER_ID())
SET_PLAYER_CONTROL(PLAYER_ID(), TRUE)
ENDIF
ENDPROC
#ENDIF
//╒═════════════════════════════════════════════════════════════════════════════╕
//╞════════════════════════╡ Heist End Screen Control ╞═════════════════════════╡
//╘═════════════════════════════════════════════════════════════════════════════╛
#IF IS_DEBUG_BUILD
PROC CREATE_HEIST_END_SCREEN_WIDGET(INT iHeistIndex, BOOL &bRefresh, WIDGET_GROUP_ID &widgetGroup)
INT index
INT iHeistChoice
TEXT_LABEL_63 tWidgetName = "End Screen - "
tWidgetName += GET_HEIST_INDEX_DEBUG_STRING(iHeistIndex)
widgetGroup = START_WIDGET_GROUP(tWidgetName)
ADD_WIDGET_BOOL("Refresh", bRefresh)
IF bRefresh
iHeistChoice = GET_MISSION_FLOW_INT_VALUE(Get_Heist_Choice_FlowInt_ID(iHeistIndex))
START_WIDGET_GROUP("Money Breakdown")
ADD_WIDGET_STRING("Main")
ADD_WIDGET_INT_READ_ONLY("Potential Take", g_savedGlobals.sHeistData.sEndScreenData[iHeistIndex].iPotentialTake)
ADD_WIDGET_INT_READ_ONLY("Actual Take", g_savedGlobals.sHeistData.sEndScreenData[iHeistIndex].iActualTake)
ADD_WIDGET_STRING("Crew")
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize index
TEXT_LABEL_23 tCrewTakeLabel = GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_FIRST_NAME_LABEL(g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][index]))
tCrewTakeLabel += "'s Take"
ADD_WIDGET_INT_READ_ONLY(tCrewTakeLabel, g_savedGlobals.sHeistData.sEndScreenData[iHeistIndex].iCrewMemberTake[index])
ENDREPEAT
STOP_WIDGET_GROUP()
START_WIDGET_GROUP("Crew Status")
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize index
STRING strCrewName = GET_STRING_FROM_TEXT_FILE(GET_CREW_MEMBER_NAME_LABEL(g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][index]))
ADD_WIDGET_STRING(strCrewName)
ADD_WIDGET_STRING(GET_HEIST_CREW_STATUS_DEBUG_STRING(g_savedGlobals.sHeistData.sEndScreenData[iHeistIndex].eCrewStatus[index]))
ENDREPEAT
STOP_WIDGET_GROUP()
ENDIF
STOP_WIDGET_GROUP()
ENDPROC
PROC UPDATE_HEIST_END_SCREEN_WIDGET(INT iHeistIndex, BOOL &bRefresh, WIDGET_GROUP_ID &widgetGroup)
IF bRefresh
DELETE_WIDGET_GROUP(widgetGroup)
CREATE_HEIST_END_SCREEN_WIDGET(iHeistIndex, bRefresh, widgetGroup)
bRefresh = FALSE
ENDIF
ENDPROC
#ENDIF
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
// potentialTake - An int representing the maximum value (in dollars) that can be stolen on a heist.
//PURPOSE:
PROC SET_HEIST_END_SCREEN_POTENTIAL_TAKE(INT heistIndex, INT potentialTake)
IF potentialTake < 0
SCRIPT_ASSERT("SET_HEIST_END_SCREEN_POTENTIAL_TAKE: Tried to set potential take to an invalid value (< 0).")
ENDIF
g_savedGlobals.sHeistData.sEndScreenData[heistIndex].iPotentialTake = potentialTake
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, GET_THIS_SCRIPT_NAME(), " set max potential take for ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), " to $", potentialTake, ".")
#ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
// actualTake - An int representing the maximum value (in dollars) that was stolen on a heist.
//PURPOSE:
PROC SET_HEIST_END_SCREEN_ACTUAL_TAKE(INT heistIndex, INT actualTake)
IF actualTake < 0
SCRIPT_ASSERT("SET_HEIST_END_SCREEN_ACTUAL_TAKE: Tried to set potential take to an invalid value (< 0). Trying to set actual to match potential as a fallback")
g_savedGlobals.sHeistData.sEndScreenData[heistIndex].iActualTake = g_savedGlobals.sHeistData.sEndScreenData[heistIndex].iPotentialTake
ELSE
g_savedGlobals.sHeistData.sEndScreenData[heistIndex].iActualTake = actualTake
ENDIF
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, GET_THIS_SCRIPT_NAME(), " set actual take for ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), " to $", actualTake, ".")
#ENDIF
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
// crewMem - A CrewMember ENUM pointing to the crew member who's status is to be set.
// status - A CrewMemberStatus ENUM that details the status of the crew member.
//PURPOSE: Sets a crew member's status in a heist end screen. This will automatically add expenses if the crew member is INJURED or KIA.
PROC SET_HEIST_END_SCREEN_CREW_STATUS(INT heistIndex, CrewMember crewMem, CrewMemberStatus status)
INT crewIndex = -1
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
//Search for this crew member in the heists crew slots.
INT index = 0
REPEAT MAX_CREW_SIZE index
IF crewMem = g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][index]
crewIndex = index
ENDIF
ENDREPEAT
//Check if the crew member was found.
IF crewIndex = -1
SCRIPT_ASSERT("SET_HEIST_END_SCREEN_CREW_STATUS - Tried to set the status of a crew member who is not part of the end screen's heist.")
EXIT
ENDIF
#IF IS_DEBUG_BUILD
TEXT_LABEL_15 tCrewNameLabel = GET_CREW_MEMBER_NAME_LABEL(crewMem)
CPRINTLN(DEBUG_HEIST, "Status of ", GET_STRING_FROM_TEXT_FILE(tCrewNameLabel), " stored as ", GET_HEIST_CREW_STATUS_DEBUG_STRING(status), " in index ", crewIndex, ".")
#ENDIF
//Flag the crew member as dead for the rest of this playthrough.
IF status = CMST_KILLED
SET_HEIST_CREW_MEMBER_DEAD(crewMem)
ENDIF
//Set status.
g_savedGlobals.sHeistData.sEndScreenData[heistIndex].eCrewStatus[crewIndex] = status
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist.
//PURPOSE: Resets the statuses set for all crew members on a heist's end screen.
PROC RESET_HEIST_END_SCREEN_CREW_MEMBER_STATUSES(INT heistIndex)
PRIVATE_Reset_Heist_End_Screen_Crew_Member_Statuses(heistIndex)
#IF IS_DEBUG_BUILD
CPRINTLN(DEBUG_HEIST, GET_THIS_SCRIPT_NAME(), " reset crew member statuses for ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), ".")
#ENDIF
ENDPROC
//
// Heist Planning Board Control
//
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist. See constant INT definitions beginning HEIST_ in heist_globals.sch.
// displayGroup - An enum referencing a preconfigured group of items on a planning board.
//PURPOSE: Sets a preconfigured group of planning board items to be visible on the specified heist's planning board.
PROC SET_HEIST_BOARD_DISPLAY_GROUP_VISIBLE(INT heistIndex, g_eBoardDisplayGroups displayGroup, BOOL setVisible)
IF setVisible
CPRINTLN(DEBUG_HEIST, "Script ", GET_THIS_SCRIPT_NAME(), " turned display group ", ENUM_TO_INT(displayGroup), " ON for ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), ".")
SET_BIT(g_savedGlobals.sHeistData.iDisplayGroupVisibleBitset[heistIndex], ENUM_TO_INT(displayGroup))
ELSE
CPRINTLN(DEBUG_HEIST, "Script ", GET_THIS_SCRIPT_NAME(), " turned display group ", ENUM_TO_INT(displayGroup), " OFF for ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), ".")
CLEAR_BIT(g_savedGlobals.sHeistData.iDisplayGroupVisibleBitset[heistIndex], ENUM_TO_INT(displayGroup))
ENDIF
SET_BIT(g_iBitsetHeistBoardUpdated, heistIndex)
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist. See constant INT definitions beginning HEIST_ in heist_globals.sch.
// bPinBoard - Should the board be pinned or unpinned in memory.
//PURPOSE: Flags whether or not a board should be forced to load, create, and remain created until unpinned.
PROC PIN_HEIST_BOARD_IN_MEMORY(INT heistIndex, BOOL bPinBoard)
IF bPinBoard
IF NOT IS_BIT_SET(g_iBitsetHeistBoardPinned, heistIndex)
CPRINTLN(DEBUG_HEIST, "Script ", GET_THIS_SCRIPT_NAME(), " pinned ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), "'s planning board in memory.")
SET_BIT(g_iBitsetHeistBoardPinned, heistIndex)
ENDIF
ELSE
IF IS_BIT_SET(g_iBitsetHeistBoardPinned, heistIndex)
CPRINTLN(DEBUG_HEIST, "Script ", GET_THIS_SCRIPT_NAME(), " unpinned ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), "'s planning board in memory.")
CLEAR_BIT(g_iBitsetHeistBoardPinned, heistIndex)
ENDIF
ENDIF
ENDPROC
PROC CREATE_PINNED_HEIST_BOARD(INT heistIndex)
CPRINTLN(DEBUG_HEIST, "Script ", GET_THIS_SCRIPT_NAME(), " allowing ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), "'s pinned planning board to create this frame.")
SET_BIT(g_iBitsetHeistBoardAllowCreation, heistIndex)
ENDPROC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist. See constant INT definitions beginning HEIST_ in heist_globals.sch.
//PURPOSE: Checks whether or not a specific heist's planning board exists in the world at any given moment.
FUNC BOOL HAS_HEIST_BOARD_LOADED(INT heistIndex)
RETURN IS_BIT_SET(g_iBitsetHeistBoardLoaded, heistIndex)
ENDFUNC
//INFO: Author - Ben Rollinson
//PARAM NOTES:
// heistIndex - An index referencing a specific heist. See constant INT definitions beginning HEIST_ in heist_globals.sch.
//PURPOSE: Runs santiy checks over the crew members that have been selected for a heist. Replaces any invalid seletions with
// random valid ones.
PROC VALIDATE_AND_REPAIR_CREW_MEMBERS_FOR_HEIST(INT heistIndex)
CPRINTLN(DEBUG_HEIST, "<CREW-VALID> Validating and repairing crew selections for heist ", GET_HEIST_INDEX_DEBUG_STRING(heistIndex), ".")
INT iHeistChoice = Get_Mission_Flow_Int_Value(Get_Heist_Choice_FlowInt_ID(heistIndex))
CDEBUG1LN(DEBUG_HEIST, "<CREW-VALID> Heist variation being validated is ", PRIVATE_Get_Heist_Choice_Debug_String(iHeistChoice), ".")
CDEBUG1LN(DEBUG_HEIST, "<CREW-VALID> Crew size for variation is ", g_sHeistChoiceData[iHeistChoice].iCrewSize, ".")
INT iCrewIndex
REPEAT g_sHeistChoiceData[iHeistChoice].iCrewSize iCrewIndex
IF g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iCrewIndex] = CM_EMPTY
CDEBUG1LN(DEBUG_HEIST, "<CREW-VALID> Crew member at index ", iCrewIndex, " is set to EMPTY. Repairing.")
PRIVATE_Set_Valid_Crew_Member_For_Heist_Choice_Slot(iHeistChoice, iCrewIndex)
ELIF g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iCrewIndex] = CM_ERROR
CDEBUG1LN(DEBUG_HEIST, "<CREW-VALID> Crew member at index ", iCrewIndex, " is set to ERROR. Repairing.")
PRIVATE_Set_Valid_Crew_Member_For_Heist_Choice_Slot(iHeistChoice, iCrewIndex)
ELIF GET_CREW_MEMBER_TYPE(g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iCrewIndex]) != g_sHeistChoiceData[iHeistChoice].eCrewType[iCrewIndex]
CDEBUG1LN(DEBUG_HEIST, "<CREW-VALID> Crew member at index ", iCrewIndex, " is type ", GET_HEIST_CREW_TYPE_DEBUG_STRING(GET_CREW_MEMBER_TYPE(g_savedGlobals.sHeistData.eSelectedCrew[iHeistChoice][iCrewIndex])), " but should be ", GET_HEIST_CREW_TYPE_DEBUG_STRING(g_sHeistChoiceData[iHeistChoice].eCrewType[iCrewIndex]), ". Repairing.")
PRIVATE_Set_Valid_Crew_Member_For_Heist_Choice_Slot(iHeistChoice, iCrewIndex)
#IF IS_DEBUG_BUILD
ELSE
CDEBUG1LN(DEBUG_HEIST, "<CREW-VALID> Crew member at index ", iCrewIndex, " is valid.")
#ENDIF
ENDIF
ENDREPEAT
ENDPROC