Revert "Visualization: Tweak systems a bit"

This reverts commit 6c24ad8244.
This commit is contained in:
Christopher Snowhill 2025-02-01 15:08:25 -08:00
parent 591f3ceb18
commit 5392a5fa91
3 changed files with 62 additions and 106 deletions

View file

@ -12,7 +12,7 @@ class VisualizationController : NSObject {
var serialQueue = DispatchQueue(label: "Visualization Queue") var serialQueue = DispatchQueue(label: "Visualization Queue")
var sampleRate = 0.0 var sampleRate = 0.0
var latency = 0.0 var latency = 0.0
var visAudio: [Float] = Array<Float>(repeating: 0.0, count: 44100 * 45) var visAudio: [Float] = Array(repeating: 0.0, count: 44100 * 45)
var visAudioCursor = 0 var visAudioCursor = 0
var visAudioSize = 0 var visAudioSize = 0
var visSamplesPosted: UInt64 = 0 var visSamplesPosted: UInt64 = 0
@ -30,10 +30,12 @@ class VisualizationController : NSObject {
@objc @objc
func reset() { func reset() {
serialQueue.sync { serialQueue.sync {
self.latency = 0 self.latency = 0;
self.visAudioSize = 44100 * 45 let amount = self.visAudioSize
self.visAudio = Array<Float>(repeating: 0.0, count: visAudioSize) for i in 0..<amount {
self.visSamplesPosted = 0 self.visAudio[i] = 0
}
self.visSamplesPosted = 0;
} }
} }
@ -52,9 +54,9 @@ class VisualizationController : NSObject {
serialQueue.sync { serialQueue.sync {
if(self.sampleRate != sampleRate) { if(self.sampleRate != sampleRate) {
self.sampleRate = sampleRate self.sampleRate = sampleRate
self.visAudioSize = (Int)(sampleRate * 45.0) visAudioSize = (Int)(sampleRate * 45.0)
self.visAudio = Array<Float>(repeating: 0.0, count: visAudioSize) visAudio = Array(repeating: 0.0, count: visAudioSize)
self.visAudioCursor = 0 visAudioCursor = 0
} }
} }
} }
@ -62,23 +64,17 @@ class VisualizationController : NSObject {
@objc @objc
func postVisPCM(_ inPCM: UnsafePointer<Float>?, amount: Int) { func postVisPCM(_ inPCM: UnsafePointer<Float>?, amount: Int) {
serialQueue.sync { serialQueue.sync {
if(self.visAudioSize == 0) { let bufferPointer = UnsafeBufferPointer<Float>(start: inPCM, count: amount)
return var j = self.visAudioCursor
} let k = self.visAudioSize
let bufferPointer = UnsafeRawPointer(inPCM) for i in 0..<amount {
if let bptr = bufferPointer { let x = bufferPointer[i]
let dataArray = bptr.assumingMemoryBound(to: Float.self) self.visAudio[j] = x
var j = self.visAudioCursor j += 1; if j >= k { j = 0 }
let k = self.visAudioSize
for i in 0..<amount {
let x = dataArray[i]
self.visAudio[j] = x
j += 1; if j >= k { j = 0 }
}
self.visAudioCursor = j
self.latency += Double(amount) / self.sampleRate
self.visSamplesPosted += UInt64(amount)
} }
self.visAudioCursor = j
self.latency += Double(amount) / self.sampleRate
self.visSamplesPosted += UInt64(amount);
} }
} }
@ -91,10 +87,19 @@ class VisualizationController : NSObject {
@objc @objc
func copyVisPCM(_ outPCM: UnsafeMutablePointer<Float>?, visFFT: UnsafeMutablePointer<Float>?, latencyOffset: Double) { func copyVisPCM(_ outPCM: UnsafeMutablePointer<Float>?, visFFT: UnsafeMutablePointer<Float>?, latencyOffset: Double) {
outPCM?.update(repeating: 0.0, count: 4096)
visFFT?.update(repeating: 0.0, count: 2048)
if(self.visAudioSize == 0) { if(self.visAudioSize == 0) {
if(outPCM != nil) {
let pcmPointer = UnsafeMutableBufferPointer<Float>(start: outPCM, count: 4096)
for i in 0...4095 {
pcmPointer[i] = 0.0
}
}
if(visFFT != nil) {
let fftPointer = UnsafeMutableBufferPointer<Float>(start: visFFT, count: 2048)
for i in 0...2047 {
fftPointer[i] = 0.0
}
}
return return
} }
@ -103,16 +108,13 @@ class VisualizationController : NSObject {
serialQueue.sync { serialQueue.sync {
// Offset latency so the target sample is in the center of the window // Offset latency so the target sample is in the center of the window
let latencySamples = (Int)((self.latency + latencyOffset) * self.sampleRate) + 2048 let latencySamples = (Int)((self.latency + latencyOffset) * self.sampleRate) + 2048
var samplesToDo = 4096 var samplesToDo = 4096;
if(latencySamples < 0) { if(latencySamples < 0) {
return return;
}
if(latencySamples + 4096 > visAudioSize) {
return
} }
if(latencySamples < 4096) { if(latencySamples < 4096) {
// Latency can sometimes dip below this threshold // Latency can sometimes dip below this threshold
samplesToDo = latencySamples samplesToDo = latencySamples;
} }
var j = self.visAudioCursor - latencySamples var j = self.visAudioCursor - latencySamples
let k = self.visAudioSize let k = self.visAudioSize
@ -129,7 +131,13 @@ class VisualizationController : NSObject {
} }
} }
outPCM?.update(from: outPCMCopy, count: 4096) if(outPCM != nil) {
let pcmPointer = UnsafeMutableBufferPointer<Float>(start: outPCM, count: 4096)
for i in 0...4095 {
let x = outPCMCopy[i]
pcmPointer[i] = x
}
}
if(visFFT != nil) { if(visFFT != nil) {
serialQueue.sync { serialQueue.sync {

View file

@ -41,8 +41,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
NSColor *borderColor; NSColor *borderColor;
ddb_analyzer_t _analyzer; ddb_analyzer_t _analyzer;
ddb_analyzer_draw_data_t _draw_data; ddb_analyzer_draw_data_t _draw_data;
BOOL invalidateSpectrum;
float analyzerLastWidth;
float visAudio[4096], visFFT[2048]; float visAudio[4096], visFFT[2048];
@ -98,12 +96,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
paused = NO; paused = NO;
isListening = NO; isListening = NO;
visSamplesLastPosted = [self->visController samplesPosted];
invalidateSpectrum = YES;
analyzerLastWidth = -1.0f;
saLowerBound = LOWER_BOUND; saLowerBound = LOWER_BOUND;
[self colorsDidChange:nil]; [self colorsDidChange:nil];
@ -130,7 +122,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
- (void)enableFullView { - (void)enableFullView {
isFullView = YES; isFullView = YES;
_analyzer.freq_is_log = 1; _analyzer.freq_is_log = 1;
invalidateSpectrum = YES;
[self repaint]; [self repaint];
} }
@ -248,10 +239,8 @@ extern NSString *CogPlaybackDidStopNotificiation;
} }
- (void)timerRun:(NSTimer *)timer { - (void)timerRun:(NSTimer *)timer {
invalidateSpectrum = YES;
[self repaint]; [self repaint];
if(visSamplesLastPosted) visLatencyOffset -= 1.0 / 60.0;
visLatencyOffset -= 1.0f / 60.0f;
} }
- (void)colorsDidChange:(NSNotification *)notification { - (void)colorsDidChange:(NSNotification *)notification {
@ -424,28 +413,16 @@ extern NSString *CogPlaybackDidStopNotificiation;
} }
UInt64 samplesPosted = [self->visController samplesPosted]; UInt64 samplesPosted = [self->visController samplesPosted];
if(!samplesPosted) return; if (samplesPosted != visSamplesLastPosted) {
if(samplesPosted != visSamplesLastPosted) {
float latencyOffset = (float)(((double)((SInt64)samplesPosted - (SInt64)visSamplesLastPosted)) / [self->visController readSampleRate]);
if (latencyOffset < 0)
latencyOffset = -visLatencyOffset;
visSamplesLastPosted = samplesPosted; visSamplesLastPosted = samplesPosted;
visLatencyOffset += latencyOffset; visLatencyOffset = 0.0;
} }
BOOL invalidateWidth = isFullView && (fabs(analyzerLastWidth - self.bounds.size.width) > 1e-5); [self->visController copyVisPCM:&visAudio[0] visFFT:&visFFT[0] latencyOffset:visLatencyOffset];
if(invalidateWidth)
analyzerLastWidth = self.bounds.size.width;
if(invalidateWidth || invalidateSpectrum) { ddb_analyzer_process(&_analyzer, [self->visController readSampleRate] / 2.0, 1, visFFT, 2048);
[self->visController copyVisPCM:&visAudio[0] visFFT:&visFFT[0] latencyOffset:visLatencyOffset]; ddb_analyzer_tick(&_analyzer);
ddb_analyzer_get_draw_data(&_analyzer, self.bounds.size.width, self.bounds.size.height, &_draw_data);
ddb_analyzer_process(&_analyzer, [self->visController readSampleRate] / 2.0, 1, visFFT, 2048);
ddb_analyzer_tick(&_analyzer);
ddb_analyzer_get_draw_data(&_analyzer, self.bounds.size.width, self.bounds.size.height, &_draw_data);
invalidateSpectrum = NO;
}
if(isFullView) { if(isFullView) {
[self drawSaGrid]; [self drawSaGrid];
@ -461,7 +438,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
_analyzer.mode = freqMode ? DDB_ANALYZER_MODE_FREQUENCIES : DDB_ANALYZER_MODE_OCTAVE_NOTE_BANDS; _analyzer.mode = freqMode ? DDB_ANALYZER_MODE_FREQUENCIES : DDB_ANALYZER_MODE_OCTAVE_NOTE_BANDS;
_analyzer.mode_did_change = 1; _analyzer.mode_did_change = 1;
invalidateSpectrum = YES;
[self repaint]; [self repaint];
} }

View file

@ -39,7 +39,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
NSColor *backgroundColor; NSColor *backgroundColor;
ddb_analyzer_t _analyzer; ddb_analyzer_t _analyzer;
ddb_analyzer_draw_data_t _draw_data; ddb_analyzer_draw_data_t _draw_data;
BOOL invalidateSpectrum;
SCNVector3 cameraPosition2d; SCNVector3 cameraPosition2d;
SCNVector3 cameraEulerAngles2d; SCNVector3 cameraEulerAngles2d;
@ -85,7 +84,7 @@ extern NSString *CogPlaybackDidStopNotificiation;
NSDictionary *sceneOptions = @{ NSDictionary *sceneOptions = @{
SCNPreferredRenderingAPIKey: @(SCNRenderingAPIMetal), SCNPreferredRenderingAPIKey: @(SCNRenderingAPIMetal),
SCNPreferredDeviceKey: device, SCNPreferredDeviceKey: device,
SCNPreferLowPowerDeviceKey: @(YES) SCNPreferLowPowerDeviceKey: @(NO)
}; };
self = [super initWithFrame:frame options:sceneOptions]; self = [super initWithFrame:frame options:sceneOptions];
@ -192,10 +191,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
isListening = NO; isListening = NO;
cameraControlEnabled = NO; cameraControlEnabled = NO;
invalidateSpectrum = YES;
visSamplesLastPosted = [self->visController samplesPosted];
[self setBackgroundColor:[NSColor clearColor]]; [self setBackgroundColor:[NSColor clearColor]];
SCNScene *theScene = [SCNScene sceneNamed:@"Scenes.scnassets/Spectrum.scn"]; SCNScene *theScene = [SCNScene sceneNamed:@"Scenes.scnassets/Spectrum.scn"];
@ -316,38 +311,21 @@ extern NSString *CogPlaybackDidStopNotificiation;
[self updateVisListening]; [self updateVisListening];
if(stopped) { if(stopped) {
if(invalidateSpectrum) { [self drawBaseBands];
[self drawBaseBands];
invalidateSpectrum = NO;
}
return; return;
} }
UInt64 samplesPosted = [self->visController samplesPosted]; UInt64 samplesPosted = [self->visController samplesPosted];
if(!samplesPosted) { if (samplesPosted != visSamplesLastPosted) {
if(invalidateSpectrum) {
[self drawBaseBands];
invalidateSpectrum = NO;
}
return;
}
if(samplesPosted != visSamplesLastPosted) {
float latencyOffset = (float)(((double)((SInt64)samplesPosted - (SInt64)visSamplesLastPosted)) / [self->visController readSampleRate]);
if (latencyOffset < 0)
latencyOffset = -visLatencyOffset;
visSamplesLastPosted = samplesPosted; visSamplesLastPosted = samplesPosted;
visLatencyOffset += latencyOffset; visLatencyOffset = 0.0;
} }
if(invalidateSpectrum) { [self->visController copyVisPCM:&visAudio[0] visFFT:&visFFT[0] latencyOffset:visLatencyOffset];
[self->visController copyVisPCM:&visAudio[0] visFFT:&visFFT[0] latencyOffset:visLatencyOffset];
ddb_analyzer_process(&_analyzer, [self->visController readSampleRate] / 2.0, 1, visFFT, 2048); ddb_analyzer_process(&_analyzer, [self->visController readSampleRate] / 2.0, 1, visFFT, 2048);
ddb_analyzer_tick(&_analyzer); ddb_analyzer_tick(&_analyzer);
ddb_analyzer_get_draw_data(&_analyzer, 11.0, 1.0, &_draw_data); ddb_analyzer_get_draw_data(&_analyzer, 11.0, 1.0, &_draw_data);
invalidateSpectrum = NO;
}
[self drawAnalyzer]; [self drawAnalyzer];
} }
@ -368,10 +346,8 @@ extern NSString *CogPlaybackDidStopNotificiation;
} }
- (void)timerRun:(NSTimer *)timer { - (void)timerRun:(NSTimer *)timer {
invalidateSpectrum = YES;
[self repaint]; [self repaint];
if(visSamplesLastPosted) visLatencyOffset -= 1.0 / 60.0;
visLatencyOffset -= 1.0f / 60.0f;
} }
- (void)startPlayback { - (void)startPlayback {
@ -400,7 +376,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
stopped = YES; stopped = YES;
paused = NO; paused = NO;
bandsReset = NO; bandsReset = NO;
invalidateSpectrum = YES;
[self updateVisListening]; [self updateVisListening];
[self repaint]; [self repaint];
} }
@ -445,13 +420,11 @@ extern NSString *CogPlaybackDidStopNotificiation;
const int barBase = i * barStep; const int barBase = i * barStep;
const int barIndex = barBase + j; const int barIndex = barBase + j;
if(barIndex < _draw_data.bar_count) { if(barIndex < _draw_data.bar_count) {
const float bar_height = bar[barIndex].bar_height; if(bar[barIndex].bar_height > maxValue) {
const float peak_ypos = bar[barIndex].peak_ypos; maxValue = bar[barIndex].bar_height;
if(bar_height > maxValue) {
maxValue = bar_height;
} }
if(peak_ypos > maxMax) { if(bar[barIndex].peak_ypos > maxMax) {
maxMax = peak_ypos; maxMax = bar[barIndex].peak_ypos;
} }
} }
} }
@ -482,7 +455,6 @@ extern NSString *CogPlaybackDidStopNotificiation;
_analyzer.mode = freqMode ? DDB_ANALYZER_MODE_FREQUENCIES : DDB_ANALYZER_MODE_OCTAVE_NOTE_BANDS; _analyzer.mode = freqMode ? DDB_ANALYZER_MODE_FREQUENCIES : DDB_ANALYZER_MODE_OCTAVE_NOTE_BANDS;
_analyzer.mode_did_change = 1; _analyzer.mode_did_change = 1;
invalidateSpectrum = YES;
[self repaint]; [self repaint];
} }