[XProto] Remove usage of all Xlib headers
This CL removes <X11/Xlib.h> from //ui/gfx/x/x11.h. What was provided by Xlib.h is now provided with inline declarations. The intent is that I'll incrementally remove declarations from x11.h until there's nothing left, at which point the dependency on Xlib will be removed and therefore x11.h can be removed. Doing it this way will ensure no additional usages of Xlib are introduced, and it gives a nice way of tracking progress as usages are removed. * All Xlib macros are now gone, so it's safe to remove the XProto "undef" files. * For some usages of Xlib (events in particular), it's easier to port to XProto now rather than add declarations to x11.h. * ui/gfx/x/keysyms/keysyms.h is added in its own directory because it's needed by xkbcommon code, which is also built on ChromeOS, but ui/gfx/x/BUIDL.gn asserts that the platform is desktop Linux. BUG=1066670 R=sky Change-Id: If8679721548d45bdea48bcd8a898191b3f87eb10 Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2392140 Auto-Submit: Thomas Anderson <thomasanderson@chromium.org> Commit-Queue: Scott Violet <sky@chromium.org> Reviewed-by: Scott Violet <sky@chromium.org> Reviewed-by: Nick Yamane <nickdiego@igalia.com> Reviewed-by: Zhenyao Mo <zmo@chromium.org> Cr-Commit-Position: refs/heads/master@{#805533}
This commit is contained in:
PRESUBMIT.py
chrome/test/chromedriver
gpu
tools
compositor_model_bench
vulkan
media/base
remoting/host
third_party
ui
aura
base
x
compositor
events
blink
keycodes
BUILD.gnkeyboard_code_conversion_x.cckeyboard_code_conversion_xkb.cckeysym_to_unicode.ccxkb_keysym.h
platform
test
gfx
x
gl
gl_bindings.ccgl_bindings.hgl_context_glx_unittest.ccgl_glx_api_implementation.ccgl_image_glx.ccgl_surface_egl_x11.ccgl_surface_egl_x11_gles2.ccgl_surface_glx.cc
gtk
ozone
platform
platform_window
views
45
PRESUBMIT.py
45
PRESUBMIT.py
@ -455,43 +455,6 @@ _BANNED_CPP_FUNCTIONS = (
|
||||
False,
|
||||
(),
|
||||
),
|
||||
(
|
||||
r'/XSelectInput|CWEventMask|XCB_CW_EVENT_MASK',
|
||||
(
|
||||
'Chrome clients wishing to select events on X windows should use',
|
||||
'ui::XScopedEventSelector. It is safe to ignore this warning only if',
|
||||
'you are selecting events from the GPU process, or if you are using',
|
||||
'an XDisplay other than gfx::GetXDisplay().',
|
||||
),
|
||||
True,
|
||||
(
|
||||
r"^ui[\\/]events[\\/]x[\\/].*\.cc$",
|
||||
r"^ui[\\/]gl[\\/].*\.cc$",
|
||||
r"^media[\\/]gpu[\\/].*\.cc$",
|
||||
r"^gpu[\\/].*\.cc$",
|
||||
r"^ui[\\/]base[\\/]x[\\/]xwmstartupcheck[\\/]xwmstartupcheck\.cc$",
|
||||
),
|
||||
),
|
||||
(
|
||||
r'/\WX?(((Width|Height)(MM)?OfScreen)|(Display(Width|Height)))\(',
|
||||
(
|
||||
'Use the corresponding fields in x11::Screen instead.',
|
||||
),
|
||||
True,
|
||||
(),
|
||||
),
|
||||
(
|
||||
r'/XInternAtom|xcb_intern_atom',
|
||||
(
|
||||
'Use gfx::GetAtom() instead of interning atoms directly.',
|
||||
),
|
||||
True,
|
||||
(
|
||||
r"^gpu[\\/]ipc[\\/]service[\\/]gpu_watchdog_thread\.cc$",
|
||||
r"^remoting[\\/]host[\\/]linux[\\/]x_server_clipboard\.cc$",
|
||||
r"^ui[\\/]gfx[\\/]x[\\/]x11_atom_cache\.cc$",
|
||||
),
|
||||
),
|
||||
(
|
||||
'setMatrixClip',
|
||||
(
|
||||
@ -845,6 +808,14 @@ _BANNED_CPP_FUNCTIONS = (
|
||||
True,
|
||||
[_THIRD_PARTY_EXCEPT_BLINK], # Not an error in third_party folders.
|
||||
),
|
||||
(
|
||||
r'/\b#include <X11/',
|
||||
(
|
||||
'Do not use Xlib. Use xproto (from //ui/gfx/x:xproto) instead.',
|
||||
),
|
||||
True,
|
||||
[_THIRD_PARTY_EXCEPT_BLINK], # Not an error in third_party folders.
|
||||
),
|
||||
(
|
||||
r'/\bstd::ratio\b',
|
||||
(
|
||||
|
@ -14,6 +14,8 @@
|
||||
#include "chrome/test/chromedriver/chrome/ui_events.h"
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/events/keycodes/keyboard_code_conversion_x.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
namespace {
|
||||
@ -109,7 +111,8 @@ bool GetXModifierMask(Display* display,
|
||||
for (int mod_index = 0; mod_index <= 8; ++mod_index) {
|
||||
for (int key_index = 0; key_index < max_mod_keys; ++key_index) {
|
||||
int key = mod_map->modifiermap[mod_index * max_mod_keys + key_index];
|
||||
int keysym = XkbKeycodeToKeysym(display, key, 0, 0);
|
||||
int keysym =
|
||||
static_cast<int>(x11::Connection::Get()->KeycodeToKeysym(key, 0));
|
||||
if (modifier == kAltKeyModifierMask)
|
||||
found = keysym == XK_Alt_L || keysym == XK_Alt_R;
|
||||
else if (modifier == kMetaKeyModifierMask)
|
||||
|
@ -34,7 +34,10 @@
|
||||
#include "gpu/tools/compositor_model_bench/render_model_utils.h"
|
||||
#include "gpu/tools/compositor_model_bench/render_models.h"
|
||||
#include "gpu/tools/compositor_model_bench/render_tree.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
#include "ui/gl/init/gl_factory.h"
|
||||
|
||||
using base::TimeTicks;
|
||||
@ -123,19 +126,16 @@ class Simulator {
|
||||
|
||||
void ProcessEvents() {
|
||||
// Consume all the X events.
|
||||
while (XPending(display_)) {
|
||||
XEvent e;
|
||||
XNextEvent(display_, &e);
|
||||
switch (e.type) {
|
||||
case Expose:
|
||||
UpdateLoop();
|
||||
break;
|
||||
case ConfigureNotify:
|
||||
Resize(e.xconfigure.width, e.xconfigure.height);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
connection_->Flush();
|
||||
connection_->ReadResponses();
|
||||
auto& events = connection_->events();
|
||||
while (!events.empty()) {
|
||||
auto event = std::move(events.front());
|
||||
events.pop_front();
|
||||
if (event.As<x11::ExposeEvent>())
|
||||
UpdateLoop();
|
||||
else if (auto* configure = event.As<x11::ConfigureNotifyEvent>())
|
||||
Resize(configure->width, configure->height);
|
||||
}
|
||||
}
|
||||
|
||||
@ -148,26 +148,21 @@ class Simulator {
|
||||
// Initialize X11. Returns true if successful. This method creates the
|
||||
// X11 window. Further initialization is done in X11VideoRenderer.
|
||||
bool InitX11() {
|
||||
display_ = XOpenDisplay(nullptr);
|
||||
connection_ = std::make_unique<x11::Connection>();
|
||||
display_ = connection_->display();
|
||||
if (!display_) {
|
||||
LOG(FATAL) << "Cannot open display";
|
||||
return false;
|
||||
}
|
||||
|
||||
// Get properties of the screen.
|
||||
int screen = DefaultScreen(display_);
|
||||
int root_window = XRootWindow(display_, screen);
|
||||
int screen = XDefaultScreen(display_);
|
||||
int root_window = XDefaultRootWindow(display_);
|
||||
|
||||
// Creates the window.
|
||||
window_ = XCreateSimpleWindow(display_,
|
||||
root_window,
|
||||
1,
|
||||
1,
|
||||
window_width_,
|
||||
window_height_,
|
||||
0,
|
||||
BlackPixel(display_, screen),
|
||||
BlackPixel(display_, screen));
|
||||
window_ = XCreateSimpleWindow(
|
||||
display_, root_window, 1, 1, window_width_, window_height_, 0,
|
||||
XBlackPixel(display_, screen), XBlackPixel(display_, screen));
|
||||
XStoreName(display_, window_, "Compositor Model Bench");
|
||||
|
||||
XSelectInput(display_, window_,
|
||||
@ -191,9 +186,9 @@ class Simulator {
|
||||
XVisualInfo visual_info_template;
|
||||
visual_info_template.visualid = XVisualIDFromVisual(attributes.visual);
|
||||
int visual_info_count = 0;
|
||||
XVisualInfo* visual_info_list = XGetVisualInfo(display_, VisualIDMask,
|
||||
&visual_info_template,
|
||||
&visual_info_count);
|
||||
constexpr int kVisualIdMask = 1;
|
||||
XVisualInfo* visual_info_list = XGetVisualInfo(
|
||||
display_, kVisualIdMask, &visual_info_template, &visual_info_count);
|
||||
|
||||
for (int i = 0; i < visual_info_count && !gl_context_; ++i) {
|
||||
gl_context_ = glXCreateContext(display_, visual_info_list + i, 0,
|
||||
@ -246,10 +241,13 @@ class Simulator {
|
||||
|
||||
glXSwapBuffers(display_, window_);
|
||||
|
||||
XExposeEvent ev = { Expose, 0, 1, display_, window_,
|
||||
0, 0, WINDOW_WIDTH, WINDOW_HEIGHT, 0 };
|
||||
XSendEvent(display_, window_, x11::False, ExposureMask,
|
||||
reinterpret_cast<XEvent*>(&ev));
|
||||
auto window = static_cast<x11::Window>(window_);
|
||||
x11::ExposeEvent ev{
|
||||
.window = window,
|
||||
.width = WINDOW_WIDTH,
|
||||
.height = WINDOW_HEIGHT,
|
||||
};
|
||||
x11::SendEvent(ev, window, x11::EventMask::Exposure);
|
||||
|
||||
base::ThreadTaskRunnerHandle::Get()->PostTask(
|
||||
FROM_HERE,
|
||||
@ -334,6 +332,7 @@ class Simulator {
|
||||
// Amount of time to run each simulation
|
||||
int seconds_per_test_;
|
||||
// GUI data
|
||||
std::unique_ptr<x11::Connection> connection_;
|
||||
Display* display_;
|
||||
Window window_;
|
||||
GLXContext gl_context_;
|
||||
|
@ -8,10 +8,6 @@ import("//gpu/vulkan/features.gni")
|
||||
assert(enable_vulkan)
|
||||
assert(use_x11 || use_ozone)
|
||||
|
||||
config("vulkan_x11") {
|
||||
defines = [ "VK_USE_PLATFORM_XLIB_KHR" ]
|
||||
}
|
||||
|
||||
component("x") {
|
||||
output_name = "vulkan_x11"
|
||||
|
||||
@ -24,8 +20,6 @@ component("x") {
|
||||
|
||||
defines = [ "IS_VULKAN_X11_IMPL" ]
|
||||
|
||||
public_configs = [ ":vulkan_x11" ]
|
||||
|
||||
deps = [
|
||||
"//ui/base/x",
|
||||
"//ui/events/platform/x11",
|
||||
|
@ -18,6 +18,7 @@
|
||||
#include "gpu/vulkan/x/vulkan_surface_x11.h"
|
||||
#include "ui/gfx/gpu_fence.h"
|
||||
#include "ui/gfx/gpu_memory_buffer.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
|
||||
namespace gpu {
|
||||
@ -141,7 +142,7 @@ bool VulkanImplementationX11::GetPhysicalDevicePresentationSupport(
|
||||
XDisplay* display = gfx::GetXDisplay();
|
||||
return vkGetPhysicalDeviceXlibPresentationSupportKHR(
|
||||
device, queue_family_index, display,
|
||||
XVisualIDFromVisual(DefaultVisual(display, DefaultScreen(display))));
|
||||
XVisualIDFromVisual(XDefaultVisual(display, XDefaultScreen(display))));
|
||||
}
|
||||
|
||||
std::vector<const char*>
|
||||
|
@ -11,6 +11,7 @@
|
||||
#include "ui/gfx/native_widget_types.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
namespace gpu {
|
||||
|
||||
@ -124,7 +125,7 @@ bool VulkanSurfaceX11::CanDispatchXEvent(const x11::Event* x11_event) {
|
||||
void VulkanSurfaceX11::ForwardXExposeEvent(const x11::Event* event) {
|
||||
auto forwarded_event = *event->As<x11::ExposeEvent>();
|
||||
forwarded_event.window = parent_window_;
|
||||
ui::SendEvent(forwarded_event, parent_window_, x11::EventMask::Exposure);
|
||||
x11::SendEvent(forwarded_event, parent_window_, x11::EventMask::Exposure);
|
||||
x11::Connection::Get()->Flush();
|
||||
}
|
||||
|
||||
|
@ -179,7 +179,7 @@ void UserInputMonitorLinuxCore::StartMonitor() {
|
||||
// Register OnConnectionData() to be called every time there is something to
|
||||
// read from |connection_|.
|
||||
watch_controller_ = base::FileDescriptorWatcher::WatchReadable(
|
||||
ConnectionNumber(connection_->display()),
|
||||
XConnectionNumber(connection_->display()),
|
||||
base::BindRepeating(&UserInputMonitorLinuxCore::OnConnectionData,
|
||||
base::Unretained(this)));
|
||||
|
||||
|
@ -77,7 +77,7 @@ void ClipboardX11::Start(
|
||||
base::Unretained(this)));
|
||||
|
||||
x_connection_watch_controller_ = base::FileDescriptorWatcher::WatchReadable(
|
||||
ConnectionNumber(connection_->display()),
|
||||
XConnectionNumber(connection_->display()),
|
||||
base::BindRepeating(&ClipboardX11::PumpXEvents, base::Unretained(this)));
|
||||
PumpXEvents();
|
||||
}
|
||||
|
@ -29,8 +29,10 @@
|
||||
#include "third_party/webrtc/modules/desktop_capture/desktop_geometry.h"
|
||||
#include "ui/events/keycodes/dom/dom_code.h"
|
||||
#include "ui/events/keycodes/dom/keycode_converter.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xinput.h"
|
||||
#include "ui/gfx/x/xkb.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xtest.h"
|
||||
|
||||
@ -166,7 +168,7 @@ class InputInjectorX11 : public InputInjector {
|
||||
// X11 graphics context.
|
||||
x11::Connection connection_;
|
||||
Display* display_ = connection_.display();
|
||||
Window root_window_ = BadValue;
|
||||
Window root_window_ = x11::None;
|
||||
|
||||
// Number of buttons we support.
|
||||
// Left, Right, Middle, VScroll Up/Down, HScroll Left/Right, back, forward.
|
||||
@ -241,8 +243,8 @@ bool InputInjectorX11::Core::Init() {
|
||||
task_runner_->PostTask(FROM_HERE,
|
||||
base::BindOnce(&Core::InitClipboard, this));
|
||||
|
||||
root_window_ = XRootWindow(display_, DefaultScreen(display_));
|
||||
if (root_window_ == BadValue) {
|
||||
root_window_ = XDefaultRootWindow(display_);
|
||||
if (!root_window_) {
|
||||
LOG(ERROR) << "Unable to get the root window";
|
||||
return false;
|
||||
}
|
||||
@ -371,27 +373,27 @@ void InputInjectorX11::Core::InitClipboard() {
|
||||
}
|
||||
|
||||
bool InputInjectorX11::Core::IsAutoRepeatEnabled() {
|
||||
XKeyboardState state;
|
||||
if (!XGetKeyboardControl(display_, &state)) {
|
||||
LOG(ERROR) << "Failed to get keyboard auto-repeat status, assuming ON.";
|
||||
return true;
|
||||
}
|
||||
return state.global_auto_repeat == AutoRepeatModeOn;
|
||||
if (auto reply = connection_.GetKeyboardControl({}).Sync())
|
||||
return reply->global_auto_repeat == x11::AutoRepeatMode::On;
|
||||
LOG(ERROR) << "Failed to get keyboard auto-repeat status, assuming ON.";
|
||||
return true;
|
||||
}
|
||||
|
||||
void InputInjectorX11::Core::SetAutoRepeatEnabled(bool mode) {
|
||||
XKeyboardControl control;
|
||||
control.auto_repeat_mode = mode ? AutoRepeatModeOn : AutoRepeatModeOff;
|
||||
XChangeKeyboardControl(display_, KBAutoRepeatMode, &control);
|
||||
XFlush(display_);
|
||||
connection_.ChangeKeyboardControl(
|
||||
{.auto_repeat_mode =
|
||||
mode ? x11::AutoRepeatMode::On : x11::AutoRepeatMode::Off});
|
||||
connection_.Flush();
|
||||
}
|
||||
|
||||
bool InputInjectorX11::Core::IsLockKey(KeyCode keycode) {
|
||||
XkbStateRec state;
|
||||
auto state = connection_.xkb().GetState({}).Sync();
|
||||
if (!state)
|
||||
return false;
|
||||
auto mods = state->baseMods | state->latchedMods | state->lockedMods;
|
||||
KeySym keysym;
|
||||
if (XkbGetState(display_, XkbUseCoreKbd, &state) == x11::Success &&
|
||||
XkbLookupKeySym(display_, keycode, XkbStateMods(&state), nullptr,
|
||||
&keysym) == x11::True) {
|
||||
if (state && XkbLookupKeySym(display_, keycode, static_cast<unsigned>(mods),
|
||||
nullptr, &keysym) == x11::True) {
|
||||
return keysym == XK_Caps_Lock || keysym == XK_Num_Lock;
|
||||
} else {
|
||||
return false;
|
||||
@ -422,7 +424,8 @@ void InputInjectorX11::Core::SetLockStates(base::Optional<bool> caps_lock,
|
||||
}
|
||||
|
||||
if (update_mask) {
|
||||
XkbLockModifiers(display_, XkbUseCoreKbd, update_mask, lock_values);
|
||||
XkbLockModifiers(display_, static_cast<unsigned>(x11::Xkb::Id::UseCoreKbd),
|
||||
update_mask, lock_values);
|
||||
}
|
||||
}
|
||||
|
||||
@ -581,14 +584,12 @@ void InputInjectorX11::Core::InitMouseButtonMap() {
|
||||
// Instead, try to work around it by reversing the mapping.
|
||||
// Note that if a user has a global mapping that completely disables a button
|
||||
// (by assigning 0 to it), we won't be able to inject it.
|
||||
int num_buttons = XGetPointerMapping(display_, nullptr, 0);
|
||||
std::unique_ptr<unsigned char[]> pointer_mapping(
|
||||
new unsigned char[num_buttons]);
|
||||
num_buttons =
|
||||
XGetPointerMapping(display_, pointer_mapping.get(), num_buttons);
|
||||
std::vector<uint8_t> pointer_mapping;
|
||||
if (auto reply = connection_.GetPointerMapping({}).Sync())
|
||||
pointer_mapping = std::move(reply->map);
|
||||
for (int& i : pointer_button_map_)
|
||||
i = -1;
|
||||
for (int i = 0; i < num_buttons; i++) {
|
||||
for (size_t i = 0; i < pointer_mapping.size(); i++) {
|
||||
// Reverse the mapping.
|
||||
if (pointer_mapping[i] > 0 && pointer_mapping[i] <= kNumPointerButtons)
|
||||
pointer_button_map_[pointer_mapping[i] - 1] = i + 1;
|
||||
|
@ -20,6 +20,7 @@
|
||||
#include "base/single_thread_task_runner.h"
|
||||
#include "ui/events/devices/x11/xinput_util.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xinput.h"
|
||||
|
||||
@ -161,7 +162,7 @@ void LocalHotkeyInputMonitorX11::Core::StartOnInputThread() {
|
||||
// Register OnConnectionData() to be called every time there is
|
||||
// something to read from |connection_|.
|
||||
controller_ = base::FileDescriptorWatcher::WatchReadable(
|
||||
ConnectionNumber(connection_->display()),
|
||||
XConnectionNumber(connection_->display()),
|
||||
base::BindRepeating(&Core::OnConnectionData, base::Unretained(this)));
|
||||
|
||||
// Fetch pending events if any.
|
||||
|
@ -156,7 +156,7 @@ void LocalMouseInputMonitorX11::Core::StartOnInputThread() {
|
||||
// Register OnConnectionData() to be called every time there is
|
||||
// something to read from |connection_|.
|
||||
controller_ = base::FileDescriptorWatcher::WatchReadable(
|
||||
ConnectionNumber(connection_->display()),
|
||||
XConnectionNumber(connection_->display()),
|
||||
base::BindRepeating(&Core::OnConnectionData, base::Unretained(this)));
|
||||
|
||||
// Fetch pending events if any.
|
||||
|
@ -8,6 +8,7 @@
|
||||
|
||||
#include "base/bind.h"
|
||||
#include "base/callback.h"
|
||||
#include "base/files/file_descriptor_watcher_posix.h"
|
||||
#include "base/logging.h"
|
||||
#include "base/memory/weak_ptr.h"
|
||||
#include "base/optional.h"
|
||||
@ -40,32 +41,31 @@ class GtkThreadDeleter {
|
||||
|
||||
// Can be constructed on any thread, but must be started and destroyed on the
|
||||
// main GTK+ thread (i.e., the GLib global default main context).
|
||||
class GdkLayoutMonitorOnGtkThread {
|
||||
class GdkLayoutMonitorOnGtkThread : public x11::Connection::Delegate {
|
||||
public:
|
||||
GdkLayoutMonitorOnGtkThread(
|
||||
scoped_refptr<base::SequencedTaskRunner> task_runner,
|
||||
base::WeakPtr<KeyboardLayoutMonitorLinux> weak_ptr);
|
||||
|
||||
// Must be called on GTK Thread
|
||||
~GdkLayoutMonitorOnGtkThread();
|
||||
~GdkLayoutMonitorOnGtkThread() override;
|
||||
void Start();
|
||||
|
||||
private:
|
||||
// x11::Connection::Delegate:
|
||||
bool ShouldContinueStream() const override;
|
||||
void DispatchXEvent(x11::Event* event) override;
|
||||
|
||||
void QueryLayout();
|
||||
static GdkFilterReturn OnXEventThunk(GdkXEvent* xevent,
|
||||
GdkEvent* event,
|
||||
gpointer data);
|
||||
GdkFilterReturn OnXEvent(XEvent* xevent, GdkEvent* event);
|
||||
void OnConnectionData();
|
||||
CHROMEG_CALLBACK_0(GdkLayoutMonitorOnGtkThread,
|
||||
void,
|
||||
OnKeysChanged,
|
||||
GdkKeymap*);
|
||||
scoped_refptr<base::SequencedTaskRunner> task_runner_;
|
||||
base::WeakPtr<KeyboardLayoutMonitorLinux> weak_ptr_;
|
||||
// xkb_event_type_ is initialized in Start(). It is only used by OnXEvent,
|
||||
// which is only registered as a callback after xkb_event_type_ has been
|
||||
// initialized.
|
||||
int xkb_event_type_;
|
||||
std::unique_ptr<x11::Connection> connection_;
|
||||
std::unique_ptr<base::FileDescriptorWatcher::Controller> controller_;
|
||||
GdkDisplay* display_ = nullptr;
|
||||
GdkKeymap* keymap_ = nullptr;
|
||||
int current_group_ = 0;
|
||||
@ -119,10 +119,8 @@ GdkLayoutMonitorOnGtkThread::GdkLayoutMonitorOnGtkThread(
|
||||
|
||||
GdkLayoutMonitorOnGtkThread::~GdkLayoutMonitorOnGtkThread() {
|
||||
DCHECK(g_main_context_is_owner(g_main_context_default()));
|
||||
if (handler_id_) {
|
||||
if (handler_id_)
|
||||
g_signal_handler_disconnect(keymap_, handler_id_);
|
||||
gdk_window_remove_filter(nullptr, OnXEventThunk, this);
|
||||
}
|
||||
}
|
||||
|
||||
void GdkLayoutMonitorOnGtkThread::Start() {
|
||||
@ -144,16 +142,28 @@ void GdkLayoutMonitorOnGtkThread::Start() {
|
||||
// when switching between groups with different writing directions. As a
|
||||
// result, we have to use Xkb directly to get and monitor that information,
|
||||
// which is a pain.
|
||||
auto* connection = x11::Connection::Get();
|
||||
if (connection->xkb()
|
||||
.UseExtension({x11::Xkb::major_version, x11::Xkb::minor_version})
|
||||
connection_ = std::make_unique<x11::Connection>();
|
||||
auto& xkb = connection_->xkb();
|
||||
if (xkb.UseExtension({x11::Xkb::major_version, x11::Xkb::minor_version})
|
||||
.Sync()) {
|
||||
xkb_event_type_ = connection->xkb().first_event();
|
||||
auto req = connection->xkb().GetState(
|
||||
auto req = xkb.GetState(
|
||||
{static_cast<x11::Xkb::DeviceSpec>(x11::Xkb::Id::UseCoreKbd)});
|
||||
if (auto reply = req.Sync()) {
|
||||
current_group_ = static_cast<int>(reply->group);
|
||||
gdk_window_add_filter(nullptr, OnXEventThunk, this);
|
||||
constexpr auto kXkbAllStateComponentsMask =
|
||||
static_cast<x11::Xkb::StatePart>(0x3fff);
|
||||
xkb.SelectEvents({
|
||||
.deviceSpec =
|
||||
static_cast<x11::Xkb::DeviceSpec>(x11::Xkb::Id::UseCoreKbd),
|
||||
.affectWhich = x11::Xkb::EventType::StateNotify,
|
||||
.affectState = kXkbAllStateComponentsMask,
|
||||
.stateDetails = x11::Xkb::StatePart::GroupState,
|
||||
});
|
||||
connection_->Flush();
|
||||
controller_ = base::FileDescriptorWatcher::WatchReadable(
|
||||
XConnectionNumber(connection_->display()),
|
||||
base::BindRepeating(&GdkLayoutMonitorOnGtkThread::OnConnectionData,
|
||||
base::Unretained(this)));
|
||||
}
|
||||
}
|
||||
|
||||
@ -163,6 +173,21 @@ void GdkLayoutMonitorOnGtkThread::Start() {
|
||||
QueryLayout();
|
||||
}
|
||||
|
||||
bool GdkLayoutMonitorOnGtkThread::ShouldContinueStream() const {
|
||||
return true;
|
||||
}
|
||||
|
||||
void GdkLayoutMonitorOnGtkThread::DispatchXEvent(x11::Event* event) {
|
||||
if (auto* notify = event->As<x11::Xkb::StateNotifyEvent>()) {
|
||||
int new_group = notify->baseGroup + notify->latchedGroup +
|
||||
static_cast<int16_t>(notify->lockedGroup);
|
||||
if (new_group != current_group_) {
|
||||
current_group_ = new_group;
|
||||
QueryLayout();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void GdkLayoutMonitorOnGtkThread::QueryLayout() {
|
||||
protocol::KeyboardLayout layout_message;
|
||||
|
||||
@ -272,30 +297,8 @@ void GdkLayoutMonitorOnGtkThread::QueryLayout() {
|
||||
weak_ptr_, std::move(layout_message)));
|
||||
}
|
||||
|
||||
// static
|
||||
GdkFilterReturn GdkLayoutMonitorOnGtkThread::OnXEventThunk(GdkXEvent* xevent,
|
||||
GdkEvent* event,
|
||||
gpointer data) {
|
||||
// GdkXEvent is documented to be castable to the window-system event type
|
||||
// XEvent in this case.
|
||||
return static_cast<GdkLayoutMonitorOnGtkThread*>(data)->OnXEvent(
|
||||
static_cast<XEvent*>(xevent), event);
|
||||
}
|
||||
|
||||
GdkFilterReturn GdkLayoutMonitorOnGtkThread::OnXEvent(XEvent* xevent,
|
||||
GdkEvent* event) {
|
||||
if (xevent->type == xkb_event_type_) {
|
||||
XkbEvent* xkb_event = reinterpret_cast<XkbEvent*>(xevent);
|
||||
if (xkb_event->any.xkb_type == XkbStateNotify) {
|
||||
int new_group = XkbStateGroup(&xkb_event->state);
|
||||
if (new_group != current_group_) {
|
||||
current_group_ = new_group;
|
||||
QueryLayout();
|
||||
}
|
||||
}
|
||||
}
|
||||
// GDK also needs to process this event.
|
||||
return GDK_FILTER_CONTINUE;
|
||||
void GdkLayoutMonitorOnGtkThread::OnConnectionData() {
|
||||
connection_->Dispatch(this);
|
||||
}
|
||||
|
||||
void GdkLayoutMonitorOnGtkThread::OnKeysChanged(GdkKeymap* keymap) {
|
||||
|
@ -7,6 +7,7 @@
|
||||
#include <algorithm>
|
||||
|
||||
#include "base/stl_util.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
namespace remoting {
|
||||
|
@ -9,6 +9,7 @@
|
||||
#include "remoting/host/linux/unicode_to_keysym.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
#include "ui/gfx/x/xkb.h"
|
||||
#include "ui/gfx/x/xtest.h"
|
||||
|
||||
namespace {
|
||||
@ -80,12 +81,14 @@ std::vector<uint32_t> X11KeyboardImpl::GetUnusedKeycodes() {
|
||||
}
|
||||
|
||||
void X11KeyboardImpl::PressKey(uint32_t keycode, uint32_t modifiers) {
|
||||
XkbLockModifiers(display_, XkbUseCoreKbd, modifiers, modifiers);
|
||||
XkbLockModifiers(display_, static_cast<unsigned>(x11::Xkb::Id::UseCoreKbd),
|
||||
modifiers, modifiers);
|
||||
|
||||
connection_->xtest().FakeInput({x11::KeyEvent::Press, keycode});
|
||||
connection_->xtest().FakeInput({x11::KeyEvent::Release, keycode});
|
||||
|
||||
XkbLockModifiers(display_, XkbUseCoreKbd, modifiers, 0);
|
||||
XkbLockModifiers(display_, static_cast<unsigned>(x11::Xkb::Id::UseCoreKbd),
|
||||
modifiers, 0);
|
||||
}
|
||||
|
||||
bool X11KeyboardImpl::FindKeycode(uint32_t code_point,
|
||||
|
@ -12,11 +12,12 @@
|
||||
#include "ui/gfx/x/extension_manager.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
namespace remoting {
|
||||
|
||||
XServerClipboard::XServerClipboard()
|
||||
: clipboard_window_(BadValue),
|
||||
: clipboard_window_(x11::None),
|
||||
clipboard_atom_(x11::None),
|
||||
large_selection_atom_(x11::None),
|
||||
selection_string_atom_(x11::None),
|
||||
@ -52,7 +53,7 @@ void XServerClipboard::Init(x11::Connection* connection,
|
||||
|
||||
clipboard_window_ =
|
||||
XCreateSimpleWindow(connection_->display(),
|
||||
DefaultRootWindow(connection_->display()), 0, 0, 1,
|
||||
XDefaultRootWindow(connection_->display()), 0, 0, 1,
|
||||
1, // x, y, width, height
|
||||
0, 0, 0);
|
||||
|
||||
@ -88,7 +89,7 @@ void XServerClipboard::SetClipboard(const std::string& mime_type,
|
||||
const std::string& data) {
|
||||
DCHECK(connection_->display());
|
||||
|
||||
if (clipboard_window_ == BadValue)
|
||||
if (clipboard_window_ == x11::None)
|
||||
return;
|
||||
|
||||
// Currently only UTF-8 is supported.
|
||||
@ -106,7 +107,7 @@ void XServerClipboard::SetClipboard(const std::string& mime_type,
|
||||
}
|
||||
|
||||
void XServerClipboard::ProcessXEvent(const x11::Event& event) {
|
||||
if (clipboard_window_ == BadValue ||
|
||||
if (clipboard_window_ == x11::None ||
|
||||
event.window() != static_cast<x11::Window>(clipboard_window_)) {
|
||||
return;
|
||||
}
|
||||
@ -211,33 +212,34 @@ void XServerClipboard::OnSelectionNotify(
|
||||
|
||||
void XServerClipboard::OnSelectionRequest(
|
||||
const x11::SelectionRequestEvent& event) {
|
||||
XSelectionEvent selection_event;
|
||||
selection_event.type = SelectionNotify;
|
||||
selection_event.display = connection_->display();
|
||||
selection_event.requestor = static_cast<uint32_t>(event.requestor);
|
||||
selection_event.selection = static_cast<uint32_t>(event.selection);
|
||||
selection_event.time = static_cast<uint32_t>(event.time);
|
||||
selection_event.target = static_cast<uint32_t>(event.target);
|
||||
x11::SelectionNotifyEvent selection_event;
|
||||
selection_event.requestor = event.requestor;
|
||||
selection_event.selection = event.selection;
|
||||
selection_event.time = event.time;
|
||||
selection_event.target = event.target;
|
||||
auto property =
|
||||
event.property == x11::Atom::None ? event.target : event.property;
|
||||
if (!IsSelectionOwner(selection_event.selection)) {
|
||||
selection_event.property = x11::None;
|
||||
if (!IsSelectionOwner(static_cast<uint32_t>(selection_event.selection))) {
|
||||
selection_event.property = x11::Atom::None;
|
||||
} else {
|
||||
selection_event.property = static_cast<uint32_t>(property);
|
||||
if (selection_event.target == targets_atom_) {
|
||||
SendTargetsResponse(selection_event.requestor, selection_event.property);
|
||||
} else if (selection_event.target == timestamp_atom_) {
|
||||
SendTimestampResponse(selection_event.requestor,
|
||||
selection_event.property);
|
||||
} else if (selection_event.target == utf8_string_atom_ ||
|
||||
selection_event.target ==
|
||||
static_cast<uint32_t>(x11::Atom::STRING)) {
|
||||
SendStringResponse(selection_event.requestor, selection_event.property,
|
||||
selection_event.target);
|
||||
selection_event.property = property;
|
||||
if (selection_event.target == static_cast<x11::Atom>(targets_atom_)) {
|
||||
SendTargetsResponse(static_cast<uint32_t>(selection_event.requestor),
|
||||
static_cast<uint32_t>(selection_event.property));
|
||||
} else if (selection_event.target ==
|
||||
static_cast<x11::Atom>(timestamp_atom_)) {
|
||||
SendTimestampResponse(static_cast<uint32_t>(selection_event.requestor),
|
||||
static_cast<uint32_t>(selection_event.property));
|
||||
} else if (selection_event.target ==
|
||||
static_cast<x11::Atom>(utf8_string_atom_) ||
|
||||
selection_event.target == x11::Atom::STRING) {
|
||||
SendStringResponse(static_cast<uint32_t>(selection_event.requestor),
|
||||
static_cast<uint32_t>(selection_event.property),
|
||||
static_cast<uint32_t>(selection_event.target));
|
||||
}
|
||||
}
|
||||
XSendEvent(connection_->display(), selection_event.requestor, x11::False, 0,
|
||||
reinterpret_cast<XEvent*>(&selection_event));
|
||||
x11::SendEvent(selection_event, selection_event.requestor,
|
||||
x11::EventMask::NoEvent, connection_);
|
||||
}
|
||||
|
||||
void XServerClipboard::OnSelectionClear(const x11::SelectionClearEvent& event) {
|
||||
|
6
third_party/khronos/EGL/eglplatform.h
vendored
6
third_party/khronos/EGL/eglplatform.h
vendored
@ -102,8 +102,10 @@ typedef intptr_t EGLNativePixmapType;
|
||||
#elif defined(__unix__)
|
||||
|
||||
/* X11 (tentative) */
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/Xutil.h>
|
||||
typedef unsigned long XID;
|
||||
typedef XID Pixmap;
|
||||
typedef XID Window;
|
||||
typedef struct _XDisplay Display;
|
||||
|
||||
typedef Display *EGLNativeDisplayType;
|
||||
typedef Pixmap EGLNativePixmapType;
|
||||
|
1
third_party/khronos/README.chromium
vendored
1
third_party/khronos/README.chromium
vendored
@ -32,6 +32,7 @@ GLES2/gl2ext.h
|
||||
EGL/eglplatform.h
|
||||
- Added EGLNative*Type for Mac.
|
||||
- Added EGLNative*Type for native linux framebuffers.
|
||||
- Forward declare Xlib types instead of including Xlib headers.
|
||||
EGL/eglext.h
|
||||
- Added support for EGL_EXT_image_flush_external extension
|
||||
- Added support for EGL_ANGLE_stream_producer_d3d_texture
|
||||
|
88
third_party/xcbproto/patch.diff
vendored
88
third_party/xcbproto/patch.diff
vendored
@ -1,6 +1,71 @@
|
||||
diff -ru xcbproto/src/glx.xml src/src/glx.xml
|
||||
--- xcbproto/src/glx.xml 2020-09-04 10:01:19.893846873 -0700
|
||||
+++ src/src/glx.xml 2020-09-04 10:00:42.997648219 -0700
|
||||
@@ -214,27 +214,27 @@
|
||||
|
||||
<!-- Enum for CopyContext: mask -->
|
||||
<enum name="GC">
|
||||
- <item name="GL_CURRENT_BIT"><bit>0</bit></item>
|
||||
- <item name="GL_POINT_BIT"><bit>1</bit></item>
|
||||
- <item name="GL_LINE_BIT"><bit>2</bit></item>
|
||||
- <item name="GL_POLYGON_BIT"><bit>3</bit></item>
|
||||
- <item name="GL_POLYGON_STIPPLE_BIT"><bit>4</bit></item>
|
||||
- <item name="GL_PIXEL_MODE_BIT"><bit>5</bit></item>
|
||||
- <item name="GL_LIGHTING_BIT"><bit>6</bit></item>
|
||||
- <item name="GL_FOG_BIT"><bit>7</bit></item>
|
||||
- <item name="GL_DEPTH_BUFFER_BIT"><bit>8</bit></item>
|
||||
- <item name="GL_ACCUM_BUFFER_BIT"><bit>9</bit></item>
|
||||
- <item name="GL_STENCIL_BUFFER_BIT"><bit>10</bit></item>
|
||||
- <item name="GL_VIEWPORT_BIT"><bit>11</bit></item>
|
||||
- <item name="GL_TRANSFORM_BIT"><bit>12</bit></item>
|
||||
- <item name="GL_ENABLE_BIT"><bit>13</bit></item>
|
||||
- <item name="GL_COLOR_BUFFER_BIT"><bit>14</bit></item>
|
||||
- <item name="GL_HINT_BIT"><bit>15</bit></item>
|
||||
- <item name="GL_EVAL_BIT"><bit>16</bit></item>
|
||||
- <item name="GL_LIST_BIT"><bit>17</bit></item>
|
||||
- <item name="GL_TEXTURE_BIT"><bit>18</bit></item>
|
||||
- <item name="GL_SCISSOR_BIT"><bit>19</bit></item>
|
||||
- <item name="GL_ALL_ATTRIB_BITS"><value>16777215<!--0x000ffffff--></value></item>
|
||||
+ <item name="XPROTO_GL_CURRENT_BIT"><bit>0</bit></item>
|
||||
+ <item name="XPROTO_GL_POINT_BIT"><bit>1</bit></item>
|
||||
+ <item name="XPROTO_GL_LINE_BIT"><bit>2</bit></item>
|
||||
+ <item name="XPROTO_GL_POLYGON_BIT"><bit>3</bit></item>
|
||||
+ <item name="XPROTO_GL_POLYGON_STIPPLE_BIT"><bit>4</bit></item>
|
||||
+ <item name="XPROTO_GL_PIXEL_MODE_BIT"><bit>5</bit></item>
|
||||
+ <item name="XPROTO_GL_LIGHTING_BIT"><bit>6</bit></item>
|
||||
+ <item name="XPROTO_GL_FOG_BIT"><bit>7</bit></item>
|
||||
+ <item name="XPROTO_GL_DEPTH_BUFFER_BIT"><bit>8</bit></item>
|
||||
+ <item name="XPROTO_GL_ACCUM_BUFFER_BIT"><bit>9</bit></item>
|
||||
+ <item name="XPROTO_GL_STENCIL_BUFFER_BIT"><bit>10</bit></item>
|
||||
+ <item name="XPROTO_GL_VIEWPORT_BIT"><bit>11</bit></item>
|
||||
+ <item name="XPROTO_GL_TRANSFORM_BIT"><bit>12</bit></item>
|
||||
+ <item name="XPROTO_GL_ENABLE_BIT"><bit>13</bit></item>
|
||||
+ <item name="XPROTO_GL_COLOR_BUFFER_BIT"><bit>14</bit></item>
|
||||
+ <item name="XPROTO_GL_HINT_BIT"><bit>15</bit></item>
|
||||
+ <item name="XPROTO_GL_EVAL_BIT"><bit>16</bit></item>
|
||||
+ <item name="XPROTO_GL_LIST_BIT"><bit>17</bit></item>
|
||||
+ <item name="XPROTO_GL_TEXTURE_BIT"><bit>18</bit></item>
|
||||
+ <item name="XPROTO_GL_SCISSOR_BIT"><bit>19</bit></item>
|
||||
+ <item name="XPROTO_GL_ALL_ATTRIB_BITS"><value>16777215<!--0x000ffffff--></value></item>
|
||||
</enum>
|
||||
|
||||
<request name="SwapBuffers" opcode="11">
|
||||
@@ -594,9 +594,9 @@
|
||||
</request>
|
||||
|
||||
<enum name="RM">
|
||||
- <item name="GL_RENDER"><value>7168</value></item>
|
||||
- <item name="GL_FEEDBACK"><value>7169</value></item>
|
||||
- <item name="GL_SELECT"><value>7170</value></item>
|
||||
+ <item name="XPROTO_GL_RENDER"><value>7168</value></item>
|
||||
+ <item name="XPROTO_GL_FEEDBACK"><value>7169</value></item>
|
||||
+ <item name="XPROTO_GL_SELECT"><value>7170</value></item>
|
||||
</enum>
|
||||
|
||||
<request name="Finish" opcode="108">
|
||||
diff -ru xcbproto/src/randr.xml src/src/randr.xml
|
||||
--- xcbproto/src/randr.xml 2020-08-13 11:56:17.249075684 -0700
|
||||
+++ src/src/randr.xml 2020-08-03 10:33:29.428868544 -0700
|
||||
--- xcbproto/src/randr.xml 2020-09-04 10:01:19.893846873 -0700
|
||||
+++ src/src/randr.xml 2020-07-07 18:37:12.793121218 -0700
|
||||
@@ -803,64 +803,6 @@
|
||||
<item name="Lease"> <value>6</value></item>
|
||||
</enum>
|
||||
@ -174,8 +239,8 @@ diff -ru xcbproto/src/randr.xml src/src/randr.xml
|
||||
</event>
|
||||
</xcb>
|
||||
diff -ru xcbproto/src/shm.xml src/src/shm.xml
|
||||
--- xcbproto/src/shm.xml 2020-08-13 11:56:17.253075706 -0700
|
||||
+++ src/src/shm.xml 2020-08-13 11:54:58.612654139 -0700
|
||||
--- xcbproto/src/shm.xml 2020-09-04 10:01:19.897846895 -0700
|
||||
+++ src/src/shm.xml 2020-08-24 11:14:24.865499307 -0700
|
||||
@@ -78,7 +78,7 @@
|
||||
<field type="INT16" name="dst_x" />
|
||||
<field type="INT16" name="dst_y" />
|
||||
@ -186,8 +251,8 @@ diff -ru xcbproto/src/shm.xml src/src/shm.xml
|
||||
<pad bytes="1" />
|
||||
<field type="SEG" name="shmseg" />
|
||||
diff -ru xcbproto/src/xinput.xml src/src/xinput.xml
|
||||
--- xcbproto/src/xinput.xml 2020-08-13 11:56:17.253075706 -0700
|
||||
+++ src/src/xinput.xml 2020-08-13 11:15:42.336096659 -0700
|
||||
--- xcbproto/src/xinput.xml 2020-09-04 10:01:19.897846895 -0700
|
||||
+++ src/src/xinput.xml 2020-08-24 11:14:24.865499307 -0700
|
||||
@@ -200,7 +200,12 @@
|
||||
<list type="STR" name="names">
|
||||
<fieldref>devices_len</fieldref>
|
||||
@ -213,8 +278,8 @@ diff -ru xcbproto/src/xinput.xml src/src/xinput.xml
|
||||
<item name="AllMaster"> <value>1</value> </item>
|
||||
</enum>
|
||||
diff -ru xcbproto/src/xproto.xml src/src/xproto.xml
|
||||
--- xcbproto/src/xproto.xml 2020-08-13 11:56:17.253075706 -0700
|
||||
+++ src/src/xproto.xml 2020-08-03 10:33:29.428868544 -0700
|
||||
--- xcbproto/src/xproto.xml 2020-09-04 10:01:19.897846895 -0700
|
||||
+++ src/src/xproto.xml 2020-07-30 12:03:48.681938397 -0700
|
||||
@@ -4686,7 +4686,7 @@
|
||||
<field type="CARD8" name="left_pad" />
|
||||
<field type="CARD8" name="depth" />
|
||||
@ -233,3 +298,10 @@ diff -ru xcbproto/src/xproto.xml src/src/xproto.xml
|
||||
<op op="*">
|
||||
<fieldref>length</fieldref>
|
||||
<value>4</value>
|
||||
Only in src/xcbgen: align.pyc
|
||||
Only in src/xcbgen: error.pyc
|
||||
Only in src/xcbgen: expr.pyc
|
||||
Only in src/xcbgen: __init__.pyc
|
||||
Only in src/xcbgen: matcher.pyc
|
||||
Only in src/xcbgen: state.pyc
|
||||
Only in src/xcbgen: xtypes.pyc
|
||||
|
48
third_party/xcbproto/src/src/glx.xml
vendored
48
third_party/xcbproto/src/src/glx.xml
vendored
@ -214,27 +214,27 @@ The patch that fixed this server bug in X.org CVS is here:
|
||||
|
||||
<!-- Enum for CopyContext: mask -->
|
||||
<enum name="GC">
|
||||
<item name="GL_CURRENT_BIT"><bit>0</bit></item>
|
||||
<item name="GL_POINT_BIT"><bit>1</bit></item>
|
||||
<item name="GL_LINE_BIT"><bit>2</bit></item>
|
||||
<item name="GL_POLYGON_BIT"><bit>3</bit></item>
|
||||
<item name="GL_POLYGON_STIPPLE_BIT"><bit>4</bit></item>
|
||||
<item name="GL_PIXEL_MODE_BIT"><bit>5</bit></item>
|
||||
<item name="GL_LIGHTING_BIT"><bit>6</bit></item>
|
||||
<item name="GL_FOG_BIT"><bit>7</bit></item>
|
||||
<item name="GL_DEPTH_BUFFER_BIT"><bit>8</bit></item>
|
||||
<item name="GL_ACCUM_BUFFER_BIT"><bit>9</bit></item>
|
||||
<item name="GL_STENCIL_BUFFER_BIT"><bit>10</bit></item>
|
||||
<item name="GL_VIEWPORT_BIT"><bit>11</bit></item>
|
||||
<item name="GL_TRANSFORM_BIT"><bit>12</bit></item>
|
||||
<item name="GL_ENABLE_BIT"><bit>13</bit></item>
|
||||
<item name="GL_COLOR_BUFFER_BIT"><bit>14</bit></item>
|
||||
<item name="GL_HINT_BIT"><bit>15</bit></item>
|
||||
<item name="GL_EVAL_BIT"><bit>16</bit></item>
|
||||
<item name="GL_LIST_BIT"><bit>17</bit></item>
|
||||
<item name="GL_TEXTURE_BIT"><bit>18</bit></item>
|
||||
<item name="GL_SCISSOR_BIT"><bit>19</bit></item>
|
||||
<item name="GL_ALL_ATTRIB_BITS"><value>16777215<!--0x000ffffff--></value></item>
|
||||
<item name="XPROTO_GL_CURRENT_BIT"><bit>0</bit></item>
|
||||
<item name="XPROTO_GL_POINT_BIT"><bit>1</bit></item>
|
||||
<item name="XPROTO_GL_LINE_BIT"><bit>2</bit></item>
|
||||
<item name="XPROTO_GL_POLYGON_BIT"><bit>3</bit></item>
|
||||
<item name="XPROTO_GL_POLYGON_STIPPLE_BIT"><bit>4</bit></item>
|
||||
<item name="XPROTO_GL_PIXEL_MODE_BIT"><bit>5</bit></item>
|
||||
<item name="XPROTO_GL_LIGHTING_BIT"><bit>6</bit></item>
|
||||
<item name="XPROTO_GL_FOG_BIT"><bit>7</bit></item>
|
||||
<item name="XPROTO_GL_DEPTH_BUFFER_BIT"><bit>8</bit></item>
|
||||
<item name="XPROTO_GL_ACCUM_BUFFER_BIT"><bit>9</bit></item>
|
||||
<item name="XPROTO_GL_STENCIL_BUFFER_BIT"><bit>10</bit></item>
|
||||
<item name="XPROTO_GL_VIEWPORT_BIT"><bit>11</bit></item>
|
||||
<item name="XPROTO_GL_TRANSFORM_BIT"><bit>12</bit></item>
|
||||
<item name="XPROTO_GL_ENABLE_BIT"><bit>13</bit></item>
|
||||
<item name="XPROTO_GL_COLOR_BUFFER_BIT"><bit>14</bit></item>
|
||||
<item name="XPROTO_GL_HINT_BIT"><bit>15</bit></item>
|
||||
<item name="XPROTO_GL_EVAL_BIT"><bit>16</bit></item>
|
||||
<item name="XPROTO_GL_LIST_BIT"><bit>17</bit></item>
|
||||
<item name="XPROTO_GL_TEXTURE_BIT"><bit>18</bit></item>
|
||||
<item name="XPROTO_GL_SCISSOR_BIT"><bit>19</bit></item>
|
||||
<item name="XPROTO_GL_ALL_ATTRIB_BITS"><value>16777215<!--0x000ffffff--></value></item>
|
||||
</enum>
|
||||
|
||||
<request name="SwapBuffers" opcode="11">
|
||||
@ -594,9 +594,9 @@ The patch that fixed this server bug in X.org CVS is here:
|
||||
</request>
|
||||
|
||||
<enum name="RM">
|
||||
<item name="GL_RENDER"><value>7168</value></item>
|
||||
<item name="GL_FEEDBACK"><value>7169</value></item>
|
||||
<item name="GL_SELECT"><value>7170</value></item>
|
||||
<item name="XPROTO_GL_RENDER"><value>7168</value></item>
|
||||
<item name="XPROTO_GL_FEEDBACK"><value>7169</value></item>
|
||||
<item name="XPROTO_GL_SELECT"><value>7170</value></item>
|
||||
</enum>
|
||||
|
||||
<request name="Finish" opcode="108">
|
||||
|
@ -255,7 +255,6 @@ static_library("test_support") {
|
||||
sources += [
|
||||
"test/ui_controls_aurax11.cc",
|
||||
"test/ui_controls_aurax11.h",
|
||||
"test/x11_event_sender.cc",
|
||||
"test/x11_event_sender.h",
|
||||
]
|
||||
|
||||
|
@ -4,6 +4,10 @@
|
||||
|
||||
#include "ui/aura/test/ui_controls_aurax11.h"
|
||||
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
|
||||
namespace aura {
|
||||
namespace test {
|
||||
namespace {
|
||||
@ -42,9 +46,9 @@ bool UIControlsX11::SendKeyPressNotifyWhenDone(gfx::NativeWindow window,
|
||||
bool alt,
|
||||
bool command,
|
||||
base::OnceClosure closure) {
|
||||
XEvent xevent;
|
||||
xevent.xkey = {};
|
||||
xevent.xkey.type = x11::KeyEvent::Press;
|
||||
x11::KeyEvent xevent;
|
||||
xevent.detail = {};
|
||||
xevent.opcode = x11::KeyEvent::Press;
|
||||
if (control)
|
||||
SetKeycodeAndSendThenMask(&xevent, XK_Control_L, ControlMask);
|
||||
if (shift)
|
||||
@ -53,13 +57,13 @@ bool UIControlsX11::SendKeyPressNotifyWhenDone(gfx::NativeWindow window,
|
||||
SetKeycodeAndSendThenMask(&xevent, XK_Alt_L, Mod1Mask);
|
||||
if (command)
|
||||
SetKeycodeAndSendThenMask(&xevent, XK_Meta_L, Mod4Mask);
|
||||
xevent.xkey.keycode = XKeysymToKeycode(
|
||||
gfx::GetXDisplay(), ui::XKeysymForWindowsKeyCode(key, shift));
|
||||
PostEventToWindowTreeHost(xevent, host_);
|
||||
xevent.detail = x11::Connection::Get()->KeysymToKeycode(
|
||||
static_cast<x11::KeySym>(ui::XKeysymForWindowsKeyCode(key, shift)));
|
||||
PostEventToWindowTreeHost(host_, &xevent);
|
||||
|
||||
// Send key release events.
|
||||
xevent.xkey.type = x11::KeyEvent::Release;
|
||||
PostEventToWindowTreeHost(xevent, host_);
|
||||
xevent.opcode = x11::KeyEvent::Release;
|
||||
PostEventToWindowTreeHost(host_, &xevent);
|
||||
if (alt)
|
||||
UnmaskAndSetKeycodeThenSend(&xevent, Mod1Mask, XK_Alt_L);
|
||||
if (shift)
|
||||
@ -68,7 +72,7 @@ bool UIControlsX11::SendKeyPressNotifyWhenDone(gfx::NativeWindow window,
|
||||
UnmaskAndSetKeycodeThenSend(&xevent, ControlMask, XK_Control_L);
|
||||
if (command)
|
||||
UnmaskAndSetKeycodeThenSend(&xevent, Mod4Mask, XK_Meta_L);
|
||||
DCHECK(!xevent.xkey.state);
|
||||
DCHECK_EQ(xevent.state, x11::KeyButMask{});
|
||||
RunClosureAfterAllPendingUIEvents(std::move(closure));
|
||||
return true;
|
||||
}
|
||||
@ -96,16 +100,14 @@ bool UIControlsX11::SendMouseMoveNotifyWhenDone(int screen_x,
|
||||
// current mouse position as a result of XGrabPointer()
|
||||
host_->window()->MoveCursorTo(root_location);
|
||||
} else {
|
||||
XEvent xevent;
|
||||
xevent.xmotion = {};
|
||||
XMotionEvent* xmotion = &xevent.xmotion;
|
||||
xmotion->type = MotionNotify;
|
||||
xmotion->x = root_location.x();
|
||||
xmotion->y = root_location.y();
|
||||
xmotion->state = button_down_mask;
|
||||
xmotion->same_screen = x11::True;
|
||||
x11::MotionNotifyEvent xevent{
|
||||
.event_x = root_location.x(),
|
||||
.event_y = root_location.y(),
|
||||
.state = static_cast<x11::KeyButMask>(button_down_mask),
|
||||
.same_screen = true,
|
||||
};
|
||||
// WindowTreeHost will take care of other necessary fields.
|
||||
PostEventToWindowTreeHost(xevent, host_);
|
||||
PostEventToWindowTreeHost(host_, &xevent);
|
||||
}
|
||||
RunClosureAfterAllPendingUIEvents(std::move(closure));
|
||||
return true;
|
||||
@ -122,53 +124,51 @@ bool UIControlsX11::SendMouseEventsNotifyWhenDone(MouseButton type,
|
||||
int button_state,
|
||||
base::OnceClosure closure,
|
||||
int accelerator_state) {
|
||||
XEvent xevent;
|
||||
xevent.xbutton = {};
|
||||
XButtonEvent* xbutton = &xevent.xbutton;
|
||||
x11::ButtonEvent xevent;
|
||||
gfx::Point mouse_loc = Env::GetInstance()->last_mouse_location();
|
||||
aura::client::ScreenPositionClient* screen_position_client =
|
||||
aura::client::GetScreenPositionClient(host_->window());
|
||||
if (screen_position_client) {
|
||||
screen_position_client->ConvertPointFromScreen(host_->window(), &mouse_loc);
|
||||
}
|
||||
xbutton->x = mouse_loc.x();
|
||||
xbutton->y = mouse_loc.y();
|
||||
xbutton->same_screen = x11::True;
|
||||
xevent.event_x = mouse_loc.x();
|
||||
xevent.event_y = mouse_loc.y();
|
||||
switch (type) {
|
||||
case LEFT:
|
||||
xbutton->button = 1;
|
||||
xbutton->state = Button1Mask;
|
||||
xevent.detail = static_cast<x11::Button>(1);
|
||||
xevent.state = x11::KeyButMask::Button1;
|
||||
break;
|
||||
case MIDDLE:
|
||||
xbutton->button = 2;
|
||||
xbutton->state = Button2Mask;
|
||||
xevent.detail = static_cast<x11::Button>(2);
|
||||
xevent.state = x11::KeyButMask::Button2;
|
||||
break;
|
||||
case RIGHT:
|
||||
xbutton->button = 3;
|
||||
xbutton->state = Button3Mask;
|
||||
xevent.detail = static_cast<x11::Button>(3);
|
||||
xevent.state = x11::KeyButMask::Button3;
|
||||
break;
|
||||
}
|
||||
|
||||
// Process accelerator key state.
|
||||
if (accelerator_state & ui_controls::kShift)
|
||||
xbutton->state |= ShiftMask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Shift;
|
||||
if (accelerator_state & ui_controls::kControl)
|
||||
xbutton->state |= ControlMask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Control;
|
||||
if (accelerator_state & ui_controls::kAlt)
|
||||
xbutton->state |= Mod1Mask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Mod1;
|
||||
if (accelerator_state & ui_controls::kCommand)
|
||||
xbutton->state |= Mod4Mask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Mod4;
|
||||
|
||||
// WindowEventDispatcher will take care of other necessary fields.
|
||||
if (button_state & DOWN) {
|
||||
xevent.xbutton.type = x11::ButtonEvent::Press;
|
||||
PostEventToWindowTreeHost(xevent, host_);
|
||||
button_down_mask |= xbutton->state;
|
||||
xevent.opcode = x11::ButtonEvent::Press;
|
||||
PostEventToWindowTreeHost(host_, &xevent);
|
||||
button_down_mask |= static_cast<int>(xevent.state);
|
||||
}
|
||||
if (button_state & UP) {
|
||||
xevent.xbutton.type = x11::ButtonEvent::Release;
|
||||
PostEventToWindowTreeHost(xevent, host_);
|
||||
button_down_mask = (button_down_mask | xbutton->state) ^ xbutton->state;
|
||||
xevent.opcode = x11::ButtonEvent::Release;
|
||||
PostEventToWindowTreeHost(host_, &xevent);
|
||||
int state = static_cast<int>(xevent.state);
|
||||
button_down_mask = (button_down_mask | state) ^ state;
|
||||
}
|
||||
RunClosureAfterAllPendingUIEvents(std::move(closure));
|
||||
return true;
|
||||
@ -187,20 +187,23 @@ void UIControlsX11::RunClosureAfterAllPendingUIEvents(
|
||||
std::move(closure));
|
||||
}
|
||||
|
||||
void UIControlsX11::SetKeycodeAndSendThenMask(XEvent* xevent,
|
||||
void UIControlsX11::SetKeycodeAndSendThenMask(x11::KeyEvent* xevent,
|
||||
KeySym keysym,
|
||||
unsigned int mask) {
|
||||
xevent->xkey.keycode = XKeysymToKeycode(gfx::GetXDisplay(), keysym);
|
||||
PostEventToWindowTreeHost(*xevent, host_);
|
||||
xevent->xkey.state |= mask;
|
||||
xevent->detail =
|
||||
x11::Connection::Get()->KeysymToKeycode(static_cast<x11::KeySym>(keysym));
|
||||
PostEventToWindowTreeHost(host_, xevent);
|
||||
xevent->state = xevent->state | static_cast<x11::KeyButMask>(mask);
|
||||
}
|
||||
|
||||
void UIControlsX11::UnmaskAndSetKeycodeThenSend(XEvent* xevent,
|
||||
void UIControlsX11::UnmaskAndSetKeycodeThenSend(x11::KeyEvent* xevent,
|
||||
unsigned int mask,
|
||||
KeySym keysym) {
|
||||
xevent->xkey.state ^= mask;
|
||||
xevent->xkey.keycode = XKeysymToKeycode(gfx::GetXDisplay(), keysym);
|
||||
PostEventToWindowTreeHost(*xevent, host_);
|
||||
xevent->state =
|
||||
static_cast<x11::KeyButMask>(static_cast<uint32_t>(xevent->state) ^ mask);
|
||||
xevent->detail =
|
||||
x11::Connection::Get()->KeysymToKeycode(static_cast<x11::KeySym>(keysym));
|
||||
PostEventToWindowTreeHost(host_, xevent);
|
||||
}
|
||||
|
||||
} // namespace test
|
||||
|
@ -64,11 +64,11 @@ class UIControlsX11 : public ui_controls::UIControlsAura {
|
||||
void RunClosureAfterAllPendingUIEvents(base::OnceClosure closure);
|
||||
|
||||
private:
|
||||
void SetKeycodeAndSendThenMask(XEvent* xevent,
|
||||
void SetKeycodeAndSendThenMask(x11::KeyEvent* xevent,
|
||||
KeySym keysym,
|
||||
unsigned int mask);
|
||||
|
||||
void UnmaskAndSetKeycodeThenSend(XEvent* xevent,
|
||||
void UnmaskAndSetKeycodeThenSend(x11::KeyEvent* xevent,
|
||||
unsigned int mask,
|
||||
KeySym keysym);
|
||||
WindowTreeHost* const host_;
|
||||
|
@ -1,49 +0,0 @@
|
||||
// Copyright 2014 The Chromium Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include "ui/aura/test/x11_event_sender.h"
|
||||
|
||||
#include "ui/aura/window_tree_host.h"
|
||||
#include "ui/gfx/geometry/point.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
namespace aura {
|
||||
namespace test {
|
||||
|
||||
void PostEventToWindowTreeHost(const XEvent& xevent, WindowTreeHost* host) {
|
||||
XDisplay* xdisplay = gfx::GetXDisplay();
|
||||
x11::Window xwindow = static_cast<x11::Window>(host->GetAcceleratedWidget());
|
||||
XEvent event = xevent;
|
||||
event.xany.display = xdisplay;
|
||||
event.xany.window = static_cast<uint32_t>(xwindow);
|
||||
|
||||
switch (event.type) {
|
||||
case x11::CrossingEvent::EnterNotify:
|
||||
case x11::CrossingEvent::LeaveNotify:
|
||||
case x11::MotionNotifyEvent::opcode:
|
||||
case x11::KeyEvent::Press:
|
||||
case x11::KeyEvent::Release:
|
||||
case x11::ButtonEvent::Press:
|
||||
case x11::ButtonEvent::Release: {
|
||||
// The fields used below are in the same place for all of events
|
||||
// above. Using xmotion from XEvent's unions to avoid repeating
|
||||
// the code.
|
||||
event.xmotion.root = DefaultRootWindow(event.xany.display);
|
||||
event.xmotion.time = x11::CurrentTime;
|
||||
|
||||
gfx::Point point(event.xmotion.x, event.xmotion.y);
|
||||
host->ConvertDIPToScreenInPixels(&point);
|
||||
event.xmotion.x_root = point.x();
|
||||
event.xmotion.y_root = point.y();
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
XSendEvent(xdisplay, static_cast<uint32_t>(xwindow), x11::False, 0, &event);
|
||||
XFlush(xdisplay);
|
||||
}
|
||||
|
||||
} // namespace test
|
||||
} // namespace aura
|
@ -5,17 +5,34 @@
|
||||
#ifndef UI_AURA_TEST_X11_EVENT_SENDER_H_
|
||||
#define UI_AURA_TEST_X11_EVENT_SENDER_H_
|
||||
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
|
||||
using XEvent = union _XEvent;
|
||||
#include "ui/aura/window_tree_host.h"
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/gfx/geometry/point.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
namespace aura {
|
||||
|
||||
class WindowTreeHost;
|
||||
|
||||
namespace test {
|
||||
|
||||
void PostEventToWindowTreeHost(const XEvent& xevent, WindowTreeHost* host);
|
||||
// The root, time, root_x, and root_y fields of |xevent| may be modified.
|
||||
template <typename T>
|
||||
void PostEventToWindowTreeHost(WindowTreeHost* host, T* xevent) {
|
||||
auto* connection = x11::Connection::Get();
|
||||
x11::Window xwindow = static_cast<x11::Window>(host->GetAcceleratedWidget());
|
||||
xevent->event = xwindow;
|
||||
|
||||
xevent->root = connection->default_root();
|
||||
xevent->time = x11::Time::CurrentTime;
|
||||
|
||||
gfx::Point point(xevent->event_x, xevent->event_y);
|
||||
host->ConvertDIPToScreenInPixels(&point);
|
||||
xevent->root_x = point.x();
|
||||
xevent->root_y = point.y();
|
||||
|
||||
x11::SendEvent(*xevent, xwindow, x11::EventMask::NoEvent);
|
||||
connection->Flush();
|
||||
}
|
||||
|
||||
} // namespace test
|
||||
} // namespace aura
|
||||
|
@ -15,6 +15,7 @@
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_atom_cache.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
namespace ui {
|
||||
|
||||
@ -160,7 +161,7 @@ void SelectionOwner::OnSelectionRequest(const x11::Event& x11_event) {
|
||||
}
|
||||
|
||||
// Send off the reply.
|
||||
ui::SendEvent(reply, requestor, x11::EventMask::NoEvent);
|
||||
x11::SendEvent(reply, requestor, x11::EventMask::NoEvent);
|
||||
}
|
||||
|
||||
void SelectionOwner::OnSelectionClear(const x11::Event& event) {
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/x11_atom_cache.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
// Reading recommended for understanding the implementation in this file:
|
||||
//
|
||||
@ -623,7 +624,7 @@ void XDragDropClient::SendXClientEvent(x11::Window window,
|
||||
//
|
||||
// I'm unsure if I have to jump through those hoops, or if XSendEvent is
|
||||
// sufficient.
|
||||
ui::SendEvent(xev, window, x11::EventMask::NoEvent);
|
||||
x11::SendEvent(xev, window, x11::EventMask::NoEvent);
|
||||
}
|
||||
|
||||
void XDragDropClient::SendXdndEnter(x11::Window dest_window,
|
||||
|
@ -70,7 +70,7 @@ bool ShouldUseMitShm(x11::Connection* connection) {
|
||||
// codepath. It may be possible in contrived cases for there to be a
|
||||
// false-positive, but in that case we'll just fallback to the non-SHM
|
||||
// codepath.
|
||||
char* display_string = DisplayString(connection->display());
|
||||
char* display_string = XDisplayString(connection->display());
|
||||
char* host = nullptr;
|
||||
int display_id = 0;
|
||||
int screen = 0;
|
||||
|
@ -195,23 +195,6 @@ void SetProperty(x11::Window window,
|
||||
SetArrayProperty(window, name, type, std::vector<T>{value});
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
x11::Future<void> SendEvent(const T& event,
|
||||
x11::Window target,
|
||||
x11::EventMask mask) {
|
||||
static_assert(T::type_id > 0, "T must be an x11::*Event type");
|
||||
auto write_buffer = x11::Write(event);
|
||||
DCHECK_EQ(write_buffer.GetBuffers().size(), 1ul);
|
||||
auto& first_buffer = write_buffer.GetBuffers()[0];
|
||||
DCHECK_LE(first_buffer->size(), 32ul);
|
||||
std::vector<uint8_t> event_bytes(32);
|
||||
memcpy(event_bytes.data(), first_buffer->data(), first_buffer->size());
|
||||
|
||||
x11::SendEventRequest send_event{false, target, mask};
|
||||
std::copy(event_bytes.begin(), event_bytes.end(), send_event.event.begin());
|
||||
return x11::Connection::Get()->SendEvent(send_event);
|
||||
}
|
||||
|
||||
COMPONENT_EXPORT(UI_BASE_X)
|
||||
void DeleteProperty(x11::Window window, x11::Atom name);
|
||||
|
||||
|
@ -40,6 +40,7 @@
|
||||
#include "ui/gfx/x/xfixes.h"
|
||||
#include "ui/gfx/x/xinput.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
#include "ui/platform_window/common/platform_window_defaults.h"
|
||||
|
||||
namespace ui {
|
||||
@ -1160,9 +1161,9 @@ void XWindow::ProcessEvent(x11::Event* xev) {
|
||||
} else if (protocol == gfx::GetAtom("_NET_WM_PING")) {
|
||||
x11::ClientMessageEvent reply_event = *client;
|
||||
reply_event.window = x_root_window_;
|
||||
SendEvent(reply_event, x_root_window_,
|
||||
x11::EventMask::SubstructureNotify |
|
||||
x11::EventMask::SubstructureRedirect);
|
||||
x11::SendEvent(reply_event, x_root_window_,
|
||||
x11::EventMask::SubstructureNotify |
|
||||
x11::EventMask::SubstructureRedirect);
|
||||
} else if (protocol == gfx::GetAtom("_NET_WM_SYNC_REQUEST")) {
|
||||
pending_counter_value_ =
|
||||
client->data.data32[2] +
|
||||
|
@ -57,7 +57,7 @@ int main(int argc, char* argv[]) {
|
||||
connection.MapWindow({dummy_window});
|
||||
connection.Flush();
|
||||
|
||||
int display_fd = ConnectionNumber(connection.display());
|
||||
int display_fd = XConnectionNumber(connection.display());
|
||||
|
||||
// Set deadline as 30s.
|
||||
struct timespec now, deadline;
|
||||
|
@ -30,7 +30,7 @@ void TestCompositorHostX11::Show() {
|
||||
XSetWindowAttributes swa;
|
||||
swa.override_redirect = x11::True;
|
||||
window_ = static_cast<x11::Window>(XCreateWindow(
|
||||
display, XRootWindow(display, DefaultScreen(display)), // parent
|
||||
display, XDefaultRootWindow(display), // parent
|
||||
bounds_.x(), bounds_.y(), bounds_.width(), bounds_.height(),
|
||||
0, // border width
|
||||
static_cast<int>(x11::WindowClass::CopyFromParent), // depth
|
||||
|
@ -26,6 +26,7 @@
|
||||
#include "ui/events/test/events_test_utils_x11.h" // nogncheck
|
||||
#include "ui/events/x/x11_event_translation.h" // nogncheck
|
||||
#include "ui/gfx/x/event.h" // nogncheck
|
||||
#include "ui/gfx/x/keysyms/keysyms.h" // nogncheck
|
||||
#include "ui/gfx/x/x11.h" // nogncheck
|
||||
#include "ui/gfx/x/x11_types.h" // nogncheck
|
||||
#include "ui/gfx/x/xproto.h" // nogncheck
|
||||
|
@ -14,16 +14,15 @@ source_set("xkb") {
|
||||
"xkb_keysym.h",
|
||||
]
|
||||
|
||||
public_deps = [ "//ui/base:buildflags" ]
|
||||
public_deps = [
|
||||
"//ui/base:buildflags",
|
||||
"//ui/gfx/x/keysyms",
|
||||
]
|
||||
|
||||
deps = [
|
||||
"//base",
|
||||
"//ui/events:dom_keycode_converter",
|
||||
]
|
||||
|
||||
if (!use_xkbcommon) {
|
||||
public_deps += [ "//ui/gfx/x" ]
|
||||
}
|
||||
}
|
||||
|
||||
if (use_x11 || ozone_platform_x11) {
|
||||
|
@ -17,6 +17,8 @@
|
||||
#include "ui/events/keycodes/keyboard_code_conversion_xkb.h"
|
||||
#include "ui/events/keycodes/keyboard_codes_posix.h"
|
||||
#include "ui/events/keycodes/keysym_to_unicode.h"
|
||||
#include "ui/events/keycodes/xkb_keysym.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xinput.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
|
@ -6,10 +6,8 @@
|
||||
|
||||
#include "build/build_config.h"
|
||||
#include "ui/events/keycodes/dom/dom_key.h"
|
||||
|
||||
#ifndef XK_dead_greek
|
||||
#define XK_dead_greek 0xfe8c
|
||||
#endif
|
||||
#include "ui/events/keycodes/keyboard_code_conversion_xkb.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
|
||||
namespace ui {
|
||||
|
||||
|
@ -8,6 +8,7 @@
|
||||
|
||||
#include "base/lazy_instance.h"
|
||||
#include "base/stl_util.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
namespace ui {
|
||||
|
@ -17,7 +17,7 @@
|
||||
|
||||
#else // !BUILDFLAG(USE_XKBCOMMON)
|
||||
|
||||
#include "ui/gfx/x/x11.h" // nogncheck
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
|
||||
using xkb_keysym_t = uint32_t;
|
||||
|
||||
|
@ -22,7 +22,7 @@ void X11EventWatcherFdWatch::StartWatching() {
|
||||
|
||||
DCHECK(event_source_->connection()) << "Unable to get connection to X server";
|
||||
|
||||
int fd = ConnectionNumber(event_source_->connection()->display());
|
||||
int fd = XConnectionNumber(event_source_->connection()->display());
|
||||
base::CurrentUIThread::Get()->WatchFileDescriptor(
|
||||
fd, true, base::MessagePumpForUI::WATCH_READ, &watcher_controller_, this);
|
||||
started_ = true;
|
||||
|
@ -65,7 +65,7 @@ void X11EventWatcherGlib::StartWatching() {
|
||||
return;
|
||||
|
||||
x_poll_ = std::make_unique<GPollFD>();
|
||||
x_poll_->fd = ConnectionNumber(display);
|
||||
x_poll_->fd = XConnectionNumber(display);
|
||||
x_poll_->events = G_IO_IN;
|
||||
x_poll_->revents = 0;
|
||||
|
||||
|
@ -116,7 +116,8 @@ x11::Event CreateXInput2Event(int deviceid,
|
||||
event.detail = tracking_id;
|
||||
event.event_x = ToFp1616(location.x()),
|
||||
event.event_y = ToFp1616(location.y()),
|
||||
event.event = static_cast<x11::Window>(DefaultRootWindow(gfx::GetXDisplay()));
|
||||
event.event =
|
||||
static_cast<x11::Window>(XDefaultRootWindow(gfx::GetXDisplay()));
|
||||
event.button_mask = {0, 0};
|
||||
return x11::Event(std::move(event));
|
||||
}
|
||||
|
@ -5,29 +5,27 @@
|
||||
#include "ui/events/test/x11_event_waiter.h"
|
||||
|
||||
#include "base/threading/thread_task_runner_handle.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_atom_cache.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
namespace ui {
|
||||
|
||||
// static
|
||||
XEventWaiter* XEventWaiter::Create(x11::Window window,
|
||||
base::OnceClosure callback) {
|
||||
Display* display = gfx::GetXDisplay();
|
||||
static XEvent* marker_event = nullptr;
|
||||
if (!marker_event) {
|
||||
marker_event = new XEvent();
|
||||
marker_event->xclient.type = ClientMessage;
|
||||
marker_event->xclient.display = display;
|
||||
marker_event->xclient.window = static_cast<uint32_t>(window);
|
||||
marker_event->xclient.format = 8;
|
||||
}
|
||||
marker_event->xclient.message_type = static_cast<uint32_t>(MarkerEventAtom());
|
||||
auto* connection = x11::Connection::Get();
|
||||
|
||||
XSendEvent(display, static_cast<uint32_t>(window), x11::False, 0,
|
||||
marker_event);
|
||||
XFlush(display);
|
||||
x11::ClientMessageEvent marker_event{
|
||||
.format = 8,
|
||||
.window = window,
|
||||
.type = MarkerEventAtom(),
|
||||
};
|
||||
|
||||
x11::SendEvent(marker_event, window, x11::EventMask::NoEvent);
|
||||
connection->Flush();
|
||||
|
||||
// Will be deallocated when the expected event is received.
|
||||
return new XEventWaiter(std::move(callback));
|
||||
|
@ -65,7 +65,6 @@ action("gen_xprotos") {
|
||||
foreach(proto, protos) {
|
||||
sources += [ "$xcbproto_path/src/${proto}.xml" ]
|
||||
outputs += [
|
||||
"$target_gen_dir/${proto}_undef.h",
|
||||
"$target_gen_dir/${proto}.h",
|
||||
"$target_gen_dir/${proto}.cc",
|
||||
]
|
||||
@ -85,6 +84,7 @@ component("xprotos") {
|
||||
"//base:i18n",
|
||||
"//ui/events/platform",
|
||||
]
|
||||
public_deps = [ "//ui/gfx/x/keysyms" ]
|
||||
sources = get_target_outputs(":gen_xprotos") + [
|
||||
"xproto_internal.h",
|
||||
"xproto_internal.cc",
|
||||
|
@ -18,6 +18,7 @@
|
||||
#include "base/threading/thread_local.h"
|
||||
#include "ui/gfx/x/bigreq.h"
|
||||
#include "ui/gfx/x/event.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/randr.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_switches.h"
|
||||
@ -301,7 +302,7 @@ int Connection::DefaultScreenId() const {
|
||||
// This is not part of the setup data as the server has no concept of a
|
||||
// default screen. Instead, it's part of the display name. Eg in
|
||||
// "localhost:0.0", the screen ID is the second "0".
|
||||
return DefaultScreen(display_);
|
||||
return XDefaultScreen(display_);
|
||||
}
|
||||
|
||||
bool Connection::Ready() const {
|
||||
|
@ -70,6 +70,10 @@ class COMPONENT_EXPORT(X11) Event {
|
||||
uint32_t sequence() const { return sequence_; }
|
||||
|
||||
x11::Window window() const { return window_ ? *window_ : x11::Window::None; }
|
||||
void set_window(x11::Window window) {
|
||||
if (window_)
|
||||
*window_ = window;
|
||||
}
|
||||
|
||||
private:
|
||||
friend void ReadEvent(Event* event,
|
||||
|
@ -236,6 +236,10 @@ WRITE_SPECIAL = set([
|
||||
('xcb', 'Expose'),
|
||||
('xcb', 'UnmapNotify'),
|
||||
('xcb', 'SelectionNotify'),
|
||||
('xcb', 'MotionNotify'),
|
||||
('xcb', 'Key'),
|
||||
('xcb', 'Button'),
|
||||
('xcb', 'PropertyNotify'),
|
||||
])
|
||||
|
||||
|
||||
@ -365,8 +369,6 @@ class GenXproto(FileWriter):
|
||||
self.xml_filename = os.path.join(proto_dir, '%s.xml' % proto)
|
||||
self.header_file = open(os.path.join(gen_dir, '%s.h' % proto), 'w')
|
||||
self.source_file = open(os.path.join(gen_dir, '%s.cc' % proto), 'w')
|
||||
self.undef_file = open(os.path.join(gen_dir, '%s_undef.h' % proto),
|
||||
'w')
|
||||
|
||||
# Top-level xcbgen python module
|
||||
self.xcbgen = xcbgen
|
||||
@ -510,12 +512,6 @@ class GenXproto(FileWriter):
|
||||
return field
|
||||
return None
|
||||
|
||||
# Work around conflicts caused by Xlib's liberal use of macros.
|
||||
def undef(self, name):
|
||||
print('#ifdef %s' % name, file=self.undef_file)
|
||||
print('#undef %s' % name, file=self.undef_file)
|
||||
print('#endif', file=self.undef_file)
|
||||
|
||||
def expr(self, expr):
|
||||
if expr.op == 'popcount':
|
||||
return 'PopCount(%s)' % self.expr(expr.rhs)
|
||||
@ -633,7 +629,11 @@ class GenXproto(FileWriter):
|
||||
else:
|
||||
container_type, container_name = field.parent
|
||||
assert container_type.is_event
|
||||
opcode = container_type.opcodes[container_name]
|
||||
# Extension events require offsetting the opcode, so make
|
||||
# sure this path is only hit for non-extension events for now.
|
||||
assert not self.module.namespace.is_ext
|
||||
opcode = container_type.opcodes.get(container_name,
|
||||
'obj.opcode')
|
||||
self.write('%s %s = %s;' % (type_name, name, opcode))
|
||||
self.copy_primitive(name)
|
||||
elif name in ('extension', 'error_code', 'event_type'):
|
||||
@ -827,10 +827,8 @@ class GenXproto(FileWriter):
|
||||
def declare_enum(self, enum):
|
||||
def declare_enum_entry(name, value):
|
||||
name = safe_name(name)
|
||||
self.undef(name)
|
||||
self.write('%s = %s,' % (name, value))
|
||||
|
||||
self.undef(enum.name[-1])
|
||||
with Indent(
|
||||
self, 'enum class %s : %s {' %
|
||||
(adjust_type_name(enum.name[-1]), self.enum_types[enum.name][0]
|
||||
@ -901,7 +899,6 @@ class GenXproto(FileWriter):
|
||||
|
||||
def declare_event(self, event, name):
|
||||
event_name = name[-1] + 'Event'
|
||||
self.undef(event_name)
|
||||
with Indent(self, 'struct %s {' % adjust_type_name(event_name), '};'):
|
||||
self.write('static constexpr int type_id = %d;' % event.type_id)
|
||||
if len(event.opcodes) == 1:
|
||||
@ -912,7 +909,6 @@ class GenXproto(FileWriter):
|
||||
items = [(int(x), y)
|
||||
for (y, x) in event.enum_opcodes.items()]
|
||||
for opcode, opname in sorted(items):
|
||||
self.undef(opname)
|
||||
self.write('%s = %s,' % (opname, opcode))
|
||||
self.write('bool send_event{};')
|
||||
self.declare_fields(event.fields)
|
||||
@ -925,7 +921,6 @@ class GenXproto(FileWriter):
|
||||
|
||||
def declare_container(self, struct, struct_name):
|
||||
name = struct_name[-1] + self.type_suffix(struct)
|
||||
self.undef(name)
|
||||
with Indent(self, 'struct %s {' % adjust_type_name(name), '};'):
|
||||
self.declare_fields(struct.fields)
|
||||
self.write()
|
||||
@ -1325,7 +1320,6 @@ class GenXproto(FileWriter):
|
||||
imports.add(('xproto', 'xproto'))
|
||||
for direct_import in sorted(list(imports)):
|
||||
self.write('#include "%s.h"' % direct_import[-1])
|
||||
self.write('#include "%s_undef.h"' % self.module.namespace.header)
|
||||
self.write()
|
||||
self.write('namespace x11 {')
|
||||
self.write()
|
||||
@ -1338,7 +1332,6 @@ class GenXproto(FileWriter):
|
||||
self.declare_type(item, name)
|
||||
|
||||
name = self.class_name
|
||||
self.undef(name)
|
||||
with Indent(self, 'class COMPONENT_EXPORT(X11) %s {' % name, '};'):
|
||||
self.namespace = ['x11', self.class_name]
|
||||
self.write('public:')
|
||||
@ -1452,9 +1445,6 @@ class GenExtensionManager(FileWriter):
|
||||
self.write()
|
||||
self.write('#include "base/component_export.h"')
|
||||
self.write()
|
||||
self.write('// Avoid conflicts caused by the GenericEvent macro.')
|
||||
self.write('#include "ui/gfx/x/ge_undef.h"')
|
||||
self.write()
|
||||
self.write('namespace x11 {')
|
||||
self.write()
|
||||
self.write('class Connection;')
|
||||
|
7
ui/gfx/x/keysyms/BUILD.gn
Normal file
7
ui/gfx/x/keysyms/BUILD.gn
Normal file
@ -0,0 +1,7 @@
|
||||
# Copyright 2020 The Chromium Authors. All rights reserved.
|
||||
# Use of this source code is governed by a BSD-style license that can be
|
||||
# found in the LICENSE file.
|
||||
|
||||
source_set("keysyms") {
|
||||
public = [ "keysyms.h" ]
|
||||
}
|
1161
ui/gfx/x/keysyms/keysyms.h
Normal file
1161
ui/gfx/x/keysyms/keysyms.h
Normal file
File diff suppressed because it is too large
Load Diff
450
ui/gfx/x/x11.h
450
ui/gfx/x/x11.h
@ -2,99 +2,387 @@
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
// This header file replaces includes of X11 system includes while
|
||||
// preventing them from redefining and making a mess of commonly used
|
||||
// keywords like "None" and "Status". Instead those are placed inside
|
||||
// an X11 namespace where they will not clash with other code.
|
||||
// This header file replaces <X11/Xlib.h>. https://crbug.com/1066670 is
|
||||
// tracking removing usage of Xlib altogether. Do not add more Xlib
|
||||
// declarations here. The intention is to incrementally remove declarations
|
||||
// until there is nothing left, at which point this file will be removed.
|
||||
|
||||
#ifndef UI_GFX_X_X11
|
||||
#define UI_GFX_X_X11
|
||||
|
||||
extern "C" {
|
||||
// Xlib.h defines base types so it must be included before the less
|
||||
// central X11 headers can be included.
|
||||
#include <X11/Xlib.h>
|
||||
|
||||
// And the rest so that nobody needs to include them manually...
|
||||
#include <X11/XKBlib.h>
|
||||
#include <X11/Xlib-xcb.h>
|
||||
|
||||
// Define XK_xxx before the #include of <X11/keysym.h> so that <X11/keysym.h>
|
||||
// defines all KeySyms we need.
|
||||
#define XK_3270 // For XK_3270_BackTab in particular.
|
||||
#define XK_MISCELLANY
|
||||
#define XK_LATIN1
|
||||
#define XK_LATIN2
|
||||
#define XK_LATIN3
|
||||
#define XK_LATIN4
|
||||
#define XK_LATIN8
|
||||
#define XK_LATIN9
|
||||
#define XK_KATAKANA
|
||||
#define XK_ARABIC
|
||||
#define XK_CYRILLIC
|
||||
#define XK_GREEK
|
||||
#define XK_TECHNICAL
|
||||
#define XK_SPECIAL
|
||||
#define XK_PUBLISHING
|
||||
#define XK_APL
|
||||
#define XK_HEBREW
|
||||
#define XK_THAI
|
||||
#define XK_KOREAN
|
||||
#define XK_ARMENIAN
|
||||
#define XK_GEORGIAN
|
||||
#define XK_CAUCASUS
|
||||
#define XK_VIETNAMESE
|
||||
#define XK_CURRENCY
|
||||
#define XK_MATHEMATICAL
|
||||
#define XK_BRAILLE
|
||||
#define XK_SINHALA
|
||||
#define XK_XKB_KEYS
|
||||
|
||||
#ifndef XK_dead_greek
|
||||
#define XK_dead_greek 0xfe8c
|
||||
#endif
|
||||
|
||||
#include <X11/Sunkeysym.h>
|
||||
#include <X11/XF86keysym.h>
|
||||
#include <X11/keysym.h>
|
||||
}
|
||||
|
||||
#include "ui/gfx/x/xproto_undef.h"
|
||||
#ifndef UI_GFX_X_X11_H_
|
||||
#define UI_GFX_X_X11_H_
|
||||
|
||||
#include "ui/gfx/x/connection.h"
|
||||
|
||||
// These commonly used names are undefined and if necessary recreated
|
||||
// in the x11 namespace below. This is the main purpose of this header
|
||||
// file.
|
||||
// Temporarily declare Xlib symbols we require. Do not add more Xlib
|
||||
// declarations here and do not include anything from <X11/*>.
|
||||
|
||||
// Not using common words is extra important for jumbo builds
|
||||
// where cc files are merged. Those merged filed get to see many more
|
||||
// headers than initially expected, including system headers like
|
||||
// those from X11.
|
||||
extern "C" {
|
||||
|
||||
#undef Status // Defined by X11/Xlib.h to int
|
||||
#undef Bool // Defined by X11/Xlib.h to int
|
||||
#undef RootWindow // Defined by X11/Xlib.h
|
||||
#undef DestroyAll // Defined by X11/X.h to 0
|
||||
#undef Always // Defined by X11/X.h to 2
|
||||
#undef FocusIn // Defined by X.h to 9
|
||||
#undef FocusOut // Defined by X.h to 10
|
||||
#undef None // Defined by X11/X.h to 0L
|
||||
#undef True // Defined by X11/Xlib.h to 1
|
||||
#undef False // Defined by X11/Xlib.h to 0
|
||||
#undef CurrentTime // Defined by X11/X.h to 0L
|
||||
#undef Success // Defined by X11/X.h to 0
|
||||
static constexpr auto GrabModeAsync = 1;
|
||||
|
||||
// The x11 namespace allows to scope X11 constants and types that
|
||||
// would be problematic at the default preprocessor level.
|
||||
static constexpr auto ShiftMask = 1 << 0;
|
||||
static constexpr auto LockMask = 1 << 1;
|
||||
static constexpr auto ControlMask = 1 << 2;
|
||||
static constexpr auto Mod1Mask = 1 << 3;
|
||||
static constexpr auto Mod2Mask = 1 << 4;
|
||||
static constexpr auto Mod3Mask = 1 << 5;
|
||||
static constexpr auto Mod4Mask = 1 << 6;
|
||||
static constexpr auto Mod5Mask = 1 << 7;
|
||||
|
||||
static constexpr auto NoEventMask = 0L;
|
||||
static constexpr auto KeyPressMask = 1L << 0;
|
||||
static constexpr auto KeyReleaseMask = 1L << 1;
|
||||
static constexpr auto ButtonPressMask = 1L << 2;
|
||||
static constexpr auto ButtonReleaseMask = 1L << 3;
|
||||
static constexpr auto EnterWindowMask = 1L << 4;
|
||||
static constexpr auto LeaveWindowMask = 1L << 5;
|
||||
static constexpr auto PointerMotionMask = 1L << 6;
|
||||
static constexpr auto PointerMotionHintMask = 1L << 7;
|
||||
static constexpr auto Button1MotionMask = 1L << 8;
|
||||
static constexpr auto Button2MotionMask = 1L << 9;
|
||||
static constexpr auto Button3MotionMask = 1L << 10;
|
||||
static constexpr auto Button4MotionMask = 1L << 11;
|
||||
static constexpr auto Button5MotionMask = 1L << 12;
|
||||
static constexpr auto ButtonMotionMask = 1L << 13;
|
||||
static constexpr auto KeymapStateMask = 1L << 14;
|
||||
static constexpr auto ExposureMask = 1L << 15;
|
||||
static constexpr auto VisibilityChangeMask = 1L << 16;
|
||||
static constexpr auto StructureNotifyMask = 1L << 17;
|
||||
static constexpr auto ResizeRedirectMask = 1L << 18;
|
||||
static constexpr auto SubstructureNotifyMask = 1L << 19;
|
||||
static constexpr auto SubstructureRedirectMask = 1L << 20;
|
||||
static constexpr auto FocusChangeMask = 1L << 21;
|
||||
static constexpr auto PropertyChangeMask = 1L << 22;
|
||||
static constexpr auto ColormapChangeMask = 1L << 23;
|
||||
static constexpr auto OwnerGrabButtonMask = 1L << 24;
|
||||
|
||||
static constexpr auto CWBackPixmap = 1L << 0;
|
||||
static constexpr auto CWBackPixel = 1L << 1;
|
||||
static constexpr auto CWBorderPixmap = 1L << 2;
|
||||
static constexpr auto CWBorderPixel = 1L << 3;
|
||||
static constexpr auto CWBitGravity = 1L << 4;
|
||||
static constexpr auto CWWinGravity = 1L << 5;
|
||||
static constexpr auto CWBackingStore = 1L << 6;
|
||||
static constexpr auto CWBackingPlanes = 1L << 7;
|
||||
static constexpr auto CWBackingPixel = 1L << 8;
|
||||
static constexpr auto CWOverrideRedirect = 1L << 9;
|
||||
static constexpr auto CWSaveUnder = 1L << 10;
|
||||
static constexpr auto CWEventMask = 1L << 11;
|
||||
static constexpr auto CWDontPropagate = 1L << 12;
|
||||
static constexpr auto CWColormap = 1L << 13;
|
||||
static constexpr auto CWCursor = 1L << 14;
|
||||
|
||||
static constexpr auto ForgetGravity = 0;
|
||||
static constexpr auto NorthWestGravity = 1;
|
||||
static constexpr auto NorthGravity = 2;
|
||||
static constexpr auto NorthEastGravity = 3;
|
||||
static constexpr auto WestGravity = 4;
|
||||
static constexpr auto CenterGravity = 5;
|
||||
static constexpr auto EastGravity = 6;
|
||||
static constexpr auto SouthWestGravity = 7;
|
||||
static constexpr auto SouthGravity = 8;
|
||||
static constexpr auto SouthEastGravity = 9;
|
||||
static constexpr auto StaticGravity = 10;
|
||||
|
||||
static constexpr auto Button1Mask = 1 << 8;
|
||||
static constexpr auto Button2Mask = 1 << 9;
|
||||
static constexpr auto Button3Mask = 1 << 10;
|
||||
static constexpr auto Button4Mask = 1 << 11;
|
||||
static constexpr auto Button5Mask = 1 << 12;
|
||||
|
||||
static constexpr auto CWX = 1 << 0;
|
||||
static constexpr auto CWY = 1 << 1;
|
||||
static constexpr auto CWWidth = 1 << 2;
|
||||
static constexpr auto CWHeight = 1 << 3;
|
||||
static constexpr auto CWBorderWidth = 1 << 4;
|
||||
static constexpr auto CWSibling = 1 << 5;
|
||||
static constexpr auto CWStackMode = 1 << 6;
|
||||
|
||||
static constexpr auto NotifyNormal = 0;
|
||||
static constexpr auto NotifyGrab = 1;
|
||||
static constexpr auto NotifyUngrab = 2;
|
||||
static constexpr auto NotifyWhileGrabbed = 3;
|
||||
|
||||
static constexpr auto NotifyAncestor = 0;
|
||||
static constexpr auto NotifyVirtual = 1;
|
||||
static constexpr auto NotifyInferior = 2;
|
||||
static constexpr auto NotifyNonlinear = 3;
|
||||
static constexpr auto NotifyNonlinearVirtual = 4;
|
||||
static constexpr auto NotifyPointer = 5;
|
||||
static constexpr auto NotifyPointerRoot = 6;
|
||||
static constexpr auto NotifyDetailNone = 7;
|
||||
|
||||
static constexpr auto PropModeReplace = 0;
|
||||
static constexpr auto PropModePrepend = 1;
|
||||
static constexpr auto PropModeAppend = 2;
|
||||
|
||||
static constexpr auto AnyPropertyType = 0L;
|
||||
|
||||
static constexpr auto NoSymbol = 0L;
|
||||
|
||||
using Status = int;
|
||||
using Bool = int;
|
||||
using XID = unsigned long;
|
||||
using KeySym = XID;
|
||||
using KeyCode = unsigned char;
|
||||
using Window = XID;
|
||||
using Pixmap = XID;
|
||||
using Font = XID;
|
||||
using VisualID = unsigned long;
|
||||
using XPointer = char*;
|
||||
using Colormap = XID;
|
||||
using Cursor = XID;
|
||||
using Atom = unsigned long;
|
||||
using Time = unsigned long;
|
||||
using GC = struct _XGC*;
|
||||
using Display = struct _XDisplay;
|
||||
using xcb_connection_t = struct xcb_connection_t;
|
||||
|
||||
enum XEventQueueOwner { XlibOwnsEventQueue = 0, XCBOwnsEventQueue };
|
||||
|
||||
using XErrorEvent = struct {
|
||||
int type;
|
||||
Display* display;
|
||||
XID resourceid;
|
||||
unsigned long serial;
|
||||
unsigned char error_code;
|
||||
unsigned char request_code;
|
||||
unsigned char minor_code;
|
||||
};
|
||||
|
||||
using XRectangle = struct {
|
||||
short x, y;
|
||||
unsigned short width, height;
|
||||
};
|
||||
|
||||
using XExtData = struct _XExtData {
|
||||
int number;
|
||||
struct _XExtData* next;
|
||||
int (*free_private)(struct _XExtData* extension);
|
||||
XPointer private_data;
|
||||
};
|
||||
|
||||
using Visual = struct {
|
||||
XExtData* ext_data;
|
||||
VisualID visualid;
|
||||
int c_class;
|
||||
unsigned long red_mask, green_mask, blue_mask;
|
||||
int bits_per_rgb;
|
||||
int map_entries;
|
||||
};
|
||||
|
||||
using XVisualInfo = struct {
|
||||
Visual* visual;
|
||||
VisualID visualid;
|
||||
int screen;
|
||||
int depth;
|
||||
int c_class;
|
||||
unsigned long red_mask;
|
||||
unsigned long green_mask;
|
||||
unsigned long blue_mask;
|
||||
int colormap_size;
|
||||
int bits_per_rgb;
|
||||
};
|
||||
|
||||
using Depth = struct {
|
||||
int depth;
|
||||
int nvisuals;
|
||||
Visual* visuals;
|
||||
};
|
||||
|
||||
using Screen = struct {
|
||||
XExtData* ext_data;
|
||||
struct _XDisplay* display;
|
||||
Window root;
|
||||
int width, height;
|
||||
int mwidth, mheight;
|
||||
int ndepths;
|
||||
Depth* depths;
|
||||
int root_depth;
|
||||
Visual* root_visual;
|
||||
GC default_gc;
|
||||
Colormap cmap;
|
||||
unsigned long white_pixel;
|
||||
unsigned long black_pixel;
|
||||
int max_maps, min_maps;
|
||||
int backing_store;
|
||||
Bool save_unders;
|
||||
long root_input_mask;
|
||||
};
|
||||
|
||||
using XSetWindowAttributes = struct {
|
||||
Pixmap background_pixmap;
|
||||
unsigned long background_pixel;
|
||||
Pixmap border_pixmap;
|
||||
unsigned long border_pixel;
|
||||
int bit_gravity;
|
||||
int win_gravity;
|
||||
int backing_store;
|
||||
unsigned long backing_planes;
|
||||
unsigned long backing_pixel;
|
||||
Bool save_under;
|
||||
long event_mask;
|
||||
long do_not_propagate_mask;
|
||||
Bool override_redirect;
|
||||
Colormap colormap;
|
||||
Cursor cursor;
|
||||
};
|
||||
|
||||
using XWindowAttributes = struct {
|
||||
int x, y;
|
||||
int width, height;
|
||||
int border_width;
|
||||
int depth;
|
||||
Visual* visual;
|
||||
Window root;
|
||||
int c_class;
|
||||
int bit_gravity;
|
||||
int win_gravity;
|
||||
int backing_store;
|
||||
unsigned long backing_planes;
|
||||
unsigned long backing_pixel;
|
||||
Bool save_under;
|
||||
Colormap colormap;
|
||||
Bool map_installed;
|
||||
int map_state;
|
||||
long all_event_masks;
|
||||
long your_event_mask;
|
||||
long do_not_propagate_mask;
|
||||
Bool override_redirect;
|
||||
Screen* screen;
|
||||
};
|
||||
|
||||
using XWindowChanges = struct {
|
||||
int x, y;
|
||||
int width, height;
|
||||
int border_width;
|
||||
Window sibling;
|
||||
int stack_mode;
|
||||
};
|
||||
|
||||
using XModifierKeymap = struct {
|
||||
int max_keypermod;
|
||||
KeyCode* modifiermap;
|
||||
};
|
||||
|
||||
using XErrorHandler = int (*)(Display*, XErrorEvent*);
|
||||
using XIOErrorHandler = int (*)(Display*);
|
||||
|
||||
Status XInitThreads(void);
|
||||
Display* XOpenDisplay(const char*);
|
||||
int XCloseDisplay(Display*);
|
||||
char* XDisplayString(Display*);
|
||||
int XFlush(Display*);
|
||||
xcb_connection_t* XGetXCBConnection(Display* dpy);
|
||||
void XSetEventQueueOwner(Display* dpy, enum XEventQueueOwner owner);
|
||||
int XDefaultScreen(Display*);
|
||||
Window XDefaultRootWindow(Display*);
|
||||
Visual* XDefaultVisual(Display*, int);
|
||||
unsigned long XLastKnownRequestProcessed(Display*);
|
||||
int (*XSynchronize(Display*, Bool))(Display*);
|
||||
int XGetErrorDatabaseText(Display*,
|
||||
const char*,
|
||||
const char*,
|
||||
const char*,
|
||||
char*,
|
||||
int);
|
||||
int XGetErrorText(Display*, int, char*, int);
|
||||
Bool XQueryExtension(Display*, const char*, int*, int*, int*);
|
||||
int XSync(Display*, Bool);
|
||||
XErrorHandler XSetErrorHandler(XErrorHandler);
|
||||
XIOErrorHandler XSetIOErrorHandler(XIOErrorHandler);
|
||||
void XLockDisplay(Display*);
|
||||
extern void XUnlockDisplay(Display*);
|
||||
int XConnectionNumber(Display*);
|
||||
int XGrabKey(Display*, int, unsigned int, Window, Bool, int, int);
|
||||
int XUngrabKey(Display*, int, unsigned int, Window);
|
||||
int XSelectInput(Display*, Window, long);
|
||||
int XSetWindowBackgroundPixmap(Display*, Window, Pixmap);
|
||||
Window XCreateWindow(Display*,
|
||||
Window,
|
||||
int,
|
||||
int,
|
||||
unsigned int,
|
||||
unsigned int,
|
||||
unsigned int,
|
||||
int,
|
||||
unsigned int,
|
||||
Visual*,
|
||||
unsigned long,
|
||||
XSetWindowAttributes*);
|
||||
Window XCreateSimpleWindow(Display*,
|
||||
Window,
|
||||
int,
|
||||
int,
|
||||
unsigned int,
|
||||
unsigned int,
|
||||
unsigned int,
|
||||
unsigned long,
|
||||
unsigned long);
|
||||
int XDestroyWindow(Display*, Window);
|
||||
Status XGetWindowAttributes(Display*, Window, XWindowAttributes*);
|
||||
VisualID XVisualIDFromVisual(Visual*);
|
||||
int XResizeWindow(Display*, Window, unsigned int, unsigned int);
|
||||
int XMapWindow(Display*, Window);
|
||||
KeyCode XKeysymToKeycode(Display*, KeySym);
|
||||
char* XKeysymToString(KeySym);
|
||||
XModifierKeymap* XGetModifierMapping(Display*);
|
||||
int XFreeModifiermap(XModifierKeymap*);
|
||||
int XGrabServer(Display*);
|
||||
int XUngrabServer(Display*);
|
||||
unsigned long XBlackPixel(Display*, int);
|
||||
int XStoreName(Display*, Window, const char*);
|
||||
Status XIconifyWindow(Display*, Window, int);
|
||||
int XConfigureWindow(Display*, Window, unsigned int, XWindowChanges*);
|
||||
XVisualInfo* XGetVisualInfo(Display*, long, XVisualInfo*, int*);
|
||||
int XFree(void*);
|
||||
int XConvertSelection(Display*, Atom, Atom, Atom, Window, Time);
|
||||
Window XGetSelectionOwner(Display*, Atom);
|
||||
int XSetSelectionOwner(Display*, Atom, Window, Time);
|
||||
int XChangeProperty(Display*,
|
||||
Window,
|
||||
Atom,
|
||||
Atom,
|
||||
int,
|
||||
int,
|
||||
const unsigned char*,
|
||||
int);
|
||||
int XGetWindowProperty(Display*,
|
||||
Window,
|
||||
Atom,
|
||||
long,
|
||||
long,
|
||||
Bool,
|
||||
Atom,
|
||||
Atom*,
|
||||
int*,
|
||||
unsigned long*,
|
||||
unsigned long*,
|
||||
unsigned char**);
|
||||
Status XInternAtoms(Display*, char**, int, Bool, Atom*);
|
||||
int XDisplayKeycodes(Display*, int*, int*);
|
||||
KeySym* XGetKeyboardMapping(Display*, KeyCode, int, int*);
|
||||
KeySym XStringToKeysym(const char*);
|
||||
int XChangeKeyboardMapping(Display*, int, int, KeySym*, int);
|
||||
Bool XkbLookupKeySym(Display*, KeyCode, unsigned int, unsigned int*, KeySym*);
|
||||
Bool XkbLockModifiers(Display*, unsigned int, unsigned int, unsigned int);
|
||||
unsigned int XkbKeysymToModifiers(Display*, KeySym);
|
||||
}
|
||||
|
||||
inline int XkbGroupForCoreState(int s) {
|
||||
return (s >> 13) & 0x3;
|
||||
}
|
||||
|
||||
inline int XkbBuildCoreState(int m, int g) {
|
||||
return ((g & 0x3) << 13) | (m & 0xff);
|
||||
}
|
||||
|
||||
// Deprecated.
|
||||
namespace x11 {
|
||||
static constexpr unsigned long None = 0L;
|
||||
static constexpr long CurrentTime = 0L;
|
||||
static constexpr int False = 0;
|
||||
static constexpr int True = 1;
|
||||
static constexpr int Success = 0;
|
||||
typedef int Bool;
|
||||
typedef int Status;
|
||||
} // namespace x11
|
||||
|
||||
#endif // UI_GFX_X_X11
|
||||
#endif // UI_GFX_X_X11_H_
|
||||
|
@ -20,7 +20,7 @@ XDisplay* GetXDisplay() {
|
||||
}
|
||||
|
||||
XDisplay* CloneXDisplay(XDisplay* display) {
|
||||
return XOpenDisplay(DisplayString(display));
|
||||
return XOpenDisplay(XDisplayString(display));
|
||||
}
|
||||
|
||||
} // namespace gfx
|
||||
|
@ -9,6 +9,7 @@
|
||||
#include "base/memory/scoped_refptr.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/xproto_internal.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
namespace x11 {
|
||||
|
||||
|
@ -12,12 +12,12 @@
|
||||
|
||||
#include "base/bind.h"
|
||||
#include "base/callback.h"
|
||||
#include "base/component_export.h"
|
||||
#include "base/files/scoped_file.h"
|
||||
#include "base/memory/free_deleter.h"
|
||||
#include "base/memory/ref_counted_memory.h"
|
||||
#include "base/memory/scoped_refptr.h"
|
||||
#include "base/optional.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
typedef struct _XDisplay XDisplay;
|
||||
|
||||
|
@ -8,9 +8,31 @@
|
||||
#include <cstdint>
|
||||
|
||||
#include "base/component_export.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_types.h"
|
||||
|
||||
namespace x11 {
|
||||
|
||||
template <typename T>
|
||||
x11::Future<void> SendEvent(
|
||||
const T& event,
|
||||
x11::Window target,
|
||||
x11::EventMask mask,
|
||||
x11::Connection* connection = x11::Connection::Get()) {
|
||||
static_assert(T::type_id > 0, "T must be an x11::*Event type");
|
||||
auto write_buffer = x11::Write(event);
|
||||
DCHECK_EQ(write_buffer.GetBuffers().size(), 1ul);
|
||||
auto& first_buffer = write_buffer.GetBuffers()[0];
|
||||
DCHECK_LE(first_buffer->size(), 32ul);
|
||||
std::vector<uint8_t> event_bytes(32);
|
||||
memcpy(event_bytes.data(), first_buffer->data(), first_buffer->size());
|
||||
|
||||
x11::SendEventRequest send_event{false, target, mask};
|
||||
std::copy(event_bytes.begin(), event_bytes.end(), send_event.event.begin());
|
||||
return connection->SendEvent(send_event);
|
||||
}
|
||||
|
||||
COMPONENT_EXPORT(X11)
|
||||
void LogErrorEventDescription(unsigned long serial,
|
||||
uint8_t error_code,
|
||||
|
@ -74,7 +74,7 @@ std::string DriverEGL::GetClientExtensions() {
|
||||
#if defined(USE_GLX)
|
||||
std::string DriverGLX::GetPlatformExtensions() {
|
||||
Display* display = gfx::GetXDisplay();
|
||||
const int screen = (display == EGL_NO_DISPLAY ? 0 : DefaultScreen(display));
|
||||
const int screen = (display == EGL_NO_DISPLAY ? 0 : XDefaultScreen(display));
|
||||
const char* str = glXQueryExtensionsString(display, screen);
|
||||
return str ? std::string(str) : "";
|
||||
}
|
||||
|
@ -16,17 +16,6 @@
|
||||
#if defined(OS_POSIX) && !defined(__STDC_FORMAT_MACROS)
|
||||
#define __STDC_FORMAT_MACROS
|
||||
#endif
|
||||
#if defined(USE_GLX)
|
||||
// Must be included before GL headers or they might pollute the global
|
||||
// namespace with X11 macros indirectly.
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
// GL headers expect Bool and Status this to be defined but we avoid
|
||||
// defining them since they clash with too much code. Instead we have
|
||||
// to add them temporarily here and undef them again below.
|
||||
#define Bool int
|
||||
#define Status int
|
||||
#endif // USE_GLX
|
||||
|
||||
#include <GL/gl.h>
|
||||
#include <GL/glext.h>
|
||||
@ -48,12 +37,19 @@
|
||||
#elif defined(OS_APPLE)
|
||||
#include <OpenGL/OpenGL.h>
|
||||
#elif defined(USE_GLX)
|
||||
#include <GL/glx.h>
|
||||
#include <GL/glxext.h>
|
||||
using XID = unsigned long;
|
||||
using GLXPixmap = XID;
|
||||
using GLXWindow = XID;
|
||||
using GLXDrawable = XID;
|
||||
using GLXPbuffer = XID;
|
||||
using GLXContextID = XID;
|
||||
using GLXContext = struct __GLXcontextRec*;
|
||||
using GLXFBConfig = struct __GLXFBConfigRec*;
|
||||
|
||||
// Done with these temporary macros now
|
||||
#undef Bool
|
||||
#undef Status
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
#include <GL/glxext.h>
|
||||
#include <GL/glxtokens.h>
|
||||
#endif
|
||||
|
||||
// GLES2 defines not part of Desktop GL
|
||||
|
@ -36,7 +36,7 @@ TEST(GLContextGLXTest, MAYBE_DoNotDestroyOnFailedMakeCurrent) {
|
||||
swa.background_pixmap = 0;
|
||||
swa.override_redirect = x11::True;
|
||||
auto xwindow = static_cast<x11::Window>(XCreateWindow(
|
||||
xdisplay, DefaultRootWindow(xdisplay), 0, 0, 10,
|
||||
xdisplay, XDefaultRootWindow(xdisplay), 0, 0, 10,
|
||||
10, // x, y, width, height
|
||||
0, // border width
|
||||
static_cast<int>(x11::WindowClass::CopyFromParent), // depth
|
||||
|
@ -110,7 +110,7 @@ void TraceGLXApi::SetDisabledExtensions(
|
||||
bool GetGLWindowSystemBindingInfoGLX(const GLVersionInfo& gl_info,
|
||||
GLWindowSystemBindingInfo* info) {
|
||||
Display* display = glXGetCurrentDisplay();
|
||||
const int screen = (display ? DefaultScreen(display) : 0);
|
||||
const int screen = (display ? XDefaultScreen(display) : 0);
|
||||
const char* vendor = glXQueryServerString(display, screen, GLX_VENDOR);
|
||||
const char* version = glXQueryServerString(display, screen, GLX_VERSION);
|
||||
const char* extensions = glXQueryExtensionsString(display, screen);
|
||||
|
@ -47,7 +47,7 @@ bool GLImageGLX::Initialize(XID pixmap) {
|
||||
int attrs[] = {GLX_FBCONFIG_ID, static_cast<uint32_t>(fbconfig_id), 0};
|
||||
int nitems;
|
||||
gfx::XScopedPtr<GLXFBConfig> configs(
|
||||
glXChooseFBConfig(display, DefaultScreen(display), attrs, &nitems));
|
||||
glXChooseFBConfig(display, XDefaultScreen(display), attrs, &nitems));
|
||||
if (!nitems)
|
||||
return false;
|
||||
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include "ui/gfx/x/randr.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
#include "ui/gl/egl_util.h"
|
||||
|
||||
namespace gl {
|
||||
@ -117,7 +118,7 @@ bool NativeViewGLSurfaceEGLX11::DispatchXEvent(x11::Event* x11_event) {
|
||||
auto expose_copy = *expose;
|
||||
auto window = static_cast<x11::Window>(window_);
|
||||
expose_copy.window = window;
|
||||
ui::SendEvent(expose_copy, window, x11::EventMask::Exposure);
|
||||
x11::SendEvent(expose_copy, window, x11::EventMask::Exposure);
|
||||
x11::Connection::Get()->Flush();
|
||||
return true;
|
||||
}
|
||||
|
@ -6,6 +6,7 @@
|
||||
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
#include "ui/gl/egl_util.h"
|
||||
|
||||
using ui::GetLastEGLErrorString;
|
||||
@ -153,7 +154,7 @@ bool NativeViewGLSurfaceEGLX11GLES2::DispatchXEvent(x11::Event* x11_event) {
|
||||
|
||||
auto expose_copy = *expose;
|
||||
expose_copy.window = parent_window_;
|
||||
ui::SendEvent(expose_copy, parent_window_, x11::EventMask::Exposure);
|
||||
x11::SendEvent(expose_copy, parent_window_, x11::EventMask::Exposure);
|
||||
x11::Connection::Get()->Flush();
|
||||
return true;
|
||||
}
|
||||
|
@ -34,6 +34,7 @@
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
#include "ui/gfx/x/xf86vidmode.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
#include "ui/gl/gl_bindings.h"
|
||||
#include "ui/gl/gl_context.h"
|
||||
#include "ui/gl/gl_implementation.h"
|
||||
@ -93,7 +94,7 @@ GLXFBConfig GetConfigForWindow(Display* display,
|
||||
|
||||
int num_elements = 0;
|
||||
gfx::XScopedPtr<GLXFBConfig> configs(
|
||||
glXGetFBConfigs(display, DefaultScreen(display), &num_elements));
|
||||
glXGetFBConfigs(display, XDefaultScreen(display), &num_elements));
|
||||
if (!configs.get()) {
|
||||
LOG(ERROR) << "glXGetFBConfigs failed.";
|
||||
return nullptr;
|
||||
@ -601,7 +602,7 @@ void GLSurfaceGLX::ShutdownOneOff() {
|
||||
// static
|
||||
std::string GLSurfaceGLX::QueryGLXExtensions() {
|
||||
Display* display = gfx::GetXDisplay();
|
||||
const int screen = (display ? DefaultScreen(display) : 0);
|
||||
const int screen = (display ? XDefaultScreen(display) : 0);
|
||||
const char* extensions = glXQueryExtensionsString(display, screen);
|
||||
if (extensions) {
|
||||
return std::string(extensions);
|
||||
@ -882,7 +883,7 @@ void NativeViewGLSurfaceGLX::ForwardExposeEvent(x11::Event* event) {
|
||||
auto forwarded_event = *event->As<x11::ExposeEvent>();
|
||||
auto window = static_cast<x11::Window>(parent_window_);
|
||||
forwarded_event.window = window;
|
||||
ui::SendEvent(forwarded_event, window, x11::EventMask::Exposure);
|
||||
x11::SendEvent(forwarded_event, window, x11::EventMask::Exposure);
|
||||
x11::Connection::Get()->Flush();
|
||||
}
|
||||
|
||||
|
@ -2,10 +2,7 @@
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include <gdk/gdkx.h>
|
||||
#include <gtk/gtk.h>
|
||||
#include <stddef.h>
|
||||
|
||||
#include <cstddef>
|
||||
#include <memory>
|
||||
#include <set>
|
||||
|
||||
|
@ -5,7 +5,6 @@
|
||||
#include "ui/gtk/x/gtk_event_loop_x11.h"
|
||||
|
||||
#include <gdk/gdk.h>
|
||||
#include <gdk/gdkx.h>
|
||||
#include <gtk/gtk.h>
|
||||
#include <xcb/xcb.h>
|
||||
#include <xcb/xproto.h>
|
||||
@ -15,6 +14,10 @@
|
||||
#include "ui/gfx/x/event.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
|
||||
extern "C" {
|
||||
Window gdk_x11_window_get_xid(GdkWindow* window);
|
||||
}
|
||||
|
||||
namespace ui {
|
||||
|
||||
namespace {
|
||||
@ -80,8 +83,8 @@ void GtkEventLoopX11::ProcessGdkEventKey(const GdkEventKey& gdk_event_key) {
|
||||
: x11::KeyEvent::Release;
|
||||
if (gdk_event_key.send_event)
|
||||
key_event->response_type |= x11::kSendEventMask;
|
||||
key_event->event = GDK_WINDOW_XID(gdk_event_key.window);
|
||||
key_event->root = DefaultRootWindow(display);
|
||||
key_event->event = gdk_x11_window_get_xid(gdk_event_key.window);
|
||||
key_event->root = XDefaultRootWindow(display);
|
||||
key_event->time = gdk_event_key.time;
|
||||
key_event->detail = gdk_event_key.hardware_keycode;
|
||||
key_event->same_screen = true;
|
||||
|
@ -4,13 +4,8 @@
|
||||
|
||||
#include "ui/gtk/x/gtk_ui_delegate_x11.h"
|
||||
|
||||
#include <gdk/gdkx.h>
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
// gdkx.h includes Xlib.h directly, so we need to manually undef any macros
|
||||
// that conflict with the below includes.
|
||||
#undef None
|
||||
|
||||
#include "base/check.h"
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/events/platform/x11/x11_event_source.h"
|
||||
@ -20,6 +15,16 @@
|
||||
#include "ui/platform_window/x11/x11_window.h"
|
||||
#include "ui/platform_window/x11/x11_window_manager.h"
|
||||
|
||||
extern "C" {
|
||||
GdkWindow* gdk_x11_window_foreign_new_for_display(GdkDisplay* display,
|
||||
Window window);
|
||||
|
||||
GdkWindow* gdk_x11_window_lookup_for_display(GdkDisplay* display,
|
||||
Window window);
|
||||
|
||||
Window gdk_x11_window_get_xid(GdkWindow* window);
|
||||
}
|
||||
|
||||
namespace ui {
|
||||
|
||||
GtkUiDelegateX11::GtkUiDelegateX11(x11::Connection* connection)
|
||||
@ -53,13 +58,13 @@ GdkWindow* GtkUiDelegateX11::GetGdkWindow(gfx::AcceleratedWidget window_id) {
|
||||
|
||||
bool GtkUiDelegateX11::SetGdkWindowTransientFor(GdkWindow* window,
|
||||
gfx::AcceleratedWidget parent) {
|
||||
SetProperty(static_cast<x11::Window>(GDK_WINDOW_XID(window)),
|
||||
x11::Atom::WM_TRANSIENT_FOR, x11::Atom::WINDOW, parent);
|
||||
auto x11_window = static_cast<x11::Window>(gdk_x11_window_get_xid(window));
|
||||
SetProperty(x11_window, x11::Atom::WM_TRANSIENT_FOR, x11::Atom::WINDOW,
|
||||
parent);
|
||||
|
||||
ui::X11Window* parent_window =
|
||||
ui::X11WindowManager::GetInstance()->GetWindow(parent);
|
||||
parent_window->SetTransientWindow(
|
||||
static_cast<x11::Window>(gdk_x11_window_get_xid(window)));
|
||||
parent_window->SetTransientWindow(x11_window);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
@ -16,6 +16,7 @@
|
||||
#include "ui/gfx/x/x11_atom_cache.h"
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
|
||||
using base::Contains;
|
||||
|
||||
@ -183,8 +184,8 @@ bool X11ClipboardOzone::OnSelectionRequest(
|
||||
.target = event.target,
|
||||
.property = event.property,
|
||||
};
|
||||
SendEvent(selection_event, selection_event.requestor,
|
||||
x11::EventMask::NoEvent);
|
||||
x11::SendEvent(selection_event, selection_event.requestor,
|
||||
x11::EventMask::NoEvent);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -23,6 +23,7 @@
|
||||
#include "ui/events/types/event_type.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/event.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
|
@ -20,6 +20,8 @@
|
||||
#include "ui/gfx/transform.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_atom_cache.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/gfx/x/xproto_util.h"
|
||||
#include "ui/platform_window/extensions/x11_extension_delegate.h"
|
||||
|
||||
namespace ui {
|
||||
@ -386,21 +388,10 @@ TEST_F(X11WindowTest, WindowManagerTogglesFullscreen) {
|
||||
// Emulate the window manager exiting fullscreen via a window manager
|
||||
// accelerator key.
|
||||
{
|
||||
XEvent xclient;
|
||||
memset(&xclient, 0, sizeof(xclient));
|
||||
xclient.type = ClientMessage;
|
||||
xclient.xclient.window = static_cast<uint32_t>(x11_window);
|
||||
xclient.xclient.message_type =
|
||||
static_cast<uint32_t>(gfx::GetAtom("_NET_WM_STATE"));
|
||||
xclient.xclient.format = 32;
|
||||
xclient.xclient.data.l[0] = 0;
|
||||
xclient.xclient.data.l[1] =
|
||||
static_cast<uint32_t>(gfx::GetAtom("_NET_WM_STATE_FULLSCREEN"));
|
||||
xclient.xclient.data.l[2] = 0;
|
||||
xclient.xclient.data.l[3] = 1;
|
||||
xclient.xclient.data.l[4] = 0;
|
||||
XSendEvent(display, DefaultRootWindow(display), x11::False,
|
||||
SubstructureRedirectMask | SubstructureNotifyMask, &xclient);
|
||||
ui::SendClientMessage(
|
||||
x11_window, ui::GetX11RootWindow(), gfx::GetAtom("_NET_WM_STATE"),
|
||||
{0, static_cast<uint32_t>(gfx::GetAtom("_NET_WM_STATE_FULLSCREEN")), 0,
|
||||
1, 0});
|
||||
|
||||
WMStateWaiter waiter(x11_window, "_NET_WM_STATE_FULLSCREEN", false);
|
||||
waiter.Wait();
|
||||
@ -448,7 +439,6 @@ TEST_F(X11WindowTest, ToggleMinimizePropogateToPlatformWindowDelegate) {
|
||||
ui::X11EventSource::GetInstance()->DispatchXEvents();
|
||||
|
||||
x11::Window x11_window = window->window();
|
||||
Display* display = gfx::GetXDisplay();
|
||||
|
||||
// Minimize by sending _NET_WM_STATE_HIDDEN
|
||||
{
|
||||
@ -456,18 +446,14 @@ TEST_F(X11WindowTest, ToggleMinimizePropogateToPlatformWindowDelegate) {
|
||||
atom_list.push_back(gfx::GetAtom("_NET_WM_STATE_HIDDEN"));
|
||||
ui::SetAtomArrayProperty(x11_window, "_NET_WM_STATE", "ATOM", atom_list);
|
||||
|
||||
XEvent xevent;
|
||||
memset(&xevent, 0, sizeof(xevent));
|
||||
xevent.type = PropertyNotify;
|
||||
xevent.xproperty.type = PropertyNotify;
|
||||
xevent.xproperty.send_event = 1;
|
||||
xevent.xproperty.display = display;
|
||||
xevent.xproperty.window = static_cast<uint32_t>(x11_window);
|
||||
xevent.xproperty.atom =
|
||||
static_cast<uint32_t>(gfx::GetAtom("_NET_WM_STATE"));
|
||||
xevent.xproperty.state = 0;
|
||||
XSendEvent(display, DefaultRootWindow(display), x11::False,
|
||||
SubstructureRedirectMask | SubstructureNotifyMask, &xevent);
|
||||
x11::PropertyNotifyEvent xevent{
|
||||
.send_event = true,
|
||||
.window = x11_window,
|
||||
.atom = gfx::GetAtom("_NET_WM_STATE"),
|
||||
};
|
||||
x11::SendEvent(xevent, ui::GetX11RootWindow(),
|
||||
x11::EventMask::SubstructureNotify |
|
||||
x11::EventMask::SubstructureRedirect);
|
||||
|
||||
WMStateWaiter waiter(x11_window, "_NET_WM_STATE_HIDDEN", true);
|
||||
waiter.Wait();
|
||||
@ -481,18 +467,14 @@ TEST_F(X11WindowTest, ToggleMinimizePropogateToPlatformWindowDelegate) {
|
||||
atom_list.push_back(gfx::GetAtom("_NET_WM_STATE_FOCUSED"));
|
||||
ui::SetAtomArrayProperty(x11_window, "_NET_WM_STATE", "ATOM", atom_list);
|
||||
|
||||
XEvent xevent;
|
||||
memset(&xevent, 0, sizeof(xevent));
|
||||
xevent.type = PropertyNotify;
|
||||
xevent.xproperty.type = PropertyNotify;
|
||||
xevent.xproperty.send_event = 1;
|
||||
xevent.xproperty.display = display;
|
||||
xevent.xproperty.window = static_cast<uint32_t>(x11_window);
|
||||
xevent.xproperty.atom =
|
||||
static_cast<uint32_t>(gfx::GetAtom("_NET_WM_STATE"));
|
||||
xevent.xproperty.state = 0;
|
||||
XSendEvent(display, DefaultRootWindow(display), x11::False,
|
||||
SubstructureRedirectMask | SubstructureNotifyMask, &xevent);
|
||||
x11::PropertyNotifyEvent xevent{
|
||||
.send_event = true,
|
||||
.window = x11_window,
|
||||
.atom = gfx::GetAtom("_NET_WM_STATE"),
|
||||
};
|
||||
x11::SendEvent(xevent, ui::GetX11RootWindow(),
|
||||
x11::EventMask::SubstructureNotify |
|
||||
x11::EventMask::SubstructureRedirect);
|
||||
|
||||
WMStateWaiter waiter(x11_window, "_NET_WM_STATE_FOCUSED", true);
|
||||
waiter.Wait();
|
||||
|
@ -24,8 +24,11 @@
|
||||
#include "ui/compositor/dip_util.h"
|
||||
#include "ui/events/keycodes/keyboard_code_conversion_x.h"
|
||||
#include "ui/events/test/x11_event_waiter.h"
|
||||
#include "ui/gfx/x/connection.h"
|
||||
#include "ui/gfx/x/keysyms/keysyms.h"
|
||||
#include "ui/gfx/x/x11.h"
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/views/test/test_desktop_screen_x11.h"
|
||||
#include "ui/views/widget/desktop_aura/desktop_window_tree_host_linux.h"
|
||||
|
||||
@ -44,42 +47,15 @@ using ui_controls::UP;
|
||||
// Mask of the buttons currently down.
|
||||
unsigned button_down_mask = 0;
|
||||
|
||||
// Restore Xlib constants that were #undef'ed by gen/ui/gfx/x/xproto.h.
|
||||
constexpr int CopyFromParent = 0;
|
||||
constexpr int InputOnly = 2;
|
||||
constexpr int KeyPress = 2;
|
||||
constexpr int KeyRelease = 3;
|
||||
constexpr int ButtonPress = 4;
|
||||
constexpr int ButtonRelease = 5;
|
||||
constexpr int Button1 = 1;
|
||||
constexpr int Button2 = 2;
|
||||
constexpr int Button3 = 3;
|
||||
|
||||
class UIControlsDesktopX11 : public UIControlsAura {
|
||||
public:
|
||||
UIControlsDesktopX11()
|
||||
: x_display_(gfx::GetXDisplay()),
|
||||
: connection_(x11::Connection::Get()),
|
||||
x_root_window_(ui::GetX11RootWindow()),
|
||||
x_window_(static_cast<x11::Window>(
|
||||
XCreateWindow(x_display_,
|
||||
static_cast<uint32_t>(x_root_window_),
|
||||
-100, // x
|
||||
-100, // y
|
||||
10, // width
|
||||
10, // height
|
||||
0, // border width
|
||||
CopyFromParent, // depth
|
||||
InputOnly,
|
||||
reinterpret_cast<Visual*>(CopyFromParent),
|
||||
0,
|
||||
nullptr))) {
|
||||
XStoreName(x_display_, static_cast<uint32_t>(x_window_),
|
||||
"Chromium UIControlsDesktopX11 Window");
|
||||
}
|
||||
x_window_(
|
||||
ui::CreateDummyWindow("Chromium UIControlsDesktopX11 Window")) {}
|
||||
|
||||
~UIControlsDesktopX11() override {
|
||||
XDestroyWindow(x_display_, static_cast<uint32_t>(x_window_));
|
||||
}
|
||||
~UIControlsDesktopX11() override { connection_->DestroyWindow({x_window_}); }
|
||||
|
||||
bool SendKeyPress(gfx::NativeWindow window,
|
||||
ui::KeyboardCode key,
|
||||
@ -103,9 +79,8 @@ class UIControlsDesktopX11 : public UIControlsAura {
|
||||
|
||||
aura::WindowTreeHost* host = window->GetHost();
|
||||
|
||||
XEvent xevent;
|
||||
xevent.xkey = {};
|
||||
xevent.xkey.type = KeyPress;
|
||||
x11::KeyEvent xevent;
|
||||
xevent.opcode = x11::KeyEvent::Press;
|
||||
if (control) {
|
||||
SetKeycodeAndSendThenMask(host, &xevent, XK_Control_L, ControlMask);
|
||||
}
|
||||
@ -113,21 +88,20 @@ class UIControlsDesktopX11 : public UIControlsAura {
|
||||
SetKeycodeAndSendThenMask(host, &xevent, XK_Shift_L, ShiftMask);
|
||||
if (alt)
|
||||
SetKeycodeAndSendThenMask(host, &xevent, XK_Alt_L, Mod1Mask);
|
||||
xevent.xkey.keycode =
|
||||
XKeysymToKeycode(x_display_, ui::XKeysymForWindowsKeyCode(key, shift));
|
||||
aura::test::PostEventToWindowTreeHost(xevent, host);
|
||||
xevent.detail = x11::Connection::Get()->KeysymToKeycode(
|
||||
static_cast<x11::KeySym>(ui::XKeysymForWindowsKeyCode(key, shift)));
|
||||
aura::test::PostEventToWindowTreeHost(host, &xevent);
|
||||
|
||||
// Send key release events.
|
||||
xevent.xkey.type = KeyRelease;
|
||||
aura::test::PostEventToWindowTreeHost(xevent, host);
|
||||
xevent.opcode = x11::KeyEvent::Release;
|
||||
aura::test::PostEventToWindowTreeHost(host, &xevent);
|
||||
if (alt)
|
||||
UnmaskAndSetKeycodeThenSend(host, &xevent, Mod1Mask, XK_Alt_L);
|
||||
if (shift)
|
||||
UnmaskAndSetKeycodeThenSend(host, &xevent, ShiftMask, XK_Shift_L);
|
||||
if (control) {
|
||||
if (control)
|
||||
UnmaskAndSetKeycodeThenSend(host, &xevent, ControlMask, XK_Control_L);
|
||||
}
|
||||
DCHECK(!xevent.xkey.state);
|
||||
DCHECK_EQ(xevent.state, x11::KeyButMask{});
|
||||
RunClosureAfterAllPendingUIEvents(std::move(closure));
|
||||
return true;
|
||||
}
|
||||
@ -163,16 +137,14 @@ class UIControlsDesktopX11 : public UIControlsAura {
|
||||
// current mouse position as a result of XGrabPointer()
|
||||
root_window->MoveCursorTo(root_location);
|
||||
} else {
|
||||
XEvent xevent;
|
||||
xevent.xmotion = {};
|
||||
XMotionEvent* xmotion = &xevent.xmotion;
|
||||
xmotion->type = MotionNotify;
|
||||
xmotion->x = root_location.x();
|
||||
xmotion->y = root_location.y();
|
||||
xmotion->state = button_down_mask;
|
||||
xmotion->same_screen = x11::True;
|
||||
x11::MotionNotifyEvent xevent{
|
||||
.event_x = root_location.x(),
|
||||
.event_y = root_location.y(),
|
||||
.state = static_cast<x11::KeyButMask>(button_down_mask),
|
||||
.same_screen = true,
|
||||
};
|
||||
// RootWindow will take care of other necessary fields.
|
||||
aura::test::PostEventToWindowTreeHost(xevent, host);
|
||||
aura::test::PostEventToWindowTreeHost(host, &xevent);
|
||||
}
|
||||
RunClosureAfterAllPendingUIEvents(std::move(closure));
|
||||
return true;
|
||||
@ -187,52 +159,51 @@ class UIControlsDesktopX11 : public UIControlsAura {
|
||||
int button_state,
|
||||
base::OnceClosure closure,
|
||||
int accelerator_state) override {
|
||||
XEvent xevent;
|
||||
xevent.xbutton = {};
|
||||
XButtonEvent* xbutton = &xevent.xbutton;
|
||||
x11::ButtonEvent xevent;
|
||||
gfx::Point mouse_loc = aura::Env::GetInstance()->last_mouse_location();
|
||||
aura::Window* root_window = RootWindowForPoint(mouse_loc);
|
||||
aura::client::ScreenPositionClient* screen_position_client =
|
||||
aura::client::GetScreenPositionClient(root_window);
|
||||
if (screen_position_client)
|
||||
screen_position_client->ConvertPointFromScreen(root_window, &mouse_loc);
|
||||
xbutton->x = mouse_loc.x();
|
||||
xbutton->y = mouse_loc.y();
|
||||
xbutton->same_screen = x11::True;
|
||||
xevent.event_x = mouse_loc.x();
|
||||
xevent.event_y = mouse_loc.y();
|
||||
switch (type) {
|
||||
case LEFT:
|
||||
xbutton->button = Button1;
|
||||
xbutton->state = Button1Mask;
|
||||
xevent.detail = static_cast<x11::Button>(1);
|
||||
xevent.state = x11::KeyButMask::Button1;
|
||||
break;
|
||||
case MIDDLE:
|
||||
xbutton->button = Button2;
|
||||
xbutton->state = Button2Mask;
|
||||
xevent.detail = static_cast<x11::Button>(2);
|
||||
xevent.state = x11::KeyButMask::Button2;
|
||||
break;
|
||||
case RIGHT:
|
||||
xbutton->button = Button3;
|
||||
xbutton->state = Button3Mask;
|
||||
xevent.detail = static_cast<x11::Button>(3);
|
||||
xevent.state = x11::KeyButMask::Button3;
|
||||
break;
|
||||
}
|
||||
// Process the accelerator key state.
|
||||
|
||||
// Process accelerator key state.
|
||||
if (accelerator_state & ui_controls::kShift)
|
||||
xbutton->state |= ShiftMask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Shift;
|
||||
if (accelerator_state & ui_controls::kControl)
|
||||
xbutton->state |= ControlMask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Control;
|
||||
if (accelerator_state & ui_controls::kAlt)
|
||||
xbutton->state |= Mod1Mask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Mod1;
|
||||
if (accelerator_state & ui_controls::kCommand)
|
||||
xbutton->state |= Mod4Mask;
|
||||
xevent.state = xevent.state | x11::KeyButMask::Mod4;
|
||||
|
||||
// RootWindow will take care of other necessary fields.
|
||||
if (button_state & DOWN) {
|
||||
xevent.xbutton.type = ButtonPress;
|
||||
aura::test::PostEventToWindowTreeHost(xevent, root_window->GetHost());
|
||||
button_down_mask |= xbutton->state;
|
||||
xevent.opcode = x11::ButtonEvent::Press;
|
||||
aura::test::PostEventToWindowTreeHost(root_window->GetHost(), &xevent);
|
||||
button_down_mask |= static_cast<int>(xevent.state);
|
||||
}
|
||||
if (button_state & UP) {
|
||||
xevent.xbutton.type = ButtonRelease;
|
||||
aura::test::PostEventToWindowTreeHost(xevent, root_window->GetHost());
|
||||
button_down_mask = (button_down_mask | xbutton->state) ^ xbutton->state;
|
||||
xevent.opcode = x11::ButtonEvent::Release;
|
||||
aura::test::PostEventToWindowTreeHost(root_window->GetHost(), &xevent);
|
||||
int state = static_cast<int>(xevent.state);
|
||||
button_down_mask = (button_down_mask | state) ^ state;
|
||||
}
|
||||
RunClosureAfterAllPendingUIEvents(std::move(closure));
|
||||
return true;
|
||||
@ -266,25 +237,28 @@ class UIControlsDesktopX11 : public UIControlsAura {
|
||||
}
|
||||
|
||||
void SetKeycodeAndSendThenMask(aura::WindowTreeHost* host,
|
||||
XEvent* xevent,
|
||||
x11::KeyEvent* xevent,
|
||||
KeySym keysym,
|
||||
unsigned int mask) {
|
||||
xevent->xkey.keycode = XKeysymToKeycode(x_display_, keysym);
|
||||
aura::test::PostEventToWindowTreeHost(*xevent, host);
|
||||
xevent->xkey.state |= mask;
|
||||
xevent->detail = x11::Connection::Get()->KeysymToKeycode(
|
||||
static_cast<x11::KeySym>(keysym));
|
||||
aura::test::PostEventToWindowTreeHost(host, xevent);
|
||||
xevent->state = xevent->state | static_cast<x11::KeyButMask>(mask);
|
||||
}
|
||||
|
||||
void UnmaskAndSetKeycodeThenSend(aura::WindowTreeHost* host,
|
||||
XEvent* xevent,
|
||||
x11::KeyEvent* xevent,
|
||||
unsigned int mask,
|
||||
KeySym keysym) {
|
||||
xevent->xkey.state ^= mask;
|
||||
xevent->xkey.keycode = XKeysymToKeycode(x_display_, keysym);
|
||||
aura::test::PostEventToWindowTreeHost(*xevent, host);
|
||||
xevent->state = static_cast<x11::KeyButMask>(
|
||||
static_cast<uint32_t>(xevent->state) ^ mask);
|
||||
xevent->detail = x11::Connection::Get()->KeysymToKeycode(
|
||||
static_cast<x11::KeySym>(keysym));
|
||||
aura::test::PostEventToWindowTreeHost(host, xevent);
|
||||
}
|
||||
|
||||
// Our X11 state.
|
||||
Display* x_display_;
|
||||
x11::Connection* connection_;
|
||||
x11::Window x_root_window_;
|
||||
|
||||
// Input-only window used for events.
|
||||
|
@ -2,6 +2,7 @@
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include "ui/gfx/x/xproto.h"
|
||||
#include "ui/views/widget/desktop_aura/desktop_window_tree_host_linux.h"
|
||||
|
||||
#include "ui/aura/client/aura_constants.h"
|
||||
@ -71,7 +72,7 @@ void DispatchMouseMotionEvent(DesktopWindowTreeHostLinux* desktop_host,
|
||||
xcb_generic_event_t ge;
|
||||
memset(&ge, 0, sizeof(ge));
|
||||
auto* xev = reinterpret_cast<xcb_motion_notify_event_t*>(&ge);
|
||||
xev->response_type = MotionNotify;
|
||||
xev->response_type = x11::MotionNotifyEvent::opcode;
|
||||
xev->event = static_cast<uint32_t>(desktop_host->GetAcceleratedWidget());
|
||||
xev->root = static_cast<uint32_t>(connection->default_screen().root);
|
||||
xev->child = 0;
|
||||
|
Reference in New Issue
Block a user