Chromium Code Reviews| Index: ui/views/bubble/bubble_delegate_unittest.cc |
| diff --git a/ui/views/bubble/bubble_delegate_unittest.cc b/ui/views/bubble/bubble_delegate_unittest.cc |
| index 2fa3b403616530f09566f614685953bf3261af71..009cbcd1e8758eab5001aa9b236f5fa89c4bc803 100644 |
| --- a/ui/views/bubble/bubble_delegate_unittest.cc |
| +++ b/ui/views/bubble/bubble_delegate_unittest.cc |
| @@ -9,6 +9,40 @@ |
| namespace views { |
| +namespace { |
| + |
| +// A Widget observer class used in the tests below to observe bubbles closing. |
| +class TestWidgetObserver : public WidgetObserver { |
| +public: |
|
Ben Goodger (Google)
2012/08/28 22:21:19
1-space indent here and below
msw
2012/08/28 22:28:31
Done.
|
| + explicit TestWidgetObserver(Widget* widget); |
| + virtual ~TestWidgetObserver(); |
| + |
| + // WidgetObserver overrides: |
| + virtual void OnWidgetClosing(Widget* widget) OVERRIDE; |
| + |
| + bool widget_closed() const { return widget_ == NULL; } |
| + |
| + private: |
| + Widget* widget_; |
| +}; |
| + |
| +TestWidgetObserver::TestWidgetObserver(Widget* widget) |
| + : widget_(widget) { |
| + widget_->AddObserver(this); |
| +} |
| + |
| +TestWidgetObserver::~TestWidgetObserver() { |
| + if (widget_) |
| + widget_->RemoveObserver(this); |
| +} |
| + |
| +void TestWidgetObserver::OnWidgetClosing(Widget* widget) { |
| + DCHECK_EQ(widget_, widget); |
| + widget_ = NULL; |
| +} |
| + |
| +} |
| + |
| typedef ViewsTestBase BubbleDelegateTest; |
| TEST_F(BubbleDelegateTest, CreateDelegate) { |
| @@ -19,6 +53,8 @@ TEST_F(BubbleDelegateTest, CreateDelegate) { |
| BubbleDelegateView::CreateBubble(bubble_delegate)); |
| EXPECT_EQ(bubble_delegate, bubble_widget->widget_delegate()); |
| EXPECT_EQ(bubble_widget, bubble_delegate->GetWidget()); |
| + TestWidgetObserver bubble_observer(bubble_widget); |
| + EXPECT_FALSE(bubble_observer.widget_closed()); |
| BubbleBorder* border = |
| bubble_delegate->GetBubbleFrameView()->bubble_border(); |
| @@ -27,52 +63,83 @@ TEST_F(BubbleDelegateTest, CreateDelegate) { |
| bubble_widget->CloseNow(); |
| RunPendingMessages(); |
| + EXPECT_TRUE(bubble_observer.widget_closed()); |
| } |
| -TEST_F(BubbleDelegateTest, ResetAnchorWidget) { |
| - // Create the anchor widget first. |
| - Widget* widget = new Widget; |
| - View* contents = new View; |
| - |
| +TEST_F(BubbleDelegateTest, CloseAnchorWidget) { |
| + // Create the anchor widget. |
| Widget::InitParams params(Widget::InitParams::TYPE_WINDOW); |
| - widget->Init(params); |
| - widget->SetContentsView(contents); |
| - widget->Show(); |
| + params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; |
| + scoped_ptr<Widget> anchor_widget(new Widget); |
| + anchor_widget->Init(params); |
| + anchor_widget->Show(); |
| + |
| + BubbleDelegateView* bubble_delegate = new BubbleDelegateView( |
| + anchor_widget->GetContentsView(), BubbleBorder::NONE); |
| + // Preventing close on deactivate should not prevent closing with the anchor. |
| + bubble_delegate->set_close_on_deactivate(false); |
| + Widget* bubble_widget = BubbleDelegateView::CreateBubble(bubble_delegate); |
| + EXPECT_EQ(bubble_delegate, bubble_widget->widget_delegate()); |
| + EXPECT_EQ(bubble_widget, bubble_delegate->GetWidget()); |
| + EXPECT_EQ(anchor_widget.get(), bubble_delegate->anchor_widget()); |
| + TestWidgetObserver bubble_observer(bubble_widget); |
| + EXPECT_FALSE(bubble_observer.widget_closed()); |
| + |
| + bubble_widget->Show(); |
| + RunPendingMessages(); |
| + EXPECT_EQ(anchor_widget.get(), bubble_delegate->anchor_widget()); |
| + EXPECT_FALSE(bubble_observer.widget_closed()); |
| + |
| + // Ensure that closing the anchor widget also closes the bubble itself. |
| + anchor_widget->CloseNow(); |
| + RunPendingMessages(); |
| + EXPECT_TRUE(bubble_observer.widget_closed()); |
| +} |
| - Widget* parent = new Widget; |
| - parent->Init(params); |
| - parent->SetContentsView(new View); |
| - parent->Show(); |
| +TEST_F(BubbleDelegateTest, ResetAnchorWidget) { |
| + // Create the anchor and parent widgets. |
| + Widget::InitParams params(Widget::InitParams::TYPE_WINDOW); |
| + params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; |
| + scoped_ptr<Widget> anchor_widget(new Widget); |
| + anchor_widget->Init(params); |
| + anchor_widget->Show(); |
| + scoped_ptr<Widget> parent_widget(new Widget); |
| + parent_widget->Init(params); |
| + parent_widget->Show(); |
| // Make sure the bubble widget is parented to a widget other than the anchor |
| // widget so that closing the anchor widget does not close the bubble widget. |
| - BubbleDelegateView* bubble_delegate = |
| - new BubbleDelegateView(contents, BubbleBorder::NONE); |
| - bubble_delegate->set_parent_window(parent->GetNativeView()); |
| - bubble_delegate->set_color(SK_ColorGREEN); |
| - Widget* bubble_widget( |
| - BubbleDelegateView::CreateBubble(bubble_delegate)); |
| + BubbleDelegateView* bubble_delegate = new BubbleDelegateView( |
| + anchor_widget->GetContentsView(), BubbleBorder::NONE); |
| + bubble_delegate->set_parent_window(parent_widget->GetNativeView()); |
| + // Preventing close on deactivate should not prevent closing with the parent. |
| + bubble_delegate->set_close_on_deactivate(false); |
| + Widget* bubble_widget = BubbleDelegateView::CreateBubble(bubble_delegate); |
| EXPECT_EQ(bubble_delegate, bubble_widget->widget_delegate()); |
| EXPECT_EQ(bubble_widget, bubble_delegate->GetWidget()); |
| - EXPECT_EQ(widget, bubble_delegate->anchor_widget()); |
| + EXPECT_EQ(anchor_widget.get(), bubble_delegate->anchor_widget()); |
| + TestWidgetObserver bubble_observer(bubble_widget); |
| + EXPECT_FALSE(bubble_observer.widget_closed()); |
| + // Showing and hiding the bubble widget should have no effect on its anchor. |
| bubble_widget->Show(); |
| RunPendingMessages(); |
| - EXPECT_EQ(widget, bubble_delegate->anchor_widget()); |
| - |
| + EXPECT_EQ(anchor_widget.get(), bubble_delegate->anchor_widget()); |
| bubble_widget->Hide(); |
| RunPendingMessages(); |
| - EXPECT_EQ(widget, bubble_delegate->anchor_widget()); |
| + EXPECT_EQ(anchor_widget.get(), bubble_delegate->anchor_widget()); |
| - // Closing the anchor widget should unset the reference to the anchor widget |
| - // for the bubble. |
| - widget->CloseNow(); |
| + // Ensure that closing the anchor widget clears the bubble's reference to that |
| + // anchor widget, but the bubble itself does not close. |
| + anchor_widget->CloseNow(); |
| RunPendingMessages(); |
| - EXPECT_NE(bubble_delegate->anchor_widget(), widget); |
| + EXPECT_NE(anchor_widget.get(), bubble_delegate->anchor_widget()); |
| + EXPECT_FALSE(bubble_observer.widget_closed()); |
| - bubble_widget->CloseNow(); |
| - parent->CloseNow(); |
| + // Ensure that closing the parent widget also closes the bubble itself. |
| + parent_widget->CloseNow(); |
| RunPendingMessages(); |
| + EXPECT_TRUE(bubble_observer.widget_closed()); |
| } |
| } // namespace views |