Apple Interface Builder UserGuide
Apple Interface Builder UserGuide
2010-07-12
Apple Inc. 2010 Apple Inc. All rights reserved. No part of this publication may be reproduced, stored in a retrieval system, or transmitted, in any form or by any means, mechanical, electronic, photocopying, recording, or otherwise, without prior written permission of Apple Inc., with the following exceptions: Any person is hereby authorized to store documentation on a single computer for personal use only and to print copies of documentation for personal use provided that the documentation contains Apples copyright notice. The Apple logo is a trademark of Apple Inc. Use of the keyboard Apple logo (Option-Shift-K) for commercial purposes without the prior written consent of Apple may constitute trademark infringement and unfair competition in violation of federal and state laws. No licenses, express or implied, are granted with respect to any of the technology described in this document. Apple retains all intellectual property rights associated with the technology described in this document. This document is intended to assist application developers to develop applications only for Apple-labeled computers. Every effort has been made to ensure that the information in this document is accurate. Apple is not responsible for typographical errors. Apple Inc. 1 Infinite Loop Cupertino, CA 95014 408-996-1010 .Mac is a registered service mark of Apple Inc. Apple, the Apple logo, AppleScript, Bonjour, Carbon, Cocoa, Cocoa Touch, Finder, iPhone, iPod, iPod touch, Mac, Mac OS, Objective-C, Quartz, and Xcode are trademarks of Apple Inc., registered in the United States and other countries. iPad is a trademark of Apple Inc. IOS is a trademark or registered trademark of Cisco in the U.S. and other countries and is used under license. OpenGL is a registered trademark of Silicon Graphics, Inc.
Contents
Introduction
Introduction 13
Who Should Read This Document? 13 Organization of This Document 13 Platform and Language Support 14 Getting Interface Builder 14 Reporting Bugs 14 See Also 15
Chapter 1
Chapter 2
3
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CONTENTS
Chapter 3
Chapter 4
Nib Objects 55
iOS Interface Objects 55 Windows 55 Views and Controls 56 Custom Views 57 Toolbars 58 Controller Objects 60 View Controllers 61 Tab Bars 63 Navigation Bars 67 Mac OS X Interface Objects 71 Windows and Panels 72 Views 73 Custom Views 74 Controls and Cells 74 Custom Cells 75 Toolbars 75 Menus and Menu Items 78 Collection Views 80 Controller Objects 80 View Controllers 81 Core Data Objects 82 Formatter Objects 83 Placeholder Objects 83 Files Owner 83 First Responder 85 Application 85 Custom Placeholder Objects 85 Finding Objects in a Nib File 86 Tips for Organizing Your Nib Objects 86
4
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CONTENTS
Interface Layout 89
Layout Tools 89 Moving and Sizing Objects 89 Moving Views 90 Resizing Views 91 Moving and Resizing Windows 92 Changing the Size of a Control 94 Setting a Views Autosizing Behavior 94 Design-Time Resizing Modes for Windows 95 Aligning Objects 95 About Alignment Guides 96 Aligning Objects Relative to One Another 96 Displaying Bounding and Layout Rectangles 97 Getting Dynamic Layout Information 98 Using Custom Guides 100 Changing the Window Orientation in iOS 100 Managing Parent-Child View Relationships 101 Embedding Views in a Parent Container 102 Changing a Views Parent to Another View 102 Using ibtool to Gather Layout Metrics 102 Tips for Creating Effective Layouts 103 Follow the Automatic Guides 103 Use Proper Alignment for Labels and Controls in Mac OS X 103 Group Related Controls in Mac OS X 104
Chapter 6
5
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CONTENTS
Assigning Command IDs to Objects 115 Assigning a Signature and Control ID 115 Adding Auxiliary Properties 116 Adding Custom HIView Parameters 116 Attribute Guidelines 116 Use Consistent Control Sizes in Mac OS X 117 Assign Names to Your Objects 117 Chapter 7
Chapter 8
Chapter 9
6
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CONTENTS
Localization 153
Locking Down Your Nib File 153 Localizing Your Nib Files Content 154 Performing the Initial Localization of a Nib File 155 Performing Incremental Localization Updates 155
Chapter 11
Appendix A
7
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CONTENTS
8
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
Chapter 2
Chapter 4
Nib Objects 55
Figure 4-1 Figure 4-2 Figure 4-3 Figure 4-4 Figure 4-5 Figure 4-6 Figure 4-7 Figure 4-8 Figure 4-9 Figure 4-10 Figure 4-11 Figure 4-12 Figure 4-13 Custom UIView object 58 Bar button items in a toolbar 59 Controllers and custom objects in Cocoa Touch nib files 61 View controller editor window 62 Interface modes of the Clock application 63 A tab bar controller and its default set of objects 63 Tab bar controller editor window 64 Components of a navigation bar interface 67 A navigation controller and its default set of objects 68 Navigation controller editor window 69 Custom NSView object 74 Adding a toolbar to a window 76 Customizing a toolbar 76
9
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
Menu objects in the library 78 Controllers and custom objects 81 Core Data objects 83 Typical classes used for Files Owner 84
Interface Layout 89
Figure 5-1 Figure 5-2 Figure 5-3 Figure 5-4 Figure 5-5 Figure 5-6 Figure 5-7 Figure 5-8 Figure 5-9 Figure 5-10 Figure 5-11 Table 5-1 Table 5-2 The Size pane of the inspector 90 Examples of selection handles 91 A resize operation 92 Size inspector for windows 93 Configuring the autosizing rules of a view 95 Alignment controls in the Size pane of the inspector 97 Bounding and layout rectangles for a window 98 Option dragging a control 99 Showing the distance between two views 99 Custom layout guides 100 Changing the orientation of an iPhone window 101 Tools to help with laying out user interfaces 89 Techniques for grouping controls 104
Chapter 6
Chapter 7
Chapter 8
10
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
Chapter 10
Localization 153
Figure 10-1 Table 10-1 Merging changes into a localized nib file 156 Locking options for nib-file objects 153
Chapter 11
11
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
12
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
INTRODUCTION
Introduction
Interface Builder is a visual design tool you use to create the user interfaces of your iOS and Mac OS X applications. Using the graphical environment of Interface Builder, you assemble windows, views, controls, menus, and other elements from a library of configurable objects. You arrange these items, set their attributes, establish connections between them, and then save them in a special type of resource file, called a nib file. (The term nib is historical and is an acronym for NextSTEP Interface Builder.) A nib file stores your objects, including their configuration and layout information, in a format that at runtime can be used to recreate the actual objects.
Interface Builder Quick Start (page 17) gives you a quick tour of Interface Builder, including a hands-on tutorial. Interface Builder Basic Concepts (page 33) provides an overview of Interface Builder and the role of nib files in your applications. Xcode Integration (page 139) provides an overview of how nib files integrate with your Xcode projects. Nib File Management (page 47) shows you how to create and save nib files and how to work with them in your projects. Nib Objects (page 55) describes the types of objects you can add to nib files and when you might want to do so. Interface Layout (page 89) describes techniques for organizing window and view hierarchies and for adjusting the layout of individual objects. Object Attributes (page 105) describes the techniques for configuring the objects in your nib file with custom attributes. Connections and Bindings (page 119) describes the role of connections in nib files and how to configure outlets, actions, and bindings. Testing and Validation (page 149) describes the tools available for testing your nib file contents and ensuring your nib file works properly with your Xcode project.
13
INTRODUCTION
Introduction
Localization (page 153) describes the tools and processes for localizing the contents of a nib file. Interface Builder Customization (page 159) describes the ways in which you can change the Interface Builder environment to suit your personal tastes. Interface Builder Gesture Guide (page 169) summarizes the keyboard and mouse actions you can use to make connections, execute commands, and so on.
The Glossary at the end contains a list of Interface Builder terms and their definitions.
Reporting Bugs
If you encounter bugs in Apple software or documentation, you are encouraged to report them to Apple. You can also file enhancement requests to indicate features you would like to see in future revisions of a product or document. To file bugs or enhancement requests, go to the Bug Reporting page of the ADC website, which is at the following URL: http://developer.apple.com/bugreporter/
14
INTRODUCTION
Introduction
You must have a valid ADC login name and password to file bugs. You can obtain a login name for free by following the instructions found on the Bug Reporting page.
See Also
For information on how to use nib files at runtime, including how to load them from your code, see Resource Programming Guide.
See Also
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
15
INTRODUCTION
Introduction
16
See Also
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 1
Interface Builder is Apple's graphical editor for designing and testing application user interfaces. This chapter provides a quick tour of Interface Builder, including a hands-on tutorial. If you have used Interface Builder before, you may want to proceed to the next chapter, Interface Builder Basic Concepts (page 33). Note: Interface Builder is included in the Xcode toolset. You can download the latest version of Xcode from the Apple Developer website (http://developer.apple.com/). Registration is required but free.
You can open Interface Builder by double-clicking its application icon in the Finder. The Interface Builder application is located in <Xcode>/Applications, where <Xcode> is the root directory of your Xcode installation. (The default root directory for an Xcode installation is the /Developer directory.) You can open Interface Builder by double-clicking an Interface Builder document in the Finder. Interface Builder documents are files with the extension .nib or .xib. These documents are often referred to as nib files. You can open Interface Builder by double-clicking the name of an Interface Builder document in an Xcode project window.
17
CHAPTER 1
Figure 1-1
For each new document you create, Interface Builder prompts you to select a starting template. These templates define the initial set of objects to use in your document. Interface Builder provides several different templates, listed in Table 1-1, each geared toward a different goal. You can use the Empty template if you want to add a specific set of objects to your document manually. For any of the templates, you can also remove objects you do not want. Table 1-1 Interface Builder document templates Description
Application Creates a document you can use to design an interface for a Cocoa Touch application. The document includes a window. View Creates a document you can use to design a view for a Cocoa Touch application. Creates a document you can use to design a window for a Cocoa Touch application. Creates a document to which you can add your own interface objects. To learn how to select and add these objects, see Workflow Tools (page 35).
Window
Empty
iOS
iPad
Application Creates a document suitable for creating an iPad application, including an application delegate and window. View Creates a document you can use to design a view for an iPad application.
18
CHAPTER 1
Description Creates a document you can use to design a window for an iPad application. Creates a document to which you can add your own interface objects. To learn how to select and add these objects, see Workflow Tools (page 35).
Empty
Mac OS X Cocoa
Application Creates a document you can use to design an interface for a Cocoa application. The document includes a menu bar and a window. Main Menu Creates a document you can use to design a menu bar for a Cocoa application. View Creates a document you can use to design a view for a Cocoa application. Creates a document you can use to design a window for a Cocoa application. Creates a document to which you can add your own interface objects. To learn how to select and add these objects, see Workflow Tools (page 35).
Window
Empty
Mac OS X Carbon
Application Creates a document you can use to design an interface for a Carbon application. The document includes a menu bar and a window. Dialog Creates a document you can use to design a dialog for a Carbon application.
Main Menu Creates a document you can use to design a menu bar for a Carbon application. Window Creates a document you can use to design a window for a Carbon application. Creates a document to which you can add your own interface objects. To learn how to select and add these objects, see Workflow Tools (page 35). Creates a document you can use to design an inspector for an Interface Builder plug-in.
Empty
Inspector
Library
Creates a document you can use to design library components for an Interface Builder plug-in.
19
CHAPTER 1
20
CHAPTER 1
Figure 1-3
21
CHAPTER 1
Figure 1-4
22
CHAPTER 1
Note: To complete this tutorial, youll need to install Mac OS X v10.6 or later and Xcode 3.2 or later.
23
CHAPTER 1
a. b. c. d. e. f. 3.
In the Groups & Files list, open the Targets group and select the QCDemo target. Press Command-I to display the Target Info window. Click General. Under linked libraries, click the plus (+) button. A dialog appears with a list of libraries. Choose Quartz.framework from the list and click the Add button. Close the Target Info window.
Open The QCDemo projects Interface Builder document. a. b. c. In the projects Groups & Files list, open the Resources group. Find the file MainMenu.xib. Double-click MainMenu.xib to open the document.
4.
Set the size attributes of the QCDemo window. a. b. c. d. e. In the document window, select the window object. Press Command-3 to open the Size pane of the inspector window. Set the windows width and height to 480 x 420. Select the Minimum Size option. Set the minimum size to the current size by clicking the Use Current button.
5.
Add a Quartz Composer view to the QCDemo window. a. b. c. Press Command-Shift-L to open the Library window. Click Objects and enter quartz in the search field at the bottom of the window. Drag the Quartz Composer view object from the Library window to the QCDemo window.
6.
Set the size attributes of the Quartz Composer view. a. b. c. d. In the QCDemo window, select the Quartz Composer view object. Press Command-3 to open the Size pane of the inspector window. Set the views position X and Y to 0 x 60. Set the views width and height to 480 x 360.
24
CHAPTER 1
e.
Set the views autosizing control as shown in Figure 1-7. To learn more about this control, see Setting a Views Autosizing Behavior (page 94).
Figure 1-7
7.
Select an initial composition for the Quartz Composer view. a. b. c. d. In the QCDemo window, select the Quartz Composer view object. Press Command-1 to open the Attributes pane of the inspector window. Click the Load button. Select the composition at the following location:
/System/Library/Screen Savers/Shell.qtz
8. 9.
Save the Interface Builder document. Run a simulation of the QCDemo user interface. a. b. c. Press Command-R to start the simulation and display the composition. Try resizing the QCDemo window and observe what happens to the composition. Press Command-Q to quit the simulation.
10. In Xcode, build and run the QCDemo application. a. Click Build and Run.
25
CHAPTER 1
b. c.
Verify that the application runs correctly. Press Command-Q or click Stop to quit the application.
Set the attributes of the push button. a. b. c. d. Press Command-1 to open the Attributes pane. Set the buttons title to Pause and its alternate title to Play. Change the button type to Toggle. The settings in the Attributes pane should look like Figure 1-4 (page 22).
26
CHAPTER 1
3.
In the Size pane, set the buttons autosizing control as shown in Figure 1-8.
Figure 1-8
4.
Connect the button to the QC views play: action. a. b. c. Hold down the Control key. Drag from the Pause/Play button to the QC view. Select the play: action from the list that appears.
5. 6.
Save the Interface Builder document. Run a simulation of the user interface. a. b. c. d. Press Command-R to start the simulation. Try out the button and verify its behavior. Resize the QCDemo window and make sure the button retains its correct position. Press Command-Q to quit the simulation.
7.
In Xcode, build and run the QCDemo application. a. b. Click Build and Run. Verify that the application runs correctly.
27
CHAPTER 1
c.
2.
Add the code in Listing 1-1 to the AppController.h source file. AppController class interface
Listing 1-1
#import <Cocoa/Cocoa.h> #import <Quartz/Quartz.h> @interface AppController : NSObject { IBOutlet NSWindow* qcWindow; IBOutlet QCView* qcView; } - (IBAction) loadComposition:(id)sender; @end
3. 4.
Save the AppController.h source file. Add the code in Listing 1-2 to the AppController.m source file. AppController class implementation
Listing 1-2
#import "AppController.h" @implementation AppController - (IBAction) loadComposition:(id)sender { void (^handler)(NSInteger); NSOpenPanel *panel = [NSOpenPanel openPanel]; [panel setAllowedFileTypes:[NSArray arrayWithObjects: @"qtz", nil]];
28
CHAPTER 1
handler = ^(NSInteger result) { if (result == NSFileHandlingPanelOKButton) { NSString *filePath = [[[panel URLs] objectAtIndex:0] path]; if (![qcView loadCompositionFromFile:filePath]) { NSLog(@"Could not load composition"); } } }; [panel beginSheetModalForWindow:qcWindow completionHandler:handler]; } @end
5. 6.
Save the AppController.m source file. Build the QCDemo application (to verify that the code you just added is free of errors.) a. b. In Xcode, click Build or press Command-B. Verify that the message Build succeeded appears at the bottom of the project window.
Connect the App Controllers qcWindow outlet to the design window. a. b. c. Hold down the Control key. In the document window, drag from the App Controller to the Window object. Select the qcWindow outlet from the list that appears.
3.
Connect the App Controllers qcView outlet to the QC view in the design window. a. b. c. Hold down the Control key. Drag from the App Controller to the QC view in the design window. Select the qcView outlet from the list that appears.
29
CHAPTER 1
In the Attributes pane of the inspector, set the buttons title to Load. In the Size pane of the inspector, set the buttons autosizing control as shown in Figure 1-8 (page 27). Connect the button to the App Controllers loadComposition: action. a. b. c. Hold down the Control key. Drag from the Load button to the App Controller. Select the loadComposition: action from the list that appears.
5. 6.
Save the Interface Builder document. Run a simulation of the user interface. a. b. c. Press Command-R to start the simulation. Verify that the QCDemo window looks like the window shown in Figure 1-6 (page 23). Press Command-Q to quit the simulation.
7.
In Xcode, build and run the QCDemo application. a. b. c. Click Build and Run. The QCDemo window appears. Click Load. A sheet dialog appears. Use the dialog to load another Quartz Composer composition. For example, load:
/System/Library/Screen Savers/Arabesque.qtz
d.
30
CHAPTER 1
Whats Next?
Now you can begin to explore the Interface Builder application in more detail.
Whats Next?
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
31
CHAPTER 1
32
Whats Next?
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 2
Interface Builder is the application you use to assemble the visual components (such as windows and menus) of your application. In Interface Builder, you assemble your windows and menus by dragging preconfigured objects into an Interface Builder document. You can reposition those objects and change their attributes as needed to achieve the desired look for your interface. For some application types, you can even create explicit relationships between those objects, which ultimately result in the creation of links between objects at runtime. This chapter provides a high-level overview of the concepts surrounding the Interface Builder application, including an introduction to nib files (the Interface Builder document type) and the basic features of the Interface Builder application. If you have never used Interface Builder before, you should read this chapter at least once to familiarize yourself with these fundamental concepts. While reading this chapter, you may also want to have the Interface Builder application open so that you can explore features as you read about them. Note: Interface Builder is included in the Xcode toolset. You can download the latest version of Xcode from the members area of the Apple Developer Connection (ADC) website (http://connect.apple.com/). Registration is required but free.
33
CHAPTER 2
Figure 2-1
Placeholder objects
Interface objects
Table 2-1 lists the key controls in the Interface Builder documents toolbar and how you use them to manage the documents contents. Table 2-1 Control Interface Builder document controls Description
View mode selector Lets you pick between Icon, Outline, and Browser modes for viewing your document contents. Icon mode shows the key objects of your nib file only. Outline mode displays the objects in a hierarchical tree that reflects the parent-child relationships between the objects. Browser mode also shows the parent-child relationships between objects but using a browser control. Information button Displays basic information about the documents configuration, including which platform and OS versions it supports. Displays the Interface Builder Library window. See The Library Window (page 35). Displays the Interface Builder inspector window. See The Inspector Window (page 38). Lets you search for objects in the document by name. Search results are automatically displayed in the Outline view mode.
Search field
In addition to the document toolbar, Interface Builder includes a View menu that you can use to modify the presentation of the document. This menu contains commands that perform the same functions as the toolbars view mode selector. In addition, you can use this menu to customize the toolbar in various ways.
34
CHAPTER 2
The content area of the document displays the objects that are created or referenced when the document is loaded by your application at runtime. There are two basic types of objects that can appear in this area: interface objects and placeholder objects. Interface objects are the objects that are actually created when the document is loaded and typically comprise the bulk of the objects. Placeholder objects are used to refer to objects that live outside of the document but which are intimately tied to the contents of the document. When you save an Interface Builder document, you save it using either the xib file or nib file format. Both formats store the same information but do so in different ways. Xib files are intermediate XMLbased files that are intended for use only during the development of your project. Because they are text-based, you can save them in your source-code management system and perform diffs on them. During deployment, xib files are converted to nib files, which contain a binary version of the document data and are what your application actually loads at runtime. For any new projects, you should save your documents as xib files. For existing projects, you can also save your documents directly to the nib file format. Note: Interface Builder documents are often referred to as nib files as a convenience and the two terms are considered synonymous. A nib file is simply the end result of an Interface Builder document. For more information about the objects you put in your nib files, including interface and placeholder objects, see Nib Objects (page 55). For more information about the xib and nib file formats and when you should use each one, see About Nib and Xib Files (page 47).
Workflow Tools
Interface Builder provides several tools to help you create your nib files. The following sections provide an overview of these tools and how you use them.
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
35
CHAPTER 2
Figure 2-2
Groups pane
Items pane
Details pane
The Library window is context sensitive, always showing you the objects supported by the currently active Interface Builder document. You can organize the contents of the Library window in several different ways, including the following:
Type a string in the Filter field to display only those items whose name or type matches the specified text. Select one or more groups in the Organization pane to display items from only those groups. Create custom groups and add specific items to those groups. Create smart groups to display items that match dynamically-determined criteria, such as when they were last used. Rearrange items within a custom group.
For more information on how to customize the Library window, including its contents, see Customizing the Library Window (page 159).
36
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 2
Classes
The Library window provides a central place to view and manage classes. Experienced users of Interface Builder may recognize some of the same features found in the class hierarchy browser in Interface Builder 2.x. You can use the classes tab to:
Instantiate a class View the lineage of a class Find out where a class is defined Open a class definition file in Xcode View the actions and outlets for a class Define custom classes for a project Add actions and outlets to a custom class Write out updated class files
The classes tab in the Library window contains a hierarchical view of all the classes that Interface Builder knows about for a given Xcode project. This class information is drawn from four sources: project headers, Interface Builder plugins, linked frameworks, and the Interface Builder document itself. These four different sources are reflected in the definitions detail view. When you select a class, the details pane displays information about the selected class such as its inheritance (lineage detail view), the sources from which Interface Builder has gathered information about the class (definitions detail view), class outlets (outlets detail view), and class actions (actions detail view). A useful by-product of this central repository of class information is that you can easily instantiate classes that are not defined in an Interface Builder plugin. When Interface Builder builds the list of classes, it looks for the actual objects in the Objects library that most closely match the classes. If you create a subclass of NSButton in your code and call it MyButton, for example, and you drag MyButton out of the Classes library, you drag out an NSButton, not just an NSObject instance. Even though Interface Builder has a central place for class management, the definition of your custom classes (changing the superclass, adding outlets and actions, and so on) should be done in Xcode. The ability to add new classes by subclassing in the classes tab or adding actions and outlets is more a prototyping benefit. Because the classes tab makes it easy to instantiate your custom classes, the recommended workflow becomes: 1. 2. Create your custom classes in Xcode. Instantiate them in Interface Builder by dragging them out of the Classes library.
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
37
CHAPTER 2
This eliminates the need to drag out a generic view or object and then set its custom class.
Size
Title area
Content area
38
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 2
Table 2-2 lists the different panes found in the standard inspector windows and describes their behavior. Cocoa inspectors use all of the panes listed in this table. Cocoa Touch and Carbon inspectors use a subset of panes, which are indicated in the table. This table lists the panes in left-to-right order as they appear in the inspector window. Table 2-2 Inspector pane behavior
Inspector pane Description Attributes Displays the object-specific configuration attributes. For Cocoa and Cocoa Touch objects, the sections in this pane reflect the classes in the inheritance hierarchy of the selected object. For Carbon objects, the sections reflect opaque type groupings. For more information, see Object Attributes (page 105). Displays the Core Animationbased and Core Graphicsbased attributes associated with the object. You can use this pane to add transparency and shadow effects and apply other types of effects and filters. This pane applies to Cocoa objects only. For more information, see Attaching Graphical Effects in Mac OS X (page 106). Displays information about the size and position of the object and also displays alignment controls and autosizing attributes. This pane applies only to objects that have this information, typically visual objects such as windows, views, and cells. For more information, see Interface Layout (page 89). Displays the available bindings for an object and provides an interface for binding those objects to one or more controllers. This pane applies to Cocoa objects only. For more information, see Connections and Bindings (page 119). Displays the outlets and actions of the object along with information about which ones are currently connected to other objects. In addition to viewing these connections, you can also use this pane to remove a connection. This pane applies to Cocoa and Cocoa Touch objects only. For more information, see Connections and Bindings (page 119). Displays information that helps identify the object, either at design time or runtime. You use this pane to set the exact type of an object and assign other descriptive information. This information is usually set once and never changed. For more information, see Object Attributes (page 105).
Effects
Size
Bindings
Connections
Identity
Each pane of the inspector window displays as much information as possible when multiple objects are selected. The Attributes pane in particular displays all of the sections that are common to the currently selected objects. For example, if a Cocoa text field and button are selected, the inspector window displays the Control and View sections but does not display the Button or Text Field sections. If a given pane cannot display any relevant information, it instead displays a message to that effect.
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
39
CHAPTER 2
Figure 2-4 shows the connections panel for a button and Table 2-3 (page 40) lists the sections that may be displayed by the panel. If an outlet or action is currently connected, information about that connection is displayed to the right of the outlet or action name. You can create new connections by clicking in the circle to the right of the outlet or action name and dragging to the target object. To break existing connections, click in the break connection box next to the connection target. Figure 2-4 Connections panel
Related object selector Close box Not connected Connected
Slice content
Connections panel section descriptions Description Lists the outlets exposed by the object. An outlet is a member variable of the class that has the IBOutlet keyword associated with it. Outlets let you create inter-object references from within Interface Builder. For information about adding outlets to an object, see Defining Outlets (page 142). Shows the target of a controls action message. An action is a message that is sent by a control in response to a user interaction. For example, when a user clicks a button, the button object sends its action message to the associated target object. In Mac OS X applications, a control sends its action message to a single target object. In iOS applications, a control may send several different action messages in response to different types of user interaction with the control and it may send those messages to multiple target objects.
Sent Actions
Received Actions
Lists the incoming actions that the current object is capable of handling. Each of these entries corresponds to a member method of the object. A received action may be associated with multiple objects. For information about defining an objects action methods, see Defining Action Methods (page 143).
40
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 2
Section Accessibility
Description Lists standard outlets for storing accessibility related information. These outlets are present for all visual elements. Lists the source objects that refer directly to the selected object through an accessibility connection. Lists the source objects that currently refer to this object through an outlet. This section can list multiple sources.
When you control-click an object, the connections panel appears at the point where you clicked. If you click another object without moving the panel, the panel disappears automatically. This is convenient if you want to make a connection quickly and then work on other objects. To keep the panel from disappearing automatically, simply drag the panel away from its original position. Any change in position causes the panel to remain visible. To close a panel that is still visible, click its close box. Although the connections panel displays the outlets and actions for the clicked object, you can use the same panel to display the outlets and actions for nearby objects as well. The popup menu in the upper-right corner of the panel lists all of the objects at the current mouse location. You can use this menu to access objects that overlap each other on the design surface and might otherwise be hard to click on directly. For more information about creating and managing connections in an Interface Builder document, see Connections and Bindings (page 119).
Workflow Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
41
CHAPTER 2
Figure 2-5
The strings window displays the strings from all objects in all open nib files by default. There are a few ways to narrow the list of strings though:
Use the Document Scope control to show the strings from only the selected nib file. Use the Filter control to list only entries that match the specified text. Use the Filter controls menu to exclude strings that do not have a value. Choose Edit > Find > Find to locate strings whose value matches the specified text.
You can edit strings directly from the Strings window by double-clicking the value of an entry and typing a new value. To sort the strings, click on the appropriate column header.
Modifier Keys
Interface Builder uses the standard modifier keys to modify the way it treats objects. For a summary of modifier key actions, see Modifier Keys (page 170).
42
CHAPTER 2
Note: To select objects nested even further down in a view hierarchy, you may have to wait and click multiple times. Most other selection behaviors work the same way in Interface Builder as they do in other applications. For example, you can use the Shift and Command keys to extend or toggle the selection of items. Interface Builder does impose some restrictions when selecting multiple objects, however. All objects in a selection must have the same parent object. Figure 2-6 shows how Interface Builder reflects the currently selected item in a window. The selected item is drawn with one or more resize handles and an optional change in shading. The parent of the selected item is drawn normally, but everything outside of that parents frame is shaded. You can use these visual cues, along with the title of the inspector window, to help determine which item is currently selected.
43
CHAPTER 2
Figure 2-6
Nothing selected
Box selected
View selected
Button selected
Set the viewing mode of your Interface Builder document window to Outline or Browser mode and select the object there. Control-Shift click (or Shift right-click) the object obscuring the desired view and select the desired object from the menu that appears.
Control-Shift clicking an object is a way to select any of the objects that lie directly beneath the mouse. When you do it, Interface Builder displays a menu, from which you can select the desired object.
44
CHAPTER 2
Figure 2-7
Inactive
Active
45
CHAPTER 2
46
CHAPTER 3
Nib files play an integral role in the development of your applications. They are a powerful type of resource that you use to store runtime objects and interface-related content. They are also the fundamental document type of the Interface Builder application. Interface Builder 3.0 and later offer many options for creating and working with nib files themselves. Understanding these options can help save you time and effort during development. This chapter offers guidelines to help you create nib files that integrate well with your Xcode projects.
Window resources Menu resources (both menu bars and individual menus) Views Formatter objects Controller objects (view controllers, array controllers, object controllers, and so on) Core Data managed object contexts
47
CHAPTER 3
Some of these objects must be at the top level of the nib file. For example, windows and menus must always be at the top level of a nib file. In addition, controller objects are almost always at the top level. This is because controller objects cannot be embedded inside windows, views, or menus. (Cells and formatters are special because they work in conjunction with a view or control to implement its appearance.) Most other view-based objects are typically situated inside a window or view, although they can appear at the top level of the nib file as well.
For your applications main nib file, include only your menu bar (or in the case of an iOS application, just the main window). For document nib files in Mac OS X, include only the document window and the objects (such as controllers) needed to display that window. For other nib files, focus the nib file on a key object, such as a single window or panel that you intend to display. All other objects in the nib file should then facilitate the immediate operation of that window or panel. For windows that change their embedded view hierarchies, if the hierarchy changes infrequently, consider storing any additional hierarchies in separate nib files. Load each view hierarchy only as it is used.
48
CHAPTER 3
If you already have large nib files, you can use Interface Builders refactoring tools to break them into several smaller nib files. For information on how to use Interface Builders refactoring tools, see Refactoring Your Nib Files (page 53). For information about how to load nib files explicitly from your code, see Resource Programming Guide.
49
CHAPTER 3
The xib file format was introduced in Interface Builder 3.0 as a development-time format and was conceived as a way to provide tighter integration with your Xcode projects, particularly in the areas of SCM support, diff support, and refactoring. Xcode automatically converts files in the xib format to the nib format at build time. Because there are two supported file formats for Interface Builder documents, you have to choose which format to use for your own projects. If youre developing for iOS, the choice is easyyou must use the xib file format for your project. For Mac OS X, you may use either the xib or nib file format. In almost every case, you should use the xib format. The nib format is recommended for a project only if the project target is an Interface Builder plug-in that depends on itself. Interface Builder 3.0 and later fully supports opening nib files created with Interface Builder 2.5.x and earlier. Nib files created or modified with Interface Builder 3.2 and later cant be opened with Interface Builder 2.5.x and earlier.
50
CHAPTER 3
Version 3.x development-time format (.xib extension) Version 3.x deployment format (.nib extension)
Depending on the situation and your needs, you may find yourself using one or both of these formats for a given project. For guidance on which format to choose for your project, see Choosing the Best File Format (page 49) and the following sections.
Important: Although it is a text-based format, you should never edit a xib file by hand. The xib file format represents a flattened archive of the nib file object graph. Even if you are cautious, making changes to one portion of this graph could cause unexpected changes to other portions. You should also avoid using source code management tools to merge a xib file with another file. A textual merge, even one without conflicts, will likely produce an invalid xib file.
51
CHAPTER 3
Interface Builder supports version 3.x of the deployment format. The 3.x version is a more modern format supported by Interface Builder 3.0 and later. This format supports new objects that are available only in Interface Builder 3.0 and later. Important: If you are developing applications using Xcode 3.0 or later, you should avoid using the deployment nib file format during development. Instead, you should use the development-time nib file format and let Xcode create the appropriate deployment nib files for you. The development-time format makes it easier to integrate your nib file code with source-control systems and build scripts. To save a file using the deployment nib file format, do the following: 1. 2. 3. Choose File > Save (or File > Save As) to display the Save panel. Select the NIB 3.x format from the File Type pop-up menu. Click Save.
Drag an image from the media browser and drop it onto a window to create an image view configured with that image. Drag an image from the media browser and drop it onto a toolbar, button bar, or tab bar (depending on the platform) to create a new item for that view. Drag an image from the media browser and drop it onto a control to assign that image to that controls cell (where applicable).
Although you can reference image and sound resources from your nib file, those resources are still stored outside of the nib file itself. Interface Builder gets the list of available resources from the Xcode project associated with your nib file. Therefore, if you want to use image and sound resources in your nib files, add them to your Xcode project. In addition to your project resources, the Cocoa and Cocoa Touch platforms make some standard system images available for applications to use. These images are displayed in the Media browser by default but you can also refer to these images by name. The reference documentation for the associated platform lists the constants containing the name strings you use to access them. In nearly all cases, the names used by Interface Builder are a shortened version of the constant name. For example, in Cocoa applications, Interface Builder uses the string NSBonjour to represent the image identified by the NSImageNameBonjour constant. For a list of constants you can use in Cocoa applications, see NSImage Class Reference. For Cocoa Touch applications, these constants are spread across several classes in UIKit Framework Reference.
52
CHAPTER 3
When in doubt about whether a control supports image or sound resources, check the inspector window. If a control includes an image or sound field as one of its attributes, then you can assign the appropriate resource to it. (For example, you can assign both an image and sound resource to a push button control in Cocoa.) In addition to typing the resource name in the appropriate field, the inspector window typically includes a drop-down list that includes the known resources from your Xcode project.
53
CHAPTER 3
54
CHAPTER 4
Nib Objects
The editing environment of Interface Builder is organized around the direct manipulation of objects. How you manipulate a given object, though, depends on the type of the object and its typical relationship to other objects. Views are the most common type of object used in Interface Builder. Views are rectangular regions that provide some visual content and optional event-handling behavior. Controls are a special type of view that respond to user interactions and send runtime messages to an interested target object when those interactions occur. Windows and menus are also the main building blocks of many Interface Builder nib files. Most nib files are created around a specific window, menu, or view, and all of the other objects in that nib file are there to support that window, menu, or view. In addition to visual objects such as windows, views, and menus, nib files used with Mac OS X and iOS applications can also include non-visual objects. Because Mac OS X and iOS applications use the Model-View-Controller design paradigm, most non-visual objects are controller objects whose job is to manage all or part of the user interface stored in the nib file. The following sections introduce you to the key objects you are going to find in a nib file and how you use them to build your interface. These sections are not intended as a comprehensive catalog of all the objects you can add to a nib file. Instead, these sections group together objects with similar behavior and treat them as one in order to simplify the explanations of how they work.
Windows
A typical iOS application has only one window, which provides the backdrop for all of the applications content. Applications can include additional windows, if desired, but doing so is rare and generally not recommended.
55
CHAPTER 4
Nib Objects
Removing a window removes the window, its contents, and any connections to other objects from the nib file.
56
CHAPTER 4
Nib Objects
3. 4.
Drag the view or control out of the Library window. Drop it onto the design surface.
As you drag a view onto the design surface, Interface Builder highlights different portions of the surface to show you where the drop would occur. Upon dropping the view, the highlighted object becomes the parent of the dropped view.
Removing a view removes its subviews and any connections and bindings to other objects from the nib file.
Custom Views
Although the standard system views and controls provide a variety of choices for building an interface, there are many times when you may want to provide customized behavior for your application. If your nib document is associated with a Cocoa Touch project, Interface Builder is aware of any custom views declared in your source code. You can find your custom views listed in the Classes tab of the Library window. Dragging a custom view object to a window (or to the top level of your nib document) creates an unadorned rectangular area representing the space occupied by the object. Interface Builder sets the objects class name in the identity inspector, as illustrated in Figure 4-1. To learn about setting the class identity of a generic view object, see Setting the Class of an Object (page 139).
57
CHAPTER 4
Nib Objects
Figure 4-1
Toolbars
Toolbars contain a collection of buttons representing frequently used commands in an application. Toolbars are typically located along the bottom edge of your user interface. You can configure the appearance of a toolbar in different styles to suit your interface needs. You can also configure the buttons in a toolbar using several different styles, which are shown in Figure 4-2.
58
CHAPTER 4
Nib Objects
Figure 4-2
Flexible spaces
Plain button
Bordered button
Done button
To add a toolbar to your user interface, drag a tool bar view from the library and drop it in your window or view. The default toolbar contains a single bar button item, but you can add additional items by dragging them from the library. You can configure the properties of each bar button item using the inspector. You can also edit the title of a bar button item by double-clicking it on the design surface.
59
CHAPTER 4
Nib Objects
Flexible-space buttons expand to fill the available space on the toolbar, pushing other buttons all the way to the right edge of the toolbar. Fixed-space buttons fit the available space as best they can initially and can be reconfigured later to specify the desired amount of space you want. To change the size of a fixed-space item, open the Size inspector and change the value in the Width field located in the Bar Button Item Size section. Flexible-space buttons ignore the value in this field. Note: If your application supports both landscape and portrait orientations, you should favor flexible-space items over fixed-space items whenever possible. When changing orientations, flexible-space items expand or contract as needed to fill the available space.
You connect the bar button item to its target object using either the Connections inspector or the connections panel. The bar button item has a single selector action that you can connect to the action method of the designated target object. You can initiate the connection either from the bar button item or the target object. When initiating a connection from the bar button item, you must start from the selector action and release the mouse button over the target object, selecting the desired method of that object to complete the connection. For more information about creating connections between objects, see Connections and Bindings (page 119).
Controller Objects
In addition to visual objects, Cocoa Touch nib files can include any type of custom object (including non-visual objects) needed by an application. The ability to include any instance of NSObject is typically used as a way to facilitate the Model-View-Controller design pattern used by iOS applications. The non-visual objects in a nib file act as controllers for the visual objects. Figure 4-3 shows the basic object types you can add to a Cocoa Touch nib file. In addition to the generic object type, Cocoa Touch nib files can include two other special object types. View controller objects provide custom management for an applications user interface and are used heavily in iOS applications. Because an applications interface may be spread over multiple nib files, Interface Builder also includes a placeholder object, which you can use to represent any additional objects that are distinct from the Files Owner placeholder.
60
CHAPTER 4
Nib Objects
Figure 4-3
Any NSObject
View Controllers
Because an iOS application has only one window, the application changes the windows content by changing the content views displayed in the window. The content view is the portion of an iOS window that you use to display your applications custom content. The content view is not necessarily a single view but may in fact comprise several views embedded inside a parent (or root) view. Management of the content view is the responsibility of a view controller object, which coordinates the movement of that content on and off the screen. Because it is a controller, you can also add custom logic to your view controller classes to manage interactions between the content view and your applications data model. In addition to providing navigation and tab bar controller objects, Interface Builder provides a generic view controller object that you can use for managing individual views. The most common way to use a view controller is as the Files Owner of a nib file, but you can also instantiate them inside your nib file as needed.
Open the view and add any additional subviews to it to define your user interface. Connect any additional outlets and actions. Save the new nib file and add it to your Xcode project.
Nib files configured in this way are associated with the corresponding view controller class at runtime. When you create a new instance of your view controller, you pass the name of your nib file to the initWithNibName:bundle: method of the UIViewController class. The first time your application asks the view controller for its view, the view controller loads the associated nib file and returns the view attached to its view outlet. The view controller continues to manage the contents of the nib file internally, purging the views as needed during low-memory conditions and reloading them later as needed.
61
CHAPTER 4
Nib Objects
Nib files configured in this manner are often used to implement tab bar and navigation-style interfaces. The content view for each distinct screen is stored in its own nib file and associated with a view controller class. The navigation and tab bar controllers then manage the loading and unloading of each view controller and its associated nib file.
The view controller editor displays a status bar (and other top bars and bottom bars) if the properties of that view controller indicate that one is present. These elements are not saved with your nib file and are provided to help you position your views and other content. You should configure the attributes of your view controller to match the presence of the status bar or other elements in your application window.
62
CHAPTER 4
Nib Objects
Tab Bars
Tab bars give the user a way to switch between different user interface modes in an application. Tab bars are typically used by applications to manage large amounts of information or to present information in different ways for the user. For example, the Clock application uses a tab bar to change between different clock-related utilities, as shown in Figure 4-5. Pressing each button in the tab bar displays a unique interface for that mode. Figure 4-5 Interface modes of the Clock application
In Interface Builder, the way to configure a tab bar interface is not by adding views to your window. Instead, you need to add a tab bar controller object to the top level of your nib file and configure your views using the custom editor for that object. When you add a tab bar controller object to your document, Interface Builder actually adds several other objects. In addition to the tab bar controller, it adds a tab bar view and two generic view controllers, each of which contains its own tab bar item. Interface Builder groups these objects together under the tab bar controller, as shown in Figure 4-6. Figure 4-6 A tab bar controller and its default set of objects
63
CHAPTER 4
Nib Objects
The grouping of the tab bar objects as children under a tab bar controller reflects the object graph relationships between those objects. A tab bar controllers children consist of its tab bar view and the view controllers used to manage each of its tabs. The view controllers are actually stored in the viewControllers property of the tab bar controller object, which can also be set programmatically. The tab bar view is added to the overall view associated with the tab bar controller, which is stored in the controllers view property. The relationship of objects in the document window also reflects the way those objects are presented by Interface Builder. When you double-click a tab bar controller object, Interface Builder displays the tab bar controller editor window, shown in Figure 4-7. This editor window reflects the child objects of the tab bar controller and is where you configure your tab-based user interface. Items you add using this interface are similarly added as children to the tab bar controller or the view controller that owns them. Figure 4-7 Tab bar controller editor window
The tab bar controller editor displays a status bar (and other top bars and bottom bars) if the properties of that view controller indicate that one is present. These elements are not saved with your nib file and are provided to help you position your views and other content. You should configure the attributes of your tab bar controller to match the presence of the status bar or other elements in your application window. Selecting one of the tab bar items in the tab bar controller editor window shows the views associated with the corresponding tab. In fact, clicking a tab bar item once selects the view controller that manages that item. Clicking the same item again selects the actual tab bar item.
64
CHAPTER 4
Nib Objects
Although the tab bar controller lets you edit the objects associated with the tab bar interface, simply editing those objects does not make them appear in your application window. To display your tab bar interface, you must programmatically retrieve the tab bar controllers view and add it to your window as a subview. For example, if your application delegate has outlets referring to your tab bar controller object and application window, its applicationDidFinishLaunching: method would need to look something like the following:
- (void)applicationDidFinishLaunching:(UIApplication *)application { [window addSubview:[myTabBarController view]]; }
For information about configuring tab bars and tab bar controllers programmatically in your application, see Tab Bar Controllers in View Controller Programming Guide for iOS.
Drag the desired view controller from the library and drop it onto the tab bar in the tab bar editor window. Select the tab bar controller object and add a new tab using the plus (+) button in the Attributes inspector. Drag a tab bar item from the library and drop it on the tab bar editor window.
Whenever you add a new tab to your interface, Interface Builder adds both a new tab bar item and a view controller to your nib file. When dragging items over the editor window, Interface Builder shows you the proposed placement for the new item. You can rearrange items later by dragging them around the tab bar or by modifying the order of the view controllers in your document window. If you want an existing tab to use a different view controller class, select the tab bar controller object and open the Attributes inspector. The Tab Bar Controller section contains a table listing the view controller objects associated with the tab bar. To change the class of one of these view controllers, use the provided pop-up menu in the Class column. If you are adding a new tab, as opposed to modifying an existing tab, drag the desired controller object from the Library window and drop it directly onto the tab bar in the tab bar editor window. To remove a tab from your interface, select the corresponding tab bar item and choose Edit > Delete or simply press the Delete key.
65
CHAPTER 4
Nib Objects
Because of the way tab bar items are organized, clicking an item in the editor window selects the view controller that owns that item. Clicking that item again selects the tab bar item associated with that view controller. You can select either the tab bar item or the view controller directly from your Interface Builder document window while it is in the outline or browser view mode. Note: If your tab bar contains more than five items, do not create a More button to allow the user to configure which items to display in the tab bar. Instead, configure the customizableViewControllers property of the tab bar controller programmatically as described in Tab Bar Controllers in View Controller Programming Guide for iOS. Configuring this property automatically adds a More button with the desired behavior.
Use one or more separate nib files to specify the views. (Recommended) Embed the views in the same nib file that contains the view controller.
By their nature, tab bar interfaces add complexity (and many more views) to an applications user interface. Although you can embed all of your applications views in the same nib file as your tab bar controller object, doing so is not terribly efficient. Storing all of those views in the same nib file causes them to be loaded into memory at launch time and never unloaded. Using one or more nib files for each distinct tab makes it possible to load and dispose of the views in that tab on demand, potentially reducing your applications memory footprint. How many nib files you use to specify the interface for a tab depends on the contents of the tab. The basic UIViewController class is designed to manage a single content view, which corresponds to a screens worth of your applications custom content. (Thus, for simple interfaces with only one screen, you would need only one nib file.) For complex view controllers such as navigation controllers, you may need multiple nib files, each one representing the interface for a single distinct screen. At a minimum, every tab should have one nib file that you use to specify the root view for the tab. To configure the root view for a tab, do the following: 1. 2. Create a new nib file and configure it as described in Using a View Controller as Files Owner of a Nib File (page 61). In the nib file containing your tab bar controller object, select the view controller for the appropriate tab. (You can also select the view controller by clicking the appropriate tab bar item once in the editor window.) Open the Attributes inspector. In the Nib Name field of the inspector, enter the name of the nib file (without any filename extension) you just created. Save your nib file.
3. 4. 5.
Configuring the Nib Name property of your view controller object in this manner is similar to creating your view controller programmatically using the initWithNibName:bundle: method. Whenever your application code requests its associated view, the view controller loads the specified nib file if it is not already in memory.
66
CHAPTER 4
Nib Objects
Specifying the nib file name also gives the view controller the option of releasing the contents of that nib file when they are not in use. It might do this in situations where the amount of free memory is running low. It can always reload the nib file again later if needed. If you would rather create the views for the tab in the same nib file as your tab bar controller, simply select the tab in the tab bar controller editor window and drag the views into the provided space. The first view you add to the editor becomes the root view for your view hierarchy. If you intend to use multiple views, you should add a generic UIView object that can span the entire visible area and act as a parent for other views. Your remaining views would then be children of this root view.
Navigation Bars
Navigation bars are a visual element used in conjunction with a navigation controller object to navigate complex data hierarchies quickly and easily. The navigation bar displays the current location in the navigation hierarchy, provides an optional button for navigating back to the previous location, and provides an optional button for manipulating data at the current level. Figure 4-8 shows these components in the navigation bar used by the Mail application. Figure 4-8
Back button
Although the navigation bar conveys contextual information to the user, the navigation controller provides the driving force behind displaying that interface and managing the view controllers that coordinate each screens content view. Therefore, to configure a navigation interface in your nib file, you add a navigation controller object to the top level of your nib file. When you add a navigation controller object to your Interface Builder document, you actually get several objects. In addition to the navigation controller, you get a navigation bar and a generic view controller. Interface Builder groups these objects together under the navigation controller, as shown in Figure 4-9.
67
CHAPTER 4
Nib Objects
Figure 4-9
Important: A navigation controller object can have only two child objects: a navigation bar view and a view controller for managing its root view. Both of these objects must be present in order to initialize your navigation controller properly at runtime. When you double-click a navigation controller object, Interface Builder displays the navigation controller editor window, which is shown in Figure 4-10. This editor window displays the child objects of the navigation controller object and is where you configure the root view of your navigation-based user interface.
68
CHAPTER 4
Nib Objects
Figure 4-10
The navigation controller editor displays a status bar (and other top bars and bottom bars) if the properties of that view controller indicate that one is present. These elements are not saved with your nib file and are provided to help you position your views and other content. You should configure the attributes of your navigation controller to match the presence of the status bar or other elements in your application window. Although the navigation controller lets you edit the objects associated with the navigation-style interface, simply editing those objects does not make them appear in your application window. To display your navigation interface, you must programmatically retrieve the navigation controllers view and add it to your window as a subview. For example, if your application delegate has outlets referring to your navigation controller object and application window, its applicationDidFinishLaunching: method would need to look something like the following:
- (void)applicationDidFinishLaunching:(UIApplication *)application { [window addSubview:[myNavBarController view]]; }
If your navigation-style interface is used in conjunction with a tab bar interface, you would show the tab bar controllers view in your delegates applicationDidFinishLaunching: method instead of your navigation interface. Whenever you combine navigation and tab bar interfaces, the tab bar interface must be used for the root level of your window. You can embed navigation controllers inside of a tab bar interface but you cannot do the reverse. For information about configuring navigation bars and navigation controllers programmatically in your application, see Navigation Controllers in View Controller Programming Guide for iOS.
69
CHAPTER 4
Nib Objects
Use a separate nib file to specify the views. (Recommended) Embed the views in the same nib file that contains the root view controller.
Although you can embed the views for the root view controller in the same nib file as your navigation controller object, doing so requires those views to stay resident in memory when they are not in use. Storing the root views in a separate nib file makes it possible to load and dispose of those views on demand. To create the view hierarchy for the root view controller using a separate nib file, do the following: 1. Create a new nib file and configure it as described in Using a View Controller as Files Owner of a Nib File (page 61). The class of the nibs Files Owner should be the same as your root view controllers class. 2. 3. 4. 5. 6. In the nib file containing your navigation controller, select the root view controller embedded inside the navigation controller object. Open the Attributes inspector. Set the class of the root view controller to your custom class. In the Nib Name field of the inspector, enter the name of the nib file (without any filename extension) you just created. Save your nib file.
Configuring the Nib Name property of your view controller object in this manner is similar to creating your view controller programmatically using the initWithNibName:bundle: method. Whenever your application code requests its associated view, the view controller loads the specified nib file if it is not already in memory. This gives the view controller the option of releasing the contents of the nib file when they are not in use and the amount of free memory is running low. If you would rather create your the views for the root level of your navigation interface in the same nib file as your navigation controller, simply drag the desired views into the navigation controller editor window. The first view you add to the editor becomes the root view for your view hierarchy. If you intend to use multiple views, you should add a generic UIView object that can span the entire visible area and act as a parent for other views. Your remaining views would then be children of this root view.
70
CHAPTER 4
Nib Objects
Open the view and add any additional subviews to it to define your user interface. Connect any additional outlets and actions. Save the new nib file and add it to your Xcode project.
To push a new view controller at runtime, create a new instance of your custom UIViewController subclass, initialize it with the nib file you created for it, and push it on the navigation controller stack. For example:
MyViewController* vc = [[[MyViewController alloc] initWithNibName:@"MyViewController" bundle:nil] autorelease]; [myNavController pushViewController:vc animated:YES];
The new instance manages its views and content separate from any other instances you created previously. For more information on how to push view controllers on the navigation stack, see Navigation Controllers in View Controller Programming Guide for iOS.
71
CHAPTER 4
Nib Objects
3.
Dropping a window object onto the desktop adds that window to the top level of the active Interface Builder document window. The place where you drop the window becomes the windows initial position at load time. Once a window is associated with an Interface Builder document, dragging it around the desktop does not change its load-time position. Instead, dragging it around simply moves it out of the way and makes it easier to organize your workspace. To change the load-time position of the window from its initial setting, use the Size pane of the inspector window, as described in Moving and Resizing Windows (page 92). Important: If you subsequently include an OpenGL view in one of your Cocoa windows, be sure to disable the windows One Shot option. The one-shot option deletes the window object when it is hidden or miniaturized to the dock. Unfortunately, destroying the window in this manner breaks the link between the OpenGL drawing context and the window, which means the view can no longer draw its contents. Disabling the one-shot option maintains the connection and ensures that the OpenGL view has a place to render its content. When you double-click a window object, Interface Builder opens that window on the desktop (or makes it the active window if it is already open). The content area of the window represents the design surface and is where you build the appearance of your window.
72
CHAPTER 4
Nib Objects
Removing a window removes the window, its contents, and any connections and bindings to other objects from the nib file.
Views
Views are the most commonly used objects in Interface Builder. The standard system views display data, respond to user input, and implement standard interface paradigms such as scrollable areas, controls, and many others. Applications can also create custom views and use them to display custom visual content and respond to user interactions. In Cocoa applications, views are based on the NSView class of the AppKit framework. In Carbon applications, views are based on the HIViewRef data type.
You can drag a view out of the library and drop it onto a window. In Cocoa nib files, you can drag the view to the top level of the nib file.
As you drag a view around your window, Interface Builder highlights different portions of the window to show you where the drop would occur. Upon dropping the view, the highlighted object becomes the parent of the dropped view. Interface Builder inserts the dropped view into the parents view hierarchy and applies the parents clipping rectangle. You can drag the view around the design surface to position it or change its parent view as needed. You might place a view at the top level of your nib file in situations where you want to load only a view and not an entire window, such as when creating content for an accessory panel. When placing views at the top level of your document, be sure to assign them to an outlet of your Files Owner object so that you can dispose of them properly later. For more information about memory management and the objects in your nib file, see Resource Programming Guide. In addition to adding standard system views to your window, you can also add views for which your Xcode project provides the view implementation. If you add such a view to your window, you must set the class of that view so that the proper object is created at load time. For more information about configuring custom views, see Custom Views (page 74).
Removing a view removes the view, its child objects, and any connections and bindings to other objects from the nib file.
73
CHAPTER 4
Nib Objects
Custom Views
Although the standard system views and controls provide a variety of choices for building an interface, there are many times when you may want to provide customized behavior for your application. If your nib document is associated with a Cocoa project, Interface Builder is aware of any custom views declared in your source code. You can find your custom views listed in the Classes tab of the Library window. Dragging a custom view object to a window (or to the top level of your nib document) creates an unadorned rectangular area representing the space occupied by the object. Interface Builder sets the objects class name in the identity inspector, as illustrated in Figure 4-11. To learn about setting the class identity of a generic view object, see Setting the Class of an Object (page 139). Figure 4-11 Custom NSView object
Because a custom view is one you are in the process of creating in your Xcode project, Interface Builder does not attempt to draw anything other than a generic box at design time. If you want to see the appearance of your custom view as it would appear at runtime, you must incorporate the finished view into an Interface Builder plug-in and load that plug-in. For more information about plug-ins, see Using Plug-ins to Integrate New Objects into the Library (page 167).
74
CHAPTER 4
Nib Objects
actions of a cell independent of the the parent control object. The only time you might do this, however, is for the NSMatrix class, which can contain multiple cells. In most other cases, you should treat a control and its cell as a single entity. You add controls to your window and remove them in the same manner as views. If you define custom cell classes, however, you can also substitute your custom cell for the standard cell of a control. To change the class of a cell, do the following: 1. 2. 3. Select the cell using the click-wait-click action on the control. (Alternatively, select the cell from the document window while it is in outline mode.) Open the inspector window and choose the Identity pane. In the Class field of the Class Identity section, enter the new class name for the cell. (If the class is defined in the associated Xcode project, Interface Builder automatically displays any outlets and actions defined by the custom cell class.)
When you save your Cocoa nib file, Interface Builder archives the custom cell information with the control. When the nib file is loaded at runtime, the nib loading code automatically creates your custom cell object instead of the standard one and assigns it to the control. This alleviates the need for you to set the cell object in your awakeFromNib method and also makes it easier to use different cell types for each control.
Custom Cells
Prior to Interface Builder 3.2, the library contained only specific NSCell subclasses such as NSTextFieldCell. This made it impossible to use a class that descended directly from NSCell in Interface Builder. The custom cell solves this problem. A custom cell is analogous to a custom view. You can use a custom cell to represent any NSCell subclass.
Toolbars
Toolbars provide the user with a convenient way to access frequently used commands without leaving the current window. A toolbar occupies the space between the title bar of a window and the windows content view. It spans the width of the window and displays one or more commands using a combination of icons and text. Toolbars are configurable by the user at runtime and developers use a very similar technique at design time to create the initial toolbar configuration in Interface Builder. Note: Toolbars have always been available in Mac OS X but until version 3.0 were not configurable in Interface Builder. In Interface Builder 3.0 and later, you can add toolbars only to your Cocoa nib files and only if they are targeted at Mac OS X v10.5 and later.
75
CHAPTER 4
Nib Objects
Figure 4-12
76
CHAPTER 4
Nib Objects
1. 2. 3.
Drag an Image Toolbar Item from the Library window and drop it onto the customization sheet. Select the Image Toolbar Item and open the inspector window. In the Attributes pane of the inspector window, set the following attributes:
The name of the image to use for the item (Image Name attribute) The item text as it appears in the toolbar (Label attribute) The name of the item as it appears in the user customization sheet (Pal. Label attribute)
4. 5. 6.
Position the item in the customization sheet by dragging it to the desired location. If you want the item to be part of the default toolbar, drag it to the toolbar. Click Done to close the customization sheet.
Note: You must add toolbar items to the customization sheet before you can add them to the toolbar itself. The image name you specify should correspond to an image resource from your associated Xcode project. When specifying the image name in the inspector window, you do not need to include the filename extension. Your images should be sized appropriately for the size of the toolbar you plan to use. Regular size toolbars use images that are 32 by 32 pixels. Small toolbars use images that are 24 by 24 pixels. If an image file contains multiple image representations, the Image Toolbar item chooses the one that is closest to the toolbar size and then scales it as needed.
77
CHAPTER 4
Nib Objects
Menu resource
Menu items
Item Submenu Separator
Standard menus
The following sections describe the standard ways to create and organize menu bar and menu resources. For information on how to tie those menu items to specific parts of your application code, see Connecting Menu Items to Your Code (page 127).
To add a new custom menu to the menu bar, drag a Submenu Menu Item from the library and drop it on the menu bar. (You must use the Submenu item and not the Menu resource when adding menus to a menu bar.)
78
CHAPTER 4
Nib Objects
To add a standard Mac OS X menu (File, Edit, Window, and so on) to the menu bar, drag the appropriate menu object from the library to the menu bar. To select a menu, click the menu title, wait, and then click the title again so that the menu is selected but its underlying menu is closed. To remove an existing menu, select the menu and choose Edit > Delete (or simply press the Delete key). (The menu must be closed before you can delete it.) To change the name of a menu, double-click its title to edit the name in place, or select the menu and change its title in the inspector window.
When adding new menus to a menu bar, if an existing menu is already open, hold the mouse over the menu bar for a few seconds until the current menu closes. At that point, you can drop the new menu on the menu bar. For information about modifying the individual items in a menu, see Creating and Modifying Menus (page 79)
To add an item to a menu, drag the item from the library and drop it on the menu. If the target menu is closed, hold the item over the menu title (if in the menu bar) or menu resource until the menu opens automatically. As you drag the item, Interface Builder shows you the target location for the item in the menu. To select a menu item, click the menu item title. If the item represents a submenu, you must click the item again to close the submenu and select the item. To remove a menu item, select it and choose Edit > Delete (or simply press the Delete key). To rearrange items in a menu, drag them to the desired location in the menu. To embed an existing menu item in a new submenu, select the item (or items) and choose Layout > Embed Objects In > Submenu. To change the title of an item, double-click its title string to edit the title in place or select the item and change its title in the inspector window.
79
CHAPTER 4
Nib Objects
To edit the items attributes, select the item and make the changes in the inspector window.
Tip: To quickly add several new items to a menu, add the first item by dragging it from the Library window, select that item, and choose Edit > Copy. You can then paste multiple copies of the item in quick succession below the selected item.
Collection Views
In Mac OS X v10.5 and later, you use collection view objects to manage a grid of NSView objects in a Cocoa application. You can use a collection view in situations where using NSCell objects in a matrix would be insufficient. Because they are full-fledged views (and not cells), the views in a collection view can handle events, perform mouse tracking, and do anything else a view could normally do without having to write a lot of custom code. When you drag a collection view to one of your windows, Interface Builder creates two additional objects at the top level of your nib file:
A generic NSView object, which acts as a template view for the items in the collection. An NSCollectionViewItem object, which is a controller that manages the relationship between a model object and a single view in the collection.
These two objects serve as the prototype for each item in the collection view. The collection view uses the prototype view as a template for creating each new view in the collection. Each time it creates a new view at runtime, it also creates the corresponding NSCollectionViewItem object to manage that view. Configuring a collection view involves configuring the template view and setting up bindings between it and the corresponding controller object. The contents of your view can be anything you want. You could even use a tab-less tab view to create different interfaces for different views. The controls in your view are then bound to the NSCollectionViewItem object through its representedObject binding. To provide the actual data behind the representedObject binding, you must set the content of the collection view object itself (not the NSCollectionViewItem controller). You can do so directly using the setContent: method of the NSCollectionView class, or you can set the content using Cocoa bindings. The content attribute of NSCollectionView stores an array of data objects, each of which contains the custom data to be displayed by one view in the collection. As it populates the grid of views, the collection view automatically associates the items in this array with the corresponding NSCollectionViewItem objects used to manage the grid views. Each collection view item then exposes its particular piece of data through its representedObject attribute. If the custom data objects you set as the content for your collection view are KVC and KVO compliant, you can bind to their exposed attributes. For example, if your custom data object exposed a name attribute, you could bind a text field in your template view to the collection item controller using the key path representedObject.name.
Controller Objects
In addition to visual objects, Cocoa nib files can include any type of custom object (including non-visual objects) needed by an application. The ability to include any instance of NSObject is typically used as a way to facilitate the Model-View-Controller design pattern used by Cocoa applications. The non-visual objects in a nib file act as controllers for the visual objects.
80
CHAPTER 4
Nib Objects
Including controller objects directly inside a nib file has many advantages over creating them separately. Cocoa nib files are typically managed by a single object (known as the Files Owner) that exists outside of the nib file itself. However, it is often convenient to use additional controller objects to manage portions of the nib file contents. In particular, Cocoa bindings make extensive use of custom controller objects to manage the interactions between the views and the applications underlying data model. Figure 4-15 shows the types of custom objects you can add to a Cocoa nib file. The generic NSObject type lets you create an instance of any object that descends from the NSObject class. In addition to this type, Interface Builder provides specialized objects representing specific NSController subclasses for managing Cocoa bindings. The Core Data objects provide a way to incorporate managed object contexts and interfaces for your Core Data entities into your nib files. Figure 4-15 Controllers and custom objects
Bindings Controllers
Any NSObject
To add a generic NSObject instance to your nib file, simply drag the Object item from the library and drop it on your Interface Builder document window. (Custom objects cannot be embedded inside other objects in your nib file; they must reside at the top level of the Interface Builder document window.) After adding a generic object to your nib file, you should specify the intended class of that object right away. Doing so lets you connect any outlets or actions of that object to other objects in your nib file. For information on how to set the class of an object, see Setting the Class of an Object (page 139). Like generic objects, you must drag controller objects to the top level of your Interface Builder document window. Unlike generic objects, you should not change the class of a bindings controller object. For information on how to configure the bindings controllers, see Using Cocoa Controller Objects (page 134).
View Controllers
Applications with only one window often change their content by changing the content views displayed in that window. The content view is the portion of a window that you use to display your applications custom content. The content view is not necessarily a single view but may in fact comprise several views embedded inside a parent (or root) view. Management of the content view is the responsibility of a view controller object, which coordinates the movement of that content on and off the screen. Because it is a controller, you can also add custom logic to your view controller classes to manage interactions between the content view and your applications data model. Interface Builder provides a generic view controller object that you can use for managing individual views. The most common way to use a view controller is to instantiate it inside your nib file, but you can also use it as the Files Owner of the nib file.
81
CHAPTER 4
Nib Objects
Open the view and add any additional subviews to it to define your user interface. Connect any additional outlets and actions. Save the new nib file and add it to your Xcode project.
Nib files configured in this way are associated with the corresponding view controller class at runtime. When you create a new instance of your view controller, you pass the name of your nib file to the initWithNibName:bundle: method of the NSViewController class. The first time your application asks the view controller for its view, the view controller loads the associated nib file and returns the view attached to its view outlet. The view controller continues to manage the contents of the nib file internally, purging the views as needed during low-memory conditions and reloading them later as needed. Nib files configured in this manner are often used to implement tab bar and navigation-style interfaces. The content view for each distinct screen is stored in its own nib file and associated with a view controller class. The navigation and tab bar controllers then manage the loading and unloading of each view controller and its associated nib file.
82
CHAPTER 4
Nib Objects
Figure 4-16
For more information about creating user interfaces for Core Data applications, see Xcode Tools for Core Data. For more information about creating Core Data programs, see Core Data Programming Guide.
Formatter Objects
Cocoa applications can use formatter objects to automatically format data displayed in text-based controls. Cocoa provides built-in formatters for number and date values. The formatters themselves use a set of predetermined rules to format the values they receive into something more understandable for the user. For example, you can use a number formatter to display a number as a currency value, with the appropriate separator characters and monetary indicator included in the resulting string. For information about how to apply formatters to your Cocoa objects, see Applying Formatters (page 109).
Placeholder Objects
In Cocoa and Cocoa Touch nib files, a placeholder object is a placeholder for an object that is used in a nib file but not stored in it. (Placeholder objects are not available in Carbon nib files.) It is important to remember that a nib file is simply a set of objects stored in an archival format. When you load a nib file, the nib-loading code unarchives the objects, effectively reconstituting them inside your application. Without placeholder objects, however, those objects would be isolated from the rest of your application code. The presence of placeholder objects inside a nib file provides a bridge between the code you define in your application and the objects in your nib file. The following sections describe the standard placeholder objects that are provided automatically by Interface Builder where appropriate. For information about how to create custom placeholder objects in iOS nib files, see Custom Placeholder Objects (page 85). For additional information about how placeholder objects are replaced by actual objects at load time, see Resource Programming Guide.
Files Owner
Files Owner is the most commonly used placeholder object in nib files and is supported by both Cocoa and Cocoa Touch nib files. In essence, the Files Owner placeholder is the main bridge between your application and the contents of a nib file. In a nib file, the Files Owner placeholder is a placeholder for an object that you plan to specify when you load the nib file. The object does not exist in the nib file itself and is not created when the nib file is loaded.
Placeholder Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
83
CHAPTER 4
Nib Objects
When you load your nib file into memory, the nib-loading methods expect you to pass along an object that you want to designate as the nib-file owner. The class of the object you specify must match the class of the Files Owner placeholder in the nib file. As the nib file is loaded into memory, the nib-loading code substitutes the object you provide for any references to the Files Owner placeholder in the nib file. This substitution results in your objects outlets and actions being automatically connected to the objects inside the nib file. You can designate any of your application objects as the Files Owner of a nib file. Typically, the Files owner object is a controller object that manages the interactions with the views and other controller objects inside the nib file. Table 4-1 lists some of the standard classes that are commonly used to represent Files Owner in applications. Table 4-1 Class
NSDocument
Typical classes used for Files Owner Description Cocoa document-based applications store the document window and other required interface objects in a nib file. The Files Owner of this nib file is traditionally the document object itself (a subclass of NSDocument). When the user requests a new document, Cocoa creates the NSDocument object and uses its associated NSWindowController object to load and manage the associated nib file contents. Each document in the application receives its own custom copy of the nib file objects so as to avoid unwanted interactions between documents.
to manage custom alert panels, modeless panels, and other windows. Window controllers provide a great deal of automatic management for nib files and are especially useful when your nib file contains only one window and perhaps some supporting objects or controls.
NSViewController
In Cocoa applications, a view controller manages custom accessory views and other view-based content. For example, printing accessory panels rely on the use of a view controller to manage the printing behavior. In iOS applications, separate nib files are often used to manage the content view for each distinct screens worth of content. The manager for this content view is a custom UIViewController object, which also provides automatic nib-loading and purging support. If you want to manage a nib file manually, you can use practically any object you like. You might use a custom subclass in situations where you want more control over the management of the nib-file objects. It is up to you to define the relationships between this object and the objects in your nib file.
UIViewController
To configure the File's Owner placeholder, select it in the Interface Builder document window and open the Identity inspector. In the Class field of the Class Identity section, set the value to the corresponding class in your application. Once the class is set, Control-clicking the File's Owner object displays the outlets and actions defined by that class. You can use these outlets and actions to connect other objects to File's Owner. You can use File's Owner as a target for your bindings. For information about configuring and connecting to File's Owner, see Connections and Bindings (page 119).
84
Placeholder Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 4
Nib Objects
First Responder
Cocoa and Cocoa Touch applications use the First Responder placeholder object as a placeholder for the first object in the responder chain. The First Responder typically corresponds to the currently selected object or the object with the current focus in the frontmost window. You use the First Responder as a target for any messages that operate on the current selection or need to be handled by the frontmost window or document. For example, if you wanted a menu command to be handled by the frontmost window, you would dispatch that command to the First Responder object. The First Responder is not required to respond to a given message. If the First Responder does not respond to a given message, Cocoa passes that message to other objects in the responder chain until one does respond. If no object responds, the message is ignored. It is the responsibility of the objects in your responder chain to implement action methods for messages you want to handle. The First Responder placeholder initially displays all of the actions that are either supported natively by Cocoa or defined in your Xcode source files. If you want to add action methods to the First Responder that are not present in either of these locations, you can do so using the Identity inspector. The First Responder Actions section of the Identity inspector includes a plus (+) button for adding new actions to the available list. For information on how to make connections to the First Responder placeholder, see Establishing Connections to the First Responder (page 126). For more information about event handling and the responder chain in Mac OS X applications, see Cocoa Event-Handling Guide. For information about the role of the responder chain in iOS applications, see iOS Application Programming Guide.
Application
In Cocoa nib files, the Application placeholder object gives you a way to connect the outlets of your applications shared NSApplication object to custom objects in your nib file. The default application object has outlets for its delegate object and, in Cocoa applications, the application menu bar. If you define a custom subclass of NSApplication, you can connect to any additional outlets and actions defined in your subclass. At load time, the nib-loading code automatically replaces the application placeholder object with the shared application object from your application. You do not need to specify this object explicitly when loading your nib files.
Placeholder Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
85
CHAPTER 4
Nib Objects
the nib must be accompanied by a pointer to the real object that represents the placeholder. The nib-loading code then swaps in the real object for the placeholder and proceeds to reconnect the outlets and actions of that object. You can include any number of custom placeholder objects in your nib file. The key to replacing a placeholder object at load time is in naming the object. The nib-loading code requires you to specify both the replacement object and the name of that object in a dictionary. You specify the name of the object in the Name field of the Identity inspector. Placeholder object names in your nib file must be unique in order to ensure the correct objects are connected to the right placeholder. The rest of the placeholder object configuration is the same as it is for other objects. You set the class as described in Setting the Class of an Object (page 139) and configure the actions and outlets as usual. For information about how to replace placeholder objects with real objects at load time, see Resource Programming Guide.
Type the name of the object in the search field. Select the object on the design surface and choose Tools > Reveal in Document Window.
To find objects on the design surface, select the object in the document window and choose Tools > Reveal in Workspace.
86
CHAPTER 4
Nib Objects
If you already have nib files with many unrelated resources, you can use the built-in refactoring tools to break your nib file up into smaller, independent nib files. For information about using the refactoring tools, see Refactoring Your Nib Files (page 53).
87
CHAPTER 4
Nib Objects
88
CHAPTER 5
Interface Layout
Interface Builder helps you experiment with different user interface designs by providing you with tools that make it easy to add and change the layout of the windows and views that comprise your interface. You make most of your layout changes directly using the mouse. You start by dragging objects out of the library and into your Interface Builder document. You then use the mouse to position those objects, resize them, and edit their attributes either inline or from the inspector window. In situations where the mouse does not offer the level of control you need, Interface Builder provides other tools to give you precise control over the size and position of individual objects or groups of objects. The following sections describe the layout tools available for you to use along with guidelines on how to use those tools effectively.
Layout Tools
Table 5-1 lists the layout tools that are available for you to use in Interface Builder. Table 5-1 Tool The mouse Tools to help with laying out user interfaces Description The mouse is the tool you use to make coarse adjustments in the position or size of an item. As you move the mouse, the cursor image changes to reflect the action that would occur if you clicked at the current point. For example, a hand cursor indicates that you can drag an item. The size inspector contains field for fine tuning the size and position of items. It also contains tools for aligning and positioning multiple objects relative to one another. Guides provide alignment information for items on the design surface. You can use the automatic layout guides, custom fixed guides, and instantaneous guides. For information about using guides, see About Alignment Guides (page 96).
Size inspector
Guides
Outline view mode In outline view mode, an Interface Builder document displays the hierarchy of the objects in that document. While in this mode, you can rearrange view hierarchies by dragging and dropping objects.
Layout Tools
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
89
CHAPTER 5
Interface Layout
Moving Views
There are several different ways to change the position of a view relative to its parent view:
If the view is unselected, click and drag it to its new location. If the view is selected, move the cursor over the view until the open hand cursor appears. With that cursor visible, click and drag the view to reposition it. If the view is selected, change the values in the X and Y fields of the inspector window (Figure 5-1). If the view is selected, use the arrow keys to nudge it one pixel in any direction. The Size pane of the inspector
Figure 5-1
Moving and resizing operations do not automatically change a views relationship to its parent view. If you click and drag a view that is embedded in another view, Interface Builder moves the dragged view within its parent views frame and clips the dragged view appropriately. For information on how to disassociate a view from its parent so that you can drag it elsewhere in a window, see Changing a Views Parent to Another View (page 102). When moving views using the inspector, you can use the grid control (in the Size & Position section) to position the view relative to different points in its frame. For example, instead of specifying the position of the views lower-left corner, you could specify the position of its center. To do that, you would click the middle point in the grid control to establish that the X and Y values should reflect the center point of the views frame. Changes to those values would then change the position of the view so that its center point matched the new values.
90
CHAPTER 5
Interface Layout
To nudge an object by more than one pixel at a time, you can either hold down the arrow key or use it in combination with the Shift key. Holding down an arrow key nudges the selected view repeatedly at the same speed as the current key repeat rate. Holding down the Shift key increases the nudge increment from one pixel to five pixels. For information on moving windows, see Moving and Resizing Windows (page 92).
Resizing Views
After selecting a view, there are two ways to resize it:
Drag one of its selection handles. Change the width and height values in the size inspector.
Figure 5-2 shows the selection handles created for several different types of views in Mac OS X. You can use a views selection handles to resize that view in any of the available directions. Moving the mouse over a selection handle changes the cursor to indicate that a click would initiate a resize operation. Figure 5-2 Examples of selection handles
During a resize operation, the current width and height of the view (in points) are displayed. If you press the Shift key while diagonally resizing a view with the mouse, Interface Builder maintains the initial aspect ratio of the view. Figure 5-3 illustrates both of these features.
91
CHAPTER 5
Interface Layout
Figure 5-3
A resize operation
If a control is too smallfor example, if the controls title is too wide to be displayedInterface Builder draws a plus icon over the control. Clicking the plus icon sizes the control to fit. If you want to disable this behavior, uncheck the Show Clipping Indicators menu item in the Layout menu.
92
CHAPTER 5
Interface Layout
Figure 5-4
Window anchors
Click and drag the resize handle in the lower-right corner of the window. Change the width and height values in the Content Frame section of the size inspector.
Pressing the Shift key while dragging a windows resize handle constrains the resizing operation to the current dragging direction. A horizontal drag keeps the windows height fixed but changes the width, while a vertical drag resizes only the window height. A diagonal drag resizes the window proportionally in both the horizontal and vertical directions. Note: When resizing a window using its resize handle, Interface Builder does not change the size or position of the windows contained views by default. You can toggle this behavior in situations where you want any contained views to scale up or down based on the new window size. For more information, see Design-Time Resizing Modes for Windows (page 95). In addition to setting the windows size and initial position, you can use this inspector to configure both a minimum and maximum size for the window. Setting these values is recommended, especially if making your window too small or too large might cause controls to be obscured or the layout of your windows contents to change drastically.
93
CHAPTER 5
Interface Layout
You can also use this inspector to modify the windows content border. If you choose autosize, Interface Builder uses a standard content border. In some cases, you can customize this border by entering the desired inset value in the bottom or top fields. This section maps directly to two methods in the NSWindow class:
setAutorecalculatesContentBorderThickness:forEdge: setContentBorderThickness:forEdge:
The NSWindow API supports modifying the content border thickness for all four window edges, but the current implementation only supports setting the bottom, and in some cases the top. Because of this, Interface Builder only shows inspector elements to configure the top and bottom inset values.
94
CHAPTER 5
Interface Layout
Figure 5-5
Struts
Springs
In addition to configuring your views autosizing behavior in Interface Builder, you can also configure it programmatically. For UIView objects, you do so using the autoresizingMask property of the view. For NSView objects, you use the setAutoresizingMask: method of the view. In Carbon, you use the HIViewSetLayoutInfo function. Important: In a Cocoa nib file, if you do not set any springs or struts for your view in Interface Builder but then do use the setAutoresizingMask: method to add autosizing behavior at runtime, your view may still not exhibit the correct autoresizing behavior. The reason is that Interface Builder disables autosizing of a parent views children altogether if those children have no springs and struts set. To enable the autosizing behavior again, you must pass YES to the setAutoresizesSubviews: method of the parent view. Upon doing that, the child views should autosize correctly.
You can resize just the window. You can resize the window and all of its contents.
By default, resizing a window resizes just the window. To resize the window and its contents, hold down the Command key while you click and drag the windows resize handle. Holding down the Command key causes Interface Builder to apply the autoresizing behavior currently in place for the windows contained views. This technique lets you view the runtime resizing behavior of your window or scale the window and its contents to a desired size. You can toggle the default resizing mode by choosing Layout > Live Autoresizing from the menu. When toggled, holding down the Command key resizes just the window.
Aligning Objects
Interface Builder provides numerous tools to help you position objects precisely in your view. The following sections discuss these tools and how to use them.
Aligning Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
95
CHAPTER 5
Interface Layout
Choose the desired alignment from the Layout > Alignment menu. Choose the desired alignment command from the size inspector.
Figure 5-6 shows the buttons in the size inspector that you use to align views. (These buttons reflect the same set of commands available in the menus.) Most of the alignment controls require you to select at least two views but the group placement controls can be used with only one selected view. The vertical and horizontal alignment controls use the layout rectangles of the selected views to perform their layout. The group placement controls center the selected views as a unit along the horizontal or vertical centerline of the window.
96
Aligning Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 5
Interface Layout
Figure 5-6
Top
Center
Right
The baseline vertical alignment control lets you align controls along the baseline of any text in the control. If a control does not contain any text, Interface Builder uses the bottom edge of the control in place of the baseline. If a control has multiple baselines, Interface Builder uses the first baseline returned by the control.
To display the bounding rectangle for all views, choose Layout > Show Bounds Rectangles. To display the layout rectangles for all views, choose Layout > Show Layout Rectangles.
Important: Seeing the bounding rectangle for a view can help you avoid overlapping views in your design. However, you should always do your layout based on layout rectangles. Interface Builder draws bounding rectangles in blue and layout rectangles in red as shown in Figure 5-7. You can display one or both sets of rectangles at any given time or display neither of them. You can use the information provided by these rectangles to assist you during layout.
Aligning Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
97
CHAPTER 5
Interface Layout
Figure 5-7
No rectangles
Bounding rectangles
Layout rectangles
To display guides that show distance from a views layout rectangle to the edge of the windows content view, select the view, press the Option key, and move the mouse over the content view. Figure 5-8 shows a selected button and the dynamic guides that appear.
98
Aligning Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 5
Interface Layout
Figure 5-8
To display guides that show the distance from the currently selected view to any other view, press the Option key and move the mouse over the other view. Figure 5-9 shows a window with a selected box and the distance from that box to a button in the window.
Figure 5-9
You can use the Option key in combination with most other modifier keys and keyboard shortcuts to display layout information while you modify the views. For example, holding down the Option key while using the arrow keys lets you see your layout information while moving a view pixel by pixel.
Aligning Objects
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
99
CHAPTER 5
Interface Layout
Custom guide
100
CHAPTER 5
Interface Layout
Figure 5-11
362
362
280
280
When you change the orientation of your window, Interface Builder does not attempt to resize your views to fit the new orientation. Because nib files reflect the state of your user interface at load time, you must choose one orientation up front and design for that orientation. As a result, you should always set your window orientation prior to adding any views.
Its visible rectangle Its position within the window Its autosizing behavior
Whenever you move a parent view, its child views move with it, always staying in the same position relative to the parent views frame. Similarly, if you delete a view, or cut or copy it, that views children are deleted, cut, or copied as well. Although these relationships are set when you drop the view, you can still change the relationship of a child view to its parent if needed. The following sections describe the different ways to modify the parent of a view.
101
CHAPTER 5
Interface Layout
2.
102
CHAPTER 5
Interface Layout
Exporting nib-file information is useful if you want to view that information or use it as a template for other interfaces. For example, a Carbon developer could use the output of a nib file to gather metrics for laying out windows and controls programmatically. Because the exported data is XML, you can parse it using the XML support found in Cocoa and Core Foundation. You can also open this file using the Property List Editor application (located in <Xcode>/Applications/Utilities). If after exporting your nib object information you want to reimport some changes, you can do so with the --import option in ibtool. For example, to reimport the modified property list from the previous example, you would use the following command:
ibtool --import mynib.plist --write MyNewNib.nib MyNib.nib
When modifying exported properties, you should be aware that setting a property might alter other properties in the nib file upon reimport. During reimport, you should always use the --write option to output the changes to a copy of your nib file.
103
CHAPTER 5
Interface Layout
Group delimiter Notes Boxes Provides the strongest group association but also requires the most space within a window. Provides strong group associations when space is at a premium. Provides good group associations when space is less of an issue. Typically, you would use this technique for smaller groups of controls.
104
CHAPTER 6
Object Attributes
One of the biggest advantages of using nib files in an application is that when you load that nib file, the objects inside retain the same attribute values that you set in Interface Builder. Rather than have to reconfigure your objects programmatically, the nib-file objects are ready to go almost immediately after being loaded into your program. You configure most object attributes using the inspector window. The attributes and identity inspectors expose the more commonly configured attributes for an object. Other panes may also expose important attributes for configuring the visual style of a view. There are a handful of views that support direct editing of text-related attributes on the design surface. Finally, some text-oriented views also support the use of a formatter object, which defines rules for presenting the text in that view. The following sections describe the different techniques for modifying object attributes in Interface Builder. These sections do not cover the specific attributes of the objects themselves. Object attributes are tied to the exposed attributes of the underlying class, and therefore the class reference documentation and human interface guidelines for the target platform are the definitive source for that information.
Select the object and change the desired value in the inspector window. Select the object and change the desired font or color using the font or color panel. (Not available for all views.) To display the font panel, choose Font > Show Fonts. To display the color panel, choose Font > Show Colors. For example, to change the background color of a table view, select the view, bring the color panel forward, and choose the desired color.
Double-click the object in the design surface to edit relevant attributes. (Not available for all views.) If an object displays any text, double-clicking the text string usually opens a field editor that you can use to change the text. For controls such as checkboxes that display a selection state, clicking the control lets you set the default state. Double-clicking a control with a menu (such as a pop-up button) opens the menu for editing.
Changes you make in the inspector window take effect immediately. To revert a change, use the Undo command or change the value in the inspector again. If multiple objects are selected, the inspector window lets you change as many attributes as makes sense for the selection. If all of the selected objects have the exact same underlying class, the inspector shows you all of the same information you would get if just one object were selected. If the classes differ, the inspector shows you all of the attributes that the selected objects have in common. For example, selecting a push button and a text field shows only the control and view attributes in the Attributes pane, while other panes display reduced sets of information.
105
CHAPTER 6
Object Attributes
106
CHAPTER 6
Object Attributes
Figure 6-1
Effects inspector
The Effects pane of the inspector window is divided into several sections, each of which lets you add specific visual effects to your view. Table 6-1 summarizes the sections available in the inspector and the visual effects each one applies. Table 6-1 Section Wants Core Animation Layer Appearance Supported effects Description Lists the selected view and its parent views. Clicking the check boxes in this section enables layers for the given view and any child views. Lists the basic visual effects you can apply to your view. You use this section to apply transparency and shadow effects to your view. Shadow effects that fall outside the bounds of your view are clipped by non Core Animation superviews. Applies Core Image effects to the selected view and its subviews. Applies Core Image effects to the content located behind the view. These filters are applied to any background content prior to compositing that content with your view.
107
CHAPTER 6
Object Attributes
Description Applies a Core Image filter that specifies how your view should be composited with a background image or with the content behind your view. Compositing lets you blend your view contents with other views or images. Adds transition effects to the selected view. These effects are applied to subviews whenever those subviews are added to or removed from the view. Transitions represent an expanded version of the behavior offered by the NSViewAnimation class.
Transitions
For information about how to apply the Core Animation effects associated with your views in your nib file, see Core Animation Programming Guide.
Configuring Filters
Filters let you apply interesting visual effects to the contents of your views. You can use filters to create a specific look for your user interface, to highlight specific portions of your interface, or to apply visual effects to user-defined or dynamically changing content. The advantage of using filters is that you do not have to render the content in advance. You simply add the desired filter to your view and Core Animation composites the filter along with the rest of your views content. This allows you to create and update your content in real time while still providing stunning visual effects. You can use the effects inspector to configure three basic types of filter for your views:
A view can have only one compositing filter but may have multiple content and background filters. To enable a compositing filter, select the desired filter from the list and configure its options. To configure content and background filters, do the following: 1. In either of the Content Filters or Background Filters sections, click the plus (+) button to add a new filter. A filter selection sheet appears.
108
CHAPTER 6
Object Attributes
2. 3. 4.
From the filter selection sheet, select the filter you want to apply and click OK. The filter should appear in the corresponding filter table of the section. To configure the new filter, select it and expand the Details section below the table to display the filter attributes. Change the filter attributes as desired.
You can apply multiple content and background filters to a single view. The filters you add are applied in the order listed in the content filters or background filters tables. To delete a filter, select it from the appropriate table and click the minus (-) sign.
Applying Formatters
Formatters are special objects that modify the textual representations of Cocoa objects. Formatters provide a fast and easy way to format complex text information without writing any code. For example, you might use a formatter in a text field to format a sequence of numbers as a currency or date value. For controls that can accept text input from users, formatters not only reformat the entered text, they also validate it to ensure it does not contain any illicit characters. Cocoa defines two concrete formatter classes that you can use as-is in your interfaces. The NSNumberFormatter class lets you format strings containing integers, floating-point values, currency values, percentage values, and so on. The NSDateFormatter class lets you format strings containing date and time information. You do not have to write any code to use these objects. Instead, each object supports a flexible
Applying Formatters
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
109
CHAPTER 6
Object Attributes
notation that you enter in the inspector to specify how you want text formatted. When subsequently attached to an object, the formatter automatically formats the corresponding objects contents based on the parameters you specified. If you want to format something other than number or date values, you can create your own custom formatters and integrate them into Interface Builder using plug-ins. The NSFormatter class provides the basic interface used by formatters to interact with Cocoa controls and cells. For information on how to create a custom formatter, see Data Formatting Guide. Note: If you are an iOS developer, you can use formatter objects to format text strings prior to display. Formatter objects must be applied from your code, however, and cannot be configured in Interface Builder. Carbon developers must similarly use formatters from their code but must use Core Foundation formatters instead of the Cocoa formatter objects. For information about using formatters programmatically, see Data Formatting Guide or Data Formatting Guide for Core Foundation.
Drag the formatter object from the Library window and drop it on the control. (Recommended) Drag the formatter object to the top level of the nib document window and connect it to the formatter outlet of the target control.
When you drag a formatter object around your window, Interface Builder highlights any controls that can accept that formatter. Essentially, you can attach a formatter to any Cocoa object whose cell defines a formatter outlet. When you drop a formatter onto an object, Interface Builder attaches the formatter to the cell but does not mark its formatter outlet as connected. Instead, it configures the outlet lazily at runtime when the nib file is loaded. To show that the object does have a formatter, Interface Builder displays a badge next to the object when it is selected. To select the formatter, click its badge. Dropping a formatter on a control associates the formatter with that control, configuring all of the necessary connections automatically. From that point, all you have to do is configure the formatter parameters in the inspector and you are done. In addition to being easier to configure initially, this technique reduces the overhead required to manage the formatter object at runtime. Formatters attached directly to an object are released automatically when the object itself is released. Dragging a formatter object to the nib document window adds that formatter to the top level of your nib file. Objects at the top level of the nib file are not released automatically and must be released explicitly by the code that loaded them. The only time you might want to place a formatter object at the top level of your nib file is in cases where several objects need to share the same formatter object. Objects that share a formatter also share the same formatting behavior, and any changes you make to the formatter affect all connected objects. For information on how to connect objects to outlets, see Creating and Managing Outlet and Action Connections (page 120). Note: You should never attach more than one formatter to an object in your nib file. To remove a formatter that you dragged to an object, select its badge and choose Edit > Delete or press the Delete key.
110
Applying Formatters
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 6
Object Attributes
In Mac OS X v10.4 and later, formatters support the conventions defined in Unicode Technical Standard #35. (Recommended) In all versions of Mac OS X, formatters support a set of custom conventions defined in Number Format String Syntax (Mac OS X Versions 10.0 to 10.3) in Data Formatting Guide.
The Unicode conventions include significant enhancements over the older conventions and are recommended for use in any new applications you create. Collection Views lists the key field groups in the inspector and how you use them to configure your format strings. Table 6-2 Para Style Inspector fields for modern formatters Para Default styles for standard types of numerical formatting. Selecting a value from the pop-up menu populates other inspector fields with reasonable starting values. The core format strings for positive and negative values. These fields reflect the current format string derived from the other inspector options. You can also use these fields to modify the format string directly. The padding to apply to the prefix or suffix portion of the format. Each string format can have a prefix, a numeric part, and a suffix. The prefix and suffix portions usually correspond to things like currency or percent symbols that are integral to the format but not part of the numerical portion. You can use the controls associated with this field to specify how many padding characters (and which character) to include before or after the prefix or suffix. Padding may be inserted at only one of the specified locations. Changes you make to this field are reflected in the Format fields. The rounding rules to apply to the number. You can round numbers up or down in various ways and can specify the rounding increment to use. For example, using the half-even setting with an increment of 50, the value 1230 would round to 1250. Changes you make to this field are reflected in the Format fields. The factor to use when converting between numerical values and the corresponding strings. Multipliers allow the formatted value to be different than the value used internally by your program. For more information, see NSNumberFormatter Class Reference. The number of digits to group together between separator characters. The primary grouping represents the digits immediately to the left of the decimal point. Secondary groupings represent the spacing for the remaining digits to the left of the first separator. Specify 0 for the secondary grouping value to use the primary grouping throughout. You can also use the grouping checkboxes to configure additional grouping-related options. Changes you make to this field are reflected in the Format fields.
Format
Padding
Multiplier
Grouping
Applying Formatters
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
111
CHAPTER 6
Object Attributes
Para Constraints
Para The constraints to apply to the resulting number. You can set limits on the value itself or on the number of digits it contains. You can also specify the default symbols to use, although typically these are obtained from the current locale.
For additional information and examples on how to specify formatting strings using the older notation, see Data Formatting Guide. For more information on formatting strings using the Unicode conventions, see Unicode Technical Standard #35.
112
CHAPTER 6
Object Attributes
Help tags are short strings that appear when the user hovers the mouse over a control in Mac OS X applications. You can use help tags to provide the user with basic information about the purpose of a view or give some indication of how it should be used. You specify the help tag for a given control using the Identity pane of the inspector.
For Cocoa nib files, use the Tool Tip section of the identity inspector to set the help tag text. For Carbon nib files, use the fields in the Object Help Identity section of the identity inspector to set help tags
For Carbon controls you can specify both a simple help tag and an extended help description. You use the Help field to specify the basic help text that appears when the user hovers the mouse over a view. You use the Extended Help field to provide an extended version of the help text that appears when the user presses the Command key. Cocoa controls support only the basic help tag information. Nib files in iOS do not support help tags.
113
CHAPTER 6
Object Attributes
Note: For guidelines on how to write your tooltips, see the section on User Assistance in Using Mac OS X Technologies in Apple Human Interface Guidelines. For Cocoa nib files, another way you can provide assistance is by adding Section 508 information (also known as accessibility information) to your controls and views. System technologies such as VoiceOver use accessibility information to describe user interface features to users with impaired vision or other disabilities. Accessibility support is an important feature for many industries and is mandatory if you sell your software into the government sector. You specify accessibility text using the Identity pane of the inspector window. Use the Description field to provide the user with information about an objects purpose. You can also use the Help string to provide a short hint on how to handle the object, although Cocoa uses the views help tag by default if this field is empty. For more information about accessibility and Cocoa, see Accessibility Programming Guidelines for Cocoa. Note: For Carbon nibs, you must add accessibility information programmatically. For information on how to do so, see Accessibility Programming Guidelines for Carbon
The custom view will get these messages when the nib is loaded:
114
CHAPTER 6
Object Attributes
[customView setValue:[NSNumber numberWithBoolean:YES] forKeyPath:@"enabled"]; [customView setValue:@"myID" forKeyPath:@"parent.identifier"]; [customView setValue:nil forKeyPath:@"representedObject"];
For more information about command IDs and how they are used, see Carbon Event Manager Programming Guide.
115
CHAPTER 6
Object Attributes
2. 3.
Open the inspector window and select the Attributes pane. In the View section, set values for the Control Signature and ID fields.
For more information about working with Carbon controls, see Handling Carbon Windows and Controls.
Attribute Guidelines
When building your interface, you should consider the intended use of the windows and menus in your application. Although Interface Builder helps you to create good looking user interfaces in many ways, it is still just a tool that does what you ask it to do. It is up to you to make appropriate design choices as you build your interface. A good source of information about interface design is the human interface guidelines for the target platform:
116
Attribute Guidelines
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 6
Object Attributes
Apple Human Interface Guidelines for Mac OS X iOS Human Interface Guidelines and iPad Human Interface Guidelines for iOS
All interface designers should read the human interface guidelines at least once to understand the basic design principles for the platform. The following sections provide additional guidance for you to consider as you create your windows and menus in Interface Builder.
Names you specify in the identity inspector do not appear in your actual user interface. They are simply cues that Interface Builder displays when you edit your nib file. In addition to assigning names, you can also add notes to your objects. Notes can provide even more help to translators by offering additional context about how an object is used in your user interface. Like names, notes reside in your nib file and never appear in your user interface.
Attribute Guidelines
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
117
CHAPTER 6
Object Attributes
118
Attribute Guidelines
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
CHAPTER 7
For Mac OS X and iOS developers, the ability to connect objects at design time is a key part of the rapid development aspect of applications. Many Cocoa classes use connections to implement basic behaviors, including event handling, window management, focus management, and action dispatch. Connections are therefore an important consideration in the design of your Mac OS X Cocoa and iOS applications. This chapter covers the techniques for creating connections and bindings using Interface Builder. Note: The information in this chapter applies to nib files developed for Cocoa and iOS applications only. Carbon applications do not support connections. Instead, Carbon objects must be configured with command IDs that are then used by the underlying code to respond to interactions with views and controls. For more information on configuring Carbon nib files, see Specifying Carbon Attributes (page 115).
Outlet connections Action connections (Mac OS X only) Event connections (iOS only) Bindings (Mac OS X only)
An outlet connection is a special type of instance variable that you specify in your source files and configure using Interface Builder. You use outlets to store references to important objects in your nib file, such as important views, controls, and controller objects. Your view classes can similarly use outlets to store references to related objects. For example, many Cocoa views use outlets to locate the data formatters, delegates, and contextual menus they should use. Because they are instance variables, you can modify outlets programmatically if you wish, but doing so is unusual. In most cases, you connect an outlet to its target object in Interface Builder and do not change the outlet later. Note: The name outlet comes from the notion that when you connect an object to an outlet, you plug in the object to that outlet. An action connection is a message-passing relationship between a control and a target object in a Cocoa application. Whenever the user interacts with a control in a predetermined way or selects a menu item from a menu, the control or menu invokes the action method of its associated target object. You can use action methods to perform whatever tasks are needed to respond to the given interaction. For example, if the user clicked an Apply button in a panel, your action method could apply the specified settings to your applications data structures. Clicking a push button, checking or unchecking a checkbox, or selecting an item from a pop-up menu button are all examples of control interactions that generate action messages.
119
CHAPTER 7
An event connection is similar in nature to an action connection but is specific to iOS applications. Controls in the UIKit framework can send different action messages for different types of interactions within a control. For example, a control can send separate messages when the user first touches the control and then subsequently lifts that finger from the screen. In addition each event can have multiple target objects, so that when the event occurs, different action messages are sent to each object. Cocoa bindings are a way to connect your applications user interface to its underlying data without writing a lot of glue code to synchronize the two. Bindings take advantage of the key-value coding (KVC) and key-value observing (KVO) protocols to bridge the data in your data structures with the views you create in Interface Builder. Whenever the user changes a value in a view, the bindings code automatically propagates that change down to the associated data structure. Similarly, if your program changes the data by calling an accessor method, the bindings code propagates that change back to the associated view.
When you use the control-drag gesture to create a connection for an action, the final part of the drag involves picking the action name from a list of actions. Outlets have a similar list of outlets. If there are previous connections that have the same name, the menu items to pick those names will be flagged. If an identical connection to the one being made already exists, the menu item will be flagged with a dot. If a connection exists with that name, but to a different object, it will be flagged with a dash.
120
CHAPTER 7
For action connections in Cocoa, this technique is equivalent to opening the connections panel and configuring the source objects sent actions connection. Because a source object in Cocoa can send its action message to only one target object, you should use this technique only once to configure a given source objects action connection. Repeating the process for the same source object would break the old connection before establishing the new one. You can use this technique, however, to configure each of the source objects outlets.
121
CHAPTER 7
You can start at the target object and connect one of its action methods to the desired source object.
To create a connection starting at the source object, Control-click it to display the connections panel and scroll to the appropriate entry. Click in the circle next to the entry and drag to the desired target object that you want to receive the action or event message, as shown in Figure 7-1. When you let go of the mouse over a valid target object, Interface Builder displays a second connections panel that lists the action methods of the target object. Selecting a method from the list completes the connection. Figure 7-1 Connecting from source to target
To create a connection starting at the target object (the one that defines the action method), control-click the target object to display its connections panel. Click in the circle next to the desired action method and drag to the source object, as shown in Figure 7-2. When dragging from the target to the source object in a Cocoa application, Interface Builder does not need to display a second panel at the source object. For iOS applications, however, it displays a second panel so that you can choose the event you want to trigger the action message.
122
CHAPTER 7
Figure 7-2
When connecting from target to source, you can connect each action method multiple times. After you make the first connection, the circle next to the action method is filled to show that there is an associated source object. To connect an additional source object, simply click in the circle again and drag to the desired object. Performing this action does not remove the original connection.
123
CHAPTER 7
Figure 7-3
Note: In Mac OS X and in iOS 3.3 and earlier, only one object at a time may be connected to a given outlet. In iOS 3.4 and later, multiple objects can be connected to a given outlet. See Defining Outlets and Actions in Interface Builder (page 145) for details. To connect an outlet starting at the target object, open the connections panel and click in the circle next to the New Referencing Outlet entry. From there, drag to the object that contains the desired outlet and release the mouse over that object. When you release the mouse, Interface Builder prompts you to select the outlet from a list of available outlets on the source object. Selecting an item from that list completes the connection.
124
CHAPTER 7
Figure 7-4
Connections inspector
To make a connection, do the following: 1. 2. 3. Select an object and open the connections inspector. Click in the circle next to the entry you want to connect and hold the mouse button down. Drag the mouse over the target object for the connection. (If the target of a connection is not visible, hovering over its parent object causes the parent to open and reveal its children.) The target object should highlight to indicate a connection is possible. If it does not highlight, the target object is not of the right type and cannot be connected to the source object in that way. 4. 5. If the target object highlights, release the mouse button to create the connection. If you are using the connections inspector to configure the sent action or referencing outlet for the object, Interface Builder displays a list of the target objects action methods or outlets. Select the desired action method or outlet from the list to finish the connection. Other types of connections do not require this configuration step. After you establish a connection, the connections inspector fills the circle next to that entry and displays information about the connection. Each connection also includes a close box icon that you can use to break the connection. If a received action has multiple source objects associated with it, the panel displays a disclosure triangle, which you can use to reveal the individual connections.
125
CHAPTER 7
Breaking Connections
To break a connection using the connections panel, do the following: 1. 2. 3. Control-click the desired object to display its connections panel. Locate the outlet or action whose connection you want to break. Click the "Break connection box next to the name of the connected object.
An alternative to using the connections panel is to break connections using the inspector window. The Connections pane of the inspector window lists all of the connections for the currently selected objects. To break a connection using the inspector window, you locate the connection and click its break connection box. For more information about the connections inspector, see Making Connections Using the Inspector (page 124).
Document-level operations (such as undo, save, and print) Pasteboard operations Text-manipulation operations Selection management operations (such as select all) Application-level operations (open document, hide, unhide, show help) Custom actions that you define
In iOS applications, touch events are delivered to the first responder initially and then passed down the responder chain as needed until an object handles the event. In most cases, the first responder is the view in which a touch occurred, but it can be other views or objects in the application.
126
CHAPTER 7
If you have an action message that should be handled by the First Responder, you can use the First Responder placeholder object as the target object for your action. By default, the First Responder knows about the action messages supported by the system (if any) and those defined in your Xcode source files. If you want to add new action messages, you must add those messages to the First Responders supported list by doing the following: 1. 2. 3. 4. 5. 6. Select the First Responder placeholder object in your Interface Builder document. Open the inspector window and select the Identity pane. Click the plus (+) button in the First Responder Actions section to create a new action method entry. (The new method name is selected by default.) Type a new name for the method. (The syntax of the method must match the expected syntax for action methods on the given platform; see Defining Action Methods (page 143) for more information.) Press Return to save the action method. Repeat as needed to add additional action methods.
Adding action methods to the First Responder placeholder object does not add the corresponding method definition to your Xcode source files. All it does is let Interface Builder know that such a method exists in one of your programs objects. It is up to you to ensure the method names you add to the First Responder placeholder match the names of the methods in your code. Interface Builder does not validate these method names for you. At runtime, if a method name is misspelled or does not exist in an object, the corresponding action message will never be received by the target object. Note: The First Responder placeholder is only for configuring action messages. You cannot connect the First Responder placeholder object to one of your custom outlets in hopes of receiving a dynamically changing pointer to the selected object in your window. In Cocoa applications, you should instead use the firstResponder method of the current NSWindow object to get the first responder. In iOS applications, there is no single first responder object; the first responder is always the view that is the target of a touch. Interface Builder does not prevent you from deleting the standard system messages associated with the First Responder placeholder. Doing so removes the message name from the current nib file only.
Connect the corresponding menu item to a First Responder method. Connect the menu item to a method of your custom application object or your application delegate object.
Of these two techniques, the first is somewhat more common given that many menu commands act on the current document or its contents, which are part of the responder chain. The second technique is used primarily to handle commands that are global to the application, such as displaying preferences or creating a new document. It is possible for a custom application object or its delegate to dispatch events to documents, but doing so is generally more cumbersome and prone to errors.
127
CHAPTER 7
The behavior for connecting a menu command to an appropriate target is the same as for creating other types of connections. You can use the connections panel or do a quick connection by Control-clicking and dragging from the menu item to the desired target. For information about creating connections using these techniques, see Making Connections Using the Connections Panel (page 121) and Making Quick Connections By Dragging (page 120). Note: In addition to implementing action methods to respond to your menu commands, also remember to implement the methods of the NSMenuValidation protocol to enable the menu items for those commands.
Creating a Binding
In Interface Builder, you typically bind Cocoa views and controller objects in your nib file to the data in your custom controller objects. The high-level process for creating a binding in Interface Builder is as follows: 1. Create the views needed to display your data.
128
CHAPTER 7
2.
Create any intermediate controller objects needed to manage your data. (Typical controller objects include instances of your custom NSDocument or NSWindowController subclasses, NSController subclasses, or custom NSObject subclasses that you create to manage your data structures.) Use the Bindings pane of the inspector window (Figure 7-5) to configure each desired binding.
Figure 7-5
3.
Bindings inspector
Although each binding displays several configuration options, the most important part of a binding is the target of the binding. You must configure, at a minimum, the following fields for any given binding:
The Bind to field specifies the controller object to use as the starting point for accessing the target data. The Model Key Path field contains a string representing the key path for the desired data. Key path strings are of the form <property_name>[.<property_name>]*. The first property name in this string is a property on the controller object specified by the Bind to field. Each subsequent property name corresponds to a property of the object returned by the previous property name. Say, for example, that you have a custom controller object and the key path string person.address.street. The person property returns the person object of the bound controller. The address property returns the address of the corresponding person object. And the street property returns the desired data value stored in the address object.
129
CHAPTER 7
Because key paths are dependent on your data model, the best way to understand how to configure them in Interface Builder is to go through some examples. The following sections show how to bind a text field to an NSNumber object so as to display the number value in that text field. In each successive example, the data model used to access the number value gets progressively more complex, and so the bindings must be adjusted to compensate for the increased complexity. For additional bindings examples, see Cocoa Bindings Programming Topics. For information about the key fields in the bindings inspector, see Configuring the Attributes of a Binding (page 133).
NSNumber
Note: Because Cocoa knows how to convert between many scalar types and their object equivalents, the binding configuration would be the same if you implemented the quantity property as a scalar value.
130
CHAPTER 7
Figure 7-7
File's Owner MyDocument entry
Entry quantity
NSNumber
Although the preceding example would work when the documents entry property is non-nil, a problem arises if entry ever becomes nil. When Cocoa encounters a nil value in the middle of a key path, it generates a runtime error. This error does not abort your program but it does prevent Cocoa from retrieving and setting the bound value, which is certainly undesirable. Rather than binding the text field directly to the Files Owner, as in the previous example, a better solution is to bind the text field to the value through an NSObjectController object. Controller objects act somewhat like a buffer layer between your views and data object. In this case, the controller object acts as a placeholder for the documents current Entry object, providing a valid binding target even if the documents entry property is nil. Figure 7-8 therefore shows the newly introduced object controller and the revised bindings paths. Now, the text field binds to the object controller as if it were the documents Entry object. The object controller, in turn, binds to the entry property of the document. Figure 7-8
File's Owner MyDocument entry Binding: "Content Object" Bind to: File's Owner Model Key Path: "entry" Entry quantity NSObjectController Binding: "Value" Bind to: NSObjectController Controller Key: "selection" Model Key Path: "quantity" NSTextField
NSNumber
131
CHAPTER 7
Because it knows about controllers and their properties, Interface Builder displays the bindable properties of the selected controller object in the Controller Key popup menu. You typically set the value of this field to either selection or selectedObjects, depending on your needs. To finish your binding, you add the target property in the Model Key Path field, which in this case is quantity. Cocoa combines the strings in the Controller Key and Model Key Path fields to get the final key path. In this case, the final key path would be selection.quantity.
NSNumber
Although the array controller manages the selection indexes for you, you can bind an NSMutableIndexSet object to the array controller if you want to keep track of the currently selected indexes. You might store the selected index information as part of your document format. You can also use the index set to change the currently selected objects (instead of using the methods of the NSArrayController class). When modifying your bound index set directly, however, you must do so in a KVO-compliant manner by calling the willChangeValueForKey: and didChangeValueForKey: methods before and after you make your changes. If you forget to call these methods, the array controller may not notice your changes.
132
CHAPTER 7
Controller Key
Value Transformer
No Selection Placeholder
133
CHAPTER 7
Description The behavior of a view when an exception is raised because the key of an object cannot be applied for some reason. This might occur if the specified object is not key-value coding compliant for the specified key. The behavior of a view when the binding is associated with a nil object. The exact configuration of this field depends on the type of the object. For views and controls, you can use this field to specify a default value to display.
Null Placeholder
For an exact list of bindings available for a given view or controller object, see Cocoa Bindings Reference.
Controller objects manage their own current selection and placeholder values, providing appropriate values if the selection is empty. Controller objects implement the NSEditor and NSEditorRegistration protocols, which provide the associated view with a way to negotiate uncommitted changes between itself and the controller. Controller objects eliminate the need for complex management code. Nearly all of your controller object setup is done in Interface Builder. Most controllers provide default actions for manipulating the managed content.
Cocoa provides controller objects for managing several different types of data objects. Most of these controllers enable you to manage collections of objects, with the controller object itself managing things like the currently selected objects. Table 7-2 lists the available controller object classes along with information about when you might use each one and how you configure its attributes. Table 7-2 Class Cocoa controller objects Description
NSObjectController Manages any single NSObject instance. Use this controller to manage a single
custom object and its properties. When configuring the attributes for this controller, the Class Name field (in the Attributes pane of the inspector) should contain the class of the object being managed.
NSArrayController
Manages the contents of an NSArray or NSSet object. (You can also use this controller to manage custom data objects that implement ordered sets of data. For more information, see Cocoa Bindings Programming Topics.) An array controller tracks not only the contents of the array or set but also the subset of objects in the set that represent the current selection. When configuring the attributes for this controller, the Class Name field (in the Attributes pane of the inspector) should contain the class of the objects in the array and not the class of the array itself.
134
CHAPTER 7
Class
NSTreeController
Description Manages a custom set of objects organized in a tree structure. When configuring this controller, you must specify the keys used to access child objects in the tree. In addition, the Class Name field (in the Attributes pane of the inspector) should contain the class of the objects in the tree. For more information, see Configuring an NSTreeController Object (page 135). Provides your application with access to the applications defaults database. You typically use this controller to implement preferences panels by binding the controls in your preferences window to keys in the defaults database. The user defaults controller does not use object class name information. For more information, see Using the Shared User Defaults Controller (page 136). Introduced in Mac OS X v10.5, this controller manages the keys and values inside an NSDictionary object. The controller turns the contents of the dictionary into an array of key-value pairs that can be bound to user interface items, such as columns in a table view. For more information about using this object, see NSDictionaryController Class Reference.
NSUserDefaultsController
NSDictionaryController
When creating bindings in your nib file, you should always use Cocoa controller objects when you are binding through some intermediate object. In other words, unless you are binding directly to a scalar type, you should probably be using a Cocoa controller object to manage the objects in your binding key path. Note: Cocoa controller objects are not necessary for managing data in Cocoa objects that store scalar data types, including NSString, NSNumber, and NSValue. You can bind directly to those objects as if they were scalar types. In the Attributes pane of the inspector window, many controllers let you specify a list of key names. These keys represent the properties of the managed object to which clients can bind themselves. Adding keys to this list is a shortcut that eliminates the need to type the key name each time you want to bind to them. Interface Builder displays the key names in the Model Key Path fields popup menu whenever you bind to the corresponding controller object. To finish the binding, simply select the key from this menu. For more information about object management in controllers, see Cocoa Bindings Programming Topics.
In Class Name field, specify the class name of the objects in the tree.
135
CHAPTER 7
Optionally, specify any custom keys of the tree objects that you want to expose in the Model Key Path field of the bindings inspector.
4.
In the Children field, specify the key path for the property that identifies the child nodes of a given tree object. In the Count field, specify the key path for the property that indicates how many children a given tree object has. (This key path is optional.) In the Leaf field, specify the key path for the property that identifies whether the current tree object is a leaf node. (This key path is optional but recommended because it can improve the tree controllers performance as it navigates your tree at runtime.)
For more information on using tree controllers, see Cocoa Bindings Programming Topics.
By default, the shared user defaults controller sets the value in the Controller Key field to "values Individual . preference values are accessed through this property on the user defaults controller, so you should leave this field configured as is. For more information on configuring user defaults bindings, see User Defaults and Bindings in Cocoa Bindings Programming Topics.
136
CHAPTER 7
duplicated to and from the pasteboard with the object that declares the outlet, not the object the outlet points to. Bindings are duplicated to and from the pasteboard with the bound objects, not the controllers the objects are bound to. Here are some examples:
Duplicating a table view would duplicate the delegate and data source outlets. Duplicating a "My Application Delegate" controller object would duplicate all of its outlet connections. Duplicating a table view would duplicate all of its bindings to controllers.
137
CHAPTER 7
138
CHAPTER 8
Xcode Integration
Interface Builder itself is not a coding environment; it is a visual design environment. Although you can use it to define new Objective-C classes, and to add outlets and actions to existing classes, the preferred approach is to use Xcode for those tasks. Interface Builder is tightly integrated with Xcode and is able to retrieve information about the classes in a project and make that information available to you as you work on the projects associated nib files. To make the most of Interface Builders integration with Xcode, you should do the following during development: 1. 2. 3. Keep your Xcode project open while editing your nib files. Whenever you want to create a new class, or add an outlet or action to an existing class, do it in Xcode. To set the class of an object, simply type its name in the Identity pane of the inspector window.
The Xcode integration works best if both Xcode and Interface builder are running at the same time. If your Xcode project is open, Interface Builder periodically queries it for information about new classes or changes to existing classes. You can tell if a document is associated with an Xcode project by looking at status bar along the bottom edge of the document window. This bar displays the name of the associated Xcode project and an indicator that lights up green when the project is available. Note: Because it associates each nib file with a specific Xcode project, Interface Builder knows only about the classes that are defined in that project. If the project includes an external framework that defines custom controls or objects, you must add any class definitions from that framework to your nib file manually as described in Establishing Connections to the First Responder (page 126). If Xcode is not running, Interface Builder supports alternate ways to associate your class information with your nib files. The following sections describe these techniques and show you how to use the Xcode integration to build your user interfaces efficiently. The Xcode integration is supported only for applications that use the AppKit or UIKit frameworks and is not supported for Carbon applications. For additional information about working in the Xcode environment, see Xcode Workspace Guide.
139
CHAPTER 8
Xcode Integration
Figure 8-1
Generic NSView
Generic objects
Generic NSObject
To add a custom view or object to your Interface Builder document, do the following: 1. Drag the desired object from the library.
For a generic view, drop it onto your windows design surface. (You can also drop views onto the Interface Builder document window if you just want a view resource without a surrounding window.) For a generic object, drop it into your Interface Builder document window.
2. 3. 4.
Select the view or object. Open the identity inspector. Use the available controls to configure the class information.
In Cocoa and Cocoa Touch nib files, configure the class name using the Class Identity section of the identity inspector; see Figure 8-2. Type the name of your class in the Class field or use the combo box control to select the class from the current list of known classes.
140
CHAPTER 8
Xcode Integration
Figure 8-2
In Carbon nib files, specify the Class ID of the class in the Class Identity section of the identity inspector.
If your nib file is associated with an Xcode project, Interface Builder attempts to complete the class name automatically as you type it. When the class is set, Interface Builder displays the known outlets and actions for that class in the inspector. If your nib file is not associated with an Xcode project, Interface Builder displays the class name but does not display any outlets or actions initially. You can add outlet and action information using the appropriate sections of the inspector if you like. If you do so, however, you must manually add those same outlets and actions to your source files later. For information about using Interface Builder to define outlets and actions, see Defining Outlets and Actions in Interface Builder (page 145).
Custom Objects
Because the Classes library makes it easy to instantiate your custom classes, the recommended workflow is: 1. 2. Create your custom classes in Xcode. Instantiate them in Interface Builder by dragging them out of the Classes library.
141
CHAPTER 8
Xcode Integration
This eliminates the need to drag out a generic view or object and then set its custom class.
Defining Outlets
The IBOutlet and IBOutletCollection keywords signal to Interface Builder that you want to populate a variable with real objects when a nib file is loaded. Outlets can be weakly typed or strongly typed in your code. Weakly typed outlets (those whose type is id) can be connected to any object in your nib file. Strongly typed outlets can be connected only to an object whose class matches the type of the outlet. To add an outlet to a class, you can insert the IBOutlet keyword in front of its instance variable declaration, as shown in the following example:
@interface MyClass : NSObject { IBOutlet id aGenericOutlet; IBOutlet NSView* aViewOutlet; } @end
If you use this approach, you should define accessor methods that ensure the objects are retained at runtime. In Mac OS X and in iOS 3.2 and earlier, you can connect an outlet to only a single object. However, starting with iOS 4.0, you can connect an outlet to multiple objects. To do so, use the IBOutletCollection keyword. For example, to connect a view controller to multiple objects of type UILabel, you could add the following code in Xcode:
@interface MyController : UIViewController { IBOutletCollection (UILabel) NSArray* multipleLabels; } @end
If the output targets are not all the same kind of object, use id for the object type in the declaration, or omit the object type in the parentheses following IBObjectCollection; for example:
@interface MyController : UIViewController { IBOutletCollection (id) NSArray* multipleObjects; } @end
A better approach is to declare each outlet as a property. The IBOutlet or IBOutletCollection keyword goes immediately before the propertys type information and after any parenthetical attributes, as shown in this example:
@interface MyClass : NSObject
142
CHAPTER 8
Xcode Integration
{ id NSView* NSArray* NSArray* } @property @property @property @property @end aGenericOutlet; aViewOutlet; multipleLabels; multipleObjects;
(nonatomic, retain) IBOutlet id aGenericOutlet; (nonatomic, retain) IBOutlet NSView* aViewOutlet; (nonatomic, retain) IBOutletCollection (UILabel) NSArray *mutipleLabels; (nonatomic, retain) IBOutletCollection (id) NSArray *mutipleObjects;
For more information about properties, see The Objective-C Programming Language.
In Cocoa Touch applications, an action method can take one of three forms, shown here:
- (IBAction)respondToButtonClick; - (IBAction)respondToButtonClick:(id)sender; - (IBAction)respondToButtonClick:(id)sender forEvent:(UIEvent*)event;
Action methods do not require a one-to-one correspondence with the controls in your interface. You can define one action method for each control in your interface or several controls can share a single action method. When present, the sender parameter in an action method contains the object that sent the action and can be used to help process the action. In iOS, the optional event parameter conveys additional details about the specific type of event that triggered the action. If you subclass standard system classes, you should check the definitions for any parent class before adding your own custom action methods. For example, many Cocoa classes already implement cut:, copy:, and paste: action methods to respond to pasteboard actions. Using inherited action methods lets you respond to messages sent by your own code and also messages sent by the system. In general, you should implement custom action methods only when the action methods provided by parent classes are insufficient or do not provide the behavior you need.
143
CHAPTER 8
Xcode Integration
144
CHAPTER 8
Xcode Integration
When you type the name of an unknown class in the identity inspector, Interface Builder assumes that this class exists somewhere outside the nib file. After creating the class, you can define outlets and actions for it as described in Defining Outlets and Actions in Interface Builder (page 145) and use those outlets and actions to create connections in your nib file. Classes created in this manner have an unknown superclass and exist only within Interface Builder.
145
CHAPTER 8
Xcode Integration
Note: Beginning in Interface Builder 3.2, the management of actions and outlets and been moved from the identity inspector to the classes tab in the Library window. The only exception to this is the First Responder. Actions and Outlets for the First Responder have been moved to the attributes inspector. Figure 8-3 Defining outlets and actions in the Library window
To add an outlet or action, do the following: 1. 2. Click the plus (+) button in the appropriate section to add the new action or outlet. Type a new name. As you type the name of an action method, Interface Builder displays warnings in the Class Actions section of the inspector to let you know if you are specifying an invalid method name. In Mac OS X, action methods take a single parameter and therefore the method name must end with a colon (:) character. In iOS, action methods may take zero, one, or two parameters. 3. Optionally, specify a custom type for outlets by typing the appropriate class name. (You can also change the parameter type of action methods, although id is the standard parameter type.)
146
CHAPTER 8
Xcode Integration
To remove a custom defined outlet or action, select it in the identity inspector and click the minus (-) button. You can remove only those outlets and actions you previously added using Interface Builder. You cannot remove outlets and actions you created in your Xcode source files or those defined in a Cocoa parent class. The outlets and actions you add using the Library window remain local to Interface Builder and your Interface Builder document. Interface Builder does not attempt to merge these outlets and actions back into your Xcode source files; you must do that manually. You can write out source and header files containing the outlet and action definitions for your class by choosing File > Write Class Files. You can then use the generated files as your initial source or merge their contents in with your existing source files using your favorite merge tool, such as the FileMerge application. Note: To copy outlets and actions into your Xcode source files, you can drag entries from the Library window and drop them into the corresponding source file. Xcode pastes a properly formatted outlet or action declaration into the source file at the drop point. You can also select an outlet or action entry in the Library window and select Edit > Copy to copy the declaration to the pasteboard.
Beginning in Interface Builder 3.2, you can generate or update source files using the classes tab in the Library window: 1. 2. Select the class for which you want to generate or update source files. Display the action menu and choose Write Updated Class Files or Generate Class Files.
After generating the source files, you should add them to your Xcode project and make any future changes from there. Changes made to source files in your Xcode project are automatically picked up by Interface Builder, but the reverse is not true. Interface Builder does not update source files after it generates them. Instead, you must incorporate any additional changes into the source files manually from Xcode.
147
CHAPTER 8
Xcode Integration
Drag the class header files from Xcode or the Finder and drop them onto your Interface Builder document window. From Interface Builder, choose File > Read Class Files and select the header files.
When you use either of these techniques, Interface Builder parses the provided header files for information and caches that information in your Interface Builder document. The cached information remains valid until the next time you import header files or until Interface Builder accesses the class information from the associated Xcode project. If the header files you import refer to other custom classes, you should import the header files for those other classes as well. This is especially important if the parent of your custom class is also a custom class. Without the full parent class hierarchy, Interface Builder cannot build a complete picture of the outlets and actions of the class. However, you do not need to import classes defined in the AppKit or UIKit frameworks or those that are defined in an Interface Builder plug-in.
148
CHAPTER 9
Interface Builder provides tools to help you validate the contents of your documents against the platform on which you plan to use them. In addition to testing the behavior of your interface in the simulator, you can also verify that the operating system on which you plan to run your software supports all of your nib file objects. Different versions of an operating system may support different objects or different attributes for those objects. If your nib files contain objects that are not available on the current platform, your program may crash. The following sections show you how to use Interface Builder to test your nib files.
The associated Xcode project information The document format (nib or xib) The lock attributes for the nib file; see Locking Down Your Nib File (page 153) The intended deployment and development targets Any design errors, warnings, and notes
Figure 9-1 shows an information window with a design time issue. Double-clicking an item in this table selects the item and brings it to the foreground.
149
CHAPTER 9
Figure 9-1
Set the deployment target value to match the deployment target of the Xcode target that uses the nib file. Interface Builder uses deployment targets to identify potential problems with your nib file. For example, if your deployment target is set to Mac OS X v10.3 but a window includes a control that was introduced in Mac OS X v10.5, Interface Builder reports the inclusion of the control as an error. Correcting deployment errors ensures that the nib file can be loaded successfully on the target platform. The deployment target has a default setting which you can set and forget. The default setting is tied to the associated Xcode project's SDK setting. When you change the projects base SDK, the deployment target of the NIB file changes automatically.
Set the development target value to indicate which versions of Interface Builder can use the file. If the development target is set to 3.2, the file will be usable with Interface Builder 3.2 and later. If the target is set to 3.0, the file will be usable with Interface Builder 3.0, 3.1, and 3.2. For example, if your development target is set to 3.0 and you have a custom object with user-defined runtime attributes (a feature introduced in 3.2), Interface Builder reports an error. Correcting development errors ensures that the nib file can be edited successfully with the target version of Interface Builder.
You must remove errors before saving your nib file and should try to remove warnings as well. Although you can change the severity of different types of design issues from the Interface Builder preferences window, you should do so only when you know that it will not affect the ability to load and use your nib file.
150
CHAPTER 9
The resizing rules of your window work exactly as they would at runtime. Cocoa bindings are active. Any views bound to user defaults or other views display the appropriate data. Actions that occur relative to other views in the window can be exercised.
To enter simulation mode for a window, select the window and choose File > Simulate Interface. To exit simulation mode, choose Quit from the simulator application menu or press Command-Q. Upon quitting the simulator, you are returned to Interface Builder. If your interface is designed for an iOS device, you may want to simulate the interface for a different device, iPhone or iPad. For an iPhone interface, choose File > Simulate as iPhone/iPod touch. For an iPad interface, choose File > Simulate as iPad.
151
CHAPTER 9
152
CHAPTER 10
Localization
After you finish your applications user interface, you can hand off completed nib files to your localization team for translation into other languages. The localization team can use the ibtool command-line program to extract any localizable strings from your nib files and create matching nib files in your products target languages. The team can also use Interface Builder to lock nib files to prevent engineers from making further changes that might impact in-progress localizations. The following sections discuss how to use these features in Interface Builder.
Non-localizable properties The user may change user-visible strings and attributes such as the size of the object, but may not change any other attributes of the object. The localization team can use this mode to incorporate translations without accidentally changing other object attributes. You can apply lock attributes to your entire nib file or on an object-by-object basis. By default, nib-file objects are configured to inherit their lock attribute from their parent object, with top-level objects inheriting their lock attribute from the nib file itself. Changing the lock attribute for a given object affects the selected object and all of its children. Thus, you can use this behavior to lock specific portions of your user interface while still allowing you to work on other portions.
153
CHAPTER 10
Localization
To change the lock attribute for a single object, do the following: 1. 2. 3. Select the object. Open the inspector window and select the Identity pane. In the Interface Builder Identity section, select the desired locking option from the Lock pop-up menu.
To change the lock attributes for your entire nib file, do the following: 1. 2. 3. Select the nib document window. Select Window > Document Info to open the information panel. Select the desired locking option from the Document Locking pop-up menu.
If you want to remove any custom lock attributes from the objects in your nib file, you can do so manually by modifying the individual objects, or you can use the Reset All Objects button in the nib information window. Clicking this button returns all nib-file objects to their default state, whereby they inherit their lock attribute from their parent object. You can use this button to ensure that all nib-file objects are set to a known state.
The following sections describe the steps for extracting the localizable strings from your nib file and for reincorporating them later. This process is accomplished using ibtool, which is a command-line program used to manipulate nib files. This tool is included with Xcode 3.0 and later, and is located in the <Xcode>/usr/bin directory.
154
CHAPTER 10
Localization
Note: The ibtool program is a reworked version of the nibtool command-line program, which is included with earlier versions of Xcode. The nibtool program can only parse nib files created by Interface Builder 2.5.x and earlier. The ibtool program is capable of parsing Interface Builder 3.0 documents as well as earlier nib file formats. If youre using Interface Builder 3.0 or later, you should convert your 2.x format nib files to one of the 3.x formats before you localize them. Each time you run it, ibtool outputs a status report to the Terminal window. The status report contains any information you requested about the nib file along with any errors that were encountered. The output is formatted as an XML-based property list file, which you can copy and paste into a text file with a .plist file and then open using the Property List Editor application (located in <Xcode>/Applications/Utilities). For more about the types of information you can include in this property list, see the ibtool man page. The ibtool program supports the XLIFF format when working with strings files. XLIFF is a file format than is used to exchange information between many localization tools. For more information about this format, see XLIFF 1.2 specification.
The --generate-stringsfile option causes ibtool to parse the specified nib file and generate a strings file containing all of the strings that should be localized, including things such as control titles, tool tips, placeholder text, and accessibility information. The strings file is written out using the UTF-16 encoding, which is the recommended encoding for strings files. For each entry, the file includes comments indicating the object that contains the string, the objects ID, and the current string if one is set. After you translate the exported strings, you use ibtool to merge the translations back into your nib file. In Terminal, you should invoke ibtool using a command similar to the following:
ibtool --strings-file MyNib.strings --write MyNewNib.nib MyNib.nib
Using these parameters, ibtool copies the specified nib file, merges in the contents of the strings file, and writes out a new nib with the changes. When using the --strings-file option, ibtool updates only those strings that are listed in the specified strings file. If you added any strings to your nib file after extracting the initial strings file, those new strings are not touched during the merge. The --write option specifies the name of the new nib file to write out with the localized strings.
155
CHAPTER 10
Localization
Figure 10-1 shows the files involved in an incremental localization update. In this example, changes were made to the English nib file in version 2.0 of the program. The updated English nib file also contains a handful of new controls, the strings for which have been translated into French and incorporated into an updated version of the French strings file. Figure 10-1 Merging changes into a localized nib file
Version 1.0 en.lproj Version 2.0
fr.lproj
Merged nib
During the merge, ibtool pulls information from both the original and the new versions of the English nib file, plus the original French nib file and updated strings file, to create the new French nib file. The command you would use in Terminal to perform this merge would look similar to the following (without the extra formatting):
ibtool --previous-file ./old/Resources/en.lproj/MyNib.nib --incremental-file ./old/Resources/fr.lproj/MyNib.nib --strings-file ./new/Resources/fr.lproj/French_2.0.strings --localize-incremental --write ./new/Resources/fr.lproj/MyNib.nib ./new/Resources/en.lproj/MyNib.nib
The --previous-file and --incremental-file options specify the master and translated nib files from the previous release. In this case, these are the original English nib file and its French counterpart. The input file for ibtool is the updated master nib file containing the new content for the new version of your application. The --strings-file parameter is optional and only necessary when you want to incorporate updated or new translations into the merged nib file. The --write option specifies the name of the file you want to create based on these inputs. As it performs the merge, ibtool starts with a copy of the new master nib file and then migrates changes from the older translated nib file based on a fixed set of rules. Using the English and French nib files from Figure 10-1 (page 156) to provide context, these rules are as follows: 1. The ibtool program copies version 2.0 of the English nib file and uses that as the starting point for the new version 2.0 French nib file. The ibtool program compares the objects in versions 1.0 and 2.0 of the English nib files.
2.
156
CHAPTER 10
Localization
If the properties of an object are the same in both versions of the English nib file, ibtool copies the corresponding object from version 1.0 of the French nib file into version 2.0 of the French nib file (replacing the English version of that object). The assumption here is that if nothing changed between the English versions, the object from the older French nib file can be used as is. If version 2.0 contains an object that is not present in version 1.0, ibtool does nothing. (This means that the version 2.0 of the French nib file contains the new object but with English content.) If version 1.0 contains an object that is not present in version 2.0, ibtool does nothing. (The object was removed, so it does not need to be merged into the new nib file.)
3.
If a strings file was specified, ibtool merges the strings into version 2.0 of the French nib file.
When the merge is complete, what you receive is a new nib file that contains all of your new views and controls but also contains as much translated content as possible. Any new objects you added to your interface must still be translated, assuming you did not provide translations in a strings file during the merge, but at least the number of objects requiring translation is reduced. Warning: Because ibtool operates only on the objects found in your master nib files, you should limit the changes you make to localized nib files to changes in strings and geometry only. You should never add objects to, or remove objects from, your localized nib files. You should also not change the type of an object. Such changes are lost when performing an incremental update.
157
CHAPTER 10
Localization
158
CHAPTER 11
Interface Builder supports a number of customizations to its workflow environment that are designed to make working with the tool easier. Most of these changes are designed to help you find the information you need quickly. This chapter covers some of the more prevalent techniques designed to make working with the library easier. It also covers the basic Interface Builder preferences and explains how you can integrate your custom objects into the Library window.
Select a subset of library groups. Use the filter control at the bottom of the Library window.
In the groups pane of the Library window, the Library group contains all of the objects currently integrated into Interface Builder. The contents of the Library group are further subdivided based on the currently loaded plug-ins. Each plug-in can provide further groupings for the controls it defines. Selecting one or more of these subgroups limits the items displayed in the items pane to those in the selected groups. Figure 11-1 shows the window with two groups selected and the resulting list of items that are displayed.
159
CHAPTER 11
Figure 11-1
To select a group, simply click it. To add groups to the current selection, hold down the Command key and click on each group. To select a range of groups, hold down the Shift key when clicking. You can also filter the list of displayed objects using the filter control at the bottom of the Library window. The filter control always operates on the entire library and cannot be combined with other filtering options. Typing the name of an object or a textual description of it restricts the current list of items to those that match the specified string. For example, typing the word Font in the default library displays two items, as shown in Figure 11-2.
160
CHAPTER 11
Figure 11-2
161
CHAPTER 11
Figure 11-3
Note: Although you can drag objects between custom groups, doing so moves the object from one group to the other. To keep the item in both groups, hold the Option key while dragging or drag the item from the Library group.
162
CHAPTER 11
Figure 11-4
You can build smart groups to accommodate a variety of conditions. For example, you can build groups that filter based on the objects description or type, or you can build a smart group that displays the objects you used most recently. Table 11-1 lists the types of rules you can configure in the rule editor and describes how Interface Builder matches objects using those rules. Table 11-1 Search type Label Rule editor search criteria Description Example
Matches the specified string against the label Searching the string Font yields the Font of the object. You can specify whether the Menu item and the Show Fonts Toolbar label should start with, end with, or contain item . the specified string. Matches objects that were dragged from the Specifying a setting of 1 day yields the Library window within the specified time objects dragged from the library within the period. You can use this criteria to show most recent 24-hour period of time. frequently used items.
Used Within
163
CHAPTER 11
Description
Example
Matches the specified string against the label Specifying the string NSP matches objects or class name of the object. The object must with types such as NSPopUpButton, simply contain the string to match. NSProgressIndicator, and NSPredicateEditor. Matches the specified string against generic Specifying the string toolbar with the keywords indicating the type of an object. Contains Something Like operator matches You might use this criteria in combination toolbar and toolbar item objects. with others to limit filters to a particular type of object. Matches objects against the specified class name. Specify "NSControl to match only those objects that are descendants of the NSControl class. You must specify whole class names and not just part of a class name.
Categories
Is a Kind Of
Press the Delete key. Choose Remove Group from the action menu.
164
CHAPTER 11
3. 4.
In the organization pane of the Library window, drop the object on the Custom Objects group or on a custom group you created. Interface Builder prompts you for information about the dropped object. Fill in the information about your object and press OK.
You can use this technique to drag one object or a group of objects. When dragging more than one object, the entire group becomes a single item in the Library window. Dragging that item back out of the library creates all of the original objects. The items you add to the library persist between Interface Builder sessions so that you can use them over and over again. To remove a custom item from the Library window, do the following: 1. 2. 3. Select the Custom Objects group in the library to see the items in that group. Select your custom item. Press the Delete key.
You must remove custom items from the Custom Objects group in order to remove them from the Library window. Removing items from your custom group folders removes them from the group but not the library. In addition to adding custom configurations of objects to the library, you can also add entirely new objects to the library through an Interface Builder plug-in. Plug-ins are typically used in situations where you want to be able to configure and edit the attributes of your custom classes. For more information, see Using Plug-ins to Integrate New Objects into the Library (page 167).
165
CHAPTER 11
Figure 11-5
To return to the full organization pane, drag the split bar back down until the pane appears.
Preference pane Description General Plug-ins Contains preferences for document handling. Displays the list of plug-ins currently loaded into the Interface Builder application. You can also use this pane to install or remove plug-ins containing custom controls. Displays preferences for deciding what constitutes errors, warnings, and noteworthy events in a nib file.
Alerts
166
CHAPTER 11
Preference pane Description Simulator Displays preferences for managing the simulator user defaults cache. Objects can use the simulator user defaults as a source of initial data. For example, the user defaults controller object takes information from the user defaults database.
Note: If your Xcode project includes a framework that contains an Interface Builder plug-in, Interface Builder loads the plug-in automatically when you open a nib file from that project. You do not need to load it manually using the preferences window.
64-Bit Plug-Ins
Interface Builder 3.2 or later is a 64-bit application. Consequently, you should modify your plug-in to use 64-bit addressing. For general information about conversion to 64-bit addressing, see 64-Bit Transition Guide. Both Interface Builder and ibtool can auto-relaunch in 32-bit mode to load 32-bit plug-ins.
167
CHAPTER 11
168
APPENDIX A
3. 4.
169
APPENDIX A
Modifier Keys
Modifier key Description Command When you hold down this key, single-clicking an object toggles its selected state. You can use this modifier key to add objects to the current selection one at a time. You can also toggle the resize behavior for windows by holding down this key; see Design-Time Resizing Modes for Windows (page 95). After selecting an object, pressing this key and moving the mouse over a different object displays alignment information for that object relative to the selected object. Pressing the Option key during drag-and-drop operations copies the selected objects instead of moving them. When pressed, single-clicking an object adds that object to the current selection. Pressing this key while resizing an object maintains the objects aspect ratio. When held down, clicking a Cocoa object displays its connections panel. Holding down the Control key is equivalent to right-clicking the object and the two behaviors have the same end result.
Option
Shift
Control
Inspector Gestures
Action Display inspector window Display attributes inspector Display effects inspector Display size inspector Display bindings inspector Gesture Shift-Command-I Command-1 Command-2 Command-3 Command-4
Library Gestures
Action Display Library window Gesture Command-Shift-L
170
Modifier Keys
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
APPENDIX A
Workspace Gestures
Action Location Move selection by 1 pixel Move selection by 5 pixels Size Resize selection to fit Guides Display position guides Display layout rectangles Add horizontal guide Add vertical guide Navigation Reveal selection in document window Reveal selection in Library window Command-Option-Up Arrow Command-Option-Right Arrow Option (with selection) Command-L Command-Shift-_ Command-Shift-| Command-= Arrow (Left, Up, Right, Down) Shift-Arrow Gesture
Display in a popup menu all of the objects currently under the mouse Shift-Control-Click
Workspace Gestures
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
171
APPENDIX A
172
Glossary
action A connection that involves the sending of a message from one object to another when a certain user action occurs. For example, when a user presses a button, the button object calls the action method of its target object to notify that object that the action occurred. autosizing behavior A mechanism that automatically adjusts the size and position of views during resize operations based on a set of options. See also spring and strut. automatic guide An alignment tool that shows the spacing required to meet the appropriate interface guidelines for the target platform. This type of guide appears and disappears automatically. binding A two-way connection between the objects of your data model and the views of your interface. Cocoa bindings provide automatic synchronization between your data objects and the views displaying information about those objects. connections panel A panel that appears as needed to display the connection status of outlets and actions. content view In iOS applications, the portion of an iOS window that displays the applications custom content. Each content view may be represented by one or more actual views and typically presents a single screens worth of application content. In Mac OS X applications, it is the view object that acts as the root for all other views in the window. controller object An object that manages the interactions between an applications data objects and the objects that display that data. Core Data A technology for managing structured data in your application. The data model of a Core Data application is built on a schema that defines one or more entities and their properties and the
relationships between those entities. At runtime, Core Data manages the data for those entities using a database or other structured form of data store. custom guide An alignment tool that is placed by the user in order to align objects to an arbitrary location on the design surface. design surface The content area of a window object. This area is where you drop views and other visual objects and is also where you manipulate those objects directly. dynamic guide An alignment tool that provides information about the position of a view relative to other objects on the design surface. Dynamic guides appear only when the Option key is held down. event A type of connection that is specific to iOS applications. Events represent different phases of user interaction for a control. Each event connection can also have multiple assigned target objects, each with its own distinct action message. Files Owner The runtime object that manages the contents of a nib file. The Files Owner is typically a controller object that maintains pointers to key objects in a nib file and responds to user interactions with those objects. First Responder The object given the first opportunity to respond to events. The First Responder object is determined dynamically at runtime based on the several conditions, including which view is selected or has focus and which view is willing to accept certain types of events. If the First Responder does not handle an event, it passes the event to other objects in the responder chain.
173
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
GLOSSARY
interface object An object in a nib file that is created for your application at load time. Interface objects can consist of both visual objects (such as windows, views, and menus) and non-visual objects (such as controllers). nib document The runtime representation of a nib file. Nib documents are the primary document type of the Interface Builder application. The on-disk representation of a nib document is a nib file. nib file An on-disk collection of resource data. Nib files contain binary data representing one or more resources that you want to load into your application at runtime. outlet A pointer to another object that can be set in Interface Builder. Applications use outlets to store references to objects in nib files. placeholder object A placeholder for an object that is specified at runtime. Placeholder objects act as stand-ins for objects that are not available at design time. Instead, such objects are created by a running application and connected to the objects in a nib file when that nib file is loaded. Cocoa nib files use placeholder objects to represent the owner of a nib files contents, the application object itself, and the first object to respond to events. resource A generic term for structured data that is used at runtime to simplify the creation of some complex feature. Nib files store window resources, view resources, menu resources, and all the relationships between those objects and other objects in your application. When a nib file is loaded, its resources are turned into actual objects that can be used exactly as if theyd been created programmatically. Responder chain The set of objects responsible for handling events in a window. spring An element in the Size pane of the inspector window that controls the autosizing behavior of a view or control. When a spring is present, the width or height of your view grows and shrinks proportionally to its parent view. When no spring is present, the width or height of your view remains fixed.
strut An element in the Size pane of the inspector window that controls the autosizing behavior of a view or control. When a strut is present, the distance between the edge of a view to its parent view remains fixed. When absent, the distance grows and shrinks as the size of the views change. xib file An XMLbased version of a nib file. Xib files are the preferred format to use during development of your application. At build-time, they are compiled into nib files so that they can be deployed in your application bundle.
174
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
REVISION HISTORY
This table describes the changes to Interface Builder User Guide. Date 2010-07-12 2010-03-25 Notes Updated iOS terminology. Added information about the IBOutletCollection keyword and about making multiple connections in Interface Builder. Added information about iPad support. Made minor editorial corrections. Added information about user-defined runtime attributes. Replaced the term proxy object with placeholder object. 2009-08-28 Updated with new information about Interface Builder features. Added the chapter Interface Builder Quick Start (page 17) for new users. Described the new feature Classes (page 37) in the Library window. Added the appendix Interface Builder Gesture Guide (page 169). 2008-06-26 2007-10-31 Updated to incorporate information about nib files in iOS. New document that describes how to use the Interface Builder application.
175
2010-07-12 | 2010 Apple Inc. All Rights Reserved.
REVISION HISTORY
176
2010-07-12 | 2010 Apple Inc. All Rights Reserved.