forked from mirror/openmw-tes3mp
Merged pull request #1568
This commit is contained in:
commit
b151a89528
11 changed files with 122 additions and 28 deletions
|
@ -244,7 +244,7 @@ BookTypesetter::Ptr JournalBooks::createLatinJournalIndex ()
|
|||
const MWGui::TextColours& textColours = MWBase::Environment::get().getWindowManager()->getTextColours();
|
||||
BookTypesetter::Style* style = typesetter->createHotStyle (body, textColours.journalTopic,
|
||||
textColours.journalTopicOver,
|
||||
textColours.journalTopicPressed, (uint32_t) ch);
|
||||
textColours.journalTopicPressed, (Utf8Stream::UnicodeChar) ch);
|
||||
|
||||
if (i == 13)
|
||||
typesetter->sectionBreak ();
|
||||
|
@ -274,7 +274,7 @@ BookTypesetter::Ptr JournalBooks::createCyrillicJournalIndex ()
|
|||
sprintf(buffer, "( %c%c )", ch[0], ch[1]);
|
||||
|
||||
Utf8Stream stream ((char*) ch);
|
||||
uint32_t first = stream.peek();
|
||||
Utf8Stream::UnicodeChar first = stream.peek();
|
||||
|
||||
const MWGui::TextColours& textColours = MWBase::Environment::get().getWindowManager()->getTextColours();
|
||||
BookTypesetter::Style* style = typesetter->createHotStyle (body, textColours.journalTopic,
|
||||
|
|
|
@ -7,7 +7,6 @@
|
|||
|
||||
#include <components/translation/translation.hpp>
|
||||
#include <components/misc/stringops.hpp>
|
||||
#include <components/misc/utf8stream.hpp>
|
||||
|
||||
#include "../mwbase/world.hpp"
|
||||
#include "../mwbase/journal.hpp"
|
||||
|
@ -307,39 +306,22 @@ struct JournalViewModelImpl : JournalViewModel
|
|||
visitor (toUtf8Span (topic.getName()));
|
||||
}
|
||||
|
||||
void visitTopicNamesStartingWith (uint32_t character, std::function < void (const std::string&) > visitor) const
|
||||
void visitTopicNamesStartingWith (Utf8Stream::UnicodeChar character, std::function < void (const std::string&) > visitor) const
|
||||
{
|
||||
MWBase::Journal * journal = MWBase::Environment::get().getJournal();
|
||||
|
||||
for (MWBase::Journal::TTopicIter i = journal->topicBegin (); i != journal->topicEnd (); ++i)
|
||||
{
|
||||
Utf8Stream stream (i->first.c_str());
|
||||
uint32_t first = toUpper(stream.peek());
|
||||
Utf8Stream::UnicodeChar first = Misc::StringUtils::toLowerUtf8(stream.peek());
|
||||
|
||||
if (first != character)
|
||||
if (first != Misc::StringUtils::toLowerUtf8(character))
|
||||
continue;
|
||||
|
||||
visitor (i->second.getName());
|
||||
}
|
||||
}
|
||||
|
||||
static uint32_t toUpper(uint32_t ch)
|
||||
{
|
||||
// Russian alphabet
|
||||
if (ch >= 0x0430 && ch < 0x0450)
|
||||
ch -= 0x20;
|
||||
|
||||
// Cyrillic IO character
|
||||
if (ch == 0x0451)
|
||||
ch -= 0x50;
|
||||
|
||||
// Latin alphabet
|
||||
if (ch >= 0x61 && ch < 0x80)
|
||||
ch -= 0x20;
|
||||
|
||||
return ch;
|
||||
}
|
||||
|
||||
struct TopicEntryImpl : BaseEntry <MWDialogue::Topic::TEntryIter, TopicEntry>
|
||||
{
|
||||
MWDialogue::Topic const & mTopic;
|
||||
|
|
|
@ -6,6 +6,8 @@
|
|||
#include <functional>
|
||||
#include <stdint.h>
|
||||
|
||||
#include <components/misc/utf8stream.hpp>
|
||||
|
||||
namespace MWGui
|
||||
{
|
||||
/// View-Model for the journal GUI
|
||||
|
@ -76,7 +78,7 @@ namespace MWGui
|
|||
virtual void visitTopicName (TopicId topicId, std::function <void (Utf8Span)> visitor) const = 0;
|
||||
|
||||
/// walks over the topics whose names start with the character
|
||||
virtual void visitTopicNamesStartingWith (uint32_t character, std::function < void (const std::string&) > visitor) const = 0;
|
||||
virtual void visitTopicNamesStartingWith (Utf8Stream::UnicodeChar character, std::function < void (const std::string&) > visitor) const = 0;
|
||||
|
||||
/// walks over the topic entries for the topic specified by its identifier
|
||||
virtual void visitTopicEntries (TopicId topicId, std::function <void (TopicEntry const &)> visitor) const = 0;
|
||||
|
|
|
@ -14,6 +14,9 @@ namespace MWGui
|
|||
|
||||
bool shouldAcceptKeyFocus(MyGUI::Widget* w)
|
||||
{
|
||||
if (w && w->getUserString("IgnoreTabKey") == "y")
|
||||
return false;
|
||||
|
||||
return w && !w->castType<MyGUI::Window>(false) && w->getInheritedEnabled() && w->getInheritedVisible() && w->getVisible() && w->getEnabled();
|
||||
}
|
||||
|
||||
|
|
|
@ -32,10 +32,14 @@ namespace
|
|||
namespace MWGui
|
||||
{
|
||||
|
||||
SpellModel::SpellModel(const MWWorld::Ptr &actor, const std::string& filter)
|
||||
: mActor(actor), mFilter(filter)
|
||||
{
|
||||
}
|
||||
|
||||
SpellModel::SpellModel(const MWWorld::Ptr &actor)
|
||||
: mActor(actor)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void SpellModel::update()
|
||||
|
@ -48,12 +52,19 @@ namespace MWGui
|
|||
const MWWorld::ESMStore &esmStore =
|
||||
MWBase::Environment::get().getWorld()->getStore();
|
||||
|
||||
std::string filter = Misc::StringUtils::lowerCaseUtf8(mFilter);
|
||||
|
||||
for (MWMechanics::Spells::TIterator it = spells.begin(); it != spells.end(); ++it)
|
||||
{
|
||||
const ESM::Spell* spell = it->first;
|
||||
if (spell->mData.mType != ESM::Spell::ST_Power && spell->mData.mType != ESM::Spell::ST_Spell)
|
||||
continue;
|
||||
|
||||
std::string name = Misc::StringUtils::lowerCaseUtf8(spell->mName);
|
||||
|
||||
if (name.find(filter) == std::string::npos)
|
||||
continue;
|
||||
|
||||
Spell newSpell;
|
||||
newSpell.mName = spell->mName;
|
||||
if (spell->mData.mType == ESM::Spell::ST_Spell)
|
||||
|
@ -89,6 +100,11 @@ namespace MWGui
|
|||
if (enchant->mData.mType != ESM::Enchantment::WhenUsed && enchant->mData.mType != ESM::Enchantment::CastOnce)
|
||||
continue;
|
||||
|
||||
std::string name = Misc::StringUtils::lowerCaseUtf8(item.getClass().getName(item));
|
||||
|
||||
if (name.find(filter) == std::string::npos)
|
||||
continue;
|
||||
|
||||
Spell newSpell;
|
||||
newSpell.mItem = item;
|
||||
newSpell.mId = item.getCellRef().getRefId();
|
||||
|
|
|
@ -35,6 +35,7 @@ namespace MWGui
|
|||
class SpellModel
|
||||
{
|
||||
public:
|
||||
SpellModel(const MWWorld::Ptr& actor, const std::string& filter);
|
||||
SpellModel(const MWWorld::Ptr& actor);
|
||||
|
||||
typedef int ModelIndex;
|
||||
|
@ -50,6 +51,8 @@ namespace MWGui
|
|||
MWWorld::Ptr mActor;
|
||||
|
||||
std::vector<Spell> mSpells;
|
||||
|
||||
std::string mFilter;
|
||||
};
|
||||
|
||||
}
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
#include <boost/format.hpp>
|
||||
|
||||
#include <MyGUI_EditBox.h>
|
||||
#include <MyGUI_InputManager.h>
|
||||
|
||||
#include <components/settings/settings.hpp>
|
||||
|
@ -38,8 +39,12 @@ namespace MWGui
|
|||
|
||||
getWidget(mSpellView, "SpellView");
|
||||
getWidget(mEffectBox, "EffectsBox");
|
||||
getWidget(mFilterEdit, "FilterEdit");
|
||||
|
||||
mFilterEdit->setUserString("IgnoreTabKey", "y");
|
||||
|
||||
mSpellView->eventSpellClicked += MyGUI::newDelegate(this, &SpellWindow::onModelIndexSelected);
|
||||
mFilterEdit->eventEditTextChange += MyGUI::newDelegate(this, &SpellWindow::onFilterChanged);
|
||||
|
||||
setCoord(498, 300, 302, 300);
|
||||
}
|
||||
|
@ -64,6 +69,11 @@ namespace MWGui
|
|||
|
||||
void SpellWindow::onOpen()
|
||||
{
|
||||
// Reset the filter focus when opening the window
|
||||
MyGUI::Widget* focus = MyGUI::InputManager::getInstance().getKeyFocusWidget();
|
||||
if (focus == mFilterEdit)
|
||||
MWBase::Environment::get().getWindowManager()->setKeyFocusWidget(NULL);
|
||||
|
||||
updateSpells();
|
||||
}
|
||||
|
||||
|
@ -82,7 +92,7 @@ namespace MWGui
|
|||
{
|
||||
mSpellIcons->updateWidgets(mEffectBox, false);
|
||||
|
||||
mSpellView->setModel(new SpellModel(MWMechanics::getPlayer()));
|
||||
mSpellView->setModel(new SpellModel(MWMechanics::getPlayer(), mFilterEdit->getCaption()));
|
||||
}
|
||||
|
||||
void SpellWindow::onEnchantedItemSelected(MWWorld::Ptr item, bool alreadyEquipped)
|
||||
|
@ -167,6 +177,11 @@ namespace MWGui
|
|||
}
|
||||
}
|
||||
|
||||
void SpellWindow::onFilterChanged(MyGUI::EditBox *sender)
|
||||
{
|
||||
mSpellView->setModel(new SpellModel(MWMechanics::getPlayer(), sender->getCaption()));
|
||||
}
|
||||
|
||||
void SpellWindow::onSpellSelected(const std::string& spellId)
|
||||
{
|
||||
MWWorld::Ptr player = MWMechanics::getPlayer();
|
||||
|
@ -202,7 +217,7 @@ namespace MWGui
|
|||
if (stats.isParalyzed() || stats.getKnockedDown() || stats.isDead() || stats.getHitRecovery())
|
||||
return;
|
||||
|
||||
mSpellView->setModel(new SpellModel(MWMechanics::getPlayer()));
|
||||
mSpellView->setModel(new SpellModel(MWMechanics::getPlayer(), ""));
|
||||
|
||||
SpellModel::ModelIndex selected = 0;
|
||||
for (SpellModel::ModelIndex i = 0; i<int(mSpellView->getModel()->getItemCount()); ++i)
|
||||
|
|
|
@ -32,6 +32,7 @@ namespace MWGui
|
|||
void onEnchantedItemSelected(MWWorld::Ptr item, bool alreadyEquipped);
|
||||
void onSpellSelected(const std::string& spellId);
|
||||
void onModelIndexSelected(SpellModel::ModelIndex index);
|
||||
void onFilterChanged(MyGUI::EditBox *sender);
|
||||
void onDeleteSpellAccept();
|
||||
void askDeleteSpell(const std::string& spellId);
|
||||
|
||||
|
@ -41,6 +42,7 @@ namespace MWGui
|
|||
|
||||
SpellView* mSpellView;
|
||||
SpellIcons* mSpellIcons;
|
||||
MyGUI::EditBox* mFilterEdit;
|
||||
|
||||
private:
|
||||
float mUpdateTimer;
|
||||
|
|
|
@ -6,6 +6,8 @@
|
|||
#include <string>
|
||||
#include <algorithm>
|
||||
|
||||
#include "utf8stream.hpp"
|
||||
|
||||
namespace Misc
|
||||
{
|
||||
class StringUtils
|
||||
|
@ -56,6 +58,70 @@ public:
|
|||
};
|
||||
}
|
||||
|
||||
static Utf8Stream::UnicodeChar toLowerUtf8(Utf8Stream::UnicodeChar ch)
|
||||
{
|
||||
// Russian alphabet
|
||||
if (ch >= 0x0410 && ch < 0x0430)
|
||||
return ch += 0x20;
|
||||
|
||||
// Cyrillic IO character
|
||||
if (ch == 0x0401)
|
||||
return ch += 0x50;
|
||||
|
||||
// Latin alphabet
|
||||
if (ch >= 0x41 && ch < 0x60)
|
||||
return ch += 0x20;
|
||||
|
||||
// Deutch characters
|
||||
if (ch == 0xc4 || ch == 0xd6 || ch == 0xdc)
|
||||
return ch += 0x20;
|
||||
if (ch == 0x1e9e)
|
||||
return 0xdf;
|
||||
|
||||
// TODO: probably we will need to support characters from other languages
|
||||
|
||||
return ch;
|
||||
}
|
||||
|
||||
static std::string lowerCaseUtf8(const std::string str)
|
||||
{
|
||||
if (str.empty())
|
||||
return str;
|
||||
|
||||
// Decode string as utf8 characters, convert to lower case and pack them to string
|
||||
std::string out;
|
||||
Utf8Stream stream (str.c_str());
|
||||
while (!stream.eof ())
|
||||
{
|
||||
Utf8Stream::UnicodeChar character = toLowerUtf8(stream.peek());
|
||||
|
||||
if (character <= 0x7f)
|
||||
out.append(1, static_cast<char>(character));
|
||||
else if (character <= 0x7ff)
|
||||
{
|
||||
out.append(1, static_cast<char>(0xc0 | ((character >> 6) & 0x1f)));
|
||||
out.append(1, static_cast<char>(0x80 | (character & 0x3f)));
|
||||
}
|
||||
else if (character <= 0xffff)
|
||||
{
|
||||
out.append(1, static_cast<char>(0xe0 | ((character >> 12) & 0x0f)));
|
||||
out.append(1, static_cast<char>(0x80 | ((character >> 6) & 0x3f)));
|
||||
out.append(1, static_cast<char>(0x80 | (character & 0x3f)));
|
||||
}
|
||||
else
|
||||
{
|
||||
out.append(1, static_cast<char>(0xf0 | ((character >> 18) & 0x07)));
|
||||
out.append(1, static_cast<char>(0x80 | ((character >> 12) & 0x3f)));
|
||||
out.append(1, static_cast<char>(0x80 | ((character >> 6) & 0x3f)));
|
||||
out.append(1, static_cast<char>(0x80 | (character & 0x3f)));
|
||||
}
|
||||
|
||||
stream.consume();
|
||||
}
|
||||
|
||||
return out;
|
||||
}
|
||||
|
||||
static bool ciLess(const std::string &x, const std::string &y) {
|
||||
return std::lexicographical_compare(x.begin(), x.end(), y.begin(), y.end(), ci());
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#ifndef MISC_UTF8ITER_HPP
|
||||
#define MISC_UTF8ITER_HPP
|
||||
|
||||
#include <cstring>
|
||||
#include <tuple>
|
||||
|
||||
class Utf8Stream
|
||||
|
|
|
@ -10,7 +10,11 @@
|
|||
</Widget>
|
||||
|
||||
<!-- Spell list -->
|
||||
<Widget type="SpellView" skin="MW_SpellView" position="8 38 268 518" align="Left Top Stretch" name="SpellView">
|
||||
<Widget type="SpellView" skin="MW_SpellView" position="8 38 268 490" align="Left Top Stretch" name="SpellView">
|
||||
</Widget>
|
||||
|
||||
<!-- Search box-->
|
||||
<Widget type="EditBox" skin="MW_TextBoxEditWithBorder" position="8 535 268 23" align="Left Bottom HStretch" name="FilterEdit">
|
||||
</Widget>
|
||||
|
||||
</Widget>
|
||||
|
|
Loading…
Reference in a new issue