diff --git a/data/editor/speedup.png b/data/editor/speedup.png index 0ba0d71aa5a..429565c76d4 100644 Binary files a/data/editor/speedup.png and b/data/editor/speedup.png differ diff --git a/src/game/client/components/chat.cpp b/src/game/client/components/chat.cpp index ab1b178e391..d19d5d34e6f 100644 --- a/src/game/client/components/chat.cpp +++ b/src/game/client/components/chat.cpp @@ -796,41 +796,55 @@ void CChat::AddLine(int ClientId, int Team, const char *pLine) } else { - auto &LineAuthor = m_pClient->m_aClients[pCurrentLine->m_ClientId]; + const auto &LineAuthor = m_pClient->m_aClients[pCurrentLine->m_ClientId]; - if(LineAuthor.m_Team == TEAM_SPECTATORS) - pCurrentLine->m_NameColor = TEAM_SPECTATORS; - - if(m_pClient->IsTeamPlay()) + if(LineAuthor.m_Active) { - if(LineAuthor.m_Team == TEAM_RED) - pCurrentLine->m_NameColor = TEAM_RED; - else if(LineAuthor.m_Team == TEAM_BLUE) - pCurrentLine->m_NameColor = TEAM_BLUE; + if(LineAuthor.m_Team == TEAM_SPECTATORS) + pCurrentLine->m_NameColor = TEAM_SPECTATORS; + + if(m_pClient->IsTeamPlay()) + { + if(LineAuthor.m_Team == TEAM_RED) + pCurrentLine->m_NameColor = TEAM_RED; + else if(LineAuthor.m_Team == TEAM_BLUE) + pCurrentLine->m_NameColor = TEAM_BLUE; + } } if(Team == TEAM_WHISPER_SEND) { - str_format(pCurrentLine->m_aName, sizeof(pCurrentLine->m_aName), "→ %s", LineAuthor.m_aName); + str_copy(pCurrentLine->m_aName, "→"); + if(LineAuthor.m_Active) + { + str_append(pCurrentLine->m_aName, " "); + str_append(pCurrentLine->m_aName, LineAuthor.m_aName); + } pCurrentLine->m_NameColor = TEAM_BLUE; pCurrentLine->m_Highlighted = false; Highlighted = false; } else if(Team == TEAM_WHISPER_RECV) { - str_format(pCurrentLine->m_aName, sizeof(pCurrentLine->m_aName), "← %s", LineAuthor.m_aName); + str_copy(pCurrentLine->m_aName, "←"); + if(LineAuthor.m_Active) + { + str_append(pCurrentLine->m_aName, " "); + str_append(pCurrentLine->m_aName, LineAuthor.m_aName); + } pCurrentLine->m_NameColor = TEAM_RED; pCurrentLine->m_Highlighted = true; Highlighted = true; } else + { str_copy(pCurrentLine->m_aName, LineAuthor.m_aName); - + } str_copy(pCurrentLine->m_aText, pLine); - pCurrentLine->m_Friend = LineAuthor.m_Friend; - if(pCurrentLine->m_aName[0] != '\0') + if(LineAuthor.m_Active) { + pCurrentLine->m_Friend = LineAuthor.m_Friend; pCurrentLine->m_pManagedTeeRenderInfo = GameClient()->CreateManagedTeeRenderInfo(LineAuthor); } } diff --git a/src/game/client/components/mapimages.cpp b/src/game/client/components/mapimages.cpp index 3099472823c..068f15a5b3d 100644 --- a/src/game/client/components/mapimages.cpp +++ b/src/game/client/components/mapimages.cpp @@ -210,7 +210,7 @@ static bool IsValidTile(int LayerType, bool EntitiesAreMasked, EMapImageModType if(EntitiesModType == MAP_IMAGE_MOD_TYPE_DDNET || EntitiesModType == MAP_IMAGE_MOD_TYPE_DDRACE) { - if(EntitiesModType == MAP_IMAGE_MOD_TYPE_DDNET || TileIndex != TILE_SPEED_BOOST_OLD || TileIndex != TILE_SPEED_BOOST) + if(EntitiesModType == MAP_IMAGE_MOD_TYPE_DDNET || TileIndex != TILE_SPEED_BOOST_OLD || TileIndex != TILE_SPEED_BOOST || TileIndex != TILE_SPEED_LIMIT) { if(LayerType == MAP_IMAGE_ENTITY_LAYER_TYPE_ALL_EXCEPT_SWITCH && !IsValidGameTile(TileIndex) && diff --git a/src/game/client/prediction/entities/character.cpp b/src/game/client/prediction/entities/character.cpp index afdc366cb86..48c8b2433fc 100644 --- a/src/game/client/prediction/entities/character.cpp +++ b/src/game/client/prediction/entities/character.cpp @@ -716,6 +716,15 @@ void CCharacter::HandleSkippableTiles(int Index) } m_Core.m_Vel = ClampVel(m_MoveRestrictions, TempVel); } + else if(Type == TILE_SPEED_LIMIT) + { + float Speed = length(m_Core.m_Vel); + if(Speed > MaxSpeed) + { + TempVel *= (float)MaxSpeed / Speed; + } + m_Core.m_Vel = ClampVel(m_MoveRestrictions, TempVel); + } } } diff --git a/src/game/editor/explanations.cpp b/src/game/editor/explanations.cpp index 1684580ebe7..18eef3f349b 100644 --- a/src/game/editor/explanations.cpp +++ b/src/game/editor/explanations.cpp @@ -147,9 +147,11 @@ const char *CEditor::ExplainDDNet(int Tile, int Layer) if(Layer == LAYER_SPEEDUP) return "SPEEDUP: Gives tee defined speed. Arrow shows direction and angle."; break; - case TILE_TELECHECKOUT: + case TILE_TELECHECKOUT: // also TILE_SPEED_LIMIT if(Layer == LAYER_TELE) return "CHECKPOINT TELEPORT TO: Tees will appear here after touching TELEPORT CHECKPOINT with the same number and falling into CFROM TELEPORT."; + if(Layer == LAYER_SPEEDUP) + return "SPEED LIMIT: Limits the speed of a tee in all directions."; break; case TILE_TELECHECKIN: if(Layer == LAYER_TELE) diff --git a/src/game/editor/mapitems/layer_speedup.cpp b/src/game/editor/mapitems/layer_speedup.cpp index 7ff33c958a4..0ec38e0d08f 100644 --- a/src/game/editor/mapitems/layer_speedup.cpp +++ b/src/game/editor/mapitems/layer_speedup.cpp @@ -289,6 +289,12 @@ void CLayerSpeedup::FillSelection(bool Empty, std::shared_ptr pBrush, CU else m_pSpeedupTile[TgtIndex].m_MaxSpeed = pLt->m_pSpeedupTile[SrcIndex].m_MaxSpeed; } + else + { + m_pTiles[TgtIndex].m_Index = 0; + m_pSpeedupTile[TgtIndex].m_Force = 0; + m_pSpeedupTile[TgtIndex].m_Angle = 0; + } } SSpeedupTileStateChange::SData Current{ diff --git a/src/game/editor/mapitems/layer_switch.cpp b/src/game/editor/mapitems/layer_switch.cpp index e0b2c0f44c5..9279bd825c1 100644 --- a/src/game/editor/mapitems/layer_switch.cpp +++ b/src/game/editor/mapitems/layer_switch.cpp @@ -301,6 +301,13 @@ void CLayerSwitch::FillSelection(bool Empty, std::shared_ptr pBrush, CUI else m_pSwitchTile[TgtIndex].m_Flags = pLt->m_pSwitchTile[SrcIndex].m_Flags; } + else + { + m_pTiles[TgtIndex].m_Index = 0; + m_pSwitchTile[TgtIndex].m_Type = 0; + m_pSwitchTile[TgtIndex].m_Number = 0; + m_pSwitchTile[TgtIndex].m_Delay = 0; + } } SSwitchTileStateChange::SData Current{ diff --git a/src/game/editor/mapitems/layer_tele.cpp b/src/game/editor/mapitems/layer_tele.cpp index f5aca5d2986..62fc3aad150 100644 --- a/src/game/editor/mapitems/layer_tele.cpp +++ b/src/game/editor/mapitems/layer_tele.cpp @@ -284,6 +284,12 @@ void CLayerTele::FillSelection(bool Empty, std::shared_ptr pBrush, CUIRe else m_pTeleTile[TgtIndex].m_Number = pLt->m_pTeleTile[SrcIndex].m_Number; } + else + { + m_pTiles[TgtIndex].m_Index = 0; + m_pTeleTile[TgtIndex].m_Type = 0; + m_pTeleTile[TgtIndex].m_Number = 0; + } } STeleTileStateChange::SData Current{ diff --git a/src/game/editor/mapitems/layer_tune.cpp b/src/game/editor/mapitems/layer_tune.cpp index 89788274a27..50ca56a6bd6 100644 --- a/src/game/editor/mapitems/layer_tune.cpp +++ b/src/game/editor/mapitems/layer_tune.cpp @@ -256,6 +256,12 @@ void CLayerTune::FillSelection(bool Empty, std::shared_ptr pBrush, CUIRe else m_pTuneTile[TgtIndex].m_Number = pLt->m_pTuneTile[SrcIndex].m_Number; } + else + { + m_pTiles[TgtIndex].m_Index = 0; + m_pTuneTile[TgtIndex].m_Type = 0; + m_pTuneTile[TgtIndex].m_Number = 0; + } } STuneTileStateChange::SData Current{ diff --git a/src/game/mapitems.cpp b/src/game/mapitems.cpp index f9b0420b9a2..06c53a1da78 100644 --- a/src/game/mapitems.cpp +++ b/src/game/mapitems.cpp @@ -78,7 +78,7 @@ bool IsTeleTileNumberUsedAny(int Index) bool IsValidSpeedupTile(int Index) { - return Index == TILE_SPEED_BOOST_OLD || Index == TILE_SPEED_BOOST; + return Index == TILE_SPEED_BOOST_OLD || Index == TILE_SPEED_BOOST || Index == TILE_SPEED_LIMIT; } bool IsValidSwitchTile(int Index) diff --git a/src/game/mapitems.h b/src/game/mapitems.h index 215d5f6f3e3..e4b2d9d0323 100644 --- a/src/game/mapitems.h +++ b/src/game/mapitems.h @@ -130,6 +130,7 @@ enum TILE_TELEOUT, TILE_SPEED_BOOST_OLD = 28, TILE_SPEED_BOOST, + TILE_SPEED_LIMIT, TILE_TELECHECK = 29, TILE_TELECHECKOUT, TILE_TELECHECKIN, diff --git a/src/game/server/entities/character.cpp b/src/game/server/entities/character.cpp index b213f0fecc0..e2448fda8c9 100644 --- a/src/game/server/entities/character.cpp +++ b/src/game/server/entities/character.cpp @@ -1492,6 +1492,15 @@ void CCharacter::HandleSkippableTiles(int Index) } m_Core.m_Vel = ClampVel(m_MoveRestrictions, TempVel); } + else if(Type == TILE_SPEED_LIMIT) + { + float Speed = length(m_Core.m_Vel); + if(Speed > MaxSpeed) + { + TempVel *= (float)MaxSpeed / Speed; + } + m_Core.m_Vel = ClampVel(m_MoveRestrictions, TempVel); + } } }