Created
September 27, 2021 02:30
-
-
Save nin-jat/7946d50ca41b73d4102b438f7b45c2a9 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# This script content aware/steam carves frames from the provided video. | |
# It works by exploding each frame into a bmp. Passing each bmp through | |
# imgagemagick's convert-im6 program set to screw with each frame. | |
# The lastly, combine the frames back into a video with the audio from | |
# to source video file. | |
# As you can see, most of this script is inspired by what's found at | |
# https://gitgud.io/-/snippets/498, In-fact the ffprobe and last ffmpeg | |
# command was copied over. My version just adds some extra bits to | |
# improve my "meme" production. | |
# How many processes should we run until we wait for them to complete. | |
maxProcesses=18 | |
## === Prepare to do processing === | |
# Configure glob to return nothing if nothing is found. | |
shopt -s nullglob | |
# Get the filename from the 1st argument. | |
filename="${1%.*}" | |
# Prepare our directories for the frames. | |
mkdir ./frames | |
mkdir ./frames/"$filename" | |
mkdir ./frames/"$filename"/liquid | |
# Grab the FPS from the source video (1st arg.) as we need it to reconstruct | |
# the video at the end. | |
fps=$(ffprobe -v 0 -of csv=p=0 -select_streams v:0 -show_entries stream=r_frame_rate "$1") | |
# Strip the frames from the source video. | |
ffmpeg -i "$1" "frames/$filename/%06d.bmp" | |
# Cound the frames in the folder. | |
totalFrames=$(ls ./frames/"$filename"/*.bmp | wc -l) | |
# Get the size of the image. | |
size=$(identify -format "%[fx:w]x%[fx:h]" ./frames/"$filename"/000001.bmp) | |
## === Doing the processing === | |
i=1 | |
t=0 | |
for f in "./frames/$filename/"*.bmp; do | |
# Calculate how much scaling we do based on how far through the frames we are. | |
let "scale=512 - ($i * 340 / $totalFrames)" | |
# Make a filename to dump the new frame into. | |
frame_name=./frames/"$filename"/liquid/$(printf %06d $i).bmp | |
# The magick (ha get it) happens here. We run it in the background too. | |
convert-im6 "$f" -liquid-rescale "$scale"x"$scale" -resize $size\! "$frame_name" & | |
# Increment our frame "I"ncrement and "C"oncurrent processes counter. | |
((i++)) | |
((c++)) | |
# When our concurrent processes exceeds our limit, wait until the finish and | |
# reset our counter. | |
if (( $c > $maxProcesses )); then | |
echo "Processing batch $i/$totalFrames" | |
wait | |
c=0 | |
fi | |
done | |
# Hold up, wait a minute. | |
# Wait for any background processes to finish before we re combine the frames. | |
wait | |
# Convert the images into a video again and merge the audio from the source back in. | |
ffmpeg -framerate "$fps" -thread_queue_size 1024 -i ./frames/"$filename"/liquid/%06d.bmp -thread_queue_size 1024 -i "$1" -c:v libx264 -preset slow -crf 23 -pix_fmt yuv420p -map "0:v:0" -map "1:a:0?" -y "./liquid_$filename.mp4" | |
# Delete all the left over junk. | |
rm -rf ./frames/"$filename" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment