World of Might and Magic  0.2.0
Open reimplementation of Might and Magic 6 7 8 game engine
GUIFont.cpp
См. документацию.
1 #include "GUI/GUIFont.h"
2 
3 #include <cstdarg>
4 
5 #include <sstream>
6 
7 #include "Engine/Engine.h"
8 #include "Engine/LOD.h"
9 
11 
12 #include "GUI/GUIWindow.h"
13 
15 
17 GUIFont *pSpellFont = nullptr;
18 GUIFont *pFontArrus = nullptr;
19 GUIFont *pFontLucida = nullptr;
20 GUIFont *pBook2Font = nullptr;
21 GUIFont *pBookFont = nullptr;
22 GUIFont *pFontCreate = nullptr;
23 GUIFont *pFontCChar = nullptr;
24 GUIFont *pFontComic = nullptr;
26 
27 char temp_string[2048];
28 
29 std::array<char, 10000> pTmpBuf3;
30 
31 #pragma pack(push, 1)
32 struct GUICharMetric {
36 };
37 #pragma pack(pop)
38 
39 #pragma pack(push, 1)
40 struct FontData {
52  uint8_t pFontData[0]; // array of font pixels
53 };
54 #pragma pack(pop)
55 
56 GUIFont *GUIFont::LoadFont(const char *pFontFile, const char *pFontPalette, ...) {
57  // static_assert(sizeof(GUICharMetric) == 12, "Wrong GUICharMetric type size");
58  // static_assert(sizeof(FontData) == 4128, "Wrong FontData type size");
59 
60  unsigned int palletes_count = 0;
61  va_list palettes_ptr;
62 
63  GUIFont *pFont = new GUIFont;
64  pFont->pData = (FontData*)pIcons_LOD->LoadCompressedTexture(pFontFile);
65  va_start(palettes_ptr, pFontFile);
66 
67  while (NULL != (pFontPalette = va_arg(palettes_ptr, const char *))) {
68  int pallete_index = pIcons_LOD->LoadTexture(pFontPalette, TEXTURE_24BIT_PALETTE);
69  if (pallete_index == -1)
70  Error("Unable to open %s", pFontPalette);
71 
72  pFont->pData->pFontPalettes[palletes_count] = pIcons_LOD->pTextures[pallete_index].pPalette24;
73  ++palletes_count;
74  }
75  va_end(palettes_ptr);
76  pFont->pData->palletes_count = palletes_count;
77  return pFont;
78 }
79 
80 bool GUIFont::IsCharValid(unsigned char c) const {
81  return (c >= pData->cFirstChar) && (c <= pData->cLastChar) || (c == '\f') || (c == '\r') || (c == '\t') || (c == '\n');
82 }
83 
84 unsigned int GUIFont::GetHeight() const {
85  return pData->uFontHeight;
86 }
87 
88 void GUIFont::DrawTextLine(const String &text, uint16_t uDefaultColor, int uX, int uY, int max_len_pix) {
89  if (text.empty()) {
90  return;
91  }
92 
93  uint16_t text_color = ui_current_text_color;
94  size_t text_length = text.size();
95  int uX_pos = uX;
96  for (int i = 0; i < text_length; ++i) {
97  unsigned char c = text[i];
98  if (IsCharValid(c)) {
99  switch (c) {
100  case '\n': // Line Feed 0A 10:
101  return;
102  break;
103  case '\f': { // Form Feed, page eject 0C 12
104  char color_code[20];
105  strncpy(color_code, &text[i + 1], 5);
106  color_code[5] = 0;
107  text_color = atoi(color_code);
108  ui_current_text_color = text_color;
109  i += 5;
110  break;
111  }
112  case '\t': // Horizontal tab 09
113  case '\r': // Carriage Return 0D 13
114  break;
115  default:
116  int uCharWidth = pData->pMetrics[c].uWidth;
117  if (uCharWidth) {
118  if (i > 0) {
119  uX_pos += pData->pMetrics[c].uLeftSpacing;
120  }
121  uint16_t draw_color = text_color;
122  uint8_t *pCharPixels = &pData->pFontData[pData->font_pixels_offset[c]];
123  if (!text_color) {
124  draw_color = -1;
125  }
126  render->DrawText(uX_pos, uY, pCharPixels, uCharWidth, pData->uFontHeight,
127  pData->pFontPalettes[0], draw_color, 0);
128  uX_pos += uCharWidth;
129  if (i < text_length) {
130  uX_pos += pData->pMetrics[c].uRightSpacing;
131  }
132  }
133  }
134  }
135  }
136 }
137 
138 void DrawCharToBuff(uint32_t *draw_buff, uint8_t *pCharPixels, int uCharWidth, int uCharHeight,
139  uint8_t *pFontPalette, uint16_t draw_color, int line_width) {
140  uint8_t *pPixels = pCharPixels;
141  for (int y = 0; y < uCharHeight; ++y) {
142  for (int x = 0; x < uCharWidth; ++x) {
143  uint8_t char_pxl = *pPixels++;
144  if (char_pxl) {
145  if (char_pxl == 1) {
146  uint8_t r = pFontPalette[3];
147  uint8_t g = pFontPalette[4];
148  uint8_t b = pFontPalette[5];
149  *draw_buff = Color32(r, g, b);
150  } else {
151  *draw_buff = Color32(draw_color);
152  }
153  }
154  ++draw_buff;
155  }
156  draw_buff += line_width - uCharWidth;
157  }
158 }
159 
160 void GUIFont::DrawTextLineToBuff(uint16_t uColor, uint32_t *uX_buff_pos, const String &text, int line_width) {
161  if (text.empty()) {
162  return;
163  }
164 
165  char color_code[20];
166 
167  uint16_t text_color = ui_current_text_color;
168  size_t text_length = text.length();
169  uint32_t *uX_pos = uX_buff_pos;
170  for (size_t i = 0; i < text_length; ++i) {
171  uint8_t c = text[i];
172  if (IsCharValid(c)) {
173  switch (c) {
174  case '\n': // Line Feed 0A 10:
175  return;
176  break;
177  case '\f': // Form Feed, page eject 0C 12
178  strncpy(color_code, &text[i + 1], 5);
179  color_code[5] = 0;
180  text_color = atoi(color_code);
181  ui_current_text_color = text_color;
182  i += 5;
183  break;
184  case '\t': // Horizontal tab 09
185  case '_':
186  break;
187  default:
188  {
189  int uCharWidth = pData->pMetrics[c].uWidth;
190  if (uCharWidth) {
191  if (i > 0) {
192  uX_pos += pData->pMetrics[c].uLeftSpacing;
193  }
194  uint16_t draw_color = text_color;
195  uint8_t *pCharPixels = &pData->pFontData[pData->font_pixels_offset[c]];
196  if (!text_color) {
197  draw_color = -1;
198  }
199  DrawCharToBuff(uX_pos, pCharPixels, uCharWidth, pData->uFontHeight, pData->pFontPalettes[0], draw_color, line_width);
200  uX_pos += uCharWidth;
201  if (i < text_length) {
202  uX_pos += pData->pMetrics[c].uRightSpacing;
203  }
204  }
205  }
206  }
207  }
208  }
209 }
210 
211 String GUIFont::GetPageTop(const String &pInString, GUIWindow *pWindow, unsigned int uX, int a5) {
212  if (pInString.empty()) {
213  return "";
214  }
215 
216  int text_height = 0;
217 
218  String text_str = FitTextInAWindow(pInString, pWindow->uFrameWidth, uX);
219  int text_length = text_str.length();
220  for (int i = 0; i < text_length; ++i) {
221  unsigned char c = text_str[i];
222  if (IsCharValid(c)) {
223  switch (c) {
224  case '\n': // Line Feed 0A 10
225  text_height += (pData->uFontHeight - 3);
226  if (text_height >= (int)(a5 * (pWindow->uFrameHeight - (pData->uFontHeight - 3)))) {
227  return &text_str[i];
228  }
229  break;
230  case '\f': // Form Feed, page eject 0C 12
231  i += 5;
232  break;
233  case '\t': // Horizontal tab 09
234  case '\r': // Carriage Return 0D 13
235  i += 3;
236  break;
237  }
238  if (text_height >= (int)(a5 * pWindow->uFrameHeight)) {
239  break;
240  }
241  }
242  }
243  return text_str;
244 }
245 
246 unsigned int GUIFont::CalcTextHeight(const String &pString, unsigned int width,
247  int uXOffset, bool return_on_carriage) {
248  if (pString.empty()) {
249  return 0;
250  }
251 
252  unsigned int uAllHeght = pData->uFontHeight - 6;
253  String test_string = FitTextInAWindow(pString, width, uXOffset);
254  size_t uStringLen = pString.length();
255  for (int i = 0; i < uStringLen; ++i) {
256  unsigned char c = test_string[i];
257  if (IsCharValid(c)) {
258  switch (c) {
259  case '\n': // Line Feed 0A 10
260  uAllHeght += pData->uFontHeight - 3;
261  break;
262  case '\f': // Form Feed, page eject 0C 12
263  i += 5;
264  break;
265  case '\t': // Horizontal tab 09
266  case '\r': // Carriage Return 0D 13
267  if (!return_on_carriage) {
268  i += 3;
269  }
270  break;
271  }
272  }
273  }
274 
275  return uAllHeght;
276 }
277 
278 unsigned int GUIFont::GetLineWidth(const String &inString) {
279  size_t str_len = inString.length();
280  unsigned int string_line_width = 0;
281  for (int i = 0; i < str_len; ++i) {
282  unsigned char c = inString[i];
283  if (IsCharValid(c)) {
284  switch (c) {
285  case '\t':
286  case '\n':
287  case '\r':
288  return string_line_width;
289  case '\f':
290  i += 5;
291  break;
292  default:
293  if (i > 0) {
294  string_line_width += pData->pMetrics[c].uLeftSpacing;
295  }
296  string_line_width += pData->pMetrics[c].uWidth;
297  if (i < str_len) {
298  string_line_width += pData->pMetrics[c].uRightSpacing;
299  }
300  }
301  }
302  }
303  return string_line_width;
304 }
305 
306 unsigned int GUIFont::AlignText_Center(unsigned int width, const String &pString) {
307  int position = ((int)width - (int)GetLineWidth(pString)) / 2;
308  return (position < 0) ? 0 : position;
309 }
310 
311 String GUIFont::FitTextInAWindow(const String &inString, unsigned int width, int uX, bool return_on_carriage) {
312  size_t uInStrLen = inString.length();
313  strcpy(temp_string, inString.c_str());
314  if (uInStrLen == 0) {
315  return &temp_string[0];
316  }
317 
318  int start_pixel_offset = uX;
319  int string_pixel_Width = uX;
320  int possible_transition_point = 0;
321  for (int i = 0; i < uInStrLen; ++i) {
322  unsigned char c = temp_string[i];
323  if (IsCharValid(c)) {
324  switch (c) {
325  case '\t':
326  { // Horizontal tab 09
327  char digits[4];
328  strncpy(digits, &temp_string[i + 1], 3);
329  digits[3] = 0;
330  string_pixel_Width = atoi(digits) + uX;
331  i += 3;
332  break;
333  }
334  case '\n':
335  { // Line Feed 0A 10 (êîíåö ñòðîêè)
336  string_pixel_Width = start_pixel_offset;
337  possible_transition_point = i;
338  break;
339  }
340  case '\f':
341  { // Form Feed, page eject 0C 12
342  i += 5;
343  break;
344  }
345  case '\r':
346  { // Carriage Return 0D 13
347  if (!return_on_carriage) {
348  return inString;
349  }
350  break;
351  }
352  case ' ':
353  { // Space
354  string_pixel_Width += pData->pMetrics[c].uWidth;
355  possible_transition_point = i;
356  break;
357  }
358  default:
359  if ((string_pixel_Width + pData->pMetrics[c].uWidth + pData->pMetrics[c].uLeftSpacing +
360  pData->pMetrics[c].uRightSpacing) < width) { // íàðàùèâàíèå äëèíû ñòðîêè èëè ïåðåíîñ
361  if (i > possible_transition_point)
362  string_pixel_Width += pData->pMetrics[c].uLeftSpacing;
363  string_pixel_Width += pData->pMetrics[c].uWidth;
364  if (i < uInStrLen)
365  string_pixel_Width += pData->pMetrics[c].uRightSpacing;
366  } else { // ïåðåíîñ ñòðîêè è ñëîâà
367  temp_string[possible_transition_point] = '\n';
368  string_pixel_Width = start_pixel_offset;
369  if (i > possible_transition_point) {
370  for (int j = possible_transition_point; j < i; ++j) {
371  c = temp_string[j];
372  if (IsCharValid(c)) {
373  if (j > possible_transition_point)
374  string_pixel_Width += pData->pMetrics[c].uLeftSpacing;
375  string_pixel_Width += pData->pMetrics[c].uWidth;
376  if (j < i)
377  string_pixel_Width += pData->pMetrics[c].uRightSpacing;
378  }
379  }
380  }
381  }
382  }
383  }
384  }
385  return temp_string;
386 }
387 
388 void GUIFont::DrawText(GUIWindow *pWindow, int uX, int uY, uint16_t uFontColor, const String &str,
389  bool present_time_transparency, int max_text_height, int uFontShadowColor) {
390  int left_margin = 0;
391  if (str.empty()) {
392  return;
393  }
394  if (str == "null") {
395  return;
396  }
397 
398  size_t v30 = str.length();
399  if (!uX) {
400  uX = 12;
401  }
402 
403  String string_begin = str;
404  if (max_text_height == 0) {
405  string_begin = FitTextInAWindow(str, pWindow->uFrameWidth, uX);
406  }
407  auto string_end = string_begin;
408  auto string_base = string_begin;
409 
410  int out_x = uX + pWindow->uFrameX;
411  int out_y = uY + pWindow->uFrameY;
412 
413  if (max_text_height != 0 && out_y + pData->uFontHeight > max_text_height) {
414  return;
415  }
416 
417  char Dest[6] = { 0 };
418  size_t v14 = 0;
419  if (v30 > 0) {
420  do {
421  uint8_t c = string_base[v14];
422  if (c >= pData->cFirstChar && c <= pData->cLastChar
423  || c == '\f'
424  || c == '\r'
425  || c == '\t'
426  || c == '\n') {
427  switch (c) {
428  case '\t':
429  strncpy(Dest, &string_base[v14 + 1], 3);
430  Dest[3] = 0;
431  v14 += 3;
432  left_margin = atoi(Dest);
433  out_x = uX + pWindow->uFrameX + left_margin;
434  break;
435  case '\n':
436  uY = uY + pData->uFontHeight - 3;
437  out_y = uY + pWindow->uFrameY;
438  out_x = uX + pWindow->uFrameX + left_margin;
439  if (max_text_height != 0) {
440  if (pData->uFontHeight + out_y - 3 > max_text_height) {
441  return;
442  }
443  }
444  break;
445  case '\f':
446  strncpy(Dest, &string_base[v14 + 1], 5);
447  Dest[5] = 0;
448  uFontColor = atoi(Dest);
449  v14 += 5;
450  break;
451  case '\r':
452  strncpy(Dest, &string_base[v14 + 1], 3);
453  Dest[3] = 0;
454  v14 += 3;
455  left_margin = atoi(Dest);
456  out_x = pWindow->uFrameZ - this->GetLineWidth(&string_base[v14]) - left_margin;
457  out_y = uY + pWindow->uFrameY;
458  if (max_text_height != 0) {
459  if (pData->uFontHeight + out_y - 3 > max_text_height) {
460  return;
461  }
462  break;
463  }
464  break;
465 
466  default:
467  if (c == '\"' && string_base[v14 + 1] == '\"') {
468  ++v14;
469  }
470 
471  c = (uint8_t)string_base[v14];
472  if (v14 > 0) {
473  out_x += pData->pMetrics[c].uLeftSpacing;
474  }
475 
476  unsigned char *letter_pixels = &pData->pFontData[pData->font_pixels_offset[c]];
477  if (uFontColor) {
478  render->DrawText(out_x, out_y, letter_pixels, pData->pMetrics[c].uWidth, pData->uFontHeight,
479  pData->pFontPalettes[0], uFontColor, uFontShadowColor);
480  } else {
481  render->DrawTextAlpha(out_x, out_y, letter_pixels, pData->pMetrics[c].uWidth, pData->uFontHeight,
482  pData->pFontPalettes[0], present_time_transparency);
483  }
484 
485  out_x += pData->pMetrics[c].uWidth;
486  if (v14 < v30) {
487  out_x += pData->pMetrics[c].uRightSpacing;
488  }
489  break;
490  }
491  }
492  } while (++v14 < v30);
493  }
494 }
495 
496 int GUIFont::DrawTextInRect(GUIWindow *pWindow, unsigned int uX, unsigned int uY, uint16_t uColor, const String &str, int rect_width, int reverse_text) {
497  char text[4096];
498  Assert(str.length() < sizeof(text));
499  strcpy(text, str.c_str());
500 
501  size_t pNumLen = strlen(text);
502  if (pNumLen == 0) return 0;
503 
504  unsigned int pLineWidth = this->GetLineWidth(text);
505  if (pLineWidth < rect_width) {
506  this->DrawText(pWindow, uX, uY, uColor, text, 0, 0, 0);
507  return pLineWidth;
508  }
509 
510  unsigned int text_width = 0;
511  if (reverse_text) {
512  _strrev(text);
513  }
514 
515  size_t Str1a = 0;
516  size_t i = 0;
517  for (i = 0; i < pNumLen; ++i) {
518  if (text_width >= rect_width) {
519  break;
520  }
521  uint8_t v12 = text[i];
522  if (this->IsCharValid(v12)) {
523  switch (v12) {
524  case '\t': // Horizontal tab 09
525  case '\n': // Line Feed 0A 10
526  case '\r': // Form Feed, page eject 0C 12
527  break;
528  case '\f': // Carriage Return 0D 13
529  i += 5;
530  break;
531  default:
532  if (i > 0) {
533  text_width += pData->pMetrics[v12].uLeftSpacing;
534  }
535  text_width += pData->pMetrics[v12].uWidth;
536  if (i < pNumLen) {
537  text_width += pData->pMetrics[v12].uRightSpacing;
538  }
539  }
540  }
541  }
542  text[i - 1] = 0;
543 
544  pNumLen = strlen(text);
545  unsigned int v28 = this->GetLineWidth(text);
546  if (reverse_text) {
547  _strrev(text);
548  }
549 
550  int width = uX + pWindow->uFrameX;
551  int height = uY + pWindow->uFrameY;
552  for (i = 0; i < pNumLen; ++i) {
553  uint8_t v15 = text[i];
554  if (this->IsCharValid(v15)) {
555  switch (v15) {
556  case '\t': { // Horizontal tab 09
557  char Str[6];
558  strncpy(Str, &text[i + 1], 3);
559  Str[3] = 0;
560  // atoi(Str);
561  i += 3;
562  break;
563  }
564  case '\n': { // Line Feed 0A 10
565  unsigned int v24 = pData->uFontHeight;
566  width = uX;
567  uY = uY + pData->uFontHeight - 3;
568  height = uY + pData->uFontHeight - 3;
569  break;
570  }
571  case '\r': { // Form Feed, page eject 0C 12
572  char Str[6];
573  strncpy(Str, &text[i + 1], 5);
574  Str[5] = 0;
575  i += 5;
576  uColor = atoi(Str);
577  break;
578  }
579  case '\f': { // Carriage Return 0D 13
580  char Str[6];
581  strncpy(Str, &text[i + 1], 3);
582  Str[3] = 0;
583  i += 3;
584  unsigned int v23 = this->GetLineWidth(&text[i]);
585  width = pWindow->uFrameZ - v23 - atoi(Str);
586  height = uY;
587  break;
588  }
589  default: {
590  unsigned int v20 = pData->pMetrics[v15].uWidth;
591  if (i > 0) {
592  width += pData->pMetrics[v15].uLeftSpacing;
593  }
595  if (uColor) {
596  render->DrawText(width, height, v21, v20, pData->uFontHeight, pData->pFontPalettes[0], uColor, 0);
597  } else {
598  render->DrawTextAlpha(width, height, v21, v20, pData->uFontHeight, pData->pFontPalettes[0], false);
599  }
600  width += v20;
601  if (i < (int)pNumLen) {
603  }
604  }
605  }
606  }
607  }
608  return v28;
609 }
610 
611 void GUIFont::DrawCreditsEntry(GUIFont *pSecondFont, int uFrameX, int uFrameY, unsigned int w, unsigned int h,
612  uint16_t firstColor, uint16_t secondColor, const String &pString,
613  Image *image) {
614  GUIWindow draw_window;
615  draw_window.uFrameHeight = h;
616  draw_window.uFrameW = uFrameY + h - 1;
617  draw_window.uFrameWidth = w;
618  draw_window.uFrameZ = uFrameX + w - 1;
619  ui_current_text_color = firstColor;
620  draw_window.uFrameX = uFrameX;
621  draw_window.uFrameY = uFrameY;
622 
623  String work_string = FitTwoFontStringINWindow(pString, pSecondFont, &draw_window, 0, 1);
624  std::istringstream stream(work_string);
625  std::getline(stream, work_string);
626 
627  uint32_t *pPixels = (uint32_t*)image->GetPixels(IMAGE_FORMAT_A8R8G8B8);
628  uint32_t *curr_pixel_pos = &pPixels[image->GetWidth() * uFrameY];
629  if (!work_string.empty()) {
630  int half_frameX = uFrameX >> 1;
631  while (!stream.eof()) {
632  GUIFont *currentFont = this;
633  ui_current_text_color = firstColor;
634  int start_str_pos = 0;
635  int currentColor = firstColor;
636  if (work_string[0] == '_') {
637  currentFont = pSecondFont;
638  currentColor = secondColor;
639  ui_current_text_color = secondColor;
640  start_str_pos = 1;
641  }
642  int line_w = (int)(w - currentFont->GetLineWidth(&work_string[start_str_pos])) / 2;
643  if (line_w < 0) {
644  line_w = 0;
645  }
646  currentFont->DrawTextLineToBuff(currentColor, &curr_pixel_pos[line_w + half_frameX],
647  work_string, image->GetWidth());
648  curr_pixel_pos += image->GetWidth() * (currentFont->GetHeight() - 3);
649  std::getline(stream, work_string);
650  if (work_string.empty()) {
651  break;
652  }
653  }
654  }
655 }
656 
657 String GUIFont::FitTwoFontStringINWindow(const String &pString, GUIFont *pFontSecond, GUIWindow* pWindow, int startPixlOff, int a6) {
658  if (pString.empty()) {
659  return String();
660  }
661  GUIFont *currentFont = this;
662  size_t uInStrLen = pString.length();
663  Assert(uInStrLen < sizeof(pTmpBuf3));
664  strcpy(pTmpBuf3.data(), pString.c_str());
665  if (uInStrLen == 0) {
666  return pTmpBuf3.data();
667  }
668 
669  int string_pixel_Width = startPixlOff;
670  int start_pixel_offset = startPixlOff;
671  int possible_transition_point = 0;
672  for (int i = 0; i < uInStrLen; ++i) {
673  unsigned char c = pTmpBuf3[i];
674  if (IsCharValid(c)) {
675  switch (c) {
676  case '\t': { // Horizontal tab 09
677  char digits[4];
678  strncpy(digits, &pTmpBuf3[i + 1], 3);
679  digits[3] = 0;
680  string_pixel_Width = atoi(digits) + startPixlOff;
681  i += 3;
682  break;
683  }
684  case '\n': { // Line Feed 0A 10
685  string_pixel_Width = start_pixel_offset;
686  possible_transition_point = i;
687  currentFont = this;
688  break;
689  }
690  case '\f': { // Form Feed, page eject 0C 12
691  i += 5;
692  break;
693  }
694  case '\r': { // Carriage Return 0D 13
695  if (!a6)
696  return pString;
697  break;
698  }
699  case ' ': {
700  string_pixel_Width += currentFont->pData->pMetrics[c].uWidth;
701  possible_transition_point = i;
702  break;
703  }
704  case '_':
705  currentFont = pFontSecond;
706  break;
707  default:
708 
709  if ((string_pixel_Width + currentFont->pData->pMetrics[c].uWidth + currentFont->pData->pMetrics[c].uLeftSpacing + currentFont->pData->pMetrics[c].uRightSpacing) < pWindow->uFrameWidth) {
710  if (i > possible_transition_point)
711  string_pixel_Width += currentFont->pData->pMetrics[c].uLeftSpacing;
712  string_pixel_Width += currentFont->pData->pMetrics[c].uWidth;
713  if (i < uInStrLen)
714  string_pixel_Width += currentFont->pData->pMetrics[c].uRightSpacing;
715  } else {
716  pTmpBuf3[possible_transition_point] = '\n';
717  if (currentFont == pFontSecond) {
718  for (int k = uInStrLen - 1; k >= possible_transition_point + 1; --k) {
719  pTmpBuf3[k] = pTmpBuf3[k - 1];
720  }
721  ++uInStrLen;
722  ++possible_transition_point;
723  pTmpBuf3[possible_transition_point] = '_';
724  }
725  string_pixel_Width = start_pixel_offset;
726 
727  for (int j = possible_transition_point; j < i; ++j) {
728  c = pTmpBuf3[j];
729  if (IsCharValid(c)) {
730  if (j > possible_transition_point) {
731  string_pixel_Width += pData->pMetrics[c].uLeftSpacing;
732  }
733  string_pixel_Width += pData->pMetrics[c].uWidth;
734  if (j < i) {
735  string_pixel_Width += pData->pMetrics[c].uRightSpacing;
736  }
737  }
738  }
739  }
740  }
741  }
742  }
743 
744  return String(pTmpBuf3.data());
745 }
746 
747 int GUIFont::GetStringHeight2(GUIFont *secondFont, const String &text_str, GUIWindow* pWindow, int startX, int a6) {
748  if (text_str.empty()) {
749  return 0;
750  }
751 
752  int uAllHeght = GetHeight() - 3;
753  String test_string = FitTwoFontStringINWindow(text_str, secondFont, pWindow, startX, 0);
754  size_t uStringLen = test_string.length();
755  for (size_t i = 0; i < uStringLen; ++i) {
756  unsigned char c = test_string[i];
757  if (IsCharValid(c)) {
758  switch (c) {
759  case '\n': // Line Feed 0A 10:
760  uAllHeght += GetHeight() - 3;
761  break;
762  case '\f': // Form Feed, page eject 0C 12
763  i += 5;
764  break;
765  case '\t': // Horizontal tab 09
766  case '\r': // Carriage Return 0D 13
767  if (a6 != 1)
768  i += 3;
769  break;
770  }
771  }
772  }
773 
774  return uAllHeght;
775 }
GUICharMetric
Definition: GUIFont.cpp:32
uint16_t
unsigned __int16 uint16_t
Definition: SDL_config.h:37
FontData::field_4
uint8_t field_4
Definition: GUIFont.cpp:45
GUIWindow::uFrameW
unsigned int uFrameW
Definition: GUIWindow.h:473
pAutonoteFont
GUIFont * pAutonoteFont
Definition: GUIFont.cpp:16
LOD.h
GUIFont
Definition: GUIFont.h:8
GUIWindow
Definition: GUIWindow.h:433
FontData::field_3
uint8_t field_3
Definition: GUIFont.cpp:44
GUIFont::DrawCreditsEntry
void DrawCreditsEntry(GUIFont *pSecondFont, int uFrameX, int uFrameY, unsigned int w, unsigned int h, uint16_t firstColor, uint16_t secondColor, const String &pString, Image *image)
Definition: GUIFont.cpp:611
pFontCChar
GUIFont * pFontCChar
Definition: GUIFont.cpp:23
GUIFont::pData
FontData * pData
Definition: GUIFont.h:45
FontData::pFontPalettes
uint8_t * pFontPalettes[5]
Definition: GUIFont.cpp:49
LOD::File::LoadCompressedTexture
void * LoadCompressedTexture(const String &pContainer, size_t *data_size=nullptr)
Definition: LOD.cpp:921
height
EGLSurface EGLint EGLint EGLint EGLint height
Definition: SDL_egl.h:1596
GUIFont::DrawTextInRect
int DrawTextInRect(GUIWindow *pWindow, unsigned int uX, unsigned int uY, uint16_t uColor, const String &str, int rect_width, int reverse_text)
Definition: GUIFont.cpp:496
pTmpBuf3
std::array< char, 10000 > pTmpBuf3
Definition: GUIFont.cpp:29
GUICharMetric::uWidth
uint32_t uWidth
Definition: GUIFont.cpp:34
GUICharMetric::uRightSpacing
uint32_t uRightSpacing
Definition: GUIFont.cpp:35
Color32
uint32_t Color32(uint16_t color16)
Definition: Engine.cpp:135
FontData
Definition: GUIFont.cpp:40
GUIFont::GetLineWidth
unsigned int GetLineWidth(const String &str)
Definition: GUIFont.cpp:278
FontData::cLastChar
uint8_t cLastChar
Definition: GUIFont.cpp:42
GUIFont.h
w
GLubyte GLubyte GLubyte GLubyte w
Definition: SDL_opengl_glext.h:734
GUIFont::GetHeight
unsigned int GetHeight() const
Definition: GUIFont.cpp:84
GUIFont::GetStringHeight2
int GetStringHeight2(GUIFont *secondFont, const String &text_str, GUIWindow *pWindow, int startX, int a6)
Definition: GUIFont.cpp:747
pFontCreate
GUIFont * pFontCreate
Definition: GUIFont.cpp:22
GUIWindow::uFrameWidth
unsigned int uFrameWidth
Definition: GUIWindow.h:470
h
GLfloat GLfloat GLfloat GLfloat h
Definition: SDL_opengl_glext.h:1949
GUIWindow::uFrameZ
unsigned int uFrameZ
Definition: GUIWindow.h:472
Engine.h
TEXTURE_24BIT_PALETTE
@ TEXTURE_24BIT_PALETTE
Definition: LOD.h:17
IMAGE_FORMAT_A8R8G8B8
@ IMAGE_FORMAT_A8R8G8B8
Definition: Image.h:7
FontData::uFontHeight
uint16_t uFontHeight
Definition: GUIFont.cpp:46
y
EGLSurface EGLint EGLint y
Definition: SDL_egl.h:1596
FontData::pMetrics
GUICharMetric pMetrics[256]
Definition: GUIFont.cpp:50
GUIFont::DrawTextLine
void DrawTextLine(const String &text, uint16_t uDefaultColor, int uX, int uY, int max_len_pix)
Definition: GUIFont.cpp:88
Image
Definition: Image.h:19
pFontArrus
GUIFont * pFontArrus
Definition: GUIFont.cpp:18
IRender.h
GUIFont::IsCharValid
bool IsCharValid(unsigned char c) const
Definition: GUIFont.cpp:80
pSpellFont
GUIFont * pSpellFont
Definition: GUIFont.cpp:17
x
EGLSurface EGLint x
Definition: SDL_egl.h:1596
GUIFont::AlignText_Center
unsigned int AlignText_Center(unsigned int width, const String &str)
Definition: GUIFont.cpp:306
GUIWindow::uFrameHeight
unsigned int uFrameHeight
Definition: GUIWindow.h:471
GUIFont::LoadFont
static GUIFont * LoadFont(const char *pFontFile, const char *pFontPalette,...)
Definition: GUIFont.cpp:56
pBook2Font
GUIFont * pBook2Font
Definition: GUIFont.cpp:20
width
EGLSurface EGLint EGLint EGLint width
Definition: SDL_egl.h:1596
LODFile_IconsBitmaps::LoadTexture
unsigned int LoadTexture(const char *pContainer, enum TEXTURE_TYPE uTextureType=TEXTURE_DEFAULT)
Definition: LOD.cpp:1185
GUIFont::CalcTextHeight
unsigned int CalcTextHeight(const String &str, unsigned int width, int x_offset, bool return_on_carriage=false)
Definition: GUIFont.cpp:246
FontData::field_7
uint8_t field_7
Definition: GUIFont.cpp:47
GUIFont::GetPageTop
String GetPageTop(const String &pInString, GUIWindow *pWindow, unsigned int uX, int a5)
Definition: GUIFont.cpp:211
_strrev
char * _strrev(char *str)
Definition: PlatformLinux.h:16
ui_current_text_color
int ui_current_text_color
Definition: mm7_data.cpp:649
GUIFont::DrawText
void DrawText(GUIWindow *pWindow, int uX, int uY, uint16_t uFontColor, const String &str, bool present_time_transparency, int max_text_height, int uFontShadowColor)
Definition: GUIFont.cpp:388
pBookFont
GUIFont * pBookFont
Definition: GUIFont.cpp:21
GUIWindow::uFrameY
unsigned int uFrameY
Definition: GUIWindow.h:469
stream
EGLStreamKHR stream
Definition: SDL_egl.h:1082
FontData::cFirstChar
uint8_t cFirstChar
Definition: GUIFont.cpp:41
pFontComic
GUIFont * pFontComic
Definition: GUIFont.cpp:24
GUICharMetric::uLeftSpacing
uint32_t uLeftSpacing
Definition: GUIFont.cpp:33
LODFile_IconsBitmaps
Definition: LOD.h:125
uint8_t
unsigned __int8 uint8_t
Definition: SDL_config.h:35
pIcons_LOD
LODFile_IconsBitmaps * pIcons_LOD
Definition: LOD.cpp:12
FontData::field_2
uint8_t field_2
Definition: GUIFont.cpp:43
GUIFont::DrawTextLineToBuff
void DrawTextLineToBuff(uint16_t uColor, uint32_t *uX_buff_pos, const String &text, int line_width)
Definition: GUIFont.cpp:160
FontData::palletes_count
uint32_t palletes_count
Definition: GUIFont.cpp:48
b
GLboolean GLboolean GLboolean b
Definition: SDL_opengl_glext.h:1112
r
GLdouble GLdouble GLdouble r
Definition: SDL_opengl.h:2079
FontData::font_pixels_offset
uint32_t font_pixels_offset[256]
Definition: GUIFont.cpp:51
c
const GLubyte * c
Definition: SDL_opengl_glext.h:11096
GUIFont::FitTwoFontStringINWindow
String FitTwoFontStringINWindow(const String &pString, GUIFont *pFontSecond, GUIWindow *pWindow, int startPixlOff, int a6)
Definition: GUIFont.cpp:657
GUIFont::FitTextInAWindow
String FitTextInAWindow(const String &inString, unsigned int width, int uX, bool return_on_carriage=false)
Definition: GUIFont.cpp:311
DrawCharToBuff
void DrawCharToBuff(uint32_t *draw_buff, uint8_t *pCharPixels, int uCharWidth, int uCharHeight, uint8_t *pFontPalette, uint16_t draw_color, int line_width)
Definition: GUIFont.cpp:138
GUIWindow::uFrameX
unsigned int uFrameX
Definition: GUIWindow.h:468
FontData::pFontData
uint8_t pFontData[0]
Definition: GUIFont.cpp:52
GUIWindow.h
temp_string
char temp_string[2048]
Definition: GUIFont.cpp:27
Texture_MM7::pPalette24
uint8_t * pPalette24
Definition: Image.h:104
pFontLucida
GUIFont * pFontLucida
Definition: GUIFont.cpp:19
LODFile_IconsBitmaps::pTextures
Texture_MM7 pTextures[MAX_LOD_TEXTURES]
Definition: LOD.h:158
image
EGLImageKHR image
Definition: SDL_egl.h:953
g
GLboolean GLboolean g
Definition: SDL_opengl_glext.h:1112
uint32_t
unsigned __int32 uint32_t
Definition: SDL_config.h:39
String
std::string String
Definition: Strings.h:10
pFontSmallnum
GUIFont * pFontSmallnum
Definition: GUIFont.cpp:25
render
std::shared_ptr< IRender > render
Definition: RenderOpenGL.cpp:52