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.
5 #ifndef CHROME_BROWSER_UI_VIEWS_OMNIBOX_OMNIBOX_POPUP_CONTENTS_VIEW_H_
6 #define CHROME_BROWSER_UI_VIEWS_OMNIBOX_OMNIBOX_POPUP_CONTENTS_VIEW_H_
8 #include "base/memory/weak_ptr.h"
9 #include "chrome/browser/ui/omnibox/omnibox_popup_model.h"
10 #include "chrome/browser/ui/omnibox/omnibox_popup_view.h"
11 #include "chrome/browser/ui/views/omnibox/omnibox_result_view_model.h"
12 #include "ui/base/window_open_disposition.h"
13 #include "ui/gfx/animation/animation_delegate.h"
14 #include "ui/gfx/animation/slide_animation.h"
15 #include "ui/gfx/font_list.h"
16 #include "ui/views/view.h"
18 struct AutocompleteMatch;
19 class LocationBarView;
20 class OmniboxEditModel;
21 class OmniboxResultView;
25 // A view representing the contents of the autocomplete popup.
26 class OmniboxPopupContentsView : public views::View,
27 public OmniboxResultViewModel,
28 public OmniboxPopupView,
29 public gfx::AnimationDelegate {
31 // Factory method for creating the AutocompletePopupView.
32 static OmniboxPopupView* Create(const gfx::FontList& font_list,
33 OmniboxView* omnibox_view,
34 OmniboxEditModel* edit_model,
35 LocationBarView* location_bar_view);
37 // Returns the bounds the popup should be shown at. This is the display bounds
38 // and includes offsets for the dropshadow which this view's border renders.
39 gfx::Rect GetPopupBounds() const;
41 virtual void LayoutChildren();
43 // Overridden from OmniboxPopupView:
44 virtual bool IsOpen() const OVERRIDE;
45 virtual void InvalidateLine(size_t line) OVERRIDE;
46 virtual void UpdatePopupAppearance() OVERRIDE;
47 virtual gfx::Rect GetTargetBounds() OVERRIDE;
48 virtual void PaintUpdatesNow() OVERRIDE;
49 virtual void OnDragCanceled() OVERRIDE;
51 // Overridden from OmniboxResultViewModel:
52 virtual bool IsSelectedIndex(size_t index) const OVERRIDE;
53 virtual bool IsHoveredIndex(size_t index) const OVERRIDE;
54 virtual gfx::Image GetIconIfExtensionMatch(size_t index) const OVERRIDE;
56 // Overridden from gfx::AnimationDelegate:
57 virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
59 // Overridden from views::View:
60 virtual void Layout() OVERRIDE;
61 virtual views::View* GetEventHandlerForPoint(
62 const gfx::Point& point) OVERRIDE;
63 virtual views::View* GetTooltipHandlerForPoint(
64 const gfx::Point& point) OVERRIDE;
65 virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE;
66 virtual bool OnMouseDragged(const ui::MouseEvent& event) OVERRIDE;
67 virtual void OnMouseReleased(const ui::MouseEvent& event) OVERRIDE;
68 virtual void OnMouseCaptureLost() OVERRIDE;
69 virtual void OnMouseMoved(const ui::MouseEvent& event) OVERRIDE;
70 virtual void OnMouseEntered(const ui::MouseEvent& event) OVERRIDE;
71 virtual void OnMouseExited(const ui::MouseEvent& event) OVERRIDE;
73 // Overridden from ui::EventHandler:
74 virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE;
77 OmniboxPopupContentsView(const gfx::FontList& font_list,
78 OmniboxView* omnibox_view,
79 OmniboxEditModel* edit_model,
80 LocationBarView* location_bar_view);
81 virtual ~OmniboxPopupContentsView();
83 LocationBarView* location_bar_view() { return location_bar_view_; }
85 virtual void PaintResultViews(gfx::Canvas* canvas);
87 // Calculates the height needed to show all the results in the model.
88 virtual int CalculatePopupHeight();
89 virtual OmniboxResultView* CreateResultView(OmniboxResultViewModel* model,
91 const gfx::FontList& font_list);
93 // Overridden from views::View:
94 virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE;
95 // This method should not be triggered directly as we paint our children
96 // in an un-conventional way inside OnPaint. We use a separate canvas to
97 // paint the children. Hence we override this method to a no-op so that
98 // the view hierarchy does not "accidentally" trigger this.
99 virtual void PaintChildren(gfx::Canvas* canvas) OVERRIDE;
101 scoped_ptr<OmniboxPopupModel> model_;
104 class AutocompletePopupWidget;
106 // Call immediately after construction.
109 // Returns true if the model has a match at the specified index.
110 bool HasMatchAt(size_t index) const;
112 // Returns the match at the specified index within the popup model.
113 const AutocompleteMatch& GetMatchAtIndex(size_t index) const;
115 // Fill a path for the contents' roundrect. |bounding_rect| is the rect that
117 void MakeContentsPath(gfx::Path* path, const gfx::Rect& bounding_rect);
119 // Find the index of the match under the given |point|, specified in window
120 // coordinates. Returns OmniboxPopupModel::kNoMatch if there isn't a match at
121 // the specified point.
122 size_t GetIndexForPoint(const gfx::Point& point);
124 // Processes a located event (e.g. mouse/gesture) and sets the selection/hover
125 // state of a line in the list.
126 void UpdateLineEvent(const ui::LocatedEvent& event,
127 bool should_set_selected_line);
129 // Opens an entry from the list depending on the event and the selected
131 void OpenSelectedLine(const ui::LocatedEvent& event,
132 WindowOpenDisposition disposition);
134 OmniboxResultView* result_view_at(size_t i);
136 // The popup that contains this view. We create this, but it deletes itself
137 // when its window is destroyed. This is a WeakPtr because it's possible for
138 // the OS to destroy the window and thus delete this object before we're
139 // deleted, or without our knowledge.
140 base::WeakPtr<AutocompletePopupWidget> popup_;
142 // The edit view that invokes us.
143 OmniboxView* omnibox_view_;
145 LocationBarView* location_bar_view_;
147 // The font list used for result rows, based on the omnibox font list.
148 gfx::FontList font_list_;
150 // If the user cancels a dragging action (i.e. by pressing ESC), we don't have
151 // a convenient way to release mouse capture. Instead we use this flag to
152 // simply ignore all remaining drag events, and the eventual mouse release
153 // event. Since OnDragCanceled() can be called when we're not dragging, this
154 // flag is reset to false on a mouse pressed event, to make sure we don't
155 // erroneously ignore the next drag.
156 bool ignore_mouse_drag_;
158 // The popup sizes vertically using an animation when the popup is getting
159 // shorter (not larger, that makes it look "slow").
160 gfx::SlideAnimation size_animation_;
161 gfx::Rect start_bounds_;
162 gfx::Rect target_bounds_;
167 const gfx::ImageSkia* bottom_shadow_; // Ptr owned by resource bundle.
169 // Amount of extra padding to add to the popup on the top and bottom.
170 int outside_vertical_padding_;
172 DISALLOW_COPY_AND_ASSIGN(OmniboxPopupContentsView);
175 #endif // CHROME_BROWSER_UI_VIEWS_OMNIBOX_OMNIBOX_POPUP_CONTENTS_VIEW_H_