Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(156)

Side by Side Diff: chrome/browser/ui/views/sidebar/sidebar_tab_strip.cc

Issue 6250141: Sidebar mini tabs UI (views version).... Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: '' Created 9 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
Property Changes:
Added: svn:eol-style
+ LF
OLDNEW
(Empty)
1 // Copyright (c) 2010 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 #include "chrome/browser/ui/views/sidebar/sidebar_tab_strip.h"
6
7 #include "base/compiler_specific.h"
8 #include "base/stl_util-inl.h"
9 #include "chrome/browser/defaults.h"
10 #include "chrome/browser/themes/browser_theme_provider.h"
11 #include "chrome/browser/ui/browser.h"
12 #include "chrome/browser/ui/view_ids.h"
13 #include "chrome/browser/ui/views/sidebar/sidebar_tab.h"
14 #include "chrome/browser/ui/views/sidebar/sidebar_tab_strip_controller.h"
15 #include "chrome/common/pref_names.h"
16 #include "gfx/canvas_skia.h"
17 #include "gfx/path.h"
18 #include "gfx/point.h"
19 #include "gfx/rect.h"
20 #include "gfx/size.h"
21 #include "grit/generated_resources.h"
22 #include "grit/theme_resources.h"
23 #include "ui/base/l10n/l10n_util.h"
24 #include "ui/base/resource/resource_bundle.h"
25 #include "views/controls/image_view.h"
26 #include "views/widget/default_theme_provider.h"
27 #include "views/window/non_client_view.h"
28 #include "views/window/window.h"
29
30 #undef min
31 #undef max
32
33 namespace {
34 const int kTabOffset = -1;
35 const int kFisrtTabInitalHeight = 6;
36 } // namespace
37
38 // SidebarTabStrip, public:
39
40 SidebarTabStrip::SidebarTabStrip(SidebarTabStripController* controller)
41 : SidebarBaseTabStrip(controller),
42 animation_container_(new ui::AnimationContainer()) {
43 }
44
45 SidebarTabStrip::~SidebarTabStrip() {
46 // The animations may reference the tabs. Shut down the animation before we
47 // delete the tabs.
48 StopAnimating();
49
50 // The children (tabs) may callback to us from their destructor. Delete them
51 // so that if they call back we aren't in a weird state.
52 RemoveAllChildViews(true);
53 }
54
55 // SidebarTabStrip, views::View overrides:
56
57 void SidebarTabStrip::Layout() {
58 UpdateViewBounds();
59
60 SchedulePaint();
61 }
62
63 views::View* SidebarTabStrip::GetViewForPoint(const gfx::Point& point) {
64 // Return any view that isn't a SidebarTab or this SidebarTabStrip
65 // immediately. We don't want to interfere.
66 views::View* v = View::GetViewForPoint(point);
67 if (v && v != this && v->GetClassName() != SidebarTab::kViewClassName)
68 return v;
69
70 // The display order doesn't necessarily match the child list order, so we
71 // walk the display list hit-testing Tabs. Since the selected tab always
72 // renders on top of adjacent tabs, it needs to be hit-tested before any
73 // left-adjacent SidebarTab, so we look ahead for it as we walk.
74 for (int i = 0; i < tab_count(); ++i) {
75 SidebarBaseTab* next_tab =
76 i < (tab_count() - 1) ? base_tab_at_tab_index(i + 1) : NULL;
77 if (next_tab && next_tab->IsSelected() && IsPointInTab(next_tab, point))
78 return next_tab;
79 SidebarBaseTab* tab = base_tab_at_tab_index(i);
80 if (IsPointInTab(tab, point))
81 return tab;
82 }
83
84 // No need to do any floating view stuff, we don't use them
85 // in the SidebarTabStrip.
86 return this;
87 }
88
89 // Overridden to support automation. See automation_proxy_uitest.cc.
90 views::View* SidebarTabStrip::GetViewByID(int view_id) const {
91 if (tab_count() > 0) {
92 if (view_id == VIEW_ID_TAB_LAST)
93 return base_tab_at_tab_index(tab_count() - 1);
94 if ((view_id >= VIEW_ID_TAB_0) && (view_id < VIEW_ID_TAB_LAST)) {
95 int index = view_id - VIEW_ID_TAB_0;
96 if (index >= 0 && index < tab_count())
97 return base_tab_at_tab_index(index);
98 return NULL;
99 }
100 }
101
102 return View::GetViewByID(view_id);
103 }
104
105 AccessibilityTypes::Role SidebarTabStrip::GetAccessibleRole() {
106 return AccessibilityTypes::ROLE_PAGETABLIST;
107 }
108
109 void SidebarTabStrip::PaintChildren(gfx::Canvas* canvas) {
110 // Painting closing tabs first, so they appear behind the regular ones.
111 for (int i = tab_count() - 1; i >= 0; --i) {
112 SidebarBaseTab* tab = base_tab_at_tab_index(i);
113 // We must ask the _Tab's_ model, not ourselves, because in some situations
114 // the model will be different to this object, e.g. when a SidebarTab
115 // is being removed after its TabContents has been destroyed.
116 if (tab->closing())
117 tab->ProcessPaint(canvas);
118 }
119
120 // Tabs are painted in reverse order, so they stack to the bottom.
121 SidebarBaseTab* selected_tab = NULL;
122
123 // Paint all non-closing tabs, except the selected one.
124 for (int i = tab_count() - 1; i >= 0; --i) {
125 SidebarBaseTab* tab = base_tab_at_tab_index(i);
126 if (!tab->closing()) {
127 if (!tab->IsSelected())
128 tab->ProcessPaint(canvas);
129 else
130 selected_tab = tab;
131 }
132 }
133
134 // Paint the selected tab last, so it overlaps all the others.
135 if (selected_tab)
136 selected_tab->ProcessPaint(canvas);
137 }
138
139 // SidebarBaseTabStrip overrides:
140
141 SidebarBaseTab* SidebarTabStrip::CreateTab() {
142 SidebarTab* tab = new SidebarTab(this);
143 tab->set_animation_container(animation_container_.get());
144 return tab;
145 }
146
147 void SidebarTabStrip::StartInsertTabAnimation(int model_index) {
148 // The only tab should not be animated, it looks wierd.
149 DCHECK_GT(tab_count(), 1);
150
151 GenerateIdealBounds();
152
153 // Override inserted tab bounds to achieve a desired animation effect.
154 int tab_data_index = ModelIndexToTabIndex(model_index);
155 SidebarBaseTab* tab = base_tab_at_tab_index(tab_data_index);
156 if (tab_data_index == 0) {
157 // First tab is animated from its own ideal bounds().y(), so in combination
158 // with tab strip position update it looks like this new tab grows and
159 // pushes all other tabs up.
160 tab->SetBounds(0, ideal_bounds(tab_data_index).y(),
161 ideal_bounds(tab_data_index).width(), kFisrtTabInitalHeight);
162 } else {
163 // Non-first tabs are animated from the previous tab position, so they
164 // slide up from underneath the previous tab and pushes the rest of the tabs
165 // up.
166 SidebarBaseTab* previous_tab = base_tab_at_tab_index(tab_data_index - 1);
167 tab->SetBoundsRect(previous_tab->bounds());
168 }
169
170 AnimateToIdealBounds();
171 }
172
173 void SidebarTabStrip::StartRemoveTabAnimation(int model_index) {
174 // Mark the tab as closing.
175 SidebarBaseTab* tab = GetBaseTabAtModelIndex(model_index);
176 tab->set_closing(true);
177
178 // Start an animation for the tabs.
179 GenerateIdealBounds();
180 AnimateToIdealBounds();
181 }
182
183 void SidebarTabStrip::GenerateIdealBounds() {
184 if (tab_count() == 0)
185 return;
186
187 int non_closing_tab_count = 0;
188 for (int i = 0; i < tab_count(); ++i) {
189 if (!base_tab_at_tab_index(i)->closing())
190 ++non_closing_tab_count;
191 }
192
193 int tab_width = SidebarTab::GetStandardSize().width();
194 int tab_height = SidebarTab::GetStandardSize().height();
195 int tab_y = non_closing_tab_count == 0 ? 0 :
196 (non_closing_tab_count - 1) * (tab_height + kTabOffset);
197
198 bool first_non_closing_tab = true;
199 gfx::Rect current_tab_bounds(0, tab_y, tab_width, tab_height);
200
201 for (int i = 0; i < tab_count(); ++i) {
202 if (!base_tab_at_tab_index(i)->closing()) {
203 if (!first_non_closing_tab) {
204 tab_y -= tab_height + kTabOffset;
205 current_tab_bounds.set_y(tab_y);
206 } else {
207 first_non_closing_tab = false;
208 }
209 }
210 set_ideal_bounds(i, current_tab_bounds);
211 }
212 }
213
214 // SidebarTabStrip, private:
215
216 bool SidebarTabStrip::IsPointInTab(
217 SidebarBaseTab* tab,
218 const gfx::Point& point_in_tab_strip_coords) {
219 gfx::Point point_in_tab_coords(point_in_tab_strip_coords);
220 View::ConvertPointToView(this, tab, &point_in_tab_coords);
221 return tab->HitTest(point_in_tab_coords);
222 }
223
OLDNEW
« no previous file with comments | « chrome/browser/ui/views/sidebar/sidebar_tab_strip.h ('k') | chrome/browser/ui/views/sidebar/sidebar_tab_strip_controller.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698