diff --git a/THEMES.md b/THEMES.md index a4741ccce..1394950d9 100644 --- a/THEMES.md +++ b/THEMES.md @@ -342,6 +342,7 @@ Reference * `image name="logo"` - PATH - A logo image, to be displayed in the system logo carousel. * You can use extra elements (elements with `extra="true"`) to add your own backgrounds, etc. They will be displayed behind the carousel, and scroll relative to the carousel. + --- #### fastSelect @@ -419,6 +420,7 @@ Can be created as an extra. - Size of the font as a percentage of screen height (e.g. for a value of `0.1`, the text's height would be 10% of the screen height). * `alignment` - type: STRING. - Valid values are "left", "center", or "right". Controls alignment on the X axis. "center" will also align vertically. +* `forceUppercase` - type: BOOLEAN. Draw text in uppercase. #### textlist @@ -440,6 +442,7 @@ Can be created as an extra. - Valid values are "left", "center", or "right". Controls alignment on the X axis. * `horizontalMargin` - type: FLOAT. - Horizontal offset for text from the alignment point. If `alignment` is "left", offsets the text to the right. If `alignment` is "right", offsets text to the left. No effect if `alignment` is "center". Given as a percentage of the element's parent's width (same unit as `size`'s X value). +* `forceUppercase` - type: BOOLEAN. Draw text in uppercase. #### ninepatch @@ -467,6 +470,7 @@ EmulationStation borrows the concept of "nine patches" from Android (or "9-Slice * `color` - type: COLOR. * `fontPath` - type: PATH. * `fontSize` - type: FLOAT. +* `forceUppercase` - type: BOOLEAN. Draw text in uppercase. #### sound diff --git a/src/ThemeData.cpp b/src/ThemeData.cpp index f7712d29a..e3b7ede1a 100644 --- a/src/ThemeData.cpp +++ b/src/ThemeData.cpp @@ -39,7 +39,8 @@ std::map< std::string, ElementMapType > ThemeData::sElementMap = boost::assign:: ("color", COLOR) ("fontPath", PATH) ("fontSize", FLOAT) - ("alignment", STRING))) + ("alignment", STRING) + ("forceUppercase", BOOLEAN))) ("textlist", makeMap(boost::assign::map_list_of ("pos", NORMALIZED_PAIR) ("size", NORMALIZED_PAIR) @@ -51,7 +52,8 @@ std::map< std::string, ElementMapType > ThemeData::sElementMap = boost::assign:: ("fontSize", FLOAT) ("scrollSound", PATH) ("alignment", STRING) - ("horizontalMargin", FLOAT))) + ("horizontalMargin", FLOAT) + ("forceUppercase", BOOLEAN))) ("container", makeMap(boost::assign::map_list_of ("pos", NORMALIZED_PAIR) ("size", NORMALIZED_PAIR))) @@ -64,7 +66,8 @@ std::map< std::string, ElementMapType > ThemeData::sElementMap = boost::assign:: ("size", NORMALIZED_PAIR) ("color", COLOR) ("fontPath", PATH) - ("fontSize", FLOAT))) + ("fontSize", FLOAT) + ("forceUppercase", BOOLEAN))) ("rating", makeMap(boost::assign::map_list_of ("pos", NORMALIZED_PAIR) ("size", NORMALIZED_PAIR) diff --git a/src/ThemeData.h b/src/ThemeData.h index 0e23fa5c5..b9653d9ba 100644 --- a/src/ThemeData.h +++ b/src/ThemeData.h @@ -35,6 +35,7 @@ namespace ThemeFlags SOUND = 128, ALIGNMENT = 256, TEXT = 512, + FORCE_UPPERCASE = 1024, ALL = 0xFFFFFFFF }; diff --git a/src/components/DateTimeComponent.cpp b/src/components/DateTimeComponent.cpp index cf62d06e6..c9ed78ee1 100644 --- a/src/components/DateTimeComponent.cpp +++ b/src/components/DateTimeComponent.cpp @@ -7,7 +7,7 @@ DateTimeComponent::DateTimeComponent(Window* window, DisplayMode dispMode) : GuiComponent(window), mEditing(false), mEditIndex(0), mDisplayMode(dispMode), mRelativeUpdateAccumulator(0), - mColor(0x777777FF), mFont(Font::get(FONT_SIZE_SMALL, FONT_PATH_LIGHT)), mSizeSet(false) + mColor(0x777777FF), mFont(Font::get(FONT_SIZE_SMALL, FONT_PATH_LIGHT)), mUppercase(false), mSizeSet(false) { updateTextCache(); } @@ -15,6 +15,7 @@ DateTimeComponent::DateTimeComponent(Window* window, DisplayMode dispMode) : Gui void DateTimeComponent::setDisplayMode(DisplayMode mode) { mDisplayMode = mode; + updateTextCache(); } bool DateTimeComponent::input(InputConfig* config, Input input) @@ -249,7 +250,7 @@ std::shared_ptr DateTimeComponent::getFont() const void DateTimeComponent::updateTextCache() { DisplayMode mode = getCurrentDisplayMode(); - const std::string dispString = getDisplayString(mode); + const std::string dispString = mUppercase ? strToUpper(getDisplayString(mode)) : getDisplayString(mode); std::shared_ptr font = getFont(); mTextCache = std::unique_ptr(font->buildTextCache(dispString, 0, 0, mColor)); @@ -302,6 +303,12 @@ void DateTimeComponent::onSizeChanged() updateTextCache(); } +void DateTimeComponent::setUppercase(bool uppercase) +{ + mUppercase = uppercase; + updateTextCache(); +} + void DateTimeComponent::applyTheme(const std::shared_ptr& theme, const std::string& view, const std::string& element, unsigned int properties) { GuiComponent::applyTheme(theme, view, element, properties); @@ -315,5 +322,8 @@ void DateTimeComponent::applyTheme(const std::shared_ptr& theme, cons if(properties & COLOR && elem->has("color")) setColor(elem->get("color")); + if(properties & FORCE_UPPERCASE && elem->has("forceUppercase")) + setUppercase(elem->get("forceUppercase")); + setFont(Font::getFromTheme(elem, properties, mFont)); } diff --git a/src/components/DateTimeComponent.h b/src/components/DateTimeComponent.h index 039cf17bd..17e5ee920 100644 --- a/src/components/DateTimeComponent.h +++ b/src/components/DateTimeComponent.h @@ -34,6 +34,7 @@ public: void setColor(unsigned int color); // Text color. void setFont(std::shared_ptr font); // Font to display with. Default is Font::get(FONT_SIZE_MEDIUM). + void setUppercase(bool uppercase); // Force text to be uppercase when in DISP_RELATIVE_TO_NOW mode. virtual void applyTheme(const std::shared_ptr& theme, const std::string& view, const std::string& element, unsigned int properties) override; @@ -59,6 +60,7 @@ private: unsigned int mColor; std::shared_ptr mFont; + bool mUppercase; bool mSizeSet; }; diff --git a/src/components/TextComponent.cpp b/src/components/TextComponent.cpp index d64586769..dde58662d 100644 --- a/src/components/TextComponent.cpp +++ b/src/components/TextComponent.cpp @@ -7,13 +7,13 @@ #include "../Settings.h" TextComponent::TextComponent(Window* window) : GuiComponent(window), - mFont(Font::get(FONT_SIZE_MEDIUM)), mColor(0x000000FF), mAutoCalcExtent(true, true), mAlignment(ALIGN_LEFT) + mFont(Font::get(FONT_SIZE_MEDIUM)), mUppercase(false), mColor(0x000000FF), mAutoCalcExtent(true, true), mAlignment(ALIGN_LEFT) { } TextComponent::TextComponent(Window* window, const std::string& text, const std::shared_ptr& font, unsigned int color, Alignment align, Eigen::Vector3f pos, Eigen::Vector2f size) : GuiComponent(window), - mFont(NULL), mColor(0x000000FF), mAutoCalcExtent(true, true), mAlignment(align) + mFont(NULL), mUppercase(false), mColor(0x000000FF), mAutoCalcExtent(true, true), mAlignment(align) { setFont(font); setColor(color); @@ -63,6 +63,12 @@ void TextComponent::setText(const std::string& text) onTextChanged(); } +void TextComponent::setUppercase(bool uppercase) +{ + mUppercase = uppercase; + onTextChanged(); +} + void TextComponent::render(const Eigen::Affine3f& parentTrans) { Eigen::Affine3f trans = parentTrans * getTransform(); @@ -118,11 +124,11 @@ void TextComponent::calculateExtent() { if(mAutoCalcExtent.x()) { - mSize = mFont->sizeText(mText); + mSize = mFont->sizeText(mUppercase ? strToUpper(mText) : mText); }else{ if(mAutoCalcExtent.y()) { - mSize[1] = mFont->sizeWrappedText(mText, getSize().x()).y(); + mSize[1] = mFont->sizeWrappedText(mUppercase ? strToUpper(mText) : mText, getSize().x()).y(); } } } @@ -131,16 +137,17 @@ void TextComponent::onTextChanged() { calculateExtent(); + std::string text = mUppercase ? strToUpper(mText) : mText; + std::shared_ptr f = getFont(); const bool wrap = (mSize.y() == 0 || (int)mSize.y() > f->getHeight()); - Eigen::Vector2f size = f->sizeText(mText); - if(!wrap && mSize.x() && mText.size() && size.x() > mSize.x()) + Eigen::Vector2f size = f->sizeText(text); + if(!wrap && mSize.x() && text.size() && size.x() > mSize.x()) { // abbreviate text const std::string abbrev = "..."; Eigen::Vector2f abbrevSize = f->sizeText(abbrev); - std::string text = mText; while(text.size() && size.x() + abbrevSize.x() > mSize.x()) { text.erase(text.size() - 1, 1); @@ -151,7 +158,7 @@ void TextComponent::onTextChanged() mTextCache = std::shared_ptr(f->buildTextCache(text, 0, 0, (mColor >> 8 << 8) | mOpacity)); }else{ - mTextCache = std::shared_ptr(f->buildTextCache(f->wrapText(mText, mSize.x()), 0, 0, (mColor >> 8 << 8) | mOpacity)); + mTextCache = std::shared_ptr(f->buildTextCache(f->wrapText(text, mSize.x()), 0, 0, (mColor >> 8 << 8) | mOpacity)); } } @@ -202,5 +209,8 @@ void TextComponent::applyTheme(const std::shared_ptr& theme, const st if(properties & TEXT && elem->has("text")) setText(elem->get("text")); + if(properties & FORCE_UPPERCASE && elem->has("forceUppercase")) + setUppercase(elem->get("forceUppercase")); + setFont(Font::getFromTheme(elem, properties, mFont)); } diff --git a/src/components/TextComponent.h b/src/components/TextComponent.h index db6931cd5..52dfcb2a0 100644 --- a/src/components/TextComponent.h +++ b/src/components/TextComponent.h @@ -19,6 +19,7 @@ public: Eigen::Vector3f pos = Eigen::Vector3f::Zero(), Eigen::Vector2f size = Eigen::Vector2f::Zero()); void setFont(const std::shared_ptr& font); + void setUppercase(bool uppercase); void onSizeChanged() override; void setText(const std::string& text); void setColor(unsigned int color); @@ -44,6 +45,7 @@ private: unsigned int mColor; std::shared_ptr mFont; + bool mUppercase; Eigen::Matrix mAutoCalcExtent; std::string mText; std::shared_ptr mTextCache; diff --git a/src/components/TextListComponent.h b/src/components/TextListComponent.h index dc88f7c50..31267d42f 100644 --- a/src/components/TextListComponent.h +++ b/src/components/TextListComponent.h @@ -10,6 +10,7 @@ #include "../Sound.h" #include "../Log.h" #include "../ThemeData.h" +#include "../Util.h" #include struct TextListData @@ -60,7 +61,13 @@ public: inline void setFont(const std::shared_ptr& font) { mFont = font; - + for(auto it = mEntries.begin(); it != mEntries.end(); it++) + it->data.textCache.reset(); + } + + inline void setUppercase(bool uppercase) + { + mUppercase = true; for(auto it = mEntries.begin(); it != mEntries.end(); it++) it->data.textCache.reset(); } @@ -75,7 +82,6 @@ protected: virtual void onScroll(int amt) { if(mScrollSound) mScrollSound->play(); } virtual void onCursorChanged(const CursorState& state); - private: static const int MARQUEE_DELAY = 900; static const int MARQUEE_SPEED = 16; @@ -90,6 +96,7 @@ private: std::function mCursorChangedCallback; std::shared_ptr mFont; + bool mUppercase; unsigned int mSelectorColor; unsigned int mSelectedColor; std::shared_ptr mScrollSound; @@ -108,6 +115,7 @@ TextListComponent::TextListComponent(Window* window) : mAlignment = ALIGN_CENTER; mFont = Font::get(FONT_SIZE_MEDIUM); + mUppercase = false; mSelectorColor = 0x000000FF; mSelectedColor = 0; mColors[0] = 0x0000FFFF; @@ -171,7 +179,7 @@ void TextListComponent::render(const Eigen::Affine3f& parentTrans) color = mColors[entry.data.colorId]; if(!entry.data.textCache) - entry.data.textCache = std::unique_ptr(font->buildTextCache(entry.name, 0, 0, 0x000000FF)); + entry.data.textCache = std::unique_ptr(font->buildTextCache(mUppercase ? strToUpper(entry.name) : entry.name, 0, 0, 0x000000FF)); entry.data.textCache->setColor(color); @@ -351,4 +359,7 @@ void TextListComponent::applyTheme(const std::shared_ptr& theme, c mHorizontalMargin = elem->get("horizontalMargin") * (this->mParent ? this->mParent->getSize().x() : (float)Renderer::getScreenWidth()); } } + + if(properties & FORCE_UPPERCASE && elem->has("forceUppercase")) + setUppercase(elem->get("forceUppercase")); } diff --git a/src/views/gamelist/DetailedGameListView.cpp b/src/views/gamelist/DetailedGameListView.cpp index 5285f372c..6aa464c6d 100644 --- a/src/views/gamelist/DetailedGameListView.cpp +++ b/src/views/gamelist/DetailedGameListView.cpp @@ -107,7 +107,7 @@ void DetailedGameListView::onThemeChanged(const std::shared_ptr& them mDescContainer.applyTheme(theme, getName(), "md_description", POSITION | ThemeFlags::SIZE); mDescription.setSize(mDescContainer.getSize().x(), 0); - mDescription.applyTheme(theme, getName(), "md_description", FONT_PATH | FONT_SIZE | COLOR); + mDescription.applyTheme(theme, getName(), "md_description", FONT_PATH | FONT_SIZE | COLOR | FORCE_UPPERCASE); } void DetailedGameListView::initMDLabels()