Add configurable framesPerSecond preference for CADisplayLink

Allow users to configure the target frame rate via preferences instead of
hardcoding 30fps. Defaults to 30fps when not specified.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Mousen
2025-12-10 05:17:54 +05:00
parent c8ba31e8c6
commit e62a54a8c4
4 changed files with 32 additions and 9 deletions

View File

@@ -14,7 +14,8 @@
nativeWidth:(size_t)nativeWidth nativeWidth:(size_t)nativeWidth
nativeHeight:(size_t)nativeHeight nativeHeight:(size_t)nativeHeight
renderServerSurface:(IOSurfaceRef)renderServerSurface renderServerSurface:(IOSurfaceRef)renderServerSurface
captureModeBlock:(CaptureMode(^)(void))captureModeBlock; captureModeBlock:(CaptureMode(^)(void))captureModeBlock
preferredFramesPerSecond:(int)preferredFramesPerSecond;
- (void)startFrameLoop; - (void)startFrameLoop;
- (void)stopFrameLoop; - (void)stopFrameLoop;
@end @end

View File

@@ -22,6 +22,9 @@
IOSurfaceRef _renderServerSurface; // Separate surface for CARenderServer (avoids framebuffer locking) IOSurfaceRef _renderServerSurface; // Separate surface for CARenderServer (avoids framebuffer locking)
CaptureMode(^_captureModeBlock)(void); CaptureMode(^_captureModeBlock)(void);
// Frame rate
int _preferredFramesPerSecond;
// Diagnostics // Diagnostics
uint64_t _timerFires; uint64_t _timerFires;
uint64_t _framesRendered; uint64_t _framesRendered;
@@ -40,7 +43,8 @@
nativeWidth:(size_t)nativeWidth nativeWidth:(size_t)nativeWidth
nativeHeight:(size_t)nativeHeight nativeHeight:(size_t)nativeHeight
renderServerSurface:(IOSurfaceRef)renderServerSurface renderServerSurface:(IOSurfaceRef)renderServerSurface
captureModeBlock:(CaptureMode(^)(void))captureModeBlock { captureModeBlock:(CaptureMode(^)(void))captureModeBlock
preferredFramesPerSecond:(int)preferredFramesPerSecond {
if ((self = [super init])) { if ((self = [super init])) {
_q = [[NSOperationQueue alloc] init]; _q = [[NSOperationQueue alloc] init];
_q.maxConcurrentOperationCount = 1; // Serialize to prevent frame queue buildup _q.maxConcurrentOperationCount = 1; // Serialize to prevent frame queue buildup
@@ -59,6 +63,7 @@
_renderServerSurface = renderServerSurface; _renderServerSurface = renderServerSurface;
_captureModeBlock = [captureModeBlock copy]; _captureModeBlock = [captureModeBlock copy];
_preferredFramesPerSecond = preferredFramesPerSecond;
} }
return self; return self;
} }
@@ -155,7 +160,7 @@
dispatch_async(dispatch_get_main_queue(), ^{ dispatch_async(dispatch_get_main_queue(), ^{
_displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(_updateFrame)]; _displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(_updateFrame)];
_displayLink.preferredFramesPerSecond = 30; _displayLink.preferredFramesPerSecond = _preferredFramesPerSecond;
[_displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes]; [_displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
}); });
} }

View File

@@ -10,6 +10,7 @@
@implementation ScreenDumpVNC { @implementation ScreenDumpVNC {
int _prefsHeight; int _prefsHeight;
int _prefsWidth; int _prefsWidth;
int _prefsFramesPerSecond;
bool _enabled; bool _enabled;
NSString *_password; NSString *_password;
rfbScreenInfoPtr _rfbScreenInfo; rfbScreenInfoPtr _rfbScreenInfo;
@@ -90,6 +91,9 @@
NSNumber *enabled = [defaults objectForKey:@"enabled"]; NSNumber *enabled = [defaults objectForKey:@"enabled"];
_enabled = enabled ? [enabled boolValue] : NO; _enabled = enabled ? [enabled boolValue] : NO;
_password = [defaults objectForKey:@"password"]; _password = [defaults objectForKey:@"password"];
NSNumber *framesPerSecond = [defaults objectForKey:@"framesPerSecond"];
_prefsFramesPerSecond = framesPerSecond ? [framesPerSecond intValue] : 30;
} }
-(void)setupVNCAuthentication { -(void)setupVNCAuthentication {
@@ -319,7 +323,8 @@
captureModeBlock:^CaptureMode(void) { captureModeBlock:^CaptureMode(void) {
ScreenDumpVNC *strongSelf = weakSelf; ScreenDumpVNC *strongSelf = weakSelf;
return strongSelf ? strongSelf->_captureMode : CaptureModeCARenderServer; return strongSelf ? strongSelf->_captureMode : CaptureModeCARenderServer;
}]; }
preferredFramesPerSecond:_prefsFramesPerSecond];
} }
-(rfbBool)handleVNCAuthorization:(rfbClientPtr)client data:(const char *)data size:(int)size { -(rfbBool)handleVNCAuthorization:(rfbClientPtr)client data:(const char *)data size:(int)size {

View File

@@ -16,8 +16,6 @@
<dict> <dict>
<key>cell</key> <key>cell</key>
<string>PSGroupCell</string> <string>PSGroupCell</string>
<key>label</key>
<string>General</string>
</dict> </dict>
<dict> <dict>
<key>PostNotification</key> <key>PostNotification</key>
@@ -49,9 +47,7 @@
<key>cell</key> <key>cell</key>
<string>PSGroupCell</string> <string>PSGroupCell</string>
<key>label</key> <key>label</key>
<string>Custom Resolution</string> <string>Performance</string>
<key>footerText</key>
<string>High Resolution Can Be Slow</string>
</dict> </dict>
<dict> <dict>
<key>PostNotification</key> <key>PostNotification</key>
@@ -81,6 +77,22 @@
<key>isNumeric</key> <key>isNumeric</key>
<true/> <true/>
</dict> </dict>
<dict>
<key>PostNotification</key>
<string>com.mousen.screendump/restart</string>
<key>cell</key>
<string>PSEditTextCell</string>
<key>defaults</key>
<string>com.mousen.screendump</string>
<key>key</key>
<string>framesPerSecond</string>
<key>label</key>
<string>Max FPS</string>
<key>default</key>
<integer>30</integer>
<key>isNumeric</key>
<true/>
</dict>
</array> </array>
</dict> </dict>
</plist> </plist>