diff --git a/Audio/AudioPlayer.h b/Audio/AudioPlayer.h index 20c41024a..db22efcc8 100644 --- a/Audio/AudioPlayer.h +++ b/Audio/AudioPlayer.h @@ -25,7 +25,6 @@ BufferChain *bufferChain; OutputNode *output; - BOOL muted; double volume; double pitch; double tempo; @@ -77,9 +76,6 @@ - (double)volumeUp:(double)amount; - (double)volumeDown:(double)amount; -- (void)mute; -- (void)unmute; - - (double)amountPlayed; - (double)amountPlayedInterval; diff --git a/Audio/AudioPlayer.m b/Audio/AudioPlayer.m index dd2d8c521..6fbcd4ed1 100644 --- a/Audio/AudioPlayer.m +++ b/Audio/AudioPlayer.m @@ -78,9 +78,6 @@ output = [[OutputNode alloc] initWithController:self previous:nil]; } [output setup]; - if(muted) { - [output mute]; - } @synchronized(chainQueue) { for(id anObject in chainQueue) { [anObject setShouldContinue:NO]; @@ -179,10 +176,6 @@ [output resume]; [self setPlaybackStatus:CogStatusPlaying waitUntilDone:YES]; - - if(muted) { - [self unmute]; - } } - (void)seekToTimeBG:(NSNumber *)time { @@ -190,7 +183,6 @@ } - (void)seekToTime:(double)time { - [self mute]; if(endOfInputReached) { // This is a dirty hack in case the playback has finished with the track // that the user thinks they're seeking into @@ -225,20 +217,6 @@ return volume; } -- (void)mute { - if(!muted) { - [output mute]; - muted = YES; - } -} - -- (void)unmute { - if(muted) { - [output unmute]; - muted = NO; - } -} - // This is called by the delegate DURING a requestNextStream request. - (void)setNextStream:(NSURL *)url { [self setNextStream:url withUserInfo:nil withRGInfo:nil]; diff --git a/Audio/Chain/BufferChain.m b/Audio/Chain/BufferChain.m index 9aab848c3..7a21d6003 100644 --- a/Audio/Chain/BufferChain.m +++ b/Audio/Chain/BufferChain.m @@ -230,7 +230,6 @@ AudioPlayer * audioPlayer = controller; OutputNode *outputNode = [audioPlayer output]; - [audioPlayer mute]; [inputNode seek:frame]; } diff --git a/Audio/Chain/InputNode.m b/Audio/Chain/InputNode.m index 769eeae8e..efc925b9a 100644 --- a/Audio/Chain/InputNode.m +++ b/Audio/Chain/InputNode.m @@ -160,30 +160,11 @@ static void *kInputNodeContext = &kInputNodeContext; while([self shouldContinue] == YES && [self endOfStream] == NO) { if(shouldSeek == YES) { BufferChain *bufferChain = controller; - AudioPlayer *audioPlayer = [controller controller]; - [audioPlayer mute]; + AudioPlayer *audioPlayer = [bufferChain controller]; OutputNode *outputNode = [audioPlayer output]; - [outputNode resetBuffer]; - ConverterNode *converter = [bufferChain converter]; - DSPRubberbandNode *rubberband = [bufferChain rubberband]; - DSPFSurroundNode *fsurround = [bufferChain fsurround]; - DSPEqualizerNode *equalizer = [bufferChain equalizer]; - DSPHRTFNode *hrtf = [bufferChain hrtf]; - DSPDownmixNode *downmix = [bufferChain downmix]; - VisualizationNode *visualization = [bufferChain visualization]; DLog(@"SEEKING! Resetting Buffer"); - - // This resets the converter's buffer - [self resetBuffer]; - [converter resetBuffer]; - [converter inputFormatDidChange:[bufferChain inputFormat] inputConfig:[bufferChain inputConfig]]; - [rubberband resetBuffer]; - [fsurround resetBuffer]; - [equalizer resetBuffer]; - [hrtf resetBuffer]; - [downmix resetBuffer]; - [visualization resetBuffer]; + [outputNode resetBackwards]; DLog(@"Reset buffer!"); @@ -199,8 +180,6 @@ static void *kInputNodeContext = &kInputNodeContext; if(seekError) { [controller setError:YES]; } - - [audioPlayer unmute]; } AudioChunk *chunk; @@ -214,6 +193,11 @@ static void *kInputNodeContext = &kInputNodeContext; chunk = nil; } } else { + if(chunk) { + @autoreleasepool { + chunk = nil; + } + } DLog(@"End of stream? %@", [self properties]); endOfStream = YES; diff --git a/Audio/Chain/Node.h b/Audio/Chain/Node.h index 77a58a2a2..05ea06dee 100644 --- a/Audio/Chain/Node.h +++ b/Audio/Chain/Node.h @@ -66,6 +66,7 @@ - (void)setShouldReset:(BOOL)s; - (BOOL)shouldReset; +- (void)resetBackwards; - (void)setPreviousNode:(id _Nullable)p; - (id _Nullable)previousNode; diff --git a/Audio/Chain/Node.m b/Audio/Chain/Node.m index dfdeffaf2..aca67d826 100644 --- a/Audio/Chain/Node.m +++ b/Audio/Chain/Node.m @@ -523,6 +523,20 @@ } } +- (void)lockedResetBuffer { + @autoreleasepool { + [buffer reset]; + } +} + +- (void)unlockedResetBuffer { + @autoreleasepool { + [accessLock lock]; + [buffer reset]; + [accessLock unlock]; + } +} + // Implementations should override - (BOOL)paused { return NO; @@ -556,4 +570,23 @@ return 0.0; } +// Reset everything in the chain +- (void)resetBackwards { + [accessLock lock]; + if(buffer) { + [self lockedResetBuffer]; + [writeSemaphore signal]; + [readSemaphore signal]; + } + Node *node = previousNode; + while(node) { + [node unlockedResetBuffer]; + [node setShouldReset:YES]; + [[node writeSemaphore] signal]; + [[node readSemaphore] signal]; + node = [node previousNode]; + } + [accessLock unlock]; +} + @end diff --git a/Audio/Chain/OutputNode.h b/Audio/Chain/OutputNode.h index a2a603667..7c6a38877 100644 --- a/Audio/Chain/OutputNode.h +++ b/Audio/Chain/OutputNode.h @@ -62,9 +62,6 @@ - (double)volume; - (void)setVolume:(double)v; -- (void)mute; -- (void)unmute; - - (void)setShouldContinue:(BOOL)s; - (void)setShouldPlayOutBuffer:(BOOL)s; diff --git a/Audio/Chain/OutputNode.m b/Audio/Chain/OutputNode.m index 1fa0fac8c..0ede9847d 100644 --- a/Audio/Chain/OutputNode.m +++ b/Audio/Chain/OutputNode.m @@ -50,14 +50,6 @@ [output resume]; } -- (void)mute { - [output mute]; -} - -- (void)unmute { - [output unmute]; -} - - (void)incrementAmountPlayed:(double)seconds { amountPlayed += seconds; amountPlayedInterval += seconds; @@ -189,7 +181,6 @@ } } if(formatChanged) { - [audioPlayer mute]; InputNode *inputNode = [bufferChain inputNode]; if(converter) { [converter setOutputFormat:format]; diff --git a/Audio/Output/OutputCoreAudio.h b/Audio/Output/OutputCoreAudio.h index 2a833532f..c832fa9cc 100644 --- a/Audio/Output/OutputCoreAudio.h +++ b/Audio/Output/OutputCoreAudio.h @@ -105,7 +105,6 @@ using std::atomic_long; float tempBuffer[512 * 32]; float inputBuffer[4096 * 32]; // 4096 samples times maximum supported channel count - BOOL muted; #ifdef OUTPUT_LOG FILE *_logFile; #endif @@ -126,9 +125,6 @@ using std::atomic_long; - (double)volume; - (void)setVolume:(double)v; -- (void)mute; -- (void)unmute; - - (void)setShouldPlayOutBuffer:(BOOL)enabled; - (void)sustainHDCD; diff --git a/Audio/Output/OutputCoreAudio.m b/Audio/Output/OutputCoreAudio.m index 80a30c4fc..e60dcbcfe 100644 --- a/Audio/Output/OutputCoreAudio.m +++ b/Audio/Output/OutputCoreAudio.m @@ -203,6 +203,7 @@ current_device_listener(AudioObjectID inObjectID, UInt32 inNumberAddresses, cons started = NO; restarted = NO; lastClippedSampleRate = 0.0; + inputRemain = 0; [outputLock unlock]; } @@ -618,12 +619,6 @@ current_device_listener(AudioObjectID inObjectID, UInt32 inNumberAddresses, cons @autoreleasepool { while(renderedSamples < frameCount) { - if(_self->muted) { - inputData->mBuffers[0].mDataByteSize = frameCount * format->mBytesPerPacket; - inputData->mBuffers[0].mNumberChannels = channels; - bzero(inputData->mBuffers[0].mData, inputData->mBuffers[0].mDataByteSize); - return 0; - } int inputRemain = _self->inputRemain; while(!inputRemain) { inputRemain = [_self renderAndConvert]; @@ -746,17 +741,6 @@ current_device_listener(AudioObjectID inObjectID, UInt32 inNumberAddresses, cons volume = v * 0.01f; } -- (void)mute { - if(!muted) { - muted = YES; - inputRemain = 0; - } -} - -- (void)unmute { - muted = NO; -} - - (double)latency { return 0.0; }