diff options
Diffstat (limited to 'python/pyqt/build.py')
-rw-r--r-- | python/pyqt/build.py | 730 |
1 files changed, 0 insertions, 730 deletions
diff --git a/python/pyqt/build.py b/python/pyqt/build.py deleted file mode 100644 index b2c39c20..00000000 --- a/python/pyqt/build.py +++ /dev/null @@ -1,730 +0,0 @@ -# Copyright (c) 2007 -# Riverbank Computing Limited <info@riverbankcomputing.co.uk> -# -# This file is part of PyQt. -# -# This copy of PyQt 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. -# -# PyQt is supplied 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 -# PyQt; see the file LICENSE. If not, write to the Free Software Foundation, -# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. -# -# This is the build script for PyQt. It should be run in the top level -# directory of the source distribution and by the Python interpreter for which -# it is being built. It uses either qmake or tmake to do the hard work of -# generating the platform specific Makefiles. - - -import sys -import os -import glob -import tempfile -import shutil -import py_compile -import compileall -import string - - -# Get the SIP configuration. -try: - import sipconfig -except: - print "Unable to import the sipconfig module. Please make sure you have" - print "SIP v3.9 or later installed." - sys.exit(1) - -config = sipconfig.SIPConfig("PyQt 3.17.2") - - -# Initialise the globals. -sipMajorVersion = config.sip_version >> 16 -sciIncDir = config.qt_inc_dir -sciLibDir = config.qt_lib_dir -sciLib = None -sciVersion = None -binDir = config.default_bin_dir -modDir = config.default_mod_dir -sipDir = config.default_sip_dir -buildModules = ["qt"] -tempBuildDir = None -catCppFiles = 0 -catSplit = 1 -qpeTag = None -trace = 0 -releaseGIL = 0 - - -def usage(rcode = 2): - """Display a usage message and exit. - - rcode is the return code passed back to the calling process. - """ - print "Usage:" - print " %s [-h] [-a version] [-b dir] [-c] [-d dir] [-g] [-j #] [-n dir] [-o dir] [-r] [-v dir]" % sipconfig.script() - print "where:" - print " -h display this help message" - print " -a tag explicitly enable the qtpe module" - print " -b dir where pyuic and pylupdate will be installed [default %s]" % config.default_bin_dir - print " -c concatenate each module's C++ source files" - print " -d dir where the PyQt modules will be installed [default %s]" % config.default_mod_dir - print " -g always release the GIL (SIP v3.x behaviour)" - print " -j # split the concatenated C++ source files into # pieces [default 1]" - print " -n dir the directory containing the QScintilla header files [default %s]" % config.qt_inc_dir - print " -o dir the directory containing the QScintilla library [default %s]" % config.qt_lib_dir - print " -r generate code with tracing enabled [default disabled]" - print " -v dir where the PyQt .sip files will be installed [default %s]" % config.default_sip_dir - - sys.exit(rcode) - - -def mkTempBuildDir(olddir=None): - """Create a temporary build directory for a console application called - qttest, complete with patched Makefile. The global tempBuildDir is set to - the name of the directory. The temporary directory becomes the current - directory. - - olddir is None if the directory should be created, otherwise it is deleted. - - Returns the name of the previous current directory. - """ - global tempBuildDir - - if olddir is None: - tempBuildDir = tempfile.mktemp() - - try: - os.mkdir(tempBuildDir) - except: - sipconfig.error("Unable to create temporary directory.") - - prevdir = sipconfig.push_dir(tempBuildDir) - - sipconfig.copy_to_file("qttest.pro.in", -"""TEMPLATE = app -TARGET = qttest -CONFIG += console warn_off @TEST_OPENGL@ @BLX_CONFIG_APP@ -INCLUDEPATH = @BLX_INCLUDEPATH@ @TEST_QSCINTILLA_INC@ -DEFINES = @BLX_DEFINES@ -SOURCES = qttest.cpp -LIBS += @TEST_QUI_LIB@ @TEST_QSCINTILLA_LIB@ -""") - - # Disable OpenGL, qui and QScintilla support by default. - config.patches["@TEST_OPENGL@"] = "" - config.patches["@TEST_QUI_LIB@"] = "" - config.patches["@TEST_QSCINTILLA_INC@"] = "" - config.patches["@TEST_QSCINTILLA_LIB@"] = "" - - # Create a dummy source file to suppress a qmake warning. - sipconfig.copy_to_file("qttest.cpp", "") - - config.create_makefile("qttest.pro") - else: - sipconfig.pop_dir(olddir) - prevdir = None - - shutil.rmtree(tempBuildDir, 1) - - return prevdir - - -def tryModule(maindir, mname, incfile, ctor): - """See if a PyQt module should be built and update the buildModules list - accordingly. - - maindir is the directory containing this script. - mname is the name of the PyQt module. - incfile is the C++ header file that defines the class being used for the - test. - ctor is the constructor of the class being used for the test. - """ - # Check for the existence of the module .sip file. - msip = os.path.join(maindir, "sip", mname, mname + "mod.sip") - - if not os.access(msip, os.F_OK): - return - - sipconfig.copy_to_file("qttest.cpp", -"""#include <%s> - -int main(int argc,char **argv) -{ - new %s; -} -""" % (incfile, ctor)) - - if sipconfig.run_make(None,0) == 0: - buildModules.append(mname) - sipconfig.inform("The %s module will be built." % mname) - else: - sipconfig.inform("The %s module will not be built." % mname) - - sipconfig.run_make("clean") - - -def checkQScintilla(): - """See if QScintilla can be found and what its version is. - """ - # Find the QScintilla header files. - sciglobal = os.path.join(sciIncDir, "qextscintillaglobal.h") - - if os.access(sciglobal,os.F_OK): - config.patches["@PYQT_QSCINTILLA_INC@"] = sciIncDir - - sipconfig.inform("%s contains qextscintillaglobal.h." % (sciIncDir)) - - # Get the QScintilla version number. - global sciVersion - - sciVersion, sciversstr = sipconfig.read_version(sciglobal, "QScintilla", "QSCINTILLA_VERSION", "QSCINTILLA_VERSION_STR") - - sipconfig.inform("QScintilla %s is being used." % (sciversstr)) - - # If we find a snapshot then set the version number to 0 as a special - # case. - if sciversstr[:8] == "snapshot": - sciVersion = 0 - - # Find the QScintilla library. - if sys.platform == "win32": - lpatt = "qscintilla.lib" - else: - lpatt = "libqscintilla.*" - - if len(glob.glob(os.path.join(sciLibDir, lpatt))): - sipconfig.inform("%s contains the QScintilla library." % sciLibDir) - - global sciLib - - if sys.platform == "win32": - sciLib = sipconfig.escape(os.path.join(sciLibDir, "qscintilla.lib")) - else: - sciLib = sipconfig.escape("-L" + sciLibDir) + " -lqscintilla" - - config.patches["@PYQT_QSCINTILLA_LIB@"] = sciLib - else: - sipconfig.inform("The QScintilla library could not be found in %s and so the qtext module will not be built. If QScintilla is installed then use the -o argument to explicitly specify the correct directory." % (sciLibDir)) - - sciVersion = -1 - else: - sipconfig.inform("qextscintillaglobal.h could not be found in %s and so the qtext module will not be built. If QScintilla is installed then use the -n argument to explicitly specify the correct directory." % sciIncDir) - - sciVersion = -1 - - -def moduleChecks(maindir): - """See which PyQt modules to build. - """ - sipconfig.inform("Checking which additional PyQt modules to build."); - - tryModule(maindir,"qtcanvas", "qcanvas.h", "QCanvas()") - tryModule(maindir,"qtnetwork", "qsocket.h", "QSocket()") - tryModule(maindir,"qttable", "qtable.h", "QTable()") - tryModule(maindir,"qtxml", "qdom.h", "QDomImplementation()") - - if config.qt_version >= 0x030000: - tryModule(maindir,"qtsql", "qsql.h", "QSql()") - - # We need a different Makefile for the qtgl module. - config.patches["@TEST_OPENGL@"] = "opengl" - config.create_makefile("qttest.pro") - - tryModule(maindir,"qtgl", "qgl.h", "QGLWidget()") - - # Put things back. - config.patches["@TEST_OPENGL@"] = "" - config.create_makefile("qttest.pro") - - # Check for the qui library. - if config.qt_version >= 0x030000: - if sys.platform == "win32": - quilib = r"$(QTDIR)\lib\qui.lib" - else: - quilib = "-lqui" - - config.patches["@PYQT_QUI_LIB@"] = quilib - - config.patches["@TEST_QUI_LIB@"] = quilib - config.create_makefile("qttest.pro") - - tryModule(maindir,"qtui", "qwidgetfactory.h", "QWidgetFactory()") - - # Put things back. - config.patches["@TEST_QUI_LIB@"] = "" - config.create_makefile("qttest.pro") - - # Check for the QScintilla library. - if sciVersion >= 0: - config.patches["@TEST_QSCINTILLA_INC@"] = sciIncDir - config.patches["@TEST_QSCINTILLA_LIB@"] = sciLib - config.create_makefile("qttest.pro") - - tryModule(maindir,"qtext", "qextscintillabase.h", "QextScintillaBase()") - - # Put things back. - config.patches["@TEST_QSCINTILLA_INC@"] = "" - config.patches["@TEST_QSCINTILLA_LIB@"] = "" - config.create_makefile("qttest.pro") - - -def generateFeatures(featfile): - """Generate the header file describing the Qt features that are enabled if - it doesn't already exist. (If it already exists then we are probably cross - compiling and generated the file through other means.) - - featfile is the name of the features file. - """ - if os.access(featfile,os.F_OK): - sipconfig.inform("Using existing features file.") - return - - sipconfig.inform("Generating the features file.") - - # The features that a given Qt configuration may or may not support. Note - # that STYLE_WINDOWSXP requires special handling. - flist = ["ACTION", "CLIPBOARD", "CODECS", "COLORDIALOG", "DATASTREAM", - "DIAL", "DNS", "DOM", "DRAGANDDROP", "ICONVIEW", "IMAGE_TEXT", - "INPUTDIALOG", "FILEDIALOG", "FONTDATABASE", "FONTDIALOG", - "MESSAGEBOX", "MIMECLIPBOARD", "NETWORKPROTOCOL", "PICTURE", - "PRINTDIALOG", "PRINTER", "PROGRESSDIALOG", "PROPERTIES", - "SEMIMODAL", "SIZEGRIP", "SOUND", "SPLITTER", "STYLE_CDE", - "STYLE_INTERLACE", "STYLE_MOTIF", "STYLE_MOTIFPLUS", - "STYLE_PLATINUM", "STYLE_SGI", "STYLE_WINDOWS", "TABDIALOG", - "TABLE", "TABLEVIEW", "TRANSFORMATIONS", "TRANSLATION", "WIZARD", - "WORKSPACE"] - - # Generate the program which will generate the features file. - f = open("qttest.cpp","w") - - # Escape the backslashes so that the name can be embedded in a C++ string. - ffstr = string.replace(featfile, "\\", "\\\\") - - f.write( -"""#include <stdio.h> -#include <qglobal.h> -#include <qapplication.h> - -int main(int argc,char **argv) -{ - FILE *fp; - QApplication app(argc,argv,0); - - if ((fp = fopen("%s","w")) == NULL) - { - printf("Unable to create '%s'\\n"); - return 1; - } - -#if !defined(QT_THREAD_SUPPORT) - fprintf(fp,"-x Qt_THREAD_SUPPORT\\n"); -#endif - -#if (defined(Q_OS_WIN32) || defined(Q_OS_WIN64)) && QT_VERSION >= 0x030000 - if (qWinVersion() != Qt::WV_XP) - fprintf(fp,"-x Qt_STYLE_WINDOWSXP\\n"); -#endif -""" % (ffstr, ffstr)) - - for feat in flist: - f.write( -""" -#if defined(QT_NO_%s) - fprintf(fp,"-x Qt_%s\\n"); -#endif -""" % (feat, feat)) - - f.write( -""" - fclose(fp); - - return 0; -} -""") - - f.close() - - sipconfig.run_make() - sipconfig.run_program(os.path.join(os.getcwd(), "qttest")) - sipconfig.run_make("clean") - - sipconfig.inform("Generated the features file.") - - -def generateSource(mname, plattag, qttag, xtrtag): - """Generate the C++ source code for a particular PyQt module. - - mname is the name of the module. - plattag is the SIP tag for the platform. - qttag is the SIP tag for the Qt version. - xtrtag is an optional extra SIP tag. - """ - sipconfig.inform("Generating the C++ source for the %s module." % mname) - - try: - shutil.rmtree(mname) - except: - pass - - try: - os.mkdir(mname) - except: - sipconfig.error("Unable to create the %s directory." % mname) - - pro = mname + ".pro" - - argv = ["-t", plattag, - "-t", qttag, - "-z", "features", - "-I", "sip", - "-m", mname + "/" + pro + ".in", - "-c", mname, - "sip/" + mname + "/" + mname + "mod.sip"] - - if xtrtag: - argv.insert(0,xtrtag) - argv.insert(0,"-t") - - if trace: - argv.insert(0,"-r") - - if releaseGIL: - argv.insert(0,"-g") - - sipconfig.run_program(config.sip_bin, argv) - - # Generate the Makefile. - sipconfig.inform("Generating the Makefile for the %s module." % mname) - - olddir = sipconfig.push_dir(mname) - - if catCppFiles: - sipconfig.cat_source_files(mname, catSplit) - - config.create_makefile(pro, mname) - - icmds = [] - - if sipMajorVersion == 3: - icmds.append(("copy", mname + ".py", modDir)) - icmds.append(("copy", mname + ".pyc", modDir)) - - config.add_install_target(icmds) - - if sipMajorVersion == 3: - # Compile the Python part of the module. - pyname = mname + ".py" - - sipconfig.inform("Compiling %s." % (pyname)) - py_compile.compile(pyname) - - sipconfig.pop_dir(olddir) - - -def versionToTag(vers, tags, desc): - """Convert a version number to a tag. - - vers is the version number. - tags is the dictionary of tags keyed by version number. - desc is the descriptive name of the package. - - Returns the corresponding tag. - """ - tag = None - - vl = tags.keys() - vl.sort() - - # For a snapshot use the latest tag. - if vers == 0: - tag = tags[vl[-1]] - else: - for v in vl: - if vers < v: - tag = tags[v] - break - - if tag is None: - sipconfig.error("Invalid %s version: 0x%06x." % (desc, vers)) - - return tag - - -def main(argv): - """The main function of the script. - - argv is the list of command line arguments. - """ - import getopt - - # Parse the command line. - try: - optlist, args = getopt.getopt(argv[1:],"ha:b:cd:gj:n:o:rv:") - except getopt.GetoptError: - usage() - - for opt, arg in optlist: - if opt == "-h": - usage(0) - elif opt == "-a": - global qpeTag - qpeTag = arg - elif opt == "-b": - global binDir - binDir = arg - elif opt == "-c": - global catCppFiles - catCppFiles = 1 - elif opt == "-d": - global modDir - modDir = arg - elif opt == "-g": - global releaseGIL - releaseGIL = 1 - elif opt == "-j": - global catSplit - - try: - catSplit = int(arg) - except: - catSplit = 0 - - if catSplit < 1: - usage() - elif opt == "-n": - global sciIncDir - sciIncDir = arg - elif opt == "-o": - global sciLibDir - sciLibDir = arg - elif opt == "-r": - global trace - trace = 1 - elif opt == "-v": - global sipDir - sipDir = arg - - # Confirm the license. - sipconfig.confirm_license() - - # If there should be a license file then check it is where it should be. - if config.license_file: - if os.access(os.path.join("sip", config.license_file), os.F_OK): - sipconfig.inform("Found the license file %s.\n" % config.license_file) - else: - sipconfig.error("Please copy the license file %s to the sip directory.\n" % config.license_file) - - # Check the Qt version. - if config.qt_version == 0: - sipconfig.error("SIP has been built with Qt support disabled.\n") - - # Early versions of Qt for the Mac didn't include everything. Rather than - # maintain these in the future we just mandate a later version. - if sys.platform == "darwin" and config.qt_version < 0x030100: - sipconfig.error("PyQt for MacOS/X requires Qt v3.1.0 or later.\n") - - # Check the installation directory is valid and add it as a patch. - if not os.access(modDir,os.F_OK): - sipconfig.error("The %s PyQt destination directory does not seem to exist. Use the -d argument to set the correct directory." % (modDir)) - - config.patches["@PYQT_MODDIR@"] = sipconfig.escape(modDir) - - sipconfig.inform("%s is the PyQt installation directory." % (modDir)) - - # Enable warnings for SIP v4 generated code. - if sipMajorVersion >= 4: - warn = "warn_on" - else: - warn = "warn_off" - - config.patches["@PYQT_WARN@"] = warn - - # Create patches to allow some modules to link against others. - if sipMajorVersion >= 4: - modlink = "" - elif sys.platform == "win32": - modlink = sipconfig.escape(os.path.join(modDir, "libqtc.lib")) - else: - modlink = sipconfig.escape("-L" + modDir) + " -lqtcmodule" - - config.patches["@PYQT_QT_MODULE@"] = modlink - - if sipMajorVersion >= 4: - modlink = "" - elif sys.platform == "win32": - modlink = sipconfig.escape(os.path.join(modDir, "libqttablec.lib")) + " " + sipconfig.escape(os.path.join(modDir, "libqtc.lib")) - else: - modlink = sipconfig.escape("-L" + modDir) + " -lqttablecmodule -lqtcmodule" - - config.patches["@PYQT_QTTABLE_MODULE@"] = modlink - - # The professional edition needs special handling if XML support is needed. - if config.qt_edition == "professional": - rbprof = "rbprof" - else: - rbprof = "" - - config.patches["@PYQT_RBPROF@"] = rbprof - - # Link in the qassistantclient library for Qt v3.1+. - qaclib = "" - - if config.qt_version >= 0x030100: - if sys.platform == "win32": - qaclib = r"$(QTDIR)\lib\qassistantclient.lib" - else: - qaclib = "-lqassistantclient" - - config.patches["@PYQT_QASSISTANTCLIENT_LIB@"] = qaclib - - # Check for QScintilla. - if config.qt_version >= 0x030000: - checkQScintilla() - - # Create a build directory that we can compile test programs. - maindir = mkTempBuildDir() - - # Check what additional modules to build. - if config.qt_version >= 0x020000: - moduleChecks(maindir) - - # Work out the platform and Qt version tags to pass to SIP to generate the - # code we need. - if config.qt_lib == "qte": - plattag = "WS_QWS" - elif sys.platform == "win32": - plattag = "WS_WIN" - elif sys.platform == "darwin": - plattag = "WS_MACX" - else: - plattag = "WS_X11" - - qttags = { - 0x020000: "Qt_1_43", - 0x020100: "Qt_2_00", - 0x020200: "Qt_2_1_0", - 0x020300: "Qt_2_2_0", - 0x020301: "Qt_2_3_0", - 0x030000: "Qt_2_3_1", - 0x030001: "Qt_3_0_0", - 0x030002: "Qt_3_0_1", - 0x030004: "Qt_3_0_2", - 0x030005: "Qt_3_0_4", - 0x030006: "Qt_3_0_5", - 0x030100: "Qt_3_0_6", - 0x030101: "Qt_3_1_0", - 0x030102: "Qt_3_1_1", - 0x030200: "Qt_3_1_2", - 0x030300: "Qt_3_2_0", - 0x040000: "Qt_3_3_0" - } - - qttag = versionToTag(config.qt_version, qttags, "Qt") - - # Work out the QScintilla tag. - if sciVersion >= 0: - scitags = { - 0x010100: "QScintilla_1_0", - 0x010200: "QScintilla_1_1", - 0x020000: "QScintilla_1_2" - } - - scitag = versionToTag(sciVersion, scitags, "QScintilla") - else: - scitag = None - - # Generate the features file. - generateFeatures(os.path.join(maindir, "features")) - - # We don't need the temporary build directory anymore. - mkTempBuildDir(maindir) - - subdirs = [] - for mname in buildModules: - if mname == "qtext": - xtratag = scitag - else: - xtratag = None - - generateSource(mname, plattag, qttag, xtratag) - subdirs.append(mname) - - # We handle the qtpe module explicitly rather than auto-detect. This is - # because it does things a bit differently and I'm too lazy to deal with it - # properly at the moment. - if qpeTag: - generateSource("qtpe", plattag, qttag, qpeTag) - subdirs.append("qtpe") - - # Install the .sip files. - sipconfig.inform("Creating Makefile for .sip files.") - olddir = sipconfig.push_dir("sip") - sipconfig.copy_to_file("Makefile", "all:\n") - - icmds = [] - - for mname in buildModules: - dstdir = os.path.join(sipDir, mname) - - icmds.append(("mkdir", dstdir, None)) - - for sf in os.listdir(os.path.join(olddir, "sip", mname)): - icmds.append(("copy", os.path.join(mname, sf), os.path.join(dstdir, sf))) - - config.add_install_target(icmds) - sipconfig.pop_dir(olddir) - subdirs.append("sip") - - # See which version of pyuic to build. - config.patches["@PYQT_BINDIR@"] = sipconfig.escape(binDir) - - if config.qt_version >= 0x030000: - sipconfig.inform("Creating Makefile for pyuic3.") - subdirs.append("pyuic3") - olddir = sipconfig.push_dir("pyuic3") - elif config.qt_version >= 0x020000: - sipconfig.inform("Creating Makefile for pyuic2.") - subdirs.append("pyuic2") - olddir = sipconfig.push_dir("pyuic2") - - config.create_makefile("pyuic.pro", []) - sipconfig.pop_dir(olddir) - - # Build pylupdate if Qt v3.0 or later. - if config.qt_version >= 0x030000: - sipconfig.inform("Creating Makefile for pylupdate3.") - subdirs.append("pylupdate3") - olddir = sipconfig.push_dir("pylupdate3") - - config.create_makefile("pylupdate.pro", []) - sipconfig.pop_dir(olddir) - - # Generate the top-level Makefile. - sipconfig.inform("Creating top level Makefile.") - sipconfig.copy_to_file("PyQt.pro.in", "TEMPLATE = subdirs\nSUBDIRS = " + string.join(subdirs) + "\n") - config.create_makefile("PyQt.pro") - - # Tell the user what to do next. - msg = "The build of the PyQt source code for your system is now complete. To compile and install PyQt run \"%s\" and \"%s install\" with appropriate user privileges." % (config.make_bin, config.make_bin) - - sipconfig.inform(msg) - - -if __name__ == "__main__": - try: - main(sys.argv) - except SystemExit: - raise - except: - print \ -"""An internal error occured. Please report all the output from the program, -including the following traceback, to support@riverbankcomputing.co.uk. -""" - raise |