فهرست منبع

Cleanup: Link socket templates in new file

also fixes mistaken wrong names in Transformation in last commit
Joseph Brandenburg 10 ماه پیش
والد
کامیت
033d0526ff
3فایلهای تغییر یافته به همراه409 افزوده شده و 443 حذف شده
  1. 3 416
      link_containers.py
  2. 2 27
      link_definitions.py
  3. 404 0
      link_socket_templates.py

+ 3 - 416
link_containers.py

@@ -1,7 +1,7 @@
 from .node_container_common import *
 from bpy.types import Bone, NodeTree
 from .base_definitions import MantisNode, GraphError, FLOAT_EPSILON
-from .base_definitions import MantisSocketTemplate as SockTemplate
+from .link_socket_templates import *
 
 def TellClasses():
     return [
@@ -33,90 +33,10 @@ def TellClasses():
              LinkDrivenParameter,
             ]
 
-# Socket Templates we will reuse:
-# inputs:
-InputRelationshipTemplate : SockTemplate = SockTemplate(
-    name="Input Relationship", is_input=True,  bl_idname='RelationshipSocket', )
-TargetTemplate : SockTemplate = SockTemplate(
-    name="Target", is_input=True,  bl_idname='xFormSocket', )
-Head_Tail_Template : SockTemplate = SockTemplate(
-    name="Head/Tail", is_input=True,  bl_idname='FloatFactorSocket',
-    default_value=1.0, blender_property='head_tail' )
-UseBBoneTemplate : SockTemplate = SockTemplate(
-    name="UseBBone", is_input=True,  bl_idname='BooleanSocket',
-    default_value=False, blender_property='use_bbone_shape' )
-AxeSockTemplate : SockTemplate = SockTemplate(
-    name="Axes", is_input=True,  bl_idname='BooleanThreeTupleSocket',
-    default_value=[True, True, True], blender_property=['use_x', 'use_y', 'use_z'])
-AxesInvertTemplate : SockTemplate = SockTemplate(
-    name="Invert", is_input=True,  bl_idname='BooleanThreeTupleSocket',
-    default_value=[False, False, False], blender_property=['invert_x', 'invert_y', 'invert_z'])
-TargetSpaceTemplate : SockTemplate = SockTemplate(
-    name="Target Space", is_input=True,  bl_idname='TransformSpaceSocket',
-    default_value="WORLD", blender_property='target_space' )
-OwnerSpaceTemplate : SockTemplate = SockTemplate(
-    name="Owner Space", is_input=True,  bl_idname='TransformSpaceSocket',
-    default_value="WORLD", blender_property='owner_space' )
-InfluenceTemplate : SockTemplate = SockTemplate(
-    name="Influence", is_input=True,  bl_idname='FloatFactorSocket',
-    default_value=1.0, blender_property='influence')
-EnableTemplate : SockTemplate = SockTemplate(
-    name="Enable", is_input=True,  bl_idname='EnableSocket',
-    default_value=True, blender_property='mute')
-OffsetTemplate : SockTemplate = SockTemplate(
-    name="Offset", bl_idname='BooleanSocket', is_input=True,
-    default_value=False, blender_property='use_offset')
-# Limit Constraints follow a pattern and can use this generator
-LimitTemplateGenerator = lambda name_stub, axis : SockTemplate(
-    name=name_stub+axis.upper(), is_input=True,  bl_idname='BooleanSocket' if "Use" in name_stub else "FloatSocket",
-    default_value=False, blender_property=name_stub.lower().replace(' ', '_')+axis.lower())
-LimitAxesSocketTemplates = [] # could generate these with loops, but this is easier to understand
-LimitAxesSocketTemplates.append(UseMaxXTemplate := LimitTemplateGenerator("Use Max ", "X"))
-LimitAxesSocketTemplates.append(MaxXTemplate    := LimitTemplateGenerator("Max ", "X"))
-LimitAxesSocketTemplates.append(UseMaxYTemplate := LimitTemplateGenerator("Use Max ", "Y"))
-LimitAxesSocketTemplates.append(MaxYTemplate    := LimitTemplateGenerator("Max ", "Y"))
-LimitAxesSocketTemplates.append(UseMaxZTemplate := LimitTemplateGenerator("Use Max ", "Z"))
-LimitAxesSocketTemplates.append(MaxZTemplate    := LimitTemplateGenerator("Min ", "Z"))
-LimitAxesSocketTemplates.append(UseMinXTemplate := LimitTemplateGenerator("Use Min ", "X"))
-LimitAxesSocketTemplates.append(MinXTemplate    := LimitTemplateGenerator("Min ", "X"))
-LimitAxesSocketTemplates.append(UseMinYTemplate := LimitTemplateGenerator("Use Min ", "Y"))
-LimitAxesSocketTemplates.append(MinYTemplate    := LimitTemplateGenerator("Min ", "Y"))
-LimitAxesSocketTemplates.append(UseMinZTemplate := LimitTemplateGenerator("Use Min ", "Z"))
-LimitAxesSocketTemplates.append(MinZTemplate    := LimitTemplateGenerator("Min ", "Z"))
-LimitRotationSocketTemplates = [
-    UseXTemplate := LimitTemplateGenerator("Use ", "X"),
-    MaxXTemplate,
-    MinXTemplate,
-    UseYTemplate := LimitTemplateGenerator("Use ", "Y"),
-    MaxYTemplate,
-    MinYTemplate,
-    UseZTemplate := LimitTemplateGenerator("Use ", "Z"),
-    MaxZTemplate,
-    MinZTemplate,
-]
-# annoyingly these are a little different than the pattern:
-UseXTemplate.blender_property='use_limit_x'
-UseYTemplate.blender_property='use_limit_y'
-UseZTemplate.blender_property='use_limit_z'
-AffectTransformTemplate : SockTemplate = SockTemplate(
-    name="Affect Transform", bl_idname='BooleanSocket', is_input=True,
-    default_value=False, blender_property='use_transform_limit')
-# Tracking
-
-TrackAxisTemplate= SockTemplate(name="Track Axis", bl_idname="EnumTrackAxis",
-            is_input=True, default_value='TRACK_Y', blender_property='track_axis')
-
-# outputs:
-OutputRelationshipTemplate : SockTemplate = SockTemplate(
-    name="Output Relationship", is_input=False,  bl_idname='RelationshipSocket', )
-
-
 # set the name if it is available, otherwise just use the constraint's nice name
 set_constraint_name = lambda nc : nc.evaluate_input("Name") if nc.evaluate_input("Name") else nc.__class__.__name__
 
 
-
-
 class MantisLinkNode(MantisNode):
     def __init__(self, signature : tuple,
                  base_tree : NodeTree,
@@ -175,17 +95,6 @@ def GetxForm(nc):
             return node
     raise GraphError("%s is not connected to a downstream xForm" % nc)
 
-LinkInheritSockets = [              
-    SockTemplate(name="Inherit Rotation", is_input=True,
-                 bl_idname='BooleanSocket',       default_value=True,),
-    SockTemplate(name="Inherit Scale",    is_input=True,
-                 bl_idname='EnumInheritScale',    default_value="FULL",),
-    SockTemplate(name="Connected",        is_input=True,
-                 bl_idname='BooleanSocket',       default_value=False,),
-    SockTemplate(name="Parent",           is_input=True,   bl_idname='xFormSocket',),
-    SockTemplate(name="Inheritance",      is_input=False,  bl_idname='RelationshipSocket',),
-]
-
 class LinkInherit(MantisLinkNode):
     '''A node representing inheritance'''
     
@@ -203,21 +112,6 @@ class LinkInherit(MantisLinkNode):
                 return node
         raise GraphError("%s is not connected to a downstream xForm" % self)
 
-LinkCopyLocationSockets = [
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    AxeSockTemplate,
-    AxesInvertTemplate,
-    TargetSpaceTemplate,
-    OwnerSpaceTemplate,
-    OffsetTemplate,
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkCopyLocation(MantisLinkNode):
     '''A node representing Copy Location'''
     
@@ -246,25 +140,6 @@ class LinkCopyLocation(MantisLinkNode):
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
         
-
-    
-
-LinkCopyRotationSockets = [
-    InputRelationshipTemplate,
-    SockTemplate(name='RotationOrder', bl_idname='RotationOrderSocket', is_input=True,
-                         default_value='AUTO', blender_property='euler_order'),
-    SockTemplate(name='Rotation Mix',  bl_idname='EnumRotationMix', is_input=True,
-                         default_value='REPLACE', blender_property='mix_mode'),
-    AxeSockTemplate,
-    AxesInvertTemplate,
-    TargetSpaceTemplate,
-    OwnerSpaceTemplate,
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkCopyRotation(MantisLinkNode):
     '''A node representing Copy Rotation'''
     
@@ -300,24 +175,6 @@ class LinkCopyRotation(MantisLinkNode):
         props_sockets = self.gen_property_socket_map()
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
-            
-
-
-LinkCopyScaleSockets = [
-    InputRelationshipTemplate,
-    OffsetTemplate,
-    SockTemplate(name='Average', bl_idname = 'BooleanSocket', is_input=True,
-                         default_value=False, blender_property='use_make_uniform'),
-    SockTemplate(name='Additive', bl_idname = 'BooleanSocket', is_input=True,
-                         default_value=False, blender_property='use_add'),
-    AxeSockTemplate,
-    TargetSpaceTemplate,
-    OwnerSpaceTemplate,
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
         
 class LinkCopyScale(MantisLinkNode):
     '''A node representing Copy Scale'''
@@ -360,21 +217,6 @@ class LinkCopyScale(MantisLinkNode):
         self.executed = True 
             
 
-
-LinkCopyTransformsSockets = [
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    SockTemplate(name='Mix', bl_idname = 'EnumRotationMixCopyTransforms', is_input=True,
-                         default_value="REPLACE", blender_property='mix_mode'),
-    TargetSpaceTemplate,
-    OwnerSpaceTemplate,
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkCopyTransforms(MantisLinkNode):
     '''A node representing Copy Transfoms'''
     
@@ -402,58 +244,6 @@ class LinkCopyTransforms(MantisLinkNode):
         evaluate_sockets(self, c, props_sockets)  
         self.executed = True
 
-
-
-TransformationMinMaxTemplateGenerator = lambda name, bprop  : SockTemplate(
-    name=name, is_input=True,
-    bl_idname='EnumTransformationAxes' if "Source" in name else "FloatSocket",
-    default_value=False, blender_property=bprop)
-    
-LinkTransformationSockets = [
-    InputRelationshipTemplate,
-    TargetTemplate,
-    OwnerSpaceTemplate,
-    TargetSpaceTemplate,
-    SockTemplate(name="Extrapolate", is_input=True, bl_idname='BooleanSocket',
-                default_value=False, blender_property='use_motion_extrapolate'),
-    SockTemplate(name="Map From", is_input=True, bl_idname='EnumTransformationMap',
-                default_value="LOCATION", blender_property='map_from'),
-    SockTemplate(name="Rotation Mode", is_input=True, bl_idname='EnumTransformationRotationMode',
-                default_value="AUTO", blender_property='from_rotation_mode', hide=True),
-    TransformationMinMaxTemplateGenerator("X Min From", "from_min_x"),
-    TransformationMinMaxTemplateGenerator("X Max From", "from_max_x"),
-    TransformationMinMaxTemplateGenerator("Y Min From", "from_min_y"),
-    TransformationMinMaxTemplateGenerator("Y Max From", "from_max_y"),
-    TransformationMinMaxTemplateGenerator("Z Min From", "from_min_z"),
-    TransformationMinMaxTemplateGenerator("Z Max From", "from_max_z"),
-    SockTemplate(name="Map To", is_input=True, bl_idname='EnumTransformationMap',
-                default_value="LOCATION", blender_property='map_to'),
-    SockTemplate(name="Rotation Order", is_input=True, bl_idname='EnumTransformationRotationOrder',
-                default_value="AUTO", blender_property='to_euler_order', hide=True),
-    TransformationMinMaxTemplateGenerator("X Source Axis", "map_to_x_from"),
-    TransformationMinMaxTemplateGenerator("X Min To", "to_min_x"),
-    TransformationMinMaxTemplateGenerator("X Max To", "to_max_x"),
-    TransformationMinMaxTemplateGenerator("Y Source Axis", "map_to_y_from"),
-    TransformationMinMaxTemplateGenerator("Y Min To", "to_min_y"),
-    TransformationMinMaxTemplateGenerator("Y Max To", "to_max_y"),
-    TransformationMinMaxTemplateGenerator("Z Source Axis", "map_to_z_from"),
-    TransformationMinMaxTemplateGenerator("Z Min To", "to_min_z"),
-    TransformationMinMaxTemplateGenerator("Z Max To", "to_max_z"),
-    SockTemplate(name="Mix Mode (Translation)", is_input=True,
-                 bl_idname='EnumTransformationTranslationMixMode',
-                default_value="ADD", blender_property='mix_mode',),
-    SockTemplate(name="Mix Mode (Translation)", is_input=True,
-                 bl_idname='EnumTransformationRotationMixMode',
-                default_value="ADD", blender_property='mix_mode_rot',  hide=True),
-    SockTemplate(name="Mix Mode (Translation)", is_input=True,
-                 bl_idname='EnumTransformationScaleMixMode',
-                default_value="REPLACE", blender_property='mix_mode_scale',  hide=True),
-    InfluenceTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-
-]
-
 class LinkTransformation(MantisLinkNode):
     '''A node representing Copy Transfoms'''
     
@@ -480,16 +270,6 @@ class LinkTransformation(MantisLinkNode):
         evaluate_sockets(self, c, props_sockets)  
         self.executed = True
 
-LinkLimitLocationScaleSockets = [
-    InputRelationshipTemplate,
-    *LimitAxesSocketTemplates, # we generated these ahead of time in a list
-    AffectTransformTemplate,
-    OwnerSpaceTemplate,
-    InfluenceTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkLimitLocation(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkLimitLocationScaleSockets)
@@ -514,16 +294,6 @@ class LinkLimitLocation(MantisLinkNode):
         props_sockets = self.gen_property_socket_map()
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
-
-LinkLimitRotationSockets = [
-    InputRelationshipTemplate,
-    *LimitRotationSocketTemplates, # we generated these ahead of time in a list
-    AffectTransformTemplate,
-    OwnerSpaceTemplate,
-    InfluenceTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
         
 class LinkLimitRotation(MantisLinkNode):
     def __init__(self, signature, base_tree):
@@ -549,16 +319,6 @@ class LinkLimitRotation(MantisLinkNode):
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
 
-LinkLimitLocationScaleSockets = [
-    InputRelationshipTemplate,
-    *LimitAxesSocketTemplates, # we generated these ahead of time in a list
-    AffectTransformTemplate,
-    OwnerSpaceTemplate,
-    InfluenceTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-] 
-        
 class LinkLimitScale(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkLimitLocationScaleSockets)
@@ -582,22 +342,7 @@ class LinkLimitScale(MantisLinkNode):
         props_sockets = self.gen_property_socket_map()
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
-
-LinkLimitDistanceSockets = [
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    SockTemplate(name="Distance", bl_idname='FloatSocket', is_input=True,
-                 default_value=0.0, blender_property='distance'),
-    SockTemplate(name="Clamp Region", bl_idname="EnumLimitMode", is_input=True,
-                 default_value='LIMITDIST_INSIDE', blender_property='limit_mode'),
-    AffectTransformTemplate,
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-        
+ 
 class LinkLimitDistance(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkLimitDistanceSockets)
@@ -624,34 +369,6 @@ class LinkLimitDistance(MantisLinkNode):
 
 # Tracking
 
-LinkStretchToSockets = [
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    SockTemplate(name="Original Length", bl_idname='FloatSocket', is_input=True,
-                 default_value=0.0, blender_property='rest_length'),
-    SockTemplate(name="Volume Variation", bl_idname='FloatSocket', is_input=True,
-                 default_value=1.0, blender_property='bulge'),
-    SockTemplate(name="Use Volume Min", bl_idname='BoolUpdateParentNode', is_input=True,
-                 default_value=False, blender_property='use_bulge_min'),
-    SockTemplate(name="Volume Min", bl_idname='FloatSocket', is_input=True,
-                 default_value=1.0, blender_property='bulge_min'),
-    SockTemplate(name="Use Volume Max", bl_idname='BoolUpdateParentNode', is_input=True,
-                 default_value=False, blender_property='use_bulge_max'),
-    SockTemplate(name="Volume Max", bl_idname='FloatSocket', is_input=True,
-                 default_value=1.0, blender_property='bulge_max'),
-    SockTemplate(name="Smooth", bl_idname='FloatFactorSocket', is_input=True,
-                 default_value=0.0, blender_property='bulge_smooth'),
-    SockTemplate(name="Maintain Volume", bl_idname='EnumMaintainVolumeStretchToSocket', is_input=True,
-                 default_value="VOLUME_XZX", blender_property='volume'),
-    SockTemplate(name="Rotation", bl_idname='EnumRotationStretchTo', is_input=True,
-                 default_value="SWING_Y", blender_property='keep_axis'),
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkStretchTo(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkStretchToSockets)
@@ -678,17 +395,6 @@ class LinkStretchTo(MantisLinkNode):
             # this is meant to be set automatically.
             c.rest_length = self.GetxForm().bGetObject().bone.length
         self.executed = True
-        
-LinkDampedTrackSockets =[
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    TrackAxisTemplate,
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
 
 class LinkDampedTrack(MantisLinkNode):
     def __init__(self, signature, base_tree):
@@ -712,19 +418,6 @@ class LinkDampedTrack(MantisLinkNode):
         props_sockets = self.gen_property_socket_map()
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
-    
-LinkLockedTrackSockets =[
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    TrackAxisTemplate,
-    SockTemplate(name="Lock Axis", bl_idname="EnumLockAxis", is_input=True,
-                 default_value="LOCK_Z", blender_property='lock_axis'),
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]   
 
 class LinkLockedTrack(MantisLinkNode):
     def __init__(self, signature, base_tree):
@@ -749,25 +442,6 @@ class LinkLockedTrack(MantisLinkNode):
         evaluate_sockets(self, c, props_sockets)
         self.executed = True
 
-
-
-# NOTE: I am setting different default values here than Blender in order to remain
-#       consistent with the track constraints tracking the bone to the target.
-LinkTrackToSockets = [
-    InputRelationshipTemplate,
-    Head_Tail_Template,
-    UseBBoneTemplate,
-    TrackAxisTemplate,
-    SockTemplate(name="Up Axis", bl_idname="EnumUpAxis", is_input=True,
-                 default_value="UP_Z", blender_property='up_axis'),
-    SockTemplate(name="Use Target Z", bl_idname="BooleanSocket", is_input=True,
-                 default_value=False, blender_property='use_target_z'),
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkTrackTo(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkTrackToSockets)
@@ -792,26 +466,6 @@ class LinkTrackTo(MantisLinkNode):
         self.executed = True
 
 
-
-# relationships & misc.
-
-LinkInheritConstraintSockets = [
-    InputRelationshipTemplate,
-    SockTemplate(name="Location", bl_idname='BooleanThreeTupleSocket',
-                  is_input=True, default_value=[True, True, True],
-                 blender_property=['use_location_x', 'use_location_y', 'use_location_z']),
-    SockTemplate(name="Rotation", bl_idname='BooleanThreeTupleSocket',
-                  is_input=True, default_value=[True, True, True],
-                 blender_property=['use_rotation_x', 'use_rotation_y', 'use_rotation_z']),
-    SockTemplate(name="Scale", bl_idname='BooleanThreeTupleSocket',
-                  is_input=True, default_value=[True, True, True],
-                 blender_property=['use_scale_x', 'use_scale_y', 'use_scale_z']),
-    InfluenceTemplate,
-    TargetTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkInheritConstraint(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkInheritConstraintSockets)
@@ -837,26 +491,6 @@ class LinkInheritConstraint(MantisLinkNode):
         c.set_inverse_pending
         self.executed = True
 
-LinkInverseKinematicsSockets = [
-    InputRelationshipTemplate,
-    ChainLengthTemplate := SockTemplate(name="Chain Length",
-                 bl_idname="IntSocket", is_input=True,
-                 default_value=0, blender_property='chain_count'),
-    SockTemplate(name="Use Tail", bl_idname="BooleanSocket", is_input=True,
-                 default_value=True, blender_property='use_tail'),
-    SockTemplate(name="Stretch", bl_idname="BooleanSocket", is_input=True,
-                 default_value=True, blender_property='use_stretch'),
-    SockTemplate(name="Position", bl_idname="FloatFactorSocket", is_input=True,
-                 default_value=1.0, blender_property='weight'),
-    SockTemplate(name="Rotation", bl_idname="FloatFactorSocket", is_input=True,
-                 default_value=0.0, blender_property='orient_weight'),
-    InfluenceTemplate,
-    TargetTemplate,
-    SockTemplate(name="Pole Target", is_input=True,  bl_idname='xFormSocket', ),
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkInverseKinematics(MantisLinkNode):
     def __init__(self, signature, base_tree):
         super().__init__(signature, base_tree, LinkInverseKinematicsSockets)
@@ -931,7 +565,6 @@ class LinkInverseKinematics(MantisLinkNode):
 
         return knee_direction.angle(pole_direction)
 
-    
     def calc_pole_angle_post(self, c, ik_bone, context):
         """
             This function should give us a completely accurate result for IK.
@@ -1060,17 +693,6 @@ def ik_report_error(pb, context, do_print=False):
         print (f"IK Scale Error   : {scale_error}")
     return (location_error, rotation_error, scale_error) 
 
-LinkDrivenParameterSockets = [
-    InputRelationshipTemplate,
-    SockTemplate(name="Value", bl_idname="FloatSocket", is_input=True,
-                 default_value=-0.0,),
-    SockTemplate(name="Parameter", bl_idname="ParameterStringSocket", is_input=True,
-                 default_value="",),
-    SockTemplate(name="Index", bl_idname="IntSocket", is_input=True,
-                 default_value=0,),
-    OutputRelationshipTemplate,
-]
-
 # This is kinda a weird design decision?
 class LinkDrivenParameter(MantisLinkNode):
     '''A node representing an armature object'''
@@ -1127,20 +749,7 @@ class LinkDrivenParameter(MantisLinkNode):
         except TypeError:
             self.parameters["Value"] = driver
         super().bFinalize(bContext)
-        
-LinkArmatureSockets=[
-    InputRelationshipTemplate,
-    SockTemplate(name="Preserve Volume", bl_idname='BooleanSocket', is_input=True,
-                 default_value=False, blender_property='use_deform_preserve_volume'),
-    SockTemplate(name="Use Envelopes", bl_idname='BooleanSocket', is_input=True,
-                 default_value=False, blender_property='use_bone_envelopes'),
-    SockTemplate(name="Use Current Location", bl_idname='BooleanSocket', is_input=True,
-                 default_value=False, blender_property='use_current_location'),
-    InfluenceTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-        
+    
 class LinkArmature(MantisLinkNode):
     '''A node representing an armature object'''
 
@@ -1181,28 +790,6 @@ class LinkArmature(MantisLinkNode):
             c.targets[target].weight=value
         self.executed = True
 
-LinkSplineIKSockets = [
-    InputRelationshipTemplate,
-    TargetTemplate,
-    ChainLengthTemplate,
-    SockTemplate(name="Even Divisions", bl_idname="BooleanSocket", is_input=True,
-                 default_value=False, blender_property='use_even_divisions'),
-    SockTemplate(name="Chain Offset", bl_idname="BooleanSocket", is_input=True,
-                 default_value=False, blender_property='use_chain_offset'),
-    SockTemplate(name="Use Curve Radius", bl_idname="BooleanSocket", is_input=True,
-                 default_value=True, blender_property='use_curve_radius'),
-    SockTemplate(name="Y Scale Mode", bl_idname="EnumYScaleMode", is_input=True,
-                 default_value="FIT_CURVE", blender_property='y_scale_mode'),
-    SockTemplate(name="XZ Scale Mode", bl_idname="EnumXZScaleMode", is_input=True,
-                 default_value="NONE", blender_property='xz_scale_mode'),
-    #IMPORTANT TODO: This socket is removed in 4.5
-    SockTemplate(name="Use Original Scale", bl_idname="BooleanSocket", is_input=True,
-                 default_value=False, blender_property='use_original_scale'),
-    InfluenceTemplate,
-    EnableTemplate,
-    OutputRelationshipTemplate,
-]
-
 class LinkSplineIK(MantisLinkNode):
     '''A node representing an armature object'''
 

+ 2 - 27
link_definitions.py

@@ -7,6 +7,7 @@ from .utilities import (prRed, prGreen, prPurple, prWhite,
                               wrapOrange,)
 
 from .base_definitions import get_signature_from_edited_tree
+from .link_socket_templates import *
 
 def TellClasses():
     return [ LinkInheritNode,
@@ -49,14 +50,8 @@ class LinkInheritNode(Node, LinkNode):
     initialized : bpy.props.BoolProperty(default = False)
     mantis_node_class_name="LinkInherit"
     
-    
-    # bone_prev : bpy.props.BoolProperty(default=False)
-    # bone_next : bpy.props.BoolProperty(default=False)
-
     def init(self, context):
-        from .link_containers import LinkInheritSockets
         self.init_sockets(LinkInheritSockets)
-        # set default values...
         self.initialized = True
         self.use_custom_color = True
         self.color = inheritColor
@@ -102,7 +97,6 @@ class LinkInverseKinematics(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkInverseKinematicsSockets
         self.init_sockets(LinkInverseKinematicsSockets)
         self.initialized = True
         self.use_custom_color = True
@@ -118,7 +112,6 @@ class LinkCopyLocationNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkCopyLocationSockets
         self.init_sockets(LinkCopyLocationSockets)
         self.use_custom_color = True
         self.color = linkColor
@@ -134,7 +127,6 @@ class LinkCopyRotationNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkCopyRotationSockets
         self.init_sockets(LinkCopyRotationSockets)
         self.use_custom_color = True
         self.color = linkColor
@@ -151,7 +143,6 @@ class LinkCopyScaleNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkCopyScaleSockets
         self.init_sockets(LinkCopyScaleSockets)
         self.use_custom_color = True
         self.color = linkColor
@@ -171,7 +162,6 @@ class LinkInheritConstraintNode(Node, LinkNode):
 
     # === Optional Functions ===
     def init(self, context):
-        from .link_containers import LinkInheritConstraintSockets
         self.init_sockets(LinkInheritConstraintSockets)
         self.use_custom_color = True
         self.color = inheritColor
@@ -189,7 +179,6 @@ class LinkCopyTransformNode(Node, LinkNode):
 
     # === Optional Functions ===
     def init(self, context):
-        from .link_containers import LinkCopyTransformsSockets
         self.init_sockets(LinkCopyTransformsSockets)
         self.use_custom_color = True
         self.color = linkColor
@@ -206,7 +195,6 @@ class LinkStretchToNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkStretchToSockets
         self.init_sockets(LinkStretchToSockets)
         self.initialized = True
         self.use_custom_color = True
@@ -221,7 +209,6 @@ class LinkDampedTrackNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkDampedTrackSockets
         self.init_sockets(LinkDampedTrackSockets)
         self.initialized = True
         self.use_custom_color = True
@@ -236,7 +223,7 @@ class LinkLockedTrackNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkLockedTrackSockets
+        self.init_sockets(LinkLockedTrackSockets)
         self.initialized = True
         self.use_custom_color = True
         self.color = trackingColor
@@ -250,7 +237,6 @@ class LinkTrackToNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkTrackToSockets
         self.init_sockets(LinkTrackToSockets)
         self.initialized = True
         self.use_custom_color = True
@@ -265,7 +251,6 @@ class LinkLimitLocationNode(Node, LinkNode):
     initialized : bpy.props.BoolProperty(default = False)
 
     def init(self, context):
-        from .link_containers import LinkLimitLocationScaleSockets
         self.init_sockets(LinkLimitLocationScaleSockets)
         self.initialized = True
         self.use_custom_color = True
@@ -280,15 +265,12 @@ class LinkLimitScaleNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkLimitLocationScaleSockets
         self.init_sockets(LinkLimitLocationScaleSockets)
         self.initialized = True
         self.use_custom_color = True
         self.color = linkColor
  
 class LinkLimitRotationNode(Node, LinkNode):
-    # === Basics ===
-    # Description string
     '''A node representing Limit Rotation'''
     bl_idname = 'LinkLimitRotation'
     bl_label = "Limit Rotation"
@@ -296,9 +278,7 @@ class LinkLimitRotationNode(Node, LinkNode):
     initialized : bpy.props.BoolProperty(default = False)
     mantis_node_class_name=bl_idname
 
-    # === Optional Functions ===
     def init(self, context):
-        from .link_containers import LinkLimitRotationSockets
         self.init_sockets(LinkLimitRotationSockets)
         self.initialized = True
         # color
@@ -314,7 +294,6 @@ class LinkLimitDistanceNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkLimitDistanceSockets
         self.init_sockets(LinkLimitDistanceSockets)
         self.use_custom_color = True
         self.color = linkColor
@@ -330,7 +309,6 @@ class LinkTransformationNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
 
     def init(self, context):
-        from .link_containers import LinkTransformationSockets
         self.init_sockets(LinkTransformationSockets)
         self.use_custom_color = True
         self.color = linkColor
@@ -369,7 +347,6 @@ class LinkArmatureNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
     
     def init(self, context):
-        from .link_containers import LinkArmatureSockets
         self.init_sockets(LinkArmatureSockets)
         self.use_custom_color = True
         self.color = inheritColor
@@ -392,7 +369,6 @@ class LinkSplineIKNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
     
     def init(self, context):
-        from .link_containers import LinkSplineIKSockets
         self.init_sockets(LinkSplineIKSockets)
         self.use_custom_color = True
         self.color = ikColor
@@ -409,7 +385,6 @@ class LinkDrivenParameterNode(Node, LinkNode):
     mantis_node_class_name=bl_idname
     
     def init(self, context):
-        from .link_containers import LinkDrivenParameterSockets
         self.init_sockets(LinkDrivenParameterSockets)
         self.use_custom_color = True
         self.color = linkColor

+ 404 - 0
link_socket_templates.py

@@ -0,0 +1,404 @@
+from .base_definitions import MantisSocketTemplate as SockTemplate
+from bpy import app
+
+# Socket Templates we will reuse:
+# inputs:
+InputRelationshipTemplate : SockTemplate = SockTemplate(
+    name="Input Relationship", is_input=True,  bl_idname='RelationshipSocket', )
+TargetTemplate : SockTemplate = SockTemplate(
+    name="Target", is_input=True,  bl_idname='xFormSocket', )
+Head_Tail_Template : SockTemplate = SockTemplate(
+    name="Head/Tail", is_input=True,  bl_idname='FloatFactorSocket',
+    default_value=1.0, blender_property='head_tail' )
+UseBBoneTemplate : SockTemplate = SockTemplate(
+    name="UseBBone", is_input=True,  bl_idname='BooleanSocket',
+    default_value=False, blender_property='use_bbone_shape' )
+AxeSockTemplate : SockTemplate = SockTemplate(
+    name="Axes", is_input=True,  bl_idname='BooleanThreeTupleSocket',
+    default_value=[True, True, True], blender_property=['use_x', 'use_y', 'use_z'])
+AxesInvertTemplate : SockTemplate = SockTemplate(
+    name="Invert", is_input=True,  bl_idname='BooleanThreeTupleSocket',
+    default_value=[False, False, False], blender_property=['invert_x', 'invert_y', 'invert_z'])
+TargetSpaceTemplate : SockTemplate = SockTemplate(
+    name="Target Space", is_input=True,  bl_idname='TransformSpaceSocket',
+    default_value="WORLD", blender_property='target_space' )
+OwnerSpaceTemplate : SockTemplate = SockTemplate(
+    name="Owner Space", is_input=True,  bl_idname='TransformSpaceSocket',
+    default_value="WORLD", blender_property='owner_space' )
+InfluenceTemplate : SockTemplate = SockTemplate(
+    name="Influence", is_input=True,  bl_idname='FloatFactorSocket',
+    default_value=1.0, blender_property='influence')
+EnableTemplate : SockTemplate = SockTemplate(
+    name="Enable", is_input=True,  bl_idname='EnableSocket',
+    default_value=True, blender_property='mute')
+OffsetTemplate : SockTemplate = SockTemplate(
+    name="Offset", bl_idname='BooleanSocket', is_input=True,
+    default_value=False, blender_property='use_offset')
+# Limit Constraints follow a pattern and can use this generator
+LimitTemplateGenerator = lambda name_stub, axis : SockTemplate(
+    name=name_stub+axis.upper(), is_input=True,  bl_idname='BooleanSocket' if "Use" in name_stub else "FloatSocket",
+    default_value=False, blender_property=name_stub.lower().replace(' ', '_')+axis.lower())
+LimitAxesSocketTemplates = [] # could generate these with loops, but this is easier to understand
+LimitAxesSocketTemplates.append(UseMaxXTemplate := LimitTemplateGenerator("Use Max ", "X"))
+LimitAxesSocketTemplates.append(MaxXTemplate    := LimitTemplateGenerator("Max ", "X"))
+LimitAxesSocketTemplates.append(UseMaxYTemplate := LimitTemplateGenerator("Use Max ", "Y"))
+LimitAxesSocketTemplates.append(MaxYTemplate    := LimitTemplateGenerator("Max ", "Y"))
+LimitAxesSocketTemplates.append(UseMaxZTemplate := LimitTemplateGenerator("Use Max ", "Z"))
+LimitAxesSocketTemplates.append(MaxZTemplate    := LimitTemplateGenerator("Min ", "Z"))
+LimitAxesSocketTemplates.append(UseMinXTemplate := LimitTemplateGenerator("Use Min ", "X"))
+LimitAxesSocketTemplates.append(MinXTemplate    := LimitTemplateGenerator("Min ", "X"))
+LimitAxesSocketTemplates.append(UseMinYTemplate := LimitTemplateGenerator("Use Min ", "Y"))
+LimitAxesSocketTemplates.append(MinYTemplate    := LimitTemplateGenerator("Min ", "Y"))
+LimitAxesSocketTemplates.append(UseMinZTemplate := LimitTemplateGenerator("Use Min ", "Z"))
+LimitAxesSocketTemplates.append(MinZTemplate    := LimitTemplateGenerator("Min ", "Z"))
+LimitRotationSocketTemplates = [
+    UseXTemplate := LimitTemplateGenerator("Use ", "X"),
+    MaxXTemplate,
+    MinXTemplate,
+    UseYTemplate := LimitTemplateGenerator("Use ", "Y"),
+    MaxYTemplate,
+    MinYTemplate,
+    UseZTemplate := LimitTemplateGenerator("Use ", "Z"),
+    MaxZTemplate,
+    MinZTemplate,
+]
+# annoyingly these are a little different than the pattern:
+UseXTemplate.blender_property='use_limit_x'
+UseYTemplate.blender_property='use_limit_y'
+UseZTemplate.blender_property='use_limit_z'
+AffectTransformTemplate : SockTemplate = SockTemplate(
+    name="Affect Transform", bl_idname='BooleanSocket', is_input=True,
+    default_value=False, blender_property='use_transform_limit')
+
+# Tracking
+TrackAxisTemplate= SockTemplate(name="Track Axis", bl_idname="EnumTrackAxis",
+            is_input=True, default_value='TRACK_Y', blender_property='track_axis')
+
+# outputs:
+OutputRelationshipTemplate : SockTemplate = SockTemplate(
+    name="Output Relationship", is_input=False,  bl_idname='RelationshipSocket', )
+
+
+LinkInheritSockets = [              
+    SockTemplate(name="Inherit Rotation", is_input=True,
+                 bl_idname='BooleanSocket',       default_value=True,),
+    SockTemplate(name="Inherit Scale",    is_input=True,
+                 bl_idname='EnumInheritScale',    default_value="FULL",),
+    SockTemplate(name="Connected",        is_input=True,
+                 bl_idname='BooleanSocket',       default_value=False,),
+    SockTemplate(name="Parent",           is_input=True,   bl_idname='xFormSocket',),
+    SockTemplate(name="Inheritance",      is_input=False,  bl_idname='RelationshipSocket',),
+]
+
+
+LinkCopyLocationSockets = [
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    AxeSockTemplate,
+    AxesInvertTemplate,
+    TargetSpaceTemplate,
+    OwnerSpaceTemplate,
+    OffsetTemplate,
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+    
+LinkCopyRotationSockets = [
+    InputRelationshipTemplate,
+    SockTemplate(name='RotationOrder', bl_idname='RotationOrderSocket', is_input=True,
+                         default_value='AUTO', blender_property='euler_order'),
+    SockTemplate(name='Rotation Mix',  bl_idname='EnumRotationMix', is_input=True,
+                         default_value='REPLACE', blender_property='mix_mode'),
+    AxeSockTemplate,
+    AxesInvertTemplate,
+    TargetSpaceTemplate,
+    OwnerSpaceTemplate,
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkCopyScaleSockets = [
+    InputRelationshipTemplate,
+    OffsetTemplate,
+    SockTemplate(name='Average', bl_idname = 'BooleanSocket', is_input=True,
+                         default_value=False, blender_property='use_make_uniform'),
+    SockTemplate(name='Additive', bl_idname = 'BooleanSocket', is_input=True,
+                         default_value=False, blender_property='use_add'),
+    AxeSockTemplate,
+    TargetSpaceTemplate,
+    OwnerSpaceTemplate,
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkCopyTransformsSockets = [
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    SockTemplate(name='Mix', bl_idname = 'EnumRotationMixCopyTransforms', is_input=True,
+                         default_value="REPLACE", blender_property='mix_mode'),
+    TargetSpaceTemplate,
+    OwnerSpaceTemplate,
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+TransformationMinMaxTemplateGenerator = lambda name, bprop  : SockTemplate(
+    name=name, is_input=True,
+    bl_idname='EnumTransformationAxes' if "Source" in name else "FloatSocket",
+    default_value='X' if "Source" in name else 1.0,
+    blender_property=bprop)
+    
+LinkTransformationSockets = [
+    InputRelationshipTemplate,
+    TargetTemplate,
+    OwnerSpaceTemplate,
+    TargetSpaceTemplate,
+    SockTemplate(name="Extrapolate", is_input=True, bl_idname='BooleanSocket',
+                default_value=False, blender_property='use_motion_extrapolate'),
+    SockTemplate(name="Map From", is_input=True, bl_idname='EnumTransformationMap',
+                default_value="LOCATION", blender_property='map_from'),
+    SockTemplate(name="Rotation Mode", is_input=True, bl_idname='EnumTransformationRotationMode',
+                default_value="AUTO", blender_property='from_rotation_mode', hide=True),
+    TransformationMinMaxTemplateGenerator("X Min From", "from_min_x"),
+    TransformationMinMaxTemplateGenerator("X Max From", "from_max_x"),
+    TransformationMinMaxTemplateGenerator("Y Min From", "from_min_y"),
+    TransformationMinMaxTemplateGenerator("Y Max From", "from_max_y"),
+    TransformationMinMaxTemplateGenerator("Z Min From", "from_min_z"),
+    TransformationMinMaxTemplateGenerator("Z Max From", "from_max_z"),
+    SockTemplate(name="Map To", is_input=True, bl_idname='EnumTransformationMap',
+                default_value="LOCATION", blender_property='map_to'),
+    SockTemplate(name="Rotation Order", is_input=True, bl_idname='EnumTransformationRotationOrder',
+                default_value="AUTO", blender_property='to_euler_order', hide=True),
+    TransformationMinMaxTemplateGenerator("X Source Axis", "map_to_x_from"),
+    TransformationMinMaxTemplateGenerator("X Min To", "to_min_x"),
+    TransformationMinMaxTemplateGenerator("X Max To", "to_max_x"),
+    TransformationMinMaxTemplateGenerator("Y Source Axis", "map_to_y_from"),
+    TransformationMinMaxTemplateGenerator("Y Min To", "to_min_y"),
+    TransformationMinMaxTemplateGenerator("Y Max To", "to_max_y"),
+    TransformationMinMaxTemplateGenerator("Z Source Axis", "map_to_z_from"),
+    TransformationMinMaxTemplateGenerator("Z Min To", "to_min_z"),
+    TransformationMinMaxTemplateGenerator("Z Max To", "to_max_z"),
+    SockTemplate(name="Mix Mode (Translation)", is_input=True,
+                 bl_idname='EnumTransformationTranslationMixMode',
+                default_value="REPLACE", blender_property='mix_mode',),
+    SockTemplate(name="Mix Mode (Rotation)", is_input=True,
+                 bl_idname='EnumTransformationRotationMixMode',
+                default_value="ADD", blender_property='mix_mode_rot',  hide=True),
+    SockTemplate(name="Mix Mode (Scale)", is_input=True,
+                 bl_idname='EnumTransformationScaleMixMode',
+                default_value="REPLACE", blender_property='mix_mode_scale',  hide=True),
+    InfluenceTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkLimitLocationScaleSockets = [
+    InputRelationshipTemplate,
+    *LimitAxesSocketTemplates, # we generated these ahead of time in a list
+    AffectTransformTemplate,
+    OwnerSpaceTemplate,
+    InfluenceTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkLimitRotationSockets = [
+    InputRelationshipTemplate,
+    *LimitRotationSocketTemplates, # we generated these ahead of time in a list
+    AffectTransformTemplate,
+    OwnerSpaceTemplate,
+    InfluenceTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkLimitLocationScaleSockets = [
+    InputRelationshipTemplate,
+    *LimitAxesSocketTemplates, # we generated these ahead of time in a list
+    AffectTransformTemplate,
+    OwnerSpaceTemplate,
+    InfluenceTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+LinkLimitDistanceSockets = [
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    SockTemplate(name="Distance", bl_idname='FloatSocket', is_input=True,
+                 default_value=0.0, blender_property='distance'),
+    SockTemplate(name="Clamp Region", bl_idname="EnumLimitMode", is_input=True,
+                 default_value='LIMITDIST_INSIDE', blender_property='limit_mode'),
+    AffectTransformTemplate,
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkStretchToSockets = [
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    SockTemplate(name="Original Length", bl_idname='FloatSocket', is_input=True,
+                 default_value=0.0, blender_property='rest_length'),
+    SockTemplate(name="Volume Variation", bl_idname='FloatSocket', is_input=True,
+                 default_value=1.0, blender_property='bulge'),
+    SockTemplate(name="Use Volume Min", bl_idname='BoolUpdateParentNode', is_input=True,
+                 default_value=False, blender_property='use_bulge_min'),
+    SockTemplate(name="Volume Min", bl_idname='FloatSocket', is_input=True,
+                 default_value=1.0, blender_property='bulge_min'),
+    SockTemplate(name="Use Volume Max", bl_idname='BoolUpdateParentNode', is_input=True,
+                 default_value=False, blender_property='use_bulge_max'),
+    SockTemplate(name="Volume Max", bl_idname='FloatSocket', is_input=True,
+                 default_value=1.0, blender_property='bulge_max'),
+    SockTemplate(name="Smooth", bl_idname='FloatFactorSocket', is_input=True,
+                 default_value=0.0, blender_property='bulge_smooth'),
+    SockTemplate(name="Maintain Volume", bl_idname='EnumMaintainVolumeStretchToSocket', is_input=True,
+                 default_value="VOLUME_XZX", blender_property='volume'),
+    SockTemplate(name="Rotation", bl_idname='EnumRotationStretchTo', is_input=True,
+                 default_value="SWING_Y", blender_property='keep_axis'),
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkDampedTrackSockets =[
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    TrackAxisTemplate,
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkLockedTrackSockets =[
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    TrackAxisTemplate,
+    SockTemplate(name="Lock Axis", bl_idname="EnumLockAxis", is_input=True,
+                 default_value="LOCK_Z", blender_property='lock_axis'),
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+# NOTE: I am setting different default values here than Blender in order to remain
+#       consistent with the track constraints tracking the bone to the target.
+LinkTrackToSockets = [
+    InputRelationshipTemplate,
+    Head_Tail_Template,
+    UseBBoneTemplate,
+    TrackAxisTemplate,
+    SockTemplate(name="Up Axis", bl_idname="EnumUpAxis", is_input=True,
+                 default_value="UP_Z", blender_property='up_axis'),
+    SockTemplate(name="Use Target Z", bl_idname="BooleanSocket", is_input=True,
+                 default_value=False, blender_property='use_target_z'),
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+# relationships & misc.
+LinkInheritConstraintSockets = [
+    InputRelationshipTemplate,
+    SockTemplate(name="Location", bl_idname='BooleanThreeTupleSocket',
+                  is_input=True, default_value=[True, True, True],
+                 blender_property=['use_location_x', 'use_location_y', 'use_location_z']),
+    SockTemplate(name="Rotation", bl_idname='BooleanThreeTupleSocket',
+                  is_input=True, default_value=[True, True, True],
+                 blender_property=['use_rotation_x', 'use_rotation_y', 'use_rotation_z']),
+    SockTemplate(name="Scale", bl_idname='BooleanThreeTupleSocket',
+                  is_input=True, default_value=[True, True, True],
+                 blender_property=['use_scale_x', 'use_scale_y', 'use_scale_z']),
+    InfluenceTemplate,
+    TargetTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkInverseKinematicsSockets = [
+    InputRelationshipTemplate,
+    ChainLengthTemplate := SockTemplate(name="Chain Length",
+                 bl_idname="IntSocket", is_input=True,
+                 default_value=0, blender_property='chain_count'),
+    SockTemplate(name="Use Tail", bl_idname="BooleanSocket", is_input=True,
+                 default_value=True, blender_property='use_tail'),
+    SockTemplate(name="Stretch", bl_idname="BooleanSocket", is_input=True,
+                 default_value=True, blender_property='use_stretch'),
+    SockTemplate(name="Position", bl_idname="FloatFactorSocket", is_input=True,
+                 default_value=1.0, blender_property='weight'),
+    SockTemplate(name="Rotation", bl_idname="FloatFactorSocket", is_input=True,
+                 default_value=0.0, blender_property='orient_weight'),
+    InfluenceTemplate,
+    TargetTemplate,
+    SockTemplate(name="Pole Target", is_input=True,  bl_idname='xFormSocket', ),
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkDrivenParameterSockets = [
+    InputRelationshipTemplate,
+    SockTemplate(name="Value", bl_idname="FloatSocket", is_input=True,
+                 default_value=-0.0,),
+    SockTemplate(name="Parameter", bl_idname="ParameterStringSocket", is_input=True,
+                 default_value="",),
+    SockTemplate(name="Index", bl_idname="IntSocket", is_input=True,
+                 default_value=0,),
+    OutputRelationshipTemplate,
+]
+  
+LinkArmatureSockets=[
+    InputRelationshipTemplate,
+    SockTemplate(name="Preserve Volume", bl_idname='BooleanSocket', is_input=True,
+                 default_value=False, blender_property='use_deform_preserve_volume'),
+    SockTemplate(name="Use Envelopes", bl_idname='BooleanSocket', is_input=True,
+                 default_value=False, blender_property='use_bone_envelopes'),
+    SockTemplate(name="Use Current Location", bl_idname='BooleanSocket', is_input=True,
+                 default_value=False, blender_property='use_current_location'),
+    InfluenceTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+LinkSplineIKSockets = [
+    InputRelationshipTemplate,
+    TargetTemplate,
+    ChainLengthTemplate,
+    SockTemplate(name="Even Divisions", bl_idname="BooleanSocket", is_input=True,
+                 default_value=False, blender_property='use_even_divisions'),
+    SockTemplate(name="Chain Offset", bl_idname="BooleanSocket", is_input=True,
+                 default_value=False, blender_property='use_chain_offset'),
+    SockTemplate(name="Use Curve Radius", bl_idname="BooleanSocket", is_input=True,
+                 default_value=True, blender_property='use_curve_radius'),
+    SockTemplate(name="Y Scale Mode", bl_idname="EnumYScaleMode", is_input=True,
+                 default_value="FIT_CURVE", blender_property='y_scale_mode'),
+    SockTemplate(name="XZ Scale Mode", bl_idname="EnumXZScaleMode", is_input=True,
+                 default_value="NONE", blender_property='xz_scale_mode'),
+    #IMPORTANT NOTE: This socket is removed in 4.5
+    SockTemplate(name="Use Original Scale", bl_idname="BooleanSocket", is_input=True,
+                 default_value=False, blender_property='use_original_scale'),
+    InfluenceTemplate,
+    EnableTemplate,
+    OutputRelationshipTemplate,
+]
+
+# Remove this socket because of Blender changes.
+if (app.version >= (4, 5, 0)):
+    LinkSplineIKSockets.pop(8)