Compare commits

...

16 commits

Author SHA1 Message Date
iZePlayz
632977dea6
Merge b0ebaeed63 into 5fd55ffac1 2025-10-29 18:53:51 +01:00
Cooliokid956
5fd55ffac1
djui_hud_is_mouse_locked() (#986)
Some checks failed
Build coop / build-linux (push) Has been cancelled
Build coop / build-steamos (push) Has been cancelled
Build coop / build-windows-opengl (push) Has been cancelled
Build coop / build-windows-directx (push) Has been cancelled
Build coop / build-macos-arm (push) Has been cancelled
Build coop / build-macos-intel (push) Has been cancelled
* djui_hud_get_mouse_locked()

Adds a total of 1 function:
# `bool djui_hud_get_mouse_locked()`
Returns the DJUI mouse lock status

Tip: This won't return the true state of mouse lock, so make sure to use `get_first_person_enabled()` and `camera_config_is_mouse_look_enabled()` as well

---
This also fills in some descriptions left out by Isaac in his viewport/scissor functions

* djui_hud_is_mouse_locked()

Same as before but is

* this is better imo
2025-10-29 18:41:27 +01:00
Emily♥
9f7ad0f93e
Some syncing fixes for Bowser and Heave Ho (#989)
* Fix Eyerok pounding in multiplayer

Eyerok now only enters the double pound state if ALL players stand on the pedestal rather than just one. Players standing on the pedestal will be ignored. I had to write a new function for this, I hope this is acceptable.

* Suggested changes

I didn't want to change the name of arg0 in eyerok_check_mario_relative_z because it was a vanilla function, but I suppose I can.

* Remove interaction limit for PVP

Fixes issues with certain mods

* Fixes for Bowser and Heave Ho

Hopefully this makes things a bit better.
2025-10-29 18:39:40 +01:00
iZePlayzYT
b0ebaeed63 Added hide chat setting and clearified chat width setting 2025-09-28 07:15:56 +02:00
iZePlayzYT
b2f029bea7 Added Chat Width Config Setting 2025-09-28 06:03:54 +02:00
iZePlayzYT
6c48a5c115 Fixed black text when selecting text in chat 2025-09-28 05:35:18 +02:00
iZePlayzYT
e16e2b4d5c Added char amount display to the chat input box 2025-09-28 05:10:56 +02:00
iZePlayzYT
5812dad90a Chat UI redesigned 2025-09-28 04:25:55 +02:00
iZePlayzYT
5c939c6ded Add tab completion preview for chat commands & subcommands 2025-09-27 22:44:13 +02:00
iZePlayzYT
88a7b246ab Improved chat controls setting checkbox text 2025-09-27 20:55:04 +02:00
iZePlayzYT
9138125c8a Enable classic chatbox controls by default 2025-09-27 20:43:29 +02:00
iZePlayzYT
2decea5693 Prevent duplicate messages in chat history 2025-09-27 20:40:24 +02:00
iZePlayzYT
1805004135 Add keybind to open chat with "/" pre-written 2025-09-25 22:56:27 +02:00
iZePlayzYT
09d29d8e98 Added translations keys 2025-09-24 20:45:01 +02:00
iZePlayzYT
7990d05ccb Added reverse tab completion logic 2025-09-24 20:41:52 +02:00
iZePlayzYT
f137f77826 Fixed the tab completion for the subcommands off the /psc command 2025-09-24 20:32:53 +02:00
33 changed files with 697 additions and 91 deletions

View file

@ -3914,8 +3914,14 @@ function djui_hud_get_raw_mouse_y()
-- ... -- ...
end end
--- @return boolean
--- Checks if the cursor is locked to the window
function djui_hud_is_mouse_locked()
-- ...
end
--- @param locked boolean --- @param locked boolean
--- Sets if the cursor is hidden and constrainted to the window --- Locks (or unlocks) the cursor to the window
function djui_hud_set_mouse_locked(locked) function djui_hud_set_mouse_locked(locked)
-- ... -- ...
end end
@ -3954,12 +3960,12 @@ end
--- @param y number --- @param y number
--- @param width number --- @param width number
--- @param height number --- @param height number
--- Sets the viewport to the specified position and size, this will resize --- Sets the viewport to the specified position and size, this will resize any subsequent DJUI graphics
function djui_hud_set_viewport(x, y, width, height) function djui_hud_set_viewport(x, y, width, height)
-- ... -- ...
end end
--- put the description here --- Resets the viewport to a fullscreen state
function djui_hud_reset_viewport() function djui_hud_reset_viewport()
-- ... -- ...
end end
@ -3968,12 +3974,12 @@ end
--- @param y number --- @param y number
--- @param width number --- @param width number
--- @param height number --- @param height number
--- put the description here --- Sets the scissor rectangle to the specified position and size, this will cut off any subsequent DJUI graphics not within the rectangle
function djui_hud_set_scissor(x, y, width, height) function djui_hud_set_scissor(x, y, width, height)
-- ... -- ...
end end
--- put the description here --- Resets the scissor rectangle to a fullscreen state
function djui_hud_reset_scissor() function djui_hud_reset_scissor()
-- ... -- ...
end end
@ -6443,14 +6449,14 @@ end
--- @param m MarioState --- @param m MarioState
--- @return integer --- @return integer
--- Performs a full Mario stationary physics step (4 substeps) and returns an `GROUND_STEP_*` result --- Performs a full Mario stationary physics step (4 substeps) and returns a `GROUND_STEP_*` result
function stationary_ground_step(m) function stationary_ground_step(m)
-- ... -- ...
end end
--- @param m MarioState --- @param m MarioState
--- @return integer --- @return integer
--- Performs a full Mario ground physics step (4 substeps) and returns an `GROUND_STEP_*` result --- Performs a full Mario ground physics step (4 substeps) and returns a `GROUND_STEP_*` result
function perform_ground_step(m) function perform_ground_step(m)
-- ... -- ...
end end
@ -10029,7 +10035,7 @@ end
--- @param player integer --- @param player integer
--- @return integer --- @return integer
--- Gets the tempo of `player` --- Gets the `tempo` of `player`
function sequence_player_get_tempo(player) function sequence_player_get_tempo(player)
-- ... -- ...
end end
@ -10043,7 +10049,7 @@ end
--- @param player integer --- @param player integer
--- @return integer --- @return integer
--- Gets the tempoAcc (tempo accumulation) of `player` --- Gets the `tempoAcc` (tempo accumulation) of `player`
function sequence_player_get_tempo_acc(player) function sequence_player_get_tempo_acc(player)
-- ... -- ...
end end
@ -10057,7 +10063,7 @@ end
--- @param player integer --- @param player integer
--- @return integer --- @return integer
--- Gets the transposition (pitch) of `player` --- Gets the `transposition` (pitch) of `player`
function sequence_player_get_transposition(player) function sequence_player_get_transposition(player)
-- ... -- ...
end end

View file

@ -3140,10 +3140,31 @@ Returns the y coordinate of the mouse relative to the screen
<br /> <br />
## [djui_hud_is_mouse_locked](#djui_hud_is_mouse_locked)
### Description
Checks if the cursor is locked to the window
### Lua Example
`local booleanValue = djui_hud_is_mouse_locked()`
### Parameters
- None
### Returns
- `boolean`
### C Prototype
`bool djui_hud_is_mouse_locked(void);`
[:arrow_up_small:](#)
<br />
## [djui_hud_set_mouse_locked](#djui_hud_set_mouse_locked) ## [djui_hud_set_mouse_locked](#djui_hud_set_mouse_locked)
### Description ### Description
Sets if the cursor is hidden and constrainted to the window Locks (or unlocks) the cursor to the window
### Lua Example ### Lua Example
`djui_hud_set_mouse_locked(locked)` `djui_hud_set_mouse_locked(locked)`
@ -3271,7 +3292,7 @@ Returns the amount scrolled vertically (-down/up+)
## [djui_hud_set_viewport](#djui_hud_set_viewport) ## [djui_hud_set_viewport](#djui_hud_set_viewport)
### Description ### Description
Sets the viewport to the specified position and size, this will resize Sets the viewport to the specified position and size, this will resize any subsequent DJUI graphics
### Lua Example ### Lua Example
`djui_hud_set_viewport(x, y, width, height)` `djui_hud_set_viewport(x, y, width, height)`
@ -3297,7 +3318,7 @@ Sets the viewport to the specified position and size, this will resize
## [djui_hud_reset_viewport](#djui_hud_reset_viewport) ## [djui_hud_reset_viewport](#djui_hud_reset_viewport)
### Description ### Description
put the description here Resets the viewport to a fullscreen state
### Lua Example ### Lua Example
`djui_hud_reset_viewport()` `djui_hud_reset_viewport()`
@ -3318,7 +3339,7 @@ put the description here
## [djui_hud_set_scissor](#djui_hud_set_scissor) ## [djui_hud_set_scissor](#djui_hud_set_scissor)
### Description ### Description
put the description here Sets the scissor rectangle to the specified position and size, this will cut off any subsequent DJUI graphics not within the rectangle
### Lua Example ### Lua Example
`djui_hud_set_scissor(x, y, width, height)` `djui_hud_set_scissor(x, y, width, height)`
@ -3344,7 +3365,7 @@ put the description here
## [djui_hud_reset_scissor](#djui_hud_reset_scissor) ## [djui_hud_reset_scissor](#djui_hud_reset_scissor)
### Description ### Description
put the description here Resets the scissor rectangle to a fullscreen state
### Lua Example ### Lua Example
`djui_hud_reset_scissor()` `djui_hud_reset_scissor()`

View file

@ -4070,7 +4070,7 @@ Sets all of Mario's velocity variables to 0 and sets his Y position to the floor
## [stationary_ground_step](#stationary_ground_step) ## [stationary_ground_step](#stationary_ground_step)
### Description ### Description
Performs a full Mario stationary physics step (4 substeps) and returns an `GROUND_STEP_*` result Performs a full Mario stationary physics step (4 substeps) and returns a `GROUND_STEP_*` result
### Lua Example ### Lua Example
`local integerValue = stationary_ground_step(m)` `local integerValue = stationary_ground_step(m)`
@ -4093,7 +4093,7 @@ Performs a full Mario stationary physics step (4 substeps) and returns an `GROUN
## [perform_ground_step](#perform_ground_step) ## [perform_ground_step](#perform_ground_step)
### Description ### Description
Performs a full Mario ground physics step (4 substeps) and returns an `GROUND_STEP_*` result Performs a full Mario ground physics step (4 substeps) and returns a `GROUND_STEP_*` result
### Lua Example ### Lua Example
`local integerValue = perform_ground_step(m)` `local integerValue = perform_ground_step(m)`

View file

@ -5276,7 +5276,7 @@ Returns the current sound mode (e.g., stereo, mono) stored in the save file. Use
## [sequence_player_get_tempo](#sequence_player_get_tempo) ## [sequence_player_get_tempo](#sequence_player_get_tempo)
### Description ### Description
Gets the tempo of `player` Gets the `tempo` of `player`
### Lua Example ### Lua Example
`local integerValue = sequence_player_get_tempo(player)` `local integerValue = sequence_player_get_tempo(player)`
@ -5323,7 +5323,7 @@ Sets the `tempo` of `player`. Resets when another sequence is played
## [sequence_player_get_tempo_acc](#sequence_player_get_tempo_acc) ## [sequence_player_get_tempo_acc](#sequence_player_get_tempo_acc)
### Description ### Description
Gets the tempoAcc (tempo accumulation) of `player` Gets the `tempoAcc` (tempo accumulation) of `player`
### Lua Example ### Lua Example
`local integerValue = sequence_player_get_tempo_acc(player)` `local integerValue = sequence_player_get_tempo_acc(player)`
@ -5370,7 +5370,7 @@ Sets the `tempoAcc` (tempo accumulation) of `player`. Resets when another sequen
## [sequence_player_get_transposition](#sequence_player_get_transposition) ## [sequence_player_get_transposition](#sequence_player_get_transposition)
### Description ### Description
Gets the transposition (pitch) of `player` Gets the `transposition` (pitch) of `player`
### Lua Example ### Lua Example
`local integerValue = sequence_player_get_transposition(player)` `local integerValue = sequence_player_get_transposition(player)`

View file

@ -770,6 +770,7 @@
- [djui_hud_get_mouse_y](functions-3.md#djui_hud_get_mouse_y) - [djui_hud_get_mouse_y](functions-3.md#djui_hud_get_mouse_y)
- [djui_hud_get_raw_mouse_x](functions-3.md#djui_hud_get_raw_mouse_x) - [djui_hud_get_raw_mouse_x](functions-3.md#djui_hud_get_raw_mouse_x)
- [djui_hud_get_raw_mouse_y](functions-3.md#djui_hud_get_raw_mouse_y) - [djui_hud_get_raw_mouse_y](functions-3.md#djui_hud_get_raw_mouse_y)
- [djui_hud_is_mouse_locked](functions-3.md#djui_hud_is_mouse_locked)
- [djui_hud_set_mouse_locked](functions-3.md#djui_hud_set_mouse_locked) - [djui_hud_set_mouse_locked](functions-3.md#djui_hud_set_mouse_locked)
- [djui_hud_get_mouse_buttons_down](functions-3.md#djui_hud_get_mouse_buttons_down) - [djui_hud_get_mouse_buttons_down](functions-3.md#djui_hud_get_mouse_buttons_down)
- [djui_hud_get_mouse_buttons_pressed](functions-3.md#djui_hud_get_mouse_buttons_pressed) - [djui_hud_get_mouse_buttons_pressed](functions-3.md#djui_hud_get_mouse_buttons_pressed)

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [JMÉNO|ID] - Hráč bude moci používat příkazy jako
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Změňte, zda vidíte svůj vlastní štítek a zda vidíte zdraví" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Změňte, zda vidíte svůj vlastní štítek a zda vidíte zdraví"
UNRECOGNIZED = "Neznámý příkaz." UNRECOGNIZED = "Neznámý příkaz."
MOD_GRANTED = "\\#fff982\\Jste nyní moderátor." MOD_GRANTED = "\\#fff982\\Jste nyní moderátor."
ALL_COMMANDS = "Všechny příkazy"
TAB_COMPLETE_INFO = "Stiskni TAB pro automatické dokončení příkazů, Shift+TAB naviguje zpět"
[MENU] [MENU]
BACK = "Zpět" BACK = "Zpět"
@ -105,6 +107,7 @@ DEADZONE = "Deadzone"
RUMBLE_STRENGTH = "Síla vibrace" RUMBLE_STRENGTH = "Síla vibrace"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Příkaz)"
PLAYERS = "Hráči" PLAYERS = "Hráči"
D_UP = "D-Pad nahoru" D_UP = "D-Pad nahoru"
D_DOWN = "D-Pad dolů" D_DOWN = "D-Pad dolů"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Debug Errors"
MISC_TITLE = "JINE" MISC_TITLE = "JINE"
PAUSE_IN_SINGLEPLAYER = "Pauza v hře s jedním hráčem" PAUSE_IN_SINGLEPLAYER = "Pauza v hře s jedním hráčem"
DISABLE_POPUPS = "Vypnout vyskakovací okna" DISABLE_POPUPS = "Vypnout vyskakovací okna"
USE_STANDARD_KEY_BINDINGS_CHAT = "Klasické ovládání chatu" USE_STANDARD_KEY_BINDINGS_CHAT = "Použít ovládání chatu Terminal/CMD"
CHAT_WIDTH = "Šířka chatu"
CHAT_WIDTH_TINY = "Drobná"
CHAT_WIDTH_VERY_SMALL = "Velmi malá"
CHAT_WIDTH_SMALL = "Malá"
CHAT_WIDTH_NORMAL = "Normální"
CHAT_WIDTH_BIG = "Velká"
CHAT_WIDTH_VERY_BIG = "Velmi velká"
CHAT_WIDTH_HUGE = "Obrovská"
CHAT_CHAR_COUNTER = "Zobrazit počitadlo znaků chatu"
DISABLE_CHAT_WHEN_CLOSED = "Skrýt chat, když je zavřený"
MENU_OPTIONS = "Nastavení hlavního menu" MENU_OPTIONS = "Nastavení hlavního menu"
INFORMATION = "Informace" INFORMATION = "Informace"
DEBUG = "Debug" DEBUG = "Debug"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAAM|ID] - Geeft deze spelere de toestemming om commando
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Verander of je je eigen naamtag ziet en of je gezondheid ziet" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Verander of je je eigen naamtag ziet en of je gezondheid ziet"
UNRECOGNIZED = "onbekent Chat commando." UNRECOGNIZED = "onbekent Chat commando."
MOD_GRANTED = "\\#fff982\\Je bent nu een Moderator." MOD_GRANTED = "\\#fff982\\Je bent nu een Moderator."
ALL_COMMANDS = "Alle commando's"
TAB_COMPLETE_INFO = "Druk op TAB om opdrachten automatisch aan te vullen, gebruik Shift+TAB om terug te gaan"
[MENU] [MENU]
BACK = "Terug" BACK = "Terug"
@ -105,6 +107,7 @@ DEADZONE = "Doode-zone"
RUMBLE_STRENGTH = "Rommel Kracht" RUMBLE_STRENGTH = "Rommel Kracht"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Commando)"
PLAYERS = "Spelers" PLAYERS = "Spelers"
D_UP = "D Omhoog" D_UP = "D Omhoog"
D_DOWN = "D Naar Beneden" D_DOWN = "D Naar Beneden"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Debug Errors"
MISC_TITLE = "MISC" MISC_TITLE = "MISC"
PAUSE_IN_SINGLEPLAYER = "Pauzeer in een speler" PAUSE_IN_SINGLEPLAYER = "Pauzeer in een speler"
DISABLE_POPUPS = "Popups uitzetten" DISABLE_POPUPS = "Popups uitzetten"
USE_STANDARD_KEY_BINDINGS_CHAT = "Klassieke chatbediening" USE_STANDARD_KEY_BINDINGS_CHAT = "Terminal/CMD Chatbox besturingen gebruiken"
CHAT_WIDTH = "Chatbreedte"
CHAT_WIDTH_TINY = "Zeer klein"
CHAT_WIDTH_VERY_SMALL = "Erg klein"
CHAT_WIDTH_SMALL = "Klein"
CHAT_WIDTH_NORMAL = "Normaal"
CHAT_WIDTH_BIG = "Groot"
CHAT_WIDTH_VERY_BIG = "Zeer groot"
CHAT_WIDTH_HUGE = "Enorm"
CHAT_CHAR_COUNTER = "Chat-tekensteller weergeven"
DISABLE_CHAT_WHEN_CLOSED = "Chat verbergen wanneer gesloten"
MENU_OPTIONS = "Menu Instellingen" MENU_OPTIONS = "Menu Instellingen"
INFORMATION = "Informatie" INFORMATION = "Informatie"
DEBUG = "Debug" DEBUG = "Debug"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Make this player able to use commands like /k
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Change whether or not you see your own nametag and whether or not you see health" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Change whether or not you see your own nametag and whether or not you see health"
UNRECOGNIZED = "Unrecognized chat command." UNRECOGNIZED = "Unrecognized chat command."
MOD_GRANTED = "\\#fff982\\You are now a Moderator." MOD_GRANTED = "\\#fff982\\You are now a Moderator."
ALL_COMMANDS = "All commands"
TAB_COMPLETE_INFO = "Press TAB to autocomplete commands, use Shift+TAB to navigate backwards"
[MENU] [MENU]
BACK = "Back" BACK = "Back"
@ -105,6 +107,7 @@ DEADZONE = "Deadzone"
RUMBLE_STRENGTH = "Rumble Strength" RUMBLE_STRENGTH = "Rumble Strength"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Command)"
PLAYERS = "Players" PLAYERS = "Players"
D_UP = "D-Up" D_UP = "D-Up"
D_DOWN = "D-Down" D_DOWN = "D-Down"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Debug Errors"
MISC_TITLE = "MISC" MISC_TITLE = "MISC"
PAUSE_IN_SINGLEPLAYER = "Pause In Singleplayer" PAUSE_IN_SINGLEPLAYER = "Pause In Singleplayer"
DISABLE_POPUPS = "Disable Popups" DISABLE_POPUPS = "Disable Popups"
USE_STANDARD_KEY_BINDINGS_CHAT = "Classic Chatbox Controls" USE_STANDARD_KEY_BINDINGS_CHAT = "Use Terminal/CMD Chatbox Controls"
CHAT_WIDTH = "Chat Width"
CHAT_WIDTH_TINY = "Tiny"
CHAT_WIDTH_VERY_SMALL = "Very Small"
CHAT_WIDTH_SMALL = "Small"
CHAT_WIDTH_NORMAL = "Normal"
CHAT_WIDTH_BIG = "Big"
CHAT_WIDTH_VERY_BIG = "Very Big"
CHAT_WIDTH_HUGE = "Huge"
CHAT_CHAR_COUNTER = "Show Chat Character Counter"
DISABLE_CHAT_WHEN_CLOSED = "Hide Chat When Closed"
MENU_OPTIONS = "Menu Options" MENU_OPTIONS = "Menu Options"
INFORMATION = "Info" INFORMATION = "Info"
DEBUG = "Debug" DEBUG = "Debug"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Rend ce joueur capable d'utiliser des command
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Modifiez si vous voyez votre propre étiquette de nom et si vous voyez la santé" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Modifiez si vous voyez votre propre étiquette de nom et si vous voyez la santé"
UNRECOGNIZED = "Cette commande n'est pas reconnue." UNRECOGNIZED = "Cette commande n'est pas reconnue."
MOD_GRANTED = "\\#fff982\\Vous êtes désormais un modérateur." MOD_GRANTED = "\\#fff982\\Vous êtes désormais un modérateur."
ALL_COMMANDS = "Toutes les commandes"
TAB_COMPLETE_INFO = "Appuie sur TAB pour compléter automatiquement les commandes, utilise Shift+TAB pour revenir en arrière"
[MENU] [MENU]
BACK = "Retour" BACK = "Retour"
@ -105,6 +107,7 @@ DEADZONE = "Zone Morte"
RUMBLE_STRENGTH = "Vibrations" RUMBLE_STRENGTH = "Vibrations"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Commande)"
PLAYERS = "Joueurs" PLAYERS = "Joueurs"
D_UP = "D Haut" D_UP = "D Haut"
D_DOWN = "D Bas" D_DOWN = "D Bas"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Erreurs de Débogage"
MISC_TITLE = "AUTRES" MISC_TITLE = "AUTRES"
PAUSE_IN_SINGLEPLAYER = "Pause en Solo" PAUSE_IN_SINGLEPLAYER = "Pause en Solo"
DISABLE_POPUPS = "Désactiver les Pop-ups" DISABLE_POPUPS = "Désactiver les Pop-ups"
USE_STANDARD_KEY_BINDINGS_CHAT = "Commandes de chat classiques" USE_STANDARD_KEY_BINDINGS_CHAT = "Utiliser les contrôles de chat Terminal/CMD"
CHAT_WIDTH = "Largeur du chat"
CHAT_WIDTH_TINY = "Minuscule"
CHAT_WIDTH_VERY_SMALL = "Très petite"
CHAT_WIDTH_SMALL = "Petite"
CHAT_WIDTH_NORMAL = "Normale"
CHAT_WIDTH_BIG = "Grande"
CHAT_WIDTH_VERY_BIG = "Très grande"
CHAT_WIDTH_HUGE = "Énorme"
CHAT_CHAR_COUNTER = "Afficher le compteur de caractères du chat"
DISABLE_CHAT_WHEN_CLOSED = "Masquer le chat lorsqu'il est fermé"
MENU_OPTIONS = "Options du menu" MENU_OPTIONS = "Options du menu"
INFORMATION = "Information" INFORMATION = "Information"
DEBUG = "Débogage" DEBUG = "Débogage"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Gebe einem Spieler Moderator rechte wie /kick
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Sichtbarkeit von Spielernamen sowie der KP/Kraft aktivieren oder deaktivieren " NAMETAGS_DESC = "/nametags [show-tag|show-health] - Sichtbarkeit von Spielernamen sowie der KP/Kraft aktivieren oder deaktivieren "
UNRECOGNIZED = "Unbekannter Befehl!" UNRECOGNIZED = "Unbekannter Befehl!"
MOD_GRANTED = "\\#fff982\\Du bist jetzt ein Moderator." MOD_GRANTED = "\\#fff982\\Du bist jetzt ein Moderator."
ALL_COMMANDS = "Alle Befehle"
TAB_COMPLETE_INFO = "Drücke TAB zum Autovervollständigen der Befehle, mit Shift+TAB navigierst du rückwärts"
[MENU] [MENU]
BACK = "Zurück" BACK = "Zurück"
@ -105,6 +107,7 @@ DEADZONE = "Tote Zone"
RUMBLE_STRENGTH = "Vibration-Stärke" RUMBLE_STRENGTH = "Vibration-Stärke"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Befehl)"
PLAYERS = "Spieler" PLAYERS = "Spieler"
D_UP = "D-Hoch" D_UP = "D-Hoch"
D_DOWN = "D-Unten" D_DOWN = "D-Unten"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Debug Fehler"
MISC_TITLE = "SONSTIGES" MISC_TITLE = "SONSTIGES"
PAUSE_IN_SINGLEPLAYER = "Pause im Einzelspieler" PAUSE_IN_SINGLEPLAYER = "Pause im Einzelspieler"
DISABLE_POPUPS = "Pop-ups deaktivieren" DISABLE_POPUPS = "Pop-ups deaktivieren"
USE_STANDARD_KEY_BINDINGS_CHAT = "Standard-Tastennavigation im Chat" USE_STANDARD_KEY_BINDINGS_CHAT = "Terminal/CMD Chatbox-Steuerung verwenden"
CHAT_WIDTH = "Chatbreite"
CHAT_WIDTH_TINY = "Winzig"
CHAT_WIDTH_VERY_SMALL = "Sehr klein"
CHAT_WIDTH_SMALL = "Klein"
CHAT_WIDTH_NORMAL = "Normal"
CHAT_WIDTH_BIG = "Groß"
CHAT_WIDTH_VERY_BIG = "Sehr groß"
CHAT_WIDTH_HUGE = "Riesig"
CHAT_CHAR_COUNTER = "Chat-Zeichenzähler anzeigen"
DISABLE_CHAT_WHEN_CLOSED = "Verstecke Chat wenn geschlossen"
MENU_OPTIONS = "Menüoptionen" MENU_OPTIONS = "Menüoptionen"
INFORMATION = "Info" INFORMATION = "Info"
DEBUG = "Debug" DEBUG = "Debug"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Dai al giocatore il permesso di eseguire coma
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Cambia la visibilità del tuo nome e della salute" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Cambia la visibilità del tuo nome e della salute"
UNRECOGNIZED = "Comando non riconosciuto." UNRECOGNIZED = "Comando non riconosciuto."
MOD_GRANTED = "\\#fff982\\Ora sei un moderatore." MOD_GRANTED = "\\#fff982\\Ora sei un moderatore."
ALL_COMMANDS = "Tutti i comandi"
TAB_COMPLETE_INFO = "Premi TAB per completare automaticamente i comandi, usa Shift+TAB per navigare all'indietro"
[MENU] [MENU]
BACK = "Indietro" BACK = "Indietro"
@ -103,6 +105,7 @@ GAMEPAD = "Controller"
DEADZONE = "Zona Morta" DEADZONE = "Zona Morta"
RUMBLE_STRENGTH = "Intesità Vibrazione" RUMBLE_STRENGTH = "Intesità Vibrazione"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Comando)"
PLAYERS = "Giocatori" PLAYERS = "Giocatori"
D_UP = "D Su" D_UP = "D Su"
D_DOWN = "D Giù" D_DOWN = "D Giù"
@ -317,7 +320,17 @@ DEBUG_ERRORS = "Errori di debug"
MISC_TITLE = "VARIE" MISC_TITLE = "VARIE"
PAUSE_IN_SINGLEPLAYER = "Pausa in Giocatore Singolo" PAUSE_IN_SINGLEPLAYER = "Pausa in Giocatore Singolo"
DISABLE_POPUPS = "Disabilita Popup" DISABLE_POPUPS = "Disabilita Popup"
USE_STANDARD_KEY_BINDINGS_CHAT = "Controlli della chat classici" USE_STANDARD_KEY_BINDINGS_CHAT = "Usa controlli chat Terminale/CMD"
CHAT_WIDTH = "Larghezza chat"
CHAT_WIDTH_TINY = "Minuscola"
CHAT_WIDTH_VERY_SMALL = "Molto piccola"
CHAT_WIDTH_SMALL = "Piccola"
CHAT_WIDTH_NORMAL = "Normale"
CHAT_WIDTH_BIG = "Grande"
CHAT_WIDTH_VERY_BIG = "Molto grande"
CHAT_WIDTH_HUGE = "Enorme"
CHAT_CHAR_COUNTER = "Mostra contatore caratteri della chat"
DISABLE_CHAT_WHEN_CLOSED = "Nascondi chat quando è chiusa"
MENU_OPTIONS = "Opzioni Menù" MENU_OPTIONS = "Opzioni Menù"
INFORMATION = "Informazione" INFORMATION = "Informazione"
DEBUG = "Debug" DEBUG = "Debug"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - プレイヤーに/kick、/ban、/permbanの
NAMETAGS_DESC = "/nametags [show-tag|show-health] - あなたの体力やネームタグの表示を変更します。" NAMETAGS_DESC = "/nametags [show-tag|show-health] - あなたの体力やネームタグの表示を変更します。"
UNRECOGNIZED = "未知のコマンドです。" UNRECOGNIZED = "未知のコマンドです。"
MOD_GRANTED = "\\#fff982\\あなたはモデレーターになりました。" MOD_GRANTED = "\\#fff982\\あなたはモデレーターになりました。"
ALL_COMMANDS = "すべてのコマンド"
TAB_COMPLETE_INFO = "TABキーでコマンドを自動補完、Shift+TABで逆方向に移動"
[MENU] [MENU]
BACK = "戻る" BACK = "戻る"
@ -106,6 +108,7 @@ DEADZONE = "デッドゾーン"
RUMBLE_STRENGTH = "振動の強さ" RUMBLE_STRENGTH = "振動の強さ"
CHAT = "チャット" CHAT = "チャット"
CHAT_COMMAND = "チャット(コマンド)"
PLAYERS = "プレイヤーリストの表示" PLAYERS = "プレイヤーリストの表示"
D_UP = "十字キー 上" D_UP = "十字キー 上"
D_DOWN = "十字キー 下" D_DOWN = "十字キー 下"
@ -320,7 +323,17 @@ DEBUG_ERRORS = "デバッグのエラー"
MISC_TITLE = "MISC" MISC_TITLE = "MISC"
PAUSE_IN_SINGLEPLAYER = "ソロプレイでの一時停止" PAUSE_IN_SINGLEPLAYER = "ソロプレイでの一時停止"
DISABLE_POPUPS = "ポップアップを無効にする" DISABLE_POPUPS = "ポップアップを無効にする"
USE_STANDARD_KEY_BINDINGS_CHAT = "初期のチャット操作" USE_STANDARD_KEY_BINDINGS_CHAT = "ターミナル/CMDチャットボックスコントロールを使用"
CHAT_WIDTH = "チャット幅"
CHAT_WIDTH_TINY = "とても小さい"
CHAT_WIDTH_VERY_SMALL = "かなり小さい"
CHAT_WIDTH_SMALL = "小さい"
CHAT_WIDTH_NORMAL = "標準"
CHAT_WIDTH_BIG = "大きい"
CHAT_WIDTH_VERY_BIG = "とても大きい"
CHAT_WIDTH_HUGE = "巨大"
CHAT_CHAR_COUNTER = "チャットの文字数カウンターを表示"
DISABLE_CHAT_WHEN_CLOSED = "閉じているときはチャットを隠す"
MENU_OPTIONS = "メニューの設定" MENU_OPTIONS = "メニューの設定"
INFORMATION = "情報" INFORMATION = "情報"
DEBUG = "デバッグ" DEBUG = "デバッグ"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Umożliwia temu graczowi korzystanie z polece
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Zmień, czy widzisz swój identyfikator i czy widzisz zdrowie" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Zmień, czy widzisz swój identyfikator i czy widzisz zdrowie"
UNRECOGNIZED = "Nieznane polecenie czatu." UNRECOGNIZED = "Nieznane polecenie czatu."
MOD_GRANTED = "\\#fff982\\Jesteś teraz Moderatorem." MOD_GRANTED = "\\#fff982\\Jesteś teraz Moderatorem."
ALL_COMMANDS = "Wszystkie komendy"
TAB_COMPLETE_INFO = "Naciśnij TAB, aby autouzupełnić polecenia, użyj Shift+TAB, aby cofnąć się"
[MENU] [MENU]
BACK = "Wróć" BACK = "Wróć"
@ -105,6 +107,7 @@ DEADZONE = "Martwa Strefa"
RUMBLE_STRENGTH = "Siła Wibracji" RUMBLE_STRENGTH = "Siła Wibracji"
CHAT = "Czat" CHAT = "Czat"
CHAT_COMMAND = "Czat (Komenda)"
PLAYERS = "Gracze" PLAYERS = "Gracze"
D_UP = "Kierunek w Górę" D_UP = "Kierunek w Górę"
D_DOWN = "Kierunek w Dół" D_DOWN = "Kierunek w Dół"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Błędy z Debugowania"
MISC_TITLE = "POZOSTAŁE OPCJE" MISC_TITLE = "POZOSTAŁE OPCJE"
PAUSE_IN_SINGLEPLAYER = "Pauza w Trybie Pojedynczego Gracza" PAUSE_IN_SINGLEPLAYER = "Pauza w Trybie Pojedynczego Gracza"
DISABLE_POPUPS = "Wyłącz Dymki Powiadomień" DISABLE_POPUPS = "Wyłącz Dymki Powiadomień"
USE_STANDARD_KEY_BINDINGS_CHAT = "Klasyczna Historia Czatu" USE_STANDARD_KEY_BINDINGS_CHAT = "Użyj sterowania czatu Terminal/CMD"
CHAT_WIDTH = "Szerokość czatu"
CHAT_WIDTH_TINY = "Maleńka"
CHAT_WIDTH_VERY_SMALL = "Bardzo mała"
CHAT_WIDTH_SMALL = "Mała"
CHAT_WIDTH_NORMAL = "Normalna"
CHAT_WIDTH_BIG = "Duża"
CHAT_WIDTH_VERY_BIG = "Bardzo duża"
CHAT_WIDTH_HUGE = "Ogromna"
CHAT_CHAR_COUNTER = "Pokaż licznik znaków czatu"
DISABLE_CHAT_WHEN_CLOSED = "Ukryj czat, gdy jest zamknięty"
MENU_OPTIONS = "Opcje Menu" MENU_OPTIONS = "Opcje Menu"
INFORMATION = "Informacja" INFORMATION = "Informacja"
DEBUG = "Debugowanie" DEBUG = "Debugowanie"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NOME|ID] - Permite que um jogador use comandos como /kic
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Altera se você vê sua própria etiqueta ou a barra de vida de outros jogadores" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Altera se você vê sua própria etiqueta ou a barra de vida de outros jogadores"
UNRECOGNIZED = "Comando de chat desconhecido." UNRECOGNIZED = "Comando de chat desconhecido."
MOD_GRANTED = "\\#fff982\\Você é um(a) moderador(a) agora." MOD_GRANTED = "\\#fff982\\Você é um(a) moderador(a) agora."
ALL_COMMANDS = "Todos os comandos"
TAB_COMPLETE_INFO = "Pressiona TAB para autocompletar comandos, usa Shift+TAB para navegar para trás"
[MENU] [MENU]
BACK = "Voltar" BACK = "Voltar"
@ -105,6 +107,7 @@ DEADZONE = "Zona morta"
RUMBLE_STRENGTH = "Força de vibração" RUMBLE_STRENGTH = "Força de vibração"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Comando)"
PLAYERS = "Jogadores" PLAYERS = "Jogadores"
D_UP = "D-Cima" D_UP = "D-Cima"
D_DOWN = "D-Baixo" D_DOWN = "D-Baixo"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Erros de debug"
MISC_TITLE = "OUTROS" MISC_TITLE = "OUTROS"
PAUSE_IN_SINGLEPLAYER = "Pausar com apenas um jogador" PAUSE_IN_SINGLEPLAYER = "Pausar com apenas um jogador"
DISABLE_POPUPS = "Desativar pop-ups" DISABLE_POPUPS = "Desativar pop-ups"
USE_STANDARD_KEY_BINDINGS_CHAT = "Controles clássicos do chat" USE_STANDARD_KEY_BINDINGS_CHAT = "Usar controles de chat Terminal/CMD"
CHAT_WIDTH = "Largura do chat"
CHAT_WIDTH_TINY = "Minúsculo"
CHAT_WIDTH_VERY_SMALL = "Muito pequena"
CHAT_WIDTH_SMALL = "Pequena"
CHAT_WIDTH_NORMAL = "Normal"
CHAT_WIDTH_BIG = "Grande"
CHAT_WIDTH_VERY_BIG = "Muito grande"
CHAT_WIDTH_HUGE = "Enorme"
CHAT_CHAR_COUNTER = "Mostrar contador de caracteres do chat"
DISABLE_CHAT_WHEN_CLOSED = "Ocultar chat quando fechado"
MENU_OPTIONS = "Opções de menu" MENU_OPTIONS = "Opções de menu"
INFORMATION = "Informações" INFORMATION = "Informações"
DEBUG = "Debug" DEBUG = "Debug"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Разрешить игроку исполь
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Измените, видите ли вы свой собственный тег и видите ли здоровье" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Измените, видите ли вы свой собственный тег и видите ли здоровье"
UNRECOGNIZED = "Неизвестная команда чата." UNRECOGNIZED = "Неизвестная команда чата."
MOD_GRANTED = "\\#fff982\\Теперь вы модератор." MOD_GRANTED = "\\#fff982\\Теперь вы модератор."
ALL_COMMANDS = "Все команды"
TAB_COMPLETE_INFO = "Нажми TAB для автодополнения команд, Shift+TAB — переход назад"
[MENU] [MENU]
BACK = "Назад" BACK = "Назад"
@ -104,6 +106,7 @@ DEADZONE = "Mёртвая зона"
RUMBLE_STRENGTH = "Вибрация" RUMBLE_STRENGTH = "Вибрация"
CHAT = "Чат" CHAT = "Чат"
CHAT_COMMAND = "Чат (Команда)"
PLAYERS = "Игроки" PLAYERS = "Игроки"
D_UP = "Крестовина вверх" D_UP = "Крестовина вверх"
D_DOWN = "Крестовина вниз" D_DOWN = "Крестовина вниз"
@ -318,7 +321,17 @@ DEBUG_ERRORS = "Ошибки отладки"
MISC_TITLE = "MISC" MISC_TITLE = "MISC"
PAUSE_IN_SINGLEPLAYER = "Пауза в одиночной игре" PAUSE_IN_SINGLEPLAYER = "Пауза в одиночной игре"
DISABLE_POPUPS = "Отключить всплывающие окна" DISABLE_POPUPS = "Отключить всплывающие окна"
USE_STANDARD_KEY_BINDINGS_CHAT = "Классическое управление чатом" USE_STANDARD_KEY_BINDINGS_CHAT = "Использовать управление чатом Terminal/CMD"
CHAT_WIDTH = "Ширина чата"
CHAT_WIDTH_TINY = "Крошечная"
CHAT_WIDTH_VERY_SMALL = "Очень маленькая"
CHAT_WIDTH_SMALL = "Маленькая"
CHAT_WIDTH_NORMAL = "Обычная"
CHAT_WIDTH_BIG = "Большая"
CHAT_WIDTH_VERY_BIG = "Очень большая"
CHAT_WIDTH_HUGE = "Огромная"
CHAT_CHAR_COUNTER = "Показывать счётчик символов чата"
DISABLE_CHAT_WHEN_CLOSED = "Скрывать чат, когда он закрыт"
MENU_OPTIONS = "Параметры меню" MENU_OPTIONS = "Параметры меню"
INFORMATION = "Информация" INFORMATION = "Информация"
DEBUG = "Отладка" DEBUG = "Отладка"

View file

@ -58,6 +58,8 @@ MOD_DESC = "/moderator [NAME|ID] - Permite a un jugador usar comandos como /kick
NAMETAGS_DESC = "/nametags [show-tag|show-health] - Cambia si ves tu propia etiqueta y si ves la salud" NAMETAGS_DESC = "/nametags [show-tag|show-health] - Cambia si ves tu propia etiqueta y si ves la salud"
UNRECOGNIZED = "Comando desconocido." UNRECOGNIZED = "Comando desconocido."
MOD_GRANTED = "\\#fff982\\Ahora eres un moderador." MOD_GRANTED = "\\#fff982\\Ahora eres un moderador."
ALL_COMMANDS = "Todos los comandos"
TAB_COMPLETE_INFO = "Pulsa TAB para autocompletar comandos, usa Shift+TAB para retroceder"
[MENU] [MENU]
BACK = "Volver" BACK = "Volver"
@ -105,6 +107,7 @@ DEADZONE = "Zona muerta"
RUMBLE_STRENGTH = "Intensidad de vibración" RUMBLE_STRENGTH = "Intensidad de vibración"
CHAT = "Chat" CHAT = "Chat"
CHAT_COMMAND = "Chat (Comando)"
PLAYERS = "Jugadores" PLAYERS = "Jugadores"
D_UP = "Cruz Arriba" D_UP = "Cruz Arriba"
D_DOWN = "Cruz Abajo" D_DOWN = "Cruz Abajo"
@ -319,7 +322,17 @@ DEBUG_ERRORS = "Errores de Depuración"
MISC_TITLE = "OTROS" MISC_TITLE = "OTROS"
PAUSE_IN_SINGLEPLAYER = "Pausa en modo de un jugador" PAUSE_IN_SINGLEPLAYER = "Pausa en modo de un jugador"
DISABLE_POPUPS = "Deshabilitar mensajes emergentes" DISABLE_POPUPS = "Deshabilitar mensajes emergentes"
USE_STANDARD_KEY_BINDINGS_CHAT = "Controles de chat clásicos" USE_STANDARD_KEY_BINDINGS_CHAT = "Usar controles de chat Terminal/CMD"
CHAT_WIDTH = "Ancho del chat"
CHAT_WIDTH_TINY = "Minúsculo"
CHAT_WIDTH_VERY_SMALL = "Muy pequeño"
CHAT_WIDTH_SMALL = "Pequeño"
CHAT_WIDTH_NORMAL = "Normal"
CHAT_WIDTH_BIG = "Grande"
CHAT_WIDTH_VERY_BIG = "Muy grande"
CHAT_WIDTH_HUGE = "Enorme"
CHAT_CHAR_COUNTER = "Mostrar contador de caracteres del chat"
DISABLE_CHAT_WHEN_CLOSED = "Ocultar chat cuando esté cerrado"
MENU_OPTIONS = "Opciones del menú" MENU_OPTIONS = "Opciones del menú"
INFORMATION = "Información" INFORMATION = "Información"
DEBUG = "Depuración" DEBUG = "Depuración"

View file

@ -300,7 +300,7 @@ hook_event(HOOK_ON_INTERACT, star_counter_on_interact)
hook_event(HOOK_ON_HUD_RENDER, hud_render_psc) hook_event(HOOK_ON_HUD_RENDER, hud_render_psc)
hook_event(HOOK_ON_HUD_RENDER_BEHIND, behind_hud_render_psc) hook_event(HOOK_ON_HUD_RENDER_BEHIND, behind_hud_render_psc)
hook_event(HOOK_UPDATE, psc_update) hook_event(HOOK_UPDATE, psc_update)
hook_chat_command('psc', "On|Off - Displays stars you've collected. Default is On.", toggle_psc) hook_chat_command('psc', "[On|Off] - Displays stars you've collected. Default is On.", toggle_psc)
-- Globalize functions for other mods to use -- Globalize functions for other mods to use
-- Created by PeachyPeach -- Created by PeachyPeach

View file

@ -15,15 +15,15 @@ void sequence_channel_set_volume(struct SequenceChannel *seqChannel, u8 volume);
void process_sequences(s32 iterationsRemaining); void process_sequences(s32 iterationsRemaining);
void init_sequence_player(u32 player); void init_sequence_player(u32 player);
void init_sequence_players(void); void init_sequence_players(void);
/* |description|Gets the tempo of `player`|descriptionEnd| */ /* |description|Gets the `tempo` of `player`|descriptionEnd| */
u16 sequence_player_get_tempo(u8 player); u16 sequence_player_get_tempo(u8 player);
/* |description|Sets the `tempo` of `player`. Resets when another sequence is played|descriptionEnd| */ /* |description|Sets the `tempo` of `player`. Resets when another sequence is played|descriptionEnd| */
void sequence_player_set_tempo(u8 player, u16 tempo); void sequence_player_set_tempo(u8 player, u16 tempo);
/* |description|Gets the tempoAcc (tempo accumulation) of `player`|descriptionEnd| */ /* |description|Gets the `tempoAcc` (tempo accumulation) of `player`|descriptionEnd| */
u16 sequence_player_get_tempo_acc(u8 player); u16 sequence_player_get_tempo_acc(u8 player);
/* |description|Sets the `tempoAcc` (tempo accumulation) of `player`. Resets when another sequence is played|descriptionEnd| */ /* |description|Sets the `tempoAcc` (tempo accumulation) of `player`. Resets when another sequence is played|descriptionEnd| */
void sequence_player_set_tempo_acc(u8 player, u16 tempoAcc); void sequence_player_set_tempo_acc(u8 player, u16 tempoAcc);
/* |description|Gets the transposition (pitch) of `player`|descriptionEnd| */ /* |description|Gets the `transposition` (pitch) of `player`|descriptionEnd| */
u16 sequence_player_get_transposition(u8 player); u16 sequence_player_get_transposition(u8 player);
/* |description|Sets the `transposition` (pitch) of `player`. Resets when another sequence is played|descriptionEnd| */ /* |description|Sets the `transposition` (pitch) of `player`. Resets when another sequence is played|descriptionEnd| */
void sequence_player_set_transposition(u8 player, u16 transposition); void sequence_player_set_transposition(u8 player, u16 transposition);

View file

@ -3,6 +3,7 @@ static u32 networkBowserAnimationIndex = 0;
static u8 bowserIsDying = FALSE; static u8 bowserIsDying = FALSE;
static u8 bowserCutscenePlayed = FALSE; static u8 bowserCutscenePlayed = FALSE;
static u8 bowserIsCutscenePlayer = FALSE; static u8 bowserIsCutscenePlayer = FALSE;
static u8 bowserCutsceneGlobalIndex = UNKNOWN_GLOBAL_INDEX;
void bowser_tail_anchor_act_0(void) { void bowser_tail_anchor_act_0(void) {
struct Object* bowser = o->parentObj; struct Object* bowser = o->parentObj;
@ -777,6 +778,10 @@ void bowser_act_thrown_dropped(void)
o->oAction = 4; o->oAction = 4;
else else
o->oAction = 12; o->oAction = 12;
if (is_nearest_mario_state_to_object(gMarioState, o)) {
network_send_object(o);
}
} }
} }
@ -1125,8 +1130,17 @@ void bowser_act_ride_tilting_platform(void) {
cur_obj_extend_animation_if_at_end(); cur_obj_extend_animation_if_at_end();
} }
void bowser_act_nothing(void) { void bowser_act_nothing(void) { // start moving if cutscene player is inactive
if (bowserCutsceneGlobalIndex == UNKNOWN_GLOBAL_INDEX) {
return;
}
struct NetworkPlayer* np = network_player_from_global_index(bowserCutsceneGlobalIndex);
if (np == NULL || !is_player_active(&gMarioStates[np->localIndex])) {
bowserCutscenePlayed = TRUE;
bowser_initialize_action();
return;
}
} }
s32 bowser_check_fallen_off_stage(void) // bowser off stage? s32 bowser_check_fallen_off_stage(void) // bowser off stage?
@ -1232,6 +1246,7 @@ void bowser_held_update(void) {
return; return;
} }
o->parentObj = player;
o->oBowserUnkF4 &= ~0x20000; o->oBowserUnkF4 &= ~0x20000;
cur_obj_become_intangible(); cur_obj_become_intangible();
@ -1385,6 +1400,13 @@ static u8 bhv_bowser_ignore_if_true(void) {
return FALSE; return FALSE;
} }
static void bhv_bowser_on_received_post(UNUSED u8 localIndex) {
// prevent sync from putting bowser in text action instead of nothing action
if (!(bowserIsCutscenePlayer || bowserCutscenePlayed) && (o->oAction == 5 || o->oAction == 6)) {
o->oAction = 20;
}
}
void bhv_bowser_init(void) { void bhv_bowser_init(void) {
bowserIsDying = FALSE; bowserIsDying = FALSE;
s32 level; // 0 is dw, 1 is fs, 2 is sky s32 level; // 0 is dw, 1 is fs, 2 is sky
@ -1408,9 +1430,11 @@ void bhv_bowser_init(void) {
// Make sure we're the first to trigger Bowser. // Make sure we're the first to trigger Bowser.
if (!is_other_player_active()) { if (!is_other_player_active()) {
bowserIsCutscenePlayer = TRUE; bowserIsCutscenePlayer = TRUE;
bowserCutsceneGlobalIndex = gNetworkPlayerLocal->globalIndex;
o->oAction = 5; // bowser_act_text_wait o->oAction = 5; // bowser_act_text_wait
} else { // If we aren't do nothing till we get our sync. } else { // If we aren't do nothing till we get our sync.
bowserIsCutscenePlayer = FALSE; bowserIsCutscenePlayer = FALSE;
bowserCutsceneGlobalIndex = UNKNOWN_GLOBAL_INDEX;
o->oAction = 20; // bowser_act_nothing o->oAction = 20; // bowser_act_nothing
} }
@ -1419,9 +1443,11 @@ void bhv_bowser_init(void) {
if (so) { if (so) {
so->override_ownership = bhv_bowser_override_ownership; so->override_ownership = bhv_bowser_override_ownership;
so->ignore_if_true = bhv_bowser_ignore_if_true; so->ignore_if_true = bhv_bowser_ignore_if_true;
so->on_received_post = bhv_bowser_on_received_post;
so->fullObjectSync = TRUE; so->fullObjectSync = TRUE;
sync_object_init_field_with_size(o, &o->header.gfx.node.flags, 16); sync_object_init_field_with_size(o, &o->header.gfx.node.flags, 16);
sync_object_init_field_with_size(o, &o->header.gfx.animInfo.animFrame, 16); sync_object_init_field_with_size(o, &o->header.gfx.animInfo.animFrame, 16);
sync_object_init_field_with_size(o, &bowserCutsceneGlobalIndex, 8);
sync_object_init_field(o, &networkBowserAnimationIndex); sync_object_init_field(o, &networkBowserAnimationIndex);
sync_object_init_field(o, &o->header.gfx.scale[0]); sync_object_init_field(o, &o->header.gfx.scale[0]);
sync_object_init_field(o, &o->header.gfx.scale[1]); sync_object_init_field(o, &o->header.gfx.scale[1]);

View file

@ -23,7 +23,7 @@ void bhv_heave_ho_throw_mario_loop(void) {
if (player) { if (player) {
player->oInteractStatus |= INT_STATUS_MARIO_UNK2; player->oInteractStatus |= INT_STATUS_MARIO_UNK2;
} }
if (marioState) { if (marioState && marioState->action == ACT_GRABBED) {
marioState->forwardVel = -45.0f; marioState->forwardVel = -45.0f;
marioState->vel[1] = 95.0f; marioState->vel[1] = 95.0f;
} }

View file

@ -36,9 +36,9 @@ u32 mario_update_moving_sand(struct MarioState *m);
u32 mario_update_windy_ground(struct MarioState *m); u32 mario_update_windy_ground(struct MarioState *m);
/* |description|Sets all of Mario's velocity variables to 0 and sets his Y position to the floor height|descriptionEnd| */ /* |description|Sets all of Mario's velocity variables to 0 and sets his Y position to the floor height|descriptionEnd| */
void stop_and_set_height_to_floor(struct MarioState *m); void stop_and_set_height_to_floor(struct MarioState *m);
/* |description|Performs a full Mario stationary physics step (4 substeps) and returns an `GROUND_STEP_*` result|descriptionEnd| */ /* |description|Performs a full Mario stationary physics step (4 substeps) and returns a `GROUND_STEP_*` result|descriptionEnd| */
s32 stationary_ground_step(struct MarioState *m); s32 stationary_ground_step(struct MarioState *m);
/* |description|Performs a full Mario ground physics step (4 substeps) and returns an `GROUND_STEP_*` result|descriptionEnd| */ /* |description|Performs a full Mario ground physics step (4 substeps) and returns a `GROUND_STEP_*` result|descriptionEnd| */
s32 perform_ground_step(struct MarioState *m); s32 perform_ground_step(struct MarioState *m);
/* |description|Performs a full Mario air physics step (4 substeps) and returns an `AIR_STEP_*` result|descriptionEnd| */ /* |description|Performs a full Mario air physics step (4 substeps) and returns an `AIR_STEP_*` result|descriptionEnd| */
s32 perform_air_step(struct MarioState *m, u32 stepArg); s32 perform_air_step(struct MarioState *m, u32 stepArg);

View file

@ -4,6 +4,9 @@
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
#include <assert.h> #include <assert.h>
#ifdef _WIN32
#include <windows.h>
#endif
#include <ctype.h> #include <ctype.h>
#include "platform.h" #include "platform.h"
@ -114,6 +117,7 @@ unsigned int configKeyStickDown[MAX_BINDS] = { 0x001F, VK_INVALID, VK
unsigned int configKeyStickLeft[MAX_BINDS] = { 0x001E, VK_INVALID, VK_INVALID }; unsigned int configKeyStickLeft[MAX_BINDS] = { 0x001E, VK_INVALID, VK_INVALID };
unsigned int configKeyStickRight[MAX_BINDS] = { 0x0020, VK_INVALID, VK_INVALID }; unsigned int configKeyStickRight[MAX_BINDS] = { 0x0020, VK_INVALID, VK_INVALID };
unsigned int configKeyChat[MAX_BINDS] = { 0x001C, VK_INVALID, VK_INVALID }; unsigned int configKeyChat[MAX_BINDS] = { 0x001C, VK_INVALID, VK_INVALID };
unsigned int configKeyChatCommand[MAX_BINDS] = { VK_INVALID, VK_INVALID, VK_INVALID };
unsigned int configKeyPlayerList[MAX_BINDS] = { 0x000F, 0x1004, VK_INVALID }; unsigned int configKeyPlayerList[MAX_BINDS] = { 0x000F, 0x1004, VK_INVALID };
unsigned int configKeyDUp[MAX_BINDS] = { 0x0147, 0x100b, VK_INVALID }; unsigned int configKeyDUp[MAX_BINDS] = { 0x0147, 0x100b, VK_INVALID };
unsigned int configKeyDDown[MAX_BINDS] = { 0x014f, 0x100c, VK_INVALID }; unsigned int configKeyDDown[MAX_BINDS] = { 0x014f, 0x100c, VK_INVALID };
@ -128,7 +132,10 @@ unsigned int configRumbleStrength = 50;
unsigned int configGamepadNumber = 0; unsigned int configGamepadNumber = 0;
bool configBackgroundGamepad = true; bool configBackgroundGamepad = true;
bool configDisableGamepads = false; bool configDisableGamepads = false;
bool configUseStandardKeyBindingsChat = false; bool configUseStandardKeyBindingsChat = true;
bool configChatCharCounter = true;
bool configDisableChatWhenClosed = false;
unsigned int configChatWidth = 800;
bool configSmoothScrolling = false; bool configSmoothScrolling = false;
// free camera settings // free camera settings
bool configEnableFreeCamera = false; bool configEnableFreeCamera = false;
@ -257,6 +264,7 @@ static const struct ConfigOption options[] = {
{.name = "key_stickleft", .type = CONFIG_TYPE_BIND, .uintValue = configKeyStickLeft}, {.name = "key_stickleft", .type = CONFIG_TYPE_BIND, .uintValue = configKeyStickLeft},
{.name = "key_stickright", .type = CONFIG_TYPE_BIND, .uintValue = configKeyStickRight}, {.name = "key_stickright", .type = CONFIG_TYPE_BIND, .uintValue = configKeyStickRight},
{.name = "key_chat", .type = CONFIG_TYPE_BIND, .uintValue = configKeyChat}, {.name = "key_chat", .type = CONFIG_TYPE_BIND, .uintValue = configKeyChat},
{.name = "key_chat_command", .type = CONFIG_TYPE_BIND, .uintValue = configKeyChatCommand},
{.name = "key_playerlist", .type = CONFIG_TYPE_BIND, .uintValue = configKeyPlayerList}, {.name = "key_playerlist", .type = CONFIG_TYPE_BIND, .uintValue = configKeyPlayerList},
{.name = "key_dup", .type = CONFIG_TYPE_BIND, .uintValue = configKeyDUp}, {.name = "key_dup", .type = CONFIG_TYPE_BIND, .uintValue = configKeyDUp},
{.name = "key_ddown", .type = CONFIG_TYPE_BIND, .uintValue = configKeyDDown}, {.name = "key_ddown", .type = CONFIG_TYPE_BIND, .uintValue = configKeyDDown},
@ -274,6 +282,9 @@ static const struct ConfigOption options[] = {
{.name = "disable_gamepads", .type = CONFIG_TYPE_BOOL, .boolValue = &configDisableGamepads}, {.name = "disable_gamepads", .type = CONFIG_TYPE_BOOL, .boolValue = &configDisableGamepads},
#endif #endif
{.name = "use_standard_key_bindings_chat", .type = CONFIG_TYPE_BOOL, .boolValue = &configUseStandardKeyBindingsChat}, {.name = "use_standard_key_bindings_chat", .type = CONFIG_TYPE_BOOL, .boolValue = &configUseStandardKeyBindingsChat},
{.name = "chat_width", .type = CONFIG_TYPE_UINT, .uintValue = &configChatWidth},
{.name = "chat_char_counter", .type = CONFIG_TYPE_BOOL, .boolValue = &configChatCharCounter},
{.name = "disable_chat_when_closed", .type = CONFIG_TYPE_BOOL, .boolValue = &configDisableChatWhenClosed},
{.name = "smooth_scrolling", .type = CONFIG_TYPE_BOOL, .boolValue = &configSmoothScrolling}, {.name = "smooth_scrolling", .type = CONFIG_TYPE_BOOL, .boolValue = &configSmoothScrolling},
{.name = "stick_rotate_left", .type = CONFIG_TYPE_BOOL, .boolValue = &configStick.rotateLeft}, {.name = "stick_rotate_left", .type = CONFIG_TYPE_BOOL, .boolValue = &configStick.rotateLeft},
{.name = "stick_invert_left_x", .type = CONFIG_TYPE_BOOL, .boolValue = &configStick.invertLeftX}, {.name = "stick_invert_left_x", .type = CONFIG_TYPE_BOOL, .boolValue = &configStick.invertLeftX},
@ -666,6 +677,23 @@ static void configfile_load_internal(const char *filename, bool* error) {
if (file == NULL) { if (file == NULL) {
// Create a new config file and save defaults // Create a new config file and save defaults
printf("Config file '%s' not found. Creating it.\n", filename); printf("Config file '%s' not found. Creating it.\n", filename);
// set sensible default for chat command key depending on keyboard layout
if (configKeyChatCommand[0] == VK_INVALID && configKeyChatCommand[1] == VK_INVALID && configKeyChatCommand[2] == VK_INVALID) {
#ifdef _WIN32
HKL hkl = GetKeyboardLayout(0);
LANGID lang = LOWORD(hkl);
switch (PRIMARYLANGID(lang)) {
case LANG_GERMAN:
configKeyChatCommand[0] = 0x002B; // '#' on QWERTZ (OEM_5 position)
break;
default:
configKeyChatCommand[0] = 0x0035; // '/' on US QWERTY
break;
}
#else
configKeyChatCommand[0] = 0x0035; // '/' default on non-Windows
#endif
}
configfile_save(filename); configfile_save(filename);
return; return;
} }
@ -777,6 +805,23 @@ NEXT_OPTION:
} }
fs_close(file); fs_close(file);
// If user has no chat command bind yet, set a default based on layout
if (configKeyChatCommand[0] == VK_INVALID && configKeyChatCommand[1] == VK_INVALID && configKeyChatCommand[2] == VK_INVALID) {
#ifdef _WIN32
HKL hkl = GetKeyboardLayout(0);
LANGID lang = LOWORD(hkl);
switch (PRIMARYLANGID(lang)) {
case LANG_GERMAN:
configKeyChatCommand[0] = 0x002B; // '#'
break;
default:
configKeyChatCommand[0] = 0x0035; // '/'
break;
}
#else
configKeyChatCommand[0] = 0x0035;
#endif
}
if (configFramerateMode < 0 || configFramerateMode > RRM_MAX) { configFramerateMode = 0; } if (configFramerateMode < 0 || configFramerateMode > RRM_MAX) { configFramerateMode = 0; }
if (configFrameLimit < 30) { configFrameLimit = 30; } if (configFrameLimit < 30) { configFrameLimit = 30; }

View file

@ -80,6 +80,7 @@ extern unsigned int configKeyStickDown[MAX_BINDS];
extern unsigned int configKeyStickLeft[MAX_BINDS]; extern unsigned int configKeyStickLeft[MAX_BINDS];
extern unsigned int configKeyStickRight[MAX_BINDS]; extern unsigned int configKeyStickRight[MAX_BINDS];
extern unsigned int configKeyChat[MAX_BINDS]; extern unsigned int configKeyChat[MAX_BINDS];
extern unsigned int configKeyChatCommand[MAX_BINDS];
extern unsigned int configKeyPlayerList[MAX_BINDS]; extern unsigned int configKeyPlayerList[MAX_BINDS];
extern unsigned int configKeyDUp[MAX_BINDS]; extern unsigned int configKeyDUp[MAX_BINDS];
extern unsigned int configKeyDDown[MAX_BINDS]; extern unsigned int configKeyDDown[MAX_BINDS];
@ -95,6 +96,9 @@ extern unsigned int configGamepadNumber;
extern bool configBackgroundGamepad; extern bool configBackgroundGamepad;
extern bool configDisableGamepads; extern bool configDisableGamepads;
extern bool configUseStandardKeyBindingsChat; extern bool configUseStandardKeyBindingsChat;
extern bool configChatCharCounter;
extern bool configDisableChatWhenClosed;
extern unsigned int configChatWidth;
extern bool configSmoothScrolling; extern bool configSmoothScrolling;
// free camera settings // free camera settings
extern bool configEnableFreeCamera; extern bool configEnableFreeCamera;

View file

@ -54,6 +54,11 @@ void sent_history_init(ArrayList *arrayList) {
void sent_history_add_message(ArrayList *arrayList, const char *newMessage) { void sent_history_add_message(ArrayList *arrayList, const char *newMessage) {
if (!configUseStandardKeyBindingsChat && (!newMessage || newMessage[0] != '/')) { return; } if (!configUseStandardKeyBindingsChat && (!newMessage || newMessage[0] != '/')) { return; }
// Don't add duplicate messages - check if the new message is the same as the last one
if (arrayList->size > 0 && strcmp(arrayList->messages[arrayList->size - 1], newMessage) == 0) {
return;
}
if (arrayList->size == MAX_HISTORY_SIZE) { if (arrayList->size == MAX_HISTORY_SIZE) {
for (s32 i = 1; i < MAX_HISTORY_SIZE; i++) { for (s32 i = 1; i < MAX_HISTORY_SIZE; i++) {
snprintf(arrayList->messages[i-1], MAX_CHAT_MSG_LENGTH, "%s", arrayList->messages[i]); snprintf(arrayList->messages[i-1], MAX_CHAT_MSG_LENGTH, "%s", arrayList->messages[i]);
@ -100,7 +105,7 @@ void sent_history_reset_navigation(ArrayList *arrayList) {
bool djui_chat_box_render(struct DjuiBase* base) { bool djui_chat_box_render(struct DjuiBase* base) {
struct DjuiChatBox* chatBox = (struct DjuiChatBox*)base; struct DjuiChatBox* chatBox = (struct DjuiChatBox*)base;
struct DjuiBase* ccBase = &chatBox->chatContainer->base; struct DjuiBase* ccBase = &chatBox->chatContainer->base;
djui_base_set_size(ccBase, 1.0f, chatBox->base.comp.height - 32 - 8); djui_base_set_size(ccBase, 1.0f, chatBox->base.comp.height - 32 - 18);
if (chatBox->scrolling) { if (chatBox->scrolling) {
f32 yMax = chatBox->chatContainer->base.elem.height - chatBox->chatFlow->base.height.value; f32 yMax = chatBox->chatContainer->base.elem.height - chatBox->chatFlow->base.height.value;
f32 target = chatBox->chatFlow->base.y.value + (chatBox->scrollY - chatBox->chatFlow->base.y.value) * (configSmoothScrolling ? 0.5f : 1.f); f32 target = chatBox->chatFlow->base.y.value + (chatBox->scrollY - chatBox->chatFlow->base.y.value) * (configSmoothScrolling ? 0.5f : 1.f);
@ -130,7 +135,12 @@ static void djui_chat_box_set_focus_style(void) {
djui_interactable_set_input_focus(&gDjuiChatBox->chatInput->base); djui_interactable_set_input_focus(&gDjuiChatBox->chatInput->base);
} }
djui_base_set_color(&gDjuiChatBox->chatFlow->base, 0, 0, 0, gDjuiChatBoxFocus ? 128 : 0); bool hasMessages = (gDjuiChatBox->chatFlow->base.height.value > 2.0f);
u8 alpha = 0;
if (hasMessages) {
alpha = gDjuiChatBoxFocus ? 160 : 0;
}
djui_base_set_color(&gDjuiChatBox->chatFlow->base, 0, 0, 0, alpha);
} }
static void djui_chat_box_input_enter(struct DjuiInputbox* chatInput) { static void djui_chat_box_input_enter(struct DjuiInputbox* chatInput) {
@ -140,6 +150,10 @@ static void djui_chat_box_input_enter(struct DjuiInputbox* chatInput) {
sent_history_add_message(&sentHistory, chatInput->buffer); sent_history_add_message(&sentHistory, chatInput->buffer);
if (chatInput->buffer[0] == '/') { if (chatInput->buffer[0] == '/') {
if (strcmp(chatInput->buffer, "/help") == 0 || strcmp(chatInput->buffer, "/?") == 0 || strcmp(chatInput->buffer, "/") == 0) { if (strcmp(chatInput->buffer, "/help") == 0 || strcmp(chatInput->buffer, "/?") == 0 || strcmp(chatInput->buffer, "/") == 0) {
char tabcompletionHint[MAX_CHAT_MSG_LENGTH];
snprintf(tabcompletionHint, sizeof(tabcompletionHint), "\\#ff2020\\%s \\#ffa020\\(%s)\\#ff2020\\:\\#000000\\",
DLANG(CHAT, ALL_COMMANDS), DLANG(CHAT, TAB_COMPLETE_INFO));
djui_chat_message_create(tabcompletionHint);
display_chat_commands(); display_chat_commands();
} else if (!exec_chat_command(chatInput->buffer)) { } else if (!exec_chat_command(chatInput->buffer)) {
char extendedUnknownCommandMessage[MAX_CHAT_MSG_LENGTH]; char extendedUnknownCommandMessage[MAX_CHAT_MSG_LENGTH];
@ -176,7 +190,7 @@ static char* get_main_command_from_input(const char* input) {
return command; return command;
} }
static bool complete_subcommand(const char* mainCommand, const char* subCommandPrefix) { static bool complete_subcommand(const char* mainCommand, const char* subCommandPrefix, bool reverse) {
char** subcommands = smlua_get_chat_subcommands_list(mainCommand); char** subcommands = smlua_get_chat_subcommands_list(mainCommand);
if (!subcommands || !subcommands[0]) { if (!subcommands || !subcommands[0]) {
@ -192,7 +206,13 @@ static bool complete_subcommand(const char* mainCommand, const char* subCommandP
bool completionSuccess = false; bool completionSuccess = false;
if (foundSubCommandsCount > 0) { if (foundSubCommandsCount > 0) {
sCommandsTabCompletionIndex = (sCommandsTabCompletionIndex + 1) % foundSubCommandsCount; if (reverse) {
sCommandsTabCompletionIndex = (sCommandsTabCompletionIndex <= 0)
? foundSubCommandsCount - 1
: (sCommandsTabCompletionIndex - 1) % foundSubCommandsCount;
} else {
sCommandsTabCompletionIndex = (sCommandsTabCompletionIndex + 1) % foundSubCommandsCount;
}
s32 currentIndex = 0; s32 currentIndex = 0;
for (s32 i = 0; subcommands[i] != NULL; i++) { for (s32 i = 0; subcommands[i] != NULL; i++) {
@ -273,7 +293,7 @@ void djui_inputbox_replace_current_word(struct DjuiInputbox* inputbox, char* tex
djui_inputbox_move_cursor_to_position(inputbox, currentWordStart + strlen(text)); djui_inputbox_move_cursor_to_position(inputbox, currentWordStart + strlen(text));
} }
static bool complete_player_name(const char* namePrefix) { static bool complete_player_name(const char* namePrefix, bool reverse) {
char** playerNames = smlua_get_chat_player_list(); char** playerNames = smlua_get_chat_player_list();
if (!playerNames || !playerNames[0]) { if (!playerNames || !playerNames[0]) {
if (playerNames) { if (playerNames) {
@ -291,7 +311,13 @@ static bool complete_player_name(const char* namePrefix) {
bool completionSuccess = false; bool completionSuccess = false;
if (foundNamesCount > 0) { if (foundNamesCount > 0) {
sPlayersTabCompletionIndex = (sPlayersTabCompletionIndex + 1) % foundNamesCount; if (reverse) {
sPlayersTabCompletionIndex = (sPlayersTabCompletionIndex <= 0)
? foundNamesCount - 1
: (sPlayersTabCompletionIndex - 1) % foundNamesCount;
} else {
sPlayersTabCompletionIndex = (sPlayersTabCompletionIndex + 1) % foundNamesCount;
}
s32 currentIndex = 0; s32 currentIndex = 0;
for (s32 i = 0; playerNames[i] != NULL; i++) { for (s32 i = 0; playerNames[i] != NULL; i++) {
@ -314,14 +340,83 @@ static bool complete_player_name(const char* namePrefix) {
return completionSuccess; return completionSuccess;
} }
static void handle_tab_completion(void) { char* get_next_tab_completion_preview(const char* input) {
if (input[0] != '/') {
return NULL;
}
char* spacePosition = strrchr(input, ' ');
if (spacePosition != NULL) {
// Subcommand completion
char* mainCommand = get_main_command_from_input(input);
if (mainCommand) {
char** subcommands = smlua_get_chat_subcommands_list(mainCommand + 1);
if (subcommands && subcommands[0]) {
s32 foundSubCommandsCount = 0;
// Count matching subcommands
for (s32 i = 0; subcommands[i] != NULL; i++) {
if (strncmp(subcommands[i], spacePosition + 1, strlen(spacePosition + 1)) == 0) {
foundSubCommandsCount++;
}
}
if (foundSubCommandsCount > 0) {
// Find the first matching subcommand
for (s32 i = 0; subcommands[i] != NULL; i++) {
if (strncmp(subcommands[i], spacePosition + 1, strlen(spacePosition + 1)) == 0) {
char* preview = malloc(MAX_CHAT_MSG_LENGTH);
// Only show the missing part of the subcommand
char* inputSubcommand = spacePosition + 1;
char* missingPart = subcommands[i] + strlen(inputSubcommand);
snprintf(preview, MAX_CHAT_MSG_LENGTH, "%s", missingPart);
free(mainCommand);
return preview;
}
}
}
}
free(mainCommand);
}
} else {
// Main command completion
char* bufferWithoutSlash = (char*)input + 1;
char** commands = smlua_get_chat_maincommands_list();
if (commands && commands[0]) {
s32 foundCommandsCount = 0;
// Count matching commands
for (s32 i = 0; commands[i] != NULL; i++) {
if (strncmp(commands[i], bufferWithoutSlash, strlen(bufferWithoutSlash)) == 0) {
foundCommandsCount++;
}
}
if (foundCommandsCount > 0) {
// Find the first matching command
for (s32 i = 0; commands[i] != NULL; i++) {
if (strncmp(commands[i], bufferWithoutSlash, strlen(bufferWithoutSlash)) == 0) {
char* preview = malloc(MAX_CHAT_MSG_LENGTH);
// Only show the missing part of the command
snprintf(preview, MAX_CHAT_MSG_LENGTH, "%s", commands[i] + strlen(bufferWithoutSlash));
return preview;
}
}
}
}
}
return NULL;
}
static void handle_tab_completion(bool reverse) {
bool alreadyTabCompleted = false; bool alreadyTabCompleted = false;
if (gDjuiChatBox->chatInput->buffer[0] == '/') { if (gDjuiChatBox->chatInput->buffer[0] == '/') {
char* spacePosition = strrchr(sCommandsTabCompletionOriginalText, ' '); char* spacePosition = strrchr(sCommandsTabCompletionOriginalText, ' ');
if (spacePosition != NULL) { if (spacePosition != NULL) {
char* mainCommand = get_main_command_from_input(sCommandsTabCompletionOriginalText); char* mainCommand = get_main_command_from_input(sCommandsTabCompletionOriginalText);
if (mainCommand) { if (mainCommand) {
if (!complete_subcommand(mainCommand + 1, spacePosition + 1)) { if (!complete_subcommand(mainCommand + 1, spacePosition + 1, reverse)) {
reset_tab_completion_all(); reset_tab_completion_all();
} else { } else {
alreadyTabCompleted = true; alreadyTabCompleted = true;
@ -344,7 +439,13 @@ static void handle_tab_completion(void) {
} }
if (foundCommandsCount > 0) { if (foundCommandsCount > 0) {
sCommandsTabCompletionIndex = (sCommandsTabCompletionIndex + 1) % foundCommandsCount; if (reverse) {
sCommandsTabCompletionIndex = (sCommandsTabCompletionIndex <= 0)
? foundCommandsCount - 1
: (sCommandsTabCompletionIndex - 1) % foundCommandsCount;
} else {
sCommandsTabCompletionIndex = (sCommandsTabCompletionIndex + 1) % foundCommandsCount;
}
s32 currentIndex = 0; s32 currentIndex = 0;
for (s32 i = 0; commands[i] != NULL; i++) { for (s32 i = 0; commands[i] != NULL; i++) {
@ -364,7 +465,7 @@ static void handle_tab_completion(void) {
if (spacePositionB != NULL) { if (spacePositionB != NULL) {
char* mainCommandB = get_main_command_from_input(sCommandsTabCompletionOriginalText); char* mainCommandB = get_main_command_from_input(sCommandsTabCompletionOriginalText);
if (mainCommandB) { if (mainCommandB) {
if (!complete_subcommand(mainCommandB + 1, spacePositionB + 1)) { if (!complete_subcommand(mainCommandB + 1, spacePositionB + 1, reverse)) {
reset_tab_completion_all(); reset_tab_completion_all();
} else { } else {
alreadyTabCompleted = true; alreadyTabCompleted = true;
@ -404,7 +505,7 @@ static void handle_tab_completion(void) {
if (sPlayersTabCompletionIndex == -1) { if (sPlayersTabCompletionIndex == -1) {
snprintf(sPlayersTabCompletionOriginalText, MAX_CHAT_MSG_LENGTH, "%s", wordInfo.word); snprintf(sPlayersTabCompletionOriginalText, MAX_CHAT_MSG_LENGTH, "%s", wordInfo.word);
} }
if (!complete_player_name(sPlayersTabCompletionOriginalText)) { if (!complete_player_name(sPlayersTabCompletionOriginalText, reverse)) {
reset_tab_completion_players(); reset_tab_completion_players();
} else { } else {
alreadyTabCompleted = true; alreadyTabCompleted = true;
@ -457,7 +558,7 @@ static bool djui_chat_box_input_on_key_down(UNUSED struct DjuiBase* base, int sc
gDjuiChatBox->scrollY -= pageAmount; gDjuiChatBox->scrollY -= pageAmount;
break; break;
case SCANCODE_TAB: case SCANCODE_TAB:
handle_tab_completion(); handle_tab_completion(gDjuiInputHeldShift);
return true; return true;
case SCANCODE_ENTER: case SCANCODE_ENTER:
reset_tab_completion_all(); reset_tab_completion_all();
@ -520,6 +621,19 @@ void djui_chat_box_toggle(void) {
gDjuiChatBox->chatFlow->base.y.value = gDjuiChatBox->chatContainer->base.elem.height - gDjuiChatBox->chatFlow->base.height.value; gDjuiChatBox->chatFlow->base.y.value = gDjuiChatBox->chatContainer->base.elem.height - gDjuiChatBox->chatFlow->base.height.value;
} }
void djui_chat_box_open_with_text(const char* text) {
if (gDjuiChatBox == NULL) { return; }
if (!gDjuiChatBoxFocus) {
sDjuiChatBoxClearText = false;
gDjuiChatBoxFocus = true;
djui_chat_box_set_focus_style();
}
if (gDjuiChatBox->chatInput != NULL && text != NULL) {
djui_inputbox_set_text(gDjuiChatBox->chatInput, (char*)text);
djui_inputbox_move_cursor_to_end(gDjuiChatBox->chatInput);
}
}
struct DjuiChatBox* djui_chat_box_create(void) { struct DjuiChatBox* djui_chat_box_create(void) {
if (gDjuiChatBox != NULL) { if (gDjuiChatBox != NULL) {
djui_base_destroy(&gDjuiChatBox->base); djui_base_destroy(&gDjuiChatBox->base);
@ -531,7 +645,7 @@ struct DjuiChatBox* djui_chat_box_create(void) {
djui_base_init(&gDjuiRoot->base, base, djui_chat_box_render, djui_chat_box_destroy); djui_base_init(&gDjuiRoot->base, base, djui_chat_box_render, djui_chat_box_destroy);
djui_base_set_size_type(base, DJUI_SVT_ABSOLUTE, DJUI_SVT_ABSOLUTE); djui_base_set_size_type(base, DJUI_SVT_ABSOLUTE, DJUI_SVT_ABSOLUTE);
djui_base_set_size(base, 600, 400); djui_base_set_size(base, configChatWidth, 400);
djui_base_set_alignment(base, DJUI_HALIGN_LEFT, DJUI_VALIGN_BOTTOM); djui_base_set_alignment(base, DJUI_HALIGN_LEFT, DJUI_VALIGN_BOTTOM);
djui_base_set_color(base, 0, 0, 0, 0); djui_base_set_color(base, 0, 0, 0, 0);
djui_base_set_padding(base, 0, 8, 8, 8); djui_base_set_padding(base, 0, 8, 8, 8);
@ -545,12 +659,12 @@ struct DjuiChatBox* djui_chat_box_create(void) {
struct DjuiFlowLayout* chatFlow = djui_flow_layout_create(ccBase); struct DjuiFlowLayout* chatFlow = djui_flow_layout_create(ccBase);
struct DjuiBase* cfBase = &chatFlow->base; struct DjuiBase* cfBase = &chatFlow->base;
djui_base_set_location(cfBase, 0, 0); djui_base_set_location(cfBase, 0, 8);
djui_base_set_size_type(cfBase, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE); djui_base_set_size_type(cfBase, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE);
djui_base_set_size(cfBase, 1.0f, 2); djui_base_set_size(cfBase, 1.0f, 2);
djui_base_set_color(cfBase, 0, 0, 0, 128); djui_base_set_color(cfBase, 0, 0, 0, 64);
djui_base_set_padding(cfBase, 2, 2, 2, 2); djui_base_set_padding(cfBase, 0, 2, 0, 2);
djui_flow_layout_set_margin(chatFlow, 2); djui_flow_layout_set_margin(chatFlow, 0);
djui_flow_layout_set_flow_direction(chatFlow, DJUI_FLOW_DIR_UP); djui_flow_layout_set_flow_direction(chatFlow, DJUI_FLOW_DIR_UP);
cfBase->addChildrenToHead = true; cfBase->addChildrenToHead = true;
cfBase->abandonAfterChildRenderFail = true; cfBase->abandonAfterChildRenderFail = true;
@ -561,6 +675,9 @@ struct DjuiChatBox* djui_chat_box_create(void) {
djui_base_set_size_type(ciBase, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE); djui_base_set_size_type(ciBase, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE);
djui_base_set_size(ciBase, 1.0f, 32); djui_base_set_size(ciBase, 1.0f, 32);
djui_base_set_alignment(ciBase, DJUI_HALIGN_LEFT, DJUI_VALIGN_BOTTOM); djui_base_set_alignment(ciBase, DJUI_HALIGN_LEFT, DJUI_VALIGN_BOTTOM);
djui_base_set_location(ciBase, 0, 0);
djui_base_set_border_width(ciBase, 0);
djui_interactable_hook_key(&chatInput->base, djui_chat_box_input_on_key_down, djui_inputbox_on_key_up); djui_interactable_hook_key(&chatInput->base, djui_chat_box_input_on_key_down, djui_inputbox_on_key_up);
djui_interactable_hook_text_input(&chatInput->base, djui_chat_box_input_on_text_input); djui_interactable_hook_text_input(&chatInput->base, djui_chat_box_input_on_text_input);
djui_interactable_hook_text_editing(&chatInput->base, djui_chat_box_input_on_text_editing); djui_interactable_hook_text_editing(&chatInput->base, djui_chat_box_input_on_text_editing);

View file

@ -14,4 +14,6 @@ extern struct DjuiChatBox* gDjuiChatBox;
extern bool gDjuiChatBoxFocus; extern bool gDjuiChatBoxFocus;
void djui_chat_box_toggle(void); void djui_chat_box_toggle(void);
void djui_chat_box_open_with_text(const char* text);
char* get_next_tab_completion_preview(const char* input);
struct DjuiChatBox* djui_chat_box_create(void); struct DjuiChatBox* djui_chat_box_create(void);

View file

@ -24,14 +24,16 @@ static bool djui_chat_message_render(struct DjuiBase* base) {
} }
if (gDjuiChatBoxFocus) { if (gDjuiChatBoxFocus) {
djui_base_set_color(base, 0, 0, 0, 120); djui_base_set_color(base, 0, 0, 0, 0);
djui_base_set_color(ctBase, 255, 255, 255, 255); djui_base_set_color(ctBase, 255, 255, 255, 255);
djui_base_set_size_type(base, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE); djui_base_set_size_type(base, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE);
djui_base_set_size(base, 1.0f, chatMessage->base.height.value); djui_base_set_size(base, 1.0f, chatMessage->base.height.value);
} else if (configDisableChatWhenClosed) {
return false;
} else if (f <= 0.1f) { } else if (f <= 0.1f) {
return false; return false;
} else { } else {
djui_base_set_color(base, 0, 0, 0, 180 * f); djui_base_set_color(base, 0, 0, 0, 140 * f);
djui_base_set_color(ctBase, 255, 255, 255, 255 * f); djui_base_set_color(ctBase, 255, 255, 255, 255 * f);
djui_base_set_size_type(base, DJUI_SVT_ABSOLUTE, DJUI_SVT_ABSOLUTE); djui_base_set_size_type(base, DJUI_SVT_ABSOLUTE, DJUI_SVT_ABSOLUTE);
djui_base_set_size(base, chatMessage->messageWidth, chatMessage->base.height.value); djui_base_set_size(base, chatMessage->messageWidth, chatMessage->base.height.value);
@ -76,8 +78,8 @@ void djui_chat_message_create(const char* message) {
djui_base_init(&gDjuiChatBox->chatFlow->base, base, djui_chat_message_render, djui_chat_message_destroy); djui_base_init(&gDjuiChatBox->chatFlow->base, base, djui_chat_message_render, djui_chat_message_destroy);
djui_base_set_size_type(base, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE); djui_base_set_size_type(base, DJUI_SVT_RELATIVE, DJUI_SVT_ABSOLUTE);
djui_base_set_size(base, 1.0f, 0); djui_base_set_size(base, 1.0f, 0);
djui_base_set_color(base, 0, 0, 0, 64); djui_base_set_color(base, 0, 0, 0, 0);
djui_base_set_padding(base, 2, 4, 2, 4); djui_base_set_padding(base, 0, 4, 0, 4);
djui_base_set_alignment(base, DJUI_HALIGN_LEFT, DJUI_VALIGN_BOTTOM); djui_base_set_alignment(base, DJUI_HALIGN_LEFT, DJUI_VALIGN_BOTTOM);
f32 maxTextWidth = gDjuiChatBox->base.width.value - gDjuiChatBox->base.padding.left.value - gDjuiChatBox->base.padding.right.value - base->padding.left.value - base->padding.right.value; f32 maxTextWidth = gDjuiChatBox->base.width.value - gDjuiChatBox->base.padding.left.value - gDjuiChatBox->base.padding.right.value - base->padding.left.value - base->padding.right.value;

View file

@ -33,7 +33,7 @@ static struct DjuiColor sRefColor = { 255, 255, 255, 255 };
static bool sLegacy = false; static bool sLegacy = false;
f32 gDjuiHudUtilsZ = 0; f32 gDjuiHudUtilsZ = 0;
u8 gDjuiHudLockMouse = false; bool gDjuiHudLockMouse = false;
extern ALIGNED8 const u8 texture_hud_char_camera[]; extern ALIGNED8 const u8 texture_hud_char_camera[];
extern ALIGNED8 const u8 texture_hud_char_lakitu[]; extern ALIGNED8 const u8 texture_hud_char_lakitu[];
@ -297,6 +297,10 @@ f32 djui_hud_get_raw_mouse_y(void) {
return mouse_y; return mouse_y;
} }
bool djui_hud_is_mouse_locked(void) {
return gDjuiHudLockMouse;
}
void djui_hud_set_mouse_locked(bool locked) { void djui_hud_set_mouse_locked(bool locked) {
gDjuiHudLockMouse = locked; gDjuiHudLockMouse = locked;
} }

View file

@ -52,7 +52,7 @@ struct GlobalTextures {
extern struct GlobalTextures gGlobalTextures; extern struct GlobalTextures gGlobalTextures;
extern f32 gDjuiHudUtilsZ; extern f32 gDjuiHudUtilsZ;
extern u8 gDjuiHudLockMouse; extern bool gDjuiHudLockMouse;
/* |description|Gets the current DJUI HUD resolution|descriptionEnd| */ /* |description|Gets the current DJUI HUD resolution|descriptionEnd| */
u8 djui_hud_get_resolution(void); u8 djui_hud_get_resolution(void);
@ -92,7 +92,9 @@ f32 djui_hud_get_mouse_y(void);
f32 djui_hud_get_raw_mouse_x(void); f32 djui_hud_get_raw_mouse_x(void);
/* |description|Returns the y coordinate of the mouse relative to the screen|descriptionEnd| */ /* |description|Returns the y coordinate of the mouse relative to the screen|descriptionEnd| */
f32 djui_hud_get_raw_mouse_y(void); f32 djui_hud_get_raw_mouse_y(void);
/* |description|Sets if the cursor is hidden and constrainted to the window|descriptionEnd| */ /* |description|Checks if the cursor is locked to the window|descriptionEnd| */
bool djui_hud_is_mouse_locked(void);
/* |description|Locks (or unlocks) the cursor to the window|descriptionEnd| */
void djui_hud_set_mouse_locked(bool locked); void djui_hud_set_mouse_locked(bool locked);
/* |description|Returns the flags of the mouse buttons held down|descriptionEnd| */ /* |description|Returns the flags of the mouse buttons held down|descriptionEnd| */
u8 djui_hud_get_mouse_buttons_down(void); u8 djui_hud_get_mouse_buttons_down(void);
@ -104,13 +106,13 @@ u8 djui_hud_get_mouse_buttons_released(void);
f32 djui_hud_get_mouse_scroll_x(void); f32 djui_hud_get_mouse_scroll_x(void);
/* |description|Returns the amount scrolled vertically (-down/up+)|descriptionEnd| */ /* |description|Returns the amount scrolled vertically (-down/up+)|descriptionEnd| */
f32 djui_hud_get_mouse_scroll_y(void); f32 djui_hud_get_mouse_scroll_y(void);
/* |description|Sets the viewport to the specified position and size, this will resize |descriptionEnd| */ /* |description|Sets the viewport to the specified position and size, this will resize any subsequent DJUI graphics|descriptionEnd| */
void djui_hud_set_viewport(f32 x, f32 y, f32 width, f32 height); void djui_hud_set_viewport(f32 x, f32 y, f32 width, f32 height);
/* |description|put the description here|descriptionEnd| */ /* |description|Resets the viewport to a fullscreen state|descriptionEnd| */
void djui_hud_reset_viewport(void); void djui_hud_reset_viewport(void);
/* |description|put the description here|descriptionEnd| */ /* |description|Sets the scissor rectangle to the specified position and size, this will cut off any subsequent DJUI graphics not within the rectangle|descriptionEnd| */
void djui_hud_set_scissor(f32 x, f32 y, f32 width, f32 height); void djui_hud_set_scissor(f32 x, f32 y, f32 width, f32 height);
/* |description|put the description here|descriptionEnd| */ /* |description|Resets the scissor rectangle to a fullscreen state|descriptionEnd| */
void djui_hud_reset_scissor(void); void djui_hud_reset_scissor(void);
/* |description|Measures the length of `message` in the current font|descriptionEnd| */ /* |description|Measures the length of `message` in the current font|descriptionEnd| */

View file

@ -3,12 +3,14 @@
#include "djui.h" #include "djui.h"
#include "djui_unicode.h" #include "djui_unicode.h"
#include "djui_hud_utils.h" #include "djui_hud_utils.h"
#include "djui_chat_box.h"
#include "pc/gfx/gfx_window_manager_api.h" #include "pc/gfx/gfx_window_manager_api.h"
#include "pc/pc_main.h" #include "pc/pc_main.h"
#include "game/segment2.h" #include "game/segment2.h"
#include "pc/controller/controller_keyboard.h" #include "pc/controller/controller_keyboard.h"
#include "pc/configfile.h"
#define DJUI_INPUTBOX_YOFF (-3) #define DJUI_INPUTBOX_YOFF (-2)
#define DJUI_INPUTBOX_MAX_BLINK 50 #define DJUI_INPUTBOX_MAX_BLINK 50
#define DJUI_INPUTBOX_MID_BLINK (DJUI_INPUTBOX_MAX_BLINK / 2) #define DJUI_INPUTBOX_MID_BLINK (DJUI_INPUTBOX_MAX_BLINK / 2)
#define DJUI_INPUTBOX_CURSOR_WIDTH (2.0f / 32.0f) #define DJUI_INPUTBOX_CURSOR_WIDTH (2.0f / 32.0f)
@ -20,6 +22,14 @@ static u8 sCursorBlink = 0;
static void djui_inputbox_update_style(struct DjuiBase* base) { static void djui_inputbox_update_style(struct DjuiBase* base) {
struct DjuiInputbox* inputbox = (struct DjuiInputbox*)base; struct DjuiInputbox* inputbox = (struct DjuiInputbox*)base;
if (gDjuiChatBox != NULL && &gDjuiChatBox->chatInput->base == base) {
djui_base_set_border_width(base, 0);
djui_base_set_border_color(base, 0, 0, 0, 0);
u8 alpha = gDjuiChatBoxFocus ? 200 : 150;
djui_base_set_color(&inputbox->base, 0, 0, 0, alpha);
return;
}
if (!inputbox->base.enabled) { if (!inputbox->base.enabled) {
djui_base_set_border_color(base, 90, 90, 90, 255); djui_base_set_border_color(base, 90, 90, 90, 255);
djui_base_set_color(&inputbox->base, 140, 140, 140, 255); djui_base_set_color(&inputbox->base, 140, 140, 140, 255);
@ -447,8 +457,63 @@ static void djui_inputbox_render_char(struct DjuiInputbox* inputbox, char* c, f3
*additionalShift += charWidth; *additionalShift += charWidth;
} }
static void djui_inputbox_render_preview_text(struct DjuiInputbox* inputbox) {
// Always show debug preview when focused (remove all conditions for testing)
if (!djui_interactable_is_input_focus(&inputbox->base)) {
return;
}
const struct DjuiFont* font = gDjuiFonts[configDjuiThemeFont == 0 ? FONT_NORMAL : FONT_ALIASED];
struct DjuiBaseRect* comp = &inputbox->base.comp;
// Calculate current text width
f32 currentTextWidth = 0;
char* c = inputbox->buffer;
while (*c != '\0') {
char* dc = inputbox->passwordChar[0] ? inputbox->passwordChar : c;
currentTextWidth += font->char_width(dc) * font->defaultFontScale;
c = djui_unicode_next_char(c);
}
// Calculate preview position - use absolute positioning
f32 previewX = comp->x + inputbox->viewX + currentTextWidth + 50; // Add 50px offset
f32 previewY = comp->y + DJUI_INPUTBOX_YOFF + 30; // Move down 30px
// Apply position translation
djui_gfx_position_translate(&previewX, &previewY);
// Create translation matrix for the preview text
create_dl_translation_matrix(DJUI_MTX_PUSH, previewX, previewY, 0);
f32 translatedFontSize = font->defaultFontScale;
djui_gfx_size_translate(&translatedFontSize);
create_dl_scale_matrix(DJUI_MTX_NOPUSH, translatedFontSize, translatedFontSize, 1.0f);
// Set bright red color for debug visibility
gDPSetEnvColor(gDisplayListHead++, 255, 0, 0, 255);
// Begin font rendering
if (font->textBeginDisplayList != NULL) {
gSPDisplayList(gDisplayListHead++, font->textBeginDisplayList);
}
// Render debug text
char testText[] = "DEBUG";
char* testChar = testText;
while (*testChar != '\0') {
font->render_char(testChar);
f32 charWidth = font->char_width(testChar);
previewX += charWidth * font->defaultFontScale;
testChar = djui_unicode_next_char(testChar);
}
// Clean up matrices
gSPPopMatrix(gDisplayListHead++, G_MTX_MODELVIEW);
gSPDisplayList(gDisplayListHead++, dl_ia_text_end);
}
static void djui_inputbox_render_selection(struct DjuiInputbox* inputbox) { static void djui_inputbox_render_selection(struct DjuiInputbox* inputbox) {
const struct DjuiFont* font = gDjuiFonts[configDjuiThemeFont == 0 ? FONT_NORMAL : FONT_ALIASED]; const struct DjuiFont* font = gDjuiFonts[configDjuiThemeFont == 0 ? FONT_NORMAL : FONT_ALIASED];
bool isChatInput = (gDjuiChatBox != NULL && &gDjuiChatBox->chatInput->base == &inputbox->base);
// make selection well formed // make selection well formed
u16 selection[2] = { 0 }; u16 selection[2] = { 0 };
@ -486,7 +551,11 @@ static void djui_inputbox_render_selection(struct DjuiInputbox* inputbox) {
if (sCursorBlink < DJUI_INPUTBOX_MID_BLINK && djui_interactable_is_input_focus(&inputbox->base)) { if (sCursorBlink < DJUI_INPUTBOX_MID_BLINK && djui_interactable_is_input_focus(&inputbox->base)) {
create_dl_translation_matrix(DJUI_MTX_PUSH, renderX - DJUI_INPUTBOX_CURSOR_WIDTH / 2.0f, -0.1f, 0); create_dl_translation_matrix(DJUI_MTX_PUSH, renderX - DJUI_INPUTBOX_CURSOR_WIDTH / 2.0f, -0.1f, 0);
create_dl_scale_matrix(DJUI_MTX_NOPUSH, DJUI_INPUTBOX_CURSOR_WIDTH, 0.8f, 1.0f); create_dl_scale_matrix(DJUI_MTX_NOPUSH, DJUI_INPUTBOX_CURSOR_WIDTH, 0.8f, 1.0f);
gDPSetEnvColor(gDisplayListHead++, 0, 0, 0, 255); if (isChatInput) {
gDPSetEnvColor(gDisplayListHead++, 255, 255, 255, 255);
} else {
gDPSetEnvColor(gDisplayListHead++, 0, 0, 0, 255);
}
gSPDisplayList(gDisplayListHead++, dl_djui_simple_rect); gSPDisplayList(gDisplayListHead++, dl_djui_simple_rect);
gSPPopMatrix(gDisplayListHead++, G_MTX_MODELVIEW); gSPPopMatrix(gDisplayListHead++, G_MTX_MODELVIEW);
} }
@ -550,9 +619,15 @@ static bool djui_inputbox_render(struct DjuiBase* base) {
const struct DjuiFont* font = gDjuiFonts[configDjuiThemeFont == 0 ? FONT_NORMAL : FONT_ALIASED]; const struct DjuiFont* font = gDjuiFonts[configDjuiThemeFont == 0 ? FONT_NORMAL : FONT_ALIASED];
djui_rect_render(base); djui_rect_render(base);
// Shift the text away from the left side a tad bool isChatInput = (gDjuiChatBox != NULL && &gDjuiChatBox->chatInput->base == base);
comp->x += 2; if (isChatInput) {
comp->width -= 2; comp->x += 6;
comp->y -= 1;
comp->width -= 6;
} else {
comp->x += 2;
comp->width -= 2;
}
// shift the viewing window to keep the selection in view // shift the viewing window to keep the selection in view
djui_inputbox_keep_selection_in_view(inputbox); djui_inputbox_keep_selection_in_view(inputbox);
@ -560,6 +635,12 @@ static bool djui_inputbox_render(struct DjuiBase* base) {
// translate position // translate position
f32 translatedX = comp->x + inputbox->viewX; f32 translatedX = comp->x + inputbox->viewX;
f32 translatedY = comp->y + DJUI_INPUTBOX_YOFF; f32 translatedY = comp->y + DJUI_INPUTBOX_YOFF;
if (isChatInput) {
f32 lineHeight = font->lineHeight * font->defaultFontScale;
f32 innerHeight = comp->height - base->borderWidth.value * 2;
f32 centerOffset = (innerHeight - lineHeight) * 0.5f;
translatedY += fmaxf(centerOffset, 0.0f);
}
djui_gfx_position_translate(&translatedX, &translatedY); djui_gfx_position_translate(&translatedX, &translatedY);
create_dl_translation_matrix(DJUI_MTX_PUSH, translatedX, translatedY, 0); create_dl_translation_matrix(DJUI_MTX_PUSH, translatedX, translatedY, 0);
@ -576,8 +657,14 @@ static bool djui_inputbox_render(struct DjuiBase* base) {
gSPDisplayList(gDisplayListHead++, font->textBeginDisplayList); gSPDisplayList(gDisplayListHead++, font->textBeginDisplayList);
} }
// set color // render preview text (for tab completion) - after font setup
gDPSetEnvColor(gDisplayListHead++, inputbox->textColor.r, inputbox->textColor.g, inputbox->textColor.b, inputbox->textColor.a); // djui_inputbox_render_preview_text(inputbox);
if (isChatInput) {
gDPSetEnvColor(gDisplayListHead++, 255, 255, 255, 255);
} else {
gDPSetEnvColor(gDisplayListHead++, inputbox->textColor.r, inputbox->textColor.g, inputbox->textColor.b, inputbox->textColor.a);
}
// make selection well formed // make selection well formed
u16 selection[2] = { 0 }; u16 selection[2] = { 0 };
@ -608,7 +695,11 @@ static bool djui_inputbox_render(struct DjuiBase* base) {
if (insideSelection && !wasInsideSelection) { if (insideSelection && !wasInsideSelection) {
gDPSetEnvColor(gDisplayListHead++, 255, 255, 255, 255); gDPSetEnvColor(gDisplayListHead++, 255, 255, 255, 255);
} else if (!insideSelection && wasInsideSelection) { } else if (!insideSelection && wasInsideSelection) {
gDPSetEnvColor(gDisplayListHead++, inputbox->textColor.r, inputbox->textColor.g, inputbox->textColor.b, inputbox->textColor.a); if (isChatInput) {
gDPSetEnvColor(gDisplayListHead++, 255, 255, 255, 255);
} else {
gDPSetEnvColor(gDisplayListHead++, inputbox->textColor.r, inputbox->textColor.g, inputbox->textColor.b, inputbox->textColor.a);
}
} }
wasInsideSelection = insideSelection; wasInsideSelection = insideSelection;
} }
@ -617,9 +708,101 @@ static bool djui_inputbox_render(struct DjuiBase* base) {
djui_inputbox_render_char(inputbox, c, &drawX, &additionalShift); djui_inputbox_render_char(inputbox, c, &drawX, &additionalShift);
c = djui_unicode_next_char(c); c = djui_unicode_next_char(c);
} }
// Tab completion preview - show what would happen if TAB was pressed
if (djui_interactable_is_input_focus(&inputbox->base) && inputbox->buffer[0] == '/') {
// Get preview text from tab completion function
extern char* get_next_tab_completion_preview(const char* input);
char* previewText = get_next_tab_completion_preview(inputbox->buffer);
if (previewText != NULL && strlen(previewText) > 0) {
// Set gray color for preview text
gDPSetEnvColor(gDisplayListHead++, 128, 128, 128, 128);
// Render preview text at the current position
char* previewChar = previewText;
while (*previewChar != '\0') {
djui_inputbox_render_char(inputbox, previewChar, &drawX, &additionalShift);
previewChar = djui_unicode_next_char(previewChar);
}
// Free the preview text
free(previewText);
// Reset color back to normal
gDPSetEnvColor(gDisplayListHead++, inputbox->textColor.r, inputbox->textColor.g, inputbox->textColor.b, inputbox->textColor.a);
}
}
gSPPopMatrix(gDisplayListHead++, G_MTX_MODELVIEW); gSPPopMatrix(gDisplayListHead++, G_MTX_MODELVIEW);
gSPDisplayList(gDisplayListHead++, dl_ia_text_end); gSPDisplayList(gDisplayListHead++, dl_ia_text_end);
if (isChatInput && djui_interactable_is_input_focus(&inputbox->base) && configChatCharCounter) {
char charCountText[32];
int currentLength = djui_unicode_len(inputbox->buffer);
snprintf(charCountText, sizeof(charCountText), "%d", currentLength);
f32 originalX = comp->x;
f32 originalY = comp->y;
f32 originalWidth = comp->width;
if (isChatInput) {
originalX -= 6;
originalY += 1;
originalWidth += 6;
} else {
originalX -= 2;
originalWidth += 2;
}
f32 counterX = originalX + originalWidth + 10 - 3;
f32 counterY = originalY + (comp->height - font->lineHeight * font->defaultFontScale) * 0.5f - 3;
djui_gfx_position_translate(&counterX, &counterY);
create_dl_translation_matrix(DJUI_MTX_PUSH, counterX, counterY, 0);
f32 translatedFontSize = font->defaultFontScale;
djui_gfx_size_translate(&translatedFontSize);
create_dl_scale_matrix(DJUI_MTX_NOPUSH, translatedFontSize, translatedFontSize, 1.0f);
u8 colR = 255, colG = 255, colB = 255;
if (currentLength >= 499) {
colG = 0; colB = 0;
} else if (currentLength >= 256) {
colG = 128; colB = 64;
} else if (currentLength >= 192) {
colG = 192; colB = 64;
} else if (currentLength >= 128) {
colG = 255; colB = 64;
}
gDPSetEnvColor(gDisplayListHead++, colR, colG, colB, 255);
if (font->textBeginDisplayList != NULL) {
gSPDisplayList(gDisplayListHead++, font->textBeginDisplayList);
}
char* c = charCountText;
while (*c != '\0') {
font->render_char(c);
f32 cw = font->char_width(c);
create_dl_translation_matrix(DJUI_MTX_NOPUSH, cw, 0, 0);
c = djui_unicode_next_char(c);
}
gSPDisplayList(gDisplayListHead++, dl_ia_text_end);
gSPPopMatrix(gDisplayListHead++, G_MTX_MODELVIEW);
}
if (isChatInput) {
comp->x -= 6;
comp->y += 1;
comp->width += 6;
} else {
comp->x -= 2;
comp->width += 2;
}
return true; return true;
} }

View file

@ -211,16 +211,23 @@ bool djui_interactable_on_key_down(int scancode) {
} }
} }
if (gDjuiChatBox != NULL && !gDjuiChatBoxFocus) { if (gDjuiChatBox != NULL) {
bool pressChat = false; bool pressChat = false;
bool pressChatCommand = false;
for (int i = 0; i < MAX_BINDS; i++) { for (int i = 0; i < MAX_BINDS; i++) {
if (scancode == (int)configKeyChat[i]) { pressChat = true; } if (scancode == (int)configKeyChat[i]) { pressChat = true; }
if (scancode == (int)configKeyChatCommand[i]) { pressChatCommand = true; }
} }
if (pressChat && !gDjuiConsoleFocus) { if (pressChat && !gDjuiConsoleFocus && !gDjuiChatBoxFocus) {
djui_chat_box_toggle(); djui_chat_box_toggle();
return true; return true;
} }
if (pressChatCommand && !gDjuiConsoleFocus) {
djui_chat_box_open_with_text("/");
return true;
}
} }
if ((gDjuiPlayerList != NULL || gDjuiModList != NULL)) { if ((gDjuiPlayerList != NULL || gDjuiModList != NULL)) {

View file

@ -42,6 +42,32 @@ void djui_panel_controls_create(struct DjuiBase* caller) {
#endif #endif
djui_checkbox_create(body, DLANG(MISC, USE_STANDARD_KEY_BINDINGS_CHAT), &configUseStandardKeyBindingsChat, NULL); djui_checkbox_create(body, DLANG(MISC, USE_STANDARD_KEY_BINDINGS_CHAT), &configUseStandardKeyBindingsChat, NULL);
djui_checkbox_create(body, DLANG(MISC, CHAT_CHAR_COUNTER), &configChatCharCounter, NULL);
djui_checkbox_create(body, DLANG(MISC, DISABLE_CHAT_WHEN_CLOSED), &configDisableChatWhenClosed, NULL);
static unsigned int sChatWidthIndex = 3;
switch (configChatWidth) {
case 500: sChatWidthIndex = 0; break;
case 600: sChatWidthIndex = 1; break;
case 700: sChatWidthIndex = 2; break;
case 800: sChatWidthIndex = 3; break;
case 900: sChatWidthIndex = 4; break;
case 1000: sChatWidthIndex = 5; break;
case 1100: sChatWidthIndex = 6; break;
default: sChatWidthIndex = 3; break;
}
char* chatWidthChoices[] = { DLANG(MISC, CHAT_WIDTH_TINY), DLANG(MISC, CHAT_WIDTH_VERY_SMALL), DLANG(MISC, CHAT_WIDTH_SMALL), DLANG(MISC, CHAT_WIDTH_NORMAL), DLANG(MISC, CHAT_WIDTH_BIG), DLANG(MISC, CHAT_WIDTH_VERY_BIG), DLANG(MISC, CHAT_WIDTH_HUGE) };
void on_chat_width_change(UNUSED struct DjuiBase* b) {
unsigned int idx = sChatWidthIndex;
unsigned int widths[] = {500,600,700,800,900,1000,1100};
configChatWidth = widths[idx];
if (gDjuiChatBox != NULL) {
djui_base_set_size(&gDjuiChatBox->base, configChatWidth, gDjuiChatBox->base.height.value);
}
}
djui_selectionbox_create(body, DLANG(MISC, CHAT_WIDTH), chatWidthChoices, 7, &sChatWidthIndex, on_chat_width_change);
#ifdef HAVE_SDL2 #ifdef HAVE_SDL2
int numJoys = SDL_NumJoysticks(); int numJoys = SDL_NumJoysticks();
if (numJoys == 0) { numJoys = 1; } if (numJoys == 0) { numJoys = 1; }

View file

@ -15,18 +15,19 @@ void djui_panel_controls_extra_create(struct DjuiBase* caller) {
djui_base_set_color(&bindBody->base, 0, 0, 0, 0); djui_base_set_color(&bindBody->base, 0, 0, 0, 0);
djui_flow_layout_set_margin(bindBody, 1); djui_flow_layout_set_margin(bindBody, 1);
{ {
djui_bind_create(&bindBody->base, DLANG(CONTROLS, CHAT), configKeyChat); djui_bind_create(&bindBody->base, DLANG(CONTROLS, CHAT), configKeyChat);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, PLAYERS), configKeyPlayerList); djui_bind_create(&bindBody->base, DLANG(CONTROLS, CHAT_COMMAND), configKeyChatCommand);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_UP), configKeyDUp); djui_bind_create(&bindBody->base, DLANG(CONTROLS, PLAYERS), configKeyPlayerList);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_DOWN), configKeyDDown); djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_UP), configKeyDUp);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_LEFT), configKeyDLeft); djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_DOWN), configKeyDDown);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_RIGHT), configKeyDRight); djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_LEFT), configKeyDLeft);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, X), configKeyX); djui_bind_create(&bindBody->base, DLANG(CONTROLS, D_RIGHT), configKeyDRight);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, Y), configKeyY); djui_bind_create(&bindBody->base, DLANG(CONTROLS, X), configKeyX);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, CONSOLE), configKeyConsole); djui_bind_create(&bindBody->base, DLANG(CONTROLS, Y), configKeyY);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, PREV), configKeyPrevPage); djui_bind_create(&bindBody->base, DLANG(CONTROLS, CONSOLE), configKeyConsole);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, NEXT), configKeyNextPage); djui_bind_create(&bindBody->base, DLANG(CONTROLS, PREV), configKeyPrevPage);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, DISCONNECT), configKeyDisconnect); djui_bind_create(&bindBody->base, DLANG(CONTROLS, NEXT), configKeyNextPage);
djui_bind_create(&bindBody->base, DLANG(CONTROLS, DISCONNECT), configKeyDisconnect);
} }
djui_button_create(body, DLANG(MENU, BACK), DJUI_BUTTON_STYLE_BACK, djui_panel_menu_back); djui_button_create(body, DLANG(MENU, BACK), DJUI_BUTTON_STYLE_BACK, djui_panel_menu_back);

View file

@ -12698,6 +12698,21 @@ int smlua_func_djui_hud_get_raw_mouse_y(UNUSED lua_State* L) {
return 1; return 1;
} }
int smlua_func_djui_hud_is_mouse_locked(UNUSED lua_State* L) {
if (L == NULL) { return 0; }
int top = lua_gettop(L);
if (top != 0) {
LOG_LUA_LINE("Improper param count for '%s': Expected %u, Received %u", "djui_hud_is_mouse_locked", 0, top);
return 0;
}
lua_pushboolean(L, djui_hud_is_mouse_locked());
return 1;
}
int smlua_func_djui_hud_set_mouse_locked(lua_State* L) { int smlua_func_djui_hud_set_mouse_locked(lua_State* L) {
if (L == NULL) { return 0; } if (L == NULL) { return 0; }
@ -37431,6 +37446,7 @@ void smlua_bind_functions_autogen(void) {
smlua_bind_function(L, "djui_hud_get_mouse_y", smlua_func_djui_hud_get_mouse_y); smlua_bind_function(L, "djui_hud_get_mouse_y", smlua_func_djui_hud_get_mouse_y);
smlua_bind_function(L, "djui_hud_get_raw_mouse_x", smlua_func_djui_hud_get_raw_mouse_x); smlua_bind_function(L, "djui_hud_get_raw_mouse_x", smlua_func_djui_hud_get_raw_mouse_x);
smlua_bind_function(L, "djui_hud_get_raw_mouse_y", smlua_func_djui_hud_get_raw_mouse_y); smlua_bind_function(L, "djui_hud_get_raw_mouse_y", smlua_func_djui_hud_get_raw_mouse_y);
smlua_bind_function(L, "djui_hud_is_mouse_locked", smlua_func_djui_hud_is_mouse_locked);
smlua_bind_function(L, "djui_hud_set_mouse_locked", smlua_func_djui_hud_set_mouse_locked); smlua_bind_function(L, "djui_hud_set_mouse_locked", smlua_func_djui_hud_set_mouse_locked);
smlua_bind_function(L, "djui_hud_get_mouse_buttons_down", smlua_func_djui_hud_get_mouse_buttons_down); smlua_bind_function(L, "djui_hud_get_mouse_buttons_down", smlua_func_djui_hud_get_mouse_buttons_down);
smlua_bind_function(L, "djui_hud_get_mouse_buttons_pressed", smlua_func_djui_hud_get_mouse_buttons_pressed); smlua_bind_function(L, "djui_hud_get_mouse_buttons_pressed", smlua_func_djui_hud_get_mouse_buttons_pressed);