From 26729c3f349f19b62e6b751772d07210b04f8490 Mon Sep 17 00:00:00 2001 From: HJfod <60038575+HJfod@users.noreply.github.com> Date: Thu, 9 May 2024 11:49:19 +0300 Subject: [PATCH] cherry-pick changes to ui/General from new-index-but-better --- loader/include/Geode/ui/General.hpp | 52 ++++++++++++++++ loader/src/ui/nodes/General.cpp | 93 +++++++++++++++++++++++++++++ 2 files changed, 145 insertions(+) diff --git a/loader/include/Geode/ui/General.hpp b/loader/include/Geode/ui/General.hpp index 941e2dbf..e8b6acbc 100644 --- a/loader/include/Geode/ui/General.hpp +++ b/loader/include/Geode/ui/General.hpp @@ -11,12 +11,64 @@ namespace geode { */ GEODE_DLL cocos2d::CCSprite* createLayerBG(); + enum class SideArt { + BottomLeft = 0b0001, + BottomRight = 0b0010, + TopLeft = 0b0100, + TopRight = 0b1000, + Bottom = 0b0011, + Top = 0b1100, + All = 0b1111, + }; + constexpr SideArt operator|(SideArt a, SideArt b) { + return static_cast<SideArt>(static_cast<int>(a) | static_cast<int>(b)); + } + constexpr bool operator&(SideArt a, SideArt b) { + return static_cast<bool>(static_cast<int>(a) & static_cast<int>(b)); + } + + /** + * Add side art (corner pieces) for a layer + * @param to Layer to add corner pieces to + * @param sides Which corners to populate; by default, populates all + * @param useAnchorLayout If true, `to` is given an `AnchorLayout` and the + * corners' positions are dynamically updated + */ + GEODE_DLL void addSideArt(cocos2d::CCNode* to, SideArt sides = SideArt::All, bool useAnchorLayout = false); + /** * Add the rounded comment borders to a node + * @note Use the `ListBorders` class for increased control */ GEODE_DLL void addListBorders( cocos2d::CCNode* to, cocos2d::CCPoint const& center, cocos2d::CCSize const& size ); + + class GEODE_DLL ListBorders : public cocos2d::CCNode { + protected: + cocos2d::extension::CCScale9Sprite* m_top = nullptr; + cocos2d::extension::CCScale9Sprite* m_bottom = nullptr; + cocos2d::CCSprite* m_left = nullptr; + cocos2d::CCSprite* m_right = nullptr; + float m_topPadding = 7.5f; + float m_bottomPadding = 7.5f; + + bool init(); + + public: + static ListBorders* create(); + + void setSpriteFrames(const char* topAndBottom, const char* sides, float topPadding = 7.5f); + void setSprites( + cocos2d::extension::CCScale9Sprite* top, + cocos2d::extension::CCScale9Sprite* bottom, + cocos2d::CCSprite* left, + cocos2d::CCSprite* right, + float topPadding = 7.5f, + float bottomPadding = 7.5f + ); + void setContentSize(cocos2d::CCSize const& size) override; + }; } diff --git a/loader/src/ui/nodes/General.cpp b/loader/src/ui/nodes/General.cpp index b5163d29..df8f524c 100644 --- a/loader/src/ui/nodes/General.cpp +++ b/loader/src/ui/nodes/General.cpp @@ -18,6 +18,29 @@ CCSprite* geode::createLayerBG() { return bg; } +void geode::addSideArt(CCNode* to, SideArt sides, bool useAnchorLayout) { + if (sides & SideArt::BottomLeft) { + auto spr = CCSprite::createWithSpriteFrameName("GJ_sideArt_001.png"); + to->addChildAtPosition(spr, Anchor::BottomLeft, ccp(35, 35), useAnchorLayout); + } + if (sides & SideArt::BottomRight) { + auto spr = CCSprite::createWithSpriteFrameName("GJ_sideArt_001.png"); + spr->setFlipX(true); + to->addChildAtPosition(spr, Anchor::BottomRight, ccp(-35, 35), useAnchorLayout); + } + if (sides & SideArt::TopLeft) { + auto spr = CCSprite::createWithSpriteFrameName("GJ_sideArt_001.png"); + spr->setFlipY(true); + to->addChildAtPosition(spr, Anchor::TopLeft, ccp(35, -35), useAnchorLayout); + } + if (sides & SideArt::TopRight) { + auto spr = CCSprite::createWithSpriteFrameName("GJ_sideArt_001.png"); + spr->setFlipX(true); + spr->setFlipY(true); + to->addChildAtPosition(spr, Anchor::TopRight, ccp(-35, -35), useAnchorLayout); + } +} + void geode::addListBorders(CCNode* to, CCPoint const& center, CCSize const& size) { // if the size is 346.f, the top aligns perfectly by default :3 if (size.width == 346.f) { @@ -89,3 +112,73 @@ void geode::addListBorders(CCNode* to, CCPoint const& center, CCSize const& size }); to->addChild(layerRightSpr); } + +bool ListBorders::init() { + if (!CCNode::init()) + return false; + + this->setAnchorPoint({ .5f, .5f }); + this->setSpriteFrames("GJ_commentTop_001.png", "GJ_commentSide_001.png"); + + return true; +} + +ListBorders* ListBorders::create() { + auto ret = new ListBorders(); + if (ret && ret->init()) { + ret->autorelease(); + return ret; + } + CC_SAFE_DELETE(ret); + return nullptr; +} + +void ListBorders::setSpriteFrames(const char* topAndBottom, const char* side, float topPadding) { + this->setSprites( + CCScale9Sprite::createWithSpriteFrameName(topAndBottom), + CCScale9Sprite::createWithSpriteFrameName(topAndBottom), + CCSprite::createWithSpriteFrameName(side), + CCSprite::createWithSpriteFrameName(side), + topPadding, + topPadding + ); + m_bottom->setScaleY(-1); + m_right->setFlipX(true); +} +void ListBorders::setSprites( + CCScale9Sprite* top, CCScale9Sprite* bottom, + CCSprite* left, CCSprite* right, + float topPadding, float bottomPadding +) { + if (m_top) m_top->removeFromParent(); + if (m_bottom) m_bottom->removeFromParent(); + if (m_left) m_left->removeFromParent(); + if (m_right) m_right->removeFromParent(); + + m_top = top; + this->addChildAtPosition(m_top, Anchor::Top, ccp(0, -m_top->getScaledContentHeight() / 3)); + + m_bottom = bottom; + this->addChildAtPosition(m_bottom, Anchor::Bottom, ccp(0, m_bottom->getScaledContentHeight() / 3)); + + m_left = left; + this->addChildAtPosition(m_left, Anchor::Left, ccp(0, 0)); + + m_right = right; + this->addChildAtPosition(m_right, Anchor::Right, ccp(0, 0)); + + m_topPadding = topPadding; + m_bottomPadding = bottomPadding; + + this->setContentSize(m_obContentSize); +} +void ListBorders::setContentSize(CCSize const& size) { + CCNode::setContentSize(size); + this->updateLayout(); + + m_top->setContentWidth(size.width + m_topPadding); + m_bottom->setContentWidth(size.width + m_bottomPadding); + auto height = m_top->getContentHeight() * 0.75 + m_bottom->getContentHeight() * 0.75; + m_left->setScaleY((size.height - height) / m_left->getContentHeight()); + m_right->setScaleY((size.height - height) / m_right->getContentHeight()); +}