values passing from one window to other in cocoa application - cocoa

im new in cocoa ..
can any one say how yo pass values fromm one window to other
i tried but windowController
not allowing to create instance of other class

For passing one value to other Window ??
Window is just a view, you pass model's value, not view's values.
So, whenever you need to pass the value, you can use
Notification
Delegate
Shared Class.

Related

How to share model object between view controllers?

I created a basic OS X application with a storyboard to just draw circles in a custom view. The main window contains a NSSplitViewControllercontaining two sub-views (content and side bar like Apple Pages or Numbers have). The content view is a custom subclass of NSView for drawing circles while the side bar view contains standard controls. Both should be bound to a model object which holds the properties like number of circles, diameter and so on.
As I understand both subviews have their own controllers in any case. How do have a data model object (let's call it Circles) which both controllers reference so I can hook up key-value observation for redrawing my custom view on changing the controls' values?
My idea would be to create the model object in the common parent controller and pass it on to the children, but how to set that up in Interface Builder in Xcode 7.2?
Working off my comment. You can use the representedObject property of NSViewController to pass any object along to other view controllers. The one downside to this though is that the property is of type AnyObject? so making that work with Swift can be awkward. In your NSViewController subclass you can make a new property to store the data and give it the correct type, or you could make a protocol to define the computed property that serves as a wrapper around representedObject property.

NSTableView & CoreData: Delete Object at clicked row

I am pretty new to Core Data and am currently working on a small (OSX) app that uses an NSTableView to organise objects. I would now like to delete a row/object with the click of a button on that targeted row.
I access the managed object within the table controller by calling [NSApp managedObjectContext] (still trying to figure out that dependency injection thing) but I can't easily delete an objectAtIndex: like I used to with the array (which has now been replaced by the core data stack, right?).
How do I identify the object to be deleted? And consequently, how can I cleanly remove it from the stack?
This is probably a really basic question but I couldn't find any resources on it. Bindings obviously don't work because the row does not get selected before the click occurs.
Any help is much appreciated!
Bindings would work, in that you could have the button's IBAction query the objectValue for the parent NSTableCellView. Once you have that objectValue, you could call the bound arrayController to delete the object, and then the cell/row would disappear.
So, if you have a tableCellView that has a delete button with an IBAction, within that IBAction, you could get the sender's superview, ensure it's an NSTableCellView, get the objectValue, and call [myArrayController removeObject:...]
As it says in the NSTableCellView class reference:
The objectValue is automatically set by the table when using bindings or is the object returned by the NSTableViewDataSource protocol method tableView:objectValueForTableColumn:row:.
This is actually a typical pattern with views in cocoa. objectValue or often representedObject are properties on the views that refer to the data model objects they represent, so if you have a view pointer from sender on the IBAction, you can get the related data model object. And if you're using bindings and a controller, you can then just have the controller remove that object.
With bindings, you will often create buttons that need IBActions attached, rather than some direct binding. But those IBActions can most definitely interact with the controller and not the view.
And with core data, array controllers are really slick vs. assuming you have to do it all programmatically.

NSArrayController returns null

I have an NSArrayController bound to CoreData in my application. It is also bound to a TableView that displays the data. Two buttons are bound to the ArrayController that add and remove lines. All of this is working as expected. I can add, edit, save, and remove CoreData Entries.
There is a section of my app that is to accept drag and drop operations from files (working). It takes the data from the files, looks for various information, and is to insert this information into the Core Data database via the NSArray Controller.
I have added the class handling the parsing/adding of the file to the database as an object in IB. I created an IBOutlet for the array controller in the class, and bound the controller to the class' referencing outlet.
If I add a button to the interface to directly call the method that adds a custom record to the database, everything works. If the method is called via the drag and drop operation, nothing works, even logging a simple [arrayController className] returns null (though returns NSArrayController as expected when the method is called from the button click).
The only difference I can see is that when accessed through the button click, the method is called directly, while the other way passes through my drag and drop class before loading the parsing class, but I'm completely stuck on how to remedy this situation. I'll be happy to provide code, just not sure which code you'll need.
Any help is appreciated. Thanks!
==================
UPDATE
turns out I was connecting the IBOutlet to a class (a subclass of a view) object in IB instead of to the view itself handling the drops. Connecting these up made things work. Well, not work, I have other issues to iron out now, but the Array controller is now instantiated.
Moved from comment to answer: The array controller you are trying to add stuff is not instantiated. I assume you are not referring to your original NSArrayControllerinstance but maybe a new created one? Probably a problem of communication between your class instances.
Debugging this should be straightforward ... using the debugger. Set a few breakpoints (one at each action the button(s) call, and one at each point where your class instances are meant to talk to each other (your importer and your main controller)). Run, test, step through the code when the debugger breaks at each breakpoint.
My guess: An outlet is not hooked up (is nil) in IB or is not yet reconnected at runtime (see -awakeFromNib and make sure you're not trying to touch an outlet or action that hasn't been fully reconnected from the nib at runtime by the time you're trying to use it).
Something’s not hooked up right, BUT you don’t want to do it this way anyways. There’s no advantage to inserting via an NSArrayController. Just create new objects with NSEntityDescriptions:
+ (id)insertNewObjectForEntityForName:(NSString *)entityName inManagedObjectContext:(NSManagedObjectContext *)context;
And you’re done. If your NSArrayController is hooked up correctly it’ll auto-fetch the new objects at the end of the event so the user will see them “immediately.”

What is the best approach for a multi window document based Cocoa app?

My app - a document based Core Data app - is going through a second iteration and now needs multiple windows to manage several model objects. Currently it manages Events and Locations through one window and one controller. The standard generated document class acts as controller for the main window at the moment.
I now want a separate window for managing Locations model objects. It seems good design to have a separate controller (NSWindowController) for each window, but then I realised that these controllers will not have access to the Managed Object Context, which is required to access the model objects.
What is the best approach here?
EDIT:
I followed ughoavgfhw solution as follows:
Created a new XIB for Locations and added an Array Controller to load Location objects
Created a custom controller ManageLocationsController as a subclass of NSWindowController
Made the custom controller the File Owner in Locations XIB
Mapped the Array Controller's context to File Owner and keyPath document.managedObjectContext
I open the Location window with:
ManageLocationsController *aController = [[ManageLocationsController alloc] initWithWindowNibName:#"ManageLocations"];
[aController showWindow: self];
This is done from EventDocument, which is the default class generated by XCode.
When mapping the Array Controller, this left a round black exclamation mark in the keyPath field and when I open the Location window it throws an exception saying "cannot perform operation without a managed object". Obviously not good. What am I missing?
Using custom window controllers is the best way to do this. A window controller might not have direct access to the managed object context, but it has access to the document, which does. You can access it programmatically using windowController.document.managedObjectContext or from bindings with the key path document.managedObjectContext. If you want to simulate direct access to the managed object context, you could create a readonly property which loads it from the document.
// header
#property (readonly) NSManagedObjectContext *managedObjectContext;
// implementation
- (NSManagedObjectContext *)managedObjectContext {
return self.document.managedObjectContext;
}
+ (NSSet *)keyPathsForValuesAffectingManagedObjectContext {
return [NSSet setWithObject:#"document.managedObjectContext"];
}
The keyPathsForValuesAffectingManagedObjectContext method is used to tell the key-value observing system that any object observing the managedObjectContext property should be notified of changes whenever the paths it returns change.
In order for the window controllers to work properly, they must be added to the document using addWindowController:. If you are creating multiple windows when the document opens, then you should override makeWindowControllers in your document method to create the window controllers, since this will be called automatically at the right time. If you are creating window controllers upon request, you can make them in whatever method you want, just be sure to add them to the document.
[theDocument addWindowController:myNewController];
As for the little black exclamation mark in IB, you will just have to ignore that. The document property of NSWindowController is defined with the type NSDocument, but the managedObjectContext property is defined by the NSPersistentDocument subclass. IB is warning you that the property might not be there, but you know it will be so you can just ignore it.

Cannot pass message (or Call a function) using the outlet of a customized class

When a class is customized, by using its outlet , you cant access its method. Is there any better solution to access the method of a customized class? without posting notification?
To be more specific, sometimes when a Controller Class having outlets of other classes, could
access the method of the corresponding classes. But the reverse is not always true. Why is this behavior?
You don't put a class in an outlet, you put an instance there. That's because a nib never contains classes, only instances.
And you most certainly can send messages to objects in outlet variables. The view, where by “view” I mean the object that's in a controller's outlet, can't talk back to the controller only if the view does not have an outlet of its own that's connected to the controller. So, give the view an outlet to the controller.
Note that the nib system treats outlets as properties, so you'll want the controller's outlet to be retaining (unless the view is a subview of another view, or the content view of a window) and the view's outlet to be non-retaining (assigning). If both properties are retaining, you'll have a retain cycle.

Resources