feature: adding the skeleton of support for the sway input command via IPC (#212)

This commit is contained in:
Matthew Kosarek 2024-08-21 19:31:02 -04:00 committed by GitHub
parent bd17e5b260
commit 9f38b095a4
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
6 changed files with 103 additions and 5 deletions

View File

@ -19,6 +19,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#include "jpcre2.h"
#include "window_controller.h"
#include "window_helpers.h"
#include "string_extensions.h"
#include <cstring>
#include <ranges>
@ -215,7 +216,7 @@ std::vector<I3ScopedCommandList> I3ScopedCommandList::parse(std::string_view con
I3Command next_command = { I3CommandType::none };
// Next, we can now read the command tokens space-by-space
for (auto const& command_token : ((command_view) | std::ranges::views::split(' ')))
for (auto const& command_token : ((trim_left(command_view)) | std::ranges::views::split(' ')))
{
if (next_command.type == I3CommandType::none)
{
@ -261,6 +262,8 @@ std::vector<I3ScopedCommandList> I3ScopedCommandList::parse(std::string_view con
next_command.type = I3CommandType::i3_bar;
else if (equals(command_token.data(), "gaps"))
next_command.type = I3CommandType::gaps;
else if (equals(command_token.data(), "input"))
next_command.type = I3CommandType::input;
else
{
mir::log_error("Invalid i3 command type: %s", command_token.data());
@ -281,4 +284,4 @@ std::vector<I3ScopedCommandList> I3ScopedCommandList::parse(std::string_view con
}
return list;
}
}

View File

@ -51,7 +51,8 @@ enum class I3CommandType
scratchpad,
nop,
i3_bar,
gaps
gaps,
input
};
enum class I3ScopeType

View File

@ -69,6 +69,9 @@ void I3CommandExecutor::process(miracle::I3ScopedCommandList const& command_list
case I3CommandType::exit:
policy.quit();
break;
case I3CommandType::input:
process_input(command, command_list);
break;
default:
break;
}
@ -429,4 +432,63 @@ void I3CommandExecutor::process_sticky(I3Command const& command, I3ScopedCommand
policy.toggle_pinned_to_workspace();
else
mir::log_warning("process_sticky: unknown arguments: %s", arg0.c_str());
}
}
// This command will be
void I3CommandExecutor::process_input(I3Command const& command, I3ScopedCommandList const& command_list)
{
// Payloads appear in the following format:
// [type:X, xkb_Y, Z]
// where X is something like "keyboard", Y is the variable that we want to change
// and Z is the value of that variable. Z may not be included at all, in which
// case the variable is set to the default.
if (command.arguments.size() < 2)
{
mir::log_warning("process_input: expects at least 2 arguments");
return;
}
const char* const TYPE_PREFIX = "type:";
const size_t TYPE_PREFIX_LEN = strlen(TYPE_PREFIX);
std::string_view type_str = command.arguments[0];
if (!type_str.starts_with("type:"))
{
mir::log_warning("process_input: 'type' string is misformatted: %s", command.arguments[0].c_str());
return;
}
std::string_view type = type_str.substr(TYPE_PREFIX_LEN);
assert(type == "keyboard");
std::string_view xkb_str = command.arguments[1];
const char* const XKB_PREFIX = "xkb_";
const size_t XKB_PREFIX_LEN = strlen(XKB_PREFIX);
if (!xkb_str.starts_with(XKB_PREFIX))
{
mir::log_warning("process_input: 'xkb' string is misformatted: %s", command.arguments[1].c_str());
return;
}
std::string_view xkb_variable_name = xkb_str.substr(XKB_PREFIX_LEN);
assert(xkb_variable_name == "model"
|| xkb_variable_name == "layout"
|| xkb_variable_name == "variant"
|| xkb_variable_name == "options");
mir::log_info("Processing input from locale1: type=%s, xkb_variable=%s", type.data(), xkb_variable_name.data());
// TODO: This is where we need to process the request
if (command.arguments.size() == 3)
{
}
else if (command.arguments.size() < 3)
{
// TODO: Set to the default
}
else
{
mir::log_warning("process_input: > 3 arguments were provided but only <= 3 are expected");
return;
}
}

View File

@ -55,6 +55,7 @@ private:
void process_focus(I3Command const&, I3ScopedCommandList const&);
void process_move(I3Command const&, I3ScopedCommandList const&);
void process_sticky(I3Command const&, I3ScopedCommandList const&);
void process_input(I3Command const&, I3ScopedCommandList const&);
};
} // miracle

View File

@ -265,7 +265,7 @@ bool Policy::handle_pointer_event(MirPointerEvent const* event)
}
}
if (state.has_clicked_floating_window || state.active->get_type() == ContainerType::floating_window)
if (state.has_clicked_floating_window || (state.active && state.active->get_type() == ContainerType::floating_window))
{
if (action == mir_pointer_action_button_down)
state.has_clicked_floating_window = true;

31
src/string_extensions.h Normal file
View File

@ -0,0 +1,31 @@
/**
Copyright (C) 2024 Matthew Kosarek
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
**/
#ifndef MIRACLE_WM_STRING_EXTENSIONS_H
#define MIRACLE_WM_STRING_EXTENSIONS_H
#include <string_view>
template <typename T>
std::string_view trim_left (T const & data)
{
std::string_view sv{data};
sv.remove_prefix( std::min(sv.find_first_not_of(' '), sv.size()));
return sv;
}
#endif //MIRACLE_WM_STRING_EXTENSIONS_H