NSToolbar in Xcode 7 using storyboards (NSWindowController & # 8594; NSSplitViewController)

Hi, I have asked this question several times, but without a definite answer, so I created it for xcode 7 and swift2 (which may have changed the situation a bit).

I created a project using Xcode 7 and the Cocoa OSX Story + swift2 plugins, so my project started with NSWindowController , which connects to NSViewController (as expected!). I added NSToolbar to my window controller and added NSButton to the toolbar. I changed my NSViewController to one of the new NSSplitViewController , which refers to the three NSViewController and displays their views horizontally - with vertical dividers - (similar to the layout that you see in the application or pages in Yosemite +). My ultimate goal will be that the button on the "My" toolbar shows and hides the first split.

This is my understanding, and I would expect that for this I should create an action in the NSSplitViewController that more or less replaces the limitations of the automatic layout in how they work here: How to minimize and expand the view in a Mac application? .

And then somehow connect this action with the NSButton, which is on the toolbar ... which happens to be in the NSWindowController (remotely and isolated in the hierarchy) ...

I already looked at other questions about NSToolbar and storyboards and couldn't complete my task:

  • YouTube Video: Cocoa Programming L17 is NSToolbar , which is closest to solving the problem, but its method does not work for storyboards, creating only your own xib file.
  • In this question: How to use NSToolBar in Xcode 6 and storyboard? One person suggests making a link using the first reviewer, and expects that everything will connect to the launch (which looks a bit quirky, and not how the apple will implement it, I think ...). The second person suggested creating a view controller variable in NSWindowController and manipulating its properties from there ... but again, a bit dodgy.

  • One last comment I saw on this question, which seems to be the best way to solve the problem (but still not as good as I assume it might be), was to add NSObjectController to the dock of each scene and when loading the scene set the values ​​of the objects to another selenium controller. Is this really the best way to go next? If so, how can I achieve this?

Apple mentioned (once again) in WWDC15 that they created storyboards for osx and a split view controller that owns view controllers so that you can move your logic and work with a specific view controller, so I would expect to do everything from inside my controller with a split image as it is the goal that needs to be changed.

Does anyone know how to achieve this from the controller itself? I really could not find a way to associate my ToolBarItem with it.

+8
swift xcode7 macos nstoolbar nssplitviewcontroller
source share
3 answers

Well, I created this question just recently, and there is no answer yet, so I respond with what I recently did to overcome this problem.

After creating my Xcode project, I did the following:

  • Created a subclass of MySplitViewController for NSSplitViewController
  • Added IBOutlet for each NSSplitViewItem. For example:

    @IBOutlet weak var mySplitViewItem: NSSplitViewItem!

  • Subclass WindowController for NSWindowController created

  • Added IBAction in the WindowController class, which refers to NSToolbarItem (my button)
  • Added a property that receives the contents of the Window Controller as MySplitViewController

    var mySplitViewController: MySplitViewController {return self.window? .contentViewController as! MySplitViewController}

  • Now I can access the split view controller property from the Window Controller in the action I created:

    mySplitViewController. mySplitViewItem.collapsed = true

I created some sample code that does this (but using the view controller and changing the text for the label here , just in case someone wants to see a working draft with this behavior. Blog post about this too :)

+3
source share

So, I worked on the same problem and did not find the solution you experienced. I read your post and tried to understand how to implement my decision when it occurred to me to use a notification. After about 30 seconds, I had a perfectly fine working solution:

In your Controller window add IBAction to post such a notification

-(IBAction)toggleMasterViewClicked:(id)sender { [[NSNotificationCenter defaultCenter] postNotificationName:@"TestNotification" object:nil]; } 

Connect this action to your NSToolbarItem , then in the viewController add yourself as an observer for this notification, for example:

 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(toggleMasterView:) name:@"TestNotification" object:nil]; 

In your case, the selector will be updateMyLabelText

Here I do not see a lack. Reference to other objects is not required, without dependencies. Works flawlessly for me

0
source share

One person suggests making a link using the first reviewer, and expects that everything will connect at runtime (which looks a bit quirky, not how the apple will implement it, I think ...).

I think this first answer method really is the right way.

As an example:

Add something similar to the following, depending on which view controller makes sense.

 @IBAction func doSomething(_ sender: AnyObject?) { print("Do something.") } 

This will magically appear in the first responder:

enter image description here

In your storyboard, right-click the orange “first responder” icon above your window controller and you should see doSomething in a very long list. You just need to connect this to your toolbar.

In the next screen capture, you can see that my Toggle Sidebar button is connected to the toggleSidebar action in my first responder.

enter image description here

I didn’t even have to write this method - it is provided by NSSplitViewController :

  @IBAction open func toggleSidebar(_ sender: Any?) 
0
source share

All Articles