1
0
Fork 0
mirror of https://github.com/OpenMW/openmw.git synced 2025-06-30 19:41:34 +00:00

new alternate

This commit is contained in:
kuyondo 2021-11-28 04:47:14 +08:00
commit eadad7a4b3
12 changed files with 108 additions and 46 deletions

View file

@ -80,7 +80,9 @@
Bug #6386: Artifacts in water reflection due to imprecise screen-space coordinate computation
Bug #6396: Inputting certain Unicode characters triggers an assertion
Bug #6416: Morphs are applied to the wrong target
Bug #6417: OpenMW doesn't always use the right node to accumulate movement
Bug #6429: Wyrmhaven: Can't add AI packages to player
Bug #6433: Items bound to Quick Keys sometimes do not appear until the Quick Key menu is opened.
Feature #890: OpenMW-CS: Column filtering
Feature #1465: "Reset" argument for AI functions
Feature #2554: Modifying an object triggers the instances table to scroll to the corresponding record

View file

@ -69,6 +69,7 @@ namespace MWGui
class DialogueWindow;
class WindowModal;
class JailScreen;
class MessageBox;
enum ShowInDialogueMode {
ShowInDialogueMode_IfPossible,
@ -145,6 +146,7 @@ namespace MWBase
virtual MWGui::CountDialog* getCountDialog() = 0;
virtual MWGui::ConfirmationDialog* getConfirmationDialog() = 0;
virtual MWGui::TradeWindow* getTradeWindow() = 0;
virtual const std::vector<MWGui::MessageBox*> getActiveMessageBoxes() = 0;
/// Make the player use an item, while updating GUI state accordingly
virtual void useItem(const MWWorld::Ptr& item, bool force=false) = 0;

View file

@ -170,6 +170,12 @@ namespace MWGui
return false;
}
const std::vector<MessageBox*> MessageBoxManager::getActiveMessageBoxes()
{
return mMessageBoxes;
}
int MessageBoxManager::readPressedButton (bool reset)
{
int pressed = mLastButtonPressed;
@ -211,6 +217,11 @@ namespace MWGui
mMainWidget->setPosition(pos);
}
const std::string MessageBox::getMessage()
{
return mMessage;
}
int MessageBox::getHeight ()
{
return mMainWidget->getHeight()+mNextBoxPadding;

View file

@ -49,6 +49,8 @@ namespace MWGui
void setVisible(bool value);
const std::vector<MessageBox*> getActiveMessageBoxes();
private:
std::vector<MessageBox*> mMessageBoxes;
InteractiveMessageBox* mInterMessageBoxe;
@ -63,6 +65,7 @@ namespace MWGui
public:
MessageBox (MessageBoxManager& parMessageBoxManager, const std::string& message);
void setMessage (const std::string& message);
const std::string getMessage();
int getHeight ();
void update (int height);
void setVisible(bool value);
@ -73,7 +76,7 @@ namespace MWGui
protected:
MessageBoxManager& mMessageBoxManager;
const std::string& mMessage;
const std::string mMessage;
MyGUI::EditBox* mMessageWidget;
int mBottomPadding;
int mNextBoxPadding;

View file

@ -79,41 +79,45 @@ namespace MWGui
delete mMagicSelectionDialog;
}
inline void QuickKeysMenu::validate(int index)
{
MWWorld::Ptr player = MWMechanics::getPlayer();
MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player);
switch (mKey[index].type)
{
case Type_Unassigned:
case Type_HandToHand:
case Type_Magic:
break;
case Type_Item:
case Type_MagicItem:
{
MWWorld::Ptr item = *mKey[index].button->getUserData<MWWorld::Ptr>();
// Make sure the item is available and is not broken
if (!item || item.getRefData().getCount() < 1 ||
(item.getClass().hasItemHealth(item) &&
item.getClass().getItemHealth(item) <= 0))
{
// Try searching for a compatible replacement
item = store.findReplacement(mKey[index].id);
if (item)
mKey[index].button->setUserData(MWWorld::Ptr(item));
break;
}
}
}
}
void QuickKeysMenu::onOpen()
{
WindowBase::onOpen();
MWWorld::Ptr player = MWMechanics::getPlayer();
MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player);
// Check if quick keys are still valid
for (int i=0; i<10; ++i)
// Quick key index
for (int index = 0; index < 10; ++index)
{
switch (mKey[i].type)
{
case Type_Unassigned:
case Type_HandToHand:
case Type_Magic:
break;
case Type_Item:
case Type_MagicItem:
{
MWWorld::Ptr item = *mKey[i].button->getUserData<MWWorld::Ptr>();
// Make sure the item is available and is not broken
if (!item || item.getRefData().getCount() < 1 ||
(item.getClass().hasItemHealth(item) &&
item.getClass().getItemHealth(item) <= 0))
{
// Try searching for a compatible replacement
item = store.findReplacement(mKey[i].id);
if (item)
mKey[i].button->setUserData(MWWorld::Ptr(item));
break;
}
}
}
validate(index);
}
}
@ -329,11 +333,13 @@ namespace MWGui
assert(index >= 1 && index <= 10);
keyData *key = &mKey[index-1];
MWWorld::Ptr player = MWMechanics::getPlayer();
MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player);
const MWMechanics::CreatureStats &playerStats = player.getClass().getCreatureStats(player);
validate(index-1);
// Delay action executing,
// if player is busy for now (casting a spell, attacking someone, etc.)
bool isDelayNeeded = MWBase::Environment::get().getMechanicsManager()->isAttackingOrSpell(player)

