basic font redering
This commit is contained in:
parent
b1ec45783e
commit
9464f99c90
|
@ -32,31 +32,46 @@ typedef uint32 RGBA;
|
||||||
class Color
|
class Color
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Color() : color(0) { }
|
enum {
|
||||||
Color(uint8 r, uint8 g, uint8 b, uint8 a = 0xFF) : color(((r & 0xff)<<24) | ((g & 0xff)<<16) | ((b & 0xff)<<8) | (a & 0xff)) { }
|
white = 0xFFFFFFFF,
|
||||||
Color(const Color& other) : color(other.color) { }
|
pink = 0xFF00FFFF
|
||||||
Color(RGBA rgba) : color(rgba) { }
|
};
|
||||||
|
|
||||||
uint8 red() const { return (color >> 24) & 0xFF; }
|
inline Color() : color(0) { }
|
||||||
uint8 green() const { return (color >> 16) & 0xFF; }
|
inline Color(uint8 r, uint8 g, uint8 b, uint8 a = 0xFF) : color(((r & 0xff)<<24) | ((g & 0xff)<<16) | ((b & 0xff)<<8) | (a & 0xff)) { }
|
||||||
uint8 blue() const { return (color >> 8) & 0xFF; }
|
inline Color(const Color& other) : color(other.color) { }
|
||||||
uint8 alpha() const { return color & 0xFF; }
|
inline Color(RGBA rgba) : color(rgba) { }
|
||||||
RGBA rgba() const { return color; }
|
|
||||||
const uint8* rgbaPtr() const { return (const uint8*)&color; }
|
|
||||||
|
|
||||||
void setRed(uint8 r) { color = ((r & 0xff)<<24) | (color & 0x00ffffff); }
|
inline uint8 red() const { return (color >> 24) & 0xFF; }
|
||||||
void setGreen(uint8 g) { color = ((g & 0xff)<<16) | (color & 0xff00ffff); }
|
inline uint8 green() const { return (color >> 16) & 0xFF; }
|
||||||
void setBlue(uint8 b) { color = ((b & 0xff)<<8) | (color & 0xffff00ff); }
|
inline uint8 blue() const { return (color >> 8) & 0xFF; }
|
||||||
void setAlpha(uint8 a) { color = (a & 0xff) | (color & 0xffffff00); }
|
inline uint8 alpha() const { return color & 0xFF; }
|
||||||
void setRGBA(uint8 r, uint8 g, uint8 b, uint8 a = 0xFF) { color = ((r & 0xff)<<24) | ((g & 0xff)<<16) | ((b & 0xff)<<8) | (a & 0xff); }
|
inline RGBA rgba() const { return color; }
|
||||||
void setRGBA(uint32 rgba) { color = rgba; }
|
inline const uint8* rgbaPtr() const { return (const uint8*)&color; }
|
||||||
|
|
||||||
Color& operator=(const Color& other) { color = other.color; return *this; }
|
inline void setRed(uint8 r) { color = ((r & 0xff)<<24) | (color & 0x00ffffff); }
|
||||||
bool operator==(const Color& other) const { return other.color == color; }
|
inline void setGreen(uint8 g) { color = ((g & 0xff)<<16) | (color & 0xff00ffff); }
|
||||||
bool operator!=(const Color& other) const { return other.color != color; }
|
inline void setBlue(uint8 b) { color = ((b & 0xff)<<8) | (color & 0xffff00ff); }
|
||||||
|
inline void setAlpha(uint8 a) { color = (a & 0xff) | (color & 0xffffff00); }
|
||||||
|
inline void setRGBA(uint8 r, uint8 g, uint8 b, uint8 a = 0xFF) { color = ((r & 0xff)<<24) | ((g & 0xff)<<16) | ((b & 0xff)<<8) | (a & 0xff); }
|
||||||
|
inline void setRGBA(uint32 rgba) { color = rgba; }
|
||||||
|
|
||||||
|
inline Color& operator=(const Color& other) { color = other.color; return *this; }
|
||||||
|
inline bool operator==(const Color& other) const { return other.color == color; }
|
||||||
|
inline bool operator!=(const Color& other) const { return other.color != color; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
RGBA color;
|
RGBA color;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
inline void operator>>(const YAML::Node& node, Color& color)
|
||||||
|
{
|
||||||
|
int r, g, b, a;
|
||||||
|
node[0] >> r;
|
||||||
|
node[1] >> g;
|
||||||
|
node[2] >> b;
|
||||||
|
node[3] >> a;
|
||||||
|
color.setRGBA(r,g,b,a);
|
||||||
|
}
|
||||||
|
|
||||||
#endif // COLOR_H
|
#endif // COLOR_H
|
||||||
|
|
|
@ -25,8 +25,6 @@
|
||||||
#include "configs.h"
|
#include "configs.h"
|
||||||
#include "resources.h"
|
#include "resources.h"
|
||||||
|
|
||||||
#include <yaml-cpp/yaml.h>
|
|
||||||
|
|
||||||
Configs g_configs;
|
Configs g_configs;
|
||||||
|
|
||||||
bool Configs::load(const std::string& fileName)
|
bool Configs::load(const std::string& fileName)
|
||||||
|
@ -48,7 +46,7 @@ bool Configs::load(const std::string& fileName)
|
||||||
YAML::Node doc;
|
YAML::Node doc;
|
||||||
parser.GetNextDocument(doc);
|
parser.GetNextDocument(doc);
|
||||||
|
|
||||||
for(YAML::Iterator it = doc.begin(); it != doc.end(); ++it) {
|
for(auto it = doc.begin(); it != doc.end(); ++it) {
|
||||||
std::string key, value;
|
std::string key, value;
|
||||||
it.first() >> key;
|
it.first() >> key;
|
||||||
it.second() >> value;
|
it.second() >> value;
|
||||||
|
|
|
@ -23,8 +23,145 @@
|
||||||
|
|
||||||
|
|
||||||
#include "font.h"
|
#include "font.h"
|
||||||
|
#include "resources.h"
|
||||||
|
#include "textures.h"
|
||||||
|
#include "graphics.h"
|
||||||
|
|
||||||
|
#include <GL/gl.h>
|
||||||
|
#include <GL/glu.h>
|
||||||
|
#include <GL/glext.h>
|
||||||
|
|
||||||
|
Font::Font() :
|
||||||
|
m_lineHeight(14),
|
||||||
|
m_cursorSize(14),
|
||||||
|
m_color(Color::white)
|
||||||
|
{
|
||||||
|
bzero(m_glyphWidths, sizeof(m_glyphWidths));
|
||||||
|
}
|
||||||
|
|
||||||
bool Font::load(const std::string& file)
|
bool Font::load(const std::string& file)
|
||||||
{
|
{
|
||||||
return false;
|
if(!g_resources.fileExists(file)) {
|
||||||
|
error("Font file %s does not exists", file.c_str());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string fileContents = g_resources.loadTextFile(file);
|
||||||
|
if(!fileContents.size()) {
|
||||||
|
error("Empty font file \"%s", file.c_str());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::istringstream fin(fileContents);
|
||||||
|
|
||||||
|
std::string textureName;
|
||||||
|
|
||||||
|
try {
|
||||||
|
YAML::Parser parser(fin);
|
||||||
|
|
||||||
|
YAML::Node doc;
|
||||||
|
parser.GetNextDocument(doc);
|
||||||
|
|
||||||
|
doc["name"] >> m_name;
|
||||||
|
doc["line height"] >> m_lineHeight;
|
||||||
|
doc["cursor size"] >> m_cursorSize;
|
||||||
|
doc["color"] >> m_color;
|
||||||
|
doc["first glyph"] >> m_firstGlyph;
|
||||||
|
doc["image"] >> textureName;
|
||||||
|
doc["image glyph size"] >> m_glyphSize;
|
||||||
|
|
||||||
|
const YAML::Node& widthsNode = doc["widths"];
|
||||||
|
for(auto it = widthsNode.begin(); it != widthsNode.end(); ++it) {
|
||||||
|
int id, width;
|
||||||
|
it.first() >> id;
|
||||||
|
it.second() >> width;
|
||||||
|
m_glyphWidths[id] = width;
|
||||||
|
}
|
||||||
|
} catch (YAML::ParserException& e) {
|
||||||
|
error("Malformed font file \"%s\"", file.c_str());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_texture = g_textures.get("fonts/" + textureName);
|
||||||
|
m_numHorizontalGlyphs = m_texture->getSize().width() / m_glyphSize.width();
|
||||||
|
m_numVerticalGlyphs = m_texture->getSize().height() / m_glyphSize.height();
|
||||||
|
|
||||||
|
if(!m_texture) {
|
||||||
|
error("Failed to load image for font \"%s\"", file.c_str());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Font::renderText(const Point& pos, const std::string& text)
|
||||||
|
{
|
||||||
|
// bind font texture
|
||||||
|
glBindTexture(GL_TEXTURE_2D, m_texture->getTextureId());
|
||||||
|
|
||||||
|
// set font color
|
||||||
|
glColor4ubv(m_color.rgbaPtr());
|
||||||
|
|
||||||
|
// begin render
|
||||||
|
glBegin(GL_QUADS);
|
||||||
|
|
||||||
|
Point currentPos = pos;
|
||||||
|
const Size& screenSize = g_graphics.getScreenSize();
|
||||||
|
int textLenght = text.length();
|
||||||
|
|
||||||
|
for(int i = 0; i < textLenght; ++i) {
|
||||||
|
int c = (int)text[i];
|
||||||
|
|
||||||
|
// check if is visible
|
||||||
|
if(currentPos.x >= screenSize.width())
|
||||||
|
continue;
|
||||||
|
if(currentPos.y >= screenSize.height())
|
||||||
|
break;
|
||||||
|
|
||||||
|
// new line
|
||||||
|
if(c == '\n') {
|
||||||
|
currentPos.y += m_lineHeight;
|
||||||
|
currentPos.x = pos.x;
|
||||||
|
}
|
||||||
|
// text eof
|
||||||
|
else if(c == '\0') {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
// normal glyph
|
||||||
|
else if(c >= 32 && c <= 255) {
|
||||||
|
currentPos.x += renderGlyph(currentPos, c);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// end font render
|
||||||
|
glEnd();
|
||||||
|
}
|
||||||
|
|
||||||
|
int Font::renderGlyph(const Point& pos, int glyph)
|
||||||
|
{
|
||||||
|
// get glyph width
|
||||||
|
int glyphWidth = m_glyphWidths[glyph];
|
||||||
|
|
||||||
|
// calculate glyph coords on texture font
|
||||||
|
const Size& textureSize = m_texture->getSize();
|
||||||
|
int glyphTexCoordX = ((glyph - m_firstGlyph) % m_numHorizontalGlyphs) * m_glyphSize.width();
|
||||||
|
int glyphTexCoordY = ((glyph - m_firstGlyph) / m_numVerticalGlyphs) * m_glyphSize.height();
|
||||||
|
float textureRight = (float)(glyphTexCoordX + glyphWidth) / textureSize.width();
|
||||||
|
float textureBottom = (float)(glyphTexCoordY + m_glyphSize.height()) / textureSize.height();
|
||||||
|
float textureTop = (float)(glyphTexCoordY) / textureSize.height();
|
||||||
|
float textureLeft = (float)(glyphTexCoordX) / textureSize.width();
|
||||||
|
|
||||||
|
// calculate glyph coords on screen
|
||||||
|
int right = pos.x + glyphWidth;
|
||||||
|
int bottom = pos.y + m_glyphSize.height();
|
||||||
|
int top = pos.y;
|
||||||
|
int left = pos.x;
|
||||||
|
|
||||||
|
// render glyph
|
||||||
|
glTexCoord2f(textureLeft, textureTop); glVertex2i(left, top);
|
||||||
|
glTexCoord2f(textureLeft, textureBottom); glVertex2i(left, bottom);
|
||||||
|
glTexCoord2f(textureRight, textureBottom); glVertex2i(right, bottom);
|
||||||
|
glTexCoord2f(textureRight, textureTop); glVertex2i(right, top);
|
||||||
|
|
||||||
|
return glyphWidth;
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,20 +26,56 @@
|
||||||
#define FONT_H
|
#define FONT_H
|
||||||
|
|
||||||
#include "prerequisites.h"
|
#include "prerequisites.h"
|
||||||
|
#include "color.h"
|
||||||
|
#include "texture.h"
|
||||||
|
|
||||||
class Font
|
class Font
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Font() { }
|
Font();
|
||||||
virtual ~Font() { }
|
virtual ~Font() { }
|
||||||
|
|
||||||
/// Load font from file
|
/// Load font from file
|
||||||
bool load(const std::string &file);
|
bool load(const std::string &file);
|
||||||
|
|
||||||
|
/// Simple text render
|
||||||
|
void renderText(const Point& pos, const std::string& text);
|
||||||
|
|
||||||
|
/*
|
||||||
|
enum EAlign {
|
||||||
|
ALIGN_TOP = 1 << 0,
|
||||||
|
ALIGN_BOTTOM = 1 << 1,
|
||||||
|
ALIGN_LEFT = 1 << 2,
|
||||||
|
ALIGN_RIGHT = 1 << 3,
|
||||||
|
ALIGN_HORIZONTAL_CENTER = 1 << 4,
|
||||||
|
ALIGN_VERTICAL_CENTER = 1 << 5,
|
||||||
|
ALIGN_CENTER = ALIGN_HORIZONTAL_CENTER | ALIGN_VERTICAL_CENTER,
|
||||||
|
ALIGN_TOP_RIGHT = ALIGN_TOP | ALIGN_RIGHT,
|
||||||
|
ALIGN_TOP_LEFT = ALIGN_TOP | ALIGN_LEFT,
|
||||||
|
ALIGN_BOTTOM_RIGHT = ALIGN_BOTTOM | ALIGN_RIGHT,
|
||||||
|
ALIGN_BOTTOM_LEFT = ALIGN_BOTTOM | ALIGN_LEFT
|
||||||
|
};
|
||||||
|
/// Render a text inside a rect
|
||||||
|
void renderText(const Rect& screenCoords, EAlign align, const std::string& text);
|
||||||
|
*/
|
||||||
|
|
||||||
|
/// Render a text
|
||||||
const std::string& getName() const { return m_name; }
|
const std::string& getName() const { return m_name; }
|
||||||
|
int renderGlyph(const Point& pos, int glyph);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
std::string m_name;
|
std::string m_name;
|
||||||
|
int m_lineHeight;
|
||||||
|
int m_cursorSize;
|
||||||
|
Color m_color;
|
||||||
|
TexturePtr m_texture;
|
||||||
|
Size m_textureSize;
|
||||||
|
Size m_glyphSize;
|
||||||
|
int m_firstGlyph;
|
||||||
|
int m_glyphWidths[256];
|
||||||
|
int m_numHorizontalGlyphs;
|
||||||
|
int m_numVerticalGlyphs;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // FONT_H
|
#endif // FONT_H
|
||||||
|
|
|
@ -34,7 +34,7 @@ void Fonts::init()
|
||||||
foreach(const std::string& file, files) {
|
foreach(const std::string& file, files) {
|
||||||
if(boost::ends_with(file, ".yml")) {
|
if(boost::ends_with(file, ".yml")) {
|
||||||
std::shared_ptr<Font> font(new Font);
|
std::shared_ptr<Font> font(new Font);
|
||||||
font->load(file);
|
font->load("fonts/" + file);
|
||||||
m_fonts[font->getName()] = font;
|
m_fonts[font->getName()] = font;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -43,7 +43,9 @@ void Fonts::init()
|
||||||
Font* Fonts::get(const std::string& fontName)
|
Font* Fonts::get(const std::string& fontName)
|
||||||
{
|
{
|
||||||
auto it = m_fonts.find(fontName);
|
auto it = m_fonts.find(fontName);
|
||||||
if(it != m_fonts.end())
|
if(it != m_fonts.end()) {
|
||||||
return it->second.get();
|
return it->second.get();
|
||||||
|
}
|
||||||
|
error("Font \"%s\" not found", fontName.c_str());
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
|
@ -140,13 +140,12 @@ void Graphics::drawTexturedRect(const Rect& screenCoords, const Texture *texture
|
||||||
|
|
||||||
if(!textureCoords.isEmpty()) {
|
if(!textureCoords.isEmpty()) {
|
||||||
const Size& textureSize = texture->getSize();
|
const Size& textureSize = texture->getSize();
|
||||||
|
|
||||||
textureRight = (float)(textureCoords.right() + 1) / textureSize.width();
|
textureRight = (float)(textureCoords.right() + 1) / textureSize.width();
|
||||||
textureBottom = (float)(textureCoords.bottom() + 1) / textureSize.height();
|
textureBottom = (float)(textureCoords.bottom() + 1) / textureSize.height();
|
||||||
textureTop = (float)textureCoords.top() / textureSize.height();
|
textureTop = (float)textureCoords.top() / textureSize.height();
|
||||||
textureLeft = (float)textureCoords.left() / textureSize.width();
|
textureLeft = (float)textureCoords.left() / textureSize.width();
|
||||||
}
|
}
|
||||||
|
|
||||||
glBindTexture(GL_TEXTURE_2D, texture->getTextureId());
|
glBindTexture(GL_TEXTURE_2D, texture->getTextureId());
|
||||||
glBegin(GL_QUADS);
|
glBegin(GL_QUADS);
|
||||||
glTexCoord2f(textureLeft, textureTop); glVertex2i(left, top);
|
glTexCoord2f(textureLeft, textureTop); glVertex2i(left, top);
|
||||||
|
|
|
@ -59,6 +59,6 @@ private:
|
||||||
std::ostringstream m_buf;
|
std::ostringstream m_buf;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define dump() Dump()
|
#define dump Dump()
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -77,4 +77,12 @@ public:
|
||||||
typedef TPoint<int> Point;
|
typedef TPoint<int> Point;
|
||||||
typedef TPoint<float> PointF;
|
typedef TPoint<float> PointF;
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
inline void operator>>(const YAML::Node& node, TPoint<T>& point)
|
||||||
|
{
|
||||||
|
T x, y;
|
||||||
|
node[0] >> point.x;
|
||||||
|
node[1] >> point.y;
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -65,6 +65,9 @@ typedef int8_t int8;
|
||||||
#include <boost/foreach.hpp>
|
#include <boost/foreach.hpp>
|
||||||
#define foreach BOOST_FOREACH
|
#define foreach BOOST_FOREACH
|
||||||
|
|
||||||
|
// yaml
|
||||||
|
#include <yaml-cpp/yaml.h>
|
||||||
|
|
||||||
// internal logger
|
// internal logger
|
||||||
#include "logger.h"
|
#include "logger.h"
|
||||||
|
|
||||||
|
|
|
@ -98,7 +98,7 @@ public:
|
||||||
inline TRect<T> translated(int x, int y) const { return TRect<T>(TPoint<T>(x1 + x, y1 + y), TPoint<T>(x2 + x, y2 + y)); }
|
inline TRect<T> translated(int x, int y) const { return TRect<T>(TPoint<T>(x1 + x, y1 + y), TPoint<T>(x2 + x, y2 + y)); }
|
||||||
inline TRect<T> translated(const TPoint<T> &p) const { return TRect<T>(TPoint<T>(x1 + p.x(), y1 + p.y()), TPoint<T>(x2 + p.x(), y2 + p.y())); }
|
inline TRect<T> translated(const TPoint<T> &p) const { return TRect<T>(TPoint<T>(x1 + p.x(), y1 + p.y()), TPoint<T>(x2 + p.x(), y2 + p.y())); }
|
||||||
|
|
||||||
void moveCenter(const TPoint<T> &p) {
|
inline void moveCenter(const TPoint<T> &p) {
|
||||||
T w = x2 - x1;
|
T w = x2 - x1;
|
||||||
T h = y2 - y1;
|
T h = y2 - y1;
|
||||||
x1 = p.x() - w/2;
|
x1 = p.x() - w/2;
|
||||||
|
@ -107,7 +107,7 @@ public:
|
||||||
y2 = y1 + h;
|
y2 = y1 + h;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool contains(const TPoint<T> &p, bool insideOnly = false) const {
|
inline bool contains(const TPoint<T> &p, bool insideOnly = false) const {
|
||||||
T l, r;
|
T l, r;
|
||||||
if(x2 < x1 - 1) {
|
if(x2 < x1 - 1) {
|
||||||
l = x2;
|
l = x2;
|
||||||
|
@ -141,7 +141,7 @@ public:
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool intersects(const TRect<T> &r) const {
|
inline bool intersects(const TRect<T> &r) const {
|
||||||
if(isNull() || r.isNull())
|
if(isNull() || r.isNull())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
@ -182,7 +182,7 @@ public:
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
TRect<T> united(const TRect<T> &r) const {
|
inline TRect<T> united(const TRect<T> &r) const {
|
||||||
if(isNull() || r.isNull())
|
if(isNull() || r.isNull())
|
||||||
return TRect<T>();
|
return TRect<T>();
|
||||||
|
|
||||||
|
@ -228,7 +228,7 @@ public:
|
||||||
return tmp;
|
return tmp;
|
||||||
}
|
}
|
||||||
|
|
||||||
TRect<T> intersection(const TRect<T> &r) const {
|
inline TRect<T> intersection(const TRect<T> &r) const {
|
||||||
if(isNull())
|
if(isNull())
|
||||||
return r;
|
return r;
|
||||||
if(r.isNull())
|
if(r.isNull())
|
||||||
|
@ -281,4 +281,15 @@ private:
|
||||||
typedef TRect<int> Rect;
|
typedef TRect<int> Rect;
|
||||||
typedef TRect<float> RectF;
|
typedef TRect<float> RectF;
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
inline void operator>>(const YAML::Node& node, TRect<T>& rect)
|
||||||
|
{
|
||||||
|
T x, y, width, height;
|
||||||
|
node[0] >> x;
|
||||||
|
node[1] >> y;
|
||||||
|
node[2] >> width;
|
||||||
|
node[3] >> height;
|
||||||
|
rect.setRect(x, y, width, height);
|
||||||
|
}
|
||||||
|
|
||||||
#endif // RECT_H
|
#endif // RECT_H
|
||||||
|
|
|
@ -38,9 +38,9 @@ template <class T>
|
||||||
class TSize
|
class TSize
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
TSize() : wd(-1), ht(-1) {};
|
inline TSize() : wd(-1), ht(-1) {};
|
||||||
TSize(T width, T height) : wd(width), ht(height) { };
|
inline TSize(T width, T height) : wd(width), ht(height) { };
|
||||||
TSize(const TSize<T>& other) : wd(other.wd), ht(other.ht) { };
|
inline TSize(const TSize<T>& other) : wd(other.wd), ht(other.ht) { };
|
||||||
|
|
||||||
inline TPoint<T> toPoint() const { return TPoint<T>(wd, ht); }
|
inline TPoint<T> toPoint() const { return TPoint<T>(wd, ht); }
|
||||||
|
|
||||||
|
@ -51,6 +51,7 @@ public:
|
||||||
inline int width() const { return wd; }
|
inline int width() const { return wd; }
|
||||||
inline int height() const { return ht; }
|
inline int height() const { return ht; }
|
||||||
|
|
||||||
|
inline void setSize(T w, T h) { wd = w; ht = h; }
|
||||||
inline void setWidth(T w) { wd = w; }
|
inline void setWidth(T w) { wd = w; }
|
||||||
inline void setHeight(T h) { ht = h; }
|
inline void setHeight(T h) { ht = h; }
|
||||||
|
|
||||||
|
@ -76,7 +77,7 @@ public:
|
||||||
inline TSize<T> expandedTo(const TSize<T>& other) const { return TSize<T>(std::max(wd,other.wd), std::max(ht,other.ht)); }
|
inline TSize<T> expandedTo(const TSize<T>& other) const { return TSize<T>(std::max(wd,other.wd), std::max(ht,other.ht)); }
|
||||||
inline TSize<T> boundedTo(const TSize<T>& other) const { return TSize<T>(std::min(wd,other.wd), std::min(ht,other.ht)); }
|
inline TSize<T> boundedTo(const TSize<T>& other) const { return TSize<T>(std::min(wd,other.wd), std::min(ht,other.ht)); }
|
||||||
|
|
||||||
void scale(const TSize<T>& s, ESizeScaleMode mode) {
|
inline void scale(const TSize<T>& s, ESizeScaleMode mode) {
|
||||||
if(mode == IGNORE_ASPECT_RATIO || wd == 0 || ht == 0) {
|
if(mode == IGNORE_ASPECT_RATIO || wd == 0 || ht == 0) {
|
||||||
wd = s.wd;
|
wd = s.wd;
|
||||||
ht = s.ht;
|
ht = s.ht;
|
||||||
|
@ -98,7 +99,7 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
void scale(int w, int h, ESizeScaleMode mode) { scale(TSize<T>(w, h)); }
|
inline void scale(int w, int h, ESizeScaleMode mode) { scale(TSize<T>(w, h)); }
|
||||||
|
|
||||||
inline float ratio() const { return (float)wd/ht; }
|
inline float ratio() const { return (float)wd/ht; }
|
||||||
inline T area() const { return wd*ht; }
|
inline T area() const { return wd*ht; }
|
||||||
|
@ -110,4 +111,13 @@ private:
|
||||||
typedef TSize<int> Size;
|
typedef TSize<int> Size;
|
||||||
typedef TSize<float> SizeF;
|
typedef TSize<float> SizeF;
|
||||||
|
|
||||||
|
template <class T>
|
||||||
|
inline void operator>>(const YAML::Node& node, TSize<T>& size)
|
||||||
|
{
|
||||||
|
T w, h;
|
||||||
|
node[0] >> w;
|
||||||
|
node[1] >> h;
|
||||||
|
size.setSize(w, h);
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -29,6 +29,7 @@
|
||||||
#include "framework/logger.h"
|
#include "framework/logger.h"
|
||||||
#include "framework/engine.h"
|
#include "framework/engine.h"
|
||||||
#include "framework/rect.h"
|
#include "framework/rect.h"
|
||||||
|
#include "framework/fonts.h"
|
||||||
|
|
||||||
TexturePtr background;
|
TexturePtr background;
|
||||||
|
|
||||||
|
@ -65,8 +66,11 @@ void MenuState::render()
|
||||||
|
|
||||||
Rect texCoords(0, 0, texCoordsSize);
|
Rect texCoords(0, 0, texCoordsSize);
|
||||||
texCoords.moveBottomRight(texSize.toPoint());
|
texCoords.moveBottomRight(texSize.toPoint());
|
||||||
|
|
||||||
g_graphics.drawTexturedRect(Rect(0, 0, screenSize), m_background.get(), texCoords);
|
g_graphics.drawTexturedRect(Rect(0, 0, screenSize), m_background.get(), texCoords);
|
||||||
|
|
||||||
|
Font *font = g_fonts.get("sans14");
|
||||||
|
if(font)
|
||||||
|
font->renderText(Point(10,10), "hello\nworld!");
|
||||||
}
|
}
|
||||||
|
|
||||||
void MenuState::update(int ticks, int elapsedTicks)
|
void MenuState::update(int ticks, int elapsedTicks)
|
||||||
|
|
Loading…
Reference in New Issue