diff --git a/Package/Environment/Common/Layouts/Default 16x9/Age.otf b/Package/Environment/Common/Layouts/Default 16x9/Age.otf
deleted file mode 100644
index 5d76781..0000000
Binary files a/Package/Environment/Common/Layouts/Default 16x9/Age.otf and /dev/null differ
diff --git a/Package/Environment/Common/Layouts/Default 16x9/Lato-Black.ttf b/Package/Environment/Common/Layouts/Default 16x9/Lato-Black.ttf
new file mode 100644
index 0000000..a87109f
Binary files /dev/null and b/Package/Environment/Common/Layouts/Default 16x9/Lato-Black.ttf differ
diff --git a/Package/Environment/Common/Layouts/Default 16x9/Layout.xml b/Package/Environment/Common/Layouts/Default 16x9/Layout.xml
index ccaedaf..10be7ab 100644
--- a/Package/Environment/Common/Layouts/Default 16x9/Layout.xml
+++ b/Package/Environment/Common/Layouts/Default 16x9/Layout.xml
@@ -1,14 +1,77 @@
-
-
-
-
+
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
diff --git a/Package/Environment/Common/Layouts/Default 16x9/Splash.xml b/Package/Environment/Common/Layouts/Default 16x9/Splash.xml
new file mode 100644
index 0000000..71953ce
--- /dev/null
+++ b/Package/Environment/Common/Layouts/Default 16x9/Splash.xml
@@ -0,0 +1,31 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Package/Environment/Common/Layouts/Default 16x9/background.png b/Package/Environment/Common/Layouts/Default 16x9/background.png
deleted file mode 100644
index 5d5f7e6..0000000
Binary files a/Package/Environment/Common/Layouts/Default 16x9/background.png and /dev/null differ
diff --git a/Package/Environment/Common/Layouts/Default 16x9/square.png b/Package/Environment/Common/Layouts/Default 16x9/square.png
deleted file mode 100644
index de7cb82..0000000
Binary files a/Package/Environment/Common/Layouts/Default 16x9/square.png and /dev/null differ
diff --git a/Package/Environment/Common/Layouts/Splash/Layout.xml b/Package/Environment/Common/Layouts/Splash/Layout.xml
new file mode 100644
index 0000000..71953ce
--- /dev/null
+++ b/Package/Environment/Common/Layouts/Splash/Layout.xml
@@ -0,0 +1,31 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Package/Environment/Common/Layouts/Splash/logo.png b/Package/Environment/Common/Layouts/Splash/logo.png
new file mode 100644
index 0000000..54bd5ac
Binary files /dev/null and b/Package/Environment/Common/Layouts/Splash/logo.png differ
diff --git a/RetroFE/Source/Graphics/Page.cpp b/RetroFE/Source/Graphics/Page.cpp
index 7fd6d4f..e079a9a 100644
--- a/RetroFE/Source/Graphics/Page.cpp
+++ b/RetroFE/Source/Graphics/Page.cpp
@@ -97,7 +97,11 @@ void Page::SetMenu(ScrollingList *s)
{
// todo: delete the old menu
Menu = s;
- Menu->AddComponentForNotifications(this);
+
+ if(Menu)
+ {
+ Menu->AddComponentForNotifications(this);
+ }
}
bool Page::AddComponent(Component *c)
@@ -127,7 +131,7 @@ bool Page::IsIdle()
{
bool idle = true;
- if(!Menu->IsIdle())
+ if(Menu && !Menu->IsIdle())
{
idle = false;
}
@@ -146,7 +150,7 @@ bool Page::IsIdle()
bool Page::IsHidden()
{
- bool hidden = Menu->IsHidden();
+ bool hidden = (!Menu || Menu->IsHidden());
for(unsigned int i = 0; hidden && i < NUM_LAYERS; ++i)
{
@@ -161,7 +165,10 @@ bool Page::IsHidden()
void Page::Start()
{
- Menu->TriggerEnterEvent();
+ if(Menu)
+ {
+ Menu->TriggerEnterEvent();
+ }
if(LoadSoundChunk)
{
@@ -179,8 +186,10 @@ void Page::Start()
void Page::Stop()
{
- Menu->TriggerExitEvent();
-
+ if(Menu)
+ {
+ Menu->TriggerExitEvent();
+ }
if(UnloadSoundChunk)
{
UnloadSoundChunk->Play();
@@ -204,7 +213,10 @@ Item *Page::GetSelectedItem()
void Page::RemoveSelectedItem()
{
//todo: change method to RemoveItem() and pass in SelectedItem
- Menu->RemoveSelectedItem();
+ if(Menu)
+ {
+ Menu->RemoveSelectedItem();
+ }
SelectedItem = NULL;
}
@@ -216,8 +228,11 @@ void Page::Highlight()
if(item)
{
- Menu->TriggerHighlightEvent(item);
- Menu->SetScrollActive(ScrollActive);
+ if(Menu)
+ {
+ Menu->TriggerHighlightEvent(item);
+ Menu->SetScrollActive(ScrollActive);
+ }
for(unsigned int i = 0; i < NUM_LAYERS; ++i)
{
@@ -252,18 +267,24 @@ void Page::SetScrolling(ScrollDirection direction)
break;
}
- Menu->SetScrollDirection(menuDirection);
+ if(Menu)
+ {
+ Menu->SetScrollDirection(menuDirection);
+ }
}
void Page::PageScroll(ScrollDirection direction)
{
- if(direction == ScrollDirectionForward)
+ if(Menu)
{
- Menu->PageDown();
- }
- if(direction == ScrollDirectionBack)
- {
- Menu->PageUp();
+ if(direction == ScrollDirectionForward)
+ {
+ Menu->PageDown();
+ }
+ if(direction == ScrollDirectionBack)
+ {
+ Menu->PageUp();
+ }
}
}
@@ -271,16 +292,20 @@ void Page::PageScroll(ScrollDirection direction)
void Page::SetItems(std::vector- *items)
{
std::vector *sprites = ComponentItemBindingBuilder::BuildCollectionItems(items);
-
- Menu->SetItems(sprites);
+ if(Menu)
+ {
+ Menu->SetItems(sprites);
+ }
}
void Page::Update(float dt)
{
- Menu->Update(dt);
-
+ if(Menu)
+ {
+ Menu->Update(dt);
+ }
if(SelectedItemChanged && !HasSoundedWhenActive && HighlightSoundChunk)
{
// skip the first sound being played (as it is part of the on-enter)
@@ -317,7 +342,10 @@ void Page::Draw()
(*it)->Draw();
}
- Menu->Draw(i);
+ if(Menu)
+ {
+ Menu->Draw(i);
+ }
}
}
@@ -329,7 +357,10 @@ const std::string& Page::GetCollectionName() const
void Page::FreeGraphicsMemory()
{
Logger::Write(Logger::ZONE_DEBUG, "Page", "Free");
- Menu->FreeGraphicsMemory();
+ if(Menu)
+ {
+ Menu->FreeGraphicsMemory();
+ }
if(LoadSoundChunk) LoadSoundChunk->Free();
if(UnloadSoundChunk) UnloadSoundChunk->Free();
@@ -349,7 +380,10 @@ void Page::AllocateGraphicsMemory()
{
FirstSoundPlayed = false;
Logger::Write(Logger::ZONE_DEBUG, "Page", "Allocating graphics memory");
- Menu->AllocateGraphicsMemory();
+ if(Menu)
+ {
+ Menu->AllocateGraphicsMemory();
+ }
if(LoadSoundChunk) LoadSoundChunk->Allocate();
if(UnloadSoundChunk) UnloadSoundChunk->Allocate();
@@ -368,7 +402,10 @@ void Page::AllocateGraphicsMemory()
void Page::LaunchEnter()
{
- Menu->LaunchEnter();
+ if(Menu)
+ {
+ Menu->LaunchEnter();
+ }
for(unsigned int i = 0; i < NUM_LAYERS; ++i)
{
@@ -381,7 +418,10 @@ void Page::LaunchEnter()
void Page::LaunchExit()
{
- Menu->LaunchExit();
+ if(Menu)
+ {
+ Menu->LaunchExit();
+ }
for(unsigned int i = 0; i < NUM_LAYERS; ++i)
{
diff --git a/RetroFE/Source/Graphics/PageBuilder.cpp b/RetroFE/Source/Graphics/PageBuilder.cpp
index 3c5d7a8..28a8e9c 100644
--- a/RetroFE/Source/Graphics/PageBuilder.cpp
+++ b/RetroFE/Source/Graphics/PageBuilder.cpp
@@ -229,6 +229,8 @@ Page *PageBuilder::BuildPage()
Logger::Write(Logger::ZONE_DEBUG, "Layout", "Created page");
}
+ Logger::Write(Logger::ZONE_INFO, "Layout", "Initialized");
+
return page;
}
@@ -307,14 +309,12 @@ bool PageBuilder::BuildComponents(xml_node<> *layout, Page *page)
{
xml_node<> *menuXml = layout->first_node("menu");
- if(!menuXml)
+ if(menuXml)
{
- Logger::Write(Logger::ZONE_ERROR, "Layout", "Missing menu tag");
- return false;
+ ScrollingList *scrollingList = BuildMenu(menuXml);
+ page->SetMenu(scrollingList);
}
- ScrollingList *scrollingList = BuildMenu(menuXml);
- page->SetMenu(scrollingList);
for(xml_node<> *componentXml = layout->first_node("container"); componentXml; componentXml = componentXml->next_sibling("container"))
{
diff --git a/RetroFE/Source/Main.cpp b/RetroFE/Source/Main.cpp
index e0bb07d..204a52c 100644
--- a/RetroFE/Source/Main.cpp
+++ b/RetroFE/Source/Main.cpp
@@ -18,7 +18,6 @@
#include "Database/CollectionDatabase.h"
#include "Collection/CollectionInfoBuilder.h"
#include "Collection/CollectionInfo.h"
-#include "Database/DB.h"
#include "Database/MamelistMetadata.h"
#include "Execute/Launcher.h"
#include "Utility/Log.h"
@@ -49,26 +48,9 @@ int main(int argc, char *argv[])
return -1;
}
- DB db(Configuration::GetAbsolutePath() + "/cache.db");
+ RetroFE p(config);
- if(!db.Initialize())
- {
- return -1;
- }
-
-
- CollectionDatabase *cdb = InitializeCollectionDatabase(db, config);
- if(!cdb)
- {
- return -1;
- }
-
- RetroFE p(*cdb, config);
-
- if(p.Initialize())
- {
- p.Run();
- }
+ p.Run();
p.DeInitialize();
@@ -184,24 +166,3 @@ bool StartLogging()
return true;
}
-CollectionDatabase *InitializeCollectionDatabase(DB &db, Configuration &config)
-{
- CollectionDatabase *cdb = NULL;
- std::string dbFile = (Configuration::GetAbsolutePath() + "/cache.db");
- std::ifstream infile(dbFile.c_str());
-
- cdb = new CollectionDatabase(db, config);
-
- if(!cdb->Initialize())
- {
- delete cdb;
- cdb = NULL;
- }
- else if(!cdb->Import())
- {
- delete cdb;
- cdb = NULL;
- }
-
- return cdb;
-}
\ No newline at end of file
diff --git a/RetroFE/Source/RetroFE.cpp b/RetroFE/Source/RetroFE.cpp
index 6a80110..40d27eb 100644
--- a/RetroFE/Source/RetroFE.cpp
+++ b/RetroFE/Source/RetroFE.cpp
@@ -33,11 +33,15 @@
#ifdef WIN32
#include
#include
+#include
#endif
-RetroFE::RetroFE(CollectionDatabase &db, Configuration &c)
- : Config(c)
- , CollectionDB(db)
+RetroFE::RetroFE(Configuration &c)
+ : Initialized(false)
+ , InitializeThread(NULL)
+ , Config(c)
+ , Db(NULL)
+ , CollectionDB(NULL)
, Input(Config)
, KeyInputDisable(0)
, CurrentTime(0)
@@ -49,41 +53,88 @@ RetroFE::~RetroFE()
DeInitialize();
}
+CollectionDatabase *RetroFE::InitializeCollectionDatabase(DB &db, Configuration &config)
+{
+ CollectionDatabase *cdb = NULL;
+
+ std::string dbFile = (Configuration::GetAbsolutePath() + "/cache.db");
+ std::ifstream infile(dbFile.c_str());
+
+ cdb = new CollectionDatabase(db, config);
+
+ if(!cdb->Initialize())
+ {
+ delete cdb;
+ cdb = NULL;
+ }
+ else if(!cdb->Import())
+ {
+ delete cdb;
+ cdb = NULL;
+ }
+
+ return cdb;
+}
+
void RetroFE::Render()
{
SDL_LockMutex(SDL::GetMutex());
SDL_SetRenderDrawColor(SDL::GetRenderer(), 0x0, 0x0, 0x00, 0xFF);
SDL_RenderClear(SDL::GetRenderer());
- Page *page = PageChain.back();
-
- if(page)
+ if(PageChain.size() > 0)
{
- page->Draw();
- }
+ Page *page = PageChain.back();
+ if(page)
+ {
+ page->Draw();
+ }
+ }
SDL_RenderPresent(SDL::GetRenderer());
SDL_UnlockMutex(SDL::GetMutex());
}
-bool RetroFE::Initialize()
+int RetroFE::Initialize(void *context)
{
+ int retVal = 0;
+ RetroFE *instance = static_cast(context);
+
Logger::Write(Logger::ZONE_INFO, "RetroFE", "Initializing");
-
- if(!Input.Initialize()) return false;
- if(!SDL::Initialize(Config)) return false;
- FC.Initialize();
-
bool videoEnable = true;
int videoLoop = 0;
- Config.GetProperty("videoEnable", videoEnable);
- Config.GetProperty("videoLoop", videoLoop);
+ if(!instance->Input.Initialize()) return -1;
+
+ instance->Db = new DB(Configuration::GetAbsolutePath() + "/cache.db");
+
+ if(!instance->Db->Initialize())
+ {
+ Logger::Write(Logger::ZONE_ERROR, "RetroFE", "Could not initialize database");
+ return -1;
+ }
+
+
+ instance->CollectionDB = instance->InitializeCollectionDatabase(*instance->Db, instance->Config);
+
+ if(!instance->CollectionDB)
+ {
+ Logger::Write(Logger::ZONE_ERROR, "RetroFE", "Could not initialize CollectionDB!");
+ delete instance->Db;
+ return -1;
+ }
+
+
+ instance->FC.Initialize();
+
+ instance->Config.GetProperty("videoEnable", videoEnable);
+ instance->Config.GetProperty("videoLoop", videoLoop);
VideoFactory::SetEnabled(videoEnable);
VideoFactory::SetNumLoops(videoLoop);
- return true;
+ instance->Initialized = true;
+ return 0;
}
void RetroFE::LaunchEnter()
@@ -149,32 +200,59 @@ bool RetroFE::DeInitialize()
delete page;
PageChain.pop_back();
}
+ if(Db)
+ {
+ delete Db;
+ Db = NULL;
+ }
+ if(CollectionDB)
+ {
+ delete CollectionDB;
+ Db = NULL;
+ }
+ Initialized = false;
//todo: handle video deallocation
return retVal;
}
void RetroFE::Run()
{
+ if(!SDL::Initialize(Config)) return;
+
+ InitializeThread = SDL_CreateThread(Initialize, "RetroFEInit", (void *)this);
+
+ if(!InitializeThread)
+ {
+ Logger::Write(Logger::ZONE_INFO, "RetroFE", "Could not initialize RetroFE");
+ return;
+ }
+
int attractModeTime = 0;
std::string firstCollection = "Main";
bool running = true;
Item *nextPageItem = NULL;
bool adminMode = false;
- RETROFE_STATE state = RETROFE_IDLE;
+ RETROFE_STATE state = RETROFE_NEW;
Config.GetProperty("attractModeTime", attractModeTime);
Config.GetProperty("firstCollection", firstCollection);
Attract.SetIdleTime(static_cast(attractModeTime));
- LoadPage(firstCollection);
+
+ int initializeStatus = 0;
+
+ // load the initial splash screen, unload it once it is complete
+ Page * page = LoadSplashPage();
+ bool splashMode = true;
+
+ Launcher l(*this, Config);
while (running)
{
float lastTime = 0;
float deltaTime = 0;
- Page *page = PageChain.back();
- Launcher l(*this, Config);
+ page = PageChain.back();
if(!page)
{
@@ -182,12 +260,22 @@ void RetroFE::Run()
running = false;
break;
}
-
// todo: This could be transformed to use the state design pattern.
switch(state)
{
case RETROFE_IDLE:
- state = ProcessUserInput(page);
+ if(page && !splashMode)
+ {
+ state = ProcessUserInput(page);
+ }
+
+ if(Initialized && splashMode)
+ {
+ SDL_WaitThread(InitializeThread, &initializeStatus);
+ state = RETROFE_BACK_WAIT;
+ page->Stop();
+ }
+
break;
case RETROFE_NEXT_PAGE_REQUEST:
@@ -219,7 +307,8 @@ void RetroFE::Run()
PageChain.pop_back();
delete page;
- page = PageChain.back();
+ page = (splashMode) ? LoadPage(firstCollection) : PageChain.back();
+ splashMode = false;
CurrentTime = (float)SDL_GetTicks() / 1000;
page->AllocateGraphicsMemory();
@@ -267,12 +356,16 @@ void RetroFE::Run()
SDL_Delay(static_cast(sleepTime));
}
- Attract.Update(deltaTime, *page);
+ if(page)
+ {
+ Attract.Update(deltaTime, *page);
+ page->Update(deltaTime);
+ }
- page->Update(deltaTime);
Render();
}
}
+
}
@@ -372,6 +465,30 @@ RetroFE::RETROFE_STATE RetroFE::ProcessUserInput(Page *page)
}
+void RetroFE::WaitToInitialize()
+{
+ Logger::Write(Logger::ZONE_INFO, "RetroFE", "Loading splash screen");
+
+ PageBuilder pb("splash", "", Config, &FC);
+ Page * page = pb.BuildPage();
+
+ while(!Initialized)
+ {
+ SDL_SetRenderDrawColor(SDL::GetRenderer(), 0x0, 0x0, 0x00, 0xFF);
+ SDL_RenderClear(SDL::GetRenderer());
+// image->Draw();
+ //todo: decouple page from a collection
+ page->Draw();
+ SDL_RenderPresent(SDL::GetRenderer());
+
+ SDL_Delay(2000);
+ }
+
+ int status = 0;
+ delete page;
+ SDL_WaitThread(InitializeThread, &status);
+}
+
Page *RetroFE::LoadPage(std::string collectionName)
{
@@ -405,14 +522,27 @@ Page *RetroFE::LoadPage(std::string collectionName)
return page;
}
+Page *RetroFE::LoadSplashPage()
+{
+ PageBuilder pb("splash", "", Config, &FC);
+ std::vector
- *coll = new std::vector
- ();
+ Page * page = pb.BuildPage();
+ page->SetItems(coll);
+ page->Start();
+ PageChain.push_back(page);
+
+ return page;
+}
+
std::vector
- *RetroFE::GetCollection(std::string collectionName)
{
- std::vector
- *collection = new std::vector
- (); // the page will deallocate this once its done
+ // the page will deallocate this once its done
+ std::vector
- *collection = new std::vector
- ();
MenuParser mp;
- mp.GetMenuItems(&CollectionDB, collectionName, *collection);
- CollectionDB.GetCollection(collectionName, *collection);
+ mp.GetMenuItems(CollectionDB, collectionName, *collection);
+ CollectionDB->GetCollection(collectionName, *collection);
if(collection->size() == 0)
{
diff --git a/RetroFE/Source/RetroFE.h b/RetroFE/Source/RetroFE.h
index 1e4a54a..c2054f1 100644
--- a/RetroFE/Source/RetroFE.h
+++ b/RetroFE/Source/RetroFE.h
@@ -5,6 +5,7 @@
#include "Collection/Item.h"
#include "Control/UserInput.h"
+#include "Database/DB.h"
#include "Execute/AttractMode.h"
#include "Graphics/FontCache.h"
#include "Video/IVideo.h"
@@ -19,9 +20,8 @@ class Page;
class RetroFE
{
public:
- RetroFE(CollectionDatabase &db, Configuration &c);
+ RetroFE(Configuration &c);
virtual ~RetroFE();
- bool Initialize();
bool DeInitialize();
void Run();
void FreeGraphicsMemory();
@@ -29,6 +29,10 @@ public:
void LaunchEnter();
void LaunchExit();
private:
+ bool Initialized;
+ SDL_Thread *InitializeThread;
+ static int Initialize(void *context);
+
enum RETROFE_STATE
{
RETROFE_IDLE,
@@ -43,15 +47,19 @@ private:
};
void Render();
+ CollectionDatabase *InitializeCollectionDatabase(DB &db, Configuration &config);
bool Back(bool &exit);
void Quit();
+ void WaitToInitialize();
Page *LoadPage(std::string collectionName);
+ Page *LoadSplashPage();
RETROFE_STATE ProcessUserInput(Page *page);
void Update(float dt, bool scrollActive);
std::string GetLayout(std::string collectionName);
std::vector
- *GetCollection(std::string collectionName);
Configuration &Config;
- CollectionDatabase &CollectionDB;
+ DB *Db;
+ CollectionDatabase *CollectionDB;
UserInput Input;
std::list PageChain;
float KeyInputDisable;