PTLib  Version 2.12.9
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
pwavfile.h
Go to the documentation of this file.
1 /*
2  * pwavfile.h
3  *
4  * WAV file I/O channel class.
5  *
6  * Portable Tools Library
7  *
8  * Copyright (c) 2001 Equivalence Pty. Ltd.
9  *
10  * The contents of this file are subject to the Mozilla Public License
11  * Version 1.0 (the "License"); you may not use this file except in
12  * compliance with the License. You may obtain a copy of the License at
13  * http://www.mozilla.org/MPL/
14  *
15  * Software distributed under the License is distributed on an "AS IS"
16  * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
17  * the License for the specific language governing rights and limitations
18  * under the License.
19  *
20  * The Original Code is Portable Windows Library.
21  *
22  * The Initial Developer of the Original Code is
23  * Roger Hardiman <roger@freebsd.org>
24  * and Shawn Pai-Hsiang Hsiao <shawn@eecs.harvard.edu>
25  *
26  * All Rights Reserved.
27  *
28  * Contributor(s): ______________________________________.
29  *
30  * $Revision: 27140 $
31  * $Author: rjongbloed $
32  * $Date: 2012-03-07 14:53:56 +1100 (Wed, 07 Mar 2012) $
33  */
34 
35 #ifndef PTLIB_PWAVFILE_H
36 #define PTLIB_PWAVFILE_H
37 
38 //#ifdef P_USE_PRAGMA
39 //#pragma interface
40 //#endif
41 
42 #include <ptbuildopts.h>
43 
44 #ifdef P_WAVFILE
45 
46 #include <ptlib/pfactory.h>
47 
48 class PWAVFile;
49 
50 namespace PWAV {
51 
52  struct ChunkHeader
53  {
54  char tag[4];
55  P_PACK_FIELD(PInt32l len);
56  };
57 
58  struct RIFFChunkHeader
59  {
60  ChunkHeader hdr;
61  char tag[4];
62  };
63 
64  struct FMTChunk
65  {
66  ChunkHeader hdr;
67  P_PACK_FIELD(PUInt16l format);
68  P_PACK_FIELD(PUInt16l numChannels);
69  P_PACK_FIELD(PUInt32l sampleRate);
70  P_PACK_FIELD(PUInt32l bytesPerSec);
71  P_PACK_FIELD(PUInt16l bytesPerSample);
72  P_PACK_FIELD(PUInt16l bitsPerSample);
73  };
74 
75 }; // namespace PWAV
76 
77 
80 class PWAVFileFormat
81 {
82 public:
83  virtual ~PWAVFileFormat() { }
84 
87  virtual unsigned GetFormat() const = 0;
88 
91  virtual PString GetFormatString() const = 0;
92 
95  virtual PString GetDescription() const = 0;
96 
98  virtual bool CanSetChannels(unsigned channels) const = 0;
99 
102  virtual void CreateHeader(PWAV::FMTChunk & header, PBYTEArray & extendedHeader) = 0;
103 
106  virtual void UpdateHeader(PWAV::FMTChunk & /*header*/, PBYTEArray & /*extendedHeader*/)
107  { }
108 
111  virtual PBoolean WriteExtraChunks(PWAVFile & /*file*/)
112  { return true; }
113 
116  virtual PBoolean ReadExtraChunks(PWAVFile & /*file*/)
117  { return true; }
118 
121  virtual void OnStart()
122  { }
123 
126  virtual void OnStop()
127  { }
128 
131  virtual PBoolean Read(PWAVFile & file, void * buf, PINDEX & len);
132 
135  virtual PBoolean Write(PWAVFile & file, const void * buf, PINDEX & len);
136 };
137 
138 typedef PFactory<PWAVFileFormat, PCaselessString> PWAVFileFormatByFormatFactory;
139 typedef PFactory<PWAVFileFormat, unsigned> PWAVFileFormatByIDFactory;
140 
141 PFACTORY_LOAD(PWAVFileFormatPCM);
142 
143 
146 class PWAVFileConverter
147 {
148 public:
149  virtual ~PWAVFileConverter() { }
150  virtual unsigned GetFormat (const PWAVFile & file) const = 0;
151  virtual off_t GetPosition (const PWAVFile & file) const = 0;
152  virtual PBoolean SetPosition (PWAVFile & file, off_t pos, PFile::FilePositionOrigin origin) = 0;
153  virtual unsigned GetSampleSize(const PWAVFile & file) const = 0;
154  virtual off_t GetDataLength (PWAVFile & file) = 0;
155  virtual PBoolean Read (PWAVFile & file, void * buf, PINDEX len) = 0;
156  virtual PBoolean Write (PWAVFile & file, const void * buf, PINDEX len) = 0;
157 };
158 
159 typedef PFactory<PWAVFileConverter, unsigned> PWAVFileConverterFactory;
160 
163 class PWAVFile : public PFile
164 {
165  PCLASSINFO(PWAVFile, PFile);
166 
167 public:
173  enum WaveType {
174  fmt_PCM = 1,
175  fmt_MSADPCM = 2,
176  fmt_ALaw = 6,
177  fmt_uLaw = 7,
178  fmt_VOXADPCM = 0x10,
179  fmt_IMAADPCM = 0x11,
180  fmt_GSM = 0x31,
181  fmt_G728 = 0x41,
182  fmt_G723 = 0x42,
183  fmt_MSG7231 = 0x42,
184  fmt_G726 = 0x64,
185  fmt_G722 = 0x65,
186  fmt_G729 = 0x83,
187  fmt_VivoG7231 = 0x111,
188 
189  // For backward compatibility
190  PCM_WavFile = fmt_PCM,
191  G7231_WavFile = fmt_VivoG7231,
192 
193  // allow opening files without knowing the format
194  fmt_NotKnown = 0x10000
195  };
196 
206  PWAVFile(
207  unsigned format = fmt_PCM
208  );
209 
222  PWAVFile(
223  OpenMode mode,
224  OpenOptions opts = ModeDefault,
225  unsigned format = fmt_PCM
226  );
227 
237  PWAVFile(
238  const PFilePath & name,
239  OpenMode mode = ReadWrite,
240  OpenOptions opts = ModeDefault,
241  unsigned format = fmt_PCM
242  );
243 
244  PWAVFile(
245  const PString & format,
246  const PFilePath & name,
247  OpenMode mode = ReadWrite,
248  OpenOptions opts = ModeDefault
249  );
250 
253  ~PWAVFile();
255 
265  virtual PBoolean Read(
266  void * buf,
267  PINDEX len
268  );
269 
277  virtual PBoolean Write(
278  const void * buf,
279  PINDEX len
280  );
281 
294  virtual PBoolean Open(
295  OpenMode mode = ReadWrite,
296  OpenOptions opts = ModeDefault
297  );
298 
312  virtual PBoolean Open(
313  const PFilePath & name,
314  OpenMode mode = ReadWrite,
315  OpenOptions opts = ModeDefault
316  );
317 
323  virtual PBoolean Close();
324 
339  virtual PBoolean SetPosition(
340  off_t pos,
341  FilePositionOrigin origin = Start
342  );
343 
351  virtual off_t GetPosition() const;
353 
358  virtual PBoolean SetFormat(unsigned fmt);
359  virtual PBoolean SetFormat(const PString & format);
360 
363  virtual unsigned GetFormat() const;
364  virtual PString GetFormatAsString() const;
365 
369  virtual unsigned GetChannels() const;
370  virtual void SetChannels(unsigned v);
371 
374  virtual unsigned GetSampleRate() const;
375  virtual void SetSampleRate(unsigned v);
376 
379  virtual unsigned GetSampleSize() const;
380  virtual void SetSampleSize(unsigned v);
381 
384  virtual unsigned GetBytesPerSecond() const;
385  virtual void SetBytesPerSecond(unsigned v);
386 
389  off_t GetHeaderLength() const;
390 
393  virtual off_t GetDataLength();
394 
401  PBoolean IsValid() const { return isValidWAV; }
402 
405  PString GetFormatString() const
406  { if (formatHandler == NULL) return PString("N/A"); else return formatHandler->GetFormatString(); }
407 
410  void SetAutoconvert();
411 
413 
414  PBoolean RawRead(void * buf, PINDEX len);
415  PBoolean RawWrite(const void * buf, PINDEX len);
416 
417  PBoolean FileRead(void * buf, PINDEX len);
418  PBoolean FileWrite(const void * buf, PINDEX len);
419 
420  off_t RawGetPosition() const;
421  PBoolean RawSetPosition(off_t pos, FilePositionOrigin origin);
422  off_t RawGetDataLength();
423 
424  void SetLastReadCount(PINDEX v) { lastReadCount = v; }
425  void SetLastWriteCount(PINDEX v) { lastWriteCount = v; }
426 
427  // Restored for backward compatibility reasons
428  static PWAVFile * format(const PString & format);
429  static PWAVFile * format(const PString & format, OpenMode mode, OpenOptions opts = ModeDefault);
430 
431 
432 protected:
433  void Construct();
434  bool SelectFormat(unsigned fmt);
435  bool SelectFormat(const PString & format);
436 
437  PBoolean ProcessHeader();
438  PBoolean GenerateHeader();
439  PBoolean UpdateHeader();
440 
441  PBYTEArray wavHeaderData;
442  PWAV::FMTChunk wavFmtChunk;
443  PBYTEArray extendedHeader;
444 
445  bool isValidWAV;
446 
447  unsigned int origFmt;
448  PWAVFileFormat * formatHandler;
449 
450  PBoolean autoConvert;
451  PWAVFileConverter * autoConverter;
452 
453  off_t lenHeader;
454  off_t lenData;
455 
456  bool header_needs_updating;
457 
458 friend class PWAVFileConverter;
459 };
460 
461 #endif // P_WAVFILE
462 
463 #endif // PTLIB_PWAVFILE_H
464 
465 // End Of File ///////////////////////////////////////////////////////////////