Merge branch 'master' into inventoryGUI

Conflicts:
	apps/openmw/CMakeLists.txt
	apps/openmw/mwgui/window_manager.cpp
	apps/openmw/mwgui/window_manager.hpp
	files/mygui/core.xml
actorid
scrawl 13 years ago
commit a1b86acc38

@ -103,6 +103,7 @@ set(OENGINE_OGRE
${LIBDIR}/openengine/ogre/mouselook.cpp
${LIBDIR}/openengine/ogre/fader.cpp
${LIBDIR}/openengine/ogre/imagerotate.cpp
${LIBDIR}/openengine/ogre/atlas.cpp
)
set(OENGINE_GUI
${LIBDIR}/openengine/gui/events.cpp

@ -0,0 +1,10 @@
Dongle's Oblivion Daedric font set
http://www.uesp.net/wiki/Lore:Daedric_Alphabet#Daedric_Font
---------------------------------------------------
This was done entirely as a personal project. Bethesda Softworks graciously granted me the permission for it. I am not connected with them in any way.
You may freely use these fonts to create anything you'd like. You may re-distribute the fonts freely, over the Internet, or by any other means. Always keep the .zip file intact, and this read me included.
Please do not modify and redistribute the fonts without my permission.
You may NOT sell any of these fonts under any circumstances. This includes putting them on compilation font CDs for sale, putting them in a "members only" pay-area of a website, or any other means of financial gain connected in ANY way with the redistribution of any of these fonts.
You have my permission to create and sell any artwork made with these fonts, however you may need to contact Bethesda Softworks before doing so.

@ -24,8 +24,9 @@ add_openmw_dir (mwinput
add_openmw_dir (mwgui
layouts text_input widgets race class birth review window_manager console dialogue
dialogue_history window_base stats_window messagebox journalwindow charactercreation container
map_window window_pinnable_base cursorreplace inventorywindow tooltips itemwidget
dialogue_history window_base stats_window messagebox journalwindow charactercreation
map_window window_pinnable_base cursorreplace tooltips scrollwindow bookwindow list
formatting itemwidget inventorywindow container
)
add_openmw_dir (mwdialogue
@ -46,7 +47,7 @@ add_openmw_dir (mwsound
add_openmw_dir (mwworld
refdata world physicssystem scene globals class action nullaction actionteleport
containerstore actiontalk actiontake manualref player cellfunctors
cells localscripts customdata weather inventorystore ptr actionopen
cells localscripts customdata weather inventorystore ptr actionopen actionread
)
add_openmw_dir (mwclass

@ -194,6 +194,12 @@ void OMW::Engine::addResourcesDirectory (const boost::filesystem::path& path)
Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME, true);
}
void OMW::Engine::addZipResource (const boost::filesystem::path& path)
{
mOgre->getRoot()->addResourceLocation (path.string(), "Zip",
Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME, false);
}
void OMW::Engine::enableFSStrict(bool fsStrict)
{
mFSStrict = fsStrict;
@ -316,6 +322,7 @@ void OMW::Engine::go()
addResourcesDirectory(mResDir / "water");
addResourcesDirectory(mResDir / "gbuffer");
addResourcesDirectory(mResDir / "shadows");
addZipResource(mResDir / "mygui" / "Obliviontt.zip");
// Create the window
mOgre->createWindow("OpenMW");

@ -91,9 +91,11 @@ namespace OMW
/// add resources directory
/// \note This function works recursively.
void addResourcesDirectory (const boost::filesystem::path& path);
/// add a .zip resource
void addZipResource (const boost::filesystem::path& path);
/// Load all BSA files in data directory.
void loadBSA();

@ -8,7 +8,7 @@
#include "../mwbase/environment.hpp"
#include "../mwworld/ptr.hpp"
#include "../mwworld/actiontake.hpp"
#include "../mwworld/actionread.hpp"
#include "../mwworld/world.hpp"
#include "../mwrender/objects.hpp"
@ -60,12 +60,8 @@ namespace MWClass
boost::shared_ptr<MWWorld::Action> Book::activate (const MWWorld::Ptr& ptr,
const MWWorld::Ptr& actor) const
{
// TODO implement reading
MWBase::Environment::get().getSoundManager()->playSound3D (ptr, getUpSoundId(ptr), 1.0, 1.0, MWSound::Play_NoTrack);
return boost::shared_ptr<MWWorld::Action> (
new MWWorld::ActionTake (ptr));
new MWWorld::ActionRead (ptr));
}
std::string Book::getScript (const MWWorld::Ptr& ptr) const

@ -6,6 +6,8 @@
#include "../mwgui/window_manager.hpp"
#include "../mwgui/messagebox.hpp"
#include "../mwworld/world.hpp"
namespace MWDialogue
{
Quest& Journal::getQuest (const std::string& id)
@ -38,7 +40,7 @@ namespace MWDialogue
quest.addEntry (entry, *MWBase::Environment::get().getWorld()); // we are doing slicing on purpose here
std::vector<std::string> empty;
std::string notification = "Your Journal has been updated.";
std::string notification = MWBase::Environment::get().getWorld()->getStore().gameSettings.search("sJournalEntry")->str;
MWBase::Environment::get().getWindowManager()->messageBox (notification, empty);
}

@ -0,0 +1,140 @@
#include "bookwindow.hpp"
#include "formatting.hpp"
#include "../mwbase/environment.hpp"
#include "../mwinput/inputmanager.hpp"
#include "../mwsound/soundmanager.hpp"
#include "../mwworld/actiontake.hpp"
#include <boost/lexical_cast.hpp>
using namespace MWGui;
BookWindow::BookWindow (WindowManager& parWindowManager) :
WindowBase("openmw_book_layout.xml", parWindowManager)
{
getWidget(mCloseButton, "CloseButton");
mCloseButton->eventMouseButtonClick += MyGUI::newDelegate(this, &BookWindow::onCloseButtonClicked);
getWidget(mTakeButton, "TakeButton");
mTakeButton->eventMouseButtonClick += MyGUI::newDelegate(this, &BookWindow::onTakeButtonClicked);
getWidget(mNextPageButton, "NextPageBTN");
mNextPageButton->eventMouseButtonClick += MyGUI::newDelegate(this, &BookWindow::onNextPageButtonClicked);
getWidget(mPrevPageButton, "PrevPageBTN");
mPrevPageButton->eventMouseButtonClick += MyGUI::newDelegate(this, &BookWindow::onPrevPageButtonClicked);
getWidget(mLeftPageNumber, "LeftPageNumber");
getWidget(mRightPageNumber, "RightPageNumber");
getWidget(mLeftPage, "LeftPage");
getWidget(mRightPage, "RightPage");
center();
}
void BookWindow::clearPages()
{
for (std::vector<MyGUI::Widget*>::iterator it=mPages.begin();
it!=mPages.end(); ++it)
{
MyGUI::Gui::getInstance().destroyWidget(*it);
}
mPages.clear();
}
void BookWindow::open (MWWorld::Ptr book)
{
mBook = book;
clearPages();
mCurrentPage = 0;
MWBase::Environment::get().getSoundManager()->playSound3D (book, "book open", 1.0, 1.0);
ESMS::LiveCellRef<ESM::Book, MWWorld::RefData> *ref =
mBook.get<ESM::Book>();
BookTextParser parser;
std::vector<std::string> results = parser.split(ref->base->text, mLeftPage->getSize().width, mLeftPage->getSize().height);
int i=0;
for (std::vector<std::string>::iterator it=results.begin();
it!=results.end(); ++it)
{
MyGUI::Widget* parent;
if (i%2 == 0)
parent = mLeftPage;
else
parent = mRightPage;
MyGUI::Widget* pageWidget = parent->createWidgetReal<MyGUI::Widget>("", MyGUI::FloatCoord(0.0,0.0,1.0,1.0), MyGUI::Align::Default, "BookPage" + boost::lexical_cast<std::string>(i));
parser.parse(*it, pageWidget, mLeftPage->getSize().width);
mPages.push_back(pageWidget);
++i;
}
updatePages();
}
void BookWindow::onCloseButtonClicked (MyGUI::Widget* _sender)
{
MWBase::Environment::get().getSoundManager()->playSound3D (mBook, "book close", 1.0, 1.0);
MWBase::Environment::get().getInputManager()->setGuiMode(MWGui::GM_Game);
}
void BookWindow::onTakeButtonClicked (MyGUI::Widget* _sender)
{
MWBase::Environment::get().getSoundManager()->playSound3D (mBook, "Item Book Up", 1.0, 1.0, MWSound::Play_NoTrack);
MWWorld::ActionTake take(mBook);
take.execute();
MWBase::Environment::get().getInputManager()->setGuiMode (GM_Game);
}
void BookWindow::onNextPageButtonClicked (MyGUI::Widget* _sender)
{
if ((mCurrentPage+1)*2 < mPages.size())
{
MWBase::Environment::get().getSoundManager()->playSound ("book page2", 1.0, 1.0);
++mCurrentPage;
updatePages();
}
}
void BookWindow::onPrevPageButtonClicked (MyGUI::Widget* _sender)
{
if (mCurrentPage > 0)
{
MWBase::Environment::get().getSoundManager()->playSound ("book page", 1.0, 1.0);
--mCurrentPage;
updatePages();
}
}
void BookWindow::updatePages()
{
mLeftPageNumber->setCaption( boost::lexical_cast<std::string>(mCurrentPage*2 + 1) );
mRightPageNumber->setCaption( boost::lexical_cast<std::string>(mCurrentPage*2 + 2) );
unsigned int i=0;
for (std::vector<MyGUI::Widget*>::iterator it = mPages.begin();
it != mPages.end(); ++it)
{
if (mCurrentPage*2 == i || mCurrentPage*2+1 == i)
(*it)->setVisible(true);
else
{
(*it)->setVisible(false);
}
++i;
}
}

@ -0,0 +1,44 @@
#ifndef MWGUI_BOOKWINDOW_H
#define MWGUI_BOOKWINDOW_H
#include "window_base.hpp"
#include "../mwworld/ptr.hpp"
namespace MWGui
{
class BookWindow : public WindowBase
{
public:
BookWindow(WindowManager& parWindowManager);
void open(MWWorld::Ptr book);
protected:
void onNextPageButtonClicked (MyGUI::Widget* _sender);
void onPrevPageButtonClicked (MyGUI::Widget* _sender);
void onCloseButtonClicked (MyGUI::Widget* _sender);
void onTakeButtonClicked (MyGUI::Widget* _sender);
void updatePages();
void clearPages();
private:
MyGUI::Button* mCloseButton;
MyGUI::Button* mTakeButton;
MyGUI::Button* mNextPageButton;
MyGUI::Button* mPrevPageButton;
MyGUI::TextBox* mLeftPageNumber;
MyGUI::TextBox* mRightPageNumber;
MyGUI::Widget* mLeftPage;
MyGUI::Widget* mRightPage;
unsigned int mCurrentPage; // 0 is first page
std::vector<MyGUI::Widget*> mPages;
MWWorld::Ptr mBook;
};
}
#endif

@ -183,6 +183,7 @@ void CharacterCreation::spawnDialog(const char id)
if (mCreateClassDialog)
mWM->removeDialog(mCreateClassDialog);
mCreateClassDialog = new CreateClassDialog(*mWM);
mCreateClassDialog->setNextButtonShow(mCreationStage >= CSE_ClassChosen);
mCreateClassDialog->eventDone += MyGUI::newDelegate(this, &CharacterCreation::onCreateClassDialogDone);
mCreateClassDialog->eventBack += MyGUI::newDelegate(this, &CharacterCreation::onCreateClassDialogBack);
mCreateClassDialog->open();

@ -111,6 +111,7 @@ PickClassDialog::PickClassDialog(WindowManager& parWindowManager)
MyGUI::ButtonPtr backButton;
getWidget(backButton, "BackButton");
backButton->eventMouseButtonClick += MyGUI::newDelegate(this, &PickClassDialog::onBackClicked);
backButton->setCaption(mWindowManager.getGameSettingString("sBack", ""));
MyGUI::ButtonPtr okButton;
getWidget(okButton, "OKButton");
@ -431,6 +432,7 @@ CreateClassDialog::CreateClassDialog(WindowManager& parWindowManager)
MyGUI::ButtonPtr backButton;
getWidget(backButton, "BackButton");
backButton->eventMouseButtonClick += MyGUI::newDelegate(this, &CreateClassDialog::onBackClicked);
backButton->setCaption(mWindowManager.getGameSettingString("sBack", ""));
MyGUI::ButtonPtr okButton;
getWidget(okButton, "OKButton");

@ -39,10 +39,10 @@ ContainerWindow::ContainerWindow(WindowManager& parWindowManager,DragAndDrop* dr
adjustWindowCaption();
getWidget(mContainerWidget, "Items");
getWidget(takeButton, "TakeButton");
getWidget(closeButton, "CloseButton");
getWidget(mTakeButton, "TakeButton");
getWidget(mCloseButton, "CloseButton");
closeButton->eventMouseButtonClick += MyGUI::newDelegate(this, &ContainerWindow::onByeClicked);
mCloseButton->eventMouseButtonClick += MyGUI::newDelegate(this, &ContainerWindow::onCloseButtonClicked);
mContainerWidget->eventMouseButtonClick += MyGUI::newDelegate(this, &ContainerWindow::onContainerClicked);
setText("CloseButton","Close");
setText("TakeButton","Take All");

@ -60,8 +60,8 @@ namespace MWGui
std::vector<MyGUI::WidgetPtr> mContainerWidgets;
MyGUI::ItemBoxPtr mContainerWidget;
MyGUI::ButtonPtr takeButton;
MyGUI::ButtonPtr closeButton;
MyGUI::ButtonPtr mTakeButton;
MyGUI::ButtonPtr mCloseButton;
DragAndDrop* mDragAndDrop;
MWWorld::Ptr mContainer;

@ -2,6 +2,7 @@
#include <boost/filesystem.hpp>
#include <openengine/ogre/imagerotate.hpp>
#include <openengine/ogre/atlas.hpp>
#include <OgreResourceGroupManager.h>
#include <OgreRoot.h>
@ -13,4 +14,6 @@ CursorReplace::CursorReplace()
OEngine::Render::ImageRotate::rotate("textures\\tx_cursormove.dds", "mwpointer_vresize.png", 90);
OEngine::Render::ImageRotate::rotate("textures\\tx_cursormove.dds", "mwpointer_dresize1.png", -45);
OEngine::Render::ImageRotate::rotate("textures\\tx_cursormove.dds", "mwpointer_dresize2.png", 45);
OEngine::Render::Atlas::createFromFile("atlas1.cfg", "mwgui1", "textures\\");
}

@ -2,6 +2,7 @@
#include "dialogue_history.hpp"
#include "window_manager.hpp"
#include "widgets.hpp"
#include "list.hpp"
#include "components/esm_store/store.hpp"
#include "../mwbase/environment.hpp"
#include "../mwdialogue/dialoguemanager.hpp"
@ -56,9 +57,8 @@ DialogueWindow::DialogueWindow(WindowManager& parWindowManager)
//Topics list
getWidget(topicsList, "TopicsList");
topicsList->setScrollVisible(true);
//topicsList->eventListSelectAccept += MyGUI::newDelegate(this, &DialogueWindow::onSelectTopic);
topicsList->eventListMouseItemActivate += MyGUI::newDelegate(this, &DialogueWindow::onSelectTopic);
topicsList->eventItemSelected += MyGUI::newDelegate(this, &DialogueWindow::onSelectTopic);
//topicsList->eventListChangePosition += MyGUI::newDelegate(this, &DialogueWindow::onSelectTopic);
MyGUI::ButtonPtr byeButton;
@ -67,6 +67,8 @@ DialogueWindow::DialogueWindow(WindowManager& parWindowManager)
getWidget(pDispositionBar, "Disposition");
getWidget(pDispositionText,"DispositionText");
static_cast<MyGUI::Window*>(mMainWidget)->eventWindowChangeCoord += MyGUI::newDelegate(this, &DialogueWindow::onWindowResize);
}
void DialogueWindow::onHistoryClicked(MyGUI::Widget* _sender)
@ -88,6 +90,11 @@ void DialogueWindow::onHistoryClicked(MyGUI::Widget* _sender)
}
}
void DialogueWindow::onWindowResize(MyGUI::Window* _sender)
{
topicsList->adjustSize();
}
void DialogueWindow::onMouseWheel(MyGUI::Widget* _sender, int _rel)
{
if (history->getVScrollPosition() - _rel*0.3 < 0)
@ -98,7 +105,7 @@ void DialogueWindow::onMouseWheel(MyGUI::Widget* _sender, int _rel)
void DialogueWindow::open()
{
topicsList->removeAllItems();
topicsList->clear();
pTopicsText.clear();
history->eraseText(0,history->getTextLength());
updateOptions();
@ -110,11 +117,8 @@ void DialogueWindow::onByeClicked(MyGUI::Widget* _sender)
MWBase::Environment::get().getDialogueManager()->goodbyeSelected();
}
void DialogueWindow::onSelectTopic(MyGUI::ListBox* _sender, size_t _index)
void DialogueWindow::onSelectTopic(std::string topic)
{
if (_index == MyGUI::ITEM_NONE)
return;
std::string topic = _sender->getItemNameAt(_index);
MWBase::Environment::get().getDialogueManager()->keywordSelected(lower_string(topic));
}
@ -126,7 +130,7 @@ void DialogueWindow::startDialogue(std::string npcName)
void DialogueWindow::setKeywords(std::list<std::string> keyWords)
{
topicsList->removeAllItems();
topicsList->clear();
for(std::list<std::string>::iterator it = keyWords.begin(); it != keyWords.end(); it++)
{
topicsList->addItem(*it);
@ -135,9 +139,9 @@ void DialogueWindow::setKeywords(std::list<std::string> keyWords)
void DialogueWindow::removeKeyword(std::string keyWord)
{
if(topicsList->findItemIndexWith(keyWord) != MyGUI::ITEM_NONE)
if(topicsList->hasItem(keyWord))
{
topicsList->removeItemAt(topicsList->findItemIndexWith(keyWord));
topicsList->removeItem(keyWord);
pTopicsText.erase(keyWord);
}
}
@ -211,7 +215,7 @@ void DialogueWindow::askQuestion(std::string question)
void DialogueWindow::updateOptions()
{
//Clear the list of topics
topicsList->removeAllItems();
topicsList->clear();
pTopicsText.clear();
history->eraseText(0,history->getTextLength());

@ -7,6 +7,11 @@
namespace MWGui
{
class WindowManager;
namespace Widgets
{
class MWList;
}
}
/*
@ -42,10 +47,11 @@ namespace MWGui
void askQuestion(std::string question);
protected:
void onSelectTopic(MyGUI::ListBox* _sender, size_t _index);
void onSelectTopic(std::string topic);
void onByeClicked(MyGUI::Widget* _sender);
void onHistoryClicked(MyGUI::Widget* _sender);
void onMouseWheel(MyGUI::Widget* _sender, int _rel);
void onWindowResize(MyGUI::Window* _sender);
private:
void updateOptions();
@ -55,7 +61,7 @@ namespace MWGui
std::string parseText(std::string text);
DialogueHistory* history;
MyGUI::ListBox* topicsList;
Widgets::MWList* topicsList;
MyGUI::ProgressPtr pDispositionBar;
MyGUI::EditPtr pDispositionText;
std::map<std::string,std::string> pTopicsText;// this map links keyword and "real" text.

@ -0,0 +1,331 @@
#include "formatting.hpp"
#include <boost/algorithm/string/replace.hpp>
#include <boost/lexical_cast.hpp>
using namespace MWGui;
namespace
{
int convertFromHex(std::string hex)
{
int value = 0;
int a = 0;
int b = hex.length() - 1;
for (; b >= 0; a++, b--)
{
if (hex[b] >= '0' && hex[b] <= '9')
{
value += (hex[b] - '0') * (1 << (a * 4));
}
else
{
switch (hex[b])
{
case 'A':
case 'a':
value += 10 * (1 << (a * 4));
break;
case 'B':
case 'b':
value += 11 * (1 << (a * 4));
break;
case 'C':
case 'c':
value += 12 * (1 << (a * 4));
break;
case 'D':
case 'd':
value += 13 * (1 << (a * 4));
break;
case 'E':
case 'e':
value += 14 * (1 << (a * 4));
break;
case 'F':
case 'f':
value += 15 * (1 << (a * 4));
break;
default:
throw std::runtime_error("invalid character in hex number");
break;
}
}
}
return value;
}
}
std::vector<std::string> BookTextParser::split(std::string text, const int width, const int height)
{
std::vector<std::string> result;
boost::algorithm::replace_all(text, "<BR>", "\n");
boost::algorithm::replace_all(text, "<P>", "\n\n");
const int spacing = 48;
while (text.size() > 0)
{
// read in characters until we have exceeded the size, or run out of text
int currentWidth = 0;
int currentHeight = 0;
std::string currentText;
std::string currentWord;
unsigned int i=0;
while (currentHeight <= height-spacing && i<text.size())
{
if (text[i] == '<')
{
if (text.find('>', i) == std::string::npos)
throw std::runtime_error("BookTextParser Error: Tag is not terminated");
if (text.size() > i+4 && text.substr(i, 4) == "<IMG")
{
int h = mHeight;
parseImage(text.substr(i, text.find('>', i)-i), false);
currentHeight += (mHeight-h);
currentWidth = 0;
}
else if (text.size() > i+5 && text.substr(i, 5) == "<FONT")
{
parseFont(text.substr(i, text.find('>', i)-i));
currentHeight += 18; // keep this in sync with the font size
currentWidth = 0;
}
else if (text.size() > i+4 && text.substr(i, 4) == "<DIV")
{
parseDiv(text.substr(i, text.find('>', i)-i));
currentHeight += 18; // keep this in sync with the font size
currentWidth = 0;
}
currentText += text.substr(i, text.find('>', i)-i+1);
i = text.find('>', i);
}
else if (text[i] == '\n')
{
currentHeight += 18; // keep this in sync with the font size
currentWidth = 0;
currentWord = "";
currentText += text[i];
}
else if (text[i] == ' ')
{
currentWidth += 3; // keep this in sync with the font's SpaceWidth property
currentWord = "";
currentText += text[i];
}
else
{
currentWidth +=
MyGUI::FontManager::getInstance().getByName (mTextStyle.mFont == "Default" ? "EB Garamond" : mTextStyle.mFont)
->getGlyphInfo(static_cast<unsigned int>(text[i]))->width;
currentWord += text[i];
currentText += text[i];
}
if (currentWidth > width)
{
currentHeight += 18; // keep this in sync with the font size
currentWidth = 0;
// add size of the current word
unsigned int j=0;
while (j<currentWord.size())
{
currentWidth +=
MyGUI::FontManager::getInstance().getByName (mTextStyle.mFont == "Default" ? "EB Garamond" : mTextStyle.mFont)
->getGlyphInfo(static_cast<unsigned int>(currentWord[j]))->width;
++j;
}
}
++i;
}
if (currentHeight > height-spacing)
{
// remove the last word
currentText.erase(currentText.size()-currentWord.size(), currentText.size());
}
result.push_back(currentText);
text.erase(0, currentText.size());
}
return result;
}
MyGUI::IntSize BookTextParser::parse(std::string text, MyGUI::Widget* parent, const int width)
{
mParent = parent;
mWidth = width;
mHeight = 0;
assert(mParent);
while (mParent->getChildCount())
{
MyGUI::Gui::getInstance().destroyWidget(mParent->getChildAt(0));
}
boost::algorithm::replace_all(text, "<BR>", "\n");
boost::algorithm::replace_all(text, "<P>", "\n\n");
// remove leading newlines
//while (text[0] == '\n')
// text.erase(0);
// remove trailing "
if (text[text.size()-1] == '\"')
text.erase(text.size()-1);
parseSubText(text);
return MyGUI::IntSize(mWidth, mHeight);
}
void BookTextParser::parseImage(std::string tag, bool createWidget)
{
int src_start = tag.find("SRC=")+5;
std::string image = tag.substr(src_start, tag.find('"', src_start)-src_start);
// fix texture extension to .dds
if (image.size() > 4)
{
image[image.size()-3] = 'd';
image[image.size()-2] = 'd';
image[image.size()-1] = 's';
}
int width_start = tag.find("WIDTH=")+7;
int width = boost::lexical_cast<int>(tag.substr(width_start, tag.find('"', width_start)-width_start));
int height_start = tag.find("HEIGHT=")+8;
int height = boost::lexical_cast<int>(tag.substr(height_start, tag.find('"', height_start)-height_start));
if (createWidget)
{
MyGUI::ImageBox* box = mParent->createWidget<MyGUI::ImageBox> ("ImageBox",
MyGUI::IntCoord(0, mHeight, width, height), MyGUI::Align::Left | MyGUI::Align::Top,
mParent->getName() + boost::lexical_cast<std::string>(mParent->getChildCount()));
box->setImageTexture("bookart\\" + image);
box->setProperty("NeedMouse", "false");
}
mWidth = std::max(mWidth, width);
mHeight += height;
}
void BookTextParser::parseDiv(std::string tag)
{
if (tag.find("ALIGN=") == std::string::npos)
return;
int align_start = tag.find("ALIGN=")+7;
std::string align = tag.substr(align_start, tag.find('"', align_start)-align_start);
if (align == "CENTER")
mTextStyle.mTextAlign = MyGUI::Align::HCenter;
else if (align == "LEFT")
mTextStyle.mTextAlign = MyGUI::Align::Left;
}
void BookTextParser::parseFont(std::string tag)
{
if (tag.find("COLOR=") != std::string::npos)
{
int color_start = tag.find("COLOR=")+7;
std::string color = tag.substr(color_start, tag.find('"', color_start)-color_start);
mTextStyle.mColour = MyGUI::Colour(
convertFromHex(color.substr(0, 2))/255.0,
convertFromHex(color.substr(2, 2))/255.0,
convertFromHex(color.substr(4, 2))/255.0);
}
if (tag.find("FACE=") != std::string::npos)
{
int face_start = tag.find("FACE=")+6;
std::string face = tag.substr(face_start, tag.find('"', face_start)-face_start);
if (face != "Magic Cards")
mTextStyle.mFont = face;
}
if (tag.find("SIZE=") != std::string::npos)
{
/// \todo
}
}
void BookTextParser::parseSubText(std::string text)
{
if (text[0] == '<')
{
if (text.find('>') == std::string::npos)
throw std::runtime_error("BookTextParser Error: Tag is not terminated");
if (text.size() > 4 && text.substr(0, 4) == "<IMG")
parseImage(text.substr(0, text.find('>')));
else if (text.size() > 5 && text.substr(0, 5) == "<FONT")
parseFont(text.substr(0, text.find('>')));
else if (text.size() > 4 && text.substr(0, 4) == "<DIV")
parseDiv(text.substr(0, text.find('>')));
text.erase(0, text.find('>')+1);
}
bool tagFound = false;
std::string realText; // real text, without tags
unsigned int i=0;
for (; i<text.size(); ++i)
{
char c = text[i];
if (c == '<')
{
if (text[i+1] == '/') // ignore closing tags
{
while (c != '>')
{
if (i >= text.size())
throw std::runtime_error("BookTextParser Error: Tag is not terminated");
++i;
c = text[i];
}
continue;
}
else
{
tagFound = true;
break;
}
}
else
realText += c;
}
MyGUI::EditBox* box = mParent->createWidget<MyGUI::EditBox>("NormalText",
MyGUI::IntCoord(0, mHeight, mWidth, 24), MyGUI::Align::Left | MyGUI::Align::Top,
mParent->getName() + boost::lexical_cast<std::string>(mParent->getChildCount()));
box->setProperty("Static", "true");
box->setProperty("MultiLine", "true");
box->setProperty("WordWrap", "true");
box->setProperty("NeedMouse", "false");
box->setMaxTextLength(realText.size());
box->setTextAlign(mTextStyle.mTextAlign);
box->setTextColour(mTextStyle.mColour);
box->setFontName(mTextStyle.mFont);
box->setCaption(realText);
box->setSize(box->getSize().width, box->getTextSize().height);
mHeight += box->getTextSize().height;
if (tagFound)
{
parseSubText(text.substr(i, text.size()));
}
}

@ -0,0 +1,56 @@
#ifndef MWGUI_FORMATTING_H
#define MWGUI_FORMATTING_H
#include <MyGUI.h>
namespace MWGui
{
struct TextStyle
{
TextStyle() :
mColour(0,0,0)
, mFont("Default")
, mTextSize(16)
, mTextAlign(MyGUI::Align::Left | MyGUI::Align::Top)
{
}
MyGUI::Colour mColour;
std::string mFont;
int mTextSize;
MyGUI::Align mTextAlign;
};
/// \brief utilities for parsing book/scroll text as mygui widgets
class BookTextParser
{
public:
/**
* Parse markup as MyGUI widgets
* @param markup to parse
* @param parent for the created widgets
* @param maximum width
* @return size of the created widgets
*/
MyGUI::IntSize parse(std::string text, MyGUI::Widget* parent, const int width);
/**
* Split the specified text into pieces that fit in the area specified by width and height parameters
*/
std::vector<std::string> split(std::string text, const int width, const int height);
protected:
void parseSubText(std::string text);
void parseImage(std::string tag, bool createWidget=true);
void parseDiv(std::string tag);
void parseFont(std::string tag);
private:
MyGUI::Widget* mParent;
int mWidth; // maximum width
int mHeight; // current height
TextStyle mTextStyle;
};
}
#endif

@ -82,6 +82,7 @@ book formatText(std::string text,book mBook,int maxLine, int lineSize)
MWGui::JournalWindow::JournalWindow (WindowManager& parWindowManager)
: WindowBase("openmw_journal_layout.xml", parWindowManager)
, lastPos(0)
, mVisible(false)
{
//setCoord(0,0,498, 342);
center();
@ -109,9 +110,15 @@ MWGui::JournalWindow::JournalWindow (WindowManager& parWindowManager)
//std::list<std::string> list = formatText("OpenMW rgh dsfg sqef srg ZT uzql n ZLIEHRF LQSJH GLOIjf qjfmj hslkdgn jlkdjhg qlr isgli shli uhs fiuh qksf cg ksjnf lkqsnbf ksbf sbfkl zbf kuyzflkj sbgdfkj zlfh ozhjfmo hzmfh lizuf rty qzt ezy tkyEZT RYYJ DG fgh is an open-source implementation of the game engine found in the game Morrowind. This is a dumb test text msodjbg smojg smoig fiiinnn");
//std::list<std::string> list = formatText();
//displayLeftText(list.front());
}
void MWGui::JournalWindow::setVisible(bool visible)
{
if (mVisible && !visible)
MWBase::Environment::get().getSoundManager()->playSound ("book close", 1.0, 1.0);
mVisible = visible;
MyGUI::WindowPtr t = static_cast<MyGUI::WindowPtr>(mMainWidget);
t->eventWindowChangeCoord += MyGUI::newDelegate(this, &JournalWindow::onWindowResize);
mMainWidget->setVisible(visible);
}
void MWGui::JournalWindow::open()
@ -159,10 +166,6 @@ void MWGui::JournalWindow::open()
}
}
void MWGui::JournalWindow::onWindowResize(MyGUI::Window* window)
{
}
void MWGui::JournalWindow::displayLeftText(std::string text)
{
mLeftTextWidget->eraseText(0,mLeftTextWidget->getTextLength());

@ -18,16 +18,9 @@ namespace MWGui
JournalWindow(WindowManager& parWindowManager);
void open();
private:
enum ColorStyle
{
CS_Sub,
CS_Normal,
CS_Super
};
void onWindowResize(MyGUI::Window* window);
virtual void setVisible(bool visible); // only used to play close sound
private:
void displayLeftText(std::string text);
void displayRightText(std::string text);
@ -50,6 +43,7 @@ namespace MWGui
std::vector<std::string> leftPages;
std::vector<std::string> rightPages;
int mPageNumber; //store the number of the current left page
bool mVisible;
};
}

