Thanks Eric. I will look it over and study it.
Here is the finalized script, this time with a "--help" option. Many thanks again to Pavlos for his assistance it confirming the script's functionality.
---- edit ----
Added some specific command line examples in the help.
Added some control of the background for the timestamp text.
----- end of edit -----
Script "VIDEO__Record_LiveStreamWithTimeStamp.sh":
#!/bin/bash
####################################################################################################
###
### Script to simplify interraction with ffmpeg for recording from video stream
###
### AUTHOR: Eric Marceau, Ottawa, Canada
### Version: 3.1 2024-10-29
### License: GNU AGPLv3
###
###HELPSTART
### Command line options:
###
### --slices {count}
### --single [default if neither specified]
### These options are mutually exclusive.
### {count} is the number of equal-length video files the will be created.
### "--single" will force the entire recording as a one file only.
###
### --hours {hours}
### --minutes {minutes}
### These options are mutually exclusive.
### Specify the length of the total recording time in either {hours} or {minutes}.
### No fractional/decimal values permitted.
###
### --wait {minutes}
### This options tells the script to wait the specified {minutes} before starting the recording.
###
### --label_hms [default if neither specified]
### --label_int
### These options are mutually exclusive.
### "--label_hms" will add start time of recording to filenames
### using the format specifier '%Y%m%d_%H%M%S'.
### "--label_int" will add start time of recording to filenames
### using the format specifier '%Y%m%d_%H%M'_##m.
###
### --label {string} [if not specified, default value is 'vidrecord']
### This allows the custom specification of a prefix string for the video files.
### When defining this, note that one of the options "--label_int" or "--label_hms"
### already includes one of the two pre-defined "date and time"
### modifier strings for filename.
### filename={string}_{modifierstring}.mp4
###
### --posn { "ul" | "ur" | "ll" | "lr" } [ "ul" is default position ]
### This specifies the placement of the timestamp string at one of the
### 4 corners of the video window
### ul => upper left
### ur => upper right
### ll => lower left
### lr => lower right
###
### --dark
### --light
### These options are mutually exclusive.
### Selection of background for timestamp text.
### "--black" specified white text on black background.
### "--light" specified black text on white background.
###
### Examples:
###
### VIDEO__Record_LiveStreamWithTimeStamp.sh --single --minutes 120 --label_int
###
### Starting capture of video stream for next 120 minutes as:
### -> vidrecord_20241024_1741_120m.mp4
###
###
### VIDEO__Record_LiveStreamWithTimeStamp.sh --slices 6 --hours 2 --label_hms
###
### Starting capture of video stream for next 20 minutes as:
### -> vidrecord_20241024_181047.mp4
###
###
### VIDEO__Record_LiveStreamWithTimeStamp.sh --single --minutes 120 --label_int --label myvid --wait 2
###
### WAITING 2 minute(s) before proceed with video recording ...
### Starting capture of video stream for next 120 minutes as:
### -> myvid_20241027_1725_120m.mp4
###
### REF: https://askubuntu.com/a/428501
### REF: https://ubuntu-mate.community/t/cheese-recording-not-showing-landlord-coming-into-my-trailer-for-repair/28390/9
###HELPEND
###
### FUTURES:
### * systemd service
### * option to specify video repository directory
### * option to specify purging old videos by age
###
####################################################################################################
show_help()
{
awk 'BEGIN{
doPrint=0 ;
}{
if( $1 ~ /###HELPEND/ ){
doPrint=0 ;
} ;
if( doPrint == 1 ){
gsub(/^###/, "", $0 ) ;
print $0 ;
} ;
if( $1 ~ /###HELPSTART/ ){
doPrint=1 ;
} ;
}' <$0
}
####################################################################################################
recordSegment()
{
###
### Options used in REF which were not used by Pavlos in his response demo
###
# -f video4linux2 \
# -s 640x480 \
# -r 30 \
# -vcodec libx264 \
# -vb 2000k \
ffmpeg \
-i /dev/video0 \
-preset ultrafast \
${segInterval} \
-vf "${textOverlayParameters}" \
-f mp4 "${videoFile}"
}
####################################################################################################
recordSlice()
{
videoFile="${videoFilePref}_${sliceStart}.mp4"
printf "\n\t Starting capture of video stream for next ${sliceMax} minutes as:\n\t -> ${videoFile}\n"
recordSegment
}
specify_timestamp()
{
####################################################################################################
###
### 'drawtext' Option Specifications for TimeStamp Placement and Styling
###
col_light="[email protected]"
col_dark="black"
case ${dark} in
1) txt="${col_light}"
bkg="${col_dark}"
;;
2) txt="${col_dark}"
bkg="${col_light}"
;;
esac
###
### Specifying Background Attributes
###
bkgd_toggle="box=1"
bkgd_color="boxcolor=${bkg}"
bkgd_margin="boxborderw=5"
###
### Specifying Timestamp Attributes
###
#fontSpec="fontfile=DejaVuSans-Bold.ttf"
size=14
fontSize="fontsize=${size}"
fontSpec="fontfile=FreeMono.ttf"
fontClr="fontcolor=${txt}"
###
### Specifying Text Position
###
### coordinates specify the upper left corner of the text string's position
### x=0,y=0 at upper left corner of video
margin=7
case "${locn}" in
"ul" )
### default
timePosn="x=${margin}:y=${margin}"
;;
"ll" )
### option for bottom left corner
timePosn="x=${margin}:y=(h-text_h-${margin})"
;;
"ur" )
### option for upper right corner
timePosn="x=(w-text_w-${margin}):y=${margin}"
;;
"lr" )
### option for bottom right corner
timePosn="x=(w-text_w-${margin}):y=(h-text_h-${margin})"
;;
* ) printf "\n\t Invalid parameter used on command line. \n\t Only valid options for "--posn" : ul | bl | ur | br \n Bye!\n\n" ; exit 1
esac
#timeFmt="text='\\%T'"
timeFmt="text='\\%{localtime}'"
textOverlayParameters="drawtext=${bkgd_toggle}:${bkgd_color}:${bkgd_margin}:${fontSpec}:${timeFmt}:${fontClr}:${timePosn}"
#echo ${textOverlayParameters}
#exit
}
####################################################################################################
locn="ll"
mode=1
timeTot=0
timeWait=0
count=0
label=0
dark=1
videoFilePref="vidrecord"
sliceMax=0
while [ $# -gt 0 ]
do
case "${1}" in
"--help" )
show_help
exit 0
;;
"--single" )
mode=1
shift
;;
"--dark" )
dark=1
shift
;;
"--light" )
dark=0
shift
;;
"--slices" )
### number of recording slices to cover specified duration
mode=2
slices="${2}"
shift ; shift
;;
"--hours" )
### total recording time [ units in hours ]
timeTot=$( expr ${2} \* 60 )
count=1
shift ; shift
;;
"--minutes" )
### total recording time [ units in minutes ]
timeTot="${2}"
count=1
shift ; shift
;;
"--wait" )
### wait time before start [ units in minutes ]
timeWait="${2}"
shift ; shift
;;
"--label" )
videoFilePref="${2}"
shift ; shift
;;
"--label_int" )
label=1
shift
;;
"--label_hms" )
label=0
shift
;;
"--posn" )
locn="${2}"
shift ; shift
;;
* ) printf "\n\t Invalid parameter used on command line. \n\t Only valid options: [ --single | --slices {count} ] [ --hours {hours} | --minutes {minutes} ] [ --wait {minutes} ] [ --label {string} ] [ --label_int | --label_hms ] [ --posn [ ul | ur | ll | lr ] ] \n Bye!\n\n" ; exit 1
esac
done
specify_timestamp
####################################################################################################
if [ ${mode} -eq 1 ]
then
test ${timeTot} -eq 0 && { printf "\n\t ERROR: Need to specify total record time with one of '--hours {hours}' or '--minutes' {minutes} options.\n Bye!\n\n" ; exit 1 ; }
if [ ${timeWait} -gt 0 ]
then
printf "\n\t WAITING ${timeWait} minute(s) before proceed with video recording ...\n\n"
hTime=$( expr ${timeWait} \* 60 )
sleep ${hTime}
fi
#sliceMax=$( expr ${timeTot} \* 60 )
sliceMax=${timeTot}
segInterval="-t $( expr ${sliceMax} \* 60 )"
if [ ${label} -eq 1 ]
then
sliceStart="$(date '+%Y%m%d_%H%M' )_${sliceMax}m"
else
sliceStart=$(date '+%Y%m%d_%H%M%S' )
fi
recordSlice
exit
fi
if [ ${mode} -eq 2 ]
then
test ${timeTot} -eq 0 && { printf "\n\t ERROR: Need to specify total record time with '--duration {hours}' option.\n Bye!\n\n" ; exit 1 ; }
if [ ${timeWait} -gt 0 ]
then
printf "\n\t WAITING ${timeWait} minute(s) before proceed with video recording ...\n\n"
hTime=$( expr ${timeWait} \* 60 )
sleep ${hTime}
fi
#duration=$( expr ${timeTot} \* 60 )
duration=${timeTot}
sliceMax=$( expr ${duration} / ${slices} )
segInterval="-t $( expr ${sliceMax} \* 60 )"
indx=0
while [ ${indx} -lt ${slices} ]
do
if [ ${label} -eq 1 ]
then
sliceStart="$(date '+%Y%m%d_%H%M' )_${sliceMax}m"
else
sliceStart=$(date '+%Y%m%d_%H%M%S' )
fi
recordSlice
indx=$( expr ${indx} + 1 )
done
exit
fi
exit
Script looks good, I really like it !
I think I will need that, is that information stored in the mp4 itself ?
I think it is meta data.
I got a video today for court use. It shows an unrestrained dog about 50 yards from the owners residence.
I would like the time date info to be able to nail when the video was taken.
Thanks.
Newest
The video shows the time date only on the original.
I wanted to shrink it to send to my lawyer.
If the date/time timestamp is not a visible part of the recording, your untampered file needs to remain on your disk until appropriate authorities come to claim the file, verifying to their satisfaction that the filesystem and file have not been tampered with. That is called protecting the chain of evidence.
Because that is near impossible, people use security systems that incorporate that date/time timestamp in the video of itself. Hence the reason that I incorporated the following enhancements in my latest version, posted 5 days ago:
- ability to specify number of recordings (--slices option) to cover the specified total recording time (thereby ensuring per your choice, for your context, each recorded segment will be small enough and manageable enough), and
- ability to specify the "--dark" or "--light" options for ensuring the date/time timestamp is always legible on a uniform and constant background colour.
The original script had the timestamp over the actual video stream, which should have been visible for the entire recording. So you should have at least that. If you don't, I can explain why.
However, depending on the background colour provided by the video stream itself near the location of that timestamp, it could, in the worst case, have minimal to no contrast, which is not legible, hence the changes I made to guarantee that it would always be legible.
So, worst case, you would need to make another recording (or rather another set or recordings) using the --slice option with a value of possibly 40 over a period of 10 hours, making each segment cover 15 minutes.
I just discovered the "-timestamp" option for ffmpeg on the documentation page.
You might also want to look at this response on StackExchange for some discussion on that.
I don't have time to go further with this right now. Sorry.
UM help
I used this to shrink a file so it could be sent as a attachment.
ffmpeg -i *.mp4 -s hd480 -strict -2 output.mp4
I have sent the video to my attorney.
It will be argued in court that someone could have avoided a dog.
The video from today contains another dog which is illegally unrestrained.
The dog is about 50 yards from the owners house.
It has the time date stamp in the video. So it is admissable.
That proves the owner of the dog is again willfully breaking the law.
When I lived there, I took walks to see the deer and nature.
I had a good day.
For some UM help.
I think that you would have a much stronger legal case if you have different recordings on multiple days, showing a habitual pattern of disregard for laws.
A single recording is always written off as a blip and "accidental oversight", and owners usually get off, and courts give benefit of doubt.
----- edit -----
I looked into it further and " -timestamp" is not the mechanism for obtaining a proper timestamp in the file's metadata. There is a different approach required, using the "-metadata" options.
You can download the updated script that does that correctly from my GitHub account. The link for the updated file is this.
These are the changes:
Added logic for --storage option, to specify full path to video output repository.
Added logic for --test option, to generate test-pattern video showing timestamp as specified.
Added logic for --purge option, to safely purge all videos older than a specified age in days.
Added logic for FFMPEG -metadata options, to correctly embed creation_date value in the video file's metadata.
Changed default setting to provide uniformly light-coloured background for the in-stream live timestamp.
That is my baseline version of the script, which I don't plan on modifying any further, since it accomplishes everything that I see as necessary.
Hey Eric.
I now have 2 recordings of unrestrained dogs.
We can talk more in PM.
I could use help with this.
https://www.youtube.com/watch?v=yeafFw9Ad-8&ab_channel=RickyAdames
When it gets to about 20 seconds into it I ran into difficulties.
I got the first edge of the panel of the panel off.
I dare not go any furthur because it becomes much more difficult.
I could use any suggessions as to how to get that panel off.
thanks.