Update Files
This commit is contained in:
@ -0,0 +1,176 @@
|
||||
from lnx.logicnode.lnx_nodes import *
|
||||
|
||||
class AddPhysicsConstraintNode(LnxLogicTreeNode):
|
||||
"""
|
||||
Add a physics constraint to constrain two rigid bodies if not already present.
|
||||
|
||||
@option Fixed: No fredom of movement. Relative positions and rotations of rigid bodies are fixed
|
||||
|
||||
@option Point: Both rigid bodies are constrained at the pivot object.
|
||||
|
||||
@option Hinge: Constrained objects can move only along angular Z axis of the pivot object.
|
||||
|
||||
@option Slider: Constrained objects can move only along linear X axis of the pivot object.
|
||||
|
||||
@option Piston: Constrained objects can move only and rotate along X axis of the pivot object.
|
||||
|
||||
@option GenericSpring: Fully custimizable generic 6 degree of freedom constraint with optional springs. All liner and angular axes can be constrained
|
||||
along with spring options. Use `Physics Constraint Node` to set a combination of constraints and springs.
|
||||
|
||||
@seeNode Physics Constraint
|
||||
|
||||
@input Pivot object: The object to which the physics constraint traint is applied. This object will not be affected by the constraint
|
||||
but is necessary to specify the constraint axes and location. Hence, the pivot object need not be a rigid body. Typically an `Empty`
|
||||
object may be used. Each pivot object can have only one constraint trait applied. Moving/rotating/parenting the pivot object after the constraint
|
||||
is applied has no effect. However, removig the pivot object removes the constraint and `RB 1` and `RB 2` are no longer constrained.
|
||||
|
||||
@input RB 1: The first rigid body to be constrained. Must be a rigid body. This object can be constrained by more than one constraint.
|
||||
|
||||
@input RB 2: The second rigid body to be constrained. Must be a rigid body. This object can be constrained by more than one constraint.
|
||||
|
||||
@input Disable Collisions: Disable collisions between `RB 1` and `RB 2`
|
||||
|
||||
@input Breakable: Constraint can break if stress on the constraint is more than the set threshold. Disable this option to disable breaking.
|
||||
|
||||
@input Breaking threshold: Stress on the constraint above which the constraint breaks. Depends on the mass, velocity of rigid bodies and type of constraint.
|
||||
|
||||
@input Limit Lower: Lower limit of the consraint in that particular axis
|
||||
|
||||
@input Limit Upper: Upper limit of the constraint in that particular axis. (`lower limit` = `upper limit`) --> Fully constrained. (`lower limit` < `upper limit`) --> Partially constrained
|
||||
(`lower limit` > `upper limit`) --> Full freedom.
|
||||
|
||||
@input Angular limits: Limits to constarin rotation. Specified in degrees. Range (-360 to +360)
|
||||
|
||||
@input Add Constarint: Option to add custom constraint to `Generic Spring` type.
|
||||
"""
|
||||
|
||||
|
||||
bl_idname = 'LNAddPhysicsConstraintNode'
|
||||
bl_label = 'Add Physics Constraint'
|
||||
lnx_section = 'add'
|
||||
lnx_version = 1
|
||||
|
||||
@staticmethod
|
||||
def get_enum_id_value(obj, prop_name, value):
|
||||
return obj.bl_rna.properties[prop_name].enum_items[value].identifier
|
||||
|
||||
@staticmethod
|
||||
def get_count_in(type_name):
|
||||
return {
|
||||
'Fixed': 0,
|
||||
'Point': 1,
|
||||
'Hinge': 2,
|
||||
'Slider': 3,
|
||||
'Piston': 4,
|
||||
'Generic Spring': 5
|
||||
}.get(type_name, 0)
|
||||
|
||||
def get_enum(self):
|
||||
return self.get('property0', 0)
|
||||
|
||||
def set_enum(self, value):
|
||||
# Checking the selection of another type
|
||||
select_current = self.get_enum_id_value(self, 'property0', value)
|
||||
select_prev = self.property0
|
||||
|
||||
#Check if a different type is selected
|
||||
if select_prev != select_current:
|
||||
print('New value selected')
|
||||
# Arguements for type Fixed
|
||||
if (self.get_count_in(select_current) == 0):
|
||||
while (len(self.inputs) > 7):
|
||||
self.inputs.remove(self.inputs.values()[-1])
|
||||
|
||||
# Arguements for type Point
|
||||
if (self.get_count_in(select_current) == 1):
|
||||
while (len(self.inputs) > 7):
|
||||
self.inputs.remove(self.inputs.values()[-1])
|
||||
|
||||
#Arguements for type Hinge
|
||||
if (self.get_count_in(select_current) == 2):
|
||||
while (len(self.inputs) > 7):
|
||||
self.inputs.remove(self.inputs.values()[-1])
|
||||
#Z ang limits
|
||||
self.add_input('LnxBoolSocket', 'Z angle')
|
||||
self.add_input('LnxFloatSocket', 'Z ang lower', -45.0)
|
||||
self.add_input('LnxFloatSocket', 'Z ang upper', 45.0)
|
||||
|
||||
#Arguements for type Slider
|
||||
if (self.get_count_in(select_current) == 3):
|
||||
while (len(self.inputs) > 7):
|
||||
self.inputs.remove(self.inputs.values()[-1])
|
||||
#X lin limits
|
||||
self.add_input('LnxBoolSocket', 'X linear')
|
||||
self.add_input('LnxFloatSocket', 'X lin lower')
|
||||
self.add_input('LnxFloatSocket', 'X lin upper')
|
||||
|
||||
#Arguements for type Piston
|
||||
if (self.get_count_in(select_current) == 4):
|
||||
while (len(self.inputs) > 7):
|
||||
self.inputs.remove(self.inputs.values()[-1])
|
||||
#X lin limits
|
||||
self.add_input('LnxBoolSocket', 'X linear')
|
||||
self.add_input('LnxFloatSocket', 'X lin lower')
|
||||
self.add_input('LnxFloatSocket', 'X lin upper')
|
||||
#X ang limits
|
||||
self.add_input('LnxBoolSocket', 'X angle')
|
||||
self.add_input('LnxFloatSocket', 'X ang lower', -45.0)
|
||||
self.add_input('LnxFloatSocket', 'X ang upper', 45.0)
|
||||
|
||||
#Arguements for type GenericSpring
|
||||
if (self.get_count_in(select_current) == 5):
|
||||
while (len(self.inputs) > 7):
|
||||
self.inputs.remove(self.inputs.values()[-1])
|
||||
|
||||
self['property0'] = value
|
||||
|
||||
property0: HaxeEnumProperty(
|
||||
'property0',
|
||||
items = [('Fixed', 'Fixed', 'Fixed'),
|
||||
('Point', 'Point', 'Point'),
|
||||
('Hinge', 'Hinge', 'Hinge'),
|
||||
('Slider', 'Slider', 'Slider'),
|
||||
('Piston', 'Piston', 'Piston'),
|
||||
('Generic Spring', 'Generic Spring', 'Generic Spring')],
|
||||
name='Type', default='Fixed', set=set_enum, get=get_enum)
|
||||
|
||||
def __init__(self):
|
||||
array_nodes[str(id(self))] = self
|
||||
|
||||
def lnx_init(self, context):
|
||||
self.add_input('LnxNodeSocketAction', 'In')
|
||||
self.add_input('LnxNodeSocketObject', 'Pivot Object')
|
||||
self.add_input('LnxNodeSocketObject', 'RB 1')
|
||||
self.add_input('LnxNodeSocketObject', 'RB 2')
|
||||
self.add_input('LnxBoolSocket', 'Disable Collissions')
|
||||
self.add_input('LnxBoolSocket', 'Breakable')
|
||||
self.add_input('LnxFloatSocket', 'Breaking Threshold')
|
||||
self.add_output('LnxNodeSocketAction', 'Out')
|
||||
|
||||
def draw_buttons(self, context, layout):
|
||||
layout.prop(self, 'property0')
|
||||
|
||||
#GenericSpring:
|
||||
if (self.get_count_in(self.property0) == 5):
|
||||
grid0 = layout.grid_flow(row_major=True, columns=1, align=True)
|
||||
grid0.label(text="Possible Constraints:")
|
||||
grid0.label(text="Linear [X, Y, Z]")
|
||||
grid0.label(text="Angular [X, Y, Z]")
|
||||
grid0.label(text="Spring Linear [X, Y, Z]")
|
||||
grid0.label(text="Spring Angular [X, Y, Z]")
|
||||
row = layout.row(align=True)
|
||||
column = row.column(align=True)
|
||||
op = column.operator('lnx.node_add_input', text='Add Constraint', icon='PLUS', emboss=True)
|
||||
op.node_index = str(id(self))
|
||||
op.socket_type = 'LnxDynamicSocket'
|
||||
op.name_format = 'Constraint {0}'.format(len(self.inputs) - 6)
|
||||
column1 = row.column(align=True)
|
||||
op = column1.operator('lnx.node_remove_input', text='', icon='X', emboss=True)
|
||||
op.node_index = str(id(self))
|
||||
#Static inputs
|
||||
if len(self.inputs) < 8:
|
||||
column1.enabled = False
|
||||
#Max Possible inputs
|
||||
if len(self.inputs) > 18:
|
||||
column.enabled = False
|
||||
|
Reference in New Issue
Block a user