mirror of
https://github.com/RGBCube/serenity
synced 2025-07-23 09:17:36 +00:00
IRCClient: Add handling of some basic messages and commands.
This commit is contained in:
parent
b4f787090c
commit
f44ba6a4c6
5 changed files with 123 additions and 3 deletions
|
@ -55,3 +55,24 @@ void IRCChannel::say(const String& text)
|
||||||
m_client.send_privmsg(m_name, text);
|
m_client.send_privmsg(m_name, text);
|
||||||
add_message(' ', m_client.nickname(), text);
|
add_message(' ', m_client.nickname(), text);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void IRCChannel::handle_join(const String& nick, const String& hostmask)
|
||||||
|
{
|
||||||
|
if (nick == m_client.nickname())
|
||||||
|
m_open = true;
|
||||||
|
add_message(' ', "", String::format("*** %s [%s] has joined %s", nick.characters(), hostmask.characters(), m_name.characters()));
|
||||||
|
}
|
||||||
|
|
||||||
|
void IRCChannel::handle_part(const String& nick, const String& hostmask)
|
||||||
|
{
|
||||||
|
if (nick == m_client.nickname())
|
||||||
|
m_open = false;
|
||||||
|
add_message(' ', "", String::format("*** %s [%s] has parted from %s", nick.characters(), hostmask.characters(), m_name.characters()));
|
||||||
|
}
|
||||||
|
|
||||||
|
void IRCChannel::handle_topic(const String& nick, const String& topic)
|
||||||
|
{
|
||||||
|
if (nick == m_client.nickname())
|
||||||
|
m_open = false;
|
||||||
|
add_message(' ', "", String::format("*** %s set topic to \"%s\"", nick.characters(), topic.characters()));
|
||||||
|
}
|
||||||
|
|
|
@ -39,14 +39,21 @@ public:
|
||||||
int member_count() const { return m_members.size(); }
|
int member_count() const { return m_members.size(); }
|
||||||
String member_at(int i) { return m_members[i].name; }
|
String member_at(int i) { return m_members[i].name; }
|
||||||
|
|
||||||
|
void handle_join(const String& nick, const String& hostmask);
|
||||||
|
void handle_part(const String& nick, const String& hostmask);
|
||||||
|
void handle_topic(const String& nick, const String& topic);
|
||||||
|
|
||||||
IRCWindow& window() { return *m_window; }
|
IRCWindow& window() { return *m_window; }
|
||||||
const IRCWindow& window() const { return *m_window; }
|
const IRCWindow& window() const { return *m_window; }
|
||||||
|
|
||||||
|
String topic() const { return m_topic; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
IRCChannel(IRCClient&, const String&);
|
IRCChannel(IRCClient&, const String&);
|
||||||
|
|
||||||
IRCClient& m_client;
|
IRCClient& m_client;
|
||||||
String m_name;
|
String m_name;
|
||||||
|
String m_topic;
|
||||||
struct Member {
|
struct Member {
|
||||||
String name;
|
String name;
|
||||||
char prefix { 0 };
|
char prefix { 0 };
|
||||||
|
|
|
@ -11,9 +11,11 @@
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
//#define IRC_DEBUG
|
#define IRC_DEBUG
|
||||||
|
|
||||||
enum IRCNumeric {
|
enum IRCNumeric {
|
||||||
|
RPL_TOPIC = 332,
|
||||||
|
RPL_TOPICWHOTIME = 333,
|
||||||
RPL_NAMREPLY = 353,
|
RPL_NAMREPLY = 353,
|
||||||
RPL_ENDOFNAMES = 366,
|
RPL_ENDOFNAMES = 366,
|
||||||
};
|
};
|
||||||
|
@ -201,6 +203,11 @@ void IRCClient::join_channel(const String& channel_name)
|
||||||
send(String::format("JOIN %s\r\n", channel_name.characters()));
|
send(String::format("JOIN %s\r\n", channel_name.characters()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void IRCClient::part_channel(const String& channel_name)
|
||||||
|
{
|
||||||
|
send(String::format("PART %s\r\n", channel_name.characters()));
|
||||||
|
}
|
||||||
|
|
||||||
void IRCClient::handle(const Message& msg, const String&)
|
void IRCClient::handle(const Message& msg, const String&)
|
||||||
{
|
{
|
||||||
#ifdef IRC_DEBUG
|
#ifdef IRC_DEBUG
|
||||||
|
@ -225,6 +232,9 @@ void IRCClient::handle(const Message& msg, const String&)
|
||||||
case RPL_NAMREPLY:
|
case RPL_NAMREPLY:
|
||||||
handle_namreply(msg);
|
handle_namreply(msg);
|
||||||
return;
|
return;
|
||||||
|
case RPL_TOPIC:
|
||||||
|
handle_rpl_topic(msg);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -234,6 +244,12 @@ void IRCClient::handle(const Message& msg, const String&)
|
||||||
if (msg.command == "JOIN")
|
if (msg.command == "JOIN")
|
||||||
return handle_join(msg);
|
return handle_join(msg);
|
||||||
|
|
||||||
|
if (msg.command == "PART")
|
||||||
|
return handle_part(msg);
|
||||||
|
|
||||||
|
if (msg.command == "TOPIC")
|
||||||
|
return handle_topic(msg);
|
||||||
|
|
||||||
if (msg.command == "PRIVMSG")
|
if (msg.command == "PRIVMSG")
|
||||||
return handle_privmsg(msg);
|
return handle_privmsg(msg);
|
||||||
|
|
||||||
|
@ -252,6 +268,8 @@ void IRCClient::handle_user_input_in_channel(const String& channel_name, const S
|
||||||
{
|
{
|
||||||
if (input.is_empty())
|
if (input.is_empty())
|
||||||
return;
|
return;
|
||||||
|
if (input[0] == '/')
|
||||||
|
return handle_user_command(input);
|
||||||
ensure_channel(channel_name).say(input);
|
ensure_channel(channel_name).say(input);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -259,6 +277,8 @@ void IRCClient::handle_user_input_in_query(const String& query_name, const Strin
|
||||||
{
|
{
|
||||||
if (input.is_empty())
|
if (input.is_empty())
|
||||||
return;
|
return;
|
||||||
|
if (input[0] == '/')
|
||||||
|
return handle_user_command(input);
|
||||||
ensure_query(query_name).say(input);
|
ensure_query(query_name).say(input);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -266,6 +286,8 @@ void IRCClient::handle_user_input_in_server(const String& input)
|
||||||
{
|
{
|
||||||
if (input.is_empty())
|
if (input.is_empty())
|
||||||
return;
|
return;
|
||||||
|
if (input[0] == '/')
|
||||||
|
return handle_user_command(input);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IRCClient::is_nick_prefix(char ch) const
|
bool IRCClient::is_nick_prefix(char ch) const
|
||||||
|
@ -349,8 +371,47 @@ void IRCClient::handle_join(const Message& msg)
|
||||||
{
|
{
|
||||||
if (msg.arguments.size() != 1)
|
if (msg.arguments.size() != 1)
|
||||||
return;
|
return;
|
||||||
|
auto prefix_parts = msg.prefix.split('!');
|
||||||
|
if (prefix_parts.size() < 1)
|
||||||
|
return;
|
||||||
|
auto nick = prefix_parts[0];
|
||||||
auto& channel_name = msg.arguments[0];
|
auto& channel_name = msg.arguments[0];
|
||||||
ensure_channel(channel_name);
|
ensure_channel(channel_name).handle_join(nick, msg.prefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
void IRCClient::handle_part(const Message& msg)
|
||||||
|
{
|
||||||
|
if (msg.arguments.size() != 1)
|
||||||
|
return;
|
||||||
|
auto prefix_parts = msg.prefix.split('!');
|
||||||
|
if (prefix_parts.size() < 1)
|
||||||
|
return;
|
||||||
|
auto nick = prefix_parts[0];
|
||||||
|
auto& channel_name = msg.arguments[0];
|
||||||
|
ensure_channel(channel_name).handle_part(nick, msg.prefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
void IRCClient::handle_topic(const Message& msg)
|
||||||
|
{
|
||||||
|
if (msg.arguments.size() != 2)
|
||||||
|
return;
|
||||||
|
auto prefix_parts = msg.prefix.split('!');
|
||||||
|
if (prefix_parts.size() < 1)
|
||||||
|
return;
|
||||||
|
auto nick = prefix_parts[0];
|
||||||
|
auto& channel_name = msg.arguments[0];
|
||||||
|
ensure_channel(channel_name).handle_topic(nick, msg.arguments[1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
void IRCClient::handle_rpl_topic(const Message& msg)
|
||||||
|
{
|
||||||
|
if (msg.arguments.size() != 3)
|
||||||
|
return;
|
||||||
|
auto& nick = msg.arguments[0];
|
||||||
|
auto& channel_name = msg.arguments[1];
|
||||||
|
auto& topic = msg.arguments[2];
|
||||||
|
ensure_channel(channel_name).handle_topic(nick, topic);
|
||||||
|
// FIXME: Handle RPL_TOPICWHOTIME so we can know who set it and when.
|
||||||
}
|
}
|
||||||
|
|
||||||
void IRCClient::handle_namreply(const Message& msg)
|
void IRCClient::handle_namreply(const Message& msg)
|
||||||
|
@ -403,3 +464,26 @@ void IRCClient::unregister_subwindow(IRCWindow& subwindow)
|
||||||
}
|
}
|
||||||
m_client_window_list_model->update();
|
m_client_window_list_model->update();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void IRCClient::handle_user_command(const String& input)
|
||||||
|
{
|
||||||
|
auto parts = input.split(' ');
|
||||||
|
if (parts.is_empty())
|
||||||
|
return;
|
||||||
|
auto command = parts[0].to_uppercase();
|
||||||
|
if (command == "/JOIN") {
|
||||||
|
if (parts.size() >= 2)
|
||||||
|
join_channel(parts[1]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (command == "/PART") {
|
||||||
|
if (parts.size() >= 2)
|
||||||
|
part_channel(parts[1]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (command == "/QUERY") {
|
||||||
|
if (parts.size() >= 2)
|
||||||
|
ensure_query(parts[1]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -27,6 +27,7 @@ public:
|
||||||
String nickname() const { return m_nickname; }
|
String nickname() const { return m_nickname; }
|
||||||
|
|
||||||
void join_channel(const String&);
|
void join_channel(const String&);
|
||||||
|
void part_channel(const String&);
|
||||||
|
|
||||||
bool is_nick_prefix(char) const;
|
bool is_nick_prefix(char) const;
|
||||||
|
|
||||||
|
@ -73,10 +74,14 @@ private:
|
||||||
void send_privmsg(const String& target, const String&);
|
void send_privmsg(const String& target, const String&);
|
||||||
void process_line();
|
void process_line();
|
||||||
void handle_join(const Message&);
|
void handle_join(const Message&);
|
||||||
|
void handle_part(const Message&);
|
||||||
void handle_ping(const Message&);
|
void handle_ping(const Message&);
|
||||||
|
void handle_topic(const Message&);
|
||||||
|
void handle_rpl_topic(const Message&);
|
||||||
void handle_namreply(const Message&);
|
void handle_namreply(const Message&);
|
||||||
void handle_privmsg(const Message&);
|
void handle_privmsg(const Message&);
|
||||||
void handle(const Message&, const String& verbatim);
|
void handle(const Message&, const String& verbatim);
|
||||||
|
void handle_user_command(const String&);
|
||||||
|
|
||||||
String m_hostname;
|
String m_hostname;
|
||||||
int m_port { 0 };
|
int m_port { 0 };
|
||||||
|
|
|
@ -51,7 +51,10 @@ GVariant IRCLogBufferModel::data(const GModelIndex& index, Role) const
|
||||||
auto* tm = localtime(&entry.timestamp);
|
auto* tm = localtime(&entry.timestamp);
|
||||||
return String::format("%02u:%02u:%02u", tm->tm_hour, tm->tm_min, tm->tm_sec);
|
return String::format("%02u:%02u:%02u", tm->tm_hour, tm->tm_min, tm->tm_sec);
|
||||||
}
|
}
|
||||||
case Column::Name: return String::format("<%c%s>", entry.prefix ? entry.prefix : ' ', entry.sender.characters());
|
case Column::Name:
|
||||||
|
if (entry.sender.is_empty())
|
||||||
|
return String::empty();
|
||||||
|
return String::format("<%c%s>", entry.prefix ? entry.prefix : ' ', entry.sender.characters());
|
||||||
case Column::Text: return entry.text;
|
case Column::Text: return entry.text;
|
||||||
}
|
}
|
||||||
ASSERT_NOT_REACHED();
|
ASSERT_NOT_REACHED();
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue