예제 #1
0
파일: text.cpp 프로젝트: Tellus/colobot
bool CText::Create()
{
    if (TTF_Init() != 0)
    {
        m_error = std::string("TTF_Init error: ") + std::string(TTF_GetError());
        return false;
    }

    m_fonts[FONT_COLOBOT]        = new MultisizeFont("fonts/dvu_sans.ttf");
    m_fonts[FONT_COLOBOT_BOLD]   = new MultisizeFont("fonts/dvu_sans_bold.ttf");
    m_fonts[FONT_COLOBOT_ITALIC] = new MultisizeFont("fonts/dvu_sans_italic.ttf");

    m_fonts[FONT_COURIER]        = new MultisizeFont("fonts/dvu_sans_mono.ttf");
    m_fonts[FONT_COURIER_BOLD]   = new MultisizeFont("fonts/dvu_sans_mono_bold.ttf");

    for (auto it = m_fonts.begin(); it != m_fonts.end(); ++it)
    {
        FontType type = (*it).first;
        CachedFont* cf = GetOrOpenFont(type, m_defaultSize);
        if (cf == nullptr || cf->font == nullptr)
            return false;
    }

    return true;
}
예제 #2
0
파일: text.cpp 프로젝트: xiendev/colobot
void CText::DrawCharAndAdjustPos(UTF8Char ch, FontType font, float size, Math::Point &pos, Color color)
{
    // TODO: if (font == FONT_BUTTON)
    if (font == FONT_BUTTON) return;

    // TODO: special chars?

    CachedFont* cf = GetOrOpenFont(font, size);

    if (cf == nullptr)
        return;

    int width = 1;
    if (ch.c1 > 0 && ch.c1 < 32) { // FIXME add support for chars with code 9 10 23
        if (ch.c1 == '\t') {
            ch.c1 = ':';
            width = 4;
        } else {
            ch.c1 = ' ';
        }
        ch.c2 = 0;
        ch.c3 = 0;
    }

    auto it = cf->cache.find(ch);
    CharTexture tex;
    if (it != cf->cache.end())
    {
        tex = (*it).second;
    }
    else
    {
        tex = CreateCharTexture(ch, cf);

        if (tex.id == 0) // invalid
            return;

        cf->cache[ch] = tex;
    }

    Math::Point p1(pos.x, pos.y + tex.charSize.y - tex.texSize.y);
    Math::Point p2(pos.x + tex.texSize.x, pos.y + tex.charSize.y);

    Math::Vector n(0.0f, 0.0f, -1.0f);  // normal

    Vertex quad[4] =
    {
        Vertex(Math::Vector(p1.x, p1.y, 0.0f), n, Math::Point(0.0f, 1.0f)),
        Vertex(Math::Vector(p1.x, p2.y, 0.0f), n, Math::Point(0.0f, 0.0f)),
        Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(1.0f, 1.0f)),
        Vertex(Math::Vector(p2.x, p2.y, 0.0f), n, Math::Point(1.0f, 0.0f))
    };

    m_device->SetTexture(0, tex.id);
    m_device->DrawPrimitive(PRIMITIVE_TRIANGLE_STRIP, quad, 4, color);
    m_engine->AddStatisticTriangle(2);

    pos.x += tex.charSize.x * width;
}
예제 #3
0
파일: text.cpp 프로젝트: Tellus/colobot
float CText::GetHeight(FontType font, float size)
{
    assert(font != FONT_BUTTON);

    CachedFont* cf = GetOrOpenFont(font, size);
    assert(cf != nullptr);
    Math::IntPoint wndSize;
    wndSize.y = TTF_FontHeight(cf->font);
    Math::Point ifSize = m_engine->WindowToInterfaceSize(wndSize);
    return ifSize.y;
}
예제 #4
0
파일: text.cpp 프로젝트: xiendev/colobot
float CText::GetStringWidth(const std::string &text, FontType font, float size)
{
    assert(font != FONT_BUTTON);

    // TODO: special chars?

    CachedFont* cf = GetOrOpenFont(font, size);
    assert(cf != nullptr);
    Math::IntPoint wndSize;
    TTF_SizeUTF8(cf->font, text.c_str(), &wndSize.x, &wndSize.y);
    Math::Point ifSize = m_engine->WindowToInterfaceSize(wndSize);
    return ifSize.x;
}
예제 #5
0
파일: text.cpp 프로젝트: Tellus/colobot
float CText::GetStringWidth(std::string text, FontType font, float size)
{
    assert(font != FONT_BUTTON);

    // Skip special chars
    for (char& c : text)
    {
        if (c < 32 && c >= 0)
            c = ':';
    }

    CachedFont* cf = GetOrOpenFont(font, size);
    assert(cf != nullptr);
    Math::IntPoint wndSize;
    TTF_SizeUTF8(cf->font, text.c_str(), &wndSize.x, &wndSize.y);
    Math::Point ifSize = m_engine->WindowToInterfaceSize(wndSize);
    return ifSize.x;
}
예제 #6
0
파일: text.cpp 프로젝트: xiendev/colobot
float CText::GetCharWidth(UTF8Char ch, FontType font, float size, float offset)
{
    // TODO: if (font == FONT_BUTTON)
    if (font == FONT_BUTTON) return 0.0f;

    // TODO: special chars?
    // TODO: tab sizing

    CachedFont* cf = GetOrOpenFont(font, size);
    assert(cf != nullptr);

    CharTexture tex;
    auto it = cf->cache.find(ch);
    if (it != cf->cache.end())
        tex = (*it).second;
    else
        tex = CreateCharTexture(ch, cf);

    return tex.charSize.x;
}
예제 #7
0
파일: text.cpp 프로젝트: Tellus/colobot
float CText::GetCharWidth(UTF8Char ch, FontType font, float size, float offset)
{
    if (font == FONT_BUTTON) {
        Math::IntPoint windowSize = m_engine->GetWindowSize();
        float height = GetHeight(FONT_COLOBOT, size);
        float width = height*(static_cast<float>(windowSize.y)/windowSize.x);
        return width;
    }

    int width = 1;
    if (ch.c1 < 32 && ch.c1 >= 0)
    {
        if (ch.c1 == '\t')
            width = m_tabSize;

        // TODO: tab sizing at intervals?

        ch.c1 = ':';
    }

    CachedFont* cf = GetOrOpenFont(font, size);
    assert(cf != nullptr);

    Math::Point charSize;
    auto it = cf->cache.find(ch);
    if (it != cf->cache.end())
    {
        charSize = (*it).second.charSize;
    }
    else
    {
        Math::IntPoint wndSize;
        std::string text;
        text.append({ch.c1, ch.c2, ch.c3});
        TTF_SizeUTF8(cf->font, text.c_str(), &wndSize.x, &wndSize.y);
        charSize = m_engine->WindowToInterfaceSize(wndSize);
    }

    return charSize.x * width;
}
예제 #8
0
파일: text.cpp 프로젝트: Tellus/colobot
void CText::DrawCharAndAdjustPos(UTF8Char ch, FontType font, float size, Math::Point &pos, Color color)
{
    if(font == FONT_BUTTON)
    {
        Math::IntPoint windowSize = m_engine->GetWindowSize();
        float height = GetHeight(FONT_COLOBOT, size);
        float width = height*(static_cast<float>(windowSize.y)/windowSize.x);

        Math::Point p1(pos.x, pos.y);
        Math::Point p2(pos.x + width, pos.y + height);

        Math::Vector n(0.0f, 0.0f, -1.0f);  // normal

        // For whatever reason ch.c1 is a SIGNED char, we need to fix that
        unsigned char icon = static_cast<unsigned char>(ch.c1);
        if ( icon >= 192 )
        {
            icon -= 192;
            m_engine->SetTexture("textures/interface/text.png");
            m_engine->SetState(ENG_RSTATE_TTEXTURE_WHITE);
        }
        else if ( icon >= 128 )
        {
            icon -= 128;
            m_engine->SetTexture("textures/interface/button3.png");
            m_engine->SetState(ENG_RSTATE_TTEXTURE_WHITE);
        }
        else if ( icon >= 64 )
        {
            icon -= 64;
            m_engine->SetTexture("textures/interface/button2.png");
            m_engine->SetState(ENG_RSTATE_TTEXTURE_WHITE);
        }
        else
        {
            m_engine->SetTexture("textures/interface/button1.png");
            m_engine->SetState(ENG_RSTATE_TTEXTURE_WHITE);
        }

        Math::Point uv1, uv2;
        uv1.x = (32.0f / 256.0f) * (icon%8);
        uv1.y = (32.0f / 256.0f) * (icon/8);
        uv2.x = (32.0f / 256.0f) + uv1.x;
        uv2.y = (32.0f / 256.0f) + uv1.y;

        float dp = 0.5f / 256.0f;
        uv1.x += dp;
        uv1.y += dp;
        uv2.x -= dp;
        uv2.y -= dp;

        Vertex quad[4] =
        {
            Vertex(Math::Vector(p1.x, p1.y, 0.0f), n, Math::Point(uv1.x, uv2.y)),
            Vertex(Math::Vector(p1.x, p2.y, 0.0f), n, Math::Point(uv1.x, uv1.y)),
            Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(uv2.x, uv2.y)),
            Vertex(Math::Vector(p2.x, p2.y, 0.0f), n, Math::Point(uv2.x, uv1.y))
        };

        m_device->DrawPrimitive(PRIMITIVE_TRIANGLE_STRIP, quad, 4, color);
        m_engine->AddStatisticTriangle(2);

        pos.x += width;

        // Don't forget to restore the state!
        m_engine->SetState(ENG_RSTATE_TEXT);
    }
    else
    {
        CachedFont* cf = GetOrOpenFont(font, size);

        if (cf == nullptr)
            return;

        int width = 1;
        if (ch.c1 > 0 && ch.c1 < 32)
        {
            if (ch.c1 == '\t')
                width = m_tabSize;

            ch = TranslateSpecialChar(ch.c1);
        }

        auto it = cf->cache.find(ch);
        CharTexture tex;
        if (it != cf->cache.end())
        {
            tex = (*it).second;
        }
        else
        {
            tex = CreateCharTexture(ch, cf);

            if (tex.id == 0) // invalid
                return;

            cf->cache[ch] = tex;
        }

        Math::Point p1(pos.x, pos.y + tex.charSize.y - tex.texSize.y);
        Math::Point p2(pos.x + tex.texSize.x, pos.y + tex.charSize.y);

        Math::Vector n(0.0f, 0.0f, -1.0f);  // normal

        Vertex quad[4] =
        {
            Vertex(Math::Vector(p1.x, p1.y, 0.0f), n, Math::Point(0.0f, 1.0f)),
            Vertex(Math::Vector(p1.x, p2.y, 0.0f), n, Math::Point(0.0f, 0.0f)),
            Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(1.0f, 1.0f)),
            Vertex(Math::Vector(p2.x, p2.y, 0.0f), n, Math::Point(1.0f, 0.0f))
        };

        m_device->SetTexture(0, tex.id);
        m_device->DrawPrimitive(PRIMITIVE_TRIANGLE_STRIP, quad, 4, color);
        m_engine->AddStatisticTriangle(2);

        pos.x += tex.charSize.x * width;
    }
}