@ -0,0 +1,121 @@
#include "list.hpp"
#include <MyGUI.h>
using namespace MWGui;
using namespace MWGui::Widgets;
MWList::MWList() :
mClient(0)
, mScrollView(0)
, mItemHeight(0)
{
}
void MWList::initialiseOverride()
{
Base::initialiseOverride();
assignWidget(mClient, "Client");
if (mClient == 0)
mClient = this;
mScrollView = mClient->createWidgetReal<MyGUI::ScrollView>(
"MW_ScrollView", MyGUI::FloatCoord(0.0, 0.0, 1.0, 1.0),
MyGUI::Align::Top | MyGUI::Align::Left | MyGUI::Align::Stretch, getName() + "_ScrollView");
}
void MWList::addItem(const std::string& name)
{
mItems.push_back(name);
redraw();
}
void MWList::adjustSize()
{
redraw();
}
void MWList::redraw(bool scrollbarShown)
{
const int _scrollBarWidth = 24; // fetch this from skin?
const int scrollBarWidth = scrollbarShown ? _scrollBarWidth : 0;
const int spacing = 3;
while (mScrollView->getChildCount())
{
MyGUI::Gui::getInstance().destroyWidget(mScrollView->getChildAt(0));
}
mItemHeight = 0;
for (std::vector<std::string>::const_iterator it=mItems.begin();
it!=mItems.end(); ++it)
{
MyGUI::Button* button = mScrollView->createWidget<MyGUI::Button>(
"MW_ListLine", MyGUI::IntCoord(0, mItemHeight, mScrollView->getSize().width - scrollBarWidth - 2, 24),
MyGUI::Align::Left | MyGUI::Align::Top, getName() + "_item_" + (*it));
button->setCaption((*it));
button->getSubWidgetText()->setWordWrap(true);
button->getSubWidgetText()->setTextAlign(MyGUI::Align::Left);
button->eventMouseWheel += MyGUI::newDelegate(this, &MWList::onMouseWheel);
button->eventMouseButtonClick += MyGUI::newDelegate(this, &MWList::onItemSelected);
int height = button->getTextSize().height;
button->setSize(MyGUI::IntSize(button->getSize().width, height));
mItemHeight += height + spacing;
}
mScrollView->setCanvasSize(mClient->getSize().width + (_scrollBarWidth-scrollBarWidth), std::max(mItemHeight, mClient->getSize().height));
mScrollView->setViewOffset(MyGUI::IntPoint(0,0));
if (!scrollbarShown && mItemHeight > mClient->getSize().height)
redraw(true);
}
bool MWList::hasItem(const std::string& name)
{
return (std::find(mItems.begin(), mItems.end(), name) != mItems.end());
}
unsigned int MWList::getItemCount()
{
return mItems.size();
}
std::string MWList::getItemNameAt(unsigned int at)
{
assert(at < mItems.size() && "List item out of bounds");
return mItems[at];
}
void MWList::removeItem(const std::string& name)
{
assert( std::find(mItems.begin(), mItems.end(), name) != mItems.end() );
mItems.erase( std::find(mItems.begin(), mItems.end(), name) );
redraw();
}
void MWList::clear()
{
mItems.clear();
redraw();
}
void MWList::onMouseWheel(MyGUI::Widget* _sender, int _rel)
{
//NB view offset is negative
if (mScrollView->getViewOffset().top + _rel*0.3 > 0)
mScrollView->setViewOffset(MyGUI::IntPoint(0, 0));
else
mScrollView->setViewOffset(MyGUI::IntPoint(0, mScrollView->getViewOffset().top + _rel*0.3));
}
void MWList::onItemSelected(MyGUI::Widget* _sender)
{
std::string name = static_cast<MyGUI::Button*>(_sender)->getCaption();
eventItemSelected(name);
}

