JScript .NET (174 characters)
A little-known programming language from Microsoft, it combines the (relative) terseness of JavaScript with the power of the .NET Common Language Runtime. Thanks minitech and Joey for Console.Beep.
This program accepts a single letter from standard input (A-Z or a-z only). It does not explicitly add intra-character pauses, but they do exist, at least on Windows 7.
morse.js
function S(a){K.Beep(750,!!(a&C)*99+50)}import System;var K=Console,C=1<<26-K.Read()%32,A=31313855&C,B=60257815&C;S(29932103);(A||B)&&S(34172681);A&&S(9538602);A&&B&&S(66070)
Compile with:
%SystemRoot%\Microsoft.NET\Framework\v4.0.30319\jsc morse.js
Explanation
Six 32-bit integers, of which 26 bits are used in each, serve as lookup tables. Each bit in a table corresponds to a letter of the alphabet, bit 25 used for A and bit 0 used for Z.
C = 1 << (26 - (K.Read() % 32)),
Because Morse code is a variable-length code that uses between 1 and 4 symbols for each letter, the tables 31313855 (bit 1) and 60257815 (bit 0) can together represent one less than the length of each letter's code.
A = 31313855 & C,
B = 60257815 & C;
The program uses additional lookup tables to store the dots and dashes for each letter. Using logic expressions of A and B, it stops once it has sent the correct number of symbols to the sound card.
S(29932103);
(A || B) && S(34172681);
A && S(9538602);
A && B && S(66070);
In each of the four lookup tables above, a zero represents a dot; a one represents a dash. !!
(logical "not-not") is used to normalize false to 0 and true to 1 (to compensate for the differing locations of bits within the integer). The multiplication and addition of this value causes a dot to be a 50 ms, 750 Hz tone and a dash to be a (50 + 99) = 149 ms tone.
function S(a) {
K.Beep(750, !!(a & C) * 99 + 50)
}