Browse Source

Selectionwindow

Laserlicht 1 year ago
parent
commit
989394de53

+ 41 - 7
client/battle/BattleInterfaceClasses.cpp

@@ -424,22 +424,26 @@ QuickSpellPanel::QuickSpellPanel(std::shared_ptr<CButton> initWidget)
 
 	addUsedEvents(LCLICK | SHOW_POPUP | MOVE);
 
-	setEnabled(false);
-
 	pos = Rect(0, 0, 52, 372);
 	background = std::make_shared<CFilledTexture>(ImagePath::builtin("DIBOXBCK"), pos);
 	rect = std::make_shared<TransparentFilledRectangle>(Rect(0, 0, pos.w + 1, pos.h + 1), ColorRGBA(0, 0, 0, 0), ColorRGBA(241, 216, 120, 255));
 
+	panelSelect = std::make_shared<QuickSpellPanelSelect>();
+
 	for(int i = 0; i < 10; i++) {
 		SpellID id = 14;
-		auto button = std::make_shared<CButton>(Point(2, 1 + 37 * i), AnimationPath::builtin("spellint"), CButton::tooltip(), [&](){ std::cout << "test"; }, EShortcut::HERO_COSTUME_0);
+		auto button = std::make_shared<CButton>(Point(2, 1 + 37 * i), AnimationPath::builtin("spellint"), CButton::tooltip(), [&](){ std::cout << "test"; });
 		button->setOverlay(std::make_shared<CAnimImage>(AnimationPath::builtin("spellint"), i > 0 ? id.num : 0));
+		button->addPopupCallback([this](){
+			panelSelect->setEnabled(true);
+		});
 
 		if(i > 3)
 		{
 			button->block(true);
 			buttonsDisabled.push_back(std::make_shared<TransparentFilledRectangle>(Rect(2, 1 + 37 * i, 48, 36), ColorRGBA(0, 0, 0, 128)));
 		}
+		labels.push_back(std::make_shared<CLabel>(7, 4 + 37 * i, EFonts::FONT_SMALL, ETextAlignment::TOPLEFT, Colors::WHITE, std::to_string(i)));
 
 		buttons.push_back(button);
 	}
