Description: TODO: Put a short summary on the line above and replace this paragraph with a longer explanation of this change. Complete the meta-information with other relevant fields (see below for details). To make it easier, the information below has been extracted from the changelog. Adjust it or drop it. . poppler (0.20.5-1) experimental; urgency=low . * New upstream release. * Update copyright. Author: Pino Toscano --- The information above should follow the Patch Tagging Guidelines, please checkout http://dep.debian.net/deps/dep3/ to learn about the format. Here are templates for supplementary fields that you might want to add: Origin: , Bug: Bug-Debian: http://bugs.debian.org/ Bug-Ubuntu: https://launchpad.net/bugs/ Forwarded: Reviewed-By: Last-Update: --- /dev/null +++ poppler-0.20.5/printreorderings.cc @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2013, Alex Bodnaru + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2, or (at your option) + * any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "printreorderings.h" + +#include "GlobalParams.h" +#include "goo/GooList.h" +#include "goo/GooString.h" + +void printReorderings() +{ + GooList *reorderNames = globalParams->getRTLReorderingNames(); + printf("Available RTL reorderings are:\n"); + for (int i = 0; i < reorderNames->getLength(); ++i) { + GooString *reorder = (GooString*)reorderNames->get(i); + printf("%s\n", reorder->getCString()); + } + delete reorderNames; +} --- poppler-0.20.5.orig/CMakeLists.txt +++ poppler-0.20.5/CMakeLists.txt @@ -30,6 +30,7 @@ option(ENABLE_CPP "Compile poppler cpp w option(ENABLE_LIBOPENJPEG "Use libopenjpeg for JPX streams." ON) option(ENABLE_LCMS "Use liblcms for color management." ON) option(ENABLE_LIBCURL "Build libcurl based HTTP support." OFF) +option(ENABLE_ICU "Build with ICU." ON) option(ENABLE_ZLIB "Build with zlib (not totally safe)." OFF) option(USE_FIXEDPOINT "Use fixed point arithmetic in the Splash backend" OFF) option(USE_FLOAT "Use single precision arithmetic in the Splash backend" OFF) @@ -124,6 +125,15 @@ if(ENABLE_CPP) set(ENABLE_CPP ${ICONV_FOUND}) set(HAVE_ICONV ${ICONV_FOUND}) endif(ENABLE_CPP) + +# well i don't know what to do here. +# the icu module is there. +if(ENABLE_ICU) + macro_optional_find_package(ICU) + set(ENABLE_ICU ${ICU_FOUND}) + set(HAVE_ICU ${ICU_FOUND}) +endif(ENABLE_ICU) + if(ENABLE_ZLIB) find_package(ZLIB) if(ZLIB_FOUND) --- poppler-0.20.5.orig/configure +++ poppler-0.20.5/configure @@ -735,6 +735,9 @@ LIBCURL_CFLAGS BUILD_ZLIB_FALSE BUILD_ZLIB_TRUE ZLIB_LIBS +ICU_CONFIG +ICU_LIBS +ICU_CFLAGS BUILD_LIBTIFF_FALSE BUILD_LIBTIFF_TRUE LIBTIFF_CFLAGSS @@ -902,6 +905,7 @@ with_x enable_libopenjpeg enable_libtiff enable_largefile +enable_icu enable_zlib enable_libcurl enable_libjpeg @@ -945,6 +949,8 @@ LIBOPENJPEG_CFLAGS LIBOPENJPEG_LIBS LIBTIFF_CFLAGS LIBTIFF_LIBS +ICU_CFLAGS +ICU_LIBS LIBCURL_CFLAGS LIBCURL_LIBS LIBJPEG_CFLAGS @@ -1608,6 +1614,8 @@ Optional Features: --disable-libopenjpeg Don't build against libopenjpeg. --disable-libtiff Don't build against libtiff. --disable-largefile omit support for large files + --enable-icu Build with icu based BIDI support. Enabled by + default. --enable-zlib Build with zlib --enable-libcurl Build with libcurl based HTTP support. --disable-libjpeg Don't build against libjpeg. @@ -1672,6 +1680,8 @@ Some influential environment variables: C compiler flags for LIBTIFF LIBTIFF_LIBS linker flags to link LIBTIFF (default is -ltiff) + ICU_CFLAGS C compiler flags for ICU, overriding pkg-config + ICU_LIBS linker flags for ICU, overriding pkg-config LIBCURL_CFLAGS C compiler flags for LIBCURL, overriding pkg-config LIBCURL_LIBS @@ -20014,6 +20024,143 @@ if test "$xpdf_cv_func_fseek64" = yes -a fi +# Check whether --enable-icu was given. +if test "${enable_icu+set}" = set; then : + enableval=$enable_icu; enable_icu=$enableval +else + enable_icu="yes" +fi + +if test x$enable_icu = xyes; then + +pkg_failed=no +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for ICU" >&5 +$as_echo_n "checking for ICU... " >&6; } + +if test -n "$ICU_CFLAGS"; then + pkg_cv_ICU_CFLAGS="$ICU_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"icu-uc\""; } >&5 + ($PKG_CONFIG --exists --print-errors "icu-uc") 2>&5 + ac_status=$? + $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_ICU_CFLAGS=`$PKG_CONFIG --cflags "icu-uc" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$ICU_LIBS"; then + pkg_cv_ICU_LIBS="$ICU_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"icu-uc\""; } >&5 + ($PKG_CONFIG --exists --print-errors "icu-uc") 2>&5 + ac_status=$? + $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_ICU_LIBS=`$PKG_CONFIG --libs "icu-uc" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + ICU_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "icu-uc" 2>&1` + else + ICU_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "icu-uc" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$ICU_PKG_ERRORS" >&5 + + icu_pkgconfig=no +elif test $pkg_failed = untried; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } + icu_pkgconfig=no +else + ICU_CFLAGS=$pkg_cv_ICU_CFLAGS + ICU_LIBS=$pkg_cv_ICU_LIBS + { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +$as_echo "yes" >&6; } + icu_pkgconfig=yes +fi + if test "x$icu_pkgconfig" = "xyes"; then + +$as_echo "#define HAVE_ICU 1" >>confdefs.h + + else + ICU_LIBS= + ICU_CFLAGS= + # Extract the first word of "icu-config", so it can be a program name with args. +set dummy icu-config; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_path_ICU_CONFIG+:} false; then : + $as_echo_n "(cached) " >&6 +else + case $ICU_CONFIG in + [\\/]* | ?:[\\/]*) + ac_cv_path_ICU_CONFIG="$ICU_CONFIG" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_path_ICU_CONFIG="$as_dir/$ac_word$ac_exec_ext" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + test -z "$ac_cv_path_ICU_CONFIG" && ac_cv_path_ICU_CONFIG="no" + ;; +esac +fi +ICU_CONFIG=$ac_cv_path_ICU_CONFIG +if test -n "$ICU_CONFIG"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ICU_CONFIG" >&5 +$as_echo "$ICU_CONFIG" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + + if test "x$ICU_CONFIG" != "xno" ; then + ICU_CFLAGS= + ICU_LIBS=`$ICU_CONFIG --ldflags-libsonly` + +$as_echo "#define HAVE_ICU 1" >>confdefs.h + + fi + fi +fi + # Check whether --enable-zlib was given. if test "${enable_zlib+set}" = set; then : enableval=$enable_zlib; @@ -26769,6 +26916,7 @@ echo " use gtk-doc: $enable_gtk_ echo " use libjpeg: $enable_libjpeg" echo " use libpng: $enable_libpng" echo " use libtiff: $enable_libtiff" +echo " use icu: $enable_icu" echo " use zlib: $enable_zlib" echo " use libcurl: $enable_libcurl" echo " use libopenjpeg: $enable_libopenjpeg" --- poppler-0.20.5.orig/config.h.in +++ poppler-0.20.5/config.h.in @@ -58,6 +58,9 @@ /* Define if you have the iconv() function and it works. */ #undef HAVE_ICONV +/* Have ICU include files */ +#undef HAVE_ICU + /* Define to 1 if you have the header file. */ #undef HAVE_INTTYPES_H --- poppler-0.20.5.orig/Makefile.am +++ poppler-0.20.5/Makefile.am @@ -86,6 +86,7 @@ EXTRA_DIST += \ cmake/modules/PopplerDefaults.cmake \ cmake/modules/PopplerMacros.cmake \ cmake/modules/FindLIBOPENJPEG.cmake \ + cmake/modules/FindICU.cmake \ config.h.cmake \ poppler-cairo.pc.cmake \ poppler/poppler-config.h.cmake \ --- poppler-0.20.5.orig/configure.ac +++ poppler-0.20.5/configure.ac @@ -265,6 +265,29 @@ if test "$xpdf_cv_func_fseek64" = yes -a AC_DEFINE(HAVE_FSEEK64) fi +dnl Test for icu +AC_ARG_ENABLE(icu, + AC_HELP_STRING([--enable-icu], + [Build with icu based BIDI support. Enabled by default.]), + enable_icu=$enableval, + enable_icu="yes") +if test x$enable_icu = xyes; then + PKG_CHECK_MODULES(ICU, icu-uc, + [icu_pkgconfig=yes], [icu_pkgconfig=no]) + if test "x$icu_pkgconfig" = "xyes"; then + AC_DEFINE(HAVE_ICU, 1, [Have ICU include files]) + else + ICU_LIBS= + ICU_CFLAGS= + AC_PATH_PROG(ICU_CONFIG, icu-config, no) + if test "x$ICU_CONFIG" != "xno" ; then + ICU_CFLAGS= + ICU_LIBS=`$ICU_CONFIG --ldflags-libsonly` + AC_DEFINE(HAVE_ICU, 1, [Have ICU include files]) + fi + fi +fi + dnl Test for zlib AC_ARG_ENABLE([zlib], [AS_HELP_STRING([--enable-zlib],[Build with zlib])], @@ -816,6 +839,7 @@ echo " use gtk-doc: $enable_gtk_ echo " use libjpeg: $enable_libjpeg" echo " use libpng: $enable_libpng" echo " use libtiff: $enable_libtiff" +echo " use icu: $enable_icu" echo " use zlib: $enable_zlib" echo " use libcurl: $enable_libcurl" echo " use libopenjpeg: $enable_libopenjpeg" --- /dev/null +++ poppler-0.20.5/utils/printreorderings.cc @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2013, Alex Bodnaru + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2, or (at your option) + * any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "printreorderings.h" + +#include "GlobalParams.h" +#include "goo/GooList.h" +#include "goo/GooString.h" + +void printReorderings() +{ + GooList *reorderNames = globalParams->getRTLReorderingNames(); + printf("Available RTL reorderings are:\n"); + for (int i = 0; i < reorderNames->getLength(); ++i) { + GooString *reorder = (GooString*)reorderNames->get(i); + printf("%s\n", reorder->getCString()); + } + delete reorderNames; +} --- /dev/null +++ poppler-0.20.5/utils/printreorderings.h @@ -0,0 +1,24 @@ +/* + * Copyright (C) 2008, Albert Astals Cid + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2, or (at your option) + * any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef PRINTREORDERINGS_H +#define PRINTREORDERINGS_H + +void printReorderings(); + +#endif --- poppler-0.20.5.orig/utils/Makefile.am +++ poppler-0.20.5/utils/Makefile.am @@ -104,6 +104,8 @@ pdftotext_SOURCES = \ pdftotext.cc \ printencodings.cc \ printencodings.h \ + printreorderings.cc \ + printreorderings.h \ $(common) pdftohtml_SOURCES = \ --- poppler-0.20.5.orig/utils/pdftotext.cc +++ poppler-0.20.5/utils/pdftotext.cc @@ -36,6 +36,7 @@ #include #include "parseargs.h" #include "printencodings.h" +#include "printreorderings.h" #include "goo/GooString.h" #include "goo/gmem.h" #include "GlobalParams.h" @@ -72,6 +73,7 @@ static double fixedPitch = 0; static GBool rawOrder = gFalse; static GBool htmlMeta = gFalse; static char textEncName[128] = ""; +static char textReorderName[33] = ""; static char textEOL[16] = ""; static GBool noPageBreaks = gFalse; static char ownerPassword[33] = "\001"; @@ -80,6 +82,7 @@ static GBool quiet = gFalse; static GBool printVersion = gFalse; static GBool printHelp = gFalse; static GBool printEnc = gFalse; +static GBool printReorder = gFalse; static const ArgDesc argDesc[] = { {"-f", argInt, &firstPage, 0, @@ -108,6 +111,10 @@ static const ArgDesc argDesc[] = { "output text encoding name"}, {"-listenc",argFlag, &printEnc, 0, "list available encodings"}, + {"-reorder", argString, textReorderName, sizeof(textReorderName), + "rtl text reordering name"}, + {"-listreorder",argFlag, &printReorder, 0, + "list available rtl text reordering modes"}, {"-eol", argString, textEOL, sizeof(textEOL), "output end-of-line convention (unix, dos, or mac)"}, {"-nopgbrk", argFlag, &noPageBreaks, 0, @@ -169,6 +176,7 @@ int main(int argc, char *argv[]) { GBool ok; char *p; int exitCode; + ReorderingMode reorderingMode = ReorderingDefault; exitCode = 99; @@ -177,7 +185,7 @@ int main(int argc, char *argv[]) { if (bbox) { htmlMeta = gTrue; } - if (!ok || (argc < 2 && !printEnc) || argc > 3 || printVersion || printHelp) { + if (!ok || (argc < 2 && !printEnc && !printReorder) || argc > 3 || printVersion || printHelp) { fprintf(stderr, "pdftotext version %s\n", PACKAGE_VERSION); fprintf(stderr, "%s\n", popplerCopyright); fprintf(stderr, "%s\n", xpdfCopyright); @@ -199,6 +207,13 @@ int main(int argc, char *argv[]) { goto err0; } + if (printReorder) { + printReorderings(); + delete globalParams; + exitCode = 0; + goto err0; + } + fileName = new GooString(argv[1]); if (fixedPitch) { physLayout = gTrue; @@ -207,6 +222,9 @@ int main(int argc, char *argv[]) { if (textEncName[0]) { globalParams->setTextEncoding(textEncName); } + if (textReorderName[0]) { + globalParams->setRTLReordering(textReorderName); + } if (textEOL[0]) { if (!globalParams->setTextEOL(textEOL)) { fprintf(stderr, "Bad '-eol' value on command line\n"); @@ -225,6 +243,8 @@ int main(int argc, char *argv[]) { delete fileName; goto err1; } + + reorderingMode = globalParams->getRTLReordering(); // open PDF file if (ownerPassword[0] != '\001') { @@ -339,7 +359,8 @@ int main(int argc, char *argv[]) { // write text file if (bbox) { - textOut = new TextOutputDev(NULL, physLayout, fixedPitch, rawOrder, htmlMeta); + textOut = new TextOutputDev(NULL, physLayout, fixedPitch, rawOrder, htmlMeta, + reorderingMode); if (!(f = fopen(textFileName->getCString(), "ab"))) { error(errIO, -1, "Couldn't open text file '{0:t}' for append", textFileName); exitCode = 2; @@ -373,7 +394,7 @@ int main(int argc, char *argv[]) { fclose(f); } else { textOut = new TextOutputDev(textFileName->getCString(), - physLayout, fixedPitch, rawOrder, htmlMeta); + physLayout, fixedPitch, rawOrder, htmlMeta, reorderingMode); if (textOut->isOk()) { if ((w==0) && (h==0) && (x==0) && (y==0)) { doc->displayPages(textOut, firstPage, lastPage, resolution, resolution, 0, --- /dev/null +++ poppler-0.20.5/cmake/modules/FindICU.cmake @@ -0,0 +1,52 @@ +# Imperfect module to find the ICU library with cmake + +find_program(ICU_CONFIG icu-config) + +if(NOT ICU_CONFIG) + set(ICU_FOUND FALSE) +else(NOT ICU_CONFIG) + + execute_process(COMMAND ${ICU_CONFIG} --exists + RESULT_VARIABLE ICU_EXISTS_RESULT) + if(NOT ${ICU_EXISTS_RESULT} EQUAL 0) + set(ICU_FOUND FALSE) + else(NOT ${ICU_EXISTS_RESULT} EQUAL 0) + + execute_process(COMMAND ${ICU_CONFIG} --cppflags-searchpath + COMMAND sed s/^-I//g + OUTPUT_VARIABLE ICU_INCLUDE_DIRS) + + execute_process(COMMAND ${ICU_CONFIG} --ldflags-libsonly + COMMAND tr -d \n + COMMAND sed "s/[\t ]*-l/ /g" + COMMAND sed "s/^[\t ]*//" + COMMAND sed "s/[\t ]*$//" + OUTPUT_VARIABLE ICU_LIBRARY_NAMES) + + separate_arguments(ICU_LIBRARY_NAMES) + +# execute_process(COMMAND ${ICU_CONFIG} --ldflags-searchpath +# COMMAND sed s/^-L// +# OUTPUT_VARIABLE ICU_LIB_DIR) + + foreach(CURRENT_LIB_NAME ${ICU_LIBRARY_NAMES}) + set(CURRENT_LIBRARY ${CURRENT_LIB_NAME}-NOTFOUND) + find_library(CURRENT_LIBRARY ${CURRENT_LIB_NAME}) + list(APPEND ICU_LIBRARIES ${CURRENT_LIBRARY}) + endforeach(CURRENT_LIB_NAME ${ICU_LIBRARY_NAMES}) + + set(ICU_FOUND TRUE) + + endif(NOT ${ICU_EXISTS_RESULT} EQUAL 0) +endif(NOT ICU_CONFIG) + +if(ICU_FOUND) + if(NOT ICU_FIND_QUIETLY) + MESSAGE(STATUS "Found ICU") + endif(NOT ICU_FIND_QUIETLY) +else(ICU_FOUND) + if(ICU_FIND_REQUIRED) + MESSAGE(FATAL_ERROR "Could not find ICU") + endif(ICU_FIND_REQUIRED) +endif(ICU_FOUND) + --- poppler-0.20.5.orig/poppler/GlobalParams.cc +++ poppler-0.20.5/poppler/GlobalParams.cc @@ -586,6 +586,9 @@ GlobalParams::GlobalParams(const char *c residentUnicodeMaps = new GooHash(); unicodeMaps = new GooHash(gTrue); cMapDirs = new GooHash(gTrue); +#if HAVE_ICU + reorderingModes = new RTLReorderingModes(); +#endif toUnicodeDirs = new GooList(); fontFiles = new GooHash(gTrue); fontDirs = new GooList(); @@ -831,6 +834,9 @@ GlobalParams::~GlobalParams() { deleteGooList(list, GooString); } delete cMapDirs; +#if HAVE_ICU + delete reorderingModes; +#endif delete cidToUnicodeCache; delete unicodeToUnicodeCache; @@ -1936,6 +1942,22 @@ GooList *GlobalParams::getEncodingNames( return result; } +GooList *GlobalParams::getRTLReorderingNames() +{ + GooList *result = new GooList; +#if HAVE_ICU + GooHashIter *iter; + GooString *key; + void *val; + reorderingModes->startIter(&iter); + while (reorderingModes->getNext(&iter, &key, &val)) { + result->append(key); + } + reorderingModes->killIter(&iter); +#endif + return result; +} + //------------------------------------------------------------------------ // functions to set parameters //------------------------------------------------------------------------ @@ -2058,6 +2080,25 @@ void GlobalParams::setTextEncoding(char unlockGlobalParams; } +void GlobalParams::setRTLReordering(char *reorderingName) { +#if HAVE_ICU + lockGlobalParams; + reorderingMode = reorderingModes->lookup(reorderingName); + reorderingName = NULL; + unlockGlobalParams; +#endif +} + +#if HAVE_ICU +UBiDiReorderingMode GlobalParams::icu_ReorderingMode(bool inverse, ReorderingMode *modep) +{ + ReorderingMode mode = ReorderingDefault; + if (modep != NULL) + mode = *modep; + return reorderingModes->icu_ReorderingMode(mode, inverse); +} +#endif + GBool GlobalParams::setTextEOL(char *s) { lockGlobalParams; if (!strcmp(s, "unix")) { --- poppler-0.20.5.orig/poppler/GlobalParams.h +++ poppler-0.20.5/poppler/GlobalParams.h @@ -43,6 +43,7 @@ #include #include "goo/gtypes.h" #include "CharTypes.h" +#include "RTL.h" #if MULTITHREADED #include "goo/GooMutex.h" @@ -201,11 +202,16 @@ public: UnicodeMap *getUnicodeMap(GooString *encodingName); CMap *getCMap(GooString *collection, GooString *cMapName, Stream *stream = NULL); UnicodeMap *getTextEncoding(); + const ReorderingMode getRTLReordering() {return reorderingMode;} +#if HAVE_ICU + UBiDiReorderingMode icu_ReorderingMode(bool inverse=true, ReorderingMode *modep=NULL); +#endif #ifdef ENABLE_PLUGINS GBool loadPlugin(char *type, char *name); #endif GooList *getEncodingNames(); + GooList *getRTLReorderingNames(); //----- functions to set parameters void addFontFile(GooString *fontName, GooString *path); @@ -227,6 +233,7 @@ public: void setPSRasterResolution(double res); void setPSRasterMono(GBool mono); void setTextEncoding(char *encodingName); + void setRTLReordering(char *reorderingName); GBool setTextEOL(char *s); void setTextPageBreaks(GBool pageBreaks); void setTextKeepTinyChars(GBool keep); @@ -287,6 +294,9 @@ private: // codes, indexed by encoding name [GooString] GooHash *cMapDirs; // list of CMap dirs, indexed by collection // name [GooList[GooString]] +#if HAVE_ICU + RTLReorderingModes *reorderingModes; // rtl reordering modes +#endif GooList *toUnicodeDirs; // list of ToUnicode CMap dirs [GooString] GBool baseFontsInitialized; #ifdef _WIN32 @@ -329,6 +339,7 @@ private: // in color (RGB/CMYK) GooString *textEncoding; // encoding (unicodeMap) to use for text // output + ReorderingMode reorderingMode; EndOfLineKind textEOL; // type of EOL marker to use for text // output GBool textPageBreaks; // insert end-of-page markers? --- /dev/null +++ poppler-0.20.5/poppler/RTL.cc @@ -0,0 +1,112 @@ +//======================================================================== +// +// RTL.cc +// +// Copyright 2013 Alex Bodnaru +// +//======================================================================== + +//======================================================================== +// +// Modified under the Poppler project - http://poppler.freedesktop.org +// +// All changes made under the Poppler project to this file are licensed +// under GPL version 2 or later +// +// Copyright (C) 2013 Alex Bodnaru +// +// To see a description of the changes please see the Changelog file that +// came with your tarball or type make ChangeLog if you are building from git +// +//======================================================================== + +#include + +#ifdef USE_GCC_PRAGMAS +#pragma implementation +#endif + +#include "RTL.h" +#include "goo/GooString.h" +#include "goo/GooHash.h" + +//------------------------------------------------------------------------ +// RTL +//------------------------------------------------------------------------ + +RTLReorderingModes::RTLReorderingModes() +{ + static struct { + char *name; + ReorderingMode mode; + } reorderingModes[] = + { + {"none", ReorderingNotNeeded}, +#if HAVE_ICU + {"windows", ReorderingNumbersSpecial}, + {"unicode", ReorderingLikeDirect}, +#endif + {"default", ReorderingDefault}, + {"", ReorderingNotNeeded} + }; + reorderingNames = new GooHash(gTrue); + int c; + for (c = 0; *reorderingModes[c].name; ++c) + { + reorderingNames->add( + new GooString(reorderingModes[c].name), reorderingModes[c].mode); + } +} + +RTLReorderingModes::~RTLReorderingModes() +{ +} + +ReorderingMode RTLReorderingModes::lookup(const char *key) +{ + int mode = reorderingNames->lookupInt(key); + return mode ? ReorderingMode(mode) : ReorderingDefault; +} + +void RTLReorderingModes::startIter(GooHashIter **iter) +{ + reorderingNames->startIter(iter); +} + +void RTLReorderingModes::killIter(GooHashIter **iter) +{ + reorderingNames->killIter(iter); +} + +GBool RTLReorderingModes::getNext(GooHashIter **iter, GooString **key, void **val) +{ + return reorderingNames->getNext(iter, key, val); +} + +GBool RTLReorderingModes::getNext(GooHashIter **iter, GooString **key, int *val) +{ + return reorderingNames->getNext(iter, key, val); +} + +#if HAVE_ICU +UBiDiReorderingMode RTLReorderingModes::icu_ReorderingMode(ReorderingMode mode, bool inverse) +{ + switch (mode) + { + case ReorderingNumbersSpecial: // windows + return inverse ? UBIDI_REORDER_INVERSE_FOR_NUMBERS_SPECIAL : UBIDI_REORDER_NUMBERS_SPECIAL; + case ReorderingLikeDirect: // unicode + return inverse ? UBIDI_REORDER_INVERSE_LIKE_DIRECT : UBIDI_REORDER_DEFAULT; + case ReorderingDefault: + return icu_ReorderingMode( +#ifdef _WIN32 + ReorderingNumbersSpecial, +#else + ReorderingLikeDirect, +#endif + inverse); + default: + return UBIDI_REORDER_DEFAULT; + }; +} +#endif --- poppler-0.20.5.orig/poppler/TextOutputDev.h +++ poppler-0.20.5/poppler/TextOutputDev.h @@ -37,6 +37,7 @@ #include "goo/gtypes.h" #include "GfxFont.h" #include "GfxState.h" +#include "RTL.h" #include "OutputDev.h" class GooString; @@ -483,7 +484,8 @@ class TextPage { public: // Constructor. - TextPage(GBool rawOrderA); + TextPage(GBool rawOrderA, + ReorderingMode reordering_modeA=ReorderingDefault); void incRefCnt(); void decRefCnt(); @@ -611,6 +613,7 @@ private: int primaryRot; // primary rotation GBool primaryLR; // primary direction (true means L-to-R, // false means R-to-L) + ReorderingMode reordering_mode; TextWord *rawWords; // list of words, in raw order (only if // rawOrder is set) TextWord *rawLastWord; // last word on rawWords list @@ -678,7 +681,8 @@ public: // content stream order. TextOutputDev(char *fileName, GBool physLayoutA, double fixedPitchA, GBool rawOrderA, - GBool append); + GBool append, + ReorderingMode reordering_modeA=ReorderingDefault); // Create a TextOutputDev which will write to a generic stream. If // is true, the original physical layout of the text @@ -686,7 +690,8 @@ public: // content stream order. TextOutputDev(TextOutputFunc func, void *stream, GBool physLayoutA, double fixedPitchA, - GBool rawOrderA); + GBool rawOrderA, + ReorderingMode reordering_modeA=ReorderingDefault); // Destructor. virtual ~TextOutputDev(); @@ -817,6 +822,7 @@ private: GBool rawOrder; // keep text in content stream order GBool doHTML; // extra processing for HTML conversion GBool ok; // set up ok? + ReorderingMode reordering_mode; ActualText *actualText; }; --- /dev/null +++ poppler-0.20.5/poppler/RTL.h @@ -0,0 +1,71 @@ +//======================================================================== +// +// RTL.h +// +// Copyright 2013 Alex Bodnaru +// +//======================================================================== + +//======================================================================== +// +// Modified under the Poppler project - http://poppler.freedesktop.org +// +// All changes made under the Poppler project to this file are licensed +// under GPL version 2 or later +// +// Copyright (C) 2013 Alex Bodnaru +// +// To see a description of the changes please see the Changelog file that +// came with your tarball or type make ChangeLog if you are building from git +// +//======================================================================== + +#ifndef RTL_H +#define RTL_H + +#ifdef USE_GCC_PRAGMAS +#pragma interface +#endif + +#include "poppler-config.h" +#if HAVE_ICU +#include +#endif +#include "goo/gtypes.h" +class GooString; +class GooHash; +class GooHashIter; + +enum ReorderingMode { + ReorderingNotNeeded=1, // 0 would mess the lookup +#if HAVE_ICU + // windows + ReorderingNumbersSpecial, + // unicode + ReorderingLikeDirect, + ReorderingDefault +#else + ReorderingDefault=ReorderingNotNeeded +#endif +}; + +class RTLReorderingModes { +public: + RTLReorderingModes(); + virtual ~RTLReorderingModes(); + + ReorderingMode lookup(const char *key); + void startIter(GooHashIter **iter); + void killIter(GooHashIter **iter); + GBool getNext(GooHashIter **iter, GooString **key, void **val); + GBool getNext(GooHashIter **iter, GooString **key, int *val); + +#if HAVE_ICU + UBiDiReorderingMode icu_ReorderingMode(ReorderingMode mode, bool inverse=true); +#endif + +private: + GooHash *reorderingNames; +}; + +#endif --- poppler-0.20.5.orig/poppler/Makefile.am +++ poppler-0.20.5/poppler/Makefile.am @@ -138,10 +138,14 @@ cms_includes = $(LCMS_CFLAGS) cms_libs = $(LCMS_LIBS) endif +icu_includes = $(ICU_CFLAGS) +icu_libs = $(ICU_LIBS) + INCLUDES = \ -I$(top_srcdir) \ -I$(top_srcdir)/goo \ $(cms_includes) \ + $(icu_includes) \ $(splash_includes) \ $(cairo_includes) \ $(arthur_includes) \ @@ -165,6 +169,7 @@ libpoppler_la_LIBADD = \ $(top_builddir)/goo/libgoo.la \ $(top_builddir)/fofi/libfofi.la \ $(cms_libs) \ + $(icu_libs) \ $(splash_libs) \ $(libtiff_libs) \ $(libjpeg_libs) \ @@ -252,6 +257,7 @@ poppler_include_HEADERS = \ TextOutputDev.h \ SecurityHandler.h \ UTF8.h \ + RTL.h \ XpdfPluginAPI.h \ Sound.h nodist_poppler_include_HEADERS = poppler-config.h @@ -317,6 +323,7 @@ libpoppler_la_SOURCES = \ strtok_r.cpp \ UnicodeMap.cc \ UnicodeTypeTable.cc \ + RTL.cc \ ViewerPreferences.cc \ XRef.cc \ PSOutputDev.cc \ --- poppler-0.20.5.orig/poppler/TextOutputDev.cc +++ poppler-0.20.5/poppler/TextOutputDev.cc @@ -48,6 +48,10 @@ #include #include #include +#if HAVE_ICU +#include +#include +#endif #ifdef _WIN32 #include // for O_BINARY #include // for setmode @@ -2050,11 +2054,13 @@ TextWord *TextWordList::get(int idx) { // TextPage //------------------------------------------------------------------------ -TextPage::TextPage(GBool rawOrderA) { +TextPage::TextPage(GBool rawOrderA, + ReorderingMode reordering_modeA) { int rot; refCnt = 1; rawOrder = rawOrderA; + reordering_mode = reordering_modeA; curWord = NULL; charPos = 0; curFont = NULL; @@ -3556,7 +3562,42 @@ GBool TextPage::findText(Unicode *s, int double xMin1, yMin1, xMax1, yMax1; GBool found; - //~ needs to handle right-to-left text +#if HAVE_ICU + UBiDi *bidi = NULL; + UErrorCode err; + UChar *output = NULL, *input = NULL; + int32_t ulen; + UConverter *conv32 = NULL; + + err = U_ZERO_ERROR; + conv32 = ucnv_open("UTF-32_PlatformEndian", &err); + ulen = ucnv_toUChars( + conv32, NULL, 0, (const char *) s, len * sizeof(Unicode), &err); + input = new UChar[ulen]; + output = new UChar[ulen]; + bidi = ubidi_open(); + + if (input && output && bidi && conv32) { + UBiDiReorderingMode ubidi_reordering_mode = + globalParams->icu_ReorderingMode(false, &reordering_mode); + UBiDiLevel level = (primaryLR) ? UBIDI_DEFAULT_LTR : UBIDI_DEFAULT_RTL; + err = U_ZERO_ERROR; + ulen = ucnv_toUChars( + conv32, input, ulen, (const char *) s, len * sizeof(Unicode), &err); + ubidi_setReorderingMode( bidi, ubidi_reordering_mode ); + ubidi_setReorderingOptions(bidi, UBIDI_OPTION_REMOVE_CONTROLS); + ubidi_setPara( bidi, input, len, level, NULL, &err ); + ubidi_writeReordered( bidi, output, len, UBIDI_DO_MIRRORING, &err ); + ucnv_fromUChars( + conv32, (char *) s, len * sizeof(Unicode), output, ulen, &err); + } + if (input != NULL) + delete input; + if (output != NULL) + delete output; + ubidi_close(bidi); + ucnv_close(conv32); +#endif if (rawOrder) { return gFalse; @@ -5107,89 +5148,77 @@ void TextPage::assignColumns(TextLineFra int TextPage::dumpFragment(Unicode *text, int len, UnicodeMap *uMap, GooString *s) { - char lre[8], rle[8], popdf[8], buf[8]; - int lreLen, rleLen, popdfLen, n; - int nCols, i, j, k; - - nCols = 0; + char buf[8]; + int nCols = 0, i, n; + +#if HAVE_ICU + if (reordering_mode != ReorderingNotNeeded && uMap->isUnicode()) { - if (uMap->isUnicode()) { + char lre[8], rle[8], popdf[8]; + int lreLen, rleLen, popdfLen, j, k; + UBiDi *bidi = NULL; + UErrorCode err = U_ZERO_ERROR; + UBiDiLevel level = UBIDI_DEFAULT_LTR; + UChar *output = NULL, *input = NULL; + int32_t ulen; + UConverter *conv32 = NULL; lreLen = uMap->mapUnicode(0x202a, lre, sizeof(lre)); rleLen = uMap->mapUnicode(0x202b, rle, sizeof(rle)); popdfLen = uMap->mapUnicode(0x202c, popdf, sizeof(popdf)); - if (primaryLR) { - - i = 0; - while (i < len) { - // output a left-to-right section - for (j = i; j < len && !unicodeTypeR(text[j]); ++j) ; - for (k = i; k < j; ++k) { - n = uMap->mapUnicode(text[k], buf, sizeof(buf)); - s->append(buf, n); - ++nCols; - } - i = j; - // output a right-to-left section - for (j = i; - j < len && !(unicodeTypeL(text[j]) || unicodeTypeNum(text[j])); - ++j) ; - if (j > i) { - s->append(rle, rleLen); - for (k = j - 1; k >= i; --k) { - n = uMap->mapUnicode(text[k], buf, sizeof(buf)); - s->append(buf, n); - ++nCols; - } - s->append(popdf, popdfLen); - i = j; - } + conv32 = ucnv_open("UTF-32_PlatformEndian", &err); + ulen = ucnv_toUChars( + conv32, NULL, 0, (const char *) text, len * sizeof(Unicode), &err); + input = new UChar[ulen]; + output = new UChar[ulen]; + bidi = ubidi_open(); + + if (input && output && bidi && conv32) { + UBiDiReorderingMode ubidi_reordering_mode = + globalParams->icu_ReorderingMode(true, &reordering_mode); + if (primaryLR) { + level = UBIDI_DEFAULT_LTR; + s->append(lre, lreLen); } - - } else { - - // Note: This code treats numeric characters (European and - // Arabic/Indic) as left-to-right, which isn't strictly correct - // (incurs extra LRE/POPDF pairs), but does produce correct - // visual formatting. - s->append(rle, rleLen); - i = len - 1; - while (i >= 0) { - // output a right-to-left section - for (j = i; - j >= 0 && !(unicodeTypeL(text[j]) || unicodeTypeNum(text[j])); - --j) ; - for (k = i; k > j; --k) { - n = uMap->mapUnicode(text[k], buf, sizeof(buf)); - s->append(buf, n); - ++nCols; - } - i = j; - // output a left-to-right section - for (j = i; j >= 0 && !unicodeTypeR(text[j]); --j) ; - if (j < i) { - s->append(lre, lreLen); - for (k = j + 1; k <= i; ++k) { - n = uMap->mapUnicode(text[k], buf, sizeof(buf)); - s->append(buf, n); - ++nCols; - } - s->append(popdf, popdfLen); - i = j; - } + else { + level = UBIDI_DEFAULT_RTL; + s->append(rle, rleLen); + } + err = U_ZERO_ERROR; + ulen = ucnv_toUChars( + conv32, input, ulen, (const char *) text, len * sizeof(Unicode), &err); + ubidi_setReorderingMode( bidi, ubidi_reordering_mode ); + ubidi_setReorderingOptions(bidi, UBIDI_OPTION_REMOVE_CONTROLS); + ubidi_setPara( bidi, input, len, level, NULL, &err ); + ubidi_writeReordered( bidi, output, len, UBIDI_DO_MIRRORING, &err ); + ucnv_fromUChars(conv32, (char *) text, len * sizeof(Unicode), + output, ulen, &err); + UCharCharacterIterator iter(output, ulen); + for (iter.first(); iter.current() != CharacterIterator::DONE; iter.next()) { + n = uMap->mapUnicode(iter.current(), buf, sizeof(buf)); + s->append(buf, n); + ++nCols; } s->append(popdf, popdfLen); - + if (input != NULL) + delete input; + if (output != NULL) + delete output; + ubidi_close(bidi); + ucnv_close(conv32); } - - } else { + } + else { +#endif for (i = 0; i < len; ++i) { n = uMap->mapUnicode(text[i], buf, sizeof(buf)); s->append(buf, n); nCols += n; } +#if (HAVE_ICU) } +#endif return nCols; } @@ -5298,11 +5327,12 @@ static void TextOutputDev_outputToFile(v TextOutputDev::TextOutputDev(char *fileName, GBool physLayoutA, double fixedPitchA, GBool rawOrderA, - GBool append) { + GBool append, ReorderingMode reordering_modeA) { text = NULL; physLayout = physLayoutA; fixedPitch = physLayout ? fixedPitchA : 0; rawOrder = rawOrderA; + reordering_mode = reordering_modeA; doHTML = gFalse; ok = gTrue; @@ -5329,21 +5359,22 @@ TextOutputDev::TextOutputDev(char *fileN } // set up text object - text = new TextPage(rawOrderA); + text = new TextPage(rawOrderA, reordering_modeA); actualText = new ActualText(text); } TextOutputDev::TextOutputDev(TextOutputFunc func, void *stream, GBool physLayoutA, double fixedPitchA, - GBool rawOrderA) { + GBool rawOrderA, ReorderingMode reordering_modeA) { outputFunc = func; outputStream = stream; needClose = gFalse; physLayout = physLayoutA; fixedPitch = physLayout ? fixedPitchA : 0; rawOrder = rawOrderA; + reordering_mode = reordering_modeA; doHTML = gFalse; - text = new TextPage(rawOrderA); + text = new TextPage(rawOrderA, reordering_modeA); actualText = new ActualText(text); ok = gTrue; } @@ -5610,6 +5641,6 @@ TextPage *TextOutputDev::takeText() { TextPage *ret; ret = text; - text = new TextPage(rawOrder); + text = new TextPage(rawOrder, reordering_mode); return ret; }