Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members | Related Pages

wvoggvorbis.h

Go to the documentation of this file.
00001 /* -*- Mode: C++ -*- 00002 * Worldvisions Weaver Software: 00003 * Copyright (C) 1997-2002 Net Integration Technologies, Inc. 00004 * 00005 * Provides a WvEncoder abstraction for Ogg vorbis files. 00006 * Only monaural audio is supported for now. 00007 */ 00008 #ifndef __WVOGGVORBIS_H 00009 #define __WVOGGVORBIS_H 00010 00011 #include "wvtypedencoder.h" 00012 #include "wvstringlist.h" 00013 #include <ogg/ogg.h> 00014 #include <vorbis/codec.h> 00015 #include <vorbis/vorbisenc.h> 00016 00017 /** 00018 * Encodes PCM audio using the Ogg Vorbis stream format. 00019 * 00020 * Input buffer must contain a sequence of signed 'float' type 00021 * values in machine order representing normalized PCM audio data. 00022 * 00023 * Outbut buffer will contain part of an Ogg bitstream. 00024 * 00025 */ 00026 class WvOggVorbisEncoder : 00027 public WvTypedEncoder<float, unsigned char> 00028 { 00029 public: 00030 static const long RANDOM_SERIALNO = 0; 00031 00032 /** 00033 * Bitrate specification. 00034 * 00035 * Identifies a particular bitrate control mechanism. 00036 * Use one of the subclasses to initialize a suitable BitrateSpec. 00037 * 00038 */ 00039 class BitrateSpec 00040 { 00041 friend class WvOggVorbisEncoder; 00042 protected: 00043 enum Mode { VBR_QUALITY, VBR_BITRATE }; 00044 Mode mode; 00045 float quality_index; 00046 long max_bitrate; 00047 long nominal_bitrate; 00048 long min_bitrate; 00049 00050 BitrateSpec(Mode mode) : mode(mode) { } 00051 public: 00052 // allow creation of uninitialized objects for later assignment 00053 BitrateSpec() { } 00054 }; 00055 00056 /** 00057 * Specifies a variable bitrate based on a quality index ranging 00058 * from 0.0 (low quality) to 1.0 (high quality). 00059 */ 00060 class VBRQuality : public BitrateSpec 00061 { 00062 public: 00063 /** 00064 * Creates a bitrate specification. 00065 * "quality" is the quality index 00066 */ 00067 VBRQuality(float quality) : BitrateSpec(VBR_QUALITY) 00068 { 00069 quality_index = quality; 00070 } 00071 }; 00072 00073 /** 00074 * Specifies a variable bitrate based on max, nominal, and min 00075 * bitrates specified in bits per second. 00076 */ 00077 class VBRBitrate : public BitrateSpec 00078 { 00079 public: 00080 /** 00081 * Creates a bitrate specification. 00082 * "nominal" is the nominal bitrate 00083 */ 00084 VBRBitrate(long nominal) : BitrateSpec(VBR_BITRATE) 00085 { 00086 max_bitrate = -1; 00087 nominal_bitrate = nominal; 00088 min_bitrate = -1; 00089 } 00090 /** 00091 * Creates a bitrate specification. 00092 * "max" is the maximum bitrate 00093 * "nominal" is the nominal bitrate 00094 * "min" is the minimum bitrate 00095 */ 00096 VBRBitrate(long max, long nominal, long min) : 00097 BitrateSpec(VBR_BITRATE) 00098 { 00099 max_bitrate = max; 00100 nominal_bitrate = nominal; 00101 min_bitrate = min; 00102 } 00103 }; 00104 00105 /** 00106 * Creates an Ogg Vorbis Encoder. 00107 * 00108 * The special constant RANDOM_SERIALNO may be specified as the 00109 * serial number to let the encoder choose one at random. The 00110 * implementation uses the rand() function and assumes that 00111 * the PRNG was previously seeded with srand(). 00112 * 00113 * "bitrate" is the bitrate specification 00114 * "samplingrate" is the number of samples per second 00115 * "channels" is number of channels (must be 1 for now), 00116 * defaults to 1 00117 * "serialno" is the Ogg bitstream serial number, 00118 * defaults to RANDOM_SERIALNO 00119 */ 00120 WvOggVorbisEncoder(const BitrateSpec &bitratespec, 00121 int samplingrate, int channels = 1, 00122 long serialno = RANDOM_SERIALNO); 00123 00124 virtual ~WvOggVorbisEncoder(); 00125 00126 /** 00127 * Adds a comment to the Ogg Vorbis stream. 00128 * 00129 * Do not call after the first invocation of encode(). 00130 * 00131 * "comment" is the comment 00132 */ 00133 void add_comment(WvStringParm comment); 00134 00135 /** 00136 * Adds a comment to the Ogg Vorbis stream. 00137 * 00138 * Do not call after the first invocation of encode(). 00139 * 00140 */ 00141 void add_comment(WVSTRING_FORMAT_DECL) 00142 { add_comment(WvString(WVSTRING_FORMAT_CALL)); } 00143 00144 /** 00145 * Adds a tag to the Ogg Vorbis stream. 00146 * 00147 * Ogg Vorbis tags are special comment strings of the form 00148 * "=" and are typically used to store artist, 00149 * date, and other simple string encoded metadata. 00150 * 00151 * Do not call after the first invocation of encode(). 00152 * 00153 * "tag" is the tag name 00154 * "value" is the value 00155 */ 00156 void add_tag(WvStringParm tag, WvStringParm value); 00157 00158 protected: 00159 virtual bool _typedencode(IBuffer &inbuf, OBuffer &outbuf, 00160 bool flush); 00161 virtual bool _typedfinish(OBuffer &outbuf); 00162 00163 private: 00164 ogg_stream_state *oggstream; 00165 vorbis_info *ovinfo; 00166 vorbis_comment *ovcomment; 00167 vorbis_dsp_state *ovdsp; 00168 vorbis_block *ovblock; 00169 bool wrote_header; 00170 00171 bool write_header(OBuffer &outbuf); 00172 bool write_stream(OBuffer &outbuf, bool flush = false); 00173 bool process_audio(OBuffer &outbuf); 00174 }; 00175 00176 00177 /** 00178 * Decodes PCM audio using the Ogg Vorbis stream format. 00179 * 00180 * Inbut buffer must contain part of an Ogg bitstream. 00181 * 00182 * Output buffer will contain a sequence of signed 'float' type 00183 * values in machine order representing normalized PCM audio data. 00184 * 00185 * If flush == false, then encode() will return true immediately 00186 * after isheaderok() becomes true without outputting any audio 00187 * data. This allows the client to examine the header and to 00188 * tailor the actual decoding process based on that information. 00189 * 00190 */ 00191 class WvOggVorbisDecoder : 00192 public WvTypedEncoder<unsigned char, float> 00193 { 00194 WvStringList comment_list; 00195 00196 public: 00197 /** 00198 * Creates a new Ogg Vorbis Decoder. 00199 * 00200 * For now, if the input bitstream is stereo, outputs the left 00201 * channel only. This behaviour may change later on. 00202 * 00203 */ 00204 WvOggVorbisDecoder(); 00205 virtual ~WvOggVorbisDecoder(); 00206 00207 /** 00208 * Returns true when the entire stream header has been processed 00209 * and the comments and vendor fields are valid. 00210 * 00211 * If false and isok(), try decoding more data. 00212 * 00213 * Returns: true when the header has been decoded 00214 */ 00215 bool isheaderok() const; 00216 00217 /** 00218 * Returns the Ogg Vorbis vendor comment string. 00219 * 00220 * Returns: the vendor comment 00221 */ 00222 WvString vendor() const 00223 { return ovcomment->vendor; } 00224 00225 /** 00226 * Returns the Ogg Vorbis list of user comments. 00227 * 00228 * The list is owned by the encoder, do not change. 00229 * 00230 * Returns: the list of comments 00231 */ 00232 WvStringList &comments() 00233 { return comment_list; } 00234 00235 /** 00236 * Returns the number of channels in the stream. 00237 * 00238 * Returns: the number of channels, non-negative 00239 */ 00240 int channels() const 00241 { return ovinfo->channels; } 00242 00243 /** 00244 * Returns the sampling rate of the stream. 00245 * 00246 * Returns: the sampling rate 00247 */ 00248 int samplingrate() const 00249 { return ovinfo->rate; } 00250 00251 protected: 00252 virtual bool _typedencode(IBuffer &inbuf, OBuffer &outbuf, 00253 bool flush); 00254 virtual bool _typedfinish(OBuffer &outbuf); 00255 00256 private: 00257 ogg_sync_state *oggsync; 00258 ogg_stream_state *oggstream; 00259 ogg_page *oggpage; 00260 vorbis_info *ovinfo; 00261 vorbis_comment *ovcomment; 00262 vorbis_dsp_state *ovdsp; 00263 vorbis_block *ovblock; 00264 bool need_serialno; 00265 int need_headers; 00266 00267 bool process_page(ogg_page *oggpage, OBuffer &outbuf); 00268 bool process_packet(ogg_packet *oggpacket, OBuffer &outbuf); 00269 bool prepare_dsp(); 00270 bool prepare_stream(long serialno); 00271 }; 00272 00273 #endif // __WVOGGVORBIS

Generated on Tue Oct 5 01:09:20 2004 for WvStreams by doxygen 1.3.7