Become a MacRumors Supporter for $50/year with no ads, ability to filter front page stories, and private forums.

ArtOfWarfare

macrumors G3
Original poster
Nov 26, 2007
9,710
6,304
My UI has several split views with sections that can be collapsed, much like Xcode's.

I'm running into several issues implementing toolbar buttons which can collapse the optional subviews, though.

1 - When you click on the toolbar buttons, they (and their background) darken, and vertical bars are added to either side of it.
2 - They don't take on a blue tint, even though they're template images.
3 - This code I found on Stack Overflow didn't do anything useful for me:

Code:
- (IBAction)toggleNavigator:(id)sender {
    [self.navigatorScroller setHidden:![self.navigatorScroller isHidden]];
    [self.verticalSplitter adjustSubviews];
}

It hides and unhides the view, but it doesn't actually expand the other view to fill the newly emptied space. Plus after doing this, dragging on the divider doesn't work.

I see that there are other answers on the question, but they look "hacky" to me, and like code that usually after I write it, I find that other, much simpler, solutions exist.

IE, I spent two hours writing complicated code for giving my split view a minimum size, but then I discovered that simply using ≥ constraints gave me the same thing in seconds instead of hours, and worked much more reliably.

Edit: Fixed #1 by dragging in a Bevel - Toggle button and having it display only an image. I'm guessing the blue tint behavior (#2) in Xcode is probably from an alternate image. I tested and I can make this toggle pretty well.

So my only remaining issue is #3...

Edit 2x: I just realized - when those buttons are pressed in Xcode, the views actually slide in and out - they don't simple appear and disappear.

Edit 3x: So... I decided to turn to objc-runtime.h since NSSplitView's clearly know a thing or two about collapsing their views, and sure enough, I turned up this private method:

_setSubview:isCollapsed:

isCollapsed presumably wants a boolean, but subview is either looking for an index or a view...

Edit 4x: I wrote this code and it works:

Code:
- (IBAction)toggleNavigator:(id)sender {
    NSMethodSignature *signature = [NSSplitView instanceMethodSignatureForSelector:@selector(_setSubview:isCollapsed:)];
    NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:signature];
    invocation.target = self.verticalSplitter;
    invocation.selector = @selector(_setSubview:isCollapsed:);
    [invocation setArgument:&_navigatorScroller atIndex:2];
    BOOL arg = YES;
    [invocation setArgument:&arg atIndex:3];
    [invocation invoke];
}

Now the question is... can I get away with this on the Mac App Store? Perhaps it's possible to decompile the code and replicate it as a non-private method?
 
Last edited:
Register on MacRumors! This sidebar will go away, and you'll see fewer ads.