Compare commits
109 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
d9ee4dccbe | ||
![]() |
ffcb65f365 | ||
![]() |
adc01ab9e3 | ||
![]() |
725a16e38e | ||
![]() |
0b29a4b466 | ||
![]() |
cb42481edd | ||
![]() |
8f9055f48b | ||
![]() |
b1bab32618 | ||
![]() |
dfb0150a7d | ||
![]() |
11cb287a21 | ||
![]() |
6f37361df0 | ||
![]() |
9c0c19b5b2 | ||
![]() |
b08d0ff157 | ||
![]() |
71c2ec5293 | ||
![]() |
72d63673ca | ||
![]() |
cbeab6f9b0 | ||
![]() |
25841e9c77 | ||
![]() |
ea0d5f3d81 | ||
![]() |
4f3be92208 | ||
![]() |
3c3ba9ef4c | ||
![]() |
2f7a06e93e | ||
![]() |
7f918a12a2 | ||
![]() |
7f6a4bbbe5 | ||
![]() |
86c462eb4d | ||
![]() |
7ece0ed8c7 | ||
![]() |
cf77df05ca | ||
![]() |
dcd6249e8f | ||
![]() |
f0ac63eb5c | ||
![]() |
d4fb6127fc | ||
![]() |
637b6ceca2 | ||
![]() |
86d06057ca | ||
![]() |
717832b791 | ||
![]() |
4c51009ed9 | ||
![]() |
0fc56c73cc | ||
![]() |
db73bbdea2 | ||
![]() |
6cd71ea02e | ||
![]() |
7f5dda5c8f | ||
![]() |
35e5dd8af8 | ||
![]() |
b34cc18f98 | ||
![]() |
469df27d9b | ||
![]() |
e7012031eb | ||
![]() |
4c3c945bab | ||
![]() |
e370ffdb0f | ||
![]() |
36a60419ec | ||
![]() |
546007f1df | ||
![]() |
cb7f855fd8 | ||
![]() |
859cb31f5d | ||
![]() |
de353e3b72 | ||
![]() |
9e208fa792 | ||
![]() |
a0b2504f11 | ||
![]() |
89c012e81f | ||
![]() |
abcc95634e | ||
![]() |
8a2d2cd5ac | ||
![]() |
654f71e75f | ||
![]() |
1bf77c35c6 | ||
![]() |
17d09f41be | ||
![]() |
ca9c33ff54 | ||
![]() |
da050a5630 | ||
![]() |
5bf03c50d6 | ||
![]() |
377c013dfe | ||
![]() |
60986eb80f | ||
![]() |
ff9f82d0c8 | ||
![]() |
80a7ecb3a4 | ||
![]() |
8d6ccb8d83 | ||
![]() |
4751941e4f | ||
![]() |
f492d291eb | ||
![]() |
26c6217bc3 | ||
![]() |
ec30567d6b | ||
![]() |
b7eef97239 | ||
![]() |
6c7a163197 | ||
![]() |
d6e8e92a45 | ||
![]() |
197a379933 | ||
![]() |
773837da98 | ||
![]() |
4536c68f00 | ||
![]() |
6966221e39 | ||
![]() |
2bd86d0695 | ||
![]() |
bcb3db4cdc | ||
![]() |
e81dd31ae3 | ||
![]() |
cf0ecf418d | ||
![]() |
9aca1644e6 | ||
![]() |
6c59124cb2 | ||
![]() |
7c06a00f82 | ||
![]() |
9f69c71b6d | ||
![]() |
4351f3c63f | ||
![]() |
4b1db2bcd6 | ||
![]() |
2fd3c643c4 | ||
![]() |
4f8f02acad | ||
![]() |
7e01306fc6 | ||
![]() |
835adfb4ce | ||
![]() |
6594b2d090 | ||
![]() |
4d0d62e364 | ||
![]() |
07959ddc04 | ||
![]() |
18af9a45ee | ||
![]() |
90f1244ab4 | ||
![]() |
9e4a9433ca | ||
![]() |
32c5f4285b | ||
![]() |
c982ca81a5 | ||
![]() |
a144174c41 | ||
![]() |
3a47c4f2e1 | ||
![]() |
0a91fff82a | ||
![]() |
95f79b45dc | ||
![]() |
839495fa9b | ||
![]() |
42b05df717 | ||
![]() |
d5b4e0929f | ||
![]() |
a8fbd6cdfc | ||
![]() |
5b65088426 | ||
![]() |
bc55cbbbd1 | ||
![]() |
c3eede9872 | ||
![]() |
8d5cd95bc4 |
@@ -1,7 +1,7 @@
|
||||
cmake_minimum_required(VERSION 2.6)
|
||||
project(otclient)
|
||||
|
||||
set(VERSION "0.6.0")
|
||||
set(VERSION "0.6.1")
|
||||
|
||||
set(FRAMEWORK_SOUND ON)
|
||||
set(FRAMEWORK_GRAPHICS ON)
|
||||
@@ -11,7 +11,9 @@ include(src/framework/CMakeLists.txt)
|
||||
include(src/client/CMakeLists.txt)
|
||||
|
||||
# functions map for reading backtraces
|
||||
set(CMAKE_CXX_LINK_FLAGS "${CMAKE_CXX_LINK_FLAGS} -Wl,-Map=${PROJECT_NAME}.map")
|
||||
if(NOT APPLE)
|
||||
set(CMAKE_CXX_LINK_FLAGS "${CMAKE_CXX_LINK_FLAGS} -Wl,-Map=${PROJECT_NAME}.map")
|
||||
endif()
|
||||
|
||||
option(USE_PCH "Use precompiled header (speed up compile)" OFF)
|
||||
|
||||
|
13
data/cursors/cursors.otml
Normal file
@@ -0,0 +1,13 @@
|
||||
Cursors
|
||||
target:
|
||||
image: targetcursor
|
||||
hot-spot: 9 9
|
||||
horizontal:
|
||||
image: horizontalcursor
|
||||
hot-spot: 9 4
|
||||
vertical:
|
||||
image: verticalcursor
|
||||
hot-spot: 4 9
|
||||
text:
|
||||
image: textcursor
|
||||
hot-spot: 4 9
|
Before Width: | Height: | Size: 230 B After Width: | Height: | Size: 230 B |
Before Width: | Height: | Size: 266 B After Width: | Height: | Size: 266 B |
Before Width: | Height: | Size: 198 B After Width: | Height: | Size: 198 B |
Before Width: | Height: | Size: 238 B After Width: | Height: | Size: 238 B |
BIN
data/images/game/minimap/flag0.png
Normal file
After Width: | Height: | Size: 335 B |
BIN
data/images/game/minimap/flag1.png
Normal file
After Width: | Height: | Size: 397 B |
BIN
data/images/game/minimap/flag10.png
Normal file
After Width: | Height: | Size: 387 B |
BIN
data/images/game/minimap/flag11.png
Normal file
After Width: | Height: | Size: 444 B |
BIN
data/images/game/minimap/flag12.png
Normal file
After Width: | Height: | Size: 362 B |
BIN
data/images/game/minimap/flag13.png
Normal file
After Width: | Height: | Size: 373 B |
BIN
data/images/game/minimap/flag14.png
Normal file
After Width: | Height: | Size: 397 B |
BIN
data/images/game/minimap/flag15.png
Normal file
After Width: | Height: | Size: 412 B |
BIN
data/images/game/minimap/flag16.png
Normal file
After Width: | Height: | Size: 418 B |
BIN
data/images/game/minimap/flag17.png
Normal file
After Width: | Height: | Size: 399 B |
BIN
data/images/game/minimap/flag18.png
Normal file
After Width: | Height: | Size: 402 B |
BIN
data/images/game/minimap/flag19.png
Normal file
After Width: | Height: | Size: 392 B |
BIN
data/images/game/minimap/flag2.png
Normal file
After Width: | Height: | Size: 418 B |
BIN
data/images/game/minimap/flag3.png
Normal file
After Width: | Height: | Size: 431 B |
BIN
data/images/game/minimap/flag4.png
Normal file
After Width: | Height: | Size: 321 B |
BIN
data/images/game/minimap/flag5.png
Normal file
After Width: | Height: | Size: 354 B |
BIN
data/images/game/minimap/flag6.png
Normal file
After Width: | Height: | Size: 427 B |
BIN
data/images/game/minimap/flag7.png
Normal file
After Width: | Height: | Size: 392 B |
BIN
data/images/game/minimap/flag8.png
Normal file
After Width: | Height: | Size: 400 B |
BIN
data/images/game/minimap/flag9.png
Normal file
After Width: | Height: | Size: 423 B |
Before Width: | Height: | Size: 2.8 KiB |
Before Width: | Height: | Size: 880 B After Width: | Height: | Size: 822 B |
BIN
data/images/ui/button_top_blink.png
Normal file
After Width: | Height: | Size: 462 B |
@@ -344,7 +344,7 @@ locale = {
|
||||
["You are dazzled"] = "Du bist geblendet",
|
||||
["You are dead."] = "Du bist tot.",
|
||||
["You are dead"] = "Du bist tot",
|
||||
["You are drowing"] = "Du ertrinkst",
|
||||
["You are drowning"] = "Du ertrinkst",
|
||||
["You are drunk"] = "Du bist betrunken",
|
||||
["You are electrified"] = "Du bist elektrifiziert",
|
||||
["You are freezing"] = "Du bist am Erfrieren",
|
||||
|
@@ -1,374 +1,376 @@
|
||||
-- special thanks for Shaday, who made these translations
|
||||
|
||||
|
||||
locale = {
|
||||
name = "es",
|
||||
charset = "cp1252",
|
||||
languageName = "Espa<EFBFBD>ol",
|
||||
|
||||
|
||||
translation = {
|
||||
["1a) Offensive Name"] = false,
|
||||
["1b) Invalid Name Format"] = false,
|
||||
["1c) Unsuitable Name"] = false,
|
||||
["1d) Name Inciting Rule Violation"] = false,
|
||||
["2a) Offensive Statement"] = false,
|
||||
["2b) Spamming"] = false,
|
||||
["2c) Illegal Advertising"] = false,
|
||||
["2d) Off-Topic Public Statement"] = false,
|
||||
["2e) Non-English Public Statement"] = false,
|
||||
["2f) Inciting Rule Violation"] = false,
|
||||
["3a) Bug Abuse"] = false,
|
||||
["3b) Game Weakness Abuse"] = false,
|
||||
["3c) Using Unofficial Software to Play"] = false,
|
||||
["3d) Hacking"] = false,
|
||||
["3e) Multi-Clienting"] = false,
|
||||
["3f) Account Trading or Sharing"] = false,
|
||||
["4a) Threatening Gamemaster"] = false,
|
||||
["4b) Pretending to Have Influence on Rule Enforcement"] = false,
|
||||
["4c) False Report to Gamemaster"] = false,
|
||||
["Accept"] = false,
|
||||
["Account name"] = "Nombre de la cuenta",
|
||||
["Account Status:"] = false,
|
||||
["Action:"] = false,
|
||||
["1a) Offensive Name"] = "1a) Nombre ofensivo",
|
||||
["1b) Invalid Name Format"] = "1b) Formato invalido para nombre",
|
||||
["1c) Unsuitable Name"] = "1c) Nombre no adecuado",
|
||||
["1d) Name Inciting Rule Violation"] = "1d) Nombre que incita una violacion al reglamento",
|
||||
["2a) Offensive Statement"] = "2a) Comentario ofensivo",
|
||||
["2b) Spamming"] = "2b) Spamming",
|
||||
["2c) Illegal Advertising"] = "2c) Publicidad ilicita",
|
||||
["2d) Off-Topic Public Statement"] = "2d) Publicacion fuera de lugar",
|
||||
["2e) Non-English Public Statement"] = "2e) Publicacion fuera del ingles",
|
||||
["2f) Inciting Rule Violation"] = "2f) Incitar a una violacion al reglamento",
|
||||
["3a) Bug Abuse"] = "3a) Abuso de error",
|
||||
["3b) Game Weakness Abuse"] = "3b) Abuso de debilidad del juego",
|
||||
["3c) Using Unofficial Software to Play"] = "3c) Usando software ilegal para jugar",
|
||||
["3d) Hacking"] = "3d) Hackeo",
|
||||
["3e) Multi-Clienting"] = "3e) Multiple Cliente",
|
||||
["3f) Account Trading or Sharing"] = "3f) Intercambio de cuenta",
|
||||
["4a) Threatening Gamemaster"] = "4a) Amenzar a un Gamemaster",
|
||||
["4b) Pretending to Have Influence on Rule Enforcement"] = "4b) Pretender tener influencia en una parte del reglamento",
|
||||
["4c) False Report to Gamemaster"] = "4c) Reporte falso a un Gamemaster",
|
||||
["Accept"] = "Aceptar",
|
||||
["Account name"] = "Nombre de cuenta",
|
||||
["Account Status:"] = "Estado de cuenta:",
|
||||
["Action:"] = "Accion:",
|
||||
["Add"] = "A<EFBFBD>adir",
|
||||
["Add new VIP"] = "A<EFBFBD>adir nuevo VIP",
|
||||
["Addon 1"] = "Addon 1",
|
||||
["Addon 2"] = "Addon 2",
|
||||
["Addon 3"] = "Addon 3",
|
||||
["Addon 2"] = "Addon 1",
|
||||
["Addon 3"] = "Addon 1",
|
||||
["Add to VIP list"] = "A<EFBFBD>adir a lista VIP",
|
||||
["Adjust volume"] = "Ajustar vol<EFBFBD>men",
|
||||
["Alas! Brave adventurer, you have met a sad fate.\nBut do not despair, for the gods will bring you back\ninto this world in exchange for a small sacrifice\n\nSimply click on Ok to resume your journeys!"] = false,
|
||||
["All"] = false,
|
||||
["All modules and scripts were reloaded."] = "Todos los m<>dulos y scripts han sido reiniciados",
|
||||
["Allow auto chase override"] = false,
|
||||
["Also known as dash in tibia community, recommended\nfor playing characters with high speed"] = false,
|
||||
["Ambient light: %s%%"] = false,
|
||||
["Adjust volume"] = "Ajustar volumen",
|
||||
["Alas! Brave adventurer, you have met a sad fate.\nBut do not despair, for the gods will bring you back\ninto this world in exchange for a small sacrifice\n\nSimply click on Ok to resume your journeys!"] = "<EFBFBD>Ay! Aventurero valiente, que ha conocido a un triste destino. \nPero no se desespere, porque los dioses le llevar<61> de vuelta \na este mundo a cambio de un peque<75>o sacrificio \n\nSimply haga clic en Aceptar para continuar con sus viajes!",
|
||||
["All"] = "Todo",
|
||||
["All modules and scripts were reloaded."] = "Todos los m<>dulos y scripts se vuelven a cargar.",
|
||||
["Allow auto chase override"] = "Permitur auto persecuci<63>n override",
|
||||
["Also known as dash in tibia community, recommended\nfor playing characters with high speed"] = "Conocido por la comunidad de tibia como dash.\nRecomenada para players de alto nivel.",
|
||||
["Ambient light: %s%%"] = "Ambiente de luz: %s%%",
|
||||
["Amount:"] = "Cantidad:",
|
||||
["Amount"] = false,
|
||||
["Anonymous"] = false,
|
||||
["Are you sure you want to logout?"] = false,
|
||||
["Amount"] = "Cantidad",
|
||||
["Anonymous"] = "An<EFBFBD>nimo",
|
||||
["Are you sure you want to logout?"] = "<EFBFBD>Estas seguro de que quieres salir?",
|
||||
["Attack"] = "Atacar",
|
||||
["Author"] = "Autor",
|
||||
["Autoload"] = "Cargar autom<6F>ticamente",
|
||||
["Autoload priority"] = "Prioridad de carga",
|
||||
["Auto login"] = "Entrar autom<6F>ticamente",
|
||||
["Auto login selected character on next charlist load"] = "Entrar autom<6F>ticamente con un personage cuando se vuelva a abrir la lista de personajes",
|
||||
["Axe Fighting"] = "Combate con Hacha",
|
||||
["Balance:"] = false,
|
||||
["Banishment"] = false,
|
||||
["Banishment + Final Warning"] = false,
|
||||
["Autoload"] = "Auto carga",
|
||||
["Autoload priority"] = "Auto carga prioritaria",
|
||||
["Auto login"] = "Auto iniciar",
|
||||
["Auto login selected character on next charlist load"] = "Auto cargar car<61>cter seleccionado en la carga charlist siguiente",
|
||||
["Axe Fighting"] = "Combate con acha",
|
||||
["Balance:"] = "Saldo:",
|
||||
["Banishment"] = "Banishment",
|
||||
["Banishment + Final Warning"] = "Banishment + Final Warning",
|
||||
["Battle"] = "Batalla",
|
||||
["Browse"] = false,
|
||||
["Bug report sent."] = false,
|
||||
["Button Assign"] = "Seleccionar Bot<6F>n",
|
||||
["Buy"] = "Comprar",
|
||||
["Buy Now"] = false,
|
||||
["Buy Offers"] = false,
|
||||
["Buy with backpack"] = "Comprar con mochila",
|
||||
["Browse"] = "Navegar",
|
||||
["Bug report sent."] = "Reporte de error enviado.",
|
||||
["Button Assign"] = "Boton asignado",
|
||||
["Buy"] = "Compra",
|
||||
["Buy Now"] = "Compra ahora",
|
||||
["Buy Offers"] = "Comprar oferta",
|
||||
["Buy with backpack"] = "Comprar con backpack",
|
||||
["Cancel"] = "Cancelar",
|
||||
["Cannot login while already in game."] = false,
|
||||
["Cap"] = false,
|
||||
["Cannot login while already in game."] = "No se puede iniciar sesi<73>n, mientras que estes en el juego.",
|
||||
["Cap"] = "Cap",
|
||||
["Capacity"] = "Capacidad",
|
||||
["Center"] = false,
|
||||
["Center"] = "Centrar",
|
||||
["Channels"] = "Canales",
|
||||
["Character List"] = "Lista de personajes",
|
||||
["Classic control"] = "Control cl<EFBFBD>sico",
|
||||
["Clear current message window"] = false,
|
||||
["Clear Messages"] = false,
|
||||
["Character List"] = "Lista de car<EFBFBD>cter",
|
||||
["Classic control"] = "Control Clasico",
|
||||
["Clear current message window"] = "Limpiar mensaje actual en ventana",
|
||||
["Clear Messages"] = "Limpiar mensaje",
|
||||
["Clear object"] = "Limpiar objeto",
|
||||
["Client needs update."] = false,
|
||||
["Client needs update."] = "El cliente necesita actualizacion.",
|
||||
["Close"] = "Cerrar",
|
||||
["Close this channel"] = "Cerrar este canal",
|
||||
["Club Fighting"] = "Combate con Maza",
|
||||
["Club Fighting"] = "Combate con mazo",
|
||||
["Combat Controls"] = "Controles de combate",
|
||||
["Comment:"] = false,
|
||||
["Connecting to game server..."] = "Conectando al servidor de juego...",
|
||||
["Connecting to login server..."] = "Conectando al servidor de autentificaci<63>n...",
|
||||
["Console"] = false,
|
||||
["Cooldowns"] = false,
|
||||
["Copy message"] = false,
|
||||
["Copy name"] = false,
|
||||
["Copy Name"] = "Copiar Nombre",
|
||||
["Create Map Mark"] = false,
|
||||
["Create mark"] = false,
|
||||
["Create New Offer"] = false,
|
||||
["Create Offer"] = false,
|
||||
["Current hotkeys:"] = "Atajos actuales",
|
||||
["Current hotkey to add: %s"] = "Atajo actual para a<>adir: %s",
|
||||
["Current Offers"] = false,
|
||||
["Default"] = "Principal",
|
||||
["Delete mark"] = false,
|
||||
["Description:"] = false,
|
||||
["Comment:"] = "Comentario:",
|
||||
["Connecting to game server..."] = "Conectando a servidor game...",
|
||||
["Connecting to login server..."] = "Conectando a servidor login...",
|
||||
["Console"] = "Consola",
|
||||
["Cooldowns"] = "Descansos",
|
||||
["Copy message"] = "Copiar mensaje",
|
||||
["Copy name"] = "Copiar nombre",
|
||||
["Copy Name"] = "Copiar nombre",
|
||||
["Create Map Mark"] = "Crear marca en mapa",
|
||||
["Create mark"] = "Crear marca",
|
||||
["Create New Offer"] = "Crear nueva oferta",
|
||||
["Create Offer"] = "Crear oferta",
|
||||
["Current hotkeys:"] = "Actuales hotkeys:",
|
||||
["Current hotkey to add: %s"] = "Actuales hotkeys a agregar: %s",
|
||||
["Current Offers"] = "Oferta actual",
|
||||
["Default"] = "Predeterminado",
|
||||
["Delete mark"] = "Borrar Marca",
|
||||
["Description:"] = "Descripci<EFBFBD>n:",
|
||||
["Description"] = "Descripci<EFBFBD>n",
|
||||
["Destructive Behaviour"] = false,
|
||||
["Destructive Behaviour"] = "Comportamiento agresivo",
|
||||
["Detail"] = "Detalle",
|
||||
["Details"] = false,
|
||||
["Details"] = "Detalles",
|
||||
["Disable Shared Experience"] = "Desactivar experiencia compartida",
|
||||
["Dismount"] = false,
|
||||
["Display connection speed to the server (milliseconds)"] = false,
|
||||
["Distance Fighting"] = "Combate a Distancia",
|
||||
["Don't stretch/shrink Game Window"] = false,
|
||||
["Edit hotkey text:"] = "Editar texto del atajo",
|
||||
["Edit List"] = false,
|
||||
["Edit Text"] = "Editar Texto",
|
||||
["Enable music"] = false,
|
||||
["Enable Shared Experience"] = "Activar experiencia compartida",
|
||||
["Enable smart walking"] = false,
|
||||
["Enable vertical synchronization"] = "Activar sincronizaci<63>n vertical",
|
||||
["Enable walk booster"] = false,
|
||||
["Dismount"] = "Desmontar",
|
||||
["Display connection speed to the server (milliseconds)"] = "Mostrar velocidad de conexion en el servidor (millisegundos)",
|
||||
["Distance Fighting"] = "Combate a distancia",
|
||||
["Don\'t stretch/shrink Game Window"] = "No estirar ni reducir el tama<6D>o de ventana",
|
||||
["Edit hotkey text:"] = "Editar texto de hotkey:",
|
||||
["Edit List"] = "Editar lista",
|
||||
["Edit Text"] = "Editar texto",
|
||||
["Enable music"] = "Habilitar musica",
|
||||
["Enable Shared Experience"] = "Habilitar experiencia compartida",
|
||||
["Enable smart walking"] = "Habilitar caminado inteligente",
|
||||
["Enable vertical synchronization"] = "Habilitar sincronizaci<63>n vertical",
|
||||
["Enable walk booster"] = "Habilitar caminado turbo",
|
||||
["Enter Game"] = "Entrar al juego",
|
||||
["Enter one name per line."] = false,
|
||||
["Enter with your account again to update your client."] = false,
|
||||
["Enter one name per line."] = "Introducir un nombre por linea.",
|
||||
["Enter with your account again to update your client."] = "",
|
||||
["Error"] = "Error",
|
||||
["Error"] = "Error",
|
||||
["Excessive Unjustified Player Killing"] = false,
|
||||
["Exclude from private chat"] = "Excluir del canal privado",
|
||||
["Exit"] = false,
|
||||
["Excessive Unjustified Player Killing"] = "Asesinato excesivo injustivicado de players",
|
||||
["Exclude from private chat"] = "Ejecutar desde un canal privado",
|
||||
["Exit"] = "Salir",
|
||||
["Experience"] = "Experiencia",
|
||||
["Filter list to match your level"] = false,
|
||||
["Filter list to match your vocation"] = false,
|
||||
["Find:"] = false,
|
||||
["Filter list to match your level"] = "Lista de filtros que coincida con el nivel",
|
||||
["Filter list to match your vocation"] = "Lista de filtros que coincida con el vocaci<63>n",
|
||||
["Find:"] = "Encontrar:",
|
||||
["Fishing"] = "Pesca",
|
||||
["Fist Fighting"] = "Combate con Pu<EFBFBD>os",
|
||||
["Fist Fighting"] = "Combate con pu<EFBFBD>os",
|
||||
["Follow"] = "Seguir",
|
||||
["Force Exit"] = false,
|
||||
["For Your Information"] = false,
|
||||
["Free Account"] = false,
|
||||
["Fullscreen"] = "Pantalla Completa",
|
||||
["Game"] = false,
|
||||
["Game framerate limit: %s"] = false,
|
||||
["Force Exit"] = "Forzar salida",
|
||||
["For Your Information"] = "Para tu informaci<63>n",
|
||||
["Free Account"] = "Account gratis",
|
||||
["Fullscreen"] = "Pantalla completa",
|
||||
["Game"] = "Juego",
|
||||
["Game framerate limit: %s"] = "Imagenes por segundo en juego: %s",
|
||||
["Graphics"] = "Gr<EFBFBD>ficos",
|
||||
["Graphics card driver not detected"] = false,
|
||||
["Graphics Engine:"] = false,
|
||||
["Graphics card driver not detected"] = "Controlador de tarjeta gr<67>fica de video no detectado",
|
||||
["Graphics Engine:"] = "Motor Grafico:",
|
||||
["Head"] = "Cabeza",
|
||||
["Healing"] = false,
|
||||
["Health Info"] = false,
|
||||
["Health Information"] = false,
|
||||
["Hide monsters"] = "Esconder monstruos",
|
||||
["Hide non-skull players"] = "Esconder jugadores sin calavera",
|
||||
["Hide Npcs"] = "Esconder NPCs",
|
||||
["Hide Offline"] = false,
|
||||
["Hide party members"] = "Esconder miembros del grupo",
|
||||
["Hide players"] = "Esconder jugadores",
|
||||
["Hide spells for higher exp. levels"] = false,
|
||||
["Hide spells for other vocations"] = false,
|
||||
["Hit Points"] = "Puntos de Vida",
|
||||
["Hold left mouse button to navigate\nScroll mouse middle button to zoom\nRight mouse button to create map marks"] = false,
|
||||
["Hotkeys"] = "Atajos",
|
||||
["If you shut down the program, your character might stay in the game.\nClick on 'Logout' to ensure that you character leaves the game properly.\nClick on 'Exit' if you want to exit the program without logging out your character."] = false,
|
||||
["Ignore"] = false,
|
||||
["Ignore capacity"] = "Ignorar capacidad",
|
||||
["Ignored players:"] = false,
|
||||
["Ignore equipped"] = "Ignorar equipado",
|
||||
["Ignore List"] = false,
|
||||
["Ignore players"] = false,
|
||||
["Ignore Private Messages"] = false,
|
||||
["Ignore Yelling"] = false,
|
||||
["Interface framerate limit: %s"] = false,
|
||||
["Healing"] = "Curacion",
|
||||
["Health Info"] = "HP Info",
|
||||
["Health Information"] = "HP Informaci<63>n",
|
||||
["Hide monsters"] = "Ocultar monsters",
|
||||
["Hide non-skull players"] = "Ocultar no-skull players",
|
||||
["Hide Npcs"] = "Ocultar NPCs",
|
||||
["Hide Offline"] = "Ocultar fuera de linea",
|
||||
["Hide party members"] = "Ocultar miembros de party",
|
||||
["Hide players"] = "Ocultar players",
|
||||
["Hide spells for higher exp. levels"] = "Ocultar spells para niveles mas altos que tu experiencia.",
|
||||
["Hide spells for other vocations"] = "Ocultar spells que sean para otra vocaci<63>n",
|
||||
["Hit Points"] = "Puntos de vida",
|
||||
["Hold left mouse button to navigate\nScroll mouse middle button to zoom\nRight mouse button to create map marks"] = "Mantenga pulsado el bot<6F>n derecho del rat<61>n para navegar\nScroll bot<6F>n central del rat<61>n para ampliar\nbot<EFBFBD>n derecho del mouse para crear marcas del mapa",
|
||||
["Hotkeys"] = "Hotkeys",
|
||||
["If you shut down the program, your character might stay in the game.\nClick on 'Logout' to ensure that you character leaves the game properly.\nClick on 'Exit' if you want to exit the program without logging out your character."] = "Si se cierra el programa, tu personaje puede permanecer en el juego.\nHaga clic en 'Salir' para asegurarse de que personaje deja el juego correctamente.\nClick en 'Salir' si desea salir del programa sin tener que salir de tu personaje.",
|
||||
["Ignore"] = "Ignorar",
|
||||
["Ignore capacity"] = "Ignorar Capacidad",
|
||||
["Ignored players:"] = "Players ignorados:",
|
||||
["Ignore equipped"] = "Ignorar lo equipodo",
|
||||
["Ignore List"] = "Ignorar lista",
|
||||
["Ignore players"] = "Ignorar players",
|
||||
["Ignore Private Messages"] = "Ignorar mensajes privados",
|
||||
["Ignore Yelling"] = "Ignorar gritos",
|
||||
["Interface framerate limit: %s"] = "Interface de imagenes por segundo: %s",
|
||||
["Inventory"] = "Inventario",
|
||||
["Invite to Party"] = "Invitar al grupo",
|
||||
["Invite to private chat"] = "Invitar al canal privado",
|
||||
["IP Address Banishment"] = false,
|
||||
["Item Offers"] = false,
|
||||
["It is empty."] = false,
|
||||
["Join %s's Party"] = false,
|
||||
["Leave Party"] = "Salir del grupo",
|
||||
["Invite to Party"] = "Ivitar a party",
|
||||
["Invite to private chat"] = "Invitar a canal privado",
|
||||
["IP Address Banishment"] = "Banishment - Direccion IP",
|
||||
["Item Offers"] = "Ofertas de objetos",
|
||||
["It is empty."] = "Est<EFBFBD> vasio.",
|
||||
["Join %s\'s Party"] = "Unir %s\'s party",
|
||||
["Leave Party"] = "Dejar party",
|
||||
["Level"] = "Nivel",
|
||||
["Lifetime Premium Account"] = false,
|
||||
["Limits FPS to 60"] = "Limita los FPS a 60",
|
||||
["List of items that you're able to buy"] = "Lista de objetos que usted puede comprar",
|
||||
["List of items that you're able to sell"] = "Lista de objetos que usted puede vender",
|
||||
["Lifetime Premium Account"] = "Tiempo de Premium Account",
|
||||
["Limits FPS to 60"] = "Limites FPS a 60",
|
||||
["List of items that you're able to buy"] = "Lista de objetos que puedes de comprar",
|
||||
["List of items that you're able to sell"] = "Lista de objetos que puedes de vender",
|
||||
["Load"] = "Cargar",
|
||||
["Logging out..."] = false,
|
||||
["Login"] = "Entrar",
|
||||
["Login Error"] = "Error de Autentificaci<EFBFBD>n",
|
||||
["Login Error"] = "Error de Autentificaci<EFBFBD>n",
|
||||
["Logout"] = false,
|
||||
["Look"] = "Ver",
|
||||
["Magic Level"] = "Nivel M<EFBFBD>gico",
|
||||
["Make sure that your client uses\nthe correct game protocol version"] = "Compruebe que tu cliente use\nuse el mismo protocolo que el servidor de juego",
|
||||
["Logging out..."] = "Cerrando sesion...",
|
||||
["Login"] = "Ingresar",
|
||||
["Login Error"] = "Error de ingreso",
|
||||
["Login Error"] = "Error de ingreso",
|
||||
["Logout"] = "Salir",
|
||||
["Look"] = "Mirar",
|
||||
["Magic Level"] = "Nivel m<EFBFBD>gico",
|
||||
["Make sure that your client uses\nthe correct game protocol version"] = "Aseg<EFBFBD>rese de que el cliente utiliza\nes el correcto de versi<73>n del protocolo",
|
||||
["Mana"] = "Mana",
|
||||
["Manage hotkeys:"] = "Configurar atajos:",
|
||||
["Market"] = false,
|
||||
["Market Offers"] = false,
|
||||
["Message of the day"] = "Mensaje del d<EFBFBD>a",
|
||||
["Message to "] = false,
|
||||
["Message to %s"] = "Mandar mensaje a %s",
|
||||
["Manage hotkeys:"] = "Administrador de hotkeys:",
|
||||
["Market"] = "Mercado",
|
||||
["Market Offers"] = "Ofertas en mercado",
|
||||
["Message of the day"] = "Mensaje del dia",
|
||||
["Message to "] = "Mensaje a",
|
||||
["Message to %s"] = "Mensaje a %s",
|
||||
["Minimap"] = "Minimapa",
|
||||
["Module Manager"] = "Administrador de M<EFBFBD>dulos",
|
||||
["Module name"] = "Nombre del m<EFBFBD>dulo",
|
||||
["Mount"] = false,
|
||||
["Move Stackable Item"] = "Mover objeto contable",
|
||||
["Module Manager"] = "Administrador de modulos",
|
||||
["Module name"] = "Nombre de modulo",
|
||||
["Mount"] = "Montura",
|
||||
["Move Stackable Item"] = "Mover objeto apilable",
|
||||
["Move up"] = "Mover arriba",
|
||||
["My Offers"] = false,
|
||||
["My Offers"] = "Mis ofertas",
|
||||
["Name:"] = "Nombre:",
|
||||
["Name Report"] = false,
|
||||
["Name Report + Banishment"] = false,
|
||||
["Name Report + Banishment + Final Warning"] = false,
|
||||
["No"] = false,
|
||||
["No graphics card detected, everything will be drawn using the CPU,\nthus the performance will be really bad.\nPlease update your graphics driver to have a better performance."] = false,
|
||||
["No item selected."] = false,
|
||||
["No Mount"] = false,
|
||||
["No Outfit"] = false,
|
||||
["No statement has been selected."] = false,
|
||||
["Notation"] = false,
|
||||
["NPC Trade"] = "Comercia con NPC",
|
||||
["Offer History"] = false,
|
||||
["Offers"] = false,
|
||||
["Offer Type:"] = false,
|
||||
["Offline Training"] = false,
|
||||
["Ok"] = "Ok",
|
||||
["on %s.\n"] = false,
|
||||
["Open"] = "Abrir",
|
||||
["Open a private message channel:"] = "Abrir un canal privado:",
|
||||
["Open charlist automatically when starting client"] = false,
|
||||
["Open in new window"] = "Abrir en una nueva ventana",
|
||||
["Open new channel"] = "Abrir novo canal",
|
||||
["Name Report"] = "Name Report",
|
||||
["Name Report + Banishment"] = "Name Report + Banishment",
|
||||
["Name Report + Banishment + Final Warning"] = "Name Report + Banishment + Final Warning",
|
||||
["No"] = "No",
|
||||
["No graphics card detected, everything will be drawn using the CPU,\nthus the performance will be really bad.\nPlease update your graphics driver to have a better performance."] = "No graphics card detected, everything will be drawn using the CPU,\npor lo tanto el rendimiento va a ser muy malo.\nPor favor, actualice su controlador de gr<67>ficos para tener un mejor rendimiento.",
|
||||
["No item selected."] = "No hay elemento seleccionado.",
|
||||
["No Mount"] = "No montura",
|
||||
["No Outfit"] = "No outfit",
|
||||
["No statement has been selected."] = "No hay comentario seleccionado.",
|
||||
["Notation"] = "Notation",
|
||||
["NPC Trade"] = "Intercambio con NPC",
|
||||
["Offer History"] = "Historial de oferta",
|
||||
["Offers"] = "Ofertas",
|
||||
["Offer Type:"] = "Tipo de oferta:",
|
||||
["Offline Training"] = "Entrenamiento offLine",
|
||||
["Ok"] = "OK",
|
||||
["on %s.\n"] = "en %s.\n",
|
||||
["Open"] = "Abierto",
|
||||
["Open a private message channel:"] = "Abrir mensaje en canal privado:",
|
||||
["Open charlist automatically when starting client"] = "Abrir lista de players automaticamente al iniciar el cliente",
|
||||
["Open in new window"] = "Abrir en nueva ventana",
|
||||
["Open new channel"] = "Abrir nuevo canal",
|
||||
["Options"] = "Opciones",
|
||||
["Overview"] = false,
|
||||
["Pass Leadership to %s"] = "Pasar el liderazgo a %s",
|
||||
["Overview"] = "Descripcion",
|
||||
["Pass Leadership to %s"] = "Pasar liderazgo a %s",
|
||||
["Password"] = "Contrase<EFBFBD>a",
|
||||
["Piece Price:"] = false,
|
||||
["Please enter a character name:"] = "Por favor, introduce el nombre de un personaje:",
|
||||
["Please, press the key you wish to add onto your hotkeys manager"] = "Por favor, presione la tecla que desee para\na<EFBFBD>adir a tu administrador de atajos",
|
||||
["Please Select"] = false,
|
||||
["Please use this dialog to only report bugs. Do not report rule violations here!"] = false,
|
||||
["Please wait"] = "Por favor, espere",
|
||||
["Piece Price:"] = "Precio por pieza:",
|
||||
["Please enter a character name:"] = "Por favor ingresar nombre del player:",
|
||||
["Please, press the key you wish to add onto your hotkeys manager"] = "Por favor, presiona la tecla que desees para que sea registrada en\nel administrador de hotkeys",
|
||||
["Please Select"] = "Por favor selecciona",
|
||||
["Please use this dialog to only report bugs. Do not report rule violations here!"] = "Por favor usa estos dialogos solo para reportar errores.\n<EFBFBD>No reportar violaciones al reglamento aqu<71>!",
|
||||
["Please wait"] = "Por favor espera",
|
||||
["Port"] = "Puerto",
|
||||
["Position:"] = false,
|
||||
["Position: %i %i %i"] = false,
|
||||
["Premium Account (%s) days left"] = false,
|
||||
["Price:"] = "Precio",
|
||||
["Position:"] = "Posici<EFBFBD>n:",
|
||||
["Position: %i %i %i"] = "Posici<EFBFBD>n: %i %i %i",
|
||||
["Premium Account (%s) days left"] = "Premium Accoun restan dias (%s)",
|
||||
["Price:"] = "Precio:",
|
||||
["Primary"] = "Primario",
|
||||
["Protocol"] = false,
|
||||
["Quest Log"] = false,
|
||||
["Randomize"] = false,
|
||||
["Randomize characters outfit"] = false,
|
||||
["Reason:"] = false,
|
||||
["Refresh"] = "Actualizar",
|
||||
["Refresh Offers"] = false,
|
||||
["Regeneration Time"] = false,
|
||||
["Reject"] = false,
|
||||
["Reload All"] = "Recargar Todos",
|
||||
["Remember account and password when starts client"] = false,
|
||||
["Protocol"] = "Protocolo",
|
||||
["Quest Log"] = "Quest Log",
|
||||
["Randomize"] = "Combinar",
|
||||
["Randomize characters outfit"] = "Combinar oufit del jugador",
|
||||
["Reason:"] = "Reason:",
|
||||
["Refresh"] = "Refrescar",
|
||||
["Refresh Offers"] = "Refrescar ofertas",
|
||||
["Regeneration Time"] = "Tiempo de regeneraci<63>n",
|
||||
["Reject"] = "Rechazar",
|
||||
["Reload All"] = "Cargar todo de nuevo",
|
||||
["Remember account and password when starts client"] = "Recordar cuenta y contrase<73>a al iniciar el cliente",
|
||||
["Remember password"] = "Recordar contrase<73>a",
|
||||
["Remove"] = "Quitar",
|
||||
["Remove %s"] = "Quitar %s",
|
||||
["Report Bug"] = false,
|
||||
["Reserved for more functionality later."] = false,
|
||||
["Reset Market"] = false,
|
||||
["Revoke %s's Invitation"] = false,
|
||||
["Rotate"] = "Girar",
|
||||
["Rule Violation"] = false,
|
||||
["Save"] = false,
|
||||
["Save Messages"] = false,
|
||||
["Remove"] = "Remover",
|
||||
["Remove %s"] = "Remover %s",
|
||||
["Report Bug"] = "Reportar error",
|
||||
["Reserved for more functionality later."] = "eservado para una funcion futura.",
|
||||
["Reset Market"] = "Reiniciar mercado",
|
||||
["Revoke %s\'s Invitation"] = "Anular %s\'s invitaci<63>n",
|
||||
["Rotate"] = "Rotar",
|
||||
["Rule Violation"] = "Violacion de regla",
|
||||
["Save"] = "Salvar",
|
||||
["Save Messages"] = "Salvar mensaje",
|
||||
["Search:"] = "Buscar:",
|
||||
["Search all items"] = false,
|
||||
["Search all items"] = "Buscar todos los objetos",
|
||||
["Secondary"] = "Secundario",
|
||||
["Select object"] = "Seleccionar objeto",
|
||||
["Select Outfit"] = "Selecionar Traje",
|
||||
["Select your language"] = false,
|
||||
["Select Outfit"] = "Seleccionar outfit",
|
||||
["Select your language"] = "Selectionar tu lenguaje",
|
||||
["Sell"] = "Vender",
|
||||
["Sell Now"] = false,
|
||||
["Sell Offers"] = false,
|
||||
["Send"] = false,
|
||||
["Send automatically"] = "Enviar autom<EFBFBD>ticamente",
|
||||
["Send Message"] = false,
|
||||
["Server"] = "Servidor",
|
||||
["Server Log"] = "Registro del servidor",
|
||||
["Set Outfit"] = "Escoger Traje",
|
||||
["Shielding"] = "Defensa",
|
||||
["Sell Now"] = "Vender ya",
|
||||
["Sell Offers"] = "Ofertas de venta",
|
||||
["Send"] = "Enviar",
|
||||
["Send automatically"] = "Enviar automaticamente",
|
||||
["Send Message"] = "Enviar mensaje",
|
||||
["Server"] = "Server",
|
||||
["Server Log"] = "Server Log",
|
||||
["Set Outfit"] = "Fijar outfit",
|
||||
["Shielding"] = "Escudo",
|
||||
["Show all items"] = "Mostrar todos los objetos",
|
||||
["Show connection ping"] = false,
|
||||
["Show Depot Only"] = false,
|
||||
["Show event messages in console"] = "Mostrar los mensajes de eventos en la consola",
|
||||
["Show frame rate"] = "Mostrar FPS",
|
||||
["Show info messages in console"] = "Mostrar los mensajes informativos en la consola",
|
||||
["Show left panel"] = false,
|
||||
["Show levels in console"] = "Mostrar los niveles en la consola",
|
||||
["Show Offline"] = false,
|
||||
["Show private messages in console"] = "Mostrar los mensajes privados en la consola",
|
||||
["Show private messages on screen"] = false,
|
||||
["Show Server Messages"] = false,
|
||||
["Show status messages in console"] = "Mostrar los mensajes de estado en la consola",
|
||||
["Show Text"] = false,
|
||||
["Show timestamps in console"] = "Mostrar la hora en la consola",
|
||||
["Show your depot items only"] = false,
|
||||
["Show connection ping"] = "Mostrar ping de conexi<78>n",
|
||||
["Show Depot Only"] = "Mostrar solo el Depot",
|
||||
["Show event messages in console"] = "Mostrar mensajes de evento en consola",
|
||||
["Show frame rate"] = "Mostrar velocidad por cuadro",
|
||||
["Show info messages in console"] = "Mostrar mensajes de informaci<EFBFBD>n en consola",
|
||||
["Show left panel"] = "Mostrar panel izquierdo",
|
||||
["Show levels in console"] = "Mostrar niveles en consola",
|
||||
["Show Offline"] = "Mostrar offLine",
|
||||
["Show private messages in console"] = "Mostrar mensajes privados en consola",
|
||||
["Show private messages on screen"] = "Mostrar mensajes privados en pantalla",
|
||||
["Show Server Messages"] = "Mostrar mensajes del servidor",
|
||||
["Show status messages in console"] = "Mostrar mensajes de estado en consola",
|
||||
["Show Text"] = "Mostrar texto",
|
||||
["Show timestamps in console"] = "Mostrar marcas de tiempo en consola",
|
||||
["Show your depot items only"] = "Mostrar solo tus objetos en depot",
|
||||
["Skills"] = "Habilidades",
|
||||
["Soul"] = false,
|
||||
["Soul Points"] = "Puntos del Alma",
|
||||
["Special"] = false,
|
||||
["Speed"] = false,
|
||||
["Spell Cooldowns"] = false,
|
||||
["Spell List"] = false,
|
||||
["Stamina"] = "Vigor",
|
||||
["Statement:"] = false,
|
||||
["Statement Report"] = false,
|
||||
["Statistics"] = false,
|
||||
["Stop Attack"] = "Detener el Ataque",
|
||||
["Stop Follow"] = "Detener el Seguimiento",
|
||||
["Support"] = false,
|
||||
["Soul"] = "Soul",
|
||||
["Soul Points"] = "Puntos de Soul",
|
||||
["Special"] = "Especial",
|
||||
["Speed"] = "Velocidad",
|
||||
["Spell Cooldowns"] = "Spells Cooldowns",
|
||||
["Spell List"] = "Lista de spells",
|
||||
["Stamina"] = "Stamina",
|
||||
["Statement:"] = "Comentario:",
|
||||
["Statement Report"] = "Statement Report",
|
||||
["Statistics"] = "Estadisticas",
|
||||
["Stop Attack"] = "Detener ataque",
|
||||
["Stop Follow"] = "Detener persecucion",
|
||||
["Support"] = "Soporte",
|
||||
["%s: (use object)"] = "%s: (usar objeto)",
|
||||
["%s: (use object on target)"] = "%s: (usar objeto en objetivo)",
|
||||
["%s: (use object on yourself)"] = "%s: (usar objeto en ti mismo)",
|
||||
["%s: (use object with crosshair)"] = "%s: (usar objeto con mirilla)",
|
||||
["Sword Fighting"] = "Combate con Espada",
|
||||
["%s: (use object on target)"] = "%s: (usar objeto en un objetivo)",
|
||||
["%s: (use object on yourself)"] = "%s: (usar objeto en mi mismo)",
|
||||
["%s: (use object with crosshair)"] = "%s: (usar objeto en aire)",
|
||||
["Sword Fighting"] = "Combate de espada",
|
||||
["Terminal"] = "Terminal",
|
||||
["There is no way."] = "No hay ruta.",
|
||||
["Title"] = false,
|
||||
["Total Price:"] = false,
|
||||
["Trade"] = "Comercial",
|
||||
["Trade with ..."] = "Comercial con ...",
|
||||
["Trying to reconnect in %s seconds."] = false,
|
||||
["Unable to load dat file, please place a valid dat in '%s'"] = false,
|
||||
["Unable to load spr file, please place a valid spr in '%s'"] = false,
|
||||
["Unable to logout."] = "No es posible salir.",
|
||||
["Unignore"] = false,
|
||||
["Unload"] = "Descarga",
|
||||
["Update needed"] = false,
|
||||
["Use"] = "Usar",
|
||||
["Use on target"] = "Usar en objetivo",
|
||||
["Use on yourself"] = "Usar en ti mismo",
|
||||
["There is no way."] = "No hay ninguna manera.",
|
||||
["Title"] = "T<EFBFBD>tulo",
|
||||
["Total Price:"] = "Total total:",
|
||||
["Trade"] = "Intercambio",
|
||||
["Trade with ..."] = "Intercambiar con ...",
|
||||
["Trying to reconnect in %s seconds."] = "",
|
||||
["Unable to load dat file, please place a valid dat in '%s'"] = "No se puede cargar el archivo dat, por favor coloque un dat v<>lido en '%s'",
|
||||
["Unable to load spr file, please place a valid spr in '%s'"] = "No se puede cargar el archivo spr, por favor coloque un spr v<>lido en '%s'",
|
||||
["Unable to logout."] = "No se puede cerrar sesi<73>n-",
|
||||
["Unignore"] = "Desactivar ignorado",
|
||||
["Unload"] = "No cargado",
|
||||
["Update needed"] = "Es necesario actualizar",
|
||||
["Use"] = "Uso",
|
||||
["Use on target"] = "Usar en un objetivo",
|
||||
["Use on yourself"] = "Usar en mi mismo",
|
||||
["Use with ..."] = "Usar en ...",
|
||||
["Version"] = "Versi<EFBFBD>n",
|
||||
["VIP List"] = "Lista VIP",
|
||||
["Voc."] = false,
|
||||
["Vocation"] = false,
|
||||
["Waiting List"] = false,
|
||||
["Website"] = "Sitio Web",
|
||||
["Weight:"] = "Peso",
|
||||
["Will detect when to use diagonal step based on the\nkeys you are pressing"] = false,
|
||||
["With crosshair"] = "Con mirilla",
|
||||
["Yes"] = false,
|
||||
["You are bleeding"] = false,
|
||||
["You are burning"] = "Est<EFBFBD>s quemando",
|
||||
["You are cursed"] = "Est<EFBFBD>s maldito",
|
||||
["You are dazzled"] = "Est<EFBFBD>s deslumbrado",
|
||||
["You are dead."] = "Has muerto.",
|
||||
["You are dead"] = false,
|
||||
["You are drowing"] = "Te est<EFBFBD>s ahogando",
|
||||
["You are drunk"] = false,
|
||||
["You are electrified"] = "Est<EFBFBD>s electrocutado",
|
||||
["You are freezing"] = "Est<EFBFBD>s congelado",
|
||||
["You are hasted"] = "Vas con prisa",
|
||||
["You are hungry"] = false,
|
||||
["You are paralysed"] = "Est<EFBFBD>s paralizado",
|
||||
["You are poisoned"] = "Est<EFBFBD>s envenenado",
|
||||
["You are protected by a magic shield"] = "Est<EFBFBD>s protegido por un escudo m<EFBFBD>gico",
|
||||
["You are strengthened"] = "Est<EFBFBD>s reforzado",
|
||||
["You are within a protection zone"] = "Est<EFBFBD>s en una zona de protecci<63>n",
|
||||
["You can enter new text."] = false,
|
||||
["You have %s percent"] = "Tienes %s por ciento",
|
||||
["You have %s percent to go"] = "Te falta %s por ciento para avanzar",
|
||||
["You may not logout during a fight"] = "No puedes salir mientras est<73>s en un combate",
|
||||
["Version"] = "Version",
|
||||
["VIP List"] = "Lista Vip",
|
||||
["Voc."] = "Voc.",
|
||||
["Vocation"] = "Vocaci<EFBFBD>n",
|
||||
["Waiting List"] = "Lista de espera",
|
||||
["Website"] = "Sitio WEB",
|
||||
["Weight:"] = "Peso:",
|
||||
["Will detect when to use diagonal step based on the\nkeys you are pressing"] = "Detectar cuando se camina en diagonal usando las flechas",
|
||||
["With crosshair"] = "Con punto de mira",
|
||||
["Yes"] = "Si",
|
||||
["You are bleeding"] = "Tu estas sangrado",
|
||||
["You are burning"] = "Tu estas quemado",
|
||||
["You are cursed"] = "Tu estas maldecido",
|
||||
["You are dazzled"] = "Tu estas deslumbrado",
|
||||
["You are dead."] = "Tu estas muerto.",
|
||||
["You are dead"] = "Tu estas muerto",
|
||||
["You are drowning"] = "Tu estas ahotado",
|
||||
["You are drunk"] = "Tu estas borracho",
|
||||
["You are electrified"] = "Tu estas electrificado",
|
||||
["You are freezing"] = "Tu estas congelado",
|
||||
["You are hasted"] = "Tu estas rapido",
|
||||
["You are hungry"] = "Tu estas hambriento",
|
||||
["You are paralysed"] = "Tu estas paralizado",
|
||||
["You are poisoned"] = "Tu estas envenedado",
|
||||
["You are protected by a magic shield"] = "Tu estas protegido por un campo magico",
|
||||
["You are strengthened"] = "Tu estas reforzado",
|
||||
["You are within a protection zone"] = "Tu estas dentro de una zona segura",
|
||||
["You can enter new text."] = "Tu puedes introducir un texto nuevo.",
|
||||
["You have %s percent"] = "Tu tienes %s porciento",
|
||||
["You have %s percent to go"] = "Tu tienes %s porciento para ir",
|
||||
["You may not logout during a fight"] = "No puedes salir durante una pelea",
|
||||
["You may not logout or enter a protection zone"] = "No puedes salir o entrar en una zona de protecci<63>n",
|
||||
["You must enter a comment."] = false,
|
||||
["You must enter a valid server address and port."] = false,
|
||||
["You must select a character to login!"] = "Debes seleccionar un personaje para entrar!",
|
||||
["Your Capacity:"] = false,
|
||||
["You read the following, written by \n%s\n"] = false,
|
||||
["You read the following, written on \n%s.\n"] = false,
|
||||
["Your Money:"] = false,
|
||||
["You must enter a comment."] = "Debes introducir un comentario.",
|
||||
["You must enter a valid server address and port."] = "Debes introducir una direcci<63>n v<>lida de servidor y el puerto.",
|
||||
["You must select a character to login!"] = "<EFBFBD>Debes seleccionar un personaje para ingresar!",
|
||||
["Your Capacity:"] = "Tu capacidad:",
|
||||
["You read the following, written by \n%s\n"] = "Uno lee lo siguiente, escrito por \n%s\n",
|
||||
["You read the following, written on \n%s.\n"] = "Uno lee lo siguiente, escrito en \n%s\n",
|
||||
["Your Money:"] = "Tu dinero:",
|
||||
["Change language"] = "Cambiar idioma",
|
||||
["Don't stretch or shrink Game Window"] = "No estirar o encoger Ventana de Juego"
|
||||
}
|
||||
}
|
||||
|
||||
modules.client_locales.installLocale(locale)
|
||||
|
||||
modules.client_locales.installLocale(locale)
|
@@ -347,7 +347,7 @@ locale = {
|
||||
["You are dazzled"] = "Jestes oslepiony",
|
||||
["You are dead."] = "Zginales marnie.",
|
||||
["You are dead"] = false,
|
||||
["You are drowing"] = "Topisz sie",
|
||||
["You are drowning"] = "Topisz sie",
|
||||
["You are drunk"] = false,
|
||||
["You are electrified"] = "Jestes porazony pradem",
|
||||
["You are freezing"] = "Marzniesz",
|
||||
|
@@ -5,6 +5,11 @@ locale = {
|
||||
|
||||
-- As tradu<64><75>es devem vir sempre em ordem alfab<61>tica.
|
||||
translation = {
|
||||
["%s of experience left"] = "%s de experi<72>ncia faltando",
|
||||
["%s: (use object on target)"] = "%s: (usar objeto no alvo)",
|
||||
["%s: (use object on yourself)"] = "%s: (usar objeto em si)",
|
||||
["%s: (use object with crosshair)"] = "%s: (usar objeto com mira)",
|
||||
["%s: (use object)"] = "%s: (usar objeto)",
|
||||
["1a) Offensive Name"] = "1a) Nome ofensivo",
|
||||
["1b) Invalid Name Format"] = "1b) Nome com formato inv<6E>lido",
|
||||
["1c) Unsuitable Name"] = "1c) Nome n<>o adequado",
|
||||
@@ -26,48 +31,50 @@ locale = {
|
||||
["4c) False Report to Gamemaster"] = "4c) Relat<61>rio falso para Gamemaster",
|
||||
["Accept"] = "Aceitar",
|
||||
["Account name"] = "Nome da conta",
|
||||
["Account Status:"] = false,
|
||||
["Action:"] = "A<EFBFBD><EFBFBD>o:",
|
||||
["Add"] = "Adicionar",
|
||||
["Account Status"] = "Estado da Conta",
|
||||
["Action"] = "A<EFBFBD><EFBFBD>o",
|
||||
["Add new VIP"] = "Adicionar nova VIP",
|
||||
["Add to VIP list"] = "Adicionar a lista VIP",
|
||||
["Add"] = "Adicionar",
|
||||
["Addon 1"] = "Addon 1",
|
||||
["Addon 2"] = "Addon 2",
|
||||
["Addon 3"] = "Addon 3",
|
||||
["Add to VIP list"] = "Adicionar a lista VIP",
|
||||
["Adjust volume"] = "Ajustar volume",
|
||||
["Alas! Brave adventurer, you have met a sad fate.\nBut do not despair, for the gods will bring you back\ninto this world in exchange for a small sacrifice\n\nSimply click on Ok to resume your journeys!"] = false,
|
||||
["All"] = "Todos",
|
||||
["All modules and scripts were reloaded."] = "Todos m<>dulos e scripts foram recarregados.",
|
||||
["All"] = "Todos",
|
||||
["Allow auto chase override"] = "Permitir sobrescrever o modo de persegui<75><69>o",
|
||||
["Also known as dash in tibia community, recommended\nfor playing characters with high speed"] = "Tamb<EFBFBD>m conhecido como dash na comunidade tibiana, recomendado\npara jogar com personagem que possuam velocidade alta",
|
||||
["Ambient light: %s%%"] = "Luz ambiente: %s%%",
|
||||
["Amount:"] = "Quantidade:",
|
||||
["Amount"] = "Quantidade",
|
||||
["Anonymous"] = "An<EFBFBD>nimo",
|
||||
["Any"] = "Qualquer",
|
||||
["Are you sure you want to logout?"] = "Voc<EFBFBD> tem certeza que quer sair?",
|
||||
["Attack"] = "Atacar",
|
||||
["Audio"] = "<EFBFBD>udio",
|
||||
["Author"] = "Autor",
|
||||
["Autoload"] = "Carregar automaticamente",
|
||||
["Autoload priority"] = "Prioridade de carregamento",
|
||||
["Auto login"] = "Entrar automaticamente",
|
||||
["Auto login selected character on next charlist load"] = "Entrar automaticamente com o personagem quando reabrir a lista de personagens",
|
||||
["Auto login"] = "Entrar automaticamente",
|
||||
["Autoload priority"] = "Prioridade de carregamento",
|
||||
["Autoload"] = "Carregar automaticamente",
|
||||
["Axe Fighting"] = "Combate com Machado",
|
||||
["Balance:"] = "Saldo:",
|
||||
["Banishment"] = "Banimento",
|
||||
["Balance"] = "Saldo",
|
||||
["Banishment + Final Warning"] = "Banimento + Aviso final",
|
||||
["Banishment"] = "Banimento",
|
||||
["Battle"] = "Batalha",
|
||||
["Browse"] = "Navegar",
|
||||
["Bug report sent."] = "Reporte de bug enviado.",
|
||||
["Button Assign"] = "Selecionar bot<6F>o",
|
||||
["Buy"] = "Comprar",
|
||||
["Buy Now"] = "Comparar agora",
|
||||
["Buy Offers"] = "Ofertas de compra",
|
||||
["Buy with backpack"] = "Comprar com mochila",
|
||||
["Buy"] = "Comprar",
|
||||
["Cancel"] = "Cancelar",
|
||||
["Cannot login while already in game."] = "N<EFBFBD>o <20> possivel logar enquanto j<> estiver jogando.",
|
||||
["Cap"] = "Cap",
|
||||
["Capacity"] = "Capacidade",
|
||||
["Center"] = "Centro",
|
||||
["Change language"] = "Trocar l<>ngua",
|
||||
["Channels"] = "Canais",
|
||||
["Character List"] = "Lista de personagens",
|
||||
["Classic control"] = "Controle cl<63>ssico",
|
||||
@@ -75,15 +82,16 @@ locale = {
|
||||
["Clear Messages"] = "Limpar mensagens",
|
||||
["Clear object"] = "Limpar objeto",
|
||||
["Client needs update."] = "O client do jogo precisa ser atualizado",
|
||||
["Close"] = "Fechar",
|
||||
["Close this channel"] = "Fechar esse canal",
|
||||
["Close"] = "Fechar",
|
||||
["Club Fighting"] = "Combate com Porrete",
|
||||
["Combat Controls"] = "Controles de combate",
|
||||
["Comment:"] = "Coment<EFBFBD>rio:",
|
||||
["Comment"] = "Coment<EFBFBD>rio",
|
||||
["Connecting to game server..."] = "Conectando no servidor do jogo...",
|
||||
["Connecting to login server..."] = "Conectando no servidor de autentica<63><61>o...",
|
||||
["Console"] = "Console",
|
||||
["Cooldowns"] = false,
|
||||
["Cooldown"] = "Cooldown",
|
||||
["Cooldowns"] = "Cooldowns",
|
||||
["Copy message"] = "Copiar mensagem",
|
||||
["Copy name"] = "Copiar nome",
|
||||
["Copy Name"] = "Copiar Nome",
|
||||
@@ -91,25 +99,33 @@ locale = {
|
||||
["Create mark"] = "Criar marca",
|
||||
["Create New Offer"] = "Criar nova oferta",
|
||||
["Create Offer"] = "Criar oferta",
|
||||
["Current hotkeys:"] = "Atalhos atuais",
|
||||
["Current hotkey to add: %s"] = "Atalho atual para adicionar: %s",
|
||||
["Current hotkeys:"] = "Atalhos atuais",
|
||||
["Current Offers"] = "Ofertas atuais",
|
||||
["Default"] = "Padr<EFBFBD>o",
|
||||
["Delete mark"] = "Deletar marca",
|
||||
["Description:"] = "Descri<EFBFBD><EFBFBD>o",
|
||||
["Description"] = "Descri<EFBFBD><EFBFBD>o",
|
||||
["Description:"] = "Descri<EFBFBD><EFBFBD>o",
|
||||
["Destructive Behaviour"] = "Comportamento destrutivo",
|
||||
["Detail"] = "Detalhe",
|
||||
["Details"] = "Detalhes",
|
||||
["Disable Shared Experience"] = "Desativar experi<72>ncia compartilhada",
|
||||
["Dismount"] = "Desmontar",
|
||||
["Display connection speed to the server (milliseconds)"] = "Exibir a velocidade de conex<65>o com o servidor (milisegundos)",
|
||||
["Display creature health bars"] = "Exibir barras de vida das criaturas",
|
||||
["Display creature names"] = "Exibir nomes das criaturas",
|
||||
["Display text messages"] = "Exibir mensagens de texto",
|
||||
["Distance Fighting"] = "Combate a Dist<73>ncia",
|
||||
["Don't stretch/shrink Game Window"] = "N<EFBFBD>o esticar a janela do game",
|
||||
["Don't stretch or shrink Game Window"] = "N<EFBFBD>o esticar ou contrair a janela do game",
|
||||
["Druid"] = "Druid",
|
||||
["Edit hotkey text:"] = "Editar texto do atalho",
|
||||
["Edit List"] = "Editar lista",
|
||||
["Edit Text"] = "Editar Texto",
|
||||
["Enable audio"] = "Ativar <20>udio",
|
||||
["Enable lights"] = "Ativar luzes",
|
||||
["Enable music sound"] = "Ativar m<>sica",
|
||||
["Enable music"] = "Ativar musica",
|
||||
["Enable shader effects"] = "Ativar efeitos shader",
|
||||
["Enable Shared Experience"] = "Ativar experi<72>ncia compartilhada",
|
||||
["Enable smart walking"] = "Ativar andar inteligente",
|
||||
["Enable vertical synchronization"] = "Ativar sincroniza<7A><61>o vertical",
|
||||
@@ -118,162 +134,167 @@ locale = {
|
||||
["Enter one name per line."] = "Entre somente um nome por linha.",
|
||||
["Enter with your account again to update your client."] = "Entre com sua conta denovo para atualizar o client.",
|
||||
["Error"] = "Erro",
|
||||
["Error"] = "Erro",
|
||||
["Excessive Unjustified Player Killing"] = "Assassinato em excesso, sem justificativa, de jogadores",
|
||||
["Exclude from private chat"] = "Excluir do canal privado",
|
||||
["Exit"] = "Sair",
|
||||
["Experience"] = "Experi<EFBFBD>ncia",
|
||||
["Filter list to match your level"] = "Filtrar a lista para o seu level",
|
||||
["Filter list to match your vocation"] = "Filtrar a lista para a sua voca<63><61>o",
|
||||
["Find:"] = "Procurar",
|
||||
["Find"] = "Procurar",
|
||||
["Fishing"] = "Pesca",
|
||||
["Fist Fighting"] = "Porrada",
|
||||
["Follow"] = "Seguir",
|
||||
["Force Exit"] = "For<EFBFBD>ar Saida",
|
||||
["For Your Information"] = "Para sua informa<6D><61>o",
|
||||
["Free Account"] = false,
|
||||
["Force Exit"] = "For<EFBFBD>ar Saida",
|
||||
["Formula"] = "F<EFBFBD>rmula",
|
||||
["Free Account"] = "Conta Gr<47>tis",
|
||||
["Fullscreen"] = "Tela cheia",
|
||||
["Game"] = "Jogo",
|
||||
["Game framerate limit: %s"] = "Limite da taxa de quadros do jogo: %s",
|
||||
["Graphics"] = "Gr<EFBFBD>ficos",
|
||||
["Graphics card driver not detected"] = false,
|
||||
["Game"] = "Jogo",
|
||||
["Graphics card driver not detected"] = "Driver da placa de v<>deo n<>o detectado",
|
||||
["Graphics Engine:"] = "Motor Gr<47>fico:",
|
||||
["Graphics"] = "Gr<EFBFBD>ficos",
|
||||
["Group"] = "Grupo",
|
||||
["Head"] = "Cabe<EFBFBD>a",
|
||||
["Healing"] = false,
|
||||
["Healing"] = "Curando",
|
||||
["Health Info"] = "Barra de Vida",
|
||||
["Health Information"] = "Informa<EFBFBD><EFBFBD>o de vida",
|
||||
["Hide monsters"] = "Esconder montros",
|
||||
["Hide non-skull players"] = "Esconder jogadores sem caveira",
|
||||
["Hide Npcs"] = "Esconder NPCs",
|
||||
["Hide Offline"] = false,
|
||||
["Hide Offline"] = "Esconder Offline",
|
||||
["Hide party members"] = "Esconder membros do grupo",
|
||||
["Hide players"] = "Esconder jogadores",
|
||||
["Hide spells for higher exp. levels"] = false,
|
||||
["Hide spells for other vocations"] = false,
|
||||
["Hide spells for higher exp. levels"] = "Esconder feiti<74>os de n<>vel maior",
|
||||
["Hide spells for other vocations"] = "Esconder feiti<74>os de outras voca<63><61>es",
|
||||
["Hit Points"] = "Pontos de Vida",
|
||||
["Hold left mouse button to navigate\nScroll mouse middle button to zoom\nRight mouse button to create map marks"] = false,
|
||||
["Hold left mouse button to navigate\nScroll mouse middle button to zoom\nRight mouse button to create map marks"] = "Segure o bot<6F>o esquerdo para navegar\nGire o bot<6F>o do centro do mouse para ampliar\nClique com o bot<6F>o direito do mouse para criar marcas",
|
||||
["Hotkeys"] = "Atalhos",
|
||||
["If you shut down the program, your character might stay in the game.\nClick on 'Logout' to ensure that you character leaves the game properly.\nClick on 'Exit' if you want to exit the program without logging out your character."] = "Se voc<6F> desligar o programa o seu personagem pode continuar no jogo.\nClique em 'Sair' para assegurar que seu personagem saia do jogo adequadamente.\nClique em 'For<6F>ar Saida' para fechar o programa sem desconectar seu personagem.",
|
||||
["Ignore"] = false,
|
||||
["Ignore capacity"] = "Ignorar capacidade",
|
||||
["Ignored players:"] = false,
|
||||
["Ignore equipped"] = "Ignorar equipado",
|
||||
["Ignore List"] = false,
|
||||
["Ignore players"] = false,
|
||||
["Ignore Private Messages"] = false,
|
||||
["Ignore Yelling"] = false,
|
||||
["Ignore List"] = "Lista de Ignorados",
|
||||
["Ignore players"] = "Jogadores ignorados",
|
||||
["Ignore Private Messages"] = "Ignorar mensagens privadas",
|
||||
["Ignore Yelling"] = "Ignorar gritos",
|
||||
["Ignore"] = "Ignorar",
|
||||
["Ignored players:"] = "Joadores ignorados:",
|
||||
["Interface framerate limit: %s"] = "Limite da taxa de quadros da interface: %s",
|
||||
["Inventory"] = "Invent<EFBFBD>rio",
|
||||
["Invite to Party"] = "Convidar para o grupo",
|
||||
["Invite to private chat"] = "Convidar para o canal privado",
|
||||
["IP Address Banishment"] = "Banimento de endere<72>o IP",
|
||||
["It is empty."] = "Est<EFBFBD> vazio.",
|
||||
["Item Offers"] = "Ofertas de items",
|
||||
["It is empty."] = false,
|
||||
["Join %s's Party"] = "Entrar na party do %s",
|
||||
["Knight"] = "Knight",
|
||||
["Leave Party"] = "Sair do grupo",
|
||||
["Level"] = "N<EFBFBD>vel",
|
||||
["Lifetime Premium Account"] = false,
|
||||
["Lifetime Premium Account"] = "Conta Premium para a vida toda.",
|
||||
["Limits FPS to 60"] = "Limita o FPS para 60",
|
||||
["List of items that you're able to buy"] = "Lista de itens que voc<6F> pode comprar",
|
||||
["List of items that you're able to sell"] = "Lista de itens que voc<6F> pode vender",
|
||||
["Load"] = "Carregar",
|
||||
["Logging out..."] = "Saindo...",
|
||||
["Login Error"] = "Erro de Autentica<63><61>o",
|
||||
["Login"] = "Entrar",
|
||||
["Login Error"] = "Erro de Autentica<63><61>o",
|
||||
["Login Error"] = "Erro de Autentica<63><61>o",
|
||||
["Logout"] = "Sair",
|
||||
["Look"] = "Olhar",
|
||||
["Magic Level"] = "N<EFBFBD>vel M<>gico",
|
||||
["Make sure that your client uses\nthe correct game protocol version"] = "Tenha certeza que o seu cliente use\no mesmo protocolo do servidor do jogo",
|
||||
["Mana"] = "Mana",
|
||||
["Manage hotkeys:"] = "Configurar atalhos:",
|
||||
["Market"] = "Mercado",
|
||||
["Market Offers"] = "Ofertas do mercado",
|
||||
["Market"] = "Mercado",
|
||||
["Message of the day"] = "Mensagem do dia",
|
||||
["Message to "] = "Mensagem para ",
|
||||
["Message to %s"] = "Mandar mensagem para %s",
|
||||
["Minimap"] = "Minimapa",
|
||||
["Module Manager"] = "Gerenciador de M<>dulos",
|
||||
["Module name"] = "Nome do m<>dulo",
|
||||
["Mount"] = false,
|
||||
["Mount"] = "Montar",
|
||||
["Move Stackable Item"] = "Mover item cont<6E>vel",
|
||||
["Move up"] = "Mover para cima",
|
||||
["Music volume: %d"] = "Volume da m<>sica: %d",
|
||||
["My Offers"] = "Minhas ofertas",
|
||||
["Name:"] = "Nome:",
|
||||
["Name Report"] = "Reportar Nome",
|
||||
["Name Report + Banishment"] = "Reportar Nome + Banimento",
|
||||
["Name Report + Banishment + Final Warning"] = "Reportar Nome + Banimento + Aviso Final",
|
||||
["No"] = "N<EFBFBD>o",
|
||||
["Name Report + Banishment"] = "Reportar Nome + Banimento",
|
||||
["Name Report"] = "Reportar Nome",
|
||||
["Name"] = "Nome",
|
||||
["No graphics card detected, everything will be drawn using the CPU,\nthus the performance will be really bad.\nPlease update your graphics driver to have a better performance."] = false,
|
||||
["No item selected."] = "Nenhum item selecionado",
|
||||
["No Mount"] = "Sem montaria",
|
||||
["No Outfit"] = "Sem roupa",
|
||||
["No statement has been selected."] = "Nenhuma afirma<6D><61>o foi selecionada.",
|
||||
["No"] = "N<EFBFBD>o",
|
||||
["Notation"] = "Nota<EFBFBD><EFBFBD>o",
|
||||
["NPC Trade"] = "Troca com NPC",
|
||||
["Offer History"] = "Hist<EFBFBD>rico de ofertas",
|
||||
["Offer Type"] = "Tipo de oferta",
|
||||
["Offers"] = "Ofertas",
|
||||
["Offer Type:"] = "Tipo de oferta:",
|
||||
["Offline Training"] = "Treino Offline",
|
||||
["Ok"] = "Ok",
|
||||
["on %s.\n"] = "em %s.\n",
|
||||
["Open"] = "Abrir",
|
||||
["Open a private message channel:"] = "Abrir um canal privado:",
|
||||
["Open charlist automatically when starting client"] = false,
|
||||
["Open charlist automatically when starting client"] = "Abrir lista de personagens ao iniciar o cliente",
|
||||
["Open in new window"] = "Abrir em nova janela",
|
||||
["Open new channel"] = "Abrir novo canal",
|
||||
["Open"] = "Abrir",
|
||||
["Options"] = "Op<EFBFBD><EFBFBD>es",
|
||||
["Overview"] = "Vis<EFBFBD>o geral",
|
||||
["Paladin"] = "Paladin",
|
||||
["Pass Leadership to %s"] = "Passar lideran<61>a para %s",
|
||||
["Password"] = "Senha",
|
||||
["Piece Price:"] = "Pre<EFBFBD>o por pe<70>a:",
|
||||
["Piece Price"] = "Pre<EFBFBD>o por pe<70>a",
|
||||
["Please enter a character name:"] = "Por favor, entre com o nome do personagem:",
|
||||
["Please, press the key you wish to add onto your hotkeys manager"] = "Por favor, pressione a tecla que voc<6F> deseja\nadicionar no gerenciador de atalhos",
|
||||
["Please Select"] = "Por favor, selecione algo",
|
||||
["Please use this dialog to only report bugs. Do not report rule violations here!"] = "Por favor, use este campo apenas para reportar defeitos. N<>o reporte viola<6C><61>o de regras aqui!",
|
||||
["Please wait"] = "Por favor, espere",
|
||||
["Please, press the key you wish to add onto your hotkeys manager"] = "Por favor, pressione a tecla que voc<6F> deseja\nadicionar no gerenciador de atalhos",
|
||||
["Port"] = "Porta",
|
||||
["Position:"] = false,
|
||||
["Position: %i %i %i"] = false,
|
||||
["Premium Account (%s) days left"] = false,
|
||||
["Price:"] = "Pre<EFBFBD>o",
|
||||
["Position"] = "Posi<EFBFBD><EFBFBD>o",
|
||||
["Position: %i %i %i"] = "Posi<EFBFBD><EFBFBD>o: %i %i %i",
|
||||
["Premium Account (%s) days left"] = "Conta Premium (%s) dias faltando",
|
||||
["Premium"] = "Premium",
|
||||
["Price"] = "Pre<EFBFBD>o",
|
||||
["Primary"] = "Prim<EFBFBD>rio",
|
||||
["Protocol"] = "Protocolo",
|
||||
["Quest Log"] = "Registro de Quest",
|
||||
["Randomize"] = "Embaralhar",
|
||||
["Randomize characters outfit"] = "Gerar roupa aleat<61>ria",
|
||||
["Reason:"] = "Motivo:",
|
||||
["Refresh"] = "Atualizar",
|
||||
["Randomize"] = "Embaralhar",
|
||||
["Reason"] = "Motivo",
|
||||
["Refresh Offers"] = "Atualizar Ofertas",
|
||||
["Refresh"] = "Atualizar",
|
||||
["Regeneration Time"] = "Tempo de Regenera<72><61>o",
|
||||
["Reject"] = "Rejeitar",
|
||||
["Reload All"] = "Recarregar Todos",
|
||||
["Remember account and password when starts client"] = false,
|
||||
["Remember account and password when starts client"] = "Lembrar conta e senha quando iniciar o cliente",
|
||||
["Remember password"] = "Lembrar senha",
|
||||
["Remove"] = "Remover",
|
||||
["Remove %s"] = "Remover %s",
|
||||
["Remove"] = "Remover",
|
||||
["Report Bug"] = "Reportar defeito",
|
||||
["Reserved for more functionality later."] = "Reservado para futura maior funcionalidade.",
|
||||
["Reset All"] = "Resetar Todos",
|
||||
["Reset Market"] = "Resetar Mercado",
|
||||
["Revoke %s's Invitation"] = "N<EFBFBD>o aceitar o convite do %s",
|
||||
["Rotate"] = "Girar",
|
||||
["Rule Violation"] = "Viola<EFBFBD><EFBFBD>o de regra",
|
||||
["Save"] = false,
|
||||
["Save Messages"] = false,
|
||||
["Search:"] = "Procurar:",
|
||||
["Save Messages"] = "Salvar Mensagens",
|
||||
["Save"] = "Salvar",
|
||||
["Search all items"] = "Procurar todos os items",
|
||||
["Search"] = "Procurar",
|
||||
["Secondary"] = "Secund<EFBFBD>rio",
|
||||
["Select object"] = "Selecionar objeto",
|
||||
["Select Outfit"] = "Selecionar Roupa",
|
||||
["Select your language"] = false,
|
||||
["Sell"] = "Vender",
|
||||
["Select your language"] = "Selecione sua l<>ngua",
|
||||
["Sell Now"] = "Vender agora",
|
||||
["Sell Offers"] = "Ofertas de venda",
|
||||
["Send"] = "Enviar",
|
||||
["Sell"] = "Vender",
|
||||
["Send automatically"] = "Enviar automaticamente",
|
||||
["Send Message"] = false,
|
||||
["Server"] = "Servidor",
|
||||
["Send Message"] = "Enviar Mensagem",
|
||||
["Send"] = "Enviar",
|
||||
["Server Log"] = "Registro do servidor",
|
||||
["Server"] = "Servidor",
|
||||
["Set Outfit"] = "Escolher Roupa",
|
||||
["Shielding"] = "Defesa",
|
||||
["Show all items"] = "Exibir todos os itens",
|
||||
@@ -284,57 +305,55 @@ locale = {
|
||||
["Show info messages in console"] = "Exibir mensagens informativas no console",
|
||||
["Show left panel"] = "Mostrar barra lateral esquerda",
|
||||
["Show levels in console"] = "Exibir n<>veis no console",
|
||||
["Show Offline"] = false,
|
||||
["Show Offline"] = "Mostrar Offline",
|
||||
["Show private messages in console"] = "Exibir mensagens privadas no console",
|
||||
["Show private messages on screen"] = "Exibir mensagens na tela",
|
||||
["Show Server Messages"] = false,
|
||||
["Show Server Messages"] = "Mostrar Mensagens do Servidor",
|
||||
["Show status messages in console"] = "Exibir mensagens de estado no console",
|
||||
["Show Text"] = "Mostrar texto",
|
||||
["Show timestamps in console"] = "Exibir o hor<6F>rio no console",
|
||||
["Show your depot items only"] = "Mostrar os itens somentedo dep<65>sito",
|
||||
["Skills"] = "Habilidades",
|
||||
["Soul"] = "Alma",
|
||||
["Sorcerer"] = "Sorcerer",
|
||||
["Soul Points"] = "Pontos de Alma",
|
||||
["Special"] = false,
|
||||
["Soul"] = "Alma",
|
||||
["Special"] = "Especial",
|
||||
["Speed"] = "Velocidade",
|
||||
["Spell Cooldowns"] = false,
|
||||
["Spell List"] = false,
|
||||
["Spell Cooldowns"] = "",
|
||||
["Spell List"] = "Lista de Feiti<74>os",
|
||||
["Stamina"] = "Vigor",
|
||||
["Statement:"] = "Afirma<EFBFBD><EFBFBD>o:",
|
||||
["Statement Report"] = "Afirmar Relato",
|
||||
["Statement"] = "Afirma<EFBFBD><EFBFBD>o",
|
||||
["Statistics"] = "Estat<EFBFBD>sticas",
|
||||
["Stop Attack"] = "Parar de Atacar",
|
||||
["Stop Follow"] = "Parar de Seguir",
|
||||
["Support"] = false,
|
||||
["%s: (use object)"] = "%s: (usar objeto)",
|
||||
["%s: (use object on target)"] = "%s: (usar objeto no alvo)",
|
||||
["%s: (use object on yourself)"] = "%s: (usar objeto em si)",
|
||||
["%s: (use object with crosshair)"] = "%s: (usar objeto com mira)",
|
||||
["Support"] = "Suporte",
|
||||
["Sword Fighting"] = "Combate com Espada",
|
||||
["Terminal"] = "Terminal",
|
||||
["There is no way."] = "N<EFBFBD>o h<> rota",
|
||||
["Title"] = false,
|
||||
["Total Price:"] = "Pre<EFBFBD>o total:",
|
||||
["Trade"] = "Trocar",
|
||||
["Title"] = "T<EFBFBD>tulo",
|
||||
["Total Price"] = "Pre<EFBFBD>o total",
|
||||
["Trade with ..."] = "Trocar com ...",
|
||||
["Trade"] = "Trocar",
|
||||
["Trying to reconnect in %s seconds."] = "Tentando reconectar em %s segundos.",
|
||||
["Type"] = "Tipo",
|
||||
["Unable to load dat file, please place a valid dat in '%s'"] = "N<EFBFBD>o foi poss<73>vel carregar o arquivo dat, por favor coloque um arquivo v<>lido em %s",
|
||||
["Unable to load spr file, please place a valid spr in '%s'"] = "N<EFBFBD>o foi poss<73>vel carregar o arquivo spr, por favor coloque um arquivo v<>lido em %s",
|
||||
["Unable to logout."] = "N<EFBFBD>o <20> possivel sair",
|
||||
["Unignore"] = false,
|
||||
["Unignore"] = "Designorar",
|
||||
["Unload"] = "Descarregar",
|
||||
["Update needed"] = false,
|
||||
["Use"] = "Usar",
|
||||
["Update needed"] = "Atualiza<EFBFBD><EFBFBD>o necess<73>ria",
|
||||
["Use on target"] = "Usar no alvo",
|
||||
["Use on yourself"] = "Usar em si",
|
||||
["Use with ..."] = "Usar com ...",
|
||||
["Use"] = "Usar",
|
||||
["Version"] = "Vers<EFBFBD>o",
|
||||
["VIP List"] = "Lista VIP",
|
||||
["Voc."] = "Voc.",
|
||||
["Vocation"] = false,
|
||||
["Vocation"] = "Voca<EFBFBD><EFBFBD>o",
|
||||
["Waiting List"] = "Lista de espera",
|
||||
["Website"] = "Website",
|
||||
["Weight:"] = "Peso",
|
||||
["Weight"] = "Peso",
|
||||
["Will detect when to use diagonal step based on the\nkeys you are pressing"] = "Detectar quando usar o passo diagonal\nbaseado nas teclas pressionadas",
|
||||
["With crosshair"] = "Com mira",
|
||||
["Yes"] = "Sim",
|
||||
@@ -342,9 +361,9 @@ locale = {
|
||||
["You are burning"] = "Voc<EFBFBD> est<73> queimando",
|
||||
["You are cursed"] = "Voc<EFBFBD> est<73> amaldi<64>oado",
|
||||
["You are dazzled"] = "Voc<EFBFBD> est<73> deslumbrado",
|
||||
["You are dead."] = "Voc<EFBFBD> est<73> morto.",
|
||||
["You are dead"] = "Voc<EFBFBD> est<73> morto",
|
||||
["You are drowing"] = "Voc<EFBFBD> est<73> se afogando",
|
||||
["You are dead."] = "Voc<EFBFBD> est<73> morto.",
|
||||
["You are drowning"] = "Voc<EFBFBD> est<73> se afogando",
|
||||
["You are drunk"] = "Voc<EFBFBD> est<73> b<>bado",
|
||||
["You are electrified"] = "Voc<EFBFBD> est<73> eletrificado",
|
||||
["You are freezing"] = "Voc<EFBFBD> est<73> congelando",
|
||||
@@ -356,17 +375,20 @@ locale = {
|
||||
["You are strengthened"] = "Voc<EFBFBD> est<73> refor<6F>ado",
|
||||
["You are within a protection zone"] = "Voc<EFBFBD> est<73> dentro de uma zona de prote<74><65>o",
|
||||
["You can enter new text."] = "Voc<EFBFBD> pode entrar com um novo texto.",
|
||||
["You have %s percent"] = "Voc<EFBFBD> tem %s porcento",
|
||||
["You have %d%% to advance to level %d."] = "Voc<EFBFBD> tem %d%% para avan<61>ar para o n<>vel %d.",
|
||||
["You have %s percent to go"] = "Voc<EFBFBD> tem %s porcento para avan<61>ar",
|
||||
["You have %s percent"] = "Voc<EFBFBD> tem %s porcento",
|
||||
["You may not logout during a fight"] = "Voc<EFBFBD> n<>o pode sair durante um combate",
|
||||
["You may not logout or enter a protection zone"] = "Voc<EFBFBD> n<>o pode sair ou entrar em uma zona de prote<74><65>o",
|
||||
["You must enter a comment."] = "Voc<EFBFBD> precisa entrar com um coment<6E>rio",
|
||||
["You must enter a valid server address and port."] = "Voc<EFBFBD> precisa colocar um endere<72>o e uma porta do servidor v<>lidos.",
|
||||
["You must select a character to login!"] = "Voc<EFBFBD> deve selecionar um personagem para entrar!",
|
||||
["Your Capacity:"] = "Sua capacidade:",
|
||||
["You read the following, written by \n%s\n"] = "Voc<EFBFBD> l<> o seguinte, escrito por \n%s\n",
|
||||
["You read the following, written on \n%s.\n"] = false,
|
||||
["Your Money:"] = "Seu dinheiro:",
|
||||
["You read the following, written on \n%s.\n"] = "Voc<EFBFBD> l<> o seguinte, escrito em \n%s.\n",
|
||||
["Your Capacity"] = "Sua capacidade",
|
||||
["Your character health is %d out of %d."] = "A vida do seu personagem <20> %d de %d.",
|
||||
["Your character mana is %d out of %d."] = "A mana do seu personagem <20> %d de %d.",
|
||||
["Your Money"] = "Seu dinheiro",
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -345,7 +345,7 @@ locale = {
|
||||
["You are dazzled"] = "Du <20>r chockad",
|
||||
["You are dead."] = "Du <20>r d<>d.",
|
||||
["You are dead"] = "Du <20>r d<>d",
|
||||
["You are drowing"] = "Du drunknar",
|
||||
["You are drowning"] = "Du drunknar",
|
||||
["You are drunk"] = "Du <20>r full.",
|
||||
["You are electrified"] = "Du <20>r elektrifierad",
|
||||
["You are freezing"] = "Du Fryser",
|
||||
|
@@ -1,35 +1,36 @@
|
||||
Particle
|
||||
name: default_particle
|
||||
name: groupcooldown_particle
|
||||
|
||||
duration: 10
|
||||
duration: 0.4
|
||||
min-position-radius: 0
|
||||
max-position-radius: 256
|
||||
max-position-radius: 32
|
||||
min-position-angle: 0
|
||||
max-position-angle: 360
|
||||
velocity: 10
|
||||
min-velocity-angle: 0
|
||||
max-velocity-angle: 360
|
||||
colors: #ffffff00 #ffffffff #00000000
|
||||
colors: #ffffff00 #ffffffff #fff13000
|
||||
colors-stops: 0 0.1 1
|
||||
size: 24 24
|
||||
texture: /data/particles/particle
|
||||
size: 1 1
|
||||
texture: /particles/particle
|
||||
composition-mode: normal
|
||||
|
||||
Effect
|
||||
name: background-effect
|
||||
description: Effect for the game background
|
||||
name: groupcooldown-effect
|
||||
description: Effect for group cooldowns in the cooldown module
|
||||
|
||||
System
|
||||
position: 0 0
|
||||
|
||||
Emitter
|
||||
position: 0 0
|
||||
delay: 0
|
||||
duration: 0
|
||||
burst-rate: 50
|
||||
burst-count: 1
|
||||
particle-type: default_particle
|
||||
delay: 0.06
|
||||
duration: 0.2
|
||||
burst-rate: 350
|
||||
burst-count: 50
|
||||
particle-type: groupcooldown_particle
|
||||
|
||||
AttractionAffector
|
||||
position: 0 0
|
||||
acceleration: 1000
|
||||
|
||||
|
@@ -4,6 +4,7 @@ TextList < UIScrollArea
|
||||
border-color: #1d222b
|
||||
background-color: #222833
|
||||
padding: 1
|
||||
auto-focus: none
|
||||
|
||||
HorizontalList < UIScrollArea
|
||||
layout: horizontalBox
|
||||
|
@@ -1,8 +1,10 @@
|
||||
Panel < UIWidget
|
||||
phantom: true
|
||||
auto-focus: first
|
||||
|
||||
ScrollablePanel < UIScrollArea
|
||||
phantom: true
|
||||
auto-focus: first
|
||||
|
||||
FlatPanel < Panel
|
||||
image-source: /images/ui/panel_flat
|
||||
|
@@ -4,6 +4,15 @@ ProgressBar < UIProgressBar
|
||||
border: 1 black
|
||||
image-source: /images/ui/progressbar
|
||||
image-border: 1
|
||||
font: verdana-11px-rounded
|
||||
text-offset: 0 2
|
||||
on: true
|
||||
|
||||
$!on:
|
||||
visible: false
|
||||
margin-top: 0
|
||||
margin-bottom: 0
|
||||
height: 0
|
||||
|
||||
ProgressRect < UIProgressRect
|
||||
anchors.fill: parent
|
||||
|
6
data/styles/20-imageview.otui
Normal file
@@ -0,0 +1,6 @@
|
||||
ImageView < UIImageView
|
||||
image-smooth: false
|
||||
image-fixed-ratio: true
|
||||
draggable: true
|
||||
border-width: 2
|
||||
border-color: #000000
|
@@ -1,17 +1,9 @@
|
||||
PopupMenuButton < UIButton
|
||||
height: 18
|
||||
margin-left: 5
|
||||
margin-right: 5
|
||||
margin-top: 1
|
||||
margin-bottom: 1
|
||||
size: 0 21
|
||||
text-offset: 0 0
|
||||
text-offset: 4 0
|
||||
text-align: left
|
||||
font: verdana-11px-antialised
|
||||
|
||||
image-source: /images/ui/button_popupmenu
|
||||
image-color: white
|
||||
image-clip: 0 0 20 20
|
||||
image-border: 2
|
||||
|
||||
color: #aaaaaa
|
||||
background-color: alpha
|
||||
@@ -24,6 +16,13 @@ PopupMenuButton < UIButton
|
||||
$disabled:
|
||||
color: #555555
|
||||
|
||||
PopupMenuShortcutLabel < Label
|
||||
font: verdana-11px-antialised
|
||||
text-align: right
|
||||
anchors.fill: parent
|
||||
margin-right: 2
|
||||
margin-left: 5
|
||||
|
||||
PopupMenuSeparator < UIWidget
|
||||
margin-left: 2
|
||||
margin-right: 2
|
||||
@@ -39,5 +38,4 @@ PopupMenu < UIPopupMenu
|
||||
width: 50
|
||||
image-source: /images/ui/menubox
|
||||
image-border: 3
|
||||
padding-top: 3
|
||||
padding-bottom: 3
|
||||
padding: 3
|
||||
|
@@ -104,7 +104,7 @@ TabBarVerticalButton < UIButton
|
||||
anchors.top: parent.top
|
||||
$!first:
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
margin-top: 10
|
||||
$hover !checked:
|
||||
color: white
|
||||
icon-color: #cccccc
|
||||
|
@@ -6,6 +6,9 @@ TopButton < UIButton
|
||||
image-color: #ffffffff
|
||||
icon-color: #ffffffff
|
||||
|
||||
$on:
|
||||
image-source: /images/ui/button_top_blink
|
||||
|
||||
$hover !disabled:
|
||||
image-color: #ffffff99
|
||||
image-clip: 26 0 26 26
|
||||
@@ -46,4 +49,4 @@ TopMenuPanel < Panel
|
||||
TopMenuFrameCounterLabel < FrameCounterLabel
|
||||
color: white
|
||||
margin-top: 4
|
||||
margin-left: 5
|
||||
margin-left: 5
|
||||
|
266
data/styles/30-minimap.otui
Normal file
@@ -0,0 +1,266 @@
|
||||
MinimapFlag < UIWidget
|
||||
size: 11 11
|
||||
anchors.left: parent.left
|
||||
anchors.top: parent.top
|
||||
|
||||
MinimapFlags < UIWidget
|
||||
anchors.fill: parent
|
||||
|
||||
MinimapFloorUpButton < Button
|
||||
size: 20 20
|
||||
margin-right: 28
|
||||
margin-bottom: 28
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
icon-source: /images/game/minimap/floor_up
|
||||
icon-clip: 0 32 16 16
|
||||
$pressed:
|
||||
icon-clip: 0 0 16 16
|
||||
$hover !pressed:
|
||||
icon-clip: 0 16 16 16
|
||||
|
||||
MinimapFloorDownButton < Button
|
||||
size: 20 20
|
||||
margin-right: 28
|
||||
margin-bottom: 4
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
icon-source: /images/game/minimap/floor_down
|
||||
icon-clip: 0 32 16 16
|
||||
$pressed:
|
||||
icon-clip: 0 0 16 16
|
||||
$hover !pressed:
|
||||
icon-clip: 0 16 16 16
|
||||
|
||||
MinimapZoomInButton < Button
|
||||
text: +
|
||||
size: 20 20
|
||||
margin-right: 4
|
||||
margin-bottom: 28
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
//icon-source: /images/game/minimap/zoom_in
|
||||
|
||||
MinimapZoomOutButton < Button
|
||||
text: -
|
||||
size: 20 20
|
||||
margin-right: 4
|
||||
margin-bottom: 4
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
//icon-source: /images/game/minimap/zoom_out
|
||||
|
||||
MinimapResetButton < Button
|
||||
!text: tr('Center')
|
||||
size: 44 20
|
||||
anchors.left: parent.left
|
||||
anchors.top: parent.top
|
||||
margin: 4
|
||||
|
||||
Minimap < UIMinimap
|
||||
draggable: true
|
||||
focusable: false
|
||||
cross: true
|
||||
@onGeometryChange: self:updateFlags()
|
||||
|
||||
MinimapFlags
|
||||
id: flags
|
||||
phantom: true
|
||||
focusable: false
|
||||
|
||||
MinimapFloorUpButton
|
||||
id: floorUp
|
||||
@onClick: self:getParent():floorUp(1)
|
||||
|
||||
MinimapFloorDownButton
|
||||
id: floorDown
|
||||
@onClick: self:getParent():floorDown(1)
|
||||
|
||||
MinimapZoomInButton
|
||||
id: zoomIn
|
||||
@onClick: self:getParent():zoomIn()
|
||||
|
||||
MinimapZoomOutButton
|
||||
id: zoomOut
|
||||
@onClick: self:getParent():zoomOut()
|
||||
|
||||
MinimapResetButton
|
||||
id: reset
|
||||
@onClick: self:getParent():reset()
|
||||
|
||||
|
||||
// Minimap Flag Create Window
|
||||
|
||||
|
||||
MinimapFlagCheckBox < CheckBox
|
||||
size: 15 15
|
||||
margin-left: 2
|
||||
image-source: /images/game/minimap/flagcheckbox
|
||||
image-size: 15 15
|
||||
image-border: 3
|
||||
icon-source: /images/game/minimap/mapflags
|
||||
icon-size: 11 11
|
||||
icon-offset: 2 4
|
||||
anchors.left: prev.right
|
||||
anchors.top: prev.top
|
||||
$!checked:
|
||||
image-clip: 26 0 26 26
|
||||
$hover !checked:
|
||||
image-clip: 78 0 26 26
|
||||
$checked:
|
||||
image-clip: 0 0 26 26
|
||||
$hover checked:
|
||||
image-clip: 52 0 26 26
|
||||
|
||||
MinimapFlagWindow < MainWindow
|
||||
!text: tr('Create Map Mark')
|
||||
size: 196 185
|
||||
|
||||
Label
|
||||
!text: tr('Position') .. ':'
|
||||
text-auto-resize: true
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
margin-top: 2
|
||||
|
||||
Label
|
||||
id: position
|
||||
text-auto-resize: true
|
||||
anchors.top: parent.top
|
||||
anchors.right: parent.right
|
||||
margin-top: 2
|
||||
|
||||
Label
|
||||
!text: tr('Description') .. ':'
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 7
|
||||
|
||||
TextEdit
|
||||
id: description
|
||||
margin-top: 3
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.right
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag0
|
||||
icon-source: /images/game/minimap/flag0
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 6
|
||||
margin-left: 0
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag1
|
||||
icon-source: /images/game/minimap/flag1
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag2
|
||||
icon-source: /images/game/minimap/flag2
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag3
|
||||
icon-source: /images/game/minimap/flag3
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag4
|
||||
icon-source: /images/game/minimap/flag4
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag5
|
||||
icon-source: /images/game/minimap/flag5
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag6
|
||||
icon-source: /images/game/minimap/flag6
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag7
|
||||
icon-source: /images/game/minimap/flag7
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag8
|
||||
icon-source: /images/game/minimap/flag8
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag9
|
||||
icon-source: /images/game/minimap/flag9
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag10
|
||||
icon-source: /images/game/minimap/flag10
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 6
|
||||
margin-left: 0
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag11
|
||||
icon-source: /images/game/minimap/flag11
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag12
|
||||
icon-source: /images/game/minimap/flag12
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag13
|
||||
icon-source: /images/game/minimap/flag13
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag14
|
||||
icon-source: /images/game/minimap/flag14
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag15
|
||||
icon-source: /images/game/minimap/flag15
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag16
|
||||
icon-source: /images/game/minimap/flag16
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag17
|
||||
icon-source: /images/game/minimap/flag17
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag18
|
||||
icon-source: /images/game/minimap/flag18
|
||||
|
||||
MinimapFlagCheckBox
|
||||
id: flag19
|
||||
icon-source: /images/game/minimap/flag19
|
||||
|
||||
Button
|
||||
id: okButton
|
||||
!text: tr('Ok')
|
||||
width: 64
|
||||
anchors.right: next.left
|
||||
anchors.bottom: parent.bottom
|
||||
margin-right: 10
|
||||
|
||||
Button
|
||||
id: cancelButton
|
||||
!text: tr('Cancel')
|
||||
width: 64
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
|
||||
// Minimap Full Panel
|
||||
|
||||
MinimapFullPanel < FlatPanel
|
||||
phantom: false
|
||||
anchors.fill: parent
|
||||
anchors.top: topMenu.bottom
|
||||
|
||||
ImageView
|
||||
id: image
|
||||
anchors.fill: parent
|
||||
|
||||
Button
|
||||
!text: tr('Close')
|
||||
margin-right: 4
|
||||
margin-top: 4
|
||||
anchors.right: parent.right
|
||||
anchors.top: parent.top
|
||||
@onClick: self:getParent():destroy()
|
8
init.lua
@@ -3,6 +3,7 @@
|
||||
|
||||
-- setup logger
|
||||
g_logger.setLogFile(g_resources.getWorkDir() .. g_app.getCompactName() .. ".log")
|
||||
g_logger.info(os.date("== application started at %b %d %Y %X"))
|
||||
|
||||
-- print first terminal message
|
||||
g_logger.info(g_app.getName() .. ' ' .. g_app.getVersion() .. ' rev ' .. g_app.getBuildRevision() .. ' (' .. g_app.getBuildCommit() .. ') built on ' .. g_app.getBuildDate() .. ' for arch ' .. g_app.getBuildArch())
|
||||
@@ -47,7 +48,8 @@ g_modules.ensureModuleLoaded("game_interface")
|
||||
-- mods 1000-9999
|
||||
g_modules.autoLoadModules(9999)
|
||||
|
||||
if g_resources.fileExists("/otclientrc") then
|
||||
dofile("/otclientrc")
|
||||
end
|
||||
local script = '/' .. g_app.getCompactName() .. 'rc'
|
||||
|
||||
if g_resources.fileExists(script) then
|
||||
dofile(script)
|
||||
end
|
@@ -13,7 +13,12 @@ end
|
||||
function reloadScripts()
|
||||
g_textures.clearTexturesCache()
|
||||
g_modules.reloadModules()
|
||||
dofile('/' .. g_app.getCompactName() .. 'rc')
|
||||
|
||||
local script = '/' .. g_app.getCompactName() .. 'rc'
|
||||
if g_resources.fileExists(script) then
|
||||
dofile(script)
|
||||
end
|
||||
|
||||
local message = tr('All modules and scripts were reloaded.')
|
||||
|
||||
modules.game_textmessage.displayGameMessage(message)
|
||||
@@ -48,6 +53,9 @@ function startup()
|
||||
end
|
||||
|
||||
function init()
|
||||
connect(g_app, { onRun = startup,
|
||||
onExit = exit })
|
||||
|
||||
g_window.setMinimumSize({ width = 600, height = 480 })
|
||||
g_sounds.preload(musicFilename)
|
||||
|
||||
@@ -82,10 +90,16 @@ function init()
|
||||
|
||||
g_keyboard.bindKeyDown('Ctrl+Shift+R', reloadScripts)
|
||||
|
||||
connect(g_app, { onRun = startup })
|
||||
-- generate machine uuid, this is a security measure for storing passwords
|
||||
if not g_crypt.setMachineUUID(g_configs.get('uuid')) then
|
||||
g_configs.set('uuid', g_crypt.getMachineUUID())
|
||||
g_configs.save()
|
||||
end
|
||||
end
|
||||
|
||||
function terminate()
|
||||
disconnect(g_app, { onRun = startup,
|
||||
onExit = exit })
|
||||
-- save window configs
|
||||
g_settings.set('window-size', g_window.getUnmaximizedSize())
|
||||
g_settings.set('window-pos', g_window.getUnmaximizedPos())
|
||||
@@ -96,3 +110,7 @@ function terminate()
|
||||
g_settings.set('protocol-version', protocolVersion)
|
||||
end
|
||||
end
|
||||
|
||||
function exit()
|
||||
g_logger.info("Exiting application..")
|
||||
end
|
||||
|
@@ -25,7 +25,6 @@ function terminate()
|
||||
|
||||
g_effects.cancelFade(background:getChildById('clientVersionLabel'))
|
||||
background:destroy()
|
||||
background = nil
|
||||
|
||||
Background = nil
|
||||
end
|
||||
|
@@ -13,25 +13,21 @@ local resendWaitEvent
|
||||
local function tryLogin(charInfo, tries)
|
||||
tries = tries or 1
|
||||
|
||||
if tries > 4 then
|
||||
CharacterList.destroyLoadBox()
|
||||
displayErrorBox(tr('Error'), tr('Unable to logout.'))
|
||||
if tries > 50 then
|
||||
return
|
||||
end
|
||||
|
||||
if g_game.isOnline() then
|
||||
if tries == 1 then
|
||||
g_game.safeLogout()
|
||||
loadBox = displayCancelBox(tr('Please wait'), tr('Logging out...'))
|
||||
end
|
||||
scheduleEvent(function() tryLogin(charInfo, tries+1) end, 250)
|
||||
scheduleEvent(function() tryLogin(charInfo, tries+1) end, 100)
|
||||
return
|
||||
end
|
||||
|
||||
CharacterList.destroyLoadBox()
|
||||
CharacterList.hide()
|
||||
|
||||
local locale = modules.client_locales.getCurrentLocale().name
|
||||
g_game.loginWorld(G.account, G.password, charInfo.worldName, charInfo.worldHost, charInfo.worldPort, charInfo.characterName, locale)
|
||||
g_game.loginWorld(G.account, G.password, charInfo.worldName, charInfo.worldHost, charInfo.worldPort, charInfo.characterName)
|
||||
|
||||
loadBox = displayCancelBox(tr('Please wait'), tr('Connecting to game server...'))
|
||||
connect(loadBox, { onCancel = function()
|
||||
@@ -41,7 +37,8 @@ local function tryLogin(charInfo, tries)
|
||||
end })
|
||||
|
||||
-- save last used character
|
||||
g_settings.set('lastUsedCharacter', charInfo.characterName)
|
||||
g_settings.set('last-used-character', charInfo.characterName)
|
||||
g_settings.set('last-used-world', charInfo.worldName)
|
||||
end
|
||||
|
||||
local function updateWait(timeStart, timeEnd)
|
||||
@@ -227,12 +224,15 @@ function CharacterList.create(characters, account, otui)
|
||||
|
||||
connect(widget, { onDoubleClick = function () CharacterList.doLogin() return true end } )
|
||||
|
||||
if i == 1 or g_settings.get('lastUsedCharacter') == widget.characterName then
|
||||
if i == 1 or (g_settings.get('last-used-character') == widget.characterName and g_settings.get('last-used-world') == widget.worldName) then
|
||||
focusLabel = widget
|
||||
end
|
||||
end
|
||||
|
||||
characterList:focusChild(focusLabel, ActiveFocusReason)
|
||||
if focusLabel then
|
||||
characterList:focusChild(focusLabel, KeyboardFocusReason)
|
||||
addEvent(function() characterList:ensureChildVisible(focusLabel) end)
|
||||
end
|
||||
|
||||
-- account
|
||||
if account.premDays > 0 and account.premDays < 65535 then
|
||||
|
@@ -1,33 +1,36 @@
|
||||
CharacterWidget < UIWidget
|
||||
height: 14
|
||||
focusable: true
|
||||
background-color: alpha
|
||||
@onFocusChange: |
|
||||
local children = self:getChildren()
|
||||
for i=1,#children do
|
||||
children[i]:setOn(self:isFocused())
|
||||
&updateOnStates: |
|
||||
function(self)
|
||||
local children = self:getChildren()
|
||||
for i=1,#children do
|
||||
children[i]:setOn(self:isFocused())
|
||||
end
|
||||
end
|
||||
@onFocusChange: self:updateOnStates()
|
||||
@onSetup: self:updateOnStates()
|
||||
|
||||
$focus:
|
||||
background-color: #ffffff22
|
||||
|
||||
Label
|
||||
id: name
|
||||
color: #ffffff
|
||||
color: #aaaaaa
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
font: verdana-11px-monochrome
|
||||
text-auto-resize: true
|
||||
background-color: alpha
|
||||
text-offset: 2 0
|
||||
on: true
|
||||
|
||||
$!on:
|
||||
color: #aaaaaa
|
||||
$on:
|
||||
color: #ffffff
|
||||
|
||||
Label
|
||||
id: worldName
|
||||
color: #ffffff
|
||||
color: #aaaaaa
|
||||
anchors.top: parent.top
|
||||
anchors.right: parent.right
|
||||
margin-right: 5
|
||||
@@ -35,10 +38,9 @@ CharacterWidget < UIWidget
|
||||
text-auto-resize: true
|
||||
background-color: alpha
|
||||
&baseText: '(%s)'
|
||||
on: true
|
||||
|
||||
$!on:
|
||||
color: #aaaaaa
|
||||
$on:
|
||||
color: #ffffff
|
||||
|
||||
MainWindow
|
||||
id: charactersWindow
|
||||
@@ -61,6 +63,7 @@ MainWindow
|
||||
padding: 1
|
||||
focusable: false
|
||||
vertical-scrollbar: characterListScrollBar
|
||||
auto-focus: first
|
||||
|
||||
VerticalScrollBar
|
||||
id: characterListScrollBar
|
||||
@@ -73,7 +76,7 @@ MainWindow
|
||||
|
||||
Label
|
||||
id: accountStatusCaption
|
||||
!text: tr('Account Status:')
|
||||
!text: tr('Account Status') .. ':'
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: next.top
|
||||
|
@@ -7,6 +7,7 @@ local motdWindow
|
||||
local motdButton
|
||||
local enterGameButton
|
||||
local protocolBox
|
||||
local protocolLogin
|
||||
|
||||
-- private functions
|
||||
local function onError(protocol, message, errorCode)
|
||||
@@ -47,25 +48,28 @@ local function onCharacterList(protocol, characters, account, otui)
|
||||
local lastMotdNumber = g_settings.getNumber("motd")
|
||||
if G.motdNumber and G.motdNumber ~= lastMotdNumber then
|
||||
g_settings.set("motd", motdNumber)
|
||||
local motdBox = displayInfoBox(tr('Message of the day'), G.motdMessage)
|
||||
connect(motdBox, { onOk = CharacterList.show })
|
||||
motdWindow = displayInfoBox(tr('Message of the day'), G.motdMessage)
|
||||
connect(motdWindow, { onOk = function() CharacterList.show() motdWindow = nil end })
|
||||
CharacterList.hide()
|
||||
end
|
||||
end
|
||||
|
||||
local function onChangeProtocol(combobox, option)
|
||||
local clients = g_game.getSupportedClients(option)
|
||||
protocolBox:setTooltip("Supports Client" .. (#clients > 1 and "s" or "") .. ": " .. table.toString(clients))
|
||||
protocolBox:setTooltip("Supports Client" .. (#clients > 1 and "s" or "") .. ": " .. table.tostring(clients))
|
||||
end
|
||||
|
||||
local function onUpdateNeeded(protocol, signature)
|
||||
loadBox:destroy()
|
||||
loadBox = nil
|
||||
|
||||
if updateFunc then
|
||||
if EnterGame.updateFunc then
|
||||
local continueFunc = EnterGame.show
|
||||
local cancelFunc = EnterGame.show
|
||||
updateFunc(signature, continueFunc, cancelFunc)
|
||||
EnterGame.updateFunc(signature, continueFunc, cancelFunc)
|
||||
else
|
||||
local errorBox = displayErrorBox(tr('Update needed'), tr('Your client needs update, try redownloading it.'))
|
||||
connect(errorBox, { onOk = EnterGame.show })
|
||||
end
|
||||
end
|
||||
|
||||
@@ -91,12 +95,12 @@ function EnterGame.init()
|
||||
if port == nil or port == 0 then port = 7171 end
|
||||
|
||||
enterGame:getChildById('accountNameTextEdit'):setText(account)
|
||||
enterGame:getChildById('accountNameTextEdit'):setCursorPos(-1)
|
||||
enterGame:getChildById('accountPasswordTextEdit'):setText(password)
|
||||
enterGame:getChildById('serverHostTextEdit'):setText(host)
|
||||
enterGame:getChildById('serverPortTextEdit'):setText(port)
|
||||
enterGame:getChildById('autoLoginBox'):setChecked(autologin)
|
||||
enterGame:getChildById('rememberPasswordBox'):setChecked(#account > 0)
|
||||
enterGame:getChildById('accountNameTextEdit'):focus()
|
||||
|
||||
protocolBox = enterGame:getChildById('protocolComboBox')
|
||||
protocolBox.onOptionChange = onChangeProtocol
|
||||
@@ -134,6 +138,7 @@ function EnterGame.terminate()
|
||||
enterGame = nil
|
||||
enterGameButton:destroy()
|
||||
enterGameButton = nil
|
||||
protocolBox = nil
|
||||
if motdWindow then
|
||||
motdWindow:destroy()
|
||||
motdWindow = nil
|
||||
@@ -142,7 +147,14 @@ function EnterGame.terminate()
|
||||
motdButton:destroy()
|
||||
motdButton = nil
|
||||
end
|
||||
protocolBox = nil
|
||||
if loadBox then
|
||||
loadBox:destroy()
|
||||
loadBox = nil
|
||||
end
|
||||
if protocolLogin then
|
||||
protocolLogin:cancelLogin()
|
||||
protocolLogin = nil
|
||||
end
|
||||
EnterGame = nil
|
||||
end
|
||||
|
||||
@@ -192,7 +204,7 @@ function EnterGame.doLogin()
|
||||
g_settings.set('host', G.host)
|
||||
g_settings.set('port', G.port)
|
||||
|
||||
local protocolLogin = ProtocolLogin.create()
|
||||
protocolLogin = ProtocolLogin.create()
|
||||
protocolLogin.onError = onError
|
||||
protocolLogin.onMotd = onMotd
|
||||
protocolLogin.onCharacterList = onCharacterList
|
||||
@@ -212,8 +224,7 @@ function EnterGame.doLogin()
|
||||
end
|
||||
|
||||
if modules.game_things.isLoaded() then
|
||||
local locale = modules.client_locales.getCurrentLocale().name
|
||||
protocolLogin:login(G.host, G.port, G.account, G.password, locale)
|
||||
protocolLogin:login(G.host, G.port, G.account, G.password)
|
||||
else
|
||||
loadBox:destroy()
|
||||
loadBox = nil
|
||||
@@ -222,7 +233,7 @@ function EnterGame.doLogin()
|
||||
end
|
||||
|
||||
function EnterGame.displayMotd()
|
||||
if not motdWindow or not motdWindow:isVisible() then
|
||||
if not motdWindow then
|
||||
motdWindow = displayInfoBox(tr('Message of the day'), G.motdMessage)
|
||||
motdWindow.onOk = function() motdWindow = nil end
|
||||
end
|
||||
|
@@ -116,3 +116,4 @@ EnterGameWindow
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
color: green
|
||||
text-auto-resize: true
|
||||
|
@@ -17,14 +17,22 @@ end
|
||||
function createWindow()
|
||||
localesWindow = g_ui.displayUI('locales')
|
||||
local localesPanel = localesWindow:getChildById('localesPanel')
|
||||
local layout = localesPanel:getLayout()
|
||||
local spacing = layout:getCellSpacing()
|
||||
local size = layout:getCellSize()
|
||||
|
||||
local count = 0
|
||||
for name,locale in pairs(installedLocales) do
|
||||
local widget = g_ui.createWidget('LocalesButton', localesPanel)
|
||||
widget:setImageSource('/images/flags/' .. name .. '')
|
||||
widget:setText(locale.languageName)
|
||||
widget.onClick = function() selectFirstLocale(name) end
|
||||
count = count + 1
|
||||
end
|
||||
|
||||
count = math.max(1, math.min(count, 3))
|
||||
localesPanel:setWidth(size.width*count + spacing*(count-1))
|
||||
|
||||
addEvent(function() addEvent(function() localesWindow:raise() localesWindow:focus() end) end)
|
||||
end
|
||||
|
||||
@@ -61,7 +69,7 @@ function init()
|
||||
pdebug('Using configured locale: ' .. userLocaleName)
|
||||
else
|
||||
setLocale(defaultLocaleName)
|
||||
connect(g_app, {onRun = createWindow})
|
||||
connect(g_app, { onRun = createWindow })
|
||||
end
|
||||
|
||||
ProtocolGame.registerExtendedOpcode(ExtendedIds.Locale, onExtendedLocales)
|
||||
@@ -73,6 +81,7 @@ function terminate()
|
||||
currentLocale = nil
|
||||
|
||||
ProtocolGame.unregisterExtendedOpcode(ExtendedIds.Locale)
|
||||
disconnect(g_app, { onRun = createWindow })
|
||||
disconnect(g_game, { onGameStart = onGameStart })
|
||||
end
|
||||
|
||||
@@ -101,6 +110,8 @@ function installLocale(locale)
|
||||
error('Unable to install locale.')
|
||||
end
|
||||
|
||||
if _G.allowedLocales and not _G.allowedLocales[locale.name] then return end
|
||||
|
||||
if locale.name ~= defaultLocaleName then
|
||||
local updatesNeeded = 0
|
||||
for _i,k in pairs(neededTranslations) do
|
||||
@@ -130,6 +141,7 @@ end
|
||||
|
||||
function setLocale(name)
|
||||
local locale = installedLocales[name]
|
||||
if locale == currentLocale then return end
|
||||
if not locale then
|
||||
pwarning("Locale " .. name .. ' does not exist.')
|
||||
return false
|
||||
|
@@ -24,8 +24,6 @@ UIWindow
|
||||
|
||||
Panel
|
||||
id: localesPanel
|
||||
!width: 96*3 + 32*3
|
||||
margin-left: 16
|
||||
margin-top: 50
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
anchors.top: prev.bottom
|
||||
|
@@ -339,7 +339,7 @@ neededTranslations = {
|
||||
"You are dazzled",
|
||||
"You are dead.",
|
||||
"You are dead",
|
||||
"You are drowing",
|
||||
"You are drowning",
|
||||
"You are drunk",
|
||||
"You are electrified",
|
||||
"You are freezing",
|
||||
|
@@ -20,18 +20,16 @@ function init()
|
||||
addEvent(listModules)
|
||||
end
|
||||
|
||||
function hideButton()
|
||||
moduleManagerButton:hide()
|
||||
end
|
||||
|
||||
function terminate()
|
||||
moduleManagerWindow:destroy()
|
||||
moduleManagerWindow = nil
|
||||
moduleManagerButton:destroy()
|
||||
moduleManagerButton = nil
|
||||
moduleList = nil
|
||||
end
|
||||
|
||||
function disable()
|
||||
moduleManagerButton:hide()
|
||||
end
|
||||
|
||||
function hide()
|
||||
moduleManagerWindow:hide()
|
||||
end
|
||||
|
36
modules/client_options/audio.otui
Normal file
@@ -0,0 +1,36 @@
|
||||
VolumeScrollbar < HorizontalScrollBar
|
||||
step: 1
|
||||
@onValueChange: modules.client_options.setOption(self:getId(), self:getValue())
|
||||
@onSetup: |
|
||||
UIScrollBar.onSetup(self)
|
||||
local value = modules.client_options.getOption(self:getId())
|
||||
self:setValue(value)
|
||||
|
||||
Panel
|
||||
OptionCheckBox
|
||||
id: enableAudio
|
||||
!text: tr('Enable audio')
|
||||
|
||||
OptionCheckBox
|
||||
id: enableMusicSound
|
||||
!text: tr('Enable music sound')
|
||||
|
||||
Label
|
||||
id: musicSoundVolumeLabel
|
||||
!text: tr('Music volume: %d', 100)
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 6
|
||||
@onSetup: |
|
||||
local value = modules.client_options.getOption('musicSoundVolume')
|
||||
self:setText(tr('Music volume: %d', value))
|
||||
|
||||
VolumeScrollbar
|
||||
id: musicSoundVolume
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 3
|
||||
minimum: 0
|
||||
maximum: 100
|
@@ -12,15 +12,6 @@ Panel
|
||||
!text: tr('Enable smart walking')
|
||||
!tooltip: tr('Will detect when to use diagonal step based on the\nkeys you are pressing')
|
||||
|
||||
OptionCheckBox
|
||||
id: walkBooster
|
||||
!text: tr('Enable walk booster')
|
||||
!tooltip: tr('Also known as dash in tibia community, recommended\nfor playing characters with high speed')
|
||||
|
||||
OptionCheckBox
|
||||
id: enableMusic
|
||||
!text: tr('Enable music')
|
||||
|
||||
OptionCheckBox
|
||||
id: showPing
|
||||
!text: tr('Show connection ping')
|
||||
@@ -30,6 +21,18 @@ Panel
|
||||
id: showLeftPanel
|
||||
!text: tr('Show left panel')
|
||||
|
||||
OptionCheckBox
|
||||
id: displayNames
|
||||
!text: tr('Display creature names')
|
||||
|
||||
OptionCheckBox
|
||||
id: displayHealth
|
||||
!text: tr('Display creature health bars')
|
||||
|
||||
OptionCheckBox
|
||||
id: displayText
|
||||
!text: tr('Display text messages')
|
||||
|
||||
Button
|
||||
id: changeLocale
|
||||
!text: tr('Change language')
|
||||
@@ -37,3 +40,4 @@ Panel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: prev.left
|
||||
margin-top: 5
|
||||
width: 120
|
||||
|
@@ -8,18 +8,12 @@ FrameRateScrollbar < HorizontalScrollBar
|
||||
self:setValue(value)
|
||||
|
||||
Panel
|
||||
Label
|
||||
!text: tr('Graphics Engine:')
|
||||
anchors.left: parent.left
|
||||
anchors.top: parent.top
|
||||
|
||||
ButtonBox
|
||||
id: opengl1
|
||||
anchors.left: prev.right
|
||||
anchors.verticalCenter: prev.verticalCenter
|
||||
anchors.left: parent.left
|
||||
anchors.top: parent.top
|
||||
text: OpenGL 1
|
||||
size: 80 20
|
||||
margin-left: 6
|
||||
|
||||
ButtonBox
|
||||
id: opengl2
|
||||
@@ -29,6 +23,14 @@ Panel
|
||||
size: 80 20
|
||||
margin-left: 4
|
||||
|
||||
ButtonBox
|
||||
id: directx9
|
||||
anchors.left: prev.right
|
||||
anchors.verticalCenter: prev.verticalCenter
|
||||
text: DirectX 9
|
||||
size: 80 20
|
||||
margin-left: 4
|
||||
|
||||
OptionCheckBox
|
||||
id: vsync
|
||||
!text: tr('Enable vertical synchronization')
|
||||
@@ -39,12 +41,13 @@ Panel
|
||||
!text: tr('Show frame rate')
|
||||
|
||||
OptionCheckBox
|
||||
id: fullscreen
|
||||
!text: tr('Fullscreen')
|
||||
id: enableLights
|
||||
!text: tr('Enable lights')
|
||||
|
||||
OptionCheckBox
|
||||
id: dontStretchShrink
|
||||
!text: tr("Don't stretch or shrink Game Window")
|
||||
id: fullscreen
|
||||
!text: tr('Fullscreen')
|
||||
tooltip: Ctrl+Shift+F
|
||||
|
||||
Label
|
||||
id: backgroundFrameRateLabel
|
||||
@@ -52,7 +55,7 @@ Panel
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 16
|
||||
margin-top: 6
|
||||
@onSetup: |
|
||||
local value = modules.client_options.getOption('backgroundFrameRate')
|
||||
local text = value
|
||||
|
@@ -1,11 +1,9 @@
|
||||
local defaultOptions = {
|
||||
vsync = false,
|
||||
showFps = true,
|
||||
showPing = true,
|
||||
showFps = false,
|
||||
showPing = false,
|
||||
fullscreen = false,
|
||||
dontStretchShrink = false,
|
||||
classicControl = false,
|
||||
walkBooster = false,
|
||||
smartWalk = false,
|
||||
autoChaseOverride = true,
|
||||
showStatusMessagesInConsole = true,
|
||||
@@ -13,40 +11,60 @@ local defaultOptions = {
|
||||
showInfoMessagesInConsole = true,
|
||||
showTimestampsInConsole = true,
|
||||
showLevelsInConsole = true,
|
||||
showPrivateMessagesInConsole = false,
|
||||
showPrivateMessagesInConsole = true,
|
||||
showPrivateMessagesOnScreen = true,
|
||||
enableMusic = true,
|
||||
showLeftPanel = false,
|
||||
foregroundFrameRate = 61,
|
||||
backgroundFrameRate = 201,
|
||||
ambientLight = 15,
|
||||
painterEngine = 0
|
||||
painterEngine = 0,
|
||||
enableAudio = true,
|
||||
enableMusicSound = true,
|
||||
musicSoundVolume = 100,
|
||||
enableLights = true,
|
||||
ambientLight = 25,
|
||||
displayNames = true,
|
||||
displayHealth = true,
|
||||
displayText = true
|
||||
}
|
||||
|
||||
local warningWindow
|
||||
local optionsWindow
|
||||
local optionsButton
|
||||
local optionsTabBar
|
||||
local options = {}
|
||||
local gamePanel
|
||||
local generalPanel
|
||||
local consolePanel
|
||||
local graphicsPanel
|
||||
local soundPanel
|
||||
local audioButton
|
||||
|
||||
local function setupGraphicsEngines()
|
||||
local enginesRadioGroup = UIRadioGroup.create()
|
||||
local ogl1 = graphicsPanel:getChildById('opengl1')
|
||||
local ogl2 = graphicsPanel:getChildById('opengl2')
|
||||
local dx9 = graphicsPanel:getChildById('directx9')
|
||||
enginesRadioGroup:addWidget(ogl1)
|
||||
enginesRadioGroup:addWidget(ogl2)
|
||||
enginesRadioGroup:addWidget(dx9)
|
||||
|
||||
if g_graphics.getPainterEngine() == 2 then
|
||||
enginesRadioGroup:selectWidget(ogl2)
|
||||
if g_window.getPlatformType() == 'WIN32-EGL' then
|
||||
enginesRadioGroup:selectWidget(dx9)
|
||||
ogl1:setEnabled(false)
|
||||
ogl2:setEnabled(false)
|
||||
dx9:setEnabled(true)
|
||||
else
|
||||
enginesRadioGroup:selectWidget(ogl1)
|
||||
end
|
||||
ogl1:setEnabled(g_graphics.isPainterEngineAvailable(1))
|
||||
ogl2:setEnabled(g_graphics.isPainterEngineAvailable(2))
|
||||
dx9:setEnabled(false)
|
||||
if g_graphics.getPainterEngine() == 2 then
|
||||
enginesRadioGroup:selectWidget(ogl2)
|
||||
else
|
||||
enginesRadioGroup:selectWidget(ogl1)
|
||||
end
|
||||
|
||||
ogl1:setEnabled(g_graphics.isPainterEngineAvailable(1))
|
||||
ogl2:setEnabled(g_graphics.isPainterEngineAvailable(2))
|
||||
if g_app.getOs() ~= 'windows' then
|
||||
dx9:hide()
|
||||
end
|
||||
end
|
||||
|
||||
enginesRadioGroup.onSelectionChange = function(self, selected)
|
||||
if selected == ogl1 then
|
||||
@@ -62,22 +80,36 @@ local function setupGraphicsEngines()
|
||||
end
|
||||
end
|
||||
|
||||
function displayWarning(widget, warning)
|
||||
if warningWindow and warningWindow:isVisible() then
|
||||
return
|
||||
end
|
||||
if widget:isChecked() then
|
||||
local yesCallback = function() warningWindow:destroy() warningWindow=nil end
|
||||
local noCallback = function() widget:setChecked(false) warningWindow:destroy() warningWindow=nil end
|
||||
function init()
|
||||
optionsWindow = g_ui.displayUI('options')
|
||||
optionsWindow:hide()
|
||||
optionsButton = modules.client_topmenu.addLeftButton('optionsButton', tr('Options'), '/images/topbuttons/options', toggle)
|
||||
|
||||
warningWindow = displayGeneralBox('Warning', tr(warning), {
|
||||
{ text='Yes', callback=yesCallback },
|
||||
{ text='No', callback=noCallback },
|
||||
anchor=AnchorHorizontalCenter}, yesCallback, noCallback)
|
||||
end
|
||||
optionsTabBar = optionsWindow:getChildById('optionsTabBar')
|
||||
optionsTabBar:setContentWidget(optionsWindow:getChildById('optionsTabContent'))
|
||||
|
||||
addEvent(function() setup() end)
|
||||
|
||||
g_keyboard.bindKeyDown('Ctrl+Shift+F', function() toggleOption('fullscreen') end)
|
||||
g_keyboard.bindKeyDown('Ctrl+N', toggleDisplays)
|
||||
|
||||
audioButton = modules.client_topmenu.addLeftButton('audioButton', tr('Audio'), '/images/topbuttons/audio', function() toggleOption('enableAudio') end)
|
||||
end
|
||||
|
||||
function init()
|
||||
function terminate()
|
||||
g_keyboard.unbindKeyDown('Ctrl+Shift+F')
|
||||
g_keyboard.unbindKeyDown('Ctrl+N')
|
||||
optionsWindow:destroy()
|
||||
optionsButton:destroy()
|
||||
audioButton:destroy()
|
||||
optionsTabBar = nil
|
||||
generalPanel = nil
|
||||
consolePanel = nil
|
||||
graphicsPanel = nil
|
||||
audioPanel = nil
|
||||
end
|
||||
|
||||
function setup()
|
||||
-- load options
|
||||
for k,v in pairs(defaultOptions) do
|
||||
g_settings.setDefault(k, v)
|
||||
@@ -88,51 +120,21 @@ function init()
|
||||
end
|
||||
end
|
||||
|
||||
g_keyboard.bindKeyDown('Ctrl+D', function() toggle() end)
|
||||
g_keyboard.bindKeyDown('Ctrl+F', function() toggleOption('fullscreen') end)
|
||||
g_keyboard.bindKeyDown('Ctrl+Shift+D', function() toggleOption('walkBooster') end)
|
||||
|
||||
optionsWindow = g_ui.displayUI('options')
|
||||
optionsWindow:hide()
|
||||
optionsButton = modules.client_topmenu.addLeftButton('optionsButton', tr('Options') .. ' (Ctrl+D)', '/images/topbuttons/options', toggle)
|
||||
|
||||
optionsTabBar = optionsWindow:getChildById('optionsTabBar')
|
||||
optionsTabBar:setContentWidget(optionsWindow:getChildById('optionsTabContent'))
|
||||
|
||||
gamePanel = g_ui.loadUI('game')
|
||||
optionsTabBar:addTab(tr('Game'), gamePanel)
|
||||
generalPanel = g_ui.loadUI('game')
|
||||
optionsTabBar:addTab(tr('Game'), generalPanel, '/images/optionstab/game')
|
||||
|
||||
consolePanel = g_ui.loadUI('console')
|
||||
optionsTabBar:addTab(tr('Console'), consolePanel)
|
||||
optionsTabBar:addTab(tr('Console'), consolePanel, '/images/optionstab/console')
|
||||
|
||||
graphicsPanel = g_ui.loadUI('graphics')
|
||||
optionsTabBar:addTab(tr('Graphics'), graphicsPanel)
|
||||
optionsTabBar:addTab(tr('Graphics'), graphicsPanel, '/images/optionstab/graphics')
|
||||
|
||||
if g_game.isOfficialTibia() then
|
||||
local optionWalkBooster = gamePanel:getChildById('walkBooster')
|
||||
optionWalkBooster.onCheckChange = function(widget)
|
||||
displayWarning(widget, "This feature could be detectable by official Tibia servers. Would like to continue?")
|
||||
setOption(widget:getId(), widget:isChecked())
|
||||
end
|
||||
end
|
||||
audioPanel = g_ui.loadUI('audio')
|
||||
optionsTabBar:addTab(tr('Audio'), audioPanel, '/images/optionstab/audio')
|
||||
|
||||
setupGraphicsEngines()
|
||||
end
|
||||
|
||||
function terminate()
|
||||
g_keyboard.unbindKeyDown('Ctrl+D')
|
||||
g_keyboard.unbindKeyDown('Ctrl+F')
|
||||
g_keyboard.unbindKeyDown('Ctrl+Shift+D')
|
||||
optionsWindow:destroy()
|
||||
optionsWindow = nil
|
||||
optionsButton:destroy()
|
||||
optionsButton = nil
|
||||
optionsTabBar = nil
|
||||
gamePanel = nil
|
||||
consolePanel = nil
|
||||
graphicsPanel = nil
|
||||
end
|
||||
|
||||
function toggle()
|
||||
if optionsWindow:isVisible() then
|
||||
hide()
|
||||
@@ -151,17 +153,29 @@ function hide()
|
||||
optionsWindow:hide()
|
||||
end
|
||||
|
||||
function toggleOption(key)
|
||||
local optionWidget = optionsWindow:recursiveGetChildById(key)
|
||||
if optionWidget then
|
||||
optionWidget:setChecked(not getOption(key))
|
||||
function toggleDisplays()
|
||||
if options['displayNames'] and options['displayHealth'] then
|
||||
setOption('displayNames', false)
|
||||
elseif options['displayHealth'] then
|
||||
setOption('displayHealth', false)
|
||||
else
|
||||
setOption(key, not getOption(key))
|
||||
if not options['displayNames'] and not options['displayHealth'] then
|
||||
setOption('displayNames', true)
|
||||
else
|
||||
setOption('displayHealth', true)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function toggleOption(key)
|
||||
setOption(key, not getOption(key))
|
||||
end
|
||||
|
||||
function setOption(key, value)
|
||||
if options[key] == value then return end
|
||||
local gameMapPanel = modules.game_interface.getMapPanel()
|
||||
|
||||
local panel = nil
|
||||
if key == 'vsync' then
|
||||
g_window.setVerticalSync(value)
|
||||
elseif key == 'showFps' then
|
||||
@@ -176,12 +190,24 @@ function setOption(key, value)
|
||||
end)
|
||||
elseif key == 'fullscreen' then
|
||||
g_window.setFullscreen(value)
|
||||
elseif key == 'dontStretchShrink' then
|
||||
addEvent(function()
|
||||
modules.game_interface.updateStretchShrink()
|
||||
end)
|
||||
elseif key == 'enableMusic' then
|
||||
panel = graphicsPanel
|
||||
elseif key == 'enableAudio' then
|
||||
g_sounds.setAudioEnabled(value)
|
||||
addEvent(function()
|
||||
if value then
|
||||
audioButton:setIcon('/images/topbuttons/audio')
|
||||
else
|
||||
audioButton:setIcon('/images/topbuttons/audio_mute')
|
||||
end
|
||||
end)
|
||||
panel = audioPanel
|
||||
elseif key == 'enableMusicSound' then
|
||||
g_sounds.getChannel(SoundChannels.Music):setEnabled(value)
|
||||
elseif key == 'musicSoundVolume' then
|
||||
g_sounds.getChannel(SoundChannels.Music):setGain(value/100)
|
||||
if audioPanel then
|
||||
audioPanel:getChildById('musicSoundVolumeLabel'):setText(tr('Music volume: %d', value))
|
||||
end
|
||||
elseif key == 'showLeftPanel' then
|
||||
addEvent(function()
|
||||
modules.game_interface.getLeftPanel():setOn(value)
|
||||
@@ -208,20 +234,46 @@ function setOption(key, value)
|
||||
graphicsPanel:getChildById('foregroundFrameRateLabel'):setText(tr('Interface framerate limit: %s', text))
|
||||
end
|
||||
g_app.setForegroundPaneMaxFps(value)
|
||||
elseif key == 'enableLights' then
|
||||
addEvent(function()
|
||||
local map = modules.game_interface.getMapPanel()
|
||||
map:setDrawLights(value and options['ambientLight'] < 100)
|
||||
|
||||
if graphicsPanel then
|
||||
graphicsPanel:getChildById('ambientLight'):setEnabled(value)
|
||||
graphicsPanel:getChildById('ambientLightLabel'):setEnabled(value)
|
||||
end
|
||||
end)
|
||||
elseif key == 'ambientLight' then
|
||||
addEvent(function()
|
||||
local map = rootWidget:recursiveGetChildById('gameMapPanel')
|
||||
local map = modules.game_interface.getMapPanel()
|
||||
if graphicsPanel then
|
||||
graphicsPanel:getChildById('ambientLightLabel'):setText(tr('Ambient light: %s%%', value))
|
||||
end
|
||||
if map then
|
||||
map:setMinimumAmbientLight(value/100)
|
||||
map:setDrawLights(value < 100)
|
||||
end
|
||||
map:setMinimumAmbientLight(value/100)
|
||||
map:setDrawLights(options['enableLights'] and value < 100)
|
||||
end)
|
||||
elseif key == 'painterEngine' then
|
||||
g_graphics.selectPainterEngine(value)
|
||||
elseif key == 'displayNames' then
|
||||
gameMapPanel:setDrawNames(value)
|
||||
panel = generalPanel
|
||||
elseif key == 'displayHealth' then
|
||||
gameMapPanel:setDrawHealthBars(value)
|
||||
panel = generalPanel
|
||||
elseif key == 'displayText' then
|
||||
gameMapPanel:setDrawTexts(value)
|
||||
panel = generalPanel
|
||||
end
|
||||
|
||||
-- change value for keybind updates
|
||||
if panel then
|
||||
local widget = panel:recursiveGetChildById(key)
|
||||
if widget and widget:getStyle().__class == 'UICheckBox' then
|
||||
widget:setChecked(value)
|
||||
end
|
||||
end
|
||||
|
||||
g_settings.set(key, value)
|
||||
options[key] = value
|
||||
end
|
||||
@@ -230,4 +282,10 @@ function getOption(key)
|
||||
return options[key]
|
||||
end
|
||||
|
||||
function addTab(name, panel, icon)
|
||||
optionsTabBar:addTab(name, panel, icon)
|
||||
end
|
||||
|
||||
function addButton(name, func, icon)
|
||||
optionsTabBar:addButton(name, func, icon)
|
||||
end
|
||||
|
@@ -17,24 +17,24 @@ OptionCheckBox < CheckBox
|
||||
MainWindow
|
||||
id: optionsWindow
|
||||
!text: tr('Options')
|
||||
size: 350 310
|
||||
size: 480 340
|
||||
|
||||
@onEnter: modules.client_options.hide()
|
||||
@onEscape: modules.client_options.hide()
|
||||
|
||||
TabBarRounded
|
||||
TabBarVertical
|
||||
id: optionsTabBar
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
|
||||
Panel
|
||||
id: optionsTabContent
|
||||
anchors.top: optionsTabBar.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.top: optionsTabBar.top
|
||||
anchors.left: optionsTabBar.right
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
margin-top: 10
|
||||
anchors.bottom: optionsTabBar.bottom
|
||||
margin-left: 10
|
||||
|
||||
Button
|
||||
!text: tr('Ok')
|
||||
|
@@ -106,5 +106,5 @@ function onRecv(protocol, message)
|
||||
end
|
||||
|
||||
function onError(protocol, message, code)
|
||||
perror('Could not send statistics: ' .. message)
|
||||
pdebug('Could not send statistics: ' .. message)
|
||||
end
|
||||
|
@@ -1,24 +1,27 @@
|
||||
function init()
|
||||
local styles = g_resources.listDirectoryFiles('/styles')
|
||||
for _i,style in pairs(styles) do
|
||||
if string.ends(style, '.otui') then
|
||||
g_ui.importStyle('/styles/' .. style)
|
||||
local files
|
||||
files = g_resources.listDirectoryFiles('/styles')
|
||||
for _,file in pairs(files) do
|
||||
if g_resources.isFileType(file, 'otui') then
|
||||
g_ui.importStyle('/styles/' .. file)
|
||||
end
|
||||
end
|
||||
|
||||
local fonts = g_resources.listDirectoryFiles('/fonts')
|
||||
for _i,font in pairs(fonts) do
|
||||
if string.ends(font, '.otfont') then
|
||||
g_fonts.importFont('/fonts/' .. font)
|
||||
files = g_resources.listDirectoryFiles('/fonts')
|
||||
for _,file in pairs(files) do
|
||||
if g_resources.isFileType(file, 'otfont') then
|
||||
g_fonts.importFont('/fonts/' .. file)
|
||||
end
|
||||
end
|
||||
|
||||
local particles = g_resources.listDirectoryFiles('/particles')
|
||||
for _i,particle in pairs(particles) do
|
||||
if string.ends(particle, '.otps') then
|
||||
g_particles.importParticle('/particles/' .. particle)
|
||||
files = g_resources.listDirectoryFiles('/particles')
|
||||
for _,file in pairs(files) do
|
||||
if g_resources.isFileType(file, 'otps')then
|
||||
g_particles.importParticle('/particles/' .. file)
|
||||
end
|
||||
end
|
||||
|
||||
g_mouse.loadCursors('/cursors/cursors')
|
||||
end
|
||||
|
||||
function terminate()
|
||||
|
@@ -25,6 +25,7 @@ local function navigateCommand(step)
|
||||
if currentHistoryIndex > 0 then
|
||||
local command = commandHistory[numCommands - currentHistoryIndex + 1]
|
||||
commandTextEdit:setText(command)
|
||||
commandTextEdit:setCursorPos(-1)
|
||||
else
|
||||
commandTextEdit:clearText()
|
||||
end
|
||||
@@ -52,6 +53,7 @@ local function completeCommand()
|
||||
-- complete command with one match
|
||||
if #possibleCommands == 1 then
|
||||
commandTextEdit:setText(possibleCommands[1])
|
||||
commandTextEdit:setCursorPos(-1)
|
||||
-- show command matches
|
||||
elseif #possibleCommands > 0 then
|
||||
print('>> ' .. commandBegin)
|
||||
@@ -75,6 +77,7 @@ local function completeCommand()
|
||||
end
|
||||
end
|
||||
commandTextEdit:setText(commandBegin)
|
||||
commandTextEdit:setCursorPos(-1)
|
||||
|
||||
for i,v in ipairs(possibleCommands) do
|
||||
print(v)
|
||||
@@ -147,12 +150,8 @@ function terminate()
|
||||
g_settings.setList('terminal-history', commandHistory)
|
||||
g_keyboard.unbindKeyDown('Ctrl+T')
|
||||
g_logger.setOnLog(nil)
|
||||
terminalButton:destroy()
|
||||
terminalButton = nil
|
||||
commandTextEdit = nil
|
||||
terminalBuffer = nil
|
||||
terminalWindow:destroy()
|
||||
terminalWindow = nil
|
||||
terminalButton:destroy()
|
||||
commandEnv = nil
|
||||
end
|
||||
|
||||
@@ -178,6 +177,11 @@ function hide()
|
||||
terminalWindow:hide()
|
||||
end
|
||||
|
||||
function disable()
|
||||
terminalButton:hide()
|
||||
g_keyboard.unbindKeyDown('Ctrl+T')
|
||||
end
|
||||
|
||||
function addLine(text, color)
|
||||
-- delete old lines if needed
|
||||
local numLines = terminalBuffer:getChildCount() + 1
|
||||
|
@@ -39,6 +39,8 @@ UIWindow
|
||||
anchors.right: parent.right
|
||||
margin-left: 5
|
||||
font: terminus-14px-bold
|
||||
selection-color: black
|
||||
selection-background-color: white
|
||||
|
||||
ResizeBorder
|
||||
id: bottomResizeBorder
|
||||
|
@@ -14,11 +14,14 @@ local function addButton(id, description, icon, callback, panel, toggle, front)
|
||||
class = 'TopButton'
|
||||
end
|
||||
|
||||
local button = g_ui.createWidget(class)
|
||||
if front then
|
||||
panel:insertChild(1, button)
|
||||
else
|
||||
panel:addChild(button)
|
||||
local button = panel:getChildById(id)
|
||||
if not button then
|
||||
button = g_ui.createWidget(class)
|
||||
if front then
|
||||
panel:insertChild(1, button)
|
||||
else
|
||||
panel:addChild(button)
|
||||
end
|
||||
end
|
||||
button:setId(id)
|
||||
button:setTooltip(description)
|
||||
@@ -54,13 +57,7 @@ function terminate()
|
||||
disconnect(g_game, { onGameStart = showGameButtons,
|
||||
onGameEnd = hideGameButtons })
|
||||
|
||||
leftButtonsPanel = nil
|
||||
rightButtonsPanel = nil
|
||||
leftGameButtonsPanel = nil
|
||||
rightGameButtonsPanel = nil
|
||||
|
||||
topMenu:destroy()
|
||||
topMenu = nil
|
||||
end
|
||||
|
||||
function addLeftButton(id, description, icon, callback, front)
|
||||
|
@@ -19,6 +19,10 @@ KeyboardFocusReason = 1
|
||||
ActiveFocusReason = 2
|
||||
OtherFocusReason = 3
|
||||
|
||||
AutoFocusNone = 0
|
||||
AutoFocusFirst = 1
|
||||
AutoFocusLast = 2
|
||||
|
||||
KeyboardNoModifier = 0
|
||||
KeyboardCtrlModifier = 1
|
||||
KeyboardAltModifier = 2
|
||||
@@ -296,7 +300,7 @@ KeyCodeDescs = {
|
||||
[KeyNumpad6] = 'Numpad6',
|
||||
[KeyNumpad7] = 'Numpad7',
|
||||
[KeyNumpad8] = 'Numpad8',
|
||||
[KeyNumpad9] = 'Numpad9'
|
||||
[KeyNumpad9] = 'Numpad9',
|
||||
}
|
||||
|
||||
NetworkMessageTypes = {
|
||||
@@ -307,5 +311,10 @@ NetworkMessageTypes = {
|
||||
U64 = 5,
|
||||
NumberString = 6,
|
||||
String = 7,
|
||||
Table = 8
|
||||
Table = 8,
|
||||
}
|
||||
|
||||
SoundChannels = {
|
||||
Music = 1,
|
||||
Ambient = 2,
|
||||
}
|
||||
|
@@ -25,8 +25,8 @@ function addEvent(callback, front)
|
||||
return event
|
||||
end
|
||||
|
||||
function cycleEvent(callback, front)
|
||||
local event = g_dispatcher.cycleEvent(callback, front)
|
||||
function cycleEvent(callback, interval)
|
||||
local event = g_dispatcher.cycleEvent(callback, interval)
|
||||
-- must hold a reference to the callback, otherwise it would be collected
|
||||
event._callback = callback
|
||||
return event
|
||||
|
@@ -35,9 +35,17 @@ end
|
||||
|
||||
function InputMessage:getColor()
|
||||
local color = {}
|
||||
color.r = msg:getU8()
|
||||
color.g = msg:getU8()
|
||||
color.b = msg:getU8()
|
||||
color.a = msg:getU8()
|
||||
color.r = self:getU8()
|
||||
color.g = self:getU8()
|
||||
color.b = self:getU8()
|
||||
color.a = self:getU8()
|
||||
return color
|
||||
end
|
||||
|
||||
function InputMessage:getPosition()
|
||||
local position = {}
|
||||
position.x = self:getU16()
|
||||
position.y = self:getU16()
|
||||
position.z = self:getU8()
|
||||
return position
|
||||
end
|
||||
|
@@ -71,10 +71,13 @@ end
|
||||
|
||||
local function onWidgetKeyDown(widget, keyCode, keyboardModifiers)
|
||||
if keyCode == KeyUnknown then return false end
|
||||
local keyComboDesc = determineKeyComboDesc(keyCode, keyboardModifiers)
|
||||
local callback = widget.boundKeyDownCombos[keyComboDesc]
|
||||
local callback = widget.boundAloneKeyDownCombos[determineKeyComboDesc(keyCode, KeyboardNoModifier)]
|
||||
if callback then
|
||||
callback()
|
||||
callback(widget, keyCode)
|
||||
end
|
||||
callback = widget.boundKeyDownCombos[determineKeyComboDesc(keyCode, keyboardModifiers)]
|
||||
if callback then
|
||||
callback(widget, keyCode)
|
||||
return true
|
||||
end
|
||||
return false
|
||||
@@ -82,10 +85,13 @@ end
|
||||
|
||||
local function onWidgetKeyUp(widget, keyCode, keyboardModifiers)
|
||||
if keyCode == KeyUnknown then return false end
|
||||
local keyComboDesc = determineKeyComboDesc(keyCode, keyboardModifiers)
|
||||
local callback = widget.boundKeyUpCombos[keyComboDesc]
|
||||
local callback = widget.boundAloneKeyUpCombos[determineKeyComboDesc(keyCode, KeyboardNoModifier)]
|
||||
if callback then
|
||||
callback()
|
||||
callback(widget, keyCode)
|
||||
end
|
||||
callback = widget.boundKeyUpCombos[determineKeyComboDesc(keyCode, keyboardModifiers)]
|
||||
if callback then
|
||||
callback(widget, keyCode)
|
||||
return true
|
||||
end
|
||||
return false
|
||||
@@ -96,7 +102,7 @@ local function onWidgetKeyPress(widget, keyCode, keyboardModifiers, autoRepeatTi
|
||||
local keyComboDesc = determineKeyComboDesc(keyCode, keyboardModifiers)
|
||||
local comboConf = widget.boundKeyPressCombos[keyComboDesc]
|
||||
if comboConf and (autoRepeatTicks >= comboConf.autoRepeatDelay or autoRepeatTicks == 0) and comboConf.callback then
|
||||
comboConf.callback()
|
||||
comboConf.callback(widget, keyCode)
|
||||
return true
|
||||
end
|
||||
return false
|
||||
@@ -106,12 +112,14 @@ local function connectKeyDownEvent(widget)
|
||||
if widget.boundKeyDownCombos then return end
|
||||
connect(widget, { onKeyDown = onWidgetKeyDown })
|
||||
widget.boundKeyDownCombos = {}
|
||||
widget.boundAloneKeyDownCombos = {}
|
||||
end
|
||||
|
||||
local function connectKeyUpEvent(widget)
|
||||
if widget.boundKeyUpCombos then return end
|
||||
connect(widget, { onKeyUp = onWidgetKeyUp })
|
||||
widget.boundKeyUpCombos = {}
|
||||
widget.boundAloneKeyUpCombos = {}
|
||||
end
|
||||
|
||||
local function connectKeyPressEvent(widget)
|
||||
@@ -121,24 +129,32 @@ local function connectKeyPressEvent(widget)
|
||||
end
|
||||
|
||||
-- public functions
|
||||
function g_keyboard.bindKeyDown(keyComboDesc, callback, widget)
|
||||
function g_keyboard.bindKeyDown(keyComboDesc, callback, widget, alone)
|
||||
widget = widget or rootWidget
|
||||
connectKeyDownEvent(widget)
|
||||
local keyComboDesc = retranslateKeyComboDesc(keyComboDesc)
|
||||
if widget.boundKeyDownCombos[keyComboDesc] then
|
||||
pwarning('KeyDown event \'' .. keyComboDesc .. '\' redefined on widget ' .. widget:getId())
|
||||
end
|
||||
widget.boundKeyDownCombos[keyComboDesc] = callback
|
||||
if alone then
|
||||
widget.boundAloneKeyDownCombos[keyComboDesc] = callback
|
||||
else
|
||||
widget.boundKeyDownCombos[keyComboDesc] = callback
|
||||
end
|
||||
end
|
||||
|
||||
function g_keyboard.bindKeyUp(keyComboDesc, callback, widget)
|
||||
function g_keyboard.bindKeyUp(keyComboDesc, callback, widget, alone)
|
||||
widget = widget or rootWidget
|
||||
connectKeyUpEvent(widget)
|
||||
local keyComboDesc = retranslateKeyComboDesc(keyComboDesc)
|
||||
if widget.boundKeyUpCombos[keyComboDesc] then
|
||||
pwarning('KeyUp event \'' .. keyComboDesc .. '\' redefined on widget ' .. widget:getId())
|
||||
end
|
||||
widget.boundKeyUpCombos[keyComboDesc] = callback
|
||||
if alone then
|
||||
widget.boundAloneKeyUpCombos[keyComboDesc] = callback
|
||||
else
|
||||
widget.boundKeyUpCombos[keyComboDesc] = callback
|
||||
end
|
||||
end
|
||||
|
||||
function g_keyboard.bindKeyPress(keyComboDesc, callback, widget, autoRepeatDelay)
|
||||
|
@@ -20,14 +20,17 @@ function g_mouse.bindPressMove(widget, callback)
|
||||
connect(widget, { onMouseMove = function(widget, mousePos, mouseMoved)
|
||||
if widget:isPressed() then
|
||||
callback(mousePos, mouseMoved)
|
||||
return true
|
||||
end
|
||||
return true
|
||||
end })
|
||||
end
|
||||
|
||||
function g_mouse.bindPress(widget, callback)
|
||||
function g_mouse.bindPress(widget, callback, button)
|
||||
connect(widget, { onMousePress = function(widget, mousePos, mouseButton)
|
||||
callback(mousePos, mouseButton)
|
||||
return true
|
||||
if not button or button == mouseButton then
|
||||
callback(mousePos, mouseButton)
|
||||
return true
|
||||
end
|
||||
return false
|
||||
end })
|
||||
end
|
||||
|
@@ -61,3 +61,9 @@ function OutputMessage:addColor(color)
|
||||
self:addU8(color.b)
|
||||
self:addU8(color.a)
|
||||
end
|
||||
|
||||
function OutputMessage:addPosition(position)
|
||||
self:addU16(position.x)
|
||||
self:addU16(position.y)
|
||||
self:addU8(position.z)
|
||||
end
|
||||
|
@@ -8,6 +8,7 @@ g_settings.getNode = g_configs.getNode
|
||||
g_settings.remove = g_configs.remove
|
||||
g_settings.setList = g_configs.setList
|
||||
g_settings.getList = g_configs.getList
|
||||
g_settings.save = g_configs.save
|
||||
|
||||
local function convertSettingValue(value)
|
||||
if type(value) == 'table' then
|
||||
|
@@ -49,4 +49,3 @@ function string:explode(sep, limit)
|
||||
table.insert(t, tmp)
|
||||
return t
|
||||
end
|
||||
|
||||
|
@@ -56,11 +56,20 @@ function table.find(t, value, lowercase)
|
||||
end
|
||||
end
|
||||
|
||||
function table.contains(t, value)
|
||||
return table.find(t, value) ~= nil
|
||||
function table.findbykey(t, key, lowercase)
|
||||
for k,v in pairs(t) do
|
||||
if lowercase and type(key) == 'string' and type(k) == 'string' then
|
||||
if k:lower() == key:lower() then return v end
|
||||
end
|
||||
if k == key then return v end
|
||||
end
|
||||
end
|
||||
|
||||
function table.findKey(t, key)
|
||||
function table.contains(t, value, lowercase)
|
||||
return table.find(t, value, lowercase) ~= nil
|
||||
end
|
||||
|
||||
function table.findkey(t, key)
|
||||
if t and type(t) == 'table' then
|
||||
for k,v in pairs(t) do
|
||||
if k == key then return k end
|
||||
@@ -68,17 +77,32 @@ function table.findKey(t, key)
|
||||
end
|
||||
end
|
||||
|
||||
function table.hasKey(t, key)
|
||||
return table.findKey(t, key) ~= nil
|
||||
function table.haskey(t, key)
|
||||
return table.findkey(t, key) ~= nil
|
||||
end
|
||||
|
||||
function table.removevalue(t, value)
|
||||
for k,v in pairs(t) do
|
||||
if v == value then
|
||||
table.remove(t, k)
|
||||
break
|
||||
return true
|
||||
end
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
function table.popvalue(value)
|
||||
local index = nil
|
||||
for k,v in pairs(t) do
|
||||
if v == value or not value then
|
||||
index = k
|
||||
end
|
||||
end
|
||||
if index then
|
||||
table.remove(t, index)
|
||||
return true
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
function table.compare(t, other)
|
||||
@@ -114,7 +138,7 @@ function table.findbyfield(t, fieldname, fieldvalue)
|
||||
return nil
|
||||
end
|
||||
|
||||
function table.toString(t)
|
||||
function table.tostring(t)
|
||||
local maxn = #t
|
||||
local str = ""
|
||||
for k,v in pairs(t) do
|
||||
|
@@ -35,3 +35,33 @@ function g_effects.cancelFade(widget)
|
||||
removeEvent(widget.fadeEvent)
|
||||
widget.fadeEvent = nil
|
||||
end
|
||||
|
||||
function g_effects.startBlink(widget, duration, interval, clickCancel)
|
||||
duration = duration or 0 -- until stop is called
|
||||
interval = interval or 500
|
||||
clickCancel = clickCancel or true
|
||||
|
||||
removeEvent(widget.blinkEvent)
|
||||
removeEvent(widget.blinkStopEvent)
|
||||
|
||||
widget.blinkEvent = cycleEvent(function()
|
||||
widget:setOn(not widget:isOn())
|
||||
end, interval)
|
||||
|
||||
if duration > 0 then
|
||||
widget.blinkStopEvent = scheduleEvent(function()
|
||||
g_effects.stopBlink(widget)
|
||||
end, duration)
|
||||
end
|
||||
|
||||
connect(widget, { onClick = g_effects.stopBlink })
|
||||
end
|
||||
|
||||
function g_effects.stopBlink(widget)
|
||||
disconnect(widget, { onClick = g_effects.stopBlink })
|
||||
removeEvent(widget.blinkEvent)
|
||||
removeEvent(widget.blinkStopEvent)
|
||||
widget.blinkEvent = nil
|
||||
widget.blinkStopEvent = nil
|
||||
widget:setOn(false)
|
||||
end
|
||||
|
@@ -67,7 +67,7 @@ function g_tooltip.terminate()
|
||||
end
|
||||
|
||||
function g_tooltip.display(text)
|
||||
if text == nil then return end
|
||||
if text == nil or text:len() == 0 then return end
|
||||
if not toolTipLabel then return end
|
||||
|
||||
toolTipLabel:setText(text)
|
||||
|
@@ -5,4 +5,8 @@ function UIButton.create()
|
||||
local button = UIButton.internalCreate()
|
||||
button:setFocusable(false)
|
||||
return button
|
||||
end
|
||||
end
|
||||
|
||||
function UIButton:onMouseRelease(pos, button)
|
||||
return self:isPressed()
|
||||
end
|
||||
|
@@ -31,7 +31,7 @@ function UIComboBox:setCurrentOption(text)
|
||||
if v.text == text and self.currentIndex ~= i then
|
||||
self.currentIndex = i
|
||||
self:setText(text)
|
||||
self:onOptionChange(text, v.data)
|
||||
signalcall(self.onOptionChange, self, text, v.data)
|
||||
return
|
||||
end
|
||||
end
|
||||
@@ -43,7 +43,7 @@ function UIComboBox:setCurrentOptionByData(data)
|
||||
if v.data == data and self.currentIndex ~= i then
|
||||
self.currentIndex = i
|
||||
self:setText(v.text)
|
||||
self:onOptionChange(v.text, v.data)
|
||||
signalcall(self.onOptionChange, self, v.text, v.data)
|
||||
return
|
||||
end
|
||||
end
|
||||
@@ -54,12 +54,12 @@ function UIComboBox:setCurrentIndex(index)
|
||||
local v = self.options[index]
|
||||
self.currentIndex = index
|
||||
self:setText(v.text)
|
||||
self:onOptionChange(v.text, v.data)
|
||||
signalcall(self.onOptionChange, self, v.text, v.data)
|
||||
end
|
||||
end
|
||||
|
||||
function UIComboBox:getCurrentOption()
|
||||
if table.hasKey(self.options, self.currentIndex) then
|
||||
if table.haskey(self.options, self.currentIndex) then
|
||||
return self.options[self.currentIndex]
|
||||
end
|
||||
end
|
||||
@@ -116,6 +116,16 @@ function UIComboBox:onStyleApply(styleName, styleNode)
|
||||
self:addOption(option)
|
||||
end
|
||||
end
|
||||
|
||||
if styleNode.data then
|
||||
for k,data in pairs(styleNode.data) do
|
||||
local option = self.options[k]
|
||||
if option then
|
||||
option.data = data
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
for name,value in pairs(styleNode) do
|
||||
if name == 'mouse-scroll' then
|
||||
self.mouseScroll = value
|
||||
@@ -130,7 +140,3 @@ end
|
||||
function UIComboBox:canMouseScroll()
|
||||
return self.mouseScroll
|
||||
end
|
||||
|
||||
function UIComboBox:onOptionChange(optionText, optionData)
|
||||
-- nothing todo
|
||||
end
|
||||
|
99
modules/corelib/ui/uiimageview.lua
Normal file
@@ -0,0 +1,99 @@
|
||||
-- @docclass
|
||||
UIImageView = extends(UIWidget)
|
||||
|
||||
function UIImageView.create()
|
||||
local imageView = UIImageView.internalCreate()
|
||||
imageView.zoom = 1
|
||||
imageView.minZoom = math.pow(10, -2)
|
||||
imageView.maxZoom = math.pow(10, 2)
|
||||
imageView:setClipping(true)
|
||||
return imageView
|
||||
end
|
||||
|
||||
function UIImageView:getDefaultZoom()
|
||||
local width = self:getWidth()
|
||||
local height = self:getHeight()
|
||||
local textureWidth = self:getImageTextureWidth()
|
||||
local textureHeight = self:getImageTextureHeight()
|
||||
local zoomX = width / textureWidth
|
||||
local zoomY = height / textureHeight
|
||||
return math.min(zoomX, zoomY)
|
||||
end
|
||||
|
||||
function UIImageView:getImagePosition(x, y)
|
||||
x = x or self:getWidth() / 2
|
||||
y = y or self:getHeight() / 2
|
||||
local offsetX = self:getImageOffsetX()
|
||||
local offsetY = self:getImageOffsetY()
|
||||
local posX = (x - offsetX) / self.zoom
|
||||
local posY = (y - offsetY) / self.zoom
|
||||
return posX, posY
|
||||
end
|
||||
|
||||
function UIImageView:setImage(image)
|
||||
self:setImageSource(image)
|
||||
local zoom = self:getDefaultZoom()
|
||||
self:setZoom(zoom)
|
||||
self:center()
|
||||
end
|
||||
|
||||
function UIImageView:setZoom(zoom, x, y)
|
||||
zoom = math.max(math.min(zoom, self.maxZoom), self.minZoom)
|
||||
local posX, posY = self:getImagePosition(x, y)
|
||||
local textureWidth = self:getImageTextureWidth()
|
||||
local textureHeight = self:getImageTextureHeight()
|
||||
local imageWidth = textureWidth * zoom
|
||||
local imageHeight = textureHeight * zoom
|
||||
self:setImageWidth(imageWidth)
|
||||
self:setImageHeight(imageHeight)
|
||||
self.zoom = zoom
|
||||
self:move(posX, posY, x, y)
|
||||
end
|
||||
|
||||
function UIImageView:zoomIn(x, y)
|
||||
local zoom = self.zoom * 1.1
|
||||
self:setZoom(zoom, x, y)
|
||||
end
|
||||
|
||||
function UIImageView:zoomOut(x, y)
|
||||
local zoom = self.zoom / 1.1
|
||||
self:setZoom(zoom, x, y)
|
||||
end
|
||||
|
||||
function UIImageView:center()
|
||||
self:move(self:getImageTextureWidth() / 2, self:getImageTextureHeight() / 2)
|
||||
end
|
||||
|
||||
function UIImageView:move(x, y, centerX, centerY)
|
||||
x = math.max(math.min(x, self:getImageTextureWidth()), 0)
|
||||
y = math.max(math.min(y, self:getImageTextureHeight()), 0)
|
||||
local centerX = centerX or self:getWidth() / 2
|
||||
local centerY = centerY or self:getHeight() / 2
|
||||
local offsetX = centerX - x * self.zoom
|
||||
local offsetY = centerY - y * self.zoom
|
||||
self:setImageOffset({x=offsetX, y=offsetY})
|
||||
end
|
||||
|
||||
function UIImageView:onDragEnter(pos)
|
||||
return true
|
||||
end
|
||||
|
||||
function UIImageView:onDragMove(pos, moved)
|
||||
local posX, posY = self:getImagePosition()
|
||||
self:move(posX - moved.x / self.zoom, posY - moved.y / self.zoom)
|
||||
return true
|
||||
end
|
||||
|
||||
function UIImageView:onDragLeave(widget, pos)
|
||||
return true
|
||||
end
|
||||
|
||||
function UIImageView:onMouseWheel(mousePos, direction)
|
||||
local x = mousePos.x - self:getX()
|
||||
local y = mousePos.y - self:getY()
|
||||
if direction == MouseWheelUp then
|
||||
self:zoomIn(x, y)
|
||||
elseif direction == MouseWheelDown then
|
||||
self:zoomOut(x, y)
|
||||
end
|
||||
end
|
@@ -38,7 +38,7 @@ function UIMiniWindowContainer:fitAll(noRemoveChild)
|
||||
end
|
||||
end
|
||||
|
||||
local selfHeight = self:getHeight() - (self:getMarginTop() + self:getMarginBottom() + self:getPaddingTop() + self:getPaddingBottom())
|
||||
local selfHeight = self:getHeight() - (self:getPaddingTop() + self:getPaddingBottom())
|
||||
if sumHeight <= selfHeight then
|
||||
return
|
||||
end
|
||||
|
@@ -11,17 +11,42 @@ local function updateMargins(tabBar, ignored)
|
||||
|
||||
local currentMargin = 0
|
||||
for i = 1, #tabBar.tabs do
|
||||
if tabBar.tabs[i] ~= ignored then
|
||||
if i == 1 then
|
||||
tabBar.tabs[i]:setMarginLeft(0)
|
||||
else
|
||||
tabBar.tabs[i]:setMarginLeft(tabBar.tabSpacing * (i - 1) + currentMargin)
|
||||
end
|
||||
end
|
||||
currentMargin = currentMargin + tabBar.tabs[i]:getWidth()
|
||||
tabBar.tabs[i]:setMarginLeft(currentMargin)
|
||||
currentMargin = currentMargin + tabBar.tabSpacing + tabBar.tabs[i]:getWidth()
|
||||
end
|
||||
end
|
||||
|
||||
local function updateIndexes(tabBar, tab, xoff)
|
||||
local tabs = tabBar.tabs
|
||||
local currentMargin = 0
|
||||
local prevIndex = table.find(tabs, tab)
|
||||
local newIndex = prevIndex
|
||||
local xmid = xoff + tab:getWidth()/2
|
||||
for i = 1, #tabs do
|
||||
local nextTab = tabs[i]
|
||||
if xmid >= currentMargin + nextTab:getWidth()/2 then
|
||||
newIndex = table.find(tabs, nextTab)
|
||||
end
|
||||
currentMargin = currentMargin + tabBar.tabSpacing * (i - 1) + tabBar.tabs[i]:getWidth()
|
||||
end
|
||||
if newIndex ~= prevIndex then
|
||||
table.remove(tabs, table.find(tabs, tab))
|
||||
table.insert(tabs, newIndex, tab)
|
||||
end
|
||||
end
|
||||
|
||||
local function getMaxMargin(tabBar, tab)
|
||||
if #tabBar.tabs == 0 then return end
|
||||
|
||||
local maxMargin = 0
|
||||
for i = 1, #tabBar.tabs do
|
||||
if tabBar.tabs[i] ~= tab then
|
||||
maxMargin = maxMargin + tabBar.tabs[i]:getWidth()
|
||||
end
|
||||
end
|
||||
return maxMargin + tabBar.tabSpacing * (#tabBar.tabs- 1)
|
||||
end
|
||||
|
||||
local function onTabMousePress(tab, mousePos, mouseButton)
|
||||
if mouseButton == MouseRightButton then
|
||||
if tab.menuCallback then tab.menuCallback(tab, mousePos, mouseButton) end
|
||||
@@ -29,8 +54,9 @@ local function onTabMousePress(tab, mousePos, mouseButton)
|
||||
end
|
||||
end
|
||||
|
||||
local function onTabDragEnter(tab)
|
||||
local function onTabDragEnter(tab, mousePos)
|
||||
tab:raise()
|
||||
tab.hotSpot = mousePos.x - tab:getMarginLeft()
|
||||
tab.tabBar.selected = tab
|
||||
return true
|
||||
end
|
||||
@@ -43,29 +69,17 @@ end
|
||||
|
||||
local function onTabDragMove(tab, mousePos, mouseMoved)
|
||||
if tab == tab.tabBar.selected then
|
||||
local newMargin = tab:getMarginLeft() + mouseMoved.x
|
||||
if newMargin >= -tab.tabBar.tabSpacing and newMargin < tab.tabBar:getWidth() - tab:getWidth() then
|
||||
tab:setMarginLeft(newMargin)
|
||||
end
|
||||
local xoff = mousePos.x - tab.hotSpot
|
||||
|
||||
local tabs = tab.tabBar.tabs
|
||||
local lastMargin = -tab.tabBar.tabSpacing
|
||||
for i = 1, #tabs do
|
||||
local nextMargin = tabs[i + 1] and (tabs[i + 1] == tab and (tabs[i]:getMarginLeft() + tabs[i]:getWidth() + tab.tabBar.tabSpacing) or tabs[i + 1]:getMarginLeft()) or tab.tabBar:getWidth()
|
||||
if (tab:getMarginLeft()+(tabs[i]:getWidth()/2)) >= lastMargin and (tab:getMarginLeft()+(tabs[i]:getWidth()/2)) < nextMargin then
|
||||
if tabs[i] ~= tab then
|
||||
local newIndex = table.find(tab.tabBar.tabs, tab.tabBar.tabs[i])
|
||||
table.remove(tab.tabBar.tabs, table.find(tab.tabBar.tabs, tab))
|
||||
table.insert(tab.tabBar.tabs, newIndex, tab)
|
||||
updateMargins(tab.tabBar, tab)
|
||||
break
|
||||
else
|
||||
updateMargins(tab.tabBar, tab)
|
||||
break
|
||||
end
|
||||
end
|
||||
lastMargin = tab.tabBar.tabs[i]:getMarginLeft() == 0 and -tab.tabBar.tabSpacing or tab.tabBar.tabs[i]:getMarginLeft()
|
||||
end
|
||||
-- update indexes
|
||||
updateIndexes(tab.tabBar, tab, xoff)
|
||||
updateIndexes(tab.tabBar, tab, xoff)
|
||||
|
||||
-- update margins
|
||||
updateMargins(tab.tabBar)
|
||||
xoff = math.max(xoff, 0)
|
||||
xoff = math.min(xoff, getMaxMargin(tab.tabBar, tab))
|
||||
tab:setMarginLeft(xoff)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -81,7 +95,7 @@ function UIMoveableTabBar.create()
|
||||
tabbar:setFocusable(false)
|
||||
tabbar.tabs = {}
|
||||
tabbar.selected = nil -- dragged tab
|
||||
tabbar.tabSpacing = 5
|
||||
tabbar.tabSpacing = 0
|
||||
tabbar.tabsMoveable = false
|
||||
return tabbar
|
||||
end
|
||||
|
@@ -18,6 +18,11 @@ function UIPopupMenu:display(pos)
|
||||
return
|
||||
end
|
||||
|
||||
if g_ui.isMouseGrabbed() then
|
||||
self:destroy()
|
||||
return
|
||||
end
|
||||
|
||||
if currentMenu then
|
||||
currentMenu:destroy()
|
||||
end
|
||||
@@ -33,19 +38,38 @@ function UIPopupMenu:display(pos)
|
||||
currentMenu = self
|
||||
end
|
||||
|
||||
function UIPopupMenu:onGeometryChange()
|
||||
function UIPopupMenu:onGeometryChange(oldRect, newRect)
|
||||
local parent = self:getParent()
|
||||
if not parent then return end
|
||||
local ymax = parent:getY() + parent:getHeight()
|
||||
local xmax = parent:getX() + parent:getWidth()
|
||||
if newRect.y + newRect.height > ymax then
|
||||
local newy = newRect.y - newRect.height
|
||||
if newy > 0 and newy + newRect.height < ymax then self:setY(newy) end
|
||||
end
|
||||
if newRect.x + newRect.width > xmax then
|
||||
local newx = newRect.x - newRect.width
|
||||
if newx > 0 and newx + newRect.width < xmax then self:setX(newx) end
|
||||
end
|
||||
self:bindRectToParent()
|
||||
end
|
||||
|
||||
function UIPopupMenu:addOption(optionName, optionCallback)
|
||||
function UIPopupMenu:addOption(optionName, optionCallback, shortcut)
|
||||
local optionWidget = g_ui.createWidget(self:getStyleName() .. 'Button', self)
|
||||
local lastOptionWidget = self:getLastChild()
|
||||
optionWidget.onClick = function(self)
|
||||
optionCallback()
|
||||
self:getParent():destroy()
|
||||
optionCallback()
|
||||
end
|
||||
optionWidget:setText(optionName)
|
||||
local width = optionWidget:getTextSize().width + optionWidget:getMarginLeft() + optionWidget:getMarginRight() + 15
|
||||
|
||||
if shortcut then
|
||||
local shortcutLabel = g_ui.createWidget(self:getStyleName() .. 'ShortcutLabel', optionWidget)
|
||||
shortcutLabel:setText(shortcut)
|
||||
width = width + shortcutLabel:getTextSize().width + shortcutLabel:getMarginLeft() + shortcutLabel:getMarginRight()
|
||||
end
|
||||
|
||||
self:setWidth(math.max(self:getWidth(), width))
|
||||
end
|
||||
|
||||
@@ -57,6 +81,7 @@ function UIPopupMenu:onDestroy()
|
||||
if currentMenu == self then
|
||||
currentMenu = nil
|
||||
end
|
||||
self:ungrabMouse()
|
||||
end
|
||||
|
||||
function UIPopupMenu:onMousePress(mousePos, mouseButton)
|
||||
|
@@ -4,35 +4,71 @@ UIProgressBar = extends(UIWidget)
|
||||
function UIProgressBar.create()
|
||||
local progressbar = UIProgressBar.internalCreate()
|
||||
progressbar:setFocusable(false)
|
||||
progressbar:setPhantom(true)
|
||||
progressbar.percent = 0
|
||||
progressbar.min = 0
|
||||
progressbar.max = 100
|
||||
progressbar.value = 0
|
||||
progressbar.bgBorderLeft = 0
|
||||
progressbar.bgBorderRight = 0
|
||||
progressbar.bgBorderTop = 0
|
||||
progressbar.bgBorderBottom = 0
|
||||
progressbar:updateBackground()
|
||||
return progressbar
|
||||
end
|
||||
|
||||
function UIProgressBar:setPercent(percent)
|
||||
self.percent = math.max(math.min(percent, 100), 0)
|
||||
function UIProgressBar:setMinimum(minimum)
|
||||
self.minimum = minimum
|
||||
if self.value < minimum then
|
||||
self:setValue(minimum)
|
||||
end
|
||||
end
|
||||
|
||||
function UIProgressBar:setMaximum(maximum)
|
||||
self.maximum = maximum
|
||||
if self.value > maximum then
|
||||
self:setValue(maximum)
|
||||
end
|
||||
end
|
||||
|
||||
function UIProgressBar:setValue(value, minimum, maximum)
|
||||
if minimum then
|
||||
self:setMinimum(minimum)
|
||||
end
|
||||
|
||||
if maximum then
|
||||
self:setMaximum(maximum)
|
||||
end
|
||||
|
||||
self.value = math.max(math.min(value, self.maximum), self.minimum)
|
||||
self:updateBackground()
|
||||
end
|
||||
|
||||
function UIProgressBar:setPercent(percent)
|
||||
self:setValue(percent, 0, 100)
|
||||
end
|
||||
|
||||
function UIProgressBar:getPercent()
|
||||
return self.percent
|
||||
return self.value
|
||||
end
|
||||
|
||||
function UIProgressBar:getPercentPixels()
|
||||
return 100 / self:getWidth()
|
||||
return (self.maximum - self.minimum) / self:getWidth()
|
||||
end
|
||||
|
||||
function UIProgressBar:getProgress()
|
||||
if self.minimum == self.maximum then return 1 end
|
||||
return (self.value - self.minimum) / (self.maximum - self.minimum)
|
||||
end
|
||||
|
||||
function UIProgressBar:updateBackground()
|
||||
local width = math.round(math.max((self.percent * (self:getWidth() - self.bgBorderLeft - self.bgBorderRight))/100, 1))
|
||||
local height = self:getHeight() - self.bgBorderTop - self.bgBorderBottom
|
||||
local rect = { x = self.bgBorderLeft, y = self.bgBorderTop, width = width, height = height }
|
||||
self:setBackgroundRect(rect)
|
||||
if self:isOn() then
|
||||
local width = math.round(math.max((self:getProgress() * (self:getWidth() - self.bgBorderLeft - self.bgBorderRight)), 1))
|
||||
local height = self:getHeight() - self.bgBorderTop - self.bgBorderBottom
|
||||
local rect = { x = self.bgBorderLeft, y = self.bgBorderTop, width = width, height = height }
|
||||
self:setBackgroundRect(rect)
|
||||
end
|
||||
end
|
||||
|
||||
function UIProgressBar:onSetup()
|
||||
self:updateBackground()
|
||||
end
|
||||
|
||||
function UIProgressBar:onStyleApply(name, node)
|
||||
@@ -55,5 +91,8 @@ function UIProgressBar:onStyleApply(name, node)
|
||||
end
|
||||
|
||||
function UIProgressBar:onGeometryChange(oldRect, newRect)
|
||||
if not self:isOn() then
|
||||
self:setHeight(0)
|
||||
end
|
||||
self:updateBackground()
|
||||
end
|
||||
|
@@ -57,4 +57,8 @@ end
|
||||
|
||||
function UIRadioGroup:getSelectedWidget()
|
||||
return self.selectedWidget
|
||||
end
|
||||
end
|
||||
|
||||
function UIRadioGroup:getFirstWidget()
|
||||
return self.widgets[1]
|
||||
end
|
||||
|
@@ -19,7 +19,7 @@ end
|
||||
|
||||
function UIResizeBorder:onDestroy()
|
||||
if self.hovering then
|
||||
g_mouse.restoreCursor()
|
||||
g_mouse.popCursor(self.cursortype)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -27,19 +27,20 @@ function UIResizeBorder:onHoverChange(hovered)
|
||||
if hovered then
|
||||
if g_mouse.isCursorChanged() or g_mouse.isPressed() then return end
|
||||
if self:getWidth() > self:getHeight() then
|
||||
g_mouse.setVerticalCursor()
|
||||
self.vertical = true
|
||||
self.cursortype = 'vertical'
|
||||
else
|
||||
g_mouse.setHorizontalCursor()
|
||||
self.vertical = false
|
||||
self.cursortype = 'horizontal'
|
||||
end
|
||||
g_mouse.pushCursor(self.cursortype)
|
||||
self.hovering = true
|
||||
if not self:isPressed() then
|
||||
g_effects.fadeIn(self)
|
||||
end
|
||||
else
|
||||
if not self:isPressed() and self.hovering then
|
||||
g_mouse.restoreCursor()
|
||||
g_mouse.popCursor(self.cursortype)
|
||||
g_effects.fadeOut(self)
|
||||
self.hovering = false
|
||||
end
|
||||
@@ -67,7 +68,7 @@ end
|
||||
|
||||
function UIResizeBorder:onMouseRelease(mousePos, mouseButton)
|
||||
if not self:isHovered() then
|
||||
g_mouse.restoreCursor()
|
||||
g_mouse.popCursor(self.cursortype)
|
||||
g_effects.fadeOut(self)
|
||||
self.hovering = false
|
||||
end
|
||||
|
@@ -14,11 +14,17 @@ function UIScrollArea:onStyleApply(styleName, styleNode)
|
||||
for name,value in pairs(styleNode) do
|
||||
if name == 'vertical-scrollbar' then
|
||||
addEvent(function()
|
||||
self:setVerticalScrollBar(self:getParent():getChildById(value))
|
||||
local parent = self:getParent()
|
||||
if parent then
|
||||
self:setVerticalScrollBar(parent:getChildById(value))
|
||||
end
|
||||
end)
|
||||
elseif name == 'horizontal-scrollbar' then
|
||||
addEvent(function()
|
||||
self:setHorizontalScrollBar(self:getParent():getChildById(value))
|
||||
local parent = self:getParent()
|
||||
if parent then
|
||||
self:setHorizontalScrollBar(self:getParent():getChildById(value))
|
||||
end
|
||||
end)
|
||||
elseif name == 'inverted-scroll' then
|
||||
self:setInverted(value)
|
||||
@@ -116,26 +122,26 @@ function UIScrollArea:onMouseWheel(mousePos, mouseWheel)
|
||||
return true
|
||||
end
|
||||
|
||||
function UIScrollArea:onChildFocusChange(focusedChild, oldFocused, reason)
|
||||
if focusedChild and (reason == MouseFocusReason or reason == KeyboardFocusReason) then
|
||||
function UIScrollArea:ensureChildVisible(child)
|
||||
if child then
|
||||
local paddingRect = self:getPaddingRect()
|
||||
if self.verticalScrollBar then
|
||||
local deltaY = paddingRect.y - focusedChild:getY()
|
||||
local deltaY = paddingRect.y - child:getY()
|
||||
if deltaY > 0 then
|
||||
self.verticalScrollBar:decrement(deltaY)
|
||||
end
|
||||
|
||||
deltaY = (focusedChild:getY() + focusedChild:getHeight()) - (paddingRect.y + paddingRect.height)
|
||||
deltaY = (child:getY() + child:getHeight()) - (paddingRect.y + paddingRect.height)
|
||||
if deltaY > 0 then
|
||||
self.verticalScrollBar:increment(deltaY)
|
||||
end
|
||||
else
|
||||
local deltaX = paddingRect.x - focusedChild:getX()
|
||||
local deltaX = paddingRect.x - child:getX()
|
||||
if deltaX > 0 then
|
||||
self.horizontalScrollBar:decrement(deltaX)
|
||||
end
|
||||
|
||||
deltaX = (focusedChild:getX() + focusedChild:getWidth()) - (paddingRect.x + paddingRect.width)
|
||||
deltaX = (child:getX() + child:getWidth()) - (paddingRect.x + paddingRect.width)
|
||||
if deltaX > 0 then
|
||||
self.horizontalScrollBar:increment(deltaX)
|
||||
end
|
||||
@@ -143,6 +149,12 @@ function UIScrollArea:onChildFocusChange(focusedChild, oldFocused, reason)
|
||||
end
|
||||
end
|
||||
|
||||
function UIScrollArea:onChildFocusChange(focusedChild, oldFocused, reason)
|
||||
if focusedChild and (reason == MouseFocusReason or reason == KeyboardFocusReason) then
|
||||
self:ensureChildVisible(focusedChild)
|
||||
end
|
||||
end
|
||||
|
||||
function UIScrollArea:onScrollWidthChange()
|
||||
if self.alwaysScrollMaximum and self.horizontalScrollBar then
|
||||
self.horizontalScrollBar:setValue(self.horizontalScrollBar:getMaximum())
|
||||
|
@@ -82,18 +82,30 @@ local function updateSlider(self)
|
||||
end
|
||||
end
|
||||
|
||||
local function parseSliderPos(self, pos, move)
|
||||
local point, delta
|
||||
local function parseSliderPos(self, slider, pos, move)
|
||||
local delta, hotDistance
|
||||
if self.orientation == 'vertical' then
|
||||
point = pos.y
|
||||
delta = move.y
|
||||
hotDistance = pos.y - slider:getY()
|
||||
else
|
||||
point = pos.x
|
||||
delta = move.x
|
||||
hotDistance = pos.x - slider:getX()
|
||||
end
|
||||
|
||||
if (delta > 0 and hotDistance + delta > self.hotDistance) or
|
||||
(delta < 0 and hotDistance + delta < self.hotDistance) then
|
||||
local range, pxrange, px, offset, center = calcValues(self)
|
||||
local newvalue = self.value + delta * (range / (pxrange - px))
|
||||
self:setValue(newvalue)
|
||||
end
|
||||
end
|
||||
|
||||
local function parseSliderPress(self, slider, pos, button)
|
||||
if self.orientation == 'vertical' then
|
||||
self.hotDistance = pos.y - slider:getY()
|
||||
else
|
||||
self.hotDistance = pos.x - slider:getX()
|
||||
end
|
||||
local range, pxrange, px, offset, center = calcValues(self)
|
||||
local newvalue = self.value + delta * (range / (pxrange - px))
|
||||
self:setValue(newvalue)
|
||||
end
|
||||
|
||||
-- public functions
|
||||
@@ -114,10 +126,11 @@ end
|
||||
|
||||
function UIScrollBar:onSetup()
|
||||
self.setupDone = true
|
||||
--signalcall(self.onValueChange, self, self.value)
|
||||
local sliderButton = self:getChildById('sliderButton')
|
||||
g_mouse.bindAutoPress(self:getChildById('decrementButton'), function() self:decrement() end, 300)
|
||||
g_mouse.bindAutoPress(self:getChildById('incrementButton'), function() self:increment() end, 300)
|
||||
g_mouse.bindPressMove(self:getChildById('sliderButton'), function(mousePos, mouseMoved) parseSliderPos(self, mousePos, mouseMoved) end)
|
||||
g_mouse.bindPressMove(sliderButton, function(mousePos, mouseMoved) parseSliderPos(self, sliderButton, mousePos, mouseMoved) end)
|
||||
g_mouse.bindPress(sliderButton, function(mousePos, mouseButton) parseSliderPress(self, sliderButton, mousePos, mouseButton) end)
|
||||
|
||||
updateSlider(self)
|
||||
end
|
||||
|
@@ -118,6 +118,10 @@ function UISpinBox:setValue(value)
|
||||
signalcall(self.onValueChange, self, value)
|
||||
end
|
||||
|
||||
function UISpinBox:getValue()
|
||||
return self.value
|
||||
end
|
||||
|
||||
function UISpinBox:setMinimum(minimum)
|
||||
minimum = minimum or -9223372036854775808
|
||||
self.minimum = minimum
|
||||
@@ -129,6 +133,10 @@ function UISpinBox:setMinimum(minimum)
|
||||
end
|
||||
end
|
||||
|
||||
function UISpinBox:getMinimum()
|
||||
return self.minimum
|
||||
end
|
||||
|
||||
function UISpinBox:setMaximum(maximum)
|
||||
maximum = maximum or 9223372036854775807
|
||||
self.maximum = maximum
|
||||
@@ -137,10 +145,10 @@ function UISpinBox:setMaximum(maximum)
|
||||
end
|
||||
end
|
||||
|
||||
function UISpinBox:getMaximum()
|
||||
return self.maximum
|
||||
end
|
||||
|
||||
function UISpinBox:setStep(step)
|
||||
self.step = step or 1
|
||||
end
|
||||
|
||||
function UISpinBox:getValue()
|
||||
return self.value
|
||||
end
|
||||
|
@@ -14,19 +14,20 @@ function UISplitter:onHoverChange(hovered)
|
||||
if hovered and (self:canUpdateMargin(margin + 1) ~= margin or self:canUpdateMargin(margin - 1) ~= margin) then
|
||||
if g_mouse.isCursorChanged() or g_mouse.isPressed() then return end
|
||||
if self:getWidth() > self:getHeight() then
|
||||
g_mouse.setVerticalCursor()
|
||||
self.vertical = true
|
||||
self.cursortype = 'vertical'
|
||||
else
|
||||
g_mouse.setHorizontalCursor()
|
||||
self.vertical = false
|
||||
self.cursortype = 'horizontal'
|
||||
end
|
||||
self.hovering = true
|
||||
g_mouse.pushCursor(self.cursortype)
|
||||
if not self:isPressed() then
|
||||
g_effects.fadeIn(self)
|
||||
end
|
||||
else
|
||||
if not self:isPressed() and self.hovering then
|
||||
g_mouse.restoreCursor()
|
||||
g_mouse.popCursor(self.cursortype)
|
||||
g_effects.fadeOut(self)
|
||||
self.hovering = false
|
||||
end
|
||||
@@ -67,7 +68,7 @@ end
|
||||
|
||||
function UISplitter:onMouseRelease(mousePos, mouseButton)
|
||||
if not self:isHovered() then
|
||||
g_mouse.restoreCursor()
|
||||
g_mouse.popCursor(self.cursortype)
|
||||
g_effects.fadeOut(self)
|
||||
self.hovering = false
|
||||
end
|
||||
|
@@ -60,6 +60,18 @@ function UITabBar:addTab(text, panel, icon)
|
||||
return tab
|
||||
end
|
||||
|
||||
function UITabBar:addButton(text, func, icon)
|
||||
local button = g_ui.createWidget(self:getStyleName() .. 'Button', self.buttonsPanel)
|
||||
button:setText(text)
|
||||
|
||||
local style = {}
|
||||
style['icon-source'] = icon
|
||||
button:mergeStyle(style)
|
||||
|
||||
button.onClick = func
|
||||
return button
|
||||
end
|
||||
|
||||
function UITabBar:removeTab(tab)
|
||||
local index = table.find(self.tabs, tab)
|
||||
if index == nil then return end
|
||||
|
@@ -216,7 +216,7 @@ end
|
||||
|
||||
function UITable:setHeaderColumnStyle(style)
|
||||
self.headerColumnBaseStyle = style
|
||||
if table.hasKey(HEADER_ID) then
|
||||
if table.haskey(HEADER_ID) then
|
||||
self.columns[HEADER_ID]:setStyle(style)
|
||||
end
|
||||
end
|
||||
|
@@ -5,6 +5,7 @@ function UIWindow.create()
|
||||
local window = UIWindow.internalCreate()
|
||||
window:setTextAlign(AlignTopCenter)
|
||||
window:setDraggable(true)
|
||||
window:setAutoFocusPolicy(AutoFocusFirst)
|
||||
return window
|
||||
end
|
||||
|
||||
|
@@ -175,14 +175,11 @@ function onCreaturePositionChange(creature, newPos, oldPos)
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
function onCreatureOutfitChange(creature, outfit, oldOutfit)
|
||||
if hasCreature(creature) then
|
||||
if doCreatureFitFilters(creature) then
|
||||
addCreature(creature)
|
||||
else
|
||||
removeCreature(creature)
|
||||
end
|
||||
if doCreatureFitFilters(creature) then
|
||||
addCreature(creature)
|
||||
else
|
||||
removeCreature(creature)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -258,6 +255,9 @@ function onBattleButtonMouseRelease(self, mousePosition, mouseButton)
|
||||
mouseWidget.cancelNextRelease = true
|
||||
g_game.look(self.creature)
|
||||
return true
|
||||
elseif mouseButton == MouseLeftButton and g_keyboard.isShiftPressed() then
|
||||
g_game.look(self.creature)
|
||||
return true
|
||||
elseif mouseButton == MouseRightButton and not g_mouse.isPressed(MouseLeftButton) then
|
||||
modules.game_interface.createThingMenu(mousePosition, nil, nil, self.creature)
|
||||
return true
|
||||
|
@@ -50,8 +50,8 @@ function terminate()
|
||||
end
|
||||
|
||||
fightModeRadioGroup:destroy()
|
||||
combatControlsButton:destroy()
|
||||
combatControlsWindow:destroy()
|
||||
combatControlsButton:destroy()
|
||||
|
||||
disconnect(g_game, {
|
||||
onGameStart = online,
|
||||
@@ -92,7 +92,7 @@ end
|
||||
function online()
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
local char = player:getName()
|
||||
local char = g_game.getCharacterName()
|
||||
|
||||
local lastCombatControls = g_settings.getNode('LastCombatControls')
|
||||
|
||||
@@ -116,7 +116,7 @@ function offline()
|
||||
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
local char = player:getName()
|
||||
local char = g_game.getCharacterName()
|
||||
lastCombatControls[char] = {
|
||||
fightMode = g_game.getFightMode(),
|
||||
chaseMode = g_game.getChaseMode(),
|
||||
|
@@ -15,6 +15,9 @@ SpeakTypesSettings = {
|
||||
channelOrange = { speakType = MessageModes.ChannelHighlight, color = '#FE6500' },
|
||||
monsterSay = { speakType = MessageModes.MonsterSay, color = '#FE6500', hideInConsole = true},
|
||||
monsterYell = { speakType = MessageModes.MonsterYell, color = '#FE6500', hideInConsole = true},
|
||||
rvrAnswerFrom = { speakType = MessageModes.RVRAnswer, color = '#FE6500' },
|
||||
rvrAnswerTo = { speakType = MessageModes.RVRAnswer, color = '#FE6500' },
|
||||
rvrContinue = { speakType = MessageModes.RVRContinue, color = '#FFFF00' },
|
||||
}
|
||||
|
||||
SpeakTypes = {
|
||||
@@ -32,6 +35,9 @@ SpeakTypes = {
|
||||
[MessageModes.ChannelHighlight] = SpeakTypesSettings.channelOrange,
|
||||
[MessageModes.MonsterSay] = SpeakTypesSettings.monsterSay,
|
||||
[MessageModes.MonsterYell] = SpeakTypesSettings.monsterYell,
|
||||
[MessageModes.RVRChannel] = SpeakTypesSettings.channelWhite,
|
||||
[MessageModes.RVRContinue] = SpeakTypesSettings.rvrContinue,
|
||||
[MessageModes.RVRAnswer] = SpeakTypesSettings.rvrAnswerFrom,
|
||||
|
||||
-- ignored types
|
||||
[MessageModes.Spell] = SpeakTypesSettings.none,
|
||||
@@ -62,11 +68,15 @@ currentMessageIndex = 0
|
||||
ignoreNpcMessages = false
|
||||
defaultTab = nil
|
||||
serverTab = nil
|
||||
violationsChannelId = nil
|
||||
violationWindow = nil
|
||||
violationReportTab = nil
|
||||
ignoredChannels = {}
|
||||
|
||||
local ignoreSettings = {
|
||||
privateMessages = false,
|
||||
yelling = false,
|
||||
players = {}
|
||||
privateMessages = false,
|
||||
yelling = false,
|
||||
players = {}
|
||||
}
|
||||
|
||||
function init()
|
||||
@@ -76,8 +86,12 @@ function init()
|
||||
onOpenPrivateChannel = onOpenPrivateChannel,
|
||||
onOpenOwnPrivateChannel = onOpenOwnPrivateChannel,
|
||||
onCloseChannel = onCloseChannel,
|
||||
onGameStart = onGameStart,
|
||||
onGameEnd = clear })
|
||||
onRuleViolationChannel = onRuleViolationChannel,
|
||||
onRuleViolationRemove = onRuleViolationRemove,
|
||||
onRuleViolationCancel = onRuleViolationCancel,
|
||||
onRuleViolationLock = onRuleViolationLock,
|
||||
onGameStart = online,
|
||||
onGameEnd = offline })
|
||||
|
||||
consolePanel = g_ui.loadUI('console', modules.game_interface.getBottomPanel())
|
||||
consoleTextEdit = consolePanel:getChildById('consoleTextEdit')
|
||||
@@ -134,8 +148,12 @@ function terminate()
|
||||
onOpenPrivateChannel = onOpenPrivateChannel,
|
||||
onOpenOwnPrivateChannel = onOpenPrivateChannel,
|
||||
onCloseChannel = onCloseChannel,
|
||||
onGameStart = onGameStart,
|
||||
onGameEnd = clear })
|
||||
onRuleViolationChannel = onRuleViolationChannel,
|
||||
onRuleViolationRemove = onRuleViolationRemove,
|
||||
onRuleViolationCancel = onRuleViolationCancel,
|
||||
onRuleViolationLock = onRuleViolationLock,
|
||||
onGameStart = online,
|
||||
onGameEnd = offline })
|
||||
|
||||
if g_game.isOnline() then clear() end
|
||||
|
||||
@@ -147,20 +165,17 @@ function terminate()
|
||||
|
||||
if channelsWindow then
|
||||
channelsWindow:destroy()
|
||||
channelsWindow = nil
|
||||
end
|
||||
|
||||
if ignoreWindow then
|
||||
ignoreWindow:destroy()
|
||||
ignoreWindow = nil
|
||||
end
|
||||
|
||||
if violationWindow then
|
||||
violationWindow:destroy()
|
||||
end
|
||||
|
||||
consolePanel:destroy()
|
||||
consolePanel = nil
|
||||
consoleTextEdit = nil
|
||||
consoleContentPanel = nil
|
||||
consoleTabBar = nil
|
||||
|
||||
ownPrivateName = nil
|
||||
|
||||
Console = nil
|
||||
@@ -177,7 +192,7 @@ end
|
||||
function clear()
|
||||
-- save last open channels
|
||||
local lastChannelsOpen = g_settings.getNode('lastChannelsOpen') or {}
|
||||
local char = g_game.getLocalPlayer():getName()
|
||||
local char = g_game.getCharacterName()
|
||||
local savedChannels = {}
|
||||
local set = false
|
||||
for channelId, channelName in pairs(channels) do
|
||||
@@ -208,8 +223,18 @@ function clear()
|
||||
consoleTabBar:removeTab(npcTab)
|
||||
end
|
||||
|
||||
if violationReportTab then
|
||||
consoleTabBar:removeTab(violationReportTab)
|
||||
violationReportTab = nil
|
||||
end
|
||||
|
||||
consoleTextEdit:clearText()
|
||||
|
||||
if violationWindow then
|
||||
violationWindow:destroy()
|
||||
violationWindow = nil
|
||||
end
|
||||
|
||||
if channelsWindow then
|
||||
channelsWindow:destroy()
|
||||
channelsWindow = nil
|
||||
@@ -223,6 +248,7 @@ end
|
||||
|
||||
function setTextEditText(text)
|
||||
consoleTextEdit:setText(text)
|
||||
consoleTextEdit:setCursorPos(-1)
|
||||
end
|
||||
|
||||
function openHelp()
|
||||
@@ -233,6 +259,24 @@ function openHelp()
|
||||
g_game.joinChannel(helpChannel)
|
||||
end
|
||||
|
||||
function openPlayerReportRuleViolationWindow()
|
||||
if violationWindow or violationReportTab then return end
|
||||
violationWindow = g_ui.loadUI('violationwindow', rootWidget)
|
||||
violationWindow.onEscape = function()
|
||||
violationWindow:destroy()
|
||||
violationWindow = nil
|
||||
end
|
||||
violationWindow.onEnter = function()
|
||||
local text = violationWindow:getChildById('text'):getText()
|
||||
g_game.talkChannel(MessageModes.RVRChannel, 0, text)
|
||||
violationReportTab = addTab(tr('Report Rule') .. '...', true)
|
||||
addTabText(tr('Please wait patiently for a gamemaster to reply') .. '.', SpeakTypesSettings.privateRed, violationReportTab)
|
||||
violationReportTab.locked = true
|
||||
violationWindow:destroy()
|
||||
violationWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
function addTab(name, focus)
|
||||
local tab = getTab(name)
|
||||
if tab then -- is channel already open
|
||||
@@ -242,18 +286,24 @@ function addTab(name, focus)
|
||||
end
|
||||
if focus then
|
||||
consoleTabBar:selectTab(tab)
|
||||
elseif not serverTab or name ~= serverTab:getText() then
|
||||
consoleTabBar:blinkTab(tab)
|
||||
end
|
||||
return tab
|
||||
end
|
||||
|
||||
function removeTab(name)
|
||||
local tab = consoleTabBar:getTab(name)
|
||||
function removeTab(tab)
|
||||
if type(tab) == 'string' then
|
||||
tab = consoleTabBar:getTab(tab)
|
||||
end
|
||||
|
||||
if tab == defaultTab or tab == serverTab then return end
|
||||
|
||||
if tab == violationReportTab then
|
||||
g_game.cancelRuleViolation()
|
||||
violationReportTab = nil
|
||||
elseif tab.violationChatName then
|
||||
g_game.closeRuleViolation(tab.violationChatName)
|
||||
-- notificate the server that we are leaving the channel
|
||||
if tab.channelId then
|
||||
elseif tab.channelId then
|
||||
for k, v in pairs(channels) do
|
||||
if (k == tab.channelId) then channels[k] = nil end
|
||||
end
|
||||
@@ -267,39 +317,43 @@ end
|
||||
|
||||
function removeCurrentTab()
|
||||
local tab = consoleTabBar:getCurrentTab()
|
||||
if tab == defaultTab or tab == serverTab then return end
|
||||
|
||||
-- notificate the server that we are leaving the channel
|
||||
if tab.channelId then
|
||||
for k, v in pairs(channels) do
|
||||
if (k == tab.channelId) then channels[k] = nil end
|
||||
end
|
||||
g_game.leaveChannel(tab.channelId)
|
||||
elseif tab:getText() == "NPCs" then
|
||||
g_game.closeNpcChannel()
|
||||
end
|
||||
|
||||
consoleTabBar:removeTab(tab)
|
||||
removeTab(tab)
|
||||
end
|
||||
|
||||
function getTab(name)
|
||||
return consoleTabBar:getTab(name)
|
||||
end
|
||||
|
||||
function getChannelTab(channelId)
|
||||
local channel = channels[channelId]
|
||||
if channel then
|
||||
return getTab(channel)
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
function getRuleViolationsTab()
|
||||
if violationsChannelId then
|
||||
return getChannelTab(violationsChannelId)
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
function getCurrentTab()
|
||||
return consoleTabBar:getCurrentTab()
|
||||
end
|
||||
|
||||
function addChannel(name, id)
|
||||
channels[id] = name
|
||||
local tab = addTab(name, true)
|
||||
local focus = not table.find(ignoredChannels, id)
|
||||
local tab = addTab(name, focus)
|
||||
tab.channelId = id
|
||||
return tab
|
||||
end
|
||||
|
||||
function addPrivateChannel(receiver)
|
||||
channels[receiver] = receiver
|
||||
return addTab(receiver, true)
|
||||
return addTab(receiver, false)
|
||||
end
|
||||
|
||||
function addPrivateText(text, speaktype, name, isPrivateCommand, creatureName)
|
||||
@@ -364,6 +418,8 @@ function getHighlightedText(text)
|
||||
end
|
||||
|
||||
function addTabText(text, speaktype, tab, creatureName)
|
||||
if not tab or tab.locked or not text or #text == 0 then return end
|
||||
|
||||
if modules.client_options.getOption('showTimestampsInConsole') then
|
||||
text = os.date('%H:%M') .. ' ' .. text
|
||||
end
|
||||
@@ -383,8 +439,7 @@ function addTabText(text, speaktype, tab, creatureName)
|
||||
labelHighlight:setId('consoleLabel' .. consoleBufferHighlight:getChildCount())
|
||||
labelHighlight:setColor("#1f9ffe")
|
||||
|
||||
local player = g_game.getLocalPlayer()
|
||||
if speaktype.npcChat and (player:getName() ~= creatureName or player:getName() == 'Account Manager') then -- Check if it is the npc who is talking
|
||||
if speaktype.npcChat and (g_game.getCharacterName() ~= creatureName or g_game.getCharacterName() == 'Account Manager') then -- Check if it is the npc who is talking
|
||||
local highlightData = getHighlightedText(text)
|
||||
if #highlightData == 0 then
|
||||
labelHighlight:setText("")
|
||||
@@ -431,8 +486,9 @@ function addTabText(text, speaktype, tab, creatureName)
|
||||
labelHighlight:setText("")
|
||||
end
|
||||
|
||||
label.name = creatureName
|
||||
label.onMouseRelease = function (self, mousePos, mouseButton)
|
||||
processMessageMenu(mousePos, mouseButton, creatureName, text)
|
||||
processMessageMenu(mousePos, mouseButton, creatureName, text, self, tab)
|
||||
end
|
||||
|
||||
if consoleBuffer:getChildCount() > MAX_LINES then
|
||||
@@ -444,6 +500,16 @@ function addTabText(text, speaktype, tab, creatureName)
|
||||
end
|
||||
end
|
||||
|
||||
function removeTabLabelByName(tab, name)
|
||||
local panel = consoleTabBar:getTabPanel(tab)
|
||||
local consoleBuffer = panel:getChildById('consoleBuffer')
|
||||
for _,label in pairs(consoleBuffer:getChildren()) do
|
||||
if label.name == name then
|
||||
label:destroy()
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function processChannelTabMenu(tab, mousePos, mouseButton)
|
||||
local menu = g_ui.createWidget('PopupMenu')
|
||||
|
||||
@@ -453,16 +519,19 @@ function processChannelTabMenu(tab, mousePos, mouseButton)
|
||||
--menu:addOption(tr('Show Server Messages'), function() --[[TODO]] end)
|
||||
menu:addSeparator()
|
||||
end
|
||||
menu:addOption(tr('Clear Messages'), function() clearChannel(consoleTabBar) end)
|
||||
|
||||
if consoleTabBar:getCurrentTab() == tab then
|
||||
menu:addOption(tr('Clear Messages'), function() clearChannel(consoleTabBar) end)
|
||||
end
|
||||
--menu:addOption(tr('Save Messages'), function() --[[TODO]] end)
|
||||
|
||||
menu:display(mousePos)
|
||||
end
|
||||
|
||||
function processMessageMenu(mousePos, mouseButton, creatureName, text)
|
||||
function processMessageMenu(mousePos, mouseButton, creatureName, text, label, tab)
|
||||
if mouseButton == MouseRightButton then
|
||||
local menu = g_ui.createWidget('PopupMenu')
|
||||
if creatureName then
|
||||
if creatureName and #creatureName > 0 then
|
||||
if creatureName ~= g_game.getCharacterName() then
|
||||
menu:addOption(tr('Message to ' .. creatureName), function () g_game.openPrivateChannel(creatureName) end)
|
||||
if not g_game.getLocalPlayer():hasVip(creatureName) then
|
||||
@@ -480,19 +549,22 @@ function processMessageMenu(mousePos, mouseButton, creatureName, text)
|
||||
end
|
||||
menu:addSeparator()
|
||||
end
|
||||
--TODO select all
|
||||
menu:addOption(tr('Copy message'), function () g_window.setClipboardText(text) end)
|
||||
|
||||
if modules.game_ruleviolation.hasWindowAccess() then
|
||||
menu:addSeparator()
|
||||
menu:addOption(tr('Rule Violation'), function() modules.game_ruleviolation.show(creatureName, text:match('.+%:%s(.+)')) end)
|
||||
menu:addSeparator()
|
||||
end
|
||||
|
||||
menu:addSeparator()
|
||||
menu:addOption(tr('Copy name'), function () g_window.setClipboardText(creatureName) end)
|
||||
else
|
||||
--TODO select all
|
||||
menu:addOption(tr('Copy message'), function () g_window.setClipboardText(text) end)
|
||||
end
|
||||
if label:hasSelection() then
|
||||
menu:addOption(tr('Copy'), function() g_window.setClipboardText(label:getSelection()) end, '(Ctrl+C)')
|
||||
end
|
||||
menu:addOption(tr('Copy message'), function() g_window.setClipboardText(text) end)
|
||||
menu:addOption(tr('Select all'), function() label:selectAll() end)
|
||||
if tab.violations then
|
||||
menu:addSeparator()
|
||||
menu:addOption(tr('Process') .. ' ' .. creatureName, function() processViolation(creatureName, text) end)
|
||||
menu:addOption(tr('Remove') .. ' ' .. creatureName, function() g_game.closeRuleViolation(creatureName) end)
|
||||
end
|
||||
menu:display(mousePos)
|
||||
end
|
||||
@@ -509,6 +581,14 @@ end
|
||||
|
||||
function sendMessage(message, tab)
|
||||
local tab = tab or getCurrentTab()
|
||||
if not tab then return end
|
||||
|
||||
-- when talking on server log, the message goes to default channel
|
||||
local name = tab:getText()
|
||||
if tab == serverTab or tab == getRuleViolationsTab() then
|
||||
tab = defaultTab
|
||||
name = defaultTab:getText()
|
||||
end
|
||||
|
||||
-- handling chat commands
|
||||
local originalMessage = message
|
||||
@@ -529,7 +609,7 @@ function sendMessage(message, tab)
|
||||
if chatCommandInitial == chatCommandEnd then
|
||||
chatCommandPrivateRepeat = false
|
||||
if chatCommandInitial == "*" then
|
||||
consoleTextEdit:setText('*'.. chatCommandPrivate .. '* ')
|
||||
setTextEditText('*'.. chatCommandPrivate .. '* ')
|
||||
end
|
||||
message = chatCommandMessage:trim()
|
||||
chatCommandPrivateReady = true
|
||||
@@ -548,13 +628,6 @@ function sendMessage(message, tab)
|
||||
end
|
||||
end
|
||||
|
||||
-- when talking on server log, the message goes to default channel
|
||||
local name = tab:getText()
|
||||
if tab == serverTab then
|
||||
tab = defaultTab
|
||||
name = defaultTab:getText()
|
||||
end
|
||||
|
||||
local speaktypedesc
|
||||
if (tab.channelId or tab == defaultTab) and not chatCommandPrivateReady then
|
||||
if tab == defaultTab then
|
||||
@@ -568,12 +641,21 @@ function sendMessage(message, tab)
|
||||
return
|
||||
else
|
||||
local isPrivateCommand = false
|
||||
local priv = true
|
||||
local tabname = name
|
||||
if chatCommandPrivateReady then
|
||||
speaktypedesc = 'privatePlayerToPlayer'
|
||||
name = chatCommandPrivate
|
||||
isPrivateCommand = true
|
||||
elseif tab.npcChat then
|
||||
speaktypedesc = 'privatePlayerToNpc'
|
||||
elseif tab == violationReportTab then
|
||||
speaktypedesc = 'rvrContinue'
|
||||
tabname = tr('Report Rule') .. '...'
|
||||
elseif tab.violationChatName then
|
||||
speaktypedesc = 'rvrAnswerTo'
|
||||
name = tab.violationChatName
|
||||
tabname = tab.violationChatName .. '\'...'
|
||||
else
|
||||
speaktypedesc = 'privatePlayerToPlayer'
|
||||
end
|
||||
@@ -583,8 +665,8 @@ function sendMessage(message, tab)
|
||||
local player = g_game.getLocalPlayer()
|
||||
g_game.talkPrivate(speaktype.speakType, name, message)
|
||||
|
||||
message = applyMessagePrefixies(player:getName(), player:getLevel(), message)
|
||||
addPrivateText(message, speaktype, name, isPrivateCommand, g_game.getCharacterName())
|
||||
message = applyMessagePrefixies(g_game.getCharacterName(), player:getLevel(), message)
|
||||
addPrivateText(message, speaktype, tabname, isPrivateCommand, g_game.getCharacterName())
|
||||
end
|
||||
end
|
||||
|
||||
@@ -615,7 +697,7 @@ function navigateMessageHistory(step)
|
||||
currentMessageIndex = math.min(math.max(currentMessageIndex + step, 0), numCommands)
|
||||
if currentMessageIndex > 0 then
|
||||
local command = messageHistory[numCommands - currentMessageIndex + 1]
|
||||
consoleTextEdit:setText(command)
|
||||
setTextEditText(command)
|
||||
else
|
||||
consoleTextEdit:clearText()
|
||||
end
|
||||
@@ -642,7 +724,13 @@ function onTalk(name, level, mode, message, channelId, creaturePos)
|
||||
if ignoreNpcMessages and mode == MessageModes.NpcFrom then return end
|
||||
|
||||
speaktype = SpeakTypes[mode]
|
||||
if name ~= g_game.getLocalPlayer():getName() then
|
||||
|
||||
if not speaktype then
|
||||
perror('unhandled onTalk message mode ' .. mode .. ': ' .. message)
|
||||
return
|
||||
end
|
||||
|
||||
if name ~= g_game.getCharacterName() then
|
||||
if mode == MessageModes.Yell and isIgnoringYelling() then
|
||||
return
|
||||
elseif speaktype.private and isIgnoringPrivate() and mode ~= MessageModes.NpcFrom then
|
||||
@@ -652,6 +740,10 @@ function onTalk(name, level, mode, message, channelId, creaturePos)
|
||||
end
|
||||
end
|
||||
|
||||
if mode == MessageModes.RVRChannel then
|
||||
channelId = violationsChannelId
|
||||
end
|
||||
|
||||
if (mode == MessageModes.Say or mode == MessageModes.Whisper or mode == MessageModes.Yell or
|
||||
mode == MessageModes.Spell or mode == MessageModes.MonsterSay or mode == MessageModes.MonsterYell or
|
||||
mode == MessageModes.NpcFrom or mode == MessageModes.BarkLow or mode == MessageModes.BarkLoud) and
|
||||
@@ -675,18 +767,18 @@ function onTalk(name, level, mode, message, channelId, creaturePos)
|
||||
|
||||
local defaultMessage = mode <= 3 and true or false
|
||||
|
||||
if not speaktype then
|
||||
perror('unhandled onTalk message mode ' .. mode .. ': ' .. message)
|
||||
return
|
||||
end
|
||||
|
||||
if speaktype == SpeakTypesSettings.none then return end
|
||||
|
||||
if speaktype.hideInConsole then return end
|
||||
|
||||
local composedMessage = applyMessagePrefixies(name, level, message)
|
||||
|
||||
if speaktype.private then
|
||||
if mode == MessageModes.RVRAnswer then
|
||||
violationReportTab.locked = false
|
||||
addTabText(composedMessage, speaktype, violationReportTab, name)
|
||||
elseif mode == MessageModes.RVRContinue then
|
||||
addText(composedMessage, speaktype, name .. '\'...', name)
|
||||
elseif speaktype.private then
|
||||
addPrivateText(composedMessage, speaktype, name, false, name)
|
||||
if modules.client_options.getOption('showPrivateMessagesOnScreen') and speaktype ~= SpeakTypesSettings.privateNpcToPlayer then
|
||||
modules.game_textmessage.displayPrivateMessage(name .. ':\n' .. message)
|
||||
@@ -735,11 +827,45 @@ function onCloseChannel(channelId)
|
||||
end
|
||||
end
|
||||
|
||||
function processViolation(name, text)
|
||||
local tabname = name .. '\'...'
|
||||
local tab = addTab(tabname, true)
|
||||
channels[tabname] = tabname
|
||||
tab.violationChatName = name
|
||||
g_game.openRuleViolation(name)
|
||||
addTabText(text, SpeakTypesSettings.say, tab, name)
|
||||
end
|
||||
|
||||
function onRuleViolationChannel(channelId)
|
||||
violationsChannelId = channelId
|
||||
local tab = addChannel(tr('Rule Violations'), channelId)
|
||||
tab.violations = true
|
||||
end
|
||||
|
||||
function onRuleViolationRemove(name)
|
||||
local tab = getRuleViolationsTab()
|
||||
if not tab then return end
|
||||
removeTabLabelByName(tab, name)
|
||||
end
|
||||
|
||||
function onRuleViolationCancel(name)
|
||||
local tab = getTab(name .. '\'...')
|
||||
if not tab then return end
|
||||
addTabText(tr('%s has finished the request', name) .. '.', SpeakTypesSettings.privateRed, tab)
|
||||
tab.locked = true
|
||||
end
|
||||
|
||||
function onRuleViolationLock()
|
||||
if not violationReportTab then return end
|
||||
addTabText(tr('Your request has been closed') .. '.', SpeakTypesSettings.privateRed, violationReportTab)
|
||||
violationReportTab.locked = true
|
||||
end
|
||||
|
||||
function doChannelListSubmit()
|
||||
local channelListPanel = channelsWindow:getChildById('channelList')
|
||||
local openPrivateChannelWith = channelsWindow:getChildById('openPrivateChannelWith'):getText()
|
||||
if openPrivateChannelWith ~= '' then
|
||||
if openPrivateChannelWith:lower() ~= g_game.getLocalPlayer():getName():lower() then
|
||||
if openPrivateChannelWith:lower() ~= g_game.getCharacterName():lower() then
|
||||
g_game.openPrivateChannel(openPrivateChannelWith)
|
||||
else
|
||||
modules.game_textmessage.displayFailureMessage('You cannot create a private chat channel with yourself.')
|
||||
@@ -885,32 +1011,32 @@ function onClickIgnoreButton()
|
||||
end
|
||||
end
|
||||
|
||||
function onGameStart()
|
||||
function online()
|
||||
if g_game.getProtocolVersion() < 862 then
|
||||
g_keyboard.bindKeyDown('Ctrl+R', openPlayerReportRuleViolationWindow)
|
||||
end
|
||||
-- open last channels
|
||||
local lastChannelsOpen = g_settings.getNode('lastChannelsOpen')
|
||||
if lastChannelsOpen then
|
||||
local savedChannels = lastChannelsOpen[g_game.getLocalPlayer():getName()]
|
||||
local savedChannels = lastChannelsOpen[g_game.getCharacterName()]
|
||||
if savedChannels then
|
||||
for channelName, channelId in pairs(savedChannels) do
|
||||
channelId = tonumber(channelId)
|
||||
if channelId ~= -1 and channelId < 100 then
|
||||
if not table.find(channels, channelId) then
|
||||
g_game.joinChannel(channelId)
|
||||
table.insert(ignoredChannels, channelId)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local tab = defaultTab
|
||||
if tab then
|
||||
--[[
|
||||
Known Issue: The server is calling to open channels after
|
||||
onGameStart is executed causing it to focus the last tab opened.
|
||||
|
||||
Fix: Don't save channels to the settings that are opened by the server.
|
||||
]]
|
||||
addEvent(function() consoleTabBar:selectTab(tab) end, true)
|
||||
end
|
||||
scheduleEvent(function() ignoredChannels = {} end, 3000)
|
||||
end
|
||||
|
||||
function offline()
|
||||
if g_game.getProtocolVersion() < 862 then
|
||||
g_keyboard.unbindKeyDown('Ctrl+R')
|
||||
end
|
||||
clear()
|
||||
end
|
||||
|
@@ -7,6 +7,9 @@ ConsoleLabel < UITextEdit
|
||||
text-auto-resize: true
|
||||
selection-color: #111416
|
||||
selection-background-color: #999999
|
||||
change-cursor-image: false
|
||||
cursor-visible: false
|
||||
editable: false
|
||||
|
||||
ConsolePhantomLabel < UILabel
|
||||
font: verdana-11px-antialised
|
||||
@@ -32,7 +35,7 @@ ConsoleTabBarPanel < MoveableTabBarPanel
|
||||
align-bottom: true
|
||||
border-width: 1
|
||||
border-color: #202327
|
||||
background: #00000044
|
||||
background: #00000066
|
||||
inverted-scroll: true
|
||||
padding: 1
|
||||
|
||||
@@ -44,8 +47,6 @@ ConsoleTabBarPanel < MoveableTabBarPanel
|
||||
layout:
|
||||
type: verticalBox
|
||||
align-bottom: true
|
||||
border-width: 1
|
||||
border-color: #202327
|
||||
inverted-scroll: true
|
||||
padding: 1
|
||||
@onScrollbarChange: |
|
||||
|
38
modules/game_console/violationwindow.otui
Normal file
@@ -0,0 +1,38 @@
|
||||
MainWindow
|
||||
id: ignoreWindow
|
||||
!text: tr('Report Rule Violation')
|
||||
size: 300 240
|
||||
|
||||
Label
|
||||
!text: tr('Please state the rule violation in one clear sentence and wait for a reply from a gamemaster. Please note that your message will disappear if you close the channel.')
|
||||
text-wrap: true
|
||||
text-auto-resize: true
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: parent.top
|
||||
|
||||
TextEdit
|
||||
id: text
|
||||
multiline: true
|
||||
anchors.top: prev.bottom
|
||||
anchors.bottom: next.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin: 8 0
|
||||
|
||||
Button
|
||||
id: buttonOk
|
||||
!text: tr('Ok')
|
||||
width: 64
|
||||
anchors.right: next.left
|
||||
anchors.bottom: parent.bottom
|
||||
margin-right: 10
|
||||
@onClick: self:getParent():onEnter()
|
||||
|
||||
Button
|
||||
id: buttonCancel
|
||||
!text: tr('Cancel')
|
||||
width: 64
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
@onClick: self:getParent():onEscape()
|
@@ -1,11 +1,16 @@
|
||||
local ProgressCallback = {
|
||||
update = 1,
|
||||
finish = 2
|
||||
}
|
||||
|
||||
cooldownWindow = nil
|
||||
cooldownButton = nil
|
||||
contentsPanel = nil
|
||||
spellCooldownPanel = nil
|
||||
lastPlayer = nil
|
||||
|
||||
function init()
|
||||
connect(g_game, { onGameStart = show,
|
||||
onGameEnd = hide,
|
||||
connect(g_game, { onGameStart = online,
|
||||
onSpellGroupCooldown = onSpellGroupCooldown,
|
||||
onSpellCooldown = onSpellCooldown })
|
||||
|
||||
@@ -19,20 +24,19 @@ function init()
|
||||
|
||||
contentsPanel = cooldownWindow:getChildById('contentsPanel')
|
||||
spellCooldownPanel = contentsPanel:getChildById('spellCooldownPanel')
|
||||
|
||||
|
||||
if g_game.isOnline() then
|
||||
show()
|
||||
online()
|
||||
end
|
||||
end
|
||||
|
||||
function terminate()
|
||||
disconnect(g_game, { onGameStart = show,
|
||||
onGameEnd = hide,
|
||||
disconnect(g_game, { onGameStart = online,
|
||||
onSpellGroupCooldown = onSpellGroupCooldown,
|
||||
onSpellCooldown = onSpellCooldown })
|
||||
|
||||
cooldownButton:destroy()
|
||||
cooldownWindow:destroy()
|
||||
cooldownButton:destroy()
|
||||
end
|
||||
|
||||
function onMiniWindowClose()
|
||||
@@ -49,75 +53,123 @@ function toggle()
|
||||
end
|
||||
end
|
||||
|
||||
function show()
|
||||
function online()
|
||||
if g_game.getFeature(GameSpellList) then
|
||||
cooldownWindow:show()
|
||||
cooldownButton:show()
|
||||
else
|
||||
hide()
|
||||
cooldownButton:hide()
|
||||
cooldownWindow:close()
|
||||
end
|
||||
|
||||
if not lastPlayer or lastPlayer ~= g_game.getCharacterName() then
|
||||
refresh()
|
||||
lastPlayer = g_game.getCharacterName()
|
||||
end
|
||||
end
|
||||
|
||||
function hide()
|
||||
cooldownWindow:hide()
|
||||
cooldownButton:hide()
|
||||
function refresh()
|
||||
spellCooldownPanel:destroyChildren()
|
||||
end
|
||||
|
||||
function updateProgressRect(progressRect, interval, init)
|
||||
if init then
|
||||
progressRect:setPercent(0)
|
||||
else
|
||||
progressRect:setPercent(progressRect:getPercent() + 5)
|
||||
function removeCooldown(progressRect)
|
||||
removeEvent(progressRect.event)
|
||||
if progressRect.icon then
|
||||
progressRect.icon:destroy()
|
||||
progressRect.icon = nil
|
||||
end
|
||||
progressRect = nil
|
||||
end
|
||||
|
||||
function turnOffCooldown(progressRect)
|
||||
removeEvent(progressRect.event)
|
||||
if progressRect.icon then
|
||||
progressRect.icon:setOn(false)
|
||||
progressRect.icon = nil
|
||||
end
|
||||
|
||||
-- create particles
|
||||
--[[local particle = g_ui.createWidget('GroupCooldownParticles', progressRect)
|
||||
particle:fill('parent')
|
||||
scheduleEvent(function() particle:destroy() end, 1000) -- hack until onEffectEnd]]
|
||||
|
||||
progressRect = nil
|
||||
end
|
||||
|
||||
function initCooldown(progressRect, updateCallback, finishCallback)
|
||||
progressRect:setPercent(0)
|
||||
|
||||
progressRect.callback = {}
|
||||
progressRect.callback[ProgressCallback.update] = updateCallback
|
||||
progressRect.callback[ProgressCallback.finish] = finishCallback
|
||||
|
||||
updateCallback()
|
||||
end
|
||||
|
||||
function updateCooldown(progressRect, interval)
|
||||
progressRect:setPercent(progressRect:getPercent() + 5)
|
||||
|
||||
if progressRect:getPercent() < 100 then
|
||||
removeEvent(progressRect.event)
|
||||
progressRect.event = scheduleEvent(function() updateProgressRect(progressRect, interval) end, interval)
|
||||
removeEvent(progressRect.event)
|
||||
progressRect.event = scheduleEvent(function() progressRect.callback[ProgressCallback.update]() end, interval)
|
||||
else
|
||||
progressRect.callback[ProgressCallback.finish]()
|
||||
end
|
||||
end
|
||||
|
||||
function onSpellCooldown(iconId, duration)
|
||||
local spellName = SpelllistSettings[modules.game_spelllist.getSpelllistProfile()].spellIcons[iconId]
|
||||
local spell, profile, spellName = Spells.getSpellByIcon(iconId)
|
||||
if not spellName then return end
|
||||
|
||||
local ping = g_game.getPing()
|
||||
if ping > 0 then duration = duration - (ping/2) end
|
||||
local otcIconId = tonumber(SpellInfo[modules.game_spelllist.getSpelllistProfile()][spellName].icon)
|
||||
if not otcIconId and SpellIcons[SpellInfo[modules.game_spelllist.getSpelllistProfile()][spellName].icon] then
|
||||
otcIconId = SpellIcons[SpellInfo[modules.game_spelllist.getSpelllistProfile()][spellName].icon][1]
|
||||
end
|
||||
|
||||
if not otcIconId then return end
|
||||
clientIconId = Spells.getClientId(spellName)
|
||||
if not clientIconId then return end
|
||||
|
||||
local icon = spellCooldownPanel:getChildById(spellName)
|
||||
if not icon then
|
||||
icon = g_ui.createWidget('SpellIcon', spellCooldownPanel)
|
||||
icon:setId(spellName)
|
||||
icon:setImageSource('/images/game/spells/' .. SpelllistSettings[modules.game_spelllist.getSpelllistProfile()].iconFile)
|
||||
icon:setImageClip(modules.game_spelllist.getIconImageClip(otcIconId))
|
||||
icon.event = scheduleEvent(function() icon:destroy() icon = nil end, duration)
|
||||
|
||||
local progressRect = g_ui.createWidget('SpellProgressRect')
|
||||
updateProgressRect(progressRect, duration/25, true)
|
||||
progressRect:setTooltip(spellName)
|
||||
end
|
||||
icon:setImageSource('/images/game/spells/' .. SpelllistSettings[profile].iconFile)
|
||||
icon:setImageClip(Spells.getImageClip(clientIconId, profile))
|
||||
|
||||
local progressRect = icon:getChildById(spellName)
|
||||
if not progressRect then
|
||||
progressRect = g_ui.createWidget('SpellProgressRect', icon)
|
||||
progressRect:setId(spellName)
|
||||
progressRect.icon = icon
|
||||
progressRect:fill('parent')
|
||||
else
|
||||
progressRect:setPercent(0)
|
||||
end
|
||||
progressRect:setTooltip(spellName)
|
||||
|
||||
local updateFunc = function()
|
||||
updateCooldown(progressRect, duration/19)
|
||||
end
|
||||
local finishFunc = function()
|
||||
removeCooldown(progressRect)
|
||||
end
|
||||
initCooldown(progressRect, updateFunc, finishFunc)
|
||||
end
|
||||
|
||||
function onSpellGroupCooldown(groupId, duration)
|
||||
if not SpellGroups[groupId] then return end
|
||||
|
||||
local ping = g_game.getPing()
|
||||
if ping > 0 then duration = duration - (ping/2) end
|
||||
|
||||
local icon = contentsPanel:getChildById('groupIcon' .. SpellGroups[groupId])
|
||||
local progressRect = contentsPanel:getChildById('progressRect' .. SpellGroups[groupId])
|
||||
if icon then
|
||||
icon:setOn(true)
|
||||
removeEvent(icon.event)
|
||||
icon.event = scheduleEvent(function() icon:setOn(false) end, duration)
|
||||
end
|
||||
|
||||
|
||||
progressRect.icon = icon
|
||||
if progressRect then
|
||||
removeEvent(progressRect.event)
|
||||
updateProgressRect(progressRect, duration/25, true)
|
||||
local updateFunc = function()
|
||||
updateCooldown(progressRect, duration/19)
|
||||
end
|
||||
local finishFunc = function()
|
||||
turnOffCooldown(progressRect)
|
||||
end
|
||||
initCooldown(progressRect, updateFunc, finishFunc)
|
||||
end
|
||||
end
|
||||
|
@@ -6,27 +6,25 @@ SpellGroupIcon < UIWidget
|
||||
margin-top: 3
|
||||
|
||||
SpellIcon < UIWidget
|
||||
size: 22 22
|
||||
image-size: 22 22
|
||||
margin-left: 2
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
size: 24 24
|
||||
image-size: 24 24
|
||||
focusable: false
|
||||
|
||||
$first:
|
||||
margin-top: 3
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
|
||||
$!first:
|
||||
margin-left: 1
|
||||
|
||||
SpellProgressRect < UIProgressRect
|
||||
background: #585858AA
|
||||
percent: 100
|
||||
focusable: false
|
||||
|
||||
GroupCooldownParticles < UIParticles
|
||||
effect: groupcooldown-effect
|
||||
|
||||
MiniWindow
|
||||
id: cooldownWindow
|
||||
!text: tr('Spell Cooldowns')
|
||||
height: 85
|
||||
height: 82
|
||||
icon: /images/topbuttons/cooldowns
|
||||
@onClose: modules.game_cooldown.onMiniWindowClose()
|
||||
&save: true
|
||||
@@ -37,7 +35,7 @@ MiniWindow
|
||||
image-clip: 0 0 20 20
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
margin-left: 3
|
||||
margin-left: 2
|
||||
$on:
|
||||
image-clip: 0 20 20 20
|
||||
|
||||
@@ -90,13 +88,14 @@ MiniWindow
|
||||
|
||||
Panel
|
||||
id: spellCooldownPanel
|
||||
margin-top: 5
|
||||
layout:
|
||||
type: horizontalBox
|
||||
height: 30
|
||||
margin-top: 3
|
||||
padding: 3
|
||||
anchors.top: groupIconSpecial.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
height: 30
|
||||
padding: 1
|
||||
margin-left: 2
|
||||
margin-right: 2
|
||||
border: 1 #444444
|
||||
|
||||
background-color: #ffffff11
|
||||
|
||||
|
||||
|
@@ -7,7 +7,7 @@ Icons[16] = { tooltip = tr('You are protected by a magic shield'), path = '/imag
|
||||
Icons[32] = { tooltip = tr('You are paralysed'), path = '/images/game/states/slowed', id = 'condition_slowed' }
|
||||
Icons[64] = { tooltip = tr('You are hasted'), path = '/images/game/states/haste', id = 'condition_haste' }
|
||||
Icons[128] = { tooltip = tr('You may not logout during a fight'), path = '/images/game/states/logout_block', id = 'condition_logout_block' }
|
||||
Icons[256] = { tooltip = tr('You are drowing'), path = '/images/game/states/drowning', id = 'condition_drowning' }
|
||||
Icons[256] = { tooltip = tr('You are drowning'), path = '/images/game/states/drowning', id = 'condition_drowning' }
|
||||
Icons[512] = { tooltip = tr('You are freezing'), path = '/images/game/states/freezing', id = 'condition_freezing' }
|
||||
Icons[1024] = { tooltip = tr('You are dazzled'), path = '/images/game/states/dazzled', id = 'condition_dazzled' }
|
||||
Icons[2048] = { tooltip = tr('You are cursed'), path = '/images/game/states/cursed', id = 'condition_cursed' }
|
||||
@@ -20,15 +20,17 @@ Icons[65536] = { tooltip = tr('You are hungry'), path = '/images/game/states/hun
|
||||
healthInfoWindow = nil
|
||||
healthBar = nil
|
||||
manaBar = nil
|
||||
soulBar = nil
|
||||
healthLabel = nil
|
||||
manaLabel = nil
|
||||
experienceBar = nil
|
||||
soulLabel = nil
|
||||
capLabel = nil
|
||||
healthTooltip = 'Your character health is %d out of %d.'
|
||||
manaTooltip = 'Your character mana is %d out of %d.'
|
||||
experienceTooltip = 'You have %d%% to advance to level %d.'
|
||||
|
||||
function init()
|
||||
connect(LocalPlayer, { onHealthChange = onHealthChange,
|
||||
onManaChange = onManaChange,
|
||||
onLevelChange = onLevelChange,
|
||||
onStatesChange = onStatesChange,
|
||||
onSoulChange = onSoulChange,
|
||||
onFreeCapacityChange = onFreeCapacityChange })
|
||||
@@ -42,9 +44,7 @@ function init()
|
||||
healthInfoWindow:disableResize()
|
||||
healthBar = healthInfoWindow:recursiveGetChildById('healthBar')
|
||||
manaBar = healthInfoWindow:recursiveGetChildById('manaBar')
|
||||
healthLabel = healthInfoWindow:recursiveGetChildById('healthLabel')
|
||||
manaLabel = healthInfoWindow:recursiveGetChildById('manaLabel')
|
||||
soulBar = healthInfoWindow:recursiveGetChildById('soulBar')
|
||||
experienceBar = healthInfoWindow:recursiveGetChildById('experienceBar')
|
||||
soulLabel = healthInfoWindow:recursiveGetChildById('soulLabel')
|
||||
capLabel = healthInfoWindow:recursiveGetChildById('capLabel')
|
||||
|
||||
@@ -52,6 +52,7 @@ function init()
|
||||
local localPlayer = g_game.getLocalPlayer()
|
||||
onHealthChange(localPlayer, localPlayer:getHealth(), localPlayer:getMaxHealth())
|
||||
onManaChange(localPlayer, localPlayer:getMana(), localPlayer:getMaxMana())
|
||||
onLevelChange(localPlayer, localPlayer:getLevel(), localPlayer:getLevelPercent())
|
||||
onStatesChange(localPlayer, localPlayer:getStates(), 0)
|
||||
onSoulChange(localPlayer, localPlayer:getSoul())
|
||||
onFreeCapacityChange(localPlayer, localPlayer:getFreeCapacity())
|
||||
@@ -63,6 +64,7 @@ end
|
||||
function terminate()
|
||||
disconnect(LocalPlayer, { onHealthChange = onHealthChange,
|
||||
onManaChange = onManaChange,
|
||||
onLevelChange = onLevelChange,
|
||||
onStatesChange = onStatesChange,
|
||||
onSoulChange = onSoulChange,
|
||||
onFreeCapacityChange = onFreeCapacityChange })
|
||||
@@ -71,19 +73,6 @@ function terminate()
|
||||
|
||||
healthInfoWindow:destroy()
|
||||
healthInfoButton:destroy()
|
||||
healthInfoWindow = nil
|
||||
healthInfoButton = nil
|
||||
|
||||
healthBar = nil
|
||||
manaBar = nil
|
||||
soulBar = nil
|
||||
|
||||
healthLabel = nil
|
||||
manaLabel = nil
|
||||
soulLabel = nil
|
||||
capLabel = nil
|
||||
|
||||
HealthInfo = nil
|
||||
end
|
||||
|
||||
function toggle()
|
||||
@@ -96,62 +85,6 @@ function toggle()
|
||||
end
|
||||
end
|
||||
|
||||
function hideLabels()
|
||||
capLabel:hide()
|
||||
soulLabel:hide()
|
||||
local removeHeight = capLabel:getHeight() + capLabel:getMarginTop() + capLabel:getMarginBottom()
|
||||
healthInfoWindow:setHeight(math.max(healthInfoWindow.minimizedHeight, healthInfoWindow:getHeight() - removeHeight))
|
||||
end
|
||||
|
||||
function onMiniWindowClose()
|
||||
healthInfoButton:setOn(false)
|
||||
end
|
||||
|
||||
function offline()
|
||||
healthInfoWindow:recursiveGetChildById('conditionPanel'):destroyChildren()
|
||||
end
|
||||
|
||||
-- hooked events
|
||||
function onHealthChange(localPlayer, health, maxHealth)
|
||||
healthLabel:setText(health .. ' / ' .. maxHealth)
|
||||
healthBar:setPercent(health / maxHealth * 100)
|
||||
end
|
||||
|
||||
function onManaChange(localPlayer, mana, maxMana)
|
||||
manaLabel:setText(mana .. ' / ' .. maxMana)
|
||||
|
||||
local percent
|
||||
if maxMana == 0 then
|
||||
percent = 100
|
||||
else
|
||||
percent = (mana * 100)/maxMana
|
||||
end
|
||||
manaBar:setPercent(percent)
|
||||
end
|
||||
|
||||
function onSoulChange(localPlayer, soul)
|
||||
soulLabel:setText(tr('Soul') .. ': ' .. soul)
|
||||
end
|
||||
|
||||
function onFreeCapacityChange(player, freeCapacity)
|
||||
capLabel:setText(tr('Cap') .. ': ' .. freeCapacity)
|
||||
end
|
||||
|
||||
|
||||
function onStatesChange(localPlayer, now, old)
|
||||
if now == old then return end
|
||||
|
||||
local bitsChanged = bit32.bxor(now, old)
|
||||
for i = 1, 32 do
|
||||
local pow = math.pow(2, i-1)
|
||||
if pow > bitsChanged then break end
|
||||
local bitChanged = bit32.band(bitsChanged, pow)
|
||||
if bitChanged ~= 0 then
|
||||
toggleIcon(bitChanged)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function toggleIcon(bitChanged)
|
||||
local content = healthInfoWindow:recursiveGetChildById('conditionPanel')
|
||||
|
||||
@@ -166,3 +99,77 @@ function toggleIcon(bitChanged)
|
||||
end
|
||||
end
|
||||
|
||||
function offline()
|
||||
healthInfoWindow:recursiveGetChildById('conditionPanel'):destroyChildren()
|
||||
end
|
||||
|
||||
-- hooked events
|
||||
function onMiniWindowClose()
|
||||
healthInfoButton:setOn(false)
|
||||
end
|
||||
|
||||
function onHealthChange(localPlayer, health, maxHealth)
|
||||
healthBar:setText(health .. ' / ' .. maxHealth)
|
||||
healthBar:setTooltip(tr(healthTooltip, health, maxHealth))
|
||||
healthBar:setValue(health, 0, maxHealth)
|
||||
end
|
||||
|
||||
function onManaChange(localPlayer, mana, maxMana)
|
||||
manaBar:setText(mana .. ' / ' .. maxMana)
|
||||
manaBar:setTooltip(tr(manaTooltip, mana, maxMana))
|
||||
manaBar:setValue(mana, 0, maxMana)
|
||||
end
|
||||
|
||||
function onLevelChange(localPlayer, value, percent)
|
||||
experienceBar:setText(percent .. '%')
|
||||
experienceBar:setTooltip(tr(experienceTooltip, percent, value+1))
|
||||
experienceBar:setPercent(percent)
|
||||
end
|
||||
|
||||
function onSoulChange(localPlayer, soul)
|
||||
soulLabel:setText(tr('Soul') .. ': ' .. soul)
|
||||
end
|
||||
|
||||
function onFreeCapacityChange(player, freeCapacity)
|
||||
capLabel:setText(tr('Cap') .. ': ' .. freeCapacity)
|
||||
end
|
||||
|
||||
function onStatesChange(localPlayer, now, old)
|
||||
if now == old then return end
|
||||
|
||||
local bitsChanged = bit32.bxor(now, old)
|
||||
for i = 1, 32 do
|
||||
local pow = math.pow(2, i-1)
|
||||
if pow > bitsChanged then break end
|
||||
local bitChanged = bit32.band(bitsChanged, pow)
|
||||
if bitChanged ~= 0 then
|
||||
toggleIcon(bitChanged)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- personalization functions
|
||||
function hideLabels()
|
||||
local removeHeight = math.max(capLabel:getMarginRect().height, soulLabel:getMarginRect().height)
|
||||
capLabel:setOn(false)
|
||||
soulLabel:setOn(false)
|
||||
healthInfoWindow:setHeight(math.max(healthInfoWindow.minimizedHeight, healthInfoWindow:getHeight() - removeHeight))
|
||||
end
|
||||
|
||||
function hideExperience()
|
||||
local removeHeight = experienceBar:getMarginRect().height
|
||||
experienceBar:setOn(false)
|
||||
healthInfoWindow:setHeight(math.max(healthInfoWindow.minimizedHeight, healthInfoWindow:getHeight() - removeHeight))
|
||||
end
|
||||
|
||||
function setHealthTooltip(tooltip)
|
||||
healthTooltip = tooltip
|
||||
end
|
||||
|
||||
function setManaTooltip(tooltip)
|
||||
manaTooltip = tooltip
|
||||
end
|
||||
|
||||
function setExperienceTooltip(tooltip)
|
||||
experienceTooltip = tooltip
|
||||
end
|
||||
|
@@ -1,6 +1,5 @@
|
||||
HealthBar < ProgressBar
|
||||
id: healthBar
|
||||
height: 15
|
||||
background-color: #ff4444
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
@@ -8,30 +7,21 @@ HealthBar < ProgressBar
|
||||
|
||||
ManaBar < ProgressBar
|
||||
id: manaBar
|
||||
height: 15
|
||||
background-color: #4444ff
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 4
|
||||
|
||||
HealthLabel < GameLabel
|
||||
id: healthLabel
|
||||
color: white
|
||||
text-align: center
|
||||
font: verdana-11px-rounded
|
||||
anchors.fill: healthBar
|
||||
margin-top: 2
|
||||
text: 0 / 0
|
||||
|
||||
ManaLabel < GameLabel
|
||||
id: manaLabel
|
||||
color: white
|
||||
text-align: center
|
||||
font: verdana-11px-rounded
|
||||
anchors.fill: manaBar
|
||||
margin-top: 2
|
||||
text: 0 / 0
|
||||
margin-top: 3
|
||||
|
||||
ExperienceBar < ProgressBar
|
||||
id: experienceBar
|
||||
background-color: #B6E866
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
//margin-top: 6
|
||||
//height: 12
|
||||
|
||||
SoulLabel < GameLabel
|
||||
id: soulLabel
|
||||
@@ -43,7 +33,12 @@ SoulLabel < GameLabel
|
||||
anchors.left: parent.horizontalCenter
|
||||
margin-top: 5
|
||||
margin-right: 3
|
||||
text: Soul:
|
||||
on: true
|
||||
|
||||
$!on:
|
||||
visible: false
|
||||
margin-top: 0
|
||||
height: 0
|
||||
|
||||
CapLabel < GameLabel
|
||||
id: capLabel
|
||||
@@ -54,7 +49,12 @@ CapLabel < GameLabel
|
||||
anchors.right: parent.horizontalCenter
|
||||
margin-top: 5
|
||||
margin-left: 3
|
||||
text: Cap:
|
||||
on: true
|
||||
|
||||
$!on:
|
||||
visible: false
|
||||
margin-top: 0
|
||||
height: 0
|
||||
|
||||
ConditionWidget < UIWidget
|
||||
size: 18 18
|
||||
@@ -66,15 +66,14 @@ MiniWindow
|
||||
icon: /images/topbuttons/healthinfo
|
||||
id: healthInfoWindow
|
||||
!text: tr('Health Info')
|
||||
height: 102
|
||||
height: 121
|
||||
@onClose: modules.game_healthinfo.onMiniWindowClose()
|
||||
&save: true
|
||||
|
||||
MiniWindowContents
|
||||
HealthBar
|
||||
HealthLabel
|
||||
ManaBar
|
||||
ManaLabel
|
||||
ExperienceBar
|
||||
Panel
|
||||
id: conditionPanel
|
||||
layout:
|
||||
|