Make djui_hud_measure_text compute text height (#1177)

- Change `djui_hud_measure_text` to return both text width and height
  - New syntax is: `local width, height = djui_hud_measure_text(text)`
  - Old syntax still works, but only returns `width`
- Fix incorrect char height for some fonts
- Fix nametags interpolation using the wrong scale
This commit is contained in:
PeachyPeach 2026-04-05 02:00:03 +02:00 committed by GitHub
parent 8afe062be1
commit de25c5437b
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 54 additions and 33 deletions

View file

@ -4033,8 +4033,9 @@ function djui_hud_reset_scissor()
end
--- @param message string
--- @return number
--- Measures the length of `message` in the current font
--- @return number width
--- @return number height
--- Measures the width and height of `message` in the current font
function djui_hud_measure_text(message)
-- ...
end

View file

@ -3511,10 +3511,10 @@ Resets the scissor rectangle to a fullscreen state
## [djui_hud_measure_text](#djui_hud_measure_text)
### Description
Measures the length of `message` in the current font
Measures the width and height of `message` in the current font
### Lua Example
`local numberValue = djui_hud_measure_text(message)`
`local width, height = djui_hud_measure_text(message)`
### Parameters
| Field | Type |
@ -3523,9 +3523,10 @@ Measures the length of `message` in the current font
### Returns
- `number`
- `number`
### C Prototype
`f32 djui_hud_measure_text(const char* message);`
`void djui_hud_measure_text(const char* message, RET f32 *width, RET f32 *height);`
[:arrow_up_small:](#)

View file

@ -79,7 +79,7 @@ static f32 djui_font_title_char_width(const char* text) {
static const struct DjuiFont sDjuiFontTitle = {
.charWidth = 1.0f,
.charHeight = 0.9f,
.charHeight = 0.95f,
.lineHeight = 0.7f,
.xOffset = 0.0f,
.yOffset = 0.0f,
@ -142,7 +142,7 @@ static f32 djui_font_hud_char_width(UNUSED const char* text) {
static const struct DjuiFont sDjuiFontHud = {
.charWidth = 1.0f,
.charHeight = 0.9f,
.charHeight = 1.0f,
.lineHeight = 1.25f,
.xOffset = 0.0f,
.yOffset = 0.0f,
@ -238,7 +238,7 @@ static f32 djui_font_custom_hud_char_width(const char* text) {
static const struct DjuiFont sDjuiFontCustomHud = {
.charWidth = 1.0f,
.charHeight = 0.9f,
.charHeight = 0.7f,
.lineHeight = 0.7f,
.xOffset = -0.25f,
.yOffset = -10.25f,
@ -252,7 +252,7 @@ static const struct DjuiFont sDjuiFontCustomHud = {
static const struct DjuiFont sDjuiFontCustomHudRecolor = {
.charWidth = 1.0f,
.charHeight = 0.9f,
.charHeight = 0.7f,
.lineHeight = 0.7f,
.xOffset = -0.25f,
.yOffset = -10.25f,

View file

@ -519,10 +519,14 @@ void djui_hud_reset_scissor(void) {
gDPSetScissor(gDisplayListHead++, G_SC_NON_INTERLACE, 0, BORDER_HEIGHT, SCREEN_WIDTH, SCREEN_HEIGHT - BORDER_HEIGHT);
}
f32 djui_hud_measure_text(const char* message) {
if (message == NULL) { return 0; }
void djui_hud_measure_text(const char* message, RET f32 *width, RET f32 *height) {
if (message == NULL) { return; }
const struct DjuiFont* font = djui_hud_get_text_font();
f32 width = 0, maxWidth = 0;
f32 maxWidth = 0.f;
*width = 0.f;
*height = font->charHeight;
char *c = (char *) message;
const char *end = message + strlen(message);
while (*c != '\0') {
@ -534,14 +538,15 @@ f32 djui_hud_measure_text(const char* message) {
// new line
if (*c == '\n') {
maxWidth = max(width, maxWidth);
width = 0;
maxWidth = max(*width, maxWidth);
*width = 0;
*height += font->lineHeight;
}
// tab: align to the next (4 x space width)
else if (*c == '\t') {
f32 tabWidth = 4 * font->char_width(" ") * (djui_hud_text_font_is_legacy() ? 0.5f : 1.0f);
width += tabWidth - fmodf(width, tabWidth);
*width += tabWidth - fmodf(*width, tabWidth);
}
// unprintable chars
@ -551,12 +556,14 @@ f32 djui_hud_measure_text(const char* message) {
// regular chars
else {
width += font->char_width(c) * (djui_hud_text_font_is_legacy() ? 0.5f : 1.0f);
*width += font->char_width(c) * (djui_hud_text_font_is_legacy() ? 0.5f : 1.0f);
}
c = djui_unicode_next_char(c);
}
return max(width, maxWidth) * font->defaultFontScale;
*width = max(*width, maxWidth) * font->defaultFontScale;
*height *= font->defaultFontScale * (djui_hud_text_font_is_legacy() ? 0.5f : 1.0f);
}
static Mtx *allocate_dl_translation_matrix() {

View file

@ -137,8 +137,8 @@ void djui_hud_set_scissor(f32 x, f32 y, f32 width, f32 height);
/* |description|Resets the scissor rectangle to a fullscreen state|descriptionEnd| */
void djui_hud_reset_scissor(void);
/* |description|Measures the length of `message` in the current font|descriptionEnd| */
f32 djui_hud_measure_text(const char* message);
/* |description|Measures the width and height of `message` in the current font|descriptionEnd| */
void djui_hud_measure_text(const char* message, RET f32 *width, RET f32 *height);
/* |description|Prints DJUI HUD text onto the screen|descriptionEnd| */
void djui_hud_print_text(const char* message, f32 x, f32 y, f32 scale);
/* |description|Prints interpolated DJUI HUD text onto the screen|descriptionEnd| */

View file

@ -12790,9 +12790,15 @@ int smlua_func_djui_hud_measure_text(lua_State* L) {
const char* message = smlua_to_string(L, 1);
if (!gSmLuaConvertSuccess) { LOG_LUA("Failed to convert parameter %u for function '%s'", 1, "djui_hud_measure_text"); return 0; }
lua_pushnumber(L, djui_hud_measure_text(message));
f32 width;
f32 height;
return 1;
djui_hud_measure_text(message, &width, &height);
lua_pushnumber(L, width);
lua_pushnumber(L, height);
return 2;
}
int smlua_func_djui_hud_print_text(lua_State* L) {

View file

@ -135,12 +135,7 @@ void nametags_render(void) {
struct MarioState *m = &gMarioStates[playerIndex];
struct NetworkPlayer *np = &gNetworkPlayers[playerIndex];
u8* color = network_get_player_text_color(m->playerIndex);
f32 measure = djui_hud_measure_text(nametag->name) * nametag->scale * 0.5f;
nametag->pos[1] -= 16 * nametag->scale;
u8 alpha = (playerIndex == 0 ? 255 : MIN(np->fadeOpacity << 3, 255)) * clamp(FADE_SCALE - nametag->scale, 0.f, 1.f);
// init interpolation
struct StateExtras* e = &sStateExtras[playerIndex];
if (!e->inited) {
vec3f_copy(e->prevPos, nametag->pos);
@ -158,20 +153,31 @@ void nametags_render(void) {
gSPViewport(gDisplayListHead++, viewport);
}
f32 width, height;
djui_hud_measure_text(nametag->name, &width, &height);
f32 currHalfWidth = width * nametag->scale * 0.5f;
f32 currHalfHeight = height * nametag->scale * 0.5f;
f32 currNametagPosY = nametag->pos[1] - currHalfHeight;
f32 prevHalfWidth = width * e->prevScale * 0.5f;
f32 prevHalfHeight = height * e->prevScale * 0.5f;
f32 prevNametagPosY = e->prevPos[1] - prevHalfHeight;
const u8 *color = network_get_player_text_color(m->playerIndex);
u8 alpha = (playerIndex == 0 ? 255 : MIN(np->fadeOpacity << 3, 255)) * clamp(FADE_SCALE - nametag->scale, 0.f, 1.f);
// render name
djui_hud_print_outlined_text_interpolated(nametag->name,
e->prevPos[0] - measure, e->prevPos[1], e->prevScale,
nametag->pos[0] - measure, nametag->pos[1], nametag->scale,
e->prevPos[0] - prevHalfWidth, prevNametagPosY, e->prevScale,
nametag->pos[0] - currHalfWidth, currNametagPosY, nametag->scale,
color[0], color[1], color[2], alpha, 0.25);
// render power meter
if (playerIndex != 0 && gNametagsSettings.showHealth) {
djui_hud_set_color(255, 255, 255, alpha);
f32 healthScale = 90 * nametag->scale;
f32 prevHealthScale = 90 * e->prevScale;
f32 currHealthSize = 90 * nametag->scale;
f32 prevHealthSize = 90 * e->prevScale;
hud_render_power_meter_interpolated(m->health,
e->prevPos[0] - (prevHealthScale * 0.5f), e->prevPos[1] - 72 * nametag->scale, prevHealthScale, prevHealthScale,
nametag->pos[0] - ( healthScale * 0.5f), nametag->pos[1] - 72 * nametag->scale, healthScale, healthScale
e->prevPos[0] - (prevHealthSize * 0.5f), prevNametagPosY - 72 * e->prevScale, prevHealthSize, prevHealthSize,
nametag->pos[0] - (currHealthSize * 0.5f), currNametagPosY - 72 * nametag->scale, currHealthSize, currHealthSize
);
}