diff --git a/glfw/cocoa_init.m b/glfw/cocoa_init.m index 5ca7cfca9..85c86fc70 100644 --- a/glfw/cocoa_init.m +++ b/glfw/cocoa_init.m @@ -992,8 +992,6 @@ void _glfwPlatformTerminate(void) _glfw.ns.appleSettings = nil; } - free(_glfw.ns.clipboardString); - _glfwTerminateNSGL(); if (global_shortcuts != nil) { [global_shortcuts release]; global_shortcuts = nil; } diff --git a/glfw/cocoa_platform.h b/glfw/cocoa_platform.h index 96a3216e2..34e6a515e 100644 --- a/glfw/cocoa_platform.h +++ b/glfw/cocoa_platform.h @@ -183,7 +183,6 @@ typedef struct _GLFWlibraryNS char keyName[64]; char text[256]; - char* clipboardString; CGPoint cascadePoint; // Where to place the cursor when re-enabled double restoreCursorPosX, restoreCursorPosY; diff --git a/glfw/cocoa_window.m b/glfw/cocoa_window.m index 2ab036ba4..5f386fe09 100644 --- a/glfw/cocoa_window.m +++ b/glfw/cocoa_window.m @@ -30,6 +30,8 @@ #include "../kitty/monotonic.h" #include +#import +#import #include #include @@ -2506,55 +2508,51 @@ bool _glfwPlatformToggleFullscreen(_GLFWwindow* w, unsigned int flags) { return made_fullscreen; } -void _glfwPlatformSetClipboardString(const char* string) -{ +// Clipboard {{{ + +static void +list_clipboard_mimetypes(GLFWclipboardwritedatafun write_data, void *object) { +#define w(x) { if (ok) ok = write_data(object, x, strlen(x)); } NSPasteboard* pasteboard = [NSPasteboard generalPasteboard]; - [pasteboard declareTypes:@[NSPasteboardTypeString] owner:nil]; - [pasteboard setString:@(string) forType:NSPasteboardTypeString]; -} - -void _glfwPlatformSetPrimarySelectionString(const char* string) { - (void)string; - // Apple doesnt have a primary selection -} - -const char* _glfwPlatformGetPrimarySelectionString(void) { return ""; } - -const char* _glfwPlatformGetClipboardString(void) -{ - NSPasteboard* pasteboard = [NSPasteboard generalPasteboard]; - free(_glfw.ns.clipboardString); _glfw.ns.clipboardString = NULL; - NSDictionary* options = @{NSPasteboardURLReadingFileURLsOnlyKey:@YES}; - NSArray* objs = [pasteboard readObjectsForClasses:@[[NSURL class], [NSString class]] options:options]; - if (objs) { - const NSUInteger count = [objs count]; - if (count) { - NSMutableString *path_list = [NSMutableString stringWithCapacity:4096]; // auto-released - NSMutableString *text_list = [NSMutableString stringWithCapacity:4096]; // auto-released - for (NSUInteger i = 0; i < count; i++) { - id obj = objs[i]; - if ([obj isKindOfClass:[NSURL class]]) { - NSURL *url = (NSURL*)obj; - if (url.fileURL && url.fileSystemRepresentation) { - if ([path_list length] > 0) [path_list appendString:@("\n")]; - [path_list appendString:@(url.fileSystemRepresentation)]; + BOOL has_file_urls = [pasteboard canReadObjectForClasses:@[[NSURL class]] options:options]; + BOOL has_strings = [pasteboard canReadObjectForClasses:@[[NSString class]] options:nil]; + /* NSLog(@"has_file_urls: %d has_strings: %d", has_file_urls, has_strings); */ + bool ok = true; + if (has_strings) w("text/plain"); + if (has_file_urls) w("text/local-path-list"); + if (@available(macOS 11.0, *)) { + for (NSPasteboardItem * item in pasteboard.pasteboardItems) { + for (NSPasteboardType type in item.types) { + /* NSLog(@"%@", type); */ + UTType *ut = [UTType typeWithIdentifier:type]; + if (ut != nil) { + /* NSLog(@"ut: %@ mt: %@ tags: %@", ut, ut.preferredMIMEType, ut.tags); */ + if (ut.preferredMIMEType != nil && ![ut.preferredMIMEType hasPrefix:@"text/plain"]) { + w([ut.preferredMIMEType UTF8String]); } - } else if ([obj isKindOfClass:[NSString class]]) { - if ([text_list length] > 0) [text_list appendString:@("\n")]; - [text_list appendString:obj]; } } - const char *text = NULL; - if (path_list.length > 0) text = [path_list UTF8String]; - else if (text_list.length > 0) text = [text_list UTF8String]; - if (text) _glfw.ns.clipboardString = _glfw_strdup(text); } } - if (!_glfw.ns.clipboardString) _glfwInputError(GLFW_PLATFORM_ERROR, "Cocoa: Failed to retrieve object from pasteboard"); - return _glfw.ns.clipboardString; +#undef w } +void +_glfwPlatformGetClipboard(GLFWClipboardType clipboard_type, const char* mime_type, GLFWclipboardwritedatafun write_data, void *object) { + if (clipboard_type != GLFW_CLIPBOARD) return; + (void)mime_type; (void) write_data; (void) object; + if (mime_type == NULL) { + list_clipboard_mimetypes(write_data, object); + return; + } +} + +void _glfwPlatformSetClipboard(GLFWClipboardType t) { + if (t != GLFW_CLIPBOARD) return; +} +// }}} + EGLenum _glfwPlatformGetEGLPlatform(EGLint** attribs) { if (_glfw.egl.ANGLE_platform_angle) diff --git a/glfw/glfw.py b/glfw/glfw.py index 4c23a15d5..32529a7e7 100755 --- a/glfw/glfw.py +++ b/glfw/glfw.py @@ -111,7 +111,7 @@ def init_env( elif module == 'cocoa': ans.cppflags.append('-DGL_SILENCE_DEPRECATION') - for f_ in 'Cocoa IOKit CoreFoundation CoreVideo'.split(): + for f_ in 'Cocoa IOKit CoreFoundation CoreVideo UniformTypeIdentifiers'.split(): ans.ldpaths.extend(('-framework', f_)) elif module == 'wayland': diff --git a/kitty/boss.py b/kitty/boss.py index e1bbb6a05..39a3aea8c 100644 --- a/kitty/boss.py +++ b/kitty/boss.py @@ -288,6 +288,7 @@ class Boss: cocoa_set_notification_activated_callback ) cocoa_set_notification_activated_callback(notification_activated) + print(111111111, self.clipboard.get_available_mime_types_for_paste()) def update_keymap(self) -> None: self.keymap = get_options().keymap.copy()