Replaced the ambiguous alignment properties with specific horizontal and vertical properties.

This commit is contained in:
Leon Styhre 2022-02-11 00:19:08 +01:00
parent e6d6f3252f
commit 4eb763d816
9 changed files with 247 additions and 75 deletions

View file

@ -44,6 +44,13 @@ std::vector<std::string> ThemeData::sLegacySupportedFeatures {
{"z-index"},
{"visible"}};
std::vector<std::string> ThemeData::sLegacyElements {
{"showSnapshotNoVideo"},
{"showSnapshotDelay"},
{"forceUppercase"},
{"alignment"},
{"logoAlignment"}};
std::vector<std::pair<std::string, std::string>> ThemeData::sSupportedAspectRatios {
{"16:9", "16:9"},
{"16:9_vertical", "16:9 vertical"},
@ -124,7 +131,8 @@ std::map<std::string, std::map<std::string, ThemeData::ElementPropertyType>>
{"origin", NORMALIZED_PAIR},
{"rotation", FLOAT},
{"rotationOrigin", NORMALIZED_PAIR},
{"alignment", STRING},
{"horizontalAlignment", STRING},
{"alignment", STRING}, // For backward compatibility with legacy themes.
{"direction", STRING},
{"lines", FLOAT},
{"itemsPerLine", FLOAT},
@ -150,7 +158,9 @@ std::map<std::string, std::map<std::string, ThemeData::ElementPropertyType>>
{"containerResetDelay", FLOAT},
{"fontPath", PATH},
{"fontSize", FLOAT},
{"alignment", STRING},
{"horizontalAlignment", STRING},
{"verticalAlignment", STRING},
{"alignment", STRING}, // For backward compatibility with legacy themes.
{"color", COLOR},
{"backgroundColor", COLOR},
{"letterCase", STRING},
@ -167,7 +177,9 @@ std::map<std::string, std::map<std::string, ThemeData::ElementPropertyType>>
{"metadata", STRING},
{"fontPath", PATH},
{"fontSize", FLOAT},
{"alignment", STRING},
{"horizontalAlignment", STRING},
{"verticalAlignment", STRING},
{"alignment", STRING}, // For backward compatibility with legacy themes.
{"color", COLOR},
{"backgroundColor", COLOR},
{"letterCase", STRING},
@ -187,7 +199,9 @@ std::map<std::string, std::map<std::string, ThemeData::ElementPropertyType>>
{"fontSize", FLOAT},
{"color", COLOR},
{"backgroundColor", COLOR},
{"alignment", STRING},
{"horizontalAlignment", STRING},
{"verticalAlignment", STRING},
{"alignment", STRING}, // For backward compatibility with legacy themes.
{"visible", BOOLEAN},
{"zIndex", FLOAT}}},
{"rating",
@ -214,7 +228,9 @@ std::map<std::string, std::map<std::string, ThemeData::ElementPropertyType>>
{"logoScale", FLOAT},
{"logoRotation", FLOAT},
{"logoRotationOrigin", NORMALIZED_PAIR},
{"logoAlignment", STRING},
{"logoHorizontalAlignment", STRING},
{"logoVerticalAlignment", STRING},
{"logoAlignment", STRING}, // For backward compatibility with legacy themes.
{"maxLogoCount", FLOAT},
{"text", STRING},
{"textColor", COLOR},
@ -243,7 +259,8 @@ std::map<std::string, std::map<std::string, ThemeData::ElementPropertyType>>
{"fontSize", FLOAT},
{"scrollHide", BOOLEAN},
{"scrollSound", PATH}, // For backward compatibility with legacy themes.
{"alignment", STRING},
{"horizontalAlignment", STRING},
{"alignment", STRING}, // For backward compatibility with legacy themes.
{"horizontalMargin", FLOAT},
{"letterCase", STRING},
{"forceUppercase", BOOLEAN}, // For backward compatibility with legacy themes.
@ -1069,14 +1086,14 @@ void ThemeData::parseElement(const pugi::xml_node& root,
std::string nodeName = node.name();
// Strictly enforce removal of legacy elements for non-legacy theme sets by creating
// an unthemed system if they're present in the configuration.
if (!mLegacyTheme) {
if (nodeName == "showSnapshotNoVideo" || nodeName == "showSnapshotDelay") {
throw error << ": Legacy <" << nodeName
<< "> property found for non-legacy theme set";
}
else if (nodeName == "forceUppercase") {
throw error << ": Legacy <" << nodeName
<< "> property found for non-legacy theme set";
for (auto& legacyElement : sLegacyElements) {
if (nodeName == legacyElement) {
throw error << ": Legacy <" << nodeName
<< "> property found for non-legacy theme set";
}
}
}

View file

@ -239,14 +239,15 @@ private:
const std::map<std::string, ElementPropertyType>& typeMap,
ThemeElement& element);
static std::map<std::string, std::map<std::string, ElementPropertyType>> sElementMap;
static std::map<std::string, std::map<std::string, std::string>> sPropertyAttributeMap;
static std::vector<std::string> sLegacySupportedFeatures;
static std::vector<std::string> sLegacySupportedViews;
static std::vector<std::string> sSupportedViews;
static std::vector<std::string> sLegacySupportedViews;
static std::vector<std::string> sLegacySupportedFeatures;
static std::vector<std::string> sLegacyElements;
static std::vector<std::pair<std::string, std::string>> sSupportedAspectRatios;
static std::map<std::string, std::map<std::string, std::string>> sPropertyAttributeMap;
static std::map<std::string, std::map<std::string, ElementPropertyType>> sElementMap;
static inline std::map<std::string, ThemeSet> mThemeSets;
std::map<std::string, ThemeData::ThemeSet>::iterator mCurrentThemeSet;

View file

@ -195,7 +195,19 @@ void BadgeComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
if (!elem)
return;
if (elem->has("alignment")) {
if (elem->has("horizontalAlignment")) {
const std::string horizontalAlignment {elem->get<std::string>("horizontalAlignment")};
if (horizontalAlignment != "left" && horizontalAlignment != "right") {
LOG(LogWarning)
<< "BadgeComponent: Invalid theme configuration, <horizontalAlignment> set to \""
<< horizontalAlignment << "\"";
}
else {
mFlexboxComponent.setAlignment(horizontalAlignment);
}
}
// Legacy themes only.
else if (elem->has("alignment")) {
const std::string alignment {elem->get<std::string>("alignment")};
if (alignment != "left" && alignment != "right") {
LOG(LogWarning) << "BadgeComponent: Invalid theme configuration, <alignment> set to \""

View file

@ -28,7 +28,8 @@ CarouselComponent::CarouselComponent()
, mTextColor {0x000000FF}
, mTextBackgroundColor {0xFFFFFF00}
, mLineSpacing {1.5f}
, mLogoAlignment {ALIGN_CENTER}
, mLogoHorizontalAlignment {ALIGN_CENTER}
, mLogoVerticalAlignment {ALIGN_CENTER}
, mMaxLogoCount {3}
, mLogoSize {Renderer::getScreenWidth() * 0.25f, Renderer::getScreenHeight() * 0.155f}
, mLogoScale {1.2f}
@ -107,31 +108,25 @@ void CarouselComponent::addEntry(const std::shared_ptr<ThemeData>& theme,
}
entry.data.logo = text;
if (mLogoAlignment == ALIGN_LEFT || mLogoAlignment == ALIGN_RIGHT) {
text->setHorizontalAlignment(mLogoAlignment);
text->setVerticalAlignment(ALIGN_CENTER);
}
else if (mLogoAlignment == ALIGN_TOP || mLogoAlignment == ALIGN_BOTTOM) {
text->setVerticalAlignment(mLogoAlignment);
text->setHorizontalAlignment(ALIGN_CENTER);
}
else {
text->setHorizontalAlignment(ALIGN_CENTER);
text->setVerticalAlignment(ALIGN_CENTER);
}
text->setHorizontalAlignment(mLogoHorizontalAlignment);
text->setVerticalAlignment(mLogoVerticalAlignment);
}
if (mLogoAlignment == ALIGN_LEFT)
// Set origin for the logos based on their alignment so they line up properly.
if (mLogoHorizontalAlignment == ALIGN_LEFT)
entry.data.logo->setOrigin(0, 0.5);
else if (mLogoAlignment == ALIGN_RIGHT)
else if (mLogoHorizontalAlignment == ALIGN_RIGHT)
entry.data.logo->setOrigin(1.0, 0.5);
else if (mLogoAlignment == ALIGN_TOP)
entry.data.logo->setOrigin(0.5, 0);
else if (mLogoAlignment == ALIGN_BOTTOM)
entry.data.logo->setOrigin(0.5, 1);
else
entry.data.logo->setOrigin(0.5, 0.5);
if (mLogoVerticalAlignment == ALIGN_TOP)
entry.data.logo->setOrigin(entry.data.logo->getOrigin().x, 0);
else if (mLogoVerticalAlignment == ALIGN_BOTTOM)
entry.data.logo->setOrigin(entry.data.logo->getOrigin().x, 1);
else
entry.data.logo->setOrigin(entry.data.logo->getOrigin().x, 0.5);
glm::vec2 denormalized {mLogoSize * entry.data.logo->getOrigin()};
entry.data.logo->setPosition(glm::vec3 {denormalized.x, denormalized.y, 0.0f});
@ -221,9 +216,9 @@ void CarouselComponent::render(const glm::mat4& parentTrans)
logoSpacing.y =
((mSize.y - (mLogoSize.y * mMaxLogoCount)) / (mMaxLogoCount)) + mLogoSize.y;
yOff = (mSize.y - mLogoSize.y) / 2.0f - (mCamOffset * logoSpacing.y);
if (mLogoAlignment == ALIGN_LEFT)
if (mLogoHorizontalAlignment == ALIGN_LEFT)
xOff = mLogoSize.x / 10.0f;
else if (mLogoAlignment == ALIGN_RIGHT)
else if (mLogoHorizontalAlignment == ALIGN_RIGHT)
xOff = mSize.x - (mLogoSize.x * 1.1f);
else
xOff = (mSize.x - mLogoSize.x) / 2.0f;
@ -233,9 +228,9 @@ void CarouselComponent::render(const glm::mat4& parentTrans)
logoSpacing.x =
((mSize.x - (mLogoSize.x * mMaxLogoCount)) / (mMaxLogoCount)) + mLogoSize.x;
xOff = std::round((mSize.x - mLogoSize.x) / 2.0f - (mCamOffset * logoSpacing.x));
if (mLogoAlignment == ALIGN_TOP)
if (mLogoVerticalAlignment == ALIGN_TOP)
yOff = mLogoSize.y / 10.0f;
else if (mLogoAlignment == ALIGN_BOTTOM)
else if (mLogoVerticalAlignment == ALIGN_BOTTOM)
yOff = mSize.y - (mLogoSize.y * 1.1f);
else
yOff = (mSize.y - mLogoSize.y) / 2.0f;
@ -321,14 +316,25 @@ void CarouselComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
return;
if (elem->has("type")) {
if (!(elem->get<std::string>("type").compare("vertical")))
mType = VERTICAL;
else if (!(elem->get<std::string>("type").compare("vertical_wheel")))
mType = VERTICAL_WHEEL;
else if (!(elem->get<std::string>("type").compare("horizontal_wheel")))
mType = HORIZONTAL_WHEEL;
else
const std::string type {elem->get<std::string>("type")};
if (type == "horizontal") {
mType = HORIZONTAL;
}
else if (type == "horizontal_wheel") {
mType = HORIZONTAL_WHEEL;
}
else if (type == "vertical") {
mType = VERTICAL;
}
else if (type == "vertical_wheel") {
mType = VERTICAL_WHEEL;
}
else {
LOG(LogWarning) << "CarouselComponent: Invalid theme configuration, property "
"<type> set to \""
<< type << "\"";
mType = HORIZONTAL;
}
}
if (elem->has("color")) {
@ -338,7 +344,7 @@ void CarouselComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
if (elem->has("colorEnd"))
mCarouselColorEnd = elem->get<unsigned int>("colorEnd");
if (elem->has("gradientType"))
mColorGradientHorizontal = !(elem->get<std::string>("gradientType").compare("horizontal"));
mColorGradientHorizontal = (elem->get<std::string>("gradientType") == "horizontal");
if (elem->has("logoScale"))
mLogoScale = glm::clamp(elem->get<float>("logoScale"), 0.5f, 3.0f);
@ -365,23 +371,74 @@ void CarouselComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
mLogoRotation = elem->get<float>("logoRotation");
if (elem->has("logoRotationOrigin"))
mLogoRotationOrigin = elem->get<glm::vec2>("logoRotationOrigin");
if (elem->has("logoAlignment")) {
if (!(elem->get<std::string>("logoAlignment").compare("left")) && mType != HORIZONTAL) {
mLogoAlignment = ALIGN_LEFT;
if (elem->has("logoHorizontalAlignment")) {
const std::string alignment {elem->get<std::string>("logoHorizontalAlignment")};
if (alignment == "left" && mType != HORIZONTAL) {
mLogoHorizontalAlignment = ALIGN_LEFT;
}
else if (!(elem->get<std::string>("logoAlignment").compare("right")) &&
mType != HORIZONTAL) {
mLogoAlignment = ALIGN_RIGHT;
else if (alignment == "right" && mType != HORIZONTAL) {
mLogoHorizontalAlignment = ALIGN_RIGHT;
}
else if (!(elem->get<std::string>("logoAlignment").compare("top")) && mType != VERTICAL) {
mLogoAlignment = ALIGN_TOP;
}
else if (!(elem->get<std::string>("logoAlignment").compare("bottom")) &&
mType != VERTICAL) {
mLogoAlignment = ALIGN_BOTTOM;
else if (alignment == "center") {
mLogoHorizontalAlignment = ALIGN_CENTER;
}
else {
mLogoAlignment = ALIGN_CENTER;
LOG(LogWarning) << "CarouselComponent: Invalid theme configuration, property "
"<logoHorizontalAlignment> set to \""
<< alignment << "\"";
mLogoHorizontalAlignment = ALIGN_CENTER;
}
}
if (elem->has("logoVerticalAlignment")) {
const std::string alignment {elem->get<std::string>("logoVerticalAlignment")};
if (alignment == "top" && mType != VERTICAL) {
mLogoVerticalAlignment = ALIGN_TOP;
}
else if (alignment == "bottom" && mType != VERTICAL) {
mLogoVerticalAlignment = ALIGN_BOTTOM;
}
else if (alignment == "center") {
mLogoVerticalAlignment = ALIGN_CENTER;
}
else {
LOG(LogWarning) << "CarouselComponent: Invalid theme configuration, property "
"<logoVerticalAlignment> set to \""
<< alignment << "\"";
mLogoVerticalAlignment = ALIGN_CENTER;
}
}
// Legacy themes only.
if (elem->has("logoAlignment")) {
const std::string alignment {elem->get<std::string>("logoAlignment")};
if (alignment == "left" && mType != HORIZONTAL) {
mLogoHorizontalAlignment = ALIGN_LEFT;
mLogoVerticalAlignment = ALIGN_CENTER;
}
else if (alignment == "right" && mType != HORIZONTAL) {
mLogoHorizontalAlignment = ALIGN_RIGHT;
mLogoVerticalAlignment = ALIGN_CENTER;
}
else if (alignment == "top" && mType != VERTICAL) {
mLogoVerticalAlignment = ALIGN_TOP;
mLogoHorizontalAlignment = ALIGN_CENTER;
}
else if (alignment == "bottom" && mType != VERTICAL) {
mLogoVerticalAlignment = ALIGN_BOTTOM;
mLogoHorizontalAlignment = ALIGN_CENTER;
}
else if (alignment == "center") {
mLogoHorizontalAlignment = ALIGN_CENTER;
mLogoVerticalAlignment = ALIGN_CENTER;
}
else {
LOG(LogWarning) << "CarouselComponent: Invalid theme configuration, property "
"<logoAlignment> set to \""
<< alignment << "\"";
mLogoHorizontalAlignment = ALIGN_CENTER;
mLogoVerticalAlignment = ALIGN_CENTER;
}
}

View file

@ -80,7 +80,8 @@ private:
unsigned int mTextBackgroundColor;
std::string mText;
float mLineSpacing;
Alignment mLogoAlignment;
Alignment mLogoHorizontalAlignment;
Alignment mLogoVerticalAlignment;
int mMaxLogoCount;
glm::vec2 mLogoSize;
float mLogoScale;

View file

@ -132,8 +132,8 @@ void DateTimeComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
setRenderBackground(true);
}
if (properties & ALIGNMENT && elem->has("alignment")) {
std::string str = elem->get<std::string>("alignment");
if (properties & ALIGNMENT && elem->has("horizontalAlignment")) {
std::string str {elem->get<std::string>("horizontalAlignment")};
if (str == "left")
setHorizontalAlignment(ALIGN_LEFT);
else if (str == "center")
@ -141,7 +141,38 @@ void DateTimeComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
else if (str == "right")
setHorizontalAlignment(ALIGN_RIGHT);
else
LOG(LogError) << "Unknown text alignment string: " << str;
LOG(LogWarning) << "DateTimeComponent: Invalid theme configuration, property "
"<horizontalAlignment> set to \""
<< str << "\"";
}
if (properties & ALIGNMENT && elem->has("verticalAlignment")) {
std::string str {elem->get<std::string>("verticalAlignment")};
if (str == "top")
setVerticalAlignment(ALIGN_TOP);
else if (str == "center")
setVerticalAlignment(ALIGN_CENTER);
else if (str == "bottom")
setVerticalAlignment(ALIGN_BOTTOM);
else
LOG(LogWarning) << "DateTimeComponent: Invalid theme configuration, property "
"<verticalAlignment> set to \""
<< str << "\"";
}
// Legacy themes only.
if (properties & ALIGNMENT && elem->has("alignment")) {
std::string str {elem->get<std::string>("alignment")};
if (str == "left")
setHorizontalAlignment(ALIGN_LEFT);
else if (str == "center")
setHorizontalAlignment(ALIGN_CENTER);
else if (str == "right")
setHorizontalAlignment(ALIGN_RIGHT);
else
LOG(LogWarning) << "DateTimeComponent: Invalid theme configuration, property "
"<alignment> set to \""
<< str << "\"";
}
if (properties & METADATA && elem->has("metadata"))

View file

@ -362,9 +362,12 @@ void TextComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
GuiComponent::applyTheme(theme, view, element, properties);
std::string elementType {"text"};
std::string componentName {"TextComponent"};
if (element.substr(0, 13) == "gamelistinfo_")
if (element.substr(0, 13) == "gamelistinfo_") {
elementType = "gamelistinfo";
componentName = "gamelistInfoComponent";
}
const ThemeData::ThemeElement* elem = theme->getElement(view, element, elementType);
if (!elem)
@ -379,8 +382,8 @@ void TextComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
setRenderBackground(true);
}
if (properties & ALIGNMENT && elem->has("alignment")) {
std::string str = elem->get<std::string>("alignment");
if (properties & ALIGNMENT && elem->has("horizontalAlignment")) {
std::string str {elem->get<std::string>("horizontalAlignment")};
if (str == "left")
setHorizontalAlignment(ALIGN_LEFT);
else if (str == "center")
@ -388,7 +391,41 @@ void TextComponent::applyTheme(const std::shared_ptr<ThemeData>& theme,
else if (str == "right")
setHorizontalAlignment(ALIGN_RIGHT);
else
LOG(LogError) << "Unknown text alignment string: " << str;
LOG(LogWarning) << componentName
<< ": Invalid theme configuration, property "
"<horizontalAlignment> set to \""
<< str << "\"";
}
if (properties & ALIGNMENT && elem->has("verticalAlignment")) {
std::string str {elem->get<std::string>("verticalAlignment")};
if (str == "top")
setVerticalAlignment(ALIGN_TOP);
else if (str == "center")
setVerticalAlignment(ALIGN_CENTER);
else if (str == "bottom")
setVerticalAlignment(ALIGN_BOTTOM);
else
LOG(LogWarning) << componentName
<< ": Invalid theme configuration, property "
"<verticalAlignment> set to \""
<< str << "\"";
}
// Legacy themes only.
if (properties & ALIGNMENT && elem->has("alignment")) {
std::string str {elem->get<std::string>("alignment")};
if (str == "left")
setHorizontalAlignment(ALIGN_LEFT);
else if (str == "center")
setHorizontalAlignment(ALIGN_CENTER);
else if (str == "right")
setHorizontalAlignment(ALIGN_RIGHT);
else
LOG(LogWarning) << componentName
<< ": Invalid theme configuration, property "
"<alignment> set to \""
<< str << "\"";
}
if (properties & TEXT && elem->has("text"))

View file

@ -491,8 +491,8 @@ void TextListComponent<T>::applyTheme(const std::shared_ptr<ThemeData>& theme,
setSelectorHeight(selectorHeight);
if (properties & ALIGNMENT) {
if (elem->has("alignment")) {
const std::string& str = elem->get<std::string>("alignment");
if (elem->has("horizontalAlignment")) {
const std::string& str {elem->get<std::string>("horizontalAlignment")};
if (str == "left")
setAlignment(ALIGN_LEFT);
else if (str == "center")
@ -500,7 +500,23 @@ void TextListComponent<T>::applyTheme(const std::shared_ptr<ThemeData>& theme,
else if (str == "right")
setAlignment(ALIGN_RIGHT);
else
LOG(LogError) << "Unknown TextListComponent alignment \"" << str << "\"!";
LOG(LogWarning) << "TextListComponent: Invalid theme configuration, property "
"<horizontalAlignment> set to \""
<< str << "\"";
}
// Legacy themes only.
else if (elem->has("alignment")) {
const std::string& str {elem->get<std::string>("alignment")};
if (str == "left")
setAlignment(ALIGN_LEFT);
else if (str == "center")
setAlignment(ALIGN_CENTER);
else if (str == "right")
setAlignment(ALIGN_RIGHT);
else
LOG(LogWarning) << "TextListComponent: Invalid theme configuration, property "
"<alignment> set to \""
<< str << "\"";
}
if (elem->has("horizontalMargin")) {
mHorizontalMargin = elem->get<float>("horizontalMargin") *

View file

@ -37,7 +37,7 @@ class TextCache;
enum Alignment {
ALIGN_LEFT,
ALIGN_CENTER, // Centers both horizontally and vertically.
ALIGN_CENTER, // Used for both horizontal and vertical alignments.
ALIGN_RIGHT,
ALIGN_TOP,
ALIGN_BOTTOM