From: Daniel Horn Subject: [Patch 2/2] wineps.drv: Allow text copy/paste from print-to-pdf Message-Id: Date: Tue, 22 Apr 2014 13:37:42 -0700 From ba58312f23e7c4c0441977f9c4a7560e399a112f Mon Sep 17 00:00:00 2001 From: Daniel Reiter Horn Date: Tue, 22 Apr 2014 20:16:51 +0000 Subject: [PATCH 2/2] Allow text copy/paste from print-to-pdf Fixes http://bugs.winehq.org/show_bug.cgi?id=6416 by using unicode encodings for fonts. This patch has been tested on hundreds of print jobs under linux ubuntu 12.04 with a wide array of applications --- dlls/wineps.drv/download.c | 17 ++++++++++------- dlls/wineps.drv/psdrv.h | 4 ++-- dlls/wineps.drv/text.c | 29 +++++++++++++++++++---------- 3 files changed, 31 insertions(+), 19 deletions(-) diff --git a/dlls/wineps.drv/download.c b/dlls/wineps.drv/download.c index e5b57f7..3a14cd0 100644 --- a/dlls/wineps.drv/download.c +++ b/dlls/wineps.drv/download.c @@ -342,7 +342,7 @@ BOOL PSDRV_WriteSetDownloadFont(PHYSDEV dev, BOOL vertical) if(pdl->type == Type42) { char g_name[MAX_G_NAME + 1]; - get_glyph_name(dev->hdc, 0, g_name); + get_glyph_name(dev->hdc, FALSE, 0, g_name); T42_download_glyph(dev, pdl, 0, g_name); } } @@ -359,10 +359,12 @@ BOOL PSDRV_WriteSetDownloadFont(PHYSDEV dev, BOOL vertical) return TRUE; } -void get_glyph_name(HDC hdc, WORD index, char *name) +void get_glyph_name(HDC hdc, BOOL unicode, WORD index, char *name) { - /* FIXME */ - sprintf(name, "g%04x", index); + if(unicode) + sprintf(name, "uni%04X", index); + else + sprintf(name, "g%04x", index); return; } @@ -372,7 +374,8 @@ void get_glyph_name(HDC hdc, WORD index, char *name) * Download and write out a number of glyphs * */ -BOOL PSDRV_WriteDownloadGlyphShow(PHYSDEV dev, const WORD *glyphs, +BOOL PSDRV_WriteDownloadGlyphShow(PHYSDEV dev, UINT flags, const WORD *glyphs, + const LPCWSTR str, UINT count) { PSDRV_PDEVICE *physDev = get_psdrv_dev( dev ); @@ -383,7 +386,7 @@ BOOL PSDRV_WriteDownloadGlyphShow(PHYSDEV dev, const WORD *glyphs, switch(physDev->font.fontinfo.Download->type) { case Type42: for(i = 0; i < count; i++) { - get_glyph_name(dev->hdc, glyphs[i], g_name); + get_glyph_name(dev->hdc, (flags & ETO_GLYPH_INDEX) == 0, str[i], g_name); T42_download_glyph(dev, physDev->font.fontinfo.Download, glyphs[i], g_name); PSDRV_WriteGlyphShow(dev, g_name); } @@ -391,7 +394,7 @@ BOOL PSDRV_WriteDownloadGlyphShow(PHYSDEV dev, const WORD *glyphs, case Type1: for(i = 0; i < count; i++) { - get_glyph_name(dev->hdc, glyphs[i], g_name); + get_glyph_name(dev->hdc, (flags & ETO_GLYPH_INDEX) == 0, str[i], g_name); T1_download_glyph(dev, physDev->font.fontinfo.Download, glyphs[i], g_name); PSDRV_WriteGlyphShow(dev, g_name); } diff --git a/dlls/wineps.drv/psdrv.h b/dlls/wineps.drv/psdrv.h index 229d04c..aeb247f 100644 --- a/dlls/wineps.drv/psdrv.h +++ b/dlls/wineps.drv/psdrv.h @@ -549,13 +549,13 @@ extern BOOL PSDRV_WriteBuiltinGlyphShow(PHYSDEV dev, LPCWSTR str, INT count) DEC extern BOOL PSDRV_SelectDownloadFont(PHYSDEV dev) DECLSPEC_HIDDEN; extern BOOL PSDRV_WriteSetDownloadFont(PHYSDEV dev, BOOL vertical) DECLSPEC_HIDDEN; -extern BOOL PSDRV_WriteDownloadGlyphShow(PHYSDEV dev, const WORD *glpyhs, UINT count) DECLSPEC_HIDDEN; +extern BOOL PSDRV_WriteDownloadGlyphShow(PHYSDEV dev, UINT flags, const WORD *glpyhs, const LPCWSTR str, UINT count) DECLSPEC_HIDDEN; extern BOOL PSDRV_EmptyDownloadList(PHYSDEV dev, BOOL write_undef) DECLSPEC_HIDDEN; extern DWORD write_spool( PHYSDEV dev, const void *data, DWORD num ) DECLSPEC_HIDDEN; #define MAX_G_NAME 31 /* max length of PS glyph name */ -extern void get_glyph_name(HDC hdc, WORD index, char *name) DECLSPEC_HIDDEN; +extern void get_glyph_name(HDC hdc, BOOL unicode, WORD index, char *name) DECLSPEC_HIDDEN; extern TYPE1 *T1_download_header(PHYSDEV dev, char *ps_name, RECT *bbox, UINT emsize) DECLSPEC_HIDDEN; diff --git a/dlls/wineps.drv/text.c b/dlls/wineps.drv/text.c index 96728ca..06c242b 100644 --- a/dlls/wineps.drv/text.c +++ b/dlls/wineps.drv/text.c @@ -205,27 +205,35 @@ BOOL PSDRV_ExtTextOut( PHYSDEV dev, INT x, INT y, UINT flags, const RECT *lprect /*********************************************************************** * PSDRV_Text */ +#define DEFAULT_PARAGRAPH_SIZE 16384 static BOOL PSDRV_Text(PHYSDEV dev, INT x, INT y, UINT flags, LPCWSTR str, UINT count, BOOL bDrawBackground, const INT *lpDx) { PSDRV_PDEVICE *physDev = get_psdrv_dev( dev ); - WORD *glyphs = NULL; - + LPCWSTR glyphs = str; + WORD *allocatedGlyphs = NULL; + WORD glyphBacking[DEFAULT_PARAGRAPH_SIZE]; if (!count) return TRUE; if(physDev->font.fontloc == Download && !(flags & ETO_GLYPH_INDEX)) { - glyphs = HeapAlloc( GetProcessHeap(), 0, count * sizeof(WORD) ); - GetGlyphIndicesW( dev->hdc, str, count, glyphs, 0 ); - str = glyphs; + WORD * rwglyphs; + if (count > DEFAULT_PARAGRAPH_SIZE) { + allocatedGlyphs = HeapAlloc( GetProcessHeap(), 0, count * sizeof(WORD) ); + rwglyphs = allocatedGlyphs; + }else { + rwglyphs = glyphBacking; + } + GetGlyphIndicesW( dev->hdc, str, count, rwglyphs, 0 ); + glyphs = rwglyphs; } PSDRV_WriteMoveTo(dev, x, y); if(!lpDx) { if(physDev->font.fontloc == Download) - PSDRV_WriteDownloadGlyphShow(dev, str, count); + PSDRV_WriteDownloadGlyphShow(dev, flags, glyphs, str, count); else PSDRV_WriteBuiltinGlyphShow(dev, str, count); } @@ -235,7 +243,7 @@ static BOOL PSDRV_Text(PHYSDEV dev, INT x, INT y, UINT flags, LPCWSTR str, for(i = 0; i < count-1; i++) { if(physDev->font.fontloc == Download) - PSDRV_WriteDownloadGlyphShow(dev, str + i, 1); + PSDRV_WriteDownloadGlyphShow(dev, flags, glyphs + i, str + i, 1); else PSDRV_WriteBuiltinGlyphShow(dev, str + i, 1); if(flags & ETO_PDY) @@ -248,11 +256,12 @@ static BOOL PSDRV_Text(PHYSDEV dev, INT x, INT y, UINT flags, LPCWSTR str, PSDRV_WriteMoveTo(dev, x + offset.x, y + offset.y); } if(physDev->font.fontloc == Download) - PSDRV_WriteDownloadGlyphShow(dev, str + i, 1); + PSDRV_WriteDownloadGlyphShow(dev, flags, glyphs + i, str + i, 1); else PSDRV_WriteBuiltinGlyphShow(dev, str + i, 1); } - - HeapFree( GetProcessHeap(), 0, glyphs ); + if (allocatedGlyphs != NULL) { + HeapFree( GetProcessHeap(), 0, allocatedGlyphs ); + } return TRUE; } -- 1.8.4.2