f_curve_animatable.py 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105
  1. from .animation import *
  2. from .logger import *
  3. from .package_level import *
  4. import bpy
  5. #===============================================================================
  6. class FCurveAnimatable:
  7. def define_animations(self, object, supportsRotation, supportsPosition, supportsScaling, xOffsetForRotation = 0):
  8. # just because a sub-class can be animatable does not mean it is
  9. self.animationsPresent = object.animation_data and object.animation_data.action
  10. if (self.animationsPresent):
  11. Logger.log('animation processing begun', 2)
  12. # instance each type of animation support regardless of whether there is any data for it
  13. if supportsRotation:
  14. if object.rotation_mode == 'QUATERNION':
  15. if object.type == 'CAMERA':
  16. # if it's a camera, convert quaternions to euler XYZ
  17. rotAnimation = QuaternionToEulerAnimation(object, 'rotation', 'rotation_quaternion', -1, xOffsetForRotation)
  18. else:
  19. rotAnimation = QuaternionAnimation(object, 'rotationQuaternion', 'rotation_quaternion', 1, xOffsetForRotation)
  20. else:
  21. rotAnimation = VectorAnimation(object, 'rotation', 'rotation_euler', -1, xOffsetForRotation)
  22. if supportsPosition:
  23. posAnimation = VectorAnimation(object, 'position', 'location')
  24. if supportsScaling:
  25. scaleAnimation = VectorAnimation(object, 'scaling', 'scale')
  26. self.ranges = []
  27. frameOffset = 0
  28. currentAction = object.animation_data.action
  29. for action in bpy.data.actions:
  30. # get the range / assigning the action to the object
  31. animationRange = AnimationRange.actionPrep(object, action, False, frameOffset)
  32. if animationRange is None:
  33. continue
  34. if supportsRotation:
  35. hasData = rotAnimation.append_range(object, animationRange)
  36. if supportsPosition:
  37. hasData |= posAnimation.append_range(object, animationRange)
  38. if supportsScaling:
  39. hasData |= scaleAnimation.append_range(object, animationRange)
  40. if hasData:
  41. Logger.log('processing action ' + animationRange.to_string(), 3)
  42. self.ranges.append(animationRange)
  43. frameOffset = animationRange.frame_end
  44. object.animation_data.action = currentAction
  45. #Set Animations
  46. self.animations = []
  47. if supportsRotation and len(rotAnimation.frames) > 0:
  48. self.animations.append(rotAnimation)
  49. if supportsPosition and len(posAnimation.frames) > 0:
  50. self.animations.append(posAnimation)
  51. if supportsScaling and len(scaleAnimation.frames) > 0:
  52. self.animations.append(scaleAnimation)
  53. if (hasattr(object.data, "autoAnimate") and object.data.autoAnimate):
  54. self.autoAnimate = True
  55. self.autoAnimateFrom = bpy.context.scene.frame_end
  56. self.autoAnimateTo = 0
  57. for animation in self.animations:
  58. if self.autoAnimateFrom > animation.get_first_frame():
  59. self.autoAnimateFrom = animation.get_first_frame()
  60. if self.autoAnimateTo < animation.get_last_frame():
  61. self.autoAnimateTo = animation.get_last_frame()
  62. self.autoAnimateLoop = True
  63. # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  64. def to_scene_file(self, file_handler):
  65. if (self.animationsPresent):
  66. file_handler.write('\n,"animations":[')
  67. first = True
  68. for animation in self.animations:
  69. if first == False:
  70. file_handler.write(',')
  71. animation.to_scene_file(file_handler)
  72. first = False
  73. file_handler.write(']')
  74. file_handler.write(',"ranges":[')
  75. first = True
  76. for range in self.ranges:
  77. if first != True:
  78. file_handler.write(',')
  79. first = False
  80. range.to_scene_file(file_handler)
  81. file_handler.write(']')
  82. if (hasattr(self, "autoAnimate") and self.autoAnimate):
  83. write_bool(file_handler, 'autoAnimate', self.autoAnimate)
  84. write_int(file_handler, 'autoAnimateFrom', self.autoAnimateFrom)
  85. write_int(file_handler, 'autoAnimateTo', self.autoAnimateTo)
  86. write_bool(file_handler, 'autoAnimateLoop', self.autoAnimateLoop)