IRCChannel.cpp 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124
  1. /*
  2. * Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
  3. *
  4. * SPDX-License-Identifier: BSD-2-Clause
  5. */
  6. #include "IRCChannel.h"
  7. #include "IRCChannelMemberListModel.h"
  8. #include "IRCClient.h"
  9. #include <stdio.h>
  10. IRCChannel::IRCChannel(IRCClient& client, const String& name)
  11. : m_client(client)
  12. , m_name(name)
  13. , m_log(IRCLogBuffer::create())
  14. , m_member_model(IRCChannelMemberListModel::create(*this))
  15. {
  16. m_window = m_client.aid_create_window(this, IRCWindow::Channel, m_name);
  17. m_window->set_log_buffer(*m_log);
  18. }
  19. IRCChannel::~IRCChannel()
  20. {
  21. }
  22. NonnullRefPtr<IRCChannel> IRCChannel::create(IRCClient& client, const String& name)
  23. {
  24. return adopt_ref(*new IRCChannel(client, name));
  25. }
  26. void IRCChannel::add_member(const String& name, char prefix)
  27. {
  28. for (auto& member : m_members) {
  29. if (member.name == name) {
  30. member.prefix = prefix;
  31. return;
  32. }
  33. }
  34. m_members.append({ name, prefix });
  35. m_member_model->update();
  36. }
  37. void IRCChannel::remove_member(const String& name)
  38. {
  39. m_members.remove_first_matching([&](auto& member) { return name == member.name; });
  40. }
  41. void IRCChannel::add_message(char prefix, const String& name, const String& text, Color color)
  42. {
  43. log().add_message(prefix, name, text, color);
  44. window().did_add_message(name, text);
  45. }
  46. void IRCChannel::add_message(const String& text, Color color)
  47. {
  48. log().add_message(text, color);
  49. window().did_add_message();
  50. }
  51. void IRCChannel::say(const String& text)
  52. {
  53. m_client.send_privmsg(m_name, text);
  54. add_message(' ', m_client.nickname(), text);
  55. }
  56. void IRCChannel::handle_join(const String& nick, const String& hostmask)
  57. {
  58. if (nick == m_client.nickname()) {
  59. m_open = true;
  60. return;
  61. }
  62. add_member(nick, (char)0);
  63. m_member_model->update();
  64. if (m_client.show_join_part_messages())
  65. add_message(String::formatted("*** {} [{}] has joined {}", nick, hostmask, m_name), Color::MidGreen);
  66. }
  67. void IRCChannel::handle_part(const String& nick, const String& hostmask)
  68. {
  69. if (nick == m_client.nickname()) {
  70. m_open = false;
  71. m_members.clear();
  72. m_client.did_part_from_channel({}, *this);
  73. } else {
  74. remove_member(nick);
  75. }
  76. m_member_model->update();
  77. if (m_client.show_join_part_messages())
  78. add_message(String::formatted("*** {} [{}] has parted from {}", nick, hostmask, m_name), Color::MidGreen);
  79. }
  80. void IRCChannel::handle_quit(const String& nick, const String& hostmask, const String& message)
  81. {
  82. if (nick == m_client.nickname()) {
  83. m_open = false;
  84. m_members.clear();
  85. m_client.did_part_from_channel({}, *this);
  86. } else {
  87. remove_member(nick);
  88. }
  89. m_member_model->update();
  90. add_message(String::formatted("*** {} [{}] has quit ({})", nick, hostmask, message), Color::MidGreen);
  91. }
  92. void IRCChannel::handle_topic(const String& nick, const String& topic)
  93. {
  94. if (nick.is_null())
  95. add_message(String::formatted("*** Topic is \"{}\"", topic), Color::MidBlue);
  96. else
  97. add_message(String::formatted("*** {} set topic to \"{}\"", nick, topic), Color::MidBlue);
  98. }
  99. void IRCChannel::notify_nick_changed(const String& old_nick, const String& new_nick)
  100. {
  101. for (auto& member : m_members) {
  102. if (member.name == old_nick) {
  103. member.name = new_nick;
  104. m_member_model->update();
  105. if (m_client.show_nick_change_messages())
  106. add_message(String::formatted("~ {} changed nickname to {}", old_nick, new_nick), Color::MidMagenta);
  107. return;
  108. }
  109. }
  110. }