bool ATeleporterBeacon::Use (bool pickup) { AInventory *drop; // [BC] This is handled server-side. if (( NETWORK_GetState( ) == NETSTATE_CLIENT ) || ( CLIENTDEMO_IsPlaying( ))) { return ( true ); } // Increase the amount by one so that when DropInventory decrements it, // the actor will have the same number of beacons that he started with. // When we return to UseInventory, it will take care of decrementing // Amount again and disposing of this item if there are no more. Amount++; drop = Owner->DropInventory (this); if (drop == NULL) { Amount--; return false; } else { drop->SetState(drop->FindState(NAME_Drop)); drop->target = Owner; return true; } }
bool ATeleporterBeacon::Use (bool pickup) { AInventory *drop; // Increase the amount by one so that when DropInventory decrements it, // the actor will have the same number of beacons that he started with. // When we return to UseInventory, it will take care of decrementing // Amount again and disposing of this item if there are no more. Amount++; drop = Owner->DropInventory (this); if (drop == NULL) { Amount--; return false; } else { drop->SetState(drop->FindState(NAME_Drop)); drop->target = Owner; return true; } }
bool AInventory::TryPickup (AActor *&toucher) { AActor *newtoucher = toucher; // in case changed by the powerup // If HandlePickup() returns true, it will set the IF_PICKUPGOOD flag // to indicate that this item has been picked up. If the item cannot be // picked up, then it leaves the flag cleared. ItemFlags &= ~IF_PICKUPGOOD; if (toucher->Inventory != NULL && toucher->Inventory->HandlePickup (this)) { // Let something else the player is holding intercept the pickup. if (!(ItemFlags & IF_PICKUPGOOD)) { return false; } ItemFlags &= ~IF_PICKUPGOOD; GoAwayAndDie (); } else if (MaxAmount == 0 && !IsKindOf(RUNTIME_CLASS(AAmmo))) { // Special case: If an item's MaxAmount is 0, you can still pick it // up if it is autoactivate-able. if (!(ItemFlags & IF_AUTOACTIVATE)) { return false; } // The item is placed in the inventory just long enough to be used. toucher->AddInventory (this); bool usegood = Use (true); toucher->RemoveInventory (this); if (usegood) { GoAwayAndDie (); } else { return false; } } else { // Add the item to the inventory. It is not already there, or HandlePickup // would have already taken care of it. AInventory *copy = CreateCopy (toucher); if (copy == NULL) { return false; } // Some powerups cannot activate absolutely, for // example, PowerMorph; fail the pickup if so. if (copy->ItemFlags & IF_INITEFFECTFAILED) { if (copy != this) copy->Destroy(); else ItemFlags &= ~IF_INITEFFECTFAILED; return false; } // Handle owner-changing powerups if (copy->ItemFlags & IF_CREATECOPYMOVED) { newtoucher = copy->Owner; copy->Owner = NULL; copy->ItemFlags &= ~IF_CREATECOPYMOVED; } // Continue onwards with the rest copy->AttachToOwner (newtoucher); if (ItemFlags & IF_AUTOACTIVATE) { if (copy->Use (true)) { if (--copy->Amount <= 0) { copy->flags &= ~MF_SPECIAL; copy->SetState (copy->FindState("HoldAndDestroy")); } } } } return true; }
//***************************************************************************** // void medal_SelectIcon( ULONG ulPlayer ) { AInventory *pInventory; player_t *pPlayer; ULONG ulActualSprite = NUM_SPRITES; // [BB] If ulPlayer carries a TeamItem, e.g. flag or skull, we store a pointer // to it in pTeamItem and set the floaty icon to the carry (or spawn) state of // the TeamItem. We also need to copy the Translation of the TeamItem to the // FloatyIcon. AInventory *pTeamItem = NULL; if ( ulPlayer >= MAXPLAYERS ) return; pPlayer = &players[ulPlayer]; if ( pPlayer->mo == NULL ) return; // Allow the user to disable icons. if (( cl_icons == false ) || ( NETWORK_GetState( ) == NETSTATE_SERVER ) || pPlayer->bSpectating ) { if ( pPlayer->pIcon ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } return; } // Verify that our current icon is valid. (i.e. We may have had a chat bubble, then // stopped talking, so we need to delete it). if ( pPlayer->pIcon && pPlayer->pIcon->bTeamItemFloatyIcon == false ) { switch ( (ULONG)( pPlayer->pIcon->state - pPlayer->pIcon->SpawnState )) { // Chat icon. Delete it if the player is no longer talking. case S_CHAT: if ( pPlayer->bChatting == false ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_CHAT; break; // In console icon. Delete it if the player is no longer in the console. case S_INCONSOLE: case ( S_INCONSOLE + 1): if ( pPlayer->bInConsole == false ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_INCONSOLE; break; // Ally icon. Delete it if the player is now our enemy or if we're spectating. // [BB] Dead spectators shall keep the icon for their teammates. case S_ALLY: if ( PLAYER_IsTrueSpectator ( &players[ SCOREBOARD_GetViewPlayer() ] ) || ( !pPlayer->mo->IsTeammate( players[ SCOREBOARD_GetViewPlayer() ].mo ) ) ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_ALLY; break; // Flag/skull icon. Delete it if the player no longer has it. case S_WHITEFLAG: case ( S_WHITEFLAG + 1 ): case ( S_WHITEFLAG + 2 ): case ( S_WHITEFLAG + 3 ): case ( S_WHITEFLAG + 4 ): case ( S_WHITEFLAG + 5 ): { bool bDelete = false; // Delete the icon if teamgame has been turned off, or if the player // is not on a team. if (( teamgame == false ) || ( pPlayer->bOnTeam == false )) { bDelete = true; } // Delete the white flag if the player no longer has it. pInventory = pPlayer->mo->FindInventory( PClass::FindClass( "WhiteFlag" )); if (( oneflagctf ) && ( pInventory == NULL )) bDelete = true; // We wish to delete the icon, so do that now. if ( bDelete ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_WHITEFLAG; } break; // Terminator artifact icon. Delete it if the player no longer has it. case S_TERMINATORARTIFACT: case ( S_TERMINATORARTIFACT + 1 ): case ( S_TERMINATORARTIFACT + 2 ): case ( S_TERMINATORARTIFACT + 3 ): if (( terminator == false ) || (( pPlayer->cheats2 & CF2_TERMINATORARTIFACT ) == false )) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_TERMINATORARTIFACT; break; // Lag icon. Delete it if the player is no longer lagging. case S_LAG: if ((( NETWORK_GetState( ) != NETSTATE_CLIENT ) && ( CLIENTDEMO_IsPlaying( ) == false )) || ( pPlayer->bLagging == false )) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_LAG; break; // Possession artifact icon. Delete it if the player no longer has it. case S_POSSESSIONARTIFACT: case ( S_POSSESSIONARTIFACT + 1 ): case ( S_POSSESSIONARTIFACT + 2 ): case ( S_POSSESSIONARTIFACT + 3 ): if ((( possession == false ) && ( teampossession == false )) || (( pPlayer->cheats2 & CF2_POSSESSIONARTIFACT ) == false )) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else ulActualSprite = SPRITE_POSSESSIONARTIFACT; break; } } // Check if we need to have an icon above us, or change the current icon. { if ( pPlayer->pIcon && pPlayer->pIcon->bTeamItemFloatyIcon ) { if ( !( GAMEMODE_GetFlags( GAMEMODE_GetCurrentMode( )) & GMF_USETEAMITEM ) || ( pPlayer->bOnTeam == false ) || ( TEAM_FindOpposingTeamsItemInPlayersInventory ( pPlayer ) == NULL ) ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } else { ulActualSprite = SPRITE_TEAMITEM; } } ULONG ulFrame = 65535; const ULONG ulDesiredSprite = medal_GetDesiredIcon ( pPlayer, pTeamItem ); // [BB] Determine the frame based on the desired sprite. switch ( ulDesiredSprite ) { case SPRITE_ALLY: ulFrame = S_ALLY; break; case SPRITE_CHAT: ulFrame = S_CHAT; break; case SPRITE_INCONSOLE: ulFrame = S_INCONSOLE; break; case SPRITE_LAG: ulFrame = S_LAG; break; case SPRITE_WHITEFLAG: ulFrame = S_WHITEFLAG; break; case SPRITE_TEAMITEM: ulFrame = 0; break; case SPRITE_TERMINATORARTIFACT: ulFrame = S_TERMINATORARTIFACT; break; case SPRITE_POSSESSIONARTIFACT: ulFrame = S_POSSESSIONARTIFACT; break; default: break; } // We have an icon that needs to be spawned. if ((( ulFrame != 65535 ) && ( ulDesiredSprite != NUM_SPRITES ))) { // [BB] If a TeamItem icon replaces an existing non-team icon, we have to delete the old icon first. if ( pPlayer->pIcon && ( pPlayer->pIcon->bTeamItemFloatyIcon == false ) && pTeamItem ) { pPlayer->pIcon->Destroy( ); pPlayer->pIcon = NULL; } if (( pPlayer->pIcon == NULL ) || ( ulDesiredSprite != ulActualSprite )) { if ( pPlayer->pIcon == NULL ) { pPlayer->pIcon = Spawn<AFloatyIcon>( pPlayer->mo->x, pPlayer->mo->y, pPlayer->mo->z + pPlayer->mo->height + ( 4 * FRACUNIT ), NO_REPLACE ); if ( pTeamItem ) { pPlayer->pIcon->bTeamItemFloatyIcon = true; FName Name = "Carry"; FState *CarryState = pTeamItem->FindState( Name ); // [BB] If the TeamItem has a Carry state (like the built in flags), use it. // Otherwise use the spawn state (the built in skulls don't have a carry state). if ( CarryState ) pPlayer->pIcon->SetState( CarryState ); else pPlayer->pIcon->SetState( pTeamItem->SpawnState ); pPlayer->pIcon->Translation = pTeamItem->Translation; } else { pPlayer->pIcon->bTeamItemFloatyIcon = false; } } if ( pPlayer->pIcon ) { // [BB] Potentially the new icon overrides an existing medal, so make sure that it doesn't fade out. pPlayer->pIcon->lTick = 0; pPlayer->pIcon->SetTracer( pPlayer->mo ); if ( pPlayer->pIcon->bTeamItemFloatyIcon == false ) pPlayer->pIcon->SetState( pPlayer->pIcon->SpawnState + ulFrame ); } } } } }