Welcome to mirror list, hosted at ThFree Co, Russian Federation.

NOD_socket_search_link.hh « nodes « blender « source - git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: b7594561dc4c67af7a419a2ef631ec38d1024150 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
/*
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
 */

#pragma once

#include <functional>

#include "BLI_string_ref.hh"
#include "BLI_vector.hh"

#include "DNA_node_types.h" /* Necessary for eNodeSocketInOut. */

#include "NOD_node_declaration.hh"

struct bContext;

namespace blender::nodes {

/**
 * Parameters for the operation operation of adding a node after the link drag search menu closes.
 */
class LinkSearchOpParams {
 private:
  /**
   * Keep track of the nodes added by the callback, so they can be selected or moved afterwards.
   */
  Vector<bNode *> &added_nodes_;

 public:
  const bContext &C;
  bNodeTree &node_tree;
  /**
   * The node that contains the #socket.
   */
  bNode &node;
  /**
   * The existing socket to connect any added nodes to. Might be an input or output socket.
   */
  bNodeSocket &socket;

  LinkSearchOpParams(const bContext &C,
                     bNodeTree &node_tree,
                     bNode &node,
                     bNodeSocket &socket,
                     Vector<bNode *> &added_nodes)
      : added_nodes_(added_nodes), C(C), node_tree(node_tree), node(node), socket(socket)
  {
  }

  bNode &add_node(StringRef idname);
  bNode &add_node(const bNodeType &type);
  /**
   * Find a socket with the given name (correctly checks for inputs and outputs)
   * and connect it to the socket the link drag started from (#socket).
   */
  void connect_available_socket(bNode &new_node, StringRef socket_name);
  /**
   * Like #connect_available_socket, but also calls the node's update function.
   */
  void update_and_connect_available_socket(bNode &new_node, StringRef socket_name);
};

struct SocketLinkOperation {
  using LinkSocketFn = std::function<void(LinkSearchOpParams &link_params)>;

  std::string name;
  LinkSocketFn fn;
  int weight = 0;
};

class GatherLinkSearchOpParams {
  /** The current node type. */
  const bNodeType &node_type_;

  const bNodeTree &node_tree_;

  const bNodeSocket &other_socket_;

  /* The operations currently being built. Owned by the caller. */
  Vector<SocketLinkOperation> &items_;

 public:
  GatherLinkSearchOpParams(const bNodeType &node_type,
                           const bNodeTree &node_tree,
                           const bNodeSocket &other_socket,
                           Vector<SocketLinkOperation> &items)
      : node_type_(node_type), node_tree_(node_tree), other_socket_(other_socket), items_(items)
  {
  }

  /**
   * The node on the other side of the dragged link.
   */
  const bNodeSocket &other_socket() const;

  /**
   * The node tree the user is editing when the search menu is created.
   */
  const bNodeTree &node_tree() const;

  /**
   * The type of the node in the current callback.
   */
  const bNodeType &node_type() const;

  /**
   * Whether to list the input or output sockets of the node.
   */
  eNodeSocketInOut in_out() const;

  /**
   * \param weight: Used to customize the order when multiple search items match.
   *
   * \warning When creating lambdas for the #fn argument, be careful not to capture this class
   * itself, since it is temporary. That is why we tend to use the same variable name for this
   * class (`params`) that we do for the argument to `LinkSocketFn`.
   */
  void add_item(std::string socket_name, SocketLinkOperation::LinkSocketFn fn, int weight = 0);
};

/**
 * This callback can be used for a node type when a few things are true about its inputs.
 * To avoid creating more boilerplate, it is the default callback for node types.
 *  - Either all declared sockets are visible in the default state of the node, *OR* the node's
 *    type's declaration has been extended with #make_available functions for those sockets.
 *
 * If a node type does not meet these criteria, the function will do nothing in a release build.
 * In a debug build, an assert will most likely be hit.
 *
 * \note For nodes with the deprecated #bNodeSocketTemplate instead of a declaration,
 * these criteria do not apply and the function just tries its best without asserting.
 */
void search_link_ops_for_basic_node(GatherLinkSearchOpParams &params);

void search_link_ops_for_declarations(GatherLinkSearchOpParams &params,
                                      Span<SocketDeclarationPtr> declarations);

}  // namespace blender::nodes