mirror of
https://github.com/coah80/LegacyVulkEdition.git
synced 2026-07-19 06:58:07 +00:00
616 lines
25 KiB
C++
616 lines
25 KiB
C++
#define NK_INCLUDE_FIXED_TYPES
|
|
#define NK_INCLUDE_STANDARD_IO
|
|
#define NK_INCLUDE_STANDARD_VARARGS
|
|
#define NK_INCLUDE_DEFAULT_ALLOCATOR
|
|
#define NK_INCLUDE_VERTEX_BUFFER_OUTPUT
|
|
#define NK_INCLUDE_FONT_BAKING
|
|
#define NK_INCLUDE_DEFAULT_FONT
|
|
#include "nuklear.h"
|
|
|
|
#include "NkBrowseMenus.h"
|
|
#include "NkCommon.h"
|
|
#include "MenuScreens.h"
|
|
#include "NuklearBridge.h"
|
|
#include <cstring>
|
|
#include <cstdio>
|
|
|
|
namespace lve { namespace ui {
|
|
|
|
static const float BASE_W = 1280.0f;
|
|
static const float BASE_H = 720.0f;
|
|
|
|
static const float TITLE_Y_POS = 30.0f;
|
|
static const float TITLE_H_POS = 40.0f;
|
|
|
|
static const float BTN_X = 415.0f;
|
|
static const float BTN_W = 450.0f;
|
|
static const float BTN_H = 32.0f;
|
|
static const float BTN_Y_START = 80.0f;
|
|
static const float BTN_Y_STEP = 34.0f;
|
|
|
|
static const float TAB_Y = 80.0f;
|
|
static const float TAB_H = 36.0f;
|
|
static const float TAB_W = 200.0f;
|
|
static const float TAB_SPACING = 8.0f;
|
|
|
|
static const float SKIN_PREVIEW_Y = 180.0f;
|
|
static const float SKIN_PREVIEW_W = 200.0f;
|
|
static const float SKIN_PREVIEW_H = 300.0f;
|
|
|
|
static const float SKIN_NAME_Y = 500.0f;
|
|
static const float SKIN_NAME_H = 30.0f;
|
|
|
|
static const float HTP_IMAGE_X = 640.0f;
|
|
static const float HTP_IMAGE_Y = 140.0f;
|
|
static const float HTP_IMAGE_W = 580.0f;
|
|
static const float HTP_IMAGE_H = 400.0f;
|
|
|
|
static const float HTP_TEXT_X = 40.0f;
|
|
static const float HTP_TEXT_Y = 140.0f;
|
|
static const float HTP_TEXT_W = 560.0f;
|
|
|
|
static const float SHADOW_OFF = 2.0f;
|
|
|
|
static MenuTextureSlot loadBrowseSlot(const char *path)
|
|
{
|
|
int w = 0, h = 0;
|
|
struct nk_image img = loadTextureWithSize(path, &w, &h);
|
|
return {img.handle.id, w, h};
|
|
}
|
|
|
|
static void drawShadowedText(nk_context *ctx, const char *text,
|
|
float x, float y, float w, float h,
|
|
struct nk_color color, bool centered)
|
|
{
|
|
struct nk_command_buffer *canvas = nk_window_get_canvas(ctx);
|
|
if (canvas == nullptr) return;
|
|
|
|
const struct nk_user_font *font = ctx->style.font;
|
|
if (font == nullptr) return;
|
|
|
|
int len = (int)strlen(text);
|
|
float textW = font->width(font->userdata, font->height, text, len);
|
|
float textX = centered ? x + (w - textW) * 0.5f : x;
|
|
float textY = y + (h - font->height) * 0.5f;
|
|
|
|
nk_draw_text(canvas, nk_rect(textX + SHADOW_OFF, textY + SHADOW_OFF, textW, font->height),
|
|
text, len, font,
|
|
nk_rgba(0, 0, 0, 0), nk_rgba(0x0F, 0x0F, 0x0F, 200));
|
|
nk_draw_text(canvas, nk_rect(textX, textY, textW, font->height),
|
|
text, len, font,
|
|
nk_rgba(0, 0, 0, 0), color);
|
|
}
|
|
|
|
static void drawShadowedTitle(nk_context *ctx, const char *title, int winW, int winH)
|
|
{
|
|
struct nk_command_buffer *canvas = nk_window_get_canvas(ctx);
|
|
if (canvas == nullptr) return;
|
|
|
|
nk_font *titleNkFont = getTitleFont();
|
|
const struct nk_user_font *font = titleNkFont ? &titleNkFont->handle : ctx->style.font;
|
|
if (font == nullptr) return;
|
|
|
|
float scaleY = (float)winH / BASE_H;
|
|
float y = TITLE_Y_POS * scaleY;
|
|
float h = TITLE_H_POS * scaleY;
|
|
|
|
int len = (int)strlen(title);
|
|
float textW = font->width(font->userdata, font->height, title, len);
|
|
float textX = ((float)winW - textW) * 0.5f;
|
|
float textY = y + (h - font->height) * 0.5f;
|
|
|
|
nk_draw_text(canvas, nk_rect(textX + SHADOW_OFF, textY + SHADOW_OFF, textW, font->height),
|
|
title, len, font,
|
|
nk_rgba(0, 0, 0, 0), nk_rgba(0x0F, 0x0F, 0x0F, 200));
|
|
nk_draw_text(canvas, nk_rect(textX, textY, textW, font->height),
|
|
title, len, font,
|
|
nk_rgba(0, 0, 0, 0), nk_rgb(255, 255, 255));
|
|
}
|
|
|
|
static bool drawTabButton(nk_context *ctx, const char *label,
|
|
float x, float y, float w, float h,
|
|
bool selected, BrowseMenuTextures &btex)
|
|
{
|
|
struct nk_command_buffer *canvas = nk_window_get_canvas(ctx);
|
|
if (canvas == nullptr) return false;
|
|
|
|
struct nk_rect r = nk_rect(x, y, w, h);
|
|
|
|
const struct nk_input *input = &ctx->input;
|
|
bool hovering = nk_input_is_mouse_hovering_rect(input, r) != 0;
|
|
|
|
if (btex.loaded) {
|
|
const MenuTextureSlot *slot;
|
|
if (selected) {
|
|
slot = hovering ? &btex.tabOverSelected : &btex.tabNormalSelected;
|
|
} else {
|
|
slot = hovering ? &btex.tabOver : &btex.tabNormal;
|
|
}
|
|
struct nk_image img = slotToNkImage(*slot);
|
|
nk_draw_image(canvas, r, &img, nk_rgb(255, 255, 255));
|
|
} else {
|
|
struct nk_color bg = selected ? nk_rgb(60, 60, 80) : nk_rgb(40, 40, 40);
|
|
if (hovering) bg = nk_rgb(80, 80, 100);
|
|
nk_fill_rect(canvas, r, 0, bg);
|
|
nk_stroke_rect(canvas, r, 0, 1.0f, nk_rgb(100, 100, 100));
|
|
}
|
|
|
|
drawShadowedText(ctx, label, x, y, w, h, nk_rgb(255, 255, 255), true);
|
|
|
|
bool clicked = hovering && nk_input_is_mouse_released(input, NK_BUTTON_LEFT) != 0;
|
|
return clicked;
|
|
}
|
|
|
|
static bool drawListRow(nk_context *ctx, const char *label,
|
|
float x, float y, float w, float h,
|
|
bool selected, bool hasTick,
|
|
BrowseMenuTextures &btex)
|
|
{
|
|
struct nk_command_buffer *canvas = nk_window_get_canvas(ctx);
|
|
if (canvas == nullptr) return false;
|
|
|
|
struct nk_rect r = nk_rect(x, y, w, h);
|
|
|
|
const struct nk_input *input = &ctx->input;
|
|
bool hovering = nk_input_is_mouse_hovering_rect(input, r) != 0;
|
|
|
|
if (btex.loaded) {
|
|
const MenuTextureSlot *slot;
|
|
if (selected || hovering)
|
|
slot = &btex.listBtnOver;
|
|
else
|
|
slot = &btex.listBtnNorm;
|
|
struct nk_image img = slotToNkImage(*slot);
|
|
nk_draw_image(canvas, r, &img, nk_rgb(255, 255, 255));
|
|
} else {
|
|
struct nk_color bg = (selected || hovering) ? nk_rgb(70, 70, 70) : nk_rgb(40, 40, 40);
|
|
nk_fill_rect(canvas, r, 0, bg);
|
|
nk_stroke_rect(canvas, r, 0, 1.0f, nk_rgb(80, 80, 80));
|
|
}
|
|
|
|
if (hasTick && btex.loaded) {
|
|
float tickS = h * 0.6f;
|
|
float tickX = x + w - tickS - 4.0f;
|
|
float tickY = y + (h - tickS) * 0.5f;
|
|
struct nk_image tickImg = slotToNkImage(btex.dlcTickSmall);
|
|
nk_draw_image(canvas, nk_rect(tickX, tickY, tickS, tickS),
|
|
&tickImg, nk_rgb(255, 255, 255));
|
|
}
|
|
|
|
drawShadowedText(ctx, label, x + 8.0f, y, w - 16.0f, h, nk_rgb(255, 255, 255), false);
|
|
|
|
bool clicked = hovering && nk_input_is_mouse_released(input, NK_BUTTON_LEFT) != 0;
|
|
return clicked;
|
|
}
|
|
|
|
bool initBrowseMenuTextures(BrowseMenuTextures &out)
|
|
{
|
|
out.tabNormal = loadBrowseSlot("../Assets/ui/skinHDGraphics/95_SkinSelect_TabNormal.png");
|
|
out.tabNormalSelected = loadBrowseSlot("../Assets/ui/skinHDGraphics/96_SkinSelect_TabNormal_Selected.png");
|
|
out.tabOver = loadBrowseSlot("../Assets/ui/skinHDGraphics/93_SkinSelect_TabOver.png");
|
|
out.tabOverSelected = loadBrowseSlot("../Assets/ui/skinHDGraphics/94_SkinSelect_TabOver_Selected.png");
|
|
out.tabBar = loadBrowseSlot("../Assets/ui/skinHDGraphics/97_SkinSelect_TabBar.png");
|
|
out.tabBarSelected = loadBrowseSlot("../Assets/ui/skinHDGraphics/98_SkinSelect_TabBar_Selected.png");
|
|
out.charBg = loadBrowseSlot("../Assets/ui/skinHDGraphics/83_CharacterBackground.png");
|
|
out.charBgSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/84_CharacterBackground_Small.png");
|
|
out.skinBottomBar = loadBrowseSlot("../Assets/ui/skinHDGraphics/79_SkinSelect_BottomBar.png");
|
|
out.skinBottomBarSelected = loadBrowseSlot("../Assets/ui/skinHDGraphics/80_SkinSelect_BottomBar_Selected.png");
|
|
out.padlock = loadBrowseSlot("../Assets/ui/skinHDGraphics/162_Padlock_Small.png");
|
|
out.listBtnNorm = loadBrowseSlot("../Assets/ui/skinHDGraphics/185_ListButton_Norm.png");
|
|
out.listBtnOver = loadBrowseSlot("../Assets/ui/skinHDGraphics/183_ListButton_Over.png");
|
|
out.listBtnOutline = loadBrowseSlot("../Assets/ui/skinHDGraphics/184_ListButton_Outline.png");
|
|
out.leaderboardBtnNorm = loadBrowseSlot("../Assets/ui/skinHDGraphics/173_LeaderboardButton_Norm.png");
|
|
out.leaderboardBtnOver = loadBrowseSlot("../Assets/ui/skinHDGraphics/172_LeaderboardButton_Over.png");
|
|
out.dlcBg = loadBrowseSlot("../Assets/ui/skinHDGraphics/165_DLCBackground.png");
|
|
out.dlcTick = loadBrowseSlot("../Assets/ui/skinHDGraphics/175_DLC_Tick.png");
|
|
out.dlcTickSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/174_DLC_TickSmall.png");
|
|
out.smallTick = loadBrowseSlot("../Assets/ui/skinHDGraphics/107_SmallTick.png");
|
|
|
|
out.lbIconWalkedSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/110_LeaderBoard_Icon_Walked_Small.png");
|
|
out.lbIconFallenSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/118_LeaderBoard_Icon_Fallen_Small.png");
|
|
out.lbIconCreeperSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/119_LeaderBoard_Icon_Creeper_Small.png");
|
|
out.lbIconZombieSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/109_LeaderBoard_Icon_Zombie_Small.png");
|
|
out.lbIconSkeletonSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/115_LeaderBoard_Icon_Skeleton_Small.png");
|
|
out.lbIconSpiderSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/113_LeaderBoard_Icon_Spider_Small.png");
|
|
out.lbIconSlimeSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/114_LeaderBoard_Icon_Slime_Small.png");
|
|
out.lbIconSpiderJockeySmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/112_LeaderBoard_Icon_SpiderJockey_Small.png");
|
|
out.lbIconZombiePigmanSmall = loadBrowseSlot("../Assets/ui/skinHDGraphics/108_LeaderBoard_Icon_ZombiePigman_Small.png");
|
|
|
|
out.lbIconWalked = loadBrowseSlot("../Assets/ui/skinHDGraphics/152_LeaderBoard_Icon_Walked.png");
|
|
out.lbIconFallen = loadBrowseSlot("../Assets/ui/skinHDGraphics/147_LeaderBoard_Icon_Fallen.png");
|
|
out.lbIconCreeper = loadBrowseSlot("../Assets/ui/skinHDGraphics/148_LeaderBoard_Icon_Creeper.png");
|
|
out.lbIconZombie = loadBrowseSlot("../Assets/ui/skinHDGraphics/151_LeaderBoard_Icon_Zombie.png");
|
|
out.lbIconSkeleton = loadBrowseSlot("../Assets/ui/skinHDGraphics/157_LeaderBoard_Icon_Skeleton.png");
|
|
out.lbIconSpider = loadBrowseSlot("../Assets/ui/skinHDGraphics/155_LeaderBoard_Icon_Spider.png");
|
|
out.lbIconSlime = loadBrowseSlot("../Assets/ui/skinHDGraphics/156_LeaderBoard_Icon_Slime.png");
|
|
out.lbIconSpiderJockey = loadBrowseSlot("../Assets/ui/skinHDGraphics/154_LeaderBoard_Icon_SpiderJockey.png");
|
|
out.lbIconZombiePigman = loadBrowseSlot("../Assets/ui/skinHDGraphics/150_LeaderBoard_Icon_ZombiePigman.png");
|
|
|
|
out.htpTrading = loadBrowseSlot("../Assets/ui/skinHDGraphics/223_HowToPlay_Trading.png");
|
|
out.htpEnderchest = loadBrowseSlot("../Assets/ui/skinHDGraphics/224_HowToPlay_Enderchest.png");
|
|
out.htpAnvil = loadBrowseSlot("../Assets/ui/skinHDGraphics/225_HowToPlay_Anvil.png");
|
|
out.htpTheEnd = loadBrowseSlot("../Assets/ui/skinHDGraphics/226_HowToPlay_TheEnd.png");
|
|
out.htpNetherPortal = loadBrowseSlot("../Assets/ui/skinHDGraphics/227_HowToPlay_NetherPortal.png");
|
|
out.htpLargeChest = loadBrowseSlot("../Assets/ui/skinHDGraphics/228_HowToPlay_LargeChest.png");
|
|
out.htpInventory = loadBrowseSlot("../Assets/ui/skinHDGraphics/229_HowToPlay_Inventory.png");
|
|
out.htpHUD = loadBrowseSlot("../Assets/ui/skinHDGraphics/230_HowToPlay_HUD.png");
|
|
out.htpFurnace = loadBrowseSlot("../Assets/ui/skinHDGraphics/231_HowToPlay_Furnace.png");
|
|
out.htpFarmingAnimals = loadBrowseSlot("../Assets/ui/skinHDGraphics/232_HowToPlay_FarmingAnimals.png");
|
|
out.htpEnchantment = loadBrowseSlot("../Assets/ui/skinHDGraphics/233_HowToPlay_Enchantment.png");
|
|
out.htpDispenser = loadBrowseSlot("../Assets/ui/skinHDGraphics/234_HowToPlay_Dispenser.png");
|
|
out.htpCreative = loadBrowseSlot("../Assets/ui/skinHDGraphics/235_HowToPlay_Creative.png");
|
|
out.htpCraftTable = loadBrowseSlot("../Assets/ui/skinHDGraphics/236_HowToPlay_CraftTable.png");
|
|
out.htpCrafting = loadBrowseSlot("../Assets/ui/skinHDGraphics/237_HowToPlay_Crafting.png");
|
|
out.htpChest = loadBrowseSlot("../Assets/ui/skinHDGraphics/238_HowToPlay_Chest.png");
|
|
out.htpBrewing = loadBrowseSlot("../Assets/ui/skinHDGraphics/239_HowToPlay_Brewing.png");
|
|
out.htpBreeding = loadBrowseSlot("../Assets/ui/skinHDGraphics/240_HowToPlay_Breeding.png");
|
|
|
|
out.loaded = true;
|
|
return true;
|
|
}
|
|
|
|
static const int SKIN_PACK_DEFAULT = 0;
|
|
static const int SKIN_PACK_FAVORITES = 1;
|
|
|
|
static const char *DEFAULT_SKIN_NAMES[] = {
|
|
"Server Selected",
|
|
"Steve",
|
|
"Tennis Steve",
|
|
"Tuxedo Steve",
|
|
"Athlete Steve",
|
|
"Scottish Steve",
|
|
"Prisoner Steve",
|
|
"Cyclist Steve",
|
|
"Boxer Steve"
|
|
};
|
|
static const int DEFAULT_SKIN_COUNT = 9;
|
|
|
|
void renderSkinSelectMenu(nk_context *ctx, int winW, int winH,
|
|
MenuTextures &tex, BrowseMenuTextures &btex)
|
|
{
|
|
static int packIndex = SKIN_PACK_DEFAULT;
|
|
static int skinIndex = 0;
|
|
static bool skinSelected = false;
|
|
|
|
float scaleX = (float)winW / BASE_W;
|
|
float scaleY = (float)winH / BASE_H;
|
|
|
|
pushCleanStyle(ctx);
|
|
|
|
if (nk_begin(ctx, "SkinSelectMenu", nk_rect(0, 0, (float)winW, (float)winH),
|
|
NK_WINDOW_NO_SCROLLBAR | NK_WINDOW_NO_INPUT | NK_WINDOW_BACKGROUND)) {
|
|
|
|
drawPanoramaBg(ctx, winW, winH, tex);
|
|
drawShadowedTitle(ctx, "Change Skin", winW, winH);
|
|
|
|
struct nk_command_buffer *canvas = nk_window_get_canvas(ctx);
|
|
const struct nk_input *input = &ctx->input;
|
|
|
|
float tabW = TAB_W * scaleX;
|
|
float tabH = TAB_H * scaleY;
|
|
float tabY = TAB_Y * scaleY;
|
|
|
|
const char *packLabels[] = { "Default", "Favorites" };
|
|
int packCount = 2;
|
|
|
|
float totalTabW = (float)packCount * tabW + (float)(packCount - 1) * TAB_SPACING * scaleX;
|
|
float tabStartX = ((float)winW - totalTabW) * 0.5f;
|
|
|
|
for (int i = 0; i < packCount; i++) {
|
|
float tx = tabStartX + (float)i * (tabW + TAB_SPACING * scaleX);
|
|
bool selected = (packIndex == i);
|
|
if (drawTabButton(ctx, packLabels[i], tx, tabY, tabW, tabH, selected, btex)) {
|
|
packIndex = i;
|
|
skinIndex = 0;
|
|
skinSelected = false;
|
|
}
|
|
}
|
|
|
|
if (btex.loaded && canvas != nullptr) {
|
|
float barY = tabY + tabH;
|
|
float barH = 4.0f * scaleY;
|
|
struct nk_image barImg = (packIndex == SKIN_PACK_DEFAULT)
|
|
? slotToNkImage(btex.tabBar) : slotToNkImage(btex.tabBarSelected);
|
|
nk_draw_image(canvas, nk_rect(tabStartX, barY, totalTabW, barH),
|
|
&barImg, nk_rgb(255, 255, 255));
|
|
}
|
|
|
|
float previewW = SKIN_PREVIEW_W * scaleX;
|
|
float previewH = SKIN_PREVIEW_H * scaleY;
|
|
float previewX = ((float)winW - previewW) * 0.5f;
|
|
float previewY = SKIN_PREVIEW_Y * scaleY;
|
|
|
|
if (canvas != nullptr && btex.loaded) {
|
|
struct nk_image charBgImg = slotToNkImage(btex.charBg);
|
|
nk_draw_image(canvas, nk_rect(previewX, previewY, previewW, previewH),
|
|
&charBgImg, nk_rgb(255, 255, 255));
|
|
} else if (canvas != nullptr) {
|
|
nk_fill_rect(canvas, nk_rect(previewX, previewY, previewW, previewH),
|
|
0, nk_rgba(0, 0, 0, 120));
|
|
}
|
|
|
|
int maxSkin = DEFAULT_SKIN_COUNT;
|
|
if (packIndex == SKIN_PACK_FAVORITES) maxSkin = 0;
|
|
|
|
if (skinIndex >= maxSkin && maxSkin > 0) skinIndex = 0;
|
|
if (skinIndex < 0) skinIndex = maxSkin - 1;
|
|
|
|
float nameY = SKIN_NAME_Y * scaleY;
|
|
float nameH = SKIN_NAME_H * scaleY;
|
|
float nameW = 400.0f * scaleX;
|
|
float nameX = ((float)winW - nameW) * 0.5f;
|
|
|
|
if (canvas != nullptr && btex.loaded) {
|
|
const MenuTextureSlot *barSlot = skinSelected
|
|
? &btex.skinBottomBarSelected : &btex.skinBottomBar;
|
|
struct nk_image skinBarImg = slotToNkImage(*barSlot);
|
|
nk_draw_image(canvas, nk_rect(nameX, nameY, nameW, nameH),
|
|
&skinBarImg, nk_rgb(255, 255, 255));
|
|
}
|
|
|
|
if (packIndex == SKIN_PACK_DEFAULT && maxSkin > 0) {
|
|
drawShadowedText(ctx, DEFAULT_SKIN_NAMES[skinIndex],
|
|
nameX, nameY, nameW, nameH, nk_rgb(255, 255, 255), true);
|
|
} else if (packIndex == SKIN_PACK_FAVORITES) {
|
|
drawShadowedText(ctx, "No Favorites",
|
|
nameX, nameY, nameW, nameH, nk_rgb(180, 180, 180), true);
|
|
}
|
|
|
|
if (skinSelected && canvas != nullptr) {
|
|
float selLabelY = nameY + nameH + 2.0f * scaleY;
|
|
drawShadowedText(ctx, "Selected", 0, selLabelY, (float)winW, 20.0f * scaleY,
|
|
nk_rgb(100, 255, 100), true);
|
|
}
|
|
|
|
float arrowW = 60.0f * scaleX;
|
|
float arrowH = 40.0f * scaleY;
|
|
float arrowY = previewY + (previewH - arrowH) * 0.5f;
|
|
float arrowLeftX = previewX - arrowW - 10.0f * scaleX;
|
|
float arrowRightX = previewX + previewW + 10.0f * scaleX;
|
|
|
|
if (maxSkin > 1) {
|
|
struct nk_rect leftRect = nk_rect(arrowLeftX, arrowY, arrowW, arrowH);
|
|
struct nk_rect rightRect = nk_rect(arrowRightX, arrowY, arrowW, arrowH);
|
|
|
|
bool leftHover = nk_input_is_mouse_hovering_rect(input, leftRect) != 0;
|
|
bool rightHover = nk_input_is_mouse_hovering_rect(input, rightRect) != 0;
|
|
|
|
if (drawBtn(ctx, "<", arrowLeftX, arrowY, arrowW, arrowH, leftHover, winH, tex)) {
|
|
skinIndex--;
|
|
if (skinIndex < 0) skinIndex = maxSkin - 1;
|
|
skinSelected = false;
|
|
}
|
|
if (drawBtn(ctx, ">", arrowRightX, arrowY, arrowW, arrowH, rightHover, winH, tex)) {
|
|
skinIndex++;
|
|
if (skinIndex >= maxSkin) skinIndex = 0;
|
|
skinSelected = false;
|
|
}
|
|
}
|
|
|
|
float selectBtnW = 200.0f * scaleX;
|
|
float selectBtnH = BTN_H * scaleY;
|
|
float selectBtnX = ((float)winW - selectBtnW) * 0.5f;
|
|
float selectBtnY = 560.0f * scaleY;
|
|
|
|
if (maxSkin > 0) {
|
|
struct nk_rect selRect = nk_rect(selectBtnX, selectBtnY, selectBtnW, selectBtnH);
|
|
bool selHover = nk_input_is_mouse_hovering_rect(input, selRect) != 0;
|
|
if (drawBtn(ctx, "Select", selectBtnX, selectBtnY, selectBtnW, selectBtnH, selHover, winH, tex)) {
|
|
skinSelected = true;
|
|
}
|
|
}
|
|
|
|
drawControllerPrompts(ctx, winW, winH, tex);
|
|
}
|
|
nk_end(ctx);
|
|
|
|
popCleanStyle(ctx);
|
|
}
|
|
|
|
static const int HTP_TOPIC_COUNT = 19;
|
|
static const char *HTP_TOPIC_LABELS[HTP_TOPIC_COUNT] = {
|
|
"What's New",
|
|
"Basics",
|
|
"Multiplayer",
|
|
"HUD",
|
|
"Creative Mode",
|
|
"Inventory",
|
|
"Chests",
|
|
"Crafting",
|
|
"Furnace",
|
|
"Dispenser",
|
|
"Brewing",
|
|
"Enchantment",
|
|
"Anvil",
|
|
"Farming Animals",
|
|
"Breeding Animals",
|
|
"Trading",
|
|
"Nether Portal",
|
|
"The End",
|
|
"Host Options"
|
|
};
|
|
|
|
void renderHowToPlayMenu(nk_context *ctx, int winW, int winH,
|
|
MenuTextures &tex, BrowseMenuTextures &btex)
|
|
{
|
|
static int selectedItem = -1;
|
|
static int scrollOffset = 0;
|
|
|
|
float scaleX = (float)winW / BASE_W;
|
|
float scaleY = (float)winH / BASE_H;
|
|
|
|
pushCleanStyle(ctx);
|
|
|
|
if (nk_begin(ctx, "HowToPlayMenu", nk_rect(0, 0, (float)winW, (float)winH),
|
|
NK_WINDOW_NO_SCROLLBAR | NK_WINDOW_NO_INPUT | NK_WINDOW_BACKGROUND)) {
|
|
|
|
drawPanoramaBg(ctx, winW, winH, tex);
|
|
drawShadowedTitle(ctx, "How to Play", winW, winH);
|
|
|
|
float listX = BTN_X * scaleX;
|
|
float listW = BTN_W * scaleX;
|
|
float rowH = BTN_H * scaleY;
|
|
float startY = BTN_Y_START * scaleY;
|
|
float step = BTN_Y_STEP * scaleY;
|
|
float bottomMargin = 50.0f * scaleY;
|
|
|
|
int visibleCount = (int)(((float)winH - bottomMargin - startY) / step);
|
|
if (visibleCount > HTP_TOPIC_COUNT) visibleCount = HTP_TOPIC_COUNT;
|
|
|
|
int maxScroll = HTP_TOPIC_COUNT - visibleCount;
|
|
if (maxScroll < 0) maxScroll = 0;
|
|
if (scrollOffset > maxScroll) scrollOffset = maxScroll;
|
|
if (scrollOffset < 0) scrollOffset = 0;
|
|
|
|
const struct nk_input *input = &ctx->input;
|
|
|
|
struct nk_rect listArea = nk_rect(listX, startY, listW,
|
|
(float)visibleCount * step);
|
|
if (nk_input_is_mouse_hovering_rect(input, listArea)) {
|
|
if (ctx->input.mouse.scroll_delta.y < 0.0f && scrollOffset < maxScroll)
|
|
scrollOffset++;
|
|
else if (ctx->input.mouse.scroll_delta.y > 0.0f && scrollOffset > 0)
|
|
scrollOffset--;
|
|
}
|
|
|
|
for (int i = 0; i < visibleCount; i++) {
|
|
int idx = i + scrollOffset;
|
|
if (idx >= HTP_TOPIC_COUNT) break;
|
|
|
|
float btnY = startY + (float)i * step;
|
|
|
|
struct nk_rect btnRect = nk_rect(listX, btnY, listW, rowH);
|
|
bool hovering = nk_input_is_mouse_hovering_rect(input, btnRect) != 0;
|
|
|
|
if (drawBtn(ctx, HTP_TOPIC_LABELS[idx], listX, btnY, listW, rowH, hovering, winH, tex)) {
|
|
selectedItem = idx;
|
|
}
|
|
}
|
|
|
|
if (scrollOffset > 0) {
|
|
float arrowY = startY - 16.0f * scaleY;
|
|
drawShadowedText(ctx, "^", listX, arrowY, listW, 14.0f * scaleY,
|
|
nk_rgb(200, 200, 200), true);
|
|
}
|
|
if (scrollOffset < maxScroll) {
|
|
float arrowY = startY + (float)visibleCount * step + 2.0f * scaleY;
|
|
drawShadowedText(ctx, "v", listX, arrowY, listW, 14.0f * scaleY,
|
|
nk_rgb(200, 200, 200), true);
|
|
}
|
|
|
|
drawControllerPrompts(ctx, winW, winH, tex);
|
|
}
|
|
nk_end(ctx);
|
|
|
|
popCleanStyle(ctx);
|
|
}
|
|
|
|
struct HtpPageDef {
|
|
const char *title;
|
|
MenuTextureSlot *illustration;
|
|
};
|
|
|
|
void renderHowToPlayPage(nk_context *ctx, int winW, int winH,
|
|
MenuTextures &tex, BrowseMenuTextures &btex)
|
|
{
|
|
static int currentPage = 1;
|
|
|
|
HtpPageDef pages[] = {
|
|
{ "What's New", nullptr },
|
|
{ "Basics", nullptr },
|
|
{ "Multiplayer", nullptr },
|
|
{ "HUD", &btex.htpHUD },
|
|
{ "Creative Mode", &btex.htpCreative },
|
|
{ "Inventory", &btex.htpInventory },
|
|
{ "Chest", &btex.htpChest },
|
|
{ "Large Chest", &btex.htpLargeChest },
|
|
{ "Ender Chest", &btex.htpEnderchest },
|
|
{ "Crafting", &btex.htpCrafting },
|
|
{ "Craft Table", &btex.htpCraftTable },
|
|
{ "Furnace", &btex.htpFurnace },
|
|
{ "Dispenser", &btex.htpDispenser },
|
|
{ "Brewing", &btex.htpBrewing },
|
|
{ "Enchantment", &btex.htpEnchantment },
|
|
{ "Anvil", &btex.htpAnvil },
|
|
{ "Farming Animals", &btex.htpFarmingAnimals },
|
|
{ "Breeding Animals", &btex.htpBreeding },
|
|
{ "Trading", &btex.htpTrading },
|
|
{ "Nether Portal", &btex.htpNetherPortal },
|
|
{ "The End", &btex.htpTheEnd },
|
|
{ "Host Options", nullptr }
|
|
};
|
|
int pageCount = 22;
|
|
|
|
if (currentPage < 0) currentPage = 0;
|
|
if (currentPage >= pageCount) currentPage = pageCount - 1;
|
|
|
|
float scaleX = (float)winW / BASE_W;
|
|
float scaleY = (float)winH / BASE_H;
|
|
|
|
pushCleanStyle(ctx);
|
|
|
|
if (nk_begin(ctx, "HowToPlayPage", nk_rect(0, 0, (float)winW, (float)winH),
|
|
NK_WINDOW_NO_SCROLLBAR | NK_WINDOW_NO_INPUT | NK_WINDOW_BACKGROUND)) {
|
|
|
|
drawPanoramaBg(ctx, winW, winH, tex);
|
|
drawShadowedTitle(ctx, pages[currentPage].title, winW, winH);
|
|
|
|
struct nk_command_buffer *canvas = nk_window_get_canvas(ctx);
|
|
|
|
if (pages[currentPage].illustration != nullptr && canvas != nullptr) {
|
|
float imgX = HTP_IMAGE_X * scaleX;
|
|
float imgY = HTP_IMAGE_Y * scaleY;
|
|
float imgW = HTP_IMAGE_W * scaleX;
|
|
float imgH = HTP_IMAGE_H * scaleY;
|
|
struct nk_image illImg = slotToNkImage(*pages[currentPage].illustration);
|
|
nk_draw_image(canvas, nk_rect(imgX, imgY, imgW, imgH),
|
|
&illImg, nk_rgb(255, 255, 255));
|
|
}
|
|
|
|
float textX = HTP_TEXT_X * scaleX;
|
|
float textY = HTP_TEXT_Y * scaleY;
|
|
float textW = HTP_TEXT_W * scaleX;
|
|
float textH = 30.0f * scaleY;
|
|
|
|
drawShadowedText(ctx, "(Page content would be rendered here)",
|
|
textX, textY, textW, textH, nk_rgb(200, 200, 200), false);
|
|
|
|
char pageLabel[32];
|
|
snprintf(pageLabel, sizeof(pageLabel), "%d / %d", currentPage + 1, pageCount);
|
|
drawShadowedText(ctx, pageLabel,
|
|
0, 620.0f * scaleY, (float)winW, 24.0f * scaleY,
|
|
nk_rgb(180, 180, 180), true);
|
|
|
|
const struct nk_input *input = &ctx->input;
|
|
|
|
float navBtnW = 120.0f * scaleX;
|
|
float navBtnH = BTN_H * scaleY;
|
|
float navY = 660.0f * scaleY;
|
|
|
|
if (currentPage > 0) {
|
|
float prevX = 40.0f * scaleX;
|
|
struct nk_rect prevRect = nk_rect(prevX, navY, navBtnW, navBtnH);
|
|
bool prevHover = nk_input_is_mouse_hovering_rect(input, prevRect) != 0;
|
|
if (drawBtn(ctx, "Previous", prevX, navY, navBtnW, navBtnH, prevHover, winH, tex)) {
|
|
currentPage--;
|
|
}
|
|
}
|
|
|
|
if (currentPage < pageCount - 1) {
|
|
float nextX = (float)winW - navBtnW - 40.0f * scaleX;
|
|
struct nk_rect nextRect = nk_rect(nextX, navY, navBtnW, navBtnH);
|
|
bool nextHover = nk_input_is_mouse_hovering_rect(input, nextRect) != 0;
|
|
if (drawBtn(ctx, "Next", nextX, navY, navBtnW, navBtnH, nextHover, winH, tex)) {
|
|
currentPage++;
|
|
}
|
|
}
|
|
|
|
drawControllerPrompts(ctx, winW, winH, tex);
|
|
}
|
|
nk_end(ctx);
|
|
|
|
popCleanStyle(ctx);
|
|
}
|
|
|
|
}}
|