Compare commits

..

1 commit

Author SHA1 Message Date
furo bea60a1c71
Merge 13e255e96c into 54271aef2a 2024-08-20 22:50:09 +02:00
153 changed files with 1924 additions and 5175 deletions

View file

@ -40,8 +40,6 @@ jobs:
run: scripts/fix_style.py --dry-run
- name: Check header guards
run: scripts/check_header_guards.py
- name: Validate Languages
run: scripts/languages/validate.py
- name: Check languages
run: scripts/languages/update_all.py
- name: Check dilated images

View file

@ -40,9 +40,7 @@ else()
set(TARGET_BITS "64")
endif()
if("${CMAKE_SYSTEM_PROCESSOR}" MATCHES "arm"
OR "${CMAKE_SYSTEM_PROCESSOR}" MATCHES "aarch64"
OR "${CMAKE_SYSTEM_PROCESSOR}" MATCHES "ARM64")
if("${CMAKE_SYSTEM_PROCESSOR}" MATCHES "arm" OR "${CMAKE_SYSTEM_PROCESSOR}" MATCHES "aarch64")
if(TARGET_BITS STREQUAL "32")
set(TARGET_CPU_ARCHITECTURE "arm")
else()
@ -2462,7 +2460,6 @@ if(CLIENT)
editor_trackers.cpp
editor_trackers.h
editor_ui.h
enums.h
explanations.cpp
layer_selector.cpp
layer_selector.h
@ -2501,13 +2498,8 @@ if(CLIENT)
mapitems/sound.cpp
mapitems/sound.h
popups.cpp
prompt.cpp
prompt.h
proof_mode.cpp
proof_mode.h
quick_action.h
quick_actions.cpp
quick_actions.h
smooth_value.cpp
smooth_value.h
tileart.cpp
@ -2930,7 +2922,6 @@ if(GTEST_FOUND OR DOWNLOAD_GTEST)
compression.cpp
csv.cpp
datafile.cpp
editor.cpp
fs.cpp
git_revision.cpp
hash.cpp
@ -3121,8 +3112,6 @@ set(CPACK_GENERATOR TGZ TXZ)
set(CPACK_ARCHIVE_COMPONENT_INSTALL ON)
if(TARGET_OS STREQUAL "mac")
set(CPACK_STRIP_FILES FALSE)
elseif(TARGET_OS STREQUAL "windows" AND TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(CPACK_STRIP_FILES FALSE)
else()
set(CPACK_STRIP_FILES TRUE)
endif()
@ -3136,11 +3125,7 @@ set(CPACK_SYSTEM_NAME ${CMAKE_SYSTEM_NAME})
if(TARGET_OS AND TARGET_BITS)
if(TARGET_OS STREQUAL "windows")
if (TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(CPACK_SYSTEM_NAME "win-arm64")
else()
set(CPACK_SYSTEM_NAME "win${TARGET_BITS}")
endif()
set(CPACK_SYSTEM_NAME "win${TARGET_BITS}")
set(CPACK_GENERATOR ZIP)
elseif(TARGET_OS STREQUAL "linux")
# Let compiler tell its arch
@ -3401,7 +3386,7 @@ foreach(ext zip tar.gz tar.xz)
endforeach()
foreach(target ${CPACK_TARGETS})
list(APPEND COPY_TARGET_COMMANDS COMMAND ${CMAKE_COMMAND} -E copy $<TARGET_FILE:${target}> ${TMPDIR}/)
if(NOT TARGET_OS STREQUAL "mac" AND NOT (TARGET_OS STREQUAL "windows" AND TARGET_CPU_ARCHITECTURE STREQUAL "arm64"))
if(NOT TARGET_OS STREQUAL "mac")
list(APPEND STRIP_TARGET_COMMANDS COMMAND strip -s ${TMPDIR}/$<TARGET_FILE_NAME:${target}>)
endif()
endforeach()

View file

@ -26,11 +26,8 @@ if(CURL_FOUND)
is_bundled(CURL_BUNDLED "${CURL_LIBRARY}")
set(CURL_LIBRARIES ${CURL_LIBRARY})
set(CURL_INCLUDE_DIRS ${CURL_INCLUDEDIR})
if (CURL_BUNDLED AND TARGET_OS STREQUAL "windows" AND TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(CURL_COPY_FILES
"${EXTRA_CURL_LIBDIR}/libcurl-4.dll"
)
elseif(CURL_BUNDLED AND TARGET_OS STREQUAL "windows")
if(CURL_BUNDLED AND TARGET_OS STREQUAL "windows")
set(CURL_COPY_FILES
"${EXTRA_CURL_LIBDIR}/libcurl.dll"
"${EXTRA_CURL_LIBDIR}/zlib1.dll"

View file

@ -11,18 +11,11 @@ if(TARGET_OS STREQUAL "windows")
if(NOT EXCEPTION_HANDLING_BUNDLED)
message(FATAL_ERROR "could not find exception handling paths")
endif()
if(TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(EXCEPTION_HANDLING_COPY_FILES
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/exchndl.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/mgwhelp.dll"
)
else()
set(EXCEPTION_HANDLING_COPY_FILES
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/exchndl.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/dbgcore.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/dbghelp.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/mgwhelp.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/symsrv.dll"
)
endif()
set(EXCEPTION_HANDLING_COPY_FILES
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/exchndl.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/dbgcore.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/dbghelp.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/mgwhelp.dll"
"${EXTRA_EXCEPTION_HANDLING_LIBDIR}/symsrv.dll"
)
endif()

View file

@ -31,9 +31,7 @@ if(FREETYPE_FOUND)
is_bundled(FREETYPE_BUNDLED "${FREETYPE_LIBRARY}")
set(FREETYPE_COPY_FILES)
if(FREETYPE_BUNDLED)
if(TARGET_OS STREQUAL "windows" AND TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(FREETYPE_COPY_FILES "${EXTRA_FREETYPE_LIBDIR}/libfreetype-6.dll")
elseif(TARGET_OS STREQUAL "windows")
if(TARGET_OS STREQUAL "windows")
set(FREETYPE_COPY_FILES "${EXTRA_FREETYPE_LIBDIR}/libfreetype.dll")
elseif(TARGET_OS STREQUAL "mac")
set(FREETYPE_COPY_FILES "${EXTRA_FREETYPE_LIBDIR}/libfreetype.6.dylib")

View file

@ -29,21 +29,12 @@ set(OPUSFILE_INCLUDE_DIRS ${OPUSFILE_INCLUDEDIR})
if(OPUSFILE_FOUND)
is_bundled(OPUSFILE_BUNDLED "${OPUSFILE_LIBRARY}")
if(OPUSFILE_BUNDLED AND TARGET_OS STREQUAL "windows")
if (TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(OPUSFILE_COPY_FILES
"${EXTRA_OPUSFILE_LIBDIR}/libopusfile-0.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libopus-0.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libogg-0.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libwinpthread-1.dll"
)
else()
set(OPUSFILE_COPY_FILES
"${EXTRA_OPUSFILE_LIBDIR}/libogg.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libopus.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libopusfile.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libwinpthread-1.dll"
)
endif()
set(OPUSFILE_COPY_FILES
"${EXTRA_OPUSFILE_LIBDIR}/libogg.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libopus.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libopusfile.dll"
"${EXTRA_OPUSFILE_LIBDIR}/libwinpthread-1.dll"
)
if(TARGET_BITS EQUAL 32)
list(APPEND OPUSFILE_COPY_FILES
"${EXTRA_OPUSFILE_LIBDIR}/libgcc_s_sjlj-1.dll"

View file

@ -40,12 +40,6 @@ if(SQLite3_FOUND)
is_bundled(SQLite3_BUNDLED "${SQLite3_LIBRARY}")
set(SQLite3_COPY_FILES)
if(SQLite3_BUNDLED AND TARGET_OS STREQUAL "windows")
if (TARGET_CPU_ARCHITECTURE STREQUAL "arm64")
set(SQLite3_COPY_FILES
"${EXTRA_SQLite3_LIBDIR}/libsqlite3-0.dll"
)
else()
set(SQLite3_COPY_FILES "${EXTRA_SQLite3_LIBDIR}/sqlite3.dll")
endif()
set(SQLite3_COPY_FILES "${EXTRA_SQLite3_LIBDIR}/sqlite3.dll")
endif()
endif()

View file

@ -1,7 +1,4 @@
# only find ssp when toolchain is gcc
if(TARGET_OS STREQUAL "windows"
AND NOT CMAKE_C_COMPILER_ID STREQUAL "Clang"
AND NOT CMAKE_C_COMPILER_ID STREQUAL "MSVC")
if(TARGET_OS STREQUAL "windows")
set_extra_dirs_lib(SSP ssp)
find_file(SSP_LIBRARY
NAMES libssp-0.dll

View file

@ -1,12 +0,0 @@
set(CMAKE_SYSTEM_NAME Windows)
set(CMAKE_SYSTEM_PROCESSOR aarch64)
set(CMAKE_C_COMPILER aarch64-w64-mingw32-clang)
set(CMAKE_CXX_COMPILER aarch64-w64-mingw32-clang++)
set(CMAKE_RC_COMPILER aarch64-w64-mingw32-windres)
set(CMAKE_RUST_COMPILER_TARGET aarch64-pc-windows-gnullvm)
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)

View file

@ -275,6 +275,9 @@ Player
Player country:
== ﺐﻋﻼﻟﺍ ﺪﻠﺑ:
Player options
== ﺐﻋﻼﻟﺍ ﺕﺍﺩﺍﺪﻋﺍ
Players
== ﻦﻴﺒﻋﻻ
@ -770,6 +773,9 @@ Skin prefix
Show HUD
== ﻞﻜﺸﻟﺍ ﺭﺎﻬﻇﺍ
Reload
== ﻞﻴﻤﺤﺘﻟﺍ ﺓﺩﺎﻋﺍ
9+ new mentions
== 9+ ﺓﺪﻳﺪﺟ ﺕﺍﺭﺎﻌﺷﺍ
@ -1020,6 +1026,9 @@ Debug mode enabled. Press Ctrl+Shift+D to disable debug mode.
Existing Player
== ﺩﻮﺟﻮﻣ ﺐﻋﻼﻟﺍ
Your nickname '%s' is already used (%d points). Do you still want to use it?
== ﻪﻣﺍﺪﺨﺘﺳﺍ ﺪﻳﺮﺗ ﺖﻟﺯﺎﻣ ﻞﻫ '%s' ﻞﻤﻌﺘﺴﻣ ﻚﻤﺳﺍ
Checking for existing player with your name
== ﻚﻤﺳﺎﺑ ﺐﻋﻻ ﺩﻮﺟﻭ ﻦﻣ ﻖﻘﺤﺘﻟﺍ
@ -1083,18 +1092,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1225,9 +1225,6 @@ Render complete
Are you sure that you want to restart?
==
Your nickname '%s' is already used (%d points). Do you still want to use it?
==
There's an unsaved map in the editor, you might want to save it.
==
@ -1481,12 +1478,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1654,7 +1645,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1828,39 +1819,6 @@ Unregister protocol and file extensions
DDNet %s is available:
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -4,7 +4,6 @@
#modified by:
# Gokturk 2024-06-09 12:00:50
# Gokturk 2024-07-17 02:24:00
# Gokturk 2024-08-29 23:39:00
##### /authors #####
##### translated strings #####
@ -275,6 +274,9 @@ Play background music
Player
== Oyunçu
Player options
== Oyunçu parametrlər
Players
== Oyunçular
@ -650,6 +652,9 @@ Connecting dummy
Connect Dummy
== Dummy daxil ol
Reload
== Yenilə
Deactivate
== Qeyri-aktiv etmək
@ -1445,6 +1450,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace interfeysi
Show client IDs in scoreboard
== Xal lövhəsində klient ID-lərini göstərin
Show DDRace HUD
== DDRace interfeysi göstər
@ -1862,54 +1870,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping
Could not resolve connect address '%s'. See local console for details.
== '%s' Link ünvanını həll etmək mümkün olmadı. Ətraflı məlumat üçün yerli konsola baxın
Connect address error
== Link ünvanı xətası
Could not connect dummy
== Dummy qoşula bilmədi
Dummy is not allowed on this server
== Bu serverdə dummy icazə verilmir
Please wait…
== Zəhmət olmasa gözləyin…
Show client IDs (scoreboard, chat, spectator)
== Klient ID'sini göstərin (aparıcı lövhə, söhbət, izləyici)
Normal:
== Normal:
Team:
== Komanda:
Dummy settings
== Dummy parametrlər
Toggle to edit your dummy settings
== Dummy parametrlərini redaktə etmək üçün açın
Randomize
== Təsadüfi
Are you sure that you want to delete '%s'?
== '%s' Bunu silmək istədiyinizə əminsiniz?
Delete skin
== Skini silin
Basic
== Sadə
Custom
== Xüsusi
Unable to delete skin
== Skin silinə bilməz
Customize
== Fərdiləşdirmək

View file

@ -2,11 +2,10 @@
#originally created by:
# arionwt1997
#modified by:
# Chill [TD] & PoKeMoN [TD] 2023-03-31 16:00:00
# Chill [TD] & PoKeMoN [TD] 2023-07-02 00:54:00
# Chill & PoKeMoN 2023-03-31 16:00:00
# Chill & PoKeMoN 2023-07-02 00:54:00
# Chill [TD] & PoKeMoN [TD] 2023-09-22 17:49:00
# Chill [TD] & PoKeMoN [TD] 2023-11-14 12:42:00
# Chill [TD] & PoKeMoN [TD] 2024-08-23 23:17:00
#
##### /authors #####
@ -282,6 +281,9 @@ Player
Player country:
== Краіна гульца:
Player options
== Опцыі гульца
Players
== Гульцы
@ -343,7 +345,7 @@ Shotgun
== Драбавік
Show chat
== Паказваць чат
== Паказаць чат
Show friends only
== Толькі з сябрамі
@ -379,7 +381,7 @@ Stop record
== Стоп запісу
Strict gametype filter
== Строгі фільтр рэжымаў
== Строгі фільтр рэжым.
Sudden Death
== Раптоўная смерць
@ -865,6 +867,9 @@ Loading ghost files
Time
== Час
Reload
== Перазагрузіць
Deactivate
== Выключыць
@ -1161,6 +1166,9 @@ Show votes window after voting
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Паказваць ID кліента ў табло ачкоў
Show DDRace HUD
== Паказваць DDRace HUD
@ -1613,7 +1621,7 @@ Go back the specified duration
[Demo player duration]
%d sec.
== %d сек.
== % сек.
Change the skip duration
== Змяніць працягласць пропуску
@ -1697,7 +1705,6 @@ Regular background color
Entities background color
== Колер фону энтыты
[Graphics error]
An error during command recording occurred. Try to update your GPU drivers.
== Адбылася памылка падчас выканання каманды запісу. Паспрабуйце абнавіць драйверы відэакарты.
@ -1707,213 +1714,162 @@ A render command failed. Try to update your GPU drivers.
[Graphics error]
Failed during initialization. Try to change gfx_backend to OpenGL or Vulkan in settings_ddnet.cfg in the config directory and try again.
== Памылка падчас ініцыялізацыі. Паспрабуйце змяніць gfx_backend на OpenGL або Vulcan у settings_dnet.cfg ў тэчцы канфігурацыйных файлаў і паспрабуйце яшчэ раз.
==
[Graphics error]
Out of VRAM. Try removing custom assets (skins, entities, etc.), especially those with high resolution.
== Недахоп VRAM. Паспрабуйце выдаліць карыстацкія тэкстуры (скіны, энтыты і г.д.), асабліва тыя, якія маюць высокую разрознасць.
==
[Graphics error]
Submitting the render commands failed. Try to update your GPU drivers.
== Адпраўка каманд рэндэрынгу не ўдалася. Паспрабуйце абнавіць драйверы відэакарты.
==
Failed saving the replay!
== Не атрымалася захаваць паўтор!
==
Saving settings to '%s' failed
== Захаванне налад у '%s' не атрымалася
==
Error saving settings
== Памылка захавання налад
==
Loading demo file from storage
== Загрузка файла дэма са сховішча
==
Searching
== Пошук
==
Enter Username
== Увядзіце імя карыстальніка
==
Enter Password
== Увядзіце пароль
==
NOT CONNECTED
== НЕ ПАДЛУЧАНА
==
Match %d of %d
== Адпаведна %d з %d
==
No results
== Няма вынікаў
==
Lines %d - %d (%s)
== Радкі %d - %d (%s)
==
Locked
== Зафіксаваныя
==
Following
== Бягучыя
==
Loading commands…
== Загрузка каманд…
==
[Spectating]
Following %s
== Назіранне за %s
==
Press a key…
== Націсніце клавішу…
==
Main menu
== Галоўнае меню
==
Are you sure that you want to restart?
== Вы ўпэўненыя, што хочаце пачаць нанова?
==
There's an unsaved map in the editor, you might want to save it.
== У рэдактары засталася не захаваная карта, магчыма вы хочаце яе захаваць.
==
Continue anyway?
== Працягнуць у любым выпадку?
==
%d/%d KiB (%.1f KiB/s)
== %d/%d КіБ (%.1f КіБ/с)
==
Example of usage
== Прыклад выкарыстання
==
No login required
== Уваход не патрабуецца
==
Communities
== Суполкі
==
Server filter
== Фільтр сервераў
==
Friends
== Сябры
==
Loading…
== Загрузка…
==
Player info change cooldown
== Затрымка абнаўлення інфармацыі пра гульца
==
Tee
== Tee
==
Info Messages
== Інфа. Паведамленні
==
Show local time always
== Заўсёды паказваць мясцовы час
==
Always show chat
== Заўсёды паказваць чат
==
Show only chat messages from team members
== Паказваць паведамленні чата толькі ад чальцоў каманды
==
Chat font size
== Памер шрыфта чата
==
Chat width
== Шырыня чата
==
Show friend mark (♥) in name plates
== Паказваць адзнаку сябра (♥) у таблічках з імёнамі
==
Show hook strength icon indicator
== Паказваць іконку індыкатара сілы крука
==
Show hook strength number indicator
== Паказваць нумар індыкатара сілы крука
==
Authed name color in scoreboard
== Колер аўтарызаваных гульцоў у табло ачкоў
==
Same clan color in scoreboard
== Колер твайго клана ў табло ачкоў
==
Show own player's hook collision line
== Паказваць сваю лінію сутыкнення крука
==
Always show own player's hook collision line
== Заўсёды паказваць сваю лінію сутыкнення крука
==
Always show other players' hook collision lines
== Заўсёды паказваць лініі сутыкнення крука іншых гульцоў
==
Show finish messages
== Паказваць паведамленні пра фініш
==
Round %d/%d
== Раўнд %d/%d
==
[Spectators]
%d others…
== %d іншых…
==
[Team and size]
%d\n(%d/%d)
== %d\n(%d/%d)
==
Team %d (%d/%d)
== Каманда %d (%d/%d)
==
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Show client IDs (scoreboard, chat, spectator)
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==

View file

@ -280,6 +280,9 @@ Player
Player country:
== Država
Player options
== Postavke igrača
Players
== Igrači
@ -648,6 +651,9 @@ Connecting dummy
Connect Dummy
== Konektuj dummy-a
Reload
== Reload
Deactivate
== Deaktiviraj
@ -945,18 +951,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1388,12 +1385,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1600,7 +1591,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1786,39 +1777,6 @@ Chat command (e.g. showall 1)
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -34,7 +34,6 @@
# Rafael Fontenelle 2024-04-30 14:52:00
# Rafael Fontenelle 2024-06-11 22:43:00
# Rafael Fontenelle 2024-07-17 12:04:00
# Rafael Fontenelle 2024-09-02 16:02:00
##### /authors #####
##### translated strings #####
@ -312,6 +311,9 @@ Player
Player country:
== País do jogador:
Player options
== Opções do jogador
Players
== Jogadores
@ -816,6 +818,9 @@ Show DDNet map finishes in server browser
transmits your player name to info.ddnet.org
== transmite seu nome de jogador para info.ddnet.org
Reload
== Recarregar
Time
== Tempo
@ -1371,6 +1376,9 @@ Show health, shields and ammo
DDRace HUD
== HUD do DDRace
Show client IDs in scoreboard
== Mostrar IDs de cliente no placar
Show DDRace HUD
== Mostrar HUD do DDRace
@ -1893,54 +1901,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping
Could not resolve connect address '%s'. See local console for details.
== Não foi possível resolver o endereço de conexão '%s'. Veja o console local para detalhes.
Connect address error
== Erro no endereço de conexão
Could not connect dummy
== Não foi possível conectar o dummy
Dummy is not allowed on this server
== Dummy não é permitido neste servidor
Please wait…
== Por favor, aguarde…
Show client IDs (scoreboard, chat, spectator)
== Mostrar IDs de clientes (placar, chat, observador)
Normal:
== Normal:
Team:
== Time:
Dummy settings
== Configurações do dummy
Toggle to edit your dummy settings
== Alterne para editar suas configurações do dummy
Randomize
== Aleatorizar
Are you sure that you want to delete '%s'?
== Tem certeza que deseja excluir '%s'?
Delete skin
== Excluir skin
Basic
== Básico
Custom
== Personalizado
Unable to delete skin
== Não foi possível excluir skin
Customize
== Personalizar

View file

@ -277,6 +277,9 @@ Player
Player country:
== Страна на играча:
Player options
== Настройки на Играча
Players
== Играчи
@ -543,18 +546,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1100,12 +1094,6 @@ Are you sure that you want to disconnect?
Connect Dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Connecting dummy
==
@ -1453,7 +1441,7 @@ Show votes window after voting
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1705,6 +1693,9 @@ Regular background color
Entities background color
==
Reload
==
Use current map as background
==
@ -1741,39 +1732,6 @@ No updates available
Check now
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -275,6 +275,9 @@ Player
Player country:
== País del jugador
Player options
== Opcions del jugador
Players
== Jugadors
@ -779,6 +782,9 @@ Show DDNet map finishes in server browser
transmits your player name to info.ddnet.org
== retransmet el teu nom de jugar a info.ddnet.org
Reload
== Recarga
Successfully saved the replay!
== S'ha guardat la repetició correctament!
@ -1191,18 +1197,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1544,12 +1541,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1681,7 +1672,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1837,39 +1828,6 @@ Entities background color
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -277,6 +277,9 @@ Player
Player country:
== Çĕршыв:
Player options
== Опцисем
Players
== Çынсем
@ -546,18 +549,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1103,12 +1097,6 @@ Are you sure that you want to disconnect?
Connect Dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Connecting dummy
==
@ -1453,7 +1441,7 @@ Show votes window after voting
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1705,6 +1693,9 @@ Regular background color
Entities background color
==
Reload
==
Use current map as background
==
@ -1741,39 +1732,6 @@ No updates available
Check now
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -6,7 +6,7 @@
# Petr 2011-04-02 23:02:33
# Medik & Petr 2011-07-02 19:37:05
# TeeWorlds-org 2011-07-15 00:34:19
# dobrykafe 2024-08-30 00:00:00
# dobrykafe 2024-06-09 00:00:00
##### /authors #####
##### translated strings #####
@ -281,6 +281,9 @@ Player
Player country:
== Země hráčů:
Player options
== Možnosti hráčů
Players
== Hráči
@ -643,6 +646,9 @@ Connecting dummy
Connect Dummy
== Připojit dummyho
Reload
== Znovu načíst
Deactivate
== Deaktivovat
@ -1628,6 +1634,9 @@ Show local time always
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Zobrazit ID klientů ve výsledkové tabulce
Show DDRace HUD
== Zobrazit DDRace HUD
@ -1844,77 +1853,26 @@ Tee
Show only chat messages from team members
== Zobrazit pouze zprávy od členů týmu
Could not resolve connect address '%s'. See local console for details.
== Nelze získat adresu k připojení '%s'. Podrobnosti najdete v místní konzoli.
Connect address error
== Chyba v adrese k připojení
Could not connect dummy
== Nepodařilo se připojit dummyho
[Spectating]
Following %s
== Sledujete %s
==
Example of usage
== Příklad použití
Dummy is not allowed on this server
== Dummy není na tomto serveru povolen
Please wait…
== Čekejte prosím…
Show client IDs (scoreboard, chat, spectator)
== Zobrazit ID klientů (výsledková tabulka, chat, divák)
Normal:
== Normální:
Team:
== Tým:
Dummy settings
== Nastavení dummyho
Toggle to edit your dummy settings
== Přepnutím upravíte nastavení dummyho
Randomize
== Randomizovat
Are you sure that you want to delete '%s'?
== Jste si jisti, že chcete smazat '%s'?
Delete skin
== Odstranit skin
Basic
== Základní
Custom
== Vlastní
Unable to delete skin
== Nelze odstranit skin
Customize
== Přizpůsobit
==
Round %d/%d
== Kolo %d/%d
==
[Spectators]
%d others…
== %d dalších…
==
[Team and size]
%d\n(%d/%d)
== %d\n(%d/%d)
==
Team %d (%d/%d)
== Tým %d (%d/%d)
==
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping
==

View file

@ -278,6 +278,9 @@ Player
Player country:
== Spillernes land:
Player options
== Spillermuligheder
Players
== Spillere
@ -673,6 +676,9 @@ Kill
Pause
== Pause
Reload
== Genindlæs
Deactivate
== Deaktiver
@ -1094,18 +1100,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1489,12 +1486,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1662,7 +1653,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1833,39 +1824,6 @@ Chat command (e.g. showall 1)
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -290,6 +290,9 @@ Player
Player country:
== Speler land:
Player options
== Speler opties
Players
== Spelers
@ -660,6 +663,9 @@ Connecting dummy
Connect Dummy
== Verbind Dummy
Reload
== Herladen
Deactivate
== Deactiveren
@ -1237,18 +1243,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1587,12 +1584,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1718,7 +1709,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1859,39 +1850,6 @@ Entities background color
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -300,6 +300,9 @@ Kill
Pause
== Paŭzi
Player options
== Ludantaj agordoj
Player
== Ludanto
@ -562,18 +565,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1059,12 +1053,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Stop record
==
@ -1493,7 +1481,7 @@ Show votes window after voting
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1736,6 +1724,9 @@ Regular background color
Entities background color
==
Reload
==
Use current map as background
==
@ -1760,39 +1751,6 @@ DDNet Client updated!
No updates available
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -281,6 +281,9 @@ Player
Player country:
== Mängija maa:
Player options
== Mängija sätted
Players
== Mängijad
@ -707,6 +710,9 @@ Kill
Pause
== Paus
Reload
== Lae uuesti
Deactivate
== Deaktiveeri
@ -1599,6 +1605,9 @@ Show local time always
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Näita kliendi ID-eid tulemustabelis
Show DDRace HUD
== Näita DDRace HUD-i
@ -1863,56 +1872,5 @@ Round %d/%d
Team %d (%d/%d)
== Tiim %d (%d/%d)
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Show client IDs (scoreboard, chat, spectator)
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
https://wiki.ddnet.org/wiki/Mapping
==

View file

@ -280,6 +280,9 @@ Player
Player country:
== Pelaajan maa:
Player options
== Pelaajavalinnat
Players
== Pelaajat
@ -706,6 +709,9 @@ Kill
Pause
== Pysäytä
Reload
== Päivitä
Deactivate
== Deaktivoi
@ -1628,6 +1634,9 @@ Show local time always
DDRace HUD
== DDrace-HUD
Show client IDs in scoreboard
== Näytä asiakas-ID:t pistetaulukossa
Show DDRace HUD
== Näytä DDRace-HUD
@ -1823,15 +1832,6 @@ Loading sound files
Moved ingame
== Liikui pelissä
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
[Spectating]
Following %s
==
@ -1842,57 +1842,15 @@ Following %s
Example of usage
==
Dummy is not allowed on this server
==
Please wait…
==
Converse
==
Tee
==
Show client IDs (scoreboard, chat, spectator)
==
Show only chat messages from team members
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -302,6 +302,9 @@ Player
Player country:
== Origine des Tees:
Player options
== Options des joueurs
Players
== Joueurs
@ -607,6 +610,9 @@ AntiPing: predict other players
Are you sure that you want to disconnect your dummy?
== Êtes vous sûrs de vouloir déconnecter votre dummy ?
Reload
== Recharger
Server best:
== Meilleur score du serveur
@ -1384,6 +1390,9 @@ Name Plate
Hook Collisions
== Collisions du grappin
Show client IDs in scoreboard
== Afficher les IDs des clients dans le tableau des scores
Hook collision line width
== Largeur de la ligne de collision du grappin
@ -1865,15 +1874,6 @@ Entities background color
Moved ingame
== Déplacé en jeu
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
[Spectating]
Following %s
==
@ -1881,48 +1881,6 @@ Following %s
Example of usage
==
Dummy is not allowed on this server
==
Please wait…
==
Show client IDs (scoreboard, chat, spectator)
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -280,6 +280,9 @@ Player
Player country:
== País do xogador
Player options
== Opcións de xogador
Players
== Xogadores
@ -649,6 +652,9 @@ Connecting dummy
Connect Dummy
== Conectar Dummy
Reload
== Recargar
Deactivate
== Desactivar
@ -1352,6 +1358,9 @@ Show health, shields and ammo
DDRace HUD
== HUD DDRace
Show client IDs in scoreboard
== Mostrar IDs de cliente na táboa de puntuación
Show DDRace HUD
== Mostrar o HUD DDRace
@ -1562,15 +1571,6 @@ Relative
Absolute
== Absoluto
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Error playing demo
==
@ -1767,12 +1767,6 @@ Delete folder
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1803,9 +1797,6 @@ Info Messages
Show local time always
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1860,39 +1851,6 @@ Regular background color
Entities background color
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -299,6 +299,9 @@ Player
Player country:
== Spielerland:
Player options
== Spieleroptionen
Players
== Spieler
@ -362,6 +365,9 @@ Shotgun
Show chat
== Chat anzeigen
Show client IDs in scoreboard
== Client-IDs in der Punktetafel anzeigen
Show DDRace HUD
== DDRace-HUD anzeigen
@ -809,6 +815,9 @@ Skin prefix
Show HUD
== HUD zeigen
Reload
== Neu laden
9+ new mentions
== 9+ Erwähnungen
@ -1878,56 +1887,5 @@ Round %d/%d
Team %d (%d/%d)
== Team %d (%d/%d)
Could not resolve connect address '%s'. See local console for details.
== Konnte Verbindungsadresse '%s' nicht auflösen, siehe lokale Konsole für Details.
Connect address error
== Fehler in Verbindungsadresse
Could not connect dummy
== Konnte Dummy nicht verbinden
Dummy is not allowed on this server
== Dummy ist auf diesem Server nicht erlaubt
Please wait…
== Bitte warten…
Show client IDs (scoreboard, chat, spectator)
== Client-IDs anzeigen (Punktetafel, Chat, Beobachter)
Normal:
== Normal:
Team:
== Team:
Dummy settings
== Dummy-Einstellungen
Toggle to edit your dummy settings
== Zu Dummy-Einstellungen wechseln
Randomize
== Randomisieren
Are you sure that you want to delete '%s'?
== Bist du sicher dass du '%s' löschen willst?
Delete skin
== Skin löschen
Basic
== Einfach
Custom
== Individuell
Unable to delete skin
== Kann Skin nicht löschen
Customize
== Anpassen
https://wiki.ddnet.org/wiki/Mapping
==

View file

@ -280,6 +280,9 @@ Player
Player country:
== Χώρα παίκτη:
Player options
== Επιλογές παίκτη
Players
== Παίκτες
@ -552,18 +555,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1106,12 +1100,6 @@ Are you sure that you want to disconnect?
Connect Dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Connecting dummy
==
@ -1456,7 +1444,7 @@ Show votes window after voting
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1705,6 +1693,9 @@ Regular background color
Entities background color
==
Reload
==
Use current map as background
==
@ -1741,39 +1732,6 @@ No updates available
Check now
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -270,6 +270,9 @@ Pistol
Player
== Játékos
Player options
== Játékosok kezelése
Players
== Játékosok
@ -786,6 +789,9 @@ Show DDNet map finishes in server browser
transmits your player name to info.ddnet.org
== továbbítja a játékosnevedet az info.ddnet.org oldalra
Reload
== Újratöltés
Hammerfly dummy
== Másolat kalapácsolás
@ -1054,6 +1060,9 @@ Auto
Replay
== Visszajátszás
The width of texture %s is not divisible by %d, or the height is not divisible by %d, which might cause visual bugs.
== Ennek a Textúrának szélessége, vagy magassága (%s) nem megfelelően osztható el ezzel a számmal: (%d), ami vizuális hibákhoz vezethet. (Méretek máshogyan fognak kinézni és a teljesítményt is ronthatja.)
Getting server list from master server
== Szerverlista lekérése a fő szerverekről
@ -1329,6 +1338,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Mutassa a kliensek ID-ét a pontszámtáblán
Show DDRace HUD
== Mutassa a DDRace HUD-ot (Speciális HUD)
@ -1539,15 +1551,6 @@ Unregister protocol and file extensions
Open the directory to add custom assets
== Megnyitni az egyedi Képek helyét
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Error playing demo
==
@ -1560,9 +1563,6 @@ Saving settings to '%s' failed
Error saving settings
==
The width of texture %s is not divisible by %d, or the height is not divisible by %d, which might cause visual bugs.
==
Loading demo file from storage
==
@ -1772,12 +1772,6 @@ Delete folder
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1808,9 +1802,6 @@ Info Messages
Show local time always
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1862,39 +1853,6 @@ Regular background color
Entities background color
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -284,6 +284,9 @@ Player
Player country:
== Filtra per paese:
Player options
== Opzioni giocatore
Players
== Giocatori
@ -706,6 +709,9 @@ Kill
Pause
== Pausa
Reload
== Ricarica
Deactivate
== Disattiva
@ -1174,7 +1180,7 @@ No server selected
== Nessun server selezionato
Online clanmates (%d)
== Compagni di clan online (%d)
== Compagni di clan online
Click to select server. Double click to join your friend.
== Fare click per selezionare il server. Fai doppio click per unirti al tuo amico.
@ -1267,6 +1273,9 @@ Hook Collisions
Show health, shields and ammo
== Mostra vita, scudi e munizioni
Show client IDs in scoreboard
== Mostra gli ID clienti nella scoreboard
Show DDRace HUD
== Mostra l'HUD DDRace
@ -1402,18 +1411,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1680,12 +1680,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1789,9 +1783,6 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1882,39 +1873,6 @@ Regular background color
Entities background color
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -274,6 +274,9 @@ Player
Player country:
== 所在地:
Player options
== プレイヤー設定
Players
== プレーヤー
@ -681,6 +684,9 @@ Kill
Pause
== 観察
Reload
== 更新
Deactivate
== 無効にする
@ -1129,18 +1135,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1515,12 +1512,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1673,7 +1664,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1838,39 +1829,6 @@ Chat command (e.g. showall 1)
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -280,6 +280,9 @@ Pistol
Player
== 플레이어
Player options
== 플레이어 옵션
Players
== 플레이어
@ -531,6 +534,9 @@ Successfully saved the replay!
Replay feature is disabled!
== 리플레이 기능을 비활성화했습니다!
The width of texture %s is not divisible by %d, or the height is not divisible by %d, which might cause visual bugs.
== 텍스처 %s 의 너비 또는 높이를 %d 으로 나눌 수 없습니다. 이는 시각적 오류를 발생시킬 수 있습니다.
Warning
== 주의
@ -696,6 +702,9 @@ Pause
Time
== 시간
Reload
== 새로고침
Deactivate
== 비활성화
@ -1350,6 +1359,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== 점수판에 클라이언트 ID 표시
Show DDRace HUD
== DDRace HUD 표시
@ -1551,15 +1563,6 @@ Copy info
Create a random skin
== 무작위 스킨 생성
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Error playing demo
==
@ -1572,9 +1575,6 @@ Saving settings to '%s' failed
Error saving settings
==
The width of texture %s is not divisible by %d, or the height is not divisible by %d, which might cause visual bugs.
==
Loading demo file from storage
==
@ -1784,12 +1784,6 @@ Delete folder
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1820,9 +1814,6 @@ Info Messages
Show local time always
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1874,39 +1865,6 @@ Regular background color
Entities background color
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -309,6 +309,9 @@ Player
Player country:
== Өлкөсү:
Player options
== Оюнчу опциялары
Players
== Оюнчулар
@ -543,18 +546,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1097,12 +1091,6 @@ Are you sure that you want to disconnect?
Connect Dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Connecting dummy
==
@ -1447,7 +1435,7 @@ Show votes window after voting
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1696,6 +1684,9 @@ Regular background color
Entities background color
==
Reload
==
Use current map as background
==
@ -1732,39 +1723,6 @@ No updates available
Check now
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -279,6 +279,9 @@ Player
Player country:
== Spillerland:
Player options
== Spillerinstillinger
Players
== Spillere
@ -650,6 +653,9 @@ Connecting dummy
Connect Dummy
== Koble til dummy
Reload
== Last på nytt
Deactivate
== Deaktiver
@ -1095,18 +1101,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1490,12 +1487,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1663,7 +1654,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1834,39 +1825,6 @@ Chat command (e.g. showall 1)
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Extras
==

View file

@ -519,6 +519,9 @@ Kill
Pause
== ﺚﮑﻣ ﺖﻟﺎﺣ
Player options
== ﻦﮑﯾﺯﺎﺑ ﺕﺎﻤﯿﻈﻨﺗ
Player
== ﻦﮑﯾﺯﺎﺑ
@ -540,6 +543,9 @@ Vote command:
Time
== ﻥﺎﻣﺯ
Reload
== ﻩﺭﺎﺑﻭﺩ ﯼﺮﯿﮔﺭﺎﺑ
Deactivate
== ﻥﺩﺮﮐ ﻝﺎﻌﻓﺮﯿﻏ
@ -1219,6 +1225,9 @@ Show votes window after voting
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== ﺯﺎﯿﺘﻣﺍ ﯼﻮﻠﺑﺎﺗ ﺭﺩ ﺖﻨﯾﻼﮐ ID ﺶﯾﺎﻤﻧ
Show DDRace HUD
== DDRace HUD ﺶﯾﺎﻤﻧ
@ -1509,18 +1518,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1754,12 +1754,6 @@ Delete folder
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1793,9 +1787,6 @@ Info Messages
Show local time always
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1850,39 +1841,6 @@ Entities background color
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -282,6 +282,9 @@ Player
Player country:
== Narodowość:
Player options
== Opcje gracza
Players
== Gracze
@ -680,6 +683,9 @@ Enable replays
Automatically create statboard csv
== Automatycznie stwórz plik csv z tabelą wyników
Reload
== Przeładuj
Replay feature is disabled!
== Funkcja odtwarzania jest wyłączona!
@ -1633,6 +1639,9 @@ Show health, shields and ammo
Show local time always
== Pokazuj czas lokalny
Show client IDs in scoreboard
== Pokazuj ID klienta w tabeli wyników
Show DDRace HUD
== Pokazuj HUD DDRace
@ -1799,15 +1808,6 @@ Submitting the render commands failed. Try to update your GPU drivers.
Failed to swap framebuffers. Try to update your GPU drivers.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Match %d of %d
==
@ -1840,12 +1840,6 @@ Folder Link
map not included
==
Dummy is not allowed on this server
==
Please wait…
==
Aim bind
==
@ -1861,45 +1855,9 @@ Tee
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
==
Show only chat messages from team members
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -290,6 +290,9 @@ Player
Player country:
== País do jogador
Player options
== Opções do jogador
Players
== Jogadores
@ -770,6 +773,9 @@ Connect Dummy
Time
== Tempo
Reload
== Recarregar
Deactivate
== Desativar
@ -884,18 +890,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1333,12 +1330,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Kill
==
@ -1572,7 +1563,7 @@ Show local time always
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1776,39 +1767,6 @@ Chat command (e.g. showall 1)
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -286,6 +286,9 @@ Player
Player country:
== Țara jucătorului:
Player options
== Opțiuni jucător
Players
== Jucători
@ -558,18 +561,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1112,12 +1106,6 @@ Are you sure that you want to disconnect?
Connect Dummy
==
Dummy is not allowed on this server
==
Please wait…
==
Connecting dummy
==
@ -1462,7 +1450,7 @@ Show votes window after voting
DDRace HUD
==
Show client IDs (scoreboard, chat, spectator)
Show client IDs in scoreboard
==
Show DDRace HUD
@ -1711,6 +1699,9 @@ Regular background color
Entities background color
==
Reload
==
Use current map as background
==
@ -1747,39 +1738,6 @@ No updates available
Check now
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Emoticons
==

View file

@ -294,6 +294,9 @@ Player
Player country:
== Страна игрока:
Player options
== Опции игрока
Players
== Игроки
@ -631,7 +634,7 @@ Loading DDNet Client
== Загрузка DDNet Client
Normal message
== Обычное
== Обычное с.
Connecting dummy
== Подключение дамми
@ -643,10 +646,10 @@ Save ghost
== Сохранять тень
DDNet Client updated!
== DDNet клиент обновлён!
== DDNet Client обновлён!
Highlighted message
== Выделенное
== Выделенное с.
Demo
== Демо
@ -724,7 +727,7 @@ Downloading %s:
== Скачивание %s:
Update failed! Check log…
== Не удалось обновиться! Подробности в логах
== Ошибка. Проверьте логи
Restart
== Рестарт
@ -747,6 +750,9 @@ Fetch Info
Connect Dummy
== Подключить дамми
Reload
== Перезагрузить
Deactivate
== Выключить
@ -799,7 +805,7 @@ Toggle dyncam
== Смена дин. камеры
Toggle dummy
== Переключение дамми
== Смена Tee
Toggle ghost
== Переключить тень
@ -844,7 +850,7 @@ DDNet
== DDNet
Friend message
== Дружеское
== Дружеское с.
Save the best demo of each race
== Сохранять лучшее демо каждой карты
@ -916,10 +922,10 @@ Ratio
== Соотношение
Net
== Сальдо
== Сеть
FPM
== У/мин
== FPM
Spree
== Серия
@ -940,7 +946,7 @@ Grabs
== 9+ упоминаний
Client message
== Клиентское
== Клиентское с.
Warning
== Предупреждение
@ -973,7 +979,7 @@ Run server
== Запустить сервер
Server executable not found, can't run server
== Файл сервера не найден, не удалось запустить сервер
== Файл сервера не найден, невозможно запустить
Editor
== Редактор
@ -1356,6 +1362,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Показывать ид. игроков
Show DDRace HUD
== Показывать DDRace HUD
@ -1826,10 +1835,10 @@ No login required
== Без логина
Player info change cooldown
== Кулдаун смены данных об игроке
== Задержка смены информации об игроке
Tee
== Тии
== Ти
Always show chat
== Всегда показывать чат
@ -1878,54 +1887,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping/ru
Could not resolve connect address '%s'. See local console for details.
== Не удалось определить адрес подключения '%s'. Подробности в локальной консоли.
Connect address error
== Ошибка адреса подключения
Could not connect dummy
== Невозможно подключить дамми
Dummy is not allowed on this server
== Дамми не разрешен на этом сервере
Please wait…
== Пожалуйста, подождите…
Show client IDs (scoreboard, chat, spectator)
== Показывать ID клиента (табло, чат, наблюдатель)
Normal:
== Обычный:
Team:
== В команде:
Dummy settings
== Настройки дамми
Toggle to edit your dummy settings
== Нажмите, чтобы изменить настройки дамми
Randomize
== Случайный
Are you sure that you want to delete '%s'?
== Вы уверены, что хотите удалить '%s'?
Delete skin
== Удалить скин
Basic
== Пресеты
Custom
== Кастомизация
Unable to delete skin
== Невозможно удалить скин
Customize
== Кастомизировать

View file

@ -281,6 +281,9 @@ Player
Player country:
== Država igrača
Player options
== Podešavanja igrača
Players
== Igrači
@ -682,6 +685,9 @@ Kill
Pause
== Pauza
Reload
== Osveži
Deactivate
== Deaktiviraj
@ -1258,6 +1264,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace Prikaz
Show client IDs in scoreboard
== Prikaži identitete na tabli rezultata
Show DDRace HUD
== Prikaži DDRace Prikaz
@ -1640,15 +1649,6 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not connect dummy
==
Error playing demo
==
@ -1785,12 +1785,6 @@ Netversion
map not included
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1815,9 +1809,6 @@ Info Messages
Show local time always
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1869,39 +1860,6 @@ Regular background color
Entities background color
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Round %d/%d
==

View file

@ -277,6 +277,9 @@ Player
Player country:
== Држава играча
Player options
== Подешавања играча
Players
== Играчи
@ -681,6 +684,9 @@ Kill
Pause
== Пауза
Reload
== Освежи
Deactivate
== Деактивирај
@ -1257,6 +1263,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace Приказ
Show client IDs in scoreboard
== Прикажи идентитете на табли резултата
Show DDRace HUD
== Прикажи DDRace Приказ
@ -1413,18 +1422,9 @@ Could not initialize the given graphics backend, reverting to the default backen
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
==
Could not resolve connect address '%s'. See local console for details.
==
Connect address error
==
Could not save downloaded map. Try manually deleting this file: %s
==
Could not connect dummy
==
Error playing demo
==
@ -1703,12 +1703,6 @@ Unable to delete the demo '%s'
Unable to delete the folder '%s'. Make sure it's empty first.
==
Dummy is not allowed on this server
==
Please wait…
==
Loading…
==
@ -1772,9 +1766,6 @@ Info Messages
Show local time always
==
Show client IDs (scoreboard, chat, spectator)
==
Always show chat
==
@ -1859,39 +1850,6 @@ Entities background color
Unregister protocol and file extensions
==
Normal:
==
Team:
==
Dummy settings
==
Toggle to edit your dummy settings
==
Randomize
==
Are you sure that you want to delete '%s'?
==
Delete skin
==
Basic
==
Custom
==
Unable to delete skin
==
Customize
==
Open the directory to add custom assets
==

View file

@ -41,7 +41,6 @@
# 2024-04-21 By
# 2024-06-10 By
# 2024-07-21 By
# 2024-08-29 Pioooooo
##### /authors #####
##### translated strings #####
@ -343,6 +342,9 @@ HUD
Player country:
== 玩家国家 / 地区:
Player options
== 玩家选项
Players
== 玩家
@ -829,6 +831,9 @@ Show DDNet map finishes in server browser
transmits your player name to info.ddnet.org
== 将会发送你的玩家昵称到 info.ddnet.org
Reload
== 刷新
Enable replays
== 启用短时回放
@ -1384,6 +1389,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== 显示客户端 IDs (计分板中)
Show DDRace HUD
== 显示 DDRace HUD
@ -1515,7 +1523,7 @@ Are you sure that you want to reset the controls to their defaults?
[Graphics error]
Failed during initialization. Try to change gfx_backend to OpenGL or Vulkan in settings_ddnet.cfg in the config directory and try again.
== 初始化失败。请尝试打开配置目录中的设置文件settings_ddnet.cfg并将 “gfx_backend” 设置为 “gfx_backend OpenGL” 或 “gfx_backend Vulkan” 再重试。
== 初始化失败。请尝试打开配置目录中的设置文件settings_ddnet.cfg并将“gfx_backend OpenGL”修改为“gfx_backend Vulkan”若没有前者则可直接输入后者再重试。
[Graphics error]
Out of VRAM. Try removing custom assets (skins, entities, etc.), especially those with high resolution.
@ -1539,7 +1547,7 @@ Failed to swap framebuffers. Try to update your GPU drivers.
[Graphics error]
Unknown error. Try to change gfx_backend to OpenGL or Vulkan in settings_ddnet.cfg in the config directory and try again.
== 未知错误。请尝试打开配置目录中的设置文件settings_ddnet.cfg并将 “gfx_backend” 设置为 “gfx_backend OpenGL” 或 “gfx_backend Vulkan” 再重试。
== 未知错误。请尝试打开配置目录中的设置文件settings_ddnet.cfg并将“gfx_backend OpenGL”修改为“gfx_backend Vulkan”若没有前者则可直接输入后者再重试。
[Graphics error]
Could not initialize the given graphics backend, reverting to the default backend now.
@ -1567,7 +1575,7 @@ No controller found. Plug in a controller.
== 未检测到任何控制器。请尝试重新连接控制器。
Unregister protocol and file extensions
== 清除协议与文件类型关联
== 未注册的协议与扩充文件
Open the directory to add custom assets
== 打开用以添加自定义资源的文件夹路径
@ -1906,54 +1914,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/index.php?title=Mapping/zh&variant=zh-hans
Could not resolve connect address '%s'. See local console for details.
== 无法解析连接地址 '%s'。检查本地控制台以获取详情。
Connect address error
== 连接地址错误
Could not connect dummy
== 无法连接分身
Dummy is not allowed on this server
== 此服务器禁止使用分身
Please wait…
== 请稍等…
Show client IDs (scoreboard, chat, spectator)
== 显示客户端 ID计分板、聊天、观战者
Normal:
== 正常:
Team:
== 队伍:
Dummy settings
== 分身设置
Toggle to edit your dummy settings
== 切换以编辑分身设置
Randomize
== 随机
Are you sure that you want to delete '%s'?
== 你确定要删除'%s'吗?
Delete skin
== 删除皮肤
Basic
== 基本
Custom
== 自定义
Unable to delete skin
== 无法删除皮肤
Customize
== 自定义

View file

@ -3,7 +3,7 @@
# Limit and Petr
#modified by:
# LimiT 2011-07-02 20:24:44
# dobrykafe 2024-08-30 00:00:00
# dobrykafe 2024-06-09 00:00:00
##### /authors #####
##### translated strings #####
@ -278,6 +278,9 @@ Player
Player country:
== Filter krajín:
Player options
== Nastavenia hráča
Players
== Hráči
@ -1417,6 +1420,9 @@ Show votes window after voting
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Zobraziť ID klientov vo výsledkovej tabuľke
Show DDRace HUD
== Zobraziť DDRace HUD
@ -1642,6 +1648,9 @@ Regular background color
Entities background color
== Farba pozadia entít
Reload
== Znovu načítať
Use current map as background
== Použiť aktuálnu mapu ako pozadie
@ -1841,77 +1850,26 @@ Tee
Show only chat messages from team members
== Zobraziť iba správy od členov tímu
Could not resolve connect address '%s'. See local console for details.
== Nie je možné získať adresu na pripojenie '%s'. Podrobnosti nájdete v miestnej konzole.
Connect address error
== Chyba v adrese na pripojenie
Could not connect dummy
== Nepodarilo sa pripojiť dummyho
[Spectating]
Following %s
== Sledujete %s
==
Example of usage
== Príklad použitia
Dummy is not allowed on this server
== Dummy nie je na tomto serveri povolený
Please wait…
== Čakajte prosím…
Show client IDs (scoreboard, chat, spectator)
== Zobraziť ID klientov (výsledková tabuľka, chat, divák)
Normal:
== Normálny:
Team:
== Tím:
Dummy settings
== Nastavenie dummyho
Toggle to edit your dummy settings
== Prepnutím upravíte nastavenie dummyho
Randomize
== Randomizovať
Are you sure that you want to delete '%s'?
== Ste si istí, že chcete zmazať '%s'?
Delete skin
== Odstrániť skin
Basic
== Základné
Custom
== Vlastné
Unable to delete skin
== Nedá sa odstrániť skin
Customize
== Prispôsobiť
==
Round %d/%d
== Kolo %d/%d
==
[Spectators]
%d others…
== %d ďalších…
==
[Team and size]
%d\n(%d/%d)
== %d\n(%d/%d)
==
Team %d (%d/%d)
== Tím %d (%d/%d)
==
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping
==

View file

@ -299,6 +299,9 @@ Player
Player country:
== País del jugador
Player options
== Opciones de jugador
Players
== Jugadores
@ -623,7 +626,7 @@ Types
== Tipos
DDNet %s is out!
== ¡DDNet %s ya está disponible!
== ¡DDNet %s ya esta disponible!
Downloading %s:
== Descargando %s:
@ -670,6 +673,9 @@ Connecting dummy
Connect Dummy
== Conectar Dummy
Reload
== Recargar
Deactivate
== Desactivar
@ -1384,6 +1390,9 @@ Show health, shields and ammo
DDRace HUD
== HUD DDRace
Show client IDs in scoreboard
== Mostrar IDs de cliente en la tabla de puntuación
Show DDRace HUD
== Mostrar el HUD DDRace
@ -1882,54 +1891,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping/es
Could not resolve connect address '%s'. See local console for details.
== No se pudo resolver la dirección de conexión '%s'. Ver la consola local para más detalles.
Connect address error
== Error de dirección de conexión
Could not connect dummy
== No se pudo conectar tu dummy
Dummy is not allowed on this server
== No se permiten dummys en este servidor
Please wait…
== Espera por favor…
Show client IDs (scoreboard, chat, spectator)
== Mostrar IDs de cliente (scoreboard, chat, espectador)
Normal:
== Normal:
Team:
== Equipo:
Dummy settings
== Configuración del dummy
Toggle to edit your dummy settings
== Actívalo para configurar tu dummy
Randomize
== Aleatorizar
Are you sure that you want to delete '%s'?
== ¿Estás seguro de que quieres eliminar '%s'?
Delete skin
== Eliminar skin
Basic
== Básico
Custom
== Personalizado
Unable to delete skin
== No se pudo borrar la skin
Customize
== Personalizar

View file

@ -7,7 +7,7 @@
# 3edcxzaq1 2020-06-25 00:00:00
# cur.ie 2020-09-28 00:00:00
# simpygirl 2022-02-20 00:00:00
# furo 2024-08-29 00:00:00
# furo 2024-07-17 00:00:00
##### /authors #####
##### translated strings #####
@ -282,6 +282,9 @@ Player
Player country:
== Land
Player options
== Spelaralternativ
Players
== Spelare
@ -897,6 +900,9 @@ Show HUD
Pause
== Pausa
Reload
== Ladda om
Spree
== Spree
@ -1510,6 +1516,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== Visa klient ID i poänglista
Show DDRace HUD
== Visa DDRace HUD
@ -1866,54 +1875,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping
Could not resolve connect address '%s'. See local console for details.
== Kunde inte förstå anslutnings adress '%s'. Se den lokala konsolen för detaljer.
Connect address error
== Anslutnings problem
Could not connect dummy
== Kunde inte ansluta dummy
Dummy is not allowed on this server
== Dummy är inte tillåten på denna server
Please wait…
== Vänligen vänta…
Show client IDs (scoreboard, chat, spectator)
== Visa klient IDen (poänglistan, chatt, åskadarmeny)
Normal:
== Normal:
Team:
== Lag:
Dummy settings
== Dummy inställningar
Toggle to edit your dummy settings
== Växla för att ändra dina dummy inställningar
Randomize
== Slumpa
Are you sure that you want to delete '%s'?
== Är du säker att du vill ta bort '%s'?
Delete skin
== Ta bort skin
Basic
== Enkel
Custom
== Anpassa
Unable to delete skin
== Kunde inte ta bort skin
Customize
== Ändra

View file

@ -30,7 +30,6 @@
# 2024-04-21 By
# 2024-06-10 By
# 2024-07-21 By
# 2024-08-29 Pioooooo
##### /authors #####
##### translated strings #####
@ -332,6 +331,9 @@ HUD
Player country:
== 玩家國家/地區:
Player options
== 玩家選項
Players
== 玩家
@ -818,6 +820,9 @@ Show DDNet map finishes in server browser
transmits your player name to info.ddnet.org
== 將會發送你的玩家名稱到 info.ddnet.org
Reload
== 重新整理
Enable replays
== 啟用短時回放
@ -1222,7 +1227,7 @@ Team %d
== 隊伍 %d
Position:
== 坐標
== 坐標
Speed:
== 速度
@ -1373,6 +1378,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace HUD
Show client IDs in scoreboard
== 顯示客戶端 IDs (計分板中)
Show DDRace HUD
== 顯示 DDRace HUD
@ -1504,7 +1512,7 @@ Are you sure that you want to reset the controls to their defaults?
[Graphics error]
Failed during initialization. Try to change gfx_backend to OpenGL or Vulkan in settings_ddnet.cfg in the config directory and try again.
== 初始化失敗。請嘗試打開配置目錄中的設定檔案 (settings_ddnet.cfg) 并將 “gfx_backend” 設定為 “gfx_backend OpenGL” 或 “gfx_backend Vulkan” 再重試。
== 初始化失敗。請嘗試打開配置目錄中的設定檔案 (settings_ddnet.cfg) 并將“gfx_backend OpenGL”修改為“gfx_backend Vulkan” (若沒有前者則可直接輸入後者) 再重試。
[Graphics error]
Out of VRAM. Try removing custom assets (skins, entities, etc.), especially those with high resolution.
@ -1528,7 +1536,7 @@ Failed to swap framebuffers. Try to update your GPU drivers.
[Graphics error]
Unknown error. Try to change gfx_backend to OpenGL or Vulkan in settings_ddnet.cfg in the config directory and try again.
== 未知錯誤。請嘗試打開配置目錄中的設定檔案 (settings_ddnet.cfg) 并將 “gfx_backend” 設定為 “gfx_backend OpenGL” 或 “gfx_backend Vulkan” 再重試。
== 未知錯誤。請嘗試打開配置目錄中的設定檔案 (settings_ddnet.cfg) 并將“gfx_backend OpenGL”修改為“gfx_backend Vulkan” (若沒有前者則可直接輸入後者) 再重試。
[Graphics error]
Could not initialize the given graphics backend, reverting to the default backend now.
@ -1556,7 +1564,7 @@ No controller found. Plug in a controller.
== 未檢測到任何控制器。請嘗試重新連接控制器。
Unregister protocol and file extensions
== 清除連結與檔案類型關聯
== 未注冊的協議與擴充檔案
Open the directory to add custom assets
== 打開用以新增自定義材質的資料夾路徑
@ -1895,54 +1903,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/index.php?title=Mapping/zh&variant=zh-hant
Could not resolve connect address '%s'. See local console for details.
== 無法解析連線地址 '%s'。檢查本機控制台以取得詳情。
Connect address error
== 連線地址錯誤
Could not connect dummy
== 無法連線分身
Dummy is not allowed on this server
== 此服務器禁止使用分身
Please wait…
== 請稍等…
Show client IDs (scoreboard, chat, spectator)
== 顯示客戶端 ID計分板、聊天、旁觀者
Normal:
== 正常:
Team:
== 隊伍:
Dummy settings
== 分身設定
Toggle to edit your dummy settings
== 切換以編輯分身設定
Randomize
== 隨機
Are you sure that you want to delete '%s'?
== 你確定要刪除'%s'嗎?
Delete skin
== 刪除外觀
Basic
== 基本
Custom
== 自定義
Unable to delete skin
== 無法刪除外觀
Customize
== 自定義

View file

@ -16,7 +16,6 @@
# Gokturk 2024-04-24 03:01:50
# Gokturk 2024-06-09 12:00:50
# Gokturk 2024-07-17 02:24:00
# Gokturk 2024-08-29 23:31:00
##### /authors #####
##### translated strings #####
@ -288,6 +287,9 @@ Play background music
Player
== Oyuncu
Player options
== Oyuncu ayarları
Players
== Oyuncular
@ -663,6 +665,9 @@ Connecting dummy
Connect Dummy
== Dummy Katıl
Reload
== Yenile
Deactivate
== Devre dışı bırak
@ -1458,6 +1463,9 @@ Show health, shields and ammo
DDRace HUD
== DDRace arayüzü
Show client IDs in scoreboard
== Skor tablosunda ki istemci ID'lerini göster
Show DDRace HUD
== DDRace arayüzünü göster
@ -1875,54 +1883,3 @@ Team %d (%d/%d)
https://wiki.ddnet.org/wiki/Mapping
== https://wiki.ddnet.org/wiki/Mapping/tr
Could not resolve connect address '%s'. See local console for details.
== '%s' Bağlantı adresi çözümlenemedi. Detaylar için yerel konsola bakın
Connect address error
== Bağlantı adresi hatası
Could not connect dummy
== Dummy bağlanamadı
Dummy is not allowed on this server
== Bu sunucuda dummy izin verilmiyor
Please wait…
== Lütfen bekleyin…
Show client IDs (scoreboard, chat, spectator)
== İstemci ID'sini göster (skor tablosu, sohbet, izleyici)
Normal:
== Normal:
Team:
== Takım:
Dummy settings
== Dummy ayarları
Toggle to edit your dummy settings
== Dummy ayarlarını düzenlemek için açın
Randomize
== Rastgele
Are you sure that you want to delete '%s'?
== '%s' bunu silmek istediğine emin misin?
Delete skin
== Skini sil
Basic
== Basit
Custom
== Özel
Unable to delete skin
== Skin silinemiyor
Customize
== Özelleştir

View file

@ -4,7 +4,6 @@
#modified by:
# 404_not_found 2011-07-30 19:50:58
# EGYT5453 (15.05.2024-04.06.2024)
# veydzh3r (31.08.2024-01.09.2024)
##### /authors #####
##### translated strings #####
@ -33,10 +32,10 @@
== ще %d…
%d player
== Гравці: %d
== Гравців: %d
%d players
== Гравці: %d
== Гравців: %d
[Demo player duration]
%d sec.
@ -77,10 +76,10 @@
== Нових згадок: 9+
A demo with this name already exists
== Демо з цією назвою уже існує
== Демо з цією назвою вже існує
A folder with this name already exists
== Тека з цією назвою уже існує
== Тека з цією назвою вже існує
[Graphics error]
A render command failed. Try to update your GPU drivers.
@ -121,7 +120,7 @@ AFR
== АФР
Aim bind
== Привязка
== Прив'язка
All
== Усі
@ -166,9 +165,6 @@ AntiPing: predict weapons
Appearance
== Вигляд
Are you sure that you want to delete '%s'?
== Ви дійсно хочете видалити '%s'?
Are you sure that you want to delete the demo '%s'?
== Ви дійсно хочете видалити демо '%s'?
@ -176,13 +172,13 @@ Are you sure that you want to delete the folder '%s'?
== Ви дійсно хочете видалити теку '%s'?
Are you sure that you want to disconnect?
== Ви дійсно хочете відєднатися?
== Ви дійсно хочете від'єднатися?
Are you sure that you want to disconnect and switch to a different server?
== Ви дійсно хочете відєднатися й приєднатися до іншого сервера?
== Ви дійсно хочете від'єднатися й приєднатися до іншого сервера?
Are you sure that you want to disconnect your dummy?
== Ви дійсно хочете відєднати свого даммі?
== Ви дійсно хочете від'єднати свого даммі?
Are you sure that you want to quit?
== Ви дійсно хочете вийти?
@ -194,7 +190,7 @@ Are you sure that you want to remove the player '%s' from your friends list?
== Ви дійсно хочете прибрати гравця '%s' зі списку друзів?
Are you sure that you want to reset the controls to their defaults?
== Ви дійсно хочете скинути налаштування керувань до початкових значень?
== Ви дійсно хочете скинути налаштування керування до значень за замовчуванням?
Are you sure that you want to restart?
== Ви дійсно хочете перезапустити?
@ -212,7 +208,7 @@ AUS
== АВС
Authed name color in scoreboard
== Колір авторизованих у таблиці
== Колір авторизованих у таблі
Auto
== Авто
@ -221,7 +217,7 @@ auto
== автоматично
Automatically create statboard csv
== Автоматично зберігати статистику у файл CSV
== Автоматично зберігати статистику у CSV-файл
Automatically record demos
== Автоматично записувати демо
@ -236,14 +232,11 @@ Axis
== Осі
Background
== Тло
== Фон
Background music volume
== Гучність фонової музики
Basic
== Базовий
Best
== НКом
@ -263,7 +256,7 @@ Call vote
== Голосувати
Can't find a Tutorial server
== Не вдається знайти навчальний сервер
== Не вдалося знайти сервер-посібник
Cancel
== Скасувати
@ -296,13 +289,13 @@ Check now
== Перевірити
Checking for existing player with your name
== Перевірка на наявність гравця з вашим ім’ям
== Перевіряємо Ваш нікнейм на доступність
CHN
== КИТ
Choose default eyes when joining a server
== Типові очі під час приєднання до сервера
== Очі, які відображатимуться за замовчуванням
Clan
== Клан
@ -329,7 +322,7 @@ Close the demo player
== Закрити програвач демо
Colors of the hook collision line, in case of a possible collision with:
== Кольори лінії зіткнення гака, в разі можливого зіткнення з:
== Кольори лінії зіткнення гака, якщо він може зіштовхнутися з:
Communities
== Спільноти
@ -337,29 +330,26 @@ Communities
Config directory
== Тека налаштувань
Connect address error
== Помилка адреси з’єднання
Connect Dummy
== Під’єднати даммі
== Приєднати даммі
Connected
== Під’єднано
== Приєднано
Connecting dummy
== Під’єднання даммі
== Приєднуємо даммі
Connecting to
== Під’єднання до
== Приєднуємося до
Connection Problems…
== Проблеми зі зєднанням…
== Проблеми зі з'єднанням…
Console
== Консоль
Continue anyway?
== Усе одно продовжити?
== Все одно продовжити?
Controller
== Контролер
@ -376,25 +366,19 @@ Converse
Copy info
== Скопіювати
Could not connect dummy
== Не вдалося під’єднати даммі
[Graphics error]
Could not initialize the given graphics backend, reverting to the default backend now.
== Не вдалося ініціалізувати заданий графічний рушій, повернення до тпового рушія.
== Не вдалося ініціалізувати заданий графічний рушій, повертаємося до рушія за замовчуванням.
[Graphics error]
Could not initialize the given graphics backend, this is probably because you didn't install the driver of the integrated graphics card.
== Не вдалося ініціалізувати заданий графічний рушій, імовірно, ви не встановили драйвери на вбудовану відеокарту.
Could not resolve connect address '%s'. See local console for details.
== Не вдалося визначити адресу з’єднання '%s'. Див. локальну консоль для подробиць.
== Не вдалося ініціалізувати заданий графічний рушій, можливо тому що ви не встановили драйвери на вбудовану відеокарту.
Could not save downloaded map. Try manually deleting this file: %s
== Не вдалося зберегти завантажену мапу. Спробуйте самостійно видалити цей файл: %s
Count players only
== Рахувати лише гравців
== Рахувати тільки гравців
Countries
== Країни
@ -411,15 +395,9 @@ Current
custom
== власний
Custom
== Власний
Custom colors
== Власні кольори
Customize
== Налаштувати
Cut interval
== Інтервал
@ -439,7 +417,7 @@ DDNet %s is out!
== Вийшов DDNet %s!
DDNet Client needs to be restarted to complete update!
== Потрібно перезапустити клієнт DDNet для завершення оновлення!
== Потрібно перезапустити клієнт DDNet, щоб завершити оновлення!
DDNet Client updated!
== Клієнт DDNet оновлено!
@ -448,22 +426,22 @@ DDRace HUD
== HUD DDRace
DDraceNetwork is a cooperative online game where the goal is for you and your group of tees to reach the finish line of the map. As a newcomer you should start on Novice servers, which host the easiest maps. Consider the ping to choose a server close to you.
== DDraceNetwork — кооперативна мережева гра, ціль якої — дістатися разом зі своєю групою тії до фінішної прямої. Новачкам варто почати із серверів «Для новачків» (Novice), на яких є найпростіші мапи. Зважайте на затримку, коли вибираєте сервер.
== DDraceNetwork — кооперативна мережева гра, ціль якої — дістатися разом зі своєю групою тії до фінішної прямої. Новачкам варто почати із серверів "Для новачків" (Novice), на яких є найпростіші мапи. Зважайте на затримку, коли вибираєте сервер.
Deactivate
== Деактивувати
Deactivate all
== Деактивувати всіх
== Деактивувати усіх
Deaths
== Смерті
== С
Debug mode enabled. Press Ctrl+Shift+D to disable debug mode.
== Увімкнено режим налагодження. Натисніть Ctrl+Shift+D, щоб його вимкнути.
default
== типово
== за замовчуванням
Default length
== Звичайна тривалість
@ -480,9 +458,6 @@ Delete demo
Delete folder
== Видалити теку
Delete skin
== Видалити скін
Demo
== Демо
@ -496,16 +471,16 @@ Demos directory
== Тека демо
Desktop fullscreen
== Робочий стіл на весь екран
== Стільничний повноекранний
Disconnect
== Відєднатися
== Від'єднатися
Disconnect Dummy
== Відєднати даммі
== Від'єднати даммі
Disconnected
== Відєднано
== Від'єднано
Discord
== Discord
@ -523,10 +498,10 @@ Download skins
== Завантажувати скіни
Downloading %s:
== Завантаження %s:
== Завантажуємо %s:
Downloading map
== Завантаження мапи
== Завантажуємо мапу
Draw!
== Нічия!
@ -537,14 +512,8 @@ Dummy
Dummy copy
== Повторювати рухи
Dummy is not allowed on this server
== Використання даммі заборонене на цьому сервері
Dummy settings
== Налаштування даммі
Dynamic Camera
== Динамічна камера
== Рухома камера
Editor
== Редактор
@ -577,7 +546,7 @@ Enable regular chat sound
== Звук звичайного повідомлення
Enable replays
== Увімкнути повтори
== Повтори
Enable server message sound
== Звук повідомлення сервера
@ -589,13 +558,13 @@ Enter Password
== Введіть пароль
Enter Username
== Введіть ім’я користувача
== Введіть логін
Entities
== Сутності
Entities background color
== Колір тла сутностей
== Колір фону сутностей
Error
== Помилка
@ -613,13 +582,13 @@ EUR
== ЄВР
Example of usage
== Приклад використання
== Наприклад
Exclude
== Виключити
Existing Player
== Гравець уже існує
== Гравець вже існує
Export cut as a separate demo
== Експортувати фрагмент як окреме демо
@ -682,7 +651,7 @@ Following
[Spectating]
Following %s
== Cпостерігання за %s
== Слідуємо за %s
Force vote
== Форсувати
@ -712,7 +681,7 @@ FSAA samples
== Вибірка FSAA
Fullscreen
== На весь екран
== Повноекранний
Game
== Гра
@ -739,13 +708,13 @@ Gameplay
== Ігролад
General
== Загальні
== Загальне
Getting game info
== Отримання інформації про гру
== Отримуємо інформацію про гру
Getting server list from master server
== Отримання списку серверів з головного сервера
== Отримуємо список серверів з головного сервера
Ghost
== Привид
@ -757,7 +726,7 @@ Go back one marker
== Перемотати до попередньої мітки
Go back one tick
== Перемотати вперед на один такт
== Перемотати вперед на один тік
Go back the specified duration
== Перемотати назад
@ -766,7 +735,7 @@ Go forward one marker
== Перемотати до наступної мітки
Go forward one tick
== Перемотати вперед на один такт
== Перемотати назад на один тік
Go forward the specified duration
== Перемотати вперед
@ -832,31 +801,31 @@ HUD
== HUD
Hue
== Відтінок
== Тон
Indicate map finish
== Позначати пройдені мапи
Info Messages
== Інфо. повідомлення
== Інфо-повідомлення
Ingame controller mode
== Режим контролера у грі
Ingame controller sens.
== Чутливість у грі
== Чутл. у грі
Ingame mouse sens.
== Чутливість у грі
== Чутл. у грі
Initializing assets
== Ініціалізація текстур
== Ініціалізуємо текстури
Initializing components
== Ініціалізація компонентів
== Ініціалізуємо компоненти
Initializing map logic
== Ініціалізація логіки мапи
== Ініціалізуємо логіку мапи
Internet
== Інтернет
@ -865,7 +834,7 @@ Invalid Demo
== Недійсне демо
It's recommended that you check the settings to adjust them to your liking before joining a server.
== Перед тим, як приєднатися до сервера, рекомендуємо змінити налаштування до ваших уподобань.
== Перед тим як приєднатися до сервера, рекомендуємо змінити налаштування до ваших уподобань.
Join blue
== До синіх
@ -877,7 +846,7 @@ Join red
== До червоних
Join Tutorial Server
== Приєднатися до навчального сервера
== Приєднатися до сервера-посібника
Jump
== Стрибок
@ -916,52 +885,52 @@ Loading…
== Завантаження…
Loading assets
== Завантаження текстур
== Завантажуємо текстури
Loading commands…
== Завантаження команд
== Завантажуємо команди
Loading DDNet Client
== Завантаження клієнта DDNet
== Завантажуємо клієнт DDNet
Loading demo file from storage
== Завантаження демо-файлу зі сховища
== Завантажуємо демо-файл зі сховища
Loading demo files
== Завантаження демо-файлів
== Завантажуємо демо-файли
Loading ghost files
== Завантаження файлів привида
== Завантажуємо файли привида
Loading map file from storage
== Завантаження файлу мапи зі сховища
== Завантажуємо файл мапи зі сховища
Loading menu images
== Завантаження зображень меню
== Завантажуємо зображення меню
Loading menu themes
== Завантаження тем меню
== Завантажуємо теми меню
Loading race demo files
== Завантаження демо-файлів забігів
== Завантажуємо демо-файли забігів
Loading skin files
== Завантаження файлів скінів
== Завантажуємо файли скінів
Loading sound files
== Завантаження звукових файлів
== Завантажуємо звукові файли
Lock team
== Замкнути команду
Locked
== Замкнено
== Заблоковано
Main menu
== Головне меню
Manual
== Уручну
== Вручну
Map
== Мапа
@ -971,7 +940,7 @@ map not included
== мапу не включено
Map sound volume
== Гучність звуків мапи
== Гучність мапи
Mark the beginning of a cut (right click to reset)
== Позначити початок фрагмента (права кнопка миші, щоб скинути)
@ -986,13 +955,13 @@ Match %d of %d
== Збіг %d з %d
Max CSVs
== Макс. кількість файлів CSV
== Найбільше CSV-файлів
Max demos
== Макс. кількість демо-файлів
== Найбільше демо-файлів
Max Screenshots
== Макс. кількість знімків екрана
== Найбільше знімків екрана
may cause delay
== може спричинити затримку
@ -1016,7 +985,7 @@ Move left
== Вліво
Move player to spectators
== Зробити гравця глядачем
== Зробити гравця спостерігачем
Move right
== Вправо
@ -1031,7 +1000,7 @@ Multi-View
== Мульти-камера
Mute when not active
== Приглушувати звук поза грою
== Приглушувати, якщо вікно неактивне
NA
== ПНА
@ -1052,7 +1021,7 @@ Netversion
== Версія
New name:
== Нова назва:
== Нова назва
New random timeout code
== Новий випадковий код тайм-ауту
@ -1064,16 +1033,16 @@ Next weapon
== Наст. зброя
Nickname
== Псевдонім
== Нікнейм
No
== Ні
No answer from server yet.
== Поки що немає відповіді від сервера.
== Сервер ще не відповів.
No controller found. Plug in a controller.
== Жодного контролера не знайдено. Під’єднайте контролер.
== Жодного контролера не знайдено. Підключіть контролер.
No demo selected
== Жодного демо не вибрано
@ -1102,9 +1071,6 @@ No updates available
None
== Немає
Normal:
== Звичайний:
Normal Color
== Колір звичайних повідомлень
@ -1112,23 +1078,23 @@ Normal message
== Звичайні повідомлення
NOT CONNECTED
== НЕ ПІД’ЄДНАНО
== НЕ ПРИЄДНАНО
Nothing hookable
== нічим, за що можна зачепитися
[friends (server browser)]
Offline (%d)
== Не в мережі (%d)
== Офлайн (%d)
Ok
== Гаразд
Online clanmates (%d)
== Співклановці в мережі (%d)
== Онлайн клановці (%d)
Online players (%d)
== Гравці в мережі (%d)
== Онлайн гравці (%d)
Only save improvements
== Зберігати лише покращення
@ -1159,7 +1125,7 @@ Open the settings file
[Graphics error]
Out of VRAM. Try removing custom assets (skins, entities, etc.), especially those with high resolution.
== Недостатньо відеопамяті. Спробуйте видалити власні текстури (скіни, сутності і т.д.), особливо ті, що мають високу роздільність.
== Недостатньо відеопам'яті. Спробуйте видалити власні текстури (скіни, сутності і т.п.), особливо ті, що мають високу роздільну здатність.
Overlay entities
== Накладати сутності
@ -1168,7 +1134,7 @@ Parent Folder
== Батьківська тека
Particles
== Частинки
== Часточки
Pause
== Пауза
@ -1210,6 +1176,9 @@ Player country:
Player info change cooldown
== Затримка зміни інформації про гравця
Player options
== Налаштування гравців
Players
== Гравці
@ -1222,14 +1191,11 @@ Please enter your nickname below.
Please use a different filename
== Будь ласка, назвіть файл по-іншому
Please wait…
== Будь ласка, зачекайте…
Position:
== Позиція:
Preparing demo playback
== Підготовлення відтворення демо
== Підготовлюємо відтворення демо
Press a key…
== Натисніть клавішу…
@ -1244,7 +1210,7 @@ Quads are used for background decoration
== Квади використовуються для декорацій
Quit
== Вийти
== Вихід
Quitting. Please wait…
== Вихід. Будь ласка, зачекайте…
@ -1252,9 +1218,6 @@ Quitting. Please wait…
Race
== Забіг
Randomize
== Навмання
Ratio
== У/С
@ -1262,7 +1225,7 @@ Reason:
== Причина:
Reconnect in %d sec
== Повторне під’єднання за %dс
== Переприєднання через %dс
Record demo
== Запис демо
@ -1277,12 +1240,15 @@ Refresh Rate
== Частота кадрів
Regular background color
== Колір звичайного тла
== Колір звичайного фону
[Ingame controller mode]
Relative
== Відносний
Reload
== Оновити
Remote console
== Віддалена консоль
@ -1320,10 +1286,10 @@ Replay
== Повтор
Replay feature is disabled!
== Повтори вимкнено!
== Повтори відключено!
Requesting to join the game
== Запит на приєднання до гри
== Запитуємо приєднання до гри
Reset
== Скинути
@ -1335,7 +1301,7 @@ Reset filter
== Скинути фільтр
Reset to defaults
== Скинути до типових
== Скинути
Restart
== Перезапустити
@ -1362,7 +1328,7 @@ SA
== ПДА
Same clan color in scoreboard
== Колір співклановців у таблиці
== Колір співклановців у таблі
Sat.
== Насич.
@ -1374,7 +1340,7 @@ Save ghost
== Зберігати привида
Save power by lowering refresh rate (higher input latency)
== Економити енергію шляхом зниження частоти кадрів (вища затримка введення)
== Зберігати енергію зниженням частоти кадрів (вища затримка вводу)
Save the best demo of each race
== Зберігати найкраще демо кожного забігу
@ -1389,7 +1355,7 @@ Score limit
== Гра до
Scoreboard
== Таблиця
== Табло
Screen
== Екран
@ -1401,10 +1367,10 @@ Search
== Пошук
Searching
== Пошук
== Шукаємо
Sending initial client info
== Надсилання початкових даних клієнта
== Надсилаємо початкові дані клієнта
Server address:
== Адреса сервера:
@ -1425,7 +1391,7 @@ Server not full
== Неповний сервер
Set all to Rifle
== Установити так, як у гвинтівки
== Встановити так, як у гвинтівки
Settings
== Налаштування
@ -1451,8 +1417,8 @@ Show chat
Show clan above name plates
== Показувати клан над ніками
Show client IDs (scoreboard, chat, spectator)
== Показувати ID клієнта (таблиця, чат, глядачі)
Show client IDs in scoreboard
== Показувати ID клієнта в таблі
Show DDNet map finishes in server browser
== Показувати пройдені мапи DDNet у браузері серверів
@ -1464,7 +1430,7 @@ Show dummy actions
== Показувати дії з даммі
Show entities
== Показ сутностей
== Сутності
Show finish messages
== Показувати повідомлення про фініші
@ -1473,7 +1439,7 @@ Show freeze bars
== Показувати смугу заморозки
Show friend mark (♥) in name plates
== Показувати позначку друга (♥) біля псевдонімів
== Показувати позначку друга (♥) біля ніків
Show friends only
== Показувати лише з друзями
@ -1482,10 +1448,10 @@ Show ghost
== Показувати привида
Show health, shields and ammo
== Показувати здоров’я, захист і набої
== Показувати здоров'я, щити й набої
Show hook strength icon indicator
== Показувати іконку індикатора сили гака
== Показувати графічний індикатор сили гака
Show hook strength number indicator
== Показувати числовий індикатор сили гака
@ -1509,10 +1475,10 @@ Show local time always
== Завжди показувати місцевий час
Show name plates
== Показувати псевдоніми
== Показувати ніки
Show names in chat in team colors
== Показувати імена в чаті в кольорах команди
== Фарбувати ніки в чаті в кольори команд
Show only chat messages from friends
== Показувати лише повідомлення від друзів
@ -1551,7 +1517,7 @@ Show text entities
== Текстові сутності
Show tiles layers from BG map
== Показувати плитки з мапи фону
== Показувати тайли з мапи фону
Show quads
== Показувати квади
@ -1581,13 +1547,13 @@ Slow down the demo
== Сповільнити
Smooth Dynamic Camera
== Гладка динамічна камера
== Гладка рухома камера
Some map images could not be loaded. Check the local console for details.
== Деякі зображення мапи не завантажилися. Див. локальну консоль для подробиць.
== Деякі зображення мапи не завантажилися. Деталі у локальній консолі.
Some map sounds could not be loaded. Check the local console for details.
== Деякі звуки мапи не завантажилися. Див. локальну консоль для подробиць.
== Деякі звуки мапи не завантажилися. Деталі у локальній консолі.
Something hookable
== чимось, за що можна зачепитися
@ -1611,10 +1577,10 @@ Spectate previous
== Попер. гравець
Spectator mode
== Режим глядача
== Режим спостерігача
Spectators
== Глядачі
== Спостерігачі
Speed
== Швидкість
@ -1666,7 +1632,7 @@ Switch weapon on pickup
== Змінювати зброю при підхопленні
Switch weapon when out of ammo
== Змінювати зброю при закінченні набоїв
== Змінювати зброю коли закінчуються набої
System message
== Повідомлення системи
@ -1674,9 +1640,6 @@ System message
Team
== Команда
Team:
== Командний:
Team %d
== Команда %d
@ -1732,10 +1695,7 @@ Toggle ghost
== Привид
Toggle keyboard shortcuts
== Перемкнути сполучення
Toggle to edit your dummy settings
== Перемкніть, щоб змінити налаштування даммі
== Перемкнути скорочення
transmits your player name to info.ddnet.org
== передає ваш нікнейм до info.ddnet.org
@ -1747,7 +1707,7 @@ Try again
== Спробувати ще раз
Trying to determine UDP connectivity…
== Спроба визначити UDP-з’єднання…
== Намагаємося визначити UDP-з'єднання…
Tutorial
== Посібник
@ -1768,13 +1728,10 @@ UI Color
== Колір інтерфейсу
UI controller sens.
== Чутл. в інтерфейсі
== Чутл. у інтерфейсі
UI mouse sens.
== Чутл. в інтерфейсі
Unable to delete skin
== Не вдалося видалити скін
== Чутл. у інтерфейсі
Unable to delete the demo '%s'
== Не вдалося видалити демо '%s'
@ -1799,25 +1756,25 @@ Unregister protocol and file extensions
== Розреєструвати протокол і розширення файлів
Update failed! Check log…
== Помилка оновлення! Перевірте журнал…
== Оновлення не вдалося! Перевірте журнал…
Update now
== Оновити
Updating…
== Оновлення
== Оновлюємо
Uploading map data to GPU
== Вивантаження даних мапи до відеокарти
== Вивантажуємо дані мапи до відеокарти
Use current map as background
== Використовувати поточну мапу як тло
== Використовувати поточну мапу як фон
Use high DPI
== Високий DPI
Use k key to kill (restart), q to pause and watch other players. See settings for other key binds.
== Натисніть «k», щоб умерти (почати спочатку), «q», щоб спостерігати за іншими гравцями. Інші призначення клавіш дивіться у налаштуваннях.
== Натисніть "k", щоб умерти (почати спочатку), "q", щоб спостерігати за іншими гравцями. Інші скорочення дивіться у налаштуваннях.
Use old chat style
== Старий стиль чату
@ -1841,7 +1798,7 @@ Video name:
== Назва відео:
Video was saved to '%s'
== Відео збережено до '%s'
== Відео було збережено до '%s'
Videos directory
== Тека відео
@ -1886,13 +1843,13 @@ Why are you slowmo replaying to read this?
== Чому ви переглядаєте це у повторі?
Windowed
== У вікні
== Віконний
Windowed borderless
== Вікно без рамок
== Віконний без рамок
Windowed fullscreen
== Вікно на весь екран
== Віконний повноекранний
Yes
== Так
@ -1901,10 +1858,10 @@ Your movements are not taken into account when calculating the line colors
== Ваші рухи не враховуються при розранку кольору лінії
You must restart the game for all settings to take effect.
== Щоб налаштування набули чинності, перезапустіть гру.
== Щоб налаштування набрали чинності, перезапустіть гру.
Your nickname '%s' is already used (%d points). Do you still want to use it?
== Ваш псевдонім «%s» вже зайнято (%d балів). Усе ще хочете використовувати його?
== Нікнейм '%s' вже зайнято (%d балів). Все ще хочете використовувати його?
Your skin
== Ваш скін

@ -1 +1 @@
Subproject commit e78f350e7898fc6b0702cdc3b7ce6ee347c97d49
Subproject commit d5f0cd9194936d1ab5bd19952645b8dffe9ae06c

View file

@ -4,7 +4,6 @@ Requirements for building for Android
- At least 10-15 GiB of free disk space.
- First follow the general instructions for setting up https://github.com/ddnet/ddnet for building on Linux.
This guide has only been tested on Linux.
- Note: Use a stable version of Rust. Using the nightly version results in linking errors.
- Install the Android NDK (version 26) in the same location
where Android Studio would unpack it (`~/Android/Sdk/ndk/`):
```shell

View file

@ -7,11 +7,12 @@ export MAKEFLAGS
ANDROID_NDK_VERSION="$(cd "$ANDROID_HOME/ndk" && find . -maxdepth 1 | sort -n | tail -1)"
ANDROID_NDK_VERSION="${ANDROID_NDK_VERSION:2}"
# ANDROID_NDK_VERSION must be exported for build.sh step
export ANDROID_NDK_VERSION
# ANDROID_NDK_HOME must be exported for cargo-ndk
export ANDROID_NDK_HOME="$ANDROID_HOME/ndk/$ANDROID_NDK_VERSION"
# ANDROID_API_LEVEL must specify the _minimum_ supported SDK version, otherwise this will cause linking errors at launch
ANDROID_API_LEVEL=24
ANDROID_API_LEVEL=34
ANDROID_SUB_BUILD_DIR=build_arch
COLOR_RED="\e[1;31m"
@ -196,7 +197,6 @@ cd "${BUILD_FOLDER}" || exit 1
mkdir -p src/main
mkdir -p src/main/res/values
mkdir -p src/main/res/xml
mkdir -p src/main/res/mipmap
function copy_dummy_files() {
@ -213,7 +213,6 @@ copy_dummy_files scripts/android/files/proguard-rules.pro proguard-rules.pro
copy_dummy_files scripts/android/files/settings.gradle settings.gradle
copy_dummy_files scripts/android/files/AndroidManifest.xml src/main/AndroidManifest.xml
copy_dummy_files scripts/android/files/res/values/strings.xml src/main/res/values/strings.xml
copy_dummy_files scripts/android/files/res/xml/shortcuts.xml src/main/res/xml/shortcuts.xml
copy_dummy_files other/icons/DDNet_256x256x32.png src/main/res/mipmap/ic_launcher.png
copy_dummy_files other/icons/DDNet_256x256x32.png src/main/res/mipmap/ic_launcher_round.png

View file

@ -1,40 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
android:installLocation="auto">
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Vulkan 1.1.0 is used if supported -->
<uses-feature
android:name="android.hardware.vulkan.version"
android:required="false"
android:version="0x00401000" />
<!-- android:glEsVersion is not specified as OpenGL ES 1.0 is supported as fallback -->
<!-- Only playable in landscape mode -->
<uses-feature
android:name="android.hardware.screen.landscape"
android:required="true" />
<!-- Touchscreen support -->
<uses-feature
android:name="android.hardware.touchscreen"
android:required="false" />
<!-- Game controller support -->
<uses-feature
android:name="android.hardware.bluetooth"
android:required="false" />
<uses-feature
android:name="android.hardware.gamepad"
android:required="false" />
<uses-feature
android:name="android.hardware.usb.host"
android:required="false" />
<!-- External mouse input events -->
<uses-feature
android:name="android.hardware.type.pc"
android:required="false" />
<!-- Teeworlds does broadcasts over local networks -->
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<uses-permission android:name="android.permission.CHANGE_WIFI_MULTICAST_STATE"/>
@ -50,30 +25,19 @@
android:isGame="true"
android:icon="@mipmap/ic_launcher"
android:roundIcon="@mipmap/ic_launcher_round"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"
android:hardwareAccelerated="true">
android:theme="@android:style/Theme.NoTitleBar.Fullscreen">
<activity
android:name="org.ddnet.client.NativeMain"
android:alwaysRetainTaskState="true"
android:exported="true"
android:configChanges="layoutDirection|locale|orientation|uiMode|screenLayout|screenSize|smallestScreenSize|keyboard|keyboardHidden|navigation"
android:preferMinimalPostProcessing="true"
android:screenOrientation="landscape"
android:launchMode="singleInstance">
android:configChanges="orientation|screenSize|screenLayout|keyboardHidden"
android:screenOrientation="landscape">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<!-- Let Android know that we can handle some USB devices and should receive this event -->
<intent-filter>
<action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" />
</intent-filter>
<meta-data
android:name="android.app.lib_name"
android:value="DDNet" />
<meta-data
android:name="android.app.shortcuts"
android:resource="@xml/shortcuts" />
</activity>
</application>
</manifest>

View file

@ -18,10 +18,11 @@ java {
android {
compileSdkVersion 34
ndkVersion "TW_NDK_VERSION"
defaultConfig {
applicationId "org.ddnet.client"
namespace("org.ddnet.client")
minSdkVersion 24
minSdkVersion 19
targetSdkVersion 34
versionCode TW_VERSION_CODE
versionName "TW_VERSION_NAME"
@ -42,7 +43,6 @@ android {
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
debug {
debuggable true
minifyEnabled false
shrinkResources false
}

View file

@ -45,13 +45,12 @@ sed -i "s/TW_KEY_NAME/${TW_KEY_NAME_ESCAPED}/g" build.gradle
sed -i "s/TW_KEY_PW/${TW_KEY_PW_ESCAPED}/g" build.gradle
sed -i "s/TW_KEY_ALIAS/${TW_KEY_ALIAS_ESCAPED}/g" build.gradle
sed -i "s/TW_NDK_VERSION/${ANDROID_NDK_VERSION}/g" build.gradle
sed -i "s/TW_VERSION_CODE/${TW_VERSION_CODE}/g" build.gradle
sed -i "s/TW_VERSION_NAME/${TW_VERSION_NAME}/g" build.gradle
sed -i "s/DDNet/${APK_BASENAME}/g" src/main/res/values/strings.xml
sed -i "s/org.ddnet.client/${APK_PACKAGE_NAME}/g" src/main/res/xml/shortcuts.xml
sed -i "s/\"DDNet\"/\"${APK_BASENAME}\"/g" src/main/AndroidManifest.xml
sed -i "s/org.ddnet.client/${APK_PACKAGE_NAME}/g" src/main/AndroidManifest.xml

View file

@ -10,8 +10,6 @@ public class NativeMain extends SDLActivity {
private static final int COMMAND_RESTART_APP = SDLActivity.COMMAND_USER + 1;
private String[] launchArguments = new String[0];
@Override
protected String[] getLibraries() {
return new String[] {
@ -22,35 +20,17 @@ public class NativeMain extends SDLActivity {
@Override
public void onCreate(Bundle SavedInstanceState) {
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
Intent intent = getIntent();
if(intent != null) {
String gfxBackend = intent.getStringExtra("gfx-backend");
if(gfxBackend != null) {
if(gfxBackend.equals("Vulkan")) {
launchArguments = new String[] {"gfx_backend Vulkan"};
} else if(gfxBackend.equals("OpenGL")) {
launchArguments = new String[] {"gfx_backend OpenGL"};
}
}
}
super.onCreate(SavedInstanceState);
}
@Override
protected String[] getArguments() {
return launchArguments;
}
@Override
protected boolean onUnhandledMessage(int command, Object param) {
if(command == COMMAND_RESTART_APP) {
restartApp();
return true;
}
return false;
}
return false;
}
private void restartApp() {
Intent restartIntent =

View file

@ -1,6 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="app_name">DDNet</string>
<string name="shortcut_play_vulkan_short">Play (Vulkan)</string>
<string name="shortcut_play_opengl_short">Play (OpenGL)</string>
<string name="app_name">DDNet</string>
</resources>

View file

@ -1,30 +0,0 @@
<shortcuts xmlns:android="http://schemas.android.com/apk/res/android">
<shortcut
android:shortcutId="play-vulkan"
android:enabled="true"
android:icon="@mipmap/ic_launcher"
android:shortcutShortLabel="@string/shortcut_play_vulkan_short">
<intent
android:action="android.intent.action.VIEW"
android:targetPackage="org.ddnet.client"
android:targetClass="org.ddnet.client.NativeMain">
<extra
android:name="gfx-backend"
android:value="Vulkan" />
</intent>
</shortcut>
<shortcut
android:shortcutId="play-opengl"
android:enabled="true"
android:icon="@mipmap/ic_launcher"
android:shortcutShortLabel="@string/shortcut_play_opengl_short">
<intent
android:action="android.intent.action.VIEW"
android:targetPackage="org.ddnet.client"
android:targetClass="org.ddnet.client.NativeMain">
<extra
android:name="gfx-backend"
android:value="OpenGL" />
</intent>
</shortcut>
</shortcuts>

View file

@ -29,8 +29,6 @@ function compile_source_android() {
-DCMAKE_SYSTEM_NAME=Android \
-DCMAKE_SYSTEM_VERSION="$1" \
-DCMAKE_ANDROID_ARCH_ABI="${3}" \
-DCMAKE_C_FLAGS="$COMPILEFLAGS" -DCMAKE_CXX_FLAGS="$COMPILEFLAGS" -DCMAKE_CXX_FLAGS_RELEASE="$COMPILEFLAGS" -DCMAKE_C_FLAGS_RELEASE="$COMPILEFLAGS" \
-DCMAKE_SHARED_LINKER_FLAGS="$LINKFLAGS" -DCMAKE_SHARED_LINKER_FLAGS_RELEASE="$LINKFLAGS" \
-B"$2" \
-DBUILD_SHARED_LIBS=OFF \
-DHIDAPI_SKIP_LIBUSB=TRUE \

View file

@ -46,8 +46,7 @@ fi
mkdir -p "$1"
cd "$1" || exit 1
# ANDROID_API_LEVEL must specify the _minimum_ supported SDK version, otherwise this will cause linking errors at launch
ANDROID_API_LEVEL=24
_ANDROID_ABI_LEVEL=34
function build_cmake_lib() {
if [ ! -d "${1}" ]; then
@ -60,7 +59,7 @@ function build_cmake_lib() {
(
cd "${1}" || exit 1
cp "${CURDIR}"/scripts/compile_libs/cmake_lib_compile.sh cmake_lib_compile.sh
./cmake_lib_compile.sh "$ANDROID_API_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
./cmake_lib_compile.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
)
}
@ -75,13 +74,13 @@ cd compile_libs || exit 1
(
cd openssl || exit 1
cp "${CURDIR}"/scripts/compile_libs/make_lib_openssl.sh make_lib_openssl.sh
./make_lib_openssl.sh "$ANDROID_API_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
./make_lib_openssl.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
)
)
build_cmake_lib zlib https://github.com/madler/zlib
build_cmake_lib png https://github.com/glennrp/libpng
build_cmake_lib curl https://github.com/curl/curl "curl-8_8_0"
build_cmake_lib curl https://github.com/curl/curl
build_cmake_lib freetype2 https://gitlab.freedesktop.org/freetype/freetype
build_cmake_lib sdl https://github.com/libsdl-org/SDL SDL2
build_cmake_lib ogg https://github.com/xiph/ogg
@ -98,7 +97,7 @@ build_cmake_lib opus https://github.com/xiph/opus
./autogen.sh
fi
cp "${CURDIR}"/scripts/compile_libs/make_lib_opusfile.sh make_lib_opusfile.sh
./make_lib_opusfile.sh "$ANDROID_API_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
./make_lib_opusfile.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
)
# SQLite, just download and built by hand
@ -110,7 +109,7 @@ fi
(
cd sqlite3 || exit 1
cp "${CURDIR}"/scripts/compile_libs/make_lib_sqlite3.sh make_lib_sqlite3.sh
./make_lib_sqlite3.sh "$ANDROID_API_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
./make_lib_sqlite3.sh "$_ANDROID_ABI_LEVEL" "$OS_NAME" "$COMPILEFLAGS" "$LINKFLAGS"
)
cd ..

View file

@ -7,6 +7,22 @@ class LanguageDecodeError(Exception):
error = f"File \"{filename}\", line {line+1}: {message}"
super().__init__(error)
# Taken from https://stackoverflow.com/questions/30011379/how-can-i-parse-a-c-format-string-in-python
cfmt = r'''\
( # start of capture group 1
% # literal "%"
(?: # first option
(?:[-+0 #]{0,5}) # optional flags
(?:\d+|\*)? # width
(?:\.(?:\d+|\*))? # precision
(?:h|l|ll|w|I|I32|I64)? # size
[cCdiouxXeEfgGaAnpsSZ] # type
) | # OR
%%) # literal "%%"
'''
def decode(fileobj, elements_per_key):
data = {}
current_context = ""
@ -29,7 +45,10 @@ def decode(fileobj, elements_per_key):
if len(data[current_key]) >= 1+elements_per_key:
raise LanguageDecodeError("Wrong number of elements per key", fileobj.name, index)
if current_key:
original = current_key[0] # pylint: disable=unsubscriptable-object
translation = line[3:]
if translation and [m.group(1) for m in re.finditer(cfmt, original, flags=re.X)] != [m.group(1) for m in re.finditer(cfmt, translation, flags=re.X)]:
raise LanguageDecodeError("Non-matching formatting string", fileobj.name, index)
data[current_key].extend([translation])
else:
raise LanguageDecodeError("Element before key given", fileobj.name, index)
@ -37,7 +56,7 @@ def decode(fileobj, elements_per_key):
if current_key:
if len(data[current_key]) != 1+elements_per_key:
raise LanguageDecodeError("Wrong number of elements per key", fileobj.name, index)
data[current_key].append(index - 1 if current_context else index)
data[current_key].append(index)
if line in data:
raise LanguageDecodeError("Key defined multiple times: " + line, fileobj.name, index)
data[(line, current_context)] = [index - 1 if current_context else index]

View file

@ -1,54 +0,0 @@
#!/usr/bin/env python3
import os
import sys
import re
import twlang
os.chdir(os.path.dirname(__file__) + "/../..")
# Taken from https://stackoverflow.com/questions/30011379/how-can-i-parse-a-c-format-string-in-python
cfmt = '''
( # start of capture group 1
% # literal "%"
(?: # first option
(?:[-+0 #]{0,5}) # optional flags
(?:\\d+|\\*)? # width
(?:\\.(?:\\d+|\\*))? # precision
(?:h|l|ll|w|I|I32|I64)? # size
[cCdiouxXeEfgGaAnpsSZ] # type
) | # OR
%%) # literal "%%"
'''
total_errors = 0
def print_validation_error(error, filename, error_line):
print(f"Invalid: {translated}")
print(f"- {error} in {filename}:{error_line + 1}\n")
global total_errors
total_errors += 1
if len(sys.argv) > 1:
languages = sys.argv[1:]
else:
languages = twlang.languages()
local = twlang.localizes()
for language in languages:
translations = twlang.translations(language)
for (english, _), (line, translated, _) in translations.items():
if not translated:
continue
# Validate c format strings. Strings that move the formatters are not validated.
if re.findall(cfmt, english, flags=re.X) != re.findall(cfmt, translated, flags=re.X) and not "1$" in translated:
print_validation_error("Non-matching formatting", language, line)
# Check for elipisis
if "" in english and "..." in translated:
print_validation_error("Usage of ... instead of the … character", language, line)
if total_errors:
print(f"Found {total_errors} {'error' if total_errors == 1 else 'errors'} ")
sys.exit(1)

View file

@ -163,19 +163,19 @@
#define CONF_ARCH_ARM 1
#define CONF_ARCH_STRING "arm"
#define CONF_ARCH_ENDIAN_BIG 1
#elif defined(__ARMEL__)
#endif
#if defined(__ARMEL__)
#define CONF_ARCH_ARM 1
#define CONF_ARCH_STRING "arm"
#define CONF_ARCH_ENDIAN_LITTLE 1
#elif defined(__aarch64__) || defined(__arm64__) || defined(__ARM_ARCH_ISA_A64)
#endif
#if defined(__aarch64__) || defined(__arm64__)
#define CONF_ARCH_ARM64 1
#define CONF_ARCH_STRING "arm64"
#if defined(__ARM_BIG_ENDIAN)
#define CONF_ARCH_ENDIAN_BIG 1
#else
#define CONF_ARCH_ENDIAN_LITTLE 1
#endif
#endif
#ifndef CONF_FAMILY_STRING
#define CONF_FAMILY_STRING "unknown"

View file

@ -1236,7 +1236,6 @@ int str_format_int(char *buffer, size_t buffer_size, int value);
template<typename... Args>
int str_format_opt(char *buffer, int buffer_size, const char *format, Args... args)
{
static_assert(sizeof...(args) > 0, "Use str_copy instead of str_format without format arguments");
return str_format(buffer, buffer_size, format, args...);
}

View file

@ -1508,9 +1508,8 @@ protected:
vkInvalidateMappedMemoryRanges(m_VKDevice, 1, &MemRange);
size_t RealFullImageSize = maximum(ImageTotalSize, (size_t)(Height * m_GetPresentedImgDataHelperMappedLayoutPitch));
size_t ExtraRowSize = Width * 4;
if(vDstData.size() < RealFullImageSize + ExtraRowSize)
vDstData.resize(RealFullImageSize + ExtraRowSize);
if(vDstData.size() < RealFullImageSize)
vDstData.resize(RealFullImageSize);
mem_copy(vDstData.data(), pResImageData, RealFullImageSize);
@ -1521,8 +1520,7 @@ protected:
{
size_t OffsetImagePacked = (Y * Width * 4);
size_t OffsetImageUnpacked = (Y * m_GetPresentedImgDataHelperMappedLayoutPitch);
mem_copy(vDstData.data() + RealFullImageSize, vDstData.data() + OffsetImageUnpacked, Width * 4);
mem_copy(vDstData.data() + OffsetImagePacked, vDstData.data() + RealFullImageSize, Width * 4);
mem_copy(vDstData.data() + OffsetImagePacked, vDstData.data() + OffsetImageUnpacked, Width * 4);
}
}

View file

@ -443,9 +443,7 @@ static bool BackendInitGlew(EBackendType BackendType, int &GlewMajor, int &GlewM
#ifdef CONF_GLEW_HAS_CONTEXT_INIT
if(GLEW_OK != glewContextInit())
#else
GLenum InitResult = glewInit();
const char *pVideoDriver = SDL_GetCurrentVideoDriver();
if(GLEW_OK != InitResult && pVideoDriver && !str_comp(pVideoDriver, "wayland") && GLEW_ERROR_NO_GLX_DISPLAY != InitResult)
if(GLEW_OK != glewInit())
#endif
return false;
@ -1021,13 +1019,6 @@ int CGraphicsBackend_SDL_GL::Init(const char *pName, int *pScreen, int *pWidth,
SDL_GetVersion(&Linked);
dbg_msg("sdl", "SDL version %d.%d.%d (compiled = %d.%d.%d)", Linked.major, Linked.minor, Linked.patch,
Compiled.major, Compiled.minor, Compiled.patch);
#if CONF_PLATFORM_LINUX && SDL_VERSION_ATLEAST(2, 0, 22)
// needed to workaround SDL from forcing exclusively X11 if linking against the GLX flavour of GLEW instead of the EGL one
// w/o this on Wayland systems (no XWayland support) SDL's Video subsystem will fail to load (starting from SDL2.30+)
if(Linked.major == 2 && Linked.minor >= 30)
SDL_SetHint(SDL_HINT_VIDEODRIVER, "x11,wayland");
#endif
}
if(!SDL_WasInit(SDL_INIT_VIDEO))

View file

@ -247,7 +247,11 @@ void CClient::SendReady(int Conn)
void CClient::SendMapRequest()
{
dbg_assert(!m_MapdownloadFileTemp, "Map download already in progress");
if(m_MapdownloadFileTemp)
{
io_close(m_MapdownloadFileTemp);
Storage()->RemoveFile(m_aMapdownloadFilenameTemp, IStorage::TYPE_SAVE);
}
m_MapdownloadFileTemp = Storage()->OpenFile(m_aMapdownloadFilenameTemp, IOFLAG_WRITE, IStorage::TYPE_SAVE);
if(IsSixup())
{
@ -652,7 +656,6 @@ void CClient::DisconnectWithReason(const char *pReason)
m_aRconAuthed[0] = 0;
mem_zero(m_aRconUsername, sizeof(m_aRconUsername));
mem_zero(m_aRconPassword, sizeof(m_aRconPassword));
m_MapDetailsPresent = false;
m_ServerSentCapabilities = false;
m_UseTempRconCommands = 0;
m_ExpectedRconCommands = -1;
@ -668,7 +671,22 @@ void CClient::DisconnectWithReason(const char *pReason)
m_CurrentServerCurrentPingTime = -1;
m_CurrentServerNextPingTime = -1;
ResetMapDownload(true);
// disable all downloads
m_MapdownloadChunk = 0;
if(m_pMapdownloadTask)
m_pMapdownloadTask->Abort();
if(m_MapdownloadFileTemp)
{
io_close(m_MapdownloadFileTemp);
Storage()->RemoveFile(m_aMapdownloadFilenameTemp, IStorage::TYPE_SAVE);
}
m_MapdownloadFileTemp = 0;
m_MapdownloadSha256Present = false;
m_MapdownloadSha256 = SHA256_ZEROED;
m_MapdownloadCrc = 0;
m_MapdownloadTotalsize = -1;
m_MapdownloadAmount = 0;
m_MapDetailsPresent = false;
// clear the current server info
mem_zero(&m_CurrentServerInfo, sizeof(m_CurrentServerInfo));
@ -1525,8 +1543,6 @@ void CClient::ProcessServerPacket(CNetChunk *pPacket, int Conn, bool Dummy)
DummyDisconnect(0);
}
ResetMapDownload(true);
SHA256_DIGEST *pMapSha256 = nullptr;
const char *pMapUrl = nullptr;
if(MapDetailsWerePresent && str_comp(m_aMapDetailsName, pMap) == 0 && m_MapDetailsCrc == MapCrc)
@ -1543,6 +1559,12 @@ void CClient::ProcessServerPacket(CNetChunk *pPacket, int Conn, bool Dummy)
}
else
{
if(m_MapdownloadFileTemp)
{
io_close(m_MapdownloadFileTemp);
Storage()->RemoveFile(m_aMapdownloadFilenameTemp, IStorage::TYPE_SAVE);
}
// start map download
FormatMapDownloadFilename(pMap, pMapSha256, MapCrc, false, m_aMapdownloadFilename, sizeof(m_aMapdownloadFilename));
FormatMapDownloadFilename(pMap, pMapSha256, MapCrc, true, m_aMapdownloadFilenameTemp, sizeof(m_aMapdownloadFilenameTemp));
@ -1551,11 +1573,16 @@ void CClient::ProcessServerPacket(CNetChunk *pPacket, int Conn, bool Dummy)
str_format(aBuf, sizeof(aBuf), "starting to download map to '%s'", m_aMapdownloadFilenameTemp);
m_pConsole->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "client/network", aBuf);
m_MapdownloadChunk = 0;
str_copy(m_aMapdownloadName, pMap);
m_MapdownloadSha256Present = (bool)pMapSha256;
m_MapdownloadSha256 = pMapSha256 ? *pMapSha256 : SHA256_ZEROED;
m_MapdownloadCrc = MapCrc;
m_MapdownloadTotalsize = MapSize;
m_MapdownloadAmount = 0;
ResetMapDownload();
if(pMapSha256)
{
@ -2193,44 +2220,24 @@ int CClient::UnpackAndValidateSnapshot(CSnapshot *pFrom, CSnapshot *pTo)
return Builder.Finish(pTo);
}
void CClient::ResetMapDownload(bool ResetActive)
void CClient::ResetMapDownload()
{
if(m_pMapdownloadTask)
{
m_pMapdownloadTask->Abort();
m_pMapdownloadTask = nullptr;
}
if(m_MapdownloadFileTemp)
{
io_close(m_MapdownloadFileTemp);
m_MapdownloadFileTemp = 0;
}
if(Storage()->FileExists(m_aMapdownloadFilenameTemp, IStorage::TYPE_SAVE))
{
Storage()->RemoveFile(m_aMapdownloadFilenameTemp, IStorage::TYPE_SAVE);
}
if(ResetActive)
{
m_MapdownloadChunk = 0;
m_MapdownloadSha256Present = false;
m_MapdownloadSha256 = SHA256_ZEROED;
m_MapdownloadCrc = 0;
m_MapdownloadTotalsize = -1;
m_MapdownloadAmount = 0;
m_aMapdownloadFilename[0] = '\0';
m_aMapdownloadFilenameTemp[0] = '\0';
m_aMapdownloadName[0] = '\0';
m_pMapdownloadTask = NULL;
}
m_MapdownloadFileTemp = 0;
m_MapdownloadAmount = 0;
}
void CClient::FinishMapDownload()
{
m_pConsole->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "client/network", "download complete, loading map");
SHA256_DIGEST *pSha256 = m_MapdownloadSha256Present ? &m_MapdownloadSha256 : nullptr;
int Prev = m_MapdownloadTotalsize;
m_MapdownloadTotalsize = -1;
SHA256_DIGEST *pSha256 = m_MapdownloadSha256Present ? &m_MapdownloadSha256 : 0;
bool FileSuccess = true;
if(Storage()->FileExists(m_aMapdownloadFilename, IStorage::TYPE_SAVE))
@ -2238,26 +2245,36 @@ void CClient::FinishMapDownload()
FileSuccess &= Storage()->RenameFile(m_aMapdownloadFilenameTemp, m_aMapdownloadFilename, IStorage::TYPE_SAVE);
if(!FileSuccess)
{
ResetMapDownload();
char aError[128 + IO_MAX_PATH_LENGTH];
str_format(aError, sizeof(aError), Localize("Could not save downloaded map. Try manually deleting this file: %s"), m_aMapdownloadFilename);
DisconnectWithReason(aError);
return;
}
// load map
const char *pError = LoadMap(m_aMapdownloadName, m_aMapdownloadFilename, pSha256, m_MapdownloadCrc);
if(!pError)
{
ResetMapDownload(true);
ResetMapDownload();
m_pConsole->Print(IConsole::OUTPUT_LEVEL_ADDINFO, "client/network", "loading done");
SendReady(CONN_MAIN);
}
else if(m_pMapdownloadTask) // fallback
{
ResetMapDownload(false);
ResetMapDownload();
m_MapdownloadTotalsize = Prev;
SendMapRequest();
}
else
{
if(m_MapdownloadFileTemp)
{
io_close(m_MapdownloadFileTemp);
m_MapdownloadFileTemp = 0;
Storage()->RemoveFile(m_aMapdownloadFilenameTemp, IStorage::TYPE_SAVE);
}
ResetMapDownload();
DisconnectWithReason(pError);
}
}
@ -2783,7 +2800,7 @@ void CClient::Update()
else if(m_pMapdownloadTask->State() == EHttpState::ERROR || m_pMapdownloadTask->State() == EHttpState::ABORTED)
{
dbg_msg("webdl", "http failed, falling back to gameserver");
ResetMapDownload(false);
ResetMapDownload();
SendMapRequest();
}
}
@ -3316,7 +3333,7 @@ bool CClient::InitNetworkClient(char *pError, size_t ErrorSize)
if(g_Config.m_Bindaddr[0])
str_format(pError, ErrorSize, "Could not open the network client, try changing or unsetting the bindaddr '%s'.", g_Config.m_Bindaddr);
else
str_copy(pError, "Could not open the network client.", ErrorSize);
str_format(pError, ErrorSize, "Could not open the network client.");
return false;
}
}
@ -4357,20 +4374,8 @@ void CClient::RegisterCommands()
// used for server browser update
m_pConsole->Chain("br_filter_string", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_exclude_string", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_full", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_empty", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_spectators", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_friends", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_country", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_country_index", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_pw", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_gametype", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_gametype_strict", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_connecting_players", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_serveraddress", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_unfinished_map", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("br_filter_login", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("add_favorite", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("remove_favorite", ConchainServerBrowserUpdate, this);
m_pConsole->Chain("end_favorite_group", ConchainServerBrowserUpdate, this);

View file

@ -360,7 +360,7 @@ public:
int UnpackAndValidateSnapshot(CSnapshot *pFrom, CSnapshot *pTo);
void ResetMapDownload(bool ResetActive);
void ResetMapDownload();
void FinishMapDownload();
void RequestDDNetInfo() override;

View file

@ -300,7 +300,7 @@ void CGraphics_Threaded::UnloadTexture(CTextureHandle *pIndex)
FreeTextureIndex(pIndex);
}
bool ConvertToRGBA(uint8_t *pDest, const CImageInfo &SrcImage)
static bool ConvertToRGBA(uint8_t *pDest, const CImageInfo &SrcImage)
{
if(SrcImage.m_Format == CImageInfo::FORMAT_RGBA)
{

View file

@ -712,9 +712,35 @@ int CInput::Update()
// handle keys
case SDL_KEYDOWN:
#if defined(CONF_PLATFORM_ANDROID)
if(Event.key.keysym.scancode == KEY_AC_BACK && m_BackButtonReleased)
{
if(m_LastBackPress == -1 || (Now - m_LastBackPress) / (float)time_freq() > 1.0f)
{
m_NumBackPresses = 1;
m_LastBackPress = Now;
}
else
{
m_NumBackPresses++;
if(m_NumBackPresses >= 3)
{
// Quit if the Android back-button was pressed 3 times within 1 second
return 1;
}
}
m_BackButtonReleased = false;
}
#endif
Scancode = TranslateScancode(Event.key);
break;
case SDL_KEYUP:
#if defined(CONF_PLATFORM_ANDROID)
if(Event.key.keysym.scancode == KEY_AC_BACK && !m_BackButtonReleased)
{
m_BackButtonReleased = true;
}
#endif
Action = IInput::FLAG_RELEASE;
Scancode = TranslateScancode(Event.key);
break;

View file

@ -76,6 +76,11 @@ private:
bool m_InputGrabbed;
bool m_MouseFocus;
#if defined(CONF_PLATFORM_ANDROID)
int m_NumBackPresses = 0;
bool m_BackButtonReleased = true;
int64_t m_LastBackPress = -1;
#endif
// IME support
std::string m_CompositionString;

View file

@ -27,6 +27,9 @@
#include <engine/http.h>
#include <engine/storage.h>
static constexpr const char *COMMUNITY_COUNTRY_NONE = "none";
static constexpr const char *COMMUNITY_TYPE_NONE = "None";
class CSortWrap
{
typedef bool (CServerBrowser::*SortFunc)(int, int) const;

View file

@ -234,6 +234,18 @@ public:
class CServerBrowser : public IServerBrowser
{
public:
class CServerEntry
{
public:
int64_t m_RequestTime;
bool m_RequestIgnoreInfo;
int m_GotInfo;
CServerInfo m_Info;
CServerEntry *m_pPrevReq; // request list
CServerEntry *m_pNextReq;
};
CServerBrowser();
virtual ~CServerBrowser();
@ -295,7 +307,7 @@ public:
void OnInit();
void QueueRequest(CServerEntry *pEntry);
CServerEntry *Find(const NETADDR &Addr) override;
CServerEntry *Find(const NETADDR &Addr);
int GetCurrentType() override { return m_ServerlistType; }
bool IsRegistered(const NETADDR &Addr);

View file

@ -228,8 +228,10 @@ int CSound::Init()
return -1;
}
m_MixingRate = g_Config.m_SndRate;
SDL_AudioSpec Format, FormatOut;
Format.freq = g_Config.m_SndRate;
Format.freq = m_MixingRate;
Format.format = AUDIO_S16;
Format.channels = 2;
Format.samples = g_Config.m_SndBufferSize;
@ -237,7 +239,7 @@ int CSound::Init()
Format.userdata = this;
// Open the audio device and start playing sound!
m_Device = SDL_OpenAudioDevice(nullptr, 0, &Format, &FormatOut, SDL_AUDIO_ALLOW_FREQUENCY_CHANGE);
m_Device = SDL_OpenAudioDevice(nullptr, 0, &Format, &FormatOut, 0);
if(m_Device == 0)
{
dbg_msg("sound", "unable to open audio: %s", SDL_GetError());
@ -246,7 +248,6 @@ int CSound::Init()
else
dbg_msg("sound", "sound init successful using audio driver '%s'", SDL_GetCurrentAudioDriver());
m_MixingRate = FormatOut.freq;
m_MaxFrames = FormatOut.samples * 2;
#if defined(CONF_VIDEORECORDER)
m_MaxFrames = maximum<uint32_t>(m_MaxFrames, 1024 * 2); // make the buffer bigger just in case

View file

@ -283,7 +283,6 @@ void CVideo::Pause(bool Pause)
void CVideo::Stop()
{
dbg_assert(!m_Stopped, "Already stopped");
m_Stopped = true;
m_pGraphics->WaitForIdle();
@ -342,6 +341,8 @@ void CVideo::Stop()
pSound->PauseAudioDevice();
delete ms_pCurrentVideo;
pSound->UnpauseAudioDevice();
m_Stopped = true;
}
void CVideo::NextVideoFrameThread()

View file

@ -53,7 +53,7 @@ public:
virtual int GetInteger(unsigned Index) const = 0;
virtual float GetFloat(unsigned Index) const = 0;
virtual const char *GetString(unsigned Index) const = 0;
virtual std::optional<ColorHSLA> GetColor(unsigned Index, bool Light) const = 0;
virtual ColorHSLA GetColor(unsigned Index, bool Light) const = 0;
virtual void RemoveArgument(unsigned Index) = 0;

View file

@ -124,8 +124,6 @@ public:
}
};
bool ConvertToRGBA(uint8_t *pDest, const CImageInfo &SrcImage);
/*
Structure: CVideoMode
*/

View file

@ -12,7 +12,6 @@
#include "kernel.h"
#include "message.h"
#include <engine/shared/jsonwriter.h>
#include <engine/shared/protocol.h>
#include <game/generated/protocol.h>
#include <game/generated/protocol7.h>
@ -254,7 +253,6 @@ public:
virtual void Ban(int ClientId, int Seconds, const char *pReason, bool VerbatimReason) = 0;
virtual void RedirectClient(int ClientId, int Port, bool Verbose = false) = 0;
virtual void ChangeMap(const char *pMap) = 0;
virtual void ReloadMap() = 0;
virtual void DemoRecorder_HandleAutoStart() = 0;
@ -367,10 +365,10 @@ public:
/**
* Used to report custom player info to master servers.
*
* @param pJsonWriter A pointer to a CJsonStringWriter which the custom data will be added to.
* @param aBuf Should be the json key values to add, starting with a ',' beforehand, like: ',"skin": "default", "team": 1'
* @param i The client id.
*/
virtual void OnUpdatePlayerServerInfo(CJsonStringWriter *pJSonWriter, int Id) = 0;
virtual void OnUpdatePlayerServerInfo(char *aBuf, int BufSize, int Id) = 0;
};
extern IGameServer *CreateGameServer();

View file

@ -24,7 +24,6 @@
#include <engine/shared/host_lookup.h>
#include <engine/shared/http.h>
#include <engine/shared/json.h>
#include <engine/shared/jsonwriter.h>
#include <engine/shared/masterserver.h>
#include <engine/shared/netban.h>
#include <engine/shared/network.h>
@ -2316,81 +2315,77 @@ void CServer::UpdateRegisterServerInfo()
int MaxPlayers = maximum(m_NetServer.MaxClients() - maximum(g_Config.m_SvSpectatorSlots, g_Config.m_SvReservedSlots), PlayerCount);
int MaxClients = maximum(m_NetServer.MaxClients() - g_Config.m_SvReservedSlots, ClientCount);
char aName[256];
char aGameType[32];
char aMapName[64];
char aVersion[64];
char aMapSha256[SHA256_MAXSTRSIZE];
sha256_str(m_aCurrentMapSha256[MAP_TYPE_SIX], aMapSha256, sizeof(aMapSha256));
CJsonStringWriter JsonWriter;
JsonWriter.BeginObject();
JsonWriter.WriteAttribute("max_clients");
JsonWriter.WriteIntValue(MaxClients);
JsonWriter.WriteAttribute("max_players");
JsonWriter.WriteIntValue(MaxPlayers);
JsonWriter.WriteAttribute("passworded");
JsonWriter.WriteBoolValue(g_Config.m_Password[0]);
JsonWriter.WriteAttribute("game_type");
JsonWriter.WriteStrValue(GameServer()->GameType());
JsonWriter.WriteAttribute("name");
JsonWriter.WriteStrValue(g_Config.m_SvName);
JsonWriter.WriteAttribute("map");
JsonWriter.BeginObject();
JsonWriter.WriteAttribute("name");
JsonWriter.WriteStrValue(GetMapName());
JsonWriter.WriteAttribute("sha256");
JsonWriter.WriteStrValue(aMapSha256);
JsonWriter.WriteAttribute("size");
JsonWriter.WriteIntValue(m_aCurrentMapSize[MAP_TYPE_SIX]);
JsonWriter.EndObject();
JsonWriter.WriteAttribute("version");
JsonWriter.WriteStrValue(GameServer()->Version());
JsonWriter.WriteAttribute("client_score_kind");
JsonWriter.WriteStrValue("time"); // "points" or "time"
JsonWriter.WriteAttribute("requires_login");
JsonWriter.WriteBoolValue(false);
JsonWriter.WriteAttribute("clients");
JsonWriter.BeginArray();
char aInfo[16384];
str_format(aInfo, sizeof(aInfo),
"{"
"\"max_clients\":%d,"
"\"max_players\":%d,"
"\"passworded\":%s,"
"\"game_type\":\"%s\","
"\"name\":\"%s\","
"\"map\":{"
"\"name\":\"%s\","
"\"sha256\":\"%s\","
"\"size\":%d"
"},"
"\"version\":\"%s\","
"\"client_score_kind\":\"time\","
"\"requires_login\":false,"
"\"clients\":[",
MaxClients,
MaxPlayers,
JsonBool(g_Config.m_Password[0]),
EscapeJson(aGameType, sizeof(aGameType), GameServer()->GameType()),
EscapeJson(aName, sizeof(aName), g_Config.m_SvName),
EscapeJson(aMapName, sizeof(aMapName), m_aCurrentMap),
aMapSha256,
m_aCurrentMapSize[MAP_TYPE_SIX],
EscapeJson(aVersion, sizeof(aVersion), GameServer()->Version()));
bool FirstPlayer = true;
for(int i = 0; i < MAX_CLIENTS; i++)
{
if(m_aClients[i].IncludedInServerInfo())
{
JsonWriter.BeginObject();
char aCName[32];
char aCClan[32];
JsonWriter.WriteAttribute("name");
JsonWriter.WriteStrValue(ClientName(i));
char aExtraPlayerInfo[512];
GameServer()->OnUpdatePlayerServerInfo(aExtraPlayerInfo, sizeof(aExtraPlayerInfo), i);
JsonWriter.WriteAttribute("clan");
JsonWriter.WriteStrValue(ClientClan(i));
JsonWriter.WriteAttribute("country");
JsonWriter.WriteIntValue(m_aClients[i].m_Country);
JsonWriter.WriteAttribute("score");
JsonWriter.WriteIntValue(m_aClients[i].m_Score.value_or(-9999));
JsonWriter.WriteAttribute("is_player");
JsonWriter.WriteBoolValue(GameServer()->IsClientPlayer(i));
GameServer()->OnUpdatePlayerServerInfo(&JsonWriter, i);
JsonWriter.EndObject();
char aClientInfo[1024];
str_format(aClientInfo, sizeof(aClientInfo),
"%s{"
"\"name\":\"%s\","
"\"clan\":\"%s\","
"\"country\":%d,"
"\"score\":%d,"
"\"is_player\":%s"
"%s"
"}",
!FirstPlayer ? "," : "",
EscapeJson(aCName, sizeof(aCName), ClientName(i)),
EscapeJson(aCClan, sizeof(aCClan), ClientClan(i)),
m_aClients[i].m_Country,
m_aClients[i].m_Score.value_or(-9999),
JsonBool(GameServer()->IsClientPlayer(i)),
aExtraPlayerInfo);
str_append(aInfo, aClientInfo);
FirstPlayer = false;
}
}
JsonWriter.EndArray();
JsonWriter.EndObject();
str_append(aInfo, "]}");
m_pRegister->OnNewInfo(JsonWriter.GetOutputString().c_str());
m_pRegister->OnNewInfo(aInfo);
}
void CServer::UpdateServerInfo(bool Resend)
@ -2551,11 +2546,6 @@ void CServer::ChangeMap(const char *pMap)
m_MapReload = str_comp(Config()->m_SvMap, m_aCurrentMap) != 0;
}
void CServer::ReloadMap()
{
m_MapReload = true;
}
int CServer::LoadMap(const char *pMapName)
{
m_MapReload = false;

View file

@ -379,7 +379,6 @@ public:
void ChangeMap(const char *pMap) override;
const char *GetMapName() const override;
void ReloadMap() override;
int LoadMap(const char *pMapName);
void SaveDemo(int ClientId, float Time) override;

View file

@ -295,23 +295,8 @@ public:
NUM_TYPES,
};
class CServerEntry
{
public:
int64_t m_RequestTime;
bool m_RequestIgnoreInfo;
int m_GotInfo;
CServerInfo m_Info;
CServerEntry *m_pPrevReq; // request list
CServerEntry *m_pNextReq;
};
static constexpr const char *COMMUNITY_DDNET = "ddnet";
static constexpr const char *COMMUNITY_NONE = "none";
static constexpr const char *COMMUNITY_COUNTRY_NONE = "none";
static constexpr const char *COMMUNITY_TYPE_NONE = "None";
/**
* Special community value for country/type filters that
* affect all communities.
@ -356,7 +341,6 @@ public:
virtual const IFilterList &TypesFilter() const = 0;
virtual void CleanFilters() = 0;
virtual CServerEntry *Find(const NETADDR &Addr) = 0;
virtual int GetCurrentType() = 0;
virtual const char *GetTutorialServer() = 0;
};

View file

@ -111,29 +111,22 @@ void SIntConfigVariable::ResetToOld()
void SColorConfigVariable::CommandCallback(IConsole::IResult *pResult, void *pUserData)
{
SColorConfigVariable *pData = static_cast<SColorConfigVariable *>(pUserData);
char aBuf[IConsole::CMDLINE_LENGTH + 64];
if(pResult->NumArguments())
{
if(pData->CheckReadOnly())
return;
const auto Color = pResult->GetColor(0, pData->m_Light);
if(Color)
{
const unsigned Value = Color->Pack(pData->m_Light ? 0.5f : 0.0f, pData->m_Alpha);
const ColorHSLA Color = pResult->GetColor(0, pData->m_Light);
const unsigned Value = Color.Pack(pData->m_Light ? 0.5f : 0.0f, pData->m_Alpha);
*pData->m_pVariable = Value;
if(pResult->m_ClientId != IConsole::CLIENT_ID_GAME)
pData->m_OldValue = Value;
}
else
{
str_format(aBuf, sizeof(aBuf), "%s is not a valid color.", pResult->GetString(0));
pData->m_pConsole->Print(IConsole::OUTPUT_LEVEL_STANDARD, "config", aBuf);
}
*pData->m_pVariable = Value;
if(pResult->m_ClientId != IConsole::CLIENT_ID_GAME)
pData->m_OldValue = Value;
}
else
{
char aBuf[256];
str_format(aBuf, sizeof(aBuf), "Value: %u", *pData->m_pVariable);
pData->m_pConsole->Print(IConsole::OUTPUT_LEVEL_STANDARD, "config", aBuf);
@ -500,8 +493,8 @@ void CConfigManager::Con_Toggle(IConsole::IResult *pResult, void *pUserData)
{
SColorConfigVariable *pColorVariable = static_cast<SColorConfigVariable *>(pVariable);
const float Darkest = pColorVariable->m_Light ? 0.5f : 0.0f;
const std::optional<ColorHSLA> Value = *pColorVariable->m_pVariable == pResult->GetColor(1, pColorVariable->m_Light).value_or(ColorHSLA(0, 0, 0)).Pack(Darkest, pColorVariable->m_Alpha) ? pResult->GetColor(2, pColorVariable->m_Light) : pResult->GetColor(1, pColorVariable->m_Light);
pColorVariable->SetValue(Value.value_or(ColorHSLA(0, 0, 0)).Pack(Darkest, pColorVariable->m_Alpha));
const ColorHSLA Value = *pColorVariable->m_pVariable == pResult->GetColor(1, pColorVariable->m_Light).Pack(Darkest, pColorVariable->m_Alpha) ? pResult->GetColor(2, pColorVariable->m_Light) : pResult->GetColor(1, pColorVariable->m_Light);
pColorVariable->SetValue(Value.Pack(Darkest, pColorVariable->m_Alpha));
}
else if(pVariable->m_Type == SConfigVariable::VAR_STRING)
{

View file

@ -105,7 +105,6 @@ MACRO_CONFIG_INT(EdZoomTarget, ed_zoom_target, 0, 0, 1, CFGFLAG_CLIENT | CFGFLAG
MACRO_CONFIG_INT(EdShowkeys, ed_showkeys, 0, 0, 1, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Show pressed keys")
MACRO_CONFIG_INT(EdAlignQuads, ed_align_quads, 1, 0, 1, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Enable/disable quad alignment. When enabled, red lines appear to show how quad/points are aligned and snapped to other quads/points when moving them")
MACRO_CONFIG_INT(EdShowQuadsRect, ed_show_quads_rect, 0, 0, 1, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Show the bounds of the selected quad. In case of multiple quads, it shows the bounds of the englobing rect. Can be helpful when aligning a group of quads")
MACRO_CONFIG_INT(EdAutoMapReload, ed_auto_map_reload, 1, 0, 1, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Run 'hot_reload' on the local server while rcon authed on map save")
MACRO_CONFIG_INT(ClShowWelcome, cl_show_welcome, 1, 0, 1, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Show welcome message indicating the first launch of the client")
MACRO_CONFIG_INT(ClMotdTime, cl_motd_time, 10, 0, 100, CFGFLAG_CLIENT | CFGFLAG_SAVE, "How long to show the server message of the day")
@ -344,9 +343,6 @@ MACRO_CONFIG_INT(BrDemoSort, br_demo_sort, 0, 0, 2, CFGFLAG_SAVE | CFGFLAG_CLIEN
MACRO_CONFIG_INT(BrDemoSortOrder, br_demo_sort_order, 0, 0, 1, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Sorting order in demo browser")
MACRO_CONFIG_INT(BrDemoFetchInfo, br_demo_fetch_info, 0, 0, 1, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Whether to auto fetch demo infos on refresh")
MACRO_CONFIG_INT(GhSort, gh_sort, 1, 0, 2, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Sorting column in ghost list")
MACRO_CONFIG_INT(GhSortOrder, gh_sort_order, 0, 0, 1, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Sorting order in ghost list")
MACRO_CONFIG_INT(SndBufferSize, snd_buffer_size, 512, 128, 32768, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Sound buffer size (may cause delay if large)")
MACRO_CONFIG_INT(SndRate, snd_rate, 48000, 5512, 384000, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Sound mixing rate")
MACRO_CONFIG_INT(SndEnable, snd_enable, 1, 0, 1, CFGFLAG_SAVE | CFGFLAG_CLIENT, "Sound enable")
@ -603,7 +599,7 @@ MACRO_CONFIG_INT(ClOverlayEntities, cl_overlay_entities, 0, 0, 100, CFGFLAG_CLIE
MACRO_CONFIG_INT(ClShowQuads, cl_showquads, 1, 0, 1, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Show quads (only interesting for mappers, or if your system has extremely bad performance)")
MACRO_CONFIG_COL(ClBackgroundColor, cl_background_color, 128, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Background color") // 0 0 128
MACRO_CONFIG_COL(ClBackgroundEntitiesColor, cl_background_entities_color, 128, CFGFLAG_CLIENT | CFGFLAG_SAVE, "Background (entities) color") // 0 0 128
MACRO_CONFIG_STR(ClBackgroundEntities, cl_background_entities, IO_MAX_PATH_LENGTH, "", CFGFLAG_CLIENT | CFGFLAG_SAVE, "Background (entities)")
MACRO_CONFIG_STR(ClBackgroundEntities, cl_background_entities, 100, "", CFGFLAG_CLIENT | CFGFLAG_SAVE, "Background (entities)")
MACRO_CONFIG_STR(ClRunOnJoin, cl_run_on_join, 100, "", CFGFLAG_CLIENT | CFGFLAG_SAVE | CFGFLAG_INSENSITIVE, "Command to run when joining a server")
// menu background map

View file

@ -40,29 +40,22 @@ float CConsole::CResult::GetFloat(unsigned Index) const
return str_tofloat(m_apArgs[Index]);
}
std::optional<ColorHSLA> CConsole::CResult::GetColor(unsigned Index, bool Light) const
ColorHSLA CConsole::CResult::GetColor(unsigned Index, bool Light) const
{
if(Index >= m_NumArgs)
return std::nullopt;
return ColorHSLA(0, 0, 0);
const char *pStr = m_apArgs[Index];
if(str_isallnum(pStr) || ((pStr[0] == '-' || pStr[0] == '+') && str_isallnum(pStr + 1))) // Teeworlds Color (Packed HSL)
{
unsigned long Value = str_toulong_base(pStr, 10);
if(Value == std::numeric_limits<unsigned long>::max())
return std::nullopt;
const ColorHSLA Hsla = ColorHSLA(Value, true);
const ColorHSLA Hsla = ColorHSLA(str_toulong_base(pStr, 10), true);
if(Light)
return Hsla.UnclampLighting();
return Hsla;
}
else if(*pStr == '$') // Hex RGB/RGBA
{
auto ParsedColor = color_parse<ColorRGBA>(pStr + 1);
if(ParsedColor)
return color_cast<ColorHSLA>(ParsedColor.value());
else
return std::nullopt;
return color_cast<ColorHSLA>(color_parse<ColorRGBA>(pStr + 1).value_or(ColorRGBA(0.0f, 0.0f, 0.0f, 1.0f)));
}
else if(!str_comp_nocase(pStr, "red"))
return ColorHSLA(0.0f / 6.0f, 1, .5f);
@ -83,7 +76,7 @@ std::optional<ColorHSLA> CConsole::CResult::GetColor(unsigned Index, bool Light)
else if(!str_comp_nocase(pStr, "black"))
return ColorHSLA(0, 0, 0);
return std::nullopt;
return ColorHSLA(0, 0, 0);
}
const IConsole::CCommandInfo *CConsole::CCommand::NextCommandInfo(int AccessLevel, int FlagMask) const
@ -136,12 +129,12 @@ int CConsole::ParseStart(CResult *pResult, const char *pString, int Length)
return 0;
}
int CConsole::ParseArgs(CResult *pResult, const char *pFormat, bool IsColor)
int CConsole::ParseArgs(CResult *pResult, const char *pFormat)
{
char Command = *pFormat;
char *pStr;
int Optional = 0;
int Error = PARSEARGS_OK;
int Error = 0;
pResult->ResetVictim();
@ -162,7 +155,7 @@ int CConsole::ParseArgs(CResult *pResult, const char *pFormat, bool IsColor)
{
if(!Optional)
{
Error = PARSEARGS_MISSING_VALUE;
Error = 1;
break;
}
@ -198,7 +191,7 @@ int CConsole::ParseArgs(CResult *pResult, const char *pFormat, bool IsColor)
pStr++; // skip due to escape
}
else if(pStr[0] == 0)
return PARSEARGS_MISSING_VALUE; // return error
return 1; // return error
*pDst = *pStr;
pDst++;
@ -222,7 +215,13 @@ int CConsole::ParseArgs(CResult *pResult, const char *pFormat, bool IsColor)
if(Command == 'r') // rest of the string
break;
else if(Command == 'v' || Command == 'i' || Command == 'f' || Command == 's')
else if(Command == 'v') // validate victim
pStr = str_skip_to_whitespace(pStr);
else if(Command == 'i') // validate int
pStr = str_skip_to_whitespace(pStr);
else if(Command == 'f') // validate float
pStr = str_skip_to_whitespace(pStr);
else if(Command == 's') // validate string
pStr = str_skip_to_whitespace(pStr);
if(pStr[0] != 0) // check for end of string
@ -231,32 +230,6 @@ int CConsole::ParseArgs(CResult *pResult, const char *pFormat, bool IsColor)
pStr++;
}
// validate args
if(Command == 'i')
{
// don't validate colors here
if(!IsColor)
{
int Value;
if(!str_toint(pResult->GetString(pResult->NumArguments() - 1), &Value) ||
Value == std::numeric_limits<int>::max() || Value == std::numeric_limits<int>::min())
{
Error = PARSEARGS_INVALID_INTEGER;
break;
}
}
}
else if(Command == 'f')
{
float Value;
if(!str_tofloat(pResult->GetString(pResult->NumArguments() - 1), &Value) ||
Value == std::numeric_limits<float>::max() || Value == std::numeric_limits<float>::min())
{
Error = PARSEARGS_INVALID_FLOAT;
break;
}
}
if(pVictim)
{
pResult->SetVictim(pVictim);
@ -341,7 +314,7 @@ void CConsole::Print(int Level, const char *pFrom, const char *pStr, ColorRGBA P
{
LEVEL LogLevel = IConsole::ToLogLevel(Level);
// if console colors are not enabled or if the color is pure white, use default terminal color
if(g_Config.m_ConsoleEnableColors && PrintColor != gs_ConsoleDefaultColor)
if(g_Config.m_ConsoleEnableColors && mem_comp(&PrintColor, &gs_ConsoleDefaultColor, sizeof(ColorRGBA)) != 0)
{
log_log_color(LogLevel, ColorToLogColor(PrintColor), pFrom, "%s", pStr);
}
@ -514,15 +487,10 @@ void CConsole::ExecuteLineStroked(int Stroke, const char *pStr, int ClientId, bo
if(Stroke || IsStrokeCommand)
{
if(int Error = ParseArgs(&Result, pCommand->m_pParams, pCommand->m_pfnCallback == &SColorConfigVariable::CommandCallback))
if(ParseArgs(&Result, pCommand->m_pParams))
{
char aBuf[CMDLINE_LENGTH + 64];
if(Error == PARSEARGS_INVALID_INTEGER)
str_format(aBuf, sizeof(aBuf), "%s is not a valid integer.", Result.GetString(Result.NumArguments() - 1));
else if(Error == PARSEARGS_INVALID_FLOAT)
str_format(aBuf, sizeof(aBuf), "%s is not a valid decimal number.", Result.GetString(Result.NumArguments() - 1));
else
str_format(aBuf, sizeof(aBuf), "Invalid arguments. Usage: %s %s", pCommand->m_pName, pCommand->m_pParams);
char aBuf[TEMPCMD_NAME_LENGTH + TEMPCMD_PARAMS_LENGTH + 32];
str_format(aBuf, sizeof(aBuf), "Invalid arguments. Usage: %s %s", pCommand->m_pName, pCommand->m_pParams);
Print(OUTPUT_LEVEL_STANDARD, "chatresp", aBuf);
}
else if(m_StoreCommands && pCommand->m_Flags & CFGFLAG_STORE)

View file

@ -115,7 +115,7 @@ class CConsole : public IConsole
const char *GetString(unsigned Index) const override;
int GetInteger(unsigned Index) const override;
float GetFloat(unsigned Index) const override;
std::optional<ColorHSLA> GetColor(unsigned Index, bool Light) const override;
ColorHSLA GetColor(unsigned Index, bool Light) const override;
void RemoveArgument(unsigned Index) override
{
@ -144,16 +144,7 @@ class CConsole : public IConsole
};
int ParseStart(CResult *pResult, const char *pString, int Length);
enum
{
PARSEARGS_OK = 0,
PARSEARGS_MISSING_VALUE,
PARSEARGS_INVALID_INTEGER,
PARSEARGS_INVALID_FLOAT,
};
int ParseArgs(CResult *pResult, const char *pFormat, bool IsColor = false);
int ParseArgs(CResult *pResult, const char *pFormat);
/*
this function will set pFormat to the next parameter (i,s,r,v,?) it contains and

View file

@ -490,7 +490,8 @@ void CNetBan::ConBans(IConsole::IResult *pResult, void *pUser)
if(NumBans == 0)
{
pThis->Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "net_ban", "The ban list is empty.");
str_format(aMsg, sizeof(aMsg), "The ban list is empty.");
pThis->Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "net_ban", aMsg);
return;
}

View file

@ -4,16 +4,6 @@
#include "protocolglue.h"
int GameFlags_ClampToSix(int Flags)
{
int Six = 0;
if(Flags & GAMEFLAG_TEAMS)
Six |= GAMEFLAG_TEAMS;
if(Flags & GAMEFLAG_FLAGS)
Six |= GAMEFLAG_FLAGS;
return Six;
}
int PlayerFlags_SevenToSix(int Flags)
{
int Six = 0;

View file

@ -1,7 +1,6 @@
#ifndef ENGINE_SHARED_PROTOCOLGLUE_H
#define ENGINE_SHARED_PROTOCOLGLUE_H
int GameFlags_ClampToSix(int Flags);
int PlayerFlags_SevenToSix(int Flags);
int PlayerFlags_SixToSeven(int Flags);
void PickupType_SevenToSix(int Type7, int &Type6, int &SubType6);

View file

@ -96,7 +96,6 @@ public:
CreateFolder("mapres", TYPE_SAVE);
CreateFolder("downloadedmaps", TYPE_SAVE);
CreateFolder("skins", TYPE_SAVE);
CreateFolder("skins7", TYPE_SAVE);
CreateFolder("downloadedskins", TYPE_SAVE);
CreateFolder("themes", TYPE_SAVE);
CreateFolder("communityicons", TYPE_SAVE);

View file

@ -93,7 +93,6 @@ MAYBE_UNUSED static const char *FONT_ICON_EARTH_AMERICAS = "\xEF\x95\xBD";
MAYBE_UNUSED static const char *FONT_ICON_NETWORK_WIRED = "\xEF\x9B\xBF";
MAYBE_UNUSED static const char *FONT_ICON_LIST_UL = "\xEF\x83\x8A";
MAYBE_UNUSED static const char *FONT_ICON_INFO = "\xEF\x84\xA9";
MAYBE_UNUSED static const char *FONT_ICON_TERMINAL = "\xEF\x84\xA0";
MAYBE_UNUSED static const char *FONT_ICON_SLASH = "\xEF\x9C\x95";
MAYBE_UNUSED static const char *FONT_ICON_PLAY = "\xEF\x81\x8B";

View file

@ -992,11 +992,7 @@ void CChat::OnPrepareLines(float y)
const char *pText = Line.m_aText;
if(Config()->m_ClStreamerMode && Line.m_ClientId == SERVER_MSG)
{
if(str_startswith(Line.m_aText, "Team save in progress. You'll be able to load with '/load ") && str_endswith(Line.m_aText, "'"))
{
pText = "Team save in progress. You'll be able to load with '/load ***'";
}
else if(str_startswith(Line.m_aText, "Team save in progress. You'll be able to load with '/load") && str_endswith(Line.m_aText, "if it fails"))
if(str_startswith(Line.m_aText, "Team save in progress. You'll be able to load with '/load") && str_endswith(Line.m_aText, "if it fails"))
{
pText = "Team save in progress. You'll be able to load with '/load ***' if save is successful or with '/load *** *** ***' if it fails";
}

View file

@ -377,10 +377,6 @@ bool CGameConsole::CInstance::OnInput(const IInput::CEvent &Event)
{
bool Handled = false;
// Don't allow input while the console is opening/closing
if(m_pGameConsole->m_ConsoleState == CONSOLE_OPENING || m_pGameConsole->m_ConsoleState == CONSOLE_CLOSING)
return Handled;
auto &&SelectNextSearchMatch = [&](int Direction) {
if(!m_vSearchMatches.empty())
{

View file

@ -160,6 +160,8 @@ class CGameConsole : public CComponent
static const ColorRGBA ms_SearchHighlightColor;
static const ColorRGBA ms_SearchSelectedColor;
void Toggle(int Type);
static void PossibleCommandsRenderCallback(int Index, const char *pStr, void *pUser);
static void ConToggleLocalConsole(IConsole::IResult *pResult, void *pUserData);
static void ConToggleRemoteConsole(IConsole::IResult *pResult, void *pUserData);
@ -194,7 +196,6 @@ public:
virtual bool OnInput(const IInput::CEvent &Event) override;
void Prompt(char (&aPrompt)[32]);
void Toggle(int Type);
bool IsClosed() { return m_ConsoleState == CONSOLE_CLOSED; }
};
#endif

View file

@ -41,7 +41,6 @@ void CEmoticon::OnReset()
m_Active = false;
m_SelectedEmote = -1;
m_SelectedEyeEmote = -1;
m_TouchPressedOutside = false;
}
void CEmoticon::OnRelease()
@ -59,16 +58,6 @@ bool CEmoticon::OnCursorMove(float x, float y, IInput::ECursorType CursorType)
return true;
}
bool CEmoticon::OnInput(const IInput::CEvent &Event)
{
if(IsActive() && Event.m_Flags & IInput::FLAG_PRESS && Event.m_Key == KEY_ESCAPE)
{
OnRelease();
return true;
}
return false;
}
void CEmoticon::OnRender()
{
if(Client()->State() != IClient::STATE_ONLINE && Client()->State() != IClient::STATE_DEMOPLAYBACK)
@ -76,13 +65,6 @@ void CEmoticon::OnRender()
if(!m_Active)
{
if(m_TouchPressedOutside)
{
m_SelectedEmote = -1;
m_SelectedEyeEmote = -1;
m_TouchPressedOutside = false;
}
if(m_WasActive && m_SelectedEmote != -1)
Emote(m_SelectedEmote);
if(m_WasActive && m_SelectedEyeEmote != -1)
@ -100,29 +82,6 @@ void CEmoticon::OnRender()
m_WasActive = true;
const CUIRect Screen = *Ui()->Screen();
const bool WasTouchPressed = m_TouchState.m_AnyPressed;
Ui()->UpdateTouchState(m_TouchState);
if(m_TouchState.m_AnyPressed)
{
const vec2 TouchPos = (m_TouchState.m_PrimaryPosition - vec2(0.5f, 0.5f)) * Screen.Size();
const float TouchCenterDistance = length(TouchPos);
if(TouchCenterDistance <= 170.0f)
{
m_SelectorMouse = TouchPos;
}
else if(TouchCenterDistance > 190.0f)
{
m_TouchPressedOutside = true;
}
}
else if(WasTouchPressed)
{
m_Active = false;
return;
}
if(length(m_SelectorMouse) > 170.0f)
m_SelectorMouse = normalize(m_SelectorMouse) * 170.0f;
@ -137,7 +96,7 @@ void CEmoticon::OnRender()
else if(length(m_SelectorMouse) > 40.0f)
m_SelectedEyeEmote = (int)(SelectedAngle / (2 * pi) * NUM_EMOTES);
const vec2 ScreenCenter = Screen.Center();
CUIRect Screen = *Ui()->Screen();
Ui()->MapScreen();
@ -146,22 +105,26 @@ void CEmoticon::OnRender()
Graphics()->TextureClear();
Graphics()->QuadsBegin();
Graphics()->SetColor(0, 0, 0, 0.3f);
Graphics()->DrawCircle(ScreenCenter.x, ScreenCenter.y, 190.0f, 64);
Graphics()->DrawCircle(Screen.w / 2, Screen.h / 2, 190.0f, 64);
Graphics()->QuadsEnd();
Graphics()->WrapClamp();
for(int Emote = 0; Emote < NUM_EMOTICONS; Emote++)
for(int i = 0; i < NUM_EMOTICONS; i++)
{
float Angle = 2 * pi * Emote / NUM_EMOTICONS;
float Angle = 2 * pi * i / NUM_EMOTICONS;
if(Angle > pi)
Angle -= 2 * pi;
Graphics()->TextureSet(GameClient()->m_EmoticonsSkin.m_aSpriteEmoticons[Emote]);
bool Selected = m_SelectedEmote == i;
float Size = Selected ? 80.0f : 50.0f;
Graphics()->TextureSet(GameClient()->m_EmoticonsSkin.m_aSpriteEmoticons[i]);
Graphics()->QuadsSetSubset(0, 0, 1, 1);
Graphics()->QuadsBegin();
const vec2 Nudge = direction(Angle) * 150.0f;
const float Size = m_SelectedEmote == Emote ? 80.0f : 50.0f;
IGraphics::CQuadItem QuadItem(ScreenCenter.x + Nudge.x, ScreenCenter.y + Nudge.y, Size, Size);
IGraphics::CQuadItem QuadItem(Screen.w / 2 + Nudge.x, Screen.h / 2 + Nudge.y, Size, Size);
Graphics()->QuadsDraw(&QuadItem, 1);
Graphics()->QuadsEnd();
}
@ -172,32 +135,34 @@ void CEmoticon::OnRender()
Graphics()->TextureClear();
Graphics()->QuadsBegin();
Graphics()->SetColor(1.0, 1.0, 1.0, 0.3f);
Graphics()->DrawCircle(ScreenCenter.x, ScreenCenter.y, 100.0f, 64);
Graphics()->DrawCircle(Screen.w / 2, Screen.h / 2, 100.0f, 64);
Graphics()->QuadsEnd();
CTeeRenderInfo TeeInfo = m_pClient->m_aClients[m_pClient->m_aLocalIds[g_Config.m_ClDummy]].m_RenderInfo;
for(int Emote = 0; Emote < NUM_EMOTES; Emote++)
for(int i = 0; i < NUM_EMOTES; i++)
{
float Angle = 2 * pi * Emote / NUM_EMOTES;
float Angle = 2 * pi * i / NUM_EMOTES;
if(Angle > pi)
Angle -= 2 * pi;
const bool Selected = m_SelectedEyeEmote == i;
const vec2 Nudge = direction(Angle) * 70.0f;
TeeInfo.m_Size = m_SelectedEyeEmote == Emote ? 64.0f : 48.0f;
RenderTools()->RenderTee(CAnimState::GetIdle(), &TeeInfo, Emote, vec2(-1, 0), ScreenCenter + Nudge);
TeeInfo.m_Size = Selected ? 64.0f : 48.0f;
RenderTools()->RenderTee(CAnimState::GetIdle(), &TeeInfo, i, vec2(-1, 0), vec2(Screen.w / 2 + Nudge.x, Screen.h / 2 + Nudge.y));
}
Graphics()->TextureClear();
Graphics()->QuadsBegin();
Graphics()->SetColor(0, 0, 0, 0.3f);
Graphics()->DrawCircle(ScreenCenter.x, ScreenCenter.y, 30.0f, 64);
Graphics()->DrawCircle(Screen.w / 2, Screen.h / 2, 30.0f, 64);
Graphics()->QuadsEnd();
}
else
m_SelectedEyeEmote = -1;
RenderTools()->RenderCursor(ScreenCenter + m_SelectorMouse, 24.0f);
RenderTools()->RenderCursor(m_SelectorMouse + vec2(Screen.w, Screen.h) / 2, 24.0f);
}
void CEmoticon::Emote(int Emoticon)

View file

@ -4,9 +4,7 @@
#define GAME_CLIENT_COMPONENTS_EMOTICON_H
#include <base/vmath.h>
#include <engine/console.h>
#include <game/client/component.h>
#include <game/client/ui.h>
class CEmoticon : public CComponent
{
@ -17,9 +15,6 @@ class CEmoticon : public CComponent
int m_SelectedEmote;
int m_SelectedEyeEmote;
CUi::CTouchState m_TouchState;
bool m_TouchPressedOutside;
static void ConKeyEmoticon(IConsole::IResult *pResult, void *pUserData);
static void ConEmote(IConsole::IResult *pResult, void *pUserData);
@ -32,12 +27,9 @@ public:
virtual void OnRender() override;
virtual void OnRelease() override;
virtual bool OnCursorMove(float x, float y, IInput::ECursorType CursorType) override;
virtual bool OnInput(const IInput::CEvent &Event) override;
void Emote(int Emoticon);
void EyeEmote(int EyeEmote);
bool IsActive() const { return m_Active; }
};
#endif

View file

@ -1693,7 +1693,8 @@ void CHud::RenderRecord()
if(m_ServerRecord > 0.0f)
{
char aBuf[64];
TextRender()->Text(5, 75, 6, Localize("Server best:"), -1.0f);
str_format(aBuf, sizeof(aBuf), Localize("Server best:"));
TextRender()->Text(5, 75, 6, aBuf, -1.0f);
char aTime[32];
str_time_float(m_ServerRecord, TIME_HOURS_CENTISECS, aTime, sizeof(aTime));
str_format(aBuf, sizeof(aBuf), "%s%s", m_ServerRecord > 3600 ? "" : " ", aTime);
@ -1704,7 +1705,8 @@ void CHud::RenderRecord()
if(PlayerRecord > 0.0f)
{
char aBuf[64];
TextRender()->Text(5, 82, 6, Localize("Personal best:"), -1.0f);
str_format(aBuf, sizeof(aBuf), Localize("Personal best:"));
TextRender()->Text(5, 82, 6, aBuf, -1.0f);
char aTime[32];
str_time_float(PlayerRecord, TIME_HOURS_CENTISECS, aTime, sizeof(aTime));
str_format(aBuf, sizeof(aBuf), "%s%s", PlayerRecord > 3600 ? "" : " ", aTime);

View file

@ -902,11 +902,16 @@ void CMenus::ConchainBackgroundEntities(IConsole::IResult *pResult, void *pUserD
if(pResult->NumArguments())
{
CMenus *pSelf = (CMenus *)pUserData;
if(str_comp(g_Config.m_ClBackgroundEntities, pSelf->m_pClient->m_Background.MapName()) != 0)
pSelf->m_pClient->m_Background.LoadBackground();
pSelf->UpdateBackgroundEntities();
}
}
void CMenus::UpdateBackgroundEntities()
{
if(str_comp(g_Config.m_ClBackgroundEntities, m_pClient->m_Background.MapName()) != 0)
m_pClient->m_Background.LoadBackground();
}
void CMenus::ConchainUpdateMusicState(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData)
{
pfnCallback(pResult, pCallbackUserData);
@ -1208,7 +1213,7 @@ void CMenus::RenderPopupFullscreen(CUIRect Screen)
pButtonText = Localize("Ok");
if(Client()->ReconnectTime() > 0)
{
str_format(aBuf, sizeof(aBuf), Localize("Reconnect in %d sec"), (int)((Client()->ReconnectTime() - time_get()) / time_freq()) + 1);
str_format(aBuf, sizeof(aBuf), Localize("Reconnect in %d sec"), (int)((Client()->ReconnectTime() - time_get()) / time_freq()));
pTitle = Client()->ErrorString();
pExtraText = aBuf;
pButtonText = Localize("Abort");
@ -1282,11 +1287,6 @@ void CMenus::RenderPopupFullscreen(CUIRect Screen)
pButtonText = m_aMessageButton;
TopAlign = true;
}
else if(m_Popup == POPUP_SAVE_SKIN)
{
pTitle = Localize("Save skin");
pExtraText = Localize("Are you sure you want to save your skin? If a skin with this name already exists, it will be replaced.");
}
CUIRect Box, Part;
Box = Screen;
@ -1399,7 +1399,7 @@ void CMenus::RenderPopupFullscreen(CUIRect Screen)
}
else if(m_Popup == POPUP_PASSWORD)
{
CUIRect AddressLabel, Address, Icon, Name, Label, TextBox, TryAgain, Abort;
CUIRect Label, TextBox, TryAgain, Abort;
Box.HSplitBottom(20.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
@ -1414,14 +1414,15 @@ void CMenus::RenderPopupFullscreen(CUIRect Screen)
if(DoButton_Menu(&s_ButtonAbort, Localize("Abort"), 0, &Abort) || Ui()->ConsumeHotkey(CUi::HOTKEY_ESCAPE))
m_Popup = POPUP_NONE;
char aAddr[NETADDR_MAXSTRSIZE];
net_addr_str(&Client()->ServerAddress(), aAddr, sizeof(aAddr), true);
static CButtonContainer s_ButtonTryAgain;
if(DoButton_Menu(&s_ButtonTryAgain, Localize("Try again"), 0, &TryAgain) || Ui()->ConsumeHotkey(CUi::HOTKEY_ENTER))
{
char aAddr[NETADDR_MAXSTRSIZE];
net_addr_str(&Client()->ServerAddress(), aAddr, sizeof(aAddr), true);
Client()->Connect(aAddr, g_Config.m_Password);
}
Box.HSplitBottom(32.f, &Box, &Part);
Box.HSplitBottom(60.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
Part.VSplitLeft(60.0f, 0, &Label);
@ -1430,35 +1431,6 @@ void CMenus::RenderPopupFullscreen(CUIRect Screen)
TextBox.VSplitRight(60.0f, &TextBox, 0);
Ui()->DoLabel(&Label, Localize("Password"), 18.0f, TEXTALIGN_ML);
Ui()->DoClearableEditBox(&m_PasswordInput, &TextBox, 12.0f);
Box.HSplitBottom(32.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
Part.VSplitLeft(60.0f, 0, &AddressLabel);
AddressLabel.VSplitLeft(100.0f, 0, &Address);
Address.VSplitLeft(20.0f, 0, &Address);
Ui()->DoLabel(&AddressLabel, Localize("Address"), 18.0f, TEXTALIGN_ML);
Ui()->DoLabel(&Address, aAddr, 18.0f, TEXTALIGN_ML);
Box.HSplitBottom(32.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
const CServerBrowser::CServerEntry *pEntry = ServerBrowser()->Find(Client()->ServerAddress());
if(pEntry != nullptr && pEntry->m_GotInfo)
{
Part.VSplitLeft(60.0f, 0, &Icon);
Icon.VSplitLeft(100.0f, 0, &Name);
Icon.VSplitLeft(80.0f, &Icon, 0);
Name.VSplitLeft(20.0f, 0, &Name);
const SCommunityIcon *pIcon = FindCommunityIcon(pEntry->m_Info.m_aCommunityId);
if(pIcon != nullptr)
RenderCommunityIcon(pIcon, Icon, true);
else
Ui()->DoLabel(&Icon, Localize("Name"), 18.0f, TEXTALIGN_ML);
Ui()->DoLabel(&Name, pEntry->m_Info.m_aName, 18.0f, TEXTALIGN_ML);
}
}
else if(m_Popup == POPUP_LANGUAGE)
{
@ -1761,52 +1733,6 @@ void CMenus::RenderPopupFullscreen(CUIRect Screen)
SetActive(false);
}
}
else if(m_Popup == POPUP_SAVE_SKIN)
{
CUIRect Label, TextBox, Yes, No;
Box.HSplitBottom(20.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
Part.VMargin(80.0f, &Part);
Part.VSplitMid(&No, &Yes);
Yes.VMargin(20.0f, &Yes);
No.VMargin(20.0f, &No);
static CButtonContainer s_ButtonNo;
if(DoButton_Menu(&s_ButtonNo, Localize("No"), 0, &No) || Ui()->ConsumeHotkey(CUi::HOTKEY_ESCAPE))
m_Popup = POPUP_NONE;
static CButtonContainer s_ButtonYes;
if(DoButton_Menu(&s_ButtonYes, Localize("Yes"), m_SkinNameInput.IsEmpty() ? 1 : 0, &Yes) || Ui()->ConsumeHotkey(CUi::HOTKEY_ENTER))
{
if(m_SkinNameInput.GetLength())
{
if(m_SkinNameInput.GetString()[0] != 'x' && m_SkinNameInput.GetString()[1] != '_')
{
if(m_pClient->m_Skins7.SaveSkinfile(m_SkinNameInput.GetString(), m_Dummy))
{
m_Popup = POPUP_NONE;
m_SkinListNeedsUpdate = true;
}
else
PopupMessage(Localize("Error"), Localize("Unable to save the skin"), Localize("Ok"), POPUP_SAVE_SKIN);
}
else
PopupMessage(Localize("Error"), Localize("Unable to save the skin with a reserved name"), Localize("Ok"), POPUP_SAVE_SKIN);
}
}
Box.HSplitBottom(60.f, &Box, &Part);
Box.HSplitBottom(24.f, &Box, &Part);
Part.VMargin(60.0f, &Label);
Label.VSplitLeft(100.0f, &Label, &TextBox);
TextBox.VSplitLeft(20.0f, nullptr, &TextBox);
Ui()->DoLabel(&Label, Localize("Name"), 18.0f, TEXTALIGN_ML);
Ui()->DoClearableEditBox(&m_SkinNameInput, &TextBox, 12.0f);
}
else
{
Box.HSplitBottom(20.f, &Box, &Part);

View file

@ -445,6 +445,7 @@ protected:
void RenderMenubar(CUIRect Box, IClient::EClientState ClientState);
void RenderNews(CUIRect MainView);
static void ConchainBackgroundEntities(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
void UpdateBackgroundEntities();
static void ConchainUpdateMusicState(IConsole::IResult *pResult, void *pUserData, IConsole::FCommandCallback pfnCallback, void *pCallbackUserData);
void UpdateMusicState();
@ -606,36 +607,6 @@ protected:
void RenderSettings(CUIRect MainView);
void RenderSettingsCustom(CUIRect MainView);
class CMapListItem
{
public:
char m_aFilename[IO_MAX_PATH_LENGTH];
bool m_IsDirectory;
};
class CPopupMapPickerContext
{
public:
std::vector<CMapListItem> m_vMaps;
char m_aCurrentMapFolder[IO_MAX_PATH_LENGTH] = "";
static int MapListFetchCallback(const CFsFileInfo *pInfo, int IsDir, int StorageType, void *pUser);
void MapListPopulate();
CMenus *m_pMenus;
int m_Selection;
};
static bool CompareFilenameAscending(const CMapListItem Lhs, const CMapListItem Rhs)
{
if(str_comp(Lhs.m_aFilename, "..") == 0)
return true;
if(str_comp(Rhs.m_aFilename, "..") == 0)
return false;
if(Lhs.m_IsDirectory != Rhs.m_IsDirectory)
return Lhs.m_IsDirectory;
return str_comp_filenames(Lhs.m_aFilename, Rhs.m_aFilename) < 0;
}
static CUi::EPopupMenuFunctionResult PopupMapPicker(void *pContext, CUIRect View, bool Active);
void SetNeedSendInfo();
void SetActive(bool Active);
void UpdateColors();
@ -768,14 +739,6 @@ public:
bool HasFile() const { return m_aFilename[0]; }
};
enum
{
GHOST_SORT_NONE = -1,
GHOST_SORT_NAME,
GHOST_SORT_TIME,
GHOST_SORT_DATE,
};
std::vector<CGhostItem> m_vGhosts;
std::chrono::nanoseconds m_GhostPopulateStartTime{0};
@ -784,7 +747,6 @@ public:
CGhostItem *GetOwnGhost();
void UpdateOwnGhost(CGhostItem Item);
void DeleteGhostItem(int Index);
void SortGhostlist();
bool CanDisplayWarning() const;
@ -811,7 +773,6 @@ public:
POPUP_QUIT,
POPUP_RESTART,
POPUP_WARNING,
POPUP_SAVE_SKIN,
// demo player states
DEMOPLAYER_NONE = 0,
@ -830,7 +791,7 @@ private:
// found in menus_settings.cpp
void RenderSettingsDDNet(CUIRect MainView);
void RenderSettingsAppearance(CUIRect MainView);
bool RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alpha, float DarkestLight);
ColorHSLA RenderHSLScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alpha = false, bool ClampedLight = false);
CServerProcess m_ServerProcess;
};

View file

@ -869,14 +869,11 @@ void CMenus::RenderServerbrowserDDNetFilter(CUIRect View,
{
if(Click == 1)
{
// Left click: when all are active, only activate one and none
// Left click: when all are active, only activate one
for(int j = 0; j < MaxItems; ++j)
{
if(const char *pItemName = GetItemName(j);
j != ItemIndex &&
!((&Filter == &ServerBrowser()->CountriesFilter() && str_comp(pItemName, IServerBrowser::COMMUNITY_COUNTRY_NONE) == 0) ||
(&Filter == &ServerBrowser()->TypesFilter() && str_comp(pItemName, IServerBrowser::COMMUNITY_TYPE_NONE) == 0)))
Filter.Add(pItemName);
if(j != ItemIndex)
Filter.Add(GetItemName(j));
}
}
else if(Click == 2)
@ -893,10 +890,7 @@ void CMenus::RenderServerbrowserDDNetFilter(CUIRect View,
bool AllFilteredExceptUs = true;
for(int j = 0; j < MaxItems; ++j)
{
if(const char *pItemName = GetItemName(j);
j != ItemIndex && !Filter.Filtered(pItemName) &&
!((&Filter == &ServerBrowser()->CountriesFilter() && str_comp(pItemName, IServerBrowser::COMMUNITY_COUNTRY_NONE) == 0) ||
(&Filter == &ServerBrowser()->TypesFilter() && str_comp(pItemName, IServerBrowser::COMMUNITY_TYPE_NONE) == 0)))
if(j != ItemIndex && !Filter.Filtered(GetItemName(j)))
{
AllFilteredExceptUs = false;
break;
@ -904,7 +898,7 @@ void CMenus::RenderServerbrowserDDNetFilter(CUIRect View,
}
// When last one is removed, re-enable all currently selectable items.
// Don't use Clear, to avoid enabling also currently unselectable items.
if(AllFilteredExceptUs && Active)
if(AllFilteredExceptUs)
{
for(int j = 0; j < MaxItems; ++j)
{

View file

@ -175,12 +175,12 @@ void CMenus::RenderDemoPlayer(CUIRect MainView)
// increase/decrease speed
if(!Input()->ModifierIsPressed() && !Input()->ShiftIsPressed() && !Input()->AltIsPressed())
{
if(Input()->KeyPress(KEY_UP) || (m_MenuActive && Input()->KeyPress(KEY_MOUSE_WHEEL_UP)))
if(Input()->KeyPress(KEY_MOUSE_WHEEL_UP) || Input()->KeyPress(KEY_UP))
{
DemoPlayer()->AdjustSpeedIndex(+1);
UpdateLastSpeedChange();
}
else if(Input()->KeyPress(KEY_DOWN) || (m_MenuActive && Input()->KeyPress(KEY_MOUSE_WHEEL_DOWN)))
else if(Input()->KeyPress(KEY_MOUSE_WHEEL_DOWN) || Input()->KeyPress(KEY_DOWN))
{
DemoPlayer()->AdjustSpeedIndex(-1);
UpdateLastSpeedChange();

View file

@ -69,14 +69,14 @@ void CMenus::RenderGame(CUIRect MainView)
}
}
ButtonBar.VSplitRight(5.0f, &ButtonBar, nullptr);
ButtonBar.VSplitRight(5.0f, &ButtonBar, 0);
ButtonBar.VSplitRight(170.0f, &ButtonBar, &Button);
static CButtonContainer s_DummyButton;
if(!Client()->DummyAllowed())
{
DoButton_Menu(&s_DummyButton, Localize("Connect Dummy"), 1, &Button);
GameClient()->m_Tooltips.DoToolTip(&s_DummyButton, &Button, Localize("Dummy is not allowed on this server"));
GameClient()->m_Tooltips.DoToolTip(&s_DummyButton, &Button, Localize("Dummy is not allowed on this server."));
}
else if(Client()->DummyConnectingDelayed())
{
@ -107,8 +107,9 @@ void CMenus::RenderGame(CUIRect MainView)
}
}
ButtonBar.VSplitRight(5.0f, &ButtonBar, nullptr);
ButtonBar.VSplitRight(5.0f, &ButtonBar, 0);
ButtonBar.VSplitRight(140.0f, &ButtonBar, &Button);
static CButtonContainer s_DemoButton;
const bool Recording = DemoRecorder(RECORDER_MANUAL)->IsRecording();
if(DoButton_Menu(&s_DemoButton, Recording ? Localize("Stop record") : Localize("Record demo"), 0, &Button))
@ -129,11 +130,12 @@ void CMenus::RenderGame(CUIRect MainView)
if(m_pClient->m_Snap.m_pLocalInfo && m_pClient->m_Snap.m_pGameInfoObj && !Paused && !Spec)
{
static CButtonContainer s_SpectateButton;
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != TEAM_SPECTATORS)
{
ButtonBar.VSplitLeft(5.0f, 0, &ButtonBar);
ButtonBar.VSplitLeft(120.0f, &Button, &ButtonBar);
ButtonBar.VSplitLeft(5.0f, nullptr, &ButtonBar);
static CButtonContainer s_SpectateButton;
if(!Client()->DummyConnecting() && DoButton_Menu(&s_SpectateButton, Localize("Spectate"), 0, &Button))
{
if(g_Config.m_ClDummy == 0 || Client()->DummyConnected())
@ -148,8 +150,8 @@ void CMenus::RenderGame(CUIRect MainView)
{
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != TEAM_RED)
{
ButtonBar.VSplitLeft(5.0f, 0, &ButtonBar);
ButtonBar.VSplitLeft(120.0f, &Button, &ButtonBar);
ButtonBar.VSplitLeft(5.0f, nullptr, &ButtonBar);
static CButtonContainer s_JoinRedButton;
if(!Client()->DummyConnecting() && DoButton_Menu(&s_JoinRedButton, Localize("Join red"), 0, &Button))
{
@ -160,8 +162,8 @@ void CMenus::RenderGame(CUIRect MainView)
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != TEAM_BLUE)
{
ButtonBar.VSplitLeft(5.0f, 0, &ButtonBar);
ButtonBar.VSplitLeft(120.0f, &Button, &ButtonBar);
ButtonBar.VSplitLeft(5.0f, nullptr, &ButtonBar);
static CButtonContainer s_JoinBlueButton;
if(!Client()->DummyConnecting() && DoButton_Menu(&s_JoinBlueButton, Localize("Join blue"), 0, &Button))
{
@ -172,14 +174,13 @@ void CMenus::RenderGame(CUIRect MainView)
}
else
{
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != TEAM_RED)
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != 0)
{
ButtonBar.VSplitLeft(5.0f, 0, &ButtonBar);
ButtonBar.VSplitLeft(120.0f, &Button, &ButtonBar);
ButtonBar.VSplitLeft(5.0f, nullptr, &ButtonBar);
static CButtonContainer s_JoinGameButton;
if(!Client()->DummyConnecting() && DoButton_Menu(&s_JoinGameButton, Localize("Join game"), 0, &Button))
if(!Client()->DummyConnecting() && DoButton_Menu(&s_SpectateButton, Localize("Join game"), 0, &Button))
{
m_pClient->SendSwitchTeam(TEAM_RED);
m_pClient->SendSwitchTeam(0);
SetActive(false);
}
}
@ -187,8 +188,8 @@ void CMenus::RenderGame(CUIRect MainView)
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != TEAM_SPECTATORS && (ShowDDRaceButtons || !(m_pClient->m_Snap.m_pGameInfoObj->m_GameFlags & GAMEFLAG_TEAMS)))
{
ButtonBar.VSplitLeft(5.0f, 0, &ButtonBar);
ButtonBar.VSplitLeft(65.0f, &Button, &ButtonBar);
ButtonBar.VSplitLeft(5.0f, nullptr, &ButtonBar);
static CButtonContainer s_KillButton;
if(DoButton_Menu(&s_KillButton, Localize("Kill"), 0, &Button))
@ -203,13 +204,13 @@ void CMenus::RenderGame(CUIRect MainView)
{
if(m_pClient->m_Snap.m_pLocalInfo->m_Team != TEAM_SPECTATORS || Paused || Spec)
{
ButtonBar.VSplitLeft(5.0f, 0, &ButtonBar);
ButtonBar.VSplitLeft((!Paused && !Spec) ? 65.0f : 120.0f, &Button, &ButtonBar);
ButtonBar.VSplitLeft(5.0f, nullptr, &ButtonBar);
static CButtonContainer s_PauseButton;
if(DoButton_Menu(&s_PauseButton, (!Paused && !Spec) ? Localize("Pause") : Localize("Join game"), 0, &Button))
{
Console()->ExecuteLine("say /pause");
m_pClient->Console()->ExecuteLine("say /pause");
SetActive(false);
}
}
@ -944,7 +945,7 @@ void CMenus::GhostlistPopulate()
m_vGhosts.clear();
m_GhostPopulateStartTime = time_get_nanoseconds();
Storage()->ListDirectoryInfo(IStorage::TYPE_ALL, m_pClient->m_Ghost.GetGhostDir(), GhostlistFetchCallback, this);
SortGhostlist();
std::sort(m_vGhosts.begin(), m_vGhosts.end());
CGhostItem *pOwnGhost = 0;
for(auto &Ghost : m_vGhosts)
@ -1000,7 +1001,6 @@ void CMenus::UpdateOwnGhost(CGhostItem Item)
Item.m_Date = std::time(0);
Item.m_Failed = false;
m_vGhosts.insert(std::lower_bound(m_vGhosts.begin(), m_vGhosts.end(), Item), Item);
SortGhostlist();
}
void CMenus::DeleteGhostItem(int Index)
@ -1010,22 +1010,6 @@ void CMenus::DeleteGhostItem(int Index)
m_vGhosts.erase(m_vGhosts.begin() + Index);
}
void CMenus::SortGhostlist()
{
if(g_Config.m_GhSort == GHOST_SORT_NAME)
std::stable_sort(m_vGhosts.begin(), m_vGhosts.end(), [](const CGhostItem &Left, const CGhostItem &Right) {
return g_Config.m_GhSortOrder ? (str_comp(Left.m_aPlayer, Right.m_aPlayer) > 0) : (str_comp(Left.m_aPlayer, Right.m_aPlayer) < 0);
});
else if(g_Config.m_GhSort == GHOST_SORT_TIME)
std::stable_sort(m_vGhosts.begin(), m_vGhosts.end(), [](const CGhostItem &Left, const CGhostItem &Right) {
return g_Config.m_GhSortOrder ? (Left.m_Time > Right.m_Time) : (Left.m_Time < Right.m_Time);
});
else if(g_Config.m_GhSort == GHOST_SORT_DATE)
std::stable_sort(m_vGhosts.begin(), m_vGhosts.end(), [](const CGhostItem &Left, const CGhostItem &Right) {
return g_Config.m_GhSortOrder ? (Left.m_Date > Right.m_Date) : (Left.m_Date < Right.m_Date);
});
}
void CMenus::RenderGhost(CUIRect MainView)
{
// render background
@ -1046,12 +1030,10 @@ void CMenus::RenderGhost(CUIRect MainView)
Headers.Draw(ColorRGBA(1, 1, 1, 0.25f), IGraphics::CORNER_T, 5.0f);
Headers.VSplitRight(20.0f, &Headers, 0);
class CColumn
struct CColumn
{
public:
const char *m_pCaption;
int m_Id;
int m_Sort;
float m_Width;
CUIRect m_Rect;
};
@ -1065,11 +1047,11 @@ void CMenus::RenderGhost(CUIRect MainView)
};
static CColumn s_aCols[] = {
{"", -1, GHOST_SORT_NONE, 2.0f, {0}},
{"", COL_ACTIVE, GHOST_SORT_NONE, 30.0f, {0}},
{Localizable("Name"), COL_NAME, GHOST_SORT_NAME, 200.0f, {0}},
{Localizable("Time"), COL_TIME, GHOST_SORT_TIME, 90.0f, {0}},
{Localizable("Date"), COL_DATE, GHOST_SORT_DATE, 150.0f, {0}},
{"", -1, 2.0f, {0}},
{"", COL_ACTIVE, 30.0f, {0}},
{Localizable("Name"), COL_NAME, 200.0f, {0}},
{Localizable("Time"), COL_TIME, 90.0f, {0}},
{Localizable("Date"), COL_DATE, 150.0f, {0}},
};
int NumCols = std::size(s_aCols);
@ -1084,22 +1066,8 @@ void CMenus::RenderGhost(CUIRect MainView)
}
// do headers
for(const auto &Col : s_aCols)
{
if(DoButton_GridHeader(&Col.m_Id, Localize(Col.m_pCaption), g_Config.m_GhSort == Col.m_Sort, &Col.m_Rect))
{
if(Col.m_Sort != GHOST_SORT_NONE)
{
if(g_Config.m_GhSort == Col.m_Sort)
g_Config.m_GhSortOrder ^= 1;
else
g_Config.m_GhSortOrder = 0;
g_Config.m_GhSort = Col.m_Sort;
SortGhostlist();
}
}
}
for(int i = 0; i < NumCols; i++)
DoButton_GridHeader(&s_aCols[i].m_Id, Localize(s_aCols[i].m_pCaption), 0, &s_aCols[i].m_Rect);
View.Draw(ColorRGBA(0, 0, 0, 0.15f), 0, 0);

View file

@ -758,7 +758,10 @@ void CMenus::RenderSettingsTee(CUIRect MainView)
{
aRects[i].HSplitTop(20.0f, &Label, &aRects[i]);
Ui()->DoLabel(&Label, apParts[i], 14.0f, TEXTALIGN_ML);
if(RenderHslaScrollbars(&aRects[i], apColors[i], false, ColorHSLA::DARKEST_LGT))
const unsigned PrevColor = *apColors[i];
RenderHSLScrollbars(&aRects[i], apColors[i], false, true);
if(PrevColor != *apColors[i])
{
SetNeedSendInfo();
}
@ -2125,39 +2128,53 @@ void CMenus::RenderSettings(CUIRect MainView)
}
}
bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alpha, float DarkestLight)
ColorHSLA CMenus::RenderHSLScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alpha, bool ClampedLight)
{
const unsigned PrevPackedColor = *pColor;
ColorHSLA Color(*pColor, Alpha);
const ColorHSLA OriginalColor = Color;
CUIRect Preview, Button, Label;
char aBuf[32];
float *apComponent[] = {&Color.h, &Color.s, &Color.l, &Color.a};
const char *apLabels[] = {Localize("Hue"), Localize("Sat."), Localize("Lht."), Localize("Alpha")};
const float SizePerEntry = 20.0f;
const float MarginPerEntry = 5.0f;
const float PreviewMargin = 2.5f;
const float PreviewHeight = 40.0f + 2 * PreviewMargin;
const float OffY = (SizePerEntry + MarginPerEntry) * (3 + (Alpha ? 1 : 0)) - PreviewHeight;
CUIRect Preview;
pRect->VSplitLeft(PreviewHeight, &Preview, pRect);
Preview.HSplitTop(OffY / 2.0f, nullptr, &Preview);
Preview.HSplitTop(PreviewHeight, &Preview, nullptr);
float SizePerEntry = 20.0f;
float MarginPerEntry = 5.0f;
Preview.Draw(ColorRGBA(0.15f, 0.15f, 0.15f, 1.0f), IGraphics::CORNER_ALL, 4.0f + PreviewMargin);
Preview.Margin(PreviewMargin, &Preview);
Preview.Draw(color_cast<ColorRGBA>(Color.UnclampLighting(DarkestLight)), IGraphics::CORNER_ALL, 4.0f + PreviewMargin);
float OffY = (SizePerEntry + MarginPerEntry) * (3 + (Alpha ? 1 : 0)) - 40.0f;
pRect->VSplitLeft(40.0f, &Preview, pRect);
Preview.HSplitTop(OffY / 2.0f, NULL, &Preview);
Preview.HSplitTop(40.0f, &Preview, NULL);
Graphics()->TextureClear();
{
const float SizeBorder = 5.0f;
Graphics()->SetColor(ColorRGBA(0.15f, 0.15f, 0.15f, 1));
int TmpCont = Graphics()->CreateRectQuadContainer(Preview.x - SizeBorder / 2.0f, Preview.y - SizeBorder / 2.0f, Preview.w + SizeBorder, Preview.h + SizeBorder, 4.0f + SizeBorder / 2.0f, IGraphics::CORNER_ALL);
Graphics()->RenderQuadContainer(TmpCont, -1);
Graphics()->DeleteQuadContainer(TmpCont);
}
ColorHSLA RenderColorHSLA(Color.r, Color.g, Color.b, Color.a);
if(ClampedLight)
RenderColorHSLA = RenderColorHSLA.UnclampLighting();
Graphics()->SetColor(color_cast<ColorRGBA>(RenderColorHSLA));
int TmpCont = Graphics()->CreateRectQuadContainer(Preview.x, Preview.y, Preview.w, Preview.h, 4.0f, IGraphics::CORNER_ALL);
Graphics()->RenderQuadContainer(TmpCont, -1);
Graphics()->DeleteQuadContainer(TmpCont);
auto &&RenderHSLColorsRect = [&](CUIRect *pColorRect) {
Graphics()->TextureClear();
Graphics()->TrianglesBegin();
auto &&RenderHueRect = [&](CUIRect *pColorRect) {
float CurXOff = pColorRect->x;
const float SizeColor = pColorRect->w / 6;
float SizeColor = pColorRect->w / 6;
// red to yellow
{
IGraphics::CColorVertex aColorVertices[] = {
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, 1, 0, 0, 1),
IGraphics::CColorVertex(1, 1, 1, 0, 1),
IGraphics::CColorVertex(2, 1, 0, 0, 1),
IGraphics::CColorVertex(3, 1, 1, 0, 1)};
Graphics()->SetColorVertex(aColorVertices, std::size(aColorVertices));
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
@ -2170,12 +2187,12 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
// yellow to green
CurXOff += SizeColor;
{
IGraphics::CColorVertex aColorVertices[] = {
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, 1, 1, 0, 1),
IGraphics::CColorVertex(1, 0, 1, 0, 1),
IGraphics::CColorVertex(2, 1, 1, 0, 1),
IGraphics::CColorVertex(3, 0, 1, 0, 1)};
Graphics()->SetColorVertex(aColorVertices, std::size(aColorVertices));
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
@ -2188,12 +2205,12 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
CurXOff += SizeColor;
// green to turquoise
{
IGraphics::CColorVertex aColorVertices[] = {
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, 0, 1, 0, 1),
IGraphics::CColorVertex(1, 0, 1, 1, 1),
IGraphics::CColorVertex(2, 0, 1, 0, 1),
IGraphics::CColorVertex(3, 0, 1, 1, 1)};
Graphics()->SetColorVertex(aColorVertices, std::size(aColorVertices));
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
@ -2206,12 +2223,12 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
CurXOff += SizeColor;
// turquoise to blue
{
IGraphics::CColorVertex aColorVertices[] = {
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, 0, 1, 1, 1),
IGraphics::CColorVertex(1, 0, 0, 1, 1),
IGraphics::CColorVertex(2, 0, 1, 1, 1),
IGraphics::CColorVertex(3, 0, 0, 1, 1)};
Graphics()->SetColorVertex(aColorVertices, std::size(aColorVertices));
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
@ -2224,12 +2241,12 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
CurXOff += SizeColor;
// blue to purple
{
IGraphics::CColorVertex aColorVertices[] = {
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, 0, 0, 1, 1),
IGraphics::CColorVertex(1, 1, 0, 1, 1),
IGraphics::CColorVertex(2, 0, 0, 1, 1),
IGraphics::CColorVertex(3, 1, 0, 1, 1)};
Graphics()->SetColorVertex(aColorVertices, std::size(aColorVertices));
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
@ -2242,12 +2259,12 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
CurXOff += SizeColor;
// purple to red
{
IGraphics::CColorVertex aColorVertices[] = {
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, 1, 0, 1, 1),
IGraphics::CColorVertex(1, 1, 0, 0, 1),
IGraphics::CColorVertex(2, 1, 0, 1, 1),
IGraphics::CColorVertex(3, 1, 0, 0, 1)};
Graphics()->SetColorVertex(aColorVertices, std::size(aColorVertices));
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
@ -2256,68 +2273,150 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
CurXOff + SizeColor, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
}
Graphics()->TrianglesEnd();
};
auto &&RenderSaturationRect = [&](CUIRect *pColorRect, const ColorRGBA &CurColor) {
ColorHSLA LeftColor = color_cast<ColorHSLA>(CurColor);
auto &&RenderHSLSatRect = [&](CUIRect *pColorRect, ColorRGBA &CurColor) {
Graphics()->TextureClear();
Graphics()->TrianglesBegin();
float CurXOff = pColorRect->x;
float SizeColor = pColorRect->w;
ColorHSLA RightColor = color_cast<ColorHSLA>(CurColor);
LeftColor.s = 0.0f;
RightColor.s = 1.0f;
const ColorRGBA LeftColorRGBA = color_cast<ColorRGBA>(LeftColor);
const ColorRGBA RightColorRGBA = color_cast<ColorRGBA>(RightColor);
Graphics()->SetColor4(LeftColorRGBA, RightColorRGBA, RightColorRGBA, LeftColorRGBA);
IGraphics::CFreeformItem Freeform(
pColorRect->x, pColorRect->y,
pColorRect->x + pColorRect->w, pColorRect->y,
pColorRect->x, pColorRect->y + pColorRect->h,
pColorRect->x + pColorRect->w, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
};
auto &&RenderLightingRect = [&](CUIRect *pColorRect, const ColorRGBA &CurColor) {
ColorHSLA LeftColor = color_cast<ColorHSLA>(CurColor);
ColorHSLA RightColor = color_cast<ColorHSLA>(CurColor);
LeftColor.l = DarkestLight;
RightColor.l = 1.0f;
LeftColor.g = 0;
RightColor.g = 1;
const ColorRGBA LeftColorRGBA = color_cast<ColorRGBA>(LeftColor);
const ColorRGBA RightColorRGBA = color_cast<ColorRGBA>(RightColor);
ColorRGBA RightColorRGBA = color_cast<ColorRGBA>(RightColor);
ColorRGBA LeftColorRGBA = color_cast<ColorRGBA>(LeftColor);
Graphics()->SetColor4(LeftColorRGBA, RightColorRGBA, RightColorRGBA, LeftColorRGBA);
// saturation
{
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, 1),
IGraphics::CColorVertex(1, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, 1),
IGraphics::CColorVertex(2, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, 1),
IGraphics::CColorVertex(3, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, 1)};
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
pColorRect->x, pColorRect->y,
pColorRect->x + pColorRect->w, pColorRect->y,
pColorRect->x, pColorRect->y + pColorRect->h,
pColorRect->x + pColorRect->w, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
CurXOff + SizeColor, pColorRect->y,
CurXOff, pColorRect->y + pColorRect->h,
CurXOff + SizeColor, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
}
Graphics()->TrianglesEnd();
};
auto &&RenderAlphaRect = [&](CUIRect *pColorRect, const ColorRGBA &CurColorFull) {
const ColorRGBA LeftColorRGBA = color_cast<ColorRGBA>(color_cast<ColorHSLA>(CurColorFull).WithAlpha(0.0f));
const ColorRGBA RightColorRGBA = color_cast<ColorRGBA>(color_cast<ColorHSLA>(CurColorFull).WithAlpha(1.0f));
auto &&RenderHSLLightRect = [&](CUIRect *pColorRect, ColorRGBA &CurColorSat) {
Graphics()->TextureClear();
Graphics()->TrianglesBegin();
Graphics()->SetColor4(LeftColorRGBA, RightColorRGBA, RightColorRGBA, LeftColorRGBA);
float CurXOff = pColorRect->x;
float SizeColor = pColorRect->w / (ClampedLight ? 1.0f : 2.0f);
IGraphics::CFreeformItem Freeform(
pColorRect->x, pColorRect->y,
pColorRect->x + pColorRect->w, pColorRect->y,
pColorRect->x, pColorRect->y + pColorRect->h,
pColorRect->x + pColorRect->w, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
ColorHSLA RightColor = color_cast<ColorHSLA>(CurColorSat);
ColorHSLA LeftColor = color_cast<ColorHSLA>(CurColorSat);
LeftColor.b = ColorHSLA::DARKEST_LGT;
RightColor.b = 1;
ColorRGBA RightColorRGBA = color_cast<ColorRGBA>(RightColor);
ColorRGBA LeftColorRGBA = color_cast<ColorRGBA>(LeftColor);
if(!ClampedLight)
CurXOff += SizeColor;
// light
{
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, 1),
IGraphics::CColorVertex(1, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, 1),
IGraphics::CColorVertex(2, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, 1),
IGraphics::CColorVertex(3, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, 1)};
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
CurXOff + SizeColor, pColorRect->y,
CurXOff, pColorRect->y + pColorRect->h,
CurXOff + SizeColor, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
}
if(!ClampedLight)
{
CurXOff -= SizeColor;
LeftColor.b = 0;
RightColor.b = ColorHSLA::DARKEST_LGT;
RightColorRGBA = color_cast<ColorRGBA>(RightColor);
LeftColorRGBA = color_cast<ColorRGBA>(LeftColor);
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, 1),
IGraphics::CColorVertex(1, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, 1),
IGraphics::CColorVertex(2, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, 1),
IGraphics::CColorVertex(3, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, 1)};
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
CurXOff + SizeColor, pColorRect->y,
CurXOff, pColorRect->y + pColorRect->h,
CurXOff + SizeColor, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
}
Graphics()->TrianglesEnd();
};
auto &&RenderHSLAlphaRect = [&](CUIRect *pColorRect, ColorRGBA &CurColorFull) {
Graphics()->TextureClear();
Graphics()->TrianglesBegin();
float CurXOff = pColorRect->x;
float SizeColor = pColorRect->w;
ColorHSLA RightColor = color_cast<ColorHSLA>(CurColorFull);
ColorHSLA LeftColor = color_cast<ColorHSLA>(CurColorFull);
LeftColor.a = 0;
RightColor.a = 1;
ColorRGBA RightColorRGBA = color_cast<ColorRGBA>(RightColor);
ColorRGBA LeftColorRGBA = color_cast<ColorRGBA>(LeftColor);
// alpha
{
IGraphics::CColorVertex Array[4] = {
IGraphics::CColorVertex(0, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, LeftColorRGBA.a),
IGraphics::CColorVertex(1, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, RightColorRGBA.a),
IGraphics::CColorVertex(2, LeftColorRGBA.r, LeftColorRGBA.g, LeftColorRGBA.b, LeftColorRGBA.a),
IGraphics::CColorVertex(3, RightColorRGBA.r, RightColorRGBA.g, RightColorRGBA.b, RightColorRGBA.a)};
Graphics()->SetColorVertex(Array, 4);
IGraphics::CFreeformItem Freeform(
CurXOff, pColorRect->y,
CurXOff + SizeColor, pColorRect->y,
CurXOff, pColorRect->y + pColorRect->h,
CurXOff + SizeColor, pColorRect->y + pColorRect->h);
Graphics()->QuadsDrawFreeform(&Freeform, 1);
}
Graphics()->TrianglesEnd();
};
for(int i = 0; i < 3 + Alpha; i++)
{
CUIRect Button, Label;
pRect->HSplitTop(SizePerEntry, &Button, pRect);
pRect->HSplitTop(MarginPerEntry, nullptr, pRect);
Button.VSplitLeft(10.0f, nullptr, &Button);
pRect->HSplitTop(MarginPerEntry, NULL, pRect);
Button.VSplitLeft(10.0f, 0, &Button);
Button.VSplitLeft(100.0f, &Label, &Button);
Button.Draw(ColorRGBA(0.15f, 0.15f, 0.15f, 1.0f), IGraphics::CORNER_ALL, 1.0f);
@ -2325,43 +2424,47 @@ bool CMenus::RenderHslaScrollbars(CUIRect *pRect, unsigned int *pColor, bool Alp
CUIRect Rail;
Button.Margin(2.0f, &Rail);
char aBuf[32];
str_format(aBuf, sizeof(aBuf), "%s: %03d", apLabels[i], round_to_int(Color[i] * 255.0f));
str_format(aBuf, sizeof(aBuf), "%s: %03d", apLabels[i], (int)(*apComponent[i] * 255));
Ui()->DoLabel(&Label, aBuf, 14.0f, TEXTALIGN_ML);
ColorRGBA HandleColor;
Graphics()->TextureClear();
Graphics()->TrianglesBegin();
ColorHSLA CurColorPureHSLA(RenderColorHSLA.r, 1, 0.5f, 1);
ColorRGBA CurColorPure = color_cast<ColorRGBA>(CurColorPureHSLA);
ColorRGBA ColorInner(1, 1, 1, 0.25f);
if(i == 0)
{
RenderHueRect(&Rail);
HandleColor = color_cast<ColorRGBA>(ColorHSLA(Color.h, 1.0f, 0.5f, 1.0f));
ColorInner = CurColorPure;
RenderHSLColorsRect(&Rail);
}
else if(i == 1)
{
RenderSaturationRect(&Rail, color_cast<ColorRGBA>(ColorHSLA(Color.h, 1.0f, 0.5f, 1.0f)));
HandleColor = color_cast<ColorRGBA>(ColorHSLA(Color.h, Color.s, 0.5f, 1.0f));
RenderHSLSatRect(&Rail, CurColorPure);
ColorInner = color_cast<ColorRGBA>(ColorHSLA(CurColorPureHSLA.r, *apComponent[1], CurColorPureHSLA.b, 1));
}
else if(i == 2)
{
RenderLightingRect(&Rail, color_cast<ColorRGBA>(ColorHSLA(Color.h, Color.s, 0.5f, 1.0f)));
HandleColor = color_cast<ColorRGBA>(ColorHSLA(Color.h, Color.s, Color.l, 1.0f).UnclampLighting(DarkestLight));
ColorRGBA CurColorSat = color_cast<ColorRGBA>(ColorHSLA(CurColorPureHSLA.r, *apComponent[1], 0.5f, 1));
RenderHSLLightRect(&Rail, CurColorSat);
float LightVal = *apComponent[2];
if(ClampedLight)
LightVal = ColorHSLA::DARKEST_LGT + LightVal * (1.0f - ColorHSLA::DARKEST_LGT);
ColorInner = color_cast<ColorRGBA>(ColorHSLA(CurColorPureHSLA.r, *apComponent[1], LightVal, 1));
}
else if(i == 3)
{
RenderAlphaRect(&Rail, color_cast<ColorRGBA>(ColorHSLA(Color.h, Color.s, Color.l, 1.0f).UnclampLighting(DarkestLight)));
HandleColor = color_cast<ColorRGBA>(Color.UnclampLighting(DarkestLight));
ColorRGBA CurColorFull = color_cast<ColorRGBA>(ColorHSLA(CurColorPureHSLA.r, *apComponent[1], *apComponent[2], 1));
RenderHSLAlphaRect(&Rail, CurColorFull);
float LightVal = *apComponent[2];
if(ClampedLight)
LightVal = ColorHSLA::DARKEST_LGT + LightVal * (1.0f - ColorHSLA::DARKEST_LGT);
ColorInner = color_cast<ColorRGBA>(ColorHSLA(CurColorPureHSLA.r, *apComponent[1], LightVal, *apComponent[3]));
}
Graphics()->TrianglesEnd();
Color[i] = Ui()->DoScrollbarH(&((char *)pColor)[i], &Button, Color[i], &HandleColor);
*apComponent[i] = Ui()->DoScrollbarH(&((char *)pColor)[i], &Button, *apComponent[i], &ColorInner);
}
if(OriginalColor != Color)
{
*pColor = Color.Pack(Alpha);
}
return PrevPackedColor != *pColor;
*pColor = Color.Pack(Alpha);
return Color;
}
enum
@ -3212,12 +3315,11 @@ void CMenus::RenderSettingsDDNet(CUIRect MainView)
static CButtonContainer s_ResetId2;
DoLine_ColorPicker(&s_ResetId2, 25.0f, 13.0f, 5.0f, &Background, Localize("Entities background color"), &g_Config.m_ClBackgroundEntitiesColor, GreyDefault, false);
CUIRect EditBox, ReloadButton;
CUIRect EditBox;
Background.HSplitTop(20.0f, &Label, &Background);
Background.HSplitTop(2.0f, nullptr, &Background);
Label.VSplitLeft(100.0f, &Label, &EditBox);
EditBox.VSplitRight(60.0f, &EditBox, &Button);
Button.VSplitMid(&ReloadButton, &Button, 5.0f);
EditBox.VSplitRight(100.0f, &EditBox, &Button);
EditBox.VSplitRight(5.0f, &EditBox, nullptr);
Ui()->DoLabel(&Label, Localize("Map"), 14.0f, TEXTALIGN_ML);
@ -3225,21 +3327,10 @@ void CMenus::RenderSettingsDDNet(CUIRect MainView)
static CLineInput s_BackgroundEntitiesInput(g_Config.m_ClBackgroundEntities, sizeof(g_Config.m_ClBackgroundEntities));
Ui()->DoEditBox(&s_BackgroundEntitiesInput, &EditBox, 14.0f);
static CButtonContainer s_BackgroundEntitiesMapPicker, s_BackgroundEntitiesReload;
if(DoButton_FontIcon(&s_BackgroundEntitiesReload, FONT_ICON_ARROW_ROTATE_RIGHT, 0, &ReloadButton))
static CButtonContainer s_BackgroundEntitiesReloadButton;
if(DoButton_Menu(&s_BackgroundEntitiesReloadButton, Localize("Reload"), 0, &Button))
{
m_pClient->m_Background.LoadBackground();
}
if(DoButton_FontIcon(&s_BackgroundEntitiesMapPicker, FONT_ICON_FOLDER, 0, &Button))
{
static SPopupMenuId s_PopupMapPickerId;
static CPopupMapPickerContext s_PopupMapPickerContext;
s_PopupMapPickerContext.m_pMenus = this;
s_PopupMapPickerContext.MapListPopulate();
Ui()->DoPopupMenu(&s_PopupMapPickerId, Ui()->MouseX(), Ui()->MouseY(), 300.0f, 250.0f, &s_PopupMapPickerContext, PopupMapPicker);
UpdateBackgroundEntities();
}
Background.HSplitTop(20.0f, &Button, &Background);
@ -3310,15 +3401,15 @@ void CMenus::RenderSettingsDDNet(CUIRect MainView)
}
}
else if(State >= IUpdater::GETTING_MANIFEST && State < IUpdater::NEED_RESTART)
str_copy(aBuf, Localize("Updating…"));
str_format(aBuf, sizeof(aBuf), Localize("Updating…"));
else if(State == IUpdater::NEED_RESTART)
{
str_copy(aBuf, Localize("DDNet Client updated!"));
str_format(aBuf, sizeof(aBuf), Localize("DDNet Client updated!"));
m_NeedRestartUpdate = true;
}
else
{
str_copy(aBuf, Localize("No updates available"));
str_format(aBuf, sizeof(aBuf), Localize("No updates available"));
UpdaterRect.VSplitLeft(TextRender()->TextWidth(14.0f, aBuf, -1, -1.0f) + 10.0f, &UpdaterRect, &Button);
Button.VSplitLeft(100.0f, &Button, nullptr);
static CButtonContainer s_ButtonUpdate;
@ -3332,104 +3423,3 @@ void CMenus::RenderSettingsDDNet(CUIRect MainView)
}
#endif
}
CUi::EPopupMenuFunctionResult CMenus::PopupMapPicker(void *pContext, CUIRect View, bool Active)
{
CPopupMapPickerContext *pPopupContext = static_cast<CPopupMapPickerContext *>(pContext);
CMenus *pMenus = pPopupContext->m_pMenus;
static CListBox s_ListBox;
s_ListBox.SetActive(Active);
s_ListBox.DoStart(20.0f, pPopupContext->m_vMaps.size(), 1, 1, -1, &View, false);
int MapIndex = 0;
for(auto &Map : pPopupContext->m_vMaps)
{
MapIndex++;
const CListboxItem Item = s_ListBox.DoNextItem(&Map, MapIndex == pPopupContext->m_Selection);
if(!Item.m_Visible)
continue;
CUIRect Label, Icon;
Item.m_Rect.VSplitLeft(20.0f, &Icon, &Label);
char aLabelText[IO_MAX_PATH_LENGTH];
str_copy(aLabelText, Map.m_aFilename);
if(Map.m_IsDirectory)
str_append(aLabelText, "/", sizeof(aLabelText));
const char *pIconType;
if(!Map.m_IsDirectory)
{
pIconType = FONT_ICON_MAP;
}
else
{
if(!str_comp(Map.m_aFilename, ".."))
pIconType = FONT_ICON_FOLDER_TREE;
else
pIconType = FONT_ICON_FOLDER;
}
pMenus->TextRender()->SetFontPreset(EFontPreset::ICON_FONT);
pMenus->TextRender()->SetRenderFlags(ETextRenderFlags::TEXT_RENDER_FLAG_ONLY_ADVANCE_WIDTH | ETextRenderFlags::TEXT_RENDER_FLAG_NO_X_BEARING | ETextRenderFlags::TEXT_RENDER_FLAG_NO_Y_BEARING);
pMenus->Ui()->DoLabel(&Icon, pIconType, 12.0f, TEXTALIGN_ML);
pMenus->TextRender()->SetRenderFlags(0);
pMenus->TextRender()->SetFontPreset(EFontPreset::DEFAULT_FONT);
pMenus->Ui()->DoLabel(&Label, aLabelText, 10.0f, TEXTALIGN_ML);
}
const int NewSelected = s_ListBox.DoEnd();
pPopupContext->m_Selection = NewSelected >= 0 ? NewSelected : -1;
if(s_ListBox.WasItemSelected() || s_ListBox.WasItemActivated())
{
const CMapListItem SelectedItem = pPopupContext->m_vMaps[pPopupContext->m_Selection];
if(SelectedItem.m_IsDirectory)
{
if(!str_comp(SelectedItem.m_aFilename, ".."))
{
fs_parent_dir(pPopupContext->m_aCurrentMapFolder);
}
else
{
str_append(pPopupContext->m_aCurrentMapFolder, "/", sizeof(pPopupContext->m_aCurrentMapFolder));
str_append(pPopupContext->m_aCurrentMapFolder, SelectedItem.m_aFilename, sizeof(pPopupContext->m_aCurrentMapFolder));
}
pPopupContext->MapListPopulate();
}
else
{
str_format(g_Config.m_ClBackgroundEntities, sizeof(g_Config.m_ClBackgroundEntities), "%s/%s", pPopupContext->m_aCurrentMapFolder, SelectedItem.m_aFilename);
pMenus->m_pClient->m_Background.LoadBackground();
return CUi::POPUP_CLOSE_CURRENT;
}
}
return CUi::POPUP_KEEP_OPEN;
}
void CMenus::CPopupMapPickerContext::MapListPopulate()
{
m_vMaps.clear();
char aTemp[IO_MAX_PATH_LENGTH];
str_format(aTemp, sizeof(aTemp), "maps/%s", m_aCurrentMapFolder);
m_pMenus->Storage()->ListDirectoryInfo(IStorage::TYPE_ALL, aTemp, MapListFetchCallback, this);
std::stable_sort(m_vMaps.begin(), m_vMaps.end(), CompareFilenameAscending);
}
int CMenus::CPopupMapPickerContext::MapListFetchCallback(const CFsFileInfo *pInfo, int IsDir, int StorageType, void *pUser)
{
CPopupMapPickerContext *pRealUser = (CPopupMapPickerContext *)pUser;
if((!IsDir && !str_endswith(pInfo->m_pName, ".map")) || !str_comp(pInfo->m_pName, ".") || (!str_comp(pInfo->m_pName, "..") && (!str_comp(pRealUser->m_aCurrentMapFolder, ""))))
return 0;
CMapListItem Item;
str_copy(Item.m_aFilename, pInfo->m_pName);
Item.m_IsDirectory = IsDir;
pRealUser->m_vMaps.emplace_back(Item);
return 0;
}

Some files were not shown because too many files have changed in this diff Show more