@@ -453,7 +457,7 @@ void QuickSpellPanel::show(Canvas & to)
 
 void QuickSpellPanel::clickReleased(const Point & cursorPosition)
 {
-	if(!pos.isInside(cursorPosition))
+	if(!pos.isInside(cursorPosition) && (!panelSelect->isActive() || !panelSelect->pos.isInside(cursorPosition)))
 		close();
 	
 	if(initWidget->pos.isInside(cursorPosition))
@@ -465,7 +469,7 @@ void QuickSpellPanel::clickReleased(const Point & cursorPosition)
 
 void QuickSpellPanel::showPopupWindow(const Point & cursorPosition)
 {
-	if(!pos.isInside(cursorPosition))
+	if(!pos.isInside(cursorPosition) && (!panelSelect->isActive() || !panelSelect->pos.isInside(cursorPosition)))
 		close();
 
 	if(initWidget->pos.isInside(cursorPosition))
@@ -476,10 +480,12 @@ void QuickSpellPanel::showPopupWindow(const Point & cursorPosition)
 
 void QuickSpellPanel::mouseMoved(const Point & cursorPosition, const Point & lastUpdateDistance)
 {
-	if(	cursorPosition.x <= initWidget->pos.x - 20 ||
+	if(	(cursorPosition.x <= initWidget->pos.x - 20 ||
 		cursorPosition.x >= initWidget->pos.x + initWidget->pos.w + 20 ||
 		cursorPosition.y <= initWidget->pos.y - pos.h - 20 ||
-		(cursorPosition.y >= initWidget->pos.y && !initWidget->pos.isInside(cursorPosition)))
+		(cursorPosition.y >= initWidget->pos.y && !initWidget->pos.isInside(cursorPosition))) &&
+		(!panelSelect->isActive() || !panelSelect->pos.resize(20).isInside(cursorPosition))
+	)
 		close();
 }
 
@@ -488,6 +494,34 @@ bool QuickSpellPanel::receiveEvent(const Point & position, int eventType) const
 	return true;  // capture click also outside of window
 }
 
+QuickSpellPanelSelect::QuickSpellPanelSelect()
+{
+	OBJECT_CONSTRUCTION_CAPTURING(255-DISPOSE);
+
+	setEnabled(false);
+
+	std::vector<ConstTransitivePtr<CSpell>> spellList;
+	for (auto const & s : VLC->spellh->objects)
+		if (s->isCombat() && !s->isSpecial() && !s->isCreatureAbility())
+			spellList.push_back(s);
+
+	auto ceil = [](int x, int y){ return(x + y - 1) / y; };
+	int columnsNeeded = ceil(spellList.size(), 10);
+
+	pos = Rect(-20 - columnsNeeded * 50, 0, columnsNeeded * 50 + 2, 372);
+	background = std::make_shared<CFilledTexture>(ImagePath::builtin("DIBOXBCK"), Rect(0, 0, pos.w, pos.h));
+	rect = std::make_shared<TransparentFilledRectangle>(Rect(0, 0, pos.w + 1, pos.h + 1), ColorRGBA(0, 0, 0, 0), ColorRGBA(241, 216, 120, 255));
+
+	for(int i = 0; i < spellList.size(); i++)
+	{
+		int y = i % 10;
+		int x = i / 10;
+		auto button = std::make_shared<CButton>(Point(2 + 50 * x, 1 + 37 * y), AnimationPath::builtin("spellint"), CButton::tooltip(), [&](){ std::cout << "test"; });
+		button->setOverlay(std::make_shared<CAnimImage>(AnimationPath::builtin("spellint"), spellList[i]->getId().num + 1));
+		buttons.push_back(button);
+	}
+}
+
 HeroInfoBasicPanel::HeroInfoBasicPanel(const InfoAboutHero & hero, Point * position, bool initializeBackground)
 	: CIntObject(0)
 {

+ 14 - 0
client/battle/BattleInterfaceClasses.h

@@ -147,6 +147,17 @@ public:
 	BattleHero(const BattleInterface & owner, const CGHeroInstance * hero, bool defender);
 };
 
+class QuickSpellPanelSelect : public CIntObject
+{
+private:
+	std::shared_ptr<CFilledTexture> background;
+	std::shared_ptr<TransparentFilledRectangle> rect;
+	std::vector<std::shared_ptr<CButton>> buttons;
+
+public:
+	QuickSpellPanelSelect();
+};
+
 class QuickSpellPanel : public CWindowObject
 {
 private:
@@ -154,6 +165,9 @@ private:
 	std::shared_ptr<TransparentFilledRectangle> rect;
 	std::vector<std::shared_ptr<CButton>> buttons;
 	std::vector<std::shared_ptr<TransparentFilledRectangle>> buttonsDisabled;
+	std::vector<std::shared_ptr<CLabel>> labels;
+
+	std::shared_ptr<QuickSpellPanelSelect> panelSelect;
 
 	bool receiveEvent(const Point & position, int eventType) const override;
 	void clickReleased(const Point & cursorPosition) override;

+ 10 - 6
client/battle/BattleWindow.cpp

@@ -104,17 +104,21 @@ BattleWindow::BattleWindow(BattleInterface & owner):
 		auto hero = owner.getBattle()->battleGetMyHero();
 		if(GH.screenDimensions().x >= 1000 && hero && owner.getBattle()->battleCanCastSpell(hero, spells::Mode::HERO) != ESpellCastProblem::NO_SPELLBOOK && settings["general"]["enableUiEnhancements"].Bool())
 		{
-			quickSpellPanelWindow = std::make_shared<QuickSpellPanel>(w);
-			quickSpellPanelWindow->moveTo(Point(w->pos.x - 2, w->pos.y - 378));
-			w->addHoverCallback([this, w](bool on)
+			auto createQuickSpellPanelWindow = [](std::shared_ptr<CButton> widget){
+				std::shared_ptr<QuickSpellPanel> window = std::make_shared<QuickSpellPanel>(widget);
+				window->moveTo(Point(widget->pos.x - 2, widget->pos.y - 378));
+				GH.windows().pushWindow(window);
+			};
+			
+			w->addHoverCallback([this, createQuickSpellPanelWindow, w](bool on)
 			{
 				if(on)
-					GH.windows().pushWindow(quickSpellPanelWindow);
+					createQuickSpellPanelWindow(w);
 			});
-			w->addPanningCallback([this](const Point & initialPosition, const Point & currentPosition, const Point & lastUpdateDistance)
+			w->addPanningCallback([this, createQuickSpellPanelWindow, w](const Point & initialPosition, const Point & currentPosition, const Point & lastUpdateDistance)
 			{
 				if((currentPosition - initialPosition).y < -20)
-					GH.windows().pushWindow(quickSpellPanelWindow);
+					createQuickSpellPanelWindow(w);
 			});
 		}
 	}

+ 0 - 1
client/battle/BattleWindow.h

@@ -40,7 +40,6 @@ class BattleWindow : public InterfaceObjectConfigurable
 	std::shared_ptr<HeroInfoBasicPanel> defenderHeroWindow;
 	std::shared_ptr<StackInfoBasicPanel> attackerStackWindow;
 	std::shared_ptr<StackInfoBasicPanel> defenderStackWindow;
-	std::shared_ptr<QuickSpellPanel> quickSpellPanelWindow;
 
 	std::shared_ptr<TurnTimerWidget> attackerTimerWidget;
 	std::shared_ptr<TurnTimerWidget> defenderTimerWidget;

+ 7 - 0
client/widgets/Buttons.cpp

@@ -67,6 +67,11 @@ void CButton::addCallback(const std::function<void()> & callback)
 	this->callback += callback;
 }
 
+void CButton::addPopupCallback(const std::function<void()> & callback)
+{
+	this->callbackPopup += callback;
+}
+
 void CButton::addHoverCallback(const std::function<void(bool)> & callback)
 {
 	this->hoverCallback += callback;
@@ -299,6 +304,8 @@ void CButton::clickCancel(const Point & cursorPosition)
 
 void CButton::showPopupWindow(const Point & cursorPosition)
 {
+	callbackPopup();
+
 	if(!helpBox.empty()) //there is no point to show window with nothing inside...
 		CRClickPopup::createAndPush(helpBox);
 }

+ 2 - 0
client/widgets/Buttons.h

@@ -69,6 +69,7 @@ public:
 class CButton : public ButtonBase
 {
 	CFunctionList<void()> callback;
+	CFunctionList<void()> callbackPopup;
 	CFunctionList<void(bool)> hoverCallback;
 	CFunctionList<void(const Point &, const Point &, const Point &)> panningCallback;
 
@@ -92,6 +93,7 @@ public:
 
 	/// adds one more callback to on-click actions
 	void addCallback(const std::function<void()> & callback);
+	void addPopupCallback(const std::function<void()> & callback);
 	void addHoverCallback(const std::function<void(bool)> & callback);
 	void addPanningCallback(const std::function<void(const Point &, const Point &, const Point &)> & callback);