Upstream version 9.38.198.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / ui / cocoa / dev_tools_controller.mm
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #import "chrome/browser/ui/cocoa/dev_tools_controller.h"
6
7 #include <algorithm>
8 #include <cmath>
9
10 #include <Cocoa/Cocoa.h>
11
12 #include "base/prefs/pref_service.h"
13 #include "chrome/browser/browser_process.h"
14 #include "chrome/browser/profiles/profile.h"
15 #import "chrome/browser/ui/cocoa/view_id_util.h"
16 #include "chrome/common/pref_names.h"
17 #include "content/public/browser/web_contents.h"
18 #include "ui/base/cocoa/base_view.h"
19 #include "ui/base/cocoa/focus_tracker.h"
20 #include "ui/gfx/mac/scoped_ns_disable_screen_updates.h"
21 #include "ui/gfx/size_conversions.h"
22
23 using content::WebContents;
24
25 @interface DevToolsContainerView : BaseView {
26   DevToolsContentsResizingStrategy strategy_;
27
28   // Weak references. Ownership via -subviews.
29   NSView* devToolsView_;
30   NSView* contentsView_;
31 }
32
33 - (void)setDevToolsView:(NSView*)devToolsView
34            withStrategy:(const DevToolsContentsResizingStrategy&)strategy;
35 - (void)adjustSubviews;
36 - (BOOL)hasDevToolsView;
37
38 @end
39
40
41 @implementation DevToolsContainerView
42
43 - (void)setDevToolsView:(NSView*)devToolsView
44            withStrategy:(const DevToolsContentsResizingStrategy&)strategy {
45   strategy_.CopyFrom(strategy);
46   if (devToolsView == devToolsView_) {
47     if (contentsView_)
48       [contentsView_ setHidden:strategy.hide_inspected_contents()];
49     return;
50   }
51
52   if (devToolsView_) {
53     DCHECK_EQ(2u, [[self subviews] count]);
54     [devToolsView_ removeFromSuperview];
55     [contentsView_ setHidden:NO];
56     contentsView_ = nil;
57     devToolsView_ = nil;
58   }
59
60   if (devToolsView) {
61     NSArray* subviews = [self subviews];
62     DCHECK_EQ(1u, [subviews count]);
63     contentsView_ = [subviews objectAtIndex:0];
64     devToolsView_ = devToolsView;
65     // Place DevTools under contents.
66     [self addSubview:devToolsView positioned:NSWindowBelow relativeTo:nil];
67
68     [contentsView_ setHidden:strategy.hide_inspected_contents()];
69   }
70 }
71
72 - (void)resizeSubviewsWithOldSize:(NSSize)oldBoundsSize {
73   [self adjustSubviews];
74 }
75
76 - (BOOL)hasDevToolsView {
77   return devToolsView_ != nil;
78 }
79
80 - (void)adjustSubviews {
81   if (![[self subviews] count])
82     return;
83
84   if (!devToolsView_) {
85     DCHECK_EQ(1u, [[self subviews] count]);
86     NSView* contents = [[self subviews] objectAtIndex:0];
87     [contents setFrame:[self bounds]];
88     return;
89   }
90
91   DCHECK_EQ(2u, [[self subviews] count]);
92
93   gfx::Rect new_devtools_bounds;
94   gfx::Rect new_contents_bounds;
95   ApplyDevToolsContentsResizingStrategy(
96       strategy_, gfx::Size(NSSizeToCGSize([self bounds].size)),
97       &new_devtools_bounds, &new_contents_bounds);
98   [devToolsView_ setFrame:[self flipRectToNSRect:new_devtools_bounds]];
99   [contentsView_ setFrame:[self flipRectToNSRect:new_contents_bounds]];
100 }
101
102 @end
103
104
105 @implementation DevToolsController
106
107 - (id)init {
108   if ((self = [super init])) {
109     devToolsContainerView_.reset(
110         [[DevToolsContainerView alloc] initWithFrame:NSZeroRect]);
111     [devToolsContainerView_
112         setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable];
113   }
114   return self;
115 }
116
117 - (NSView*)view {
118   return devToolsContainerView_.get();
119 }
120
121 - (void)updateDevToolsForWebContents:(WebContents*)contents
122                          withProfile:(Profile*)profile {
123   DevToolsContentsResizingStrategy strategy;
124   WebContents* devTools = DevToolsWindow::GetInTabWebContents(
125       contents, &strategy);
126
127   // Make sure we do not draw any transient arrangements of views.
128   gfx::ScopedNSDisableScreenUpdates disabler;
129
130   if (devTools && ![devToolsContainerView_ hasDevToolsView]) {
131     focusTracker_.reset(
132         [[FocusTracker alloc] initWithWindow:[devToolsContainerView_ window]]);
133   }
134
135   if (!devTools && [devToolsContainerView_ hasDevToolsView]) {
136     [focusTracker_ restoreFocusInWindow:[devToolsContainerView_ window]];
137     focusTracker_.reset();
138   }
139
140   NSView* devToolsView = nil;
141   if (devTools) {
142     devToolsView = devTools->GetNativeView();
143     // |devToolsView| is a WebContentsViewCocoa object, whose ViewID was
144     // set to VIEW_ID_TAB_CONTAINER initially, so we need to change it to
145     // VIEW_ID_DEV_TOOLS_DOCKED here.
146     view_id_util::SetID(devToolsView, VIEW_ID_DEV_TOOLS_DOCKED);
147
148     devTools->SetAllowOtherViews(true);
149     contents->SetAllowOtherViews(true);
150   } else {
151     contents->SetAllowOtherViews(false);
152   }
153
154   [devToolsContainerView_ setDevToolsView:devToolsView withStrategy:strategy];
155   [devToolsContainerView_ adjustSubviews];
156 }
157
158 @end