15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/views/widget/native_widget_aura.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/basictypes.h" 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/command_line.h" 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/memory/scoped_ptr.h" 10ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch#include "base/message_loop/message_loop.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gtest/include/gtest/gtest.h" 122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "ui/aura/client/aura_constants.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/aura/env.h" 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/aura/layout_manager.h" 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/aura/root_window.h" 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/aura/test/aura_test_helper.h" 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/aura/window.h" 18d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)#include "ui/events/event.h" 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/gfx/screen.h" 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/views/layout/fill_layout.h" 215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/views/widget/root_view.h" 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/views/widget/widget_delegate.h" 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace views { 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NativeWidgetAura* Init(aura::Window* parent, Widget* widget) { 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Widget::InitParams params(Widget::InitParams::TYPE_POPUP); 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.parent = parent; 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Init(params); 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return static_cast<NativeWidgetAura*>(widget->native_widget()); 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class NativeWidgetAuraTest : public testing::Test { 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NativeWidgetAuraTest() {} 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~NativeWidgetAuraTest() {} 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // testing::Test overrides: 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void SetUp() OVERRIDE { 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) aura_test_helper_.reset(new aura::test::AuraTestHelper(&message_loop_)); 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) aura_test_helper_->SetUp(); 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) root_window()->SetBounds(gfx::Rect(0, 0, 640, 480)); 45f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) dispatcher()->SetHostSize(gfx::Size(640, 480)); 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void TearDown() OVERRIDE { 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) message_loop_.RunUntilIdle(); 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) aura_test_helper_->TearDown(); 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 53f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) aura::Window* root_window() { return aura_test_helper_->root_window(); } 54f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) aura::RootWindow* dispatcher() { return aura_test_helper_->dispatcher(); } 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 57c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) base::MessageLoopForUI message_loop_; 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<aura::test::AuraTestHelper> aura_test_helper_; 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(NativeWidgetAuraTest); 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, CenterWindowLargeParent) { 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Make a parent window larger than the host represented by rootwindow. 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<aura::Window> parent(new aura::Window(NULL)); 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->Init(ui::LAYER_NOT_DRAWN); 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->SetBounds(gfx::Rect(0, 0, 1024, 800)); 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<Widget> widget(new Widget()); 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NativeWidgetAura* window = Init(parent.get(), widget.get()); 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) window->CenterWindow(gfx::Size(100, 100)); 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(gfx::Rect( (640 - 100) / 2, 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (480 - 100) / 2, 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 100, 100), 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) window->GetNativeWindow()->bounds()); 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->CloseNow(); 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, CenterWindowSmallParent) { 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Make a parent window smaller than the host represented by rootwindow. 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<aura::Window> parent(new aura::Window(NULL)); 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->Init(ui::LAYER_NOT_DRAWN); 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->SetBounds(gfx::Rect(0, 0, 480, 320)); 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<Widget> widget(new Widget()); 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NativeWidgetAura* window = Init(parent.get(), widget.get()); 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) window->CenterWindow(gfx::Size(100, 100)); 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(gfx::Rect( (480 - 100) / 2, 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (320 - 100) / 2, 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 100, 100), 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) window->GetNativeWindow()->bounds()); 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->CloseNow(); 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Verifies CenterWindow() constrains to parent size. 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, CenterWindowSmallParentNotAtOrigin) { 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Make a parent window smaller than the host represented by rootwindow and 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // offset it slightly from the origin. 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<aura::Window> parent(new aura::Window(NULL)); 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->Init(ui::LAYER_NOT_DRAWN); 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->SetBounds(gfx::Rect(20, 40, 480, 320)); 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<Widget> widget(new Widget()); 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NativeWidgetAura* window = Init(parent.get(), widget.get()); 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) window->CenterWindow(gfx::Size(500, 600)); 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |window| should be no bigger than |parent|. 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ("20,40 480x320", window->GetNativeWindow()->bounds().ToString()); 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->CloseNow(); 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Used by ShowMaximizedDoesntBounceAround. See it for details. 1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class TestLayoutManager : public aura::LayoutManager { 1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) TestLayoutManager() {} 1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnWindowResized() OVERRIDE { 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnWindowAddedToLayout(aura::Window* child) OVERRIDE { 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // This simulates what happens when adding a maximized window. 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SetChildBoundsDirect(child, gfx::Rect(0, 0, 300, 300)); 1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnWillRemoveWindowFromLayout(aura::Window* child) OVERRIDE { 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnWindowRemovedFromLayout(aura::Window* child) OVERRIDE { 1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnChildWindowVisibilityChanged(aura::Window* child, 1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool visible) OVERRIDE { 1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void SetChildBounds(aura::Window* child, 1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const gfx::Rect& requested_bounds) OVERRIDE { 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(TestLayoutManager); 1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This simulates BrowserView, which creates a custom RootView so that 1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// OnNativeWidgetSizeChanged that is invoked during Init matters. 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class TestWidget : public views::Widget { 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) TestWidget() : did_size_change_more_than_once_(false) { 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Returns true if the size changes to a non-empty size, and then to another 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // size. 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool did_size_change_more_than_once() const { 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return did_size_change_more_than_once_; 1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnNativeWidgetSizeChanged(const gfx::Size& new_size) OVERRIDE { 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (last_size_.IsEmpty()) 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_size_ = new_size; 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else if (!did_size_change_more_than_once_ && new_size != last_size_) 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) did_size_change_more_than_once_ = true; 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Widget::OnNativeWidgetSizeChanged(new_size); 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool did_size_change_more_than_once_; 1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::Size last_size_; 1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(TestWidget); 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Verifies the size of the widget doesn't change more than once during Init if 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// the window ends up maximized. This is important as otherwise 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// RenderWidgetHostViewAura ends up getting resized during construction, which 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// leads to noticable flashes. 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, ShowMaximizedDoesntBounceAround) { 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) root_window()->SetBounds(gfx::Rect(0, 0, 640, 480)); 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) root_window()->SetLayoutManager(new TestLayoutManager); 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<TestWidget> widget(new TestWidget()); 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Widget::InitParams params(Widget::InitParams::TYPE_WINDOW); 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.parent = NULL; 1762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) params.context = root_window(); 1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.show_state = ui::SHOW_STATE_MAXIMIZED; 1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.bounds = gfx::Rect(10, 10, 100, 200); 1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Init(params); 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_FALSE(widget->did_size_change_more_than_once()); 1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->CloseNow(); 1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, GetClientAreaScreenBounds) { 1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Create a widget. 1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Widget::InitParams params(Widget::InitParams::TYPE_WINDOW); 1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 1882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) params.context = root_window(); 1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.bounds.SetRect(10, 20, 300, 400); 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<Widget> widget(new Widget()); 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Init(params); 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // For Aura, client area bounds match window bounds. 1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::Rect client_bounds = widget->GetClientAreaBoundsInScreen(); 1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(10, client_bounds.x()); 1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(20, client_bounds.y()); 1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(300, client_bounds.width()); 1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(400, client_bounds.height()); 1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// View subclass that tracks whether it has gotten a gesture event. 2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class GestureTrackingView : public views::View { 2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GestureTrackingView() 2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : got_gesture_event_(false), 2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) consume_gesture_event_(true) {} 2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void set_consume_gesture_event(bool value) { 2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) consume_gesture_event_ = value; 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void clear_got_gesture_event() { 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) got_gesture_event_ = false; 2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool got_gesture_event() const { 2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return got_gesture_event_; 2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // View overrides: 2222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE { 2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) got_gesture_event_ = true; 2242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (consume_gesture_event_) 2252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) event->StopPropagation(); 2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Was OnGestureEvent() invoked? 2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool got_gesture_event_; 2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Dictates what OnGestureEvent() returns. 2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool consume_gesture_event_; 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(GestureTrackingView); 2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Verifies a capture isn't set on touch press and that the view that gets 2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// the press gets the release. 2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, DontCaptureOnGesture) { 2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Create two views (both sized the same). |child| is configured not to 2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // consume the gesture event. 2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GestureTrackingView* view = new GestureTrackingView(); 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GestureTrackingView* child = new GestureTrackingView(); 2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child->set_consume_gesture_event(false); 2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view->SetLayoutManager(new FillLayout); 2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view->AddChildView(child); 2505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<TestWidget> widget(new TestWidget()); 2512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) Widget::InitParams params(Widget::InitParams::TYPE_WINDOW_FRAMELESS); 2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 2532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) params.context = root_window(); 2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.bounds = gfx::Rect(0, 0, 100, 200); 2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Init(params); 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->SetContentsView(view); 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Show(); 2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::TouchEvent press(ui::ET_TOUCH_PRESSED, gfx::Point(41, 51), 1, 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta()); 261f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) dispatcher()->AsRootWindowHostDelegate()->OnHostTouchEvent(&press); 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Both views should get the press. 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_TRUE(view->got_gesture_event()); 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_TRUE(child->got_gesture_event()); 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view->clear_got_gesture_event(); 2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child->clear_got_gesture_event(); 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Touch events should not automatically grab capture. 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_FALSE(widget->HasCapture()); 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Release touch. Only |view| should get the release since that it consumed 2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // the press. 2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::TouchEvent release(ui::ET_TOUCH_RELEASED, gfx::Point(250, 251), 1, 2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta()); 274f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) dispatcher()->AsRootWindowHostDelegate()->OnHostTouchEvent(&release); 2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_TRUE(view->got_gesture_event()); 2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_FALSE(child->got_gesture_event()); 2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view->clear_got_gesture_event(); 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Work around for bug in NativeWidgetAura. 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // TODO: fix bug and remove this. 2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Close(); 2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, ReleaseCaptureOnTouchRelease) { 2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GestureTrackingView* view = new GestureTrackingView(); 2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<TestWidget> widget(new TestWidget()); 2872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) Widget::InitParams params(Widget::InitParams::TYPE_WINDOW_FRAMELESS); 2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 2892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) params.context = root_window(); 2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.bounds = gfx::Rect(0, 0, 100, 200); 2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Init(params); 2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->SetContentsView(view); 2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Show(); 2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::TouchEvent press(ui::ET_TOUCH_PRESSED, gfx::Point(41, 51), 1, 2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta()); 297f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) dispatcher()->AsRootWindowHostDelegate()->OnHostTouchEvent(&press); 2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_TRUE(view->got_gesture_event()); 2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view->clear_got_gesture_event(); 3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Set the capture. 3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->SetCapture(view); 3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_TRUE(widget->HasCapture()); 3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Generate a release, this should trigger releasing capture. 3055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::TouchEvent release(ui::ET_TOUCH_RELEASED, gfx::Point(41, 51), 1, 3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta()); 307f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) dispatcher()->AsRootWindowHostDelegate()->OnHostTouchEvent(&release); 3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_TRUE(view->got_gesture_event()); 3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view->clear_got_gesture_event(); 3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_FALSE(widget->HasCapture()); 3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Work around for bug in NativeWidgetAura. 3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // TODO: fix bug and remove this. 3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) widget->Close(); 3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Verifies views with layers are targeted for events properly. 3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(NativeWidgetAuraTest, PreferViewLayersToChildWindows) { 319868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Create two widgets: |parent| and |child|. |child| is a child of |parent|. 3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) views::View* parent_root = new views::View; 3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<Widget> parent(new Widget()); 3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Widget::InitParams parent_params(Widget::InitParams::TYPE_WINDOW_FRAMELESS); 3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent_params.ownership = 3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 3252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) parent_params.context = root_window(); 3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->Init(parent_params); 3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->SetContentsView(parent_root); 3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->SetBounds(gfx::Rect(0, 0, 400, 400)); 3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->Show(); 3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<Widget> child(new Widget()); 3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Widget::InitParams child_params(Widget::InitParams::TYPE_CONTROL); 3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child_params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child_params.parent = parent->GetNativeWindow(); 3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child->Init(child_params); 3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child->SetBounds(gfx::Rect(0, 0, 200, 200)); 3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) child->Show(); 3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Point is over |child|. 3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(child->GetNativeWindow(), 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->GetNativeWindow()->GetEventHandlerForPoint( 3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::Point(50, 50))); 3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 344868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Create a view with a layer and stack it at the bottom (below |child|). 3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) views::View* view_with_layer = new views::View; 3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent_root->AddChildView(view_with_layer); 3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view_with_layer->SetBounds(0, 0, 50, 50); 3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view_with_layer->SetPaintToLayer(true); 3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 350868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Make sure that |child| still gets the event. 351868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) EXPECT_EQ(child->GetNativeWindow(), 352868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) parent->GetNativeWindow()->GetEventHandlerForPoint( 353868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) gfx::Point(20, 20))); 354868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 355868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Move |view_with_layer| to the top and make sure it gets the 356868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // event when the point is within |view_with_layer|'s bounds. 357868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) view_with_layer->layer()->parent()->StackAtTop( 358868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) view_with_layer->layer()); 3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(parent->GetNativeWindow(), 3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->GetNativeWindow()->GetEventHandlerForPoint( 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::Point(20, 20))); 3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Point is over |child|, it should get the event. 3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(child->GetNativeWindow(), 3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->GetNativeWindow()->GetEventHandlerForPoint( 3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::Point(70, 70))); 3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete view_with_layer; 3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) view_with_layer = NULL; 3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_EQ(child->GetNativeWindow(), 3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->GetNativeWindow()->GetEventHandlerForPoint( 3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::Point(20, 20))); 3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Work around for bug in NativeWidgetAura. 3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // TODO: fix bug and remove this. 3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent->Close(); 3785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Verifies that widget->FlashFrame() sets aura::client::kDrawAttentionKey, 3812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// and activating the window clears it. 3822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(NativeWidgetAuraTest, FlashFrame) { 3832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) scoped_ptr<Widget> widget(new Widget()); 3842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) Widget::InitParams params(Widget::InitParams::TYPE_WINDOW); 3852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) params.context = root_window(); 3862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; 3872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) widget->Init(params); 3882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) aura::Window* window = widget->GetNativeWindow(); 3892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) EXPECT_FALSE(window->GetProperty(aura::client::kDrawAttentionKey)); 3902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) widget->FlashFrame(true); 3912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) EXPECT_TRUE(window->GetProperty(aura::client::kDrawAttentionKey)); 3922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) widget->FlashFrame(false); 3932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) EXPECT_FALSE(window->GetProperty(aura::client::kDrawAttentionKey)); 3942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) widget->FlashFrame(true); 3952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) EXPECT_TRUE(window->GetProperty(aura::client::kDrawAttentionKey)); 3962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) widget->Activate(); 3972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) EXPECT_FALSE(window->GetProperty(aura::client::kDrawAttentionKey)); 3982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 3992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(NativeWidgetAuraTest, NoCrashOnThemeAfterClose) { 4012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) scoped_ptr<aura::Window> parent(new aura::Window(NULL)); 4022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) parent->Init(ui::LAYER_NOT_DRAWN); 4032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) parent->SetBounds(gfx::Rect(0, 0, 480, 320)); 4042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) scoped_ptr<Widget> widget(new Widget()); 4052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NativeWidgetAura* window = Init(parent.get(), widget.get()); 4062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) window->Show(); 4072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) window->Close(); 408c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) base::MessageLoop::current()->RunUntilIdle(); 4092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) widget->GetNativeTheme(); // Shouldn't crash. 4102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 4112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace 4135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace views 414