OLD | NEW |
---|---|
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "remoting/host/continue_window.h" | 5 #include "remoting/host/continue_window.h" |
6 | 6 |
7 #import <Cocoa/Cocoa.h> | 7 #import <Cocoa/Cocoa.h> |
8 | 8 |
9 #include "base/compiler_specific.h" | 9 #include "base/compiler_specific.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
11 #include "base/mac/scoped_nsautorelease_pool.h" | 11 #include "base/mac/scoped_nsautorelease_pool.h" |
12 #include "base/memory/scoped_nsobject.h" | 12 #include "base/memory/scoped_nsobject.h" |
13 #include "base/sys_string_conversions.h" | 13 #include "base/sys_string_conversions.h" |
14 #include "remoting/host/chromoting_host.h" | 14 #include "remoting/host/chromoting_host.h" |
15 | 15 |
16 // As this is a plugin, there needs to be a way to find its bundle | 16 // Handles the ContinueWindow. |
17 // so that resources are able to be found. This class exists solely so that | 17 @interface ContinueWindowMacController : NSObject { |
18 // there is a way to get the bundle that this code file is in using | 18 @private |
19 // [NSBundle bundleForClass:[ContinueWindowMacClassToLocateMyBundle class]] | 19 scoped_nsobject<NSMutableArray> shades_; |
20 // It is really only a name. | 20 scoped_nsobject<NSAlert> continue_alert_; |
21 @interface ContinueWindowMacClassToLocateMyBundle : NSObject | 21 remoting::ChromotingHost* host_; |
22 @end | 22 } |
23 | 23 |
24 @implementation ContinueWindowMacClassToLocateMyBundle | 24 - (id)initWithHost:(remoting::ChromotingHost*)host; |
25 - (void)show; | |
26 - (void)hide; | |
27 - (void)onCancel:(id)sender; | |
28 - (void)onContinue:(id)sender; | |
25 @end | 29 @end |
26 | 30 |
27 namespace remoting { | 31 namespace remoting { |
28 | 32 |
33 // A bridge between C++ and ObjC implementations of ContinueWindow. | |
34 // Everything important occurs in ContinueWindowMacController. | |
29 class ContinueWindowMac : public remoting::ContinueWindow { | 35 class ContinueWindowMac : public remoting::ContinueWindow { |
30 public: | 36 public: |
31 ContinueWindowMac() : modal_session_(NULL) {} | 37 ContinueWindowMac() {} |
32 virtual ~ContinueWindowMac() {} | 38 virtual ~ContinueWindowMac() {} |
33 | 39 |
34 virtual void Show(remoting::ChromotingHost* host) OVERRIDE; | 40 virtual void Show(remoting::ChromotingHost* host) OVERRIDE; |
35 virtual void Hide() OVERRIDE; | 41 virtual void Hide() OVERRIDE; |
36 | 42 |
37 private: | 43 private: |
38 NSModalSession modal_session_; | 44 scoped_nsobject<ContinueWindowMacController> controller_; |
39 | 45 |
40 DISALLOW_COPY_AND_ASSIGN(ContinueWindowMac); | 46 DISALLOW_COPY_AND_ASSIGN(ContinueWindowMac); |
41 }; | 47 }; |
42 | 48 |
43 void ContinueWindowMac::Show(remoting::ChromotingHost* host) { | 49 void ContinueWindowMac::Show(remoting::ChromotingHost* host) { |
44 base::mac::ScopedNSAutoreleasePool pool; | 50 base::mac::ScopedNSAutoreleasePool pool; |
51 controller_.reset([[ContinueWindowMacController alloc] initWithHost:host]); | |
52 [controller_ show]; | |
45 | 53 |
54 } | |
55 | |
56 void ContinueWindowMac::Hide() { | |
57 base::mac::ScopedNSAutoreleasePool pool; | |
58 [controller_ hide]; | |
59 } | |
60 | |
61 ContinueWindow* ContinueWindow::Create() { | |
62 return new ContinueWindowMac(); | |
63 } | |
64 | |
65 } // namespace remoting | |
66 | |
67 @implementation ContinueWindowMacController | |
68 | |
69 - (id)initWithHost:(remoting::ChromotingHost*)host { | |
70 if ((self = [super init])) { | |
71 host_ = host; | |
72 } | |
73 return self; | |
74 } | |
75 | |
76 - (void)show { | |
46 // Generate window shade | 77 // Generate window shade |
47 NSArray* screens = [NSScreen screens]; | 78 NSArray* screens = [NSScreen screens]; |
48 NSMutableArray* windows = [NSMutableArray arrayWithCapacity:[screens count]]; | 79 shades_.reset([[NSMutableArray alloc] initWithCapacity:[screens count]]); |
49 for (NSScreen *screen in screens) { | 80 for (NSScreen *screen in screens) { |
50 NSWindow* window = | 81 NSWindow* window = |
Jamie
2011/11/01 20:56:20
Should this be renamed |shade| for consistency?
| |
51 [[[NSWindow alloc] initWithContentRect:[screen frame] | 82 [[[NSWindow alloc] initWithContentRect:[screen frame] |
52 styleMask:NSBorderlessWindowMask | 83 styleMask:NSBorderlessWindowMask |
53 backing:NSBackingStoreBuffered | 84 backing:NSBackingStoreBuffered |
54 defer:NO | 85 defer:NO |
55 screen:screen] autorelease]; | 86 screen:screen] autorelease]; |
56 [window setReleasedWhenClosed:NO]; | 87 [window setReleasedWhenClosed:NO]; |
57 [window setAlphaValue:0.8]; | 88 [window setAlphaValue:0.8]; |
58 [window setOpaque:NO]; | 89 [window setOpaque:NO]; |
59 [window setBackgroundColor:[NSColor blackColor]]; | 90 [window setBackgroundColor:[NSColor blackColor]]; |
60 // Raise the window shade above just about everything else. | 91 // Raise the window shade above just about everything else. |
61 // Leave the dock and menu bar exposed so the user has some basic level | 92 // Leave the dock and menu bar exposed so the user has some basic level |
62 // of control (like they can quit Chromium). | 93 // of control (like they can quit Chromium). |
63 [window setLevel:NSModalPanelWindowLevel - 1]; | 94 [window setLevel:NSModalPanelWindowLevel - 1]; |
64 [window orderFront:nil]; | 95 [window orderFront:nil]; |
65 [windows addObject:window]; | 96 [shades_ addObject:window]; |
66 } | 97 } |
67 | 98 |
68 // Put up alert | 99 // Create alert. |
69 const UiStrings& strings = host->ui_strings(); | 100 const remoting::UiStrings& strings = host_->ui_strings(); |
70 NSString* message = base::SysUTF16ToNSString(strings.continue_prompt); | 101 NSString* message = base::SysUTF16ToNSString(strings.continue_prompt); |
71 NSString* continue_button = base::SysUTF16ToNSString( | 102 NSString* continue_button_string = base::SysUTF16ToNSString( |
72 strings.continue_button_text); | 103 strings.continue_button_text); |
73 NSString* cancel_button = base::SysUTF16ToNSString( | 104 NSString* cancel_button_string = base::SysUTF16ToNSString( |
74 strings.stop_sharing_button_text); | 105 strings.stop_sharing_button_text); |
75 scoped_nsobject<NSAlert> continue_alert([[NSAlert alloc] init]); | 106 continue_alert_.reset([[NSAlert alloc] init]); |
76 [continue_alert setMessageText:message]; | 107 [continue_alert_ setMessageText:message]; |
77 [continue_alert addButtonWithTitle:continue_button]; | |
78 [continue_alert addButtonWithTitle:cancel_button]; | |
79 | 108 |
80 // See ContinueWindowMacClassToLocateMyBundle class above for details | 109 NSButton* continue_button = |
81 // on this. | 110 [continue_alert_ addButtonWithTitle:continue_button_string]; |
82 NSBundle *bundle = | 111 [continue_button setAction:@selector(onContinue:)]; |
83 [NSBundle bundleForClass:[ContinueWindowMacClassToLocateMyBundle class]]; | 112 [continue_button setTarget:self]; |
113 | |
114 NSButton* cancel_button = | |
115 [continue_alert_ addButtonWithTitle:cancel_button_string]; | |
116 [cancel_button setAction:@selector(onCancel:)]; | |
117 [cancel_button setTarget:self]; | |
118 | |
119 NSBundle *bundle = [NSBundle bundleForClass:[self class]]; | |
84 NSString *imagePath = [bundle pathForResource:@"chromoting128" ofType:@"png"]; | 120 NSString *imagePath = [bundle pathForResource:@"chromoting128" ofType:@"png"]; |
85 scoped_nsobject<NSImage> image( | 121 scoped_nsobject<NSImage> image( |
86 [[NSImage alloc] initByReferencingFile:imagePath]); | 122 [[NSImage alloc] initByReferencingFile:imagePath]); |
87 [continue_alert setIcon:image]; | 123 [continue_alert_ setIcon:image]; |
88 [continue_alert layout]; | 124 [continue_alert_ layout]; |
89 | 125 |
90 NSWindow* continue_window = [continue_alert window]; | 126 // Force alert to be at the proper level and location. |
127 NSWindow* continue_window = [continue_alert_ window]; | |
91 [continue_window center]; | 128 [continue_window center]; |
129 [continue_window setLevel:NSModalPanelWindowLevel]; | |
92 [continue_window orderWindow:NSWindowAbove | 130 [continue_window orderWindow:NSWindowAbove |
93 relativeTo:[[windows lastObject] windowNumber]]; | 131 relativeTo:[[shades_ lastObject] windowNumber]]; |
94 [continue_window makeKeyWindow]; | 132 [continue_window makeKeyWindow]; |
95 NSApplication* application = [NSApplication sharedApplication]; | 133 } |
96 modal_session_ = [application beginModalSessionForWindow:continue_window]; | |
97 NSInteger answer = 0; | |
98 do { | |
99 answer = [application runModalSession:modal_session_]; | |
100 } while (answer == NSRunContinuesResponse); | |
101 [application endModalSession:modal_session_]; | |
102 modal_session_ = NULL; | |
103 | 134 |
104 [continue_window close]; | 135 - (void)hide { |
105 | |
106 // Remove window shade. | 136 // Remove window shade. |
107 for (NSWindow* window in windows) { | 137 for (NSWindow* window in shades_.get()) { |
108 [window close]; | 138 [window close]; |
109 } | 139 } |
110 | 140 shades_.reset(); |
111 if (answer == NSAlertFirstButtonReturn) { | 141 continue_alert_.reset(); |
112 host->PauseSession(false); | |
113 } else { | |
114 host->Shutdown(NULL); | |
115 } | |
116 } | 142 } |
117 | 143 |
118 void ContinueWindowMac::Hide() { | 144 - (void)onCancel:(id)sender { |
119 if (modal_session_) { | 145 [self hide]; |
120 NSApplication* application = [NSApplication sharedApplication]; | 146 host_->Shutdown(NULL); |
121 [application stopModalWithCode:NSAlertFirstButtonReturn]; | 147 host_ = nil; |
122 } | |
123 } | 148 } |
124 | 149 |
125 ContinueWindow* ContinueWindow::Create() { | 150 - (void)onContinue:(id)sender { |
126 return new ContinueWindowMac(); | 151 [self hide]; |
152 host_->PauseSession(false); | |
153 host_ = nil; | |
127 } | 154 } |
128 | 155 |
129 } // namespace remoting | 156 @end |
OLD | NEW |