Skip to content

Commit

Permalink
Add a button that copies the mod list (#1039)
Browse files Browse the repository at this point in the history
* New image arguments format

* add ampersand support whoops

* first moves oh lord

* it's finished holy moly

* made it slightly better

* almost forgot

* texture revamp by @Alphalaneous

* why is it not loading

* whoops

* FINALLY

* targetsOutdatedVersion

* i love abi breaks

* how's this

* this thing

* this is driving me nuts
  • Loading branch information
hiimjustin000 authored Nov 19, 2024
1 parent 1ff24f0 commit dd1d835
Show file tree
Hide file tree
Showing 3 changed files with 123 additions and 0 deletions.
4 changes: 4 additions & 0 deletions loader/resources/mod.json.in
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,10 @@
"name": "Expand Installed Mods List",
"description": "Make the installed mods list a single infinite scrollable list instead of having pages"
},
"copy-mods": {
"type": "custom:copy-mods",
"name": ""
},
"developer-title": {
"type": "title",
"name": "Developer Settings"
Expand Down
43 changes: 43 additions & 0 deletions loader/src/loader/CopyButtonSetting.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
#include "CopyButtonSetting.hpp"
#include <Geode/loader/Mod.hpp>

$on_mod(Loaded) {
(void)Mod::get()->registerCustomSettingType("copy-mods", &CopyButtonSetting::parse);
}

SettingNodeV3* CopyButtonSetting::createNode(float width) {
return CopyButtonSettingNode::create(std::static_pointer_cast<CopyButtonSetting>(shared_from_this()), width);
}

void CopyButtonSettingNode::onCopy(CCObject*) {
auto mods = Loader::get()->getAllMods();
if (mods.empty()) {
Notification::create("No mods installed", NotificationIcon::Info, 0.5f)->show();
return;
}

std::sort(mods.begin(), mods.end(), [](Mod* a, Mod* b) {
auto const s1 = a->getID();
auto const s2 = b->getID();
return std::lexicographical_compare(s1.begin(), s1.end(), s2.begin(), s2.end(), [](auto a, auto b) {
return std::tolower(a) < std::tolower(b);
});
});

std::string modsList;
using namespace std::string_view_literals;
for (int i = 0; i < mods.size(); i++) {
auto& mod = mods[i];
modsList += fmt::format("{} | [{}] {}{}",
mod->isEnabled() ? "x"sv :
mod->hasLoadProblems() ? "!"sv :
mod->targetsOutdatedVersion() ? "*"sv :
" "sv,
mod->getVersion().toVString(), mod->getID(),
i < mods.size() ? "\n" : ""
);
}
clipboard::write(modsList);

Notification::create("Mods list copied to clipboard", NotificationIcon::Info, 0.5f)->show();
}
76 changes: 76 additions & 0 deletions loader/src/loader/CopyButtonSetting.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
#include <Geode/loader/SettingV3.hpp>
#include <ui/mods/GeodeStyle.hpp>

using namespace geode::prelude;

class CopyButtonSetting : public SettingV3 {
public:
static Result<std::shared_ptr<SettingV3>> parse(std::string const& key, std::string const& modID, matjson::Value const& json) {
auto res = std::make_shared<CopyButtonSetting>();
auto root = checkJson(json, "CopyButtonSetting");

res->init(key, modID, root);
res->parseNameAndDescription(root);

return root.ok(std::static_pointer_cast<SettingV3>(res));
}

bool load(matjson::Value const& json) override {
return true;
}
bool save(matjson::Value& json) const override {
return true;
}

bool isDefaultValue() const override {
return true;
}
void reset() override {}

SettingNodeV3* createNode(float width) override;
};

class CopyButtonSettingNode : public SettingNodeV3 {
protected:
bool init(std::shared_ptr<CopyButtonSetting> setting, float width) {
if (!SettingNodeV3::init(setting, width))
return false;

auto buttonSprite = createGeodeButton("Copy Mods");
buttonSprite->setScale(.5f);
auto button = CCMenuItemSpriteExtra::create(
buttonSprite, this, menu_selector(CopyButtonSettingNode::onCopy)
);
this->getButtonMenu()->addChildAtPosition(button, Anchor::Center);
this->getButtonMenu()->setPosition(getContentSize() / 2);
this->getButtonMenu()->setAnchorPoint({ .5f, .5f });
this->getButtonMenu()->updateLayout();

this->updateState(nullptr);

return true;
}

void onCopy(CCObject*);

void onCommit() override {}
void onResetToDefault() override {}

public:
static CopyButtonSettingNode* create(std::shared_ptr<CopyButtonSetting> setting, float width) {
auto ret = new CopyButtonSettingNode();
if (ret && ret->init(setting, width)) {
ret->autorelease();
return ret;
}
CC_SAFE_DELETE(ret);
return nullptr;
}

bool hasUncommittedChanges() const override {
return false;
}
bool hasNonDefaultValue() const override {
return false;
}
};

0 comments on commit dd1d835

Please sign in to comment.