What you will need

A DVD drive

This is not the place to get into an in depth discussion of what vendor/model, to go for, but suffice it to say that it must operate at a reasonable speed, and be compatible with Linux. Distrubtions may supply lists of supported players; if not there is ample documentation on the web suggesting good choices.

There are other ripping methods I have seen that require the disk to be mounted, and that brings with it various configuration issues, but the steps outlined below should work so long as you can read from the drive.
Just in case you have problems, here is the relevant line from my /etc/fstab

/dev/scd1  /mount/dvd  udf defaults,ro,user,noauto  0  0

MPlayer

http://www.mplayerhq.hu/

MPlayer is primarily distributed as source code, although RPMs are also available, as well as various unlicensed pre-compiled packages. Not only can it be used to watch DVDs, it includes MEncoder; the programme we will be using to do the ripping.

Full documentation can be found on the website, and it's worth a read, as it is unlikely to be a straight

./configure
make
make install

if you want a GUI, optimized compilation or non-standard codecs. It's worth the effort of compiling, however: I've yet to find a file MPlayer can't deal with.

libmp3lame

This will be used to encode the audio in the examples below. If you find it hard to find/install, you can use another codec of your choice, such as Ogg Vorbis. Doing so will mean you will need to make minor changes to commands, but everything said here should still be relevant.

The Ripping

Preliminaries

There are three pieces of information you need before starting to rip.

  1. The chapter you want to rip
  2. The length of that chapter
  3. The sound level of the chapter; too quiet?

To find out which chapter you want, issue the command:

    $ mplayer dvd://n -osdlevel 3

Where n is an integer. Start at n=1 and work up till you find the one you want (most films' main feature is chapter one).

To find the length of the chapter is simple - after issuing the above command, look at the time remaining part of the on screen display (OSD). If it looks like this: 00:00:05 / 1:09:10, the chapter lasts sixty-nine and a bit minutes.

Creating the ripping command

To work out the final quality of the rip, you can either work it out with the formula:

    rate=(MAX_SIZE - 128*t) / t

where rate is the video rate in kBits/sec, MAX_SIZE is the final size of the rip in kBytes and t is the length of the chapter in seconds.

OR

You can use the amateurish Perl script given at the end which does it all (and more) for you.

Manual ripping (without the script)

The ripping itself takes only one shell command. Certain formats might require special attention and odd command-line switches, for which you will have to look at the MEncoder man page, but this command (as output by my Perl script) should work in most situations:

mencoder dvd://1 -ovc lavc \
-lavcopts vcodec=mpeg4:vhq:vbitrate=qual \
-vop scale -zoom -xy 640  -oac mp3lame -lameopts \
abr:br=128 -o output_name.avi

Where qual should be replaced with the video rate value you got from the above formula.

There may be a few extra parameters that need adjusting before the output from the command is up to scratch. See below.

With the script

Copy, paste and save the Perl script given below as an executable file:

~$ dvd-rip.pl 
--==(DVD-rip quality calculator)==--

Length of DVD in minutes: 70
DVD chapter to rip: 1
File name to be output: my_backup.avi
Estimated final size: 697200 kBytes

mencoder dvd://1 -ovc lavc
  -lavcopts vcodec=mpeg4:vhq:vbitrate=1200
  -vop scale -zoom -xy 640 -oac mp3lame
  -lameopts abr:br=128 -o my_backup.avi

A command will be output that should work in most cases. However, you should run a test rip to see if all your requirements have been met before committing to a final, full rip. You can issue the output command and interrupt it at any time with Ctrl-C - watch back the video output so far and adjust parameters as discussed below in order to perfect the rip.

Tweaking the command

Using nice

You can adjust the priority of the ripping process by using nice or renice.

 ~$ nice -+19 mencoder ...

Would start MEncoder as a very low priority process, meaning you hardly notice it. If you want the ripping done as soon as possible, however, and have already started MEncoder, use

 ~# renice -20 $(pidof mencoder)

Adjusting the volume

On some DVDs, the sound level is very low. You can rectify this when ripping by adding

    :vol=vol

on to the end of the -lameopts section. For example, -lameopts abr:br=128:vol=7. The number should be between 0 and 10, ten being the loudest. To get the volume right, start the ripping with a test volume level, cancel it with Ctrl-C, play it back and adjust the volume level if required.

Other options

There are loads more options, most of which you will only need in exceptional circumstances. Some of the more useful are -sid to choose what subtitles you want, -crop to get rid of excess black space, -aspect if for some reason MEncoder does not properly recognise the dimensions of the picture and -endpos and -ss if you only want to rip part of a chapter.


Here's the Perl script I mention above. I'm no Perl hacker, please let me know about any mistakes, inelegancies or inefficiencies.

#!/usr/bin/perl -w

use POSIX("floor");

# Size of CDs (80min) in kBits
$MAX_SIZE=5600000;

print "--==(DVD-rip quality calculator)==--\n\n";

# Some DVD-specific info
print "Length of DVD in minutes: ";
$minutes=<STDIN>;
chop $minutes;

# Two or three digit number for length
while($minutes !~ /^[1-9][0-9]{1,2}$/) {
    print "Invalid length. Please enter number between 10 and 999: ";
    $minutes=<STDIN>;
    chop $minutes;
}

print "DVD chapter to rip: ";
$chapter=<STDIN>;
chop $chapter;

# One or two digit number for the chapter
while($chapter !~ /^[1-9][0-9]?$/) {
    print "Invalid chapter. Please enter number between 1 and 99: ";
    $chapter=<STDIN>;
    chop $chapter;
}

print "File name to be output: ";
$name=<STDIN>;
chop $name;

# Convert length in minutes into length in seconds
$seconds=$minutes*60;

# Calculate audio size in kBits
# Audio is at 128kBits/s
$audioSize=128*$seconds;

# Calculate room left for video in kBits
$videoSize=$MAX_SIZE-$audioSize;

# Rate of video (in kBits/sec)
$videoRate=floor($videoSize/$seconds);
$videoRate-=(5+$videoRate%5);

# Check resulting size
$overallSize=($audioSize+$videoRate*$seconds)/8;
print "Estimated final size: $overallSize kBytes\n";

# Output final command
print "\nmencoder dvd://$chapter -ovc lavc \\\
-lavcopts vcodec=mpeg4:vhq:vbitrate=$videoRate \\\
-vop scale -zoom -xy 640 -oac mp3lame \\\
-lameopts abr:br=128 -o $name\n";