Changed: Split css style from CGroupHTML
--HG-- branch : develop
This commit is contained in:
parent
7f41881be7
commit
c107bdc56f
8 changed files with 1342 additions and 1115 deletions
39
code/nel/include/nel/gui/css_parser.h
Normal file
39
code/nel/include/nel/gui/css_parser.h
Normal file
|
@ -0,0 +1,39 @@
|
|||
// Ryzom - MMORPG Framework <http://dev.ryzom.com/projects/ryzom/>
|
||||
// Copyright (C) 2010 Winch Gate Property Limited
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU Affero General Public License as
|
||||
// published by the Free Software Foundation, either version 3 of the
|
||||
// License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU Affero General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Affero General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef CL_CSS_PARSER_H
|
||||
#define CL_CSS_PARSER_H
|
||||
|
||||
#include "nel/misc/types_nl.h"
|
||||
#include "nel/gui/css_style.h"
|
||||
|
||||
namespace NLGUI
|
||||
{
|
||||
/**
|
||||
* \brief CSS style parsing
|
||||
* \date 2019-03-15 10:50 GMT
|
||||
* \author Meelis Mägi (Nimetu)
|
||||
*/
|
||||
class CCssParser {
|
||||
public:
|
||||
// parse style declaration, eg "color: red; font-size: 10px;"
|
||||
static TStyle parseDecls(const std::string &styleString);
|
||||
};
|
||||
|
||||
}//namespace
|
||||
|
||||
#endif // CL_CSS_PARSER_H
|
||||
|
141
code/nel/include/nel/gui/css_style.h
Normal file
141
code/nel/include/nel/gui/css_style.h
Normal file
|
@ -0,0 +1,141 @@
|
|||
// Ryzom - MMORPG Framework <http://dev.ryzom.com/projects/ryzom/>
|
||||
// Copyright (C) 2010 Winch Gate Property Limited
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU Affero General Public License as
|
||||
// published by the Free Software Foundation, either version 3 of the
|
||||
// License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU Affero General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Affero General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef CL_CSS_STYLE_H
|
||||
#define CL_CSS_STYLE_H
|
||||
|
||||
#include "nel/misc/types_nl.h"
|
||||
#include "nel/misc/rgba.h"
|
||||
|
||||
namespace NLGUI
|
||||
{
|
||||
typedef std::map<std::string, std::string> TStyle;
|
||||
|
||||
/**
|
||||
* \brief CSS style rules
|
||||
* \date 2019-03-15 10:50 GMT
|
||||
* \author Meelis Mägi (Nimetu)
|
||||
*/
|
||||
class CStyleParams
|
||||
{
|
||||
public:
|
||||
struct STextShadow
|
||||
{
|
||||
public:
|
||||
STextShadow(bool enabled = false, bool outline = false, sint32 x=1, sint32 y=1, NLMISC::CRGBA color=NLMISC::CRGBA::Black)
|
||||
: Enabled(enabled), Outline(outline), X(x), Y(y), Color(color)
|
||||
{ }
|
||||
|
||||
bool Enabled;
|
||||
bool Outline;
|
||||
sint32 X;
|
||||
sint32 Y;
|
||||
NLMISC::CRGBA Color;
|
||||
};
|
||||
public:
|
||||
CStyleParams () : FontFamily(""), TextColor(255,255,255,255), TextShadow()
|
||||
{
|
||||
FontSize=10;
|
||||
FontWeight=400;
|
||||
FontOblique=false;
|
||||
Underlined=false;
|
||||
StrikeThrough=false;
|
||||
GlobalColor=false;
|
||||
Width=-1;
|
||||
Height=-1;
|
||||
MaxWidth=-1;
|
||||
MaxHeight=-1;
|
||||
BorderWidth=1;
|
||||
BackgroundColor=NLMISC::CRGBA::Black;
|
||||
BackgroundColorOver=NLMISC::CRGBA::Black;
|
||||
}
|
||||
uint FontSize;
|
||||
uint FontWeight;
|
||||
bool FontOblique;
|
||||
std::string FontFamily;
|
||||
NLMISC::CRGBA TextColor;
|
||||
STextShadow TextShadow;
|
||||
bool GlobalColor;
|
||||
bool Underlined;
|
||||
bool StrikeThrough;
|
||||
sint32 Width;
|
||||
sint32 Height;
|
||||
sint32 MaxWidth;
|
||||
sint32 MaxHeight;
|
||||
sint32 BorderWidth;
|
||||
NLMISC::CRGBA BackgroundColor;
|
||||
NLMISC::CRGBA BackgroundColorOver;
|
||||
};
|
||||
|
||||
class CCssStyle {
|
||||
public:
|
||||
|
||||
|
||||
// 'browser' style, overwriten with '<html>'
|
||||
CStyleParams Root;
|
||||
|
||||
// current element style
|
||||
CStyleParams Current;
|
||||
|
||||
private:
|
||||
std::vector<CStyleParams> _StyleStack;
|
||||
|
||||
// test if str is one of "thin/medium/thick" and return its pixel value
|
||||
bool scanCssLength(const std::string& str, uint32 &px) const;
|
||||
|
||||
// read style attribute
|
||||
void getStyleParams(const std::string &styleString, CStyleParams &style, const CStyleParams ¤t) const;
|
||||
|
||||
public:
|
||||
void reset();
|
||||
|
||||
inline uint getFontSizeSmaller() const
|
||||
{
|
||||
if (Current.FontSize < 5)
|
||||
return 3;
|
||||
return Current.FontSize-2;
|
||||
}
|
||||
|
||||
inline void pushStyle()
|
||||
{
|
||||
_StyleStack.push_back(Current);
|
||||
}
|
||||
|
||||
inline void popStyle()
|
||||
{
|
||||
if (_StyleStack.empty())
|
||||
Current = Root;
|
||||
else
|
||||
{
|
||||
Current = _StyleStack.back();
|
||||
_StyleStack.pop_back();
|
||||
}
|
||||
}
|
||||
|
||||
// apply style string to this.Root
|
||||
void applyRootStyle(const std::string &styleString);
|
||||
|
||||
// apply style string to this.Current
|
||||
void applyStyle(const std::string &styleString);
|
||||
|
||||
void applyCssMinMax(sint32 &width, sint32 &height, sint32 minw=0, sint32 minh=0, sint32 maxw=0, sint32 maxh=0) const;
|
||||
|
||||
};
|
||||
|
||||
}//namespace
|
||||
|
||||
#endif // CL_CSS_STYLE_H
|
||||
|
|
@ -24,12 +24,11 @@
|
|||
#include "nel/gui/ctrl_button.h"
|
||||
#include "nel/gui/group_table.h"
|
||||
#include "nel/gui/libwww_types.h"
|
||||
#include "nel/gui/css_style.h"
|
||||
|
||||
// forward declaration
|
||||
typedef void CURLM;
|
||||
|
||||
typedef std::map<std::string, std::string> TStyle;
|
||||
|
||||
namespace NLGUI
|
||||
{
|
||||
class CCtrlButton;
|
||||
|
@ -76,58 +75,6 @@ namespace NLGUI
|
|||
|
||||
static SWebOptions options;
|
||||
|
||||
// text-shadow
|
||||
struct STextShadow
|
||||
{
|
||||
public:
|
||||
STextShadow(bool enabled = false, bool outline = false, sint32 x=1, sint32 y=1, NLMISC::CRGBA color=NLMISC::CRGBA::Black)
|
||||
: Enabled(enabled), Outline(outline), X(x), Y(y), Color(color)
|
||||
{ }
|
||||
|
||||
bool Enabled;
|
||||
bool Outline;
|
||||
sint32 X;
|
||||
sint32 Y;
|
||||
NLMISC::CRGBA Color;
|
||||
};
|
||||
|
||||
class CStyleParams
|
||||
{
|
||||
public:
|
||||
CStyleParams () : FontFamily(""), TextColor(255,255,255,255), TextShadow()
|
||||
{
|
||||
FontSize=10;
|
||||
FontWeight=400;
|
||||
FontOblique=false;
|
||||
Underlined=false;
|
||||
StrikeThrough=false;
|
||||
GlobalColor=false;
|
||||
Width=-1;
|
||||
Height=-1;
|
||||
MaxWidth=-1;
|
||||
MaxHeight=-1;
|
||||
BorderWidth=1;
|
||||
BackgroundColor=NLMISC::CRGBA::Black;
|
||||
BackgroundColorOver=NLMISC::CRGBA::Black;
|
||||
}
|
||||
uint FontSize;
|
||||
uint FontWeight;
|
||||
bool FontOblique;
|
||||
std::string FontFamily;
|
||||
NLMISC::CRGBA TextColor;
|
||||
STextShadow TextShadow;
|
||||
bool GlobalColor;
|
||||
bool Underlined;
|
||||
bool StrikeThrough;
|
||||
sint32 Width;
|
||||
sint32 Height;
|
||||
sint32 MaxWidth;
|
||||
sint32 MaxHeight;
|
||||
sint32 BorderWidth;
|
||||
NLMISC::CRGBA BackgroundColor;
|
||||
NLMISC::CRGBA BackgroundColorOver;
|
||||
};
|
||||
|
||||
// ImageDownload system
|
||||
enum TDataType {ImgType= 0, BnpType};
|
||||
enum TImageType {NormalImage=0, OverImage};
|
||||
|
@ -535,33 +482,8 @@ namespace NLGUI
|
|||
// IL mode
|
||||
bool _LI;
|
||||
|
||||
// Current active style
|
||||
CStyleParams _Style;
|
||||
// Default style
|
||||
CStyleParams _StyleDefault;
|
||||
// Nested style stack
|
||||
std::vector<CStyleParams> _StyleParams;
|
||||
inline void pushStyle()
|
||||
{
|
||||
_StyleParams.push_back(_Style);
|
||||
}
|
||||
inline void popStyle()
|
||||
{
|
||||
if (_StyleParams.empty())
|
||||
_Style = _StyleDefault;
|
||||
else
|
||||
{
|
||||
_Style = _StyleParams.back();
|
||||
_StyleParams.pop_back();
|
||||
}
|
||||
}
|
||||
|
||||
inline uint getFontSizeSmaller() const
|
||||
{
|
||||
if (_Style.FontSize < 5)
|
||||
return 3;
|
||||
return _Style.FontSize-2;
|
||||
}
|
||||
// Keep track of current element style
|
||||
CCssStyle _Style;
|
||||
|
||||
// Current link
|
||||
std::vector<std::string> _Link;
|
||||
|
@ -625,14 +547,6 @@ namespace NLGUI
|
|||
return _TR.back();
|
||||
}
|
||||
|
||||
std::vector<STextShadow> _TextShadow;
|
||||
inline STextShadow getTextShadow() const
|
||||
{
|
||||
if (_TextShadow.empty())
|
||||
return STextShadow();
|
||||
return _TextShadow.back();
|
||||
}
|
||||
|
||||
// Forms
|
||||
class CForm
|
||||
{
|
||||
|
@ -794,10 +708,6 @@ namespace NLGUI
|
|||
typedef std::map<uint32, NLMISC::CRefPtr<CGroupHTML> > TGroupHtmlByUIDMap;
|
||||
static TGroupHtmlByUIDMap _GroupHtmlByUID;
|
||||
|
||||
// read style attribute
|
||||
void getStyleParams(const std::string &styleString, CStyleParams &style, const CStyleParams ¤t);
|
||||
void applyCssMinMax(sint32 &width, sint32 &height, sint32 minw=0, sint32 minh=0, sint32 maxw=0, sint32 maxh=0);
|
||||
|
||||
// load and render local html file (from bnp for example)
|
||||
void doBrowseLocalFile(const std::string &filename);
|
||||
|
||||
|
|
|
@ -276,9 +276,14 @@ namespace NLGUI
|
|||
HTML_ATTR(H6,STYLE),
|
||||
};
|
||||
|
||||
|
||||
#undef HTML_ATTR
|
||||
|
||||
// ***************************************************************************
|
||||
// Read HTML color value from src and set dest
|
||||
// Can handle #rgb(a), #rrggbb(aa) or rgb()/rgba(), hsl(), hsla() formats
|
||||
// or color name directly
|
||||
bool scanHTMLColor(const char *src, NLMISC::CRGBA &dest);
|
||||
|
||||
// ***************************************************************************
|
||||
// Read a CSS length value, return true if one of supported units '%, rem, em, px, pt'
|
||||
// On failure: 'value' and 'unit' values are undefined
|
||||
|
|
58
code/nel/src/gui/css_parser.cpp
Normal file
58
code/nel/src/gui/css_parser.cpp
Normal file
|
@ -0,0 +1,58 @@
|
|||
// Ryzom - MMORPG Framework <http://dev.ryzom.com/projects/ryzom/>
|
||||
// Copyright (C) 2010 Winch Gate Property Limited
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU Affero General Public License as
|
||||
// published by the Free Software Foundation, either version 3 of the
|
||||
// License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU Affero General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Affero General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include "stdpch.h"
|
||||
|
||||
#include <string>
|
||||
#include "nel/misc/types_nl.h"
|
||||
#include "nel/gui/css_parser.h"
|
||||
#include "nel/gui/css_style.h"
|
||||
|
||||
using namespace NLMISC;
|
||||
|
||||
#ifdef DEBUG_NEW
|
||||
#define new DEBUG_NEW
|
||||
#endif
|
||||
|
||||
namespace NLGUI
|
||||
{
|
||||
// ***************************************************************************
|
||||
// Parse style declarations style, eg. "color:red; font-size: 10px;"
|
||||
//
|
||||
// key is converted to lowercase
|
||||
// value is left as is
|
||||
TStyle CCssParser::parseDecls(const std::string &styleString)
|
||||
{
|
||||
TStyle styles;
|
||||
std::vector<std::string> elements;
|
||||
NLMISC::splitString(styleString, ";", elements);
|
||||
|
||||
for(uint i = 0; i < elements.size(); ++i)
|
||||
{
|
||||
std::string::size_type pos;
|
||||
pos = elements[i].find_first_of(':');
|
||||
if (pos != std::string::npos)
|
||||
{
|
||||
std::string key = trim(toLower(elements[i].substr(0, pos)));
|
||||
std::string value = trim(elements[i].substr(pos+1));
|
||||
styles[key] = value;
|
||||
}
|
||||
}
|
||||
|
||||
return styles;
|
||||
}
|
||||
} // namespace
|
||||
|
496
code/nel/src/gui/css_style.cpp
Normal file
496
code/nel/src/gui/css_style.cpp
Normal file
|
@ -0,0 +1,496 @@
|
|||
// Ryzom - MMORPG Framework <http://dev.ryzom.com/projects/ryzom/>
|
||||
// Copyright (C) 2010 Winch Gate Property Limited
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU Affero General Public License as
|
||||
// published by the Free Software Foundation, either version 3 of the
|
||||
// License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU Affero General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Affero General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include "stdpch.h"
|
||||
|
||||
#include <string>
|
||||
#include "nel/misc/types_nl.h"
|
||||
#include "nel/gui/css_style.h"
|
||||
#include "nel/gui/css_parser.h"
|
||||
#include "nel/gui/libwww.h"
|
||||
|
||||
using namespace NLMISC;
|
||||
|
||||
#ifdef DEBUG_NEW
|
||||
#define new DEBUG_NEW
|
||||
#endif
|
||||
|
||||
namespace NLGUI
|
||||
{
|
||||
// ***************************************************************************
|
||||
void CCssStyle::reset()
|
||||
{
|
||||
_StyleStack.clear();
|
||||
|
||||
Root = CStyleParams();
|
||||
Current = CStyleParams();
|
||||
}
|
||||
|
||||
// ***************************************************************************
|
||||
void CCssStyle::applyRootStyle(const std::string &styleString)
|
||||
{
|
||||
getStyleParams(styleString, Root, Root);
|
||||
}
|
||||
|
||||
// ***************************************************************************
|
||||
void CCssStyle::applyStyle(const std::string &styleString)
|
||||
{
|
||||
if (_StyleStack.empty())
|
||||
{
|
||||
getStyleParams(styleString, Current, Root);
|
||||
}
|
||||
else
|
||||
{
|
||||
getStyleParams(styleString, Current, _StyleStack.back());
|
||||
}
|
||||
}
|
||||
|
||||
bool CCssStyle::scanCssLength(const std::string& str, uint32 &px) const
|
||||
{
|
||||
if (fromString(str, px))
|
||||
return true;
|
||||
|
||||
if (str == "thin")
|
||||
{
|
||||
px = 1;
|
||||
return true;
|
||||
}
|
||||
if (str == "medium")
|
||||
{
|
||||
px = 3;
|
||||
return true;
|
||||
}
|
||||
if (str == "thick")
|
||||
{
|
||||
px = 5;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
// ***************************************************************************
|
||||
// CStyleParams style;
|
||||
// style.FontSize; // font-size: 10px;
|
||||
// style.TextColor; // color: #ABCDEF;
|
||||
// style.Underlined; // text-decoration: underline; text-decoration-line: underline;
|
||||
// style.StrikeThrough; // text-decoration: line-through; text-decoration-line: line-through;
|
||||
void CCssStyle::getStyleParams(const std::string &styleString, CStyleParams &style, const CStyleParams ¤t) const
|
||||
{
|
||||
float tmpf;
|
||||
TStyle styles = CCssParser::parseDecls(styleString);
|
||||
TStyle::iterator it;
|
||||
|
||||
// first pass: get font-size for 'em' sizes
|
||||
for (it=styles.begin(); it != styles.end(); ++it)
|
||||
{
|
||||
if (it->first == "font")
|
||||
{
|
||||
if (it->second == "inherit")
|
||||
{
|
||||
style.FontSize = current.FontSize;
|
||||
style.FontFamily = current.FontFamily;
|
||||
style.FontWeight = current.FontWeight;
|
||||
style.FontOblique = current.FontOblique;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "font-size")
|
||||
{
|
||||
if (it->second == "inherit")
|
||||
{
|
||||
style.FontSize = current.FontSize;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::string unit;
|
||||
if (getCssLength(tmpf, unit, it->second.c_str()))
|
||||
{
|
||||
if (unit == "rem")
|
||||
style.FontSize = Root.FontSize * tmpf;
|
||||
else if (unit == "em")
|
||||
style.FontSize = current.FontSize * tmpf;
|
||||
else if (unit == "pt")
|
||||
style.FontSize = tmpf / 0.75f;
|
||||
else if (unit == "%")
|
||||
style.FontSize = current.FontSize * tmpf / 100.f;
|
||||
else
|
||||
style.FontSize = tmpf;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// second pass: rest of style
|
||||
for (it=styles.begin(); it != styles.end(); ++it)
|
||||
{
|
||||
if (it->first == "border")
|
||||
{
|
||||
sint32 b;
|
||||
if (it->second == "none")
|
||||
style.BorderWidth = 0;
|
||||
else
|
||||
if (fromString(it->second, b))
|
||||
style.BorderWidth = b;
|
||||
}
|
||||
else
|
||||
if (it->first == "font-style")
|
||||
{
|
||||
if (it->second == "inherit")
|
||||
style.FontOblique = current.FontOblique;
|
||||
else
|
||||
if (it->second == "italic" || it->second == "oblique")
|
||||
style.FontOblique = true;
|
||||
}
|
||||
else
|
||||
if (it->first == "font-family")
|
||||
{
|
||||
if (it->second == "inherit")
|
||||
style.FontFamily = current.FontFamily;
|
||||
else
|
||||
style.FontFamily = it->second;
|
||||
}
|
||||
else
|
||||
if (it->first == "font-weight")
|
||||
{
|
||||
// https://developer.mozilla.org/en-US/docs/Web/CSS/font-weight
|
||||
uint weight = 400;
|
||||
if (it->second == "inherit")
|
||||
weight = current.FontWeight;
|
||||
else
|
||||
if (it->second == "normal")
|
||||
weight = 400;
|
||||
else
|
||||
if (it->second == "bold")
|
||||
weight = 700;
|
||||
else
|
||||
if (it->second == "lighter")
|
||||
{
|
||||
const uint lighter[] = {100, 100, 100, 100, 100, 400, 400, 700, 700};
|
||||
uint index = current.FontWeight / 100 - 1;
|
||||
clamp(index, 1u, 9u);
|
||||
weight = lighter[index-1];
|
||||
}
|
||||
else
|
||||
if (it->second == "bolder")
|
||||
{
|
||||
const uint bolder[] = {400, 400, 400, 700, 700, 900, 900, 900, 900};
|
||||
uint index = current.FontWeight / 100 + 1;
|
||||
clamp(index, 1u, 9u);
|
||||
weight = bolder[index-1];
|
||||
}
|
||||
else
|
||||
if (fromString(it->second, weight))
|
||||
{
|
||||
weight = (weight / 100);
|
||||
clamp(weight, 1u, 9u);
|
||||
weight *= 100;
|
||||
}
|
||||
style.FontWeight = weight;
|
||||
}
|
||||
else
|
||||
if (it->first == "color")
|
||||
if (it->second == "inherit")
|
||||
style.TextColor = current.TextColor;
|
||||
else
|
||||
scanHTMLColor(it->second.c_str(), style.TextColor);
|
||||
else
|
||||
if (it->first == "text-decoration" || it->first == "text-decoration-line")
|
||||
{
|
||||
std::string prop(toLower(it->second));
|
||||
style.Underlined = (prop.find("underline") != std::string::npos);
|
||||
style.StrikeThrough = (prop.find("line-through") != std::string::npos);
|
||||
}
|
||||
else
|
||||
if (it->first == "text-stroke" || it->first == "-webkit-text-stroke")
|
||||
{
|
||||
// text-stroke: length || color
|
||||
bool success = false;
|
||||
uint px = 0;
|
||||
CRGBA color;
|
||||
std::vector<std::string> parts;
|
||||
NLMISC::splitString(it->second, " ", parts);
|
||||
if (parts.size() == 1)
|
||||
{
|
||||
success = scanCssLength(parts[0], px);
|
||||
if (!success)
|
||||
success = scanHTMLColor(parts[0].c_str(), color);
|
||||
}
|
||||
else if (parts.size() == 2)
|
||||
{
|
||||
success = scanCssLength(parts[0], px);
|
||||
if (success)
|
||||
success = scanHTMLColor(parts[1].c_str(), color);
|
||||
else
|
||||
{
|
||||
success = scanHTMLColor(parts[0].c_str(), color);
|
||||
success = success && scanCssLength(parts[1], px);
|
||||
}
|
||||
}
|
||||
|
||||
// do not disable shadow if one is already set
|
||||
if (success)
|
||||
{
|
||||
style.TextShadow.Enabled = (px > 0);
|
||||
style.TextShadow.Color = color;
|
||||
style.TextShadow.X = px;
|
||||
style.TextShadow.Y = px;
|
||||
style.TextShadow.Outline = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "text-shadow")
|
||||
{
|
||||
if (it->second == "none")
|
||||
style.TextShadow = CStyleParams::STextShadow(false);
|
||||
else
|
||||
if (it->second == "inherit")
|
||||
style.TextShadow = current.TextShadow;
|
||||
else
|
||||
{
|
||||
// text-shadow: offset-x offset-y | blur | #color
|
||||
// text-shadow: #color | offset-x offset-y
|
||||
bool success = true;
|
||||
std::string prop(it->second);
|
||||
size_t pos;
|
||||
pos = prop.find_first_of(",\n\r");
|
||||
if (pos != std::string::npos)
|
||||
prop = prop.substr(0, pos);
|
||||
|
||||
std::vector<std::string> parts;
|
||||
NLMISC::splitString(prop, " ", parts);
|
||||
switch(parts.size())
|
||||
{
|
||||
case 1:
|
||||
{
|
||||
success = scanHTMLColor(it->second.c_str(), style.TextShadow.Color);
|
||||
break;
|
||||
}
|
||||
// no case 2:
|
||||
case 3:
|
||||
{
|
||||
if (!fromString(parts[0], style.TextShadow.X))
|
||||
{
|
||||
success = scanHTMLColor(parts[0].c_str(), style.TextShadow.Color);
|
||||
success = success && fromString(parts[1], style.TextShadow.X);
|
||||
success = success && fromString(parts[2], style.TextShadow.Y);
|
||||
}
|
||||
else
|
||||
{
|
||||
success = fromString(parts[1], style.TextShadow.Y);
|
||||
success = success && scanHTMLColor(parts[2].c_str(), style.TextShadow.Color);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case 4:
|
||||
{
|
||||
if (!fromString(parts[0], style.TextShadow.X))
|
||||
{
|
||||
success = scanHTMLColor(parts[0].c_str(), style.TextShadow.Color);
|
||||
success = success && fromString(parts[1], style.TextShadow.X);
|
||||
success = success && fromString(parts[2], style.TextShadow.Y);
|
||||
// ignore blur [3]
|
||||
}
|
||||
else
|
||||
{
|
||||
success = fromString(parts[0], style.TextShadow.X);
|
||||
success = success && fromString(parts[1], style.TextShadow.Y);
|
||||
// ignore blur [2]
|
||||
success = success && scanHTMLColor(parts[3].c_str(), style.TextShadow.Color);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
// unsupported rule
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
style.TextShadow.Enabled = success;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "width")
|
||||
{
|
||||
std::string unit;
|
||||
if (getCssLength(tmpf, unit, it->second.c_str()))
|
||||
{
|
||||
if (unit == "rem")
|
||||
style.Width = tmpf * Root.FontSize;
|
||||
else if (unit == "em")
|
||||
style.Width = tmpf * style.FontSize;
|
||||
else if (unit == "pt")
|
||||
style.FontSize = tmpf / 0.75f;
|
||||
else
|
||||
style.Width = tmpf;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "height")
|
||||
{
|
||||
std::string unit;
|
||||
if (getCssLength(tmpf, unit, it->second.c_str()))
|
||||
{
|
||||
if (unit == "rem")
|
||||
style.Height = tmpf * Root.FontSize;
|
||||
else if (unit == "em")
|
||||
style.Height = tmpf * style.FontSize;
|
||||
else if (unit == "pt")
|
||||
style.FontSize = tmpf / 0.75f;
|
||||
else
|
||||
style.Height = tmpf;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "max-width")
|
||||
{
|
||||
std::string unit;
|
||||
if (getCssLength(tmpf, unit, it->second.c_str()))
|
||||
{
|
||||
if (unit == "rem")
|
||||
style.MaxWidth = tmpf * Root.FontSize;
|
||||
else if (unit == "em")
|
||||
style.MaxWidth = tmpf * style.FontSize;
|
||||
else if (unit == "pt")
|
||||
style.FontSize = tmpf / 0.75f;
|
||||
else
|
||||
style.MaxWidth = tmpf;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "max-height")
|
||||
{
|
||||
std::string unit;
|
||||
if (getCssLength(tmpf, unit, it->second.c_str()))
|
||||
{
|
||||
if (unit == "rem")
|
||||
style.MaxHeight = tmpf * Root.FontSize;
|
||||
else if (unit == "em")
|
||||
style.MaxHeight = tmpf * style.FontSize;
|
||||
else if (unit == "pt")
|
||||
style.FontSize = tmpf / 0.75f;
|
||||
else
|
||||
style.MaxHeight = tmpf;
|
||||
}
|
||||
}
|
||||
else
|
||||
if (it->first == "-ryzom-modulate-color")
|
||||
{
|
||||
bool b;
|
||||
if (it->second == "inherit")
|
||||
style.GlobalColor = current.GlobalColor;
|
||||
else
|
||||
if (fromString(it->second, b))
|
||||
style.GlobalColor = b;
|
||||
}
|
||||
else
|
||||
if (it->first == "background-color")
|
||||
{
|
||||
if (it->second == "inherit")
|
||||
style.BackgroundColor = current.BackgroundColor;
|
||||
else
|
||||
scanHTMLColor(it->second.c_str(), style.BackgroundColor);
|
||||
}
|
||||
else
|
||||
if (it->first == "-ryzom-background-color-over")
|
||||
{
|
||||
if (it->second == "inherit")
|
||||
style.BackgroundColorOver = current.BackgroundColorOver;
|
||||
else
|
||||
scanHTMLColor(it->second.c_str(), style.BackgroundColorOver);
|
||||
}
|
||||
}
|
||||
|
||||
// if outer element has underline set, then inner element cannot remove it
|
||||
if (current.Underlined)
|
||||
style.Underlined = current.Underlined;
|
||||
|
||||
// if outer element has line-through set, then inner element cannot remove it
|
||||
if (current.StrikeThrough)
|
||||
style.StrikeThrough = current.StrikeThrough;
|
||||
}
|
||||
|
||||
// ***************************************************************************
|
||||
void CCssStyle::applyCssMinMax(sint32 &width, sint32 &height, sint32 minw, sint32 minh, sint32 maxw, sint32 maxh) const
|
||||
{
|
||||
if (maxw <= 0) maxw = width;
|
||||
if (maxh <= 0) maxh = height;
|
||||
|
||||
maxw = std::max(minw, maxw);
|
||||
maxh = std::max(minh, maxh);
|
||||
|
||||
float ratio = (float) width / std::max(1, height);
|
||||
if (width > maxw)
|
||||
{
|
||||
width = maxw;
|
||||
height = std::max((sint32)(maxw /ratio), minh);
|
||||
}
|
||||
if (width < minw)
|
||||
{
|
||||
width = minw;
|
||||
height = std::min((sint32)(minw / ratio), maxh);
|
||||
}
|
||||
if (height > maxh)
|
||||
{
|
||||
width = std::max((sint32)(maxh * ratio), minw);
|
||||
height = maxh;
|
||||
}
|
||||
if (height < minh)
|
||||
{
|
||||
width = std::min((sint32)(minh * ratio), maxw);
|
||||
height = minh;
|
||||
}
|
||||
if (width > maxw && height > maxh)
|
||||
{
|
||||
if (maxw/width <= maxh/height)
|
||||
{
|
||||
width = maxw;
|
||||
height = std::max(minh, (sint32)(maxw / ratio));
|
||||
}
|
||||
else
|
||||
{
|
||||
width = std::max(minw, (sint32)(maxh * ratio));
|
||||
height = maxh;
|
||||
}
|
||||
}
|
||||
if (width < minw && height < minh)
|
||||
{
|
||||
if (minw / width <= minh / height)
|
||||
{
|
||||
width = std::min(maxw, (sint32)(minh * ratio));
|
||||
height = minh;
|
||||
}
|
||||
else
|
||||
{
|
||||
width = minw;
|
||||
height = std::min(maxh, (sint32)(minw / ratio));
|
||||
}
|
||||
}
|
||||
if (width < minw && height > maxh)
|
||||
{
|
||||
width = minw;
|
||||
height = maxh;
|
||||
}
|
||||
if (width > maxw && height < minh)
|
||||
{
|
||||
width = maxw;
|
||||
height = minh;
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
File diff suppressed because it is too large
Load diff
|
@ -345,6 +345,368 @@ namespace NLGUI
|
|||
}
|
||||
}
|
||||
|
||||
static bool isHexa(char c)
|
||||
{
|
||||
return isdigit(c) || (tolower(c) >= 'a' && tolower(c) <= 'f');
|
||||
}
|
||||
|
||||
static uint8 convertHexa(char c)
|
||||
{
|
||||
return (uint8) (tolower(c) - (isdigit(c) ? '0' : ('a' - 10)));
|
||||
}
|
||||
|
||||
// scan a color component, and return pointer to next position
|
||||
static const char *scanColorComponent(const char *src, uint8 &intensity)
|
||||
{
|
||||
if (!src) return NULL;
|
||||
if (!isHexa(*src)) return NULL;
|
||||
uint8 value = convertHexa(*src++) << 4;
|
||||
if (!isHexa(*src)) return NULL;
|
||||
value += convertHexa(*src++);
|
||||
intensity = value;
|
||||
return src;
|
||||
}
|
||||
|
||||
static float hueToRgb(float m1, float m2, float h)
|
||||
{
|
||||
if (h < 0) h += 1.0f;
|
||||
if (h > 1) h -= 1.0f;
|
||||
if (h*6 < 1.0f) return m1 + (m2 - m1)*h*6;
|
||||
if (h*2 < 1.0f) return m2;
|
||||
if (h*3 < 2.0f) return m1 + (m2 - m1) * (2.0f/3.0f - h)*6;
|
||||
return m1;
|
||||
}
|
||||
|
||||
static void hslToRgb(float h, float s, float l, CRGBA &result)
|
||||
{
|
||||
float m1, m2;
|
||||
if (l <= 0.5f)
|
||||
m2 = l * (s + 1.0f);
|
||||
else
|
||||
m2 = l + s - l * s;
|
||||
m1 = l*2 - m2;
|
||||
|
||||
result.R = 255 * hueToRgb(m1, m2, h + 1.0f/3.0f);
|
||||
result.G = 255 * hueToRgb(m1, m2, h);
|
||||
result.B = 255 * hueToRgb(m1, m2, h - 1.0f/3.0f);
|
||||
result.A = 255;
|
||||
}
|
||||
|
||||
class CNameToCol
|
||||
{
|
||||
public:
|
||||
const char *Name;
|
||||
CRGBA Color;
|
||||
CNameToCol(const char *name, CRGBA color) : Name(name), Color(color) {}
|
||||
};
|
||||
|
||||
static CNameToCol htmlColorNameToRGBA[] =
|
||||
{
|
||||
CNameToCol("AliceBlue", CRGBA(0xF0, 0xF8, 0xFF)),
|
||||
CNameToCol("AntiqueWhite", CRGBA(0xFA, 0xEB, 0xD7)),
|
||||
CNameToCol("Aqua", CRGBA(0x00, 0xFF, 0xFF)),
|
||||
CNameToCol("Aquamarine", CRGBA(0x7F, 0xFF, 0xD4)),
|
||||
CNameToCol("Azure", CRGBA(0xF0, 0xFF, 0xFF)),
|
||||
CNameToCol("Beige", CRGBA(0xF5, 0xF5, 0xDC)),
|
||||
CNameToCol("Bisque", CRGBA(0xFF, 0xE4, 0xC4)),
|
||||
CNameToCol("Black", CRGBA(0x00, 0x00, 0x00)),
|
||||
CNameToCol("BlanchedAlmond", CRGBA(0xFF, 0xEB, 0xCD)),
|
||||
CNameToCol("Blue", CRGBA(0x00, 0x00, 0xFF)),
|
||||
CNameToCol("BlueViolet", CRGBA(0x8A, 0x2B, 0xE2)),
|
||||
CNameToCol("Brown", CRGBA(0xA5, 0x2A, 0x2A)),
|
||||
CNameToCol("BurlyWood", CRGBA(0xDE, 0xB8, 0x87)),
|
||||
CNameToCol("CadetBlue", CRGBA(0x5F, 0x9E, 0xA0)),
|
||||
CNameToCol("Chartreuse", CRGBA(0x7F, 0xFF, 0x00)),
|
||||
CNameToCol("Chocolate", CRGBA(0xD2, 0x69, 0x1E)),
|
||||
CNameToCol("Coral", CRGBA(0xFF, 0x7F, 0x50)),
|
||||
CNameToCol("CornflowerBlue", CRGBA(0x64, 0x95, 0xED)),
|
||||
CNameToCol("Cornsilk", CRGBA(0xFF, 0xF8, 0xDC)),
|
||||
CNameToCol("Crimson", CRGBA(0xDC, 0x14, 0x3C)),
|
||||
CNameToCol("Cyan", CRGBA(0x00, 0xFF, 0xFF)),
|
||||
CNameToCol("DarkBlue", CRGBA(0x00, 0x00, 0x8B)),
|
||||
CNameToCol("DarkCyan", CRGBA(0x00, 0x8B, 0x8B)),
|
||||
CNameToCol("DarkGoldenRod", CRGBA(0xB8, 0x86, 0x0B)),
|
||||
CNameToCol("DarkGray", CRGBA(0xA9, 0xA9, 0xA9)),
|
||||
CNameToCol("DarkGreen", CRGBA(0x00, 0x64, 0x00)),
|
||||
CNameToCol("DarkKhaki", CRGBA(0xBD, 0xB7, 0x6B)),
|
||||
CNameToCol("DarkMagenta", CRGBA(0x8B, 0x00, 0x8B)),
|
||||
CNameToCol("DarkOliveGreen", CRGBA(0x55, 0x6B, 0x2F)),
|
||||
CNameToCol("Darkorange", CRGBA(0xFF, 0x8C, 0x00)),
|
||||
CNameToCol("DarkOrchid", CRGBA(0x99, 0x32, 0xCC)),
|
||||
CNameToCol("DarkRed", CRGBA(0x8B, 0x00, 0x00)),
|
||||
CNameToCol("DarkSalmon", CRGBA(0xE9, 0x96, 0x7A)),
|
||||
CNameToCol("DarkSeaGreen", CRGBA(0x8F, 0xBC, 0x8F)),
|
||||
CNameToCol("DarkSlateBlue", CRGBA(0x48, 0x3D, 0x8B)),
|
||||
CNameToCol("DarkSlateGray", CRGBA(0x2F, 0x4F, 0x4F)),
|
||||
CNameToCol("DarkTurquoise", CRGBA(0x00, 0xCE, 0xD1)),
|
||||
CNameToCol("DarkViolet", CRGBA(0x94, 0x00, 0xD3)),
|
||||
CNameToCol("DeepPink", CRGBA(0xFF, 0x14, 0x93)),
|
||||
CNameToCol("DeepSkyBlue", CRGBA(0x00, 0xBF, 0xFF)),
|
||||
CNameToCol("DimGray", CRGBA(0x69, 0x69, 0x69)),
|
||||
CNameToCol("DodgerBlue", CRGBA(0x1E, 0x90, 0xFF)),
|
||||
CNameToCol("Feldspar", CRGBA(0xD1, 0x92, 0x75)),
|
||||
CNameToCol("FireBrick", CRGBA(0xB2, 0x22, 0x22)),
|
||||
CNameToCol("FloralWhite", CRGBA(0xFF, 0xFA, 0xF0)),
|
||||
CNameToCol("ForestGreen", CRGBA(0x22, 0x8B, 0x22)),
|
||||
CNameToCol("Fuchsia", CRGBA(0xFF, 0x00, 0xFF)),
|
||||
CNameToCol("Gainsboro", CRGBA(0xDC, 0xDC, 0xDC)),
|
||||
CNameToCol("GhostWhite", CRGBA(0xF8, 0xF8, 0xFF)),
|
||||
CNameToCol("Gold", CRGBA(0xFF, 0xD7, 0x00)),
|
||||
CNameToCol("GoldenRod", CRGBA(0xDA, 0xA5, 0x20)),
|
||||
CNameToCol("Gray", CRGBA(0x80, 0x80, 0x80)),
|
||||
CNameToCol("Green", CRGBA(0x00, 0x80, 0x00)),
|
||||
CNameToCol("GreenYellow", CRGBA(0xAD, 0xFF, 0x2F)),
|
||||
CNameToCol("HoneyDew", CRGBA(0xF0, 0xFF, 0xF0)),
|
||||
CNameToCol("HotPink", CRGBA(0xFF, 0x69, 0xB4)),
|
||||
CNameToCol("IndianRed ", CRGBA(0xCD, 0x5C, 0x5C)),
|
||||
CNameToCol("Indigo ", CRGBA(0x4B, 0x00, 0x82)),
|
||||
CNameToCol("Ivory", CRGBA(0xFF, 0xFF, 0xF0)),
|
||||
CNameToCol("Khaki", CRGBA(0xF0, 0xE6, 0x8C)),
|
||||
CNameToCol("Lavender", CRGBA(0xE6, 0xE6, 0xFA)),
|
||||
CNameToCol("LavenderBlush", CRGBA(0xFF, 0xF0, 0xF5)),
|
||||
CNameToCol("LawnGreen", CRGBA(0x7C, 0xFC, 0x00)),
|
||||
CNameToCol("LemonChiffon", CRGBA(0xFF, 0xFA, 0xCD)),
|
||||
CNameToCol("LightBlue", CRGBA(0xAD, 0xD8, 0xE6)),
|
||||
CNameToCol("LightCoral", CRGBA(0xF0, 0x80, 0x80)),
|
||||
CNameToCol("LightCyan", CRGBA(0xE0, 0xFF, 0xFF)),
|
||||
CNameToCol("LightGoldenRodYellow", CRGBA(0xFA, 0xFA, 0xD2)),
|
||||
CNameToCol("LightGrey", CRGBA(0xD3, 0xD3, 0xD3)),
|
||||
CNameToCol("LightGreen", CRGBA(0x90, 0xEE, 0x90)),
|
||||
CNameToCol("LightPink", CRGBA(0xFF, 0xB6, 0xC1)),
|
||||
CNameToCol("LightSalmon", CRGBA(0xFF, 0xA0, 0x7A)),
|
||||
CNameToCol("LightSeaGreen", CRGBA(0x20, 0xB2, 0xAA)),
|
||||
CNameToCol("LightSkyBlue", CRGBA(0x87, 0xCE, 0xFA)),
|
||||
CNameToCol("LightSlateBlue", CRGBA(0x84, 0x70, 0xFF)),
|
||||
CNameToCol("LightSlateGray", CRGBA(0x77, 0x88, 0x99)),
|
||||
CNameToCol("LightSteelBlue", CRGBA(0xB0, 0xC4, 0xDE)),
|
||||
CNameToCol("LightYellow", CRGBA(0xFF, 0xFF, 0xE0)),
|
||||
CNameToCol("Lime", CRGBA(0x00, 0xFF, 0x00)),
|
||||
CNameToCol("LimeGreen", CRGBA(0x32, 0xCD, 0x32)),
|
||||
CNameToCol("Linen", CRGBA(0xFA, 0xF0, 0xE6)),
|
||||
CNameToCol("Magenta", CRGBA(0xFF, 0x00, 0xFF)),
|
||||
CNameToCol("Maroon", CRGBA(0x80, 0x00, 0x00)),
|
||||
CNameToCol("MediumAquaMarine", CRGBA(0x66, 0xCD, 0xAA)),
|
||||
CNameToCol("MediumBlue", CRGBA(0x00, 0x00, 0xCD)),
|
||||
CNameToCol("MediumOrchid", CRGBA(0xBA, 0x55, 0xD3)),
|
||||
CNameToCol("MediumPurple", CRGBA(0x93, 0x70, 0xD8)),
|
||||
CNameToCol("MediumSeaGreen", CRGBA(0x3C, 0xB3, 0x71)),
|
||||
CNameToCol("MediumSlateBlue", CRGBA(0x7B, 0x68, 0xEE)),
|
||||
CNameToCol("MediumSpringGreen", CRGBA(0x00, 0xFA, 0x9A)),
|
||||
CNameToCol("MediumTurquoise", CRGBA(0x48, 0xD1, 0xCC)),
|
||||
CNameToCol("MediumVioletRed", CRGBA(0xC7, 0x15, 0x85)),
|
||||
CNameToCol("MidnightBlue", CRGBA(0x19, 0x19, 0x70)),
|
||||
CNameToCol("MintCream", CRGBA(0xF5, 0xFF, 0xFA)),
|
||||
CNameToCol("MistyRose", CRGBA(0xFF, 0xE4, 0xE1)),
|
||||
CNameToCol("Moccasin", CRGBA(0xFF, 0xE4, 0xB5)),
|
||||
CNameToCol("NavajoWhite", CRGBA(0xFF, 0xDE, 0xAD)),
|
||||
CNameToCol("Navy", CRGBA(0x00, 0x00, 0x80)),
|
||||
CNameToCol("OldLace", CRGBA(0xFD, 0xF5, 0xE6)),
|
||||
CNameToCol("Olive", CRGBA(0x80, 0x80, 0x00)),
|
||||
CNameToCol("OliveDrab", CRGBA(0x6B, 0x8E, 0x23)),
|
||||
CNameToCol("Orange", CRGBA(0xFF, 0xA5, 0x00)),
|
||||
CNameToCol("OrangeRed", CRGBA(0xFF, 0x45, 0x00)),
|
||||
CNameToCol("Orchid", CRGBA(0xDA, 0x70, 0xD6)),
|
||||
CNameToCol("PaleGoldenRod", CRGBA(0xEE, 0xE8, 0xAA)),
|
||||
CNameToCol("PaleGreen", CRGBA(0x98, 0xFB, 0x98)),
|
||||
CNameToCol("PaleTurquoise", CRGBA(0xAF, 0xEE, 0xEE)),
|
||||
CNameToCol("PaleVioletRed", CRGBA(0xD8, 0x70, 0x93)),
|
||||
CNameToCol("PapayaWhip", CRGBA(0xFF, 0xEF, 0xD5)),
|
||||
CNameToCol("PeachPuff", CRGBA(0xFF, 0xDA, 0xB9)),
|
||||
CNameToCol("Peru", CRGBA(0xCD, 0x85, 0x3F)),
|
||||
CNameToCol("Pink", CRGBA(0xFF, 0xC0, 0xCB)),
|
||||
CNameToCol("Plum", CRGBA(0xDD, 0xA0, 0xDD)),
|
||||
CNameToCol("PowderBlue", CRGBA(0xB0, 0xE0, 0xE6)),
|
||||
CNameToCol("Purple", CRGBA(0x80, 0x00, 0x80)),
|
||||
CNameToCol("Red", CRGBA(0xFF, 0x00, 0x00)),
|
||||
CNameToCol("RosyBrown", CRGBA(0xBC, 0x8F, 0x8F)),
|
||||
CNameToCol("RoyalBlue", CRGBA(0x41, 0x69, 0xE1)),
|
||||
CNameToCol("SaddleBrown", CRGBA(0x8B, 0x45, 0x13)),
|
||||
CNameToCol("Salmon", CRGBA(0xFA, 0x80, 0x72)),
|
||||
CNameToCol("SandyBrown", CRGBA(0xF4, 0xA4, 0x60)),
|
||||
CNameToCol("SeaGreen", CRGBA(0x2E, 0x8B, 0x57)),
|
||||
CNameToCol("SeaShell", CRGBA(0xFF, 0xF5, 0xEE)),
|
||||
CNameToCol("Sienna", CRGBA(0xA0, 0x52, 0x2D)),
|
||||
CNameToCol("Silver", CRGBA(0xC0, 0xC0, 0xC0)),
|
||||
CNameToCol("SkyBlue", CRGBA(0x87, 0xCE, 0xEB)),
|
||||
CNameToCol("SlateBlue", CRGBA(0x6A, 0x5A, 0xCD)),
|
||||
CNameToCol("SlateGray", CRGBA(0x70, 0x80, 0x90)),
|
||||
CNameToCol("Snow", CRGBA(0xFF, 0xFA, 0xFA)),
|
||||
CNameToCol("SpringGreen", CRGBA(0x00, 0xFF, 0x7F)),
|
||||
CNameToCol("SteelBlue", CRGBA(0x46, 0x82, 0xB4)),
|
||||
CNameToCol("Tan", CRGBA(0xD2, 0xB4, 0x8C)),
|
||||
CNameToCol("Teal", CRGBA(0x00, 0x80, 0x80)),
|
||||
CNameToCol("Thistle", CRGBA(0xD8, 0xBF, 0xD8)),
|
||||
CNameToCol("Tomato", CRGBA(0xFF, 0x63, 0x47)),
|
||||
CNameToCol("Turquoise", CRGBA(0x40, 0xE0, 0xD0)),
|
||||
CNameToCol("Violet", CRGBA(0xEE, 0x82, 0xEE)),
|
||||
CNameToCol("VioletRed", CRGBA(0xD0, 0x20, 0x90)),
|
||||
CNameToCol("Wheat", CRGBA(0xF5, 0xDE, 0xB3)),
|
||||
CNameToCol("White", CRGBA(0xFF, 0xFF, 0xFF)),
|
||||
CNameToCol("WhiteSmoke", CRGBA(0xF5, 0xF5, 0xF5)),
|
||||
CNameToCol("Yellow", CRGBA(0xFF, 0xFF, 0x00)),
|
||||
CNameToCol("YellowGreen", CRGBA(0x9A, 0xCD, 0x32))
|
||||
};
|
||||
|
||||
// scan a color from a HTML form (#rrggbb format)
|
||||
bool scanHTMLColor(const char *src, CRGBA &dest)
|
||||
{
|
||||
if (!src || *src == '\0') return false;
|
||||
if (*src == '#')
|
||||
{
|
||||
++src;
|
||||
if (strlen(src) == 3 || strlen(src) == 4)
|
||||
{
|
||||
bool hasAlpha = (strlen(src) == 4);
|
||||
// check RGB for valid hex
|
||||
if (isHexa(src[0]) && isHexa(src[1]) && isHexa(src[2]))
|
||||
{
|
||||
// check optional A for valid hex
|
||||
if (hasAlpha && !isHexa(src[3])) return false;
|
||||
|
||||
dest.R = convertHexa(src[0]);
|
||||
dest.G = convertHexa(src[1]);
|
||||
dest.B = convertHexa(src[2]);
|
||||
|
||||
dest.R = dest.R << 4 | dest.R;
|
||||
dest.G = dest.G << 4 | dest.G;
|
||||
dest.B = dest.B << 4 | dest.B;
|
||||
|
||||
if (hasAlpha)
|
||||
{
|
||||
dest.A = convertHexa(src[3]);
|
||||
dest.A = dest.A << 4 | dest.A;
|
||||
}
|
||||
else
|
||||
dest.A = 255;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
CRGBA result;
|
||||
src = scanColorComponent(src, result.R); if (!src) return false;
|
||||
src = scanColorComponent(src, result.G); if (!src) return false;
|
||||
src = scanColorComponent(src, result.B); if (!src) return false;
|
||||
src = scanColorComponent(src, result.A);
|
||||
if (!src)
|
||||
{
|
||||
// Alpha is optional
|
||||
result.A = 255;
|
||||
}
|
||||
dest = result;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (strnicmp(src, "rgb(", 4) == 0 || strnicmp(src, "rgba(", 5) == 0)
|
||||
{
|
||||
src += 4;
|
||||
if (*src == '(') src++;
|
||||
|
||||
std::vector<std::string> parts;
|
||||
NLMISC::splitString(src, ",", parts);
|
||||
if (parts.size() >= 3)
|
||||
{
|
||||
CRGBA result;
|
||||
sint tmpv;
|
||||
float tmpf;
|
||||
|
||||
// R
|
||||
if (getPercentage(tmpv, tmpf, parts[0].c_str())) tmpv = 255 * tmpf;
|
||||
clamp(tmpv, 0, 255);
|
||||
result.R = tmpv;
|
||||
|
||||
// G
|
||||
if (getPercentage(tmpv, tmpf, parts[1].c_str())) tmpv = 255 * tmpf;
|
||||
clamp(tmpv, 0, 255);
|
||||
result.G = tmpv;
|
||||
|
||||
// B
|
||||
if (getPercentage(tmpv, tmpf, parts[2].c_str())) tmpv = 255 * tmpf;
|
||||
clamp(tmpv, 0, 255);
|
||||
result.B = tmpv;
|
||||
|
||||
// A
|
||||
if (parts.size() == 4)
|
||||
{
|
||||
if (!fromString(parts[3], tmpf)) return false;
|
||||
if (parts[3].find_first_of("%") != std::string::npos)
|
||||
tmpf /= 100;
|
||||
|
||||
tmpv = 255 * tmpf;
|
||||
clamp(tmpv, 0, 255);
|
||||
result.A = tmpv;
|
||||
}
|
||||
else
|
||||
result.A = 255;
|
||||
|
||||
dest = result;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
if (strnicmp(src, "hsl(", 4) == 0 || strnicmp(src, "hsla(", 5) == 0)
|
||||
{
|
||||
src += 4;
|
||||
if (*src == '(') src++;
|
||||
|
||||
std::vector<std::string> parts;
|
||||
NLMISC::splitString(src, ",", parts);
|
||||
if (parts.size() >= 3)
|
||||
{
|
||||
sint tmpv;
|
||||
float h, s, l;
|
||||
// hue
|
||||
if (!fromString(parts[0], tmpv)) return false;
|
||||
tmpv = ((tmpv % 360) + 360) % 360;
|
||||
h = (float) tmpv / 360.0f;
|
||||
|
||||
// saturation
|
||||
if (!getPercentage(tmpv, s, parts[1].c_str())) return false;
|
||||
clamp(s, 0.0f, 1.0f);
|
||||
|
||||
// lightness
|
||||
if (!getPercentage(tmpv, l, parts[2].c_str())) return false;
|
||||
clamp(l, 0.0f, 1.0f);
|
||||
|
||||
CRGBA result;
|
||||
hslToRgb(h, s, l, result);
|
||||
|
||||
// A
|
||||
if (parts.size() == 4)
|
||||
{
|
||||
float tmpf;
|
||||
if (!fromString(parts[3], tmpf)) return false;
|
||||
if (parts[3].find_first_of("%") != std::string::npos)
|
||||
tmpf /= 100;
|
||||
clamp(tmpf, 0.0f, 1.0f);
|
||||
result.A = 255 * tmpf;
|
||||
}
|
||||
|
||||
dest = result;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
{
|
||||
// slow but should suffice for now
|
||||
for(uint k = 0; k < sizeofarray(htmlColorNameToRGBA); ++k)
|
||||
{
|
||||
if (nlstricmp(src, htmlColorNameToRGBA[k].Name) == 0)
|
||||
{
|
||||
dest = htmlColorNameToRGBA[k].Color;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// ***************************************************************************
|
||||
|
||||
CRGBA getColor (const char *color)
|
||||
|
|
Loading…
Reference in a new issue