[Bf-blender-cvs] [ad96830a4b9] functions: support mapping input vsockets to multiple new sockets
Jacques Lucke
noreply at git.blender.org
Tue Nov 12 14:30:07 CET 2019
Commit: ad96830a4b9e6069ef61c9cff9db858bceeb1a56
Author: Jacques Lucke
Date: Tue Nov 12 14:15:08 2019 +0100
Branches: functions
https://developer.blender.org/rBad96830a4b9e6069ef61c9cff9db858bceeb1a56
support mapping input vsockets to multiple new sockets
===================================================================
M source/blender/functions/FN_multi_function_data_type.h
M source/blender/functions/FN_multi_function_network.h
M source/blender/functions/FN_vtree_multi_function_network.h
M source/blender/functions/intern/multi_function_network.cc
M source/blender/functions/intern/vtree_multi_function_network/builder.cc
M source/blender/functions/intern/vtree_multi_function_network/builder.h
M source/blender/functions/intern/vtree_multi_function_network/generate.cc
M source/blender/simulations/bparticles/node_frontend.cpp
M source/blender/simulations/bparticles/particle_function_builder.cpp
===================================================================
diff --git a/source/blender/functions/FN_multi_function_data_type.h b/source/blender/functions/FN_multi_function_data_type.h
index 4f8b520fa63..9585a031f96 100644
--- a/source/blender/functions/FN_multi_function_data_type.h
+++ b/source/blender/functions/FN_multi_function_data_type.h
@@ -77,6 +77,24 @@ struct MFDataType {
return !(a == b);
}
+ std::string to_string() const
+ {
+ switch (m_category) {
+ case Single:
+ return m_base_type->name();
+ case Vector:
+ return m_base_type->name() + " Vector";
+ }
+ BLI_assert(false);
+ return "";
+ }
+
+ friend std::ostream &operator<<(std::ostream &stream, MFDataType type)
+ {
+ stream << type.to_string();
+ return stream;
+ }
+
private:
Category m_category;
const CPPType *m_base_type;
diff --git a/source/blender/functions/FN_multi_function_network.h b/source/blender/functions/FN_multi_function_network.h
index 3935cb0ef3b..bf6fd3edb43 100644
--- a/source/blender/functions/FN_multi_function_network.h
+++ b/source/blender/functions/FN_multi_function_network.h
@@ -40,6 +40,9 @@ class MFBuilderNode : BLI::NonCopyable, BLI::NonMovable {
ArrayRef<MFBuilderInputSocket *> inputs();
ArrayRef<MFBuilderOutputSocket *> outputs();
+ MFBuilderInputSocket &input(uint index);
+ MFBuilderOutputSocket &output(uint index);
+
StringRefNull name();
uint id();
@@ -293,6 +296,7 @@ class MFNetwork : BLI::NonCopyable, BLI::NonMovable {
const MFNode &node_by_id(uint id) const;
const MFSocket &socket_by_id(uint id) const;
+ IndexRange socket_ids() const;
Vector<const MFOutputSocket *> find_dummy_dependencies(
ArrayRef<const MFInputSocket *> sockets) const;
@@ -315,6 +319,16 @@ inline ArrayRef<MFBuilderOutputSocket *> MFBuilderNode::outputs()
return m_outputs;
}
+inline MFBuilderInputSocket &MFBuilderNode::input(uint index)
+{
+ return *m_inputs[index];
+}
+
+inline MFBuilderOutputSocket &MFBuilderNode::output(uint index)
+{
+ return *m_outputs[index];
+}
+
inline uint MFBuilderNode::id()
{
return m_id;
@@ -576,6 +590,11 @@ inline const MFSocket &MFNetwork::socket_by_id(uint index) const
return *m_socket_by_id[index];
}
+inline IndexRange MFNetwork::socket_ids() const
+{
+ return IndexRange(m_socket_by_id.size());
+}
+
} // namespace FN
#endif /* __FN_MULTI_FUNCTION_NETWORK_H__ */
diff --git a/source/blender/functions/FN_vtree_multi_function_network.h b/source/blender/functions/FN_vtree_multi_function_network.h
index 3fabf4d352b..1ec48338d1f 100644
--- a/source/blender/functions/FN_vtree_multi_function_network.h
+++ b/source/blender/functions/FN_vtree_multi_function_network.h
@@ -3,6 +3,8 @@
#include "BKE_virtual_node_tree.h"
+#include "BLI_multi_map.h"
+
#include "FN_multi_function_network.h"
namespace FN {
@@ -12,28 +14,107 @@ using BKE::VirtualNodeTree;
using BKE::VNode;
using BKE::VOutputSocket;
using BKE::VSocket;
+using BLI::MultiMap;
+
+#define VTreeMFSocketMap_UNMAPPED UINT_MAX
+#define VTreeMFSocketMap_MULTIMAPPED (UINT_MAX - 1)
+
+class VTreeMFSocketMap {
+ private:
+ /* An input vsocket can be mapped to multiple sockets.
+ * An output vsocket can be mapped to at most one socket.
+ */
+ const VirtualNodeTree *m_vtree;
+ const MFNetwork *m_network;
+ Array<uint> m_single_socket_by_vsocket;
+ MultiMap<uint, uint> m_multiple_inputs_by_vsocket;
+ Array<uint> m_vsocket_by_socket;
+
+ public:
+ VTreeMFSocketMap(const VirtualNodeTree &vtree,
+ const MFNetwork &network,
+ Array<uint> single_socket_by_vsocket,
+ MultiMap<uint, uint> multiple_inputs_by_vsocket,
+ Array<uint> vsocket_by_socket)
+ : m_vtree(&vtree),
+ m_network(&network),
+ m_single_socket_by_vsocket(std::move(single_socket_by_vsocket)),
+ m_multiple_inputs_by_vsocket(std::move(multiple_inputs_by_vsocket)),
+ m_vsocket_by_socket(std::move(vsocket_by_socket))
+ {
+ }
+
+ bool is_mapped(const VSocket &vsocket) const
+ {
+ return m_single_socket_by_vsocket[vsocket.id()] < VTreeMFSocketMap_MULTIMAPPED;
+ }
+
+ bool is_mapped(const MFSocket &socket) const
+ {
+ return m_vsocket_by_socket[socket.id()] != VTreeMFSocketMap_UNMAPPED;
+ }
+
+ const MFInputSocket &lookup_singly_mapped_input_socket(const VInputSocket &vsocket) const
+ {
+ BLI_assert(this->lookup_socket(vsocket).size() == 1);
+ uint mapped_id = m_single_socket_by_vsocket[vsocket.id()];
+ return m_network->socket_by_id(mapped_id).as_input();
+ }
+
+ Vector<const MFInputSocket *> lookup_socket(const VInputSocket &vsocket) const
+ {
+ uint id = vsocket.id();
+ uint mapped_value = m_single_socket_by_vsocket[id];
+ switch (mapped_value) {
+ case VTreeMFSocketMap_UNMAPPED: {
+ return {};
+ }
+ case VTreeMFSocketMap_MULTIMAPPED: {
+ Vector<const MFInputSocket *> sockets;
+ for (uint mapped_id : m_multiple_inputs_by_vsocket.lookup(id)) {
+ sockets.append(&m_network->socket_by_id(mapped_id).as_input());
+ }
+ return sockets;
+ }
+ default: {
+ uint mapped_id = mapped_value;
+ const MFInputSocket &socket = m_network->socket_by_id(mapped_id).as_input();
+ return {&socket};
+ }
+ }
+ }
+
+ const MFOutputSocket &lookup_socket(const VOutputSocket &vsocket) const
+ {
+ uint mapped_id = m_single_socket_by_vsocket[vsocket.id()];
+ return m_network->socket_by_id(mapped_id).as_output();
+ }
+
+ const VInputSocket &lookup_vsocket(const MFInputSocket &socket) const
+ {
+ uint mapped_id = m_vsocket_by_socket[socket.id()];
+ return m_vtree->socket_by_id(mapped_id).as_input();
+ }
+
+ const VOutputSocket &lookup_vsocket(const MFOutputSocket &socket) const
+ {
+ uint mapped_id = m_vsocket_by_socket[socket.id()];
+ return m_vtree->socket_by_id(mapped_id).as_output();
+ }
+};
class VTreeMFNetwork {
private:
const VirtualNodeTree &m_vtree;
std::unique_ptr<MFNetwork> m_network;
- Array<const MFSocket *> m_socket_by_vsocket;
- Array<const VSocket *> m_vsocket_by_socket;
+ VTreeMFSocketMap m_socket_map;
public:
VTreeMFNetwork(const VirtualNodeTree &vtree,
std::unique_ptr<MFNetwork> network,
- Array<const MFSocket *> socket_map)
- : m_vtree(vtree), m_network(std::move(network)), m_socket_by_vsocket(std::move(socket_map))
- {
- m_vsocket_by_socket = Array<const VSocket *>(m_socket_by_vsocket.size());
- for (uint vsocket_id = 0; vsocket_id < m_socket_by_vsocket.size(); vsocket_id++) {
- const MFSocket *socket = m_socket_by_vsocket[vsocket_id];
- if (socket != nullptr) {
- const VSocket &vsocket = m_vtree.socket_by_id(vsocket_id);
- m_vsocket_by_socket[socket->id()] = &vsocket;
- }
- }
+ VTreeMFSocketMap socket_map)
+ : m_vtree(vtree), m_network(std::move(network)), m_socket_map(std::move(socket_map))
+ {
}
const VirtualNodeTree &vtree() const
@@ -48,36 +129,38 @@ class VTreeMFNetwork {
bool is_mapped(const VSocket &vsocket) const
{
- return m_socket_by_vsocket[vsocket.id()] != nullptr;
+ return m_socket_map.is_mapped(vsocket);
}
bool is_mapped(const MFSocket &socket) const
{
- return m_vsocket_by_socket[socket.id()] != nullptr;
+ return m_socket_map.is_mapped(socket);
}
- const MFInputSocket &lookup_socket(const VInputSocket &vsocket) const
+ const MFInputSocket &lookup_dummy_socket(const VInputSocket &vsocket) const
{
- return m_socket_by_vsocket[vsocket.id()]->as_input();
+ const MFInputSocket &socket = m_socket_map.lookup_singly_mapped_input_socket(vsocket);
+ BLI_assert(socket.node().is_dummy());
+ return socket;
}
const MFOutputSocket &lookup_socket(const VOutputSocket &vsocket) const
{
- return m_socket_by_vsocket[vsocket.id()]->as_output();
+ return m_socket_map.lookup_socket(vsocket);
}
const VInputSocket &lookup_vsocket(const MFInputSocket &socket) const
{
- return m_vsocket_by_socket[socket.id()]->as_input();
+ return m_socket_map.lookup_vsocket(socket);
}
const VOutputSocket &lookup_vsocket(const MFOutputSocket &socket) const
{
- return m_vsocket_by_socket[socket.id()]->as_output();
+ return m_socket_map.lookup_vsocket(socket);
}
- void lookup_sockets(ArrayRef<const VOutputSocket *> vsockets,
- MutableArrayRef<const MFOutputSocket *> r_result) const
+ void lookup_dummy_sockets(ArrayRef<const VOutputSocket *> vsockets,
+ MutableArrayRef<const MFOutputSocket *> r_result) const
{
BLI_assert(vsockets.size() == r_result.size());
for (uint i = 0; i < vsockets.size(); i++) {
@@ -85,12 +168,12 @@ class VTreeMFNetwork {
}
}
- void lookup_sockets(ArrayRef<const VInputSocket *> vsockets,
- MutableArrayRef<const MFInputSocket *> r_result) const
+ void lookup_dummy_sockets(ArrayRef<const VInputSocket *> vsockets,
+ MutableArrayRef<const MFInputSocket *> r_result) const
{
BLI_assert(vsockets.size() == r_result.size());
for (uint i = 0; i < vsockets.size(); i++) {
- r_result[i] = &this->lookup_socket(*vsockets[i]);
+ r_result[i] = &this->lookup_dummy_socket(*vsockets[i]);
}
}
};
diff --git a/source/blender/functions/intern/multi_function_network.cc b/source/blender/functions/intern/multi_function_network.cc
index 69864f2e8ee..b309d67b781 100644
--- a/source/blender/functions/intern/multi_function_network.cc
+++ b/source/blender/functions/intern/multi_function_network.cc
@@ -180,7 +180,7 @@ static void insert_node_table(std::stringstream &ss, MFBuilderNode &node)
if (i < inputs.size()) {
MFBuilderInputSocket &socket = *inputs[i];
ss << "<td align=\"left\" port=" << get_id(socket) << ">";
- ss << socket.name();
+ ss << socket.name() << " (" << socket.type() << ")";
ss << "</td>";
}
else {
@@ -190,7 +190,7 @@ static void insert_node_table(std::stringstream &ss, MFBuilderNode &node)
if (i < outputs.size()) {
MFBuilderOutputSocket &socket = *outputs[i];
ss << "<td align=\"right\" port=" << g
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list