Codec library

scenario4.svg

The Java standard library has support for few audio formats, but lacks some, for instance the popular FLAC format. The Klipspringer codec library1 is a subset of the Klipspringer software that can add support for FLAC and other formats to your Java projects. It currently supports:

  • FLAC and Ogg FLAC, for both decoding and encoding, through the official libFLAC API;
  • Ogg Vorbis (.ogg), for both decoding and encoding, throgh official Ogg Vorbis APIs;
  • Ogg Opus (.opus), for decoding only, through the opusfile API;
  • MP3, for encoding only, through the LAME API;
  • and has its own WAV handling for both decoding and encoding. (WAV is also supported by the standard Java sound system, but it can be more efficient to use the Klipspringer classes.)

In addition, the codec library includes classes for accessing ALSA devices directly (which is probably only relevant on Linux systems).

The Java classes work by making native calls to the respective APIs (except WAV, which is pure Java code), so the API libraries need to be put on your system in addition to the Klipspringer codec library for the formats to work. You also need to have a C compiler for preparing the native code part for your system, and obviously a JDK (Java Development Kit).

Like the rest of Klipspringer, the codec library is free software (GPL3 or later).

Download and prepare

Download the latest Klipspringer FLAC tarball and unpack it:

tar xfz klipspringer-codec-4.3.2.tar.gz
cd klipspringer-codec-4.3.2

The Klipspringer classes you need are in lib/klipcodec.jar, but you also need a native library file to be built for your system with:

./configure
make

The ./configure step warns if it has any problems locating the files for the API libraries supported. Only the parts that you are interested in using need to work, you can ignore warnings about others. If needed, follow the instructions for how to prepare

Then run ./configure) again.

After successful make, the lib subdirectory contains the two files you need to include in your projects: klipcodec.jar and a libklip dynamic library file whose exact name depends on the naming convention of your system. (The library file for the the full Klipspringer platform gets the same name but contains more than just the codec library code.) You can move the lib directory (and rename it if you’d like) to a suitable place.

You now hace two choices for how to incorporate FLAC, Ogg Vorbis, or Opus decoding in your project: through Java service provider interfaces or by Klipspringer’s own API. For encoding, Klipspringer’s own API needs to be used.

Using Java service provider interface (SPI)

Through SPI, decoding capability is injected into the standard Java sound system, which lets you use the standard Java sound API, without learning any of the Klipspringer interfaces, for decoding the FLAC, Ogg Vorbis, and Opus formats. It’s probably the most convenient option if it works for you, but potentially less powerful and efficient than directly interfacing with the Klipspringer classes.

Your code can read FLAC, Ogg FLAC (.oga), Ogg Vorbis (.ogg), and Ogg Opus (.opus) files exactly like it would files in the formats Java supports natively. Like this, for instance:

import java.io.File;
import javax.sound.sampled.*;

class TrySPI {
    public static void main(String[] args) throws Exception {
        AudioInputStream stream = AudioSystem
            .getAudioInputStream(new File("audio_to_play.flac"));
        SourceDataLine line = AudioSystem.getSourceDataLine(stream.getFormat());
        line.open();
        line.start();
        byte[] b = new byte[1024 * stream.getFormat().getFrameSize()];
        while (true) {
            int n = stream.read(b);
            if (n < 0) { break; }
            line.write(b, 0, n);
        }
        line.drain();
    }
}

This program can be compiled without any special options (javac TrySPI.java if you are running from the command line), but when you run it, you need to have the lib/klipcodec.jar file in your class path, and the lib directory (which contains the dynamic library file) in your java.library.path. Something like this from the command line:

java -cp .:klipspringer-codec-4.3.2/lib/klipcodec.jar -Djava.library.path=klipspringer-codec-4.3.2/lib TrySPI

This should play the file audio_to_play.flac (which you have to supply yourself) on the default audio output of your computer.

Using the Klipspringer codec API

Klipspringer uses its own audio codec API, which is designed to be integrated with the standard Java sound API, but has its own classes and interfaces for accomplishing everything that the Klipspringer platform does as efficiently as possible. In addition to decoding files, it has components for streaming audio to a channel, and its I/O operations make use of NIO direct buffers. Decoding of any format supported by the standard Java sound system (such as AIFF) can be wrapped as a Klipspringer AudioDecoder by AudioInputStreamDecoder for convenience.

For an introduction to the Klipspringer audio decoding API, you can read the FlacDecoder usage section in the blog post about FLAC files and decoding. Also take a look at FlacDecodeFile, a simple example program that reads a FLAC file and writes decoded PCM data as a WAV file, included in the examples directory in the Klipspringer codec tarball. You need to have lib/klipcodec.jar in your class path during compilation, and during execution you also need to have the lib directory (which contains the libklip dynamic library file) in your java.library.path. For instance like this from the command line:

javac -cp examples:lib/klipcodec.jar examples/FlacPlayFile.java
java -cp examples:lib/klipcodec.jar -Djava.library.path=lib FlacPlayFile your_audio_file.flac

You can get more information from examining the other files in the examples directory and by referring to the Klipspringer codec API documentation (Javadoc), which is included in the tarball as well as available on the web.

Direct ALSA access

If you are on a system with ALSA support (most Linux systems but not many others), and have the ALSA API properly set up, you may want to bypass the standard Java sound API completely, and use net.avadeaux.klipspringer.alsa.Alsa to access audio devices instead.

See examples/AlsaFlacPlayFile.java for an example of direct ALSA output.

Getting pictures from FLAC metadata

The Klipspringer codec library also has support for getting pictures from FLAC metadata.

Notes

  1. formerly the Klipspringer FLAC library