summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorrubidium <rubidium@openttd.org>2013-06-25 20:38:12 +0000
committerrubidium <rubidium@openttd.org>2013-06-25 20:38:12 +0000
commit4f0ef61d4e6d5ccc986781d55bf79e0ee707f692 (patch)
tree168dc29e0c700c59dbfabe1a52bfaf451893b8ea
parent2446b8ea6031f251e3eede83e9a17e9c1464d471 (diff)
downloadopenttd-4f0ef61d4e6d5ccc986781d55bf79e0ee707f692.tar.xz
(svn r25466) -Add: drawing routine for the layout engine
-rw-r--r--src/gfx.cpp96
-rw-r--r--src/gfx_layout.h2
2 files changed, 95 insertions, 3 deletions
diff --git a/src/gfx.cpp b/src/gfx.cpp
index 9cb199e2d..b77e42585 100644
--- a/src/gfx.cpp
+++ b/src/gfx.cpp
@@ -10,8 +10,7 @@
/** @file gfx.cpp Handling of drawing text and other gfx related stuff. */
#include "stdafx.h"
-#include "gfx_func.h"
-#include "fontcache.h"
+#include "gfx_layout.h"
#include "progress.h"
#include "zoom_func.h"
#include "blitter/factory.hpp"
@@ -487,6 +486,99 @@ static int TruncateString(char *str, int maxw, FontSize start_fontsize)
static int ReallyDoDrawString(const WChar *string, int x, int y, DrawStringParams &params, bool parse_string_also_when_clipped = false);
/**
+ * Drawing routine for drawing a laid out line of text.
+ * @param line String to draw.
+ * @param y The top most position to draw on.
+ * @param left The left most position to draw on.
+ * @param right The right most position to draw on.
+ * @param align The alignment of the string when drawing left-to-right. In the
+ * case a right-to-left language is chosen this is inverted so it
+ * will be drawn in the right direction.
+ * @param underline Whether to underline what has been drawn or not.
+ *
+ * @return In case of left or center alignment the right most pixel we have drawn to.
+ * In case of right alignment the left most pixel we have drawn to.
+ */
+static int DrawLayoutLine(ParagraphLayout::Line *line, int y, int left, int right, StringAlignment align, bool underline)
+{
+ if (line->countRuns() == 0) return 0;
+
+ int w = line->getWidth();
+ int h = line->getLeading();
+
+ /* In case we have a RTL language we swap the alignment. */
+ if (!(align & SA_FORCE) && _current_text_dir == TD_RTL && (align & SA_HOR_MASK) != SA_HOR_CENTER) align ^= SA_RIGHT;
+
+ /* right is the right most position to draw on. In this case we want to do
+ * calculations with the width of the string. In comparison right can be
+ * seen as lastof(todraw) and width as lengthof(todraw). They differ by 1.
+ * So most +1/-1 additions are to move from lengthof to 'indices'.
+ */
+ switch (align & SA_HOR_MASK) {
+ case SA_LEFT:
+ /* right + 1 = left + w */
+ right = left + w - 1;
+ break;
+
+ case SA_HOR_CENTER:
+ left = RoundDivSU(right + 1 + left - w, 2);
+ /* right + 1 = left + w */
+ right = left + w - 1;
+ break;
+
+ case SA_RIGHT:
+ left = right + 1 - w;
+ break;
+
+ default:
+ NOT_REACHED();
+ }
+
+ for (int run_index = 0; run_index < line->countRuns(); run_index++) {
+ const ParagraphLayout::VisualRun *run = line->getVisualRun(run_index);
+ const Font *f = (const Font*)run->getFont();
+
+ FontCache *fc = f->fc;
+ TextColour colour = f->colour;
+ SetColourRemap(colour);
+
+ DrawPixelInfo *dpi = _cur_dpi;
+ int dpi_left = dpi->left;
+ int dpi_right = dpi->left + dpi->width;
+
+ bool draw_shadow = fc->GetDrawGlyphShadow() && colour != TC_BLACK;
+
+ for (int i = 0; i < run->getGlyphCount(); i++) {
+ GlyphID glyph = run->getGlyphs()[i];
+
+ /* Not a valid glyph (empty) */
+ if (glyph == 0xFFFF) continue;
+
+ int begin_x = run->getPositions()[i * 2] + left;
+ int end_x = run->getPositions()[i * 2 + 2] + left;
+ int top = run->getPositions()[i * 2 + 1] + y;
+
+ /* Not within the bounds to draw. */
+ if (begin_x >= dpi_right || end_x <= dpi_left) continue;
+
+ const Sprite *sprite = fc->GetGlyph(glyph);
+ if (draw_shadow && (glyph & SPRITE_GLYPH) == 0) {
+ SetColourRemap(TC_BLACK);
+ GfxMainBlitter(sprite, begin_x + 1, top + 1, BM_COLOUR_REMAP);
+ SetColourRemap(colour);
+ }
+ GfxMainBlitter(sprite, begin_x, top, BM_COLOUR_REMAP);
+ }
+ }
+
+ if (underline) {
+ GfxFillRect(left, y + h, right, y + h, _string_colourremap[1]);
+ }
+
+ return (align & SA_HOR_MASK) == SA_RIGHT ? left : right;
+}
+
+/**
* Get the real width of the string.
* @param str the string to draw
* @param start_fontsize Fontsize to start the text with
diff --git a/src/gfx_layout.h b/src/gfx_layout.h
index cf4f1f90a..7960bf2a2 100644
--- a/src/gfx_layout.h
+++ b/src/gfx_layout.h
@@ -35,7 +35,7 @@ typedef SmallMap<int, Font *> FontMap;
* visual runs.
*
* One constructs this class with the text that needs to be split into
- * lines. Then nextLine is called with the maximum with until NULL is
+ * lines. Then nextLine is called with the maximum width until NULL is
* returned. Each nextLine call creates VisualRuns which contain the
* length of text that are to be drawn with the same font. In other
* words, the result of this class is a list of sub strings with their