annotate trunk/src/Modules/Output/FileOutputAIMC.cc @ 402:69466da9745e

- Massive refactoring to make module tree stuff work. In theory we now support configuration files again. The graphics stuff is untested as yet.
author tomwalters
date Mon, 18 Oct 2010 04:42:28 +0000
parents 3ee03a6b95a0
children 99f9bf0f7798
rev   line source
tomwalters@320 1 // Copyright 2006-2010, Thomas Walters
tomwalters@320 2 //
tomwalters@320 3 // AIM-C: A C++ implementation of the Auditory Image Model
tomwalters@320 4 // http://www.acousticscale.org/AIMC
tomwalters@320 5 //
tomwalters@320 6 // Licensed under the Apache License, Version 2.0 (the "License");
tomwalters@320 7 // you may not use this file except in compliance with the License.
tomwalters@320 8 // You may obtain a copy of the License at
tomwalters@320 9 //
tomwalters@320 10 // http://www.apache.org/licenses/LICENSE-2.0
tomwalters@320 11 //
tomwalters@320 12 // Unless required by applicable law or agreed to in writing, software
tomwalters@320 13 // distributed under the License is distributed on an "AS IS" BASIS,
tomwalters@320 14 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
tomwalters@320 15 // See the License for the specific language governing permissions and
tomwalters@320 16 // limitations under the License.
tomwalters@320 17
tomwalters@320 18 /*!
tomwalters@320 19 * \file
tomwalters@320 20 * \brief File output in the HTK format.
tomwalters@320 21 *
tomwalters@320 22 * \author Tom Walters <tom@acousticscale.org>
tomwalters@320 23 * \author Willem van Engen <cnbh@willem.engen.nl>
tomwalters@320 24 * \date created 2007/01/26
tomwalters@320 25 * \version \$Id: $
tomwalters@320 26 */
tomwalters@320 27
tomwalters@320 28 #ifdef _WINDOWS
tomwalters@320 29 # include <direct.h> // for _mkdir & _rmdir
tomwalters@320 30 #else
tomwalters@320 31 # include <sys/types.h>
tomwalters@320 32 # include <dirent.h> // for opendir & friends
tomwalters@320 33 #endif
tomwalters@320 34
tomwalters@320 35 #include <stdint.h>
tomwalters@320 36 #include <stdio.h>
tomwalters@320 37 #include <string.h>
tomwalters@320 38 #include <cmath>
tomwalters@320 39
tomwalters@320 40 #include "Modules/Output/FileOutputAIMC.h"
tomwalters@320 41
tomwalters@320 42 namespace aimc {
tomwalters@320 43 FileOutputAIMC::FileOutputAIMC(Parameters *params) : Module(params) {
tomwalters@320 44 module_description_ = "File output in AIMC format";
tomwalters@402 45 module_identifier_ = "aimc_out";
tomwalters@320 46 module_type_ = "output";
tomwalters@320 47 module_version_ = "$Id: FileOutputAIMC.cc 51 2010-03-30 22:06:24Z tomwalters $";
tomwalters@320 48
tomwalters@320 49 file_handle_ = NULL;
tomwalters@320 50 header_written_ = false;
tomwalters@320 51 frame_period_ms_ = 0.0f;
tomwalters@320 52 }
tomwalters@320 53
tomwalters@320 54 FileOutputAIMC::~FileOutputAIMC() {
tomwalters@320 55 if (file_handle_ != NULL)
tomwalters@320 56 CloseFile();
tomwalters@320 57 }
tomwalters@320 58
tomwalters@320 59 bool FileOutputAIMC::OpenFile(const char* filename, float frame_period_ms) {
tomwalters@320 60 if (file_handle_ != NULL) {
tomwalters@320 61 LOG_ERROR(_T("Couldn't open output file. A file is already open."));
tomwalters@320 62 return false;
tomwalters@320 63 }
tomwalters@320 64
tomwalters@320 65 // Check that the output file exists and is writeable
tomwalters@320 66 if ((file_handle_ = fopen(filename, "wb")) == NULL) {
tomwalters@320 67 LOG_ERROR(_T("Couldn't open output file '%s' for writing."), filename);
tomwalters@320 68 return false;
tomwalters@320 69 }
tomwalters@322 70 frame_count_ = 0;
tomwalters@320 71 frame_period_ms_ = frame_period_ms;
tomwalters@320 72 header_written_ = false;
tomwalters@320 73 if (initialized_) {
tomwalters@320 74 WriteHeader();
tomwalters@320 75 }
tomwalters@320 76 return true;
tomwalters@320 77 }
tomwalters@320 78
tomwalters@320 79 bool FileOutputAIMC::InitializeInternal(const SignalBank &input) {
tomwalters@320 80 if (file_handle_ == NULL) {
tomwalters@320 81 LOG_ERROR(_T("Couldn't initialize file output. "
tomwalters@320 82 "Please call FileOutputAIMC::OpenFile first"));
tomwalters@320 83 return false;
tomwalters@320 84 }
tomwalters@320 85 if (header_written_) {
tomwalters@320 86 LOG_ERROR(_T("A header has already been written on the output file. "
tomwalters@320 87 "Please call FileOutputAIMC::CloseFile to close that file, "
tomwalters@320 88 "and FileOutputAIMC::OpenFile to open an new one before "
tomwalters@320 89 "calling FileOutputAIMC::Initialize again."));
tomwalters@320 90 return false;
tomwalters@320 91 }
tomwalters@320 92 channel_count_ = input.channel_count();
tomwalters@398 93 buffer_length_ = input.buffer_length();
tomwalters@398 94 sample_rate_ = input.sample_rate();
tomwalters@320 95 WriteHeader();
tomwalters@320 96 return true;
tomwalters@320 97 }
tomwalters@320 98
tomwalters@320 99 void FileOutputAIMC::ResetInternal() {
tomwalters@320 100 if (file_handle_ != NULL && !header_written_) {
tomwalters@320 101 WriteHeader();
tomwalters@320 102 }
tomwalters@320 103 if (file_handle_ != NULL)
tomwalters@320 104 CloseFile();
tomwalters@320 105 }
tomwalters@320 106
tomwalters@320 107 void FileOutputAIMC::WriteHeader() {
tomwalters@320 108 if (header_written_)
tomwalters@320 109 return;
tomwalters@320 110
tomwalters@320 111 /* File format:
tomwalters@320 112 * Header: Number of frames (uint32),
tomwalters@320 113 * Frame period in milliseconds (float32),
tomwalters@320 114 * Number of channels per frame (uint32),
tomwalters@320 115 * Number of samples per channel of each frame (uint32)
tomwalters@320 116 * Sample rate (float32)
tomwalters@320 117 *
tomwalters@320 118 * Data: Series of floats, by time, then channel, then frame
tomwalters@320 119 * f1c1t1,f1c1t2,f1c1t3...
tomwalters@320 120 */
tomwalters@320 121
tomwalters@322 122 uint32_t frame_count_out = frame_count_;
tomwalters@320 123 float sample_period_out = frame_period_ms_;
tomwalters@320 124 uint32_t channels_out = channel_count_;
tomwalters@320 125 uint32_t samples_out = buffer_length_;
tomwalters@320 126 float sample_rate = sample_rate_;
tomwalters@320 127
tomwalters@322 128 fwrite(&frame_count_out, sizeof(frame_count_out), 1, file_handle_);
tomwalters@320 129 fwrite(&sample_period_out, sizeof(sample_period_out), 1, file_handle_);
tomwalters@320 130 fwrite(&channels_out, sizeof(channels_out), 1, file_handle_);
tomwalters@320 131 fwrite(&samples_out, sizeof(samples_out), 1, file_handle_);
tomwalters@320 132 fwrite(&sample_rate, sizeof(sample_rate), 1, file_handle_);
tomwalters@320 133 fflush(file_handle_);
tomwalters@320 134
tomwalters@320 135 header_written_ = true;
tomwalters@320 136 }
tomwalters@320 137
tomwalters@320 138 void FileOutputAIMC::Process(const SignalBank &input) {
tomwalters@320 139 if (file_handle_ == NULL) {
tomwalters@320 140 LOG_ERROR(_T("Couldn't process file output. No file is open."
tomwalters@320 141 "Please call FileOutputAIMC::OpenFile first"));
tomwalters@320 142 return;
tomwalters@320 143 }
tomwalters@320 144
tomwalters@320 145 if (!header_written_) {
tomwalters@320 146 LOG_ERROR(_T("No header has been written on the output file yet. Please "
tomwalters@320 147 "call FileOutputAIMC::Initialize() before calling "
tomwalters@320 148 "FileOutputAIMC::Process()"));
tomwalters@320 149 return;
tomwalters@320 150 }
tomwalters@320 151 float s;
tomwalters@320 152
tomwalters@320 153 for (int ch = 0; ch < input.channel_count(); ch++) {
tomwalters@320 154 for (int i = 0; i < input.buffer_length(); i++) {
tomwalters@320 155 s = input.sample(ch, i);
tomwalters@320 156 fwrite(&s, sizeof(s), 1, file_handle_);
tomwalters@320 157 }
tomwalters@320 158 }
tomwalters@322 159 frame_count_++;
tomwalters@320 160 }
tomwalters@320 161
tomwalters@320 162 bool FileOutputAIMC::CloseFile() {
tomwalters@320 163 if (file_handle_ == NULL)
tomwalters@320 164 return false;
tomwalters@320 165
tomwalters@320 166 // Write the first 4 bytes of the file
tomwalters@320 167 // with how many samples there are in the file
tomwalters@320 168 fflush(file_handle_);
tomwalters@320 169 rewind(file_handle_);
tomwalters@320 170 fflush(file_handle_);
tomwalters@322 171 uint32_t frame_count = frame_count_;
tomwalters@322 172 fwrite(&frame_count, sizeof(frame_count), 1, file_handle_);
tomwalters@320 173
tomwalters@320 174 // And close the file
tomwalters@320 175 fclose(file_handle_);
tomwalters@320 176 file_handle_ = NULL;
tomwalters@320 177 header_written_ = false;
tomwalters@320 178 return true;
tomwalters@320 179 }
tomwalters@320 180 } // namespace aimc
tomwalters@320 181