diff --git a/changelog.md b/changelog.md index d75f84c..1318538 100644 --- a/changelog.md +++ b/changelog.md @@ -1,3 +1,10 @@ +# v1.2.2 +- Added a requirement for 1 tag to be added for uploading +- Prevent searching in My Objects and Favorites +- Fixed issue with Object Workshop button not centering in the Editor +- Fixed the "reset zoom" button to also reset positioning +- Fixed zooming to "act like zooming" (instead of scaling based on the center) +- (hopefully) Fixed issue with crash on clicking on the cancel button of a comment popup # v1.2.1 - Fixed bug with attempting to render invalid icons crashing # v1.2.0 diff --git a/mod.json b/mod.json index 6d529db..45dc1d6 100644 --- a/mod.json +++ b/mod.json @@ -8,7 +8,7 @@ }, "id": "firee.object-workshop", "name": "Object Workshop", - "version": "v1.2.1", + "version": "v1.2.2", "developer": "Firee", "description": "Download, upload, or find custom objects made by other creators!", "resources": { @@ -59,7 +59,7 @@ }, { "id": "alphalaneous.editortab_api", - "version": ">=v1.0.0-beta.3", + "version": ">=v1.0.0", "importance": "required" } ] diff --git a/server/src/controllers/objects.ts b/server/src/controllers/objects.ts index 49246a5..85a9a20 100644 --- a/server/src/controllers/objects.ts +++ b/server/src/controllers/objects.ts @@ -147,7 +147,7 @@ oRouter.post('/objects/upload', return false; }) if (hasBlacklistedIDs) return res.status(403).json({error: "Blacklisted IDs are not allowed."}); - if (!tags || !tags.length) tags = []; + if (!tags || !tags.length) return res.status(400).json({error: "You need to add at least 1 tag!"}); if (tags.length > 5) return res.status(413).json({error: "You can only add a maximum of 5 tags!"}); if (data.length == 1) return res.status(400).json({error: "hi my name is firee"}); if (data.length == 2) return res.status(400).json({error: "hola me llamo firee"}); @@ -747,7 +747,7 @@ oRouter.post('/objects/:id/update', if (!verifyRes.user) return res.status(404).json({error: "Couldn't retrieve user."}); const accountID = verifyRes.user.account_id; try { - if (verifyRes.user && verifyRes.user.role == 3) { + if (verifyRes.user && verifyRes.user.role == 2) { const objExists = await pool.query("SELECT EXISTS (SELECT 1 FROM objects WHERE id = $1)", [objectID]) if (!objExists.rows[0].exists) return res.status(404).json({error: "Object not found."}); } else { @@ -971,7 +971,7 @@ oRouter.get('/objects/:id/comments', users u ON c.account_id = u.account_id WHERE c.object_id = $1 GROUP BY c.id, u.name, u.icon, u.role - ORDER BY c.timestamp, c.pinned ASC + ORDER BY c.pinned DESC, c.timestamp DESC LIMIT $2 OFFSET $3 `; const result = await pool.query(query, [objectID, limit, offset]); diff --git a/src/config.hpp b/src/config.hpp index 6dcbf37..e565518 100644 --- a/src/config.hpp +++ b/src/config.hpp @@ -3,3 +3,5 @@ //#define HOST_URL "http://localhost:3000" #define RESULT_LIMIT 9 +#define MAX_ZOOM 10 +#define MIN_ZOOM 0.01 diff --git a/src/main.cpp b/src/main.cpp index 87ca0ea..54b6f48 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -78,7 +78,6 @@ class $modify(LevelEditorLayer) { bool CustomObjects::init(LevelEditorLayer* editorLayer) { if (!EditorUI::init(editorLayer)) return false; EditorTabs::addTab(this, TabType::BUILD, "workshop"_spr, [this](EditorUI* ui, CCMenuItemToggler* toggler) -> CCNode* { //create the tab - auto arr = CCArray::create(); auto folder = CCSprite::createWithSpriteFrameName("gj_folderBtn_001.png"); folder->setScale(0.4F); auto labelC = CCLabelBMFont::create("C+", "bigFont.fnt"); @@ -140,9 +139,6 @@ bool CustomObjects::init(LevelEditorLayer* editorLayer) { m_fields->btn1 = CCMenuItemSpriteExtra::create(btn1Spr, this, menu_selector(CustomObjects::onWorkshop)); m_fields->menu->addChildAtPosition(m_fields->btn1, Anchor::Center, {0, -7}); m_fields->menu->setContentHeight(90.F); - //menu->setPositionY(45.F); - - arr->addObject(m_fields->menu); m_fields->menu->updateLayout(); auto token = Mod::get()->getSettingValue("token"); @@ -186,14 +182,9 @@ bool CustomObjects::init(LevelEditorLayer* editorLayer) { req.bodyJSON(myjson); m_fields->m_listener.setFilter(req.post(fmt::format("{}/user/@me", HOST_URL))); } - //m_fields->menu->setPosition({-2, -112}); - m_fields->menu->setPosition({285, 45}); - //return EditorTabUtils::createEditButtonBar(arr, ui); + auto winSize = CCDirector::sharedDirector()->getWinSize(); + m_fields->menu->setPosition({winSize.width / 2, 45}); return m_fields->menu; - }, [this](EditorUI* ui, bool state, CCNode*) { //toggled the tab (activates on every tab click) - if (m_fields->menu != nullptr) { - //m_fields->menu->setPosition({-2, -112}); - } }); return true; @@ -218,35 +209,31 @@ class $modify(ObjectBypass, EditorUI) { } else { EditorUI::onNewCustomItem(pSender); } - } - /* - if ((this->m_selectedObjects == (CCArray *)0x0) || - (uVar1 = cocos2d::CCArray::count(this->m_selectedObjects), uVar1 < 0x3e9)) { - pGVar2 = GameManager::sharedState(); - uVar1 = cocos2d::CCDictionary::count(*(CCDictionary **)(pGVar2 + 0x134)); - if (uVar1 < 200) { - if (((this->m_selectedObject == (GameObject *)0x0) && - (uVar1 = cocos2d::CCArray::count(this->m_selectedObjects), uVar1 == 0)) || - ((this->m_selectedObject != (GameObject *)0x0 && - (*(int *)((int)&(this->m_selectedObject->GameObject_data).offset_0x100 + 4) == 0x2ed)))) - goto LAB_003a366e; - uVar1 = cocos2d::CCArray::count(this->m_selectedObjects); - if (uVar1 == 0) { - this_00 = cocos2d::CCArray::create(); - cocos2d::CCArray::addObject(this_00,(CCObject *)this->m_selectedObject); - } - else { - this_00 = this->m_selectedObjects; - } - pGVar3 = copyObjects((EditorUI *)&local_24,(CCArray *)this,false,false); - if ((*(int *)(local_24 + -0xc) != 0) && - (uVar1 = cocos2d::CCArray::count(this->m_selectedObjects), uVar1 < 1001)) { - pGVar2 = GameManager::sharedState(); - GameManager::addNewCustomObject(pGVar2,(basic_string)pGVar3); - this->m_selectedObjectIndex = 0; - reloadCustomItems(this); - } - } - */ +/* + if (m_selectedObjects == nullptr || m_selectedObjects->count() <= 1000) { + if (auto gameManager = GameManager::sharedState()) { + if (gameManager->m_customObjectDict->count() < 200) { + if ((m_selectedObject == nullptr && m_selectedObjects->count() == 0) || (m_selectedObject != nullptr && m_selectedObject->m_objectID == 0x2ed)) return; + CCArray* newSelectedObjs; + if (m_selectedObjects->count() == 0) { + newSelectedObjs = cocos2d::CCArray::create(); + newSelectedObjs->addObject(m_selectedObject); + } else { + newSelectedObjs = this->m_selectedObjects; + } + gameManager->addNewCustomObject(copyObjects(newSelectedObjs, false, false)); + m_selectedObjectIndex = 0; + reloadCustomItems(); + } else { + auto string = cocos2d::CCString::createWithFormat("You cannot create more than %i custom objects.", 200); + FLAlertLayer::create(nullptr, "Max Custom Objects", string->getCString(), "OK", nullptr)->show(); + } + } + } else { + auto string = cocos2d::CCString::createWithFormat("A custom object cannot contain more than %i objects.", 1000); + FLAlertLayer::create(nullptr, "Max Limit", string->getCString(), "OK", nullptr)->show(); + } +*/ + } }; diff --git a/src/nodes/CommentCell.cpp b/src/nodes/CommentCell.cpp index 2e4f6ae..149cd0e 100644 --- a/src/nodes/CommentCell.cpp +++ b/src/nodes/CommentCell.cpp @@ -111,7 +111,38 @@ bool OWCommentCell::init(CommentData data, ObjectData obj, UserData user, utils: } void OWCommentCell::onVote(CCObject*) { - VotePopup::create(m_data, m_forceRefresh)->show(); + VotePopup::create("Vote", [this](bool like) { + auto token = Mod::get()->getSettingValue("token"); + m_listener.getFilter().cancel(); + m_listener.bind([this, token] (web::WebTask::Event* e) { + if (web::WebResponse* value = e->getValue()) { + auto jsonRes = value->json().unwrapOrDefault(); + if (!jsonRes.is_object()) return log::error("Response isn't object."); + auto isError = jsonRes.try_get("error"); + if (isError) return Notification::create(isError->c_str(), NotificationIcon::Error)->show(); + auto message = jsonRes.try_get("message"); + if (message) { + m_forceRefresh(); + Notification::create(message->c_str(), NotificationIcon::Success)->show(); + } else { + log::error("Unknown response, expected message. {}", jsonRes.dump()); + Notification::create("Got an unknown response, check logs for details.", NotificationIcon::Warning)->show(); + } + return; + } else if (web::WebProgress* progress = e->getProgress()) { + // The request is still in progress... + } else if (e->isCancelled()) { + log::error("Request was cancelled."); + } + }); + web::WebRequest req = web::WebRequest(); + auto myjson = matjson::Value(); + myjson.set("token", token); + myjson.set("like", (int)like); + req.header("Content-Type", "application/json"); + req.bodyJSON(myjson); + m_listener.setFilter(req.post(fmt::format("{}/objects/{}/comments/{}/vote", HOST_URL, m_data.objectID, m_data.id))); + })->show(); } void OWCommentCell::onPin(CCObject*) { geode::createQuickPopup( diff --git a/src/nodes/ExtPreviewBG.cpp b/src/nodes/ExtPreviewBG.cpp index 8a39b72..2ca729d 100644 --- a/src/nodes/ExtPreviewBG.cpp +++ b/src/nodes/ExtPreviewBG.cpp @@ -1,11 +1,12 @@ #include "ExtPreviewBG.hpp" -bool ExtPreviewBG::init(std::string data) { +#include "../config.hpp" +bool ExtPreviewBG::init(std::string data, CCSize contentSize) { if (!CCLayer::init()) return false; - this->setContentSize({ 124.F, 82.F }); + this->setContentSize(contentSize); this->setAnchorPoint({0.5, 0.5}); bg = CCScale9Sprite::create("square02_small.png"); bg->setOpacity(60); - bg->setContentSize({ 124.F, 82.F }); + bg->setContentSize(this->getContentSize()); auto previewLabel = CCLabelBMFont::create("Preview", "goldFont.fnt"); previewLabel->setScale(0.425F); @@ -14,21 +15,22 @@ bool ExtPreviewBG::init(std::string data) { CCLayerColor* mask = CCLayerColor::create({255, 255, 255}); mask->setContentSize(bg->getContentSize()); - auto clippingNode = CCClippingNode::create(); - clippingNode->setContentSize(bg->getContentSize()); - clippingNode->setAnchorPoint({0.5, 0.5}); + m_clippingNode = CCClippingNode::create(); + m_clippingNode->setContentSize(bg->getContentSize()); + m_clippingNode->setAnchorPoint({0.5, 0.5}); if (auto editorUI = EditorUI::get() && data.length() > 0) { auto renderLimit = Mod::get()->getSettingValue("render-objects"); auto smartBlock = CCArray::create(); objSprite = EditorUI::get()->spriteFromObjectString(data, false, false, renderLimit, smartBlock, (CCArray *)0x0,(GameObject *)0x0); LevelEditorLayer::get()->updateObjectColors(smartBlock); - objSprite->setScale((clippingNode->getContentSize().height - 20) / objSprite->getContentSize().height); + objSprite->setScale((m_clippingNode->getContentSize().height - 20) / objSprite->getContentSize().height); m_oldScale = objSprite->getScale(); - clippingNode->addChildAtPosition(objSprite, Anchor::Center, {0, -5}); + m_clippingNode->addChildAtPosition(objSprite, Anchor::Center, {0, -5}); + m_oldPos = objSprite->getPosition(); } - clippingNode->setStencil(mask); - clippingNode->setZOrder(1); - this->addChildAtPosition(clippingNode, Anchor::Center); + m_clippingNode->setStencil(mask); + m_clippingNode->setZOrder(1); + this->addChildAtPosition(m_clippingNode, Anchor::Center); this->registerWithTouchDispatcher(); this->setTouchEnabled(true); @@ -67,18 +69,40 @@ void ExtPreviewBG::ccTouchMoved(CCTouch* touch, CCEvent* event) { } void ExtPreviewBG::updateZoom(float amount) { - if (!(m_currentZoom < 0) && m_currentZoom < 25) m_currentZoom += amount; - objSprite->setScale(m_oldScale * m_currentZoom); + float newZoom = m_currentZoom + amount; + if (newZoom >= MIN_ZOOM && newZoom <= 25.0f) { + float oldZoom = m_currentZoom; + m_currentZoom += amount; + float zoomFactor = m_currentZoom / oldZoom; + + auto relativePos = (m_oldPos - objSprite->getPosition()) / oldZoom; + objSprite->setScale(m_oldScale * m_currentZoom); + objSprite->setPosition(m_oldPos - (relativePos * m_currentZoom)); + } +}; + +void ExtPreviewBG::setZoom(float amount) { + if (amount >= MIN_ZOOM && amount <= 25.0f) { + float oldZoom = m_currentZoom; + m_currentZoom = amount; + float zoomFactor = m_currentZoom / oldZoom; + + auto relativePos = (m_oldPos - objSprite->getPosition()) / oldZoom; + objSprite->setScale(m_oldScale * m_currentZoom); + objSprite->setPosition(m_oldPos - (relativePos * m_currentZoom)); + } }; + void ExtPreviewBG::resetZoom() { m_currentZoom = 1.0F; objSprite->setScale(m_oldScale * m_currentZoom); + objSprite->setPosition(m_oldPos); }; -ExtPreviewBG* ExtPreviewBG::create(std::string data) { +ExtPreviewBG* ExtPreviewBG::create(std::string data, CCSize contentSize) { auto pRet = new ExtPreviewBG(); if (pRet) { - if (pRet->init(data)) { + if (pRet->init(data, contentSize)) { pRet->autorelease(); return pRet; } diff --git a/src/nodes/ExtPreviewBG.hpp b/src/nodes/ExtPreviewBG.hpp index 2b09237..9114b91 100644 --- a/src/nodes/ExtPreviewBG.hpp +++ b/src/nodes/ExtPreviewBG.hpp @@ -8,15 +8,18 @@ class ExtPreviewBG : public CCLayer { CCSprite* objSprite; CCScale9Sprite* bg; CCPoint m_touchStart; + CCClippingNode* m_clippingNode; float m_oldScale; + CCPoint m_oldPos; float m_currentZoom = 1.0F; void touchFinished(); - virtual bool init(std::string objData); + virtual bool init(std::string objData, CCSize); bool ccTouchBegan(CCTouch*, CCEvent*) override; void ccTouchMoved(CCTouch*, CCEvent*) override; public: void updateZoom(float amount); + void setZoom(float amount = 1.0F); void resetZoom(); - static ExtPreviewBG* create(std::string objData); + static ExtPreviewBG* create(std::string objData, CCSize contentSize = {124.F, 82.F}); }; diff --git a/src/nodes/ScrollLayerExt.cpp b/src/nodes/ScrollLayerExt.cpp index d0da0cf..a392561 100644 --- a/src/nodes/ScrollLayerExt.cpp +++ b/src/nodes/ScrollLayerExt.cpp @@ -173,7 +173,7 @@ void ScrollLayerExt::fixTouchPrio() { if (auto delegate = typeinfo_cast(this)) { if (auto handler = CCTouchDispatcher::get()->findHandler(delegate)) { Loader::get()->queueInMainThread([this, handler, delegate, oldThis]() { - if (oldThis != nullptr) { + if (oldThis != nullptr && handler != nullptr && delegate != nullptr) { if (auto dispatcher = CCTouchDispatcher::get()) { dispatcher->setPriority(handler->m_nPriority - 2, delegate); } diff --git a/src/ui/ObjectWorkshop.cpp b/src/ui/ObjectWorkshop.cpp index d45bcf0..059b704 100644 --- a/src/ui/ObjectWorkshop.cpp +++ b/src/ui/ObjectWorkshop.cpp @@ -1,6 +1,5 @@ #include "../config.hpp" #include "ObjectWorkshop.hpp" -#include "Geode/ui/ListView.hpp" #include "popups/includes.h" #include "../nodes/CategoryButton.hpp" #include "../utils.hpp" @@ -116,8 +115,9 @@ bool ObjectWorkshop::setup(bool authenticated) { m_searchInput = TextInput::create(110.0F, "Search..."); m_searchInput->setMaxCharCount(64); m_searchInput->setScale(0.525F); + m_searchInput->setAnchorPoint({ 0, .5f }); m_searchInput->setTextAlign(TextInputAlign::Left); - m_buttonMenu->addChildAtPosition(m_searchInput, Anchor::BottomLeft, { 38, 18 }); + m_buttonMenu->addChildAtPosition(m_searchInput, Anchor::BottomLeft, { 8, 18 }); m_buttonMenu->addChildAtPosition(m_categoryButtons, Anchor::Left, {55, 32}); auto searchSpr = CCSprite::createWithSpriteFrameName("gj_findBtn_001.png"); @@ -988,8 +988,10 @@ void ObjectWorkshop::onClickObject(CCObject* sender) { auto reportBtn = CCMenuItemSpriteExtra::create( reportSpr, this, menu_selector(ObjectWorkshop::onReportBtn) ); - if (m_user.account_id == m_currentObject.authorAccId || m_user.role == 3) { + if (m_user.account_id == m_currentObject.authorAccId || m_user.role == 2) { menu2->addChild(editBtn); + } + if (m_user.account_id == m_currentObject.authorAccId || m_user.role == 3) { menu2->addChild(trashBtn); } if (m_user.role >= 2 && m_currentObject.pending) { @@ -1868,9 +1870,11 @@ void ObjectWorkshop::onUploadBtn(CCObject*) { void ObjectWorkshop::onSearchBtn(CCObject*) { if (m_searchInput != nullptr) { if (m_searchInput->getString().empty()) return FLAlertLayer::create("Error", "You must enter in a search query!", "OK")->show(); + if (currentMenuIndexGD < 2) return FLAlertLayer::create("Error", "You cannot search in My Objects or Favorites! Please select another category.", "OK")->show(); isSearching = true; RegenCategory(); - } + } + //ObjectPopup::create(m_currentObject, m_user)->show(); } void ObjectWorkshop::onReloadBtn(CCObject*) { @@ -1903,6 +1907,7 @@ void ObjectWorkshop::onUploadFilterBtn(CCObject*) { void ObjectWorkshop::onUpload(CCObject*) { if (auto editor = EditorUI::get()) { if (auto gameManager = GameManager::sharedState()) { + if (m_filterTags.size() == 0) return FLAlertLayer::create("Error", "You must set a tag! Click on the grey filter button to set one!", "OK")->show(); if (m_filterTags.size() > 5) return FLAlertLayer::create("Error", "You cannot set more than 5 tags!", "OK")->show(); if (m_objName == nullptr || m_objDesc == nullptr) return FLAlertLayer::create("Error", "Couldn't find input nodes", "OK")->show(); if (m_objName != nullptr && m_objName->getString().empty()) return FLAlertLayer::create("Error", "You must enter in the object name!", "OK")->show(); diff --git a/src/ui/popups/CommentPopup.cpp b/src/ui/popups/CommentPopup.cpp index 467b189..4f9337b 100644 --- a/src/ui/popups/CommentPopup.cpp +++ b/src/ui/popups/CommentPopup.cpp @@ -46,39 +46,46 @@ bool CommentPopup::setup(ObjectData obj, utils::MiniFunction callback) { } void CommentPopup::textChanged(CCTextInputNode* input) { + if (m_closed) return; updateDescText(input->getString()); } void CommentPopup::textInputClosed(CCTextInputNode* input) { + if (input == nullptr || m_closed) return; m_descText = input->getString(); updateDescText(m_descText); } void CommentPopup::updateDescText(std::string string) { + if (m_closed) return; m_descText = string; updateCharCountLabel(); } void CommentPopup::updateCharCountLabel() { + if (m_closed) return; if (m_charCountLabel != nullptr) m_charCountLabel->setString(std::to_string(100 - m_descText.length()).c_str()); } +void CommentPopup::onClose(CCObject* sender) { + m_closed = true; + Popup::onClose(sender); +} + void CommentPopup::onSubmit(CCObject*) { if (m_descText.empty()) return; + if (m_closed) return; m_mainLayer->setVisible(false); auto token = Mod::get()->getSettingValue("token"); m_listener.getFilter().cancel(); - auto notif = Notification::create("Sending...", NotificationIcon::Loading); - notif->show(); - m_listener.bind([this, notif, token] (web::WebTask::Event* e) { + m_listener.bind([this] (web::WebTask::Event* e) { if (web::WebResponse* value = e->getValue()) { auto jsonRes = value->json().unwrapOrDefault(); if (!jsonRes.is_object()) return log::error("Response isn't object."); auto isError = jsonRes.try_get("error"); - if (isError) return Notification::create(isError->c_str(), NotificationIcon::Error)->show(); - notif->hide(); + if (isError) return Notification::create(isError.value(), NotificationIcon::Error)->show(); auto message = jsonRes.try_get("message"); if (message) { this->onClose(nullptr); - Notification::create(message->c_str(), NotificationIcon::Success)->show(); + Notification::create(message.value(), NotificationIcon::Success)->show(); m_submitCallback(); } else { log::error("Unknown response, expected message. {}", jsonRes.dump()); diff --git a/src/ui/popups/CommentPopup.hpp b/src/ui/popups/CommentPopup.hpp index eb8934c..f1a4595 100644 --- a/src/ui/popups/CommentPopup.hpp +++ b/src/ui/popups/CommentPopup.hpp @@ -11,6 +11,9 @@ class CommentPopup : public geode::Popup ObjectData m_object; CCLabelBMFont* m_charCountLabel; std::string m_descText; + + bool m_closed = false; // prevent unnecessary crash because for some reason this can happen + bool setup(ObjectData obj, utils::MiniFunction) override; void onSubmit(CCObject*); void updateCharCountLabel(); @@ -20,6 +23,7 @@ class CommentPopup : public geode::Popup void textInputOpened(CCTextInputNode*) override {} void textChanged(CCTextInputNode*) override; void textInputClosed(CCTextInputNode*) override; + virtual void onClose(CCObject* sender) override; public: static CommentPopup* create(ObjectData obj, utils::MiniFunction callback) { auto ret = new CommentPopup(); diff --git a/src/ui/popups/VotePopup.cpp b/src/ui/popups/VotePopup.cpp index c787bdc..82a21c4 100644 --- a/src/ui/popups/VotePopup.cpp +++ b/src/ui/popups/VotePopup.cpp @@ -1,10 +1,8 @@ #include "VotePopup.hpp" -#include "../../config.hpp" -bool VotePopup::setup(CommentData obj, utils::MiniFunction callback) { - m_data = obj; - m_forceRefresh = callback; - auto title = CCLabelBMFont::create("Vote", "bigFont.fnt"); +bool VotePopup::setup(std::string title_str, utils::MiniFunction callback) { + m_callback = callback; + auto title = CCLabelBMFont::create(title_str.c_str(), "bigFont.fnt"); m_mainLayer->addChildAtPosition(title, Anchor::Top, {0, -20}); auto likeSpr = CCSprite::createWithSpriteFrameName("GJ_likeBtn_001.png"); likeSpr->setScale(1.2F); @@ -21,54 +19,44 @@ bool VotePopup::setup(CommentData obj, utils::MiniFunction callback) { return true; } -void VotePopup::sendVote(bool like) { - auto token = Mod::get()->getSettingValue("token"); - m_listener.getFilter().cancel(); - this->setVisible(false); - m_listener.bind([this, token] (web::WebTask::Event* e) { - if (web::WebResponse* value = e->getValue()) { - auto jsonRes = value->json().unwrapOrDefault(); - if (!jsonRes.is_object()) { - log::error("Response isn't object."); - this->onClose(nullptr); - return; - } - auto isError = jsonRes.try_get("error"); - if (isError) { - Notification::create(isError->c_str(), NotificationIcon::Error)->show(); - this->onClose(nullptr); - return; - } - auto message = jsonRes.try_get("message"); - if (message) { - m_forceRefresh(); - Notification::create(message->c_str(), NotificationIcon::Success)->show(); - this->onClose(nullptr); - } else { - log::error("Unknown response, expected message. {}", jsonRes.dump()); - Notification::create("Got an unknown response, check logs for details.", NotificationIcon::Warning)->show(); - this->onClose(nullptr); - } - return; - } else if (web::WebProgress* progress = e->getProgress()) { - // The request is still in progress... - } else if (e->isCancelled()) { - log::error("Request was cancelled."); - this->onClose(nullptr); - } - }); - web::WebRequest req = web::WebRequest(); - auto myjson = matjson::Value(); - myjson.set("token", token); - myjson.set("like", (int)like); - req.header("Content-Type", "application/json"); - req.bodyJSON(myjson); - m_listener.setFilter(req.post(fmt::format("{}/objects/{}/comments/{}/vote", HOST_URL, m_data.objectID, m_data.id))); +void VotePopup::setWarning(std::string message1, std::string message2) { + m_warningMessage1 = message1; + m_warningMessage2 = message2; + m_showWarning = true; +} + +void VotePopup::onVote(bool vote) { + m_callback(vote); + this->onClose(nullptr); } void VotePopup::onLike(CCObject*) { - VotePopup::sendVote(true); + if (m_showWarning) { + geode::createQuickPopup( + "Warning", + m_warningMessage1, + "No", + "Yes", + [this](auto, bool btn2) { + if (btn2) + onVote(true); + }); + } else { + onVote(true); + } } void VotePopup::onDislike(CCObject*) { - VotePopup::sendVote(false); + if (m_showWarning) { + geode::createQuickPopup( + "Warning", + m_warningMessage2, + "No", + "Yes", + [this](auto, bool btn2) { + if (btn2) + onVote(false); + }); + } else { + onVote(false); + } } diff --git a/src/ui/popups/VotePopup.hpp b/src/ui/popups/VotePopup.hpp index 20e491d..6ced294 100644 --- a/src/ui/popups/VotePopup.hpp +++ b/src/ui/popups/VotePopup.hpp @@ -1,25 +1,24 @@ #pragma once #include #include -#include "../../nodes/CommentCell.hpp" -#include using namespace geode::prelude; -class VotePopup : public geode::Popup> { +class VotePopup : public geode::Popup> { protected: - EventListener m_listener; - utils::MiniFunction m_forceRefresh; - CommentData m_data; + utils::MiniFunction m_callback; + std::string m_warningMessage1; + std::string m_warningMessage2; + bool m_showWarning = false; - bool setup(CommentData obj, utils::MiniFunction callback) override; + bool setup(std::string, utils::MiniFunction) override; void onLike(CCObject*); void onDislike(CCObject*); - void sendVote(bool like); - + void onVote(bool vote); public: - static VotePopup* create(CommentData obj, utils::MiniFunction callback) { + void setWarning(std::string message1, std::string message2); + static VotePopup* create(std::string title, utils::MiniFunction callback) { auto ret = new VotePopup(); - if (ret->initAnchored(200.f, 115.f, obj, callback)) { + if (ret->initAnchored(200.f, 115.f, title, callback)) { ret->autorelease(); return ret; } diff --git a/src/ui/popups/includes.h b/src/ui/popups/includes.h index aaf0003..b869045 100644 --- a/src/ui/popups/includes.h +++ b/src/ui/popups/includes.h @@ -3,3 +3,5 @@ #include "FiltersPopup.hpp" #include "ReportPopup.hpp" #include "CommentPopup.hpp" +//#include "ObjectPopup.hpp" +#include "VotePopup.hpp"