This simple set up is enough to record real-time summaries of each section directly onto videotape as you progress; no computer needed. After completing a working session, I hit record on the VCR and discuss what I just completed, then hit STOP.
The audio/video output of the VCR connects to the audio/video input of the [Hauppage] WinTV PCI video capture card in my computer. The computer continuously runs my custom timelapse video frame capture software. With the above wiring, the time-lapsed capturing can be easily paused without touching the computer by simply turning the VCR or camera off, thereby cutting off the video signal to the video capture card. I unplug my camera and turn the VCR off when I'm not working on the project to reduce any false frames.
The computer hardware is probably not critical. Mine is a 133 MHz [Intel] Pentium(R) Processor with 96 Megabytes of RAM. I have dedicated an entire 10.1 GB [IBM] Deskstar IDE hard disk drive to this project since it does require a lot of disk storage space. The operating system and everything else are on two smaller 1 GB and 2 GB SCSI disk drives. My hard disk drives are incrementally backed up onto an [HP] SCSI DAT tape drive automatically every night.
My [WinTV] frame grabber card is accessed by the excellent [BTTV] video4linux driver. I also run the way cool [xawtv] to set the card to grab from the video input and to preview what the camera is seeing.
After setting up, timelapse starts an infinite loop to run forever. The first thing it does in the loop is to sleep until it is time to examine the image for change. The time between images can be set on the command line and defaults to 60 seconds. Using a value of one will run the time-lapse capture as fast as possible.
When it is time to examine the image, timelapse runs a simple C program to capture a single frame from the video capture device to a latest.jpg file. This C program is called grabone.c and is a simplified subset of the webcam.c code that comes with xawtv.
The last saved image is now read in from disk. A copy of both images is then scaled to a smaller size. I currently use 1/16 scale or from 640x480 to 40x30. This effectively reduces the number of pixels that need to be examined; multiple pixels are averaged into one.
Next, the images are quantized from color to grayscale. Now each pixel is an 8-bit "brightness" value from 0 being black to 255 being white. The pixels of the current image are now added to come up with a total "brightness". This sum is divided by the total that a 100% white image would produce, to come up with a fraction of brightness. If this brightness is less than the configured darkness threshold, then timelapse assumes the lights are off or this picture too dark to keep. It is then dropped and the program goes back to the top of the loop.
Otherwise the picture is bright enough to consider for differences. So the program now does a composite difference of this picture and the last saved one. This basically replaces each pixel with its' difference. If the pixel did not change significantly, you get numbers near 0. If it did change, you get a number proportional to the difference. The result is a now a mostly black image with gray or white where there are differences. This can be seen in my static sample images.
Now, the pixels of this difference image are added together to come up with the amount of change. Again the sum is divided by the total that a white image would produce, to come up with a fraction of change. If this number is less than the difference threshold, the image is considered the same. It is then dropped the program goes back to the top of the loop.
Finally, if the image has passed the brightness and difference tests, then it is saved to disk. The original full-size frame is first saved as last.jpg to be used in comparison next time through the loop. A timestamp is formatted and annotated onto the image. The timestamp is also used to create a unique filename of YYYY/MM/DD/HHMM[SS].jpg and the full-size image with timestamp is written there. This is linked to final.jpg so that there is always easy access to the last final saved result. The image is also written at 1/2 scale 320x240 in .yuv format to simplify .mpg compression later.
As timelapse runs, it appends its' actions to a grab.log file. This records the timestamp of each frame saved and its' brightness and difference values on one line, separated by tab characters. When frames are skipped, their values are remembered and then written as one line just before a new frame is saved. This line contains up to 3 tab-delimited fields:
busynum darknum:min/mean/max<threshold samenum@min/mean/max<threshold
This compactly records the number of frames skipped for each reason and the minimum, mean average and maximum values compared to the threshold that caused the frame to be dropped. This allows for later analysis to determine if the thresholds are set correctly.
The busynum counts the number of frames that were not analyzed because the video capture device was busy. Since only one program can use the hardware device at a time, grabone.c fails if the device is busy. This happens for example when xawtv is being used. This turns out to be a Good Thing since xawtv may be used to watch TV. We don't want to record timelapse of random TV broadcasts! Also, it provides a convenient way to suspend the timelapse process. Simply run xawtv to prevent frames from being recorded by timelapse. Always remember to reset the card source to video input before exiting xawtv.
Distributed under the terms and conditions of the [GNU General Public License].