summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarc Zinnschlag <marc@zpages.de>2014-10-27 07:30:41 +0100
committerMarc Zinnschlag <marc@zpages.de>2014-10-27 07:30:41 +0100
commit073478a97e7d61f4409898d13e71c056d233f5bf (patch)
treef67eab299213d579b5ed77b95e05d97584466e14
parent2fa44c3c5f944836f229c4cc3c76b4e826a9193a (diff)
parentba26879fd4076976663c1862b50716b026aced05 (diff)
Merge remote-tracking branch 'origin/openmw-33' into openmw-33openmw-0.33.0
-rw-r--r--apps/openmw/mwgui/alchemywindow.cpp8
-rw-r--r--apps/openmw/mwgui/alchemywindow.hpp2
-rw-r--r--apps/openmw/mwmechanics/alchemy.cpp72
-rw-r--r--apps/openmw/mwmechanics/alchemy.hpp13
-rw-r--r--apps/openmw/mwworld/esmstore.cpp1
-rw-r--r--apps/openmw/mwworld/store.hpp19
-rw-r--r--components/esm/loaddial.cpp11
-rw-r--r--components/esm/loaddial.hpp3
8 files changed, 91 insertions, 38 deletions
diff --git a/apps/openmw/mwgui/alchemywindow.cpp b/apps/openmw/mwgui/alchemywindow.cpp
index 0fa9121b7d..b9e0044cef 100644
--- a/apps/openmw/mwgui/alchemywindow.cpp
+++ b/apps/openmw/mwgui/alchemywindow.cpp
@@ -134,11 +134,12 @@ namespace MWGui
for (MWMechanics::Alchemy::TToolsIterator iter (mAlchemy.beginTools());
iter!=mAlchemy.endTools() && index<static_cast<int> (mApparatus.size()); ++iter, ++index)
{
+ mApparatus.at (index)->setItem(*iter);
+ mApparatus.at (index)->clearUserStrings();
if (!iter->isEmpty())
{
mApparatus.at (index)->setUserString ("ToolTipType", "ItemPtr");
mApparatus.at (index)->setUserData (*iter);
- mApparatus.at (index)->setItem(*iter);
}
}
@@ -173,6 +174,11 @@ namespace MWGui
void AlchemyWindow::update()
{
+ std::string suggestedName = mAlchemy.suggestPotionName();
+ if (suggestedName != mSuggestedPotionName)
+ mNameEdit->setCaptionWithReplacing(suggestedName);
+ mSuggestedPotionName = suggestedName;
+
mSortModel->clearDragItems();
MWMechanics::Alchemy::TIngredientsIterator it = mAlchemy.beginIngredients ();
diff --git a/apps/openmw/mwgui/alchemywindow.hpp b/apps/openmw/mwgui/alchemywindow.hpp
index b538a1f808..36f540c1b6 100644
--- a/apps/openmw/mwgui/alchemywindow.hpp
+++ b/apps/openmw/mwgui/alchemywindow.hpp
@@ -23,6 +23,8 @@ namespace MWGui
virtual void exit();
private:
+ std::string mSuggestedPotionName;
+
ItemView* mItemView;
SortFilterItemModel* mSortModel;
diff --git a/apps/openmw/mwmechanics/alchemy.cpp b/apps/openmw/mwmechanics/alchemy.cpp
index 90c1808173..da2492a771 100644
--- a/apps/openmw/mwmechanics/alchemy.cpp
+++ b/apps/openmw/mwmechanics/alchemy.cpp
@@ -205,7 +205,7 @@ void MWMechanics::Alchemy::updateEffects()
}
}
-const ESM::Potion *MWMechanics::Alchemy::getRecord() const
+const ESM::Potion *MWMechanics::Alchemy::getRecord(const ESM::Potion& toFind) const
{
const MWWorld::Store<ESM::Potion> &potions =
MWBase::Environment::get().getWorld()->getStore().get<ESM::Potion>();
@@ -216,6 +216,18 @@ const ESM::Potion *MWMechanics::Alchemy::getRecord() const
if (iter->mEffects.mList.size() != mEffects.size())
continue;
+ if (iter->mName != toFind.mName
+ || iter->mScript != toFind.mScript
+ || iter->mData.mWeight != toFind.mData.mWeight
+ || iter->mData.mValue != toFind.mData.mValue
+ || iter->mData.mAutoCalc != toFind.mData.mAutoCalc)
+ continue;
+
+ // Don't choose an ID that came from the content files, would have unintended side effects
+ // where alchemy can be used to produce quest-relevant items
+ if (!potions.isDynamic(iter->mId))
+ continue;
+
bool mismatch = false;
for (int i=0; i<static_cast<int> (iter->mEffects.mList.size()); ++i)
@@ -266,37 +278,34 @@ void MWMechanics::Alchemy::removeIngredients()
void MWMechanics::Alchemy::addPotion (const std::string& name)
{
- const ESM::Potion *record = getRecord();
-
- if (!record)
- {
- ESM::Potion newRecord;
+ ESM::Potion newRecord;
- newRecord.mData.mWeight = 0;
+ newRecord.mData.mWeight = 0;
- for (TIngredientsIterator iter (beginIngredients()); iter!=endIngredients(); ++iter)
- if (!iter->isEmpty())
- newRecord.mData.mWeight += iter->get<ESM::Ingredient>()->mBase->mData.mWeight;
+ for (TIngredientsIterator iter (beginIngredients()); iter!=endIngredients(); ++iter)
+ if (!iter->isEmpty())
+ newRecord.mData.mWeight += iter->get<ESM::Ingredient>()->mBase->mData.mWeight;
- newRecord.mData.mWeight /= countIngredients();
+ newRecord.mData.mWeight /= countIngredients();
- newRecord.mData.mValue = mValue;
- newRecord.mData.mAutoCalc = 0;
+ newRecord.mData.mValue = mValue;
+ newRecord.mData.mAutoCalc = 0;
- newRecord.mName = name;
+ newRecord.mName = name;
- int index = static_cast<int> (std::rand()/(static_cast<double> (RAND_MAX)+1)*6);
- assert (index>=0 && index<6);
+ int index = static_cast<int> (std::rand()/(static_cast<double> (RAND_MAX)+1)*6);
+ assert (index>=0 && index<6);
- static const char *name[] = { "standard", "bargain", "cheap", "fresh", "exclusive", "quality" };
+ static const char *meshes[] = { "standard", "bargain", "cheap", "fresh", "exclusive", "quality" };
- newRecord.mModel = "m\\misc_potion_" + std::string (name[index]) + "_01.nif";
- newRecord.mIcon = "m\\tx_potion_" + std::string (name[index]) + "_01.dds";
+ newRecord.mModel = "m\\misc_potion_" + std::string (meshes[index]) + "_01.nif";
+ newRecord.mIcon = "m\\tx_potion_" + std::string (meshes[index]) + "_01.dds";
- newRecord.mEffects.mList = mEffects;
+ newRecord.mEffects.mList = mEffects;
+ const ESM::Potion* record = getRecord(newRecord);
+ if (!record)
record = MWBase::Environment::get().getWorld()->createRecord (newRecord);
- }
mAlchemist.getClass().getContainerStore (mAlchemist).add (record->mId, 1, mAlchemist);
}
@@ -436,14 +445,6 @@ MWMechanics::Alchemy::TEffectsIterator MWMechanics::Alchemy::endEffects() const
return mEffects.end();
}
-std::string MWMechanics::Alchemy::getPotionName() const
-{
- if (const ESM::Potion *potion = getRecord())
- return potion->mName;
-
- return "";
-}
-
MWMechanics::Alchemy::Result MWMechanics::Alchemy::create (const std::string& name)
{
if (mTools[ESM::Apparatus::MortarPestle].isEmpty())
@@ -452,7 +453,7 @@ MWMechanics::Alchemy::Result MWMechanics::Alchemy::create (const std::string& na
if (countIngredients()<2)
return Result_LessThanTwoIngredients;
- if (name.empty() && getPotionName().empty())
+ if (name.empty())
return Result_NoName;
if (listEffects().empty())
@@ -479,3 +480,14 @@ MWMechanics::Alchemy::Result MWMechanics::Alchemy::create (const std::string& na
return Result_Success;
}
+
+std::string MWMechanics::Alchemy::suggestPotionName()
+{
+ std::set<MWMechanics::EffectKey> effects = listEffects();
+ if (effects.empty())
+ return "";
+
+ int effectId = effects.begin()->mId;
+ return MWBase::Environment::get().getWorld()->getStore().get<ESM::GameSetting>().find(
+ ESM::MagicEffect::effectIdToString(effectId))->getString();
+}
diff --git a/apps/openmw/mwmechanics/alchemy.hpp b/apps/openmw/mwmechanics/alchemy.hpp
index e6b8c66509..caba26f149 100644
--- a/apps/openmw/mwmechanics/alchemy.hpp
+++ b/apps/openmw/mwmechanics/alchemy.hpp
@@ -56,8 +56,9 @@ namespace MWMechanics
void updateEffects();
- const ESM::Potion *getRecord() const;
- ///< Return existing record for created potion (may return 0)
+ const ESM::Potion *getRecord(const ESM::Potion& toFind) const;
+ ///< Try to find a potion record similar to \a toFind in the record store, or return 0 if not found
+ /// \note Does not account for record ID, model or icon
void removeIngredients();
///< Remove selected ingredients from alchemist's inventory, cleanup selected ingredients and
@@ -108,15 +109,13 @@ namespace MWMechanics
void removeIngredient (int index);
///< Remove ingredient from slot (calling this function on an empty slot is a no-op).
- std::string getPotionName() const;
- ///< Return the name of the potion that would be created when calling create (if a record for such
- /// a potion already exists) or return an empty string.
+ std::string suggestPotionName ();
+ ///< Suggest a name for the potion, based on the current effects
Result create (const std::string& name);
///< Try to create a potion from the ingredients, place it in the inventory of the alchemist and
/// adjust the skills of the alchemist accordingly.
- /// \param name must not be an empty string, unless there is already a potion record (
- /// getPotionName() does not return an empty string).
+ /// \param name must not be an empty string, or Result_NoName is returned
};
}
diff --git a/apps/openmw/mwworld/esmstore.cpp b/apps/openmw/mwworld/esmstore.cpp
index 1b5d3d1e95..56cb05c646 100644
--- a/apps/openmw/mwworld/esmstore.cpp
+++ b/apps/openmw/mwworld/esmstore.cpp
@@ -135,6 +135,7 @@ void ESMStore::setUp()
mSkills.setUp();
mMagicEffects.setUp();
mAttributes.setUp();
+ mDialogs.setUp();
}
int ESMStore::countSavedGameRecords() const
diff --git a/apps/openmw/mwworld/store.hpp b/apps/openmw/mwworld/store.hpp
index 107db68b1b..55c5b8191f 100644
--- a/apps/openmw/mwworld/store.hpp
+++ b/apps/openmw/mwworld/store.hpp
@@ -1174,6 +1174,25 @@ namespace MWWorld
mShared.erase(mShared.begin() + mStatic.size(), mShared.end());
}
+ template<>
+ inline void Store<ESM::Dialogue>::setUp()
+ {
+ // DialInfos marked as deleted are kept during the loading phase, so that the linked list
+ // structure is kept intact for inserting further INFOs. Delete them now that loading is done.
+ for (Static::iterator it = mStatic.begin(); it != mStatic.end(); ++it)
+ {
+ ESM::Dialogue& dial = it->second;
+ dial.clearDeletedInfos();
+ }
+
+ mShared.clear();
+ mShared.reserve(mStatic.size());
+ std::map<std::string, ESM::Dialogue>::iterator it = mStatic.begin();
+ for (; it != mStatic.end(); ++it) {
+ mShared.push_back(&(it->second));
+ }
+ }
+
} //end namespace
#endif
diff --git a/components/esm/loaddial.cpp b/components/esm/loaddial.cpp
index 92077b572f..ff0362aa21 100644
--- a/components/esm/loaddial.cpp
+++ b/components/esm/loaddial.cpp
@@ -110,4 +110,15 @@ void Dialogue::readInfo(ESMReader &esm, bool merge)
std::cerr << "Failed to insert info " << id << std::endl;
}
+void Dialogue::clearDeletedInfos()
+{
+ for (InfoContainer::iterator it = mInfo.begin(); it != mInfo.end(); )
+ {
+ if (it->mQuestStatus == DialInfo::QS_Deleted)
+ it = mInfo.erase(it);
+ else
+ ++it;
+ }
+}
+
}
diff --git a/components/esm/loaddial.hpp b/components/esm/loaddial.hpp
index fd46ad2109..d29948c63b 100644
--- a/components/esm/loaddial.hpp
+++ b/components/esm/loaddial.hpp
@@ -47,6 +47,9 @@ struct Dialogue
void load(ESMReader &esm);
void save(ESMWriter &esm) const;
+ /// Remove all INFOs marked as QS_Deleted from mInfos.
+ void clearDeletedInfos();
+
/// Read the next info record
/// @param merge Merge with existing list, or just push each record to the end of the list?
void readInfo (ESM::ESMReader& esm, bool merge);