diff options
Diffstat (limited to 'Build/source/texk/dvipdfm-x/dvi.c')
-rw-r--r-- | Build/source/texk/dvipdfm-x/dvi.c | 106 |
1 files changed, 76 insertions, 30 deletions
diff --git a/Build/source/texk/dvipdfm-x/dvi.c b/Build/source/texk/dvipdfm-x/dvi.c index a4afab61bdb..3dc94d440e1 100644 --- a/Build/source/texk/dvipdfm-x/dvi.c +++ b/Build/source/texk/dvipdfm-x/dvi.c @@ -806,11 +806,62 @@ dvi_set_phantom_height (double height, double depth) catch_phantom = 2; } +/* All those things related to "compensation" is intruduced due to + * bcontent/econtent specials. They are originally implemented with + * modification to very important part of pdfdev functions such as + * pdf_dev_set_string(), and it made things very unclear. + * + * It is not good idea to modify the core part of PDF output routines + * just for implementing DVI "special" command. They do not make sense + * and just look odd when PDF output routines are separated from dvipdfmx. + */ +static struct spt_coord { + spt_t x, y; +} compensation = { 0, 0 }; + +void dvi_set_compensation (double x, double y) +{ + compensation.x = (spt_t) round(x / dvi2pts); + compensation.y = (spt_t) round(y / dvi2pts); +} + +static void +set_string (spt_t xpos, + spt_t ypos, + const void *instr_ptr, + int instr_len, + spt_t width, + int font_id, + int ctype) +{ + xpos -= compensation.x; + ypos -= compensation.y; + pdf_dev_set_string(xpos, ypos, instr_ptr, instr_len, width, font_id, ctype); +} + +static void +set_rule (spt_t xpos, spt_t ypos, spt_t width, spt_t height) +{ + xpos -= compensation.x; + ypos -= compensation.y; + pdf_dev_set_rule(xpos, ypos, width, height); +} + +static void +calc_rect (pdf_rect *r, spt_t xpos, spt_t ypos, spt_t width, spt_t height, spt_t depth) +{ + xpos -= compensation.x; + ypos -= compensation.y; + pdf_dev_set_rect(r, xpos, ypos, width, height, depth); +} + void dvi_do_special (const void *buffer, int32_t size) { - double x_user, y_user, mag; + double x_user, y_user, mag; const char *p; + int is_drawable = 0; + pdf_rect rect = {0.0, 0.0, 0.0, 0.0}; graphics_mode(); @@ -820,10 +871,15 @@ dvi_do_special (const void *buffer, int32_t size) y_user = -dvi_state.v * dvi2pts; mag = dvi_tell_mag(); - if (spc_exec_special(p, size, x_user, y_user, mag) < 0) { + if (spc_exec_special(p, size, x_user, y_user, mag, &is_drawable, &rect) < 0) { if (dpx_conf.verbose_level > 0) { dump(p, p + size); } + return; + } + + if (dvi_is_tracking_boxes() && is_drawable) { + pdf_doc_expand_box(&rect); } return; @@ -1174,7 +1230,7 @@ void dvi_right (int32_t x) default: width = dvi_state.h - save_h; } - pdf_dev_set_rect (&rect, save_h, -save_v, width, height, depth); + calc_rect(&rect, save_h, -save_v, width, height, depth); pdf_doc_expand_box(&rect); } } @@ -1235,23 +1291,19 @@ dvi_set (int32_t ch) wbuf[1] = UTF32toUTF16HS(ch) & 0xff; wbuf[2] = (UTF32toUTF16LS(ch) >> 8) & 0xff; wbuf[3] = UTF32toUTF16LS(ch) & 0xff; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 4, - width, font->font_id, 2); + set_string(dvi_state.h, -dvi_state.v, wbuf, 4, width, font->font_id, 2); } else if (ch > 255) { /* _FIXME_ */ wbuf[0] = (ch >> 8) & 0xff; wbuf[1] = ch & 0xff; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 2, - width, font->font_id, 2); + set_string(dvi_state.h, -dvi_state.v, wbuf, 2, width, font->font_id, 2); } else if (font->subfont_id >= 0) { unsigned short uch = lookup_sfd_record(font->subfont_id, (unsigned char) ch); wbuf[0] = (uch >> 8) & 0xff; wbuf[1] = uch & 0xff; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 2, - width, font->font_id, 2); + set_string(dvi_state.h, -dvi_state.v, wbuf, 2, width, font->font_id, 2); } else { wbuf[0] = (unsigned char) ch; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 1, - width, font->font_id, 1); + set_string(dvi_state.h, -dvi_state.v, wbuf, 1, width, font->font_id, 1); } if (dvi_is_tracking_boxes()) { pdf_rect rect; @@ -1261,8 +1313,7 @@ dvi_set (int32_t ch) height = sqxfw(font->size, height); depth = sqxfw(font->size, depth); - pdf_dev_set_rect (&rect, dvi_state.h, -dvi_state.v, - width, height, depth); + calc_rect(&rect, dvi_state.h, -dvi_state.v, width, height, depth); pdf_doc_expand_box(&rect); } break; @@ -1302,30 +1353,27 @@ dvi_put (int32_t ch) /* Treat a single character as a one byte string and use the * string routine. */ - if (ch > 65535) { /* _FIXME_ */ + if (ch > 65535) { + /* FIXME: This is a private extension made by someone... */ wbuf[0] = (UTF32toUTF16HS(ch) >> 8) & 0xff; wbuf[1] = UTF32toUTF16HS(ch) & 0xff; wbuf[2] = (UTF32toUTF16LS(ch) >> 8) & 0xff; wbuf[3] = UTF32toUTF16LS(ch) & 0xff; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 4, - width, font->font_id, 2); + set_string(dvi_state.h, -dvi_state.v, wbuf, 4, width, font->font_id, 2); } else if (ch > 255) { /* _FIXME_ */ wbuf[0] = (ch >> 8) & 0xff; wbuf[1] = ch & 0xff; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 2, - width, font->font_id, 2); + set_string(dvi_state.h, -dvi_state.v, wbuf, 2, width, font->font_id, 2); } else if (font->subfont_id >= 0) { unsigned int uch; uch = lookup_sfd_record(font->subfont_id, (unsigned char) ch); wbuf[0] = (uch >> 8) & 0xff; wbuf[1] = uch & 0xff; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 2, - width, font->font_id, 2); + set_string(dvi_state.h, -dvi_state.v, wbuf, 2, width, font->font_id, 2); } else { wbuf[0] = (unsigned char) ch; - pdf_dev_set_string(dvi_state.h, -dvi_state.v, wbuf, 1, - width, font->font_id, 1); + set_string(dvi_state.h, -dvi_state.v, wbuf, 1, width, font->font_id, 1); } if (dvi_is_tracking_boxes()) { pdf_rect rect; @@ -1335,8 +1383,7 @@ dvi_put (int32_t ch) height = sqxfw(font->size, height); depth = sqxfw(font->size, depth); - pdf_dev_set_rect (&rect, dvi_state.h, -dvi_state.v, - width, height, depth); + calc_rect(&rect, dvi_state.h, -dvi_state.v, width, height, depth); pdf_doc_expand_box(&rect); } break; @@ -1362,13 +1409,13 @@ dvi_rule (int32_t width, int32_t height) switch (dvi_state.d) { case 0: - pdf_dev_set_rule(dvi_state.h, -dvi_state.v, width, height); + set_rule(dvi_state.h, -dvi_state.v, width, height); break; case 1: - pdf_dev_set_rule(dvi_state.h, -dvi_state.v - width, height, width); + set_rule(dvi_state.h, -dvi_state.v - width, height, width); break; case 3: - pdf_dev_set_rule(dvi_state.h - height, -dvi_state.v , height, width); + set_rule(dvi_state.h - height, -dvi_state.v , height, width); break; } } @@ -1843,15 +1890,14 @@ do_glyphs (int do_actual_text) pdf_rect rect; height = (double)font->size * ascent / (double)font->unitsPerEm; depth = (double)font->size * -descent / (double)font->unitsPerEm; - pdf_dev_set_rect(&rect, dvi_state.h + xloc[i], -dvi_state.v - yloc[i], glyph_width, height, depth); + calc_rect(&rect, dvi_state.h + xloc[i], -dvi_state.v - yloc[i], glyph_width, height, depth); pdf_doc_expand_box(&rect); } } wbuf[0] = glyph_id >> 8; wbuf[1] = glyph_id & 0xff; - pdf_dev_set_string(dvi_state.h + xloc[i], -dvi_state.v - yloc[i], wbuf, 2, - glyph_width, font->font_id, -1); + set_string(dvi_state.h + xloc[i], -dvi_state.v - yloc[i], wbuf, 2, glyph_width, font->font_id, -1); } if (font->rgba_used == 1) { |