From 07f680b4cc0e5271355b4239fce50d2ca9fd2e2e Mon Sep 17 00:00:00 2001 From: Antony Lee Date: Thu, 5 Sep 2019 21:58:21 +0200 Subject: [PATCH 1/2] Don't link ft2font to zlib. A default build of freetype (e.g. the one from MPLLOCALFREETYPE=1) uses its own vendored version of zlib (see FT_CONFIG_OPTION_SYSTEM_ZLIB in ftoption.h), so we don't need to link to zlib in that case; if we're linking against a system freetype then we can assume that pkg-config will list the right libraries to link. Not linking zlib explicitly means that the staticbuild option is not used anymore and can just be stripped out. --- .appveyor.yml | 9 ++++----- INSTALL.rst | 27 ++++++++++----------------- ci/azure-pipelines-steps.yml | 10 ---------- setupext.py | 28 ++-------------------------- 4 files changed, 16 insertions(+), 58 deletions(-) diff --git a/.appveyor.yml b/.appveyor.yml index b5efd3af0256..b466404a50c2 100644 --- a/.appveyor.yml +++ b/.appveyor.yml @@ -60,7 +60,7 @@ install: # if conda-forge gets a new pyqt, it might be nice to install it as well to have more backends # https://github.com/conda-forge/conda-forge.github.io/issues/157#issuecomment-223536381 - conda create -q -n test-environment python=%PYTHON_VERSION% - freetype=2.6 zlib=1.2 tk=8.5 + freetype=2.6 tk=8.5 pip setuptools numpy sphinx tornado - activate test-environment - echo %PYTHON_VERSION% %TARGET_ARCH% @@ -81,9 +81,9 @@ test_script: # Now build the thing.. - set LINK=/LIBPATH:%cd%\lib - pip install -ve . - # these should show no z or freetype dll... + # this should show no freetype dll... - set "DUMPBIN=%VS140COMNTOOLS%\..\..\VC\bin\dumpbin.exe" - - 'if x%MPLSTATICBUILD% == xTrue "%DUMPBIN%" /DEPENDENTS lib\matplotlib\ft2font*.pyd | findstr freetype.*.dll && exit /b 1 || exit /b 0' + - '"%DUMPBIN%" /DEPENDENTS lib\matplotlib\ft2font*.pyd | findstr freetype.*.dll && exit /b 1 || exit /b 0' # this are optional dependencies so that we don't skip so many tests... - if x%TEST_ALL% == xyes conda install -q ffmpeg inkscape miktex pillow @@ -98,9 +98,8 @@ test_script: - pytest %PYTEST_ARGS% after_test: - # After the tests were a success, build wheels with the static libs + # After the tests were a success, build wheels. # Hide the output, the copied files really clutter the build log... - - set MPLSTATICBUILD=True - 'python setup.py bdist_wheel > NUL:' - dir dist\ - echo finished... diff --git a/INSTALL.rst b/INSTALL.rst index c6574511f590..ce76d4684db8 100644 --- a/INSTALL.rst +++ b/INSTALL.rst @@ -175,27 +175,22 @@ etc., you can install the following: .. _pkg-config: https://www.freedesktop.org/wiki/Software/pkg-config/ - If not using pkg-config (in particular on Windows), you may need to set the - include path (to the FreeType and zlib headers) and link path (to - the FreeType and zlib libraries) explicitly, if they are not in - standard locations. This can be done using standard environment variables - -- on Linux and OSX: + If not using pkg-config (in particular on Windows), you may need to set + the include path (to the FreeType headers) and link path (to the FreeType + library) explicitly, if they are not in standard locations. This can be + done using standard environment variables -- on Linux and OSX: .. code-block:: sh - export CFLAGS='-I/directory/containing/ft2build.h ...' - export LDFLAGS='-L/directory/containing/libfreetype.so ...' + export CFLAGS='-I/directory/containing/ft2build.h' + export LDFLAGS='-L/directory/containing/libfreetype.so' and on Windows: .. code-block:: bat - set CL=/IC:\directory\containing\ft2build.h ... - set LINK=/LIBPATH:C:\directory\containing\freetype.lib ... - - where ``...`` means "also give, in the same format, the directories - containing ``zlib.h`` for the include path, and for - ``libz.so``/``z.lib`` for the link path." + set CL=/IC:\directory\containing\ft2build.h + set LINK=/LIBPATH:C:\directory\containing\freetype.lib .. note:: @@ -273,7 +268,7 @@ https://packaging.python.org/guides/packaging-binary-extensions/#setting-up-a-bu for how to set up a build environment. Since there is no canonical Windows package manager, the methods for building -FreeType and zlib from source code are documented as a build script +FreeType from source code are documented as a build script at `matplotlib-winbuild `_. There are a few possibilities to build Matplotlib on Windows: @@ -296,10 +291,8 @@ the list of conda packages. :: - conda create -n "matplotlib_build" python=3.7 numpy python-dateutil pyparsing tornado cycler tk zlib freetype + conda create -n "matplotlib_build" python=3.7 numpy python-dateutil pyparsing tornado cycler tk freetype conda activate matplotlib_build - # force the build against static zlib libraries - set MPLSTATICBUILD=True python setup.py bdist_wheel diff --git a/ci/azure-pipelines-steps.yml b/ci/azure-pipelines-steps.yml index 8064064b2020..3337485be857 100644 --- a/ci/azure-pipelines-steps.yml +++ b/ci/azure-pipelines-steps.yml @@ -16,16 +16,6 @@ steps: prerelease: true condition: and(succeeded(), eq(variables['python.version'], 'Pre')) -- ${{ if eq(parameters.installer, 'nuget') }}: - - task: NuGetToolInstaller@0 - displayName: 'Use latest available Nuget' - - - script: | - nuget install zlib-msvc14-x64 -ExcludeVersion -OutputDirectory "$(build.BinariesDirectory)" - echo ##vso[task.prependpath]$(build.BinariesDirectory)\zlib-msvc14-x64\build\native\bin_release - - displayName: 'Install dependencies with nuget' - - ${{ if eq(parameters.installer, 'brew') }}: - script: | brew cask install xquartz diff --git a/setupext.py b/setupext.py index 10ae966364de..e3680e929d5a 100644 --- a/setupext.py +++ b/setupext.py @@ -151,32 +151,23 @@ def write_cache(local_fn, data): # matplotlib build options, which can be altered using setup.cfg options = { 'backend': None, - 'staticbuild': False, - } +} setup_cfg = os.environ.get('MPLSETUPCFG', 'setup.cfg') if os.path.exists(setup_cfg): config = configparser.ConfigParser() config.read(setup_cfg) - if config.has_option('rc_options', 'backend'): options['backend'] = config.get("rc_options", "backend") - if config.has_option('test', 'local_freetype'): options['local_freetype'] = config.getboolean("test", "local_freetype") - - if config.has_option('build', 'staticbuild'): - options['staticbuild'] = config.getboolean("build", "staticbuild") else: config = None lft = bool(os.environ.get('MPLLOCALFREETYPE', False)) options['local_freetype'] = lft or options.get('local_freetype', False) -staticbuild = bool(os.environ.get('MPLSTATICBUILD', os.name == 'nt')) -options['staticbuild'] = staticbuild or options.get('staticbuild', False) - if '-q' in sys.argv or '--quiet' in sys.argv: def print_raw(*args, **kwargs): pass # Suppress our own output. @@ -202,21 +193,6 @@ def get_buffer_hash(fd): return hasher.hexdigest() -def deplib(libname): - if sys.platform != 'win32': - return libname - - known_libs = { - 'z': ('zlib', 'static'), - } - - libname, static_postfix = known_libs[libname] - if options['staticbuild']: - libname += static_postfix - - return libname - - @functools.lru_cache(1) # We only need to compute this once. def get_pkg_config(): """ @@ -521,7 +497,7 @@ def add_flags(self, ext): ext, 'freetype2', atleast_version='9.11.3', alt_exec=['freetype-config'], - default_libraries=['freetype', deplib('z')]) + default_libraries=['freetype']) ext.define_macros.append(('FREETYPE_BUILD_TYPE', 'system')) def do_custom_build(self): From f3165b71b4dae371572673a0764bee433b6fe7df Mon Sep 17 00:00:00 2001 From: Antony Lee Date: Thu, 5 Sep 2019 22:38:54 +0200 Subject: [PATCH 2/2] Update build docs. TL;DR: set MPLLOCALFREETYPE=1 and call it a day, unless you really know what you want to do. --- INSTALL.rst | 148 +++++++++----------------- doc/faq/environment_variables_faq.rst | 7 +- doc/faq/installing_faq.rst | 21 +--- 3 files changed, 61 insertions(+), 115 deletions(-) diff --git a/INSTALL.rst b/INSTALL.rst index ce76d4684db8..a725d24f4751 100644 --- a/INSTALL.rst +++ b/INSTALL.rst @@ -98,8 +98,8 @@ toolchain is prefixed. This may be used for cross compiling. :: export CXX=x86_64-pc-linux-gnu-g++ export PKG_CONFIG=x86_64-pc-linux-gnu-pkg-config -Once you have satisfied the requirements detailed below (mainly -Python, NumPy, and FreeType), you can build Matplotlib. +Once you have satisfied the requirements detailed below (i.e., Python and +FreeType), you can build Matplotlib. :: cd matplotlib @@ -165,96 +165,78 @@ etc., you can install the following: * `LaTeX `_ and `GhostScript (>=9.0) `_ : for rendering text with LaTeX. -.. note:: - - Matplotlib depends on non-Python libraries. +FreeType +-------- - On Linux and OSX, pkg-config_ can be used to find required non-Python - libraries and thus make the install go more smoothly if the libraries and - headers are not in the expected locations. +Matplotlib depends on FreeType, a font rendering library. It can either +download and build its own copy of the library, or use a copy of FreeType +already installed in your system. - .. _pkg-config: https://www.freedesktop.org/wiki/Software/pkg-config/ +The easiest option is to make Matplotlib download and build FreeType. This is +done by setting the :envvar:`MPLLOCALFREETYPE` environment variable to 1 -- on +Linux and OSX: - If not using pkg-config (in particular on Windows), you may need to set - the include path (to the FreeType headers) and link path (to the FreeType - library) explicitly, if they are not in standard locations. This can be - done using standard environment variables -- on Linux and OSX: +.. code-block:: sh - .. code-block:: sh + export MPLLOCALFREETYPE=1 - export CFLAGS='-I/directory/containing/ft2build.h' - export LDFLAGS='-L/directory/containing/libfreetype.so' +and on Windows: - and on Windows: +.. code-block:: bat - .. code-block:: bat + set MPLLOCALFREETYPE=1 - set CL=/IC:\directory\containing\ft2build.h - set LINK=/LIBPATH:C:\directory\containing\freetype.lib - -.. note:: +and you can continue the installation (``python -m pip install .``), ignoring +everything that follows. - The following libraries are shipped with Matplotlib: +If you wish, instead, to use the system FreeType, you need to install the +FreeType library and headers. This can be achieved using a package manager: - - ``Agg``: the Anti-Grain Geometry C++ rendering engine; - - ``qhull``: to compute Delaunay triangulation; - - ``ttconv``: a TrueType font utility. +.. code-block:: sh -.. _build_linux: + # Pick ONE of the following: + sudo apt install libfreetype6-dev # Debian/Ubuntu + sudo dnf install freetype-devel # Fedora + brew install freetype # macOS with Homebrew + conda install freetype # conda, any OS -Building on Linux ------------------ +On Linux and macOS, it is also recommended to install pkg-config_, a helper +tool for locating FreeType: -It is easiest to use your system package manager to install the dependencies. +.. code-block:: sh -If you are on Debian/Ubuntu, you can get all the dependencies -required to build Matplotlib with:: + # Pick ONE of the following: + sudo apt install pkg-config # Debian/Ubuntu + sudo dnf install pkgconf # Fedora + brew install pkg-config # macOS with Homebrew + conda install pkg-config # conda - sudo apt-get build-dep python-matplotlib +.. _pkg-config: https://www.freedesktop.org/wiki/Software/pkg-config/ -If you are on Fedora, you can get all the dependencies required to build -Matplotlib with:: +If not using pkg-config (in particular on Windows), you may need to set the +include path (to the FreeType headers) and link path (to the FreeType library) +explicitly, if they are not in standard locations. This can be done using +standard environment variables -- on Linux and OSX: - sudo dnf builddep python-matplotlib +.. code-block:: sh -If you are on RedHat, you can get all the dependencies required to build -Matplotlib by first installing ``yum-builddep`` and then running:: + export CFLAGS='-I/directory/containing/ft2build.h' + export LDFLAGS='-L/directory/containing/libfreetype.so' - su -c "yum-builddep python-matplotlib" +and on Windows: -These commands do not build Matplotlib, but instead get and install the -build dependencies, which will make building from source easier. +.. code-block:: bat -.. _build_osx: + set CL=/IC:\directory\containing\ft2build.h + set LINK=/LIBPATH:C:\directory\containing\freetype.lib -Building on macOS ------------------ - -The build situation on macOS is complicated by the various places one -can get FreeType (MacPorts, Fink, -/usr/X11R6), the different architectures (e.g., x86, ppc, universal), and -the different macOS versions (e.g., 10.4 and 10.5). We recommend that you build -the way we do for the macOS release: get the source from the tarball or the -git repository and install the required dependencies through a third-party -package manager. Two widely used package managers are Homebrew, and MacPorts. -The following example illustrates how to install FreeType using -``brew``:: - - brew install freetype pkg-config - -If you are using MacPorts, execute the following instead:: - - port install freetype pkgconfig - -After installing the above requirements, install Matplotlib from source by -executing:: +.. note:: - python -m pip install . + The following libraries are shipped with Matplotlib: -Note that your environment is somewhat important. Some conda users have -found that, to run the tests, their PYTHONPATH must include -/path/to/anaconda/.../site-packages and their DYLD_FALLBACK_LIBRARY_PATH -must include /path/to/anaconda/lib. + - ``Agg``: the Anti-Grain Geometry C++ rendering engine; + - ``qhull``: to compute Delaunay triangulation; + - ``ttconv``: a TrueType font utility. .. _build_windows: @@ -264,40 +246,14 @@ Building on Windows The Python shipped from https://www.python.org is compiled with Visual Studio 2015 for 3.5+. Python extensions should be compiled with the same compiler, see e.g. -https://packaging.python.org/guides/packaging-binary-extensions/#setting-up-a-build-environment-on-windows +https://packaging.python.org/guides/packaging-binary-extensions/#binary-extensions-for-windows for how to set up a build environment. -Since there is no canonical Windows package manager, the methods for building -FreeType from source code are documented as a build script -at `matplotlib-winbuild `_. - -There are a few possibilities to build Matplotlib on Windows: - -* Wheels via `matplotlib-winbuild `_ -* Wheels by using conda packages (see below) -* Conda packages (see below) - If you are building your own Matplotlib wheels (or sdists), note that any DLLs that you copy into the source tree will be packaged too. -Wheel builds using conda packages -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -This is a wheel build, but we use conda packages to get all the requirements. -FreeType is statically linked and therefore not needed during the wheel install. - -Set up the conda environment. Note, if you want a qt backend, add ``pyqt`` to -the list of conda packages. - -:: - - conda create -n "matplotlib_build" python=3.7 numpy python-dateutil pyparsing tornado cycler tk freetype - conda activate matplotlib_build - python setup.py bdist_wheel - - Conda packages -^^^^^^^^^^^^^^ +-------------- The conda packaging scripts for Matplotlib are available at https://github.com/conda-forge/matplotlib-feedstock. diff --git a/doc/faq/environment_variables_faq.rst b/doc/faq/environment_variables_faq.rst index 83896a70a5ed..04e7bccaef96 100644 --- a/doc/faq/environment_variables_faq.rst +++ b/doc/faq/environment_variables_faq.rst @@ -31,9 +31,14 @@ Environment Variables defined, :file:`{HOME}/.config/matplotlib` is generally used on unix-like systems and :file:`{HOME}/.matplotlib` is used on other platforms, if they are writable. Otherwise, the python standard library :func:`tempfile.gettempdir` - is used to find a base directory in which the :file:`matplotlib` subdirectory + is used to find a base directory in which the :file:`matplotlib` subdirectory is created. +.. envvar:: MPLLOCALFREETYPE + + If set, this environment variable directs Matplotlib's build script to + download and build its own copy of the FreeType library. + .. envvar:: PATH The list of directories searched to find executable programs. diff --git a/doc/faq/installing_faq.rst b/doc/faq/installing_faq.rst index 7a88b32bf2db..7777a98eb957 100644 --- a/doc/faq/installing_faq.rst +++ b/doc/faq/installing_faq.rst @@ -182,26 +182,13 @@ or:: git clone git://github.com/matplotlib/matplotlib.git -and build and install as usual with:: +and build and install with:: cd matplotlib + export MPLLOCALFREETYPE=1 # on Linux and OSX. + set MPLLOCALFREETYPE=1 # on Windows. python -mpip install . -.. note:: - - If you are on Debian/Ubuntu, you can get all the dependencies required to - build Matplotlib with:: - - sudo apt-get build-dep python-matplotlib - - If you are on Fedora/RedHat, you can get all the dependencies required to - build Matplotlib by first installing ``yum-builddep`` and then running:: - - su -c 'yum-builddep python-matplotlib' - - This does not build Matplotlib, but it does get all of the build - dependencies, which will make building from source easier. - If you want to be able to follow the development branch as it changes just replace the last step with:: @@ -211,8 +198,6 @@ This creates links and installs the command line script in the appropriate places. .. note:: - OSX users please see the :ref:`build_osx` guide. - Windows users please see the :ref:`build_windows` guide. Then, if you want to update your Matplotlib at any time, just do::