diff --git a/Abaddon.vcxproj b/Abaddon.vcxproj
index 49dc4b8..7ac7422 100644
--- a/Abaddon.vcxproj
+++ b/Abaddon.vcxproj
@@ -148,6 +148,7 @@
+
@@ -162,6 +163,7 @@
+
diff --git a/Abaddon.vcxproj.filters b/Abaddon.vcxproj.filters
index 41db77a..27b1d17 100644
--- a/Abaddon.vcxproj.filters
+++ b/Abaddon.vcxproj.filters
@@ -51,6 +51,9 @@
Source Files
+
+ Source Files
+
@@ -89,5 +92,8 @@
Header Files
+
+ Header Files
+
\ No newline at end of file
diff --git a/abaddon.cpp b/abaddon.cpp
index 954814a..0f2d0bd 100644
--- a/abaddon.cpp
+++ b/abaddon.cpp
@@ -4,6 +4,7 @@
#include
#include "discord/discord.hpp"
#include "dialogs/token.hpp"
+#include "dialogs/editmessage.hpp"
#include "abaddon.hpp"
#ifdef _WIN32
@@ -205,6 +206,15 @@ void Abaddon::ActionChatDeleteMessage(Snowflake channel_id, Snowflake id) {
m_discord.DeleteMessage(channel_id, id);
}
+void Abaddon::ActionChatEditMessage(Snowflake channel_id, Snowflake id) {
+ EditMessageDialog dlg(*m_main_window);
+ auto response = dlg.run();
+ if (response == Gtk::RESPONSE_OK) {
+ auto new_content = dlg.GetContent();
+ m_discord.EditMessage(channel_id, id, new_content);
+ }
+}
+
int main(int argc, char **argv) {
Gtk::Main::init_gtkmm_internals(); // why???
Abaddon abaddon;
diff --git a/abaddon.hpp b/abaddon.hpp
index 4f804f0..5a533b3 100644
--- a/abaddon.hpp
+++ b/abaddon.hpp
@@ -28,6 +28,7 @@ public:
void ActionChatInputSubmit(std::string msg, Snowflake channel);
void ActionChatLoadHistory(Snowflake id);
void ActionChatDeleteMessage(Snowflake channel_id, Snowflake id);
+ void ActionChatEditMessage(Snowflake channel_id, Snowflake id);
std::string GetDiscordToken() const;
bool IsDiscordActive() const;
diff --git a/components/chatmessage.cpp b/components/chatmessage.cpp
index c7cf21b..9074e91 100644
--- a/components/chatmessage.cpp
+++ b/components/chatmessage.cpp
@@ -62,6 +62,10 @@ ChatMessageItem::ChatMessageItem() {
m_menu_delete_message->signal_activate().connect(sigc::mem_fun(*this, &ChatMessageItem::on_menu_message_delete));
m_menu.append(*m_menu_delete_message);
+ m_menu_edit_message = Gtk::manage(new Gtk::MenuItem("_Edit Message", true));
+ m_menu_edit_message->signal_activate().connect(sigc::mem_fun(*this, &ChatMessageItem::on_menu_message_edit));
+ m_menu.append(*m_menu_edit_message);
+
m_menu.show_all();
}
@@ -73,6 +77,10 @@ void ChatMessageItem::on_menu_message_delete() {
m_abaddon->ActionChatDeleteMessage(ChannelID, ID);
}
+void ChatMessageItem::on_menu_message_edit() {
+ m_abaddon->ActionChatEditMessage(ChannelID, ID);
+}
+
void ChatMessageItem::on_menu_copy_id() {
Gtk::Clipboard::get()->set_text(std::to_string(ID));
}
@@ -94,7 +102,9 @@ void ChatMessageItem::AttachMenuHandler(Gtk::Widget *widget) {
void ChatMessageItem::ShowMenu(const GdkEvent *event) {
auto &client = m_abaddon->GetDiscordClient();
auto *data = client.GetMessage(ID);
- m_menu_delete_message->set_sensitive(client.GetUserData().ID == data->Author.ID);
+ bool can_manage = client.GetUserData().ID == data->Author.ID;
+ m_menu_delete_message->set_sensitive(can_manage);
+ m_menu_edit_message->set_sensitive(can_manage);
m_menu.popup_at_pointer(event);
}
diff --git a/components/chatmessage.hpp b/components/chatmessage.hpp
index 82f4504..5796002 100644
--- a/components/chatmessage.hpp
+++ b/components/chatmessage.hpp
@@ -43,10 +43,12 @@ protected:
void AttachMenuHandler(Gtk::Widget *widget);
void on_menu_copy_id();
void on_menu_message_delete();
+ void on_menu_message_edit();
Gtk::Menu m_menu;
Gtk::MenuItem *m_menu_copy_id;
Gtk::MenuItem *m_menu_delete_message;
+ Gtk::MenuItem *m_menu_edit_message;
Abaddon *m_abaddon = nullptr;
};
diff --git a/dialogs/editmessage.cpp b/dialogs/editmessage.cpp
new file mode 100644
index 0000000..e6f226e
--- /dev/null
+++ b/dialogs/editmessage.cpp
@@ -0,0 +1,39 @@
+#include "editmessage.hpp"
+
+EditMessageDialog::EditMessageDialog(Gtk::Window &parent)
+ : Gtk::Dialog("Edit Message", parent, true)
+ , m_layout(Gtk::ORIENTATION_VERTICAL)
+ , m_bbox(Gtk::ORIENTATION_HORIZONTAL)
+ , m_ok("OK")
+ , m_cancel("Cancel") {
+ set_default_size(300, 50);
+
+ m_ok.signal_clicked().connect([&]() {
+ m_content = m_text.get_buffer()->get_text();
+ response(Gtk::RESPONSE_OK);
+ });
+
+ m_cancel.signal_clicked().connect([&]() {
+ response(Gtk::RESPONSE_CANCEL);
+ });
+
+ m_bbox.pack_start(m_ok, Gtk::PACK_SHRINK);
+ m_bbox.pack_start(m_cancel, Gtk::PACK_SHRINK);
+ m_bbox.set_layout(Gtk::BUTTONBOX_END);
+
+ m_text.set_hexpand(true);
+
+ m_scroll.set_hexpand(true);
+ m_scroll.set_vexpand(true);
+ m_scroll.add(m_text);
+
+ m_layout.add(m_scroll);
+ m_layout.add(m_bbox);
+ get_content_area()->add(m_layout);
+
+ show_all_children();
+}
+
+std::string EditMessageDialog::GetContent() {
+ return m_content;
+}
diff --git a/dialogs/editmessage.hpp b/dialogs/editmessage.hpp
new file mode 100644
index 0000000..5427897
--- /dev/null
+++ b/dialogs/editmessage.hpp
@@ -0,0 +1,20 @@
+#pragma once
+#include
+#include
+
+class EditMessageDialog : public Gtk::Dialog {
+public:
+ EditMessageDialog(Gtk::Window &parent);
+ std::string GetContent();
+
+protected:
+ Gtk::Box m_layout;
+ Gtk::Button m_ok;
+ Gtk::Button m_cancel;
+ Gtk::ButtonBox m_bbox;
+ Gtk::ScrolledWindow m_scroll;
+ Gtk::TextView m_text;
+
+private:
+ std::string m_content;
+};
diff --git a/discord/discord.cpp b/discord/discord.cpp
index 37ac59f..f04c136 100644
--- a/discord/discord.cpp
+++ b/discord/discord.cpp
@@ -172,6 +172,14 @@ void DiscordClient::DeleteMessage(Snowflake channel_id, Snowflake id) {
m_http.MakeDELETE(path, [](auto) {});
}
+void DiscordClient::EditMessage(Snowflake channel_id, Snowflake id, std::string content) {
+ std::string path = "/channels/" + std::to_string(channel_id) + "/messages/" + std::to_string(id);
+ MessageEditObject obj;
+ obj.Content = content;
+ nlohmann::json j = obj;
+ m_http.MakePATCH(path, j.dump(), [](auto) {});
+}
+
void DiscordClient::UpdateToken(std::string token) {
m_token = token;
m_http.SetAuth(token);
diff --git a/discord/discord.hpp b/discord/discord.hpp
index 87e09f4..707120e 100644
--- a/discord/discord.hpp
+++ b/discord/discord.hpp
@@ -70,6 +70,7 @@ public:
void SendChatMessage(std::string content, Snowflake channel);
void DeleteMessage(Snowflake channel_id, Snowflake id);
+ void EditMessage(Snowflake channel_id, Snowflake id, std::string content);
void UpdateToken(std::string token);
diff --git a/discord/objects.cpp b/discord/objects.cpp
index ed556f4..1a8355e 100644
--- a/discord/objects.cpp
+++ b/discord/objects.cpp
@@ -295,6 +295,18 @@ void to_json(nlohmann::json &j, const CreateMessageObject &m) {
j["content"] = m.Content;
}
+void to_json(nlohmann::json &j, const MessageEditObject &m) {
+ if (m.Content.size() > 0)
+ j["content"] = m.Content;
+
+ // todo EmbedData to_json
+ // if (m.Embeds.size() > 0)
+ // j["embeds"] = m.Embeds;
+
+ if (m.Flags != -1)
+ j["flags"] = m.Flags;
+}
+
Snowflake::Snowflake()
: m_num(Invalid) {}
diff --git a/discord/objects.hpp b/discord/objects.hpp
index a8bf082..e4b40b4 100644
--- a/discord/objects.hpp
+++ b/discord/objects.hpp
@@ -424,3 +424,11 @@ struct CreateMessageObject {
friend void to_json(nlohmann::json &j, const CreateMessageObject &m);
};
+
+struct MessageEditObject {
+ std::string Content; // opt, null
+ std::vector Embeds; // opt, null
+ int Flags = -1; // opt, null
+
+ friend void to_json(nlohmann::json &j, const MessageEditObject &m);
+};