mirror of
https://github.com/RetroDECK/ES-DE.git
synced 2025-02-18 12:55:38 +00:00
Made ScraperSearchComponent use ComponentList callbacks instead of manually intercepting input.
Tweaked IList and ComponentList for this.
This commit is contained in:
parent
0464776e62
commit
719483864c
|
@ -1,5 +1,6 @@
|
||||||
#include "ComponentList.h"
|
#include "ComponentList.h"
|
||||||
#include "../Util.h"
|
#include "../Util.h"
|
||||||
|
#include "../Log.h"
|
||||||
|
|
||||||
#define TOTAL_HORIZONTAL_PADDING_PX 20
|
#define TOTAL_HORIZONTAL_PADDING_PX 20
|
||||||
|
|
||||||
|
@ -40,7 +41,7 @@ void ComponentList::onSizeChanged()
|
||||||
updateElementPosition(it->data);
|
updateElementPosition(it->data);
|
||||||
}
|
}
|
||||||
|
|
||||||
onCursorChanged(mScrollVelocity != 0 ? CURSOR_SCROLLING : CURSOR_STOPPED);
|
updateCameraOffset();
|
||||||
}
|
}
|
||||||
|
|
||||||
void ComponentList::onFocusLost()
|
void ComponentList::onFocusLost()
|
||||||
|
@ -107,6 +108,25 @@ void ComponentList::onCursorChanged(const CursorState& state)
|
||||||
mSelectorBarOffset += getRowHeight(mEntries.at(i).data);
|
mSelectorBarOffset += getRowHeight(mEntries.at(i).data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
updateCameraOffset();
|
||||||
|
|
||||||
|
// this is terribly inefficient but we don't know what we came from so...
|
||||||
|
if(size())
|
||||||
|
{
|
||||||
|
for(auto it = mEntries.begin(); it != mEntries.end(); it++)
|
||||||
|
it->data.elements.back().component->onFocusLost();
|
||||||
|
|
||||||
|
mEntries.at(mCursor).data.elements.back().component->onFocusGained();
|
||||||
|
}
|
||||||
|
|
||||||
|
if(mCursorChangedCallback)
|
||||||
|
mCursorChangedCallback(state);
|
||||||
|
|
||||||
|
updateHelpPrompts();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ComponentList::updateCameraOffset()
|
||||||
|
{
|
||||||
// move the camera to scroll
|
// move the camera to scroll
|
||||||
const float totalHeight = getTotalRowHeight();
|
const float totalHeight = getTotalRowHeight();
|
||||||
if(totalHeight > mSize.y())
|
if(totalHeight > mSize.y())
|
||||||
|
@ -129,17 +149,6 @@ void ComponentList::onCursorChanged(const CursorState& state)
|
||||||
}else{
|
}else{
|
||||||
mCameraOffset = 0;
|
mCameraOffset = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// this is terribly inefficient but we don't know what we came from so...
|
|
||||||
if(size())
|
|
||||||
{
|
|
||||||
for(auto it = mEntries.begin(); it != mEntries.end(); it++)
|
|
||||||
it->data.elements.back().component->onFocusLost();
|
|
||||||
|
|
||||||
mEntries.at(mCursor).data.elements.back().component->onFocusGained();
|
|
||||||
}
|
|
||||||
|
|
||||||
updateHelpPrompts();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ComponentList::render(const Eigen::Affine3f& parentTrans)
|
void ComponentList::render(const Eigen::Affine3f& parentTrans)
|
||||||
|
|
|
@ -65,12 +65,16 @@ public:
|
||||||
float getTotalRowHeight() const;
|
float getTotalRowHeight() const;
|
||||||
inline float getRowHeight(int row) const { return getRowHeight(mEntries.at(row).data); }
|
inline float getRowHeight(int row) const { return getRowHeight(mEntries.at(row).data); }
|
||||||
|
|
||||||
|
inline void setCursorChangedCallback(const std::function<void(CursorState state)>& callback) { mCursorChangedCallback = callback; };
|
||||||
|
inline const std::function<void(CursorState state)>& getCursorChangedCallback() const { return mCursorChangedCallback; };
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void onCursorChanged(const CursorState& state) override;
|
void onCursorChanged(const CursorState& state) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool mFocused;
|
bool mFocused;
|
||||||
|
|
||||||
|
void updateCameraOffset();
|
||||||
void updateElementPosition(const ComponentListRow& row);
|
void updateElementPosition(const ComponentListRow& row);
|
||||||
void updateElementSize(const ComponentListRow& row);
|
void updateElementSize(const ComponentListRow& row);
|
||||||
|
|
||||||
|
@ -78,4 +82,6 @@ private:
|
||||||
|
|
||||||
float mSelectorBarOffset;
|
float mSelectorBarOffset;
|
||||||
float mCameraOffset;
|
float mCameraOffset;
|
||||||
|
|
||||||
|
std::function<void(CursorState state)> mCursorChangedCallback;
|
||||||
};
|
};
|
||||||
|
|
|
@ -185,6 +185,10 @@ protected:
|
||||||
|
|
||||||
bool listInput(int velocity) // a velocity of 0 = stop scrolling
|
bool listInput(int velocity) // a velocity of 0 = stop scrolling
|
||||||
{
|
{
|
||||||
|
// generate an onCursorChanged event in the stopped state when the user lets go of the key
|
||||||
|
if(velocity == 0 && mScrollVelocity != 0)
|
||||||
|
onCursorChanged(CURSOR_STOPPED);
|
||||||
|
|
||||||
mScrollVelocity = velocity;
|
mScrollVelocity = velocity;
|
||||||
mScrollTier = 0;
|
mScrollTier = 0;
|
||||||
mScrollTierAccumulator = 0;
|
mScrollTierAccumulator = 0;
|
||||||
|
@ -268,9 +272,16 @@ protected:
|
||||||
mLoopType == LIST_NEVER_LOOP)
|
mLoopType == LIST_NEVER_LOOP)
|
||||||
{
|
{
|
||||||
if(cursor < 0)
|
if(cursor < 0)
|
||||||
|
{
|
||||||
cursor = 0;
|
cursor = 0;
|
||||||
else if(cursor >= size())
|
mScrollVelocity = 0;
|
||||||
|
mScrollTier = 0;
|
||||||
|
}else if(cursor >= size())
|
||||||
|
{
|
||||||
cursor = size() - 1;
|
cursor = size() - 1;
|
||||||
|
mScrollVelocity = 0;
|
||||||
|
mScrollTier = 0;
|
||||||
|
}
|
||||||
}else{
|
}else{
|
||||||
while(cursor < 0)
|
while(cursor < 0)
|
||||||
cursor += size();
|
cursor += size();
|
||||||
|
|
|
@ -72,7 +72,8 @@ ScraperSearchComponent::ScraperSearchComponent(Window* window, SearchType type)
|
||||||
|
|
||||||
// result list
|
// result list
|
||||||
mResultList = std::make_shared<ComponentList>(mWindow);
|
mResultList = std::make_shared<ComponentList>(mWindow);
|
||||||
|
mResultList->setCursorChangedCallback([this](CursorState state) { if(state == CURSOR_STOPPED) updateInfoPane(); });
|
||||||
|
|
||||||
updateViewStyle();
|
updateViewStyle();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -183,7 +184,11 @@ void ScraperSearchComponent::onSearchDone(const std::vector<ScraperSearchResult>
|
||||||
if(end == 0)
|
if(end == 0)
|
||||||
{
|
{
|
||||||
ComponentListRow row;
|
ComponentListRow row;
|
||||||
row.addElement(std::make_shared<TextComponent>(mWindow, "No games found!", font, color), true);
|
row.addElement(std::make_shared<TextComponent>(mWindow, "NO GAMES FOUND - SKIP", font, color), true);
|
||||||
|
|
||||||
|
if(mSkipCallback)
|
||||||
|
row.makeAcceptInputHandler(mSkipCallback);
|
||||||
|
|
||||||
mResultList->addRow(row);
|
mResultList->addRow(row);
|
||||||
mGrid.resetCursor();
|
mGrid.resetCursor();
|
||||||
}else{
|
}else{
|
||||||
|
@ -191,7 +196,8 @@ void ScraperSearchComponent::onSearchDone(const std::vector<ScraperSearchResult>
|
||||||
for(int i = 0; i < end; i++)
|
for(int i = 0; i < end; i++)
|
||||||
{
|
{
|
||||||
row.elements.clear();
|
row.elements.clear();
|
||||||
row.addElement(std::make_shared<TextComponent>(mWindow, results.at(i).mdl.get("name"), font, color), true);
|
row.addElement(std::make_shared<TextComponent>(mWindow, strToUpper(results.at(i).mdl.get("name")), font, color), true);
|
||||||
|
row.makeAcceptInputHandler([this, i] { returnResult(mScraperResults.at(i)); });
|
||||||
mResultList->addRow(row);
|
mResultList->addRow(row);
|
||||||
}
|
}
|
||||||
mGrid.resetCursor();
|
mGrid.resetCursor();
|
||||||
|
@ -222,7 +228,7 @@ void ScraperSearchComponent::onSearchError(const std::string& error)
|
||||||
|
|
||||||
int ScraperSearchComponent::getSelectedIndex()
|
int ScraperSearchComponent::getSelectedIndex()
|
||||||
{
|
{
|
||||||
if(mScraperResults.size() && mGrid.getSelectedComponent() != mResultList)
|
if(!mScraperResults.size() || mGrid.getSelectedComponent() != mResultList)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
return mResultList->getCursorId();
|
return mResultList->getCursorId();
|
||||||
|
@ -242,9 +248,11 @@ void ScraperSearchComponent::updateInfoPane()
|
||||||
mResultThumbnail->setImage("");
|
mResultThumbnail->setImage("");
|
||||||
const std::string& thumb = res.thumbnailUrl.empty() ? res.imageUrl : res.thumbnailUrl;
|
const std::string& thumb = res.thumbnailUrl.empty() ? res.imageUrl : res.thumbnailUrl;
|
||||||
if(!thumb.empty())
|
if(!thumb.empty())
|
||||||
|
{
|
||||||
mThumbnailReq = std::unique_ptr<HttpReq>(new HttpReq(thumb));
|
mThumbnailReq = std::unique_ptr<HttpReq>(new HttpReq(thumb));
|
||||||
else
|
}else{
|
||||||
mThumbnailReq.reset();
|
mThumbnailReq.reset();
|
||||||
|
}
|
||||||
|
|
||||||
// metadata
|
// metadata
|
||||||
mMD_Rating->setValue(strToUpper(res.mdl.get("rating")));
|
mMD_Rating->setValue(strToUpper(res.mdl.get("rating")));
|
||||||
|
@ -275,23 +283,9 @@ bool ScraperSearchComponent::input(InputConfig* config, Input input)
|
||||||
{
|
{
|
||||||
if(mBlockAccept)
|
if(mBlockAccept)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
//if you're on a result
|
|
||||||
if(getSelectedIndex() != -1)
|
|
||||||
{
|
|
||||||
returnResult(mScraperResults.at(getSelectedIndex()));
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ret = GuiComponent::input(config, input);
|
return GuiComponent::input(config, input);
|
||||||
|
|
||||||
if(config->isMappedTo("up", input) || config->isMappedTo("down", input) && input.value != 0)
|
|
||||||
{
|
|
||||||
updateInfoPane();
|
|
||||||
}
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScraperSearchComponent::render(const Eigen::Affine3f& parentTrans)
|
void ScraperSearchComponent::render(const Eigen::Affine3f& parentTrans)
|
||||||
|
@ -366,13 +360,13 @@ void ScraperSearchComponent::updateThumbnail()
|
||||||
{
|
{
|
||||||
std::string content = mThumbnailReq->getContent();
|
std::string content = mThumbnailReq->getContent();
|
||||||
mResultThumbnail->setImage(content.data(), content.length());
|
mResultThumbnail->setImage(content.data(), content.length());
|
||||||
|
mGrid.onSizeChanged(); // a hack to fix the thumbnail position since its size changed
|
||||||
}else{
|
}else{
|
||||||
LOG(LogWarning) << "thumbnail req failed: " << mThumbnailReq->getErrorMsg();
|
LOG(LogWarning) << "thumbnail req failed: " << mThumbnailReq->getErrorMsg();
|
||||||
mResultThumbnail->setImage("");
|
mResultThumbnail->setImage("");
|
||||||
}
|
}
|
||||||
|
|
||||||
mThumbnailReq.reset();
|
mThumbnailReq.reset();
|
||||||
mGrid.onSizeChanged(); // a hack to fix the thumbnail position since its size changed
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScraperSearchComponent::openInputScreen(ScraperSearchParams& params)
|
void ScraperSearchComponent::openInputScreen(ScraperSearchParams& params)
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
#include "GuiScraperMulti.h"
|
#include "GuiScraperMulti.h"
|
||||||
#include "../Renderer.h"
|
#include "../Renderer.h"
|
||||||
|
#include "../Log.h"
|
||||||
|
|
||||||
#include "../components/TextComponent.h"
|
#include "../components/TextComponent.h"
|
||||||
#include "../components/ButtonComponent.h"
|
#include "../components/ButtonComponent.h"
|
||||||
|
@ -10,7 +11,7 @@
|
||||||
using namespace Eigen;
|
using namespace Eigen;
|
||||||
|
|
||||||
GuiScraperMulti::GuiScraperMulti(Window* window, const std::queue<ScraperSearchParams>& searches, bool approveResults) :
|
GuiScraperMulti::GuiScraperMulti(Window* window, const std::queue<ScraperSearchParams>& searches, bool approveResults) :
|
||||||
GuiComponent(window), mBackground(window, ":/frame.png"), mGrid(window, Vector2i(1, 4)),
|
GuiComponent(window), mBackground(window, ":/frame.png"), mGrid(window, Vector2i(1, 5)),
|
||||||
mSearchQueue(searches)
|
mSearchQueue(searches)
|
||||||
{
|
{
|
||||||
addChild(&mBackground);
|
addChild(&mBackground);
|
||||||
|
@ -20,17 +21,21 @@ GuiScraperMulti::GuiScraperMulti(Window* window, const std::queue<ScraperSearchP
|
||||||
mCurrentGame = 0;
|
mCurrentGame = 0;
|
||||||
|
|
||||||
// set up grid
|
// set up grid
|
||||||
mTitle = std::make_shared<TextComponent>(mWindow, "SCRAPING IN PROGRESS", Font::get(FONT_SIZE_SMALL), 0x777777FF, TextComponent::ALIGN_CENTER);
|
mTitle = std::make_shared<TextComponent>(mWindow, "SCRAPING IN PROGRESS", Font::get(FONT_SIZE_LARGE), 0x777777FF, TextComponent::ALIGN_CENTER);
|
||||||
mGrid.setEntry(mTitle, Vector2i(0, 0), false, true);
|
mGrid.setEntry(mTitle, Vector2i(0, 0), false, true);
|
||||||
|
|
||||||
|
mSystem = std::make_shared<TextComponent>(mWindow, "SYSTEM", Font::get(FONT_SIZE_MEDIUM), 0x777777FF, TextComponent::ALIGN_CENTER);
|
||||||
|
mGrid.setEntry(mSystem, Vector2i(0, 1), false, true);
|
||||||
|
|
||||||
mSubtitle = std::make_shared<TextComponent>(mWindow, "subtitle text", Font::get(FONT_SIZE_SMALL), 0x888888FF, TextComponent::ALIGN_CENTER);
|
mSubtitle = std::make_shared<TextComponent>(mWindow, "subtitle text", Font::get(FONT_SIZE_SMALL), 0x888888FF, TextComponent::ALIGN_CENTER);
|
||||||
mGrid.setEntry(mSubtitle, Vector2i(0, 1), false, true);
|
mGrid.setEntry(mSubtitle, Vector2i(0, 2), false, true);
|
||||||
|
|
||||||
mSearchComp = std::make_shared<ScraperSearchComponent>(mWindow,
|
mSearchComp = std::make_shared<ScraperSearchComponent>(mWindow,
|
||||||
approveResults ? ScraperSearchComponent::ALWAYS_ACCEPT_MATCHING_CRC : ScraperSearchComponent::ALWAYS_ACCEPT_FIRST_RESULT);
|
approveResults ? ScraperSearchComponent::ALWAYS_ACCEPT_MATCHING_CRC : ScraperSearchComponent::ALWAYS_ACCEPT_FIRST_RESULT);
|
||||||
mSearchComp->setAcceptCallback(std::bind(&GuiScraperMulti::acceptResult, this, std::placeholders::_1));
|
mSearchComp->setAcceptCallback(std::bind(&GuiScraperMulti::acceptResult, this, std::placeholders::_1));
|
||||||
|
mSearchComp->setSkipCallback(std::bind(&GuiScraperMulti::skip, this));
|
||||||
mSearchComp->setCancelCallback(std::bind(&GuiScraperMulti::finish, this));
|
mSearchComp->setCancelCallback(std::bind(&GuiScraperMulti::finish, this));
|
||||||
mGrid.setEntry(mSearchComp, Vector2i(0, 2), approveResults, true);
|
mGrid.setEntry(mSearchComp, Vector2i(0, 3), approveResults, true);
|
||||||
|
|
||||||
std::vector< std::shared_ptr<ButtonComponent> > buttons;
|
std::vector< std::shared_ptr<ButtonComponent> > buttons;
|
||||||
buttons.push_back(std::make_shared<ButtonComponent>(mWindow, "INPUT", "search", [&] {
|
buttons.push_back(std::make_shared<ButtonComponent>(mWindow, "INPUT", "search", [&] {
|
||||||
|
@ -40,7 +45,7 @@ GuiScraperMulti::GuiScraperMulti(Window* window, const std::queue<ScraperSearchP
|
||||||
buttons.push_back(std::make_shared<ButtonComponent>(mWindow, "SKIP", "skip", std::bind(&GuiScraperMulti::skip, this)));
|
buttons.push_back(std::make_shared<ButtonComponent>(mWindow, "SKIP", "skip", std::bind(&GuiScraperMulti::skip, this)));
|
||||||
buttons.push_back(std::make_shared<ButtonComponent>(mWindow, "STOP", "stop (progress saved)", std::bind(&GuiScraperMulti::finish, this)));
|
buttons.push_back(std::make_shared<ButtonComponent>(mWindow, "STOP", "stop (progress saved)", std::bind(&GuiScraperMulti::finish, this)));
|
||||||
mButtonGrid = makeButtonGrid(mWindow, buttons);
|
mButtonGrid = makeButtonGrid(mWindow, buttons);
|
||||||
mGrid.setEntry(mButtonGrid, Vector2i(0, 3), true, false);
|
mGrid.setEntry(mButtonGrid, Vector2i(0, 4), true, false);
|
||||||
|
|
||||||
setSize(Renderer::getScreenWidth() * 0.7f, Renderer::getScreenHeight() * 0.65f);
|
setSize(Renderer::getScreenWidth() * 0.7f, Renderer::getScreenHeight() * 0.65f);
|
||||||
setPosition((Renderer::getScreenWidth() - mSize.x()) / 2, (Renderer::getScreenHeight() - mSize.y()) / 2);
|
setPosition((Renderer::getScreenWidth() - mSize.x()) / 2, (Renderer::getScreenHeight() - mSize.y()) / 2);
|
||||||
|
@ -54,8 +59,9 @@ void GuiScraperMulti::onSizeChanged()
|
||||||
mGrid.setSize(mSize);
|
mGrid.setSize(mSize);
|
||||||
|
|
||||||
mGrid.setRowHeightPerc(0, mTitle->getFont()->getHeight() / mGrid.getSize().y());
|
mGrid.setRowHeightPerc(0, mTitle->getFont()->getHeight() / mGrid.getSize().y());
|
||||||
mGrid.setRowHeightPerc(1, mSubtitle->getFont()->getHeight() / mGrid.getSize().y());
|
mGrid.setRowHeightPerc(1, mSystem->getFont()->getHeight() / mGrid.getSize().y());
|
||||||
mGrid.setRowHeightPerc(3, mButtonGrid->getSize().y() / mGrid.getSize().y());
|
mGrid.setRowHeightPerc(2, mSubtitle->getFont()->getHeight() / mGrid.getSize().y());
|
||||||
|
mGrid.setRowHeightPerc(4, mButtonGrid->getSize().y() / mGrid.getSize().y());
|
||||||
}
|
}
|
||||||
|
|
||||||
void GuiScraperMulti::doNextSearch()
|
void GuiScraperMulti::doNextSearch()
|
||||||
|
@ -66,9 +72,13 @@ void GuiScraperMulti::doNextSearch()
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// update subtitle
|
// update title
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss << "GAME " << (mCurrentGame + 1) << " OF " << mTotalGames;
|
mSystem->setText(strToUpper(mSearchQueue.front().system->getName()));
|
||||||
|
|
||||||
|
// update subtitle
|
||||||
|
ss.str(""); // clear
|
||||||
|
ss << "GAME " << (mCurrentGame + 1) << " OF " << mTotalGames << " - " << strToUpper(mSearchQueue.front().game->getPath().filename().string());
|
||||||
mSubtitle->setText(ss.str());
|
mSubtitle->setText(ss.str());
|
||||||
|
|
||||||
mSearchComp->search(mSearchQueue.front());
|
mSearchComp->search(mSearchQueue.front());
|
||||||
|
|
|
@ -33,6 +33,7 @@ private:
|
||||||
ComponentGrid mGrid;
|
ComponentGrid mGrid;
|
||||||
|
|
||||||
std::shared_ptr<TextComponent> mTitle;
|
std::shared_ptr<TextComponent> mTitle;
|
||||||
|
std::shared_ptr<TextComponent> mSystem;
|
||||||
std::shared_ptr<TextComponent> mSubtitle;
|
std::shared_ptr<TextComponent> mSubtitle;
|
||||||
std::shared_ptr<ScraperSearchComponent> mSearchComp;
|
std::shared_ptr<ScraperSearchComponent> mSearchComp;
|
||||||
std::shared_ptr<ComponentGrid> mButtonGrid;
|
std::shared_ptr<ComponentGrid> mButtonGrid;
|
||||||
|
|
Loading…
Reference in a new issue