mirror of
				https://github.com/vcmi/vcmi.git
				synced 2025-10-31 00:07:39 +02:00 
			
		
		
		
	Merge pull request #4384 from Laserlicht/shortcut
add shortcut for list item ordering
This commit is contained in:
		| @@ -18,10 +18,12 @@ | ||||
| #include "../widgets/ObjectLists.h" | ||||
| #include "../widgets/RadialMenu.h" | ||||
| #include "../windows/InfoWindows.h" | ||||
| #include "../windows/CCastleInterface.h" | ||||
| #include "../CGameInfo.h" | ||||
| #include "../CPlayerInterface.h" | ||||
| #include "../PlayerLocalState.h" | ||||
| #include "../gui/CGuiHandler.h" | ||||
| #include "../gui/Shortcut.h" | ||||
| #include "../gui/WindowHandler.h" | ||||
| #include "../render/Canvas.h" | ||||
| #include "../render/Colors.h" | ||||
| @@ -32,6 +34,8 @@ | ||||
| #include "../../lib/mapObjects/CGHeroInstance.h" | ||||
| #include "../../lib/mapObjects/CGTownInstance.h" | ||||
|  | ||||
| #include "../../CCallback.h" | ||||
|  | ||||
| CList::CListItem::CListItem(CList * Parent) | ||||
| 	: CIntObject(LCLICK | SHOW_POPUP | HOVER), | ||||
| 	parent(Parent), | ||||
| @@ -229,7 +233,7 @@ CHeroList::CHeroItem::CHeroItem(CHeroList *parent, const CGHeroInstance * Hero) | ||||
|  | ||||
| 	update(); | ||||
|  | ||||
| 	addUsedEvents(GESTURE); | ||||
| 	addUsedEvents(GESTURE | KEYBOARD); | ||||
| } | ||||
|  | ||||
| void CHeroList::CHeroItem::update() | ||||
| @@ -300,6 +304,55 @@ void CHeroList::CHeroItem::gesture(bool on, const Point & initialPosition, const | ||||
| 	GH.windows().createAndPushWindow<RadialMenu>(pos.center(), menuElements, true); | ||||
| } | ||||
|  | ||||
| void CHeroList::CHeroItem::keyPressed(EShortcut key) | ||||
| { | ||||
| 	if(!hero) | ||||
| 		return; | ||||
|  | ||||
| 	if(parent->selected != this->shared_from_this()) | ||||
| 		return; | ||||
|  | ||||
| 	auto & heroes = LOCPLINT->localState->getWanderingHeroes(); | ||||
|  | ||||
| 	if(key == EShortcut::LIST_HERO_DISMISS) | ||||
| 	{ | ||||
| 		LOCPLINT->showYesNoDialog(CGI->generaltexth->allTexts[22], [=](){ LOCPLINT->cb->dismissHero(hero); }, nullptr); | ||||
| 		return; | ||||
| 	} | ||||
|  | ||||
| 	if(heroes.size() < 2) | ||||
| 		return; | ||||
|  | ||||
| 	size_t heroPos = vstd::find_pos(heroes, hero); | ||||
| 	const CGHeroInstance * heroUpper = (heroPos < 1) ? nullptr : heroes.at(heroPos - 1); | ||||
| 	const CGHeroInstance * heroLower = (heroPos > heroes.size() - 2) ? nullptr : heroes.at(heroPos + 1); | ||||
|  | ||||
| 	switch(key) | ||||
| 	{ | ||||
| 	case EShortcut::LIST_HERO_UP: | ||||
| 		if(heroUpper) | ||||
| 			LOCPLINT->localState->swapWanderingHero(heroPos, heroPos - 1); | ||||
| 		break; | ||||
|  | ||||
| 	case EShortcut::LIST_HERO_DOWN: | ||||
| 		if(heroLower) | ||||
| 			LOCPLINT->localState->swapWanderingHero(heroPos, heroPos + 1); | ||||
| 		break; | ||||
|  | ||||
| 	case EShortcut::LIST_HERO_TOP: | ||||
| 		if(heroUpper) | ||||
| 			for (size_t i = heroPos; i > 0; i--) | ||||
| 				LOCPLINT->localState->swapWanderingHero(i, i - 1); | ||||
| 		break; | ||||
|  | ||||
| 	case EShortcut::LIST_HERO_BOTTOM: | ||||
| 		if(heroLower) | ||||
| 			for (int i = heroPos; i < heroes.size() - 1; i++) | ||||
| 				LOCPLINT->localState->swapWanderingHero(i, i + 1); | ||||
| 		break; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| std::shared_ptr<CIntObject> CHeroList::createItem(size_t index) | ||||
| { | ||||
| 	if (LOCPLINT->localState->getWanderingHeroes().size() > index) | ||||
| @@ -369,7 +422,7 @@ CTownList::CTownItem::CTownItem(CTownList *parent, const CGTownInstance *Town): | ||||
| 	pos = picture->pos; | ||||
| 	update(); | ||||
|  | ||||
| 	addUsedEvents(GESTURE); | ||||
| 	addUsedEvents(GESTURE | KEYBOARD); | ||||
| } | ||||
|  | ||||
| std::shared_ptr<CIntObject> CTownList::CTownItem::genSelection() | ||||
| @@ -418,24 +471,77 @@ void CTownList::CTownItem::gesture(bool on, const Point & initialPosition, const | ||||
| 	int townUpperPos = (townIndex < 1) ? -1 : townIndex - 1; | ||||
| 	int townLowerPos = (townIndex > towns.size() - 2) ? -1 : townIndex + 1; | ||||
|  | ||||
| 	auto updateList = [](){ | ||||
| 		for (auto ki : GH.windows().findWindows<CCastleInterface>()) | ||||
| 			ki->townChange(); //update list | ||||
| 	}; | ||||
|  | ||||
| 	std::vector<RadialMenuConfig> menuElements = { | ||||
| 		{ RadialMenuConfig::ITEM_ALT_NN, townUpperPos > -1, "altUpTop", "vcmi.radialWheel.moveTop", [townIndex]() | ||||
| 		{ RadialMenuConfig::ITEM_ALT_NN, townUpperPos > -1, "altUpTop", "vcmi.radialWheel.moveTop", [updateList, townIndex]() | ||||
| 		{ | ||||
| 			for (int i = townIndex; i > 0; i--) | ||||
| 				LOCPLINT->localState->swapOwnedTowns(i, i - 1); | ||||
| 			updateList(); | ||||
| 		} }, | ||||
| 		{ RadialMenuConfig::ITEM_ALT_NW, townUpperPos > -1, "altUp", "vcmi.radialWheel.moveUp", [townIndex, townUpperPos](){LOCPLINT->localState->swapOwnedTowns(townIndex, townUpperPos); } }, | ||||
| 		{ RadialMenuConfig::ITEM_ALT_SW, townLowerPos > -1, "altDown", "vcmi.radialWheel.moveDown", [townIndex, townLowerPos](){ LOCPLINT->localState->swapOwnedTowns(townIndex, townLowerPos); } }, | ||||
| 		{ RadialMenuConfig::ITEM_ALT_SS, townLowerPos > -1, "altDownBottom", "vcmi.radialWheel.moveBottom", [townIndex, towns]() | ||||
| 		{ RadialMenuConfig::ITEM_ALT_NW, townUpperPos > -1, "altUp", "vcmi.radialWheel.moveUp", [updateList, townIndex, townUpperPos](){LOCPLINT->localState->swapOwnedTowns(townIndex, townUpperPos); updateList(); } }, | ||||
| 		{ RadialMenuConfig::ITEM_ALT_SW, townLowerPos > -1, "altDown", "vcmi.radialWheel.moveDown", [updateList, townIndex, townLowerPos](){ LOCPLINT->localState->swapOwnedTowns(townIndex, townLowerPos); updateList(); } }, | ||||
| 		{ RadialMenuConfig::ITEM_ALT_SS, townLowerPos > -1, "altDownBottom", "vcmi.radialWheel.moveBottom", [updateList, townIndex, towns]() | ||||
| 		{ | ||||
| 			for (int i = townIndex; i < towns.size() - 1; i++) | ||||
| 				LOCPLINT->localState->swapOwnedTowns(i, i + 1); | ||||
| 			updateList(); | ||||
| 		} }, | ||||
| 	}; | ||||
|  | ||||
| 	GH.windows().createAndPushWindow<RadialMenu>(pos.center(), menuElements, true); | ||||
| } | ||||
|  | ||||
| void CTownList::CTownItem::keyPressed(EShortcut key) | ||||
| { | ||||
| 	if(parent->selected != this->shared_from_this()) | ||||
| 		return; | ||||
|  | ||||
| 	const std::vector<const CGTownInstance *> towns = LOCPLINT->localState->getOwnedTowns(); | ||||
| 	size_t townIndex = vstd::find_pos(towns, town); | ||||
|  | ||||
| 	if(townIndex + 1 > towns.size() || !towns.at(townIndex)) | ||||
| 		return; | ||||
|  | ||||
| 	if(towns.size() < 2) | ||||
| 		return; | ||||
|  | ||||
| 	int townUpperPos = (townIndex < 1) ? -1 : townIndex - 1; | ||||
| 	int townLowerPos = (townIndex > towns.size() - 2) ? -1 : townIndex + 1; | ||||
|  | ||||
| 	switch(key) | ||||
| 	{ | ||||
| 	case EShortcut::LIST_TOWN_UP: | ||||
| 		if(townUpperPos > -1) | ||||
| 			LOCPLINT->localState->swapOwnedTowns(townIndex, townUpperPos); | ||||
| 		break; | ||||
|  | ||||
| 	case EShortcut::LIST_TOWN_DOWN: | ||||
| 		if(townLowerPos > -1) | ||||
| 			LOCPLINT->localState->swapOwnedTowns(townIndex, townLowerPos); | ||||
| 		break; | ||||
|  | ||||
| 	case EShortcut::LIST_TOWN_TOP: | ||||
| 		if(townUpperPos > -1) | ||||
| 			for (int i = townIndex; i > 0; i--) | ||||
| 				LOCPLINT->localState->swapOwnedTowns(i, i - 1); | ||||
| 		break; | ||||
|  | ||||
| 	case EShortcut::LIST_TOWN_BOTTOM: | ||||
| 		if(townLowerPos > -1) | ||||
| 			for (int i = townIndex; i < towns.size() - 1; i++) | ||||
| 				LOCPLINT->localState->swapOwnedTowns(i, i + 1); | ||||
| 		break; | ||||
| 	} | ||||
|  | ||||
| 	for (auto ki : GH.windows().findWindows<CCastleInterface>()) | ||||
| 		ki->townChange(); //update list | ||||
| } | ||||
|  | ||||
| std::string CTownList::CTownItem::getHoverText() | ||||
| { | ||||
| 	return town->getObjectName(); | ||||
|   | ||||
| @@ -29,9 +29,10 @@ class CList : public Scrollable | ||||
| protected: | ||||
| 	class CListItem : public CIntObject, public std::enable_shared_from_this<CListItem> | ||||
| 	{ | ||||
| 		CList * parent; | ||||
| 		std::shared_ptr<CIntObject> selection; | ||||
| 	public: | ||||
| 		CList * parent; | ||||
|  | ||||
| 		CListItem(CList * parent); | ||||
| 		~CListItem(); | ||||
|  | ||||
| @@ -55,9 +56,6 @@ protected: | ||||
|  | ||||
| private: | ||||
| 	const size_t size; | ||||
|  | ||||
| 	//for selection\deselection | ||||
| 	std::shared_ptr<CListItem> selected; | ||||
| 	void select(std::shared_ptr<CListItem> which); | ||||
| 	friend class CListItem; | ||||
|  | ||||
| @@ -81,6 +79,9 @@ protected: | ||||
| 	void update(); | ||||
|  | ||||
| public: | ||||
| 	//for selection\deselection | ||||
| 	std::shared_ptr<CListItem> selected; | ||||
|  | ||||
| 	/// functions that will be called when selection changes | ||||
| 	CFunctionList<void()> onSelect; | ||||
|  | ||||
| @@ -128,6 +129,7 @@ class CHeroList	: public CList | ||||
| 		void open() override; | ||||
| 		void showTooltip() override; | ||||
| 		void gesture(bool on, const Point & initialPosition, const Point & finalPosition) override; | ||||
| 		void keyPressed(EShortcut key) override; | ||||
| 		std::string getHoverText() override; | ||||
| 	}; | ||||
|  | ||||
| @@ -162,6 +164,7 @@ class CTownList	: public CList | ||||
| 		void open() override; | ||||
| 		void showTooltip() override; | ||||
| 		void gesture(bool on, const Point & initialPosition, const Point & finalPosition) override; | ||||
| 		void keyPressed(EShortcut key) override; | ||||
| 		std::string getHoverText() override; | ||||
| 	}; | ||||
|  | ||||
|   | ||||
| @@ -293,5 +293,15 @@ enum class EShortcut | ||||
| 	SPELLBOOK_TAB_ADVENTURE, | ||||
| 	SPELLBOOK_TAB_COMBAT, | ||||
|  | ||||
| 	LIST_HERO_UP, | ||||
| 	LIST_HERO_DOWN, | ||||
| 	LIST_HERO_TOP, | ||||
| 	LIST_HERO_BOTTOM, | ||||
| 	LIST_HERO_DISMISS, | ||||
| 	LIST_TOWN_UP, | ||||
| 	LIST_TOWN_DOWN, | ||||
| 	LIST_TOWN_TOP, | ||||
| 	LIST_TOWN_BOTTOM, | ||||
|  | ||||
| 	AFTER_LAST | ||||
| }; | ||||
|   | ||||
| @@ -275,6 +275,15 @@ EShortcut ShortcutHandler::findShortcut(const std::string & identifier ) const | ||||
| 		{"heroCostumeLoad9",         EShortcut::HERO_COSTUME_LOAD_9       }, | ||||
| 		{"spellbookTabAdventure",    EShortcut::SPELLBOOK_TAB_ADVENTURE   }, | ||||
| 		{"spellbookTabCombat",       EShortcut::SPELLBOOK_TAB_COMBAT      }, | ||||
| 		{"listHeroUp",               EShortcut::LIST_HERO_UP              }, | ||||
| 		{"listHeroDown",             EShortcut::LIST_HERO_DOWN            }, | ||||
| 		{"listHeroTop",              EShortcut::LIST_HERO_TOP             }, | ||||
| 		{"listHeroBottom",           EShortcut::LIST_HERO_BOTTOM          }, | ||||
| 		{"listHeroDismiss",          EShortcut::LIST_HERO_DISMISS         }, | ||||
| 		{"listTownUp",               EShortcut::LIST_TOWN_UP              }, | ||||
| 		{"listTownDown",             EShortcut::LIST_TOWN_DOWN            }, | ||||
| 		{"listTownTop",              EShortcut::LIST_TOWN_TOP             }, | ||||
| 		{"listTownBottom",           EShortcut::LIST_TOWN_BOTTOM          }, | ||||
| 		{"mainMenuHotseat",          EShortcut::MAIN_MENU_HOTSEAT         }, | ||||
| 		{"mainMenuHostGame",         EShortcut::MAIN_MENU_HOST_GAME       }, | ||||
| 		{"mainMenuJoinGame",         EShortcut::MAIN_MENU_JOIN_GAME       }, | ||||
|   | ||||
| @@ -242,6 +242,15 @@ | ||||
| 		"townOpenThievesGuild":     "G", | ||||
| 		"townOpenVisitingHero":     "Ctrl+H", | ||||
| 		"townSwapArmies":           "Space", | ||||
| 		"listHeroUp":               "Ctrl+PageUp", | ||||
| 		"listHeroDown":             "Ctrl+PageDown", | ||||
| 		"listHeroTop":              "Ctrl+Home", | ||||
| 		"listHeroBottom":           "Ctrl+End", | ||||
| 		"listHeroDismiss":          "Delete", | ||||
| 		"listTownUp":               "Ctrl+PageUp", | ||||
| 		"listTownDown":             "Ctrl+PageDown", | ||||
| 		"listTownTop":              "Ctrl+Home", | ||||
| 		"listTownBottom":           "Ctrl+End", | ||||
| 		 | ||||
| 		// Controller-specific | ||||
| 		"mouseCursorX":             [], | ||||
|   | ||||
		Reference in New Issue
	
	Block a user