Audio Queue: Better handle a lot of short files playing in a row, so files don't get skipped, and so the player doesn't get overburdened starting new files

CQTexperiment
Christopher Snowhill 2021-12-27 23:21:48 -08:00
parent 120daf291a
commit ad3058c4f3
2 changed files with 68 additions and 17 deletions

View File

@ -17,6 +17,9 @@
BufferChain *bufferChain; BufferChain *bufferChain;
OutputNode *output; OutputNode *output;
BOOL stoppingReQueue;
NSOperationQueue *reQueue;
double volume; double volume;
NSMutableArray *chainQueue; NSMutableArray *chainQueue;

View File

@ -28,12 +28,22 @@
outputLaunched = NO; outputLaunched = NO;
endOfInputReached = NO; endOfInputReached = NO;
stoppingReQueue = NO;
reQueue = [[NSOperationQueue alloc] init];
[reQueue setMaxConcurrentOperationCount:1];
chainQueue = [[NSMutableArray alloc] init]; chainQueue = [[NSMutableArray alloc] init];
} }
return self; return self;
} }
- (void)dealloc
{
stoppingReQueue = YES;
[reQueue waitUntilAllOperationsAreFinished];
}
- (void)setDelegate:(id)d - (void)setDelegate:(id)d
{ {
delegate = d; delegate = d;
@ -206,7 +216,9 @@
- (void)stop - (void)stop
{ {
//Set shouldoContinue to NO on allll things //Set shouldoContinue to NO on all things
stoppingReQueue = YES;
[reQueue waitUntilAllOperationsAreFinished];
[self setShouldContinue:NO]; [self setShouldContinue:NO];
[self setPlaybackStatus:CogStatusStopped waitUntilDone:YES]; [self setPlaybackStatus:CogStatusStopped waitUntilDone:YES];
} }
@ -282,6 +294,8 @@
[anObject setShouldContinue:NO]; [anObject setShouldContinue:NO];
} }
[chainQueue removeAllObjects]; [chainQueue removeAllObjects];
stoppingReQueue = YES;
[reQueue waitUntilAllOperationsAreFinished];
if (endOfInputReached) { if (endOfInputReached) {
[self endOfInputReached:bufferChain]; [self endOfInputReached:bufferChain];
@ -330,8 +344,45 @@
[newChain setShouldContinue:YES]; [newChain setShouldContinue:YES];
[newChain launchThreads]; [newChain launchThreads];
stoppingReQueue = NO;
if (([chainQueue count] + [reQueue operationCount]) >= 5) {
NSBlockOperation *op = [[NSBlockOperation alloc] init];
[op addExecutionBlock:^{
unsigned long queueCount;
if (self->stoppingReQueue) {
return;
}
for (;;)
{
@synchronized (self->chainQueue) {
queueCount = [self->chainQueue count];
}
if (queueCount < 5) {
@synchronized (self->chainQueue) {
[self->chainQueue insertObject:newChain atIndex:[self->chainQueue count]];
}
break;
}
if (self->stoppingReQueue) {
break;
}
usleep(5000);
}
}];
[reQueue addOperation:op];
}
else {
[chainQueue insertObject:newChain atIndex:[chainQueue count]]; [chainQueue insertObject:newChain atIndex:[chainQueue count]];
} }
}
- (BOOL)endOfInputReached:(BufferChain *)sender //Sender is a BufferChain - (BOOL)endOfInputReached:(BufferChain *)sender //Sender is a BufferChain
{ {
@ -348,24 +399,21 @@
} }
} }
queueCount = [chainQueue count] + [reQueue operationCount];
}
if (queueCount >= 5)
{
[reQueue waitUntilAllOperationsAreFinished];
}
@synchronized (chainQueue) {
// We don't want to do this, it may happen with a lot of short files // We don't want to do this, it may happen with a lot of short files
//if ([chainQueue count] >= 5) //if ([chainQueue count] >= 5)
//{ //{
// return YES; // return YES;
//} //}
queueCount = [chainQueue count];
}
while (queueCount >= 5)
{
usleep(2000);
@synchronized (chainQueue) {
queueCount = [chainQueue count];
}
}
@synchronized (chainQueue) {
BufferChain *newChain = nil; BufferChain *newChain = nil;
nextStreamUserInfo = [sender userInfo]; nextStreamUserInfo = [sender userInfo];