Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions nextflow/configs/profiles/development.config
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,7 @@ singularity {

process {
executor = 'local'
maxForks = 1

// Since we can't assume local has multiple GPUs, we limit all tasks
// Note that maxForks attached to GPU label will only limit processes of the same name
Expand Down
81 changes: 81 additions & 0 deletions nextflow/modules/compression.nf
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
/**
* Video compression using quality control
*
* @param tuple
* - video_file The input video file to compress
* - crf The constant rate factor for the compression
* - keyframe_interval The keyframe interval for the compression
*
* @return file Path to compressed video
*/
process COMPRESS_VIDEO_CRF {
label "compression"

input:
tuple path(video_file), val(crf), val(keyframe_interval)

output:
path("${video_file.baseName}_g${keyframe_interval}_crf${crf}.mp4"), emit: file

script:
"""
ffmpeg -i ${video_file} -c:v libx264 -pix_fmt yuv420p -preset slow -crf ${crf} -g ${keyframe_interval} -f mp4 ${video_file.baseName}_g${keyframe_interval}_crf${crf}.mp4
"""
}

/**
* Video compression using bitrate control
*
* Runs a 2-pass encoding of the video with a target bitrate.
*
* @param tuple
* - video_file The input video file to compress
* - bitrate The target bitrate for the compression
* - keyframe_interval The keyframe interval for the compression
*
* @return file Path to compressed video
*
* @note COMPRESS_VIDEO_CRF will typically produce better videos with a low signal-to-noise ratio.
*/
process COMPRESS_VIDEO_BR {
label "compression"

input:
tuple path(video_file), val(bitrate), val(keyframe_interval)

output:
path("${video_file.baseName}_r${bitrate}_g${keyframe_interval}.mp4"), emit: file

script:
"""
ffmpeg -i ${video_file} -c:v libx264 -b:v ${bitrate}k -maxrate ${bitrate}k -bufsize \$((${bitrate}*2))k -g ${keyframe_interval} -pass 1 -f mp4 ${video_file.baseName}_r${bitrate}_g${keyframe_interval}_PASS1.mp4 && \
ffmpeg -i ${video_file.baseName}_r${bitrate}_g${keyframe_interval}_PASS1.mp4 -c:v libx264 -b:v ${bitrate}k -maxrate ${bitrate}k -bufsize \$((${bitrate}*2))k -g ${keyframe_interval} -pass 2 ${video_file.baseName}_r${bitrate}_g${keyframe_interval}.mp4 && \
rm ${video_file.baseName}_r${bitrate}_g${keyframe_interval}_PASS1.mp4 ffmpeg2pass-0.log ffmpeg2pass-0.log.mbtree

"""
}

/**
* Computes a difference between two videos
*
* @param in_video1 The first input video file
* @param in_video2 The second input video file
*
* @return The output video file with the computed difference
*
* @note Difference videos are useful in comparing changes due to compression.
*/
process COMPUTE_VIDEO_DIFFERENCE {
label "tracking"

input:
tuple path(in_video1), path(in_video2)

output:
path "${in_video2.baseName}_diff.mp4"

script:
"""
ffmpeg -i ${in_video1} -i ${in_video2} -filter_complex '[0:v]setsar=1:1[v1];[v1][1:v]blend=all_mode=difference128' -c:v mpeg4 -q 0 ${in_video2.baseName}_diff.mp4
"""
}
23 changes: 23 additions & 0 deletions nextflow/modules/pose_qc.nf
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
/**
* Render pose on video
*
* @param in_video The input video file
* @param in_pose The input pose file
*
* @return Rendered video
*/
process RENDER_POSE {
label "tracking"
publishDir "compressed/pose/", mode:'copy'

input:
tuple path(in_video), path(in_pose)

output:
path "${in_video.baseName}_pose.mp4"

script:
"""
python3 /kumar_lab_models/mouse-tracking-runtime/render_pose.py --in-vid ${in_video} --in-pose ${in_pose} --out-vid ${in_video.baseName}_pose.mp4
"""
}
7 changes: 7 additions & 0 deletions nextflow/workflows/multi_mouse_pipeline.nf
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ include { PREDICT_ARENA_CORNERS;
include { VIDEO_TO_POSE;
PUBLISH_RESULT_FILE as PUBLISH_MM_POSE_V6;
} from "${projectDir}/nextflow/modules/utils"
include { COMPRESS_VIDEO_CRF } from "${projectDir}/nextflow/modules/compression"

workflow MULTI_MOUSE_TRACKING {
take:
Expand All @@ -33,6 +34,12 @@ workflow MULTI_MOUSE_TRACKING {
}
PUBLISH_MM_POSE_V6(v_6_poses_renamed)

// Compress the original video
compressed_videos = COMPRESS_VIDEO_CRF(input_video.combine([23]).combine([3000]))
compressed_renamed = compressed_videos.map { video ->
tuple(video, "results/${video.baseName.replace("_g3000_crf23", "")}_compressed.mp4")
}

emit:
pose_v6
}