Rewritten menu scrolling methodology.

This commit is contained in:
Pieter Hulshoff 2017-01-01 15:15:11 +01:00
parent c6c21ea0ff
commit 6f68195258
5 changed files with 137 additions and 185 deletions

View File

@ -56,9 +56,6 @@ ScrollingList::ScrollingList(Configuration &c,
, itemIndex_(0) , itemIndex_(0)
, componentIndex_(0) , componentIndex_(0)
, selectedOffsetIndex_(0) , selectedOffsetIndex_(0)
, currentScrollDirection_(ScrollDirectionIdle)
, requestedScrollDirection_(ScrollDirectionIdle)
, currentScrollState_(ScrollStateIdle)
, scrollAcceleration_(0) , scrollAcceleration_(0)
, startScrollTime_(0.500) , startScrollTime_(0.500)
, scrollPeriod_(0) , scrollPeriod_(0)
@ -79,9 +76,6 @@ ScrollingList::ScrollingList(const ScrollingList &copy)
, itemIndex_(0) , itemIndex_(0)
, componentIndex_(0) , componentIndex_(0)
, selectedOffsetIndex_(copy.selectedOffsetIndex_) , selectedOffsetIndex_(copy.selectedOffsetIndex_)
, currentScrollDirection_(ScrollDirectionIdle)
, requestedScrollDirection_(ScrollDirectionIdle)
, currentScrollState_(ScrollStateIdle)
, scrollAcceleration_(copy.scrollAcceleration_) , scrollAcceleration_(copy.scrollAcceleration_)
, startScrollTime_(copy.startScrollTime_) , startScrollTime_(copy.startScrollTime_)
, scrollPeriod_(0) , scrollPeriod_(0)
@ -237,39 +231,6 @@ Item *ScrollingList::getSelectedItem()
} }
void ScrollingList::click(double nextScrollTime)
{
if(currentScrollDirection_ == ScrollDirectionBack)
{
// get the previous item
itemIndex_ = loopDecrement(itemIndex_, 1, items_->size());
Item *i = items_->at(itemIndex_);
componentIndex_ = loopDecrement(componentIndex_, 1, components_.size());
deallocateTexture(componentIndex_);
allocateTexture(componentIndex_, i);
Component *c = components_.at(componentIndex_);
ViewInfo *v = scrollPoints_->at(0);
resetTweens(c, tweenPoints_->at(componentIndex_), v, v, 0);
}
else if(currentScrollDirection_ == ScrollDirectionForward)
{
unsigned int itemIncrement = loopIncrement(itemIndex_, scrollPoints_->size(), items_->size());
itemIndex_ = loopIncrement(itemIndex_, 1, items_->size());
Item *i = items_->at(itemIncrement);
deallocateTexture(componentIndex_);
allocateTexture(componentIndex_, i);
Component *c = components_.at(componentIndex_);
ViewInfo *v = scrollPoints_->back();
resetTweens(c, tweenPoints_->at(componentIndex_), v, v, 0);
componentIndex_ = loopIncrement(componentIndex_, 1, components_.size());
}
}
void ScrollingList::pageUp() void ScrollingList::pageUp()
{ {
if(components_.size() == 0) return; if(components_.size() == 0) return;
@ -345,9 +306,6 @@ void ScrollingList::letterChange(bool increment)
void ScrollingList::freeGraphicsMemory() void ScrollingList::freeGraphicsMemory()
{ {
Component::freeGraphicsMemory(); Component::freeGraphicsMemory();
currentScrollDirection_ = ScrollDirectionIdle;
requestedScrollDirection_ = ScrollDirectionIdle;
currentScrollState_ = ScrollStateIdle;
scrollPeriod_ = 0; scrollPeriod_ = 0;
deallocateSpritePoints(); deallocateSpritePoints();
@ -411,110 +369,14 @@ void ScrollingList::update(float dt)
{ {
Component::update(dt); Component::update(dt);
bool readyToScroll = true;
bool scrollChanged = false;
bool scrollRequested = false;
bool scrollStopped = false;
if(components_.size() == 0) return; if(components_.size() == 0) return;
if(!items_ || items_->size() == 0) return; if(!items_ || items_->size() == 0) return;
// validate all scroll points are done tweening to the next position
for(std::vector<Component *>::iterator c = components_.begin(); c != components_.end(); c++)
{
if(*c && (*c)->isMenuScrolling())
{
readyToScroll = false;
break;
}
}
// check if it was requested to change directions
if(currentScrollState_ == ScrollStateActive && requestedScrollDirection_ != currentScrollDirection_)
{
currentScrollState_ = ScrollStateStopping;
}
else if(currentScrollState_ == ScrollStateIdle && readyToScroll)
{
scrollPeriod_ = startScrollTime_;
// check to see if requested to scroll
if(requestedScrollDirection_ != ScrollDirectionIdle)
{
currentScrollState_ = ScrollStateActive;
currentScrollDirection_ = requestedScrollDirection_;
scrollRequested = true;
}
}
// if currently scrolling, process it
if(!scrollRequested && readyToScroll)
{
if(currentScrollState_ == ScrollStateStopping)
{
currentScrollState_ = ScrollStateIdle;
scrollStopped = true;
click(0);
for(unsigned int i = 0; i < tweenPoints_->size(); ++i)
{
unsigned int cindex = loopIncrement(componentIndex_, i, components_.size());
Component *c = components_.at(cindex);
if(c) c->setTweens(tweenPoints_->at(i));
}
}
else if(currentScrollState_ == ScrollStateActive)
{
scrollPeriod_ -= scrollAcceleration_;
if(scrollPeriod_ < scrollAcceleration_)
{
scrollPeriod_ = scrollAcceleration_;
}
click(scrollPeriod_);
scrollChanged = true;
}
}
for(unsigned int i = 0; i < scrollPoints_->size(); i++) for(unsigned int i = 0; i < scrollPoints_->size(); i++)
{ {
unsigned int cindex = loopIncrement(componentIndex_, i, components_.size()); unsigned int cindex = loopIncrement(componentIndex_, i, components_.size());
Component *c = components_.at(cindex); Component *c = components_.at(cindex);
if(c && readyToScroll && (scrollRequested || scrollChanged))
{
unsigned int nextI = 0;
if(currentScrollDirection_ == ScrollDirectionBack)
{
nextI = loopIncrement(i, 1, scrollPoints_->size());
}
if(currentScrollDirection_ == ScrollDirectionForward)
{
nextI = loopDecrement(i, 1, scrollPoints_->size());
}
ViewInfo *currentvi = scrollPoints_->at(i);
ViewInfo *nextvi = scrollPoints_->at(nextI);
resetTweens(c, tweenPoints_->at(i), currentvi, nextvi, scrollPeriod_);
c->baseViewInfo.font = nextvi->font; // Use the font settings of the next index
c->triggerEvent( "menuScroll" );
}
if(c) c->update(dt); if(c) c->update(dt);
}
if(scrollStopped)
{
if(currentScrollState_ == ScrollStatePageChange)
{
currentScrollState_ = ScrollStateIdle;
}
} }
} }
@ -737,15 +599,9 @@ void ScrollingList::draw(unsigned int layer)
} }
void ScrollingList::setScrollDirection(ScrollDirection direction)
{
requestedScrollDirection_ = direction;
}
bool ScrollingList::isIdle() bool ScrollingList::isIdle()
{ {
if(!Component::isIdle() || currentScrollState_ != ScrollStateIdle) return false; if(!Component::isIdle()) return false;
for(unsigned int i = 0; i < components_.size(); ++i) for(unsigned int i = 0; i < components_.size(); ++i)
{ {
@ -757,3 +613,73 @@ bool ScrollingList::isIdle()
} }
void ScrollingList::resetScrollPeriod()
{
scrollPeriod_ = startScrollTime_;
return;
}
void ScrollingList::updateScrollPeriod()
{
scrollPeriod_ -= scrollAcceleration_;
if(scrollPeriod_ < scrollAcceleration_)
{
scrollPeriod_ = scrollAcceleration_;
}
}
void ScrollingList::scroll(bool forward)
{
if(forward)
{
Item *i = items_->at(loopIncrement(itemIndex_, scrollPoints_->size(), items_->size()));
deallocateTexture(componentIndex_);
allocateTexture(componentIndex_, i);
}
else
{
Item *i = items_->at(loopDecrement(itemIndex_, 1, items_->size()));
deallocateTexture(loopDecrement(componentIndex_, 1, components_.size()));
allocateTexture(loopDecrement(componentIndex_, 1, components_.size()), i);
}
for(unsigned int i = 0; i < scrollPoints_->size(); i++)
{
unsigned int cindex = loopIncrement(componentIndex_, i, components_.size());
Component *c = components_.at(cindex);
unsigned int nextI = 0;
if(forward)
{
nextI = loopDecrement(i, 1, scrollPoints_->size());
}
else
{
nextI = loopIncrement(i, 1, scrollPoints_->size());
}
ViewInfo *currentvi = scrollPoints_->at(i);
ViewInfo *nextvi = scrollPoints_->at(nextI);
resetTweens(c, tweenPoints_->at(i), currentvi, nextvi, scrollPeriod_);
c->baseViewInfo.font = nextvi->font; // Use the font settings of the next index
c->triggerEvent( "menuScroll" );
}
if(forward)
{
itemIndex_ = loopIncrement(itemIndex_, 1, items_->size());
componentIndex_ = loopIncrement(componentIndex_, 1, components_.size());
}
else
{
itemIndex_ = loopDecrement(itemIndex_, 1, items_->size());
componentIndex_ = loopDecrement(componentIndex_, 1, components_.size());
}
return;
}

View File

@ -34,14 +34,6 @@ class Font;
class ScrollingList : public Component class ScrollingList : public Component
{ {
public: public:
enum ScrollDirection
{
ScrollDirectionBack,
ScrollDirectionForward,
ScrollDirectionIdle,
};
ScrollingList(Configuration &c, ScrollingList(Configuration &c,
Page &p, Page &p,
bool layoutMode, bool layoutMode,
@ -65,7 +57,6 @@ public:
void setItems(std::vector<Item *> *items); void setItems(std::vector<Item *> *items);
void destroyItems(); void destroyItems();
void setPoints(std::vector<ViewInfo *> *scrollPoints, std::vector<AnimationEvents *> *tweenPoints); void setPoints(std::vector<ViewInfo *> *scrollPoints, std::vector<AnimationEvents *> *tweenPoints);
void setScrollDirection(ScrollDirection direction);
unsigned int getSelectedIndex(); unsigned int getSelectedIndex();
unsigned int getSize(); unsigned int getSize();
void pageUp(); void pageUp();
@ -89,22 +80,16 @@ public:
bool horizontalScroll; bool horizontalScroll;
void deallocateSpritePoints(); void deallocateSpritePoints();
void allocateSpritePoints(); void allocateSpritePoints();
void resetScrollPeriod();
void updateScrollPeriod();
void scroll(bool forward);
private: private:
void click(double nextScrollTime);
void resetTweens(Component *c, AnimationEvents *sets, ViewInfo *currentViewInfo, ViewInfo *nextViewInfo, double scrollTime); void resetTweens(Component *c, AnimationEvents *sets, ViewInfo *currentViewInfo, ViewInfo *nextViewInfo, double scrollTime);
unsigned int loopIncrement(unsigned int offset, unsigned int i, unsigned int size); unsigned int loopIncrement(unsigned int offset, unsigned int i, unsigned int size);
unsigned int loopDecrement(unsigned int offset, unsigned int i, unsigned int size); unsigned int loopDecrement(unsigned int offset, unsigned int i, unsigned int size);
enum ScrollState
{
ScrollStateActive,
ScrollStatePageChange,
ScrollStateStopping,
ScrollStateIdle
};
bool layoutMode_; bool layoutMode_;
std::vector<Component *> *spriteList_; std::vector<Component *> *spriteList_;
std::vector<ViewInfo *> *scrollPoints_; std::vector<ViewInfo *> *scrollPoints_;
@ -114,10 +99,6 @@ private:
unsigned int componentIndex_; unsigned int componentIndex_;
unsigned int selectedOffsetIndex_; unsigned int selectedOffsetIndex_;
ScrollDirection currentScrollDirection_;
ScrollDirection requestedScrollDirection_;
ScrollState currentScrollState_;
float scrollAcceleration_; float scrollAcceleration_;
float startScrollTime_; float startScrollTime_;
float scrollPeriod_; float scrollPeriod_;

View File

@ -390,9 +390,6 @@ void Page::highlightExit()
void Page::setScrolling(ScrollDirection direction) void Page::setScrolling(ScrollDirection direction)
{ {
ScrollingList::ScrollDirection menuDirection;
bool prevScrollActive = scrollActive_;
switch(direction) switch(direction)
{ {
case ScrollDirectionForward: case ScrollDirectionForward:
@ -400,7 +397,6 @@ void Page::setScrolling(ScrollDirection direction)
{ {
menuScroll(); menuScroll();
} }
menuDirection = ScrollingList::ScrollDirectionForward;
scrollActive_ = true; scrollActive_ = true;
break; break;
case ScrollDirectionBack: case ScrollDirectionBack:
@ -408,23 +404,14 @@ void Page::setScrolling(ScrollDirection direction)
{ {
menuScroll(); menuScroll();
} }
menuDirection = ScrollingList::ScrollDirectionBack;
scrollActive_ = true; scrollActive_ = true;
break; break;
case ScrollDirectionIdle: case ScrollDirectionIdle:
default: default:
menuDirection = ScrollingList::ScrollDirectionIdle;
scrollActive_ = false; scrollActive_ = false;
break; break;
} }
if(!prevScrollActive && scrollActive_ && highlightSoundChunk_)
{
highlightSoundChunk_->play();
}
activeMenu_->setScrollDirection(menuDirection);
} }
bool Page::isHorizontalScroll() bool Page::isHorizontalScroll()
@ -856,4 +843,35 @@ bool Page::isPlaying()
return retVal; return retVal;
} }
void Page::resetScrollPeriod()
{
if(activeMenu_)
{
activeMenu_->resetScrollPeriod();
}
return;
}
void Page::updateScrollPeriod()
{
if(activeMenu_)
{
activeMenu_->updateScrollPeriod();
}
return;
}
void Page::scroll(bool forward)
{
if(activeMenu_)
{
activeMenu_->scroll(forward);
highlightSoundChunk_->play();
}
return;
}

View File

@ -96,6 +96,9 @@ public:
void reallocateMenuSpritePoints(); void reallocateMenuSpritePoints();
bool isMenuScrolling(); bool isMenuScrolling();
bool isPlaying(); bool isPlaying();
void resetScrollPeriod();
void updateScrollPeriod();
void scroll(bool forward);
private: private:
void playlistChange(); void playlistChange();

View File

@ -257,7 +257,7 @@ void RetroFE::run()
float lastTime = 0; float lastTime = 0;
float deltaTime = 0; float deltaTime = 0;
SDL_Event e; SDL_Event e;
if (SDL_PollEvent(&e)) if (splashMode && SDL_PollEvent(&e))
{ {
if(input_.update(e)) if(input_.update(e))
{ {
@ -281,7 +281,10 @@ void RetroFE::run()
// account for when returning from a menu and the previous key was still "stuck" // account for when returning from a menu and the previous key was still "stuck"
if(lastLaunchReturnTime_ == 0 || (currentTime_ - lastLaunchReturnTime_ > .3)) if(lastLaunchReturnTime_ == 0 || (currentTime_ - lastLaunchReturnTime_ > .3))
{ {
state = processUserInput(currentPage_); if(currentPage_->isMenuIdle())
{
state = processUserInput(currentPage_);
}
lastLaunchReturnTime_ = 0; lastLaunchReturnTime_ = 0;
} }
} }
@ -398,7 +401,7 @@ void RetroFE::run()
break; break;
case RETROFE_HIGHLIGHT_EXIT: case RETROFE_HIGHLIGHT_EXIT:
if (processUserInput(currentPage_) == RETROFE_HIGHLIGHT_REQUEST) if (currentPage_->isMenuIdle() && processUserInput(currentPage_) == RETROFE_HIGHLIGHT_REQUEST)
{ {
state = RETROFE_HIGHLIGHT_MENU_IDLE; state = RETROFE_HIGHLIGHT_MENU_IDLE;
} }
@ -415,7 +418,7 @@ void RetroFE::run()
break; break;
case RETROFE_HIGHLIGHT_ENTER: case RETROFE_HIGHLIGHT_ENTER:
if (processUserInput(currentPage_) == RETROFE_HIGHLIGHT_REQUEST) if (currentPage_->isMenuIdle() && processUserInput(currentPage_) == RETROFE_HIGHLIGHT_REQUEST)
{ {
state = RETROFE_HIGHLIGHT_REQUEST; state = RETROFE_HIGHLIGHT_REQUEST;
} }
@ -655,15 +658,29 @@ RetroFE::RETROFE_STATE RetroFE::processUserInput(Page *page)
bool exit = false; bool exit = false;
RETROFE_STATE state = RETROFE_IDLE; RETROFE_STATE state = RETROFE_IDLE;
SDL_Event e;
while (SDL_PollEvent(&e))
{
input_.update(e);
if(e.type == SDL_KEYDOWN && !e.key.repeat)
{
break;
}
}
if(page->isHorizontalScroll()) if(page->isHorizontalScroll())
{ {
if (input_.keystate(UserInput::KeyCodeLeft)) if (input_.keystate(UserInput::KeyCodeLeft))
{ {
page->setScrolling(Page::ScrollDirectionBack); page->setScrolling(Page::ScrollDirectionBack);
page->scroll(false);
page->updateScrollPeriod();
} }
if (input_.keystate(UserInput::KeyCodeRight)) if (input_.keystate(UserInput::KeyCodeRight))
{ {
page->setScrolling(Page::ScrollDirectionForward); page->setScrolling(Page::ScrollDirectionForward);
page->scroll(true);
page->updateScrollPeriod();
} }
} }
else else
@ -671,10 +688,14 @@ RetroFE::RETROFE_STATE RetroFE::processUserInput(Page *page)
if (input_.keystate(UserInput::KeyCodeUp)) if (input_.keystate(UserInput::KeyCodeUp))
{ {
page->setScrolling(Page::ScrollDirectionBack); page->setScrolling(Page::ScrollDirectionBack);
page->scroll(false);
page->updateScrollPeriod();
} }
if (input_.keystate(UserInput::KeyCodeDown)) if (input_.keystate(UserInput::KeyCodeDown))
{ {
page->setScrolling(Page::ScrollDirectionForward); page->setScrolling(Page::ScrollDirectionForward);
page->scroll(true);
page->updateScrollPeriod();
} }
} }
@ -790,8 +811,11 @@ RetroFE::RETROFE_STATE RetroFE::processUserInput(Page *page)
!input_.keystate(UserInput::KeyCodePageDown) && !input_.keystate(UserInput::KeyCodePageDown) &&
!attract_.isActive()) !attract_.isActive())
{ {
page->resetScrollPeriod();
if (page->isMenuScrolling()) if (page->isMenuScrolling())
{
state = RETROFE_HIGHLIGHT_REQUEST; state = RETROFE_HIGHLIGHT_REQUEST;
}
} }
return state; return state;