mirror of
https://github.com/vcmi/vcmi.git
synced 2025-08-13 19:54:17 +02:00
Resources trade panel
This commit is contained in:
@@ -20,7 +20,7 @@
|
||||
#include "../../lib/CGeneralTextHandler.h"
|
||||
#include "../../lib/mapObjects/CGHeroInstance.h"
|
||||
|
||||
CTradeBase::CTradeableItem::CTradeableItem(Point pos, EType Type, int ID, bool Left, int Serial)
|
||||
CTradeableItem::CTradeableItem(Point pos, EType Type, int ID, bool Left, int Serial)
|
||||
: CIntObject(LCLICK | HOVER | SHOW_POPUP, pos)
|
||||
, type(EType(-1)) // set to invalid, will be corrected in setType
|
||||
, id(ID)
|
||||
@@ -38,7 +38,7 @@ CTradeBase::CTradeableItem::CTradeableItem(Point pos, EType Type, int ID, bool L
|
||||
}
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::setType(EType newType)
|
||||
void CTradeableItem::setType(EType newType)
|
||||
{
|
||||
if(type != newType)
|
||||
{
|
||||
@@ -57,7 +57,7 @@ void CTradeBase::CTradeableItem::setType(EType newType)
|
||||
}
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::setID(int newID)
|
||||
void CTradeableItem::setID(int newID)
|
||||
{
|
||||
if(id != newID)
|
||||
{
|
||||
@@ -76,7 +76,7 @@ void CTradeBase::CTradeableItem::setID(int newID)
|
||||
}
|
||||
}
|
||||
|
||||
AnimationPath CTradeBase::CTradeableItem::getFilename()
|
||||
AnimationPath CTradeableItem::getFilename()
|
||||
{
|
||||
switch(type)
|
||||
{
|
||||
@@ -95,7 +95,7 @@ AnimationPath CTradeBase::CTradeableItem::getFilename()
|
||||
}
|
||||
}
|
||||
|
||||
int CTradeBase::CTradeableItem::getIndex()
|
||||
int CTradeableItem::getIndex()
|
||||
{
|
||||
if(id < 0)
|
||||
return -1;
|
||||
@@ -116,7 +116,7 @@ int CTradeBase::CTradeableItem::getIndex()
|
||||
}
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::showAll(Canvas & to)
|
||||
void CTradeableItem::showAll(Canvas & to)
|
||||
{
|
||||
Point posToBitmap;
|
||||
Point posToSubCenter;
|
||||
@@ -154,13 +154,13 @@ void CTradeBase::CTradeableItem::showAll(Canvas & to)
|
||||
to.drawText(pos.topLeft() + posToSubCenter, FONT_SMALL, Colors::WHITE, ETextAlignment::CENTER, subtitle);
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::clickPressed(const Point& cursorPosition)
|
||||
void CTradeableItem::clickPressed(const Point & cursorPosition)
|
||||
{
|
||||
if(clickPressedCallback)
|
||||
clickPressedCallback(shared_from_this());
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::showAllAt(const Point& dstPos, const std::string& customSub, Canvas& to)
|
||||
void CTradeableItem::showAllAt(const Point & dstPos, const std::string & customSub, Canvas & to)
|
||||
{
|
||||
Rect oldPos = pos;
|
||||
std::string oldSub = subtitle;
|
||||
@@ -175,7 +175,7 @@ void CTradeBase::CTradeableItem::showAllAt(const Point& dstPos, const std::strin
|
||||
subtitle = oldSub;
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::hover(bool on)
|
||||
void CTradeableItem::hover(bool on)
|
||||
{
|
||||
if(!on)
|
||||
{
|
||||
@@ -198,7 +198,7 @@ void CTradeBase::CTradeableItem::hover(bool on)
|
||||
}
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::showPopupWindow(const Point& cursorPosition)
|
||||
void CTradeableItem::showPopupWindow(const Point & cursorPosition)
|
||||
{
|
||||
switch(type)
|
||||
{
|
||||
@@ -214,7 +214,7 @@ void CTradeBase::CTradeableItem::showPopupWindow(const Point& cursorPosition)
|
||||
}
|
||||
}
|
||||
|
||||
std::string CTradeBase::CTradeableItem::getName(int number) const
|
||||
std::string CTradeableItem::getName(int number) const
|
||||
{
|
||||
switch(type)
|
||||
{
|
||||
@@ -235,7 +235,7 @@ std::string CTradeBase::CTradeableItem::getName(int number) const
|
||||
return "";
|
||||
}
|
||||
|
||||
const CArtifactInstance* CTradeBase::CTradeableItem::getArtInstance() const
|
||||
const CArtifactInstance * CTradeableItem::getArtInstance() const
|
||||
{
|
||||
switch(type)
|
||||
{
|
||||
@@ -247,7 +247,7 @@ const CArtifactInstance* CTradeBase::CTradeableItem::getArtInstance() const
|
||||
}
|
||||
}
|
||||
|
||||
void CTradeBase::CTradeableItem::setArtInstance(const CArtifactInstance * art)
|
||||
void CTradeableItem::setArtInstance(const CArtifactInstance * art)
|
||||
{
|
||||
assert(type == ARTIFACT_PLACEHOLDER || type == ARTIFACT_INSTANCE);
|
||||
hlp = art;
|
||||
@@ -257,6 +257,26 @@ void CTradeBase::CTradeableItem::setArtInstance(const CArtifactInstance * art)
|
||||
setID(-1);
|
||||
}
|
||||
|
||||
SResourcesPanel::SResourcesPanel(CTradeableItem::ClickPressedFunctor clickPressedCallback, updatePanelFunctor updateSubtitles)
|
||||
: updateSubtitles(updateSubtitles)
|
||||
{
|
||||
assert(resourcesForTrade.size() == slotsPos.size());
|
||||
OBJECT_CONSTRUCTION_CUSTOM_CAPTURING(255 - DISPOSE);
|
||||
|
||||
for(const auto & res : resourcesForTrade)
|
||||
{
|
||||
slots.emplace_back(std::make_shared<CTradeableItem>(slotsPos[res.num], EType::RESOURCE, res.num, true, res.num));
|
||||
slots.back()->clickPressedCallback = clickPressedCallback;
|
||||
slots.back()->pos.w = 69; slots.back()->pos.h = 66;
|
||||
}
|
||||
}
|
||||
|
||||
void SResourcesPanel::updateSlots()
|
||||
{
|
||||
if(updateSubtitles)
|
||||
updateSubtitles();
|
||||
}
|
||||
|
||||
CTradeBase::CTradeBase(const IMarket * market, const CGHeroInstance * hero)
|
||||
: market(market)
|
||||
, hero(hero)
|
||||
|
@@ -23,52 +23,79 @@ VCMI_LIB_NAMESPACE_END
|
||||
class CButton;
|
||||
class CTextBox;
|
||||
|
||||
enum EType
|
||||
{
|
||||
RESOURCE, PLAYER, ARTIFACT_TYPE, CREATURE, CREATURE_PLACEHOLDER, ARTIFACT_PLACEHOLDER, ARTIFACT_INSTANCE
|
||||
};
|
||||
|
||||
class CTradeableItem : public CIntObject, public std::enable_shared_from_this<CTradeableItem>
|
||||
{
|
||||
std::shared_ptr<CAnimImage> image;
|
||||
AnimationPath getFilename();
|
||||
int getIndex();
|
||||
public:
|
||||
using ClickPressedFunctor = std::function<void(std::shared_ptr<CTradeableItem>)>;
|
||||
|
||||
const CArtifactInstance * hlp; //holds ptr to artifact instance id type artifact
|
||||
EType type;
|
||||
int id;
|
||||
const int serial;
|
||||
const bool left;
|
||||
std::string subtitle; //empty if default
|
||||
ClickPressedFunctor clickPressedCallback;
|
||||
|
||||
void setType(EType newType);
|
||||
void setID(int newID);
|
||||
|
||||
const CArtifactInstance * getArtInstance() const;
|
||||
void setArtInstance(const CArtifactInstance * art);
|
||||
|
||||
CFunctionList<void()> callback;
|
||||
bool downSelection;
|
||||
|
||||
void showAllAt(const Point & dstPos, const std::string & customSub, Canvas & to);
|
||||
|
||||
void showPopupWindow(const Point & cursorPosition) override;
|
||||
void hover(bool on) override;
|
||||
void showAll(Canvas & to) override;
|
||||
void clickPressed(const Point & cursorPosition) override;
|
||||
std::string getName(int number = -1) const;
|
||||
CTradeableItem(Point pos, EType Type, int ID, bool Left, int Serial);
|
||||
};
|
||||
|
||||
struct SResourcesPanel : public CIntObject
|
||||
{
|
||||
using updatePanelFunctor = std::function<void()>;
|
||||
|
||||
const std::vector<GameResID> resourcesForTrade =
|
||||
{
|
||||
GameResID::WOOD, GameResID::MERCURY, GameResID::ORE,
|
||||
GameResID::SULFUR, GameResID::CRYSTAL, GameResID::GEMS,
|
||||
GameResID::GOLD
|
||||
};
|
||||
const std::vector<Point> slotsPos =
|
||||
{
|
||||
Point(0, 0), Point(83, 0), Point(166, 0),
|
||||
Point(0, 79), Point(83, 79), Point(166, 79),
|
||||
Point(83, 158)
|
||||
};
|
||||
std::vector<std::shared_ptr<CTradeableItem>> slots;
|
||||
std::function<void()> updateSubtitles;
|
||||
|
||||
SResourcesPanel(CTradeableItem::ClickPressedFunctor clickPressedCallback, updatePanelFunctor updateSubtitles);
|
||||
void updateSlots();
|
||||
};
|
||||
|
||||
class CTradeBase
|
||||
{
|
||||
public:
|
||||
enum EType
|
||||
{
|
||||
RESOURCE, PLAYER, ARTIFACT_TYPE, CREATURE, CREATURE_PLACEHOLDER, ARTIFACT_PLACEHOLDER, ARTIFACT_INSTANCE
|
||||
};
|
||||
|
||||
class CTradeableItem : public CIntObject, public std::enable_shared_from_this<CTradeableItem>
|
||||
{
|
||||
std::shared_ptr<CAnimImage> image;
|
||||
AnimationPath getFilename();
|
||||
int getIndex();
|
||||
public:
|
||||
const CArtifactInstance * hlp; //holds ptr to artifact instance id type artifact
|
||||
EType type;
|
||||
int id;
|
||||
const int serial;
|
||||
const bool left;
|
||||
std::string subtitle; //empty if default
|
||||
std::function<void(std::shared_ptr<CTradeableItem> altarSlot)> clickPressedCallback;
|
||||
|
||||
void setType(EType newType);
|
||||
void setID(int newID);
|
||||
|
||||
const CArtifactInstance* getArtInstance() const;
|
||||
void setArtInstance(const CArtifactInstance * art);
|
||||
|
||||
CFunctionList<void()> callback;
|
||||
bool downSelection;
|
||||
|
||||
void showAllAt(const Point & dstPos, const std::string & customSub, Canvas & to);
|
||||
|
||||
void showPopupWindow(const Point & cursorPosition) override;
|
||||
void hover(bool on) override;
|
||||
void showAll(Canvas & to) override;
|
||||
void clickPressed(const Point & cursorPosition) override;
|
||||
std::string getName(int number = -1) const;
|
||||
CTradeableItem(Point pos, EType Type, int ID, bool Left, int Serial);
|
||||
};
|
||||
|
||||
const IMarket * market;
|
||||
const CGHeroInstance * hero;
|
||||
|
||||
//all indexes: 1 = left, 0 = right
|
||||
std::array<std::vector<std::shared_ptr<CTradeableItem>>, 2> items;
|
||||
std::shared_ptr<SResourcesPanel> resoursesPanelPlayer;
|
||||
std::shared_ptr<SResourcesPanel> resoursesPanelMarket;
|
||||
|
||||
//highlighted items (nullptr if no highlight)
|
||||
std::shared_ptr<CTradeableItem> hLeft;
|
||||
|
@@ -84,6 +84,66 @@ void CTradeWindow::initItems(bool Left)
|
||||
}
|
||||
else
|
||||
{
|
||||
if(Left && itemsType[1] == RESOURCE)
|
||||
{
|
||||
resoursesPanelPlayer = std::make_shared<SResourcesPanel>(
|
||||
[this](std::shared_ptr<CTradeableItem> marketSlot) -> void
|
||||
{
|
||||
if(hLeft != marketSlot)
|
||||
hLeft = marketSlot;
|
||||
else
|
||||
return;
|
||||
selectionChanged(true);
|
||||
},
|
||||
[this]() -> void
|
||||
{
|
||||
for(auto & slot : resoursesPanelPlayer->slots)
|
||||
slot->subtitle = std::to_string(LOCPLINT->cb->getResourceAmount(static_cast<EGameResID>(slot->serial)));
|
||||
});
|
||||
resoursesPanelPlayer->moveBy(Point(39, 182));
|
||||
resoursesPanelPlayer->updateSlots();
|
||||
return;
|
||||
}
|
||||
if(!Left && itemsType[0] == RESOURCE)
|
||||
{
|
||||
resoursesPanelMarket = std::make_shared<SResourcesPanel>(
|
||||
[this](std::shared_ptr<CTradeableItem> marketSlot) -> void
|
||||
{
|
||||
if(hRight != marketSlot)
|
||||
hRight = marketSlot;
|
||||
else
|
||||
return;
|
||||
selectionChanged(false);
|
||||
initSubs(false);
|
||||
},
|
||||
[this]() -> void
|
||||
{
|
||||
for(auto & slot : resoursesPanelMarket->slots)
|
||||
{
|
||||
if(hLeft) //artifact, creature
|
||||
{
|
||||
int h1, h2; //hlp variables for getting offer
|
||||
market->getOffer(hLeft->id, slot->id, h1, h2, mode);
|
||||
if(slot->id != hLeft->id || mode != EMarketMode::RESOURCE_RESOURCE) //don't allow exchanging same resources
|
||||
{
|
||||
std::ostringstream oss;
|
||||
oss << h2;
|
||||
if(h1 != 1)
|
||||
oss << "/" << h1;
|
||||
slot->subtitle = oss.str();
|
||||
}
|
||||
else
|
||||
slot->subtitle = CGI->generaltexth->allTexts[164]; // n/a
|
||||
}
|
||||
else
|
||||
slot->subtitle = "";
|
||||
}
|
||||
});
|
||||
resoursesPanelMarket->moveBy(Point(327, 182));
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
std::vector<int> *ids = getItemsIds(Left);
|
||||
std::vector<Rect> pos;
|
||||
int amount = -1;
|
||||
@@ -185,14 +245,6 @@ void CTradeWindow::getPositionsFor(std::vector<Rect> &poss, bool Left, EType typ
|
||||
|
||||
switch(type)
|
||||
{
|
||||
case RESOURCE:
|
||||
dx = 82;
|
||||
dy = 79;
|
||||
x = 39;
|
||||
y = 180;
|
||||
h = 68;
|
||||
w = 70;
|
||||
break;
|
||||
case PLAYER:
|
||||
dx = 83;
|
||||
dy = 118;
|
||||
@@ -244,6 +296,15 @@ void CTradeWindow::getPositionsFor(std::vector<Rect> &poss, bool Left, EType typ
|
||||
|
||||
void CTradeWindow::initSubs(bool Left)
|
||||
{
|
||||
if(itemsType[Left] == RESOURCE)
|
||||
{
|
||||
if(Left)
|
||||
resoursesPanelPlayer->updateSlots();
|
||||
else
|
||||
resoursesPanelMarket->updateSlots();
|
||||
return;
|
||||
}
|
||||
|
||||
for(auto item : items[Left])
|
||||
{
|
||||
if(Left)
|
||||
@@ -253,9 +314,6 @@ void CTradeWindow::initSubs(bool Left)
|
||||
case CREATURE:
|
||||
item->subtitle = std::to_string(hero->getStackCount(SlotID(item->serial)));
|
||||
break;
|
||||
case RESOURCE:
|
||||
item->subtitle = std::to_string(LOCPLINT->cb->getResourceAmount(static_cast<EGameResID>(item->serial)));
|
||||
break;
|
||||
}
|
||||
}
|
||||
else //right side
|
||||
@@ -264,23 +322,6 @@ void CTradeWindow::initSubs(bool Left)
|
||||
{
|
||||
item->subtitle = CGI->generaltexth->capColors[item->id];
|
||||
}
|
||||
else if(hLeft)//artifact, creature
|
||||
{
|
||||
int h1, h2; //hlp variables for getting offer
|
||||
market->getOffer(hLeft->id, item->id, h1, h2, mode);
|
||||
if(item->id != hLeft->id || mode != EMarketMode::RESOURCE_RESOURCE) //don't allow exchanging same resources
|
||||
{
|
||||
std::ostringstream oss;
|
||||
oss << h2;
|
||||
if(h1!=1)
|
||||
oss << "/" << h1;
|
||||
item->subtitle = oss.str();
|
||||
}
|
||||
else
|
||||
item->subtitle = CGI->generaltexth->allTexts[164]; // n/a
|
||||
}
|
||||
else
|
||||
item->subtitle = "";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user