HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
OP_Node.h
Go to the documentation of this file.
1 /*
2  * PROPRIETARY INFORMATION. This software is proprietary to
3  * Side Effects Software Inc., and is not to be reproduced,
4  * transmitted, or disclosed in any way without written permission.
5  *
6  * NAME: OP Library (C++)
7  *
8  * COMMENTS: The base class for all OP operators
9  *
10  */
11 
12 #ifndef __OP_Node_h__
13 #define __OP_Node_h__
14 
15 #include "OP_API.h"
16 #include "OP_BundleReferences.h"
17 #include "OP_Cache.h"
18 #include "OP_ConnectorId.h"
19 #include "OP_Context.h"
20 #include "OP_DataMicroNode.h"
21 #include "OP_DataTypes.h"
22 #include "OP_Dependency.h"
23 #include "OP_Error.h"
24 #include "OP_EventMicroNode.h"
25 #include "OP_InterestRef.h"
26 #include "OP_ItemId.h"
27 #include "OP_Lock.h"
28 #include "OP_NetworkBoxItem.h"
29 #include "OP_NodeFlags.h"
30 #include "OP_OpTypeId.h"
31 #include "OP_OTLLicenseType.h"
32 #include "OP_Parameters.h"
33 #include "OP_Value.h"
34 #include "OP_Version.h"
35 
36 #include <CH/CH_EventManager.h>
37 #include <CH/CH_Types.h>
38 #include <EXPR/EXPR_Lock.h>
39 #include <DEP/DEP_MicroNode.h>
40 #include <PY/PY_Result.h>
41 #include <UT/UT_Algorithm.h>
42 #include <UT/UT_Array.h>
43 #include <UT/UT_ArrayMap.h>
44 #include <UT/UT_Assert.h>
45 #include <UT/UT_BitArray.h>
46 #include <UT/UT_BoundingBox.h>
47 #include <UT/UT_Color.h>
48 #include <UT/UT_Error.h>
49 #include <UT/UT_LockedRawPtr.h>
50 #include <UT/UT_Matrix4.h>
51 #include <UT/UT_Options.h>
52 #include <UT/UT_PathSearch.h>
53 #include <UT/UT_SharedPtr.h>
54 #include <UT/UT_SmallArray.h>
55 #include <UT/UT_String.h>
56 #include <UT/UT_StringHolder.h>
57 #include <UT/UT_StringMap.h>
58 #include <UT/UT_StringView.h>
59 #include <UT/UT_SymbolTable.h>
60 #include <UT/UT_TaskState.h>
61 #include <UT/UT_TokenString.h>
62 #include <UT/UT_UniquePtr.h>
63 #include <UT/UT_ValArray.h>
64 #include <UT/UT_Vector3.h>
65 #include <UT/UT_VectorTypes.h>
66 #include <UT/UT_XformOrder.h>
67 #include <SYS/SYS_AtomicInt.h>
68 #include <SYS/SYS_Deprecated.h>
69 #include <SYS/SYS_Math.h>
70 #include <SYS/SYS_Types.h>
71 
72 #include <iosfwd>
73 #include <limits.h>
74 #include <string.h>
75 
76 class UT_InfoTree;
77 class UT_IStream;
78 class UT_Ramp;
79 class UT_StringArray;
80 class UT_Undo;
81 class UT_WorkArgs;
82 class UT_WorkBuffer;
83 class IMG_Raster;
84 class PY_CompiledCode;
86 class PY_OpaqueObject;
87 class DD_Source;
88 class DD_ChoiceList;
89 class CL_Clip;
90 class CL_Track;
91 class CMD_Args;
92 class CH_Channel;
93 class CH_ChannelRef;
94 class CH_LocalVariable;
95 class PRM_BatchList;
96 class PRM_Name;
97 class PRM_Parm;
98 class PRM_ParmList;
99 class PRM_ParmMicroNode;
100 class PRM_RefId;
101 class PRM_Template;
102 class OP_Bundle;
103 class OP_DopParent;
104 class OP_Dot;
105 class OP_EditorContext;
106 class OP_GalleryEntry;
107 class OP_GlobContext;
108 class OP_Group;
109 class OP_IndirectInput;
110 class OP_Input;
111 class OP_Network;
112 class OP_NetworkBox;
113 class OP_Node;
114 class OP_NodeInfoParms;
116 class OP_Operator;
117 class OP_Output;
118 class OP_OutputCodeParms;
119 class OP_PostIt;
120 class OP_PreDefRules;
121 class OP_PropagateData;
122 class OP_SaveFlags;
124 class DOP_Parent;
125 class VOP_CodeGenerator;
128 
129 // avoid lengthy compilation dependency
131 
132 typedef int (*OP_EditCallback)(void *data, OP_Node *src,
133  CL_Track *track, fpreal t, fpreal value);
134 
138 
140 {
143 };
144 
146 {
149 };
150 
152 {
153  OP_NodeParmRef(const OP_Node *eval_node = 0,
154  const PRM_Parm *parm_ref = 0,
155  int vi = -1)
156  : myEvalNode(eval_node)
157  , myParmRef(parm_ref)
158  , myVectorIndex(vi)
159  {
160  }
161 
162  bool operator==(const OP_NodeParmRef &other)
163  {
164  return (myEvalNode == other.myEvalNode
165  && myParmRef == other.myParmRef
166  && myVectorIndex == other.myVectorIndex);
167  }
168 
169  const OP_Node * myEvalNode; // node evaluating the given parameter
170  const PRM_Parm * myParmRef; // pointer to evaluated parameter
171  int myVectorIndex; // parameter component index
172 };
173 
175 {
178 };
179 
180 // Utility for detecting cycles when traversing graphs
183 
187 
188 // The prefix used to specify an operator where a path would normally be used.
189 #define OPREF_PREFIX "op:"
190 #define OPREF_PREFIX_LEN 3
191 
192 // Default value of hash for compiled code associated with this node that
193 // shouldn't conflict with the hash of any actual cached code.
194 #define DEFAULT_COMP_HASH_VALUE (17*19)
195 
196 // Please, no spaces in these table names!
197 #define INVALID_TABLE_NAME "Node"
198 #define OBJ_TABLE_NAME "Object"
199 #define SOP_TABLE_NAME "Sop"
200 #define POPNET_TABLE_NAME "Particle"
201 #define POP_TABLE_NAME "Pop"
202 #define CHOPNET_TABLE_NAME "ChopNet"
203 #define CHOP_TABLE_NAME "Chop"
204 #define ROP_TABLE_NAME "Driver"
205 #define SHOP_TABLE_NAME "Shop"
206 #define COP2_TABLE_NAME "Cop2"
207 #define COPNET_TABLE_NAME "CopNet"
208 #define VOP_TABLE_NAME "Vop"
209 #define VOPNET_TABLE_NAME "VopNet"
210 #define DOP_TABLE_NAME "Dop"
211 #define TOP_TABLE_NAME "Top"
212 #define LOP_TABLE_NAME "Lop"
213 
214 // Manager and Director tabel names:
215 #define MGR_TABLE_NAME "Manager"
216 #define DIR_TABLE_NAME "Director"
217 
218 // These are the "script" directories where help and initialization scripts
219 // are found.
220 #define INVALID_SCRIPT_NAME "node"
221 #define OBJ_SCRIPT_NAME "obj"
222 #define SOP_SCRIPT_NAME "sop"
223 #define POPNET_SCRIPT_NAME "part"
224 #define POP_SCRIPT_NAME "pop"
225 #define CHOPNET_SCRIPT_NAME "ch"
226 #define CHOP_SCRIPT_NAME "chop"
227 #define ROP_SCRIPT_NAME "out"
228 #define SHOP_SCRIPT_NAME "shop"
229 #define COPNET_SCRIPT_NAME "img"
230 #define COP2_SCRIPT_NAME "cop2"
231 #define VOP_SCRIPT_NAME "vop"
232 #define VOPNET_SCRIPT_NAME "vex"
233 #define DOP_SCRIPT_NAME "dop"
234 #define TOP_SCRIPT_NAME "top"
235 #define LOP_SCRIPT_NAME "lop"
236 
237 // Manager and Director scripts... I doubt these will be used.
238 #define MGR_SCRIPT_NAME "mgr"
239 #define DIR_SCRIPT_NAME "dir"
240 #define MAT_SCRIPT_NAME "mat"
241 
242 // These are the op type names. These are used by icons among others.
243 #define INVALID_OPTYPE_NAME "NODE"
244 #define OBJ_OPTYPE_NAME "OBJ"
245 #define SOP_OPTYPE_NAME "SOP"
246 #define POPNET_OPTYPE_NAME "PART"
247 #define POP_OPTYPE_NAME "POP"
248 #define CHOPNET_OPTYPE_NAME "CHOPNET"
249 #define CHOP_OPTYPE_NAME "CHOP"
250 #define ROP_OPTYPE_NAME "ROP"
251 #define SHOP_OPTYPE_NAME "SHOP"
252 #define COP2_OPTYPE_NAME "COP2"
253 #define COPNET_OPTYPE_NAME "IMG"
254 #define VOP_OPTYPE_NAME "VOP"
255 #define VOPNET_OPTYPE_NAME "VOPNET"
256 #define DOP_OPTYPE_NAME "DOP"
257 #define TOP_OPTYPE_NAME "TOP"
258 #define LOP_OPTYPE_NAME "LOP"
259 
260 // These are the types of the manager nodes & director nodes.
261 // Manager nodes are things like /shop which don't have a specific
262 // type
263 // The director node is the root node which has everything inside it.
264 #define MGR_OPTYPE_NAME "MGR"
265 #define DIR_OPTYPE_NAME "DIR"
266 
267 /// Nice label names used by network view, corresponding to OP_OpTypeId
268 OP_API extern const char *OPtypeIdLabels[NUM_MANAGERS];
269 
270 // Stores the status of the node - undefined for currently
271 // uncached state,
273 {
277 };
278 
279 // These are some special defines used by VOPs. They need to be here
280 // because the OP_ConnectionMemory has to handle these operators in a
281 // special way,
282 #define VOP_OUTPUT_NODE_NAME "output"
283 #define VOP_SUBNET_OUTPUT_NODE_NAME "suboutput"
284 #define VOP_SUBNET_INPUT_NODE_NAME "subinput"
285 
286 // These defines provide a common place where the names of the management
287 // operator types are defined.
288 #define SHOP_MANAGEMENT_OPTYPE "shopnet"
289 #define POP_MANAGEMENT_OPTYPE "popnet"
290 #define COP2_MANAGEMENT_OPTYPE "cop2net"
291 #define ROP_MANAGEMENT_OPTYPE "ropnet"
292 #define CHOP_MANAGEMENT_OPTYPE "chopnet"
293 #define SOP_MANAGEMENT_OPTYPE "sopnet"
294 #define OBJ_MANAGEMENT_OPTYPE "objnet"
295 #define VOP_MANAGEMENT_OPTYPE "vopnet"
296 #define DOP_MANAGEMENT_OPTYPE "dopnet"
297 #define TOP_MANAGEMENT_OPTYPE "topnet"
298 #define LOP_MANAGEMENT_OPTYPE "lopnet"
299 
300 // This class has each of the above entities filled out.
301 // You can thus convert between different types by looking up
302 // with the known key and extracting what you want from this class.
303 // Looking up by id is fast, the rest requires a scan.
305 {
306 public:
311 };
312 
313 /// Options class for use with OP_Node::saveCommand()
315 {
316  // Initialize the options to match the opscript defaults
318  ( bool values_only_ = false
319  , bool defaultstoo_ = true
320  , bool docreate_ = true
321  , bool doparms_ = true
322  , bool doflags_ = true
323  , bool dowires_ = true
324  , bool dowiresout_ = true
325  , bool frames_ = false
326  , bool dogeneral_ = false
327  , bool dochblock_ = true
328  , bool dospareparms_ = true
329  , bool omit_version_info_ = false
330  )
331  : values_only(values_only_)
332  , defaultstoo(defaultstoo_)
333  , docreate(docreate_)
334  , doparms(doparms_)
335  , doflags(doflags_)
336  , dowires(dowires_)
337  , dowiresout(dowiresout_)
338  , frames(frames_)
339  , dogeneral(dogeneral_)
340  , dochblock(dochblock_)
341  , dospareparms(dospareparms_)
342  , omit_version_info(omit_version_info_)
343  {
344  }
345 
348  bool docreate;
349  bool doparms;
350  bool doflags;
351  bool dowires;
353  bool frames;
354  bool dogeneral;
355  bool dochblock;
358 };
359 
360 // Simple class that makes it easy to write loops that iterate over all the
361 // outputs from a node. The parameters are passed on to getOutputNodes.
362 class OP_API OP_OutputIterator : public UT_SmallArray<OP_Node*>
363 {
364 public:
365  OP_OutputIterator(const OP_Node &node,
366  bool into_subnets = false,
367  bool through_dots = true,
368  int output_idx = -1);
369 };
370 
371 // Same as above, but with the iterators all swapped around so a range loop
372 // will go backwards (without having to mess with reverse adaptors)
374 {
375 public:
377  bool into_subnets = false,
378  bool through_dots = true,
379  int output_idx = -1);
380 
382  { return OP_NodeList::rbegin(); }
384  { return OP_NodeList::rend(); }
386  { return OP_NodeList::rbegin(); }
388  { return OP_NodeList::rend(); }
389 
391  { return OP_NodeList::begin(); }
393  { return OP_NodeList::end(); }
395  { return OP_NodeList::begin(); }
397  { return OP_NodeList::end(); }
398 };
399 
400 //___________________________________________________________________________
401 
402 
403 //
404 // a container class to describe the instantaneous state of a parameter
405 //
407 {
408 public:
412  int myIndex;
414 
415  int operator==(const opParmData &v) const
416  {
417  return (myValue == v.myValue &&
418  myLabel == v.myLabel &&
419  myNode == v.myNode &&
420  myIndex == v.myIndex &&
421  mySubIndex == v.mySubIndex
422  );
423  }
424 };
425 
426 
427 // Blank class definitions for all our node types...
428 class OBJ_Node;
429 class SOP_Node;
430 class POP_Node;
431 class POPNET_Node;
432 class CHOPNET_Node;
433 class CHOP_Node;
434 class COP2_Node;
435 class COPNET_Node;
436 class ROP_Node;
437 class TOP_Node;
438 class LOP_Node;
439 class SHOP_Node;
440 class VOP_Node;
441 class VOPNET_Node;
442 class DOP_Node;
443 
444 #define INSTANTIATE_FINDNODE_FUNCTIONS(PREFIX) \
445  PREFIX##_Node *find##PREFIX##Node(const char *path) const \
446  { \
447  OP_Node *node; \
448  \
449  node = findNode(path); \
450  if (node) return node->castTo##PREFIX##Node(); \
451  return 0; \
452  }
453 #define INSTANTIATE_CASTNODE_FUNCTIONS(PREFIX) \
454  PREFIX##_Node *castTo##PREFIX##Node() const \
455  { \
456  /* If this is triggered, use CAST_FOONODE instead */ \
457  /* This is because foo->bar() should not be done with */ \
458  /* NULL foo for aesthetic reasons. */ \
459  { const void *this_local = this; \
460  UT_ASSERT(this_local); \
461  if (!this_local) return 0; } \
462  if (getOpTypeID() == PREFIX##_OPTYPE_ID) \
463  { \
464  return (PREFIX##_Node *) this; \
465  } \
466  return 0; \
467  }
468 
469 /// This macro allows us to run another macro for all node types
470 #define INSTANTIATE_FOR_ALL_NODE_TYPES(MACRO_FUNC) \
471  MACRO_FUNC(OBJ) \
472  MACRO_FUNC(SOP) \
473  MACRO_FUNC(POPNET) \
474  MACRO_FUNC(POP) \
475  MACRO_FUNC(CHOPNET) \
476  MACRO_FUNC(CHOP) \
477  MACRO_FUNC(ROP) \
478  MACRO_FUNC(SHOP) \
479  MACRO_FUNC(COP2) \
480  MACRO_FUNC(COPNET) \
481  MACRO_FUNC(VOP) \
482  MACRO_FUNC(VOPNET) \
483  MACRO_FUNC(DOP) \
484  MACRO_FUNC(TOP) \
485  MACRO_FUNC(LOP)
486 
491 
493 {
494 public:
495  // Methods to convert our enums and strings:
496  static const OP_TypeInfo *getOpInfoFromOpTypeID(OP_OpTypeId opid);
497  static const OP_TypeInfo *getOpInfoFromOpTypeName(const char *name);
498  static const OP_TypeInfo *getOpInfoFromTableName(const char *name);
499  static const OP_TypeInfo *getOpInfoFromScriptDir(const char *dir);
500  static const char *getOpTableNameFromManagerTypeName(const char *name);
501 
503  { return myParent; }
505  { return myRootCompiledParent; }
506 
507  //Return the network this item resides in (i.e. getParent()). This method
508  //was introduced to provide a standardized way of accessing the parent
509  //network of all different network box item types.
510  virtual OP_Network *getParentNetwork() const;
511 
512  // This function looks up our parent tree to determine if the given node
513  // is our parent, grandparent, great-grandparent...
514  bool getIsContainedBy(const OP_Node *testparent) const;
515 
516  /// Return the name of this node's parent
517  const UT_String &getNetName() const;
518 
519  /// This returns the OP_OpTypeId which corresponds to this node type.
520  /// Management nodes will return the type they really are, which
521  /// is likely different than the network they currently reside in.
522  virtual OP_OpTypeId getOpTypeID() const = 0;
523 
524  // This is the proper way to determine the optype.
525  // Do not assume your parents child type is your type! This will only
526  // become less true as time goes on :>
527  // The strings returned are the *_OPTYPE_NAME defined in OP_Network.h
528  virtual const char *getOpType() const = 0;
529 
530  virtual OP_ItemType getItemType() const;
531 
532  /// @anchor OP_Node_findFOONode
533  ///
534  /// FOO_Node *findFOONode(const char *path) const; @n
535  /// This function searches for the node at path relative
536  /// to this node. If not found, or if the found node is
537  /// not of type FOO_Node, it returns NULL. The result
538  /// is already cast to FOO_Node.
539  /// findOBJNode(const char *path)
540  /// findSOPNode(const char *path)
541  /// findPOPNETNode(const char *path)
542  /// findPOPNode(const char *path)
543  /// findCHOPNETNode(const char *path)
544  /// findCHOPNode(const char *path)
545  /// findROPNode(const char *path)
546  /// findSHOPNode(const char *path)
547  /// findCOP2Node(const char *path)
548  /// findCOPNETNode(const char *path)
549  /// findVOPNode(const char *path)
550  /// findVOPNETNode(const char *path)
551  /// findDOPNode(const char *path)
552  /// findTOPNode(const char *path)
553  /// findLOPNode(const char *path)
554  // @{
556  // @}
557 
558  /// @anchor OP_Node_castToFOONode
559  ///
560  /// FOO_Node *castToFOONode() const; @n
561  /// This type checks the current node against FOO_Node.
562  /// If the cast is legal, this is returned. Otherwise, NULL.
563  /// While it likely will do the "right" thing with this == NULL,
564  /// that case is UT_ASSERTed as it is just asking for trouble.
565  /// castToOBJNode()
566  /// castToSOPNode()
567  /// castToPOPNETNode()
568  /// castToPOPNode()
569  /// castToCHOPNETNode()
570  /// castToCHOPNode()
571  /// castToROPNode()
572  /// castToSHOPNode()
573  /// castToCOP2Node()
574  /// castToCOPNETNode()
575  /// castToVOPNode()
576  /// castToVOPNETNode()
577  /// castToDOPNode()
578  /// castToTOPNode()
579  /// castToLOPNode()
580  // @{
582  // @}
584  /// Obtain the node's script which is called when it is being deleted.
585  const UT_String &getDelScript(void) const { return myDelScript; }
586 
587  /// Set the node's deletion script. Returns true if the delete script was
588  /// set successfully.
589  bool setDelScript(const char *str);
590 
591  /// Accessors for this node's comment string.
592  // @{
593  const UT_String &getComment(void) const { return myComment; }
594  bool setComment(const char *str);
595  // @}
596 
597  /// Overrides the NetworkBoxItem implementations of getColor and setColor
598  /// to provide support Node-specific features like using the default color.
599  // @{
600  virtual UT_Color getColor() const;
601  virtual bool setColor(const UT_Color &col);
602  // @}
603 
604  /// Accessors for this node's flag indicating if it should use its
605  /// operator's default color instead of its local color.
606  // @{
607  int getColorDefault() const;
608  int setColorDefault(int usedefault);
609 
610  /// Accessors for this node's shape
611  // @{
612  const UT_StringHolder &getNodeShape() const;
613  void setNodeShape(const UT_StringHolder &shape);
614  // @}
615 
616  /// Node position/scale is used by the UI.
617  // @{
618  // These are in absolute coordinates, not the UI coordinates found in
619  // OPUI_Worksheet, though.
620  virtual void setXY(fpreal x, fpreal y);
621  virtual fpreal getX() const { return myPosX; }
622  virtual fpreal getY() const { return myPosY; }
623  virtual fpreal getW() const;
624  virtual fpreal getH() const;
625  // @}
626 
627  void pickRequest(int shift);
628 
629  /// Set allow_rel_paths to true to accept "." or ".." as valid paths.
630  static bool isValidOpName(const UT_StringView &s,
631  bool allow_rel_paths = false,
632  bool ignore_node_names_env_var = false);
633  static bool isValidOpName(const char *s,
634  bool allow_rel_paths = false,
635  bool ignore_node_names_env_var = false)
636  {
637  return isValidOpName(UT_StringView(s),
638  allow_rel_paths,
639  ignore_node_names_env_var);
640  }
641  static bool isValidOpPath(const UT_StringRef &s);
642  static bool forceValidOpName(UT_String &name);
643 
644  /// Override these methods so that search-and-replace operations
645  /// affect our delete script as well as our parameters.
646  // @{
647  virtual int findString(const char *str, bool fullword,
648  bool usewildcards) const;
649  virtual int changeString(const char *from, const char *to,
650  bool fullword);
651  // @}
652 
653  /// Mark this node, its descendants, and all data dependents containing
654  /// varname as being dirty. If changed_nodes is non-NULL, then it is
655  /// updated with the list of dirtied nodes which contains varname.
656  /// Returns true iff at least one node was dirtied.
657  bool notifyVarChange(
658  const char *varname,
659  OP_NodeList *changed_nodes = nullptr);
660 
661  // These are no-ops for nodes but will be implemented for networks:
662  virtual int getNchildren() const;
663  virtual OP_Node *getChild(const char *name, int *hint=0) const;
664  virtual OP_Node *getChild(int index) const;
665  void getPickedChildren(OP_NodeList &picked,
666  bool include_hidden=false) const;
667  void getAllChildren(OP_NodeList &children) const;
668  virtual OP_Node *matchChild(const char *pattern, OP_Node *prevmatch=0,
669  const char *optype=0,
670  int casesensitive = 0) const;
671  virtual OP_Node *matchChildBackwards(const char *pattern,
672  OP_Node *prevmatch=0,
673  const char *optype=0,
674  int casesensitive = 0) const;
675  virtual OP_Network *createProxyRefNode( const char *path );
677  // Returns the node with the requested unique integer identifier.
678  static OP_Node *lookupNode(int unique_id, bool include_proxy=false)
679  {
680  if( unique_id >= 0 && unique_id <= theUniqueId
681  && theUniqueNodes[unique_id] )
682  {
683  if( include_proxy || !theUniqueNodes[unique_id]
684  ->isProxyRefNode() )
685  return theUniqueNodes[unique_id];
686  }
687  return 0;
688  }
689  static int getNumUniqueIds()
690  { return theUniqueId + 1; }
691  // Fills the provided array with every node that currently exists.
692  static void getAllNodes(OP_NodeList &nodes);
693 
694  int getUniqueId() const
695  { return myUniqueId; }
696  virtual int64 getItemUniqueId() const
697  { return myUniqueId; }
698 
699  // The following function will take a standard pattern and expand
700  // all the groups out of the pattern, leaving a simple pattern
701  // in the result.
702  bool expandGroupPattern(const char *pattern,
703  UT_String &result,
704  bool expandToFullPaths = false);
705 
706  // The following methods take a standard pattern and return whether
707  // the pattern contains the specified bundle or group.
708  bool patternContainsBundle(const char *pattern,
709  const OP_Bundle *bundle) const;
710  bool patternContainsGroup(const char *pattern,
711  const OP_Group *group) const;
712 
713  virtual int isManager() const;
714  // This differs from isManager. Managers are the old school static
715  // things which are always present in fixed directories. Management
716  // nodes are managers that are in the wrong directory.
717  virtual int isManagementNode() const;
718  // This is a bit broader than management nodes. These nodes may
719  // be in the right directory, but represent an unexpected change
720  // of directory type, so need to be tracked so our tree filter
721  // will know about them.
722  bool isEffectivelyAManagementNode() const;
723 
724  // This function checks if the node is a subnet. Now that we can have
725  // NWN subnets (object subnets, vopnet subnets), we need to explicitly
726  // specify if these types of subnets count. In some cases we want them
727  // to count (such as checking for VOPNET subnets to see if we can
728  // generate code, or SHOP subnets to see if we can save to a palette).
729  // In other cases we want to exclude these management ops (such as
730  // when deciding to show the "Create Type From" menu item or checking
731  // if we can do an opwire -i command).
732  virtual int isSubNetwork(bool includemanagementops) const;
733  virtual int isNetwork() const;
734  virtual int isInSubNetwork() const;
735 
736  bool isProxyRefNode() const
737  { return myIsProxyRefNode; }
738  void setProxyRefNode(bool f)
739  { myIsProxyRefNode = f; }
740 
741  // Used by SOPs to determine which node is the output of a subnetwork.
742  virtual bool isOutputNode() const;
743  // Returns which output this node represents.
744  virtual int whichOutputNode() const;
745 
746  // isNetworkWithKids() will return 1 if the node is a network and the
747  // operator table for the node contains children which can be added to the
748  // node.
749  int isNetworkWithKids() const;
750 
751  virtual int isVex() const;
752 
753  // methods for managing the bundles we depend on in so that any change to
754  // the bundle in which we are interested triggers bundleChange call.
755  // NB: getParmBundle methods find or create a bundle ad it to the
756  // internal list of referenced bundles
757  OP_Bundle * getParmBundle(const char* parm_name, int vector_index,
758  UT_String &pattern, OP_Network *creator,
759  const char *filter);
760  void markBundleRefsAsUnused();
761  void cleanUnusedBundleRefs();
762  void cleanAllBundleRefs();
763 
764  static void getValueAsBundlePaths(fpreal t,
765  UT_WorkBuffer &resultbuf,
766  PRM_Parm *parm, int index,
767  OP_Node *srcnode
768  );
769  static void getValueAsBundlePaths(fpreal t,
770  OP_NodeList &resultnodes,
771  PRM_Parm *parm, int index,
772  OP_Node *srcnode
773  );
774 
775  // The bundleChanged() method is called whenever a bundle referenced by the
776  // OP is changed. The bundle is passed to the OP to let the OP know that
777  // it's out of date. The function should return 1 if the event was handled
778  // properly or 0 if it failed. The return codes are used for debugging
779  // only.
780  virtual bool bundleChanged(const OP_Bundle *bundle);
781  // If a bundle changes, you should call this method to touch the parameter
782  // which the bundle affects. The name is the token of the parm.
783  void touchBundleParm(const char *name);
784  void touchBundleParm(int parm_index);
786  // Function to determine if Display and Render node ptrs are the same
787  virtual int getDandROpsEqual() { return 1; }
788  // Function to update info about whether Render and Display node ptrs
789  // are the same. Recurses tree and updates all kids values.
790  virtual int updateDandROpsEqual(int = 1) { return 1; }
791 
792  /// Check to see whether @c node is an ancestor of @c this node in the
793  /// input hierarchy. Optionally check extra inputs. This method will
794  /// recurse using @c getInputs() (and optional getExtraInputNodes()
795  /// @note This node is considered to be an ancestor of itself
796  bool isInputAncestor(const OP_Node *parent,
797  bool check_extra=true) const;
798  /// Check to see whether the @c parent node is an ancestor of @c this node
799  /// in the parent/child hierarchy. That is, this method will call
800  /// getParent()/getChild() to traverse the hierarchy.
801  /// @note This node is considered to be an ancestor of itself
802  bool isParentAncestor(const OP_Node *parent) const;
803 
804  /// Get the info text for this op. This non-virtual function does
805  /// all the stuff common to all operator types.
806  /// @warning The return value is the value of the work buffer in the
807  /// OP_NodeInfoParms. Thus, you should never do @code
808  /// str = node->getInfoText(context, OP_NodeInfoParms());
809  /// @endcode
810  /// Since the lifetime of the temporary may not be long enough to extract
811  /// the string properly.
812  const char *getInfoText(OP_Context &context,
813  OP_NodeInfoParms &parms);
814  // Get Info Text that is specific to this node type.
815  virtual void getNodeSpecificInfoText(OP_Context &context,
816  OP_NodeInfoParms &parms);
817 
818  /// Uses the path (eg. "/obj/geo1") to find a node in our heirarchy
819  OP_Node *findNode(const char *path) const;
820 
821  /// Same as findNode() except it will return NULL if the path is to a node
822  /// that is either not a descendent of this node, or if it isn't the same
823  /// type as our children.
824  OP_Node *findSubNode(const char *path) const;
825 
826  // These are all Implemented in OP_Network, but put here as a virtual to
827  // make working / with hscript easier so that it can be called directly on
828  // an op node
829  virtual OP_NetworkBox *findNetworkBox(const char *name)
830  { return nullptr; }
831  virtual OP_PostIt *findPostItNote(const char *const_path)
832  { return nullptr; }
833  virtual OP_Dot *findDot(const char *const_path)
834  { return nullptr; }
835  virtual OP_SubnetIndirectInput *findParentInput(const char *const_path)
836  { return nullptr; }
837  virtual OP_NetworkBoxItem *findItem(const char *const_path,
838  OP_ItemTypeMask item_type =
840  { return nullptr; }
841 
842  // These functions will adhere to certain conventions, such as a reference
843  // to an object actually means a reference to the display or render
844  // guy in that object. This will also check this->isCookingRender
845  // to determine if it should auto-use the Render or Display.
846  // These will not fail if the returned node is the node itself.
847  SOP_Node *getSOPNode(const char *path, int addextra = 0) const;
848  // This method will use the render node of the composite network if
849  // it is a comp rather than a cop2 that is pointed to...
850  COP2_Node *getCOP2Node(const char *path, int addextra = 0) const;
851  // And this one will also use the render node, which corresponds to the
852  // cook node in POPs land.
853  POP_Node *getPOPNode(const char *path, int addextra = 0) const;
854  // And this one will use the display node, which corresponds to the
855  // cook node in DOPs land.
856  DOP_Node *getDOPNode(const char *path, int addextra = 0) const;
857  ROP_Node *getROPNode(const char *path, int addextra = 0) const;
858  // This method will use the audio node of the chop network
859  CHOP_Node *getCHOPNode(const char *path, int addextra = 0, bool *got_by_flag=0) const;
860  // This method will use the display node of the top network
861  TOP_Node *getTOPNode(const char *path, int addextra = 0) const;
862  // This method will use the display node of the lop network
863  LOP_Node *getLOPNode(const char *path, int addextra = 0) const;
864  OBJ_Node *getOBJNode(const char *path, int addextra = 0) const;
865 
866  virtual OP_Node *castToOPNode() { return this; }
867  virtual const OP_Node *castToOPNode() const { return this; }
868 
869  /// Returns the path of this node relative to its getCreator()
870  virtual void getPathWithSubnet(UT_String &str) const;
871  void getPathWithSubnet(UT_StringHolder &str) const
872  { UT_String tmp; getPathWithSubnet(tmp); str.adoptFromString(tmp); }
873 
874  /// This will try to complete the path by finding the longest suffix
875  /// that will work with the given prefix. It will only complete up
876  /// to the next child. If it finds a valid child, it will append
877  /// a slash (/).
878  void completePath(const char *prefixpath,
879  UT_String &completepath) const;
880 
881  virtual CH_Channel *getTrackChannel(const char *name);
882 
883  virtual bool findParmFromTrack(const OP_FollowChanRefsOptions& opt,
884  const char *trackname,
885  OP_NodeParmRefCycle &cycle,
886  OP_Node *&node,
887  PRM_Parm *&parm, int &vecidx);
888 
889  // Batch evaluation of named parameters. This method requires extra lookup
890  // since parameters are specified by names, but it can handle generic
891  // parameter layout.
892  virtual void evaluateBatchParms(PRM_BatchList &list, fpreal now);
893 
894  // Do global expansion on a pattern - get lists of channels or nodes
895  // If expand is given, concatenated with full list of names
896  // If list is given, appended with list of nodes.
897  // If dependent given, addExtraInputs.
898  void globNodes(const char *pat, UT_String *expand,
899  UT_ValArray<OP_Node *> *list=0,
900  OP_GlobContext *context = 0,
901  const char *prefix = " ");
902 
903  CH_Channel *findChannel(const char *path);
904  void globChannels(const char *, UT_String &expand,
905  OP_GlobContext *context = 0,
906  const char *prefix = " ") const;
907 
908  void globChannels(const char *pattern,
909  CH_ChannelList &clist,
910  OP_GlobContext *context = 0,
911  OP_Node *dependent = 0);
912  // If use_multi_match is false, the pattern is
913  // treated as a single pattern instead of a space
914  // separated list of patterns. (Only applies
915  // to direct parameter names, i.e. the pattern must not be
916  // a path and must not contain a slash)
917  void globChanRefs(const char *pattern,
918  CH_ChannelRefList &list,
919  OP_GlobContext *context = 0,
920  OP_Node *dependent = 0,
921  bool use_multi_match = true);
922 
923  int globParms(const char *pattern, fpreal t,
924  UT_Array<opParmData> &list,
925  OP_GlobContext *context = 0,
926  OP_Node *dependent = 0,
927  int calc_value = 1);
928 
929  // this version only globs the current node
930  void globNodeParms(const char *pattern, fpreal t,
931  UT_Array<opParmData> &list,
932  OP_GlobContext *context,
933  OP_Node *dependent,
934  int calc_value,
935  bool animated_only);
936 
937  // this version only globs the current node
938  void globNodeChannels(const char *pattern,
939  CH_ChannelList &list,
940  OP_GlobContext *context,
941  int *parm_start = nullptr,
942  UT_IntArray *parm_indices = nullptr,
943  UT_IntArray *parm_sub_indices = nullptr
944  ) const;
945 
946  // this version only globs the current node
947  // If use_multi_match is false, the pattern is
948  // treated as a single pattern instead of a space
949  // separated list of patterns
950  void globNodeChanRefs(const char *pattern,
951  CH_ChannelRefList &list,
952  OP_GlobContext *context,
953  int *parm_start = nullptr,
954  UT_IntArray *parm_indices = nullptr,
955  UT_IntArray *parm_sub_indices=nullptr,
956  bool use_multi_match = true
957  ) const;
958 
959  ///Same as 'globNodes', except for network boxes. This is to be implemented
960  ///by OP_Network, but has been put here so it can be called directly on
961  ///OP_Node like all the other "glob" methods without a cast
962  virtual void globNetworkBoxes(const char *pat, UT_String *expand,
964  OP_GlobContext *glob_context = 0,
965  const char *prefix = " ");
966 
967  virtual void globPostIts(const char *pat, UT_String *expand,
968  UT_ValArray<OP_PostIt *> *list=0,
969  OP_GlobContext *glob_context = 0,
970  const char *prefix = " ");
971 
972  // Fetch all channels from this node on down.
973  int getAllChannels(CH_ChannelList &list, int scoped=0);
974 
975  // If you override opChanged() in a sub-class, you must call
976  // the OP_Node base method from the sub-class method
977  virtual void opChanged(OP_EventType reason, void *data=0);
978 
979  // If you override opChanged() in a subclass, you should first call
980  // opShouldHandleChange() before taking any custom action.
981  virtual bool opShouldHandleChange(OP_EventType reason);
982 
983  // This function is called whenever we have a parameter that references
984  // another parameter, and that referenced parameter changes. The pi
985  // value is the index of the parameter containing the reference.
986  virtual void referencedParmChanged(int pi);
987 
988  /// Mark this node as needing a full recook.
989  /// If 'evensmartcache' is true, a recook will occur even if all the
990  /// parameters match in this node and all its inputs (only valid for
991  /// COP2_Node).
992  virtual void forceRecook(bool evensmartcache = true);
993 
994  /// This method causes any operators that load files to recook.
995  /// By default, this searches for 'file' operators by iterating through
996  /// inputs. Parms of type PRM_FILE are also marked dirty. Other nodes that
997  /// load files differently may wish to override this method.
998  virtual void reloadExternalFiles();
999 
1000  /// Determines if this node needs to cook.
1001  ///
1002  /// The queryonly flag will not flag this as a read attempt to the
1003  /// caching mechanisms, and thus not update the touch time.
1004  virtual unsigned needToCook(OP_Context &context, bool queryonly=false);
1005 
1006  /// Cook this node's data. Returns true upon success, false otherwise.
1007  ///
1008  /// Upon failure, use OP_Parameters::error() and
1009  /// OP_Parameters::getErrorMessages() to determine reason.
1010  virtual bool cook(OP_Context &context);
1011 
1012  /// Schedule a task for cooking this node in parallel and wait for it to
1013  /// finish. Returns true upon success, false otherwise.
1014  bool parallelCook(OP_Context &context);
1015 
1016  /// Cook the given node list in parallel
1017  static bool parallelCook(OP_Context &context,
1018  const OP_NodeList &nodes);
1019 
1020  /// The cook lock is used to protect per node data structures during
1021  /// cooking. Subclasses should use this when calling cook(). Example:
1022  /// @code
1023  /// cookLockedExecute([&]() {
1024  /// // run code
1025  /// });
1026  /// @endcode
1027  template <typename F>
1028  void cookLockedExecute(const F &functor)
1029  {
1031  {
1032  OP_CookLock::Scope scope(myCookLock);
1033  functor();
1034  });
1035  }
1036 
1037  /// The cook lock is used to protect per node data structures during
1038  /// cooking. Subclasses should use lock this to protect private data.
1039  OP_CookLock & getCookLock() { return myCookLock; }
1041  UT_TaskState & taskState() { return myTaskState; }
1042  const UT_TaskState & taskState() const { return myTaskState; }
1043 
1044  // This normally chains to cookInputGroups.
1045  // Some networks, such as SOPs, use it to be able to
1046  // properly lock their gdp pointer around the cook.
1047  virtual OP_ERROR pubCookInputGroups(OP_Context &context, int alone = 0);
1048 
1049  void bumpVersionParm()
1050  {
1051  dataMicroNode().bumpModVersion();
1052  if (hasIndepParmListMicroNode())
1053  parmListMicroNode().bumpModVersion();
1054  }
1055  int cookParmsModified() const
1056  { return parmListMicroNodeConst()
1057  .isModVersionOutdated(); }
1058 
1059  // The data class of an OP is currently used solely for networks which
1060  // contain heterogeneous node types (i.e. used in SHOP networks to
1061  // distinguish different shader types). A data class of 0 is returned by
1062  // default.
1063  // A value of 0 is returned by default.
1064  virtual int getDataClass() const;
1065 
1066  // The xform order for how to interpret the given channel. Default
1067  // is XYZ.
1068  virtual void getXformOrder(UT_XformOrder &xord,
1069  const CH_Channel *chp) const;
1070 
1071  // "getCookedData" should return a void * version of the results of
1072  // the cook. NULL if it fails with appropriate stuff in our error manager.
1073  virtual OP_DataType getCookedDataType() const = 0;
1074  virtual void *getCookedData(OP_Context &);
1075  virtual void deleteCookedData() = 0;
1076 
1077  virtual int saveCookedData(std::ostream &os, OP_Context &,
1078  int binary = 0) = 0;
1079  virtual bool loadCookedData(UT_IStream &is, const char *path=0);
1080  virtual int saveCookedData(const char *filename, OP_Context &) = 0;
1081 
1082  /// Get the transform from this node's space to the 'to' node's space.
1083  /// Returns 1 if this was possible, 0 otherwise (e.g. failure to cook).
1084  virtual int getRelativeTransform(OP_Node &to, UT_Matrix4 &xform,
1085  OP_Context &context);
1086  virtual int getRelativeTransform(OP_Node &to, UT_DMatrix4 &xform,
1087  OP_Context &context);
1088  // overrides for OPs that can capture (right now only OBJ_Bone)
1089  virtual int getRelativeCaptureTransform(OP_Node &to,
1090  UT_Matrix4 &xform,
1091  OP_Context &context);
1092  virtual int getRelativeCaptureTransform(OP_Node &to,
1093  UT_DMatrix4 &xform,
1094  OP_Context &context);
1095 
1097  {
1098  TRANSFORM_WORLD,
1099  TRANSFORM_IWORLD,
1100  TRANSFORM_PRE,
1101  TRANSFORM_PARENT,
1102  TRANSFORM_PARM,
1103  TRANSFORM_PRECONSTRAINT,
1104  TRANSFORM_PARENTBONE,
1105  };
1106 
1107  // these next 3 are the minimal overrides for subclasses that have
1108  // transforms (see OBJ_Node)
1109  virtual bool getWorldTransform(UT_Matrix4D &xform, OP_Context &);
1110  virtual bool getIWorldTransform(UT_Matrix4D &xform, OP_Context &);
1111  virtual bool getTransform( TransformMode mode, UT_Matrix4D &xform, OP_Context &);
1113  // single precision versions of the above
1114  bool getWorldTransform(UT_Matrix4F &xform, OP_Context &ctx)
1115  {
1116  UT_Matrix4D m;
1117  bool ok = getWorldTransform(m, ctx);
1118  xform = m;
1119  return ok;
1120  }
1121  bool getIWorldTransform(UT_Matrix4F &xform, OP_Context &ctx)
1122  {
1123  UT_Matrix4D m;
1124  bool ok = getIWorldTransform(m, ctx);
1125  xform = m;
1126  return ok;
1127  }
1128  bool getTransform( TransformMode mode, UT_Matrix4F &xform, OP_Context &ctx)
1129  {
1130  UT_Matrix4D m;
1131  bool ok = getTransform(mode, m, ctx);
1132  xform = m;
1133  return ok;
1134  }
1135 
1136  /// Registers an error for cooking the given node's transform. If label is
1137  /// supplied, then it will be used as a label of the transform error.
1138  void addTransformError(const OP_Node &node,
1139  const char *label=0) const;
1140 
1141  // Compute the bounding box for the operator (if applicable). If the box
1142  // could be computed, return true, else return false.
1143  virtual bool getBoundingBox(UT_BoundingBox &box, OP_Context &);
1144 
1145  // This is used by VOPNETs to determine which table needs to be
1146  // refreshed when they change.
1147  virtual const char *getInternalOpTable() const
1148  { return INVALID_TABLE_NAME; }
1149  virtual OP_Operator *getInternalOperator() const
1150  { return 0; }
1151 
1152  virtual const char *inputLabel(unsigned idx) const;
1153  virtual const char *outputLabel(unsigned idx) const;
1154 
1155  // Here's a useful method which will return the string "Source %d", where
1156  // %d is the idx passed. Lets us check if the input label is using the
1157  // default or not.
1158  const char *inputLabelNum(unsigned idx) const;
1159  const char *outputLabelNum(unsigned idx) const;
1160 
1161  // returns a label that is applied to the drawn connector. NULL may be
1162  // returned as 'no label'.
1163  virtual const char *inputConnectorLabel(unsigned idx);
1164 
1165  // if true, the connector to the input will be dashed rather than solid.
1166  virtual int isRefInput(unsigned idx) const;
1167 
1168  // returns the index of the auxilary input, if any (currently only used
1169  // for the mask inputs in COPs).
1170  virtual int getAuxInput() const;
1171  virtual void getAuxInputName(OP_ConnectorId& name_out);
1172 
1173  // The lock method is used to lock the OP.
1174  // Returns the previous state of the lock flag.
1175  //
1176  // Note that to mimic the behaviour of the lock button, you MUST
1177  // call setModelLock, not setLock, or your next unlock won't have
1178  // a cached data.
1179  int setLock(int state, int saveundo = 1);
1180  int getSoftLock() const {return flags().getSoftLocked();}
1181  int getHardLock() const {return flags().getHardLocked();}
1182  int getLock() const {return flags().getLocked(); }
1183  // getNetworkLock() checks to see if the OP is effectively locked by
1184  // the network, i.e., each of the OPs output branches connect to a locked
1185  // OP down the network. Returns > 0 if locked, <= 0 if unlocked.
1186  // When relaxedlockcheck is set, subnet branches that are not displayed
1187  // are ignored.
1188  int getNetworkLock(bool relaxedlockcheck = false,
1189  const OP_Node *inputNode=nullptr) const;
1190  // The Model lock is similar to the normal lock but will also cause
1191  // the node data to be saved.
1192  virtual int setModelLock(int on_off,
1193  void *modeler = 0,
1194  int allow_softlock_promotion=0,
1195  UT_Undo *undo = 0);
1196  int getModelLock() const;
1197 
1198  // The unload flag triggers whether we keep the ops data around
1199  // after a cook or discard it as soon as its not needed. Its currently
1200  // only implemented in CHOPs.
1201  int setUnload(int on_off);
1202  int getUnload() const;
1204  // Returns whether this node has data loaded into it.
1205  virtual bool isLoaded() const { return true; }
1206 
1207  // This will explicitly delete all data associated with the OP
1208  // false is returned if no data was deleted (ie, OP is in use, etc)
1209  // Only works with SOPs now.
1210  virtual bool unloadData();
1211 
1212  // Take control for flags
1213  void takeActivateFlag(uchar flag, bool enable=true,
1214  bool send_flag_event=true);
1215  void takeDeactivateFlag(uchar flag)
1216  { takeActivateFlag(flag, false); }
1217  bool takeIsActiveFlag(uchar flag) const;
1218  void setHasTakeData(int onoff);
1219 
1220  bool canAccessFlag(unsigned mask, uchar flag) const;
1221 
1222  // The template flag indicates that the node date should be displayed
1223  // The display & render flags indicate that the node is turned on
1224  // for display purposes or for rendering purposes, which may take
1225  // on different meanings per node type.
1226  // Setting save data only has meaning for some node types.
1227  virtual int setPicked(int on_off,
1228  bool propagate_parent_event = true);
1229 
1230  /// The edit flag is used whenever something is picked
1231  /// from the viewport. This causes the pane paths to
1232  /// be changed to the first writable parent of the
1233  /// node being picked.
1234  int setEditPicked(int on_off,
1235  bool propagate_parent_event = true);
1236 
1237  // The Autoscope flag on OP_Node is used to temporary turn-off the Auto-Add to Channel List
1238  // behavior when selecting nodes.
1239  // This is used when setting selected nodes from selected channels in the channel list
1240  void setAutoscope(bool on_off) { myAutoscope = on_off; }
1241  bool isAutoscope() { return myAutoscope; }
1242 
1243  int setCurrent(int on_off);
1244  int setExpose(int on_off);
1245  int setBypass(int on_off);
1246  int setTemplate(int on_off);
1247  int setFootprint(int on_off);
1248  int setXray(int on_off);
1249  int setDisplay(int on_off);
1250  int setRender(int on_off);
1251  int setHighlight(int on_off);
1252  int setModified(int on_off);
1253  int setSaveBypass(int on_off);
1254  int setSaveData(int on_off);
1255  // these are for subclasses to implement, they do nothing by default
1256  virtual int setPickable(int on_off)
1257  { return 0; }
1258  virtual int setAudio(int on_off)
1259  { return 0; }
1260  virtual int setExport(int on_off)
1261  { return 0; }
1262  virtual int setDebug(int on_off)
1263  { return 0; }
1264  virtual int setDisplayOrigin(int on_off_unchanged)
1265  { return 0; }
1266 
1267  /// The user has set the template flag. If we are turning on the template
1268  /// flag, we do the same as setTemplate(). If we are turning it *off*,
1269  /// we also turn off the selectable template (footprint) flag.
1270  void userSetTemplate(bool onoff);
1271 
1272  /// The user has set the selectable template flag. If we are making a node
1273  /// into a selectable template, we turn on the template flag as well.
1274  /// If we are turning off selectable template, we leave template alone.
1275  void userSetSelectableTemplate(bool onoff);
1276 
1277  // Here are the generalised versions, they add a bit of overhead to
1278  // the code because of the big switch statement.
1279  virtual int setFlag(char tag, int on_off);
1280  virtual int getFlag(char tag) const;
1282  virtual int getPicked() const {return flags().getPicked(); }
1283  virtual int getEditPicked() const
1284  { return flags().getEditPicked(); }
1285  int getCurrent() const;
1286  int getDisplay() const {return flags().getDisplay(); }
1287  int getRender() const {return flags().getRender(); }
1288  int getHighlight()const {return flags().getHighlight();}
1289  int getBypass() const {return flags().getBypass(); }
1290  int getTemplate() const {return flags().getTemplate(); }
1291  int getFootprint() const {return flags().getFootprint(); }
1292  int getXray() const {return flags().getXray(); }
1293  int getExpose() const {return flags().getExpose(); }
1294  int getModified() const {return flags().getModified(); }
1295  int getSaveBypass() const{return flags().getSaveBypass(); }
1296  int getSaveData() const {return flags().getSaveData(); }
1297  virtual int getHasTakeData() const
1298  { return flags().getHasTakeData(); }
1299  virtual int getPickable()
1300  { return 0; }
1301  virtual int getAudio() const
1302  { return 0; }
1303  virtual int getExport() const
1304  { return 0; }
1305  virtual int getDebug() const
1306  { return 0; }
1307  virtual int getDisplayOrigin() const
1308  { return 0; }
1309  virtual bool getItemExpose() const { return getExpose(); }
1310  virtual void setItemExpose(bool expose) { setExpose(expose); }
1311  virtual bool getUseBypassLook(const OP_EditorContext &ctx) const;
1312 
1313  int getDisplayDescriptiveName() const
1314  {return flags().getDisplayDescriptiveName();}
1315  int setDisplayDescriptiveName(int state);
1316  int getDisplayComment() const
1317  {return flags().getDisplayComment();}
1318  int setDisplayComment(int state);
1319 
1320  OP_Node *getPickableSelfOrParent();
1321 
1322  // The compress flag indicates that the OP connector should be displayed
1323  // in a compressed UI. In ICE this means don't display the mini raster
1324  // image.
1325  int setCompress(int on_off);
1326  int getCompress() const;
1327 
1328  // This method sets this node as the current and picked node and correctly
1329  // adjusts the picked states of the other sibling nodes.
1330  void setCurrentAndPicked();
1331 
1332  // setVisible() simply calls setDisplay() at this level but subclasses
1333  // override this to perform smarter behaviour. Objects for example will
1334  // try to set the display flag on parent subnets and change visible object
1335  // parameters as necessary.
1336  // Returns true if it was successful, false if there were not sufficient
1337  // permissions.
1338  virtual bool setVisible(int onoff);
1339  virtual bool getVisible() const;
1340 
1341  const OP_NodeFlags &flags() const
1342  { return myFlags; }
1343  OP_NodeFlags &flags()
1344  { return myFlags; }
1345 
1346  virtual void getSaveFlagsString(UT_String &cmd,
1347  const char *flags,
1348  bool save_to_hip) const;
1349  virtual void getPreParmSaveFlagsString( UT_String &cmd ) const;
1350  virtual void getPostParmSaveFlagsString( UT_String &cmd ) const;
1351 
1352  int hasOpInterest(void *data, OP_EventMethod m) const
1353  { return myEventValue.hasOpInterest(data, m); }
1354  void addOpInterest(void *data, OP_EventMethod m)
1355  { myEventValue.addOpInterest(data, m); }
1356  void removeOpInterest(void *data, OP_EventMethod m)
1357  { myEventValue.removeOpInterest(data, m); }
1358  int isBeingDeleted() const
1359  { return myBeingDeleted; }
1360  void setNodeBeingDeleted(int beingdeleted);
1361 
1362  /// Sets the flag that prevents consolidation of variable inputs.
1363  /// Returns previous value of the flag;
1364  bool setInhibitInputConsolidation(bool value);
1365 
1366  /// Move the upper-left most node in 'ops' to x-coordinate 'x' and to have
1367  /// its TOP border at y-coordinate 'y', and move all other nodes in 'ops'
1368  /// by the same amount. All netboxes in 'netboxes' will also be moved that
1369  /// amount. If a netbox's top border is higher than any node's top border,
1370  /// everything will be moved down accordingly. Note that the repositioning
1371  /// calculation does not include the nodes contained in the network boxes
1372  /// in 'netboxes'.
1373  static void repositionOpsMaxY(OP_NetworkBoxItemList &items,
1374  fpreal x, fpreal y);
1375 
1376  /// Minimum inputs that must be connected to a node for it to cook.
1377  virtual unsigned minInputs() const;
1378 
1379  /// Maximum inputs that can be connected to a node.
1380  virtual unsigned maxInputs() const;
1381 
1382  /// Number of input connectors that should be visible on a node. This is
1383  /// only used by VOPs and DOPs. All other OPs return maxInputs() here.
1384  virtual unsigned getNumVisibleInputs() const;
1385 
1386  /// Returns the number of ordered inputs on a node with unordered inputs.
1387  /// Even nodes with unordered inputs can have a few ordered inputs before
1388  /// the unordered inputs start. If hasUnorderedInputs returns false, this
1389  /// function is meaningless.
1390  virtual unsigned orderedInputs() const;
1391 
1392  /// Maximum number of output connectors on a node. Only VOPs and DOPs ever
1393  /// return a value other than 1 here.
1394  virtual unsigned maxOutputs() const;
1395 
1396  /// Number of output connections that should be visible on a node tile.
1397  /// Only used by VOPs and DOPs.
1398  virtual unsigned getNumVisibleOutputs() const;
1399 
1400  /// Returns true if the operator type says we have unordered inputs.
1401  bool hasUnorderedInputs() const;
1402 
1403  /// Returns the index of the last connected input incremented by one.
1404  /// If there are no inputs connected, returns 0. This means that the
1405  /// function behaves as if the lasted connected input was always the
1406  /// last entry in the inputs array. Note that other array entries up
1407  /// to the index of the one returned may contain null entries, so this
1408  /// is not necessarily the same as the number of connections. Also note
1409  /// that there may be more null entries at indices beyond the returned
1410  /// one.
1411  virtual unsigned nInputs() const;
1412 
1413  /// The number of nodes actually connected to this node. This function
1414  /// goes through the myInputs array and counts non-null entries.
1415  /// @param check_subnet_inside If true, the (vopnet) subnet node will check
1416  /// if a corresponding connector is connected inside, and count it in
1417  /// if so.
1418  unsigned nConnectedInputs(bool check_subnet_inside=true) const;
1419 
1420  unsigned getActiveInputIndex() const
1421  { return myActiveInputIndex; }
1422  void setActiveInputIndex(unsigned idx);
1423 
1424  /// Returns the node connected to a particular input (may be null).
1425  OP_Node *getInput(unsigned idx, bool mark_used=false) const;
1426 
1427  /// Returns the connected input, may be null. If it is a SOP & subnet,
1428  /// and not primary output, will chase to the child output node.
1429  /// This may induce flag dependencies, the provided micronode
1430  /// can accumulate them.
1431  OP_Node *getInputFollowingOutputs(int input,
1432  DEP_MicroNode *depnode=0) const;
1433 
1434  /// Returns the first non-null input beyond the specified starting index.
1435  /// This function can be used to easily loop through all connected inputs.
1436  int getConnectedInputIndex(int startAt = -1) const;
1437 
1438  /// Gets the index of the Nth non-null connection to this node.
1439  int getNthConnectedInput(int n) const;
1440 
1441  /// Override this to specify the inputs which are needed for cooking this
1442  /// node which can be executed in parallel.
1443  virtual void getParallelInputs(OP_Context &context,
1444  OP_NodeList &nodes) const;
1445 
1446  /// Forcibly clear an input. Used when deleting the input.
1447  void forceClearInput(int idx);
1448 
1449  /// Sets a given input to connect to an output of a particular node.
1450  virtual OP_ERROR setInput(unsigned idx, OP_Node *op,
1451  unsigned outputIdx = 0);
1452 
1453  /// Connects an input to an indirect input of our parent subnet.
1454  virtual OP_ERROR setIndirectInput(unsigned idx,
1455  OP_IndirectInput *input);
1456 
1457  /// Connects an input to particular node by name in the network.
1458  virtual OP_ERROR setInputReference(unsigned idx, const char *label,
1459  int keeppos, unsigned outputIdx = 0);
1460 
1461  /// Returns the index of the first connection from node "who" to this node,
1462  /// or -1 if "who" is not an input.
1463  int whichInputIs(const OP_Node *who) const;
1464 
1465  /// Returns the index of the first connection of an indirect input.
1466  int whichInputIs(const OP_IndirectInput *who) const;
1467 
1468  // Returns the index of the Nth connection of an idirect input.
1469  int whichInputIs(const OP_IndirectInput *whoi,
1470  int cnt) const;
1471 
1472  // Returns an index of the output which goes out from this node to
1473  // the target_node, and connects to the target_node at the specified
1474  // input index. Returns -1 if the connection doesn't exist.
1475  // Use whichOutputIsFollowingIndirect for a more robust solution.
1476  int whichOutputIs(const OP_Node* target_node,
1477  int input_on_target_node) const;
1478 
1479  // Computes the output, but handles the case that target_node's input
1480  // is an indirect input. This will then follow the indirect chain
1481  // up until a node's real input.
1482  int whichOutputIsFollowingIndirect(
1483  const OP_Node* target_node,
1484  int input_on_target_node) const;
1485 
1486  // Returns the index of an input into which source_node is connected
1487  // on this node. counter determines the Nth such connection from
1488  // source node to this particular node.
1489  int whichInputIs(OP_Node* source_node, int counter);
1490 
1491  // Compacts the inputs array, removing all null entries.
1492  void consolidateInputs();
1493  virtual void clearUnreferencedInputs();
1494  virtual bool allowConsolidatingInput(int idx);
1495 
1496  // Returns a pointer to an input given an input index. If the input index
1497  // is less than nInputs() it will always return a valid input. If the grow
1498  // flag is set to true, then any inputs between nInputs and the index
1499  // given will be created, up to maxInputs().
1500  virtual OP_Input *getInputReference(unsigned idx, bool grow);
1501 
1502  // As before, except missing inputs are not created. NULL is returned for
1503  // non-existent inputs.
1504  virtual OP_Input *getInputReferenceConst(unsigned idx) const;
1505 
1506  virtual int doDeleteRewire() const { return 1; }
1507  // This moves the input at srcidx to dstidx. forcesubnet will enable
1508  // modificatio of subnet inputs and outputs even when inside a
1509  // blockModify().
1510  virtual void moveInput(int srcidx, int dstidx,
1511  bool forcesubnet = false);
1512  OP_ERROR insertInput(unsigned idx, OP_Node *op,
1513  unsigned outputIdx);
1514  OP_ERROR insertIndirectInput(unsigned idx,
1515  OP_IndirectInput *input);
1516 
1517  // For nodes with editable input names, this function is used to set the
1518  // default name for a new input.
1519  virtual UT_Options getInputDataDefault(int idx) const
1520  { return UT_Options(); }
1521 
1522  /// The following methods are used for nodes that allow reordering inputs.
1523  /// Returns the number of inputs that editor should display.
1524  virtual int getInputEditorInputs();
1525  /// Returns true if editor should display parameter option menu button.
1526  virtual bool allowInputEditorInputParm();
1527  /// Returns true if editor should display delete input button.
1528  virtual bool allowInputEditorInputDelete();
1529  /// Gets the input label to display in editor and returns true. Otherwise,
1530  /// returns false if editor should use backward-compatible labeling scheme.
1531  virtual bool getInputEditorInputLabel(UT_String &label, int idx);
1533  virtual const OP_DataMicroNode &
1534  dataMicroNodeConst() const
1535  { return myDataMicroNode; }
1536  OP_DataMicroNode & dataMicroNode()
1537  {
1538  return const_cast<OP_DataMicroNode &>(
1539  dataMicroNodeConst());
1540  }
1541 
1542  /// Subclasses should override this to customize the micro-node dependency
1543  /// of their parameter list. The default is just dataMicroNode().
1544  virtual const OP_DataMicroNode &
1545  parmListMicroNodeConst() const
1546  { return dataMicroNodeConst(); }
1547  OP_DataMicroNode & parmListMicroNode()
1548  {
1549  return const_cast<OP_DataMicroNode &>(
1550  parmListMicroNodeConst());
1551  }
1552 
1553  bool hasIndepParmListMicroNode() const
1554  {
1555  return (&parmListMicroNodeConst()
1556  != &dataMicroNodeConst());
1557  }
1558 
1559  DEP_MicroNode & flagMicroNode()
1560  { return myFlagMicroNode; }
1561  DEP_MicroNode & parmMicroNode(int parm_idx, int vi)
1562  { return getParmList()->parmMicroNode(
1563  parm_idx, vi); }
1565  /// Accessors to event micro nodes.
1566  const DEP_MicroNode &eventMicroNodeConst(OP_EventType e) const
1567  {
1568  return SYSconst_cast(this)->eventMicroNode(e);
1569  }
1570  DEP_MicroNode & eventMicroNode(OP_EventType e)
1571  {
1572  // Create the micro node if it does not exist.
1573  if (!myEventMicroNodes[e])
1574  {
1575  myEventMicroNodes[e] =
1576  new OP_EventMicroNode(*this, e);
1577  }
1578 
1579  return *myEventMicroNodes[e];
1580  }
1581 
1582  /// Subclasses should override this provide any additional micronodes that
1583  /// they own. This list is used in places such as node deletion so that
1584  /// dependents are dirtied.
1585  virtual void getOwnedMicroNodes(
1586  DEP_MicroNodeList &micronodes);
1587 
1588  /// Explicitly propagate dirtiness for a particular micronode owned by
1589  /// some node.
1590  void propagateDirtyMicroNode(
1591  DEP_MicroNode &micronode,
1592  OP_EventType reason,
1593  void *data,
1594  bool send_root_event);
1595 
1596  /// Declares that this node's data depends on the @c op for the given
1597  /// reason (OP_INTEREST_DATA, OP_INTEREST_FLAG).
1598  /// @note There are no other acceptable values for type.
1599  virtual void addExtraInput(OP_Node *op, OP_InterestType type)
1600  { addExtraInput(OP_InterestRef(*op, type)); }
1601 
1602  /// Declares that this node's data depends on @c op channel. If vec_i is
1603  /// -1, then this node depends on all the channels of the parameter.
1604  void addExtraInput(OP_Node &op, int parm_i, int vec_i)
1605  { addExtraInput(OP_InterestRef(op,parm_i,vec_i)); }
1606 
1607  /// Generic version of addExtraInput() which adds a dependency from an
1608  /// source ref to this node's data micronode.
1609  void addExtraInput(const OP_InterestRef &source_ref);
1610 
1611  /// Generic version of addExtraInput() which adds a dependency from an
1612  /// source micronode to this node's data micronode.
1613  void addExtraInput(DEP_MicroNode &source_micronode);
1614 
1615  /// Marks this to be dependent on all the parameters inside of the
1616  /// multiparm.
1617  void addMultiparmInterests(OP_Node *srcnode, PRM_Parm &parm);
1618 
1619 
1620  static DEP_MicroNode *getEvalChannelMicroNode(int thread);
1621 
1622  /// Declare from an expression callback that the current evaluation channel
1623  /// is dependent on the given source.
1624  // @{
1625  static void addExtraInputToEvalChannel(
1626  int thread,
1628  {
1629  addExtraInputToEvalChannel(
1630  thread,
1631  OP_InterestRef(op, type));
1632  }
1633  static void addExtraInputToEvalChannel(
1634  int thread,
1635  OP_Node &op, int parm_i, int vec_i)
1636  {
1637  addExtraInputToEvalChannel(
1638  thread,
1639  OP_InterestRef(op,parm_i,vec_i));
1640  }
1641  static void addExtraInputToEvalChannel(
1642  int thread,
1643  const OP_InterestRef &source_ref)
1644  {
1645  DEP_MicroNode *
1646  target = getEvalChannelMicroNode(thread);
1647  if (target)
1648  OP_Node::addExtraInput(*target, source_ref);
1649  }
1650  static void addExtraInputToEvalChannel(
1651  int thread,
1652  DEP_MicroNode &src_micronode)
1653  {
1654  DEP_MicroNode *
1655  target = getEvalChannelMicroNode(thread);
1656  if (target)
1657  target->addExplicitInput(src_micronode);
1658  }
1659  // @}
1660 
1661  /// Generic versions of addExtraInput() used by the others. In particular,
1662  /// the static version of addExtraInput() allows you to define channel to
1663  /// channel dependencies.
1664  // @{
1665  static void addExtraInput(
1666  const OP_InterestRef &target_ref,
1667  const OP_InterestRef &source_ref);
1668  static void addExtraInput(
1669  const OP_InterestRef &target_ref,
1670  DEP_MicroNode &source_micronode);
1671  static void addExtraInput(
1672  DEP_MicroNode &target_micronode,
1673  const OP_InterestRef &source_ref);
1674  // @}
1675 
1676  static void addMultiparmInterests(const OP_InterestRef &target_ref,
1677  OP_Node *srcnode,
1678  PRM_Parm &parm);
1679  static void addMultiparmInterests(DEP_MicroNode &target,
1680  OP_Node *srcnode,
1681  PRM_Parm &parm);
1682 
1683  void getExtraInputNodes(
1684  OP_NodeList &extras,
1685  bool remove_duplicates = true,
1686  bool data_interest = true,
1687  bool parm_interest = true,
1688  bool flag_interest = true,
1689  bool include_parmlist = true) const;
1690  void getExtraOutputNodes(
1691  OP_NodeList &extras,
1692  bool remove_duplicates = true,
1693  bool data_interest = true,
1694  bool parm_interest = true,
1695  bool flag_interest = true) const;
1696 
1697  int getNumExtraInputs() const;
1698 
1699  void dumpExtraInputs(
1700  std::ostream &os,
1701  bool as_DOT,
1702  int indent_level = 0) const;
1703 
1704  // addExprOpDependency is a helper function for building dependencies for
1705  // the expression library callback functions.
1706  static void addExprOpDependency(const char *arg_str,
1707  const PRM_RefId &ref_id,
1708  OP_InterestType interest_type);
1709  static void addExprOpDependency1From2(const char *arg_str1,
1710  const char *arg_str2,
1711  const PRM_RefId &ref_id,
1712  OP_InterestType interest_type);
1713  static void addExprOpParmDependency(const char *arg_str,
1714  const PRM_RefId &ref_id,
1715  OP_InterestType interest_type);
1716  // NB: is reponsible for freeing new_arg!
1717  static void changeExprOpRef(const char *arg_str,
1718  char *&new_arg,
1719  const char *new_fullpath,
1720  const char *old_fullpath,
1721  const char *old_cwd);
1722  // NB: is reponsible for freeing new_arg!
1723  static void changeExprOpRef1From2(const char *arg_str1,
1724  const char *arg_str2,
1725  char *&new_arg1,
1726  char *&new_arg2,
1727  const char *new_fullpath,
1728  const char *old_fullpath,
1729  const char *old_cwd);
1730  // NB: is reponsible for freeing new_arg!
1731  static void changeExprOpParmRef(const char *arg_str,
1732  char *&new_arg,
1733  const char *new_fullpath,
1734  const char *old_fullpath,
1735  const char *old_cwd,
1736  const char *chan_name,
1737  const char *old_chan_name);
1738 
1739  void addGenericOpNameReference( const UT_String &oppath );
1740  void addGenericOpNameReference( const PRM_RefId &ref_id,
1741  OP_Node *node );
1742  void addGenericOpInputReference( const PRM_RefId &ref_id,
1743  OP_Node *node );
1744 
1745  static void moveAndUpdateDependencies(
1746  const OP_NodeList &src_nodes,
1747  const OP_NodeList &dest_nodes );
1748 
1749  static void updateChannelPtrs( CH_CollectionList &parents );
1750 
1751  bool getParmBaseNodePath(
1752  UT_String &path,
1753  int parm_index,
1754  int thread) const;
1755 
1756  // Make this function public so it can be called by OPUI_EditSubnet
1757  // and possibly others. Note that it is defined in PRM_ParmOwner so
1758  // that it can be called from the PRM library.
1759  virtual void rebuildParmDependency( int parm_index );
1760 
1761  // Clear op name dependencies
1762  virtual void clearParmDependency( int parm_index );
1763  // decrementOpReference() should only be called by clearParmDependency()
1764  void decrementOpReference(int node_id);
1765 
1766  virtual void dumpDependencies(std::ostream &os);
1767  void dumpOpDependents(OP_Node *ref, int brief,
1768  std::ostream &os);
1769  const OP_DependencyList
1770  &getOpDependents() const { return myOpDependents; }
1771 
1772 
1773  // INTERNAL: Do NOT use outside of OP_Node! Will be made private.
1774  int countReferences(int op_id);
1775 
1776  // Get the existing node *NAME* references (eg. expr references)
1777  // NB: This function assumes that refs is sorted without duplicate entries!
1778  void getExistingOpReferences(OP_NodeList &refs,
1779  bool recurse) const;
1780 
1781  // Get the as complete list of data references as possible for this node.
1782  // This combines getExistingOpReferences() which exist without cooking, and
1783  // getExtraInputNodes() which are the current references since the last
1784  // cook of its refernces.
1785  void getFullOpReferences(OP_NodeList &refs,
1786  bool include_descendants) const;
1787 
1788  // Get the existing node *NAME* dependents (eg. expr references)
1789  // NB: This function assumes that deps is sorted without duplicate entries!
1790  void getExistingOpDependents(OP_NodeList &deps,
1791  bool include_descendants) const;
1792 
1793  // Get the as complete list of data dependents as possible for this node.
1794  // This combines getExistingOpDependents() which exist without cooking, and
1795  // getExtraOutputNodes() which are the current dependents since the last
1796  // cook.
1797  void getFullOpDependents(OP_NodeList &deps,
1798  bool include_descendants) const;
1799 
1800  // Gets a list of parms that reference one of our channels/parms.
1801  void getParmsThatReference(const char *channame,
1802  UT_ValArray<PRM_Parm *> &parms,
1803  UT_IntArray &parmsubidxs);
1804 
1805  virtual void inputConnectChanged(int which);
1806 
1807  // Returns the number of output entries in the output array. Note
1808  // that this done regardless of which entries have any outputs connected.
1809  unsigned nOutputEntries() const;
1810  // Get access to the raw network items connected to our outputs.
1811  // These functions can focus on a single output connector, or treat
1812  // all outputs as a flat array by passign output_idx = -1.
1813  int nOutputItems(int output_idx = -1) const;
1814  OP_NetworkBoxItem *getOutputItem(int idx, int output_idx = -1) const;
1815  // Quick check if this node has any node outputs.
1816  bool hasAnyOutputNodes(bool through_dots = true,
1817  int output_idx = -1) const;
1818  // Fills a node list with all outputs from this node. This function can
1819  // search through dots, and dive into subnets. It can also run on a
1820  // single output connector or all of them.
1821  void getOutputNodes(UT_Array<OP_Node*> &outputs,
1822  bool into_subnets = false,
1823  bool through_dots = true,
1824  int output_idx = -1) const;
1825  // Quick function to return the first output node, searching depth first
1826  // through dots if requested.
1827  OP_Node *getFirstOutputNode(bool through_dots = true,
1828  int output_idx = -1) const;
1829 
1830  // obtains an output node that leads to a target node (e.g., during network
1831  // traversal). Null if target is not a descendent.
1832  OP_Node *getOutputTowardsNode(const OP_Node *target);
1833 
1834  /// Fill in 'tree' with details that are common to all node types. Then call
1835  /// fillInfoTreeNodeSpecific() to get specific details about this specific
1836  /// node (be it a SOP, CHOP, etc)
1837  void fillInfoTree(UT_InfoTree &tree,
1838  const OP_NodeInfoTreeParms &parms);
1839 
1840  /// Triggered by 'fillInfoTree()', this virtual function adds all node-
1841  /// specific info to 'tree'. All child classes must create their own
1842  /// branches under 'tree' to place their info
1843  virtual void fillInfoTreeNodeSpecific(UT_InfoTree &tree,
1844  const OP_NodeInfoTreeParms &parms);
1845 
1846  /// Optionally called on parent from fillInfoTreeNodeSpecific() to provide
1847  /// some information about node that only parent network can provide.
1848  /// @return True if parent added info specific to that child.
1849  virtual bool fillInfoTreeChildSpecific(UT_InfoTree &tree,
1850  const OP_NodeInfoTreeParms &parms,
1851  OP_Node *child);
1852 
1853  /// This method has to do with 'fillInfoTree()' above. When the call to
1854  /// fillInfoTree() completes, the UT_InfoTree 'tree' will be parsed and
1855  /// displayed in a dialog box by OPUI_OpInfoDialog, at which point, that
1856  /// class will want to ask us - which branch of the tree would you like to
1857  /// be selected by default when the dialog is displayed for the first time?
1858  virtual const char *getDefaultSelectedInfoTreeBranchName() const;
1859 
1860  // These methods get input data for the OP. If they return an error code
1861  // >= UT_ERROR abort, then the errno should be set, and there may be a
1862  // further local error message. There is no error checking to ensure that
1863  // each locked source is only released once, so it's up to the user. The
1864  // standard method is to call lockInputs(), then call unlockInputs() on
1865  // exit. However, in some cases (i.e. switch SOP) only some sources need
1866  // to be cooked.
1867  //
1868  // lockInput() will return an error code >= UT_ERROR iff idx <
1869  // minInputs(). Otherwise, it's considered to be an optional input, so no
1870  // data will be returned. A simple rule of thumb: If lockInput() returns
1871  // ok, the source has to be unlocked, otherwise it shouldn't be unlocked!
1872  // If lockInputs() detects an error, it will automatically unlock the
1873  // inputs so that unlockInputs() should NOT be called!
1874  virtual OP_ERROR lockInput(unsigned idx, OP_Context &context);
1875  virtual void unlockInput(unsigned idx);
1876  virtual OP_ERROR lockInputs(OP_Context &context);
1877  virtual void unlockInputs(void);
1878 
1879  // This "serial" number refers to the number of times that the geometry
1880  // had been changed. Note, only the "modeller" should bump the cook count,
1881  // the OP cook method does this also, but has privilaged access.
1882  int getCookCount(void) const { return myCookCount; }
1883  void triggerOutputChanged();
1884 
1885  void triggerUIChanged(
1888  // Returns the index of cooked input to a SOP switch
1889  virtual int cookedInputIndex() const { return -1; }
1890 
1891  /// For nodes which simply pass-through their data from some other node,
1892  /// this returns the node whose data will used transparently as this node's
1893  /// output. This function can give different values depending on its
1894  /// parameters. Used by node traversal algorithms.
1895  ///
1896  /// The default implementation returns the first input if it's bypassed, so
1897  /// subclasses should only do something different if this function returns
1898  /// NULL.
1899  ///
1900  /// @param t Eval time
1901  /// @param mark_used Mark this node is using the returned node (if
1902  /// non-NULL).
1903  ///
1904  virtual OP_Node *getPassThroughNode(
1905  fpreal t,
1906  bool mark_used = false);
1907 
1908  bool setMinimumCacheSize(int min_size);
1909 
1910  OP_VERSION getVersionParms() const
1911  { return dataMicroNodeConst().modVersion(); }
1912 
1913  // This will be called if the timeInterest flag is set.
1914  // This will return true if the node needs to be dirtied for cooking
1915  virtual bool handleTimeChange(fpreal /* t */) { return false; }
1916 
1917  /// Returns true if the OP depends on time at the given time. This
1918  /// is sensitive to handleTimeChange's overrides.
1919  bool isTimeDependent(OP_Context &context);
1920 
1921  static int getGlobbedNodes(OP_Node *cwd, UT_String &holder,
1922  const char *pattern, UT_WorkArgs &argv,
1923  OP_GlobContext *context);
1924 
1925  static int getGlobbedNetworkBoxes(OP_Node *cwd, UT_String &holder,
1926  const char *pattern, UT_WorkArgs &argv,
1927  OP_GlobContext *context);
1928 
1929  static int getGlobbedPostIts(OP_Node *cwd, UT_String &holder,
1930  const char *pattern, UT_WorkArgs &argv,
1931  OP_GlobContext *context);
1932 
1933 
1934  /// Obtains additional nodes that should be copied or deleted when this
1935  /// node is copied or deleted. It applies to situations, such as, where
1936  /// an hidden input node feeds only to this node and serves only that
1937  /// purpose, so it should be coppied/deleted along with the master.
1938  virtual void getExtraNodesForCopyOrDelete(OP_NodeList &extras)const;
1939 
1940  // Runs the creation script (if there is one). The return value is false
1941  // if the node was deleted while running the script. In this case
1942  // obviously the node pointer becomes invalid and should not be used
1943  // any more. It returns true if the node still exists.
1944  virtual bool runCreateScript();
1945  // Go through all our parms to match the values to the current hip file
1946  // units settings.
1947  void updateParmsToMatchCurrentUnits();
1948 
1949  /// Matches the node to the current HDA definition, loading the contents
1950  /// section if ncecessary and setting the match flag.
1951  virtual void matchOTLDefinition();
1952 
1953  /// Unmatches (unlocks) the node from the current HDA definition.
1954  virtual void unmatchOTLDefinition();
1955 
1956  /// Method that is invoked when the HDA index file has been cleared
1957  /// because the underlying HDA definition has changed.
1958  virtual void handleOTLIndexFileCleared();
1959 
1960  /// Returns the error string where we keep all errors generated during
1961  /// our most recent synchronization attempt.
1962  const UT_String &getSyncErrors() const
1963  { return mySyncErrors; }
1964  /// Returns the error level generated in our last synchronization attempt.
1965  OP_ERROR getSyncErrorLevel() const
1966  { return mySyncErrorLevel; }
1967 
1968  /// Interface to flag that specifies whether or not we match our definition.
1969  int getMatchesOTLDefinition() const;
1970 
1971  /// Utility function for syncing/unsyncing all uncestor nodes.
1972  static void propagateMatchOTLDefinitionToAncestors(OP_Node *node,
1973  bool sync_flag);
1974 
1975  // Some extra functions for dealing with access rights as they relate
1976  // to matching the OTL definition.
1977  int getCanDeviateFromOTLDefinition() const;
1978  void setAllChildAssetPermissions(int permission);
1979  // Recompute the asset permissions because something changed like the node
1980  // was locked or unlocked.
1981  void computeAllChildAssetPermissions();
1982  // Returns true if this node is contained inside a locked HDA, but
1983  // is marked as an editable node within that HDA.
1984  bool getIsEditableAssetSubNode() const;
1985 
1986  // Turn off our export flag and the export flags of our children.
1987  void turnOffAllChildExports(void);
1988 
1989  // Collection of methods for working with licensed assets.
1990  bool haveLicenseToAccessContents(
1991  OP_Node* opt_specific_child = nullptr) const;
1992  bool haveLicenseToAccessParentContents() const;
1993  bool haveAncestorWithoutFullLicense(bool ignore_self) const;
1994  OP_OTLLicenseType getLicense() const;
1995  // Get the first (oldest) ancestor without a license to access contents.
1996  OP_Node *getFirstExecLicenseOnlyAncestor(
1997  bool ignore_self = true) const;
1998  // Get the last (youngest) ancestor without a license to access contents.
1999  OP_Node *getLastExecLicenseOnlyAncestor(
2000  bool ignore_self = true) const;
2001 
2002  bool isCompiled() const;
2003 
2004  // Save as a series of ASCII commands.
2005  void saveWires(std::ostream &os, const char *name,
2006  int dogeneral = 0);
2007  void saveOutputWires(std::ostream &os, const char *name,
2008  int dogeneral = 0);
2009  virtual void saveIntrinsicCommand(std::ostream &os,
2010  const char *name);
2011 
2012  /// Writes to 'os' a string of hscript commands to recreate this node.
2013  virtual OP_ERROR saveCommand(std::ostream &os,
2014  const char *name,
2015  fpreal x,
2016  fpreal y,
2017  const char *netboxname,
2018  const OP_SaveCommandOptions &options);
2019 
2020  // This method saves a chlock style command for this node's parameters.
2021  // name - the name of the node to print on the command;
2022  // command - the name of the command;
2023  // flag_method - a PRM_Parm method that can be queried for the flag to
2024  // output;
2025  // defaultstoo - prints a default "-*" or "+*" as the first parameter
2026  // reverse - normally the default is "-*" followed by the list of
2027  // parameters that result true for flag_method(). If
2028  // reverse is true, then the default is "+*" followed by
2029  // the parameters where flag_method() is false. Only useful
2030  // when defaultstoo is true.
2031  // parm_array - an optional array of parameters whose values should be
2032  // printed. If this array is NULL, then the entire node
2033  // is searched.
2034  void saveParameterFlags(std::ostream &os, const char *name,
2035  const char *command,
2036  bool (PRM_Parm::*flag_method)(int) const,
2037  bool defaultstoo, bool reverse,
2038  UT_Array<opParmData> *parm_array);
2039 
2040  void saveUserDataCommand(
2041  std::ostream &os, const char *node_name,
2042  bool omit_version = false);
2043 
2045  {
2046  RAMP_ERR_SUCCESS,
2047  RAMP_ERR_NOT_FOUND,
2048  RAMP_ERR_ONLY_KEY
2049  };
2050  virtual RampError rampCommand(bool remove, fpreal pos, float rgba[4]);
2051  RampError rampCommand(bool remove, fpreal pos, float rgba[4],
2052  UT_Ramp &ramp);
2053 
2054  virtual bool loadRamp(UT_IStream &is, const char *path=0);
2055 
2056  bool loadRamp(UT_IStream &is, UT_Ramp &ramp,
2057  const char *path=0);
2058  OP_ERROR saveRamp(std::ostream &os, UT_Ramp &ramp,
2059  const char *name = 0, int command = 0);
2060 
2061  bool getUserData(const UT_StringRef &key,
2062  UT_StringHolder &result) const;
2063  void setUserData(const UT_StringRef &key,
2064  const UT_StringHolder &data,
2065  bool save_undo);
2066  bool hasUserData(const UT_StringRef &key) const;
2067  bool deleteUserData(const UT_StringRef &key,
2068  bool save_undo);
2069  const UT_Options &userData() const
2070  { return myUserData; }
2071  bool loadUserData(UT_IStream &is, const char *path=nullptr);
2072  OP_ERROR saveUserData(std::ostream &os, const char *path);
2073  void clearUserData(bool save_undo);
2074  virtual void userDataChanged(const UT_StringHolder &key);
2076  /// Prefix to use for internally used user data.
2077  static const char *internalUserDataPrefix() { return "sidefx::"; }
2078 
2079  /// Returns a shared pointer to a previously stored blind data. If no
2080  /// blind data exists with the given key, an empty shared pointer is
2081  /// returned.
2082  UT_SharedPtr<void> getBlindData(const char *key) const;
2083 
2084  /// Return a pointer to a previously stored blind data, statically cast
2085  /// to the type given. If the cast fails, or if there's no data of that
2086  /// type, a NULL pointer is returned. To distinguish between the two cases
2087  /// call hasBlindData().
2088  template<typename T>
2089  UT_SharedPtr<T> getBlindData(const char *key) const
2090  { return UTstatic_pointer_cast<T>(getBlindData(key)); }
2091 
2092  /// Stores a blind data pointer on this OP_Node object. Any entry that
2093  /// previously existed will be erased, and, if it is the last reference,
2094  /// the object itself deleted. The \c void type can convert from any other
2095  /// shared pointer type, while storing the deleter function, allowing
2096  /// OP_Node to delete the data without knowing anything about the class.
2097  /// Blind data is *not* stored with the class.
2098  void setBlindData(const char *key, UT_SharedPtr<void> ptr);
2099 
2100  /// Returns true if this object stores a blind data with the given key.
2101  bool hasBlindData(const char *key) const;
2102 
2103  /// Remove any reference to the blind data of the given key from this
2104  /// object.
2105  bool deleteBlindData(const char *key);
2106 
2107  void getDataBlockKeys(UT_StringArray &keys,
2108  const UT_StringHolder &type =
2109  UT_StringHolder()) const;
2110  OP_DataBlockPtr getDataBlock(const char *key) const;
2111  void setDataBlock(const char *key, OP_DataBlockPtr ptr);
2112  OP_ERROR saveDataBlocksPacket(std::ostream &os,
2113  const char *path_prefix,
2114  const UT_String &node_name);
2115  bool loadDataBlocks(UT_IStream &is, const char *path);
2116  virtual void dataBlockChanged(const UT_StringHolder &key);
2117 
2118  // deleteNodeData is called when the OP_Cache wants to delete some data.
2119  // This method should return 1 if you want change events to be propagated
2120  // to the extra inputs when data is deleted from the cache.
2121  virtual int deleteNodeData(void *);
2122  void propagateNodeDataDeleted();
2123 
2124  // getCachedPythonObject returns NULL if no object exists with the given
2125  // key.
2126  PY_OpaqueObject *getCachedPythonObject(const char *key) const;
2127  // Call setCachedPythonObject with a PyObject * cast to a void *, not with
2128  // a PY_OpaqueObject * cast to a void *. The pointer must not be null.
2129  void setCachedPythonObject(
2130  const char *key, void *opaque_py_object);
2131  // deleteCachedPythonObject returns false if no value exists with that key.
2132  bool deleteCachedPythonObject(const char *key);
2133  // cachedPythonObjects returns a UT_SymbolMap containing pointers to
2134  // PY_OpaqueObjects. The pointers are not null.
2135  const OP_PythonObjectCache &cachedPythonObjects() const
2136  { return myCachedPythonObjects; }
2137 
2138  bool loadExtraInputs(UT_IStream &is, const char *path=0);
2139 
2140  void saveOverrides(std::ostream &os);
2141  void saveOverrides(std::ostream &os, OP_Node *root,
2142  const UT_String &rootpath,
2143  bool &added);
2144  void saveChildOverrides(std::ostream &os, OP_Node *root,
2145  const UT_String &rootpath,
2146  bool &added);
2147  bool loadOverride(UT_IStream &is);
2148  virtual UT_ErrorSeverity
2149  prmCookOverrides(fpreal t, int thread,
2150  const char *parm_name, int vec_idx);
2151  virtual bool isParmPendingOverride(const char *parm_name,
2152  int vec_idx) const;
2153  OP_ERROR cookOverrides(OP_Context &c);
2155  virtual void removeOverrideDestination(OP_Node * /*dest*/) {}
2156  virtual void removeOverrideDestination(OP_Node * /*dest*/,
2157  int /*parm_idx*/) {}
2158 
2159  // Overriding virtual function in PRM_ParmOwner to run a command.
2160  virtual void executeCommand(const char *command,
2161  std::ostream *out,
2162  std::ostream *err) const;
2163  virtual void pushAsPwdAndRunPython(
2164  PY_CompiledCode &compiled_code,
2165  PY_Result::Type desired_result_type,
2166  PY_Result &result,
2167  PY_EvaluationContext *context=nullptr) const;
2168 
2169  OP_ERROR executeHscriptScript(UT_String &script,
2170  const OP_Context &context);
2171  OP_ERROR executePythonScript(UT_String &script,
2172  const OP_Context &context);
2173 
2174  void addPythonNodeError(const PY_Result &py_result);
2175 
2176  void saveInputs(std::ostream &os, bool compile_basic);
2177  bool loadInputs(UT_IStream &is, const char *path=0,
2178  bool named = false);
2179  void saveNamedInputs(std::ostream &os, bool compile_basic);
2180  void saveNamedOutputs(std::ostream &os);
2181  bool loadNamedOutputs(UT_IStream &is, const char *path=0);
2182 
2183  // These methods provide access to the options that can be stored on each
2184  // input of a node, if the node type enables this feature.
2185  void getEditableInputDataKeys(int idx,
2186  UT_StringArray &keys) const;
2187  const UT_OptionEntry*getEditableInputData(int idx,
2188  const UT_StringRef &key) const;
2189  void setEditableInputData(int idx,
2190  const UT_StringHolder &key,
2191  const UT_OptionEntry &value);
2192  void saveEditableInputData(std::ostream &os) const;
2193  bool loadEditableInputData(UT_IStream &is,
2194  const char *path);
2195  // Special case functions for getting and setting the input "name", which
2196  // just call the generic InputData functions.
2197  UT_StringHolder getEditableInputString(int idx,
2198  const UT_StringRef &key) const;
2199  void setEditableInputString(int idx,
2200  const UT_StringRef &key,
2201  const UT_StringHolder &str);
2202 
2203  /// @{ If a subclass is interested in the saved input or output names, then
2204  /// it should override this method. The array will be filled during load.
2205  virtual UT_StringArray * getArrayForLoadedInputNames();
2206  virtual UT_StringArray * getArrayForLoadedOutputNames();
2207  /// @}
2208 
2209  void checkInputs(); // this method will check the
2210  // node references in all the inputs
2211 
2212  // Saves out extra information for this node to be included in a dialog
2213  // script that defines an operator type created from this one.
2214  virtual void saveDialogScriptExtraInfo(std::ostream &os);
2215 
2216  // Fills in the supplied default gallery entry with info from this node.
2217  virtual void createGalleryEntry(OP_GalleryEntry &entry);
2218 
2219  // When a string parameter can have the syntax: 'op:/...', use these
2220  // evaulate methods to do the approprate checking and reference building.
2221  // These methods will return a reference to the OP_Node if one is
2222  // referenced. If the syntax is something like:
2223  // op:/foo/bar[32]
2224  // Then the optime will be (32-1)/$FPS rather than the evaluation time.
2225  void evalOpPathString(UT_String &val, int pi, int vi,
2226  fpreal t, int &op_id, fpreal &op_time,
2227  int expanded = 1);
2228  void evalOpPathString(UT_String &val, const char *pn,
2229  int &pi, int vi, fpreal t,
2230  int &op_id, fpreal &op_time,
2231  int expanded=1);
2232  static int findOpFramePair(const char *path, int &op_id,
2233  fpreal &frame);
2234 
2235  /// Build a UT_XformOrder out of TRS and XYZ parameter values
2236  static void buildXformOrder(int trs, int xyz,
2237  UT_XformOrder &order);
2238 
2239  /// Translate a TRS parameter menu index into the UT_XformOrder type
2240  static UT_XformOrder::rstOrder getMainOrder( int trs );
2241  /// Translate a UT_XformOrder type into a TRS parameter menu index
2242  /// (inverse of getMainOrder())
2243  static int getMainOrderMenuIndex(UT_XformOrder::rstOrder order);
2244  /// Translate a XYZ parameter menu index into the UT_XformOrder type
2245  static UT_XformOrder::xyzOrder getRotOrder( int xyz );
2246  /// Translate a UT_XformOrder type into a XYZ parameter menu index
2247  /// (inverse of getRotOrder())
2248  static int getRotOrderMenuIndex(UT_XformOrder::xyzOrder order);
2249 
2250  /// NB: None of the getXformPivot() or getPivotParmValue() methods take
2251  /// any pivot compensation transform into account. It is up to the
2252  /// caller to account for any such transform.
2253  static UT_Vector3R getXformPivot(int trs,
2254  fpreal tx, fpreal ty, fpreal tz,
2255  fpreal px, fpreal py, fpreal pz);
2256  static UT_Vector3R getXformPivot(int trs,
2257  fpreal tx, fpreal ty, fpreal tz,
2258  fpreal px, fpreal py, fpreal pz,
2259  fpreal pivot_rx, fpreal pivot_ry,
2260  fpreal pivot_rz, bool inverse = false);
2261  static UT_Vector3R getPivotParmValue(int trs,
2262  fpreal tx, fpreal ty, fpreal tz,
2263  fpreal px, fpreal py, fpreal pz);
2264  static UT_Vector3R getPivotParmValue(int trs,
2265  fpreal tx, fpreal ty, fpreal tz,
2266  fpreal px, fpreal py, fpreal pz,
2267  fpreal pivot_rx, fpreal pivot_ry,
2268  fpreal pivot_rz, bool inverse = false);
2269 
2270  static void buildXform(int trs, int xyz,
2271  float tx, float ty, float tz,
2272  float rx, float ry, float rz,
2273  float sx, float sy, float sz,
2274  float px, float py, float pz,
2275  UT_Matrix4 &mat);
2276  static void buildXform(int trs, int xyz,
2277  double tx, double ty, double tz,
2278  double rx, double ry, double rz,
2279  double sx, double sy, double sz,
2280  double px, double py, double pz,
2281  UT_DMatrix4 &mat);
2282  static void buildXform(int trs, int xyz,
2283  float tx, float ty, float tz,
2284  float rx, float ry, float rz,
2285  float sx, float sy, float sz,
2287  UT_Matrix4 &mat);
2288  static void buildXform(int trs, int xyz,
2289  double tx, double ty, double tz,
2290  double rx, double ry, double rz,
2291  double sx, double sy, double sz,
2293  UT_DMatrix4 &mat);
2294  static void buildXform(int trs, int xyz,
2295  float tx, float ty, float tz,
2296  float rx, float ry, float rz,
2297  float sx, float sy, float sz,
2298  float s_xy, float s_xz, float s_yz,
2299  float px, float py, float pz,
2300  UT_Matrix4 &mat);
2301  static void buildXform(int trs, int xyz,
2302  double tx, double ty, double tz,
2303  double rx, double ry, double rz,
2304  double sx, double sy, double sz,
2305  double s_xy, double s_xz, double s_yz,
2306  double px, double py, double pz,
2307  UT_DMatrix4 &mat);
2308  static void buildXform(int trs, int xyz,
2309  float tx, float ty, float tz,
2310  float rx, float ry, float rz,
2311  float sx, float sy, float sz,
2312  float s_xy, float s_xz, float s_yz,
2314  UT_Matrix4 &mat);
2315  static void buildXform(int trs, int xyz,
2316  double tx, double ty, double tz,
2317  double rx, double ry, double rz,
2318  double sx, double sy, double sz,
2319  double s_xy, double s_xz, double s_yz,
2321  UT_DMatrix4 &mat);
2322  static void buildXform(
2323  const UT_Matrix4F::FullTransformModel &parms,
2324  UT_Matrix4F &mat);
2325  static void buildXform(
2326  const UT_Matrix4D::FullTransformModel &parms,
2327  UT_Matrix4D &mat);
2328  static void buildXform(int trs,
2329  float tx, float ty, float rz,
2330  float sx, float sy, float px, float py,
2331  UT_Matrix3 &mat);
2332  static void buildXform(int trs,
2333  double tx, double ty, double rz,
2334  double sx, double sy, double px, double py,
2335  UT_DMatrix3 &mat);
2336  static void buildXform(int trs,
2337  float tx, float ty, float rz,
2338  float sx, float sy, float s_xy,
2339  float px, float py,
2340  UT_Matrix3 &mat);
2341  static void buildXform(int trs,
2342  double tx, double ty, double rz,
2343  double sx, double sy, double s_xy,
2344  double px, double py,
2345  UT_DMatrix3 &mat);
2346 
2347  virtual int getTranslateParmIndex();
2348 
2349  // This is done only after a load to make sure that
2350  // all inputs have been resolved correctly.
2351  void resolveInputReferences();
2352 
2353  static void clearAllPendingUndoFlags();
2354 
2355  virtual void clearUndoFlags();
2356  virtual void setAnyUndoFlag();
2357  void saveForUndoInput();
2358 
2359  void blockModify(int on_off, int propagate = 1);
2360  int isBlockModify(void) const;
2361  bool isModifyWaiting() const;
2362  virtual void propagateEndBlockModify();
2363 
2364  // Only returns anything in the case of chops
2365  virtual const CL_Clip *getClip(OP_Context *context = 0);
2366 
2367  /// Returns the a chop network path suitable for storing motion effects
2368  /// associated with this node.
2369  void getMotionEffectsNetworkPath(UT_String &path);
2370 
2371  /// Return the cook information as a formatted string.
2372  void getCookInfo(UT_String &info) const;
2373  /// Return the cook information in a UT_InfoTree.
2374  void getCookInfoTree(UT_InfoTree &tree) const;
2375 
2376  // Query color for Net Overview rendering
2377  virtual int getNetOverviewColor( UT_Color &color );
2378 
2379  // Those operators which need a ramp editor must define this method.
2380  virtual UT_Ramp *getRamp();
2381 
2382  virtual int isCookingRender() const { return 0; }
2383  virtual void setCookingRender(int val);
2384 
2385  virtual void clearInterrupted()
2386  { clearInterruptedImpl(/*allow_recook*/true); }
2387  int wasInterrupted() const
2388  { return flags().getInterrupted(); }
2389 
2390  // work-around to display warning message when export src or destination
2391  // are renamed. OP_Node::cook clears the error messages when a node export
2392  // changes so we had to save the fact that a rename conflict is pending
2393  void setRenameConflict()
2394  { myRenameConflict = 1; }
2395  void setRunningCreateScript(int onoff);
2396 
2397  // Base class methods to output code to a file or a stream:
2398  virtual int outputCode(OP_OutputCodeParms &, OP_Context &);
2399 
2400  virtual fpreal getTimeTransform(int input, fpreal t);
2401  virtual void getInputRes(int input, fpreal t,
2402  const OP_Context &context,
2403  OP_Context &input_context);
2404 
2405  // Utility methods:
2406  UT_TokenString & getHashCode(OP_Context &context, int group_mask =1);
2407  virtual UT_TokenString & getParmHashCode(OP_Context &context,
2408  int group_mask = 1);
2409 
2410  virtual int getNumInputsToHash();
2411  virtual OP_Node *getInputToHash(int i);
2413  void clearHashCodeFlags();
2414  bool isHashCodeBuilt() const { return myBuiltHashCode;}
2415  void builtHashCode(bool b = true) { myBuiltHashCode = b; }
2416  void buildInputHashCode(UT_TokenString &string,
2417  OP_Context &context,
2418  int group_mask,
2419  int level);
2421  // If an interactive state was used to create this node, set it here.
2422  void setCreatorState(const char *s)
2423  { myCreatorState.harden(s); }
2424  const UT_String &getCreatorState() const { return myCreatorState; }
2425  void builtExplicitly(int yn) { myBuiltExplicitly = yn; }
2426  int wasBuiltExplicitly() const{ return myBuiltExplicitly; }
2427 
2428  bool matchesState(const char *state) const;
2429 
2430  /// Some nodes (VOPs and SHOPs) represent shaders, so this method
2431  /// returns node parameters that are used as shader parameters.
2432  virtual const PRM_Template *getShaderParmTemplates();
2433 
2434  // Don't even think about calling changeParmTemplate if you aren't
2435  // OP_Operator.
2436  virtual void changeParmTemplate(PRM_Template *new_template);
2437 
2438  // Deletes any input or output connections in excess of maximum allowed.
2439  virtual void ensureInputsAndOutputsAreValid();
2440 
2441  // Connect the node to an input. If branch_off is false and the input node
2442  // currently has outputs, the node will be inserted before the outputs.
2443  void connectToInputNode(OP_Node &inputnode, int input_idx,
2444  int branch_off=0);
2445 
2446  // This method should be called when the user edits an overridden channel
2447  virtual int editCallback(CL_Track *track, fpreal t,
2448  fpreal newValue);
2449 
2450  // This mechanism allows users to communicate editing changes
2451  static OP_EditCallback getEditCallback(void *&data);
2452  //static void setEditCallback(OP_EditCallback func,
2453  //void *data);
2454 
2455  // These build an xform matrix based upon the given parameters.
2456  // The axis is the axis around which to rotate by 90 degrees. If
2457  // it is lower case, it will be rotated by +90, if it is upper case,
2458  // by -90. To not rotate at all, use '-'.
2459  static void buildQuadricXform(UT_Matrix4 &mat,
2460  float tx, float ty, float tz,
2461  float sx, float sy, float sz,
2462  char axis = 'y',
2463  float rx = 0.0f, float ry = 0.0f,
2464  float rz = 0.0f);
2465 
2466  static void buildQuadricXform(UT_DMatrix4 &mat,
2467  double tx, double ty, double tz,
2468  double sx, double sy, double sz,
2469  char axis = 'y',
2470  double rx = 0.0, double ry = 0.0,
2471  double rz = 0.0);
2472 
2473  static int buildOpMenu(OP_Network *net, PRM_Name *theMenu,
2474  int theMenuSize, int (*doAdd)(OP_Node *) = 0,
2475  int startItem = 0, const PRM_Parm *parm = 0,
2476  int showSubnets = 1, int expandSubnets = 1,
2477  bool recurse = false);
2478 
2479  // Build the "Predefined Rules" menu that is common to several OPs
2480  // including Event and Group POPs. This is built from the text file table
2481  // OP<name>Rules, where name is the OP type (ie Event).
2482  static void buildPreDefRulesMenu(PRM_Name *menu,
2483  OP_PreDefRules &pdr);
2484 
2485  // Allows operators to use their own local table for variables and build
2486  // structures on demand... Implement the syntax highlight version only
2487  // if you need to resolve variables for syntax highlighting that are not
2488  // normally resolved by the generic resolveVariable() method.
2489  virtual const CH_LocalVariable *resolveVariable(const char *name);
2490  virtual const CH_LocalVariable *resolveExtraVariableForSyntaxHighlight(
2491  const char *name);
2492 
2493  // This value bumps whenever nodes are created/deleted/renamed.
2494  static int getNameSerialIndex();
2495 
2496  // export mapping techniques
2497  virtual void setMapping(int idx, int type, const char *label = 0);
2498  virtual int getMapping(int idx, const char *&label) const;
2499 
2500  // drag-n-drop receive methods
2501  virtual int acceptDragDrop(DD_Source &src, const char *label);
2502  virtual int testDragDrop(DD_Source &src);
2503  virtual void getDragDropChoice(DD_Source &src, DD_ChoiceList &c);
2504 
2505  // These methods are used to give quick overview information about a node
2506  bool hasComment() const;
2507  bool hasParmsNotAtFactoryDefault() const;
2508  bool hasAnimatedParms() const;
2509  bool hasChopOverriddenParms() const;
2510 
2511  /// traverseInputs calls 'callback' on this node and all its inputs.
2512  /// If callback returns true for any node, it will stop and return
2513  /// true, otherwise it will return false;
2514  /// @param callback Callback function
2515  /// @param data User data passed to the callback function
2516  /// @param follow_subnets If input is a subnet, we continue
2517  /// traversing from its display node.
2518  /// @param follow_ref_inputs Follow inputs marked as reference inputs
2519  /// @param follow_extra_inputs Follow nodes which this node implicitly
2520  /// depends on.
2521  /// @param extra_interest_mask For extra inputs, this mask allows one to
2522  /// restrict which of those dependency types
2523  /// follow.
2524  //@{
2525  bool traverseInputs(bool (*callback)(OP_Node &, void *),
2526  void *data,
2527  bool follow_subnets,
2528  bool follow_ref_inputs,
2529  bool follow_extra_inputs,
2530  bool follow_passthrough_inputs,
2531  OP_InterestType extra_interest_mask =
2532  OP_INTEREST_ALL);
2533  bool traverseInputs(bool (*callback)(const OP_Node &, void*),
2534  void *data,
2535  bool follow_subnets,
2536  bool follow_ref_inputs,
2537  bool follow_extra_inputs,
2538  bool follow_passthrough_inputs,
2539  OP_InterestType extra_interest_mask =
2540  OP_INTEREST_ALL) const;
2541  //@}
2542 
2543  /// Traverses children of this node, calling 'callback' on all children.
2544  /// If callback returns true, the traversal stops at that node.
2545  bool traverseChildren(bool (*callback)(OP_Node &, void*),
2546  void *data,
2547  bool recurse_into_subnets);
2548 
2549  // Very specialized to see if this node (and optionally, any input
2550  // ancestors are also cooking.
2551  bool isCooking(bool include_ancestors) const;
2552 
2553  // This method returns true if the OP_Node makes use of its footprint
2554  // flag and false otherwise.
2555  virtual bool usesFootprint() const { return false; }
2556 
2557  void getExternalReferences(UT_StringArray &reflist,
2558  UT_StringArray *nodelist = 0,
2559  bool from_children_too = true,
2560  bool collapse = false,
2561  bool check_missing = false,
2562  bool show_missing_only = false);
2563  virtual bool getSaveWithVopnets();
2564  virtual void runDelScript();
2565  /// Overriden in VOPs to remove any channel refrences we may have
2566  /// to the node being deleted.
2567  virtual void preDelete() { }
2568 
2569  // Two functions for upcasting this node to a DOP_Parent. DOP_Parent
2570  // is a class which owns a simulation and has DOP_Nodes as children.
2571  virtual DOP_Parent *castToDOPParent() { return 0; }
2572  virtual const DOP_Parent *castToDOPParent() const { return 0; }
2574  // These provide a version which you can query without being above DOP.
2576  { return (OP_DopParent *) castToDOPParent(); }
2577  const OP_DopParent *castToOpDopParent() const
2578  { return (const OP_DopParent *) castToDOPParent(); }
2579 
2580  // This function upcasts this node to a VOP_CodeGenerator.
2581  // VOP_CodeGenerator is a class which generates VEX code from the VOPs
2582  // contained inside the node.
2583  virtual VOP_CodeGenerator *getVopCodeGenerator() { return 0; }
2584  virtual VOP_CodeGenerator *getVopAutoCodeGenerator() { return 0; }
2585 
2586  // Return the manager that handles exported parameters from contained
2587  // Parameter VOPs. Only certain kinds of VOP nodes can have such a manager
2588  // (i.e. Subnet VOPs, VOP HDAs). Note that a node cannot have both a code
2589  // generator AND a parms manager because the code generator already has its
2590  // own parms manager.
2591  virtual VOP_ExportedParmsManager *getVopExportedParmsManager(
2592  bool create_if_needed=false)
2593  { return nullptr; }
2594 
2595  /// @{
2596  /// Methods to postpone the update of the code generator until ending
2597  /// the last (level zero) update. This avoids recalculation of parameters
2598  /// and vop signatures, which can be quite costly.
2599  // TODO: remove these two virtuals in farour of getVopCodeGenerator()
2600  // returning OP_VopCodeGenerator from which VOP_CodeGenerator
2601  // derives and which has these two virtuals available at OP level.
2602  virtual int beginVopCodeGeneratorUpdate() { return 0; }
2603  virtual void endVopCodeGeneratorUpdate(int update_level) {}
2604  /// @}
2605 
2606  // Build a command line for a VEX script to be called with. This does all
2607  // the channel evaluation and string expansion required. If there is an
2608  // error, 0 is returned (otherwise 1).
2609  int buildVexCommand(UT_String &result,
2610  const PRM_Template *templatelist,
2611  fpreal now,
2612  int start_parm = 0,
2613  int end_parm = INT_MAX,
2614  bool use_parmvop_tag=true
2615  );
2616  int buildVexCommandWithDependencies(OP_Node *owner,
2617  DEP_MicroNode *depnode,
2618  UT_String &result,
2619  const PRM_Template *templatelist,
2620  fpreal now,
2621  int start_parm = 0,
2622  int end_parm = INT_MAX,
2623  bool use_parmvop_tag=true
2624  );
2625 
2626  // Builds a VEX script using standardized parameter names.
2627  // "vexsrc": int for myself, shop, or script.
2628  // "script": raw vex script
2629  // "soppath": for the shop path.
2630  static PRM_ChoiceList theVexSrcParmMenu;
2631  static PRM_Name theVexSrcParmName;
2632  static PRM_Name theVexScriptParmName;
2633  static PRM_Name theVexNodePathParmName;
2634  static PRM_Name theVexClearParmName;
2635  virtual void buildVexScript(UT_String &script, fpreal t,
2636  OP_Node *owner,
2637  UT_Map<int, bool> *visitlist = 0);
2638  virtual void buildVexScript(UT_String &script, fpreal t,
2639  DEP_MicroNode *depnode,
2640  UT_Map<int, bool> *visitlist = 0);
2641 
2642 
2643  // Returns true if vex shader has parameter by a given name.
2644  virtual bool hasVexShaderParameter(const char *parm_name);
2645 
2646 
2647  /// This function returns a string that encodes all the necessary
2648  /// information about a node-based material that helps the script-based
2649  /// materials to function properly. The string usually encodes info stored
2650  /// on child nodes, such as rendering properties or procedurals. Then
2651  /// the script node can use that info to provide necessary data
2652  /// for rendering.
2653  /// Returns true if the method provides usable information.
2654  virtual bool getScriptMaterialInfo( UT_String & mat_info,
2655  VOP_ScriptMaterialCodeMapper * mapper )
2656  { return false; }
2657 
2658  /// Returns the sub type name, if the node's operator wants to be
2659  /// saved as an HDA in a special way (ie, other than the regular
2660  /// scripted operator handling). The sub type name is then used
2661  /// to distinguish how to handle the HDA creation.
2662  virtual const char *getHDASubType()
2663  { return 0; }
2664 
2665  // Set the channel alias for a channel (or parm subindex). Returns true
2666  // if successful and false otherwise.
2667  bool setChannelAlias(PRM_Parm &parm, int subindex,
2668  const char *alias_name);
2669 
2670  void disconnectAllInputsOutputs(bool keepSelected,
2671  bool forceDisconnectOutputs = false);
2672 
2673  void disconnectAllInputs(void);
2674  void disconnectAllOutputs(void);
2675 
2676  // Notify dependents that a parm name has changed.
2677  virtual void notifyParmRenameDependents(
2678  const UT_String &chan_name,
2679  const UT_String &old_chan_name );
2680 
2681  void writeChannel(CH_Channel *channel, std::ostream &os,
2682  const char *name, bool frames);
2683  void writeAllChannels(std::ostream &os, const char *name,
2684  bool frames, bool dochblock,
2685  bool dospareparms);
2686 
2687  // Run the callback function for a particular parm, and the callbacks
2688  // of any parms linked to this parm. Returns false if the node is
2689  // deleted while running the callback.
2690  virtual bool triggerParmCallback(PRM_Parm *parmptr, fpreal now,
2691  int value, void *data,
2692  const UT_Options *options=0);
2693 
2694  virtual int64 getMemoryUsage(bool inclusive) const;
2695  int64 getExtraInputMemoryUsage() const;
2696  static void printOpMemoryUsageStats(std::ostream &os);
2697 
2698  /// This method will unscope all the channels belonging to this op.
2699  /// If the recurse flag is set it will recurse through the children
2700  /// (at this level the recurse flag is ignored).
2701  virtual void unscopeChannels(bool recurse);
2702 
2703  /// This method will undisplay all the channels belonging to this op.
2704  /// If the recurse flag is set it will recurse through the children
2705  /// (at this level the recurse flag is ignored).
2706  virtual void undisplayChannels(bool recurse);
2707 
2708  /// This method will unpin all the channels belonging to this op.
2709  /// If the recurse flag is set it will recurse through the children
2710  /// (at this level the recurse flag is ignored).
2711  virtual void unpinChannels(bool recurse);
2712 
2713  /// This method takes a pattern string and will perform the ch_scope_op
2714  /// on each of our paramaeters that match the pattern. This method
2715  /// primarily supports the chscope command.
2716  virtual void setChannelScope(const char *pattern,
2717  OP_ScopeOp scope_op,
2718  const OP_ScopeOptions &scope_opts);
2719 
2720  /// A simple wrapper around getName() to allow us to abstract its
2721  /// functionality up to OP_NetworkBoxItem.
2722  virtual const UT_String &getItemName() const
2723  { return getName(); };
2724  virtual bool setItemName(const UT_String &name);
2725 
2726  /// Caches the descriptive name to member data, and returns that. The
2727  /// cache is automatically dirtied in opChanged.
2728  const UT_StringHolder &getCachedDescriptiveName();
2729 
2730  // This function is called when our spare parm definition is changing.
2731  virtual bool changeSpareParms(UT_IStream &istream,
2732  UT_String &errors);
2733  // This function is called during the changeSpareParms operation when
2734  // one of our parameters is being removed.
2735  virtual void spareParmRemoved(const char *parmname);
2736 
2737  // This is a secondary parm list where all obsolete parameters are
2738  // placed (if any)
2740  virtual void resolveAndDeleteObsoleteParmList(
2741  PRM_ParmList *&obsolete_parms);
2742 
2743  virtual unsigned referenceAllParameters(OP_Parameters *from,
2744  bool relative_references = true);
2745 
2746  void clearVersionUserData();
2747  void updateVersionUserData();
2748 
2749  /// After the nodes parameter list is loaded, syncNodeVersionIfNeeded() is
2750  /// called to perform any necessary upgrades if the version number of
2751  /// the loaded node (taken from user data) is different from the node
2752  /// type's version number (getOperator()->getVersion()). Use the
2753  /// from_version parameter to override the node current version.
2754  /// If needed, this will call syncNodeVersion(). After synching, the node's
2755  /// version user data will be set to the current version if
2756  /// update_node_version is true.
2757  void syncNodeVersionIfNeeded(
2758  bool *node_deleted,
2759  const char *from_version = nullptr,
2760  bool update_node_version = false);
2761 
2762  /// Sync the node assuming that it is currently at old_version to the
2763  /// current_version. By default, this will call the corresponding
2764  /// OTL_SYNCNODEVERSION section if it exists.
2765  virtual void syncNodeVersion(
2766  const char *old_version,
2767  const char *current_version,
2768  bool *node_deleted);
2769 
2770  // Sets the given stamping parameter.
2771  // Returns true if the param was changed. Note that we may return false
2772  // even if this was a valid operation as param might have already been
2773  // set to the given value.
2774  // If the warned variable is given, then we only warn if its contents
2775  // is false. Then in that case, we will set it to true when needed.
2776  bool setGlobalFloatParam(const char *param,
2777  fpreal value,
2778  bool *warned);
2779  bool setGlobalStringParam(const char *param,
2780  const char *strvalue,
2781  bool *warned);
2782 
2783  // This allows one to prevent chop cooking due to parameter modifications
2784  // until the outermost block is done.
2785  void beginPropagateModification();
2786  void endPropagateModification();
2787 
2788  // Add any OTL-defined operators used by this node to the specified table.
2789  virtual void getActiveOperatorsDefinedByOTL(
2790  UT_Set<OP_Operator *> &active_operators) const;
2791 
2792  // Returns true if we are in the middle of a call to sendBulkNotifications,
2793  // Or doing some other operation that involves sending out a whole bunch
2794  // of change notifications all at once. This allows VOP Networks to avoid
2795  // over-cooking.
2796  static bool getDoingBulkNotification();
2797  static bool isDirectorDoingBulkNotification();
2798 
2799  /// Returns whether multi-inputs on this particular op might have different
2800  /// names for each of the inputs, or if the name will always be the same for
2801  /// all the inputs.
2802  virtual bool hasDifferentMultiInputs() const;
2803 
2804 
2805  virtual bool canCreateNewOpType() const;
2806  static bool createNewOpType
2807  (OP_Node *node,
2808  UT_String &errors,
2809  const char *typeName=nullptr,
2810  const char *typeLabel=nullptr,
2811  const char *otlFile=nullptr,
2812  const char *metaSource=nullptr,
2813  const char *comment=nullptr,
2814  const char *version=nullptr,
2815  const char *newName=nullptr,
2816  int minimumInputs=-1,
2817  int maximumInputs=-1,
2818  bool ignore_external_references=false,
2819  bool compress_contents=false,
2820  bool force=false,
2821  int *newNodeId=nullptr,
2822  bool compile_contents = false,
2823  bool change_node_type = true,
2824  bool create_backup = true);
2826  virtual UT_String *getMaterialIconFilename() { return 0; }
2827  virtual void setMaterialIconFilename(const char * /*icon_file*/) {}
2828  virtual IMG_Raster *getMaterialIconImage() { return 0; }
2829  virtual bool getMaterialIconAllowRegenerateFlag() { return true; }
2830  virtual void setMaterialIconAllowRegenerateFlag(bool) {}
2831 
2832  // Call these functions when making a lot of calls to opChanged on a
2833  // list of nodes. These functions make sure that VOP Networks only get
2834  // one change notification no matter how many child nodes are about
2835  // to send any number of change events.
2836  // @parm caller The node that starts the bulk notifications, if applicable.
2837  static void startBulkNotifications(
2838  const OP_NodeList &changed,
2839  OP_Node *caller = nullptr);
2840  static void endBulkNotifications(
2841  const OP_NodeList &changed);
2842 
2843  /// This is overriden in VOPs. It returns true if the input at input_idx
2844  /// will need *and* can perform autoconversion of its input type to the
2845  /// type it needs. If autoconversion is not needed, or is impossible,
2846  /// this will return false.
2847  virtual bool willAutoconvertInputType(int input_idx);
2848 
2849  bool isDependentOn(OP_Node* other_node, PRM_Parm* parm);
2850 
2851  // Gets whether the input at idx is collapsed. Currently this is only used
2852  // in VOPs.
2853  virtual bool getIsInputVisibleDefault(int idx);
2854 
2855  // Debugging function to confirm that all PRM_Template's are consistent
2856  // with their parameters.
2857  bool verifyTemplatesWithParameters() const;
2858 
2859  // Same as getInputReference, except using a named reference.
2860  OP_Input *getNamedInputReference(
2861  const OP_ConnectorId& input_name, bool grow);
2862  OP_Input *getNamedInputReferenceConst(
2863  const OP_ConnectorId& input_name) const;
2864 
2865  OP_Node *getNamedInput(const OP_ConnectorId& input_name,
2866  bool mark_used=false) const;
2867  /// Note that this function only looks through currently connected
2868  /// inputs for the name, not through all possible input names on
2869  /// this node. mapInputNameToIndex does that instead.
2870  virtual int getInputFromName(const UT_String &in) const;
2871  virtual int getOutputFromName(const UT_String &out) const;
2872  virtual void getInputName(UT_String &in, int idx) const;
2873  virtual void getOutputName(UT_String &out, int idx) const;
2874 
2875  int getInputFromUniqueName(
2876  const OP_ConnectorId& id) const;
2877  int getOutputFromUniqueName(
2878  const OP_ConnectorId& id) const;
2879 
2880  // Returns the unique name of the input at index idx. Creates the input if
2881  // grow is set to true.
2882  void getUniqueInputName(
2883  OP_ConnectorId& id_out, int idx, bool grow);
2884  bool getUniqueInputNameConst(
2885  OP_ConnectorId& id_out, int idx) const;
2886 
2887  void getUniqueOutputName(OP_ConnectorId& id_out, int idx);
2888  bool getUniqueOutputNameConst(
2889  OP_ConnectorId& id_out, int idx) const;
2890 
2891  /// New input functions that use names instead of indices.
2892  virtual OP_ERROR setNamedInput(const OP_ConnectorId& input_name,
2893  OP_Node *op,
2894  const OP_ConnectorId* output_name = nullptr);
2895 
2896  virtual OP_ERROR setNamedIndirectInput(
2897  const OP_ConnectorId& input_name,
2898  OP_IndirectInput *input);
2899  virtual OP_ERROR setNamedInputReference(
2900  const OP_ConnectorId& input_name,
2901  const char *label, int,
2902  const OP_ConnectorId* output_name = nullptr);
2903 
2904  OP_ERROR insertNamedInput(
2905  const OP_ConnectorId& input_name, OP_Node *op,
2906  const OP_ConnectorId* output_name);
2907  OP_ERROR insertNamedIndirectInput(
2908  const OP_ConnectorId& input_name,
2909  OP_IndirectInput *input);
2911  /// Overriden in VOPs.
2912  virtual void onCreated(void) { }
2913 
2914  virtual bool isOrderedInput(const OP_ConnectorId& input_name) const;
2915 
2916  /// Returns the name of the first connection from node "who" to this node,
2917  /// or an empty string if "who" is not an input.
2918  OP_ConnectorId whichNamedInputIs(const OP_Node *who) const;
2919 
2920  /// Returns the index of the first connection of an indirect input.
2921  OP_ConnectorId whichNamedInputIs(const OP_IndirectInput *who) const;
2922  virtual bool willAutoconvertNamedInputType(
2923  const OP_ConnectorId& input_name);
2924 
2925  /// Note: Use these carefully, since they assume that no inputs are actually
2926  /// added or removed (or renamed) during the traversal.
2927  OP_ConnectorInputIter traverseInputs(OP_ConnectorInputIter* prev_iter);
2928  OP_ConnectorInputIter traverseConnectedInputs(OP_ConnectorInputIter* prev_iter);
2929  OP_ConnectorInputIter getTraverseEndIterator(void);
2930 
2931  unsigned getInputsArraySize()
2932  { return myInputs.entries(); }
2933  /// Deprecated in favour of getInputsArraySize()
2934  SYS_DEPRECATED(17.0) unsigned isInput(unsigned idx)
2935  { return (getInputsArraySize() > idx) ? 1 : 0; }
2936 
2937  /// Retrieve a sorted list of local variables visible to this OP_Node.
2938  void getLocalVarNames(UT_StringArray &out_vars);
2939 
2940  // Forcibly enable evaluation of local variables outside of cooking code
2941  // paths so that the last cooked value can be used for things like
2942  // pivot values for handles.
2943  bool setLocalVarActive(bool f)
2944  {
2945  bool old = myLocalVarActive;
2946  myLocalVarActive = f;
2947  return old;
2948  }
2950  /// Get the myLocalVarActive flag
2951  bool isLocalVarActive() const
2952  { return myLocalVarActive; }
2953 
2954  void recomputeCompiledHash();
2955 
2956  /// Clears the compiled hash (needed when switching from a compiled library
2957  /// definition to one that is not compiled).
2958  void clearCompiledHash()
2959  { myCompHash = DEFAULT_COMP_HASH_VALUE; }
2960 
2961  /// You should use opChanged() instead. This is only for very special
2962  /// cases. If you don't know you are a special case, you aren't.
2963  void directSendEvent(OP_EventType type, void *data=0)
2964  { sendEvent(type, data); }
2965 
2966  virtual bool scopedChannelsDirty();
2967 
2968  /// This mechanism allows users to evaluate active layer contribution
2969  /// without needing to link against CHOP.
2970  virtual bool getActiveLayerContribution(const UT_String &track_name,
2971  fpreal t, fpreal &value, fpreal &weight)
2972  { return false; }
2973 
2974  /// Try to resolve exports on CHOP Channel Nodes from a value parameter
2975  /// within the array.
2976  virtual bool resolveExport(const PRM_Parm* p, int subindex,
2977  CH_ChannelRef& out_export )
2978  { return false; }
2979 
2980  /// Creates or moves an existing visualizer in this network to
2981  /// this nodes output.
2982  virtual bool addOrMoveVisualizerToOutput(int outputidx)
2983  { return false; }
2984 
2985  virtual const PRM_Parm *traverseRef(int *sub_idx, fpreal time,
2986  int parm_idx, int vec_idx) const;
2987 
2988  OP_Bundle * getParmBundle(const char* parm_name, int vector_index,
2989  UT_String &pattern, OP_Network *creator,
2990  const char *filter, bool subnet_inclusion);
2991 
2992  /// For node types with no other default color override, this is the
2993  /// final fallback default color for all nodes.
2994  static const UT_Color &getGlobalDefaultColor();
2995 
2996  /// The following methods are to be used to implement getW() and getH() in
2997  /// sub-classes. They are in absolute, pan-and-scale independent UI units.
2998 
2999  /// Get the width of flags.
3000  static fpreal getFlagWidth();
3001  /// Get the default node height.
3002  static fpreal getNodeHeight();
3003  /// Get the default width of the "node button" (the part of the node
3004  /// that you can drag and click on that isn't flags).
3005  static fpreal getNodeButtonWidth();
3006  /// Get the default connector height.
3007  static fpreal getConnectorHeight();
3008 
3009  /// Returns true if we are allowed to destroy the specified nodes. If
3010  /// nodes is non-null, we test those nodes. If nodes is null, we test
3011  /// the picked nodes of the src_net. The return value assumes that all
3012  /// specified nodes will be destroyed, which is important because it
3013  /// may be safe to delete node A iff node B is also going to be deleted.
3014  static bool canDestroyNodes(OP_Network *src_net,
3015  const OP_NodeList *nodes);
3016 
3017  /// Add an error to the given error manager, collapsing chains
3018  /// of invalid sources.
3019  static void addInputNodeErrorToManager(UT_ErrorManager *error,
3020  OP_Node *src);
3021 
3022  virtual void getDefaultState(UT_String &default_state_name);
3023 
3024  // If this node sets a context option to a specific value, we can clear
3025  // this option dependency for this node (and its outputs), because we
3026  // know that changing this option value past this node won't affect the
3027  // cooking of our input nodes, even if they use this context option. One
3028  // exception to this is if this node sets the context option as a
3029  // function of the option value handed to it. This exception is dealt with
3030  // when transferring option dependencies from our inputs to this node.
3031  //
3032  // Another exception is when the context used to cook this node has a
3033  // non-default (i.e. set by a node) value for the option. Because our
3034  // context option change may get "popped" by a node higher up the chain,
3035  // we must assume that nodes above this "pop" node depend on this option
3036  // set by one of our outputs, so we need to recook when that node changes
3037  // option value (even though we overwrite it). This isn't a problem when
3038  // the option is set to a default value because dependencies on default
3039  // values are tracked by micro nodes, so changing the default will force
3040  // a recook from the top of the chain. Testing for this case is why we
3041  // need to be passed the context passed to this nodes cook method.
3042  void clearInputContextOptionDepIfSafe(
3043  const UT_StringHolder &opt,
3044  const OP_Context &context);
3045 
3046 protected:
3047  OP_Node(OP_Network *parent, const char *name, OP_Operator *entry);
3048  virtual ~OP_Node();
3049 
3050  /// Implement the method from PRM_ParmOwner
3051  virtual void doGetFullPath(UT_WorkBuffer &str) const;
3052 
3053  /// Retrieve a list of the local variables visible to this OP_Node.
3054  /// This list is unsorted and may contain duplicates.
3055  virtual void buildLocalVarNames(UT_StringArray &out_vars);
3056 
3058  const UT_StringRef &function) const;
3059 
3060  /// Called when loadNetwork finishes loading the whole parent network of
3061  /// this node.
3062  void finishedLoadingParentNetwork(void);
3063 
3064  void setNewParent( OP_Network *new_parent );
3065 
3066  static void bumpNameSerialIndex();
3067 
3068  void setLegacyConnectingInputIndex(int index)
3069  { myLegacyConnectingInputIndex = index; }
3070 
3071  // All external references must be removed by the time this function
3072  // returns!
3073  virtual void clearAndDestroy(void);
3074 
3075  // invalidate any cached data
3076  virtual void clearCache();
3077 
3078  void clearInterruptedImpl(bool allow_recook);
3079 
3080  // "cookMe" is where the actual work is done.
3081  // The error is returned (OP_ERR_NONE on success).
3082  virtual OP_ERROR cookMe(OP_Context &context) = 0;
3083 
3084  // "bypassMe" is used to cook the op when the bypass flag is set.
3085  // The copied_input parameter should be set to indicate which input was
3086  // copied. Use -1 if no input was copied.
3087  // The error is returned (OP_ERR_NONE on success).
3088  virtual OP_ERROR bypassMe(OP_Context &context, int &copied_input) = 0;
3089 
3090  // The following two functions are called from evaluateAllParms() so that
3091  // subclasses may hook into it to do some work before and after evaluating
3092  // all the parameters.
3093  virtual void doOverridePreCook() { }
3094  virtual void doOverridePostCook() { }
3095 
3096  // These "serial" numbers are used for keeping track of how many sources
3097  // are accessing us. Only call getSourceCount() when locked inside
3098  // getCookLock()!
3099  int getSourceCount(void) const;
3100  virtual int bumpSourceCount(int d);
3101 
3102  // This is what you should override to do your own OP specific cooking.
3103  // This should not be called other than from pubCookInputGroups.
3104  virtual OP_ERROR cookInputGroups(OP_Context &context, int alone = 0);
3105 
3106  // I/O methods
3107  virtual OP_ERROR saveIntrinsic(std::ostream &os,
3108  const OP_SaveFlags &flags);
3109  virtual OP_ERROR save(std::ostream &os, const OP_SaveFlags &flags,
3110  const char *path_prefix = "",
3111  const UT_String &name_override = UT_String());
3112  OP_ERROR saveUserDataPacket(std::ostream &os,
3113  const char *path_prefix,
3114  const UT_String &node_name);
3115 
3116  bool loadIntrinsic(UT_IStream &is, const char *path=0);
3117  virtual bool loadPacket(UT_IStream &is, short class_id,
3118  short sig, const char *path=0);
3119  virtual bool loadPacket(UT_IStream &is, const char *token,
3120  const char *path=0);
3121  virtual bool load(UT_IStream &is, const char *ext="",
3122  const char *path=0);
3123 
3124  // this called when the entire network is done loading
3125  virtual void loadStart();
3126  virtual void loadFinished();
3127 
3128  // Loads the OTL_CONTENTS_SECTION for our OTL definition, if it exists,
3129  // using the syncContents method.
3130  void loadContentsSection();
3131 
3132  // This is a dummy virtual that just exists to be overridden by
3133  // OP_Network. See that class for more description.
3134  virtual bool syncContents(UT_IStream &is);
3135 
3136  /// Sets the flag idicating if the node is synced (matched) to the HDA.
3137  void setMatchesOTLDefinition(int matches);
3138 
3139  virtual const char *getFileExtension(int binary) const = 0;
3140  virtual const char *getDataFileExtension(int binary) const;
3141 
3142  // This will set the time dependent flag based on parms, inputs and/or
3143  // extra (non-graph) inputs.
3144  virtual void checkTimeDependencies(int do_parms=1,
3145  int do_inputs=1,
3146  int do_extras=1);
3147  // This will gather context option dependencies based on parms,
3148  // inputs and extra (non-graph) inputs. These dependencies are
3149  // applied to the data micro node and the node itself.
3150  virtual void checkContextOptionDependencies(int do_parms);
3151 
3152  // To allow our sub-classes to send events, we make this protected.
3153  void sendEvent(OP_EventType type, void *data=0);
3154 
3155  // haveSeenDataModification() can be used by sub-classes to decide if they
3156  // need to respond to a particular modification notice.
3157  int haveSeenDataModification(exint modification_id);
3158 
3159  // If you sub-class propagateModification, then be sure to call this
3160  // OP_Node base class method *last*.
3161  //
3162  // This routine will return TRUE if the modification is a new one for this
3163  // node. FALSE will be returned if the modification has been seen before.
3164  //
3165  // Note that "by_whom" is the immediate input node that caused the
3166  // propagation to "this" node.
3167  virtual int propagateModification(OP_Node *by_whom,
3168  OP_EventType reason,
3169  int parm_index,
3170  OP_PropagateData &prop_data);
3171 
3172  // Use this to obtain the cook cache.
3173  // @pre The caller has locked myCookLock if it is currently being cooked.
3174  OP_Cache * getCookCache() { return &myCache; }
3175 
3176  static void cmd_locate(CMD_Args &);
3177 
3178  virtual void saveFlagsForUndo();
3179  void saveForUndoLayout();
3180 
3181  static void saveForUndoDelete(OP_NodeList &nodes);
3182 
3183  /// Clears all cook dependencies (i.e., items that may cause it to cook)
3184  void clearDependency();
3185 
3186  /// This function will dirty our data if the given time is different from
3187  /// our last cooked time.
3188  ///
3189  /// This function is normally called from cook() but subclasses can prevent
3190  /// this with flags().setClearDependency(false). In that case, subclasses
3191  /// are responsible for calling this function at the appropriate time. This
3192  /// is primarily for nodes which cache their data across time. In that
3193  /// case, if they did _not_ reuse their cached data, then
3194  /// dirtyForTimeChange() needs to be called.
3195  ///
3196  /// @returns true if node was dirtied, false otherwise.
3197  bool dirtyForTimeChange(fpreal t)
3198  {
3199  if (isCookedTime(t))
3200  return false;
3201 
3202  OP_DataMicroNode &dm = dataMicroNode();
3203  OP_DataMicroNode &pm = parmListMicroNode();
3204  dm.setDirty(true);
3205  if (&dm != &pm)
3206  pm.setDirty(true);
3207 
3208  return true;
3209  }
3210 
3211  // clone dependencies from the proxy. proxy is no longer valid
3212  // after the clone!
3213  virtual void cloneFromProxyRefNode( OP_Network *proxy );
3214  // clone a new proxy node. this node is no longer valid after this!
3215  virtual OP_Network * cloneToProxyRefNode();
3216  void stealDependents( OP_Node *other );
3217 
3218  bool hasOpDependents()
3219  { return !myOpDependents.isEmpty(); }
3220  virtual int hasProxyRefNodes() const
3221  { return 0; }
3222  virtual void moveProxyRefNodes( OP_Network * /*dest */ ) { }
3223  void clearOpReferences();
3224  virtual void rebuildOpDependents( bool proxy_only );
3225 
3226  /// removeOpDependent() returns the number of dependents removed
3227  virtual int removeOpDependent(
3228  int op_id, const PRM_RefId &ref_id,
3230  virtual int removeOpDependent(
3231  int op_id, OP_InterestType mask = OP_INTEREST_ALL );
3232 
3233  // new method for dependencies: use the PRM_TYPE_OP_REF_*
3234  // in your parm template to add your dependency.
3235  // override this to do special cases, make sure you call the base class
3236  // first before adding your own dependencies!
3237  virtual void buildOpDependencies();
3238  virtual void checkChannelDependencies( CH_Channel *ch,
3239  CH_CHANGE_TYPE reason );
3240 
3241  void notifyOpDependents( OP_InterestType interest,
3242  bool recurse );
3243  virtual void moveDependencies( OP_Node *from_node );
3244  // Two functions for notifying dependent nodes of name changes. The
3245  // non-virtual function is the one that should be called to do the
3246  // update. It calls the virtual function to do the actual updating,
3247  // and generate a list of dependent nodes that were changed. Then it
3248  // forces a recook on the changed nodes.
3249  void notifyRenameDependents( const UT_String &full_from );
3250  virtual void notifyRenameDependents( const UT_String &full_from,
3251  OP_NodeList &cook_nodes );
3252  // Two functions for notifying referencing nodes of name changes. The
3253  // non-virtual function is the one that should be called to do the
3254  // update. It calls the virtual function to do the actual updating,
3255  // and generate a list of dependent nodes that were changed. Then it
3256  // forces a recook on the changed nodes.
3257  void notifyRenameReferences( const UT_String &full_from );
3258  virtual void notifyRenameReferences( const UT_String &full_from,
3259  OP_NodeList &cook_nodes );
3260  // this method is called to alert this op that its dependency has
3261  // changed. if it's a name interest, then the old full path is given
3262  virtual void handleOpDependency( int referenced_op_id,
3263  const OP_Dependency &op_dep,
3264  OP_InterestType interest_type,
3265  bool &need_cook,
3266  const char *old_fullpath,
3267  const char *old_cwd,
3268  const char *old_chan_name );
3269  virtual void buildParmDependency( int parm_index );
3270 
3271  void addOpNameReference(
3272  const PRM_RefId &ref_id, const UT_String &op_path,
3274  // chan_name must be real channel name not an alias
3275  void addChannelNameReference(
3276  const PRM_RefId &ref_id,
3277  const UT_StringRef &op_path,
3278  const UT_StringRef &chan_name,
3280 
3281  OP_Node *getNodeOrCreateProxy(const UT_StringRef &op_path);
3282 
3283  void addOpReference( const PRM_RefId &ref_id, OP_Node *node,
3284  const PRM_RefId &source_ref_id,
3286 
3287  /// This function takes the given parm string value containing an op path
3288  /// and does a search and replace given the old and new op paths.
3289  ///
3290  /// value_str - the old parm value to modify
3291  /// new_fullpath - the new path value to change to
3292  /// old_fullpath - the old path that needs changing
3293  /// old_cwd - the old path that the parm value was relative to
3294  /// new_cwd - the new path that the parm value is to be relative to
3295  ///
3296  /// The reason for old_cwd & new_cwd is when collapsing a node into a
3297  /// subnet. We need to figure out the new path references of the collapsed
3298  /// subnet since it has changed location. We match using the old_cwd but
3299  /// take the new path relative to new_cwd. Note that in this situation,
3300  /// old_fullpath is the same as new_fullpath.
3301  bool changeOpPathRef( UT_String &value_str,
3302  const char *new_fullpath,
3303  const char *old_fullpath,
3304  const char *old_cwd,
3305  const char *new_cwd );
3306 
3307  // handy functions for dealing with string parms that can have the
3308  // op:/path[frame] syntax
3309  static bool getStringParmOpPath(
3310  PRM_Parm &parm, int vi, UT_String &oppath,
3311  int thread );
3312  void handleStringParmOpPathDependency(
3313  int parm_index, int vi,
3314  const char *new_fullpath,
3315  const char *old_fullpath, const char *old_cwd );
3316 
3317  // Only OP_Network should call notifyNodeDeletion()
3318  void notifyNodeDeletion();
3319 
3320  // Only notifyNodeDeletion() should call nodeDeleted().
3321  // nodeDeleted() - gets called every time a node is deleted
3322  virtual void nodeDeleted(OP_Node *op, int propagate=1);
3323 
3324  void startCookTimer(const OP_Context &context);
3325  void stopCookTimer(const OP_Context &context);
3326 
3327  virtual const char *getCookTimerLabel(const OP_Context &context) const;
3328 
3329  // Overrides permission errors so that we don't have problems when cooking.
3330  virtual void permissionError(const char *chname = 0);
3331 
3332  // Add an error for the invalid input given by input_idx
3333  void addInputError(unsigned input_idx);
3334 
3335  // Add an error for the given node having failed to load.
3336  void addInputNodeError(OP_Node *src);
3337 
3338 protected:
3339  /// This function is currently only used by VOPs. It checks if an input
3340  /// on the subnet is connected inside the subnet. The default implementation
3341  /// here simply returns false to preserve existing behaviour for all other
3342  /// contexts.
3343  virtual bool isInputConnectedInsideSubnet(int input_idx) const;
3344  virtual bool isNamedInputConnectedInsideSubnet(
3345  const OP_ConnectorId& input_name) const;
3347  // notifier when this node is unlocked
3348  virtual void nodeUnlocked() { ; }
3349 
3350  // These functions must be used with care!
3351  virtual void setUniqueId(int id);
3352  void changeOpDependentUniqueId( int old_id, int new_id );
3353  void changeOpReferenceUniqueId( int old_id, int new_id );
3354  virtual void clearUniqueId();
3355 
3356  void setAllowBuildDependencies( int yesno )
3357  { myAllowBuildDependencies = yesno; }
3358  int allowBuildDependencies() const
3359  { return myAllowBuildDependencies; }
3360 
3361  /// Evaluate all parameters for this operator. This is used for scripted
3362  /// Ops to make sure that our dependencies get set up properly.
3363  void evaluateAllParms(fpreal t);
3364 
3365  /// Override and assign any external (file) references to the reflist,
3366  /// and if nodelist is non-null, the full pathname of the node with the
3367  /// reference.
3368  virtual void getMyExternalReferences(UT_StringArray &reflist,
3369  UT_StringArray *nodelist =0,
3370  bool collapse = false,
3371  bool check_missing = false,
3372  bool show_missing_only=false);
3373 
3374  void getExternalFiles(UT_StringArray &files,
3375  const char *stringparm,
3376  int framestart, int frameend,
3377  bool collapse,
3378  bool check_missing,
3379  bool show_only_missing,
3380  UT_KnownPath path);
3381 
3382  /// Rather than overloading the descriptive name, you can instead
3383  /// just provide a parameter name that will be evaluated to
3384  /// become the descriptive name.
3385  virtual void getDescriptiveParmName(UT_String &str) const;
3386 
3387  /// Additonal information that should be provided at the network
3388  /// level in addition to the name.
3389  /// By default will inspect the getDescriptiveParmName.
3390  virtual void getDescriptiveName(UT_String &str) const;
3391 
3392  /// Marks our cached descriptive name as dirty.
3393  void dirtyDescriptiveNameCache();
3394 
3395  /// Return true if it is safe at this time to destroy this node.
3396  virtual bool canDestroyNode();
3397 
3398  /// Override this to return true in an operator type that wants its
3399  /// cooked data to rely on all its parameter values but doesn't actually
3400  /// evaluate any parameters in its cook function (the prototypical
3401  /// example of this is SHOPs).
3402  virtual bool cookedDataUsesAllParameters() const
3403  { return false; }
3404  /// If the cook method relies on the base class cook to evaluate parameters
3405  /// (like in SHOPs), we need to trap the errors during this evaluation.
3406  virtual bool cookedDataNeedsErrors() const
3407  { return false; }
3408  /// If this node should be cooked for any output connected to it, return
3409  /// true here. Otherwise we only cook a node if something is connected to
3410  /// it's primary output. This does not let the node cook differently for
3411  /// each output, since the cook method doesn't know what output is being
3412  /// cooked for. So this should only be used if the cook is unaffected by
3413  /// the specific connected output.
3414  virtual bool cookDataForAnyOutput() const
3415  { return false; }
3416 
3417  // Returns true if we are running our creation script, or any parent
3418  // node of us is running its creation script.
3419  bool getIsRunningInCreateScript() const;
3420 
3421  /// This method is called whenever something in the network changes
3422  /// that may have an impact on the representative node this network may
3423  /// have. It is used at this level to notify parents, and at the OBJ level
3424  /// to actually refresh the representative object.
3425  virtual void refreshRepresentativeNode(OP_Node &changed_child);
3426 
3427  /// Sets up the inputs and outputs after all nodes have been loading
3428  /// from file (in case it needs its children to determine inputs/oututs).
3429  virtual void setupConnectorsAfterLoad();
3430 
3431  /// Converts opdef and oplib format paths from opdef:nodepath to
3432  /// opdef:tablename/optype.
3434 
3435  bool isCookedTime(fpreal t) const
3436  {
3437  return dataMicroNodeConst()
3438  .isEqualToLastUpdateTime(t);
3439  }
3440 
3441  /// Subclasses should override this to dump extra micronodes that they own
3442  /// for debugging purposes.
3443  virtual void dumpMicroNodes(
3444  std::ostream &os,
3445  bool as_DOT,
3446  int indent_level) const;
3449  UT_TokenString myHashCode; // Generates a unique
3450  UT_TokenString myParmHashCode; // parameters & inputs.
3451  int myLastGroupMask;
3452  OP_VERSION myHashVersion;
3453  fpreal myHashTime;
3454  int myParmLastGroupMask;
3455  OP_VERSION myParmHashVersion;
3456  fpreal myParmHashTime;
3457  UT_String mySyncErrors;
3458  OP_ERROR mySyncErrorLevel;
3459  int mySyncDepth;
3460 
3461  /// Deletes an input completely if it is disconnected. If the input
3462  /// is connected, does nothing.
3463  void deleteInput(int idx);
3464  void deleteInput(const OP_ConnectorId& input_name);
3465 
3466  /// Performs actual removal from the member input array.
3467  virtual void doDeleteInput(int idx);
3468 
3469  /// Update the error severity of this node.
3470  void updateErrorSeverity();
3472  /// Overriden in VOPs.
3473  virtual void onInputAllocated(OP_Input* new_input, int index) { }
3474 
3475  /// Debug method for checking connector consistency.
3476  void checkConnectorsConsistency(void);
3477 
3478  /// Use these to collect all inputs/outputs in cases where they will
3479  /// need to be modified.
3480  void gatherInputs(UT_Array<OP_InputPair> &input_pairs);
3481  void gatherOutputs(UT_Array<OP_OutputPair> &output_pairs);
3482 
3483  void renameInput(OP_Input* input, int new_id);
3484  void renameOutput(OP_Output* output, int new_id);
3486  // Compiled hash code
3487  uint32 myCompHash;
3488 
3489 private:
3490  bool doDebugConsistencyCheck();
3491  void createCollection( OP_Operator *entry );
3492 
3493  // these are extra private. only to be called from saveIntrinsic and save
3494  // respectively
3495  OP_ERROR saveIntrinsicError();
3496  OP_ERROR saveError();
3497  OP_ERROR saveGroupMemberships(std::ostream &os,
3498  const OP_SaveFlags &flags,
3499  const char *path_prefix);
3500  bool loadGroupMemberships(UT_IStream &is,const char*path=0);
3501 
3502  ///Make a note of which network box we're in
3503  OP_ERROR saveNetworkBox(std::ostream &os,
3504  const OP_SaveFlags &flags,
3505  const char *path_prefix);
3506 
3507  ///Put ourselves into a network box if we saved ourselves as being in one
3508  bool loadNetworkBox(UT_IStream &is, const char *path=0);
3509 
3510  bool loadNodeFlags(UT_IStream &is, const char *path);
3511 
3512  void saveForUndoComment();
3513  void saveForUndoDelScript();
3514 
3515  UT_BitArray &getGroups() { return myGroups; }
3516  const UT_BitArray &getGroups() const { return myGroups; }
3517  // Only OP_Input should call setOutput() and delOutput() functions.
3518  bool setOutput(OP_NetworkBoxItem *item, int outputIdx);
3519  bool delOutput(OP_NetworkBoxItem *item, int outputIdx);
3520  bool setNamedOutput(OP_NetworkBoxItem *item,
3521  const OP_ConnectorId& output_name);
3522  bool delNamedOutput(OP_NetworkBoxItem *item,
3523  const OP_ConnectorId& output_name);
3524 
3525  void setInterrupted();
3526 
3527  int findAncestor(const OP_Node *node) const;
3528  int findDataAncestor(const OP_Node *node) const;
3529  void clearRecursionBit() const;
3530 
3531  void initializeExpressions() const;
3532  void clearInputs();
3533  void clearOutputs();
3534 
3535  virtual PRM_ParmMicroNode
3536  *createParmMicroNodes(PRM_Parm &parm) const;
3537 
3538  static bool getMicroNodesFromRef(
3539  const OP_InterestRef &ref,
3540  DEP_MicroNodeList &micronodes,
3541  bool data_target);
3542 
3543  // new method: dependencies get created from parm template and only
3544  // gets updated when necessary. only buildOpDependencies()
3545  // needs to call this
3546  void removeOpReference(
3547  const PRM_RefId &ref_id,
3549  void removeOpReference(
3550  const PRM_RefId &ref_id,
3551  int op_id,
3553  // ref_chan_name must be the real channel name and not an alias
3554  int addOpDependent( int op_id,
3555  const PRM_RefId &source_ref,
3556  const PRM_RefId &ref_id,
3558 
3559  void updateRenameDependent( OP_Node *dependent,
3560  const char *old_cwd,
3561  OP_NodeList &cook_nodes );
3562 
3563  void notifyInputOpDependents(int input_i);
3564 
3565  void getExistingOpReferencesImpl(
3566  OP_NodeList &refs, bool include_descendants) const;
3567  void getExistingOpDependentsImpl(
3568  OP_NodeList &deps, bool include_descendants) const;
3569 
3570  void buildScriptOpDependencies();
3571  void changeScriptOpRef( const char *new_fullpath,
3572  const char *old_path,
3573  const char *old_cwd );
3574  static void changeScriptCB( UT_String &str,
3575  const char *token_start,
3576  const char *&ch, void *userdata );
3577 
3578  // Go through and find all nodes which have time interest and requires
3579  // cooking. If the update_cook flag is true, then we will call force
3580  // recook on the node as long as node != this. 'interests' if non-null,
3581  // stores the path of nodes that has time interest and will set the time
3582  // interest cook flag on those nodes.
3583  bool findTimeInterests(OP_Context &context, OP_Node *node,
3584  bool update_cook,
3585  OP_NodeCycleDetect &cycle,
3586  OP_NodeList *interests = nullptr);
3587 
3588  /// Helper method for 'completePath()'
3589  bool attemptPrefixMatch(const OP_NetworkBoxItem *item,
3590  char *childpref, int childpreflen,
3591  UT_String &maxprefix) const;
3592 
3593  /// Helper for propagateModification()
3594  void findUsedDataInterests(OP_NodeList &nodes, OP_Node *op);
3595 
3596  /// Helper function for the setGlobal*Param functions. This function
3597  /// interprets the return value from CH_Manager::setGlobal*Param.
3598  bool internalSetGlobalParam(const char *param,
3599  int setreturned,
3600  bool *warned);
3601 
3602  int internalSetPicked(int on_off,
3603  bool propagate_parent_event,
3604  bool edit);
3605 
3606  OP_ERROR internalCookInput(OP_Context &context, int input_idx,
3607  OP_Node &input_node);
3608 
3609  virtual void removeInputFromMapping(int idx);
3610  void removeOutputFromMapping(int idx);
3611 
3612  /// Helper function to skip until the next closing brace in a stream
3613  /// (including the brace itself).
3614  void skipUntilClosingBrace(UT_IStream &is);
3615 
3616  /// Resolves any inputs for which the names were not found during
3617  /// actual loading.
3618  void resolveUnresolvedLoadedInputs(void);
3619 
3620  void generateConnectorUniqueId(OP_ConnectorId& id_out);
3621  OP_Output *getOrCreateOutput(int array_index, bool create,
3622  int id_to_use);
3623 
3624  uint32 computeCompiledHash() const;
3625 
3626  // Adds a warning to the current error manager if this node has been
3627  // marked as deprecated.
3628  void addDeprecationWarningsIfAny();
3629 
3630  // Find an unused connectorId to assign to the next input/output
3631  int getConnectorNextId() const;
3632 
3633  bool computeCompiledStatus() const;
3634 
3635 public:
3636  /// SOP, OBJ, and SOP Solver DOP nodes can be a selection owner,
3637  /// but other nodes cannot.
3638  /// This replaces the previous inheritance from SOP_SelectionOwner.
3639  virtual bool isSelectionOwnerType() const
3640  { return false; }
3641 
3642 private:
3643  OP_Cache myCache;
3644 
3645  OP_ERROR myLastErrorSeverity;
3646  OP_Network *myParent;
3647  OP_Network *myRootCompiledParent;
3648  UT_ValArray<OP_Input *> myInputs;
3649  // This is a map of names to inputs.
3650  OP_ConnectorInputMap myInputsMap;
3651  mutable UT_BitArray myUsedInputs;
3652  UT_ValArray<OP_Output *> myOutputs;
3653  // This is a map of names to outputs.
3654  OP_ConnectorOutputMap myOutputsMap;
3655 
3656  // Default data micro node.
3657  OP_DataMicroNode myDataMicroNode;
3658  DEP_MicroNode myFlagMicroNode;
3659  UT_StringArray myClearInputContextOptionDeps;
3660 
3661  // Micro nodes for OP events.
3662  UT_UniquePtr<DEP_MicroNode *[]> myEventMicroNodes;
3663 
3664  UT_String myComment;
3665  UT_String myDelScript;
3666  UT_String myCreatorState;
3667  UT_BitArray myGroups;
3668  OP_Value myEventValue;
3669  fpreal myPosX;
3670  fpreal myPosY;
3671  exint myCookCount;
3672  SYS_AtomicInt32 mySourceCount;
3673  int myBlockModify;
3674  int myUniqueId;
3675  int myNextIdOverride;
3676  unsigned myActiveInputIndex;
3677  // Indicates which input is currently being connected,
3678  // -1 if none.
3679  int myLegacyConnectingInputIndex;
3680 
3681  bool myAutoscope;
3682 
3683  fpreal myCookDuration; // time spent cooking
3684  unsigned int myRenameConflict : 1,
3685  myCookedForRender : 1,
3686  myModifyWaiting : 1,
3687  myBuiltExplicitly : 1,
3688  myAllowBuildDependencies : 1,
3689  myBeingDeleted : 1,
3690  myRunningCreateScript : 1,
3691  myRunningDelScript : 1,
3692  myAlreadyRunDelScript : 1,
3693  myMatchesOTLDefinition : 1,
3694  myLoadCookedDataError : 1,
3695  myBuiltHashCode : 1,
3696  myIsProxyRefNode : 1,
3697  myInhibitInputConsolidation : 1,
3698  // Tracks if we have engaged our local variables, true from the
3699  // SOP_Node::setupLocalVars() until the SOP_Node::resetLocalVarRefs(). Any
3700  // attempt to evaluate local vars outside of here will redflag. This
3701  // flag is here instead of SOP_Node so that PI_OpHandleLink has access
3702  // to temporarily enable it.
3703  myLocalVarActive : 1;
3704 
3705  mutable bool myRecursionFlag;
3706 
3707  // Tracks the nesting level of the modification propagation chains
3708  static int thePropagateLevel;
3709 
3710  // ops that we have a reference to
3711  OP_ReferenceList myOpReferences;
3712  // ops that depend on us
3713  OP_DependencyList myOpDependents;
3714 
3715  // bundles that we have a reference to
3716  OP_BundleReferences myBundleRefs;
3717 
3718  // Locking for cooking and adding extra inputs
3719  mutable OP_CookLock myCookLock;
3720  UT_TaskState myTaskState;
3721 
3722  // Arbitrary string data that users can attach to nodes that gets saved
3723  // with the hip file.
3724  UT_Options myUserData;
3725  // Cached value for the node shape.
3726  UT_StringHolder myNodeShape;
3727 
3728  // Arbitrary blind data that users can attach to nodes. These do not get
3729  // saved with the hip file.
3730  UT_StringMap<UT_SharedPtr<void> > myBlindData;
3731 
3732  // Arbitrary data blocks that, unlike blind data, are saved with the node.
3733  // This obviously implies the data must be self contained (no pointers).
3734  UT_StringMap<OP_DataBlockPtr> myDataBlocks;
3735 
3736  // Arbitrary data (in the form of Python objects) the users can attach to
3737  // nodes that does not get saved with the hip file.
3738  OP_PythonObjectCache myCachedPythonObjects;
3739 
3740  // During load, not all of our input names are known. This stores
3741  // unresolved input names until OP_Node::loadFinished() is called,
3742  // where they are resolved.
3743  UT_Array<OP_UnresolvedConnection *> *myUnresolvedInputs;
3744 
3745  OP_NodeFlags myFlags;
3746 
3747  /// Cached evaluation of the node's descriptive name.
3748  UT_StringHolder myCachedDescriptiveName;
3749  bool myCachedDescriptiveNameDirty;
3750 
3751  /// Only used during loading. Set to false initially, it is set to true
3752  /// once we load inputsNamed intrinsic section. If we do, the regular
3753  /// inputs section will then be ignored.
3754  bool myLoadedNamedInputs;
3755 
3756  /// Used for caching the compiled status of the node. Initially undefined,
3757  /// gets set on first isCompiled() call.
3758  mutable OP_CompileStatusType myCachedCompileStatus;
3759 
3760  // Maintenance of node id's
3761  static int makeUniqueId(OP_Node *node);
3762 
3763  static bool *theCheckConnectionConsistency;
3764  static int theUniqueId;
3765  static int theUniqueSize;
3766  static OP_Node **theUniqueNodes;
3767  static bool theDoingBulkNotification;
3768  static OP_Node *theBulkNotificationCaller;
3770  friend class OP_Network;
3771  friend class OP_Group;
3772  friend class OP_DataMicroNode;
3773  friend class OP_EventMicroNode;
3774  friend class OP_ParmMicroNode;
3775  friend class OP_Input;
3776  friend class OP_IndirectInput;
3777  friend class OP_UndoDelete;
3778  friend class OP_UndoInput;
3779  friend class OP_UndoCreate;
3780  friend class OP_UndoSpareParm;
3781  friend class OP_UndoUserData;
3782 
3783  friend class op_MicroNodeDirtied;
3784 };
3785 
3786 // helper function
3787 // should always return a valid pointer
3789 
3790 // UTformat support.
3791 static inline size_t
3792 format(char *buffer, size_t buffer_size, const OP_Node &v)
3793 {
3794  UT_StringHolder s = v.getFullPath();
3795  if (!buffer)
3796  return s.length();
3797  else
3798  {
3799  size_t len = std::min(size_t(s.length()), buffer_size);
3800  ::memcpy(buffer, s.c_str(), len);
3801  return len;
3802  }
3804 
3806 {
3807 public:
3810 };
3811 
3812 #define CAST_INSTANTIATE(PREFIX) \
3813 inline static PREFIX##_Node *CAST_##PREFIX##NODE(OP_Node *op) \
3814 { \
3815  return ((op) ? (op)->castTo##PREFIX##Node() : 0); \
3816 } \
3817  \
3818 inline static const PREFIX##_Node *CAST_##PREFIX##NODE(const OP_Node *op) \
3819 { \
3820  return ((op) ? (op)->castTo##PREFIX##Node() : 0); \
3821 } \
3822 
3823 /// @anchor OP_Node_CAST_FOONODE
3824 /// These convenience functions let you do the cast without worrying if the
3825 /// underlying pointer is null or not. They aren't macros because this way we
3826 /// avoid double evaluating the op.
3827 /// CAST_OBJNODE()
3828 /// CAST_SOPNODE()
3829 /// CAST_POPNETNODE()
3830 /// CAST_POPNODE()
3831 /// CAST_CHOPNETNODE()
3832 /// CAST_CHOPNODE()
3833 /// CAST_ROPNODE()
3834 /// CAST_SHOPNODE()
3835 /// CAST_COP2NODE()
3836 /// CAST_COPNETNODE()
3837 /// CAST_VOPNODE()
3838 /// CAST_VOPNETNODE()
3839 /// CAST_DOPNODE()
3840 /// CAST_TOPNODE()
3841 /// CAST_LOPNODE()
3842 //@{
3844 //@}
3845 
3846 #undef CAST_INSTANTIATE
3847 
3848 // We don't want anyone to conflict with this..
3849 #undef INSTANTIATE_FINDNODE_FUNCTIONS
3850 #undef INSTANTIATE_CASTNODE_FUNCTIONS
3851 #undef INSTANTIATE_FOR_ALL_NODE_TYPES
3852 
3853 #endif
OP_API const UT_StringHolder OP_USERDATA_NODESHAPE
The change type wasn't set, so it could be any of them.
Definition: OP_DataTypes.h:77
virtual void executeCommand(const char *command, std::ostream *out, std::ostream *err) const =0
virtual bool setColor(const UT_Color &color)
void adoptFromString(UT_String &str)
unsigned char uchar
Definition: SYS_Types.h:38
#define CAST_INSTANTIATE(PREFIX)
Definition: OP_Node.h:3810
Definition: UT_Set.h:58
GT_API const UT_StringHolder filename
const PRM_Parm * myParmRef
Definition: OP_Node.h:170
GLuint GLsizei const GLchar * label
Definition: glcorearb.h:2544
virtual UT_ErrorSeverity prmCookOverrides(fpreal, int, const char *, int)
virtual OP_ItemType getItemType() const =0
Our children should implement this and return what type of item they are.
OP_ConnectorInputMap::iterator OP_ConnectorInputIter
Definition: OP_Node.h:137
#define SYS_DEPRECATED(__V__)
OP_NodeList::reverse_iterator end()
Definition: OP_Node.h:387
virtual void checkChannelDependencies(CH_Channel *, CH_CHANGE_TYPE)
Unsorted map container.
Definition: UT_Map.h:83
uint64 OP_VERSION
Definition: OP_Version.h:6
const UT_String & getName() const
int64 getMemoryUsage(bool inclusive) const
UT_String myInputName
Definition: OP_Node.h:176
OP_CompileStatusType
Definition: OP_Node.h:272
virtual int changeString(const char *from, const char *to, bool fullword)
UT_CycleDetect< OP_Node * > OP_NodeCycleDetect
Definition: OP_Node.h:181
GT_API const UT_StringHolder time
virtual int setPicked(int on_off, bool propagate_parent_event=true)=0
void addExplicitInput(DEP_MicroNode &inp, bool check_dup)
Methods for manipulating explicit edges.
const GLdouble * v
Definition: glcorearb.h:836
A task node for managing which thread is currently working on a given task.
Definition: UT_TaskState.h:42
png_voidp ptr
Definition: png.h:2145
virtual void opChanged(OP_EventType type, void *dataptr=0)=0
const UT_StringHolder myTableName
Definition: OP_Node.h:309
GLuint color
Definition: glcorearb.h:1260
const GLuint GLenum const void * binary
Definition: glcorearb.h:1923
UT_LockedRawPtr< OP_NodeList, OP_Lock > OP_LockedNodeList
Definition: OP_Node.h:184
GLsizei const GLchar *const * path
Definition: glcorearb.h:3340
SYS_FORCE_INLINE T * SYSconst_cast(const T *foo)
Definition: SYS_Types.h:127
base_iterator< const OP_Node *, false > const_reverse_iterator
Definition: UT_Array.h:774
#define INSTANTIATE_CASTNODE_FUNCTIONS(PREFIX)
Definition: OP_Node.h:453
virtual void setXY(fpreal x, fpreal y)=0
GLint level
Definition: glcorearb.h:107
virtual fpreal getY() const =0
GLint GLuint mask
Definition: glcorearb.h:123
UT_ErrorSeverity
Definition: UT_Error.h:25
virtual fpreal getX() const =0
GLbitfield flags
Definition: glcorearb.h:1595
Parameters for OP_Node::getInfoText()/OP_Node::getNodeSpecificInfoText()
OP_API const UT_StringHolder OP_USERDATA_BGIMAGES
const OP_DopParent * castToOpDopParent() const
Definition: OP_Node.h:2575
GLint y
Definition: glcorearb.h:102
virtual OP_Network * getParentNetwork() const =0
Returns the network that is our parent.
OP_ConnectorId myName
Definition: OP_Node.h:142
virtual void clearParmDependency(int parmidx)=0
int(* OP_EditCallback)(void *data, OP_Node *src, CL_Track *track, fpreal t, fpreal value)
Definition: OP_Node.h:132
GLuint buffer
Definition: glcorearb.h:659
png_uint_32 i
Definition: png.h:2877
virtual UT_StringHolder evaluateDisableExpression(const PRM_Parm &prm, const UT_StringRef &function) const
OP_NodeList::const_iterator rbegin() const
Definition: OP_Node.h:390
int myIndex
Definition: OP_Node.h:412
UT_SymbolMap< PY_OpaqueObject * > OP_PythonObjectCache
Definition: OP_Node.h:186
virtual int findString(const char *str, bool fullword, bool usewildcards) const
base_iterator< OP_Node *, false > reverse_iterator
Definition: UT_Array.h:773
const OP_Node * myEvalNode
Definition: OP_Node.h:169
void setDirty(bool flag, bool allow_clear=true)
Flag accessors.
virtual void setAnyUndoFlag()
PivotSpaceT< fpreal32 > PivotSpace
Definition: UT_Matrix4.h:789
fpreal myValue
Definition: OP_Node.h:409
virtual int64 getItemUniqueId() const =0
Functions to get hip-file-unique ids for any item type.
OP_ItemType
Definition: OP_ItemId.h:28
PRM_ParmList * createObsoleteParmList() override
long long int64
Definition: SYS_Types.h:107
A utility class to do read-only operations on a subset of an existing string.
Definition: UT_StringView.h:31
const char * getFullPath(UT_String &str) const
Definition: PRM_ParmOwner.h:48
virtual void pushAsPwdAndRunPython(PY_CompiledCode &compiled_code, PY_Result::Type desired_result_type, PY_Result &result, PY_EvaluationContext *context=NULL) const =0
virtual fpreal getW() const =0
GLdouble n
Definition: glcorearb.h:2007
OP_NodeList::iterator rend()
Definition: OP_Node.h:396
GLfloat f
Definition: glcorearb.h:1925
const UT_StringHolder myScriptDir
Definition: OP_Node.h:310
#define INSTANTIATE_FOR_ALL_NODE_TYPES(MACRO_FUNC)
This macro allows us to run another macro for all node types.
Definition: OP_Node.h:470
int mySubIndex
Definition: OP_Node.h:413
OP_InterestType
Definition: OP_DataTypes.h:45
UT_ValArray< const CL_Track * > CL_TrackListC
Definition: OP_Node.h:127
reverse_iterator rbegin()
Begin iterating over the array in reverse.
Definition: UT_Array.h:804
CH_CHANGE_TYPE
exint length() const
GLint ref
Definition: glcorearb.h:123
Mapper that provides an HDA section name for a given shader node.
std::shared_ptr< T > UT_SharedPtr
Wrapper around std::shared_ptr.
Definition: UT_SharedPtr.h:28
OP_OpTypeId myOptypeId
Definition: OP_Node.h:307
int64 exint
Definition: SYS_Types.h:116
void(* OP_EventMethod)(OP_Node *caller, void *callee, OP_EventType type, void *data)
Definition: OP_Value.h:153
void resolveAndDeleteObsoleteParmList(PRM_ParmList *&obsolete_parms) override
base_iterator< OP_Node *, true > iterator
Definition: UT_Array.h:771
#define INVALID_TABLE_NAME
Definition: OP_Node.h:197
OP_Network * getRootCompiledParent() const
Definition: OP_Node.h:504
UT_KnownPath
Definition: UT_PathSearch.h:52
Wrapper around hboost::intrusive_ptr.
iterator begin()
Definition: UT_Array.h:779
virtual bool triggerParmCallback(PRM_Parm *parmptr, fpreal now, int value, void *data, const UT_Options *options=0)=0
GLenum target
Definition: glcorearb.h:1666
DEP_MicroNode & parmMicroNode(int parm_idx, int vi)
SYS_FORCE_INLINE const char * c_str() const
OP_OpTypeId
Definition: OP_OpTypeId.h:15
#define INSTANTIATE_FINDNODE_FUNCTIONS(PREFIX)
Definition: OP_Node.h:444
UT_ArrayMap< OP_ConnectorId, OP_Input * > OP_ConnectorInputMap
Definition: OP_Node.h:135
virtual void doGetFullPath(UT_WorkBuffer &str) const override
Compute the full path of the node.
GLboolean * data
Definition: glcorearb.h:130
OP_UIChangeType
Definition: OP_DataTypes.h:74
virtual void setItemExpose(bool expose)
GLuint const GLchar * name
Definition: glcorearb.h:785
virtual void buildOpDependencies()
OP_NodeList::reverse_iterator begin()
Definition: OP_Node.h:385
Definition: OP_Dot.h:24
GLboolean GLboolean GLboolean b
Definition: glcorearb.h:1221
virtual bool getItemExpose() const
UT_ArrayMap< OP_ConnectorId, OP_Output * > OP_ConnectorOutputMap
Definition: OP_Node.h:136
int myVectorIndex
Definition: OP_Node.h:171
reverse_iterator rend()
End reverse iterator.
Definition: UT_Array.h:810
virtual bool changeSpareParms(UT_IStream &ds, UT_String &errors)
virtual int getPicked() const =0
OP_NodeList::const_reverse_iterator end() const
Definition: OP_Node.h:383
GLenum mode
Definition: glcorearb.h:98
GT_API const UT_StringHolder version
OP_NodeList::const_reverse_iterator begin() const
Definition: OP_Node.h:381
IFDmantra py
Definition: HDK_Image.dox:266
GLint GLint GLsizei GLint GLenum format
Definition: glcorearb.h:107
virtual void rebuildParmDependency(int parmidx)=0
unsigned int OP_ItemTypeMask
Definition: OP_ItemId.h:43
const UT_StringHolder myOptypeName
Definition: OP_Node.h:308
OP_API const char * OPtypeIdLabels[NUM_MANAGERS]
Nice label names used by network view, corresponding to OP_OpTypeId.
GLsizei const GLfloat * value
Definition: glcorearb.h:823
double fpreal
Definition: SYS_Types.h:270
A map of string to various well defined value types.
Definition: UT_Options.h:42
GLenum GLfloat param
Definition: glcorearb.h:103
Parameters for OP_Node::fillInfoTree()/OP_Node::fillInfoTreeNodeSpecific()
bool operator==(const OP_NodeParmRef &other)
Definition: OP_Node.h:162
virtual short * getInput(int size)
typedef int
Definition: png.h:1175
virtual const UT_String & getItemName() const =0
virtual void addExtraInput(OP_Node *op, OP_InterestType type)
Definition: OP_Node.h:1597
virtual bool setItemName(const UT_String &name)=0
virtual void permissionError(const char *chname=0)
Utility class for containing a color ramp.
Definition: UT_Ramp.h:84
typename set_type::iterator iterator
Inherit iterator and const_iterator.
Definition: UT_ArrayMap.h:90
#define OP_API
Definition: OP_API.h:10
GLuint index
Definition: glcorearb.h:785
OP_OTLLicenseType
OP_Output * myOutput
Definition: OP_Node.h:147
png_infop png_bytep png_size_t buffer_size
Definition: png.h:2124
GLint GLenum GLint x
Definition: glcorearb.h:408
virtual unsigned referenceAllParameters(OP_Parameters *from, bool relative_references=true)
GLuint GLfloat * val
Definition: glcorearb.h:1607
TransformMode
Definition: OP_Node.h:1094
OP_Node * myNode
Definition: OP_Node.h:411
OP_EventType
Definition: OP_Value.h:22
A global error manager scope.
GA_API const UT_StringHolder pivot
base_iterator< const OP_Node *, true > const_iterator
Definition: UT_Array.h:772
OP_DataType
Definition: OP_DataTypes.h:28
OP_API const UT_StringHolder OP_USERDATA_WIRESTYLE
GLint GLint GLsizei GLint GLenum GLenum type
Definition: glcorearb.h:107
UT_CycleDetect< OP_NodeParmRef > OP_NodeParmRefCycle
Definition: OP_Node.h:182
OP_Network * getParent() const
Definition: OP_Node.h:502
virtual void clearUndoFlags()
virtual UT_Color getColor() const
Accessors for color used in the network view.
OP_NodeList::const_iterator rend() const
Definition: OP_Node.h:392
virtual void convertOpdefToAbsolutePath(UT_String &str) const =0
This is the base class for all DOP nodes.
Definition: DOP_Node.h:75
virtual OP_Node * castToOPNode()
Definition: PRM_ParmOwner.h:45
virtual void spareParmRemoved(const char *parmname)=0
virtual fpreal getH() const =0
OP_NodeParmRef(const OP_Node *eval_node=0, const PRM_Parm *parm_ref=0, int vi=-1)
Definition: OP_Node.h:153
void lockedExecute(const F &functor)
Definition: UT_TaskLock.h:295
EXPR_API EXPR_GlobalStaticLock & ev_GlobalEvalLock()
int operator==(const opParmData &v) const
Definition: OP_Node.h:415
#define const
Definition: zconf.h:214
virtual void syncNodeVersion(const char *old_version, const char *current_version, bool *node_deleted)
Options class for use with OP_Node::saveCommand()
Definition: OP_Node.h:314
#define DEFAULT_COMP_HASH_VALUE
Definition: OP_Node.h:194
OP_ScopeOp
Definition: OP_Parameters.h:57
png_infop png_uint_32 flag
Definition: png.h:2242
bool wasInterrupted(T *i, int percent=-1)
OP_Input * myInput
Definition: OP_Node.h:141
OP_NodeFlags & flags()
Definition: OP_Node.h:1341
SYS_FORCE_INLINE PRM_ParmList * getParmList()
Definition: PRM_ParmOwner.h:67
const std::enable_if<!VecTraits< T >::IsVec, T >::type & min(const T &a, const T &b)
Definition: Composite.h:129
virtual PRM_ParmMicroNode * createParmMicroNodes(PRM_Parm &parm) const
#define UTstatic_pointer_cast
Definition: UT_SharedPtr.h:32
OP_API const UT_StringHolder OP_USERDATA_DESCRIPTIVE_PARM
OP_Input * mySavedInput
Definition: OP_Node.h:177
UT_LockedRawPtr< const OP_NodeList, OP_Lock > OP_LockedConstNodeList
Definition: OP_Node.h:185
virtual int getHasTakeData() const
Definition: OP_PostIt.h:42
iterator end()
End iterator.
Definition: UT_Array.h:784
OP_API OP_Node * OPgetNodeFromChannel(const CH_Channel *chp)
virtual bool isParmPendingOverride(const char *, int) const
OP_NodeList::iterator rbegin()
Definition: OP_Node.h:394
OP_ConnectorId myName
Definition: OP_Node.h:148
GLint GLint GLint GLint GLint GLint GLint GLbitfield GLenum filter
Definition: glcorearb.h:1296
GLenum src
Definition: glcorearb.h:1792
unsigned int uint32
Definition: SYS_Types.h:36
virtual const PRM_Parm * traverseRef(int *sub_idx, fpreal time, int parm_idx, int vec_idx) const =0
UT_String myLabel
Definition: OP_Node.h:410