1/*****************************************************************************************
2APEInfo.h
3Copyright (C) 2000 by Matthew T. Ashland   All Rights Reserved.
4
5Simple method for working with APE files... it encapsulates reading, writing and getting
6file information.  Just create a CAPEInfo class, call OpenFile(), and use the class methods
7to do whatever you need... the destructor will take care of any cleanup
8
9Notes:
10    -Most all functions return 0 upon success, and some error code (other than 0) on
11    failure.  However, all of the file functions that are wrapped from the Win32 API
12    return 0 on failure and some other number on success.  This applies to ReadFile,
13    WriteFile, SetFilePointer, etc...
14
15WARNING:
16    -This class driven system for using Monkey's Audio is still in development, so
17    I can't make any guarantees that the classes and libraries won't change before
18    everything gets finalized.  Use them at your own risk
19*****************************************************************************************/
20
21#ifndef APE_APEINFO_H
22#define APE_APEINFO_H
23
24#include "IO.h"
25#include "APETag.h"
26#include "MACLib.h"
27
28/*****************************************************************************************
29APE_FILE_INFO - structure which describes most aspects of an APE file
30(used internally for speed and ease)
31*****************************************************************************************/
32struct APE_FILE_INFO
33{
34    int nVersion;                                   // file version number * 1000 (3.93 = 3930)
35    int nCompressionLevel;                          // the compression level
36    int nFormatFlags;                               // format flags
37    int nTotalFrames;                               // the total number frames (frames are used internally)
38    int nBlocksPerFrame;                            // the samples in a frame (frames are used internally)
39    int nFinalFrameBlocks;                          // the number of samples in the final frame
40    int nChannels;                                  // audio channels
41    int nSampleRate;                                // audio samples per second
42    int nBitsPerSample;                             // audio bits per sample
43    int nBytesPerSample;                            // audio bytes per sample
44    int nBlockAlign;                                // audio block align (channels * bytes per sample)
45    int nWAVHeaderBytes;                            // header bytes of the original WAV
46    int nWAVDataBytes;                              // data bytes of the original WAV
47    int nWAVTerminatingBytes;                       // terminating bytes of the original WAV
48    int nWAVTotalBytes;                             // total bytes of the original WAV
49    int nAPETotalBytes;                             // total bytes of the APE file
50    int nTotalBlocks;                               // the total number audio blocks
51    int nLengthMS;                                  // the length in milliseconds
52    int nAverageBitrate;                            // the kbps (i.e. 637 kpbs)
53    int nDecompressedBitrate;                       // the kbps of the decompressed audio (i.e. 1440 kpbs for CD audio)
54    int nJunkHeaderBytes;                           // used for ID3v2, etc.
55    int nSeekTableElements;                         // the number of elements in the seek table(s)
56
57    CSmartPtr<uint32> spSeekByteTable;              // the seek table (byte)
58    CSmartPtr<unsigned char> spSeekBitTable;        // the seek table (bits -- legacy)
59    CSmartPtr<unsigned char> spWaveHeaderData;      // the pre-audio header data
60    CSmartPtr<APE_DESCRIPTOR> spAPEDescriptor;      // the descriptor (only with newer files)
61};
62
63/*****************************************************************************************
64Helper macros (sort of hacky)
65*****************************************************************************************/
66#define GET_USES_CRC(APE_INFO) (((APE_INFO)->GetInfo(APE_INFO_FORMAT_FLAGS) & MAC_FORMAT_FLAG_CRC) ? TRUE : FALSE)
67#define GET_FRAMES_START_ON_BYTES_BOUNDARIES(APE_INFO) (((APE_INFO)->GetInfo(APE_INFO_FILE_VERSION) > 3800) ? TRUE : FALSE)
68#define GET_USES_SPECIAL_FRAMES(APE_INFO) (((APE_INFO)->GetInfo(APE_INFO_FILE_VERSION) > 3820) ? TRUE : FALSE)
69#define GET_IO(APE_INFO) ((CIO *) (APE_INFO)->GetInfo(APE_INFO_IO_SOURCE))
70#define GET_TAG(APE_INFO) ((CAPETag *) (APE_INFO)->GetInfo(APE_INFO_TAG))
71
72/*****************************************************************************************
73CAPEInfo - use this for all work with APE files
74*****************************************************************************************/
75class CAPEInfo
76{
77public:
78
79    // construction and destruction
80    CAPEInfo(int * pErrorCode, const char* pFilename, CAPETag * pTag = NULL);
81    CAPEInfo(int * pErrorCode, CIO * pIO, CAPETag * pTag = NULL);
82    virtual ~CAPEInfo();
83
84    // query for information
85    int GetInfo(APE_DECOMPRESS_FIELDS Field, int nParam1 = 0, int nParam2 = 0);
86
87private:
88
89    // internal functions
90    int GetFileInformation(BOOL bGetTagInformation = TRUE);
91    int CloseFile();
92
93    // internal variables
94    BOOL m_bHasFileInformationLoaded;
95    CSmartPtr<CIO> m_spIO;
96    CSmartPtr<CAPETag> m_spAPETag;
97    APE_FILE_INFO    m_APEFileInfo;
98};
99
100#endif // #ifndef APE_APEINFO_H
101