00001
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "MyGUI_Precompiled.h"
00024 #include "MyGUI_ResourceManualFont.h"
00025 #include "MyGUI_SkinManager.h"
00026 #include "MyGUI_RenderManager.h"
00027 #include "MyGUI_TextureUtility.h"
00028
00029 namespace MyGUI
00030 {
00031
00032 ResourceManualFont::ResourceManualFont() :
00033 mDefaultHeight(0),
00034 mTexture(nullptr)
00035 {
00036 }
00037
00038 ResourceManualFont::~ResourceManualFont()
00039 {
00040 }
00041
00042 GlyphInfo * ResourceManualFont::getGlyphInfo(Char _id)
00043 {
00044 for (VectorRangeInfo::iterator iter=mVectorRangeInfo.begin(); iter!=mVectorRangeInfo.end(); ++iter)
00045 {
00046 GlyphInfo * info = iter->getInfo(_id);
00047 if (info == nullptr) continue;
00048 return info;
00049 }
00050
00051 return &mSpaceGlyphInfo;
00052 }
00053
00054 void ResourceManualFont::checkTexture()
00055 {
00056 if (mTexture == nullptr)
00057 {
00058 RenderManager& render = RenderManager::getInstance();
00059 mTexture = render.getTexture(mSource);
00060 if (mTexture == nullptr)
00061 {
00062 mTexture = render.createTexture(mSource);
00063 mTexture->loadFromFile(mSource);
00064 }
00065 }
00066 }
00067
00068 void ResourceManualFont::addGlyph(GlyphInfo * _info, Char _index, int _left, int _top, int _right, int _bottom, int _finalw, int _finalh, float _aspect, int _addHeight)
00069 {
00070 _info->codePoint = _index;
00071 _info->uvRect.left = (float)_left / (float)_finalw;
00072 _info->uvRect.top = (float)(_top + _addHeight) / (float)_finalh;
00073 _info->uvRect.right = (float)( _right ) / (float)_finalw;
00074 _info->uvRect.bottom = ( _bottom + _addHeight ) / (float)_finalh;
00075 _info->width = _right - _left;
00076 }
00077
00078 void ResourceManualFont::addGlyph(Char _code, const IntCoord& _coord)
00079 {
00080 mVectorPairCodeCoord.push_back(PairCodeCoord(_code, _coord));
00081 }
00082
00083 void ResourceManualFont::initialise()
00084 {
00085 if (mVectorPairCodeCoord.empty()) return;
00086
00087 std::sort(mVectorPairCodeCoord.begin(), mVectorPairCodeCoord.end());
00088
00089 const IntSize& size = texture_utility::getTextureSize(mSource);
00090 float aspect = (float)size.width / (float)size.height;
00091
00092 Char code = mVectorPairCodeCoord.front().code;
00093 size_t count = mVectorPairCodeCoord.size();
00094 size_t first = 0;
00095
00096 for (size_t pos=1; pos<count; ++pos)
00097 {
00098
00099 if (code + 1 != mVectorPairCodeCoord[pos].code)
00100 {
00101 addRange(mVectorPairCodeCoord, first, pos-1, size.width, size.height, aspect);
00102 code = mVectorPairCodeCoord[pos].code;
00103 first = pos;
00104 }
00105 else
00106 {
00107 code ++;
00108 }
00109 }
00110
00111 addRange(mVectorPairCodeCoord, first, count-1, size.width, size.height, aspect);
00112
00113
00114 VectorPairCodeCoord tmp;
00115 std::swap(tmp, mVectorPairCodeCoord);
00116
00117 checkTexture();
00118 }
00119
00120 void ResourceManualFont::addRange(VectorPairCodeCoord& _info, size_t _first, size_t _last, int _width, int _height, float _aspect)
00121 {
00122 RangeInfo range = RangeInfo(_info[_first].code, _info[_last].code);
00123
00124 for (size_t pos=_first; pos<=_last; ++pos)
00125 {
00126 GlyphInfo * info = range.getInfo(_info[pos].code);
00127 const IntCoord& coord = _info[pos].coord;
00128 addGlyph(info, _info[pos].code, coord.left, coord.top, coord.right(), coord.bottom(), _width, _height, _aspect);
00129
00130 if (_info[pos].code == FontCodeType::Space)
00131 mSpaceGlyphInfo = *info;
00132 }
00133
00134 mVectorRangeInfo.push_back(range);
00135 }
00136
00137 void ResourceManualFont::deserialization(xml::ElementPtr _node, Version _version)
00138 {
00139 Base::deserialization(_node, _version);
00140
00141 xml::ElementEnumerator node = _node->getElementEnumerator();
00142 while (node.next())
00143 {
00144 if (node->getName() == "Property")
00145 {
00146 const std::string& key = node->findAttribute("key");
00147 const std::string& value = node->findAttribute("value");
00148 if (key == "Source") mSource = value;
00149 else if (key == "DefaultHeight") mDefaultHeight = utility::parseInt(value);
00150 }
00151 else if (node->getName() == "Codes")
00152 {
00153 xml::ElementEnumerator range = node->getElementEnumerator();
00154 while (range.next("Code"))
00155 {
00156 std::string range_value;
00157 std::vector<std::string> parse_range;
00158
00159 if (range->findAttribute("index", range_value))
00160 {
00161 Char id = 0;
00162 if (range_value == "cursor")
00163 id = FontCodeType::Cursor;
00164 else if (range_value == "selected")
00165 id = FontCodeType::Selected;
00166 else if (range_value == "selected_back")
00167 id = FontCodeType::SelectedBack;
00168 else
00169 id = utility::parseUInt(range_value);
00170
00171 addGlyph(id, utility::parseValue<IntCoord>(range->findAttribute("coord")));
00172 }
00173 }
00174 }
00175 }
00176
00177
00178 initialise();
00179 }
00180
00181 }