From 393412bf6386c0088362c8ebeaabab74fe617689 Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Mon, 2 Nov 2026 10:16:31 +0100 Subject: [PATCH 1/8] try relying on stdlib for all systems --- conda/meta.yaml | 21 +++------------------ 1 file changed, 3 insertions(+), 18 deletions(-) diff --git a/conda/meta.yaml b/conda/meta.yaml index ed175e8..e4e4754 100644 --- a/conda/meta.yaml +++ b/conda/meta.yaml @@ -16,45 +16,30 @@ about: build: number: 2 - string: py{{ PY_VER }} script_env: - SETUPTOOLS_SCM_PRETEND_VERSION - # script: - # - sip-install --verbose - # - {{ PYTHON }} -m pip install . -v --no-build-isolation --no-deps --ignore-installed requirements: build: - {{ compiler('cxx') }} - - {{ stdlib('c') }} # [osx and win] + - {{ stdlib('c') }} - make # [unix] - - pkg-config # [unix] - # - libgl-devel # [linux] # match libqglviewer CDT GL strategy - # # from https://conda-forge.org/docs/maintainer/knowledge_base.html#libgl - # - python - # - sip - # - pyqt - # - pyqt-builder + - pkg-config # [unix] host: - python - pip - sip<=6.10 - pyqt - pyqt5-sip - - pyqt-builder=1.18 + - pyqt-builder 1.18.* - packaging - qt-main - libqglviewer - libgl-devel # [linux] - - libxcb # [linux] - - pthread-stubs # [linux] - - sysroot_linux-64 # [linux] - xorg-libxfixes # [linux] - run: - python - - sip<=6.10 - pyqt - libqglviewer - pyopengl From b520329f55c277349b5e4aecdd018976fad068b1 Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Mon, 2 Nov 2026 11:11:00 +0100 Subject: [PATCH 2/8] align (unused) pip build tooling with conda recipe --- pyproject.toml | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index 8a38146..cac2451 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,7 +1,7 @@ # Specify the build system. [build-system] # "setuptools", "setuptools-scm" not used -requires = ["sip<=6.10", "PyQt-builder"] +requires = ["sip<=6.10", "PyQt-builder=1.18"] build-backend = "sipbuild.api" @@ -16,7 +16,6 @@ authors = [ { name = "Frederic Boudon", email = "frederic.boudon@cirad.fr" } ] dependencies = [ - "sip<=6.10", "PyQt5", "PyQt5-sip" ] @@ -28,8 +27,7 @@ sip-files-dir = "sip" [tool.sip.bindings.PyQGLViewer] qmake-QT = ['xml', 'opengl', 'gui', 'widgets'] tags = ['QGLViewer_2_9_1'] -# include-dirs=['${CONDA_PREFIX}/include'] -# library-dirs=['${CONDA_PREFIX}/lib'] + # Could specified directly with new construct but currently only working on MacOS. Instead options set in project.py # libraries = ['QGLViewer ; system_platform == "Linux"','GLU ; system_platform == "Linux"'] \ No newline at end of file From 3c2ef94b076f67ec8503e3b74038ee2fe51cd292 Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Mon, 2 Nov 2026 11:11:42 +0100 Subject: [PATCH 3/8] only pass -L to linker --- conda/build.sh | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/conda/build.sh b/conda/build.sh index a277df2..6975972 100644 --- a/conda/build.sh +++ b/conda/build.sh @@ -18,10 +18,7 @@ if [ "$(uname)" == "Linux" ]; then chmod +x g++ gcc gcc-ar export PATH=${PWD}:${PATH} - SYSROOT_FLAGS="-L ${BUILD_PREFIX}/${HOST}/sysroot/usr/lib64 -L ${BUILD_PREFIX}/${HOST}/sysroot/usr/lib" - export CFLAGS="$SYSROOT_FLAGS $CFLAGS" - export CXXFLAGS="$SYSROOT_FLAGS $CXXFLAGS" - export LDFLAGS="$SYSROOT_FLAGS $LDFLAGS" + export LDFLAGS="-L${BUILD_PREFIX}/${HOST}/sysroot/usr/lib64 -L${BUILD_PREFIX}/${HOST}/sysroot/usr/lib ${LDFLAGS}" echo "CC=${CC}" echo "CXX=${CXX}" From 9b577a867af29af06a3380c8627c71ddde45b4e9 Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Mon, 2 Nov 2026 11:12:53 +0100 Subject: [PATCH 4/8] try removing explicit ref to sysroot (normally pulled by stdlib) --- project.py | 32 ++++++++++++-------------------- 1 file changed, 12 insertions(+), 20 deletions(-) diff --git a/project.py b/project.py index 77dd049..f0eda41 100644 --- a/project.py +++ b/project.py @@ -19,13 +19,13 @@ import os +import platform +import subprocess from pyqtbuild import PyQtBindings, PyQtProject def determine_pyqglviewer_version(): - import os, subprocess - version = os.environ.get("SETUPTOOLS_SCM_PRETEND_VERSION",None) if version is None: try: @@ -68,28 +68,20 @@ def __init__(self, project): print("Instanciation of the PyQGLViewerBindings ") def apply_user_defaults(self, tool): - import platform, os - - CONDA_PREFIX = os.environ.get('CONDA_PREFIX',None) - PREFIX = os.environ.get('PREFIX',None) - CONDA_BUILD_SYSROOT = os.environ.get('CONDA_BUILD_SYSROOT',None) - - if platform.system() in ['Darwin','Linux'] : + system = platform.system() + prefix = os.environ.get("PREFIX") or os.environ.get("CONDA_PREFIX") + + if system in ('Darwin','Linux') : self.libraries.append('QGLViewer') - if not CONDA_PREFIX is None: - self.include_dirs.append(f'{CONDA_PREFIX}/include') - self.library_dirs.append(f'{CONDA_PREFIX}/lib') - if not PREFIX is None: - self.include_dirs.append(f'{PREFIX}/include') - self.library_dirs.append(f'{PREFIX}/lib') - - if platform.system() == 'Linux': + if prefix: + self.include_dirs.append(f'{prefix}/include') + self.library_dirs.append(f'{prefix}/lib') + + if system == 'Linux': self.libraries.append('GLU') - if not CONDA_BUILD_SYSROOT is None : - self.include_dirs.append(f'{CONDA_BUILD_SYSROOT}/usr/include') - elif platform.system() == 'Windows': + elif system == 'Windows': self.libraries.append('QGLViewer2') self.libraries.append('opengl32') self.libraries.append('glu32') From 1c3463fe9127b397973705fe12fa7e99fce7533f Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Mon, 2 Nov 2026 11:27:46 +0100 Subject: [PATCH 5/8] try removing explicit sysroot exposition to linker --- conda/build.sh | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/conda/build.sh b/conda/build.sh index 6975972..bfc3925 100644 --- a/conda/build.sh +++ b/conda/build.sh @@ -3,6 +3,7 @@ # Inspired from https://github.com/conda-forge/pyqt-feedstock/tree/main/recipe if [ "$(uname)" == "Linux" ]; then + # expose compilers to qmake GXX_PATH=$(command -v "${GXX}") GCC_PATH=$(command -v "${GCC}") GCC_AR_PATH=$(command -v "${GCC_AR}") @@ -17,9 +18,7 @@ if [ "$(uname)" == "Linux" ]; then chmod +x g++ gcc gcc-ar export PATH=${PWD}:${PATH} - - export LDFLAGS="-L${BUILD_PREFIX}/${HOST}/sysroot/usr/lib64 -L${BUILD_PREFIX}/${HOST}/sysroot/usr/lib ${LDFLAGS}" - + echo "CC=${CC}" echo "CXX=${CXX}" echo "GCC=${GCC}" From f22b17160c98fa91711b73aeb1d9fdf5bbaf28e5 Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Tue, 3 Nov 2026 11:29:19 +0100 Subject: [PATCH 6/8] keep only g++ exposition --- conda/build.sh | 36 +++++------------------------------- 1 file changed, 5 insertions(+), 31 deletions(-) diff --git a/conda/build.sh b/conda/build.sh index bfc3925..a059bf6 100644 --- a/conda/build.sh +++ b/conda/build.sh @@ -3,39 +3,13 @@ # Inspired from https://github.com/conda-forge/pyqt-feedstock/tree/main/recipe if [ "$(uname)" == "Linux" ]; then - # expose compilers to qmake - GXX_PATH=$(command -v "${GXX}") - GCC_PATH=$(command -v "${GCC}") - GCC_AR_PATH=$(command -v "${GCC_AR}") - ln -sf "${GXX_PATH}" g++ - ln -sf "${GCC_PATH}" gcc - ln -sf "${GCC_AR_PATH}" gcc-ar - - export LD=${GXX} - export CC=${GCC} - export CXX=${GXX} - export PKG_CONFIG_EXECUTABLE=$(basename $(which pkg-config)) - - chmod +x g++ gcc gcc-ar + # qmake calls g++ by its plain name, that the conda compiler does not provide + ln -sf "$(command -v "${GXX}")" g++ export PATH=${PWD}:${PATH} - - echo "CC=${CC}" - echo "CXX=${CXX}" - echo "GCC=${GCC}" - echo "GXX=${GXX}" - which gcc - which g++ - - readlink -f "$(which gcc)" || true - readlink -f "$(which g++)" || true - readlink -f "$GCC" || true - readlink -f "$GXX" || true - - "${CC}" --version - "${CXX}" --version - - "$GXX" -v -E -x c++ /dev/null + # check that qmake gets the conda compiler, not the one of the runner + readlink -f "$(which g++)" + g++ --version fi echo "**** BUILD" From 67fa61c483d5c484d6b7aa32eab1c11b3696c1e8 Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Tue, 3 Nov 2026 11:47:55 +0100 Subject: [PATCH 7/8] add developer-environment files for win, linux and macos --- README.md | 7 +++++-- environment-linux.yml | 32 ++++++++++++++++++++++++++++++++ environment-macos.yml | 30 ++++++++++++++++++++++++++++++ environment-windows.yml | 27 +++++++++++++++++++++++++++ environment.yml | 13 ------------- 5 files changed, 94 insertions(+), 15 deletions(-) create mode 100644 environment-linux.yml create mode 100644 environment-macos.yml create mode 100644 environment-windows.yml delete mode 100644 environment.yml diff --git a/README.md b/README.md index 949751f..ab7c83d 100644 --- a/README.md +++ b/README.md @@ -55,12 +55,15 @@ if __name__ == '__main__': The sources are hosted on [GitHub](https://github.com/fredboudon/PyQGLViewer). -To create a conda environment with all dependencies: +To create and activate a conda environment with all dependencies, using `environment-linux.yml`, `environment-macos.yml` or `environment-windows.yml` for your platform: ``` -conda env create -f environment.yml +conda env create -f environment-linux.yml +conda activate qglviewer ``` +macOS also requires the Xcode Command Line Tools, and Windows Visual Studio 2022 with the C++ tools. + To build and install the project: ``` diff --git a/environment-linux.yml b/environment-linux.yml new file mode 100644 index 0000000..fa01196 --- /dev/null +++ b/environment-linux.yml @@ -0,0 +1,32 @@ +# Linux developer environment, mirroring conda/meta.yaml. +# Versions follow conda-forge. Only sip and pyqt-builder are pinned as in the +# recipe, and sysroot as in conda-forge-pinning. +name: qglviewer +channels: + - conda-forge +dependencies: + # compiler('cxx') and stdlib('c') from the recipe. cxx-compiler provides g++ + # without target prefix, as called by qmake (conda/build.sh creates the same + # link with conda-build). g++ finds this sysroot by itself. + - cxx-compiler + - sysroot_linux-64=2.17 + - make + - pkg-config + # host + - python + - pip + - sip<=6.10 + - pyqt + - pyqt5-sip + - pyqt-builder=1.18.* + - packaging + - qt-main + - libqglviewer + - libgl-devel + - xorg-libxfixes + # run + - pyopengl + # test + - pytest + - pytest-qt + - pytest-xvfb diff --git a/environment-macos.yml b/environment-macos.yml new file mode 100644 index 0000000..d1926e2 --- /dev/null +++ b/environment-macos.yml @@ -0,0 +1,30 @@ +# macOS developer environment (Intel and Apple Silicon), mirroring conda/meta.yaml. +# Versions follow conda-forge. Only sip and pyqt-builder are pinned as in the +# recipe. +# +# Xcode Command Line Tools are required: qmake gets the SDK path from xcrun. +name: qglviewer +channels: + - conda-forge +dependencies: + # clang++ as called by qmake. The clangxx_osx-* wrappers of compiler('cxx') + # are arch specific and only set env flags, that qmake does not read. + - cxx-compiler + - make + - pkg-config + # host + - python + - pip + - sip<=6.10 + - pyqt + - pyqt5-sip + - pyqt-builder=1.18.* + - packaging + - qt-main + - libqglviewer + # run + - pyopengl + # test + - pytest + - pytest-qt + - pytest-xvfb diff --git a/environment-windows.yml b/environment-windows.yml new file mode 100644 index 0000000..696ce73 --- /dev/null +++ b/environment-windows.yml @@ -0,0 +1,27 @@ +# Windows developer environment, mirroring conda/meta.yaml. +# Versions follow conda-forge. Only sip and pyqt-builder are pinned as in the +# recipe. +# +# Visual Studio 2022 with the C++ tools is required: activation of the env sets +# up its compiler and nmake. +name: qglviewer +channels: + - conda-forge +dependencies: + # compiler('cxx') from the recipe + - cxx-compiler + # host + - python + - pip + - sip<=6.10 + - pyqt + - pyqt5-sip + - pyqt-builder=1.18.* + - packaging + - qt-main + - libqglviewer + # run + - pyopengl + # test + - pytest + - pytest-qt diff --git a/environment.yml b/environment.yml deleted file mode 100644 index 9744c67..0000000 --- a/environment.yml +++ /dev/null @@ -1,13 +0,0 @@ -name: qglviewer -channels: - - conda-forge -dependencies: - - python - - pip - - qt-main - - pyqt - - libqglviewer - - sip - - pyqt5-sip - - xorg-libxfixes # [linux] - - pyqt-builder From b666ae2c8136556479f61f8555458de16c921a4d Mon Sep 17 00:00:00 2001 From: Christian Fournier Date: Tue, 3 Nov 2026 12:23:32 +0100 Subject: [PATCH 8/8] remove platform specific build scripts --- conda/bld.bat | 1 - conda/build.sh | 31 ------------------------------- conda/meta.yaml | 23 +++++++++++++++-------- environment-linux.yml | 4 ++-- 4 files changed, 17 insertions(+), 42 deletions(-) delete mode 100644 conda/bld.bat delete mode 100644 conda/build.sh diff --git a/conda/bld.bat b/conda/bld.bat deleted file mode 100644 index d6c2b4c..0000000 --- a/conda/bld.bat +++ /dev/null @@ -1 +0,0 @@ -sip-install --verbose diff --git a/conda/build.sh b/conda/build.sh deleted file mode 100644 index a059bf6..0000000 --- a/conda/build.sh +++ /dev/null @@ -1,31 +0,0 @@ -#!/bin/bash - -# Inspired from https://github.com/conda-forge/pyqt-feedstock/tree/main/recipe - -if [ "$(uname)" == "Linux" ]; then - # qmake calls g++ by its plain name, that the conda compiler does not provide - ln -sf "$(command -v "${GXX}")" g++ - export PATH=${PWD}:${PATH} - - # check that qmake gets the conda compiler, not the one of the runner - readlink -f "$(which g++)" - g++ --version -fi - -echo "**** BUILD" -sip-install --verbose - -echo -echo "****** CHECK PYTHON LIB" - -# To check if Python lib is not in the dependencies with conda-forge distribution. -# See https://github.com/conda-forge/boost-feedstock/issues/81 -# if [ $(uname) = "Darwin" ]; then -# otool -L $(${PYTHON} -c "import PyQGLViewer as pyqgl ; print(pyqgl.__file__)") -# fi - -if [ "$(uname)" == "Linux" ]; then - ldd $(${PYTHON} -c "import PyQGLViewer as pyqgl ; print(pyqgl.__file__)") - -fi -echo "****** END OF BUILD PROCESS" diff --git a/conda/meta.yaml b/conda/meta.yaml index e4e4754..5b67a99 100644 --- a/conda/meta.yaml +++ b/conda/meta.yaml @@ -16,6 +16,10 @@ about: build: number: 2 + script: + - readlink -f "$(which g++)" # [linux] + - g++ --version # [linux] + - sip-install --verbose script_env: - SETUPTOOLS_SCM_PRETEND_VERSION @@ -23,6 +27,8 @@ requirements: build: - {{ compiler('cxx') }} - {{ stdlib('c') }} + # on linux qmake calls g++ by its plain name, that compiler('cxx') does not provide + - gxx # [linux] - make # [unix] - pkg-config # [unix] host: @@ -46,13 +52,14 @@ requirements: - xorg-libxfixes # [linux] test: - requires: # [unix] - - pytest # [unix] - - pytest-qt # [unix] - - pytest-xvfb # [unix] + requires: + - pytest + - pytest-qt + - pytest-xvfb # [linux] imports: - PyQGLViewer - source_files: # [unix] - - test/*.py # [unix] - commands: # [unix] - - pytest -v # [unix] + source_files: + - test/*.py + commands: + - set QT_QPA_PLATFORM=offscreen # [win] + - pytest -v diff --git a/environment-linux.yml b/environment-linux.yml index fa01196..4a190e1 100644 --- a/environment-linux.yml +++ b/environment-linux.yml @@ -6,8 +6,8 @@ channels: - conda-forge dependencies: # compiler('cxx') and stdlib('c') from the recipe. cxx-compiler provides g++ - # without target prefix, as called by qmake (conda/build.sh creates the same - # link with conda-build). g++ finds this sysroot by itself. + # without target prefix, as called by qmake (gxx in the recipe does the same). + # g++ finds this sysroot by itself. - cxx-compiler - sysroot_linux-64=2.17 - make