Using singletons to pass data between views - objective-c

I have a mapView that drops annotations, and the annotations have callouts that pushes a new view to the stack. In the second view, users input text and takes a picture that appears on the view and I want it to be saved once I press the save button. But there will be multiple annotations on the map and I want the data on the second view to be different for each annotation. I was told to use a singleton to do this, and I know how to make one, but I do not know how to make it pass or store the data. Can anyone give me some pointers?

Related

Creating custom combination of widget in Cocoa

I have seen that in Cocoa I can create a custom view using drawing primitives which allows me to draw what I like but at a very low level.
Instead I'd like to create custom widgets using a combination of existing controls. For example:
I'd like to create a table with images and combobox in cells
I'd like to create a custom widget wich is a combination of several (for example a list, a button and combobox)
How can I approach this problem ?
Secondly a typical cocoa developer uses external controls? Is there a repository or a list of interesting external custom controls (commercial or free) ?
I'd like to create a table with images and combobox in cells
There already exists NSImageCell and NSComboBoxCell. Are you sure you need to do anything different?
If the problem is that you want an image and a combo box in the same cell, you will have to subclass NSCell. Currently table views can only contain cells, not views, which makes your life harder (as understanding how cell drawing works is more difficult). That will change in Lion, however, so if you can wait until then, this will become easier!
I'd like to create a custom widget wich is a combination of several (for example a list, a button and combobox)
How is your custom widget different to just placing those three things in the same view?
You could write your own NSView subclass. When it's created, it should create a list, a button and a combobox and add them as subviews to itself. Your NSView subclass should handle the logic of keeping them in sync or doing whatever it is you want them to do. Then, to use this combination control in Interface Builder, you place a Custom View and set its class (rightmost tab of the inspector) to your NSView subclass.
BTW, on a tangent, are you sure you mean combobox? Loads of people coming from Windows get this one wrong. A combobox is a combination of a menu and a text field: it allows the user to enter custom text that is not in the menu. If you just want a dropdown menu of choices (and the user can't enter a custom one), you use an NSPopupButton.
Secondly a typical cocoa developer uses external controls?
Yes, sometimes. Things like BWToolkit can be very useful. There's a lot more that are just floating around mailing lists as code snippets, rather than being cleaned up and put in a library. Search for what you need to do!

How to organize XIB files with many overlapping elements?

I have some XIB files which are very difficult to edit because many of the subviews overlap each other completely. For example, if I position a popup volume slider where it will pop up, it covers some UILabels which become impossible to click. My only chance to be able to edit them is to double-click on them in the Document window tree, move them aside, edit, then move them back. Sometimes there are 3 or more widgets that occupy the same location in the XIB, even though only a few are visible at a time while the application is running.
How are conditionally-visible screen elements actually supposed to be organized?
I would like to be able to hide groups of views to reveal what's beneath them, but I don't see a way to do that in IB.
If I create UIViewControllers for every group, I can edit them in separate windows, but I can't see them in context, and I need a lot of view controllers...
Tip: Hold down shift while right clicking the location of the object you wish to select.
I don't think IB is able to hide groups of views during design-time, but there's no reason you couldn't add that behavior yourself using an IB plugin.

Printing the Data in a NSTableView

How would print what is in my NSTableView? The View uses core data so everything is stored and can be grabbed as an NSArray. But how would I go about printing it out? At the moment when you click the print button it just seems to take a picture of the view and print that.
Yes, this works exactly as documented. The view is asked for its PDF representation (which, for an unmodified table view, is exactly what you see on screen), then this gets printed.
A view's drawing can be customized for printing versus on-screen drawing, but for a table view, this is more trouble than it's worth.
It might be easiest to generate an HTML representation of the table, then print that. You can use WebKit or just a plain NSAttributedString and off-screen NSTextView. The trick there is to generate the HTML, create an attributed string with the HTML data (there's a method just for that), then hand that to the off-screen text view. The text view would be sized as desired, then you just tell it to print. This gives you control over pagination as WebKit doesn't currently support the print-specific parts of CSS (in other words, it's "screen-only").
What I've done is taken the data and drawn it to a NSView based object in a way that the end-user would want to print. The user then prints that. it's in the docs.
I like Joshua Nozzi's idea, probably much simpler than custom drawing...

Cocoa question for displaying images

I was wondering if anyone could tell me if there is a method in Cocoa that will display information (images) on screen when a button is pressed. What I mean is NSLog "prints text" to the console is there a method that displays images just as easily like would -(void)drawView do it? Is it just setNeedsDisplay? I hope this makes sense. I am essentially wanting to know if I can call something that will display an image as easily as you can display/print text to the screen/console.
The Console is text-only, so no, you can't print an image to it the same way you log text. The closest equivalent is to export the image as TIFF data and write that data to a file in the temporary directory.
As for setNeedsDisplay:, that tells AppKit that the view should be told to redraw the next time the window redraws its views. (In other words, it sets the view as needing display—exactly what it says on the box.) Usually, this is because you've changed the model object(s) that the view displays, either by replacing them with other objects or by mutating one or more of their properties.
You would need to have a view to display; an image view would certainly qualify, but if you're looking for the image equivalent to NSLog, this isn't it, unless you don't mind either making a dedicated window just for showing this image or temporarily putting a image view into one of your real windows.
You should take a look at Apple's NSImageView Class Reference.
This a class you can use to display an image in Cocoa.
setNeedsDisplay is a NSView method that tells the graphics renderer it needs to redraw the image because the data has been modified. Presumably because you are using something like Quartz and you have called some custom drawing code. If you are drawing bitmap images then you probably won't need to use this.

Cocoa one row table view or a horizontal list view

Is it posible to use table view to show just one row of a big amount of elements? What I'm looking for is for some kind of horizontal list, like we have in XCode preferences or Aperture image list.
It would behave just like a one columnt table view, but instead of showing the elements vertically, it should be horizontally.
Can you point me to where should I start from?
If you're okay with Leopard-only, The new NSCollectionView supports horizontal display. Just set the collection view's number of rows to 1 in Interface Builder; it'll even handle the horizontal scroll bar for you. The IconCollection sample code provides a simple demonstration of how it works. It's bindings work similarly to a table view's, except instead of rows and columns, each object represented gets an 'item' (an object of type NSCollectionViewItem) that displays it, and those items will be laid out in a grid. The sample code above demonstrates how to set up these 'items' in Interface Builder, which is definitely the easiest way.
With a table view? No. If I'm understanding correctly what you want, in the past I've created my own NSView subclass for this type of control. Define a data source protocol similar to NSTableView, and in your NSView drawRect method, draw the elements in order one by one from left to right. You can either keep track of paging in your control, or put it in a scroll view and resize yourself whenever the number of items changes.
Usually this type of thing starts off pretty simple, and gets a bit complex once you start handling caching, paging, selection, mouse and keyboard input and so on. My advice, start as simple as possible and add new features one by one, only after you've finished the previous task.