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 #include "ui/base/win/hwnd_subclass.h"
7 #include "base/basictypes.h"
8 #include "testing/gtest/include/gtest/gtest.h"
9 #include "ui/gfx/win/window_impl.h"
15 class TestWindow
: public gfx::WindowImpl
{
17 TestWindow() : saw_message(false) {}
18 virtual ~TestWindow() {}
23 // Overridden from gfx::WindowImpl:
24 virtual BOOL
ProcessWindowMessage(HWND window
,
29 DWORD msg_map_id
) OVERRIDE
{
30 if (message
== WM_NCHITTEST
)
33 return FALSE
; // Results in DefWindowProc().
36 DISALLOW_COPY_AND_ASSIGN(TestWindow
);
39 class TestMessageFilter
: public HWNDMessageFilter
{
41 TestMessageFilter() : consume_messages(false), saw_message(false) {}
42 virtual ~TestMessageFilter() {}
44 // Setting to true causes the filter subclass to stop messages from reaching
45 // the subclassed window procedure.
46 bool consume_messages
;
48 // True if the message filter saw the message.
52 // Overridden from HWNDMessageFilter:
53 virtual bool FilterMessage(HWND hwnd
,
57 LRESULT
* l_result
) OVERRIDE
{
58 if (message
== WM_NCHITTEST
) {
60 return consume_messages
;
65 DISALLOW_COPY_AND_ASSIGN(TestMessageFilter
);
70 TEST(HWNDSubclassTest
, Filtering
) {
72 window
.Init(NULL
, gfx::Rect(0, 0, 100, 100));
73 EXPECT_TRUE(window
.hwnd() != NULL
);
77 HWNDSubclass::AddFilterToTarget(window
.hwnd(), &mf
);
79 // We are not filtering, so both the filter and the window should receive
81 ::SendMessage(window
.hwnd(), WM_NCHITTEST
, 0, 0);
83 EXPECT_TRUE(mf
.saw_message
);
84 EXPECT_TRUE(window
.saw_message
);
86 mf
.saw_message
= false;
87 window
.saw_message
= false;
89 mf
.consume_messages
= true;
91 // We are now filtering, so only the filter should see this message:
92 ::SendMessage(window
.hwnd(), WM_NCHITTEST
, 0, 0);
94 EXPECT_TRUE(mf
.saw_message
);
95 EXPECT_FALSE(window
.saw_message
);
99 TEST(HWNDSubclassTest
, FilteringMultipleFilters
) {
101 window
.Init(NULL
, gfx::Rect(0, 0, 100, 100));
102 EXPECT_TRUE(window
.hwnd() != NULL
);
105 TestMessageFilter mf1
;
106 TestMessageFilter mf2
;
107 HWNDSubclass::AddFilterToTarget(window
.hwnd(), &mf1
);
108 HWNDSubclass::AddFilterToTarget(window
.hwnd(), &mf2
);
110 // We are not filtering, so both the filter and the window should receive
112 ::SendMessage(window
.hwnd(), WM_NCHITTEST
, 0, 0);
114 EXPECT_TRUE(mf1
.saw_message
);
115 EXPECT_TRUE(mf2
.saw_message
);
116 EXPECT_TRUE(window
.saw_message
);
118 mf1
.saw_message
= false;
119 mf2
.saw_message
= false;
120 window
.saw_message
= false;
122 mf1
.consume_messages
= true;
124 // We are now filtering, so only the filter |mf1| should see this message:
125 ::SendMessage(window
.hwnd(), WM_NCHITTEST
, 0, 0);
127 EXPECT_TRUE(mf1
.saw_message
);
128 EXPECT_FALSE(mf2
.saw_message
);
129 EXPECT_FALSE(window
.saw_message
);
133 TEST(HWNDSubclassTest
, RemoveFilter
) {
135 window
.Init(NULL
, gfx::Rect(0, 0, 100, 100));
136 EXPECT_TRUE(window
.hwnd() != NULL
);
139 TestMessageFilter mf1
;
140 TestMessageFilter mf2
;
141 HWNDSubclass::AddFilterToTarget(window
.hwnd(), &mf1
);
142 HWNDSubclass::AddFilterToTarget(window
.hwnd(), &mf2
);
144 ::SendMessage(window
.hwnd(), WM_NCHITTEST
, 0, 0);
145 EXPECT_TRUE(mf1
.saw_message
);
146 EXPECT_TRUE(mf2
.saw_message
);
147 EXPECT_TRUE(window
.saw_message
);
149 mf1
.saw_message
= false;
150 mf2
.saw_message
= false;
151 window
.saw_message
= false;
153 // Remove a filter and try sending message again.
154 HWNDSubclass::RemoveFilterFromAllTargets(&mf1
);
155 ::SendMessage(window
.hwnd(), WM_NCHITTEST
, 0, 0);
156 EXPECT_FALSE(mf1
.saw_message
);
157 EXPECT_TRUE(mf2
.saw_message
);
158 EXPECT_TRUE(window
.saw_message
);