View file

@ -76,7 +76,8 @@ namespace MWGui
void onQuickKeyButtonClicked(MyGUI::Widget* sender);
void onOkButtonClicked(MyGUI::Widget* sender);
// Check if quick key is still valid
inline void validate(int index);
void unassign(keyData* key);
};

View file

@ -771,6 +771,11 @@ namespace MWGui
mMessageBoxManager->removeStaticMessageBox();
}
const std::vector<MWGui::MessageBox*> WindowManager::getActiveMessageBoxes()
{
return mMessageBoxManager->getActiveMessageBoxes();
}
int WindowManager::readPressedButton ()
{
return mMessageBoxManager->readPressedButton();

View file

@ -187,6 +187,7 @@ namespace MWGui
MWGui::CountDialog* getCountDialog() override;
MWGui::ConfirmationDialog* getConfirmationDialog() override;
MWGui::TradeWindow* getTradeWindow() override;
const std::vector<MWGui::MessageBox*> getActiveMessageBoxes() override;
/// Make the player use an item, while updating GUI state accordingly
void useItem(const MWWorld::Ptr& item, bool bypassBeastRestrictions=false) override;

View file

@ -22,6 +22,8 @@
#include "../mwmechanics/npcstats.hpp"
#include "../mwmechanics/actorutil.hpp"
#include "../mwgui/messagebox.hpp"
#include "actions.hpp"
#include "bindingsmanager.hpp"
@ -40,6 +42,7 @@ namespace MWInput
, mSneaking(false)
, mAttemptJump(false)
, mTimeIdle(0.f)
, mOverencumberedMessage("#{sNotifyMessage59}")
{
}
@ -96,7 +99,17 @@ namespace MWInput
if (playerPtr.getClass().getEncumbrance(playerPtr) > playerPtr.getClass().getCapacity(playerPtr))
{
player.setAutoMove (false);
MWBase::Environment::get().getWindowManager()->messageBox("#{sNotifyMessage59}");
std::vector<MWGui::MessageBox*> msgboxs = MWBase::Environment::get().getWindowManager()->getActiveMessageBoxes();
const std::vector<MWGui::MessageBox*>::iterator it = std::find_if(msgboxs.begin(), msgboxs.end(), [=](MWGui::MessageBox*& msgbox)
{
return (msgbox->getMessage() == mOverencumberedMessage);
});
// if an overencumbered messagebox is already present, reset its expiry timer, otherwise create new one.
if (it != msgboxs.end())
(*it)->mCurrentTime = 0;
else
MWBase::Environment::get().getWindowManager()->messageBox(mOverencumberedMessage);
}
}

View file

@ -67,6 +67,8 @@ namespace MWInput
bool mSneaking;
bool mAttemptJump;
const std::string mOverencumberedMessage;
float mTimeIdle;
};
}

View file

@ -624,9 +624,8 @@ namespace MWRender
return;
const NodeMap& nodeMap = getNodeMap();
for (SceneUtil::KeyframeHolder::KeyframeControllerMap::const_iterator it = animsrc->mKeyframes->mKeyframeControllers.begin();
it != animsrc->mKeyframes->mKeyframeControllers.end(); ++it)
const auto& controllerMap = animsrc->mKeyframes->mKeyframeControllers;
for (SceneUtil::KeyframeHolder::KeyframeControllerMap::const_iterator it = controllerMap.begin(); it != controllerMap.end(); ++it)
{
std::string bonename = Misc::StringUtils::lowerCase(it->first);
NodeMap::const_iterator found = nodeMap.find(bonename);
@ -652,14 +651,32 @@ namespace MWRender
SceneUtil::AssignControllerSourcesVisitor assignVisitor(mAnimationTimePtr[0]);
mObjectRoot->accept(assignVisitor);
// Determine the movement accumulation bone if necessary
if (!mAccumRoot)
{
NodeMap::const_iterator found = nodeMap.find("bip01");
if (found == nodeMap.end())
found = nodeMap.find("root bone");
if (found != nodeMap.end())
mAccumRoot = found->second;
// Priority matters! bip01 is preferred.
static const std::array<std::string, 2> accumRootNames =
{
"bip01",
"root bone"
};
NodeMap::const_iterator found = nodeMap.end();
for (const std::string& name : accumRootNames)
{
found = nodeMap.find(name);
if (found == nodeMap.end())
continue;
for (SceneUtil::KeyframeHolder::KeyframeControllerMap::const_iterator it = controllerMap.begin(); it != controllerMap.end(); ++it)
{
if (Misc::StringUtils::lowerCase(it->first) == name)
{
mAccumRoot = found->second;
break;
}
}
if (mAccumRoot)
break;
}
}
}

View file

@ -56,8 +56,6 @@ static const char exec_err[] = "!!! Failed to exec debug process\n";
static char argv0[PATH_MAX];
static char altstack[SIGSTKSZ];
static struct {
int signum;
@ -475,9 +473,10 @@ int crashCatcherInstallHandlers(int argc, char **argv, int num_signals, int *sig
/* Set an alternate signal stack so SIGSEGVs caused by stack overflows
* still run */
static char* altstack = new char [SIGSTKSZ];
altss.ss_sp = altstack;
altss.ss_flags = 0;
altss.ss_size = sizeof(altstack);
altss.ss_size = SIGSTKSZ;
sigaltstack(&altss, nullptr);
memset(&sa, 0, sizeof(sa));