Files
mcpe/source/client/gui/components/RolledSelectionList.cpp
iProgramInCpp 60b21356a1 Integrate touch related development. (#90)
* * Add BuildActionIntention crap

* * Set Client and World projects to use MP compilation

* asd

* * Use the new BuildActionIntention to break and place blocks.

* * Reverse engineer the IArea system.

* * Copy break logic from survival into creative conditionally

* * Reverse IBuildInput and MouseHandler
* Replace the new relative paths in the client project with $(MC_ROOT) again

* * Reverse Multitouch, MouseDevice

* * Reverse a bunch of auxiliary classes for input.

* * Use CustomInputHolder instead of holding inputs manually.

* * Reverse a whole BUNCH of things!

* * Add feedback textures to the gitignore.

* * D-pad now renders! Also loads of other work.

* * More Stuff

* * Finish touch control bug fixing.

* * Finalize work.

* * One last thing..

* * Add a "cramped" mode to the options screen and start menu.

* * Oh, forgot to do something
2023-11-02 00:49:11 +02:00

338 lines
7.7 KiB
C++

/********************************************************************
Minecraft: Pocket Edition - Decompilation Project
Copyright (C) 2023 iProgramInCpp
The following code is licensed under the BSD 1 clause license.
SPDX-License-Identifier: BSD-1-Clause
********************************************************************/
#include "RolledSelectionList.hpp"
static float g_RolledSelectionListUnk, g_RolledSelectionListUnk2;
RolledSelectionList::RolledSelectionList(Minecraft* minecraft, int a, int b, int c, int d, int e, int f, int g)
{
m_pMinecraft = minecraft;
m_itemWidth = g;
field_18 = a;
field_C = float(c);
field_10 = float(d);
field_1C = b;
field_20 = float(e);
field_24 = float(f);
field_28 = -2;
field_2C = 0.0f;
field_38 = 0.0f;
field_3C = -1;
m_bRenderSelection = true;
m_bComponentSelected = false;
field_44 = 0;
field_48 = false;
field_4C = 0;
field_50 = 1;
g_RolledSelectionListUnk = field_30 = field_34 = float(g - a) / 2.0f;
}
int RolledSelectionList::getItemAtXPositionRaw(int x)
{
if (x < 0)
return -1;
// @NOTE: redundant check
int idx = x / m_itemWidth;
if (idx < 0)
return -1;
if (idx >= getNumberOfItems())
return -1;
return idx;
}
int RolledSelectionList::getItemAtPosition(int x, int y)
{
if (float(y) < field_20)
return -1;
if (float(y) > field_24)
return -1;
return getItemAtXPositionRaw(transformX(x));
}
bool RolledSelectionList::capXPosition()
{
float f1 = float(m_itemWidth - field_18) / 2.0f;
int i1 = getNumberOfItems();
if (field_30 < f1)
{
field_30 = f1;
field_38 = 0.0f;
return true;
}
f1 += float(m_itemWidth * (i1 - 1));
if (field_30 > f1)
{
field_30 = f1;
field_38 = 0.0f;
return true;
}
return false;
}
void RolledSelectionList::tick()
{
float diff = g_RolledSelectionListUnk - field_34;
g_RolledSelectionListUnk = field_34;
g_RolledSelectionListUnk2 = diff;
field_34 = field_30 - field_38;
}
void RolledSelectionList::render(int mouseX, int mouseY, float f)
{
renderBackground();
int nItems = getNumberOfItems();
// @TODO: fix gotos.
if (!Mouse::isButtonDown(BUTTON_LEFT))
{
if (field_28 < 0)
{
_crap:
field_28 = -1;
field_30 = getPos(f);
goto _done;
}
if (g_RolledSelectionListUnk2 < 0.0f)
field_38 = Mth::Max(-20.0f, g_RolledSelectionListUnk2);
else
field_38 = Mth::Min(20.0f, g_RolledSelectionListUnk2);
if (fabsf(field_38) < 2.0f)
{
field_38 = 0.0f;
_continue:
if (getTimeMs() - field_4C < 300)
{
int idx = transformX(mouseX) / m_itemWidth;
if (idx >= 0)
{
if (field_50 == idx && abs(field_3C - mouseX) <= 9)
selectItem(field_50, 0);
}
goto _crap;
}
goto _crap;
}
if (fabsf(field_38) > 10.0f)
{
goto _crap;
}
goto _continue;
}
else
{
touched();
if (float(mouseY) >= field_20 && float(mouseY) <= field_24)
{
if (field_28 == -1)
{
field_4C = getTimeMs();
field_3C = mouseX;
field_50 = getItemAtPosition(mouseX, field_1C / 2);
}
else if (field_28 >= 0)
{
field_34 = field_30 = field_30 - (float(mouseX) - field_2C);
}
field_28 = 0;
}
}
_done:
field_2C = float(mouseX);
capXPosition();
glDisable(GL_LIGHTING);
glDisable(GL_FOG);
m_pMinecraft->m_pTextures->loadAndBindTexture("gui/background.png");
glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
Tesselator& t = Tesselator::instance;
t.begin();
t.color(0x202020);
t.vertexUV(field_C, field_24, 0.0f, (field_C + float(int(field_30))) / 32.0f, field_24 / 32.0f);
t.vertexUV(field_10, field_24, 0.0f, (field_10 + float(int(field_30))) / 32.0f, field_24 / 32.0f);
t.vertexUV(field_10, field_20, 0.0f, (field_10 + float(int(field_30))) / 32.0f, field_20 / 32.0f);
t.vertexUV(field_C, field_20, 0.0f, (field_C + float(int(field_30))) / 32.0f, field_20 / 32.0f);
t.draw();
if (!getNumberOfItems())
field_30 = 0.0f;
if (field_48)
renderHeader(int(field_C + 4.0f - float(int(field_30))), field_1C / 2 - 40, t);
for (int i = 0; i < nItems; i++)
{
float itemX = float(field_44 + float(int(field_C + 4.0f - float(field_30))) + m_itemWidth * i);
if (field_10 < itemX) continue;
float width = m_itemWidth - 4.0f;
if (itemX + width < field_C) continue;
if (m_bRenderSelection && isSelectedItem(i))
{
glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
glDisable(GL_TEXTURE_2D);
t.begin();
t.color(m_bComponentSelected ? 0x7F89BF : 0x808080);
float right = itemX + width;
float up = float(field_1C) / 2.0f - 48.0f - 4.0f;
float dn = float(field_1C) / 2.0f + 48.0f - 4.0f;
t.vertexUV(itemX - 2, up, 0.0f, 0.0f, 0.0f);
t.vertexUV(itemX - 2, dn, 0.0f, 1.0f, 0.0f);
t.vertexUV(right + 2, dn, 0.0f, 1.0f, 1.0f);
t.vertexUV(right + 2, up, 0.0f, 0.0f, 1.0f);
t.color(0x000000);
t.vertexUV(itemX - 1, up + 1.0f, 0.0f, 0.0f, 0.0f);
t.vertexUV(itemX - 1, dn - 1.0f, 0.0f, 1.0f, 0.0f);
t.vertexUV(right + 1, dn - 1.0f, 0.0f, 1.0f, 1.0f);
t.vertexUV(right + 1, up + 1.0f, 0.0f, 0.0f, 1.0f);
t.draw();
glEnable(GL_TEXTURE_2D);
}
renderItem(i, int(itemX), field_1C / 2 - 40, int(width), t);
}
glDisable(GL_DEPTH_TEST);
renderHoleBackground(0.0f, field_20, 255, 255);
renderHoleBackground(field_24, float(field_1C), 255, 255);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glDisable(GL_ALPHA_TEST);
glShadeModel(GL_SMOOTH);
glDisable(GL_TEXTURE_2D);
// @BUG: The X and Y coordinates have been swapped. This causes the gradient to not render
// in the right place.
#ifdef ORIGINAL_CODE
t.begin();
t.color(0, 0);
t.vertexUV(field_20, m_rotX + 4.0f, 0.0f, 0.0f, 1.0f);
t.vertexUV(field_24, m_rotX + 4.0f, 0.0f, 1.0f, 1.0f);
t.color(0, 255);
t.vertexUV(field_24, m_rotX, 0.0f, 1.0f, 0.0f);
t.vertexUV(field_20, m_rotX, 0.0f, 0.0f, 0.0f);
t.draw();
t.begin();
t.color(0, 255);
t.vertexUV(field_20, m_rotY, 0.0f, 0.0f, 1.0f);
t.vertexUV(field_24, m_rotY, 0.0f, 1.0f, 1.0f);
t.color(0, 0);
t.vertexUV(field_24, m_rotY - 4.0f, 0.0f, 1.0f, 0.0f);
t.vertexUV(field_20, m_rotY - 4.0f, 0.0f, 0.0f, 0.0f);
t.draw();
#else
t.begin();
t.color(0, 0);
t.vertexUV(field_C + 4.0f, field_20, 0.0f, 0.0f, 1.0f);
t.vertexUV(field_C + 4.0f, field_24, 0.0f, 1.0f, 1.0f);
t.color(0, 255);
t.vertexUV(field_C, field_24, 0.0f, 1.0f, 0.0f);
t.vertexUV(field_C, field_20, 0.0f, 0.0f, 0.0f);
t.draw();
t.begin();
t.color(0, 255);
t.vertexUV(field_10, field_20, 0.0f, 0.0f, 1.0f);
t.vertexUV(field_10, field_24, 0.0f, 1.0f, 1.0f);
t.color(0, 0);
t.vertexUV(field_10 - 4.0f, field_24, 0.0f, 1.0f, 0.0f);
t.vertexUV(field_10 - 4.0f, field_20, 0.0f, 0.0f, 0.0f);
t.draw();
#endif
renderDecorations(mouseX, mouseY);
glEnable(GL_TEXTURE_2D);
glEnable(GL_DEPTH_TEST);
glShadeModel(GL_FLAT);
glEnable(GL_ALPHA_TEST);
glDisable(GL_BLEND);
}
void RolledSelectionList::renderHoleBackground(float y1, float y2, int a, int b)
{
m_pMinecraft->m_pTextures->loadAndBindTexture("gui/background.png");
glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
Tesselator& t = Tesselator::instance;
t.begin();
t.color(0x505050, b);
t.vertexUV(0.0f, y2, 0.0f, 0.0f, y2 / 32.0f);
t.vertexUV(float(field_18), y2, 0.0f, float(field_18) / 32.0f, y2 / 32.0f);
t.color(0x505050, a);
t.vertexUV(float(field_18), y1, 0.0f, float(field_18) / 32.0f, y1 / 32.0f);
t.vertexUV(0.0f, y1, 0.0f, 0.0f, y1 / 32.0f);
t.draw();
}
void RolledSelectionList::setRenderSelection(bool b)
{
m_bRenderSelection = b;
}
void RolledSelectionList::setComponentSelected(bool b)
{
m_bComponentSelected = b;
}
int RolledSelectionList::getMaxPosition()
{
return field_44 + m_itemWidth * getNumberOfItems();
}
float RolledSelectionList::getPos(float f)
{
return field_34 - field_38 * f;
}
void RolledSelectionList::touched()
{
}
void RolledSelectionList::renderHeader(int a, int b, Tesselator& t)
{
}
void RolledSelectionList::renderDecorations(int x, int y)
{
}
void RolledSelectionList::clickedHeader(int x, int y)
{
}