|
import pyautogui # Import pyautogui to simulate keystrokes and mouse actions |
|
|
|
# Get the current project and timeline from DaVinci Resolve |
|
project = resolve.GetProjectManager().GetCurrentProject() |
|
timeline = project.GetCurrentTimeline() |
|
|
|
# Get the timeline frame rate as an integer |
|
frame_rate = int(project.GetSetting("timelineFrameRate")) |
|
|
|
# Function to get the clip currently under the playhead |
|
def get_clip_under_playhead(): |
|
# Convert the current playhead position from timecode to frame count |
|
playhead_position = timecode_to_frames(timeline.GetCurrentTimecode(), frame_rate) |
|
# Retrieve all clips in the first video track |
|
clips = timeline.GetItemListInTrack("video", 1) # assuming video track 1 |
|
# Iterate through clips to find one that includes the playhead position |
|
for clip in clips: |
|
if clip.GetStart() <= playhead_position <= clip.GetEnd(): |
|
return clip # Return the clip found under the playhead |
|
return None # Return None if no clip is found under the playhead |
|
|
|
# Function to convert a timecode string (HH:MM:SS:FF) to an integer frame count |
|
def timecode_to_frames(timecode, frame_rate): |
|
hh, mm, ss, ff = map(int, timecode.split(":")) |
|
# Calculate total frames based on hours, minutes, seconds, and frames |
|
total_frames = (hh * 3600 + mm * 60 + ss) * frame_rate + ff |
|
return total_frames |
|
|
|
# Function to convert a frame count back into a timecode string (HH:MM:SS:FF) |
|
def frames_to_timecode(frames, frame_rate): |
|
hours = frames // (3600 * frame_rate) |
|
minutes = (frames % (3600 * frame_rate)) // (60 * frame_rate) |
|
seconds = (frames % (60 * frame_rate)) // frame_rate |
|
frames_remaining = frames % frame_rate |
|
# Format the timecode with zero-padded values |
|
return f"{int(hours):02}:{int(minutes):02}:{int(seconds):02}:{int(frames_remaining):02}" |
|
|
|
# Function to convert seconds to frames |
|
def seconds_to_frames(seconds, frame_rate): |
|
return int(seconds * frame_rate) |
|
|
|
# Extend the freeze frame by a specified duration (in seconds or frames) |
|
def extend_freeze_frame(clip, duration_frames=None, duration_seconds=None): |
|
# Calculate frame rate and duration in frames |
|
if duration_seconds is not None: |
|
duration_frames = seconds_to_frames(duration_seconds, frame_rate) |
|
|
|
# Calculate and set new end frame |
|
current_end = clip.GetEnd() |
|
new_end_frame = current_end + duration_frames |
|
|
|
# Select the nearest edit point |
|
timeline.SetCurrentTimecode(frames_to_timecode(current_end, frame_rate)) |
|
pyautogui.press('v') |
|
|
|
# Move the playhead to the new postion |
|
timeline.SetCurrentTimecode(frames_to_timecode(new_end_frame, frame_rate)) |
|
|
|
# Extend Edit |
|
pyautogui.press('e') |
|
|
|
|
|
# Main Execution |
|
clip = get_clip_under_playhead() |
|
if clip: |
|
# Move the playhead to just before the last frame of the clip |
|
print(clip.GetName()) |
|
|
|
end_frame = clip.GetEnd() |
|
timeline.SetCurrentTimecode(frames_to_timecode(end_frame - (frame_rate / 2), frame_rate)) |
|
|
|
# Trigger keyboard shortcut for splitting the clip at the playhead |
|
pyautogui.hotkey('ctrl', '\\') |
|
|
|
# Select next clip |
|
pyautogui.hotkey('ctrl', 'right') |
|
|
|
# Move the playhead to the second last frame of the clip |
|
timeline.SetCurrentTimecode(frames_to_timecode(end_frame - 1, frame_rate)) |
|
|
|
# Apply a freeze frame by pressing Shift + R |
|
pyautogui.hotkey('shift', 'R') |
|
|
|
new_clip = get_clip_under_playhead() |
|
new_clip.SetClipColor("Orange") |
|
extend_freeze_frame(new_clip,duration_seconds=1) |
|
|
|
print("Freeze Frame applied at the last frame of the clip.") |
|
else: |
|
print("No clip found under the playhead.") # Message if no clip is detected at the playhead |