Merge pull request #932 from aws-lumberyard-dev/carlitosan-beta-fixes
SC support for unordered_set, version upgrade improvements and bug fixes
This commit is contained in:
@@ -1020,29 +1020,60 @@ namespace AZ
|
||||
}
|
||||
};
|
||||
|
||||
/// OnDemand reflection for AZStd::set
|
||||
|
||||
template<class t_Key, class t_Hasher, class t_EqualKey, class t_Allocator>
|
||||
class Iterator_VM<AZStd::unordered_set<t_Key, t_Hasher, t_EqualKey, t_Allocator>>
|
||||
{
|
||||
public:
|
||||
using ContainerType = AZStd::unordered_set<t_Key, t_Hasher, t_EqualKey, t_Allocator>;
|
||||
using IteratorType = typename ContainerType::iterator;
|
||||
Iterator_VM(ContainerType& container)
|
||||
: m_iterator(container.begin())
|
||||
, m_end(container.end())
|
||||
{}
|
||||
|
||||
const t_Key& GetKeyUnchecked() const
|
||||
{
|
||||
return *m_iterator;
|
||||
}
|
||||
|
||||
bool IsNotAtEnd() const
|
||||
{
|
||||
return m_iterator != m_end;
|
||||
}
|
||||
|
||||
t_Key& ModValueUnchecked()
|
||||
{
|
||||
return *m_iterator;
|
||||
}
|
||||
|
||||
void Next()
|
||||
{
|
||||
++m_iterator;
|
||||
}
|
||||
|
||||
private:
|
||||
IteratorType m_iterator;
|
||||
IteratorType m_end;
|
||||
};
|
||||
|
||||
/// OnDemand reflection for AZStd::unordered_set
|
||||
template<class Key, class Hasher, class EqualKey, class Allocator>
|
||||
struct OnDemandReflection< AZStd::unordered_set<Key, Hasher, EqualKey, Allocator> >
|
||||
{
|
||||
using ContainerType = AZStd::unordered_set<Key, Hasher, EqualKey, Allocator>;
|
||||
using KeyListType = AZStd::vector<Key, Allocator>;
|
||||
|
||||
static AZ::Outcome<void, void> Erase(ContainerType& thisMap, Key& key)
|
||||
using ValueIteratorType = Iterator_VM<ContainerType>;
|
||||
|
||||
static bool EraseCheck_VM(ContainerType& thisSet, Key& key)
|
||||
{
|
||||
const auto result = thisMap.erase(key);
|
||||
if (result)
|
||||
{
|
||||
return AZ::Success();
|
||||
}
|
||||
else
|
||||
{
|
||||
return AZ::Failure();
|
||||
}
|
||||
return thisSet.erase(key) != 0;
|
||||
}
|
||||
|
||||
static void Insert(ContainerType& thisSet, Key& key)
|
||||
static ContainerType& ErasePost_VM(ContainerType& thisSet, [[maybe_unused]] Key&)
|
||||
{
|
||||
thisSet.insert(key);
|
||||
return thisSet;
|
||||
}
|
||||
|
||||
static KeyListType GetKeys(ContainerType& thisSet)
|
||||
@@ -1055,6 +1086,17 @@ namespace AZ
|
||||
return keys;
|
||||
}
|
||||
|
||||
static ContainerType& Insert(ContainerType& thisSet, Key& key)
|
||||
{
|
||||
thisSet.insert(key);
|
||||
return thisSet;
|
||||
}
|
||||
|
||||
static ValueIteratorType Iterate_VM(ContainerType& thisContainer)
|
||||
{
|
||||
return ValueIteratorType(thisContainer);
|
||||
}
|
||||
|
||||
static void Swap(ContainerType& thisSet, ContainerType& otherSet)
|
||||
{
|
||||
thisSet.swap(otherSet);
|
||||
@@ -1064,33 +1106,68 @@ namespace AZ
|
||||
{
|
||||
if (BehaviorContext* behaviorContext = azrtti_cast<BehaviorContext*>(context))
|
||||
{
|
||||
BranchOnResultInfo emptyBranchInfo;
|
||||
emptyBranchInfo.m_returnResultInBranches = true;
|
||||
emptyBranchInfo.m_trueToolTip = "The container is empty";
|
||||
emptyBranchInfo.m_falseToolTip = "The container is not empty";
|
||||
|
||||
auto ContainsTransparent = [](const ContainerType& containerType, typename ContainerType::key_type& key)->bool
|
||||
{
|
||||
return containerType.contains(key);
|
||||
};
|
||||
|
||||
ExplicitOverloadInfo explicitOverloadInfo;
|
||||
behaviorContext->Class<ContainerType>()
|
||||
->Attribute(AZ::Script::Attributes::ExcludeFrom, AZ::Script::Attributes::ExcludeFlags::All)
|
||||
->Attribute(AZ::Script::Attributes::ExcludeFrom, AZ::Script::Attributes::ExcludeFlags::ListOnly)
|
||||
->Attribute(AZ::ScriptCanvasAttributes::PrettyName, ScriptCanvasOnDemandReflection::OnDemandPrettyName<ContainerType>::Get(*behaviorContext))
|
||||
->Attribute(AZ::Script::Attributes::ToolTip, ScriptCanvasOnDemandReflection::OnDemandToolTip<ContainerType>::Get(*behaviorContext))
|
||||
->Attribute(AZ::Script::Attributes::Category, ScriptCanvasOnDemandReflection::OnDemandCategoryName<ContainerType>::Get(*behaviorContext))
|
||||
->Attribute(AZ::Script::Attributes::Storage, AZ::Script::Attributes::StorageType::ScriptOwn)
|
||||
->Method("BucketCount", static_cast<typename ContainerType::size_type(ContainerType::*)() const>(&ContainerType::bucket_count))
|
||||
->Method("Erase", &Erase)
|
||||
->Method("Empty", [](ContainerType& thisSet)->bool { return thisSet.empty(); })
|
||||
->Method("Empty", static_cast<bool(ContainerType::*)() const>(&ContainerType::empty), { { { "Container", "The container to check if it is empty", nullptr, {} } } })
|
||||
->Attribute(AZ::ScriptCanvasAttributes::ExplicitOverloadCrc, ExplicitOverloadInfo("Is Empty", "Containers"))
|
||||
->Attribute(AZ::ScriptCanvasAttributes::BranchOnResult, emptyBranchInfo)
|
||||
->Method("EraseCheck_VM", &EraseCheck_VM)
|
||||
->Attribute(AZ::Script::Attributes::TreatAsMemberFunction, AZ::AttributeIsValid::IfPresent)
|
||||
->Attribute(AZ::Script::Attributes::ExcludeFrom, AZ::Script::Attributes::ExcludeFlags::All)
|
||||
->Method("Erase", &ErasePost_VM)
|
||||
->Attribute(AZ::Script::Attributes::TreatAsMemberFunction, AZ::AttributeIsValid::IfPresent)
|
||||
->Attribute(AZ::ScriptCanvasAttributes::ExplicitOverloadCrc, ExplicitOverloadInfo("Erase", "Containers"))
|
||||
->Attribute(AZ::ScriptCanvasAttributes::CheckedOperation, CheckedOperationInfo("EraseCheck_VM", {}, "Out", "Key Not Found", true))
|
||||
->Attribute(AZ::ScriptCanvasAttributes::OverloadArgumentGroup, AZ::OverloadArgumentGroupInfo({ "ContainerGroup", "" }, { "ContainerGroup" }))
|
||||
->Method("contains", ContainsTransparent)
|
||||
->Attribute(AZ::ScriptCanvasAttributes::ExplicitOverloadCrc, ExplicitOverloadInfo("Has Key", "Containers"))
|
||||
->Attribute(AZ::Script::Attributes::TreatAsMemberFunction, AZ::AttributeIsValid::IfPresent)
|
||||
->Method("Insert", &Insert)
|
||||
->Attribute(AZ::Script::Attributes::TreatAsMemberFunction, AZ::AttributeIsValid::IfPresent)
|
||||
->Attribute(AZ::ScriptCanvasAttributes::ExplicitOverloadCrc, ExplicitOverloadInfo("Insert", "Containers"))
|
||||
->Attribute(AZ::ScriptCanvasAttributes::OverloadArgumentGroup, AZ::OverloadArgumentGroupInfo({ "ContainerGroup", "", "" }, { "ContainerGroup" }))
|
||||
->Method(k_sizeName, [](ContainerType* thisPtr) { return aznumeric_cast<int>(thisPtr->size()); })
|
||||
->Attribute(AZ::Script::Attributes::Operator, AZ::Script::Attributes::OperatorType::Length)
|
||||
->Method("GetKeys", &GetKeys)
|
||||
->Attribute(AZ::Script::Attributes::ExcludeFrom, AZ::Script::Attributes::ExcludeFlags::All)
|
||||
->Method("GetSize", [](ContainerType& thisPtr) { return aznumeric_cast<int>(thisPtr.size()); })
|
||||
->Attribute(AZ::ScriptCanvasAttributes::ExplicitOverloadCrc, ExplicitOverloadInfo("Get Size", "Containers"))
|
||||
->Attribute(AZ::Script::Attributes::TreatAsMemberFunction, AZ::AttributeIsValid::IfPresent)
|
||||
->Method("Reserve", static_cast<void(ContainerType::*)(typename ContainerType::size_type)>(&ContainerType::reserve))
|
||||
->Method("Swap", &Swap)
|
||||
->Method("Clear", [](ContainerType& thisContainer)->ContainerType& { thisContainer.clear(); return thisContainer; })
|
||||
->Attribute(AZ::Script::Attributes::TreatAsMemberFunction, AZ::AttributeIsValid::IfPresent)
|
||||
->Attribute(AZ::ScriptCanvasAttributes::ExplicitOverloadCrc, ExplicitOverloadInfo("Clear All Elements", "Containers"))
|
||||
->Attribute(AZ::ScriptCanvasAttributes::OverloadArgumentGroup, AZ::OverloadArgumentGroupInfo({ "ContainerGroup" }, { "ContainerGroup" }))
|
||||
->Method(k_iteratorConstructorName, &Iterate_VM)
|
||||
;
|
||||
|
||||
behaviorContext->Class<ValueIteratorType>()
|
||||
->Attribute(AZ::Script::Attributes::ExcludeFrom, AZ::Script::Attributes::ExcludeFlags::ListOnly)
|
||||
->Attribute(AZ::Script::Attributes::Storage, AZ::Script::Attributes::StorageType::ScriptOwn)
|
||||
->Method(k_iteratorGetKeyName, &ValueIteratorType::GetKeyUnchecked)
|
||||
->Method(k_iteratorModValueName, &ValueIteratorType::ModValueUnchecked)
|
||||
->Method(k_iteratorIsNotAtEndName, &ValueIteratorType::IsNotAtEnd)
|
||||
->Method(k_iteratorNextName, &ValueIteratorType::Next)
|
||||
;
|
||||
}
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
template <>
|
||||
|
||||
@@ -165,7 +165,7 @@ namespace AZ
|
||||
|
||||
if (HasResult() != overload->HasResult())
|
||||
{
|
||||
AZ_Error("Reflection", false, "Overload failure, all methods must have the same result, or none at all");
|
||||
AZ_Error("Reflection", false, "Overload failure, all methods must have the same result, or none at all: %s", m_name.c_str());
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -176,7 +176,7 @@ namespace AZ
|
||||
|
||||
if (!(methodResult->m_typeId == overloadResult->m_typeId && methodResult->m_traits == overloadResult->m_traits))
|
||||
{
|
||||
AZ_Error("Reflection", false, "Overload failure, all methods must have the same result, or none at all");
|
||||
AZ_Error("Reflection", false, "Overload failure, all methods must have the same result, or none at all: %s", m_name.c_str());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -575,7 +575,7 @@ namespace AZ
|
||||
}
|
||||
else
|
||||
{
|
||||
AZ_Error("BehaviorContext", false, "safety check declared for method %s but it was not found in the class");
|
||||
AZ_Error("BehaviorContext", false, "Method: %s, declared safety check: %s, but it was not found in class: %s", method.m_name.c_str(), m_name.c_str(), checkedOperationInfo.m_safetyCheckName.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,10 +34,17 @@ namespace BehaviorContextUtilitiesCPP
|
||||
using argument_type = const BehaviorParameter*;
|
||||
using result_type = size_t;
|
||||
result_type operator()(const argument_type& value) const
|
||||
{
|
||||
result_type result = AZStd::hash<Uuid>()(value->m_typeId);
|
||||
AZStd::hash_combine(result, CleanTraits(value->m_traits));
|
||||
return result;
|
||||
{
|
||||
if (value)
|
||||
{
|
||||
result_type result = AZStd::hash<Uuid>()(value->m_typeId);
|
||||
AZStd::hash_combine(result, CleanTraits(value->m_traits));
|
||||
return result;
|
||||
}
|
||||
else
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
@@ -45,7 +52,11 @@ namespace BehaviorContextUtilitiesCPP
|
||||
{
|
||||
bool operator()(const BehaviorParameter* left, const BehaviorParameter* right) const
|
||||
{
|
||||
return left->m_typeId == right->m_typeId && CleanTraits(left->m_traits) == CleanTraits(right->m_traits);
|
||||
return (left == nullptr && right == nullptr)
|
||||
|| (left != nullptr
|
||||
&& right != nullptr
|
||||
&& left->m_typeId == right->m_typeId
|
||||
&& CleanTraits(left->m_traits) == CleanTraits(right->m_traits));
|
||||
}
|
||||
};
|
||||
|
||||
@@ -137,7 +148,7 @@ namespace AZ
|
||||
for (size_t argIndex = 0, argSentinel = overload.GetNumArguments(); argIndex < argSentinel; ++argIndex)
|
||||
{
|
||||
auto overloadedArgIter = variance.m_input.find(argIndex);
|
||||
if (overloadedArgIter != variance.m_input.end())
|
||||
if (overloadedArgIter != variance.m_input.end() && overloadedArgIter->second[overloadIndex])
|
||||
{
|
||||
// if this doesn't work try the type name
|
||||
overloadName += ReplaceCppArtifacts(overloadedArgIter->second[overloadIndex]->m_name);
|
||||
@@ -185,16 +196,24 @@ namespace AZ
|
||||
{
|
||||
auto argument = overloads[overloadIndex].first->GetArgument(0);
|
||||
|
||||
const bool isThisPointer
|
||||
= (argument->m_traits & AZ::BehaviorParameter::Traits::TR_THIS_PTR) != 0
|
||||
|| AZ::FindAttribute(AZ::Script::Attributes::TreatAsMemberFunction, overloads[overloadIndex].first->m_attributes);
|
||||
if (argument)
|
||||
{
|
||||
const bool isThisPointer
|
||||
= (argument->m_traits & AZ::BehaviorParameter::Traits::TR_THIS_PTR) != 0
|
||||
|| AZ::FindAttribute(AZ::Script::Attributes::TreatAsMemberFunction, overloads[overloadIndex].first->m_attributes);
|
||||
|
||||
oneArgIsThisPointer = oneArgIsThisPointer || isThisPointer;
|
||||
oneArgIsThisPointer = oneArgIsThisPointer || isThisPointer;
|
||||
}
|
||||
|
||||
types.insert(argument);
|
||||
stripedArgs.emplace_back(argument);
|
||||
}
|
||||
|
||||
if (types.size() == overloads.size())
|
||||
{
|
||||
variance.m_unambiguousInput.insert(0);
|
||||
}
|
||||
|
||||
if (types.size() > 1 && (onThis == VariantOnThis::Yes || !oneArgIsThisPointer))
|
||||
{
|
||||
variance.m_input.insert(AZStd::make_pair(0, stripedArgs));
|
||||
@@ -210,11 +229,15 @@ namespace AZ
|
||||
for (size_t overloadIndex = 0, overloadSentinel = overloads.size(); overloadIndex < overloadSentinel; ++overloadIndex)
|
||||
{
|
||||
auto argument = overloads[overloadIndex].first->GetArgument(argIndex);
|
||||
|
||||
types.insert(argument);
|
||||
stripedArgs.emplace_back(argument);
|
||||
}
|
||||
|
||||
if (types.size() == overloads.size())
|
||||
{
|
||||
variance.m_unambiguousInput.insert(0);
|
||||
}
|
||||
|
||||
if (types.size() > 1)
|
||||
{
|
||||
variance.m_input.insert(AZStd::make_pair(argIndex, stripedArgs));
|
||||
|
||||
@@ -27,6 +27,8 @@ namespace AZ
|
||||
struct OverloadVariance
|
||||
{
|
||||
AZStd::unordered_map<size_t, AZStd::vector<const BehaviorParameter*>> m_input;
|
||||
// the indices of inputs that make selection of overload unambiguous
|
||||
AZStd::unordered_set<size_t> m_unambiguousInput;
|
||||
AZStd::vector<const BehaviorParameter*> m_output;
|
||||
};
|
||||
|
||||
|
||||
+7
-2
@@ -83,7 +83,7 @@ namespace AzToolsFramework
|
||||
protected:
|
||||
QWidget* GetFirstInTabOrder() override;
|
||||
QWidget* GetLastInTabOrder() override;
|
||||
void UpdateTabOrder() override;
|
||||
void UpdateTabOrder() override;
|
||||
|
||||
void onChildComboBoxValueChange(int comboBoxIndex) override;
|
||||
|
||||
@@ -93,7 +93,7 @@ namespace AzToolsFramework
|
||||
|
||||
void addElementImpl(const AZStd::pair<T, AZStd::string>& genericValue);
|
||||
|
||||
QLabel* m_warningLabel = nullptr;
|
||||
QLabel* m_warningLabel = nullptr;
|
||||
DHQComboBox* m_pComboBox;
|
||||
AZStd::vector<AZStd::pair<T, AZStd::string>> m_values;
|
||||
AZ::AttributeFunction <void(const T&)>* m_postChangeNotifyCB{};
|
||||
@@ -131,6 +131,11 @@ namespace AzToolsFramework
|
||||
template<typename T>
|
||||
AzToolsFramework::PropertyHandlerBase* RegisterGenericComboBoxHandler()
|
||||
{
|
||||
if (!AzToolsFramework::PropertyTypeRegistrationMessages::Bus::FindFirstHandler())
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
auto propertyHandler = aznew GenericComboBoxHandler<T>();
|
||||
AzToolsFramework::PropertyTypeRegistrationMessages::Bus::Broadcast(&AzToolsFramework::PropertyTypeRegistrationMessages::RegisterPropertyType, propertyHandler);
|
||||
return propertyHandler;
|
||||
|
||||
Reference in New Issue
Block a user