]> git.lyx.org Git - lyx.git/blobdiff - lib/configure.py
Merge remote-tracking branch 'features/str-metrics'
[lyx.git] / lib / configure.py
index 61e007f088a6b5ea5d25497794f40cd8430ee5b3..08384bf90e4e1946076440bc18f61ddc1667c52e 100644 (file)
@@ -8,7 +8,7 @@
 # \author Bo Peng
 # Full author contact details are available in file CREDITS.
 
-import glob, logging, os, re, shutil, subprocess, sys
+import glob, logging, os, re, shutil, subprocess, sys, stat
 
 # set up logging
 logging.basicConfig(level = logging.DEBUG,
@@ -104,6 +104,73 @@ def setEnviron():
     os.environ['LC_CTYPE'] = os.getenv('LC_CTYPE', 'C')
 
 
+def copy_tree(src, dst, preserve_symlinks=False, level=0):
+    ''' Copy an entire directory tree 'src' to a new location 'dst'.
+    Code inspired from distutils.copy_tree.
+        Copying ignores non-regular files and the cache directory.
+    Pipes may be present as leftovers from LyX for lyx-server.
+
+    If 'preserve_symlinks' is true, symlinks will be
+    copied as symlinks (on platforms that support them!); otherwise
+    (the default), the destination of the symlink will be copied.
+    '''
+    if not os.path.isdir(src):
+        raise FileError, \
+              "cannot copy tree '%s': not a directory" % src
+    try:
+        names = os.listdir(src)
+    except os.error, (errno, errstr):
+        raise FileError, \
+              "error listing files in '%s': %s" % (src, errstr)
+    if not os.path.isdir(dst):
+        os.makedirs(dst)
+    outputs = []
+    for name in names:
+        src_name = os.path.join(src, name)
+        dst_name = os.path.join(dst, name)
+        if preserve_symlinks and os.path.islink(src_name):
+            link_dest = os.readlink(src_name)
+            os.symlink(link_dest, dst_name)
+            outputs.append(dst_name)
+        elif level == 0 and name == 'cache':
+            logger.info("Skip cache %s", src_name)
+        elif os.path.isdir(src_name):
+            outputs.extend(
+                copy_tree(src_name, dst_name, preserve_symlinks, level=(level + 1)))
+        elif stat.S_ISREG(os.stat(src_name).st_mode) or os.path.islink(src_name):
+            shutil.copy2(src_name, dst_name)
+            outputs.append(dst_name)
+        else:
+            logger.info("Ignore non-regular file %s", src_name)
+    return outputs
+
+
+def checkUpgrade():
+    ''' Check for upgrade from previous version '''
+    cwd = os.getcwd()
+    basename = os.path.basename( cwd )
+    lyxrc = os.path.join(cwd, outfile)
+    if not os.path.isfile( lyxrc ) and basename.endswith( version_suffix ) :
+        logger.info('Checking for upgrade from previous version.')
+        parent = os.path.dirname(cwd)
+        appname = basename[:(-len(version_suffix))]
+        for version in ['-2.1', '-2.0', '-1.6' ]:
+            logger.debug('Checking for upgrade from previous version ' + version)
+            previous = os.path.join(parent, appname + version)
+            logger.debug('previous = ' + previous)
+            if os.path.isdir( previous ):
+                logger.info('Found directory "%s".', previous)
+                copy_tree( previous, cwd )
+                logger.info('Content copied to directory "%s".', cwd)
+                return
+
+
 def createDirectories():
     ''' Create the build directories if necessary '''
     for dir in ['bind', 'clipart', 'doc', 'examples', 'images', 'kbd', \
@@ -198,6 +265,8 @@ def checkProg(description, progs, rc_entry = [], path = [], not_found = ''):
         if "PATHEXT" in os.environ:
             extlist = extlist + os.environ["PATHEXT"].split(os.pathsep)
         for ac_dir in path:
+            if hasattr(os, "access") and not os.access(ac_dir, os.F_OK):
+                continue
             for ext in extlist:
                 if os.path.isfile( os.path.join(ac_dir, ac_word + ext) ):
                     logger.info(msg + ' yes')
@@ -252,6 +321,8 @@ def checkProgAlternatives(description, progs, rc_entry = [], alt_rc_entry = [],
             extlist = extlist + os.environ["PATHEXT"].split(os.pathsep)
         found_alt = False
         for ac_dir in path:
+            if hasattr(os, "access") and not os.access(ac_dir, os.F_OK):
+                continue
             for ext in extlist:
                 if os.path.isfile( os.path.join(ac_dir, ac_word + ext) ):
                     logger.info(msg + ' yes')
@@ -408,7 +479,7 @@ def checkLatex(dtl_tools):
         # run platex on chklatex.ltx and check result
         if cmdOutput(PLATEX + ' chklatex.ltx').find('pLaTeX2e') != -1:
             # We have the Japanese pLaTeX2e
-            addToRC(r'\converter platex     dvi        "%s -kanji=$$E $$i"     "latex=platex"' % PLATEX)
+            addToRC(r'\converter platex   dvi       "%s"   "latex=platex"' % PLATEX)
         else:
             PLATEX = ''
             removeFiles(['chklatex.ltx', 'chklatex.log'])
@@ -549,6 +620,7 @@ def checkFormatEntries(dtl_tools):
 \Format luatex     tex    "LaTeX (LuaTeX)"        "" ""        "%%"    "document,menu=export"  ""
 \Format pdflatex   tex    "LaTeX (pdflatex)"      "" ""        "%%"    "document,menu=export"  ""
 \Format xetex      tex    "LaTeX (XeTeX)"         "" ""        "%%"    "document,menu=export"  ""
+\Format latexclipboard tex "LaTeX (clipboard)"    "" ""        "%%"    ""      ""
 \Format text       txt    "Plain text"            a  ""        "%%"    "document,menu=export"  "text/plain"
 \Format text2      txt    "Plain text (pstotext)" "" ""        "%%"    "document"      ""
 \Format text3      txt    "Plain text (ps2ascii)" "" ""        "%%"    "document"      ""
@@ -574,20 +646,22 @@ def checkFormatEntries(dtl_tools):
     #
     #checkProg('a Postscript interpreter', ['gs'],
     #  rc_entry = [ r'\ps_command "%%"' ])
-    checkViewer('a Postscript previewer', ['kghostview', 'okular', 'evince', 'gv', 'ghostview -swap'],
+    checkViewer('a Postscript previewer', ['kghostview', 'okular', 'qpdfview --unique', 'evince', 'gv', 'ghostview -swap', 'gsview64', 'gsview32'],
         rc_entry = [r'''\Format eps        eps     EPS                    "" "%%"      ""      "vector"        "image/x-eps"
 \Format eps2       eps    "EPS (uncropped)"       "" "%%"      ""      "vector"        ""
+\Format eps3       eps    "EPS (cropped)"         "" "%%"      ""      "document,menu=export"  ""
 \Format ps         ps      Postscript             t  "%%"      ""      "document,vector,menu=export"   "application/postscript"'''])
     # for xdg-open issues look here: http://www.mail-archive.com/lyx-devel@lists.lyx.org/msg151818.html
     # the MIME type is set for pdf6, because that one needs to be autodetectable by libmime
-    checkViewer('a PDF previewer', ['pdfview', 'kpdf', 'okular', 'evince', 'kghostview', 'xpdf', 'acrobat', 'acroread', \
-                   'gv', 'ghostview'],
+    checkViewer('a PDF previewer', ['pdfview', 'kpdf', 'okular', 'qpdfview --unique', 'evince', 'kghostview', 'xpdf', 'SumatraPDF', 'acrobat', 'acroread', 'mupdf', \
+                   'gv', 'ghostview', 'AcroRd32', 'gsview64', 'gsview32'],
         rc_entry = [r'''\Format pdf        pdf    "PDF (ps2pdf)"          P  "%%"      ""      "document,vector,menu=export"   ""
 \Format pdf2       pdf    "PDF (pdflatex)"        F  "%%"      ""      "document,vector,menu=export"   ""
 \Format pdf3       pdf    "PDF (dvipdfm)"         m  "%%"      ""      "document,vector,menu=export"   ""
 \Format pdf4       pdf    "PDF (XeTeX)"           X  "%%"      ""      "document,vector,menu=export"   ""
 \Format pdf5       pdf    "PDF (LuaTeX)"          u  "%%"      ""      "document,vector,menu=export"   ""
-\Format pdf6       pdf    "PDF (graphics)"        "" "%%"      ""      "vector"        "application/pdf"'''])
+\Format pdf6       pdf    "PDF (graphics)"        "" "%%"      ""      "vector"        "application/pdf"
+\Format pdf7       pdf    "PDF (cropped)"         "" "%%"      ""      "document,menu=export"  ""'''])
     #
     checkViewer('a DVI previewer', ['xdvi', 'kdvi', 'okular', 'yap', 'dviout -Set=!m'],
         rc_entry = [r'''\Format dvi        dvi     DVI                    D  "%%"      ""      "document,vector,menu=export"   "application/x-dvi"
@@ -618,8 +692,9 @@ def checkFormatEntries(dtl_tools):
 \Format lyx13x     13.lyx "LyX 1.3.x"             "" ""        ""      "document"      ""
 \Format lyx14x     14.lyx "LyX 1.4.x"             "" ""        ""      "document"      ""
 \Format lyx15x     15.lyx "LyX 1.5.x"             "" ""        ""      "document"      ""
-\Format lyx16x     16.lyx "LyX 1.6.x"             "" ""        ""      "document,menu=export"  ""
-\Format lyx20x     20.lyx "LyX 2.0.x"             "" ""        ""      "document,menu=export"  ""
+\Format lyx16x     16.lyx "LyX 1.6.x"             "" ""        ""      "document"      ""
+\Format lyx20x     20.lyx "LyX 2.0.x"             "" ""        ""      "document"      ""
+\Format lyx21x     21.lyx "LyX 2.1.x"             "" ""        ""      "document,menu=export"  ""
 \Format clyx       cjklyx "CJK LyX 1.4.x (big5)"  "" ""        ""      "document"      ""
 \Format jlyx       cjklyx "CJK LyX 1.4.x (euc-jp)" "" ""       ""      "document"      ""
 \Format klyx       cjklyx "CJK LyX 1.4.x (euc-kr)" "" ""       ""      "document"      ""
@@ -644,16 +719,22 @@ def checkConverterEntries():
     checkLuatex()
 
     # Look for tex2lyx in this order (see bugs #3308 and #6986):
-    #   1)  If we're running LyX in-place then tex2lyx will be found
-    #       in ../src/tex2lyx with respect to the srcdir.
-    #   2)  If LyX was configured with a version suffix then tex2lyx
+    #   1)  If we're building LyX with autotools then tex2lyx is found
+    #       in the subdirectory tex2lyx with respect to the binary dir.
+    #   2)  If we're building LyX with cmake then tex2lyx is found
+    #       in the binary dir.
+    #   3)  If LyX was configured with a version suffix then tex2lyx
     #       will also have this version suffix.
-    #   3)  Otherwise always use tex2lyx.
-    in_place = os.path.join(srcdir, '..', 'src', 'tex2lyx', 'tex2lyx')
-    in_place = os.path.abspath(in_place)
+    #   4)  Otherwise always use tex2lyx.
+    in_binary_subdir = os.path.join(lyx_binary_dir, 'tex2lyx', 'tex2lyx')
+    in_binary_subdir = os.path.abspath(in_binary_subdir)
+
+    in_binary_dir = os.path.join(lyx_binary_dir, 'tex2lyx')
+    in_binary_dir = os.path.abspath(in_binary_dir)
 
-    path, t2l = checkProg('a LaTeX/Noweb -> LyX converter', [in_place, 'tex2lyx' + version_suffix, 'tex2lyx'],
+    path, t2l = checkProg('a LaTeX/Noweb -> LyX converter', [in_binary_subdir, in_binary_subdir + version_suffix, in_binary_dir, in_binary_dir + version_suffix, 'tex2lyx' + version_suffix, 'tex2lyx'],
         rc_entry = [r'''\converter latex      lyx        "%% -f $$i $$o"       ""
+\converter latexclipboard lyx        "%% -fixedenc utf8 -f $$i $$o"    ""
 \converter literate   lyx        "%% -n -m noweb -f $$i $$o"   ""'''], not_found = 'tex2lyx')
     if path == '':
         logger.warning("Failed to find tex2lyx on your system.")
@@ -662,6 +743,7 @@ def checkConverterEntries():
     checkProg('a Noweb -> LaTeX converter', ['noweave -delay -index $$i > $$o'],
         rc_entry = [r'''\converter literate   latex      "%%"  ""
 \converter literate   pdflatex      "%%"       ""
+\converter literate   xetex         "%%"       ""
 \converter literate   luatex        "%%"       ""'''])
     #
     checkProg('a Sweave -> LaTeX converter', ['Rscript --verbose --no-save --no-restore $$s/scripts/lyxsweave.R $$p$$i $$p$$o $$e $$r'],
@@ -679,12 +761,15 @@ def checkConverterEntries():
     checkProg('a Sweave -> R/S code converter', ['Rscript --verbose --no-save --no-restore $$s/scripts/lyxstangle.R $$i $$e $$r'], 
         rc_entry = [ r'\converter sweave      r      "%%"    ""' ])
     #
-    checkProg('a knitr -> R/S code converter', ['Rscript --verbose --no-save --no-restore $$s/scripts/lyxknitr.R $$p$$i $$p$$o $$e $$r tangle'], 
+    checkProg('a knitr -> R/S code converter', ['Rscript --verbose --no-save --no-restore $$s/scripts/lyxknitr.R $$p$$i $$p$$o $$e $$r tangle'],
         rc_entry = [ r'\converter knitr      r      "%%"    ""' ])
     #
-    checkProg('an HTML -> LaTeX converter', ['html2latex $$i', 'gnuhtml2latex -s $$i > $$o',
+    checkProg('an HTML -> LaTeX converter', ['html2latex $$i', 'gnuhtml2latex',
         'htmltolatex -input $$i -output $$o', 'htmltolatex.jar -input $$i -output $$o'],
-        rc_entry = [ r'\converter html       latex      "%%"   ""' ])
+        rc_entry = [ r'\converter html       latex      "%%"   ""', \
+                     r'\converter html       latex      "python -tt $$s/scripts/html2latexwrapper.py %% $$i $$o"       ""', \
+                     r'\converter html       latex      "%%"   ""', \
+                     r'\converter html       latex      "%%"   ""', '' ])
     #
     checkProg('an MS Word -> LaTeX converter', ['wvCleanLatex $$i $$o'],
         rc_entry = [ r'\converter word       latex      "%%"   ""' ])
@@ -753,7 +838,7 @@ def checkConverterEntries():
     checkProg('a RTF -> HTML converter', ['unrtf --html  $$i > $$o'],
         rc_entry = [ r'\converter rtf      html        "%%"    ""' ])
     # Do not define a converter to pdf6, ps is a pure export format 
-    checkProg('a PS to PDF converter', ['ps2pdf13 $$i $$o'],
+    checkProg('a PS to PDF converter', ['ps2pdf $$i $$o'],
         rc_entry = [ r'\converter ps         pdf        "%%"   ""' ])
     #
     checkProg('a PS to TXT converter', ['pstotext $$i > $$o'],
@@ -777,6 +862,9 @@ def checkConverterEntries():
     checkProg('a PDF to EPS converter', ['pdftops -eps -f 1 -l 1 $$i $$o'],
         rc_entry = [ r'\converter pdf6        eps        "%%"  ""' ])
     #
+    checkProg('a PDF cropping tool', ['pdfcrop $$i $$o'],
+        rc_entry = [ r'\converter pdf2   pdf7       "%%"       ""' ])
+    #
     checkProg('a Beamer info extractor', ['makebeamerinfo -p $$i'],
         rc_entry = [ r'\converter pdf2         beamer.info        "%%" ""' ])
     #
@@ -786,6 +874,9 @@ def checkConverterEntries():
     checkProg('a DVI to PS converter', ['dvips -o $$o $$i'],
         rc_entry = [ r'\converter dvi        ps         "%%"   ""' ])
     #
+    checkProg('a DVI to cropped EPS converter', ['dvips -E -o $$o $$i'],
+        rc_entry = [ r'\converter dvi        eps3         "%%" ""' ])
+    #
     checkProg('a DVI to PDF converter', ['dvipdfmx -o $$o $$i', 'dvipdfm -o $$o $$i'],
         rc_entry = [ r'\converter dvi        pdf3       "%%"   ""' ])
     #
@@ -801,14 +892,13 @@ def checkConverterEntries():
 \converter fig        pstex      "python -tt $$s/scripts/fig2pstex.py $$i $$o" ""''')
     #
     checkProg('a TIFF -> PS converter', ['tiff2ps $$i > $$o'],
-        rc_entry = [ r'\converter tiff       eps        "%%"   ""', ''])
+        rc_entry = [ r'\converter tiff       eps        "%%"   ""'])
     #
     checkProg('a TGIF -> EPS/PPM converter', ['tgif'],
         rc_entry = [
             r'''\converter tgif       eps        "tgif -print -color -eps -stdout $$i > $$o"   ""
 \converter tgif       png        "tgif -print -color -png -o $$d $$i"  ""
-\converter tgif       pdf6       "tgif -print -color -pdf -stdout $$i > $$o"   ""''',
-            ''])
+\converter tgif       pdf6       "tgif -print -color -pdf -stdout $$i > $$o"   ""'''])
     #
     checkProg('a WMF -> EPS converter', ['metafile2eps $$i $$o', 'wmf2eps -o $$o $$i'],
         rc_entry = [ r'\converter wmf        eps        "%%"   ""'])
@@ -817,10 +907,10 @@ def checkConverterEntries():
         rc_entry = [ r'\converter emf        eps        "%%"   ""'])
     # Only define a converter to pdf6 for graphics
     checkProg('an EPS -> PDF converter', ['epstopdf'],
-        rc_entry = [ r'\converter eps        pdf6       "epstopdf --outfile=$$o $$i"   ""', ''])
+        rc_entry = [ r'\converter eps        pdf6       "epstopdf --outfile=$$o $$i"   ""'])
     #
     checkProg('an EPS -> PNG converter', ['convert $$i $$o'],
-        rc_entry = [ r'\converter eps        png        "%%"   ""', ''])
+        rc_entry = [ r'\converter eps        png        "%%"   ""'])
     #
     # no agr -> pdf6 converter, since the pdf library used by gracebat is not
     # free software and therefore not compiled in in many installations.
@@ -831,14 +921,12 @@ def checkConverterEntries():
             r'''\converter agr        eps        "gracebat -hardcopy -printfile $$o -hdevice EPS $$i 2>/dev/null"      ""
 \converter agr        png        "gracebat -hardcopy -printfile $$o -hdevice PNG $$i 2>/dev/null"      ""
 \converter agr        jpg        "gracebat -hardcopy -printfile $$o -hdevice JPEG $$i 2>/dev/null"     ""
-\converter agr        ppm        "gracebat -hardcopy -printfile $$o -hdevice PNM $$i 2>/dev/null"      ""''',
-            ''])
+\converter agr        ppm        "gracebat -hardcopy -printfile $$o -hdevice PNM $$i 2>/dev/null"      ""'''])
     #
     checkProg('a Dot -> Image converter', ['dot'],
         rc_entry = [
             r'''\converter dot        eps        "dot -Teps $$i -o $$o"        ""
-\converter dot        png        "dot -Tpng $$i -o $$o"        ""''',
-            ''])
+\converter dot        png        "dot -Tpng $$i -o $$o"        ""'''])
     #
     checkProg('a Dia -> PNG converter', ['dia -e $$o -t png $$i'],
         rc_entry = [ r'\converter dia        png        "%%"   ""'])
@@ -866,8 +954,7 @@ def checkConverterEntries():
     checkProg('a spreadsheet -> latex converter', ['ssconvert'],
        rc_entry = [ r'''\converter gnumeric latex "ssconvert --export-type=Gnumeric_html:latex $$i $$o" ""
 \converter oocalc latex "ssconvert --export-type=Gnumeric_html:latex $$i $$o" ""
-\converter excel  latex "ssconvert --export-type=Gnumeric_html:latex $$i $$o" ""''',
-''])
+\converter excel  latex "ssconvert --export-type=Gnumeric_html:latex $$i $$o" ""'''])
 
     path, lilypond = checkProg('a LilyPond -> EPS/PDF/PNG converter', ['lilypond'])
     if (lilypond != ''):
@@ -918,7 +1005,7 @@ def checkConverterEntries():
             logger.info('+  found LilyPond-book, but could not extract version number.')
     #
     checkProg('a Noteedit -> LilyPond converter', ['noteedit --export-lilypond $$i'],
-        rc_entry = [ r'\converter noteedit   lilypond   "%%"   ""', ''])
+        rc_entry = [ r'\converter noteedit   lilypond   "%%"   ""' ])
     #
     # Currently, lyxpak outputs a gzip compressed tar archive on *nix
     # and a zip archive on Windows.
@@ -946,6 +1033,7 @@ def checkConverterEntries():
 \converter lyx        lyx15x     "python -tt $$s/lyx2lyx/lyx2lyx -t 276 $$i > $$o"     ""
 \converter lyx        lyx16x     "python -tt $$s/lyx2lyx/lyx2lyx -t 345 $$i > $$o"     ""
 \converter lyx        lyx20x     "python -tt $$s/lyx2lyx/lyx2lyx -t 413 $$i > $$o"     ""
+\converter lyx        lyx21x     "python -tt $$s/lyx2lyx/lyx2lyx -t 474 $$i > $$o"     ""
 \converter lyx        clyx       "python -tt $$s/lyx2lyx/lyx2lyx -c big5 -t 245 $$i > $$o"     ""
 \converter lyx        jlyx       "python -tt $$s/lyx2lyx/lyx2lyx -c euc_jp -t 245 $$i > $$o"   ""
 \converter lyx        klyx       "python -tt $$s/lyx2lyx/lyx2lyx -c euc_kr -t 245 $$i > $$o"   ""
@@ -962,7 +1050,8 @@ def checkDocBook():
     path, DOCBOOK = checkProg('SGML-tools 2.x (DocBook), db2x scripts or xsltproc', ['sgmltools', 'db2dvi', 'xsltproc'],
         rc_entry = [
             r'''\converter docbook    dvi        "sgmltools -b dvi $$i"        ""
-\converter docbook    html       "sgmltools -b html $$i"       ""''',
+\converter docbook    html       "sgmltools -b html $$i"       ""
+\converter docbook    ps         "sgmltools -b ps $$i" ""''',
             r'''\converter docbook    dvi        "db2dvi $$i"  ""
 \converter docbook    html       "db2html $$i" ""''',
             r'''\converter docbook    dvi        ""    ""
@@ -1390,10 +1479,11 @@ if __name__ == '__main__':
     lyx_check_config = True
     lyx_kpsewhich = True
     outfile = 'lyxrc.defaults'
-    lyxrc_fileformat = 11
+    lyxrc_fileformat = 17
     rc_entries = ''
     lyx_keep_temps = False
     version_suffix = ''
+    lyx_binary_dir = ''
     ## Parse the command line
     for op in sys.argv[1:]:   # default shell/for list is $*, the options
         if op in [ '-help', '--help', '-h' ]:
@@ -1404,6 +1494,7 @@ Options:
     --without-kpsewhich      do not update TeX files information via kpsewhich
     --without-latex-config   do not run LaTeX to determine configuration
     --with-version-suffix=suffix suffix of binary installed files
+    --binary-dir=directory   directory of binary installed files
 '''
             sys.exit(0)
         elif op == '--without-kpsewhich':
@@ -1414,6 +1505,8 @@ Options:
             lyx_keep_temps = True
         elif op[0:22] == '--with-version-suffix=':  # never mind if op is not long enough
             version_suffix = op[22:]
+        elif op[0:13] == '--binary-dir=':
+            lyx_binary_dir = op[13:]
         else:
             print "Unknown option", op
             sys.exit(1)
@@ -1426,6 +1519,8 @@ Options:
         logger.error("configure: error: cannot find chkconfig.ltx script")
         sys.exit(1)
     setEnviron()
+    if sys.platform == 'darwin' and len(version_suffix) > 0:
+        checkUpgrade()
     createDirectories()
     dtl_tools = checkDTLtools()
     ## Write the first part of outfile