Class: Bvh::Skeleton::Bone

Inherits:
Object
  • Object
show all
Defined in:
lib/bvh/skeleton.rb

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(name = nil, parent = nil) ⇒ Bone

Returns a new instance of Bone.



25
26
27
28
29
# File 'lib/bvh/skeleton.rb', line 25

def initialize(name = nil, parent = nil)
  @name, @parent = name, parent
  @channels, @offset, @joints = [], [], []
  @frames = []
end

Instance Attribute Details

#channelsObject (readonly)

the channels, or degrees of freedom, that this bone allows – and the order that they appear in



17
18
19
# File 'lib/bvh/skeleton.rb', line 17

def channels
  @channels
end

#jointsObject (readonly)

an array of joints, or child bones. Each should have its parent set to this bone. See also #add_joint!



23
24
25
# File 'lib/bvh/skeleton.rb', line 23

def joints
  @joints
end

#nameObject

the name of this bone



11
12
13
# File 'lib/bvh/skeleton.rb', line 11

def name
  @name
end

#offsetObject (readonly)

the offset of this bone in relation to its parent



20
21
22
# File 'lib/bvh/skeleton.rb', line 20

def offset
  @offset
end

#parentObject (readonly)

this bone’s parent bone, if any (if nil, this bone is a root)



14
15
16
# File 'lib/bvh/skeleton.rb', line 14

def parent
  @parent
end

Instance Method Details

#add_joint!(joint) ⇒ Object

Adds the specified bone to this bone’s list of joints, setting its parent equal to this bone. This bone is returned.



33
34
35
36
37
38
# File 'lib/bvh/skeleton.rb', line 33

def add_joint!(joint)
  joint.instance_variable_set("@parent", self)
  raise "Cannot add joint: name '#{joint.name}' already exists" if self / joint.name
  joints << joint unless joints.include? joint
  self
end

#end_site?Boolean

returns true if this is a “leaf” node; that is, there are no joints

Returns:

  • (Boolean)


41
42
43
# File 'lib/bvh/skeleton.rb', line 41

def end_site?
  joints.length == 0
end

#find_by_name(name) ⇒ Object Also known as: /

returns the descendant joint (or self) with the specified name.



46
47
48
49
50
# File 'lib/bvh/skeleton.rb', line 46

def find_by_name(name)
  return self if self.name == name
  joints.each { |j| r = j.find_by_name(name); return r unless r.nil? }
  nil
end

#lengthObject

Returns the length of this bone, inferred from the offset of its first joint.



53
54
55
56
57
58
59
60
61
62
# File 'lib/bvh/skeleton.rb', line 53

def length
  if end_site? then 0
  else
    ofs = joints.first.offset
    # ofs is a vector, so we need its magnitude
    if ofs.nil? then 0
    else Math.sqrt(ofs[0]**2) + Math.sqrt(ofs[1]**2) + Math.sqrt(ofs[2]**2)
    end
  end
end

#orientationObject

Returns a unit vector representing the orientation of this bone, inferred from the offset of its first joint.



65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
# File 'lib/bvh/skeleton.rb', line 65

def orientation
  if end_site? then [0,0,0]
  else
    ofs = joints.first.offset
    if ofs.nil? then [0,0,0]
    else
      # ofs is a vector, so we need to normalize it
      max = proc { |a,b| a.to_f.abs > b.to_f.abs ? a.to_f.abs : b.to_f.abs }
      max = max.call(ofs[0], max.call(ofs[1], ofs[2]))
      if max > 0 then [ofs[0].to_f / max, ofs[1].to_f / max, ofs[2].to_f / max]
      else [0,0,0]
      end
    end
  end
end