+void HUD::textAlign(fntRenderer *rend, const char *s, int align,
+ float *x, float *y, float *l, float *r, float *t, float *b)
+{
+ fntFont *font = rend->getFont();
+ float gap = font->getGap();
+ float left, right, bot, top;
+ font->getBBox(s, rend->getPointSize(), rend->getSlant(), &left, &right, &bot, &top);
+
+ if (align & HUD::HCENTER)
+ *x = *x - left + gap - (right - left - gap) / 2.0;
+ else if (align & HUD::RIGHT)
+ *x = *x - right;
+ else if (align & HUD::LEFT)
+ *x = *x - left;
+
+ if (align & HUD::VCENTER)
+ *y = *y - bot - (top - bot) / 2.0;
+ else if (align & HUD::TOP)
+ *y = *y - top;
+ else if (align & HUD::BOTTOM)
+ *y = *y - bot;
+
+ *l = *x + left;
+ *r = *x + right;
+ *b = *y + bot;
+ *t = *y + top;
+}
strncpy(_msg, s, BUFSIZE);
if (!align || !s[0])
return;
-
- fntFont *f = _fnt->getFont();
- float gap = f->getGap();
- float left, right, bot, top;
- f->getBBox(s, _fnt->getPointSize(), _fnt->getSlant(), &left, &right, &bot, &top);
-
- if (align & HCENTER)
- _x = x - left + gap - (right - left - gap) / 2.0;
- else if (align & RIGHT)
- _x = x - right;
- else if (align & LEFT)
- _x = x - left;
-
- if (align & VCENTER)
- _y = y - bot - (top - bot) / 2.0;
- else if (align & TOP)
- _y = y - top;
- else if (align & BOTTOM)
- _y = y - bot;
+ float ign;
+ HUD::textAlign(fnt, s, align, &_x, &_y, &ign, &ign, &ign, &ign);
}
}
+void TextList::align(const char *s, int align, float *x, float *y,
+ float *l, float *r, float *b, float *t) const
+{
+ HUD::textAlign(_font, s, align, x, y, l, r, b, t);
+}
+
+
+void TextList::draw()
+{
+ assert(_font);
+
+ // FIXME
+ glPushAttrib(GL_COLOR_BUFFER_BIT);
+ glEnable(GL_BLEND);
+
+ _font->begin();
+ vector<HUDText>::iterator it, end = _list.end();
+ for (it = _list.begin(); it != end; ++it)
+ it->draw();
+ _font->end();
+
+ glDisable(GL_TEXTURE_2D);
+ glPopAttrib();
+}
+
+
class SGCondition;
-
class LineSegment {
public:
LineSegment(GLfloat x0, GLfloat y0, GLfloat x1, GLfloat y1)
public:
HUDText(fntRenderer *f, float x, float y, const char *s, int align = 0, int digits = 0);
void draw();
- enum {
- LEFT = 0x0001,
- RIGHT = 0x0002,
- TOP = 0x0004,
- BOTTOM = 0x0008,
- HCENTER = 0x0010,
- VCENTER = 0x0020,
- CENTER = (HCENTER|VCENTER),
- };
private:
fntRenderer *_fnt;
_list.push_back(HUDText(_font, x, y, s, align, digit));
}
void erase() { _list.erase(_list.begin(), _list.end()); }
- void draw() {
- assert(_font);
-
- // FIXME
- glPushAttrib(GL_COLOR_BUFFER_BIT);
- glEnable(GL_BLEND);
-
- _font->begin();
- vector<HUDText>::iterator it, end = _list.end();
- for (it = _list.begin(); it != end; ++it)
- it->draw();
- _font->end();
-
- glDisable(GL_TEXTURE_2D);
- glPopAttrib();
- }
+ void align(const char *s, int align, float *x, float *y,
+ float *l, float *r, float *b, float *t) const;
+ void draw();
private:
fntRenderer *_font;
inline bool is3D() const { return _3Denabled; }
inline float alphaClamp() const { return _cl; }
inline double timer() const { return _timer; }
+ static void textAlign(fntRenderer *r, const char *s, int align, float *x, float *y,
+ float *l, float *r, float *b, float *t);
enum Units { FEET, METER };
Units getUnits() const { return _units; }
NOTICKS = 0x0020,
NOTEXT = 0x0040,
BOTH = (LEFT|RIGHT),
+
+ // for alignment (with LEFT, RIGHT, TOP, BOTTOM)
+ HCENTER = 0x0080,
+ VCENTER = 0x0100,
+ CENTER = (HCENTER|VCENTER),
};
protected:
int(disp_val * _input.factor()/*+.5*/)); /// was data_scaling(), which makes no sense
if (option_left() && option_right())
- draw_text(_center_x, marker_ys, buf, HUDText::CENTER);
+ draw_text(_center_x, marker_ys, buf, CENTER);
else if (option_left())
- draw_text(marker_xs, marker_ys, buf, HUDText::RIGHT|HUDText::VCENTER);
+ draw_text(marker_xs, marker_ys, buf, RIGHT|VCENTER);
else
- draw_text(marker_xe, marker_ys, buf, HUDText::LEFT|HUDText::VCENTER);
+ draw_text(marker_xe, marker_ys, buf, LEFT|VCENTER);
}
}
}
draw_line(marker_xs, marker_ye, marker_xs, top);
if (!option_notext())
- draw_text(marker_xs, marker_ys, buf, HUDText::CENTER);
+ draw_text(marker_xs, marker_ys, buf, CENTER);
} else {
draw_line(marker_xs, marker_ys, marker_xs, marker_ye);
if (!option_notext()) {
if (option_top())
- draw_text(marker_xs, top, buf, HUDText::TOP|HUDText::HCENTER);
+ draw_text(marker_xs, top, buf, TOP|HCENTER);
else
- draw_text(marker_xs, _y, buf, HUDText::BOTTOM|HUDText::HCENTER);
+ draw_text(marker_xs, _y, buf, BOTTOM|HCENTER);
}
}
}
const char *halign = n->getStringValue("halign", "center");
if (!strcmp(halign, "left"))
- _halign = HUDText::LEFT;
+ _halign = LEFT;
else if (!strcmp(halign, "right"))
- _halign = HUDText::RIGHT;
+ _halign = RIGHT;
else
- _halign = HUDText::HCENTER;
+ _halign = HCENTER;
- _halign |= HUDText::VCENTER;
+ _halign |= VCENTER;
const char *pre = n->getStringValue("prefix", 0);
const char *post = n->getStringValue("postfix", 0);
else if (_mode == DOUBLE) // not really supported yet
snprintf(buf, BUFSIZE, _format.c_str(), double(_input.getFloatValue()));
- if (_halign & HUDText::HCENTER)
+ if (_halign & HCENTER)
draw_text(_center_x, _center_y, buf, _halign, get_digits());
- else if (_halign & HUDText::LEFT)
+ else if (_halign & LEFT)
draw_text(_x, _center_y, buf, _halign, get_digits());
- else // if (_halign & HUDText::RIGHT)
+ else // if (_halign & RIGHT)
draw_text(_x + _w, _center_y, buf, _halign, get_digits());
}
draw_nadir(0.0, y);
}
- draw_text(x_ini - 4, y, buf, HUDText::VCENTER|HUDText::LEFT);
- draw_text(x_end + 4, y, buf, HUDText::VCENTER|HUDText::RIGHT);
+ draw_text(x_ini - 4, y, buf, VCENTER|LEFT);
+ draw_text(x_end + 4, y, buf, VCENTER|RIGHT);
}
}
draw_line(x_ini, y, x_end, y);
draw_line(x_ini2, y, x_end2, y);
- draw_text(x_ini - 2.0, y, buf, HUDText::VCENTER|HUDText::RIGHT);
- draw_text(x_end2 + 2.0, y, buf, HUDText::VCENTER|HUDText::LEFT);
+ draw_text(x_ini - 2.0, y, buf, VCENTER|RIGHT);
+ draw_text(x_end2 + 2.0, y, buf, VCENTER|LEFT);
} else if (i > 0) {
//draw climb bar vertical lines
draw_line(x_ini, y, x_end, y);
draw_line(x_ini2, y, x_end2, y);
- draw_text(x_ini + 0.5, y - 0.5, buf, HUDText::TOP|HUDText::LEFT);
- draw_text(x_end2 - 0.5, y - 0.5, buf, HUDText::TOP|HUDText::RIGHT);
+ draw_text(x_ini + 0.5, y - 0.5, buf, TOP|LEFT);
+ draw_text(x_end2 - 0.5, y - 0.5, buf, TOP|RIGHT);
if (i == 90 && _zenith)
draw_zenith(0.0, y);
draw_stipple_line(x_ini2, y, x_end2, y_end);
float yoffs = 1.0 + (y - y_end) / 4.0; // too hackish?
- draw_text(x_ini + 3.0, y_end + yoffs, buf, HUDText::BOTTOM|HUDText::HCENTER);
+ draw_text(x_ini + 3.0, y_end + yoffs, buf, BOTTOM|HCENTER);
// right number shifted in a little more, because of the minus
- draw_text(x_end2 - 4.0, y_end + yoffs, buf, HUDText::BOTTOM|HUDText::HCENTER);
+ draw_text(x_end2 - 4.0, y_end + yoffs, buf, BOTTOM|HCENTER);
if (i == -90 && _nadir)
draw_nadir(0.0, y);
_draw_cap_right(n->getBoolValue("cap-right", false)),
_draw_cap_left(n->getBoolValue("cap-left", false)),
_marker_offset(n->getFloatValue("marker-offset", 0.0)),
- _label_gap(n->getFloatValue("label-gap-width", 0.0)),
+ _label_gap(n->getFloatValue("label-gap-width", 0.0) / 2.0),
_pointer(n->getBoolValue("enable-pointer", true)),
_zoom(n->getIntValue("zoom"))
{
float y = _y + (v - vmin) * factor();
- if (y < _y + 4)
+ if (y < _y + 0)
continue;
- if (y > top - 4)
+ if (y > top - 0)
break;
if (div_ratio && i % div_ratio) { // minor div
snprintf(buf, BUFSIZE, "%d", display_value);
+ float x;
+ int align;
+
if (option_both()) {
if (_tick_type == LINE) {
draw_line(_x, y, marker_xs, y);
draw_bullet(_x, y, 5.0);
}
- if (!option_notext())
- draw_text(marker_xs, y, buf, HUDText::CENTER);
+ x = marker_xs, align = CENTER;
} else {
if (_tick_type == LINE)
else // _tick_type == CIRCLE
draw_bullet(marker_xs + 4, y, 5.0);
- if (!option_notext()) {
- if (option_left())
- draw_text(marker_xs, y, buf, HUDText::RIGHT|HUDText::VCENTER);
- else
- draw_text(marker_xe + 1.0, y, buf, HUDText::LEFT|HUDText::VCENTER);
- }
- } // End if huds-both
+ if (option_left())
+ x = marker_xs, align = RIGHT|VCENTER;
+ else
+ x = marker_xe, align = LEFT|VCENTER;
+ }
+
+ if (!option_notext()) {
+ float l, r, b, t;
+ _hud->_text_list.align(buf, align, &x, &y, &l, &r, &b, &t);
+ if (b < _y || t > top)
+ continue;
+ if (_label_gap == 0.0)
+ draw_text(x, y, buf);
+ else if (b < _center_x - _label_gap && t < _center_x - _label_gap)
+ draw_text(x, y, buf);
+ else if (b > _center_x + _label_gap && t > _center_x + _label_gap)
+ draw_text(x, y, buf);
+ }
}
}
} // end of zoom
float x = _x + (v - vmin) * factor();
- if (x < _x + 4)
+ if (x < _x + 0)
continue;
- if (x > right - 4)
+ if (x > right - 0)
break;
if (div_ratio && i % div_ratio) { // minor div
snprintf(buf, BUFSIZE, "%d", display_value);
- // Draw major ticks and text only if far enough from the edge. // FIXME
- if (x < _x + 10 || x + 10 > _x + _w)
- continue;
+ float y;
+ int align;
if (option_both()) {
draw_line(x, _y, x, marker_ye);
draw_line(x, marker_ye, x, _y + _h);
-
- if (!option_notext())
- draw_text(x, marker_ys, buf, HUDText::CENTER);
+ y = marker_ys, align = CENTER;
} else {
draw_line(x, marker_ys, x, marker_ye);
- if (!option_notext()) {
- if (option_top())
- draw_text(x, top, buf, HUDText::TOP|HUDText::HCENTER);
- else
- draw_text(x, _y, buf, HUDText::BOTTOM|HUDText::HCENTER);
- }
+ if (option_top())
+ y = top, align = TOP|HCENTER;
+ else
+ y = _y, align = BOTTOM|HCENTER;
+ }
+
+ if (!option_notext()) {
+ float l, r, b, t;
+ _hud->_text_list.align(buf, align, &x, &y, &l, &r, &b, &t);
+ if (l < _x || r > right)
+ continue;
+ if (_label_gap == 0.0)
+ draw_text(x, y, buf);
+ else if (l < _center_x - _label_gap && r < _center_x - _label_gap)
+ draw_text(x, y, buf);
+ else if (l > _center_x + _label_gap && r > _center_x + _label_gap)
+ draw_text(x, y, buf);
}
}
} // end for