Merge pull request #172 from hex007/feature-powersaver

Implement Power Savings feature
This commit is contained in:
Jools Wills 2017-07-28 17:05:25 +01:00 committed by GitHub
commit 37b89fe57e
13 changed files with 182 additions and 42 deletions

View file

@ -86,7 +86,7 @@ protected:
virtual void onCursorChanged(const CursorState& state); virtual void onCursorChanged(const CursorState& state);
private: private:
static const int MARQUEE_DELAY = 2000; static const int MARQUEE_DELAY = 1000;
static const int MARQUEE_SPEED = 8; static const int MARQUEE_SPEED = 8;
static const int MARQUEE_RATE = 1; static const int MARQUEE_RATE = 1;

View file

@ -6,6 +6,7 @@
#include "scrapers/Scraper.h" #include "scrapers/Scraper.h"
#include "Renderer.h" #include "Renderer.h"
#include "Log.h" #include "Log.h"
#include "PowerSaver.h"
#include "Settings.h" #include "Settings.h"
GuiGameScraper::GuiGameScraper(Window* window, ScraperSearchParams params, std::function<void(const ScraperSearchResult&)> doneFunc) : GuiComponent(window), GuiGameScraper::GuiGameScraper(Window* window, ScraperSearchParams params, std::function<void(const ScraperSearchResult&)> doneFunc) : GuiComponent(window),
@ -14,6 +15,7 @@ GuiGameScraper::GuiGameScraper(Window* window, ScraperSearchParams params, std::
mSearchParams(params), mSearchParams(params),
mClose(false) mClose(false)
{ {
PowerSaver::setState(false);
addChild(&mBox); addChild(&mBox);
addChild(&mGrid); addChild(&mGrid);
@ -96,6 +98,7 @@ bool GuiGameScraper::input(InputConfig* config, Input input)
{ {
if(config->isMappedTo("b", input) && input.value) if(config->isMappedTo("b", input) && input.value)
{ {
PowerSaver::setState(true);
delete this; delete this;
return true; return true;
} }

View file

@ -4,6 +4,7 @@
#include "Sound.h" #include "Sound.h"
#include "Log.h" #include "Log.h"
#include "Settings.h" #include "Settings.h"
#include "PowerSaver.h"
#include "guis/GuiMsgBox.h" #include "guis/GuiMsgBox.h"
#include "guis/GuiSettings.h" #include "guis/GuiSettings.h"
#include "guis/GuiScreensaverOptions.h" #include "guis/GuiScreensaverOptions.h"
@ -175,7 +176,16 @@ GuiMenu::GuiMenu(Window* window) : GuiComponent(window), mMenu(window, "MAIN MEN
auto move_carousel = std::make_shared<SwitchComponent>(mWindow); auto move_carousel = std::make_shared<SwitchComponent>(mWindow);
move_carousel->setState(Settings::getInstance()->getBool("MoveCarousel")); move_carousel->setState(Settings::getInstance()->getBool("MoveCarousel"));
s->addWithLabel("CAROUSEL TRANSITIONS", move_carousel); s->addWithLabel("CAROUSEL TRANSITIONS", move_carousel);
s->addSaveFunc([move_carousel] { Settings::getInstance()->setBool("MoveCarousel", move_carousel->getState()); }); s->addSaveFunc([move_carousel] {
if (move_carousel->getState()
&& !Settings::getInstance()->getBool("MoveCarousel")
&& PowerSaver::ps_instant == PowerSaver::getTimeout())
{
Settings::getInstance()->setString("PowerSaverMode", "default");
PowerSaver::init();
}
Settings::getInstance()->setBool("MoveCarousel", move_carousel->getState());
});
// transition style // transition style
auto transition_style = std::make_shared< OptionListComponent<std::string> >(mWindow, "TRANSITION STYLE", false); auto transition_style = std::make_shared< OptionListComponent<std::string> >(mWindow, "TRANSITION STYLE", false);
@ -186,7 +196,16 @@ GuiMenu::GuiMenu(Window* window) : GuiComponent(window), mMenu(window, "MAIN MEN
for(auto it = transitions.begin(); it != transitions.end(); it++) for(auto it = transitions.begin(); it != transitions.end(); it++)
transition_style->add(*it, *it, Settings::getInstance()->getString("TransitionStyle") == *it); transition_style->add(*it, *it, Settings::getInstance()->getString("TransitionStyle") == *it);
s->addWithLabel("TRANSITION STYLE", transition_style); s->addWithLabel("TRANSITION STYLE", transition_style);
s->addSaveFunc([transition_style] { Settings::getInstance()->setString("TransitionStyle", transition_style->getSelected()); }); s->addSaveFunc([transition_style] {
if (Settings::getInstance()->getString("TransitionStyle") == "instant"
&& transition_style->getSelected() != "instant"
&& PowerSaver::ps_instant == PowerSaver::getTimeout())
{
Settings::getInstance()->setString("PowerSaverMode", "default");
PowerSaver::init();
}
Settings::getInstance()->setString("TransitionStyle", transition_style->getSelected());
});
// theme set // theme set
auto themeSets = ThemeData::getThemeSets(); auto themeSets = ThemeData::getThemeSets();
@ -247,6 +266,7 @@ GuiMenu::GuiMenu(Window* window) : GuiComponent(window), mMenu(window, "MAIN MEN
addEntry("GAME COLLECTION SETTINGS", 0x777777FF, true, addEntry("GAME COLLECTION SETTINGS", 0x777777FF, true,
[this] { openCollectionSystemSettings(); [this] { openCollectionSystemSettings();
}); });
addEntry("OTHER SETTINGS", 0x777777FF, true, addEntry("OTHER SETTINGS", 0x777777FF, true,
[this] { [this] {
auto s = new GuiSettings(mWindow, "OTHER SETTINGS"); auto s = new GuiSettings(mWindow, "OTHER SETTINGS");
@ -257,6 +277,32 @@ GuiMenu::GuiMenu(Window* window) : GuiComponent(window), mMenu(window, "MAIN MEN
s->addWithLabel("VRAM LIMIT", max_vram); s->addWithLabel("VRAM LIMIT", max_vram);
s->addSaveFunc([max_vram] { Settings::getInstance()->setInt("MaxVRAM", (int)round(max_vram->getValue())); }); s->addSaveFunc([max_vram] { Settings::getInstance()->setInt("MaxVRAM", (int)round(max_vram->getValue())); });
// power saver
auto power_saver = std::make_shared< OptionListComponent<std::string> >(mWindow, "POWER SAVER MODES", false);
std::vector<std::string> modes;
modes.push_back("disabled");
modes.push_back("default");
modes.push_back("enhanced");
modes.push_back("instant");
for (auto it = modes.begin(); it != modes.end(); it++)
power_saver->add(*it, *it, Settings::getInstance()->getString("PowerSaverMode") == *it);
s->addWithLabel("POWER SAVER MODES", power_saver);
s->addSaveFunc([this, power_saver] {
if (Settings::getInstance()->getString("PowerSaverMode") != "instant" && power_saver->getSelected() == "instant"){
mWindow->pushGui(new GuiMsgBox(mWindow, "Setting Power Saver to Instant Mode disables Carousel transition and sets Transition Style to Instant. Would you like to continue?"
, "YES", [] {
Settings::getInstance()->setString("TransitionStyle", "instant");
Settings::getInstance()->setString("PowerSaverMode", "instant");
Settings::getInstance()->setBool("MoveCarousel", false);
PowerSaver::init();
}, "NO", nullptr)
);
} else {
Settings::getInstance()->setString("PowerSaverMode", power_saver->getSelected());
PowerSaver::init();
}
});
// gamelists // gamelists
auto save_gamelists = std::make_shared<SwitchComponent>(mWindow); auto save_gamelists = std::make_shared<SwitchComponent>(mWindow);
save_gamelists->setState(Settings::getInstance()->getBool("SaveGamelistsOnExit")); save_gamelists->setState(Settings::getInstance()->getBool("SaveGamelistsOnExit"));
@ -366,7 +412,7 @@ GuiMenu::GuiMenu(Window* window) : GuiComponent(window), mMenu(window, "MAIN MEN
}); });
mVersion.setFont(Font::get(FONT_SIZE_SMALL)); mVersion.setFont(Font::get(FONT_SIZE_SMALL));
mVersion.setColor(0xC6C6C6FF); mVersion.setColor(0x5E5E5EFF);
mVersion.setText("EMULATIONSTATION V" + strToUpper(PROGRAM_VERSION_STRING)); mVersion.setText("EMULATIONSTATION V" + strToUpper(PROGRAM_VERSION_STRING));
mVersion.setAlignment(ALIGN_CENTER); mVersion.setAlignment(ALIGN_CENTER);

View file

@ -3,6 +3,7 @@
#include "Log.h" #include "Log.h"
#include "views/ViewController.h" #include "views/ViewController.h"
#include "Gamelist.h" #include "Gamelist.h"
#include "PowerSaver.h"
#include "components/TextComponent.h" #include "components/TextComponent.h"
#include "components/ButtonComponent.h" #include "components/ButtonComponent.h"
@ -18,6 +19,7 @@ GuiScraperMulti::GuiScraperMulti(Window* window, const std::queue<ScraperSearchP
{ {
assert(mSearchQueue.size()); assert(mSearchQueue.size());
PowerSaver::setState(false);
addChild(&mBackground); addChild(&mBackground);
addChild(&mGrid); addChild(&mGrid);
@ -93,6 +95,7 @@ void GuiScraperMulti::doNextSearch()
{ {
if(mSearchQueue.empty()) if(mSearchQueue.empty())
{ {
PowerSaver::setState(true);
finish(); finish();
return; return;
} }

View file

@ -16,6 +16,7 @@
#include "Window.h" #include "Window.h"
#include "SystemScreenSaver.h" #include "SystemScreenSaver.h"
#include "EmulationStation.h" #include "EmulationStation.h"
#include "PowerSaver.h"
#include "Settings.h" #include "Settings.h"
#include "ScraperCmdLine.h" #include "ScraperCmdLine.h"
#include <sstream> #include <sstream>
@ -224,6 +225,7 @@ int main(int argc, char* argv[])
Window window; Window window;
SystemScreenSaver screensaver(&window); SystemScreenSaver screensaver(&window);
PowerSaver::init();
ViewController::init(&window); ViewController::init(&window);
CollectionSystemManager::init(&window); CollectionSystemManager::init(&window);
window.pushGui(ViewController::get()); window.pushGui(ViewController::get());
@ -293,31 +295,50 @@ int main(int argc, char* argv[])
SDL_JoystickEventState(SDL_ENABLE); SDL_JoystickEventState(SDL_ENABLE);
int lastTime = SDL_GetTicks(); int lastTime = SDL_GetTicks();
int ps_time = SDL_GetTicks();
bool running = true; bool running = true;
bool ps_standby = false;
// assuming screensaver timeout is not updated regularly.
int timeout = (unsigned int) Settings::getInstance()->getInt("ScreenSaverTime");
while(running) while(running)
{ {
SDL_Event event; SDL_Event event;
while(SDL_PollEvent(&event)) bool ps_standby = PowerSaver::getState() && SDL_GetTicks() - ps_time > PowerSaver::getTimeout();
if(ps_standby ? SDL_WaitEventTimeout(&event, timeout - 100) : SDL_PollEvent(&event))
{ {
switch(event.type) do
{ {
case SDL_JOYHATMOTION: switch(event.type)
case SDL_JOYBUTTONDOWN: {
case SDL_JOYBUTTONUP: case SDL_JOYHATMOTION:
case SDL_KEYDOWN: case SDL_JOYBUTTONDOWN:
case SDL_KEYUP: case SDL_JOYBUTTONUP:
case SDL_JOYAXISMOTION: case SDL_KEYDOWN:
case SDL_TEXTINPUT: case SDL_KEYUP:
case SDL_TEXTEDITING: case SDL_JOYAXISMOTION:
case SDL_JOYDEVICEADDED: case SDL_TEXTINPUT:
case SDL_JOYDEVICEREMOVED: case SDL_TEXTEDITING:
InputManager::getInstance()->parseEvent(event, &window); case SDL_JOYDEVICEADDED:
break; case SDL_JOYDEVICEREMOVED:
case SDL_QUIT: InputManager::getInstance()->parseEvent(event, &window);
running = false; break;
break; case SDL_QUIT:
} running = false;
break;
}
} while(SDL_PollEvent(&event));
// triggered if exiting from SDL_WaitEvent
if (ps_standby)
// show as if continuing from last event
lastTime = SDL_GetTicks();
// reset counter
ps_time = SDL_GetTicks();
} }
if(window.isSleeping()) if(window.isSleeping())
@ -331,8 +352,8 @@ int main(int argc, char* argv[])
int deltaTime = curTime - lastTime; int deltaTime = curTime - lastTime;
lastTime = curTime; lastTime = curTime;
// cap deltaTime at 1000 // cap deltaTime
if(deltaTime > 1000 || deltaTime < 0) if(deltaTime > timeout || deltaTime < 0)
deltaTime = 1000; deltaTime = 1000;
window.update(deltaTime); window.update(deltaTime);

View file

@ -5,6 +5,7 @@
#include "Window.h" #include "Window.h"
#include "views/ViewController.h" #include "views/ViewController.h"
#include "animations/LambdaAnimation.h" #include "animations/LambdaAnimation.h"
#include "PowerSaver.h"
#include "SystemData.h" #include "SystemData.h"
#include "Settings.h" #include "Settings.h"
#include "Util.h" #include "Util.h"
@ -213,13 +214,15 @@ void SystemView::onCursorChanged(const CursorState& state)
cancelAnimation(1); cancelAnimation(1);
cancelAnimation(2); cancelAnimation(2);
std::string transition_style = Settings::getInstance()->getString("TransitionStyle");
bool goFast = transition_style == "instant";
const float infoStartOpacity = mSystemInfo.getOpacity() / 255.f; const float infoStartOpacity = mSystemInfo.getOpacity() / 255.f;
Animation* infoFadeOut = new LambdaAnimation( Animation* infoFadeOut = new LambdaAnimation(
[infoStartOpacity, this] (float t) [infoStartOpacity, this] (float t)
{ {
mSystemInfo.setOpacity((unsigned char)(lerp<float>(infoStartOpacity, 0.f, t) * 255)); mSystemInfo.setOpacity((unsigned char)(lerp<float>(infoStartOpacity, 0.f, t) * 255));
}, (int)(infoStartOpacity * 150)); }, (int)(infoStartOpacity * (goFast ? 10 : 150)));
unsigned int gameCount = getSelected()->getDisplayedGameCount(); unsigned int gameCount = getSelected()->getDisplayedGameCount();
@ -229,25 +232,20 @@ void SystemView::onCursorChanged(const CursorState& state)
if (!getSelected()->isGameSystem()) if (!getSelected()->isGameSystem())
ss << "CONFIGURATION"; ss << "CONFIGURATION";
// only display a game count if there are at least 2 games else
else if(gameCount > 1)
ss << gameCount << " GAMES AVAILABLE"; ss << gameCount << " GAMES AVAILABLE";
mSystemInfo.setText(ss.str()); mSystemInfo.setText(ss.str());
}, false, 1); }, false, 1);
// only display a game count if there are at least 2 games Animation* infoFadeIn = new LambdaAnimation(
if(gameCount > 1) [this](float t)
{ {
Animation* infoFadeIn = new LambdaAnimation( mSystemInfo.setOpacity((unsigned char)(lerp<float>(0.f, 1.f, t) * 255));
[this](float t) }, goFast ? 10 : 300);
{
mSystemInfo.setOpacity((unsigned char)(lerp<float>(0.f, 1.f, t) * 255));
}, 300);
// wait 600ms to fade in // wait 600ms to fade in
setAnimation(infoFadeIn, 2000, nullptr, false, 2); setAnimation(infoFadeIn, goFast ? 0 : 2000, nullptr, false, 2);
}
// no need to animate transition, we're not going anywhere (probably mEntries.size() == 1) // no need to animate transition, we're not going anywhere (probably mEntries.size() == 1)
if(endPos == mCamOffset && endPos == mExtrasCamOffset) if(endPos == mCamOffset && endPos == mExtrasCamOffset)
@ -255,7 +253,6 @@ void SystemView::onCursorChanged(const CursorState& state)
Animation* anim; Animation* anim;
bool move_carousel = Settings::getInstance()->getBool("MoveCarousel"); bool move_carousel = Settings::getInstance()->getBool("MoveCarousel");
std::string transition_style = Settings::getInstance()->getString("TransitionStyle");
if(transition_style == "fade") if(transition_style == "fade")
{ {
float startExtrasFade = mExtrasFadeOpacity; float startExtrasFade = mExtrasFadeOpacity;

View file

@ -2,6 +2,7 @@
#include "Log.h" #include "Log.h"
#include "SystemData.h" #include "SystemData.h"
#include "Settings.h" #include "Settings.h"
#include "PowerSaver.h"
#include "views/gamelist/BasicGameListView.h" #include "views/gamelist/BasicGameListView.h"
#include "views/gamelist/DetailedGameListView.h" #include "views/gamelist/DetailedGameListView.h"
@ -71,6 +72,7 @@ void ViewController::goToSystemView(SystemData* system)
systemList->goToSystem(system, false); systemList->goToSystem(system, false);
mCurrentView = systemList; mCurrentView = systemList;
PowerSaver::setState(true);
playViewTransition(); playViewTransition();
} }

View file

@ -11,6 +11,7 @@ set(CORE_HEADERS
${CMAKE_CURRENT_SOURCE_DIR}/src/InputManager.h ${CMAKE_CURRENT_SOURCE_DIR}/src/InputManager.h
${CMAKE_CURRENT_SOURCE_DIR}/src/Log.h ${CMAKE_CURRENT_SOURCE_DIR}/src/Log.h
${CMAKE_CURRENT_SOURCE_DIR}/src/platform.h ${CMAKE_CURRENT_SOURCE_DIR}/src/platform.h
${CMAKE_CURRENT_SOURCE_DIR}/src/PowerSaver.h
${CMAKE_CURRENT_SOURCE_DIR}/src/Renderer.h ${CMAKE_CURRENT_SOURCE_DIR}/src/Renderer.h
${CMAKE_CURRENT_SOURCE_DIR}/src/Settings.h ${CMAKE_CURRENT_SOURCE_DIR}/src/Settings.h
${CMAKE_CURRENT_SOURCE_DIR}/src/Sound.h ${CMAKE_CURRENT_SOURCE_DIR}/src/Sound.h
@ -73,6 +74,7 @@ set(CORE_SOURCES
${CMAKE_CURRENT_SOURCE_DIR}/src/InputManager.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/InputManager.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/Log.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/Log.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/platform.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/platform.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/PowerSaver.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/Renderer_draw_gl.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/Renderer_draw_gl.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/Renderer_init_sdlgl.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/Renderer_init_sdlgl.cpp
${CMAKE_CURRENT_SOURCE_DIR}/src/Settings.cpp ${CMAKE_CURRENT_SOURCE_DIR}/src/Settings.cpp

View file

@ -0,0 +1,44 @@
#include "PowerSaver.h"
#include "Settings.h"
#include <string.h>
bool PowerSaver::mState = true;
int PowerSaver::mTimeout = PowerSaver::ps_default;
void PowerSaver::init(bool state)
{
setState(true);
updateTimeout();
}
int PowerSaver::getTimeout()
{
return mTimeout;
}
void PowerSaver::updateTimeout()
{
std::string mode = Settings::getInstance()->getString("PowerSaverMode");
if (mode == "disabled") {
mTimeout = ps_disabled;
} else if (mode == "instant") {
mTimeout = ps_instant;
} else if (mode == "enhanced") {
mTimeout = ps_enhanced;
} else { // default
mTimeout = ps_default;
}
}
bool PowerSaver::getState()
{
return mState;
}
void PowerSaver::setState(bool state)
{
bool ps_enabled = Settings::getInstance()->getString("PowerSaverMode") != "disabled";
mState = ps_enabled && state;
}

17
es-core/src/PowerSaver.h Normal file
View file

@ -0,0 +1,17 @@
class PowerSaver
{
public:
enum ps_state : int { ps_disabled = -1, ps_instant = 200, ps_enhanced = 3000, ps_default = 10000 };
static void init(bool state = true);
static int getTimeout();
static void updateTimeout();
static bool getState();
static void setState(bool state);
private:
static bool mState;
static int mTimeout;
};

View file

@ -81,6 +81,7 @@ void Settings::setDefaults()
mBoolMap["ScreenSaverControls"] = true; mBoolMap["ScreenSaverControls"] = true;
mStringMap["ScreenSaverGameInfo"] = "never"; mStringMap["ScreenSaverGameInfo"] = "never";
mBoolMap["StretchVideoOnScreenSaver"] = false; mBoolMap["StretchVideoOnScreenSaver"] = false;
mStringMap["PowerSaverMode"] = "default";
// This setting only applies to raspberry pi but set it for all platforms so // This setting only applies to raspberry pi but set it for all platforms so
// we don't get a warning if we encounter it on a different platform // we don't get a warning if we encounter it on a different platform

View file

@ -2,8 +2,8 @@
#include "Renderer.h" #include "Renderer.h"
#include "Log.h" #include "Log.h"
#define AUTO_SCROLL_RESET_DELAY 10000 // ms to reset to top after we reach the bottom #define AUTO_SCROLL_RESET_DELAY 3000 // ms to reset to top after we reach the bottom
#define AUTO_SCROLL_DELAY 8000 // ms to wait before we start to scroll #define AUTO_SCROLL_DELAY 1000 // ms to wait before we start to scroll
#define AUTO_SCROLL_SPEED 50 // ms between scrolls #define AUTO_SCROLL_SPEED 50 // ms between scrolls
ScrollableContainer::ScrollableContainer(Window* window) : GuiComponent(window), ScrollableContainer::ScrollableContainer(Window* window) : GuiComponent(window),

View file

@ -3,11 +3,13 @@
#include "ThemeData.h" #include "ThemeData.h"
#include "Util.h" #include "Util.h"
#include "Settings.h" #include "Settings.h"
#include "PowerSaver.h"
#ifdef WIN32 #ifdef WIN32
#include <codecvt> #include <codecvt>
#endif #endif
libvlc_instance_t* VideoVlcComponent::mVLC = NULL; libvlc_instance_t* VideoVlcComponent::mVLC = NULL;
// VLC prepares to render a video frame. // VLC prepares to render a video frame.
static void *lock(void *data, void **p_pixels) { static void *lock(void *data, void **p_pixels) {
@ -289,7 +291,7 @@ void VideoVlcComponent::startVideo()
mMedia = libvlc_media_new_path(mVLC, path.c_str()); mMedia = libvlc_media_new_path(mVLC, path.c_str());
if (mMedia) if (mMedia)
{ {
unsigned track_count; unsigned track_count;
// Get the media metadata so we can find the aspect ratio // Get the media metadata so we can find the aspect ratio
libvlc_media_parse(mMedia); libvlc_media_parse(mMedia);
libvlc_media_track_t** tracks; libvlc_media_track_t** tracks;
@ -328,6 +330,7 @@ void VideoVlcComponent::startVideo()
} }
} }
#endif #endif
PowerSaver::setState(false);
setupContext(); setupContext();
// Setup the media player // Setup the media player
@ -358,6 +361,7 @@ void VideoVlcComponent::stopVideo()
// Release the media player so it stops calling back to us // Release the media player so it stops calling back to us
if (mMediaPlayer) if (mMediaPlayer)
{ {
PowerSaver::setState(true);
libvlc_media_player_stop(mMediaPlayer); libvlc_media_player_stop(mMediaPlayer);
libvlc_media_player_release(mMediaPlayer); libvlc_media_player_release(mMediaPlayer);
libvlc_media_release(mMedia); libvlc_media_release(mMedia);