| 277 | } |
| 278 | |
| 279 | void Player::Hit( |
| 280 | const int damage, |
| 281 | const m_Vec2& hit_direction, |
| 282 | const EntityId opponent_id, |
| 283 | Map& map, |
| 284 | const EntityId monster_id, |
| 285 | const Time current_time ) |
| 286 | { |
| 287 | PC_UNUSED( opponent_id ); |
| 288 | PC_UNUSED( current_time ); |
| 289 | |
| 290 | if( state_ != State::Alive ) |
| 291 | return; |
| 292 | |
| 293 | // TODO - in original game damage is bigger or smaller, sometimes. Know, why. |
| 294 | |
| 295 | // Armor absorbess all damage and gives 1/4 of absorbed damage to health. |
| 296 | int armor_damage= damage; |
| 297 | if( armor_damage > armor_ ) |
| 298 | armor_damage= armor_; |
| 299 | |
| 300 | int health_damage= ( damage - armor_damage ) + armor_damage / 4; |
| 301 | |
| 302 | if( !god_mode_ ) |
| 303 | { |
| 304 | armor_-= armor_damage; |
| 305 | health_-= health_damage; |
| 306 | } |
| 307 | |
| 308 | if( health_ <= 0 ) |
| 309 | { |
| 310 | // Player is dead now. |
| 311 | state_= State::DeathAnimation; |
| 312 | last_state_change_time_= current_time; |
| 313 | map.PlayMonsterSound( monster_id, Sound::PlayerMonsterSoundId::Death ); |
| 314 | } |
| 315 | else if( ( current_time - last_pain_sound_time_ ).ToSeconds() >= 0.5f ) |
| 316 | { |
| 317 | last_pain_sound_time_= current_time; |
| 318 | map.PlayMonsterSound( |
| 319 | monster_id, |
| 320 | random_generator_->RandBool() ? Sound::PlayerMonsterSoundId::Pain0 : Sound::PlayerMonsterSoundId::Pain1 ); |
| 321 | } |
| 322 | |
| 323 | // Push player, but only if hit direction length is nonzero. |
| 324 | // Zero it is for damage from environment, for example. |
| 325 | |
| 326 | const float hit_direction_square_length= hit_direction.SquareLength(); |
| 327 | if( hit_direction_square_length != 0.0f ) |
| 328 | { |
| 329 | const m_Vec2 hit_direction_normalized= hit_direction / std::sqrt( hit_direction_square_length ); |
| 330 | |
| 331 | const float c_damage_acceleration_scale= 1.0f / 12.0f; |
| 332 | |
| 333 | const m_Vec2 speed_delta= |
| 334 | float( std::min( damage, GameConstants::player_max_health ) ) * |
| 335 | c_damage_acceleration_scale * |
| 336 | hit_direction_normalized; |
no test coverage detected