@ -0,0 +1,59 @@
#ifndef MWGUI_LIST_HPP
#define MWGUI_LIST_HPP
#include <MyGUI.h>
namespace MWGui
{
namespace Widgets
{
/**
* \brief a very simple list widget that supports word-wrapping entries
* \note if the width or height of the list changes, you must call adjustSize() method
*/
class MWList : public MyGUI::Widget
{
MYGUI_RTTI_DERIVED(MWList)
public:
MWList();
typedef MyGUI::delegates::CMultiDelegate1<std::string> EventHandle_String;
/**
* Event: Item selected with the mouse.
* signature: void method(std::string itemName)
*/
EventHandle_String eventItemSelected;
/**
* Call after the size of the list changed
*/
void adjustSize();
void addItem(const std::string& name);
void removeItem(const std::string& name);
bool hasItem(const std::string& name);
unsigned int getItemCount();
std::string getItemNameAt(unsigned int at);
void clear();
protected:
void initialiseOverride();
void redraw(bool scrollbarShown = false);
void onMouseWheel(MyGUI::Widget* _sender, int _rel);
void onItemSelected(MyGUI::Widget* _sender);
private:
MyGUI::ScrollView* mScrollView;
MyGUI::Widget* mClient;
std::vector<std::string> mItems;
int mItemHeight; // height of all items
};
}
}
#endif

