diff --git a/include/sway/commands.h b/include/sway/commands.h index cfe2aa079..c4903788c 100644 --- a/include/sway/commands.h +++ b/include/sway/commands.h @@ -270,6 +270,7 @@ sway_cmd output_cmd_mode; sway_cmd output_cmd_position; sway_cmd output_cmd_scale; sway_cmd output_cmd_subpixel; +sway_cmd output_cmd_toggle; sway_cmd output_cmd_transform; sway_cmd seat_cmd_attach; diff --git a/include/sway/output.h b/include/sway/output.h index cae77e2ec..d4438c0ea 100644 --- a/include/sway/output.h +++ b/include/sway/output.h @@ -82,8 +82,12 @@ void output_damage_box(struct sway_output *output, struct wlr_box *box); void output_damage_whole_container(struct sway_output *output, struct sway_container *con); +// this ONLY includes the enabled outputs struct sway_output *output_by_name_or_id(const char *name_or_id); +// this includes all the outputs, including disabled ones +struct sway_output *all_output_by_name_or_id(const char *name_or_id); + void output_sort_workspaces(struct sway_output *output); void output_enable(struct sway_output *output, struct output_config *oc); diff --git a/sway/commands/output.c b/sway/commands/output.c index 6b9eafdbe..3903f10dc 100644 --- a/sway/commands/output.c +++ b/sway/commands/output.c @@ -19,6 +19,7 @@ static struct cmd_handler output_handlers[] = { { "resolution", output_cmd_mode }, { "scale", output_cmd_scale }, { "subpixel", output_cmd_subpixel }, + { "toggle", output_cmd_toggle }, { "transform", output_cmd_transform }, }; diff --git a/sway/commands/output/toggle.c b/sway/commands/output/toggle.c new file mode 100644 index 000000000..6342d526b --- /dev/null +++ b/sway/commands/output/toggle.c @@ -0,0 +1,37 @@ +#include "sway/commands.h" +#include "sway/config.h" +#include "sway/output.h" + +struct cmd_results *output_cmd_toggle(int argc, char **argv) { + if (!config->handler_context.output_config) { + return cmd_results_new(CMD_FAILURE, "Missing output config"); + } + + struct output_config *oc = config->handler_context.output_config; + + if (strcmp(oc->name, "*") == 0) { + return cmd_results_new(CMD_INVALID, + "Cannot apply toggle to all outputs."); + } + + struct sway_output *sway_output = all_output_by_name_or_id(oc->name); + + if (sway_output == NULL) { + return cmd_results_new(CMD_FAILURE, + "Cannot apply toggle to unknown output %s", oc->name); + } + + oc = find_output_config(sway_output); + + if (!oc || oc->enabled != 0) { + config->handler_context.output_config->enabled = 0; + } else { + config->handler_context.output_config->enabled = 1; + } + + free(oc); + config->handler_context.leftovers.argc = argc; + config->handler_context.leftovers.argv = argv; + return NULL; +} + diff --git a/sway/desktop/output.c b/sway/desktop/output.c index 0cc085254..1636a58b3 100644 --- a/sway/desktop/output.c +++ b/sway/desktop/output.c @@ -42,6 +42,19 @@ struct sway_output *output_by_name_or_id(const char *name_or_id) { return NULL; } +struct sway_output *all_output_by_name_or_id(const char *name_or_id) { + struct sway_output *output; + wl_list_for_each(output, &root->all_outputs, link) { + char identifier[128]; + output_get_identifier(identifier, sizeof(identifier), output); + if (strcasecmp(identifier, name_or_id) == 0 + || strcasecmp(output->wlr_output->name, name_or_id) == 0) { + return output; + } + } + return NULL; +} + /** * Rotate a child's position relative to a parent. The parent size is (pw, ph), * the child position is (*sx, *sy) and its size is (sw, sh). diff --git a/sway/meson.build b/sway/meson.build index 0f943a1f3..05cece7a4 100644 --- a/sway/meson.build +++ b/sway/meson.build @@ -173,6 +173,7 @@ sway_sources = files( 'commands/output/position.c', 'commands/output/scale.c', 'commands/output/subpixel.c', + 'commands/output/toggle.c', 'commands/output/transform.c', 'tree/arrange.c', diff --git a/sway/sway-output.5.scd b/sway/sway-output.5.scd index 1efe2f7bf..e20d0aba8 100644 --- a/sway/sway-output.5.scd +++ b/sway/sway-output.5.scd @@ -94,6 +94,9 @@ must be separated by one space. For example: Enables or disables the specified output (all outputs are enabled by default). +*output* toggle + Toggle the specified output. + *output* dpms on|off Enables or disables the specified output via DPMS. To turn an output off (ie. blank the screen but keep workspaces as-is), one can set DPMS to off.