source: trunk/packages/vizservers/nanovis/util/Fonts.cpp @ 3935

Last change on this file since 3935 was 3935, checked in by ldelgass, 11 years ago

First pass at loading VTK vector data for flows in nanovis

  • Property svn:eol-style set to native
File size: 7.4 KB
Line 
1/* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2/*
3 *  Copyright (c) 2004-2013  HUBzero Foundation, LLC
4 */
5
6#include <stdarg.h>
7#include <string.h>
8
9#include <fstream>
10
11#include <GL/glew.h>
12
13#include "Fonts.h"
14#include "FilePath.h"
15
16using namespace nv::util;
17
18// constants
19const int c_nFileMagicHeader = 6666;
20
21Fonts::Fonts() :
22    _fontIndex(-1),
23    _screenWidth(512),
24    _screenHeight(512)
25{
26}
27
28Fonts::~Fonts()
29{
30    for (unsigned index = 0; index < _fonts.size(); ++index) {
31        glDeleteLists(_fonts[index]._displayLists, 256);
32        glDeleteTextures(1, &(_fonts[_fontIndex]. _fontTextureID));
33    }
34}
35
36void
37Fonts::setFont(const char *fontName)
38{
39    if (fontName != NULL) {
40        unsigned int i;
41        for (i = 0; i < _fonts.size(); ++i) {
42            if (strcmp(_fonts[i]._fontName.c_str(), fontName) == 0) {
43                _fontIndex = i;
44                break;
45            }
46        }
47    }
48}
49
50void
51Fonts::addFont(const char *fontName, const char *fontFileName)
52{
53    FontAttributes sFont;
54   
55    loadFont(fontName, fontFileName, sFont);
56    initializeFont(sFont);
57    _fonts.push_back(sFont);
58}
59
60void
61Fonts::draw(const char *pString, ...) const
62{
63    va_list vlArgs;
64    char szVargsBuffer[1024];
65
66    va_start(vlArgs, pString);
67    vsprintf(szVargsBuffer, pString, vlArgs);
68
69    if (_fontIndex != -1) {
70        int length = strlen(szVargsBuffer);
71
72        glListBase(_fonts[_fontIndex]._displayLists);
73        glCallLists(length, GL_UNSIGNED_BYTE,
74                    reinterpret_cast<const GLvoid*>(szVargsBuffer));
75    }
76}
77
78void
79Fonts::begin()
80{
81    glPushAttrib(GL_TRANSFORM_BIT | GL_ENABLE_BIT);
82    glEnable(GL_TEXTURE_2D);
83    glBindTexture(GL_TEXTURE_2D, _fonts[_fontIndex]._fontTextureID);
84
85    glMatrixMode(GL_PROJECTION);
86    glPushMatrix();
87    glLoadIdentity();
88
89    gluOrtho2D(0.0f, _screenWidth, _screenHeight, 0.0f);
90
91    glMatrixMode(GL_MODELVIEW);
92    glPushMatrix();
93    glLoadIdentity();
94
95#if 0
96    glDisable(GL_BLEND);
97    glEnable(GL_DEPTH_TEST);
98#else
99    glEnable(GL_BLEND);
100    glDisable(GL_DEPTH_TEST);
101#endif
102}
103
104void
105Fonts::end()
106{
107    glBindTexture(GL_TEXTURE_2D, 0);
108
109    glMatrixMode(GL_PROJECTION);
110    glPopMatrix();
111
112    glMatrixMode(GL_MODELVIEW);
113    glPopMatrix();
114
115    glPopAttrib();
116}
117
118void
119Fonts::initializeFont(FontAttributes& attr)
120{
121    attr._displayLists = glGenLists(256);
122
123    int index;
124    for (index = 0; index < 256; ++index) {
125        FontAttributes::CharInfo& charInfo = attr._chars[index];
126        glNewList(attr._displayLists + index, GL_COMPILE);
127        if (charInfo._valid) {
128            glBegin(GL_TRIANGLE_STRIP);
129           
130            glTexCoord2f(charInfo._left, charInfo._top);
131            glVertex2i(0, 0);
132           
133            glTexCoord2f(charInfo._left, charInfo._bottom);
134            glVertex2i(0, (GLint)attr._fontHeight);
135           
136            glTexCoord2f(charInfo._right, charInfo._top);
137            glVertex2i((GLint)charInfo._width, 0);
138           
139            glTexCoord2f(charInfo._right,  charInfo._bottom);
140            glVertex2i((GLint)charInfo._width, (GLint)attr._fontHeight);
141           
142            glEnd();
143            glTranslatef(charInfo._width, 0.0f, 0.0f);
144        }
145        glEndList();
146    }
147}
148
149bool
150Fonts::loadFont(const char *fontName, const char *fontFileName,
151                FontAttributes& sFont)
152{
153    bool bSuccess = false;
154
155    std::string path = FilePath::getInstance()->getPath(fontFileName);
156    if (path.empty()) {
157        return false;
158    }
159    std::ifstream fsInput(path.c_str(), std::ios::binary);
160    if (fsInput) {
161        sFont._fontName = fontName;
162
163        // make sure this file is the correct type by checking the header
164        unsigned int uiFileId = 0;
165        fsInput.read(reinterpret_cast<char*>(&uiFileId), sizeof(unsigned int));
166        if (uiFileId == (unsigned int)c_nFileMagicHeader) {
167            // read general font/texture dimensions
168            fsInput.read(reinterpret_cast<char*>(&sFont._textureWidth),
169                         sizeof(unsigned int));
170            fsInput.read(reinterpret_cast<char*>(&sFont._textureHeight),
171                         sizeof(unsigned int));
172            fsInput.read(reinterpret_cast<char*>(&sFont._fontHeight),
173                         sizeof(unsigned int));
174
175            // read dimensions for each character in 256-char ASCII chart
176            for (int i = 0; i < 256; ++i) {
177                unsigned int uiSize = 0;
178
179                // top
180                fsInput.read(reinterpret_cast<char*>(&uiSize),
181                             sizeof(unsigned int));
182                sFont._chars[i]._top = static_cast<float>(uiSize) / sFont._textureHeight;
183                // left
184                fsInput.read(reinterpret_cast<char*>(&uiSize), sizeof(unsigned int));
185                sFont._chars[i]._left = static_cast<float>(uiSize) / sFont._textureWidth;
186                // bottom
187                fsInput.read(reinterpret_cast<char*>(&uiSize), sizeof(unsigned int));
188                sFont._chars[i]._bottom = static_cast<float>(uiSize) / sFont._textureHeight;
189                // right
190                fsInput.read(reinterpret_cast<char*>(&uiSize), sizeof(unsigned int));
191                sFont._chars[i]._right = static_cast<float>(uiSize) / sFont._textureWidth;
192                // enabled
193                fsInput.read(reinterpret_cast<char*>(&uiSize), sizeof(unsigned int));
194                sFont._chars[i]._valid = (uiSize != 0);
195                // width factor
196                float fWidthFactor = 1.0f;
197                fsInput.read(reinterpret_cast<char*>(&fWidthFactor), sizeof(float));
198                sFont._chars[i]._width = fWidthFactor * sFont._fontHeight;
199            }
200        }
201
202        // allocate and read the texture map
203        if (!fsInput.eof() && !fsInput.fail()) {
204            unsigned int uiArea = sFont._textureWidth * sFont._textureHeight;
205            unsigned char *pRawMap = new unsigned char[uiArea];
206            fsInput.read(reinterpret_cast<char *>(pRawMap), uiArea);
207
208            // we've only read the luminance values, but we need a luminance +
209            // alpha buffer, so we make a new buffer and duplicate the
210            // luminance values
211            unsigned char *pTexMap = new unsigned char[2 * uiArea];
212            unsigned char *pMap = pTexMap;
213            for (unsigned int i = 0; i < uiArea; ++i) {
214                *pMap++ = pRawMap[i];
215                *pMap++ = pRawMap[i];
216            }
217            delete[] pRawMap;
218            pRawMap = NULL;
219
220            // make texture map out of new buffer
221            glGenTextures(1, &sFont._fontTextureID);
222            glBindTexture(GL_TEXTURE_2D, sFont._fontTextureID);
223            glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE_ALPHA,
224                         sFont._textureWidth, sFont._textureHeight, 0,
225                         GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE, pTexMap);
226            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
227            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
228            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
229            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
230            glTexEnvi(GL_TEXTURE_2D, GL_TEXTURE_ENV_MODE, GL_MODULATE);
231            glBindTexture(GL_TEXTURE_2D, 0);
232
233            delete[] pTexMap;
234            pTexMap = NULL;
235
236            bSuccess = true;
237        }
238
239        fsInput.close();
240    }
241    return bSuccess;
242}
243
244void
245Fonts::resize(int width, int height)
246{
247    _screenWidth = width;
248    _screenHeight = height;
249}
250
Note: See TracBrowser for help on using the repository browser.