The Battle for Wesnoth  1.13.4+dev
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
help_text_area.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2003 - 2016 by David White <[email protected]>
3  Part of the Battle for Wesnoth Project http://www.wesnoth.org/
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY.
11 
12  See the COPYING file for more details.
13 */
14 
15 #include "help_text_area.hpp"
16 
17 #include "config.hpp" // for config, etc
18 #include "game_config.hpp" // for debug
19 #include "help/help_impl.hpp" // for parse_error, box_width, etc
20 #include "image.hpp" // for get_image
21 #include "log.hpp" // for LOG_STREAM, log_domain, etc
22 #include "sdl/rect.hpp" // for draw_rectangle, etc
23 #include "serialization/parser.hpp" // for read, write
24 #include "util.hpp" // for lexical_cast, etc
25 #include "video.hpp" // for update_rect, CVideo
26 
27 #include <algorithm> // for max, min, find_if
28 #include <ostream> // for operator<<, stringstream, etc
29 #include <vector> // for vector, etc
30 #include <SDL.h> // for TTF_STYLE_BOLD, etc
31 
32 static lg::log_domain log_display("display");
33 #define WRN_DP LOG_STREAM(warn, log_display)
34 
35 namespace help {
36 
38  gui::scrollarea(video),
39  items_(),
40  last_row_(),
41  toplevel_(toplevel),
42  shown_topic_(nullptr),
43  title_spacing_(16),
44  curr_loc_(0, 0),
45  min_row_height_(font::get_max_height(normal_font_size)),
46  curr_row_height_(min_row_height_),
47  contents_height_(0)
48 {
49  set_scroll_rate(40);
50 }
51 
52 void help_text_area::set_inner_location(SDL_Rect const &rect)
53 {
54  bg_register(rect);
55  if (shown_topic_)
56  set_items();
57 }
58 
60 {
61  shown_topic_ = &t;
62  set_items();
63  set_dirty(true);
64 }
65 
66 
68  const std::string& reference_to, bool _floating,
69  bool _box, ALIGNMENT alignment) :
70  rect(),
71  surf(surface),
72  text(_text),
73  ref_to(reference_to),
74  floating(_floating), box(_box),
75  align(alignment)
76 {
77  rect.x = x;
78  rect.y = y;
79  rect.w = box ? surface->w + box_width * 2 : surface->w;
80  rect.h = box ? surface->h + box_width * 2 : surface->h;
81 }
82 
83 help_text_area::item::item(surface surface, int x, int y, bool _floating,
84  bool _box, ALIGNMENT alignment) :
85  rect(),
86  surf(surface),
87  text(""),
88  ref_to(""),
89  floating(_floating),
90  box(_box), align(alignment)
91 {
92  rect.x = x;
93  rect.y = y;
94  rect.w = box ? surface->w + box_width * 2 : surface->w;
95  rect.h = box ? surface->h + box_width * 2 : surface->h;
96 }
97 
99 {
100  last_row_.clear();
101  items_.clear();
102  curr_loc_.first = 0;
103  curr_loc_.second = 0;
105  // Add the title item.
106  const std::string show_title =
109  font::NORMAL_COLOR, TTF_STYLE_BOLD));
110  if (surf != nullptr) {
111  add_item(item(surf, 0, 0, show_title));
112  curr_loc_.second = title_spacing_;
114  down_one_line();
115  }
116  // Parse and add the text.
117  std::vector<std::string> const &parsed_items = shown_topic_->text.parsed_text();
118  std::vector<std::string>::const_iterator it;
119  for (it = parsed_items.begin(); it != parsed_items.end(); ++it) {
120  if (*it != "" && (*it)[0] == '[') {
121  // Should be parsed as WML.
122  try {
123  config cfg;
124  std::istringstream stream(*it);
125  read(cfg, stream);
126 
127 #define TRY(name) do { \
128  if (config &child = cfg.child(#name)) \
129  handle_##name##_cfg(child); \
130  } while (0)
131 
132  TRY(ref);
133  TRY(img);
134  TRY(bold);
135  TRY(italic);
136  TRY(header);
137  TRY(jump);
138  TRY(format);
139 
140 #undef TRY
141 
142  }
143  catch (config::error& e) {
144  std::stringstream msg;
145  msg << "Error when parsing help markup as WML: '" << e.message << "'";
146  throw parse_error(msg.str());
147  }
148  }
149  else {
150  add_text_item(*it);
151  }
152  }
153  down_one_line(); // End the last line.
154  int h = height();
155  set_position(0);
157  set_shown_size(h);
158 }
159 
161 {
162  const std::string dst = cfg["dst"];
163  const std::string text = cfg["text"];
164  bool force = cfg["force"].to_bool();
165 
166  if (dst == "") {
167  std::stringstream msg;
168  msg << "Ref markup must have dst attribute. Please submit a bug"
169  " report if you have not modified the game files yourself. Erroneous config: ";
170  write(msg, cfg);
171  throw parse_error(msg.str());
172  }
173 
174  if (find_topic(toplevel_, dst) == nullptr && !force) {
175  // detect the broken link but quietly silence the hyperlink for normal user
176  add_text_item(text, game_config::debug ? dst : "", true);
177 
178  // FIXME: workaround: if different campaigns define different
179  // terrains, some terrains available in one campaign will
180  // appear in the list of seen terrains, and be displayed in the
181  // help, even if the current campaign does not handle such
182  // terrains. This will lead to the unit page generator creating
183  // invalid references.
184  //
185  // Disabling this is a kludgey workaround until the
186  // encountered_terrains system is fixed
187  //
188  // -- Ayin apr 8 2005
189 #if 0
190  if (game_config::debug) {
191  std::stringstream msg;
192  msg << "Reference to non-existent topic '" << dst
193  << "'. Please submit a bug report if you have not"
194  "modified the game files yourself. Erroneous config: ";
195  write(msg, cfg);
196  throw parse_error(msg.str());
197  }
198 #endif
199  } else {
200  add_text_item(text, dst);
201  }
202 }
203 
205 {
206  const std::string src = cfg["src"];
207  const std::string align = cfg["align"];
208  bool floating = cfg["float"].to_bool();
209  bool box = cfg["box"].to_bool(true);
210  if (src == "") {
211  throw parse_error("Img markup must have src attribute.");
212  }
213  add_img_item(src, align, floating, box);
214 }
215 
217 {
218  const std::string text = cfg["text"];
219  if (text == "") {
220  throw parse_error("Bold markup must have text attribute.");
221  }
222  add_text_item(text, "", false, -1, true);
223 }
224 
226 {
227  const std::string text = cfg["text"];
228  if (text == "") {
229  throw parse_error("Italic markup must have text attribute.");
230  }
231  add_text_item(text, "", false, -1, false, true);
232 }
233 
235 {
236  const std::string text = cfg["text"];
237  if (text == "") {
238  throw parse_error("Header markup must have text attribute.");
239  }
240  add_text_item(text, "", false, title2_size, true);
241 }
242 
244 {
245  const std::string amount_str = cfg["amount"];
246  const std::string to_str = cfg["to"];
247  if (amount_str == "" && to_str == "") {
248  throw parse_error("Jump markup must have either a to or an amount attribute.");
249  }
250  unsigned jump_to = curr_loc_.first;
251  if (amount_str != "") {
252  unsigned amount;
253  try {
254  amount = lexical_cast<unsigned, std::string>(amount_str);
255  }
256  catch (bad_lexical_cast) {
257  throw parse_error("Invalid amount the amount attribute in jump markup.");
258  }
259  jump_to += amount;
260  }
261  if (to_str != "") {
262  unsigned to;
263  try {
264  to = lexical_cast<unsigned, std::string>(to_str);
265  }
266  catch (bad_lexical_cast) {
267  throw parse_error("Invalid amount in the to attribute in jump markup.");
268  }
269  if (to < jump_to) {
270  down_one_line();
271  }
272  jump_to = to;
273  }
274  if (jump_to != 0 && static_cast<int>(jump_to) <
276 
277  curr_loc_.first = jump_to;
278  }
279 }
280 
282 {
283  const std::string text = cfg["text"];
284  if (text == "") {
285  throw parse_error("Format markup must have text attribute.");
286  }
287  bool bold = cfg["bold"].to_bool();
288  bool italic = cfg["italic"].to_bool();
289  int font_size = cfg["font_size"].to_int(normal_font_size);
290  SDL_Color color = help::string_to_color(cfg["color"]);
291  add_text_item(text, "", false, font_size, bold, italic, color);
292 }
293 
294 void help_text_area::add_text_item(const std::string& text, const std::string& ref_dst,
295  bool broken_link, int _font_size, bool bold, bool italic,
296  SDL_Color text_color
297 )
298 {
299  const int font_size = _font_size < 0 ? normal_font_size : _font_size;
300  if (text.empty())
301  return;
302  const int remaining_width = get_remaining_width();
303  size_t first_word_start = text.find_first_not_of(" ");
304  if (first_word_start == std::string::npos) {
305  first_word_start = 0;
306  }
307  if (text[first_word_start] == '\n') {
308  down_one_line();
309  std::string rest_text = text;
310  rest_text.erase(0, first_word_start + 1);
311  add_text_item(rest_text, ref_dst, broken_link, _font_size, bold, italic, text_color);
312  return;
313  }
314  const std::string first_word = get_first_word(text);
315  int state = 0;
316  state |= bold ? TTF_STYLE_BOLD : 0;
317  state |= italic ? TTF_STYLE_ITALIC : 0;
318  if (curr_loc_.first != get_min_x(curr_loc_.second, curr_row_height_)
319  && remaining_width < font::line_width(first_word, font_size, state)) {
320  // The first word does not fit, and we are not at the start of
321  // the line. Move down.
322  down_one_line();
324  add_text_item(s, ref_dst, broken_link, _font_size, bold, italic, text_color);
325  }
326  else {
327  std::vector<std::string> parts = split_in_width(text, font_size, remaining_width);
328  std::string first_part = parts.front();
329  // Always override the color if we have a cross reference.
330  SDL_Color color;
331  if(ref_dst.empty())
332  color = text_color;
333  else if(broken_link)
334  color = font::BAD_COLOR;
335  else
336  color = font::YELLOW_COLOR;
337 
338  surface surf(font::get_rendered_text(first_part, font_size, color, state));
339  if (!surf.null())
340  add_item(item(surf, curr_loc_.first, curr_loc_.second, first_part, ref_dst));
341  if (parts.size() > 1) {
342 
343  std::string& s = parts.back();
344 
345  const std::string first_word_before = get_first_word(s);
346  const std::string first_word_after = get_first_word(remove_first_space(s));
347  if (get_remaining_width() >= font::line_width(first_word_after, font_size, state)
349  < font::line_width(first_word_before, font_size, state)) {
350  // If the removal of the space made this word fit, we
351  // must move down a line, otherwise it will be drawn
352  // without a space at the end of the line.
353  s = remove_first_space(s);
354  down_one_line();
355  }
356  else if (!(font::line_width(first_word_before, font_size, state)
357  < get_remaining_width())) {
358  s = remove_first_space(s);
359  }
360  add_text_item(s, ref_dst, broken_link, _font_size, bold, italic, text_color);
361 
362  }
363  }
364 }
365 
367  const bool floating, const bool box)
368 {
370  if (surf.null())
371  return;
372  ALIGNMENT align = str_to_align(alignment);
373  if (align == HERE && floating) {
374  WRN_DP << "Floating image with align HERE, aligning left." << std::endl;
375  align = LEFT;
376  }
377  const int width = surf->w + (box ? box_width * 2 : 0);
378  int xpos;
379  int ypos = curr_loc_.second;
380  int text_width = inner_location().w;
381  switch (align) {
382  case HERE:
383  xpos = curr_loc_.first;
384  break;
385  case LEFT:
386  default:
387  xpos = 0;
388  break;
389  case MIDDLE:
390  xpos = text_width / 2 - width / 2 - (box ? box_width : 0);
391  break;
392  case RIGHT:
393  xpos = text_width - width - (box ? box_width * 2 : 0);
394  break;
395  }
396  if (curr_loc_.first != get_min_x(curr_loc_.second, curr_row_height_)
397  && (xpos < curr_loc_.first || xpos + width > text_width)) {
398  down_one_line();
399  add_img_item(path, alignment, floating, box);
400  }
401  else {
402  if (!floating) {
403  curr_loc_.first = xpos;
404  }
405  else {
406  ypos = get_y_for_floating_img(width, xpos, ypos);
407  }
408  add_item(item(surf, xpos, ypos, floating, box, align));
409  }
410 }
411 
412 int help_text_area::get_y_for_floating_img(const int width, const int x, const int desired_y)
413 {
414  int min_y = desired_y;
415  for (std::list<item>::const_iterator it = items_.begin(); it != items_.end(); ++it) {
416  const item& itm = *it;
417  if (itm.floating) {
418  if ((itm.rect.x + itm.rect.w > x && itm.rect.x < x + width)
419  || (itm.rect.x > x && itm.rect.x < x + width)) {
420  min_y = std::max<int>(min_y, itm.rect.y + itm.rect.h);
421  }
422  }
423  }
424  return min_y;
425 }
426 
427 int help_text_area::get_min_x(const int y, const int height)
428 {
429  int min_x = 0;
430  for (std::list<item>::const_iterator it = items_.begin(); it != items_.end(); ++it) {
431  const item& itm = *it;
432  if (itm.floating) {
433  if (itm.rect.y < y + height && itm.rect.y + itm.rect.h > y && itm.align == LEFT) {
434  min_x = std::max<int>(min_x, itm.rect.w + 5);
435  }
436  }
437  }
438  return min_x;
439 }
440 
441 int help_text_area::get_max_x(const int y, const int height)
442 {
443  int text_width = inner_location().w;
444  int max_x = text_width;
445  for (std::list<item>::const_iterator it = items_.begin(); it != items_.end(); ++it) {
446  const item& itm = *it;
447  if (itm.floating) {
448  if (itm.rect.y < y + height && itm.rect.y + itm.rect.h > y) {
449  if (itm.align == RIGHT) {
450  max_x = std::min<int>(max_x, text_width - itm.rect.w - 5);
451  } else if (itm.align == MIDDLE) {
452  max_x = std::min<int>(max_x, text_width / 2 - itm.rect.w / 2 - 5);
453  }
454  }
455  }
456  }
457  return max_x;
458 }
459 
461 {
462  items_.push_back(itm);
463  if (!itm.floating) {
464  curr_loc_.first += itm.rect.w;
465  curr_row_height_ = std::max<int>(itm.rect.h, curr_row_height_);
466  contents_height_ = std::max<int>(contents_height_, curr_loc_.second + curr_row_height_);
467  last_row_.push_back(&items_.back());
468  }
469  else {
470  if (itm.align == LEFT) {
471  curr_loc_.first = itm.rect.w + 5;
472  }
473  contents_height_ = std::max<int>(contents_height_, itm.rect.y + itm.rect.h);
474  }
475 }
476 
477 
479 {
480  if (cmp_str == "left") {
481  return LEFT;
482  } else if (cmp_str == "middle") {
483  return MIDDLE;
484  } else if (cmp_str == "right") {
485  return RIGHT;
486  } else if (cmp_str == "here" || cmp_str == "") { // Make the empty string be "here" alignment.
487  return HERE;
488  }
489  std::stringstream msg;
490  msg << "Invalid alignment string: '" << cmp_str << "'";
491  throw parse_error(msg.str());
492 }
493 
495 {
496  adjust_last_row();
497  last_row_.clear();
499  curr_row_height_ = min_row_height_;
500  contents_height_ = std::max<int>(curr_loc_.second + curr_row_height_, contents_height_);
501  curr_loc_.first = get_min_x(curr_loc_.second, curr_row_height_);
502 }
503 
505 {
506  for (std::list<item *>::iterator it = last_row_.begin(); it != last_row_.end(); ++it) {
507  item &itm = *(*it);
508  const int gap = curr_row_height_ - itm.rect.h;
509  itm.rect.y += gap / 2;
510  }
511 }
512 
514 {
515  const int total_w = get_max_x(curr_loc_.second, curr_row_height_);
516  return total_w - curr_loc_.first;
517 }
518 
520 {
521  SDL_Rect const &loc = inner_location();
522  bg_restore();
524  clip_rect_setter clip_rect_set(screen, &loc);
525  for(std::list<item>::const_iterator it = items_.begin(), end = items_.end(); it != end; ++it) {
526  SDL_Rect dst = it->rect;
527  dst.y -= get_position();
528  if (dst.y < static_cast<int>(loc.h) && dst.y + it->rect.h > 0) {
529  dst.x += loc.x;
530  dst.y += loc.y;
531  if (it->box) {
532  for (int i = 0; i < box_width; ++i) {
533  sdl::draw_rectangle(dst.x, dst.y, it->rect.w - i * 2, it->rect.h - i * 2,
534  0, screen);
535  ++dst.x;
536  ++dst.y;
537  }
538  }
539  sdl_blit(it->surf, nullptr, screen, &dst);
540  }
541  }
542  update_rect(loc);
543 }
544 
545 void help_text_area::scroll(unsigned int)
546 {
547  // Nothing will be done on the actual scroll event. The scroll
548  // position is checked when drawing instead and things drawn
549  // accordingly.
550  set_dirty(true);
551 }
552 
554  return sdl::point_in_rect(x_, y_, item.rect);
555 }
556 
557 std::string help_text_area::ref_at(const int x, const int y)
558 {
559  const int local_x = x - location().x;
560  const int local_y = y - location().y;
561  if (local_y < static_cast<int>(height()) && local_y > 0) {
562  const int cmp_y = local_y + get_position();
563  const std::list<item>::const_iterator it =
564  std::find_if(items_.begin(), items_.end(), item_at(local_x, cmp_y));
565  if (it != items_.end()) {
566  if ((*it).ref_to != "") {
567  return ((*it).ref_to);
568  }
569  }
570  }
571  return "";
572 }
573 
574 } // end namespace help
std::string jump_to(const unsigned pos)
Definition: help_impl.hpp:381
int get_max_x(const int y, const int height=0)
Analogous with get_min_x but return the maximum X.
surface get_image(const image::locator &i_locator, TYPE type)
function to get the surface corresponding to an image.
Definition: image.cpp:878
tformula< unsigned > x_
The x coordinate of the rectangle.
Definition: canvas.cpp:682
bool null() const
Definition: utils.hpp:104
help_text_area(CVideo &video, const section &toplevel)
void set_shown_size(unsigned h)
Definition: scrollarea.cpp:110
virtual void set_inner_location(const SDL_Rect &rect)
const int title_size
Definition: help_impl.cpp:77
const std::vector< std::string > & parsed_text() const
Definition: help_impl.cpp:346
Graphical text output.
void add_img_item(const std::string &path, const std::string &alignment, const bool floating, const bool box)
Add an image item with the specified attributes.
std::string remove_first_space(const std::string &text)
Definition: help_impl.cpp:1249
A section contains topics and sections along with title and ID.
Definition: help_impl.hpp:143
int get_remaining_width()
Return the width that remain on the line the current input point is at.
int get_y_for_floating_img(const int width, const int x, const int desired_y)
Find the lowest y coordinate where a floating img of the specified width and at the specified x coord...
Definition: video.hpp:58
game_display * screen
Definition: resources.cpp:27
void bg_register(SDL_Rect const &rect)
Definition: widget.cpp:109
help::section toplevel
Definition: help_impl.cpp:66
Thrown when the help system fails to parse something.
Definition: help_impl.hpp:221
CVideo & video() const
Definition: widget.hpp:83
General purpose widgets.
std::list< item * > last_row_
void set_scroll_rate(unsigned r)
Definition: scrollarea.cpp:124
GLint GLint GLint GLint GLint GLint y
Definition: glew.h:1220
GLenum src
Definition: glew.h:2392
const int normal_font_size
Definition: help_impl.cpp:80
void add_text_item(const std::string &text, const std::string &ref_dst="", bool broken_link=false, int font_size=-1, bool bold=false, bool italic=false, SDL_Color color=font::NORMAL_COLOR)
Add an item with text.
void set_items()
Update the vector with the items of the shown topic, creating surfaces for everything and putting thi...
To lexical_cast(From value)
Lexical cast converts one type to another.
const SDL_Color NORMAL_COLOR
Definition: font.cpp:564
#define TRY(name)
GLdouble GLdouble t
Definition: glew.h:1366
-file util.hpp
Definitions for the interface to Wesnoth Markup Language (WML).
surface & getSurface()
Definition: dummy_video.cpp:22
std::string bold(const std::string &s)
Definition: help_impl.hpp:395
topic const * shown_topic_
GLuint GLuint stream
Definition: glew.h:5239
void set_full_size(unsigned h)
Definition: scrollarea.cpp:117
void set_dirty(bool dirty=true)
Definition: widget.cpp:217
GLsizei const char ** path
Definition: glew.h:4654
GLuint GLuint end
Definition: glew.h:1221
void set_position(unsigned pos)
Definition: scrollarea.cpp:95
SDL_Rect inner_location() const
Definition: scrollarea.cpp:138
const SDL_Color BAD_COLOR
Definition: font.cpp:568
void add_item(const item &itm)
Add an item to the internal list, update the locations and row height.
std::string ref_at(const int x, const int y)
Return the ID that is cross-referenced at the (screen) coordinates x, y.
GLubyte GLubyte GLubyte GLubyte w
Definition: glew.h:1858
GLenum GLenum dst
Definition: glew.h:2392
virtual void scroll(unsigned int pos)
std::list< item > items_
const section & toplevel_
void handle_ref_cfg(const config &cfg)
const unsigned min_row_height_
Templates and utility-routines for strings and numbers.
surf
Definition: filter.cpp:143
void handle_img_cfg(const config &cfg)
GLuint color
Definition: glew.h:5801
int get_max_height(int size)
Definition: font.cpp:960
#define WRN_DP
const std::string &parameters float amount
Definition: filter.cpp:132
bool point_in_rect(int x, int y, const SDL_Rect &rect)
Tests whether a point is inside a rectangle.
Definition: rect.cpp:47
void handle_header_cfg(const config &cfg)
An item that is displayed in the text area.
const int box_width
Definition: help_impl.cpp:79
void handle_italic_cfg(const config &cfg)
void handle_bold_cfg(const config &cfg)
unsigned get_position() const
Definition: scrollarea.cpp:85
void show_topic(const topic &t)
Display the topic.
void adjust_last_row()
Adjust the heights of the items in the last row to make it look good .
GLint GLint GLsizei GLsizei GLsizei GLint GLenum format
Definition: glew.h:1222
std::pair< int, int > curr_loc_
item(surface surface, int x, int y, const std::string &text="", const std::string &reference_to="", bool floating=false, bool box=false, ALIGNMENT alignment=HERE)
GLfloat GLfloat GLfloat GLfloat h
Definition: glew.h:5910
size_t i
Definition: function.cpp:1057
static void msg(const char *act, debug_info &i, const char *to="", const char *result="")
Definition: debugger.cpp:112
GLint GLint GLint GLint GLint x
Definition: glew.h:1220
tformula< unsigned > y_
The y coordinate of the rectangle.
Definition: canvas.cpp:682
void read(config &cfg, std::istream &in, abstract_validator *validator)
Definition: parser.cpp:400
std::vector< expression_ptr > items_
Definition: formula.cpp:119
int get_min_x(const int y, const int height=0)
Return the least x coordinate at which something of the specified height can be drawn at the specifie...
void down_one_line()
Move the current input point to the next line.
GLint GLint GLint GLint GLint GLint GLsizei GLsizei height
Definition: glew.h:1220
std::string make_text_ellipsis(const std::string &text, int font_size, int max_width, int style)
If the text exceeds the specified max width, end it with an ellipsis (...)
Definition: font.cpp:996
std::string jump(const unsigned amount)
Definition: help_impl.hpp:388
Contains the SDL_Rect helper code.
void bg_restore() const
Definition: widget.cpp:251
GLenum GLint ref
Definition: glew.h:1813
void handle_format_cfg(const config &cfg)
const topic * find_topic(const section &sec, const std::string &id)
Search for the topic with the specified identifier in the section and its subsections.
Definition: help_impl.cpp:1049
GLint GLvoid * img
Definition: glew.h:1353
Standard logging facilities (interface).
bool operator()(const item &) const
std::string message
Definition: exceptions.hpp:29
const int title2_size
Definition: help_impl.cpp:78
A topic contains a title, an id and some text.
Definition: help_impl.hpp:111
ALIGNMENT str_to_align(const std::string &s)
Convert a string to an alignment.
GLint GLint GLint GLint GLint GLint GLsizei width
Definition: glew.h:1220
#define e
Definition: help.cpp:57
int width() const
Definition: widget.cpp:134
SDL_Rect rect
Relative coordinates of this item.
SDL_Color string_to_color(const std::string &cmp_str)
Return the color the string represents.
Definition: help_impl.cpp:1206
const SDL_Color YELLOW_COLOR
Definition: font.cpp:570
SDL_Rect const & location() const
Definition: widget.cpp:144
std::string title
Definition: help_impl.hpp:136
void sdl_blit(const surface &src, SDL_Rect *src_rect, surface &dst, SDL_Rect *dst_rect)
Definition: utils.hpp:112
std::string::const_iterator iterator
Definition: tokenizer.hpp:21
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:83
surface get_rendered_text(const std::string &str, int size, const SDL_Color &color, int style)
Definition: font.cpp:886
static lg::log_domain log_display("display")
GLdouble s
Definition: glew.h:1358
std::string get_first_word(const std::string &s)
Return the first word in s, not removing any spaces in the start of it.
Definition: help_impl.cpp:1257
const int font_size
void update_rect(const SDL_Rect &)
Definition: dummy_video.cpp:27
int contents_height_
The height of all items in total.
void write(std::ostream &out, configr_of const &cfg, unsigned int level)
Definition: parser.cpp:621
Thrown when a lexical_cast fails.
GLsizei const GLcharARB ** string
Definition: glew.h:4503
int line_width(const std::string &line, int font_size, int style)
Determine the width of a line of text given a certain font size.
Definition: font.cpp:969
void draw_rectangle(int x, int y, int w, int h, Uint32 color, surface target)
Draw a colored rectangle on a surface.
Definition: rect.cpp:103
void handle_jump_cfg(const config &cfg)
std::vector< std::string > split_in_width(const std::string &s, const int font_size, const unsigned width)
Make a best effort to word wrap s. All parts are less than width.
Definition: help_impl.cpp:1230
topic_text text
Definition: help_impl.hpp:137
int height() const
Definition: widget.cpp:139
Function object to find an item at the specified coordinates.