vector<float> loadDistortion(string& filename) { auto doublesBuffer = loadDoubles(filename); vector<float> floatBuffer(doublesBuffer.size()); for(int i=0; i<doublesBuffer.size(); i++) { floatBuffer[i] = (float) doublesBuffer[i]; } return floatBuffer; }
/** * 指定したバイト数だけpcmデータを読み込みます。 * エラーが発生するか、終端に達するまでsizeで指定したバイト数だけ読み込めます。 */ bool PitchShiftWaveReader::read(void *dst, std::size_t size, std::size_t *actualSize) { if(!isOpen()){ return false; } if(size == 0){ if(actualSize){ *actualSize = 0; } return true; } // 出力に必要な入力サンプル数を求める。 const std::size_t reqOutSamples = size / format_.blockAlign; //floor const WaveSize reqSrcSamples0 = resampler_ ? resampler_->calcRequiredInputSize(reqOutSamples) : reqOutSamples; if(reqSrcSamples0 > std::numeric_limits<std::size_t>::max() / format_.blockAlign){ return false; } const std::size_t reqSrcSamples = static_cast<std::size_t>(reqSrcSamples0); const std::size_t reqSrcBytes = reqSrcSamples * format_.blockAlign; // read source bytes. std::size_t actualSizeSrc = 0; HeapArray<uint8_t> byteBuffer(reqSrcBytes); if(!source_->read(byteBuffer.get(), reqSrcBytes, &actualSizeSrc)){ return false; } // pitch shift. const std::size_t actualSrcSamples = actualSizeSrc / format_.blockAlign; //floor if(shiftRatio_ != 1.0f){ HeapArray<float> floatBuffer(actualSrcSamples); for(unsigned int ch = 0; ch < format_.channels; ++ch){ demultiplex(floatBuffer.get(), byteBuffer.get(), ch, actualSrcSamples, format_.blockAlign, format_.bytesPerSample); shifters_[ch]->smbPitchShift( shiftRatio_, actualSrcSamples, fftOverlapFactor_, static_cast<float>(format_.samplesPerSec), floatBuffer.get(), floatBuffer.get()); multiplex(byteBuffer.get(), floatBuffer.get(), ch, actualSrcSamples, format_.blockAlign, format_.bytesPerSample); } } // resample. if(resampler_){ assert(actualSrcSamples == reqSrcSamples); std::size_t actualOutSamples = reqOutSamples; if(actualSrcSamples != reqSrcSamples){ const std::size_t maxOutSamples = static_cast<std::size_t>(std::min(resampler_->calcMaxOutputSize(actualSrcSamples), static_cast<WaveSize>(reqOutSamples))); if(actualOutSamples > maxOutSamples){ actualOutSamples = maxOutSamples; } } switch(format_.blockAlign){ case 1: resampler_->resample( reinterpret_cast<uint8_t *>(dst), reinterpret_cast<uint8_t *>(dst) + actualOutSamples, byteBuffer.get(), byteBuffer.get() + actualSrcSamples); break; case 2: resampler_->resample( reinterpret_cast<uint16_t *>(dst), reinterpret_cast<uint16_t *>(dst) + actualOutSamples, reinterpret_cast<const uint16_t *>(byteBuffer.get()), reinterpret_cast<const uint16_t *>(byteBuffer.get()) + actualSrcSamples); break; case 4: resampler_->resample( reinterpret_cast<uint32_t *>(dst), reinterpret_cast<uint32_t *>(dst) + actualOutSamples, reinterpret_cast<const uint32_t *>(byteBuffer.get()), reinterpret_cast<const uint32_t *>(byteBuffer.get()) + actualSrcSamples); break; } if(actualSize){ *actualSize = actualOutSamples * format_.blockAlign; } outputPos_ += actualOutSamples; } else{ std::memcpy(dst, byteBuffer.get(), actualSrcSamples * format_.blockAlign); if(actualSize){ *actualSize = actualSrcSamples * format_.blockAlign; } outputPos_ += actualSrcSamples; } return true; }