Audacity 3.2.0
Typedefs | Functions
ImportRaw.h File Reference
#include <memory>
#include <vector>
Include dependency graph for ImportRaw.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Typedefs

using NewChannelGroup = std::vector< std::shared_ptr< WaveTrack > >
 
using TrackHolders = std::vector< NewChannelGroup >
 

Functions

void ImportRaw (const AudacityProject &project, wxWindow *parent, const wxString &fileName, WaveTrackFactory *trackFactory, TrackHolders &outTracks)
 

Typedef Documentation

◆ NewChannelGroup

using NewChannelGroup = std::vector< std::shared_ptr<WaveTrack> >

Definition at line 26 of file ImportRaw.h.

◆ TrackHolders

using TrackHolders = std::vector< NewChannelGroup >

Definition at line 27 of file ImportRaw.h.

Function Documentation

◆ ImportRaw()

void ImportRaw ( const AudacityProject project,
wxWindow *  parent,
const wxString &  fileName,
WaveTrackFactory trackFactory,
TrackHolders outTracks 
)

Definition at line 110 of file ImportRaw.cpp.

112{
113 outTracks.clear();
114
115 TrackHolders results;
116 auto updateResult = ProgressResult::Success;
117
118 {
119 // On first run, set default sample rate from project rate
120 if (ImportRawDialog::mRate < 100.)
122
123 ImportRawDialog dlog(parent, fileName);
124 dlog.ShowModal();
125 if (!dlog.GetReturnCode())
126 return;
127
128 int encoding = dlog.mEncoding;
129 unsigned numChannels = dlog.mChannels;
130 double rate = dlog.mRate;
131 sf_count_t offset = (sf_count_t)dlog.mOffset;
132 double percent = dlog.mPercent;
133
134 SF_INFO sndInfo = { 0 };
135 sndInfo.samplerate = (int)rate;
136 sndInfo.channels = (int)numChannels;
137 sndInfo.format = encoding | SF_FORMAT_RAW;
138
139 wxFile f; // will be closed when it goes out of scope
140 SFFile sndFile;
141
142 if (f.Open(fileName)) {
143 // Even though there is an sf_open() that takes a filename, use the one that
144 // takes a file descriptor since wxWidgets can open a file with a Unicode name and
145 // libsndfile can't (under Windows).
146 sndFile.reset(SFCall<SNDFILE*>(sf_open_fd, f.fd(), SFM_READ, &sndInfo, FALSE));
147 }
148
149 if (!sndFile){
150 char str[1000];
151 sf_error_str((SNDFILE *)NULL, str, 1000);
152 wxPrintf("%s\n", str);
153
154 throw FileException{ FileException::Cause::Open, fileName };
155 }
156
157
158 {
159 int result = sf_command(sndFile.get(), SFC_SET_RAW_START_OFFSET, &offset, sizeof(offset));
160 if (result != 0) {
161 char str[1000];
162 sf_error_str(sndFile.get(), str, 1000);
163 wxPrintf("%s\n", str);
164
165 throw FileException{ FileException::Cause::Read, fileName };
166 }
167 }
168 SFCall<sf_count_t>(sf_seek, sndFile.get(), 0, SEEK_SET);
169
170 auto totalFrames =
171 // fraction of a sf_count_t value
172 (sampleCount)(sndInfo.frames * percent / 100.0);
173
174 //
175 // Sample format:
176 //
177 // In general, go with the user's preferences. However, if
178 // the file is higher-quality, go with a format which preserves
179 // the quality of the original file.
180 //
181
184
185 results.resize(1);
186 auto &channels = results[0];
187 channels.resize(numChannels);
188
189 {
190 // iter not used outside this scope.
191 auto iter = channels.begin();
192 for (decltype(numChannels) c = 0; c < numChannels; ++iter, ++c)
193 *iter = trackFactory->Create(format, rate);
194 }
195 const auto firstChannel = channels.begin()->get();
196 auto maxBlockSize = firstChannel->GetMaxBlockSize();
197
198 SampleBuffer srcbuffer(maxBlockSize * numChannels, format);
199 SampleBuffer buffer(maxBlockSize, format);
200
201 decltype(totalFrames) framescompleted = 0;
202 if (totalFrames < 0) {
203 wxASSERT(false);
204 totalFrames = 0;
205 }
206
207 auto msg = XO("Importing %s").Format( wxFileName::FileName(fileName).GetFullName() );
208
209 /* i18n-hint: 'Raw' means 'unprocessed' here and should usually be translated.*/
210 ProgressDialog progress(XO("Import Raw"), msg);
211
212 size_t block;
213 do {
214 block =
215 limitSampleBufferSize( maxBlockSize, totalFrames - framescompleted );
216
217 sf_count_t sf_result;
218 if (format == int16Sample)
219 sf_result = SFCall<sf_count_t>(sf_readf_short, sndFile.get(), (short *)srcbuffer.ptr(), block);
220 else
221 sf_result = SFCall<sf_count_t>(sf_readf_float, sndFile.get(), (float *)srcbuffer.ptr(), block);
222
223 if (sf_result >= 0) {
224 block = sf_result;
225 }
226 else {
227 // This is not supposed to happen, sndfile.h says result is always
228 // a count, not an invalid value for error
229 throw FileException{ FileException::Cause::Read, fileName };
230 }
231
232 if (block) {
233 auto iter = channels.begin();
234 for(decltype(numChannels) c = 0; c < numChannels; ++iter, ++c) {
235 if (format==int16Sample) {
236 for(decltype(block) j=0; j<block; j++)
237 ((short *)buffer.ptr())[j] =
238 ((short *)srcbuffer.ptr())[numChannels*j+c];
239 }
240 else {
241 for(decltype(block) j=0; j<block; j++)
242 ((float *)buffer.ptr())[j] =
243 ((float *)srcbuffer.ptr())[numChannels*j+c];
244 }
245
246 iter->get()->Append(buffer.ptr(), (format == int16Sample)?int16Sample:floatSample, block);
247 }
248 framescompleted += block;
249 }
250
251 updateResult = progress.Update(
252 framescompleted.as_long_long(),
253 totalFrames.as_long_long()
254 );
255 if (updateResult != ProgressResult::Success)
256 break;
257
258 } while (block > 0 && framescompleted < totalFrames);
259 }
260
261 if (updateResult == ProgressResult::Failed || updateResult == ProgressResult::Cancelled)
262 throw UserException{};
263
264 if (!results.empty() && !results[0].empty()) {
265 for (const auto &channel : results[0])
266 channel->Flush();
267 outTracks.swap(results);
268 }
269}
#define str(a)
int format
Definition: ExportPCM.cpp:56
sampleFormat sf_subtype_to_effective_format(unsigned int format)
Choose the narrowest value in the sampleFormat enumeration for a given libsndfile format.
std::vector< std::vector< std::shared_ptr< WaveTrack > > > TrackHolders
Definition: Import.h:39
#define XO(s)
Definition: Internat.h:31
size_t limitSampleBufferSize(size_t bufferSize, sampleCount limit)
Definition: SampleCount.cpp:23
@ floatSample
Definition: SampleFormat.h:34
@ int16Sample
Definition: SampleFormat.h:32
Thrown for failure of file or database operations in deeply nested places.
Definition: FileException.h:19
static sampleFormat ChooseFormat(sampleFormat effectiveFormat)
Choose appropriate format, which will not be narrower than the specified one.
ImportRawDialog prompts you with options such as endianness and sample size to help you importing dat...
Definition: ImportRaw.cpp:62
static double mRate
Definition: ImportRaw.cpp:79
ProgressDialog Class.
static ProjectRate & Get(AudacityProject &project)
Definition: ProjectRate.cpp:28
double GetRate() const
Definition: ProjectRate.cpp:53
Can be thrown when user cancels operations, as with a progress dialog. Delayed handler does nothing.
Definition: UserException.h:17
std::shared_ptr< WaveTrack > Create()
Creates an unnamed empty WaveTrack with default sample format and default rate.
Definition: WaveTrack.cpp:118
Positions or offsets within audio files need a wide type.
Definition: SampleCount.h:18

References ImportFileHandle::ChooseFormat(), WaveTrackFactory::Create(), floatSample, format, ProjectRate::Get(), ProjectRate::GetRate(), int16Sample, limitSampleBufferSize(), ImportRawDialog::mChannels, ImportRawDialog::mEncoding, ImportRawDialog::mOffset, ImportRawDialog::mPercent, ImportRawDialog::mRate, FileException::Open, SampleBuffer::ptr(), FileException::Read, sf_subtype_to_effective_format(), str, BasicUI::Success, ProgressDialog::Update(), and XO.

Referenced by anonymous_namespace{FileMenus.cpp}::DoImport().

Here is the call graph for this function:
Here is the caller graph for this function: