mirror of
https://bitbucket.org/chromiumembedded/cef
synced 2025-06-05 21:39:12 +02:00
Windows: Fix hidden dropdowns when the window is topmost (issue #1468)
Also add a --always-on-top flag to cefclient to allow easier testing of this behavior on Windows and Linux.
This commit is contained in:
committed by
Marshall Greenblatt
parent
fbc59483b9
commit
5969b2bbb8
@@ -78,8 +78,8 @@ bool CefBrowserPlatformDelegateNativeLinux::CreateHostWindow() {
|
||||
// Add a reference that will be released in BrowserDestroyed().
|
||||
browser_->AddRef();
|
||||
|
||||
CefWindowDelegateView* delegate_view =
|
||||
new CefWindowDelegateView(GetBackgroundColor());
|
||||
CefWindowDelegateView* delegate_view = new CefWindowDelegateView(
|
||||
GetBackgroundColor(), window_x11_->TopLevelAlwaysOnTop());
|
||||
delegate_view->Init(window_info_.window, browser_->web_contents(),
|
||||
gfx::Rect(gfx::Point(), rect.size()));
|
||||
|
||||
|
@@ -189,8 +189,15 @@ bool CefBrowserPlatformDelegateNativeWin::CreateHostWindow() {
|
||||
point =
|
||||
gfx::ToFlooredPoint(gfx::ScalePoint(gfx::PointF(point), 1.0f / scale));
|
||||
|
||||
// Stay on top if top-most window hosting the web view is topmost.
|
||||
HWND top_level_window = GetAncestor(window_info_.window, GA_ROOT);
|
||||
DWORD top_level_window_ex_styles =
|
||||
GetWindowLongPtr(top_level_window, GWL_EXSTYLE);
|
||||
bool always_on_top =
|
||||
(top_level_window_ex_styles & WS_EX_TOPMOST) == WS_EX_TOPMOST;
|
||||
|
||||
CefWindowDelegateView* delegate_view =
|
||||
new CefWindowDelegateView(GetBackgroundColor());
|
||||
new CefWindowDelegateView(GetBackgroundColor(), always_on_top);
|
||||
delegate_view->Init(window_info_.window, browser_->web_contents(),
|
||||
gfx::Rect(0, 0, point.x(), point.y()));
|
||||
|
||||
|
@@ -12,8 +12,11 @@
|
||||
#include "ui/views/layout/fill_layout.h"
|
||||
#include "ui/views/widget/widget.h"
|
||||
|
||||
CefWindowDelegateView::CefWindowDelegateView(SkColor background_color)
|
||||
: background_color_(background_color), web_view_(NULL) {}
|
||||
CefWindowDelegateView::CefWindowDelegateView(SkColor background_color,
|
||||
bool always_on_top)
|
||||
: background_color_(background_color),
|
||||
web_view_(NULL),
|
||||
always_on_top_(always_on_top) {}
|
||||
|
||||
void CefWindowDelegateView::Init(gfx::AcceleratedWidget parent_widget,
|
||||
content::WebContents* web_contents,
|
||||
@@ -44,6 +47,8 @@ void CefWindowDelegateView::Init(gfx::AcceleratedWidget parent_widget,
|
||||
// CefBrowserHostImpl::PlatformSetFocus.
|
||||
params.activatable = views::Widget::InitParams::ACTIVATABLE_YES;
|
||||
|
||||
params.keep_on_top = always_on_top_;
|
||||
|
||||
// Results in a call to InitContent().
|
||||
widget->Init(params);
|
||||
|
||||
|
@@ -20,7 +20,7 @@ class WebView;
|
||||
// will be deleted automatically when the associated root window is destroyed.
|
||||
class CefWindowDelegateView : public views::WidgetDelegateView {
|
||||
public:
|
||||
explicit CefWindowDelegateView(SkColor background_color);
|
||||
CefWindowDelegateView(SkColor background_color, bool always_on_top);
|
||||
|
||||
// Create the Widget and associated root window.
|
||||
void Init(gfx::AcceleratedWidget parent_widget,
|
||||
@@ -43,6 +43,7 @@ class CefWindowDelegateView : public views::WidgetDelegateView {
|
||||
private:
|
||||
SkColor background_color_;
|
||||
views::WebView* web_view_;
|
||||
bool always_on_top_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefWindowDelegateView);
|
||||
};
|
||||
|
@@ -396,3 +396,34 @@ void CefWindowX11::ContinueFocus() {
|
||||
browser_->SetFocus(true);
|
||||
focus_pending_ = false;
|
||||
}
|
||||
|
||||
bool CefWindowX11::TopLevelAlwaysOnTop() const {
|
||||
::Window toplevel_window = FindToplevelParent(xdisplay_, xwindow_);
|
||||
|
||||
Atom state_atom = gfx::GetAtom("_NET_WM_STATE");
|
||||
Atom state_keep_above = gfx::GetAtom("_NET_WM_STATE_KEEP_ABOVE");
|
||||
Atom* states;
|
||||
|
||||
Atom actual_type;
|
||||
int actual_format;
|
||||
unsigned long num_items;
|
||||
unsigned long bytes_after;
|
||||
|
||||
XGetWindowProperty(xdisplay_, toplevel_window, state_atom, 0, 1024,
|
||||
x11::False, XA_ATOM, &actual_type, &actual_format,
|
||||
&num_items, &bytes_after,
|
||||
reinterpret_cast<unsigned char**>(&states));
|
||||
|
||||
bool always_on_top = false;
|
||||
|
||||
for (unsigned long i = 0; i < num_items; ++i) {
|
||||
if (states[i] == state_keep_above) {
|
||||
always_on_top = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
XFree(states);
|
||||
|
||||
return always_on_top;
|
||||
}
|
||||
|
@@ -52,6 +52,8 @@ class CefWindowX11 : public ui::PlatformEventDispatcher {
|
||||
::Window xwindow() const { return xwindow_; }
|
||||
gfx::Rect bounds() const { return bounds_; }
|
||||
|
||||
bool TopLevelAlwaysOnTop() const;
|
||||
|
||||
private:
|
||||
void ContinueFocus();
|
||||
|
||||
|
Reference in New Issue
Block a user