opt: format code
fix: correct version message
This commit is contained in:
351
IM.h
351
IM.h
@@ -1,7 +1,7 @@
|
||||
#ifdef IM
|
||||
#include <assert.h>
|
||||
#include <wlr/types/wlr_text_input_v3.h>
|
||||
#include <wlr/types/wlr_input_method_v2.h>
|
||||
#include <wlr/types/wlr_text_input_v3.h>
|
||||
|
||||
/**
|
||||
* The relay structure manages the relationship between text-input and
|
||||
@@ -48,33 +48,30 @@ struct dwl_text_input {
|
||||
struct wl_listener pending_focused_surface_destroy;
|
||||
|
||||
struct wl_listener text_input_enable;
|
||||
//struct wl_listener text_input_commit;
|
||||
//struct wl_listener text_input_disable;
|
||||
// struct wl_listener text_input_commit;
|
||||
// struct wl_listener text_input_disable;
|
||||
struct wl_listener text_input_destroy;
|
||||
};
|
||||
|
||||
|
||||
struct dwl_input_popup {
|
||||
struct dwl_input_method_relay *relay;
|
||||
struct wlr_input_popup_surface_v2 *popup_surface;
|
||||
|
||||
//struct wlr_scene_node *scene;
|
||||
// struct wlr_scene_node *scene;
|
||||
struct wlr_scene_tree *scene;
|
||||
//struct wlr_scene_node *scene_surface;
|
||||
// struct wlr_scene_node *scene_surface;
|
||||
struct wlr_scene_tree *scene_surface;
|
||||
|
||||
int x, y;
|
||||
bool visible;
|
||||
|
||||
|
||||
struct wl_listener popup_map;
|
||||
struct wl_listener popup_unmap;
|
||||
struct wl_listener popup_destroy;
|
||||
//struct wl_listener popup_surface_commit;
|
||||
//struct wl_listener focused_surface_unmap;
|
||||
// struct wl_listener popup_surface_commit;
|
||||
// struct wl_listener focused_surface_unmap;
|
||||
};
|
||||
|
||||
|
||||
void dwl_input_method_relay_init(struct dwl_input_method_relay *relay);
|
||||
// Updates currently focused surface. Surface must belong to the same
|
||||
// seat.
|
||||
@@ -98,21 +95,26 @@ struct dwl_input_method_relay *input_relay;
|
||||
* or if event is from virtual keyboard of the same client as grab.
|
||||
* TODO: see https://github.com/swaywm/wlroots/issues/2322
|
||||
*/
|
||||
static struct wlr_input_method_keyboard_grab_v2 *keyboard_get_im_grab(Keyboard* kb) {
|
||||
static struct wlr_input_method_keyboard_grab_v2 *
|
||||
keyboard_get_im_grab(Keyboard *kb) {
|
||||
struct wlr_input_method_v2 *input_method = input_relay->input_method;
|
||||
struct wlr_virtual_keyboard_v1 *virtual_keyboard =
|
||||
wlr_input_device_get_virtual_keyboard(&kb->wlr_keyboard->base);
|
||||
if (!input_method || !input_method->keyboard_grab || (virtual_keyboard &&
|
||||
if (!input_method || !input_method->keyboard_grab ||
|
||||
(virtual_keyboard &&
|
||||
wl_resource_get_client(virtual_keyboard->resource) ==
|
||||
wl_resource_get_client(input_method->keyboard_grab->resource))) {
|
||||
if (!input_method){
|
||||
wlr_log(WLR_DEBUG, "keypress keyboard_get_im_grab return NULL:no input_method");
|
||||
} else if (!input_method->keyboard_grab){
|
||||
wlr_log(WLR_DEBUG, "keypress keyboard_get_im_grab return NULL:no input_method->keyboard_grab");
|
||||
if (!input_method) {
|
||||
wlr_log(WLR_DEBUG,
|
||||
"keypress keyboard_get_im_grab return NULL:no input_method");
|
||||
} else if (!input_method->keyboard_grab) {
|
||||
wlr_log(WLR_DEBUG, "keypress keyboard_get_im_grab return NULL:no "
|
||||
"input_method->keyboard_grab");
|
||||
}
|
||||
|
||||
if (virtual_keyboard) {
|
||||
wlr_log(WLR_DEBUG, "keypress keyboard_get_im_grab return NULL:virtual_keyboard");
|
||||
wlr_log(WLR_DEBUG,
|
||||
"keypress keyboard_get_im_grab return NULL:virtual_keyboard");
|
||||
}
|
||||
|
||||
return NULL;
|
||||
@@ -121,21 +123,22 @@ static struct wlr_input_method_keyboard_grab_v2 *keyboard_get_im_grab(Keyboard*
|
||||
}
|
||||
|
||||
static void handle_im_grab_keyboard(struct wl_listener *listener, void *data) {
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
input_method_grab_keyboard);
|
||||
//wl_container_of 宏的第二个参数sample, 这里是relay,无须是已经初始化的变量,只要是返回值类型的变量就可以了,这里就是dwl_input_method_relay类型的变量
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, input_method_grab_keyboard);
|
||||
// wl_container_of 宏的第二个参数sample,
|
||||
// 这里是relay,无须是已经初始化的变量,只要是返回值类型的变量就可以了,这里就是dwl_input_method_relay类型的变量
|
||||
struct wlr_input_method_keyboard_grab_v2 *keyboard_grab = data;
|
||||
|
||||
// send modifier state to grab
|
||||
struct wlr_keyboard *active_keyboard = wlr_seat_get_keyboard(seat);
|
||||
if (active_keyboard){
|
||||
wlr_log(WLR_INFO,"im_grab_keyboard");
|
||||
wlr_input_method_keyboard_grab_v2_set_keyboard(keyboard_grab,active_keyboard);
|
||||
wlr_input_method_keyboard_grab_v2_send_modifiers(keyboard_grab, &active_keyboard->modifiers);
|
||||
}
|
||||
else
|
||||
wlr_log(WLR_INFO,"im_grab_keyboard but no active keyboard");
|
||||
|
||||
if (active_keyboard) {
|
||||
wlr_log(WLR_INFO, "im_grab_keyboard");
|
||||
wlr_input_method_keyboard_grab_v2_set_keyboard(keyboard_grab,
|
||||
active_keyboard);
|
||||
wlr_input_method_keyboard_grab_v2_send_modifiers(
|
||||
keyboard_grab, &active_keyboard->modifiers);
|
||||
} else
|
||||
wlr_log(WLR_INFO, "im_grab_keyboard but no active keyboard");
|
||||
|
||||
wl_signal_add(&keyboard_grab->events.destroy,
|
||||
&relay->input_method_keyboard_grab_destroy);
|
||||
@@ -143,11 +146,12 @@ static void handle_im_grab_keyboard(struct wl_listener *listener, void *data) {
|
||||
handle_im_keyboard_grab_destroy;
|
||||
}
|
||||
|
||||
static void handle_im_keyboard_grab_destroy(struct wl_listener *listener, void *data) {
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
input_method_keyboard_grab_destroy);
|
||||
static void handle_im_keyboard_grab_destroy(struct wl_listener *listener,
|
||||
void *data) {
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, input_method_keyboard_grab_destroy);
|
||||
struct wlr_input_method_keyboard_grab_v2 *keyboard_grab = data;
|
||||
wlr_log(WLR_DEBUG,"im_keyboard_grab_destroy");
|
||||
wlr_log(WLR_DEBUG, "im_keyboard_grab_destroy");
|
||||
wl_list_remove(&relay->input_method_keyboard_grab_destroy.link);
|
||||
if (keyboard_grab->keyboard) {
|
||||
// send modifier state to original client
|
||||
@@ -156,9 +160,8 @@ static void handle_im_keyboard_grab_destroy(struct wl_listener *listener, void *
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static struct dwl_text_input *relay_get_focusable_text_input(
|
||||
struct dwl_input_method_relay *relay) {
|
||||
static struct dwl_text_input *
|
||||
relay_get_focusable_text_input(struct dwl_input_method_relay *relay) {
|
||||
struct dwl_text_input *text_input = NULL;
|
||||
wl_list_for_each(text_input, &relay->text_inputs, link) {
|
||||
if (text_input->pending_focused_surface) {
|
||||
@@ -168,8 +171,8 @@ static struct dwl_text_input *relay_get_focusable_text_input(
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static struct dwl_text_input *relay_get_focused_text_input(
|
||||
struct dwl_input_method_relay *relay) {
|
||||
static struct dwl_text_input *
|
||||
relay_get_focused_text_input(struct dwl_input_method_relay *relay) {
|
||||
struct dwl_text_input *text_input = NULL;
|
||||
wl_list_for_each(text_input, &relay->text_inputs, link) {
|
||||
if (text_input->input->focused_surface) {
|
||||
@@ -182,8 +185,8 @@ static struct dwl_text_input *relay_get_focused_text_input(
|
||||
static void handle_im_commit(struct wl_listener *listener, void *data) {
|
||||
struct wlr_input_method_v2 *context;
|
||||
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
input_method_commit);
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, input_method_commit);
|
||||
|
||||
struct dwl_text_input *text_input = relay_get_focused_text_input(relay);
|
||||
if (!text_input) {
|
||||
@@ -197,24 +200,25 @@ static void handle_im_commit(struct wl_listener *listener, void *data) {
|
||||
context->current.preedit.text,
|
||||
context->current.preedit.cursor_begin,
|
||||
context->current.preedit.cursor_end);
|
||||
wlr_log(WLR_DEBUG,"preedit_text: %s", context->current.preedit.text);
|
||||
wlr_log(WLR_DEBUG, "preedit_text: %s", context->current.preedit.text);
|
||||
}
|
||||
if (context->current.commit_text) {
|
||||
wlr_text_input_v3_send_commit_string(text_input->input,
|
||||
context->current.commit_text);
|
||||
wlr_log(WLR_DEBUG,"commit_text: %s", context->current.commit_text);
|
||||
wlr_log(WLR_DEBUG, "commit_text: %s", context->current.commit_text);
|
||||
}
|
||||
if (context->current.delete.before_length
|
||||
|| context->current.delete.after_length) {
|
||||
wlr_text_input_v3_send_delete_surrounding_text(text_input->input,
|
||||
context->current.delete.before_length,
|
||||
if (context->current.delete.before_length ||
|
||||
context->current.delete.after_length) {
|
||||
wlr_text_input_v3_send_delete_surrounding_text(
|
||||
text_input->input, context->current.delete.before_length,
|
||||
context->current.delete.after_length);
|
||||
}
|
||||
wlr_text_input_v3_send_done(text_input->input);
|
||||
}
|
||||
|
||||
static void text_input_set_pending_focused_surface(
|
||||
struct dwl_text_input *text_input, struct wlr_surface *surface) {
|
||||
static void
|
||||
text_input_set_pending_focused_surface(struct dwl_text_input *text_input,
|
||||
struct wlr_surface *surface) {
|
||||
wl_list_remove(&text_input->pending_focused_surface_destroy.link);
|
||||
text_input->pending_focused_surface = surface;
|
||||
|
||||
@@ -229,10 +233,10 @@ static void text_input_set_pending_focused_surface(
|
||||
static void handle_im_destroy(struct wl_listener *listener, void *data) {
|
||||
struct dwl_text_input *text_input;
|
||||
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
input_method_destroy);
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, input_method_destroy);
|
||||
struct wlr_input_method_v2 *context = data;
|
||||
wlr_log(WLR_INFO,"IM destroy");
|
||||
wlr_log(WLR_INFO, "IM destroy");
|
||||
assert(context == relay->input_method);
|
||||
relay->input_method = NULL;
|
||||
|
||||
@@ -254,29 +258,30 @@ static void relay_send_im_state(struct dwl_input_method_relay *relay,
|
||||
return;
|
||||
}
|
||||
// TODO: only send each of those if they were modified
|
||||
wlr_input_method_v2_send_surrounding_text(input_method,
|
||||
input->current.surrounding.text, input->current.surrounding.cursor,
|
||||
input->current.surrounding.anchor);
|
||||
wlr_input_method_v2_send_surrounding_text(
|
||||
input_method, input->current.surrounding.text,
|
||||
input->current.surrounding.cursor, input->current.surrounding.anchor);
|
||||
wlr_input_method_v2_send_text_change_cause(input_method,
|
||||
input->current.text_change_cause);
|
||||
wlr_input_method_v2_send_content_type(input_method,
|
||||
input->current.content_type.hint, input->current.content_type.purpose);
|
||||
input->current.content_type.hint,
|
||||
input->current.content_type.purpose);
|
||||
wlr_input_method_v2_send_done(input_method);
|
||||
// TODO: pass intent, display popup size
|
||||
}
|
||||
|
||||
static void handle_text_input_enable(struct wl_listener *listener, void *data) {
|
||||
struct dwl_text_input *text_input = wl_container_of(listener, text_input,
|
||||
text_input_enable);
|
||||
struct dwl_text_input *text_input =
|
||||
wl_container_of(listener, text_input, text_input_enable);
|
||||
if (text_input->relay->input_method == NULL) {
|
||||
wlr_log(WLR_INFO, "text_input_enable but input method is NULL");
|
||||
return;
|
||||
}
|
||||
|
||||
wlr_log(WLR_INFO,"text_input_enable");
|
||||
wlr_log(WLR_INFO, "text_input_enable");
|
||||
#ifdef XWAYLAND
|
||||
wlr_input_method_v2_send_activate(text_input->relay->input_method);
|
||||
wlr_log(WLR_INFO,"input_method activate for xwayland");
|
||||
wlr_log(WLR_INFO, "input_method activate for xwayland");
|
||||
#endif
|
||||
|
||||
relay_send_im_state(text_input->relay, text_input->input);
|
||||
@@ -284,14 +289,16 @@ static void handle_text_input_enable(struct wl_listener *listener, void *data) {
|
||||
|
||||
/* static void handle_text_input_commit(struct wl_listener *listener, */
|
||||
/* void *data) { */
|
||||
/* struct dwl_text_input *text_input = wl_container_of(listener, text_input, */
|
||||
/* struct dwl_text_input *text_input = wl_container_of(listener,
|
||||
* text_input, */
|
||||
/* text_input_commit); */
|
||||
/* if (!text_input->input->current_enabled) { */
|
||||
/* wlr_log(WLR_INFO, "text_input_commit but not enabled"); */
|
||||
/* return; */
|
||||
/* } */
|
||||
/* if (text_input->relay->input_method == NULL) { */
|
||||
/* wlr_log(WLR_INFO, "text_input_commit but input method is NULL"); */
|
||||
/* wlr_log(WLR_INFO, "text_input_commit but input method is NULL");
|
||||
*/
|
||||
/* return; */
|
||||
/* } */
|
||||
/* wlr_log(WLR_DEBUG, "text_input_commit"); */
|
||||
@@ -304,35 +311,34 @@ static void relay_disable_text_input(struct dwl_input_method_relay *relay,
|
||||
wlr_log(WLR_INFO, "text_input_disable, but input method is NULL");
|
||||
return;
|
||||
}
|
||||
wlr_log(WLR_INFO,"text_input_disable");
|
||||
wlr_log(WLR_INFO, "text_input_disable");
|
||||
|
||||
#ifdef XWAYLAND
|
||||
// https://gitee.com/guyuming76/dwl/commit/59328d6ecbbef1b1cd6e5ea8d90d78ccddd5c263
|
||||
wlr_input_method_v2_send_deactivate(relay->input_method);
|
||||
wlr_log(WLR_INFO,"input_method deactivate for xwayland");
|
||||
wlr_log(WLR_INFO, "input_method deactivate for xwayland");
|
||||
#endif
|
||||
//but if you keep the line above while remove the line below, input Chinese in geogebra(xwayland) won't work
|
||||
// but if you keep the line above while remove the line below, input Chinese
|
||||
// in geogebra(xwayland) won't work
|
||||
relay_send_im_state(relay, text_input->input);
|
||||
}
|
||||
|
||||
|
||||
static void handle_text_input_destroy(struct wl_listener *listener,
|
||||
void *data) {
|
||||
struct dwl_text_input *text_input = wl_container_of(listener, text_input,
|
||||
text_input_destroy);
|
||||
struct dwl_text_input *text_input =
|
||||
wl_container_of(listener, text_input, text_input_destroy);
|
||||
|
||||
if (text_input->input->current_enabled) {
|
||||
wlr_log(WLR_INFO,"text_input_destroy when still enabled");
|
||||
wlr_log(WLR_INFO, "text_input_destroy when still enabled");
|
||||
relay_disable_text_input(text_input->relay, text_input);
|
||||
}
|
||||
else {
|
||||
wlr_log(WLR_INFO,"text_input_destroy");
|
||||
} else {
|
||||
wlr_log(WLR_INFO, "text_input_destroy");
|
||||
}
|
||||
|
||||
text_input_set_pending_focused_surface(text_input, NULL);
|
||||
//wl_list_remove(&text_input->text_input_commit.link);
|
||||
// wl_list_remove(&text_input->text_input_commit.link);
|
||||
wl_list_remove(&text_input->text_input_destroy.link);
|
||||
//wl_list_remove(&text_input->text_input_disable.link);
|
||||
// wl_list_remove(&text_input->text_input_disable.link);
|
||||
wl_list_remove(&text_input->text_input_enable.link);
|
||||
wl_list_remove(&text_input->link);
|
||||
free(text_input);
|
||||
@@ -340,8 +346,8 @@ static void handle_text_input_destroy(struct wl_listener *listener,
|
||||
|
||||
static void handle_pending_focused_surface_destroy(struct wl_listener *listener,
|
||||
void *data) {
|
||||
struct dwl_text_input *text_input = wl_container_of(listener, text_input,
|
||||
pending_focused_surface_destroy);
|
||||
struct dwl_text_input *text_input =
|
||||
wl_container_of(listener, text_input, pending_focused_surface_destroy);
|
||||
struct wlr_surface *surface = data;
|
||||
assert(text_input->pending_focused_surface == surface);
|
||||
text_input->pending_focused_surface = NULL;
|
||||
@@ -349,11 +355,10 @@ static void handle_pending_focused_surface_destroy(struct wl_listener *listener,
|
||||
wl_list_init(&text_input->pending_focused_surface_destroy.link);
|
||||
}
|
||||
|
||||
|
||||
static void relay_handle_text_input_new(struct wl_listener *listener,
|
||||
void *data) {
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
text_input_new);
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, text_input_new);
|
||||
struct wlr_text_input_v3 *wlr_text_input = data;
|
||||
if (seat != wlr_text_input->seat) {
|
||||
return;
|
||||
@@ -374,8 +379,8 @@ static void relay_handle_text_input_new(struct wl_listener *listener,
|
||||
input->text_input_enable.notify = handle_text_input_enable;
|
||||
wl_signal_add(&wlr_text_input->events.enable, &input->text_input_enable);
|
||||
|
||||
//input->text_input_commit.notify = handle_text_input_commit;
|
||||
//wl_signal_add(&text_input->events.commit, &input->text_input_commit);
|
||||
// input->text_input_commit.notify = handle_text_input_commit;
|
||||
// wl_signal_add(&text_input->events.commit, &input->text_input_commit);
|
||||
|
||||
/* input->text_input_disable.notify = handle_text_input_disable; */
|
||||
/* wl_signal_add(&text_input->events.disable, &input->text_input_disable); */
|
||||
@@ -388,58 +393,73 @@ static void relay_handle_text_input_new(struct wl_listener *listener,
|
||||
wl_list_init(&input->pending_focused_surface_destroy.link);
|
||||
}
|
||||
|
||||
|
||||
static LayerSurface* layer_surface_from_wlr_layer_surface_v1(
|
||||
struct wlr_layer_surface_v1* layer_surface) {
|
||||
static LayerSurface *layer_surface_from_wlr_layer_surface_v1(
|
||||
struct wlr_layer_surface_v1 *layer_surface) {
|
||||
return layer_surface->data;
|
||||
}
|
||||
|
||||
|
||||
static void get_parent_and_output_box(struct wlr_surface *focused_surface,
|
||||
struct wlr_box *parent, struct wlr_box *output_box) {
|
||||
struct wlr_box *parent,
|
||||
struct wlr_box *output_box) {
|
||||
struct wlr_output *output;
|
||||
struct wlr_box output_box_tmp;
|
||||
struct wlr_layer_surface_v1 *layer_surface;
|
||||
Client *client = NULL;
|
||||
LayerSurface *l = NULL;
|
||||
|
||||
if ((layer_surface=wlr_layer_surface_v1_try_from_wlr_surface(focused_surface))) {
|
||||
LayerSurface* layer =
|
||||
if ((layer_surface =
|
||||
wlr_layer_surface_v1_try_from_wlr_surface(focused_surface))) {
|
||||
LayerSurface *layer =
|
||||
layer_surface_from_wlr_layer_surface_v1(layer_surface);
|
||||
output = layer->layer_surface->output;
|
||||
wlr_output_layout_get_box(output_layout, output,&output_box_tmp);
|
||||
wlr_output_layout_get_box(output_layout, output, &output_box_tmp);
|
||||
*parent = layer->geom;
|
||||
parent->x += output_box_tmp.x;
|
||||
parent->y += output_box_tmp.y;
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box layersurface output_box_tmp->x %d y %d",output_box_tmp.x, output_box_tmp.y);
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box layersurface parent->x %d y %d",parent->x,parent->y);
|
||||
wlr_log(WLR_INFO,
|
||||
"get_parent_and_output_box layersurface output_box_tmp->x %d y %d",
|
||||
output_box_tmp.x, output_box_tmp.y);
|
||||
wlr_log(WLR_INFO,
|
||||
"get_parent_and_output_box layersurface parent->x %d y %d",
|
||||
parent->x, parent->y);
|
||||
} else {
|
||||
toplevel_from_wlr_surface(focused_surface, &client, &l);
|
||||
|
||||
output = wlr_output_layout_output_at(output_layout,
|
||||
client->geom.x, client->geom.y);
|
||||
wlr_output_layout_get_box(output_layout, output,&output_box_tmp);
|
||||
output = wlr_output_layout_output_at(output_layout, client->geom.x,
|
||||
client->geom.y);
|
||||
wlr_output_layout_get_box(output_layout, output, &output_box_tmp);
|
||||
|
||||
parent->x = client->geom.x + client->bw;
|
||||
parent->y = client->geom.y + client->bw;
|
||||
parent->width = client->geom.width;
|
||||
parent->height = client->geom.height;
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box client output_box_tmp->x %d y %d",output_box_tmp.x, output_box_tmp.y);
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box client client->geom.x %d y %d",client->geom.x,client->geom.y);
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box client client->bw %d",client->bw);
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box client parent->x %d y %d",parent->x,parent->y);
|
||||
wlr_log(WLR_INFO,
|
||||
"get_parent_and_output_box client output_box_tmp->x %d y %d",
|
||||
output_box_tmp.x, output_box_tmp.y);
|
||||
wlr_log(WLR_INFO,
|
||||
"get_parent_and_output_box client client->geom.x %d y %d",
|
||||
client->geom.x, client->geom.y);
|
||||
wlr_log(WLR_INFO, "get_parent_and_output_box client client->bw %d",
|
||||
client->bw);
|
||||
wlr_log(WLR_INFO, "get_parent_and_output_box client parent->x %d y %d",
|
||||
parent->x, parent->y);
|
||||
}
|
||||
|
||||
//*output_box = output_box_tmp;
|
||||
memcpy(output_box,&output_box_tmp,sizeof(struct wlr_box));
|
||||
wlr_log(WLR_INFO,"get_parent_and_output_box output_box x %d y %d width %d height %d",output_box->x,output_box->y,output_box->width,output_box->height);
|
||||
memcpy(output_box, &output_box_tmp, sizeof(struct wlr_box));
|
||||
wlr_log(WLR_INFO,
|
||||
"get_parent_and_output_box output_box x %d y %d width %d height %d",
|
||||
output_box->x, output_box->y, output_box->width, output_box->height);
|
||||
}
|
||||
|
||||
// 如果当前focused wlr_text_input_v3.features 满足 WLR_TEXT_INPUT_V3_FEATURE_CURSOR_RECTANGLE, 不含这个feature就弹出在父窗口左上角
|
||||
// 根据 wlr_text_input_v3.current.cursor_rectangle 计算出一个wlr_box
|
||||
// 再调用 wlr_input_popup_surface_v2_send_text_input_rectangle 和 wlr_scene_node_set_position
|
||||
// 如果当前focused wlr_text_input_v3.features 满足
|
||||
// WLR_TEXT_INPUT_V3_FEATURE_CURSOR_RECTANGLE,
|
||||
// 不含这个feature就弹出在父窗口左上角 根据
|
||||
// wlr_text_input_v3.current.cursor_rectangle 计算出一个wlr_box 再调用
|
||||
// wlr_input_popup_surface_v2_send_text_input_rectangle 和
|
||||
// wlr_scene_node_set_position
|
||||
static void input_popup_update(struct dwl_input_popup *popup) {
|
||||
struct wlr_surface* focused_surface;
|
||||
struct wlr_surface *focused_surface;
|
||||
struct wlr_box output_box, parent, input_cursor;
|
||||
int x1, x2, y1, y2, x, y, available_right, available_left, available_down,
|
||||
available_up, popup_width, popup_height;
|
||||
@@ -447,18 +467,19 @@ static void input_popup_update(struct dwl_input_popup *popup) {
|
||||
|
||||
struct dwl_text_input *text_input =
|
||||
relay_get_focused_text_input(popup->relay);
|
||||
if (!text_input|| !text_input->input->focused_surface) {
|
||||
if (!text_input || !text_input->input->focused_surface) {
|
||||
return;
|
||||
}
|
||||
|
||||
//TODO: https://gitlab.freedesktop.org/wlroots/wlroots/-/commit/743da5c0ae723098fe772aadb93810f60e700ab9
|
||||
// TODO:
|
||||
// https://gitlab.freedesktop.org/wlroots/wlroots/-/commit/743da5c0ae723098fe772aadb93810f60e700ab9
|
||||
|
||||
if (!popup->popup_surface->surface->mapped) {
|
||||
return;
|
||||
}
|
||||
|
||||
cursor_rect = text_input->input->current.features
|
||||
& WLR_TEXT_INPUT_V3_FEATURE_CURSOR_RECTANGLE;
|
||||
cursor_rect = text_input->input->current.features &
|
||||
WLR_TEXT_INPUT_V3_FEATURE_CURSOR_RECTANGLE;
|
||||
|
||||
focused_surface = text_input->input->focused_surface;
|
||||
input_cursor = text_input->input->current.cursor_rectangle;
|
||||
@@ -473,14 +494,16 @@ static void input_popup_update(struct dwl_input_popup *popup) {
|
||||
input_cursor.y = 0;
|
||||
input_cursor.width = parent.width;
|
||||
input_cursor.height = parent.height;
|
||||
wlr_log(WLR_INFO,"input_popup_update !cursor_rect");
|
||||
wlr_log(WLR_INFO, "input_popup_update !cursor_rect");
|
||||
|
||||
popup->x=parent.x;
|
||||
popup->y=parent.y;
|
||||
popup->visible=true;
|
||||
}
|
||||
else {
|
||||
wlr_log(WLR_INFO,"input_popup_update input_cursor x %d y %d width %d height %d",input_cursor.x,input_cursor.y,input_cursor.width,input_cursor.height);
|
||||
popup->x = parent.x;
|
||||
popup->y = parent.y;
|
||||
popup->visible = true;
|
||||
} else {
|
||||
wlr_log(WLR_INFO,
|
||||
"input_popup_update input_cursor x %d y %d width %d height %d",
|
||||
input_cursor.x, input_cursor.y, input_cursor.width,
|
||||
input_cursor.height);
|
||||
|
||||
x1 = parent.x + input_cursor.x;
|
||||
x2 = parent.x + input_cursor.x + input_cursor.width;
|
||||
@@ -489,19 +512,26 @@ static void input_popup_update(struct dwl_input_popup *popup) {
|
||||
x = x1;
|
||||
y = y2;
|
||||
|
||||
wlr_log(WLR_INFO,"input_popup_update x1 %d x2 %d y1 %d y2 %d; x %d y %d",x1,x2,y1,y2,x,y);
|
||||
wlr_log(WLR_INFO, "input_popup_update x1 %d x2 %d y1 %d y2 %d; x %d y %d",
|
||||
x1, x2, y1, y2, x, y);
|
||||
available_right = output_box.x + output_box.width - x1;
|
||||
available_left = x2 - output_box.x;
|
||||
if (available_right < popup_width && available_left > available_right) {
|
||||
x = x2 - popup_width;
|
||||
wlr_log(WLR_INFO,"input_popup_update available_left %d popup_width %d available_right %d; x %d",available_left,popup_width,available_right,x);
|
||||
wlr_log(WLR_INFO,
|
||||
"input_popup_update available_left %d popup_width %d "
|
||||
"available_right %d; x %d",
|
||||
available_left, popup_width, available_right, x);
|
||||
}
|
||||
|
||||
available_down = output_box.y + output_box.height - y2;
|
||||
available_up = y1 - output_box.y;
|
||||
if (available_down < popup_height && available_up > available_down) {
|
||||
y = y1 - popup_height;
|
||||
wlr_log(WLR_INFO,"input_popup_update available up %d popup_height %d available_down %d; y %d",available_up,popup_height,available_down,y);
|
||||
wlr_log(WLR_INFO,
|
||||
"input_popup_update available up %d popup_height %d "
|
||||
"available_down %d; y %d",
|
||||
available_up, popup_height, available_down, y);
|
||||
}
|
||||
|
||||
popup->x = x;
|
||||
@@ -510,10 +540,10 @@ static void input_popup_update(struct dwl_input_popup *popup) {
|
||||
// Hide popup if input_cursor position is completely out of bounds
|
||||
x1_in_bounds = (input_cursor.x >= 0 && input_cursor.x < parent.width);
|
||||
y1_in_bounds = (input_cursor.y >= 0 && input_cursor.y < parent.height);
|
||||
x2_in_bounds = (input_cursor.x + input_cursor.width >= 0
|
||||
&& input_cursor.x + input_cursor.width < parent.width);
|
||||
y2_in_bounds = (input_cursor.y + input_cursor.height >= 0
|
||||
&& input_cursor.y + input_cursor.height < parent.height);
|
||||
x2_in_bounds = (input_cursor.x + input_cursor.width >= 0 &&
|
||||
input_cursor.x + input_cursor.width < parent.width);
|
||||
y2_in_bounds = (input_cursor.y + input_cursor.height >= 0 &&
|
||||
input_cursor.y + input_cursor.height < parent.height);
|
||||
popup->visible =
|
||||
(x1_in_bounds && y1_in_bounds) || (x2_in_bounds && y2_in_bounds);
|
||||
|
||||
@@ -523,40 +553,42 @@ static void input_popup_update(struct dwl_input_popup *popup) {
|
||||
.width = input_cursor.width,
|
||||
.height = input_cursor.height,
|
||||
};
|
||||
wlr_input_popup_surface_v2_send_text_input_rectangle(
|
||||
popup->popup_surface, &box);
|
||||
wlr_log(WLR_INFO,"input_popup_update send_text_input_rect box.x %d box.y %d",box.x,box.y);
|
||||
|
||||
wlr_input_popup_surface_v2_send_text_input_rectangle(popup->popup_surface,
|
||||
&box);
|
||||
wlr_log(WLR_INFO,
|
||||
"input_popup_update send_text_input_rect box.x %d box.y %d", box.x,
|
||||
box.y);
|
||||
}
|
||||
|
||||
wlr_log(WLR_INFO,"input_popup_update x %d y %d visible %s",popup->x,popup->y,popup->visible?"true":"false");
|
||||
wlr_log(WLR_INFO, "input_popup_update x %d y %d visible %s", popup->x,
|
||||
popup->y, popup->visible ? "true" : "false");
|
||||
wlr_scene_node_set_position(&popup->scene->node, popup->x, popup->y);
|
||||
}
|
||||
|
||||
static void handle_im_popup_map(struct wl_listener *listener, void *data) {
|
||||
struct dwl_input_popup *popup =
|
||||
wl_container_of(listener, popup, popup_map);
|
||||
struct dwl_input_popup *popup = wl_container_of(listener, popup, popup_map);
|
||||
|
||||
wlr_log(WLR_INFO, "IM_popup_map");
|
||||
|
||||
//popup->scene = &wlr_scene_tree_create(layers[LyrIMPopup])->node;
|
||||
// popup->scene = &wlr_scene_tree_create(layers[LyrIMPopup])->node;
|
||||
popup->scene = wlr_scene_tree_create(layers[LyrIMPopup]);
|
||||
popup->scene_surface = wlr_scene_subsurface_tree_create(popup->scene,popup->popup_surface->surface);
|
||||
//popup->scene_surface = &wlr_scene_subsurface_tree_create(popup->scene->parent,popup->popup_surface->surface)->node;
|
||||
//popup->scene_surface->data = popup;
|
||||
popup->scene_surface = wlr_scene_subsurface_tree_create(
|
||||
popup->scene, popup->popup_surface->surface);
|
||||
// popup->scene_surface =
|
||||
// &wlr_scene_subsurface_tree_create(popup->scene->parent,popup->popup_surface->surface)->node;
|
||||
// popup->scene_surface->data = popup;
|
||||
popup->scene_surface->node.data = popup;
|
||||
|
||||
input_popup_update(popup);
|
||||
|
||||
//wlr_scene_node_set_position(popup->scene, popup->x, popup->y);
|
||||
// wlr_scene_node_set_position(popup->scene, popup->x, popup->y);
|
||||
}
|
||||
|
||||
static void handle_im_popup_unmap(struct wl_listener *listener, void *data) {
|
||||
struct dwl_input_popup *popup =
|
||||
wl_container_of(listener, popup, popup_unmap);
|
||||
//input_popup_update(popup);
|
||||
struct dwl_input_popup *popup = wl_container_of(listener, popup, popup_unmap);
|
||||
// input_popup_update(popup);
|
||||
|
||||
wlr_log(WLR_INFO,"im_popup_unmap");
|
||||
wlr_log(WLR_INFO, "im_popup_unmap");
|
||||
wlr_scene_node_destroy(&popup->scene->node);
|
||||
}
|
||||
|
||||
@@ -565,23 +597,23 @@ static void handle_im_popup_destroy(struct wl_listener *listener, void *data) {
|
||||
struct dwl_input_popup *popup =
|
||||
wl_container_of(listener, popup, popup_destroy);
|
||||
|
||||
wlr_log(WLR_INFO,"im_popup_destroy");
|
||||
wlr_log(WLR_INFO, "im_popup_destroy");
|
||||
|
||||
wl_list_remove(&popup->popup_destroy.link);
|
||||
wl_list_remove(&popup->popup_unmap.link);
|
||||
wl_list_remove(&popup->popup_map.link);
|
||||
|
||||
relay=popup->relay;
|
||||
relay = popup->relay;
|
||||
free(popup->relay->popup);
|
||||
relay->popup=NULL;
|
||||
relay->popup = NULL;
|
||||
}
|
||||
|
||||
|
||||
static void handle_im_new_popup_surface(struct wl_listener *listener, void *data) {
|
||||
static void handle_im_new_popup_surface(struct wl_listener *listener,
|
||||
void *data) {
|
||||
// struct dwl_text_input* text_input;
|
||||
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
input_method_new_popup_surface);
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, input_method_new_popup_surface);
|
||||
struct dwl_input_popup *popup = calloc(1, sizeof(*popup));
|
||||
|
||||
wlr_log(WLR_INFO, "IM_new_popup_surface");
|
||||
@@ -591,39 +623,39 @@ static void handle_im_new_popup_surface(struct wl_listener *listener, void *data
|
||||
popup->popup_surface = data;
|
||||
popup->popup_surface->data = popup;
|
||||
|
||||
|
||||
wl_signal_add(&popup->popup_surface->surface->events.map, &popup->popup_map);
|
||||
popup->popup_map.notify = handle_im_popup_map;
|
||||
|
||||
wl_signal_add(&popup->popup_surface->surface->events.unmap, &popup->popup_unmap);
|
||||
wl_signal_add(&popup->popup_surface->surface->events.unmap,
|
||||
&popup->popup_unmap);
|
||||
popup->popup_unmap.notify = handle_im_popup_unmap;
|
||||
|
||||
wl_signal_add(
|
||||
&popup->popup_surface->events.destroy, &popup->popup_destroy);
|
||||
wl_signal_add(&popup->popup_surface->events.destroy, &popup->popup_destroy);
|
||||
popup->popup_destroy.notify = handle_im_popup_destroy;
|
||||
}
|
||||
|
||||
|
||||
static void relay_handle_input_method_new(struct wl_listener *listener,
|
||||
void *data) {
|
||||
struct dwl_text_input *text_input;
|
||||
|
||||
struct dwl_input_method_relay *relay = wl_container_of(listener, relay,
|
||||
input_method_new);
|
||||
struct dwl_input_method_relay *relay =
|
||||
wl_container_of(listener, relay, input_method_new);
|
||||
|
||||
struct wlr_input_method_v2 *input_method = data;
|
||||
if (seat != input_method->seat) {
|
||||
wlr_log(WLR_INFO,"input_method_new Seat does not match");
|
||||
wlr_log(WLR_INFO, "input_method_new Seat does not match");
|
||||
return;
|
||||
}
|
||||
|
||||
if (relay->input_method != NULL) {
|
||||
wlr_log(WLR_INFO, "input_method_new Attempted to connect second input method to a seat");
|
||||
wlr_log(
|
||||
WLR_INFO,
|
||||
"input_method_new Attempted to connect second input method to a seat");
|
||||
wlr_input_method_v2_send_unavailable(input_method);
|
||||
return;
|
||||
}
|
||||
|
||||
wlr_log(WLR_INFO,"input_method_new");
|
||||
wlr_log(WLR_INFO, "input_method_new");
|
||||
|
||||
relay->input_method = input_method;
|
||||
wl_signal_add(&relay->input_method->events.commit,
|
||||
@@ -652,11 +684,10 @@ static void relay_handle_input_method_new(struct wl_listener *listener,
|
||||
void dwl_input_method_relay_init(struct dwl_input_method_relay *relay) {
|
||||
wl_list_init(&relay->text_inputs);
|
||||
|
||||
relay->popup=NULL;
|
||||
relay->popup = NULL;
|
||||
|
||||
relay->text_input_new.notify = relay_handle_text_input_new;
|
||||
wl_signal_add(&text_input_manager->events.text_input,
|
||||
&relay->text_input_new);
|
||||
wl_signal_add(&text_input_manager->events.text_input, &relay->text_input_new);
|
||||
|
||||
relay->input_method_new.notify = relay_handle_input_method_new;
|
||||
wl_signal_add(&input_method_manager->events.input_method,
|
||||
@@ -684,13 +715,13 @@ void dwl_input_method_relay_set_focus(struct dwl_input_method_relay *relay,
|
||||
}
|
||||
}
|
||||
|
||||
if (surface
|
||||
&& wl_resource_get_client(text_input->input->resource)
|
||||
== wl_resource_get_client(surface->resource)) {
|
||||
if (surface && wl_resource_get_client(text_input->input->resource) ==
|
||||
wl_resource_get_client(surface->resource)) {
|
||||
if (relay->input_method) {
|
||||
wlr_text_input_v3_send_enter(text_input->input, surface);
|
||||
wlr_log(WLR_INFO, "wlr_text_input_send_enter");
|
||||
if (relay->popup) input_popup_update(relay->popup);
|
||||
if (relay->popup)
|
||||
input_popup_update(relay->popup);
|
||||
} else {
|
||||
text_input_set_pending_focused_surface(text_input, surface);
|
||||
}
|
||||
|
||||
177
client.h
177
client.h
@@ -6,18 +6,14 @@
|
||||
*/
|
||||
|
||||
/* Leave these functions first; they're used in the others */
|
||||
static inline int
|
||||
client_is_x11(Client *c)
|
||||
{
|
||||
static inline int client_is_x11(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
return c->type == X11;
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline struct wlr_surface *
|
||||
client_surface(Client *c)
|
||||
{
|
||||
static inline struct wlr_surface *client_surface(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return c->surface.xwayland->surface;
|
||||
@@ -25,9 +21,8 @@ client_surface(Client *c)
|
||||
return c->surface.xdg->surface;
|
||||
}
|
||||
|
||||
static inline int
|
||||
toplevel_from_wlr_surface(struct wlr_surface *s, Client **pc, LayerSurface **pl)
|
||||
{
|
||||
static inline int toplevel_from_wlr_surface(struct wlr_surface *s, Client **pc,
|
||||
LayerSurface **pl) {
|
||||
struct wlr_xdg_surface *xdg_surface, *tmp_xdg_surface;
|
||||
struct wlr_surface *root_surface;
|
||||
struct wlr_layer_surface_v1 *layer_surface;
|
||||
@@ -50,7 +45,8 @@ toplevel_from_wlr_surface(struct wlr_surface *s, Client **pc, LayerSurface **pl)
|
||||
}
|
||||
#endif
|
||||
|
||||
if ((layer_surface = wlr_layer_surface_v1_try_from_wlr_surface(root_surface))) {
|
||||
if ((layer_surface =
|
||||
wlr_layer_surface_v1_try_from_wlr_surface(root_surface))) {
|
||||
l = layer_surface->data;
|
||||
type = LayerShell;
|
||||
goto end;
|
||||
@@ -64,7 +60,8 @@ toplevel_from_wlr_surface(struct wlr_surface *s, Client **pc, LayerSurface **pl)
|
||||
if (!xdg_surface->popup || !xdg_surface->popup->parent)
|
||||
return -1;
|
||||
|
||||
tmp_xdg_surface = wlr_xdg_surface_try_from_wlr_surface(xdg_surface->popup->parent);
|
||||
tmp_xdg_surface =
|
||||
wlr_xdg_surface_try_from_wlr_surface(xdg_surface->popup->parent);
|
||||
|
||||
if (!tmp_xdg_surface)
|
||||
return toplevel_from_wlr_surface(xdg_surface->popup->parent, pc, pl);
|
||||
@@ -89,9 +86,8 @@ end:
|
||||
}
|
||||
|
||||
/* The others */
|
||||
static inline void
|
||||
client_activate_surface(struct wlr_surface *s, int activated)
|
||||
{
|
||||
static inline void client_activate_surface(struct wlr_surface *s,
|
||||
int activated) {
|
||||
struct wlr_xdg_toplevel *toplevel;
|
||||
#ifdef XWAYLAND
|
||||
struct wlr_xwayland_surface *xsurface;
|
||||
@@ -104,16 +100,16 @@ client_activate_surface(struct wlr_surface *s, int activated)
|
||||
wlr_xdg_toplevel_set_activated(toplevel, activated);
|
||||
}
|
||||
|
||||
static inline uint32_t
|
||||
client_set_bounds(Client *c, int32_t width, int32_t height)
|
||||
{
|
||||
static inline uint32_t client_set_bounds(Client *c, int32_t width,
|
||||
int32_t height) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return 0;
|
||||
#endif
|
||||
if (wl_resource_get_version(c->surface.xdg->toplevel->resource) >=
|
||||
XDG_TOPLEVEL_CONFIGURE_BOUNDS_SINCE_VERSION && width >= 0 && height >= 0
|
||||
&& (c->bounds.width != width || c->bounds.height != height)) {
|
||||
XDG_TOPLEVEL_CONFIGURE_BOUNDS_SINCE_VERSION &&
|
||||
width >= 0 && height >= 0 &&
|
||||
(c->bounds.width != width || c->bounds.height != height)) {
|
||||
c->bounds.width = width;
|
||||
c->bounds.height = height;
|
||||
return wlr_xdg_toplevel_set_bounds(c->surface.xdg->toplevel, width, height);
|
||||
@@ -121,9 +117,7 @@ client_set_bounds(Client *c, int32_t width, int32_t height)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline const char *
|
||||
client_get_appid(Client *c)
|
||||
{
|
||||
static inline const char *client_get_appid(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return c->surface.xwayland->class;
|
||||
@@ -131,9 +125,7 @@ client_get_appid(Client *c)
|
||||
return c->surface.xdg->toplevel->app_id;
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_get_clip(Client *c, struct wlr_box *clip)
|
||||
{
|
||||
static inline void client_get_clip(Client *c, struct wlr_box *clip) {
|
||||
struct wlr_box xdg_geom = {0};
|
||||
*clip = (struct wlr_box){
|
||||
.x = 0,
|
||||
@@ -152,9 +144,7 @@ client_get_clip(Client *c, struct wlr_box *clip)
|
||||
clip->y = xdg_geom.y;
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_get_geometry(Client *c, struct wlr_box *geom)
|
||||
{
|
||||
static inline void client_get_geometry(Client *c, struct wlr_box *geom) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c)) {
|
||||
geom->x = c->surface.xwayland->x;
|
||||
@@ -167,9 +157,7 @@ client_get_geometry(Client *c, struct wlr_box *geom)
|
||||
wlr_xdg_surface_get_geometry(c->surface.xdg, geom);
|
||||
}
|
||||
|
||||
static inline Client *
|
||||
client_get_parent(Client *c)
|
||||
{
|
||||
static inline Client *client_get_parent(Client *c) {
|
||||
Client *p = NULL;
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c)) {
|
||||
@@ -179,13 +167,12 @@ client_get_parent(Client *c)
|
||||
}
|
||||
#endif
|
||||
if (c->surface.xdg->toplevel->parent)
|
||||
toplevel_from_wlr_surface(c->surface.xdg->toplevel->parent->base->surface, &p, NULL);
|
||||
toplevel_from_wlr_surface(c->surface.xdg->toplevel->parent->base->surface,
|
||||
&p, NULL);
|
||||
return p;
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_has_children(Client *c)
|
||||
{
|
||||
static inline int client_has_children(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return !wl_list_empty(&c->surface.xwayland->children);
|
||||
@@ -195,9 +182,7 @@ client_has_children(Client *c)
|
||||
return wl_list_length(&c->surface.xdg->link) > 1;
|
||||
}
|
||||
|
||||
static inline const char *
|
||||
client_get_title(Client *c)
|
||||
{
|
||||
static inline const char *client_get_title(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return c->surface.xwayland->title;
|
||||
@@ -205,9 +190,7 @@ client_get_title(Client *c)
|
||||
return c->surface.xdg->toplevel->title;
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_is_float_type(Client *c)
|
||||
{
|
||||
static inline int client_is_float_type(Client *c) {
|
||||
struct wlr_xdg_toplevel *toplevel;
|
||||
struct wlr_xdg_toplevel_state state;
|
||||
|
||||
@@ -220,28 +203,27 @@ client_is_float_type(Client *c)
|
||||
return 1;
|
||||
|
||||
for (i = 0; i < surface->window_type_len; i++)
|
||||
if (surface->window_type[i] == netatom[NetWMWindowTypeDialog]
|
||||
|| surface->window_type[i] == netatom[NetWMWindowTypeSplash]
|
||||
|| surface->window_type[i] == netatom[NetWMWindowTypeToolbar]
|
||||
|| surface->window_type[i] == netatom[NetWMWindowTypeUtility])
|
||||
if (surface->window_type[i] == netatom[NetWMWindowTypeDialog] ||
|
||||
surface->window_type[i] == netatom[NetWMWindowTypeSplash] ||
|
||||
surface->window_type[i] == netatom[NetWMWindowTypeToolbar] ||
|
||||
surface->window_type[i] == netatom[NetWMWindowTypeUtility])
|
||||
return 1;
|
||||
|
||||
return size_hints && size_hints->min_width > 0 && size_hints->min_height > 0
|
||||
&& (size_hints->max_width == size_hints->min_width
|
||||
|| size_hints->max_height == size_hints->min_height);
|
||||
return size_hints && size_hints->min_width > 0 &&
|
||||
size_hints->min_height > 0 &&
|
||||
(size_hints->max_width == size_hints->min_width ||
|
||||
size_hints->max_height == size_hints->min_height);
|
||||
}
|
||||
#endif
|
||||
|
||||
toplevel = c->surface.xdg->toplevel;
|
||||
state = toplevel->current;
|
||||
return toplevel->parent || (state.min_width != 0 && state.min_height != 0
|
||||
&& (state.min_width == state.max_width
|
||||
|| state.min_height == state.max_height));
|
||||
return toplevel->parent || (state.min_width != 0 && state.min_height != 0 &&
|
||||
(state.min_width == state.max_width ||
|
||||
state.min_height == state.max_height));
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_is_rendered_on_mon(Client *c, Monitor *m)
|
||||
{
|
||||
static inline int client_is_rendered_on_mon(Client *c, Monitor *m) {
|
||||
/* This is needed for when you don't want to check formal assignment,
|
||||
* but rather actual displaying of the pixels.
|
||||
* Usually VISIBLEON suffices and is also faster. */
|
||||
@@ -249,15 +231,12 @@ client_is_rendered_on_mon(Client *c, Monitor *m)
|
||||
int unused_lx, unused_ly;
|
||||
if (!wlr_scene_node_coords(&c->scene->node, &unused_lx, &unused_ly))
|
||||
return 0;
|
||||
wl_list_for_each(s, &client_surface(c)->current_outputs, link)
|
||||
if (s->output == m->wlr_output)
|
||||
return 1;
|
||||
wl_list_for_each(s, &client_surface(c)->current_outputs,
|
||||
link) if (s->output == m->wlr_output) return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_is_stopped(Client *c)
|
||||
{
|
||||
static inline int client_is_stopped(Client *c) {
|
||||
int pid;
|
||||
siginfo_t in = {0};
|
||||
#ifdef XWAYLAND
|
||||
@@ -266,7 +245,7 @@ client_is_stopped(Client *c)
|
||||
#endif
|
||||
|
||||
wl_client_get_credentials(c->surface.xdg->client->client, &pid, NULL, NULL);
|
||||
if (waitid(P_PID, pid, &in, WNOHANG|WCONTINUED|WSTOPPED|WNOWAIT) < 0) {
|
||||
if (waitid(P_PID, pid, &in, WNOHANG | WCONTINUED | WSTOPPED | WNOWAIT) < 0) {
|
||||
/* This process is not our child process, while is very unluckely that
|
||||
* it is stopped, in order to do not skip frames assume that it is. */
|
||||
if (errno == ECHILD)
|
||||
@@ -281,9 +260,7 @@ client_is_stopped(Client *c)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_is_unmanaged(Client *c)
|
||||
{
|
||||
static inline int client_is_unmanaged(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return c->surface.xwayland->override_redirect;
|
||||
@@ -291,19 +268,16 @@ client_is_unmanaged(Client *c)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_notify_enter(struct wlr_surface *s, struct wlr_keyboard *kb)
|
||||
{
|
||||
static inline void client_notify_enter(struct wlr_surface *s,
|
||||
struct wlr_keyboard *kb) {
|
||||
if (kb)
|
||||
wlr_seat_keyboard_notify_enter(seat, s, kb->keycodes,
|
||||
kb->num_keycodes, &kb->modifiers);
|
||||
wlr_seat_keyboard_notify_enter(seat, s, kb->keycodes, kb->num_keycodes,
|
||||
&kb->modifiers);
|
||||
else
|
||||
wlr_seat_keyboard_notify_enter(seat, s, NULL, 0, NULL);
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_restack_surface(Client *c)
|
||||
{
|
||||
static inline void client_restack_surface(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
wlr_xwayland_surface_restack(c->surface.xwayland, NULL,
|
||||
@@ -312,9 +286,7 @@ client_restack_surface(Client *c)
|
||||
return;
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_send_close(Client *c)
|
||||
{
|
||||
static inline void client_send_close(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c)) {
|
||||
wlr_xwayland_surface_close(c->surface.xwayland);
|
||||
@@ -324,17 +296,14 @@ client_send_close(Client *c)
|
||||
wlr_xdg_toplevel_send_close(c->surface.xdg->toplevel);
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_set_border_color(Client *c, const float color[static 4])
|
||||
{
|
||||
static inline void client_set_border_color(Client *c,
|
||||
const float color[static 4]) {
|
||||
int i;
|
||||
for (i = 0; i < 4; i++)
|
||||
wlr_scene_rect_set_color(c->border[i], color);
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_set_fullscreen(Client *c, int fullscreen)
|
||||
{
|
||||
static inline void client_set_fullscreen(Client *c, int fullscreen) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c)) {
|
||||
wlr_xwayland_surface_set_fullscreen(c->surface.xwayland, fullscreen);
|
||||
@@ -344,40 +313,37 @@ client_set_fullscreen(Client *c, int fullscreen)
|
||||
wlr_xdg_toplevel_set_fullscreen(c->surface.xdg->toplevel, fullscreen);
|
||||
}
|
||||
|
||||
static inline uint32_t
|
||||
client_set_size(Client *c, uint32_t width, uint32_t height)
|
||||
{
|
||||
static inline uint32_t client_set_size(Client *c, uint32_t width,
|
||||
uint32_t height) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c)) {
|
||||
wlr_xwayland_surface_configure(c->surface.xwayland,
|
||||
c->geom.x, c->geom.y, width, height);
|
||||
wlr_xwayland_surface_configure(c->surface.xwayland, c->geom.x, c->geom.y,
|
||||
width, height);
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
if ((int32_t)width == c->surface.xdg->toplevel->current.width
|
||||
&& (int32_t)height == c->surface.xdg->toplevel->current.height)
|
||||
if ((int32_t)width == c->surface.xdg->toplevel->current.width &&
|
||||
(int32_t)height == c->surface.xdg->toplevel->current.height)
|
||||
return 0;
|
||||
return wlr_xdg_toplevel_set_size(c->surface.xdg->toplevel, (int32_t)width, (int32_t)height);
|
||||
return wlr_xdg_toplevel_set_size(c->surface.xdg->toplevel, (int32_t)width,
|
||||
(int32_t)height);
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_set_tiled(Client *c, uint32_t edges)
|
||||
{
|
||||
static inline void client_set_tiled(Client *c, uint32_t edges) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return;
|
||||
#endif
|
||||
if (wl_resource_get_version(c->surface.xdg->toplevel->resource)
|
||||
>= XDG_TOPLEVEL_STATE_TILED_RIGHT_SINCE_VERSION) {
|
||||
if (wl_resource_get_version(c->surface.xdg->toplevel->resource) >=
|
||||
XDG_TOPLEVEL_STATE_TILED_RIGHT_SINCE_VERSION) {
|
||||
wlr_xdg_toplevel_set_tiled(c->surface.xdg->toplevel, edges);
|
||||
} else {
|
||||
wlr_xdg_toplevel_set_maximized(c->surface.xdg->toplevel, edges != WLR_EDGE_NONE);
|
||||
wlr_xdg_toplevel_set_maximized(c->surface.xdg->toplevel,
|
||||
edges != WLR_EDGE_NONE);
|
||||
}
|
||||
}
|
||||
|
||||
static inline void
|
||||
client_set_suspended(Client *c, int suspended)
|
||||
{
|
||||
static inline void client_set_suspended(Client *c, int suspended) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return;
|
||||
@@ -386,20 +352,17 @@ client_set_suspended(Client *c, int suspended)
|
||||
wlr_xdg_toplevel_set_suspended(c->surface.xdg->toplevel, suspended);
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_wants_focus(Client *c)
|
||||
{
|
||||
static inline int client_wants_focus(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
return client_is_unmanaged(c)
|
||||
&& wlr_xwayland_or_surface_wants_focus(c->surface.xwayland)
|
||||
&& wlr_xwayland_icccm_input_model(c->surface.xwayland) != WLR_ICCCM_INPUT_MODEL_NONE;
|
||||
return client_is_unmanaged(c) &&
|
||||
wlr_xwayland_or_surface_wants_focus(c->surface.xwayland) &&
|
||||
wlr_xwayland_icccm_input_model(c->surface.xwayland) !=
|
||||
WLR_ICCCM_INPUT_MODEL_NONE;
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int
|
||||
client_wants_fullscreen(Client *c)
|
||||
{
|
||||
static inline int client_wants_fullscreen(Client *c) {
|
||||
#ifdef XWAYLAND
|
||||
if (client_is_x11(c))
|
||||
return c->surface.xwayland->fullscreen;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
project('maomao', ['c', 'cpp'],
|
||||
version : '0.1'
|
||||
version : '0.1.1'
|
||||
)
|
||||
|
||||
subdir('protocols')
|
||||
|
||||
121
parse_config.h
121
parse_config.h
@@ -1,7 +1,7 @@
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
|
||||
typedef struct {
|
||||
const char *id;
|
||||
@@ -48,7 +48,6 @@ typedef struct {
|
||||
Arg arg;
|
||||
} AxisBinding;
|
||||
|
||||
|
||||
typedef struct {
|
||||
int animations;
|
||||
char animation_type[10];
|
||||
@@ -120,7 +119,7 @@ typedef struct {
|
||||
|
||||
} Config;
|
||||
|
||||
int parseDirection(const char* str) {
|
||||
int parseDirection(const char *str) {
|
||||
// 将输入字符串转换为小写
|
||||
char lowerStr[10];
|
||||
int i = 0;
|
||||
@@ -177,16 +176,20 @@ uint32_t parse_mod(const char *mod_str) {
|
||||
lower_str[i] = '\0'; // 确保字符串以 NULL 结尾
|
||||
|
||||
// 检查修饰键,忽略左右键标识(如 "_l" 和 "_r")
|
||||
if (strstr(lower_str, "super") || strstr(lower_str, "super_l") || strstr(lower_str, "super_r")) {
|
||||
if (strstr(lower_str, "super") || strstr(lower_str, "super_l") ||
|
||||
strstr(lower_str, "super_r")) {
|
||||
mod |= WLR_MODIFIER_LOGO;
|
||||
}
|
||||
if (strstr(lower_str, "ctrl") || strstr(lower_str, "ctrl_l") || strstr(lower_str, "ctrl_r")) {
|
||||
if (strstr(lower_str, "ctrl") || strstr(lower_str, "ctrl_l") ||
|
||||
strstr(lower_str, "ctrl_r")) {
|
||||
mod |= WLR_MODIFIER_CTRL;
|
||||
}
|
||||
if (strstr(lower_str, "shift") || strstr(lower_str, "shift_l") || strstr(lower_str, "shift_r")) {
|
||||
if (strstr(lower_str, "shift") || strstr(lower_str, "shift_l") ||
|
||||
strstr(lower_str, "shift_r")) {
|
||||
mod |= WLR_MODIFIER_SHIFT;
|
||||
}
|
||||
if (strstr(lower_str, "alt") || strstr(lower_str, "alt_l") || strstr(lower_str, "alt_r")) {
|
||||
if (strstr(lower_str, "alt") || strstr(lower_str, "alt_l") ||
|
||||
strstr(lower_str, "alt_r")) {
|
||||
mod |= WLR_MODIFIER_ALT;
|
||||
}
|
||||
|
||||
@@ -223,7 +226,6 @@ xkb_keysym_t parse_keysym(const char *keysym_str) {
|
||||
|
||||
typedef void (*FuncType)(const Arg *);
|
||||
|
||||
|
||||
int parseButton(const char *str) {
|
||||
// 将输入字符串转换为小写
|
||||
char lowerStr[20];
|
||||
@@ -256,7 +258,6 @@ int parseButton(const char *str) {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int parseMouseAction(const char *str) {
|
||||
// 将输入字符串转换为小写
|
||||
char lowerStr[20];
|
||||
@@ -281,14 +282,14 @@ int parseMouseAction(const char *str) {
|
||||
}
|
||||
}
|
||||
|
||||
void parseColoer(float *color,unsigned long int hex) {
|
||||
void parseColoer(float *color, unsigned long int hex) {
|
||||
color[0] = ((hex >> 24) & 0xFF) / 255.0f;
|
||||
color[1] = ((hex >> 16) & 0xFF) / 255.0f;
|
||||
color[2] = ((hex >> 8) & 0xFF) / 255.0f;
|
||||
color[3] = (hex & 0xFF) / 255.0f;
|
||||
}
|
||||
|
||||
FuncType parse_func_name(char *func_name,Arg *arg, char *arg_value) {
|
||||
FuncType parse_func_name(char *func_name, Arg *arg, char *arg_value) {
|
||||
|
||||
FuncType func = NULL;
|
||||
(*arg).v = NULL;
|
||||
@@ -376,7 +377,7 @@ FuncType parse_func_name(char *func_name,Arg *arg, char *arg_value) {
|
||||
func = reload_config;
|
||||
} else if (strcmp(func_name, "tag") == 0) {
|
||||
func = tag;
|
||||
(*arg).ui = 1 << (atoi(arg_value) -1);
|
||||
(*arg).ui = 1 << (atoi(arg_value) - 1);
|
||||
} else if (strcmp(func_name, "view") == 0) {
|
||||
func = bind_to_view;
|
||||
(*arg).ui = 1 << (atoi(arg_value) - 1);
|
||||
@@ -410,7 +411,9 @@ void parse_config_line(Config *config, const char *line) {
|
||||
} else if (strcmp(key, "animation_duration_tag") == 0) {
|
||||
config->animation_duration_tag = atoi(value);
|
||||
} else if (strcmp(key, "animation_curve") == 0) {
|
||||
if (sscanf(value, "%lf,%lf,%lf,%lf", &config->animation_curve[0], &config->animation_curve[1], &config->animation_curve[2], &config->animation_curve[3]) != 4) {
|
||||
if (sscanf(value, "%lf,%lf,%lf,%lf", &config->animation_curve[0],
|
||||
&config->animation_curve[1], &config->animation_curve[2],
|
||||
&config->animation_curve[3]) != 4) {
|
||||
fprintf(stderr, "Error: Invalid animation_curve format: %s\n", value);
|
||||
}
|
||||
} else if (strcmp(key, "scroller_structs") == 0) {
|
||||
@@ -420,8 +423,11 @@ void parse_config_line(Config *config, const char *line) {
|
||||
} else if (strcmp(key, "scoller_focus_center") == 0) {
|
||||
config->scoller_focus_center = atoi(value);
|
||||
} else if (strcmp(key, "scroller_proportion_preset") == 0) {
|
||||
if (sscanf(value, "%f,%f,%f", &config->scroller_proportion_preset[0], &config->scroller_proportion_preset[1], &config->scroller_proportion_preset[2]) != 3) {
|
||||
fprintf(stderr, "Error: Invalid scroller_proportion_preset format: %s\n", value);
|
||||
if (sscanf(value, "%f,%f,%f", &config->scroller_proportion_preset[0],
|
||||
&config->scroller_proportion_preset[1],
|
||||
&config->scroller_proportion_preset[2]) != 3) {
|
||||
fprintf(stderr, "Error: Invalid scroller_proportion_preset format: %s\n",
|
||||
value);
|
||||
}
|
||||
} else if (strcmp(key, "new_is_master") == 0) {
|
||||
config->new_is_master = atoi(value);
|
||||
@@ -468,52 +474,53 @@ void parse_config_line(Config *config, const char *line) {
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid rootcolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->rootcolor,color);
|
||||
parseColoer(config->rootcolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "bordercolor") == 0) {
|
||||
long int color = parse_color(value);
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid bordercolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->bordercolor,color);
|
||||
parseColoer(config->bordercolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "focuscolor") == 0) {
|
||||
long int color = parse_color(value);
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid focuscolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->focuscolor,color);
|
||||
parseColoer(config->focuscolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "maxmizescreencolor") == 0) {
|
||||
long int color = parse_color(value);
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid maxmizescreencolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->maxmizescreencolor,color);
|
||||
parseColoer(config->maxmizescreencolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "urgentcolor") == 0) {
|
||||
long int color = parse_color(value);
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid urgentcolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->urgentcolor,color);
|
||||
parseColoer(config->urgentcolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "scratchpadcolor") == 0) {
|
||||
long int color = parse_color(value);
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid scratchpadcolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->scratchpadcolor,color);
|
||||
parseColoer(config->scratchpadcolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "globalcolor") == 0) {
|
||||
long int color = parse_color(value);
|
||||
if (color == -1) {
|
||||
fprintf(stderr, "Error: Invalid globalcolor format: %s\n", value);
|
||||
} else {
|
||||
parseColoer(config->globalcolor,color);
|
||||
parseColoer(config->globalcolor, color);
|
||||
}
|
||||
} else if (strcmp(key, "autostart") == 0) {
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,]", config->autostart[0], config->autostart[1], config->autostart[2]) != 3) {
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,]", config->autostart[0],
|
||||
config->autostart[1], config->autostart[2]) != 3) {
|
||||
fprintf(stderr, "Error: Invalid autostart format: %s\n", value);
|
||||
}
|
||||
} else if (strcmp(key, "tags") == 0) {
|
||||
@@ -522,7 +529,8 @@ void parse_config_line(Config *config, const char *line) {
|
||||
if (sscanf(value, "id:%d,layout_name:%255[^\n]", &id, layout_name) == 2) {
|
||||
if (id >= 1 && id <= 9) {
|
||||
config->tags[id - 1].id = id;
|
||||
strncpy(config->tags[id - 1].layout_name, layout_name, sizeof(config->tags[id - 1].layout_name));
|
||||
strncpy(config->tags[id - 1].layout_name, layout_name,
|
||||
sizeof(config->tags[id - 1].layout_name));
|
||||
} else {
|
||||
fprintf(stderr, "Error: Invalid tag id: %d\n", id);
|
||||
}
|
||||
@@ -530,7 +538,9 @@ void parse_config_line(Config *config, const char *line) {
|
||||
fprintf(stderr, "Error: Invalid tags format: %s\n", value);
|
||||
}
|
||||
} else if (strcmp(key, "windowrule") == 0) {
|
||||
config->window_rules = realloc(config->window_rules, (config->window_rules_count + 1) * sizeof(ConfigWinRule));
|
||||
config->window_rules =
|
||||
realloc(config->window_rules,
|
||||
(config->window_rules_count + 1) * sizeof(ConfigWinRule));
|
||||
if (!config->window_rules) {
|
||||
fprintf(stderr, "Error: Failed to allocate memory for window rules\n");
|
||||
return;
|
||||
@@ -551,7 +561,6 @@ void parse_config_line(Config *config, const char *line) {
|
||||
rule->title = NULL;
|
||||
rule->tags = 0;
|
||||
|
||||
|
||||
char *token = strtok(value, ",");
|
||||
while (token != NULL) {
|
||||
char *colon = strchr(token, ':');
|
||||
@@ -588,33 +597,32 @@ void parse_config_line(Config *config, const char *line) {
|
||||
}
|
||||
config->window_rules_count++;
|
||||
} else if (strcmp(key, "monitorrule") == 0) {
|
||||
config->monitor_rules = realloc(config->monitor_rules, (config->monitor_rules_count + 1) * sizeof(ConfigMonitorRule));
|
||||
config->monitor_rules =
|
||||
realloc(config->monitor_rules,
|
||||
(config->monitor_rules_count + 1) * sizeof(ConfigMonitorRule));
|
||||
if (!config->monitor_rules) {
|
||||
fprintf(stderr, "Error: Failed to allocate memory for monitor rules\n");
|
||||
return;
|
||||
}
|
||||
|
||||
ConfigMonitorRule *rule = &config->monitor_rules[config->monitor_rules_count];
|
||||
ConfigMonitorRule *rule =
|
||||
&config->monitor_rules[config->monitor_rules_count];
|
||||
memset(rule, 0, sizeof(ConfigMonitorRule));
|
||||
|
||||
char layout[256], name[256];
|
||||
int parsed = sscanf(value, "%255[^,],%f,%d,%255[^,],%d,%f,%d,%d",
|
||||
name,
|
||||
&rule->mfact,
|
||||
&rule->nmaster,
|
||||
layout,
|
||||
&rule->rr,
|
||||
&rule->scale,
|
||||
&rule->x,
|
||||
&rule->y);
|
||||
int parsed = sscanf(value, "%255[^,],%f,%d,%255[^,],%d,%f,%d,%d", name,
|
||||
&rule->mfact, &rule->nmaster, layout, &rule->rr,
|
||||
&rule->scale, &rule->x, &rule->y);
|
||||
|
||||
if (parsed == 8) {
|
||||
rule->name = strdup(name);
|
||||
rule->layout = strdup(layout);
|
||||
|
||||
if (!rule->name || !rule->layout) {
|
||||
if (rule->name) free((void *)rule->name);
|
||||
if (rule->layout) free((void *)rule->layout);
|
||||
if (rule->name)
|
||||
free((void *)rule->name);
|
||||
if (rule->layout)
|
||||
free((void *)rule->layout);
|
||||
fprintf(stderr, "Error: Failed to allocate memory for monitor rule\n");
|
||||
return;
|
||||
}
|
||||
@@ -624,7 +632,9 @@ void parse_config_line(Config *config, const char *line) {
|
||||
fprintf(stderr, "Error: Invalid monitorrule format: %s\n", value);
|
||||
}
|
||||
} else if (strncmp(key, "bind", 4) == 0) {
|
||||
config->key_bindings = realloc(config->key_bindings, (config->key_bindings_count + 1) * sizeof(KeyBinding));
|
||||
config->key_bindings =
|
||||
realloc(config->key_bindings,
|
||||
(config->key_bindings_count + 1) * sizeof(KeyBinding));
|
||||
if (!config->key_bindings) {
|
||||
fprintf(stderr, "Error: Failed to allocate memory for key bindings\n");
|
||||
return;
|
||||
@@ -634,7 +644,8 @@ void parse_config_line(Config *config, const char *line) {
|
||||
memset(binding, 0, sizeof(KeyBinding));
|
||||
|
||||
char mod_str[256], keysym_str[256], func_name[256], arg_value[256] = "none";
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,],%[^\n]", mod_str, keysym_str, func_name, arg_value) < 3) {
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,],%[^\n]", mod_str, keysym_str,
|
||||
func_name, arg_value) < 3) {
|
||||
fprintf(stderr, "Error: Invalid bind format: %s\n", value);
|
||||
return;
|
||||
}
|
||||
@@ -643,24 +654,28 @@ void parse_config_line(Config *config, const char *line) {
|
||||
binding->keysym = parse_keysym(keysym_str);
|
||||
binding->arg.v = NULL;
|
||||
binding->func = parse_func_name(func_name, &binding->arg, arg_value);
|
||||
if (!binding->func){
|
||||
if (!binding->func) {
|
||||
fprintf(stderr, "Error: Unknown function in bind: %s\n", func_name);
|
||||
} else {
|
||||
config->key_bindings_count++;
|
||||
}
|
||||
|
||||
} else if (strncmp(key, "mousebind", 9) == 0) {
|
||||
config->mouse_bindings = realloc(config->mouse_bindings, (config->mouse_bindings_count + 1) * sizeof(MouseBinding));
|
||||
config->mouse_bindings =
|
||||
realloc(config->mouse_bindings,
|
||||
(config->mouse_bindings_count + 1) * sizeof(MouseBinding));
|
||||
if (!config->mouse_bindings) {
|
||||
fprintf(stderr, "Error: Failed to allocate memory for mouse bindings\n");
|
||||
return;
|
||||
}
|
||||
|
||||
MouseBinding *binding = &config->mouse_bindings[config->mouse_bindings_count];
|
||||
MouseBinding *binding =
|
||||
&config->mouse_bindings[config->mouse_bindings_count];
|
||||
memset(binding, 0, sizeof(MouseBinding));
|
||||
|
||||
char mod_str[256], button_str[256], func_name[256], arg_value[256] = "none";
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,],%[^\n]", mod_str, button_str, func_name, arg_value) < 3) {
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,],%[^\n]", mod_str, button_str,
|
||||
func_name, arg_value) < 3) {
|
||||
fprintf(stderr, "Error: Invalid mousebind format: %s\n", value);
|
||||
return;
|
||||
}
|
||||
@@ -669,13 +684,15 @@ void parse_config_line(Config *config, const char *line) {
|
||||
binding->button = parseButton(button_str);
|
||||
binding->arg.v = NULL;
|
||||
binding->func = parse_func_name(func_name, &binding->arg, arg_value);
|
||||
if (!binding->func){
|
||||
if (!binding->func) {
|
||||
fprintf(stderr, "Error: Unknown function in mousebind: %s\n", func_name);
|
||||
} else {
|
||||
config->mouse_bindings_count++;
|
||||
}
|
||||
} else if (strncmp(key, "axisbind", 8) == 0) {
|
||||
config->axis_bindings = realloc(config->axis_bindings, (config->axis_bindings_count + 1) * sizeof(AxisBinding));
|
||||
config->axis_bindings =
|
||||
realloc(config->axis_bindings,
|
||||
(config->axis_bindings_count + 1) * sizeof(AxisBinding));
|
||||
if (!config->axis_bindings) {
|
||||
fprintf(stderr, "Error: Failed to allocate memory for axis bindings\n");
|
||||
return;
|
||||
@@ -685,7 +702,8 @@ void parse_config_line(Config *config, const char *line) {
|
||||
memset(binding, 0, sizeof(AxisBinding));
|
||||
|
||||
char mod_str[256], dir_str[256], func_name[256], arg_value[256] = "none";
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,],%[^\n]", mod_str, dir_str, func_name, arg_value) < 3) {
|
||||
if (sscanf(value, "%[^,],%[^,],%[^,],%[^\n]", mod_str, dir_str, func_name,
|
||||
arg_value) < 3) {
|
||||
fprintf(stderr, "Error: Invalid axisbind format: %s\n", value);
|
||||
return;
|
||||
}
|
||||
@@ -695,7 +713,7 @@ void parse_config_line(Config *config, const char *line) {
|
||||
binding->arg.v = NULL;
|
||||
binding->func = parse_func_name(func_name, &binding->arg, arg_value);
|
||||
|
||||
if (!binding->func){
|
||||
if (!binding->func) {
|
||||
fprintf(stderr, "Error: Unknown function in axisbind: %s\n", func_name);
|
||||
} else {
|
||||
config->axis_bindings_count++;
|
||||
@@ -715,7 +733,8 @@ void parse_config_file(Config *config, const char *file_path) {
|
||||
|
||||
char line[512];
|
||||
while (fgets(line, sizeof(line), file)) {
|
||||
if (line[0] == '#' || line[0] == '\n') continue;
|
||||
if (line[0] == '#' || line[0] == '\n')
|
||||
continue;
|
||||
parse_config_line(config, line);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,34 +1,33 @@
|
||||
/* speedie's maomao config */
|
||||
|
||||
#define COLOR(hex) { ((hex >> 24) & 0xFF) / 255.0f, \
|
||||
((hex >> 16) & 0xFF) / 255.0f, \
|
||||
((hex >> 8) & 0xFF) / 255.0f, \
|
||||
(hex & 0xFF) / 255.0f }
|
||||
#define COLOR(hex) \
|
||||
{((hex >> 24) & 0xFF) / 255.0f, ((hex >> 16) & 0xFF) / 255.0f, \
|
||||
((hex >> 8) & 0xFF) / 255.0f, (hex & 0xFF) / 255.0f}
|
||||
|
||||
/* animaion */
|
||||
char *animation_type = "slide"; //是否启用动画 //slide,zoom
|
||||
int animations = 1; //是否启用动画
|
||||
char *animation_type = "slide"; // 是否启用动画 //slide,zoom
|
||||
int animations = 1; // 是否启用动画
|
||||
char animation_fade_in = 1; // Enable animation fade in
|
||||
float zoom_initial_ratio = 0.5; //动画起始窗口比例
|
||||
float zoom_initial_ratio = 0.5; // 动画起始窗口比例
|
||||
float fadein_begin_opacity = 0; // Begin opac window ratio for animations
|
||||
uint32_t animation_duration_move = 500; // Animation move speed
|
||||
uint32_t animation_duration_open = 400; // Animation open speed
|
||||
uint32_t animation_duration_tag = 300; // Animation tag speed
|
||||
double animation_curve[4] = {0.46,1.0,0.29,0.99}; //动画曲线
|
||||
double animation_curve[4] = {0.46, 1.0, 0.29, 0.99}; // 动画曲线
|
||||
|
||||
/* appearance */
|
||||
unsigned int axis_bind_apply_timeout = 100; //滚轮绑定动作的触发的时间间隔
|
||||
unsigned int focus_on_activate = 1; //收到窗口激活请求是否自动跳转聚焦
|
||||
unsigned int new_is_master = 1; //新窗口是否插在头部
|
||||
unsigned int axis_bind_apply_timeout = 100; // 滚轮绑定动作的触发的时间间隔
|
||||
unsigned int focus_on_activate = 1; // 收到窗口激活请求是否自动跳转聚焦
|
||||
unsigned int new_is_master = 1; // 新窗口是否插在头部
|
||||
double default_mfact = 0.55f; // master 窗口比例
|
||||
unsigned int default_nmaster = 1; //默认master数量
|
||||
unsigned int default_nmaster = 1; // 默认master数量
|
||||
/* logging */
|
||||
int log_level = WLR_ERROR;
|
||||
unsigned int numlockon = 1; //是否打开右边小键盘
|
||||
unsigned int numlockon = 1; // 是否打开右边小键盘
|
||||
|
||||
unsigned int ov_tab_mode = 0; // alt tab切换模式
|
||||
unsigned int hotarea_size = 10; //热区大小,10x10
|
||||
unsigned int enable_hotarea = 1; //是否启用鼠标热区
|
||||
unsigned int hotarea_size = 10; // 热区大小,10x10
|
||||
unsigned int enable_hotarea = 1; // 是否启用鼠标热区
|
||||
int smartgaps = 0; /* 1 means no outer gap when there is only one window */
|
||||
int sloppyfocus = 1; /* focus follows mouse */
|
||||
unsigned int gappih = 5; /* horiz inner gap between windows */
|
||||
@@ -36,13 +35,14 @@ unsigned int gappiv = 5; /* vert inner gap between windows */
|
||||
unsigned int gappoh = 10; /* horiz outer gap between windows and screen edge */
|
||||
unsigned int gappov = 10; /* vert outer gap between windows and screen edge */
|
||||
|
||||
|
||||
int scroller_structs = 20;
|
||||
float scroller_default_proportion = 0.9;
|
||||
int scoller_focus_center = 0;
|
||||
float scroller_proportion_preset[] = {0.5,0.9,1.0};
|
||||
float scroller_proportion_preset[] = {0.5, 0.9, 1.0};
|
||||
|
||||
int bypass_surface_visibility = 0; /* 1 means idle inhibitors will disable idle tracking even if it's surface isn't visible */
|
||||
int bypass_surface_visibility =
|
||||
0; /* 1 means idle inhibitors will disable idle tracking even if it's
|
||||
surface isn't visible */
|
||||
unsigned int borderpx = 4; /* border pixel of windows */
|
||||
float rootcolor[] = COLOR(0x323232ff);
|
||||
float bordercolor[] = COLOR(0x444444ff);
|
||||
@@ -56,27 +56,24 @@ float globalcolor[] = COLOR(0xb153a7ff);
|
||||
int overviewgappi = 5; /* overview时 窗口与边缘 缝隙大小 */
|
||||
int overviewgappo = 30; /* overview时 窗口与窗口 缝隙大小 */
|
||||
|
||||
/* To conform the xdg-protocol, set the alpha to zero to restore the old behavior */
|
||||
/* To conform the xdg-protocol, set the alpha to zero to restore the old
|
||||
* behavior */
|
||||
float fullscreen_bg[] = {0.1, 0.1, 0.1, 1.0};
|
||||
|
||||
int warpcursor = 1; /* Warp cursor to focused client */
|
||||
|
||||
|
||||
/* layout(s) */
|
||||
Layout overviewlayout = { "", overview, "overview" };
|
||||
Layout overviewlayout = {"", overview, "overview"};
|
||||
|
||||
Layout layouts[] = { //最少两个,不能删除少于两个
|
||||
Layout layouts[] = {
|
||||
// 最少两个,不能删除少于两个
|
||||
/* symbol arrange function name */
|
||||
{ "S", scroller, "scroller" }, //滚动布局
|
||||
{ "T", tile, "tile" }, //堆栈布局
|
||||
{"G", grid, "grid"},
|
||||
{"M",monocle,"monocle"},
|
||||
{"D",dwindle,"dwindle"},
|
||||
{"P",spiral,"spiral"},
|
||||
{"S", scroller, "scroller"}, // 滚动布局
|
||||
{"T", tile, "tile"}, // 堆栈布局
|
||||
{"G", grid, "grid"}, {"M", monocle, "monocle"},
|
||||
{"D", dwindle, "dwindle"}, {"P", spiral, "spiral"},
|
||||
};
|
||||
|
||||
|
||||
|
||||
/* keyboard */
|
||||
struct xkb_rule_names xkb_rules = {
|
||||
/* can specify fields: rules, model, layout, variant, options */
|
||||
@@ -110,7 +107,8 @@ LIBINPUT_CONFIG_CLICK_METHOD_NONE
|
||||
LIBINPUT_CONFIG_CLICK_METHOD_BUTTON_AREAS
|
||||
LIBINPUT_CONFIG_CLICK_METHOD_CLICKFINGER
|
||||
*/
|
||||
enum libinput_config_click_method click_method = LIBINPUT_CONFIG_CLICK_METHOD_BUTTON_AREAS;
|
||||
enum libinput_config_click_method click_method =
|
||||
LIBINPUT_CONFIG_CLICK_METHOD_BUTTON_AREAS;
|
||||
|
||||
/* You can choose between:
|
||||
LIBINPUT_CONFIG_SEND_EVENTS_ENABLED
|
||||
@@ -123,7 +121,8 @@ uint32_t send_events_mode = LIBINPUT_CONFIG_SEND_EVENTS_ENABLED;
|
||||
LIBINPUT_CONFIG_ACCEL_PROFILE_FLAT
|
||||
LIBINPUT_CONFIG_ACCEL_PROFILE_ADAPTIVE
|
||||
*/
|
||||
enum libinput_config_accel_profile accel_profile = LIBINPUT_CONFIG_ACCEL_PROFILE_ADAPTIVE;
|
||||
enum libinput_config_accel_profile accel_profile =
|
||||
LIBINPUT_CONFIG_ACCEL_PROFILE_ADAPTIVE;
|
||||
double accel_speed = 0.0;
|
||||
/* You can choose between:
|
||||
LIBINPUT_CONFIG_TAP_MAP_LRM -- 1/2/3 finger tap maps to left/right/middle
|
||||
@@ -135,21 +134,9 @@ enum libinput_config_tap_button_map button_map = LIBINPUT_CONFIG_TAP_MAP_LRM;
|
||||
#define MODKEY WLR_MODIFIER_ALT
|
||||
|
||||
static const char *tags[] = {
|
||||
"1",
|
||||
"2",
|
||||
"3",
|
||||
"4",
|
||||
"5",
|
||||
"6",
|
||||
"7",
|
||||
"8",
|
||||
"9",
|
||||
"1", "2", "3", "4", "5", "6", "7", "8", "9",
|
||||
};
|
||||
|
||||
static const char *const autostart[] = {
|
||||
"/bin/sh",
|
||||
"-c",
|
||||
"~/.config/maomao/autostart.sh",
|
||||
NULL,
|
||||
NULL,
|
||||
"/bin/sh", "-c", "~/.config/maomao/autostart.sh", NULL, NULL,
|
||||
};
|
||||
9
util.c
9
util.c
@@ -6,15 +6,14 @@
|
||||
|
||||
#include "util.h"
|
||||
|
||||
void
|
||||
die(const char *fmt, ...) {
|
||||
void die(const char *fmt, ...) {
|
||||
va_list ap;
|
||||
|
||||
va_start(ap, fmt);
|
||||
vfprintf(stderr, fmt, ap);
|
||||
va_end(ap);
|
||||
|
||||
if (fmt[0] && fmt[strlen(fmt)-1] == ':') {
|
||||
if (fmt[0] && fmt[strlen(fmt) - 1] == ':') {
|
||||
fputc(' ', stderr);
|
||||
perror(NULL);
|
||||
} else {
|
||||
@@ -24,9 +23,7 @@ die(const char *fmt, ...) {
|
||||
exit(1);
|
||||
}
|
||||
|
||||
void *
|
||||
ecalloc(size_t nmemb, size_t size)
|
||||
{
|
||||
void *ecalloc(size_t nmemb, size_t size) {
|
||||
void *p;
|
||||
|
||||
if (!(p = calloc(nmemb, size)))
|
||||
|
||||
Reference in New Issue
Block a user