Otclient  14/8/2020
oggsoundfile.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2010-2020 OTClient <https://github.com/edubart/otclient>
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a copy
5  * of this software and associated documentation files (the "Software"), to deal
6  * in the Software without restriction, including without limitation the rights
7  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8  * copies of the Software, and to permit persons to whom the Software is
9  * furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice shall be included in
12  * all copies or substantial portions of the Software.
13  *
14  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20  * THE SOFTWARE.
21  */
22 
23 #include "oggsoundfile.h"
24 
25 OggSoundFile::OggSoundFile(const FileStreamPtr& fileStream) : SoundFile(fileStream)
26 {
27  memset(&m_vorbisFile, 0, sizeof(m_vorbisFile));
28 }
29 
31 {
32  ov_clear(&m_vorbisFile);
33 }
34 
36 {
37  ov_callbacks callbacks = { cb_read, cb_seek, cb_close, cb_tell };
38  ov_open_callbacks(m_file.get(), &m_vorbisFile, nullptr, 0, callbacks);
39 
40  vorbis_info* vi = ov_info(&m_vorbisFile, -1);
41  if(!vi) {
42  g_logger.error(stdext::format("ogg file not supported: %s", m_file->name()));
43  return false;
44  }
45 
46  m_channels = vi->channels;
47  m_rate = vi->rate;
48  m_bps = 16;
49  m_size = ov_pcm_total(&m_vorbisFile, -1) * (m_bps/8) * m_channels;
50 
51  return true;
52 }
53 
54 int OggSoundFile::read(void *buffer, int bufferSize)
55 {
56  char* bytesBuffer = reinterpret_cast<char*>(buffer);
57  int section = 0;
58  size_t totalBytesRead = 0;
59 
60  while(bufferSize > 0) {
61  size_t bytesToRead = bufferSize;
62  long bytesRead = ov_read(&m_vorbisFile, bytesBuffer, bytesToRead, 0, 2, 1, &section);
63  if(bytesRead == 0)
64  break;
65 
66  bufferSize -= bytesRead;
67  bytesBuffer += bytesRead;
68  totalBytesRead += bytesRead;
69  }
70 
71  return totalBytesRead;
72 }
73 
75 {
76  ov_pcm_seek(&m_vorbisFile, 0);
77 }
78 
79 size_t OggSoundFile::cb_read(void* ptr, size_t size, size_t nmemb, void* source)
80 {
81  FileStream *file = static_cast<FileStream*>(source);
82  return file->read(ptr, size, nmemb);
83 }
84 
85 int OggSoundFile::cb_seek(void* source, ogg_int64_t offset, int whence)
86 {
87  FileStream *file = static_cast<FileStream*>(source);
88  switch(whence) {
89  case SEEK_SET:
90  file->seek(offset);
91  return 0;
92  case SEEK_CUR:
93  file->seek(file->tell() + offset);
94  return 0;
95  case SEEK_END:
96  file->seek(file->size() + offset);
97  return 0;
98  }
99  return -1;
100 }
101 
102 int OggSoundFile::cb_close(void* source)
103 {
104  FileStream *file = static_cast<FileStream*>(source);
105  file->close();
106  return 0;
107 }
108 
109 long OggSoundFile::cb_tell(void* source)
110 {
111  FileStream *file = static_cast<FileStream*>(source);
112  return file->tell();
113 }
FileStream::seek
void seek(uint pos)
Definition: filestream.cpp:142
SoundFile::m_channels
int m_channels
Definition: soundfile.h:50
SoundFile::m_bps
int m_bps
Definition: soundfile.h:52
SoundFile::m_file
FileStreamPtr m_file
Definition: soundfile.h:49
FileStream::close
void close()
Definition: filestream.cpp:78
OggSoundFile::~OggSoundFile
virtual ~OggSoundFile()
Definition: oggsoundfile.cpp:30
Logger::error
void error(const std::string &what)
Definition: logger.h:54
OggSoundFile::read
int read(void *buffer, int bufferSize)
Definition: oggsoundfile.cpp:54
SoundFile::m_rate
int m_rate
Definition: soundfile.h:51
stdext::format
std::string format()
Definition: format.h:82
OggSoundFile::OggSoundFile
OggSoundFile(const FileStreamPtr &fileStream)
Definition: oggsoundfile.cpp:25
OggSoundFile::prepareOgg
bool prepareOgg()
Definition: oggsoundfile.cpp:35
SoundFile::m_size
int m_size
Definition: soundfile.h:53
g_logger
Logger g_logger
Definition: logger.cpp:35
FileStream
Definition: filestream.h:34
oggsoundfile.h
FileStream::read
int read(void *buffer, uint size, uint nmemb=1)
Definition: filestream.cpp:109
OggSoundFile::reset
void reset()
Definition: oggsoundfile.cpp:74
FileStream::name
std::string name()
Definition: filestream.h:51
FileStream::tell
uint tell()
Definition: filestream.cpp:167
stdext::shared_object_ptr< FileStream >
FileStream::size
uint size()
Definition: filestream.cpp:159
SoundFile
Definition: soundfile.h:29
stdext::shared_object_ptr::get
T * get() const
Definition: shared_object.h:82