Cocoa Programming for Mac OS X - Aaron Hillegass [82]
#pragma mark Events
- (void)mouseDown:(NSEvent *)event
{
NSLog(@"mouseDown: %ld", [event clickCount]);
}
- (void)mouseDragged:(NSEvent *)event
{
NSPoint p = [event locationInWindow];
NSLog(@"mouseDragged:%@", NSStringFromPoint(p));
}
- (void)mouseUp:(NSEvent *)event
{
NSLog(@"mouseUp:");
}
Build and run your application. Try double-clicking, and check the click count. Note that the first click is sent and then the second click. The first click has a click count of 1; the second click has a click count of 2.
Note the use of #pragma mark. The jump bar at the top of any Xcode editing window enables you to jump to any of the declarations and definitions in the file; #pragma mark puts a label into that pop-up. Stylish programmers (like you, dear reader) use it to group their methods.
Using NSOpenPanel
It would be fun to composite an image onto the view, but first you need to create a controller object that will read the image data from a file. This is a good opportunity to learn how to use NSOpenPanel. Note that the RaiseMan application used NSOpenPanel, but it was done automatically by the NSDocument class. Here you will use NSOpenPanel explicitly. Figure 18.1 shows what your application will look like once the user has chosen an image. The slider at the bottom of the window will control how opaque the image is.
Figure 18.1. Completed Application
Figure 18.2 shows the object diagram.
Figure 18.2. Object Diagram
Change the XIB File
Open the DrawingFun project from Chapter 17. In DrawingFunAppDelegate.h, add an outlet for the StretchView and an action that will start the Open panel:
#import @class StretchView; @interface DrawingFunAppDelegate : NSObject IBOutlet StretchView *stretchView; } @property (strong) IBOutlet NSWindow *window; - (IBAction)showOpenPanel:(id)sender; @end Open MainMenu.xib and bring up our drawing window. Drop a slider onto the window. In the Inspector, set its range from 0 to 1. Also, check the box labeled Continuous. This slider will control how opaque the image is (Figure 18.3). Figure 18.3. Inspect the Slider Switch to the Size Inspector and configure the slider to stretch horizontally and maintain the left, right, and bottom margins (Figure 18.4). This will make the slider resize appropriately with the window. Figure 18.4. Configure the Slider’s Autoresizing Bind the value of the slider to the app delegate’s stretchView.opacity key path. Figure 18.5. Bind the Slider’s Value Control-click on the DrawingFunAppDelegate. Connect the stretchView outlet to the StretchView on the window (Figure 18.6). Figure 18.6. Connect the stretchView Outlet Look at the main menu in your XIB. Open the File menu and delete all menu items except Open. Control-drag to connect the menu item to the DrawingFunAppDelegate’s showOpenPanel: action (Figure 18.7). Save the file. Figure 18.7. Connect the Menu Item Edit the Code #import "DrawingFunAppDelegate.h" #import "StretchView.h" @implementation DrawingFunAppDelegate @synthesize window; - (IBAction)showOpenPanel:(id)sender { __block NSOpenPanel *panel = [NSOpenPanel openPanel]; [panel setAllowedFileTypes:[NSImage imageFileTypes]]; [panel beginSheetModalForWindow:[stretchView window] completionHandler:^ (NSInteger result) { if (result == NSOKButton) { NSImage *image = [[NSImage alloc] initWithContentsOfURL:[panel URL]]; [stretchView setImage:image]; } panel = nil; // prevent strong ref cycle }]; } @end The line where you start the sheet is a very handy method: - (void)beginSheetModalForWindow:(NSWindow *)window completionHandler:(void
Edit DrawingFunAppDelegate.m to read as follows. Note that there’s some new syntax, called a block, in this method. We’ll discuss blocks in detail in Chapter 29. Note that you may see a warning that StretchView may not respond to setImage:; this is fine for now. We will fix it in the next section.