void Client::PlayerHitBlockWithSpade(spades::client::Player *p, Vector3 hitPos, IntVector3 blockPos, IntVector3 normal) { SPADES_MARK_FUNCTION(); uint32_t col = map->GetColor(blockPos.x, blockPos.y, blockPos.z); IntVector3 colV = {(uint8_t)col, (uint8_t)(col >> 8), (uint8_t)(col >> 16)}; Vector3 shiftedHitPos = hitPos; shiftedHitPos.x += normal.x * .05f; shiftedHitPos.y += normal.y * .05f; shiftedHitPos.z += normal.z * .05f; EmitBlockFragments(shiftedHitPos, colV); if (p == world->GetLocalPlayer()) { localFireVibrationTime = time; } if (!IsMuted()) { bool isLocal = p == world->GetLocalPlayer(); Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Spade/HitBlock.opus"); if (isLocal) audioDevice->PlayLocal(c, MakeVector3(.1f, -.1f, 1.2f), AudioParam()); else audioDevice->Play(c, p->GetOrigin() + p->GetFront() * 0.5f - p->GetUp() * .2f, AudioParam()); } }
void Client::PlayerCapturedIntel(spades::client::Player *p){ std::string msg; { std::string holderName = chatWindow->TeamColorMessage(p->GetName(), p->GetTeamId()); std::string otherTeamName = chatWindow->TeamColorMessage(world->GetTeam(1 - p->GetTeamId()).name, 1 - p->GetTeamId()); msg = _Tr("Client", "{0} captured {1}'s intel", holderName, otherTeamName); chatWindow->AddMessage(msg); } if ((int)cg_centerMessage != 0){ std::string holderName = p->GetName(); std::string otherTeamName = world->GetTeam(1 - p->GetTeamId()).name; msg = _Tr("Client", "{0} captured {1}'s Intel.", holderName, otherTeamName); NetLog("%s", msg.c_str()); centerMessageView->AddMessage(msg); } if(world->GetLocalPlayer() && !IsMuted()){ if(p->GetTeamId() == world->GetLocalPlayer()->GetTeamId()){ Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/CTF/YourTeamCaptured.wav"); audioDevice->PlayLocal(chunk, AudioParam()); }else{ Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/CTF/EnemyCaptured.wav"); audioDevice->PlayLocal(chunk, AudioParam()); } } }
void Client::PlayerMissedSpade(spades::client::Player *p) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { bool isLocal = p == world->GetLocalPlayer(); Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Spade/Miss.opus"); if (isLocal) audioDevice->PlayLocal(c, MakeVector3(.2f, -.1f, 0.7f), AudioParam()); else audioDevice->Play(c, p->GetOrigin() + p->GetFront() * 0.8f - p->GetUp() * .2f, AudioParam()); } }
void Client::PlayerDryFiredWeapon(spades::client::Player *p) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { bool isLocal = p == world->GetLocalPlayer(); Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/DryFire.opus"); if (isLocal) audioDevice->PlayLocal(c, MakeVector3(.4f, -.3f, .5f), AudioParam()); else audioDevice->Play(c, p->GetEye() + p->GetFront() * 0.5f - p->GetUp() * .3f + p->GetRight() * .4f, AudioParam()); } }
void Client::PlayerRestocked(spades::client::Player *p) { if (!IsMuted()) { bool isLocal = p == world->GetLocalPlayer(); Handle<IAudioChunk> c = isLocal ? audioDevice->RegisterSound("Sounds/Weapons/RestockLocal.opus") : audioDevice->RegisterSound("Sounds/Weapons/Restock.opus"); if (isLocal) audioDevice->PlayLocal(c, MakeVector3(.4f, -.3f, .5f), AudioParam()); else audioDevice->Play(c, p->GetEye() + p->GetFront() * 0.5f - p->GetUp() * .3f + p->GetRight() * .4f, AudioParam()); } }
void Client::PlayerMadeFootstep(spades::client::Player *p) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { std::array<const char *, 8> snds = {"Sounds/Player/Footstep1.opus", "Sounds/Player/Footstep2.opus", "Sounds/Player/Footstep3.opus", "Sounds/Player/Footstep4.opus", "Sounds/Player/Footstep5.opus", "Sounds/Player/Footstep6.opus", "Sounds/Player/Footstep7.opus", "Sounds/Player/Footstep8.opus"}; std::array<const char *, 12> rsnds = { "Sounds/Player/Run1.opus", "Sounds/Player/Run2.opus", "Sounds/Player/Run3.opus", "Sounds/Player/Run4.opus", "Sounds/Player/Run5.opus", "Sounds/Player/Run6.opus", "Sounds/Player/Run7.opus", "Sounds/Player/Run8.opus", "Sounds/Player/Run9.opus", "Sounds/Player/Run10.opus", "Sounds/Player/Run11.opus", "Sounds/Player/Run12.opus", }; std::array<const char *, 8> wsnds = {"Sounds/Player/Wade1.opus", "Sounds/Player/Wade2.opus", "Sounds/Player/Wade3.opus", "Sounds/Player/Wade4.opus", "Sounds/Player/Wade5.opus", "Sounds/Player/Wade6.opus", "Sounds/Player/Wade7.opus", "Sounds/Player/Wade8.opus"}; bool sprinting = clientPlayers[p->GetId()] ? clientPlayers[p->GetId()]->GetSprintState() > 0.5f : false; Handle<IAudioChunk> c = p->GetWade() ? audioDevice->RegisterSound(SampleRandomElement(wsnds)) : audioDevice->RegisterSound(SampleRandomElement(snds)); audioDevice->Play(c, p->GetOrigin(), AudioParam()); if (sprinting && !p->GetWade()) { AudioParam param; param.volume *= clientPlayers[p->GetId()]->GetSprintState(); c = audioDevice->RegisterSound(SampleRandomElement(rsnds)); audioDevice->Play(c, p->GetOrigin(), param); } } }
void LimboView::Update(float dt) { // spectator team was actually 255 if(selectedTeam > 2) selectedTeam = 2; for(size_t i = 0; i < items.size(); i++){ MenuItem& item = items[i]; item.visible = true; switch(item.type){ case MenuWeaponRifle: case MenuWeaponShotgun: case MenuWeaponSMG: if(selectedTeam == 2){ item.visible = false; } default:; } bool newHover = item.rect && cursorPos; if(!item.visible) newHover = false; if(newHover && !item.hover){ IAudioDevice *dev = client->audioDevice; Handle<IAudioChunk> chunk = dev->RegisterSound("Sounds/Feedback/Limbo/Hover.wav"); dev->PlayLocal(chunk, AudioParam()); } item.hover = newHover; } }
void Client::GrenadeDroppedIntoWater(spades::client::Grenade *g) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Grenade/DropWater.opus"); audioDevice->Play(c, g->GetPosition(), AudioParam()); } }
void Client::LocalPlayerPulledGrenadePin() { SPADES_MARK_FUNCTION(); if (!IsMuted()) { Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Grenade/Fire.opus"); audioDevice->PlayLocal(c, MakeVector3(.4f, -.3f, .5f), AudioParam()); } }
void Client::PlayerCreatedBlock(spades::client::Player *p){ SPADES_MARK_FUNCTION(); if(!IsMuted()) { Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Block/Build.wav"); audioDevice->Play(c, p->GetEye() + p->GetFront(), AudioParam()); } }
void Client::PlayerChangedTool(spades::client::Player *p) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { bool isLocal = p == world->GetLocalPlayer(); Handle<IAudioChunk> c; if (isLocal) { // played by ClientPlayer::Update return; } else { c = audioDevice->RegisterSound("Sounds/Weapons/Switch.opus"); } if (isLocal) audioDevice->PlayLocal(c, MakeVector3(.4f, -.3f, .5f), AudioParam()); else audioDevice->Play(c, p->GetEye() + p->GetFront() * 0.5f - p->GetUp() * .3f + p->GetRight() * .4f, AudioParam()); } }
void Client::PlayerThrownGrenade(spades::client::Player *p, Grenade *g) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { bool isLocal = p == world->GetLocalPlayer(); Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Grenade/Throw.opus"); if (g && isLocal) { net->SendGrenade(g); } if (isLocal) audioDevice->PlayLocal(c, MakeVector3(.4f, 0.1f, .3f), AudioParam()); else audioDevice->Play(c, p->GetEye() + p->GetFront() * 0.5f - p->GetUp() * .2f + p->GetRight() * .3f, AudioParam()); } }
void Client::GrenadeBounced(spades::client::Grenade *g) { SPADES_MARK_FUNCTION(); if (g->GetPosition().z < 63.f) { if (!IsMuted()) { Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Grenade/Bounce.opus"); audioDevice->Play(c, g->GetPosition(), AudioParam()); } } }
void Client::PlayerJumped(spades::client::Player *p) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { Handle<IAudioChunk> c = p->GetWade() ? audioDevice->RegisterSound("Sounds/Player/WaterJump.opus") : audioDevice->RegisterSound("Sounds/Player/Jump.opus"); audioDevice->Play(c, p->GetOrigin(), AudioParam()); } }
void Client::TeamCapturedTerritory(int teamId, int terId) { TCGameMode::Territory *ter = static_cast<TCGameMode *>(world->GetMode())->GetTerritory(terId); int old = ter->ownerTeamId; std::string msg; std::string teamName = chatWindow->TeamColorMessage(world->GetTeam(teamId).name, teamId); if(old < 2){ std::string otherTeam = chatWindow->TeamColorMessage(world->GetTeam(old).name, old); msg = _Tr("Client", "{0} captured {1}'s territory", teamName, otherTeam); }else{ msg = _Tr("Client", "{0} captured an neutral territory", teamName); } chatWindow->AddMessage(msg); if ((int)cg_centerMessage != 0){ teamName = world->GetTeam(teamId).name; if (old < 2){ std::string otherTeam = world->GetTeam(old).name; msg = _Tr("Client", "{0} captured {1}'s Territory", teamName, otherTeam); } else{ msg = _Tr("Client", "{0} captured an Neutral Territory", teamName); } NetLog("%s", msg.c_str()); centerMessageView->AddMessage(msg); } if(world->GetLocalPlayer() && !IsMuted()){ if(teamId == world->GetLocalPlayer()->GetTeamId()){ Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/TC/YourTeamCaptured.wav"); audioDevice->PlayLocal(chunk, AudioParam()); }else{ Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/TC/EnemyCaptured.wav"); audioDevice->PlayLocal(chunk, AudioParam()); } } }
void Client::PlayerLanded(spades::client::Player *p, bool hurt) { SPADES_MARK_FUNCTION(); if (!IsMuted()) { Handle<IAudioChunk> c; if (hurt) c = audioDevice->RegisterSound("Sounds/Player/FallHurt.opus"); else if (p->GetWade()) c = audioDevice->RegisterSound("Sounds/Player/WaterLand.opus"); else c = audioDevice->RegisterSound("Sounds/Player/Land.opus"); audioDevice->Play(c, p->GetOrigin(), AudioParam()); } }
void Client::TeamWon(int teamId){ std::string msg; msg = chatWindow->TeamColorMessage(world->GetTeam(teamId).name, teamId); msg = _Tr("Client", "{0} wins!", msg); chatWindow->AddMessage(msg); msg = world->GetTeam(teamId).name; msg = _Tr("Client", "{0} Wins!", msg); NetLog("%s", msg.c_str()); centerMessageView->AddMessage(msg); scriptedUI->RecordChatLog(msg, MakeVector4(1.f, 1.f, 1.f, 0.8f)); if(world->GetLocalPlayer()){ if(teamId == world->GetLocalPlayer()->GetTeamId()){ Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/Win.wav"); audioDevice->PlayLocal(chunk, AudioParam()); }else{ Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/Lose.wav"); audioDevice->PlayLocal(chunk, AudioParam()); } } }
void Client::PlayerSentChatMessage(spades::client::Player *p, bool global, const std::string &msg){ { std::string s; if(global) /// prefix added to global chat messages. s = _Tr("Client", "[Global] "); s += ChatWindow::TeamColorMessage(p->GetName(), p->GetTeamId()); s += ": "; s += msg; chatWindow->AddMessage(s); } { std::string s; if(global) s = "[Global] "; s += p->GetName(); s += ": "; s += msg; auto col = p->GetTeamId() < 2 ? world->GetTeam(p->GetTeamId()).color : IntVector3::Make(255, 255, 255); scriptedUI->RecordChatLog(s, MakeVector4(col.x / 255.f, col.y / 255.f, col.z / 255.f, 0.8f)); } if(global) NetLog("[Global] %s (%s): %s", p->GetName().c_str(), world->GetTeam(p->GetTeamId()).name.c_str(), msg.c_str()); else NetLog("[Team] %s (%s): %s", p->GetName().c_str(), world->GetTeam(p->GetTeamId()).name.c_str(), msg.c_str()); if((!IsMuted()) && (int)cg_chatBeep) { Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/Chat.wav"); audioDevice->PlayLocal(chunk, AudioParam()); } }
bool Tracer::Update(float dt) { if (length < 16) return false; if(!firstUpdate) { curDistance += dt * velocity; if(curDistance > length) { return false; } } firstUpdate = false; //Chameleon: .kv6 tracers if ((int)opt_tracers == 2) { matrix = Matrix4::Translate(dir * velocity * dt) * matrix; } //Chameleon: play sound if tracer after coming inbound starts going outbound. //aka: when distance to tracer starts increasing after having decreased. if (player) { Vector3 pos1 = startPos + dir * curDistance; //if tracer is heading outbound if ((pos1 - player->GetPosition()).GetLength() > flyByDist && flyByDist > 0 && flyByDist * 4 < client->soundDistance) { IAudioDevice *audio = client->GetAudioDevice(); AudioParam param = AudioParam(); param.volume = 150.f / flyByDist; param.referenceDistance = (flyByDist+10)/5.f; param.pitch = 0.8f + GetRandom()*0.4f; audio->Play(snd, pos1, param); flyByDist = -1; } else if (flyByDist != -1) { flyByDist = (pos1 - player->GetEye()).GetLength(); } } return true; }
void Client::PlayerDestroyedBlockWithWeaponOrTool(spades::IntVector3 blk){ Vector3 origin = {blk.x + .5f, blk.y + .5f, blk.z + .5f}; if(!map->IsSolid(blk.x, blk.y, blk.z)) return;; Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Misc/BlockDestroy.wav"); if(!IsMuted()){ audioDevice->Play(c, origin, AudioParam()); } uint32_t col = map->GetColor(blk.x, blk.y, blk.z); IntVector3 colV = {(uint8_t)col, (uint8_t)(col >> 8), (uint8_t)(col >> 16)}; EmitBlockDestroyFragments(blk, colV); }
void Client::BlocksFell(std::vector<IntVector3> blocks) { SPADES_MARK_FUNCTION(); if (blocks.empty()) return; FallingBlock *b = new FallingBlock(this, blocks); AddLocalEntity(b); if (!IsMuted()) { IntVector3 v = blocks[0]; Vector3 o; o.x = v.x; o.y = v.y; o.z = v.z; o += .5f; Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Misc/BlockFall.opus"); audioDevice->Play(c, o, AudioParam()); } }
void Client::PlayerDiggedBlock(spades::IntVector3 blk){ Vector3 origin = {blk.x + .5f, blk.y + .5f, blk.z + .5f}; Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Misc/BlockDestroy.wav"); if(!IsMuted()){ audioDevice->Play(c, origin, AudioParam()); } for(int z = blk.z - 1 ; z <= blk.z + 1; z++){ if(z < 0 || z > 61) continue; if(!map->IsSolid(blk.x, blk.y, z)) continue; uint32_t col = map->GetColor(blk.x, blk.y, z); IntVector3 colV = {(uint8_t)col, (uint8_t)(col >> 8), (uint8_t)(col >> 16)}; EmitBlockDestroyFragments(IntVector3::Make(blk.x, blk.y, z), colV); } }
void LimboView::KeyEvent(const std::string &key){ if(key == "LeftMouseButton"){ for(size_t i = 0; i < items.size(); i++){ MenuItem& item = items[i]; if(item.hover){ IAudioDevice *dev = client->audioDevice; Handle<IAudioChunk> chunk = dev->RegisterSound("Sounds/Feedback/Limbo/Select.wav"); dev->PlayLocal(chunk, AudioParam()); switch(item.type){ case MenuTeam1: selectedTeam = 0; break; case MenuTeam2: selectedTeam = 1; break; case MenuTeamSpectator: selectedTeam = 2; break; case MenuWeaponRifle: selectedWeapon = RIFLE_WEAPON; break; case MenuWeaponSMG: selectedWeapon = SMG_WEAPON; break; case MenuWeaponShotgun: selectedWeapon = SHOTGUN_WEAPON; break; case MenuSpawn: client->SpawnPressed(); break; } } } } }
/** Handles movement of joined local player. */ void Client::UpdateLocalPlayer(float dt) { SPADES_MARK_FUNCTION(); auto *player = world->GetLocalPlayer(); PlayerInput inp = playerInput; WeaponInput winp = weapInput; // weapon/tools are disabled while/soon after sprinting if(GetSprintState() > 0.001f) { winp.primary = false; winp.secondary = false; } // don't allow to stand up when ceilings are too low if(inp.crouch == false){ if(player->GetInput().crouch){ if(!player->TryUncrouch(false)){ inp.crouch = true; } } } // don't allow jumping in the air if(inp.jump){ if(!player->IsOnGroundOrWade()) inp.jump = false; } // weapon/tools are disabled while changing tools if(clientPlayers[world->GetLocalPlayerIndex()]->IsChangingTool()) { winp.primary = false; winp.secondary = false; } // disable weapon while reloading (except shotgun) if(player->GetTool() == Player::ToolWeapon && player->IsAwaitingReloadCompletion() && !player->GetWeapon()->IsReloadSlow()) { winp.primary = false; } player->SetInput(inp); player->SetWeaponInput(winp); //send player input // FIXME: send only there are any changed? net->SendPlayerInput(inp); net->SendWeaponInput(winp); if(hasDelayedReload) { world->GetLocalPlayer()->Reload(); net->SendReload(); hasDelayedReload = false; } //PlayerInput actualInput = player->GetInput(); WeaponInput actualWeapInput = player->GetWeaponInput(); if(actualWeapInput.secondary && player->IsToolWeapon() && player->IsAlive()){ }else{ if(player->IsToolWeapon()){ // there is a possibility that player has respawned or something. // stop aiming down weapInput.secondary = false; } } // is the selected tool no longer usable (ex. out of ammo)? if(!player->IsToolSelectable(player->GetTool())) { // release mouse button before auto-switching tools winp.primary = false; winp.secondary = false; weapInput = winp; net->SendWeaponInput(weapInput); actualWeapInput = winp = player->GetWeaponInput(); // select another tool Player::ToolType t = player->GetTool(); do{ switch(t){ case Player::ToolSpade: t = Player::ToolGrenade; break; case Player::ToolBlock: t = Player::ToolSpade; break; case Player::ToolWeapon: t = Player::ToolBlock; break; case Player::ToolGrenade: t = Player::ToolWeapon; break; } }while(!world->GetLocalPlayer()->IsToolSelectable(t)); SetSelectedTool(t); } // send orientation Vector3 curFront = player->GetFront(); if(curFront.x != lastFront.x || curFront.y != lastFront.y || curFront.z != lastFront.z) { lastFront = curFront; net->SendOrientation(curFront); } lastKills = world->GetPlayerPersistent(player->GetId()).kills; // show block count when building block lines. if(player->IsAlive() && player->GetTool() == Player::ToolBlock && player->GetWeaponInput().secondary && player->IsBlockCursorDragging()) { if(player->IsBlockCursorActive()) { auto blocks = std::move (world->CubeLine(player->GetBlockCursorDragPos(), player->GetBlockCursorPos(), 256)); auto msg = _TrN("Client", "{0} block", "{0} blocks", blocks.size()); AlertType type = static_cast<int>(blocks.size()) > player->GetNumBlocks() ? AlertType::Warning : AlertType::Notice; ShowAlert(msg, type, 0.f, true); }else{ // invalid auto msg = _Tr("Client", "-- blocks"); AlertType type = AlertType::Warning; ShowAlert(msg, type, 0.f, true); } } if(player->IsAlive()) lastAliveTime = time; if(player->GetHealth() < lastHealth){ // ouch! lastHealth = player->GetHealth(); lastHurtTime = world->GetTime(); Handle<IAudioChunk> c; switch((rand() >> 3) & 3){ case 0: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/FleshLocal1.wav"); break; case 1: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/FleshLocal2.wav"); break; case 2: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/FleshLocal3.wav"); break; case 3: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/FleshLocal4.wav"); break; } audioDevice->PlayLocal(c, AudioParam()); float hpper = player->GetHealth() / 100.f; int cnt = 18 - (int)(player->GetHealth() / 100.f * 8.f); hurtSprites.resize(std::max(cnt, 6)); for(size_t i = 0; i < hurtSprites.size(); i++) { HurtSprite& spr = hurtSprites[i]; spr.angle = GetRandom() * (2.f * static_cast<float>(M_PI)); spr.scale = .2f + GetRandom() * GetRandom() * .7f; spr.horzShift = GetRandom(); spr.strength = .3f + GetRandom() * .7f; if(hpper > .5f) { spr.strength *= 1.5f - hpper; } } }else{
void Client::PlayAlertSound() { Handle<IAudioChunk> chunk = audioDevice->RegisterSound("Sounds/Feedback/Alert.wav"); audioDevice->PlayLocal(chunk, AudioParam()); }
void Client::BulletHitPlayer(spades::client::Player *hurtPlayer, HitType type, spades::Vector3 hitPos, spades::client::Player *by) { SPADES_MARK_FUNCTION(); SPAssert(type != HitTypeBlock); // don't bleed local player if (!IsFirstPerson(GetCameraMode()) || &GetCameraTargetPlayer() != hurtPlayer) { Bleed(hitPos); } if (hurtPlayer == world->GetLocalPlayer()) { // don't player hit sound now; // local bullet impact sound is // played by checking the decrease of HP return; } if (!IsMuted()) { if (type == HitTypeMelee) { Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Weapons/Spade/HitPlayer.opus"); audioDevice->Play(c, hitPos, AudioParam()); } else { Handle<IAudioChunk> c; switch (SampleRandomInt(0, 2)) { case 0: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/Flesh1.opus"); break; case 1: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/Flesh2.opus"); break; case 2: c = audioDevice->RegisterSound("Sounds/Weapons/Impacts/Flesh3.opus"); break; } AudioParam param; param.volume = 4.f; audioDevice->Play(c, hitPos, param); } } if (by == world->GetLocalPlayer() && hurtPlayer) { net->SendHit(hurtPlayer->GetId(), type); if (type == HitTypeHead) { Handle<IAudioChunk> c = audioDevice->RegisterSound("Sounds/Feedback/HeadshotFeedback.opus"); AudioParam param; param.volume = cg_hitFeedbackSoundGain; audioDevice->PlayLocal(c, param); } hitFeedbackIconState = 1.f; if (hurtPlayer->GetTeamId() == world->GetLocalPlayer()->GetTeamId()) { hitFeedbackFriendly = true; } else { hitFeedbackFriendly = false; } } }