module; #include #include #include export module ttwhy.routers:echo; import ttwhy; import ttwhy.scanners; namespace ttwhy::routers { using namespace std::string_view_literals; constexpr auto vte_backspace_sequence = "\b \b"sv; constexpr auto vte_newline_sequence = "\r\n"sv; constexpr auto vte_horizontal_tab_sequqnce = "\t"sv; export template struct echo { explicit echo(StreamType & stream) : m_output_stream{stream} {} auto process(scanners::input_event event) -> asio::awaitable { co_await std::visit( [&](auto && event) -> asio::awaitable { using event_type = std::decay_t; if constexpr (std::same_as) { co_await process_character(event.value); } else if constexpr (std::same_as) { co_await process_control_key(event.key); } else if constexpr (std::same_as) { co_await process_navigation_key(event.key); } }, event); } private: auto process_character(char character) -> asio::awaitable { co_await asio::async_write(m_output_stream, asio::buffer(&character, 1), asio::as_tuple(asio::use_awaitable)); } auto process_control_key(scanners::control_key key) -> asio::awaitable { switch (key) { case scanners::control_key::backspace: co_await asio::async_write(m_output_stream, asio::buffer(vte_backspace_sequence), asio::as_tuple(asio::use_awaitable)); break; case scanners::control_key::enter: co_await asio::async_write(m_output_stream, asio::buffer(vte_newline_sequence), asio::as_tuple(asio::use_awaitable)); break; case scanners::control_key::tab: co_await asio::async_write(m_output_stream, asio::buffer(vte_horizontal_tab_sequqnce), asio::as_tuple(asio::use_awaitable)); break; default: co_await asio::async_write(m_output_stream, asio::buffer(std::format("{{CTRL:{}}}", std::to_underlying(key))), asio::as_tuple(asio::use_awaitable)); break; }; } auto process_navigation_key(scanners::navigation_key key) -> asio::awaitable { switch (key) { case scanners::navigation_key::delete_key: co_await asio::async_write(m_output_stream, asio::buffer("{DEL}"), asio::as_tuple(asio::use_awaitable)); break; default: co_await asio::async_write(m_output_stream, asio::buffer(std::format("{{NAV:{}}}", std::to_underlying(key))), asio::as_tuple(asio::use_awaitable)); } } StreamType & m_output_stream; }; } // namespace ttwhy::routers