Post

Replies

Boosts

Views

Activity

Reply to SwiftUI List on maCOS: highlighting content in the selected row?
This is a macOS related thing. I have chased this forever in vain. This is akin to NSCell.isHighlighted or NSCell.backgroundStyle I for sure want to use some special colors when not in highlight mode. A cell will be first highlighted in mouse down and than eventually selected on mouse up. So apple has to provide an API or an environment value to indicate to our row view that is highlighted or not. Maybe @eskimo can look up the source for this and shed some deep insight.
Jan ’23
Reply to WindowGroup bug??? Can't maximize window after minimizing
This is a known bug and has been fixed on Xcode 14, beta 5 and macOS 13. If you need this feature on older systems, such as macOS 11 + you will need to go back and use a MainMenu.xib and an AppDelegate struct SwiftUIView: View {     var body: some View {         Text("Hello, SwiftUI!")             .frame(maxWidth: .infinity, maxHeight: .infinity)     } } @main class AppDelegate: NSObject, NSApplicationDelegate {     @IBOutlet var window: NSWindow!     func applicationDidFinishLaunching(_ aNotification: Notification) {         // Insert code here to initialize your application         window = NSWindow(             contentRect: NSRect(x: 0, y: 0, width: 480, height: 270),             styleMask: [.miniaturizable, .closable, .resizable, .titled],             backing: .buffered, defer: false)         window.center()         window.title = "No Storyboard Window"         window.contentView = NSHostingView(rootView: SwiftUIView())         window.makeKeyAndOrderFront(nil)     }     func applicationWillTerminate(_ aNotification: Notification) {         // Insert code here to tear down your application     }     func applicationSupportsSecureRestorableState(_ app: NSApplication) -> Bool {         return true     } }
Aug ’22
Reply to WindowGroup bug??? Can't maximize window after minimizing
Small world. I have been banging my head for hours on this. I have a real SwiftUI app, with one Window. When this Window (mainWindow/keyWindow) is minimized an icon is added on the dock. Now if i click on the app icon, i expect this minimized window to expand again. But it does not. If i switch to another app and than click on the app icon on the doc, the minimized window is expanded as expected. It appears the app thinks it is still active applicationDidResignActive: is not called. @eskimo What magic is going on pls ?
Aug ’22
Reply to getattrlistbulk inode
These are special links, indeed, I knew a few under /Volume/ were mounts, but forgot that some others are also links such as /Applications [macos-bigsur]/usr/local> ls -ail /         12886009979 drwxrwxr-x   7 root  admin   224 Feb  4 11:00 Applications/ [macos-bigsur]/usr/local> ls -ail /System/Volumes/Data/         12886009979 drwxrwxr-x    7 root  admin    224 Feb  4 11:00 Applications/ /Applications to /System/Volumes/Data/Applications My problem comes from inconsistent results of stat() vs getattrlistbulk() Now if I could just figure that out :-)
Feb ’22
Reply to getattrlistbulk inode
- (IDDNode*)_fetchChild:(char**)entry_start :(NSString*)parentPath :(uint64)pnode { IDDNodeAttribute attribute; char* field = *entry_start; attribute.length = *(uint32_t *)field; field += sizeof(uint32_t); *entry_start += attribute.length; attribute.returned = *(attribute_set_t *)field; field += sizeof(attribute_set_t); if (attribute.returned.commonattr & ATTR_CMN_NAME) { attribute.name = field; attribute.name_info = *(attrreference_t *)field; field += sizeof(attrreference_t); // DEBUG NSString* childPath = [parentPath stringByAppendingPathComponent:[NSString stringWithUTF8String:(attribute.name + attribute.name_info.attr_dataoffset)]]; _logInfo(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@'", childPath]); } if (attribute.returned.commonattr & ATTR_CMN_FSID) { attribute.fsid = *(fsid_t *)field; field += sizeof(fsid_t); int32_t fileSystemID = (int32_t)attribute.fsid.val[0]; // DEBUG NSString* childPath = [parentPath stringByAppendingPathComponent:[NSString stringWithUTF8String:(attribute.name + attribute.name_info.attr_dataoffset)]]; _logInfo(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@' fileSystemID: '%d'", childPath, fileSystemID]); } if (attribute.returned.commonattr & ATTR_CMN_OBJTYPE) { attribute.obj_type = *(fsobj_type_t *)field; field += sizeof(fsobj_type_t); // DEBUG NSString* childPath = [parentPath stringByAppendingPathComponent:[NSString stringWithUTF8String:(attribute.name + attribute.name_info.attr_dataoffset)]]; _logInfo(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@' type: '%@'", childPath, [self _fileType:attribute.obj_type]]); } if (attribute.returned.commonattr & ATTR_CMN_MODTIME) { struct timespec time = *(struct timespec*)field; field += sizeof(struct timespec); NSDate* modificationDate = [NSDate dateWithTimeIntervalSince1970:time.tv_sec]; // DEBUG NSString* childPath = [parentPath stringByAppendingPathComponent:[NSString stringWithUTF8String:(attribute.name + attribute.name_info.attr_dataoffset)]]; _logInfo(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@' modificationDate: '%@'", childPath, modificationDate]); } if (attribute.returned.commonattr & ATTR_CMN_FILEID) { attribute.inode = *(uint64_t *)field; // DEDA DEBUG struct stat file_status; NSString* childPath = [parentPath stringByAppendingPathComponent:[NSString stringWithUTF8String:(attribute.name + attribute.name_info.attr_dataoffset)]]; _logInfo(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@' inode: '%lld'", childPath, attribute.inode]); if (lstat((const char *)[childPath fileSystemRepresentation], &file_status) == 0) { int64_t inode2 = file_status.st_ino; if (attribute.inode != inode2) { _logError(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@' inode mismatch: '%lld'", childPath, inode2]); } else { _logInfo(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"filePath: '%@' inode match: '%lld'", childPath, inode2]); } } field += sizeof(uint64_t); } return nil; }
Feb ’22
Reply to getattrlistbulk inode
typedef struct IDDNodeAttribute { uint32_t length; // ATTR_BIT_MAP_COUNT attribute_set_t returned; // ATTR_CMN_RETURNED_ATTRS char *name; attrreference_t name_info; // ATTR_CMN_NAME fsid_t fsid; // ATTR_CMN_FSID fsobj_type_t obj_type; // ATTR_CMN_OBJTYPE struct timespec modtime; // ATTR_CMN_MODTIME uint64_t inode; // ATTR_CMN_FILEID struct { u_int32_t link_count; // ATTR_FILE_LINKCOUNT off_t alloc_size; // ATTR_FILE_ALLOCSIZE off_t total_size; // ATTR_FILE_TOTALSIZE }; } __attribute__((aligned(4), packed)) IDDNodeAttribute; // buffer to place our results const int IDDNodeAttributeBufferSize = 32 * sizeof(IDDNodeAttribute); struct attrlist attrList = { .bitmapcount = ATTR_BIT_MAP_COUNT, .commonattr = ATTR_CMN_RETURNED_ATTRS | ATTR_CMN_NAME | ATTR_CMN_FSID | ATTR_CMN_OBJTYPE | ATTR_CMN_MODTIME | ATTR_CMN_FILEID, .dirattr = ATTR_DIR_ENTRYCOUNT, .fileattr = ATTR_FILE_LINKCOUNT | ATTR_FILE_ALLOCSIZE | ATTR_FILE_TOTALSIZE }; int itemCount = getattrlistbulk(dirfd, &attrList, attrBuf, IDDNodeAttributeBufferSize, 1); if (itemCount == -1) { _logError(NSStringFromSelector(_cmd), [NSString stringWithFormat:@"error: '%ld = %s' path: '%s'", (long)errno, strerror(errno), path]); break; } else if (itemCount == 0) { break; } else { char* entry_start = attrBuf; for (int index = 0; index < itemCount; index++) { IDDNode* child = [self _fetchChild:&entry_start :filePath :pnode]; if (child) { [rv addObject:child]; } } }
Feb ’22
Reply to getattrlistbulk inode
Interesting ... Here are some examples inode mismatch: '/Applications ' ' 1152921500311879699' vs ' 78133671' inode mismatch: '/Library ' ' 1152921500311879700' vs ' 78110879' inode mismatch: '/System/Library/Assets ' ' 1152921500312008804' vs ' 78132729' inode mismatch: '/System/Library/AssetsV2 ' ' 1152921500312008805' vs ' 78131512' inode mismatch: '/System/Library/Caches ' ' 1152921500312115767' vs ' 78132730' inode mismatch: '/System/Library/Speech ' ' 1152921500312658038' vs ' 78131497' inode mismatch: '/System/Volumes/Data ' ' 1152921500312709177' vs ' 1152921500311879682' inode mismatch: '/System/Volumes/Preboot ' ' 1152921500312709197' vs ' 2' inode mismatch: '/System/Volumes/Update ' ' 1152921500312709199' vs ' 2' inode mismatch: '/System/Volumes/VM ' ' 1152921500312709200' vs ' 2' inode mismatch: '/Users ' ' 1152921500312764772' vs ' 319' inode mismatch: '/Volumes ' ' 1152921500312764773' vs ' 320' inode mismatch: '/Volumes/970Raid ' ' 78720565' vs ' 2' inode mismatch: '/Volumes/Macintosh HD ' ' 78716885' vs ' 2' inode mismatch: '/Volumes/Macintosh HD - Data ' ' 78716879' vs ' 2' inode mismatch: '/Volumes/TimeMachine ' ' 78716884' vs ' 2' inode mismatch: '/Volumes/Vault ' ' 78716876' vs ' 2' inode mismatch: '/cores ' ' 1152921500312764847' vs ' 321' inode mismatch: '/dev ' ' 1152921500312764848' vs ' 388' inode mismatch: '/opt ' ' 1152921500312764850' vs ' 324' inode mismatch: '/private ' ' 1152921500312764851' vs ' 78132742' inode mismatch: '/usr/libexec/cups ' ' 1152921500312768002' vs ' 78110424' inode mismatch: '/usr/local ' ' 1152921500312773577' vs ' 78110530' inode mismatch: '/usr/share/snmp ' ' 1152921500312787193' vs ' 78110532' /Volumes/$* are mounts. The left column is the 'inode' from getattrlistbulk The right is the 'inode' as I fetch using lstat
Feb ’22
Reply to When does backgroundStyle on NSTextfield change its textColor?
This magic is frustrating when it does not work. I have a SwiftUI view (PhysicalSize) wrapped in NSHostingView that is placed inside a NSTableCellView. I have set a custom NSTableRowView on the NSTableView and AppKit is setting the proper isEmphasized status when the row is selected. Good. Then I'm setting the backgroundStyle of the cells to .emphasized Good. However the swift UI is absolutely unaware, that we are being drawn in highlighted mode and the Text color does invert. Not good. Can some apple genius chime in here. struct PhysicalSize: View {     var file: File     var body: some View {         HStack {             Spacer()             Text(file.physicalSize.compactFormatted)                 .font(.subheadline)         }     } }
Dec ’21
Reply to EXC_BAD_INSTRUCTION SIGILL
The ATTR_CMN_ERROR is not triggered. As as soon as we hit this particular folder boom, we manage to collect ATTR_CMN_NAME, ATTR_CMN_FSID and ATTR_CMN_OBJTYPE and than as soon as we attempt to fetch the ATTR_CMN_MODTIME, boom. So we are crashing on the same darn portion. Maybe I should revert this module back to the c version.             let modTimeInSeconds: Int32 = {                 if (returned.commonattr & attrgroup_t(bitPattern: ATTR_CMN_MODTIME)) != 0 {                     aligningBuffer.copyMemory(from: UnsafeRawBufferPointer(start: field, count: MemoryLayout<timespec>.size))                     let time = aligningBuffer.baseAddress!.load(as: timespec.self)                     // the following will fails cause of memory misalignment                     // let time = field.load(as: timespec.self)                     field += MemoryLayout<timespec>.size                     return Int32(time.tv_sec)                 }                 return 0             }()
Nov ’21
Reply to EXC_BAD_INSTRUCTION SIGILL
I could share some more code on a direct message basis, it you are up for a challenge. My pain is that I can't reproduce it. It just happens on a few 'lucky' customer machines. And these machines are recent. No old software or old file systems. I will add the 'ATTR_CMN_ERROR' and see if that will prevent me from digging deeper into trouble. It is possible these troubled folders are returning some error and instead of bailing out early I'm continuing to read the rest of the pointer. This class, the one that uses the getattrlistbulk was my last one to move to swift. The previous version using Objective-C was working. Mixing both obj-c and swift requires much more mental effort. Imagine speaking English and French in the same conversation randomly. Maybe I should eat it and revert this back the C base implementation. Again thank you very much for the tips. Klajd Deda let myEmail = "kdeda" + "@" + "mac.com"
Nov ’21
Reply to EXC_BAD_INSTRUCTION SIGILL
Went through the entire process of fully symbolicating a crash. And I was rewarded with some more gold nuggets. NodeFactory.appendChildren(_:_:_:_:_:_:) (in com.id-design.v7.whatsizehelper) (NodeFactory.swift:256) let modTimeInSeconds: Int32 = {}() is obviously crashing. Also another clue, it crashes always on the same folder. So the meta data for this folder is 'wrong' ?             let modTimeInSeconds: Int32 = {                 if (returned.commonattr & attrgroup_t(bitPattern: ATTR_CMN_MODTIME)) != 0 {                     aligningBuffer.copyMemory(from: UnsafeRawBufferPointer(start: field, count: MemoryLayout<timespec>.size))                     let time = aligningBuffer.baseAddress!.load(as: timespec.self)                     // the following will fails cause of memory misalignment                     // let time = field.load(as: timespec.self)                     field += MemoryLayout<timespec>.size                     return Int32(time.tv_sec)                 }                 return 0             }()
Nov ’21