PDA

View Full Version : Hopefully Simple Question - CreateKey



short223
12-30-2015, 10:44 AM
Long Story Short:
Creating a Python script that imports camera position and rotation values from a proprietary program and inserts the values for each frame to the camera in Lightwave. Kind of a camera matching script.
I have the main code working fine, Camera data is inserted as needed, I'm just trying to enhance the code to do more. Specifically I want, at each frame it inserts the camera data, to have a keyframe created so it records the motion.

From the docs I have been reading, I see there is the "CreateKey" command, but that seems to create a keyframe at a time based number. I would prefer it to be a frame based or on the current frame, since the script advances to each frame and inputs the camera data.

So in theory, I would like: Go to frame 1, make a keyframe, go to frame 2 make a keyframe etc.

I don't want to resort to using math to calculate what frame 1 is...

Thanks!

short223
12-30-2015, 10:54 AM
Also, is there the equivalent command that is like hitting the "return" or Enter button? By using the CreateKey command without a numerical number, it brings up the Create Key window but it needs a return to activate the OK button.
Any help would be appreciated.
Thanks!

Ryan Roye
12-30-2015, 11:10 AM
There are 2 ways to create a keyframe in Python:

1) Using the "CreateKey" command using the playhead's current position. The advantage is its simplicity, the disadvantage is that large keyframe operations will be very slow to process, and you cannot apply this directly to things that only exist in the graph editor. This operates relative to the current selection. Note that the "RefreshNow" command must be used after keying an item if you need to compute something relative to its updated coordinates. Example script:


CurrentTime = lwsdk.LWInterfaceInfo().curTime
lwsdk.command("CreateKey " + str(CurrentTime))
2) Using LW Python's envelope functions. This method is far more difficult to grasp, but is pretty much mandatory to know when you need to operate on specific envelopes and/or need to process hundreds or even thousands of keyframes. It isn't for the faint of heart.


UserSelection = lwsdk.LWInterfaceInfo().selected_items()

for x in range(0, len(UserSelection)):
cGrp = lwsdk.LWItemInfo().chanGroup(UserSelection[x])
chan = lwsdk.LWChannelInfo().nextChannel(cGrp, None)

while chan!= None:
chanName = lwsdk.LWChannelInfo().channelName(chan)

# Insert any channel functions here as desired.
if chanName == "Position.X":
print "Position X Found! All X Position operations go here using envelope functions commands"

chan = lwsdk.LWChannelInfo().nextChannel(cGrp, chan)
print chanName

It is very difficult to explain the logic of method 2. Basically you scan channels one at a time until there are no more. If the string of the channel name patches, it performs the envelope actions you place in that statement.

ernpchan
12-30-2015, 11:24 AM
Also, is there the equivalent command that is like hitting the "return" or Enter button? By using the CreateKey command without a numerical number, it brings up the Create Key window but it needs a return to activate the OK button.
Any help would be appreciated.
Thanks!

You could try enabling AutoConfirm. I don't remember if that works with CreateKey. Feeding a numerical argument isn't bad though. To check if you're at frame 1 or not you would just query the current time.

The second method Ryan explains is much more complicated but much more powerful.

ernpchan
12-30-2015, 11:26 AM
If the string of the channel name patches, it performs the envelope actions you place in that statement.

He means matches, not patches.

short223
12-30-2015, 12:44 PM
Thanks all. The CurrentTime code seems to get the keyframe as needed. I'm running into another issue. This code was originally written for another 3D app and uses a looping code that Lightwave seems to be ignoring.
Basically it starts:

for frame_id in range (0,51):

with the looping at the end :
if __name__ == '__main__':
main()

with main the previously def block

Does Lightwave use a different method for looping arguments. It seems the script does all the calculations for each frame first before even going to the Lightwave portion and inserts only the last frame of information.

ernpchan
12-30-2015, 01:53 PM
Can you post more? Hard to follow what you're seeing.

short223
12-30-2015, 02:08 PM
I discovered the problem as it was my Class line place in the wrong position. By placing it below the loop and cleaning up a few non items, it worked very well.

short223
12-30-2015, 02:12 PM
Thanks for all who helped!

ernpchan
12-30-2015, 02:50 PM
That's great to hear. FYI, next time you're going to post code, use the CODE tags. It'll make it easier to read your code from the rest of your post.