From d3eb857482fbdae808ef2c1da86d9ff05202afce Mon Sep 17 00:00:00 2001 From: kepler-5 Date: Tue, 4 Jul 2017 18:25:12 -0700 Subject: [PATCH] horizontal alignment support in RichText (#18027) * horizontal alignment support in RichText * split lambda into separate function * tweak shadow test's content size so horizontal aligment doesn't give the illusion of behaving incorrectly * fix alignment when the last char of a line is whitespace * fix errors from merge * fix bug in setting of size of image elements. scaling was applied effectively twice. * removed debugging code. whoops --- cocos/ui/UIRichText.cpp | 90 +++++- cocos/ui/UIRichText.h | 11 + .../UIRichTextTest/UIRichTextTest.cpp | 303 ++++++++++++++++-- .../UIRichTextTest/UIRichTextTest.h | 26 +- 4 files changed, 397 insertions(+), 33 deletions(-) diff --git a/cocos/ui/UIRichText.cpp b/cocos/ui/UIRichText.cpp index 0bff49ac0a..a3f43d314a 100644 --- a/cocos/ui/UIRichText.cpp +++ b/cocos/ui/UIRichText.cpp @@ -27,6 +27,7 @@ #include #include #include +#include #include "platform/CCFileUtils.h" #include "platform/CCApplication.h" @@ -832,6 +833,7 @@ ValueMap MyXMLVisitor::tagAttrMapWithXMLElement(const char ** attrs) const std::string RichText::KEY_VERTICAL_SPACE("KEY_VERTICAL_SPACE"); const std::string RichText::KEY_WRAP_MODE("KEY_WRAP_MODE"); +const std::string RichText::KEY_HORIZONTAL_ALIGNMENT("KEY_HORIZONTAL_ALIGNMENT"); const std::string RichText::KEY_FONT_COLOR_STRING("KEY_FONT_COLOR_STRING"); const std::string RichText::KEY_FONT_SIZE("KEY_FONT_SIZE"); const std::string RichText::KEY_FONT_SMALL("KEY_FONT_SMALL"); @@ -875,6 +877,7 @@ RichText::RichText() { _defaults[KEY_VERTICAL_SPACE] = 0.0f; _defaults[KEY_WRAP_MODE] = static_cast(WrapMode::WRAP_PER_WORD); + _defaults[KEY_HORIZONTAL_ALIGNMENT] = static_cast(HorizontalAlignment::LEFT); _defaults[KEY_FONT_COLOR_STRING] = "#ffffff"; _defaults[KEY_FONT_SIZE] = 12.0f; _defaults[KEY_FONT_FACE] = "Verdana"; @@ -995,6 +998,20 @@ void RichText::setWrapMode(RichText::WrapMode wrapMode) } } +RichText::HorizontalAlignment RichText::getHorizontalAlignment() const +{ + return static_cast(_defaults.at(KEY_HORIZONTAL_ALIGNMENT).asInt()); +} + +void RichText::setHorizontalAlignment(cocos2d::ui::RichText::HorizontalAlignment a) +{ + if (static_cast(_defaults.at(KEY_HORIZONTAL_ALIGNMENT).asInt()) != a) + { + _defaults[KEY_HORIZONTAL_ALIGNMENT] = static_cast(a); + _formatTextDirty = true; + } +} + void RichText::setFontColor(const std::string& color) { _defaults[KEY_FONT_COLOR_STRING] = color; @@ -1198,6 +1215,9 @@ void RichText::setDefaults(const ValueMap& defaults) if (defaults.find(KEY_WRAP_MODE) != defaults.end()) { _defaults[KEY_WRAP_MODE] = defaults.at(KEY_WRAP_MODE).asInt(); } + if (defaults.find(KEY_HORIZONTAL_ALIGNMENT) != defaults.end()) { + _defaults[KEY_HORIZONTAL_ALIGNMENT] = defaults.at(KEY_HORIZONTAL_ALIGNMENT).asInt(); + } if (defaults.find(KEY_FONT_COLOR_STRING) != defaults.end()) { _defaults[KEY_FONT_COLOR_STRING] = defaults.at(KEY_FONT_COLOR_STRING).asString(); } @@ -1692,7 +1712,7 @@ void RichText::handleImageRenderer(const std::string& filePath, const Color3B &/ imageRenderer->setScaleY(height / currentSize.height); imageRenderer->setContentSize(Size(currentSize.width * imageRenderer->getScaleX(), currentSize.height * imageRenderer->getScaleY())); - + imageRenderer->setScale(1.f, 1.f); handleCustomRenderer(imageRenderer); imageRenderer->addComponent(ListenerComponent::create(imageRenderer, url, @@ -1728,6 +1748,8 @@ void RichText::formarRenderers() { float newContentSizeWidth = 0.0f; float nextPosY = 0.0f; + std::vector*, float> > rowWidthPairs; + rowWidthPairs.reserve(_elementRenders.size()); for (auto& element: _elementRenders) { float nextPosX = 0.0f; @@ -1743,13 +1765,16 @@ void RichText::formarRenderers() maxY = MAX(maxY, iSize.height); } nextPosY -= maxY; + rowWidthPairs.emplace_back(&element, nextPosX); } this->setContentSize(Size(newContentSizeWidth, -nextPosY)); + for ( auto& row : rowWidthPairs ) + doHorizontalAlignment(*row.first, row.second); } else { float newContentSizeHeight = 0.0f; - float *maxHeights = new (std::nothrow) float[_elementRenders.size()]; + std::vector maxHeights(_elementRenders.size()); for (size_t i=0, size = _elementRenders.size(); iaddProtectedChild(iter, 1); nextPosX += iter->getContentSize().width; } + + doHorizontalAlignment(row, nextPosX); } - delete [] maxHeights; } _elementRenders.clear(); @@ -1794,12 +1820,66 @@ void RichText::formarRenderers() } updateContentSizeWithTextureSize(_contentSize); } - + +namespace { + float getPaddingAmount(const RichText::HorizontalAlignment alignment, const float leftOver) { + switch ( alignment ) { + case RichText::HorizontalAlignment::CENTER: + return leftOver / 2.f; + case RichText::HorizontalAlignment::RIGHT: + return leftOver; + default: + CCASSERT(false, "invalid horizontal alignment!"); + return 0.f; + } + } +} + +void RichText::doHorizontalAlignment(const Vector &row, float rowWidth) { + const auto alignment = static_cast(_defaults.at(KEY_HORIZONTAL_ALIGNMENT).asInt()); + if ( alignment != HorizontalAlignment::LEFT ) { + const auto diff = stripTrailingWhitespace(row); + const auto leftOver = getContentSize().width - (rowWidth + diff); + const float leftPadding = getPaddingAmount(alignment, leftOver); + const Vec2 offset(leftPadding, 0.f); + for ( auto& node : row ) { + node->setPosition(node->getPosition() + offset); + } + } +} + +namespace { + bool isWhitespace(char c) { + return std::isspace(c, std::locale()); + } + std::string rtrim(std::string s) { + s.erase(std::find_if_not(s.rbegin(), + s.rend(), + isWhitespace).base(), + s.end()); + return s; + } +} + +float RichText::stripTrailingWhitespace(const Vector& row) { + if ( !row.empty() ) { + if ( auto label = dynamic_cast(row.back()) ) { + const auto width = label->getContentSize().width; + const auto trimmedString = rtrim(label->getString()); + if ( label->getString() != trimmedString ) { + label->setString(trimmedString); + return label->getContentSize().width - width; + } + } + } + return 0.0f; +} + void RichText::adaptRenderers() { this->formatText(); } - + void RichText::pushToContainer(cocos2d::Node *renderer) { if (_elementRenders.size() <= 0) diff --git a/cocos/ui/UIRichText.h b/cocos/ui/UIRichText.h index 7bdcf09439..f01d70f4dd 100644 --- a/cocos/ui/UIRichText.h +++ b/cocos/ui/UIRichText.h @@ -348,6 +348,12 @@ public: WRAP_PER_CHAR }; + enum class HorizontalAlignment { + LEFT, + CENTER, + RIGHT, + }; + /** * @brief call to open a resource specified by a URL * @param url a URL @@ -363,6 +369,7 @@ public: static const std::string KEY_VERTICAL_SPACE; /*!< key of vertical space */ static const std::string KEY_WRAP_MODE; /*!< key of per word, or per char */ + static const std::string KEY_HORIZONTAL_ALIGNMENT; /*!< key of left, right, or center */ static const std::string KEY_FONT_COLOR_STRING; /*!< key of font color */ static const std::string KEY_FONT_SIZE; /*!< key of font size */ static const std::string KEY_FONT_SMALL; /*!< key of font size small */ @@ -476,6 +483,8 @@ public: void setWrapMode(WrapMode wrapMode); /*!< sets the wrapping mode: WRAP_PER_CHAR or WRAP_PER_WORD */ WrapMode getWrapMode() const; /*!< returns the current wrapping mode */ + void setHorizontalAlignment(HorizontalAlignment a); /*!< sets the horizontal alignment mode: LEFT, CENTER, or RIGHT */ + HorizontalAlignment getHorizontalAlignment() const; /*!< returns the current horizontal alignment mode */ void setFontColor(const std::string& color); /*!< Set the font color. @param color the #RRGGBB hexadecimal notation. */ std::string getFontColor(); /*!< return the current font color */ Color3B getFontColor3B(); /*!< return the current font color */ @@ -559,6 +568,8 @@ protected: void addNewLine(); int findSplitPositionForWord(cocos2d::Label* label, const std::string& text); int findSplitPositionForChar(cocos2d::Label* label, const std::string& text); + void doHorizontalAlignment(const Vector& row, float rowWidth); + float stripTrailingWhitespace(const Vector& row); bool _formatTextDirty; Vector _richElements; diff --git a/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.cpp b/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.cpp index 7ee1e7fe84..cb59ead543 100644 --- a/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.cpp +++ b/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.cpp @@ -70,11 +70,18 @@ bool UIRichTextTest::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextTest::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); - + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextTest::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::create(); @@ -151,6 +158,15 @@ void UIRichTextTest::switchWrapMode(Ref *pSender, Widget::TouchEventType type) } } +void UIRichTextTest::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLBasic // @@ -178,11 +194,18 @@ bool UIRichTextXMLBasic::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLBasic::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLBasic::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("This is just a simple text. no xml tags here. testing the basics. testing word-wrapping. testing, testing, testing"); @@ -236,6 +259,15 @@ void UIRichTextXMLBasic::switchWrapMode(Ref *pSender, Widget::TouchEventType typ } } +void UIRichTextXMLBasic::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLSmallBig // @@ -263,11 +295,18 @@ bool UIRichTextXMLSmallBig::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSmallBig::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSmallBig::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("Regular size.smaller size.bigger.normal.bigger.normal."); @@ -321,6 +360,15 @@ void UIRichTextXMLSmallBig::switchWrapMode(Ref *pSender, Widget::TouchEventType } } +void UIRichTextXMLSmallBig::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLColor // @@ -348,11 +396,18 @@ bool UIRichTextXMLColor::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLColor::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); - + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLColor::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("Default color.red.greenred again.default again"); @@ -406,6 +461,15 @@ void UIRichTextXMLColor::switchWrapMode(Ref *pSender, Widget::TouchEventType typ } } +void UIRichTextXMLColor::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLSUIB // @@ -433,11 +497,18 @@ bool UIRichTextXMLSUIB::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSUIB::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSUIB::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("system font: underlineitalicsboldstrike-through"); @@ -491,6 +562,15 @@ void UIRichTextXMLSUIB::switchWrapMode(Ref *pSender, Widget::TouchEventType type } } +void UIRichTextXMLSUIB::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLSUIB2 // @@ -518,11 +598,18 @@ bool UIRichTextXMLSUIB2::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSUIB2::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSUIB2::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("ttf font: underlineitalicsboldstrike-through"); @@ -576,6 +663,15 @@ void UIRichTextXMLSUIB2::switchWrapMode(Ref *pSender, Widget::TouchEventType typ } } +void UIRichTextXMLSUIB2::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLSUIB3 // @@ -603,11 +699,18 @@ bool UIRichTextXMLSUIB3::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSUIB3::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLSUIB3::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("ttf font: italics and underlinebold and strike-through"); @@ -661,6 +764,15 @@ void UIRichTextXMLSUIB3::switchWrapMode(Ref *pSender, Widget::TouchEventType typ } } +void UIRichTextXMLSUIB3::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLImg // @@ -688,11 +800,18 @@ bool UIRichTextXMLImg::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLImg::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLImg::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("you should see an image here: and this is text again. and this is the same image, but bigger: and here goes text again"); @@ -746,6 +865,15 @@ void UIRichTextXMLImg::switchWrapMode(Ref *pSender, Widget::TouchEventType type) } } +void UIRichTextXMLImg::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLUrl // @@ -773,11 +901,18 @@ bool UIRichTextXMLUrl::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLUrl::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLUrl::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("And this link will redirect you to google: click me"); @@ -831,6 +966,15 @@ void UIRichTextXMLUrl::switchWrapMode(Ref *pSender, Widget::TouchEventType type) } } +void UIRichTextXMLUrl::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLUrlImg // @@ -858,11 +1002,18 @@ bool UIRichTextXMLUrlImg::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLUrlImg::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); - + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLUrlImg::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("And this link will redirect you to google: "); @@ -916,6 +1067,15 @@ void UIRichTextXMLUrlImg::switchWrapMode(Ref *pSender, Widget::TouchEventType ty } } +void UIRichTextXMLUrlImg::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLFace // @@ -943,11 +1103,18 @@ bool UIRichTextXMLFace::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLFace::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLFace::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("Marker Felt 20.Arial 20.Thonburi 24 blue"); @@ -1001,6 +1168,15 @@ void UIRichTextXMLFace::switchWrapMode(Ref *pSender, Widget::TouchEventType type } } +void UIRichTextXMLFace::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLBR // @@ -1028,11 +1204,18 @@ bool UIRichTextXMLBR::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLBR::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLBR::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("this is one line.
this should be in another line.
and this is another line"); @@ -1086,6 +1269,15 @@ void UIRichTextXMLBR::switchWrapMode(Ref *pSender, Widget::TouchEventType type) } } +void UIRichTextXMLBR::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLInvalid // @@ -1150,11 +1342,18 @@ bool UIRichTextXMLOutline::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLOutline::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); - + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLOutline::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("OUTLINE"); @@ -1208,6 +1407,15 @@ void UIRichTextXMLOutline::switchWrapMode(Ref *pSender, Widget::TouchEventType t } } +void UIRichTextXMLOutline::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLShadow // @@ -1235,16 +1443,23 @@ bool UIRichTextXMLShadow::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLShadow::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); - + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLShadow::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("SHADOW"); _richText->ignoreContentAdaptWithSize(false); - _richText->setContentSize(Size(100, 100)); + _richText->setContentSize(Size(150, 100)); _richText->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2)); _richText->setLocalZOrder(10); @@ -1293,6 +1508,15 @@ void UIRichTextXMLShadow::switchWrapMode(Ref *pSender, Widget::TouchEventType ty } } +void UIRichTextXMLShadow::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLGlow // @@ -1320,11 +1544,18 @@ bool UIRichTextXMLGlow::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLGlow::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); - + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLGlow::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); // RichText _richText = RichText::createWithXML("GLOW"); @@ -1378,6 +1609,15 @@ void UIRichTextXMLGlow::switchWrapMode(Ref *pSender, Widget::TouchEventType type } } +void UIRichTextXMLGlow::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} + // // UIRichTextXMLExtend // @@ -1405,10 +1645,18 @@ bool UIRichTextXMLExtend::init() Button* button2 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); button2->setTouchEnabled(true); button2->setTitleText("wrap mode"); - button2->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button2->setPosition(Vec2(widgetSize.width / 2, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); button2->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLExtend::switchWrapMode, this)); button2->setLocalZOrder(10); _widget->addChild(button2); + + Button* button3 = Button::create("cocosui/animationbuttonnormal.png", "cocosui/animationbuttonpressed.png"); + button3->setTouchEnabled(true); + button3->setTitleText("alignment"); + button3->setPosition(Vec2(widgetSize.width * 2 / 3, widgetSize.height / 2.0f + button2->getContentSize().height * 2.5)); + button3->addTouchEventListener(CC_CALLBACK_2(UIRichTextXMLExtend::switchAlignment, this)); + button3->setLocalZOrder(10); + _widget->addChild(button3); /* Tag extension */ RichText::setTagDescription("CloseNormal", false, [](const ValueMap& tagAttrValueMap) { @@ -1498,3 +1746,12 @@ void UIRichTextXMLExtend::switchWrapMode(Ref *pSender, Widget::TouchEventType ty _richText->setWrapMode(wrapMode); } } + +void UIRichTextXMLExtend::switchAlignment(Ref *sender, Widget::TouchEventType type) { + if (type == Widget::TouchEventType::ENDED) + { + auto alignment = _richText->getHorizontalAlignment(); + alignment = static_cast((static_cast::type>(alignment)+1) % 3); + _richText->setHorizontalAlignment(alignment); + } +} diff --git a/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.h b/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.h index 3b6f564569..947e25bfff 100644 --- a/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.h +++ b/tests/cpp-tests/Classes/UITest/CocoStudioGUITest/UIRichTextTest/UIRichTextTest.h @@ -15,6 +15,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -28,6 +29,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -41,6 +43,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -54,6 +57,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -67,6 +71,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -80,6 +85,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -93,6 +99,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -106,6 +113,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -119,6 +127,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -132,7 +141,8 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); - + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + protected: cocos2d::ui::RichText* _richText; }; @@ -145,6 +155,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -158,6 +169,7 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); protected: cocos2d::ui::RichText* _richText; @@ -182,7 +194,8 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); - + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + protected: cocos2d::ui::RichText* _richText; }; @@ -195,7 +208,8 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); - + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + protected: cocos2d::ui::RichText* _richText; }; @@ -208,7 +222,8 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); - + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + protected: cocos2d::ui::RichText* _richText; }; @@ -221,7 +236,8 @@ public: bool init() override; void touchEvent(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); void switchWrapMode(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); - + void switchAlignment(cocos2d::Ref* sender, cocos2d::ui::Widget::TouchEventType type); + protected: cocos2d::ui::RichText* _richText; };