@ -13,12 +13,12 @@ namespace MWGui
GM_Console, // Console mode
GM_Journal, // Journal mode
// None of the following are implemented yet
GM_Scroll, // Read scroll
GM_Book, // Read book
GM_Dialogue, // NPC interaction
GM_Barter,
GM_Rest,
// .. more here ..
// Startup character creation dialogs
GM_Name,

@ -248,7 +248,7 @@ MyGUI::TextBox* ReviewDialog::addValueItem(const std::string text, const std::st
skillNameWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandText", coord1, MyGUI::Align::Default);
skillNameWidget->setCaption(text);
skillValueWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandTextRight", coord2, MyGUI::Align::Default);
skillValueWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandTextRight", coord2, MyGUI::Align::Top | MyGUI::Align::Right);
skillValueWidget->setCaption(value);
skillValueWidget->_setWidgetState(state);

@ -0,0 +1,61 @@
#include "scrollwindow.hpp"
#include "formatting.hpp"
#include "../mwbase/environment.hpp"
#include "../mwinput/inputmanager.hpp"
#include "../mwworld/actiontake.hpp"
#include "../mwsound/soundmanager.hpp"
using namespace MWGui;
ScrollWindow::ScrollWindow (WindowManager& parWindowManager) :
WindowBase("openmw_scroll_layout.xml", parWindowManager)
{
getWidget(mTextView, "TextView");
getWidget(mCloseButton, "CloseButton");
mCloseButton->eventMouseButtonClick += MyGUI::newDelegate(this, &ScrollWindow::onCloseButtonClicked);
getWidget(mTakeButton, "TakeButton");
mTakeButton->eventMouseButtonClick += MyGUI::newDelegate(this, &ScrollWindow::onTakeButtonClicked);
center();
}
void ScrollWindow::open (MWWorld::Ptr scroll)
{
MWBase::Environment::get().getSoundManager()->playSound3D (scroll, "scroll", 1.0, 1.0);
mScroll = scroll;
ESMS::LiveCellRef<ESM::Book, MWWorld::RefData> *ref =
mScroll.get<ESM::Book>();
BookTextParser parser;
MyGUI::IntSize size = parser.parse(ref->base->text, mTextView, 390);
if (size.height > mTextView->getSize().height)
mTextView->setCanvasSize(MyGUI::IntSize(410, size.height));
else
mTextView->setCanvasSize(410, mTextView->getSize().height);
mTextView->setViewOffset(MyGUI::IntPoint(0,0));
}
void ScrollWindow::onCloseButtonClicked (MyGUI::Widget* _sender)
{
MWBase::Environment::get().getSoundManager()->playSound3D (mScroll, "scroll", 1.0, 1.0);
MWBase::Environment::get().getInputManager()->setGuiMode (GM_Game);
}
void ScrollWindow::onTakeButtonClicked (MyGUI::Widget* _sender)
{
MWBase::Environment::get().getSoundManager()->playSound3D (mScroll, "Item Book Up", 1.0, 1.0, MWSound::Play_NoTrack);
MWWorld::ActionTake take(mScroll);
take.execute();
MWBase::Environment::get().getInputManager()->setGuiMode (GM_Game);
}

@ -0,0 +1,30 @@
#ifndef MWGUI_SCROLLWINDOW_H
#define MWGUI_SCROLLWINDOW_H
#include "window_base.hpp"
#include "../mwworld/ptr.hpp"
namespace MWGui
{
class ScrollWindow : public WindowBase
{
public:
ScrollWindow (WindowManager& parWindowManager);
void open (MWWorld::Ptr scroll);
protected:
void onCloseButtonClicked (MyGUI::Widget* _sender);
void onTakeButtonClicked (MyGUI::Widget* _sender);
private:
MyGUI::Button* mCloseButton;
MyGUI::Button* mTakeButton;
MyGUI::ScrollView* mTextView;
MWWorld::Ptr mScroll;
};
}
#endif

@ -230,7 +230,9 @@ void StatsWindow::setBirthSign (const std::string& signId)
void StatsWindow::addSeparator(MyGUI::IntCoord &coord1, MyGUI::IntCoord &coord2)
{
MyGUI::ImageBox* separator = skillClientWidget->createWidget<MyGUI::ImageBox>("MW_HLine", MyGUI::IntCoord(10, coord1.top, coord1.width + coord2.width - 4, 18), MyGUI::Align::Default);
MyGUI::ImageBox* separator = skillClientWidget->createWidget<MyGUI::ImageBox>("MW_HLine",
MyGUI::IntCoord(10, coord1.top, coord1.width + coord2.width - 4, 18),
MyGUI::Align::Left | MyGUI::Align::Top | MyGUI::Align::HStretch);
skillWidgets.push_back(separator);
coord1.top += separator->getHeight();
@ -239,7 +241,9 @@ void StatsWindow::addSeparator(MyGUI::IntCoord &coord1, MyGUI::IntCoord &coord2)
void StatsWindow::addGroup(const std::string &label, MyGUI::IntCoord &coord1, MyGUI::IntCoord &coord2)
{
MyGUI::TextBox* groupWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandBrightText", MyGUI::IntCoord(0, coord1.top, coord1.width + coord2.width, coord1.height), MyGUI::Align::Default);
MyGUI::TextBox* groupWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandBrightText",
MyGUI::IntCoord(0, coord1.top, coord1.width + coord2.width, coord1.height),
MyGUI::Align::Left | MyGUI::Align::Top | MyGUI::Align::HStretch);
groupWidget->setCaption(label);
skillWidgets.push_back(groupWidget);
@ -251,12 +255,12 @@ MyGUI::TextBox* StatsWindow::addValueItem(const std::string& text, const std::st
{
MyGUI::TextBox *skillNameWidget, *skillValueWidget;
skillNameWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandText", coord1, MyGUI::Align::Default);
skillNameWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandText", coord1, MyGUI::Align::Left | MyGUI::Align::Top | MyGUI::Align::HStretch);
skillNameWidget->setCaption(text);
skillNameWidget->setUserString("ToolTipType", "Text");
skillNameWidget->setUserString("ToolTipText", tooltip);
skillValueWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandTextRight", coord2, MyGUI::Align::Default);
skillValueWidget = skillClientWidget->createWidget<MyGUI::TextBox>("SandTextRight", coord2, MyGUI::Align::Right | MyGUI::Align::Top);
skillValueWidget->setUserString("ToolTipType", "Text");
skillValueWidget->setUserString("ToolTipText", tooltip);
skillValueWidget->setCaption(value);

@ -103,8 +103,8 @@ void ToolTips::onFrame(float frameDuration)
// adjust tooltip size to fit its content, position it above the crosshair
/// \todo Slide the tooltip along the bounding box of the focused object (like in Morrowind)
setCoord(viewSize.width/2 - (tooltipSize.width)/2.f,
viewSize.height/2 - (tooltipSize.height) - 32,
setCoord(std::max(0, viewSize.width/2 - (tooltipSize.width)/2),
std::max(0, viewSize.height/2 - (tooltipSize.height) - 32),
tooltipSize.width,
tooltipSize.height);
}

@ -11,6 +11,9 @@
#include "inventorywindow.hpp"
#include "itemwidget.hpp"
#include "tooltips.hpp"
#include "scrollwindow.hpp"
#include "bookwindow.hpp"
#include "list.hpp"
#include "../mwmechanics/mechanicsmanager.hpp"
#include "../mwinput/inputmanager.hpp"
@ -41,6 +44,8 @@ WindowManager::WindowManager(
, console(NULL)
, mJournal(NULL)
, mDialogueWindow(nullptr)
, mBookWindow(NULL)
, mScrollWindow(NULL)
, mCharGen(NULL)
, playerClass()
, playerName()
@ -73,6 +78,13 @@ WindowManager::WindowManager(
//Register own widgets with MyGUI
MyGUI::FactoryManager::getInstance().registerFactory<DialogueHistory>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<ItemWidget>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWSkill>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWAttribute>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWSpell>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWEffectList>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWSpellEffect>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWDynamicStat>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWList>("Widget");
// Get size info from the Gui object
assert(gui);
@ -99,6 +111,8 @@ WindowManager::WindowManager(
mContainerWindow = new ContainerWindow(*this,mDragAndDrop);
mInventoryWindow = new InventoryWindow(*this,mDragAndDrop);
mToolTips = new ToolTips(this);
mScrollWindow = new ScrollWindow(*this);
mBookWindow = new BookWindow(*this);
// The HUD is always on
hud->setVisible(true);
@ -116,13 +130,6 @@ WindowManager::WindowManager(
playerSkillValues.insert(std::make_pair(ESM::Skill::skillIds[i], MWMechanics::Stat<float>()));
}
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWSkill>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWAttribute>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWSpell>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWEffectList>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWSpellEffect>("Widget");
MyGUI::FactoryManager::getInstance().registerFactory<MWGui::Widgets::MWDynamicStat>("Widget");
// Set up visibility
updateVisible();
}
@ -199,6 +206,8 @@ void WindowManager::updateVisible()
mDialogueWindow->setVisible(false);
mContainerWindow->setVisible(false);
mInventoryWindow->setVisible(false);
mScrollWindow->setVisible(false);
mBookWindow->setVisible(false);
// Mouse is visible whenever we're not in game mode
MyGUI::PointerManager::getInstance().setVisible(isGuiMode());
@ -218,6 +227,12 @@ void WindowManager::updateVisible()
case GM_Console:
console->enable();
break;
case GM_Scroll:
mScrollWindow->setVisible(true);
break;
case GM_Book:
mBookWindow->setVisible(true);
break;
case GM_Name:
case GM_Race:
case GM_Class:

@ -65,6 +65,8 @@ namespace MWGui
class DragAndDrop;
class InventoryWindow;
class ToolTips;
class ScrollWindow;
class BookWindow;
class TextInputDialog;
class InfoBoxDialog;
class DialogueWindow;
@ -129,6 +131,9 @@ namespace MWGui
MWGui::ContainerWindow* getContainerWindow() {return mContainerWindow;}
MWGui::BookWindow* getBookWindow() {return mBookWindow;}
MWGui::ScrollWindow* getScrollWindow() {return mScrollWindow;}
MyGUI::Gui* getGui() const { return gui; }
void wmUpdateFps(float fps, size_t triangleCount, size_t batchCount)
@ -210,6 +215,9 @@ namespace MWGui
ContainerWindow *mContainerWindow;
DragAndDrop* mDragAndDrop;
InventoryWindow *mInventoryWindow;
ScrollWindow* mScrollWindow;
BookWindow* mBookWindow;
CharacterCreation* mCharGen;
// Various stats about player as needed by window manager

@ -133,6 +133,9 @@ namespace MWInput
void screenshot()
{
mEngine.screenshot();
std::vector<std::string> empty;
windows.messageBox ("Screenshot saved", empty);
}
/* toggleInventory() is called when the user presses the button to toggle the inventory screen. */

@ -0,0 +1,31 @@
#include "actionread.hpp"
#include "../mwbase/environment.hpp"
#include "../mwgui/window_manager.hpp"
#include "../mwgui/bookwindow.hpp"
#include "../mwgui/scrollwindow.hpp"
namespace MWWorld
{
ActionRead::ActionRead (const MWWorld::Ptr& object) : mObject (object)
{
}
void ActionRead::execute ()
{
ESMS::LiveCellRef<ESM::Book, MWWorld::RefData> *ref =
mObject.get<ESM::Book>();
if (ref->base->data.isScroll)
{
MWBase::Environment::get().getWindowManager()->setGuiMode(MWGui::GM_Scroll);
MWBase::Environment::get().getWindowManager()->getScrollWindow()->open(mObject);
}
else
{
MWBase::Environment::get().getWindowManager()->setGuiMode(MWGui::GM_Book);
MWBase::Environment::get().getWindowManager()->getBookWindow()->open(mObject);
}
}
}

@ -0,0 +1,21 @@
#ifndef GAME_MWWORLD_ACTIONREAD_H
#define GAME_MWWORLD_ACTIONREAD_H
#include "action.hpp"
#include "ptr.hpp"
namespace MWWorld
{
class ActionRead : public Action
{
Ptr mObject; // book or scroll to read
public:
/// @param book or scroll to read
ActionRead (const Ptr& object);
virtual void execute ();
};
}
#endif // ACTIONOPEN_H

@ -9,7 +9,7 @@ configure_file("${SDIR}/black.png" "${DDIR}/black.png" COPYONLY)
configure_file("${SDIR}/core.skin" "${DDIR}/core.skin" COPYONLY)
configure_file("${SDIR}/core.xml" "${DDIR}/core.xml" COPYONLY)
configure_file("${SDIR}/mwgui.png" "${DDIR}/mwgui.png" COPYONLY)
configure_file("${SDIR}/openmw_images.xml" "${DDIR}/openmw_images.xml" COPYONLY)
configure_file("${SDIR}/openmw_resources.xml" "${DDIR}/openmw_resources.xml" COPYONLY)
configure_file("${SDIR}/openmw_settings.xml" "${DDIR}/openmw_settings.xml" COPYONLY)
configure_file("${SDIR}/openmw_box.skin.xml" "${DDIR}/openmw_box.skin.xml" COPYONLY)
configure_file("${SDIR}/openmw_button.skin.xml" "${DDIR}/openmw_button.skin.xml" COPYONLY)
@ -52,7 +52,12 @@ configure_file("${SDIR}/openmw_interactive_messagebox_layout.xml" "${DDIR}/openm
configure_file("${SDIR}/openmw_journal_layout.xml" "${DDIR}/openmw_journal_layout.xml" COPYONLY)
configure_file("${SDIR}/openmw_journal_skin.xml" "${DDIR}/openmw_journal_skin.xml" COPYONLY)
configure_file("${SDIR}/openmw_tooltips.xml" "${DDIR}/openmw_tooltips.xml" COPYONLY)
configure_file("${SDIR}/openmw_scroll_layout.xml" "${DDIR}/openmw_scroll_layout.xml" COPYONLY)
configure_file("${SDIR}/openmw_scroll_skin.xml" "${DDIR}/openmw_scroll_skin.xml" COPYONLY)
configure_file("${SDIR}/openmw_book_layout.xml" "${DDIR}/openmw_book_layout.xml" COPYONLY)
configure_file("${SDIR}/atlas1.cfg" "${DDIR}/atlas1.cfg" COPYONLY)
configure_file("${SDIR}/smallbars.png" "${DDIR}/smallbars.png" COPYONLY)
configure_file("${SDIR}/transparent.png" "${DDIR}/transparent.png" COPYONLY)
configure_file("${SDIR}/EBGaramond-Regular.ttf" "${DDIR}/EBGaramond-Regular.ttf" COPYONLY)
configure_file("${SDIR}/Obliviontt.zip" "${DDIR}/Obliviontt.zip" COPYONLY)
configure_file("${SDIR}/VeraMono.ttf" "${DDIR}/VeraMono.ttf" COPYONLY)

Binary file not shown.

@ -0,0 +1,51 @@
[settings]
size_x = 512
size_y = 512
[tx_menubook_close_idle.dds]
x = 0
y = 0
[tx_menubook_close_over.dds]
x = 128
y = 0
[tx_menubook_close_pressed.dds]
x = 256
y = 0
[tx_menubook_take_idle.dds]
x = 384
y = 0
[tx_menubook_take_over.dds]
x = 0
y = 32
[tx_menubook_take_pressed.dds]
x = 128
y = 32
[tx_menubook_next_idle.dds]
x = 256
y = 32
[tx_menubook_next_over.dds]
x = 384
y = 32
[tx_menubook_next_pressed.dds]
x = 0
y = 64
[tx_menubook_prev_idle.dds]
x = 128
y = 64
[tx_menubook_prev_over.dds]
x = 256
y = 64
[tx_menubook_prev_pressed.dds]
x = 384
y = 64

@ -2,7 +2,7 @@
<MyGUI>
<MyGUI type="List">
<List file="core.skin" />
<List file="openmw_images.xml" />
<List file="openmw_resources.xml" />
<List file="openmw_layers.xml" />
<List file="openmw.pointer.xml" />
<List file="openmw.font.xml" />
@ -20,7 +20,7 @@
<List file="openmw_journal_skin.xml" />
<List file="openmw_map_window_skin.xml" />
<List file="openmw_dialogue_window_skin.xml" />
<List file="openmw_container_window_layout.xml" />
<List file="openmw_scroll_skin.xml" />
<List file="openmw_settings.xml" />
</MyGUI>
</MyGUI>

@ -6,26 +6,38 @@
<Property key="Resolution" value="72"/>
<Property key="Antialias" value="false"/>
<Property key="TabWidth" value="8"/>
<Property key="CursorWidth" value="2"/>
<Property key="OffsetHeight" value="0"/>
<Codes>
<Code range="33 126"/>
<Code range="192 382"/> <!-- Central and Eastern European languages glyphs -->
<Code range="1025 1105"/>
<Code range="8470"/>
<Code range="8216 8217"/> <!-- Single quotes -->
<Code hide="128"/>
<Code hide="1026 1039"/>
<Code hide="1104"/>
</Codes>
</Resource>
<Resource type="ResourceTrueTypeFont" name="Daedric">
<!--<Property key="Source" value="Oblivion/Oblivion Worn.ttf"/>-->
<Property key="Source" value="Oblivion/Oblivion.ttf"/>
<Property key="Size" value="24"/>
<Property key="Resolution" value="72"/>
<Property key="Antialias" value="false"/>
<Property key="TabWidth" value="8"/>
<Property key="OffsetHeight" value="0"/>
<Codes>
<Code range="65 122"/>
</Codes>
</Resource>
<Resource type="ResourceTrueTypeFont" name="MonoFont">
<Property key="Source" value="VeraMono.ttf"/>
<Property key="Size" value="18"/>
<Property key="Resolution" value="50"/>
<Property key="Antialias" value="false"/>
<Property key="TabWidth" value="8"/>
<Property key="CursorWidth" value="2"/>
<Property key="OffsetHeight" value="0"/>
<Codes>
<Code range="33 126"/>
@ -37,4 +49,4 @@
<Code hide="1104"/>
</Codes>
</Resource>
</MyGUI>
</MyGUI>

@ -0,0 +1,35 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Layout">
<Widget type="Window" skin="" layer="Windows" align="Left|Top" position="0 0 512 256" name="_Main">
<Widget type="ImageBox" skin="ImageBox" position_real="0 0 1 1" align="Top|Right" name="BookImage">
<Property key="ImageTexture" value="textures\tx_menubook.dds"/>
<Widget type="Button" skin="ButtonImage" position="251 220 96 24" name="NextPageBTN">
<Property key="ImageResource" value="MenuBook_Next"/>
</Widget>
<Widget type="Button" skin="ButtonImage" position="165 220 96 24" name="PrevPageBTN">
<Property key="ImageResource" value="MenuBook_Prev"/>
</Widget>
<Widget type="Button" skin="ButtonImage" position="75 220 96 24" name="TakeButton">
<Property key="ImageResource" value="MenuBook_Take"/>
</Widget>
<Widget type="Button" skin="ButtonImage" position="360 220 96 24" name="CloseButton">
<Property key="ImageResource" value="MenuBook_Close"/>
</Widget>
<Widget type="TextBox" skin="NormalText" position="155 215 24 24" name="LeftPageNumber">
<Property key="TextColour" value="0 0 0"/>
</Widget>
<Widget type="TextBox" skin="NormalText" position="325 215 24 24" name="RightPageNumber">
<Property key="TextColour" value="0 0 0"/>
</Widget>
<Widget type="Widget" skin="" position_real="0.15 0.1 0.3 0.75" name = "LeftPage"/>
<Widget type="Widget" skin="" position_real="0.55 0.1 0.3 0.75" name = "RightPage"/>
</Widget>
</Widget>
</MyGUI>

@ -19,7 +19,7 @@
<Widget type="EditBox" skin="MW_DispositionEdit" position_real = "0 0 1 1" align="Stretch" name = "DispositionText"/>
</Widget>
<!-- The list of topics -->
<Widget type="ListBox" skin="MW_List" position="432 31 132 328" name="TopicsList" align="Right VStretch">
<Widget type="MWList" skin="MW_SimpleList" position="432 31 132 328" name="TopicsList" align="Right VStretch">
</Widget>
<!-- The Goodbye button -->

@ -1,39 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Resource">
<Resource type="ResourceImageSet" name="ArrowPointerImage">
<Group name="Pointer" texture="textures\tx_cursor.dds" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="HResizePointerImage">
<Group name="Pointer" texture="textures\tx_cursormove.dds" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="VResizePointerImage">
<Group name="Pointer" texture="mwpointer_vresize.png" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="DResizePointerImage">
<Group name="Pointer" texture="mwpointer_dresize1.png" size="32 32">
<Index name="Pointer" >
<Frame point="o o"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="DResize2PointerImage">
<Group name="Pointer" texture="mwpointer_dresize2.png" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
</MyGUI>

@ -7,14 +7,14 @@
<Widget type="ImageBox" skin="ImageBox" position_real="0 0 1 1" align="Top|Right" name="JImage">
<Property key="ImageTexture" value="textures\tx_menubook.dds"/>
<Widget type="Button" skin="Next_btn" position="370 220 64 32" name="NextPageBTN">
<Widget type="Button" skin="ButtonImage" position="370 220 96 24" name="NextPageBTN">
<Property key="ImageResource" value="MenuBook_Next"/>
</Widget>
<Widget type="Button" skin="Prev_btn" position="80 220 128 32" name="PrevPageBTN">
<Widget type="Button" skin="ButtonImage" position="80 220 96 24" name="PrevPageBTN">
<Property key="ImageResource" value="MenuBook_Prev"/>
</Widget>
<Widget type="EditBox" skin="MW_BookPage" position_real="0.15 0.1 0.3 0.8" name = "LeftText"/>
<Widget type="EditBox" skin="MW_BookPage" position_real="0.55 0.1 0.3 0.8" name = "RightText"/>
<Widget type="EditBox" skin="MW_BookPage" position_real="0.15 0.1 0.3 0.75" name = "LeftText"/>
<Widget type="EditBox" skin="MW_BookPage" position_real="0.55 0.1 0.3 0.75" name = "RightText"/>
</Widget>
</Widget>

@ -1,18 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Skin">
<Skin name="Next_btn" size="64 32" texture="textures\tx_menubook_next_idle.dds">
<BasisSkin type="MainSkin" offset="0 0 64 32" align="ALIGN_VSTRETCH">
<State name="normal" offset="0 0 64 32"/>
</BasisSkin>
</Skin>
<Skin name="Prev_btn" size="128 32" texture="textures\tx_menubook_prev_idle.dds">
<BasisSkin type="MainSkin" offset="0 0 128 32" align="ALIGN_VSTRETCH">
<State name="normal" offset="0 0 128 32"/>
</BasisSkin>
</Skin>
<Skin name = "MW_BookClient" size = "10 10">
<Property key="FontName" value = "Default" />
<Property key="TextAlign" value = "Left Top" />

@ -212,6 +212,20 @@
<Child type="Widget" skin="IB_BR" offset="514 514 2 2" align="ALIGN_BOTTOM ALIGN_RIGHT"/>
</Skin>
<Skin name = "MW_SimpleList" size = "516 516" align = "ALIGN_LEFT ALIGN_TOP" texture="mwgui.png">
<Child type="Widget" skin="" offset = "3 3 510 510" align = "ALIGN_STRETCH" name = "Client">
</Child>
<Child type="Widget" skin="IB_T" offset="2 0 512 2" align="ALIGN_TOP ALIGN_HSTRETCH"/>
<Child type="Widget" skin="IB_B" offset="2 514 512 2" align="ALIGN_BOTTOM ALIGN_HSTRETCH"/>
<Child type="Widget" skin="IB_L" offset="0 2 2 512" align="ALIGN_LEFT ALIGN_VSTRETCH"/>
<Child type="Widget" skin="IB_R" offset="514 2 2 512" align="ALIGN_RIGHT ALIGN_VSTRETCH"/>
<Child type="Widget" skin="IB_TL" offset="0 0 2 2" align="ALIGN_TOP ALIGN_LEFT"/>
<Child type="Widget" skin="IB_TR" offset="514 0 2 2" align="ALIGN_TOP ALIGN_RIGHT"/>
<Child type="Widget" skin="IB_BL" offset="0 514 2 2" align="ALIGN_BOTTOM ALIGN_LEFT"/>
<Child type="Widget" skin="IB_BR" offset="514 514 2 2" align="ALIGN_BOTTOM ALIGN_RIGHT"/>
</Skin>
<Skin name = "MW_MultiSubList" size = "516 516" align = "ALIGN_LEFT ALIGN_TOP">
<Property key="NeedKey" value = "true" />
<Property key="SkinLine" value = "MW_ListLine" />

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Resource">
<Resource type="ResourceImageSet" name="ArrowPointerImage">
<Group name="Pointer" texture="textures\tx_cursor.dds" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="HResizePointerImage">
<Group name="Pointer" texture="textures\tx_cursormove.dds" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="VResizePointerImage">
<Group name="Pointer" texture="mwpointer_vresize.png" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="DResizePointerImage">
<Group name="Pointer" texture="mwpointer_dresize1.png" size="32 32">
<Index name="Pointer" >
<Frame point="o o"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="DResize2PointerImage">
<Group name="Pointer" texture="mwpointer_dresize2.png" size="32 32">
<Index name="Pointer" >
<Frame point="0 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="MenuBook_Close">
<Group name="States" texture="mwgui1" size="96 24">
<Index name="disabled">
<Frame point="0 0"/>
</Index>
<Index name="normal">
<Frame point="0 0"/>
</Index>
<Index name="highlighted">
<Frame point="128 0"/>
</Index>
<Index name="pushed">
<Frame point="256 0"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="MenuBook_Take">
<Group name="States" texture="mwgui1" size="96 24">
<Index name="disabled">
<Frame point="384 0"/>
</Index>
<Index name="normal">
<Frame point="384 0"/>
</Index>
<Index name="highlighted">
<Frame point="0 32"/>
</Index>
<Index name="pushed">
<Frame point="128 32"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="MenuBook_Next">
<Group name="States" texture="mwgui1" size="96 24">
<Index name="disabled">
<Frame point="256 32"/>
</Index>
<Index name="normal">
<Frame point="256 32"/>
</Index>
<Index name="highlighted">
<Frame point="384 32"/>
</Index>
<Index name="pushed">
<Frame point="0 64"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceImageSet" name="MenuBook_Prev">
<Group name="States" texture="mwgui1" size="96 24">
<Index name="disabled">
<Frame point="128 64"/>
</Index>
<Index name="normal">
<Frame point="128 64"/>
</Index>
<Index name="highlighted">
<Frame point="256 64"/>
</Index>
<Index name="pushed">
<Frame point="384 64"/>
</Index>
</Group>
</Resource>
<Resource type="ResourceLayout" name="ButtonImage" version="3.2.0">
<Widget type="Widget" skin="Default" position="20 20 16 16" name="Root">
<Property key="TextAlign" value="Center"/>
<Property key="FontName" value="Default"/>
<Property key="ModeImage" value="true"/>
<Widget type="ImageBox" skin="ImageBox" position="0 0 16 16" align="Stretch" name="Image">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
</Resource>
</MyGUI>

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Layout">
<Widget type="Window" skin="" layer="Windows" position="0 0 512 512" name="_Main">
<Widget type="ImageBox" skin="ImageBox" position_real="0 0 1 1" name="ScrollImage">
<Property key="ImageTexture" value="textures\scroll.dds"/>
<Widget type="Button" skin="ButtonImage" position="12 18 96 24" name="TakeButton">
<Property key="ImageResource" value="MenuBook_Take"/>
</Widget>
<Widget type="Button" skin="ButtonImage" position="418 24 96 24" name="CloseButton">
<Property key="ImageResource" value="MenuBook_Close"/>
</Widget>
<Widget type="ScrollView" skin="MW_ScrollView" position="60 130 410 300" name="TextView">
<Property key="CanvasSize" value="410 900"/>
</Widget>
</Widget>
</Widget>
</MyGUI>

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Skin">
<Skin name="MW_ScrollView" size="516 516" texture="mwgui.png">
<Child type="Widget" skin="" offset="0 0 516 516" align="Stretch" name="Client"/>
<Child type="ScrollBar" skin="MW_VScroll" offset="498 3 14 509" align="ALIGN_RIGHT ALIGN_VSTRETCH" name="VScroll"/>
</Skin>
</MyGUI>

@ -26,34 +26,34 @@
<Widget type="TextBox" skin="SandTextRight" position="104 40 104 18" name="ClassText"/>
</Widget>
<Widget type="Widget" skin="MW_Box" position="8 148 212 152">
<Widget type="TextBox" skin="SandText" position="4 4 100 18" name="Attrib1"/>
<Widget type="TextBox" skin="SandTextRight" position="104 4 104 18" name="AttribVal1"/>
<Widget type="Widget" skin="MW_Box" position="8 148 212 152" align="ALIGN_LEFT ALIGN_TOP ALIGN_VSTRETCH">
<Widget type="TextBox" skin="SandText" position="4 4 160 18" name="Attrib1"/>
<Widget type="TextBox" skin="SandTextRight" position="164 4 44 18" name="AttribVal1"/>
<Widget type="TextBox" skin="SandText" position="4 22 100 18" name="Attrib2"/>
<Widget type="TextBox" skin="SandTextRight" position="104 22 104 18" name="AttribVal2"/>
<Widget type="TextBox" skin="SandText" position="4 22 160 18" name="Attrib2"/>
<Widget type="TextBox" skin="SandTextRight" position="164 22 44 18" name="AttribVal2"/>
<Widget type="TextBox" skin="SandText" position="4 40 100 18" name="Attrib3"/>
<Widget type="TextBox" skin="SandTextRight" position="104 40 104 18" name="AttribVal3"/>
<Widget type="TextBox" skin="SandText" position="4 40 160 18" name="Attrib3"/>
<Widget type="TextBox" skin="SandTextRight" position="164 40 44 18" name="AttribVal3"/>
<Widget type="TextBox" skin="SandText" position="4 58 100 18" name="Attrib4"/>
<Widget type="TextBox" skin="SandTextRight" position="104 58 104 18" name="AttribVal4"/>
<Widget type="TextBox" skin="SandText" position="4 58 160 18" name="Attrib4"/>
<Widget type="TextBox" skin="SandTextRight" position="164 58 44 18" name="AttribVal4"/>
<Widget type="TextBox" skin="SandText" position="4 76 100 18" name="Attrib5"/>
<Widget type="TextBox" skin="SandTextRight" position="104 76 104 18" name="AttribVal5"/>
<Widget type="TextBox" skin="SandText" position="4 76 160 18" name="Attrib5"/>
<Widget type="TextBox" skin="SandTextRight" position="164 76 44 18" name="AttribVal5"/>
<Widget type="TextBox" skin="SandText" position="4 94 100 18" name="Attrib6"/>
<Widget type="TextBox" skin="SandTextRight" position="104 94 104 18" name="AttribVal6"/>
<Widget type="TextBox" skin="SandText" position="4 94 160 18" name="Attrib6"/>
<Widget type="TextBox" skin="SandTextRight" position="164 94 44 18" name="AttribVal6"/>
<Widget type="TextBox" skin="SandText" position="4 112 100 18" name="Attrib7"/>
<Widget type="TextBox" skin="SandTextRight" position="104 112 104 18" name="AttribVal7"/>
<Widget type="TextBox" skin="SandText" position="4 112 160 18" name="Attrib7"/>
<Widget type="TextBox" skin="SandTextRight" position="164 112 44 18" name="AttribVal7"/>
<Widget type="TextBox" skin="SandText" position="4 130 100 18" name="Attrib8"/>
<Widget type="TextBox" skin="SandTextRight" position="104 130 104 18" name="AttribVal8"/>
<Widget type="TextBox" skin="SandText" position="4 130 160 18" name="Attrib8"/>
<Widget type="TextBox" skin="SandTextRight" position="164 130 44 18" name="AttribVal8"/>
</Widget>
<!-- Player skills, factions, birthsign and reputation -->
<Widget type="Widget" skin="MW_Box" position="228 8 248 292" align="ALIGN_LEFT ALIGN_VSTRETCH" name="Skills">
<Widget type="Widget" skin="MW_Box" position="228 8 248 292" align="ALIGN_LEFT ALIGN_STRETCH" name="Skills">
<Widget type="Widget" skin="" position="4 4 222 284" align="ALIGN_STRETCH" name="SkillClient" />
<Widget type="ScrollBar" skin="MW_VScroll" position="230 4 14 284" align="ALIGN_RIGHT ALIGN_VSTRETCH" name="SkillScroller" />
</Widget>

@ -0,0 +1,113 @@
#include "atlas.hpp"
#include <OgreRoot.h>
#include <OgreSceneManager.h>
#include <OgreImage.h>
#include <OgreTexture.h>
#include <OgreRenderTarget.h>
#include <OgreCamera.h>
#include <OgreTextureUnitState.h>
#include <OgreHardwarePixelBuffer.h>
#include <OgreConfigFile.h>
#include <OgreStringConverter.h>
using namespace Ogre;
using namespace OEngine::Render;
void Atlas::createFromFile (const std::string& filename, const std::string& textureName, const std::string& texturePrefix)
{
ConfigFile file;
file.load(filename, ResourceGroupManager::AUTODETECT_RESOURCE_GROUP_NAME, "\t:=", true);
Root* root = Ogre::Root::getSingletonPtr();
SceneManager* sceneMgr = root->createSceneManager(ST_GENERIC);
Camera* camera = sceneMgr->createCamera("AtlasCamera");
int width = StringConverter::parseInt(file.getSetting("size_x", "settings"));
int height = StringConverter::parseInt(file.getSetting("size_y", "settings"));
std::vector<Rectangle2D*> rectangles;
int i = 0;
ConfigFile::SectionIterator seci = file.getSectionIterator();
while (seci.hasMoreElements())
{
Ogre::String sectionName = seci.peekNextKey();
seci.getNext();
if (sectionName == "settings" || sectionName == "")
continue;
MaterialPtr material = MaterialManager::getSingleton().create("AtlasMaterial" + StringConverter::toString(i), ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
material->getTechnique(0)->getPass(0)->setLightingEnabled(false);
material->getTechnique(0)->getPass(0)->setDepthCheckEnabled(false);
TextureUnitState* tus = material->getTechnique(0)->getPass(0)->createTextureUnitState(texturePrefix + sectionName);
tus->setTextureBorderColour(ColourValue(0, 0, 0, 0));
Rectangle2D* rect = new Rectangle2D(true);
rect->setMaterial("AtlasMaterial" + StringConverter::toString(i));
rect->setRenderQueueGroup(RENDER_QUEUE_BACKGROUND);
int x = StringConverter::parseInt(file.getSetting("x", sectionName));
int y = StringConverter::parseInt(file.getSetting("y", sectionName));
TexturePtr texture = TextureManager::getSingleton().getByName(texturePrefix + sectionName);
if (texture.isNull())
{
std::cerr << "OEngine::Render::Atlas: Can't find texture " << texturePrefix + sectionName << ", skipping..." << std::endl;
continue;
}
int textureWidth = texture->getWidth();
int textureHeight = texture->getHeight();
float left = x/float(width) * 2 - 1;
float top = (1-(y/float(height))) * 2 - 1;
float right = ((x+textureWidth))/float(width) * 2 - 1;
float bottom = (1-((y+textureHeight)/float(height))) * 2 - 1;
rect->setCorners(left, top, right, bottom);
// Use infinite AAB to always stay visible
AxisAlignedBox aabInf;
aabInf.setInfinite();
rect->setBoundingBox(aabInf);
// Attach background to the scene
SceneNode* node = sceneMgr->getRootSceneNode()->createChildSceneNode();
node->attachObject(rect);
rectangles.push_back(rect);
++i;
}
TexturePtr destTexture = TextureManager::getSingleton().createManual(
textureName,
ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME,
TEX_TYPE_2D,
width, height,
0,
PF_FLOAT16_RGBA,
TU_RENDERTARGET);
RenderTarget* rtt = destTexture->getBuffer()->getRenderTarget();
rtt->setAutoUpdated(false);
Viewport* vp = rtt->addViewport(camera);
vp->setOverlaysEnabled(false);
vp->setShadowsEnabled(false);
vp->setBackgroundColour(ColourValue(0,0,0,0));
rtt->update();
// remove all the junk we've created
for (std::vector<Rectangle2D*>::iterator it=rectangles.begin();
it!=rectangles.end(); ++it)
{
delete (*it);
}
while (i > 0)
{
MaterialManager::getSingleton().remove("AtlasMaterial" + StringConverter::toString(i-1));
--i;
}
root->destroySceneManager(sceneMgr);
}

@ -0,0 +1,27 @@
#ifndef OENGINE_OGRE_ATLAS_HPP
#define OENGINE_OGRE_ATLAS_HPP
#include <string>
namespace OEngine
{
namespace Render
{
/// \brief Creates a texture atlas at runtime
class Atlas
{
public:
/**
* @param absolute path to file that specifies layout of the texture (positions of the textures it contains)
* @param name of the destination texture to save to (in memory)
* @param texture directory prefix
*/
static void createFromFile (const std::string& filename, const std::string& textureName, const std::string& texturePrefix="textures\\");
};
}
}
#endif
Loading…
Cancel
Save