react-native-audio-api
Version:
react-native-audio-api provides system for controlling audio in React Native environment compatible with Web Audio API specification
94 lines (92 loc) • 4.31 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.decodeAudioData = decodeAudioData;
exports.decodePCMInBase64 = decodePCMInBase64;
var _reactNative = require("react-native");
var _specs = require("../specs");
var _errors = require("../errors");
var _paths = require("../utils/paths");
var _utils = require("../utils");
var _AudioBuffer = _interopRequireDefault(require("./AudioBuffer"));
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
class AudioDecoder {
static instance = null;
constructor() {
this.decoder = globalThis.createAudioDecoder();
}
async decodeAudioDataImplementation(input, sampleRate, fetchOptions) {
const rate = sampleRate ?? 0;
if (input instanceof ArrayBuffer) {
return this.decodeFromArrayBuffer(input, rate);
}
const stringSource = this.resolveStringSource(input);
this.assertSupportedStringSource(stringSource);
if ((0, _paths.isRemoteSource)(stringSource)) {
return this.decodeFromRemoteUrl(stringSource, rate, fetchOptions);
}
return this.decodeFromLocalFile(stringSource, rate);
}
async decodeFromArrayBuffer(arrayBuffer, sampleRate) {
const buffer = await this.decoder.decodeWithMemoryBlock(
// @ts-ignore internal function
new Uint8Array(arrayBuffer), sampleRate);
return new _AudioBuffer.default(buffer);
}
resolveStringSource(input) {
return typeof input === 'number' ? _reactNative.Image.resolveAssetSource(input).uri : input;
}
assertSupportedStringSource(source) {
if (typeof source !== 'string') {
throw new TypeError('Input must be a module, uri or ArrayBuffer');
}
if ((0, _paths.isBase64Source)(source)) {
throw new _errors.AudioApiError('Base64 source decoding is not currently supported, to decode raw PCM base64 strings use decodePCMInBase64 method.');
}
if ((0, _paths.isDataBlobString)(source)) {
throw new _errors.AudioApiError('Data Blob string decoding is not currently supported.');
}
}
async decodeFromRemoteUrl(url, sampleRate, fetchOptions) {
const arrayBuffer = await fetch(url, fetchOptions).then(res => res.arrayBuffer());
return this.decodeFromArrayBuffer(arrayBuffer, sampleRate);
}
async decodeFromLocalFile(stringSource, sampleRate) {
const useAndroidBundledAssetReader = _reactNative.Platform.OS === 'android' && !stringSource.startsWith('file://') && !__DEV__;
// special workaround, because android bundled assets are passed as f.e. asset_example_file
// which has to be handled on native side and extension is not passed with it so decode using memory
if (useAndroidBundledAssetReader) {
const base64Payload = await _specs.NativeAudioAPIModule.readAndroidReleaseAssetBytesAsBase64(stringSource);
const arrayBuffer = (0, _utils.base64ToArrayBuffer)(base64Payload);
return this.decodeFromArrayBuffer(arrayBuffer, sampleRate);
}
const filePath = (0, _paths.resolveLocalFilePath)(stringSource);
const buffer = await this.decoder.decodeWithFilePath(filePath, sampleRate);
return new _AudioBuffer.default(buffer);
}
static getInstance() {
if (!AudioDecoder.instance) {
AudioDecoder.instance = new AudioDecoder();
}
return AudioDecoder.instance;
}
async decodeAudioDataInstance(input, sampleRate, fetchOptions) {
const audioBuffer = await this.decodeAudioDataImplementation(input, sampleRate, fetchOptions);
if (!audioBuffer) {
throw new _errors.AudioApiError('Failed to decode audio data.');
}
return audioBuffer;
}
async decodePCMInBase64Instance(base64String, inputSampleRate, inputChannelCount, interleaved) {
const buffer = await this.decoder.decodeWithPCMInBase64(base64String, inputSampleRate, inputChannelCount, interleaved);
return new _AudioBuffer.default(buffer);
}
}
async function decodeAudioData(input, sampleRate, fetchOptions) {
return AudioDecoder.getInstance().decodeAudioDataInstance(input, sampleRate, fetchOptions);
}
async function decodePCMInBase64(base64String, inputSampleRate, inputChannelCount, isInterleaved = true) {
return AudioDecoder.getInstance().decodePCMInBase64Instance(base64String, inputSampleRate, inputChannelCount, isInterleaved);
}
//# sourceMappingURL=AudioDecoder.js.map