Thu Aug 20 12:29:19 PDT 2015

How to Make a Looping Photo VCD

Do you want to make a VCD that will display photographs on your DVD player? The following recipe is not elaborate. It doesn't deal with a sound track or with transition effects between images. However, if you want to share photographs using a DVD player and a television - this method is effective and - this is the simplest method that I could find. If you have suggestions for improvements, please let me know!

First, prepare a set of jpg files. It is convenient to do this with sequentially named files - because each jpg file will be turned into an mpg file, and the mpg files will be included in the VCD. Here is a short script which will name your jpg files IMG0001.jpg, IMG0002.jpg, etc. This script renames your existing jpg files in this directory (so work with copies of your photographs).

#!/bin/sh
count=1
BASE=IMG
for file in `ls -d *.jpg | sort -r`
do
  echo $file
  count=`expr $count + 1`
  PADDED=`printf "%04d" $count`
  name=$BASE$PADDED".jpg"
  mv -i $file $name
done

Having named the jpg files in a convenient way - we then need to insure that they are appropriately scaled. Again a short script comes in handy.

#!/bin/sh
for file in *.jpg
do
  echo $file
  jpegtopnm $file | pnmscale  -xysize 768 576 > tmp.pnm
  pnmtojpeg tmp.pnm > `basename $file .jpg`.scaled.jpg
done

Now your jpg files are appropriately named, and appropriately sized, the next step is to create a matching set of short mpg files. To do this we will make use of ffmpeg. Here is the script to achieve this.

#!/bin/sh
for file in IMG*.scaled.jpg
do
  echo $file
  count=0
  while true
  do
    count=`expr $count + 1`
    if [ $count -eq 21 ]
    then
      break
    fi
    cp $file tmp$count.jpg
  done
  ffmpeg -f image2 -i tmp%d.jpg -target ntsc-vcd `basename $file .test.jpg`.mpg
done

Now you need to create the 'selection' segments for the xml file that we will use to create the VCD image. Another script is needed. Note that here the number of images is 19 in the example that I used, and this means that there is an '18' in the script - you will probably need to change this for your files.

#!/bin/sh
#NB one less that the number of mpg's to be
#included as the vcd xml is zero based
max=18
count=0
while true
do
  thissec=`printf "%03d" $count`
  countp1=`expr $count + 1`
  nextlid=`printf "%03d" $countp1`
  sequeid=`printf "%02d" $count`
  if [ $count -eq $max ]
  then
     nextlid="000"
  fi
  cat <<!
      <selection id="lid-$thissec">
        <next ref="lid-$nextlid"/>
        <timeout ref="lid-$nextlid"/>
        <wait>5</wait>
        <play-item ref="sequence-$sequeid"/>
      </selection>
!
  count=`expr $count + 1`
  if [ $count -gt $max ]
  then
      break
  fi
done

This script will write to standard out a revised set of <selection> items to put into the xml file needed to create the VCD. Execute the command, capture its output to a file, and edit this file into the videocd.xml file created with the following command.

vcdxgen -t vcd2 IMG0002.mpg IMG0003.mpg

(include all the mpg files on the command line). Edit the selection sections into the resulting videocd.xml file - in the place of the playlist sections. Now you can create the VCD image and cue file with:

vcdxbuild videocd.xml

...and burn the resulting image with:

cdrdao write --device 1,0,0 --driver generic-mmc-raw --force --speed 4 videocd.cue

As noted in the introduction, this is not a fancy approach - but it makes nice simple photograph VCDs. In the future I may create a single script which does the work - and improve its error checking.


Posted by ZFS | Permanent link | File under: bash