From 428e71f1cd00d587b81c3007fc2dd62c97cc9425 Mon Sep 17 00:00:00 2001 From: Lovell Fuller Date: Mon, 25 Sep 2023 16:50:41 +0100 Subject: [PATCH] WIP: Distribute prebuilt binaries via the npm registry - Remove all custom download logic for prebuilt binaries - Add scripts to populate package(s) contents - Specify minimum versions of common package managers - Remove sharp.vendor runtime API as no-longer relevant - Update installation docs and issue templates --- .circleci/config.yml | 24 + .github/ISSUE_TEMPLATE/installation.md | 19 +- .github/workflows/ci.yml | 24 +- .gitignore | 3 +- .prebuildrc | 2 +- binding.gyp | 82 +- docs/install.md | 202 +- install/can-compile.js | 14 - install/check.js | 18 + install/dll-copy.js | 40 - install/libvips.js | 222 -- lib/agent.js | 44 - lib/constructor.js | 1 - lib/index.d.ts | 6 - lib/libvips.js | 117 +- lib/platform.js | 30 - lib/sharp.js | 74 +- lib/utility.js | 28 +- npm/darwin-arm64/package.json | 42 + npm/darwin-x64/package.json | 39 + npm/from-github-release.js | 51 + npm/from-local-build.js | 26 + npm/linux-arm/package.json | 45 + npm/linux-arm64/package.json | 45 + npm/linux-x64/package.json | 45 + npm/linuxmusl-arm64/package.json | 45 + npm/linuxmusl-x64/package.json | 45 + npm/package.json | 16 + npm/win32-ia32/package.json | 41 + npm/win32-x64/package.json | 41 + package.json | 62 +- src/libvips/cplusplus/VConnection.cpp | 151 - src/libvips/cplusplus/VError.cpp | 49 - src/libvips/cplusplus/VImage.cpp | 1548 --------- src/libvips/cplusplus/VInterpolate.cpp | 62 - src/libvips/cplusplus/VRegion.cpp | 27 - src/libvips/cplusplus/vips-operators.cpp | 3760 ---------------------- test/types/sharp.test-d.ts | 2 - test/unit/agent.js | 52 - test/unit/libvips.js | 87 +- test/unit/platform.js | 91 - test/unit/util.js | 8 - 42 files changed, 821 insertions(+), 6509 deletions(-) delete mode 100644 install/can-compile.js create mode 100644 install/check.js delete mode 100644 install/dll-copy.js delete mode 100644 install/libvips.js delete mode 100644 lib/agent.js delete mode 100644 lib/platform.js create mode 100644 npm/darwin-arm64/package.json create mode 100644 npm/darwin-x64/package.json create mode 100644 npm/from-github-release.js create mode 100644 npm/from-local-build.js create mode 100644 npm/linux-arm/package.json create mode 100644 npm/linux-arm64/package.json create mode 100644 npm/linux-x64/package.json create mode 100644 npm/linuxmusl-arm64/package.json create mode 100644 npm/linuxmusl-x64/package.json create mode 100644 npm/package.json create mode 100644 npm/win32-ia32/package.json create mode 100644 npm/win32-x64/package.json delete mode 100644 src/libvips/cplusplus/VConnection.cpp delete mode 100644 src/libvips/cplusplus/VError.cpp delete mode 100644 src/libvips/cplusplus/VImage.cpp delete mode 100644 src/libvips/cplusplus/VInterpolate.cpp delete mode 100644 src/libvips/cplusplus/VRegion.cpp delete mode 100644 src/libvips/cplusplus/vips-operators.cpp delete mode 100644 test/unit/agent.js delete mode 100644 test/unit/platform.js diff --git a/.circleci/config.yml b/.circleci/config.yml index 9b209eabb..fbec44bb5 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -36,6 +36,12 @@ jobs: sudo docker exec sharp sh -c "apt-get update && apt-get install -y nodejs" - run: sudo docker exec sharp sh -c "npm install --build-from-source" - run: sudo docker exec sharp sh -c "npm test" + - run: | + sudo docker exec sharp sh -c "npm run package-from-local-build" + sudo docker exec sharp sh -c "npm pkg set \"optionalDependencies.@sharpen/sharp-linux-arm64=file:./npm/linux-arm64\"" + sudo docker exec sharp sh -c "npm run clean" + sudo docker exec sharp sh -c "npm install --ignore-scripts" + sudo docker exec sharp sh -c "npm test" - run: "[[ -n $CIRCLE_TAG ]] && sudo docker exec --env prebuild_upload sharp sh -c \"npx prebuild --upload=$prebuild_upload\" || true" linux-arm64-glibc-node-20: resource_class: arm.medium @@ -54,6 +60,12 @@ jobs: sudo docker cp . sharp:/mnt/sharp/. - run: sudo docker exec sharp sh -c "npm install --build-from-source" - run: sudo docker exec sharp sh -c "npm test" + - run: | + sudo docker exec sharp sh -c "npm run package-from-local-build" + sudo docker exec sharp sh -c "npm pkg set \"optionalDependencies.@sharpen/sharp-linux-arm64=file:./npm/linux-arm64\"" + sudo docker exec sharp sh -c "npm run clean" + sudo docker exec sharp sh -c "npm install --ignore-scripts" + sudo docker exec sharp sh -c "npm test" linux-arm64-musl-node-18: resource_class: arm.medium machine: @@ -65,6 +77,12 @@ jobs: sudo docker exec sharp sh -c "apk add build-base git python3 font-noto --update-cache" - run: sudo docker exec sharp sh -c "npm install --build-from-source" - run: sudo docker exec sharp sh -c "npm test" + - run: | + sudo docker exec sharp sh -c "npm run package-from-local-build" + sudo docker exec sharp sh -c "npm pkg set \"optionalDependencies.@sharpen/sharp-linuxmusl-arm64=file:./npm/linuxmusl-arm64\"" + sudo docker exec sharp sh -c "npm run clean" + sudo docker exec sharp sh -c "npm install --ignore-scripts" + sudo docker exec sharp sh -c "npm test" - run: "[[ -n $CIRCLE_TAG ]] && sudo docker exec --env prebuild_upload sharp sh -c \"npx prebuild --upload=$prebuild_upload\" || true" linux-arm64-musl-node-20: resource_class: arm.medium @@ -79,3 +97,9 @@ jobs: sudo docker cp . sharp:/mnt/sharp/. - run: sudo docker exec sharp sh -c "npm install --build-from-source" - run: sudo docker exec sharp sh -c "npm test" + - run: | + sudo docker exec sharp sh -c "npm run package-from-local-build" + sudo docker exec sharp sh -c "npm pkg set \"optionalDependencies.@sharpen/sharp-linuxmusl-arm64=file:./npm/linuxmusl-arm64\"" + sudo docker exec sharp sh -c "npm run clean" + sudo docker exec sharp sh -c "npm install --ignore-scripts" + sudo docker exec sharp sh -c "npm test" diff --git a/.github/ISSUE_TEMPLATE/installation.md b/.github/ISSUE_TEMPLATE/installation.md index a26950765..62874070e 100644 --- a/.github/ISSUE_TEMPLATE/installation.md +++ b/.github/ISSUE_TEMPLATE/installation.md @@ -12,7 +12,6 @@ labels: installation - [ ] I have read the [documentation relating to installation](https://sharp.pixelplumbing.com/install). -- [ ] I have ensured that the architecture and platform of Node.js used for `npm install` is the same as the architecture and platform of Node.js used at runtime. ### Are you using the latest version of sharp? @@ -24,13 +23,23 @@ If you cannot confirm this, please upgrade to the latest version and try again b If you are using another package which depends on a version of `sharp` that is not the latest, please open an issue against that package instead. -### Is this a problem with filesystem permissions? +### Are you using a supported runtime? -If you are using npm v6 or earlier and installing as a `root` or `sudo` user, have you tried with the `npm install --unsafe-perm` flag? + -If you are using npm v7 or later, does the user running `npm install` own the directory it is run in? +- [ ] I am using Node.js 18 with a version >= 18.17.0 +- [ ] I am using Node.js 20 with a version >= 20.3.0 +- [ ] I am using Node.js 21 or later -If you are using the `ignore-scripts` feature of `npm`, have you tried with the `npm install --ignore-scripts=false` flag? +### Are you using a supported package manager? + + + +- [ ] I am using npm >= 9.6.5 +- [ ] I am using yarn >= 3.2.0 +- [ ] I am using pnpm >= 7.1.0 + +If you cannot confirm this, please upgrade to the latest version and try again before opening an issue. ### What is the complete output of running `npm install --verbose --foreground-scripts sharp` in an empty directory? diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b320fc053..024c250c1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -37,6 +37,7 @@ jobs: - os: macos-11 nodejs_arch: x64 nodejs_version: "^18.17.0" + nodejs_version_major: 18 platform: darwin-x64 prebuild: true - os: macos-11 @@ -98,13 +99,17 @@ jobs: architecture: ${{ matrix.nodejs_arch }} - name: Checkout uses: actions/checkout@v4 - - name: Fix working directory ownership - if: matrix.container - run: chown root.root . - name: Install run: npm install --build-from-source - name: Test run: npm test + - name: Test packaging + run: | + npm run package-from-local-build + npm pkg set "optionalDependencies.@sharpen/sharp-${{ matrix.platform }}=file:./npm/${{ matrix.platform }}" + npm run clean + npm install --ignore-scripts + npm test - name: Prebuild if: matrix.prebuild && startsWith(github.ref, 'refs/tags/') env: @@ -130,9 +135,13 @@ jobs: mkdir /opt/nodejs curl --silent https://unofficial-builds.nodejs.org/download/release/v${nodejs_version}/node-v${nodejs_version}-linux-armv6l.tar.xz | tar xJC /opt/nodejs --strip-components=1 export PATH=$PATH:/opt/nodejs/bin - chown root.root . npm install --build-from-source npx mocha --no-config --spec=test/unit/io.js + npm run package-from-local-build + npm pkg set "optionalDependencies.@sharpen/sharp-linux-arm=file:./npm/linux-arm" + npm run clean + npm install --ignore-scripts + npx mocha --no-config --spec=test/unit/io.js [[ -n $prebuild_upload ]] && npx prebuild || true macstadium-runner: permissions: @@ -167,6 +176,13 @@ jobs: run: npm install --build-from-source - name: Test run: npm test + - name: Test packaging + run: | + npm run package-from-local-build + npm pkg set "optionalDependencies.@sharpen/sharp-${{ matrix.platform }}=file:./npm/${{ matrix.platform }}" + npm run clean + npm install --ignore-scripts + npm test - name: Prebuild if: matrix.prebuild && startsWith(github.ref, 'refs/tags/') env: diff --git a/.gitignore b/.gitignore index 769e9e38e..3a85452db 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,8 @@ build node_modules /coverage +npm/*/* +!npm/*/package.json test/bench/node_modules test/fixtures/output* test/fixtures/vips-properties.xml @@ -9,7 +11,6 @@ test/saliency/report.json test/saliency/Image* test/saliency/[Uu]serData* !test/saliency/userData.js -vendor .gitattributes .DS_Store .nyc_output diff --git a/.prebuildrc b/.prebuildrc index c01a5a496..0d95c2ed2 100644 --- a/.prebuildrc +++ b/.prebuildrc @@ -1,6 +1,6 @@ { "runtime": "napi", - "include-regex": "(sharp-.+\\.node|libvips-cpp\\.dll)", + "include-regex": "(sharp-.+\\.node|libvips-.+\\.dll|libglib-.+\\.dll|libgobject-.+\\.dll)", "prerelease": true, "strip": true } diff --git a/binding.gyp b/binding.gyp index fd05b45eb..083908647 100644 --- a/binding.gyp +++ b/binding.gyp @@ -1,11 +1,16 @@ +# Copyright 2013 Lovell Fuller and others. +# SPDX-License-Identifier: Apache-2.0 + { 'variables': { 'vips_version': '= 18.17.0 @@ -18,98 +22,19 @@ Ready-compiled sharp and libvips binaries are provided for use on the most commo * macOS x64 (>= 10.13) * macOS ARM64 -* Linux x64 (glibc >= 2.17, musl >= 1.1.24, CPU with SSE4.2) -* Linux ARM64 (glibc >= 2.17, musl >= 1.1.24) +* Linux x64 (glibc >= 2.26, musl >= 1.2.2, CPU with SSE4.2) +* Linux ARM64 (glibc >= 2.26, musl >= 1.2.2) +* Linux ARM (glibc >= 2.28) * Windows x64 * Windows x86 -A ~7MB tarball containing libvips and its most commonly used dependencies -is downloaded via HTTPS, verified via Subresource Integrity -and decompressed into `node_modules/sharp/vendor` during `npm install`. - This provides support for the JPEG, PNG, WebP, AVIF (limited to 8-bit depth), TIFF, GIF and SVG (input) image formats. -The following platforms have prebuilt libvips but not sharp: - -* Linux ARMv7 (glibc >= 2.28) -* Linux ARMv6 (glibc >= 2.28) -* Windows ARM64 - -The following platforms require compilation of both libvips and sharp from source: - -* Linux x86 -* Linux ARMv7 (glibc <= 2.27, musl) -* Linux ARMv6 (glibc <= 2.27, musl) -* Linux PowerPC -* FreeBSD -* OpenBSD - -## Common problems - -The architecture and platform of Node.js used for `npm install` -must be the same as the architecture and platform of Node.js used at runtime. -See the [cross-platform](#cross-platform) section if this is not the case. - -When using npm v6 or earlier, the `npm install --unsafe-perm` flag must be used when installing as `root` or a `sudo` user. - -When using npm v7 or later, the user running `npm install` must own the directory it is run in. - -The `npm install --ignore-scripts=false` flag must be used when `npm` has been configured to ignore installation scripts. - -Check the output of running `npm install --verbose --foreground-scripts sharp` for useful error messages. - -## Apple M1 - -Prebuilt sharp and libvips binaries have been provided for macOS on ARM64 since sharp v0.29.0. - -## Cross-platform - -At `npm install` time, prebuilt binaries are automatically selected for the -current OS platform and CPU architecture, where available. - -The target platform and/or architecture can be manually selected using the following flags. - -```sh -npm install --platform=... --arch=... --arm-version=... sharp -``` - -* `--platform`: one of `linux`, `darwin` or `win32`. -* `--arch`: one of `x64`, `ia32`, `arm` or `arm64`. -* `--arm-version`: one of `6`, `7` or `8` (`arm` defaults to `6`, `arm64` defaults to `8`). -* `--libc`: one of `glibc` or `musl`. This option only works with platform `linux`, defaults to `glibc` -* `--sharp-install-force`: skip version compatibility and Subresource Integrity checks. - -These values can also be set via environment variables, -`npm_config_platform`, `npm_config_arch`, `npm_config_arm_version`, `npm_config_libc` -and `SHARP_INSTALL_FORCE` respectively. - -For example, if the target machine has a 64-bit ARM CPU and is running Alpine Linux, -use the following flags: - -```sh -npm install --arch=arm64 --platform=linux --libc=musl sharp -``` - -If the current machine is Alpine Linux and the target machine is Debian Linux on x64 cpu, -use the following flags: - -```sh -npm install --arch=x64 --platform=linux --libc=glibc sharp -``` - -Multiple platforms and architectures can be supported within the same installation tree. -The following example for macOS installs x64 binaries then adds (via a rebuild) arm64 binaries: - -```sh -npm install --platform=darwin --arch=x64 sharp -npm rebuild --platform=darwin --arch=arm64 sharp -``` - ## Custom libvips To use a custom, globally-installed version of libvips instead of the provided binaries, -make sure it is at least the version listed under `config.libvips` in the `package.json` file +make sure it is at least the version listed under `engines.libvips` in the `package.json` file and that it can be located using `pkg-config --modversion vips-cpp`. For help compiling libvips and its dependencies, please see @@ -122,92 +47,17 @@ and on macOS when running Node.js under Rosetta. This module will be compiled from source at `npm install` time when: -* a globally-installed libvips is detected (set the `SHARP_IGNORE_GLOBAL_LIBVIPS` environment variable to skip this), -* prebuilt sharp binaries do not exist for the current platform, or -* when the `npm install --build-from-source` flag is used. +* a globally-installed libvips is detected (set the `SHARP_IGNORE_GLOBAL_LIBVIPS` environment variable to skip this), or +* when the `npm install --build-from-source --ignore-scripts=false` flag is used. Building from source requires: * C++11 compiler * [node-gyp](https://github.com/nodejs/node-gyp#installation) and its dependencies -## Custom prebuilt binaries - -This is an advanced approach that most people will not require. - -### Prebuilt sharp binaries - -To install the prebuilt sharp binaries from a custom URL, -set the `sharp_binary_host` npm config option -or the `npm_config_sharp_binary_host` environment variable. - -To install the prebuilt sharp binaries from a directory on the local filesystem, -set the `sharp_local_prebuilds` npm config option -or the `npm_config_sharp_local_prebuilds` environment variable. - -URL example: -if `sharp_binary_host` is set to `https://hostname/path` -and the sharp version is `1.2.3` then the resultant URL will be -`https://hostname/path/v1.2.3/sharp-v1.2.3-napi-v5-platform-arch.tar.gz`. - -Filename example: -if `sharp_local_prebuilds` is set to `/path` -and the sharp version is `1.2.3` then the resultant filename will be -`/path/sharp-v1.2.3-napi-v5-platform-arch.tar.gz`. - -### Prebuilt libvips binaries - -To install the prebuilt libvips binaries from a custom URL, -set the `sharp_libvips_binary_host` npm config option -or the `npm_config_sharp_libvips_binary_host` environment variable. - -To install the prebuilt libvips binaries from a directory on the local filesystem, -set the `sharp_libvips_local_prebuilds` npm config option -or the `npm_config_sharp_libvips_local_prebuilds` environment variable. - -The version subpath and filename are appended to these. - -URL example: -if `sharp_libvips_binary_host` is set to `https://hostname/path` -and the libvips version is `4.5.6` then the resultant URL will be -`https://hostname/path/v4.5.6/libvips-4.5.6-platform-arch.tar.br`. - -Filename example: -if `sharp_libvips_local_prebuilds` is set to `/path` -and the libvips version is `4.5.6` then the resultant filename will be -`/path/v4.5.6/libvips-4.5.6-platform-arch.tar.br`. - -See the Chinese mirror below for a further example. - -If these binaries are modified, new integrity hashes can be provided -at install time via `npm_package_config_integrity_platform_arch` -environment variables, for example set -`npm_package_config_integrity_linux_x64` to `sha512-abc...`. - -The integrity hash of a file can be generated via: -```sh -sha512sum libvips-x.y.z-platform-arch.tar.br | cut -f1 -d' ' | xxd -r -p | base64 -w 0 -``` - -## Chinese mirror - -A mirror site based in China, provided by Alibaba, contains binaries for both sharp and libvips. - -To use this either set the following configuration: - -```sh -npm config set sharp_binary_host "https://npmmirror.com/mirrors/sharp" -npm config set sharp_libvips_binary_host "https://npmmirror.com/mirrors/sharp-libvips" -npm install sharp -``` - -or set the following environment variables: - -```sh -npm_config_sharp_binary_host="https://npmmirror.com/mirrors/sharp" \ - npm_config_sharp_libvips_binary_host="https://npmmirror.com/mirrors/sharp-libvips" \ - npm install sharp -``` +For cross-compiling, the `--platform`, `--arch` and `--libc` npm flags +(or the `npm_config_platform`, `npm_config_arch` and `npm_config_libc` environment variables) +can be used to configure the target environment. ## FreeBSD @@ -242,15 +92,18 @@ unaffected. The `node_modules` directory of the [deployment package](https://docs.aws.amazon.com/lambda/latest/dg/nodejs-package.html) -must include binaries for the Linux x64 platform. +must include binaries for either the linux-x64 or linux-arm64 platforms +depending on the chosen architecture. + +When building your deployment package on a machine that differs from the target architecture, +you will need to install either `@sharpen/sharp-linux-x64` or `@sharpen/sharp-linux-arm64` package. -When building your deployment package on machines other than Linux x64 (glibc), -run the following additional command after `npm install`: +```sh +npm install --force @sharpen/sharp-linux-x64 +``` ```sh -npm install -rm -rf node_modules/sharp -SHARP_IGNORE_GLOBAL_LIBVIPS=1 npm install --arch=x64 --platform=linux --libc=glibc sharp +npm install --force @sharpen/sharp-linux-arm64 ``` To get the best performance select the largest memory available. @@ -302,7 +155,7 @@ custom: - sharp packagerOptions: scripts: - - npm install --arch=x64 --platform=linux sharp + - npm install --force @sharpen/sharp-linux-x64 ``` ## TypeScript @@ -358,14 +211,7 @@ Module did not self-register ### Canvas and Windows -The prebuilt binaries provided by `canvas` for Windows -from v2.7.0 onwards depend on the Visual C++ Runtime (MSVCRT). -These conflict with the binaries provided by sharp, -which depend on the more modern Universal C Runtime (UCRT). - -See [Automattic/node-canvas#2155](https://github.com/Automattic/node-canvas/issues/2155). - -If both modules are used in the same Windows process, the following error will occur: +If both `canvas` and `sharp` modules are used in the same Windows process, the following error may occur: ``` The specified procedure could not be found. ``` diff --git a/install/can-compile.js b/install/can-compile.js deleted file mode 100644 index 4ea3d9386..000000000 --- a/install/can-compile.js +++ /dev/null @@ -1,14 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const libvips = require('../lib/libvips'); - -try { - if (!(libvips.useGlobalLibvips() || libvips.hasVendoredLibvips())) { - process.exitCode = 1; - } -} catch (err) { - process.exitCode = 1; -} diff --git a/install/check.js b/install/check.js new file mode 100644 index 000000000..37258dba2 --- /dev/null +++ b/install/check.js @@ -0,0 +1,18 @@ +// Copyright 2013 Lovell Fuller and others. +// SPDX-License-Identifier: Apache-2.0 + +'use strict'; + +const { useGlobalLibvips, globalLibvipsVersion, log } = require('../lib/libvips'); + +const buildFromSource = (msg) => { + log(msg); + log('Building from source via node-gyp'); + process.exitCode = 1; +}; + +if (process.env.npm_config_build_from_source) { + buildFromSource('Detected --build-from-source flag'); +} else if (useGlobalLibvips()) { + buildFromSource(`Detected globally-installed libvips v${globalLibvipsVersion()}`); +} diff --git a/install/dll-copy.js b/install/dll-copy.js deleted file mode 100644 index 58c80a396..000000000 --- a/install/dll-copy.js +++ /dev/null @@ -1,40 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const fs = require('fs'); -const path = require('path'); - -const libvips = require('../lib/libvips'); -const platform = require('../lib/platform'); - -const minimumLibvipsVersion = libvips.minimumLibvipsVersion; - -const platformAndArch = platform(); - -if (platformAndArch.startsWith('win32')) { - const buildReleaseDir = path.join(__dirname, '..', 'build', 'Release'); - libvips.log(`Creating ${buildReleaseDir}`); - try { - libvips.mkdirSync(buildReleaseDir); - } catch (err) {} - const vendorLibDir = path.join(__dirname, '..', 'vendor', minimumLibvipsVersion, platformAndArch, 'lib'); - libvips.log(`Copying DLLs from ${vendorLibDir} to ${buildReleaseDir}`); - try { - fs - .readdirSync(vendorLibDir) - .filter(function (filename) { - return /\.dll$/.test(filename); - }) - .forEach(function (filename) { - fs.copyFileSync( - path.join(vendorLibDir, filename), - path.join(buildReleaseDir, filename) - ); - }); - } catch (err) { - libvips.log(err); - process.exit(1); - } -} diff --git a/install/libvips.js b/install/libvips.js deleted file mode 100644 index 339f22284..000000000 --- a/install/libvips.js +++ /dev/null @@ -1,222 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const fs = require('fs'); -const os = require('os'); -const path = require('path'); -const stream = require('stream'); -const zlib = require('zlib'); -const { createHash } = require('crypto'); - -const detectLibc = require('detect-libc'); -const semverCoerce = require('semver/functions/coerce'); -const semverLessThan = require('semver/functions/lt'); -const semverSatisfies = require('semver/functions/satisfies'); -const simpleGet = require('simple-get'); -const tarFs = require('tar-fs'); - -const agent = require('../lib/agent'); -const libvips = require('../lib/libvips'); -const platform = require('../lib/platform'); - -const minimumGlibcVersionByArch = { - arm: '2.28', - arm64: '2.17', - x64: '2.17' -}; - -const hasSharpPrebuild = [ - 'darwin-x64', - 'darwin-arm64', - 'linux-arm64', - 'linux-x64', - 'linuxmusl-x64', - 'linuxmusl-arm64', - 'win32-ia32', - 'win32-x64' -]; - -const { minimumLibvipsVersion, minimumLibvipsVersionLabelled } = libvips; -const localLibvipsDir = process.env.npm_config_sharp_libvips_local_prebuilds || ''; -const distHost = process.env.npm_config_sharp_libvips_binary_host || 'https://github.com/lovell/sharp-libvips/releases/download'; -const distBaseUrl = process.env.npm_config_sharp_dist_base_url || process.env.SHARP_DIST_BASE_URL || `${distHost}/v${minimumLibvipsVersionLabelled}/`; -const installationForced = !!(process.env.npm_config_sharp_install_force || process.env.SHARP_INSTALL_FORCE); - -const fail = function (err) { - libvips.log(err); - if (err.code === 'EACCES') { - libvips.log('Are you trying to install as a root or sudo user?'); - libvips.log('- For npm <= v6, try again with the "--unsafe-perm" flag'); - libvips.log('- For npm >= v8, the user must own the directory "npm install" is run in'); - } - libvips.log('Please see https://sharp.pixelplumbing.com/install for required dependencies'); - process.exit(1); -}; - -const handleError = function (err) { - if (installationForced) { - libvips.log(`Installation warning: ${err.message}`); - } else { - throw err; - } -}; - -const verifyIntegrity = function (platformAndArch) { - const expected = libvips.integrity(platformAndArch); - if (installationForced || !expected) { - libvips.log(`Integrity check skipped for ${platformAndArch}`); - return new stream.PassThrough(); - } - const hash = createHash('sha512'); - return new stream.Transform({ - transform: function (chunk, _encoding, done) { - hash.update(chunk); - done(null, chunk); - }, - flush: function (done) { - const digest = `sha512-${hash.digest('base64')}`; - if (expected !== digest) { - try { - libvips.removeVendoredLibvips(); - } catch (err) { - libvips.log(err.message); - } - libvips.log(`Integrity expected: ${expected}`); - libvips.log(`Integrity received: ${digest}`); - done(new Error(`Integrity check failed for ${platformAndArch}`)); - } else { - libvips.log(`Integrity check passed for ${platformAndArch}`); - done(); - } - } - }); -}; - -const extractTarball = function (tarPath, platformAndArch) { - const versionedVendorPath = path.join(__dirname, '..', 'vendor', minimumLibvipsVersion, platformAndArch); - libvips.mkdirSync(versionedVendorPath); - - const ignoreVendorInclude = hasSharpPrebuild.includes(platformAndArch) && !process.env.npm_config_build_from_source; - const ignore = function (name) { - return ignoreVendorInclude && name.includes('include/'); - }; - - stream.pipeline( - fs.createReadStream(tarPath), - verifyIntegrity(platformAndArch), - new zlib.BrotliDecompress(), - tarFs.extract(versionedVendorPath, { ignore }), - function (err) { - if (err) { - if (/unexpected end of file/.test(err.message)) { - fail(new Error(`Please delete ${tarPath} as it is not a valid tarball`)); - } - fail(err); - } - } - ); -}; - -try { - const useGlobalLibvips = libvips.useGlobalLibvips(); - - if (useGlobalLibvips) { - const globalLibvipsVersion = libvips.globalLibvipsVersion(); - libvips.log(`Detected globally-installed libvips v${globalLibvipsVersion}`); - libvips.log('Building from source via node-gyp'); - process.exit(1); - } else if (libvips.hasVendoredLibvips()) { - libvips.log(`Using existing vendored libvips v${minimumLibvipsVersion}`); - } else { - // Is this arch/platform supported? - const arch = process.env.npm_config_arch || process.arch; - const platformAndArch = platform(); - if (arch === 'ia32' && !platformAndArch.startsWith('win32')) { - throw new Error(`Intel Architecture 32-bit systems require manual installation of libvips >= ${minimumLibvipsVersion}`); - } - if (platformAndArch === 'freebsd-x64' || platformAndArch === 'openbsd-x64' || platformAndArch === 'sunos-x64') { - throw new Error(`BSD/SunOS systems require manual installation of libvips >= ${minimumLibvipsVersion}`); - } - // Linux libc version check - const libcVersionRaw = detectLibc.versionSync(); - if (libcVersionRaw) { - const libcFamily = detectLibc.familySync(); - const libcVersion = semverCoerce(libcVersionRaw).version; - if (libcFamily === detectLibc.GLIBC && minimumGlibcVersionByArch[arch]) { - if (semverLessThan(libcVersion, semverCoerce(minimumGlibcVersionByArch[arch]).version)) { - handleError(new Error(`Use with glibc ${libcVersionRaw} requires manual installation of libvips >= ${minimumLibvipsVersion}`)); - } - } - if (libcFamily === detectLibc.MUSL) { - if (semverLessThan(libcVersion, '1.1.24')) { - handleError(new Error(`Use with musl ${libcVersionRaw} requires manual installation of libvips >= ${minimumLibvipsVersion}`)); - } - } - } - // Node.js minimum version check - const supportedNodeVersion = process.env.npm_package_engines_node || require('../package.json').engines.node; - if (!semverSatisfies(process.versions.node, supportedNodeVersion)) { - handleError(new Error(`Expected Node.js version ${supportedNodeVersion} but found ${process.versions.node}`)); - } - // Download to per-process temporary file - const tarFilename = ['libvips', minimumLibvipsVersionLabelled, platformAndArch].join('-') + '.tar.br'; - const tarPathCache = path.join(libvips.cachePath(), tarFilename); - if (fs.existsSync(tarPathCache)) { - libvips.log(`Using cached ${tarPathCache}`); - extractTarball(tarPathCache, platformAndArch); - } else if (localLibvipsDir) { - // If localLibvipsDir is given try to use binaries from local directory - const tarPathLocal = path.join(path.resolve(localLibvipsDir), `v${minimumLibvipsVersionLabelled}`, tarFilename); - libvips.log(`Using local libvips from ${tarPathLocal}`); - extractTarball(tarPathLocal, platformAndArch); - } else { - const url = distBaseUrl + tarFilename; - libvips.log(`Downloading ${url}`); - simpleGet({ url: url, agent: agent(libvips.log) }, function (err, response) { - if (err) { - fail(err); - } else if (response.statusCode === 404) { - fail(new Error(`Prebuilt libvips ${minimumLibvipsVersion} binaries are not yet available for ${platformAndArch}`)); - } else if (response.statusCode !== 200) { - fail(new Error(`Status ${response.statusCode} ${response.statusMessage}`)); - } else { - const tarPathTemp = path.join(os.tmpdir(), `${process.pid}-${tarFilename}`); - const tmpFileStream = fs.createWriteStream(tarPathTemp); - response - .on('error', function (err) { - tmpFileStream.destroy(err); - }) - .on('close', function () { - if (!response.complete) { - tmpFileStream.destroy(new Error('Download incomplete (connection was terminated)')); - } - }) - .pipe(tmpFileStream); - tmpFileStream - .on('error', function (err) { - // Clean up temporary file - try { - fs.unlinkSync(tarPathTemp); - } catch (e) {} - fail(err); - }) - .on('close', function () { - try { - // Attempt to rename - fs.renameSync(tarPathTemp, tarPathCache); - } catch (err) { - // Fall back to copy and unlink - fs.copyFileSync(tarPathTemp, tarPathCache); - fs.unlinkSync(tarPathTemp); - } - extractTarball(tarPathCache, platformAndArch); - }); - } - }); - } - } -} catch (err) { - fail(err); -} diff --git a/lib/agent.js b/lib/agent.js deleted file mode 100644 index 74b6f47e5..000000000 --- a/lib/agent.js +++ /dev/null @@ -1,44 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const url = require('url'); -const tunnelAgent = require('tunnel-agent'); - -const is = require('./is'); - -const proxies = [ - 'HTTPS_PROXY', - 'https_proxy', - 'HTTP_PROXY', - 'http_proxy', - 'npm_config_https_proxy', - 'npm_config_proxy' -]; - -function env (key) { - return process.env[key]; -} - -module.exports = function (log) { - try { - const proxy = new url.URL(proxies.map(env).find(is.string)); - const tunnel = proxy.protocol === 'https:' - ? tunnelAgent.httpsOverHttps - : tunnelAgent.httpsOverHttp; - const proxyAuth = proxy.username && proxy.password - ? `${decodeURIComponent(proxy.username)}:${decodeURIComponent(proxy.password)}` - : null; - log(`Via proxy ${proxy.protocol}//${proxy.hostname}:${proxy.port} ${proxyAuth ? 'with' : 'no'} credentials`); - return tunnel({ - proxy: { - port: Number(proxy.port), - host: proxy.hostname, - proxyAuth - } - }); - } catch (err) { - return null; - } -}; diff --git a/lib/constructor.js b/lib/constructor.js index 1fbd6e34b..bbf2534eb 100644 --- a/lib/constructor.js +++ b/lib/constructor.js @@ -7,7 +7,6 @@ const util = require('util'); const stream = require('stream'); const is = require('./is'); -require('./libvips').hasVendoredLibvips(); require('./sharp'); // Use NODE_DEBUG=sharp to enable libvips warnings diff --git a/lib/index.d.ts b/lib/index.d.ts index cf504a99c..2db30a803 100644 --- a/lib/index.d.ts +++ b/lib/index.d.ts @@ -91,12 +91,6 @@ declare namespace sharp { zlib?: string | undefined; }; - /** An Object containing the platform and architecture of the current and installed vendored binaries. */ - const vendor: { - current: string; - installed: string[]; - }; - /** An Object containing the available interpolators and their proper values */ const interpolators: Interpolators; diff --git a/lib/libvips.js b/lib/libvips.js index ca001d953..583c17b40 100644 --- a/lib/libvips.js +++ b/lib/libvips.js @@ -3,61 +3,74 @@ 'use strict'; -const fs = require('fs'); -const os = require('os'); -const path = require('path'); const spawnSync = require('child_process').spawnSync; const semverCoerce = require('semver/functions/coerce'); const semverGreaterThanOrEqualTo = require('semver/functions/gte'); +const detectLibc = require('detect-libc'); -const platform = require('./platform'); -const { config } = require('../package.json'); +const { engines } = require('../package.json'); -const env = process.env; -const minimumLibvipsVersionLabelled = env.npm_package_config_libvips || /* istanbul ignore next */ - config.libvips; +const minimumLibvipsVersionLabelled = process.env.npm_package_config_libvips || /* istanbul ignore next */ + engines.libvips; const minimumLibvipsVersion = semverCoerce(minimumLibvipsVersionLabelled).version; +const prebuiltPlatforms = [ + 'darwin-arm64', 'darwin-x64', + 'linux-arm', 'linux-arm64', 'linux-x64', + 'linuxmusl-arm64', 'linuxmusl-x64', + 'win32-ia32', 'win32-x64' +]; + const spawnSyncOptions = { encoding: 'utf8', shell: true }; -const vendorPath = path.join(__dirname, '..', 'vendor', minimumLibvipsVersion, platform()); - -const mkdirSync = function (dirPath) { - try { - fs.mkdirSync(dirPath, { recursive: true }); - } catch (err) { - /* istanbul ignore next */ - if (err.code !== 'EEXIST') { - throw err; - } +const log = (item) => { + if (item instanceof Error) { + console.error(`sharp: Installation error: ${item.message}`); + } else { + console.log(`sharp: ${item}`); } }; -const cachePath = function () { - const npmCachePath = env.npm_config_cache || /* istanbul ignore next */ - (env.APPDATA ? path.join(env.APPDATA, 'npm-cache') : path.join(os.homedir(), '.npm')); - mkdirSync(npmCachePath); - const libvipsCachePath = path.join(npmCachePath, '_libvips'); - mkdirSync(libvipsCachePath); - return libvipsCachePath; +/* istanbul ignore next */ +const runtimeLibc = () => detectLibc.isNonGlibcLinuxSync() ? detectLibc.familySync() : ''; + +const runtimePlatformArch = () => `${process.platform}${runtimeLibc()}-${process.arch}`; + +/* istanbul ignore next */ +const buildPlatformArch = () => { + /* eslint camelcase: ["error", { allow: ["^npm_config_"] }] */ + const { npm_config_arch, npm_config_platform, npm_config_libc } = process.env; + return `${npm_config_platform || process.platform}${npm_config_libc || runtimeLibc()}-${npm_config_arch || process.arch}`; }; -const integrity = function (platformAndArch) { - return env[`npm_package_config_integrity_${platformAndArch.replace('-', '_')}`] || config.integrity[platformAndArch]; +const buildSharpLibvipsIncludeDir = () => { + try { + return require('@sharpen/sharp-libvips-dev/include'); + } catch {} + /* istanbul ignore next */ + return ''; }; -const log = function (item) { - if (item instanceof Error) { - console.error(`sharp: Installation error: ${item.message}`); - } else { - console.log(`sharp: ${item}`); - } +const buildSharpLibvipsCPlusPlusDir = () => { + try { + return require('@sharpen/sharp-libvips-dev/cplusplus'); + } catch {} + /* istanbul ignore next */ + return ''; }; -const isRosetta = function () { +const buildSharpLibvipsLibDir = () => { + try { + return require(`@sharpen/sharp-libvips-${buildPlatformArch()}/lib`); + } catch {} + /* istanbul ignore next */ + return ''; +}; + +const isRosetta = () => { /* istanbul ignore next */ if (process.platform === 'darwin' && process.arch === 'x64') { const translated = spawnSync('sysctl sysctl.proc_translated', spawnSyncOptions).stdout; @@ -66,12 +79,12 @@ const isRosetta = function () { return false; }; -const globalLibvipsVersion = function () { +const globalLibvipsVersion = () => { if (process.platform !== 'win32') { const globalLibvipsVersion = spawnSync('pkg-config --modversion vips-cpp', { ...spawnSyncOptions, env: { - ...env, + ...process.env, PKG_CONFIG_PATH: pkgConfigPath() } }).stdout; @@ -82,17 +95,8 @@ const globalLibvipsVersion = function () { } }; -const hasVendoredLibvips = function () { - return fs.existsSync(vendorPath); -}; - -/* istanbul ignore next */ -const removeVendoredLibvips = function () { - fs.rmSync(vendorPath, { recursive: true, maxRetries: 3, force: true }); -}; - /* istanbul ignore next */ -const pkgConfigPath = function () { +const pkgConfigPath = () => { if (process.platform !== 'win32') { const brewPkgConfigPath = spawnSync( 'which brew >/dev/null 2>&1 && brew environment --plain | grep PKG_CONFIG_LIBDIR | cut -d" " -f2', @@ -100,7 +104,7 @@ const pkgConfigPath = function () { ).stdout || ''; return [ brewPkgConfigPath.trim(), - env.PKG_CONFIG_PATH, + process.env.PKG_CONFIG_PATH, '/usr/local/lib/pkgconfig', '/usr/lib/pkgconfig', '/usr/local/libdata/pkgconfig', @@ -111,8 +115,9 @@ const pkgConfigPath = function () { } }; -const useGlobalLibvips = function () { - if (Boolean(env.SHARP_IGNORE_GLOBAL_LIBVIPS) === true) { +const useGlobalLibvips = () => { + if (Boolean(process.env.SHARP_IGNORE_GLOBAL_LIBVIPS) === true) { + log('Detected SHARP_IGNORE_GLOBAL_LIBVIPS, skipping search for globally-installed libvips'); return false; } /* istanbul ignore next */ @@ -127,14 +132,14 @@ const useGlobalLibvips = function () { module.exports = { minimumLibvipsVersion, - minimumLibvipsVersionLabelled, - cachePath, - integrity, + prebuiltPlatforms, + buildPlatformArch, + buildSharpLibvipsIncludeDir, + buildSharpLibvipsCPlusPlusDir, + buildSharpLibvipsLibDir, + runtimePlatformArch, log, globalLibvipsVersion, - hasVendoredLibvips, - removeVendoredLibvips, pkgConfigPath, - useGlobalLibvips, - mkdirSync + useGlobalLibvips }; diff --git a/lib/platform.js b/lib/platform.js deleted file mode 100644 index 71454e3ea..000000000 --- a/lib/platform.js +++ /dev/null @@ -1,30 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const detectLibc = require('detect-libc'); - -const env = process.env; - -module.exports = function () { - const arch = env.npm_config_arch || process.arch; - const platform = env.npm_config_platform || process.platform; - const libc = process.env.npm_config_libc || - /* istanbul ignore next */ - (detectLibc.isNonGlibcLinuxSync() ? detectLibc.familySync() : ''); - const libcId = platform !== 'linux' || libc === detectLibc.GLIBC ? '' : libc; - - const platformId = [`${platform}${libcId}`]; - - if (arch === 'arm') { - const fallback = process.versions.electron ? '7' : '6'; - platformId.push(`armv${env.npm_config_arm_version || process.config.variables.arm_version || fallback}`); - } else if (arch === 'arm64') { - platformId.push(`arm64v${env.npm_config_arm_version || '8'}`); - } else { - platformId.push(arch); - } - - return platformId.join('-'); -}; diff --git a/lib/sharp.js b/lib/sharp.js index a41e83d0b..26951535d 100644 --- a/lib/sharp.js +++ b/lib/sharp.js @@ -3,36 +3,58 @@ 'use strict'; -const platformAndArch = require('./platform')(); +// Inspects the runtime environment and exports the relevant sharp.node binary + +const { familySync, versionSync } = require('detect-libc'); + +const { runtimePlatformArch, prebuiltPlatforms, minimumLibvipsVersion } = require('./libvips'); +const runtimePlatform = runtimePlatformArch(); /* istanbul ignore next */ try { - module.exports = require(`../build/Release/sharp-${platformAndArch}.node`); -} catch (err) { - // Bail early if bindings aren't available - const help = ['', 'Something went wrong installing the "sharp" module', '', err.message, '', 'Possible solutions:']; - if (/dylib/.test(err.message) && /Incompatible library version/.test(err.message)) { - help.push('- Update Homebrew: "brew update && brew upgrade vips"'); - } else { - const [platform, arch] = platformAndArch.split('-'); - if (platform === 'linux' && /Module did not self-register/.test(err.message)) { - help.push('- Using worker threads? See https://sharp.pixelplumbing.com/install#worker-threads'); + // Check for local build + module.exports = require(`../build/Release/sharp-${runtimePlatform}.node`); +} catch (errLocal) { + try { + // Check for runtime package + module.exports = require(`@sharpen/sharp-${runtimePlatform}/sharp.node`); + } catch (errPackage) { + const help = ['Could not load the "sharp" module at runtime']; + if (errLocal.code !== 'MODULE_NOT_FOUND') { + help.push(`${errLocal.code}: ${errLocal.message}`); } - help.push( - '- Install with verbose logging and look for errors: "npm install --ignore-scripts=false --foreground-scripts --verbose sharp"', - `- Install for the current ${platformAndArch} runtime: "npm install --platform=${platform} --arch=${arch} sharp"` - ); - } - help.push( - '- Consult the installation documentation: https://sharp.pixelplumbing.com/install' - ); - // Check loaded - if (process.platform === 'win32' || /symbol/.test(err.message)) { - const loadedModule = Object.keys(require.cache).find((i) => /[\\/]build[\\/]Release[\\/]sharp(.*)\.node$/.test(i)); - if (loadedModule) { - const [, loadedPackage] = loadedModule.match(/node_modules[\\/]([^\\/]+)[\\/]/); - help.push(`- Ensure the version of sharp aligns with the ${loadedPackage} package: "npm ls sharp"`); + if (errPackage.code !== 'MODULE_NOT_FOUND') { + help.push(`${errPackage.code}: ${errPackage.message}`); + } + help.push('Possible solutions:'); + // Common error messages + if (prebuiltPlatforms.includes(runtimePlatform)) { + help.push(`- Add an explicit dependency for the runtime platform: "npm install --force @sharpen/sharp-${runtimePlatform}"`); + } else { + help.push(`- The ${runtimePlatform} platform requires manual installation of libvips >= ${minimumLibvipsVersion}`); + } + if (runtimePlatform.startsWith('linux') && /symbol not found/i.test(errPackage)) { + try { + const { engines } = require(`@sharpen/sharp-libvips-${runtimePlatform}/package`); + const libcFound = `${familySync()} ${versionSync()}`; + const libcRequires = `${engines.musl ? 'musl' : 'glibc'} ${engines.musl || engines.glibc}`; + help.push(`- Update your OS: found ${libcFound}, requires ${libcRequires}`); + } catch (errEngines) {} + } + if (runtimePlatform.startsWith('darwin') && /Incompatible library version/.test(errLocal.message)) { + help.push('- Update Homebrew: "brew update && brew upgrade vips"'); + } + if (errPackage.code === 'ERR_DLOPEN_DISABLED') { + help.push('- Run Node.js without using the --no-addons flag'); + } + // Link to installation docs + if (runtimePlatform.startsWith('linux') && /Module did not self-register/.test(errLocal.message + errPackage.message)) { + help.push('- Using worker threads on Linux? See https://sharp.pixelplumbing.com/install#worker-threads'); + } else if (runtimePlatform.startsWith('win32') && /The specified procedure could not be found/.test(errPackage.message)) { + help.push('- Using the canvas package on Windows? See https://sharp.pixelplumbing.com/install#canvas-and-windows'); + } else { + help.push('- Consult the installation documentation: https://sharp.pixelplumbing.com/install'); } + throw new Error(help.join('\n')); } - throw new Error(help.join('\n')); } diff --git a/lib/utility.js b/lib/utility.js index 8b1a42e54..548ecd901 100644 --- a/lib/utility.js +++ b/lib/utility.js @@ -3,13 +3,11 @@ 'use strict'; -const fs = require('fs'); -const path = require('path'); const events = require('events'); const detectLibc = require('detect-libc'); const is = require('./is'); -const platformAndArch = require('./platform')(); +const { runtimePlatformArch } = require('./libvips'); const sharp = require('./sharp'); /** @@ -55,25 +53,14 @@ let versions = { vips: sharp.libvipsVersion() }; try { - versions = require(`../vendor/${versions.vips}/${platformAndArch}/versions.json`); -} catch (_err) { /* ignore */ } + versions = require(`@sharpen/sharp-${runtimePlatformArch()}/versions`); +} catch (_) { + try { + versions = require(`@sharpen/sharp-libvips-${runtimePlatformArch()}/versions`); + } catch (_) {} +} versions.sharp = require('../package.json').version; -/** - * An Object containing the platform and architecture - * of the current and installed vendored binaries. - * @member - * @example - * console.log(sharp.vendor); - */ -const vendor = { - current: platformAndArch, - installed: [] -}; -try { - vendor.installed = fs.readdirSync(path.join(__dirname, `../vendor/${versions.vips}`)); -} catch (_err) { /* ignore */ } - /** * Gets or, when options are provided, sets the limits of _libvips'_ operation cache. * Existing entries in the cache will be trimmed after any change in limits. @@ -280,7 +267,6 @@ module.exports = function (Sharp) { Sharp.format = format; Sharp.interpolators = interpolators; Sharp.versions = versions; - Sharp.vendor = vendor; Sharp.queue = queue; Sharp.block = block; Sharp.unblock = unblock; diff --git a/npm/darwin-arm64/package.json b/npm/darwin-arm64/package.json new file mode 100644 index 000000000..353720a88 --- /dev/null +++ b/npm/darwin-arm64/package.json @@ -0,0 +1,42 @@ +{ + "name": "@sharpen/sharp-darwin-arm64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with macOS ARM64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/darwin-arm64" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-darwin-arm64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-darwin-arm64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "glibc": ">=2.26" + }, + "os": [ + "darwin" + ], + "cpu": [ + "arm64" + ] +} diff --git a/npm/darwin-x64/package.json b/npm/darwin-x64/package.json new file mode 100644 index 000000000..89e4adb59 --- /dev/null +++ b/npm/darwin-x64/package.json @@ -0,0 +1,39 @@ +{ + "name": "@sharpen/sharp-darwin-x64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with macOS x64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/darwin-x64" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-darwin-x64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "exports": { + "./sharp.node": "./lib/sharp-darwin-x64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "glibc": ">=2.26" + }, + "os": [ + "darwin" + ], + "cpu": [ + "x64" + ] +} diff --git a/npm/from-github-release.js b/npm/from-github-release.js new file mode 100644 index 000000000..da71ce44d --- /dev/null +++ b/npm/from-github-release.js @@ -0,0 +1,51 @@ +// Copyright 2013 Lovell Fuller and others. +// SPDX-License-Identifier: Apache-2.0 + +'use strict'; + +// Populate contents of all packages with the current GitHub release + +const { writeFile, copyFile } = require('node:fs/promises'); +const path = require('node:path'); +const { Readable } = require('node:stream'); +const { pipeline } = require('node:stream/promises'); +const { createGunzip } = require('node:zlib'); +const { extract } = require('tar-fs'); + +const { workspaces } = require('./package.json'); +const { version } = require('../package.json'); + +const mapTarballEntry = (header) => { + header.name = path.basename(header.name); + return header; +}; + +workspaces.map(async platform => { + const url = `https://github.com/lovell/sharp/releases/download/v${version}/sharp-v${version}-napi-v7-${platform}.tar.gz`; + const dir = path.join(__dirname, platform); + const response = await fetch(url); + if (!response.ok) { + console.log(`Skipping ${platform}: ${response.statusText}`); + return; + } + // Extract prebuild tarball + await pipeline( + Readable.fromWeb(response.body), + createGunzip(), + extract(path.join(dir, 'lib'), { map: mapTarballEntry }) + ); + // Generate README + const { name, description } = require(`./${platform}/package.json`); + await writeFile(path.join(dir, 'README.md'), `# ${name}\n${description}`); + // Copy Apache-2.0 LICENSE + await copyFile(path.join(__dirname, '..', 'LICENSE'), path.join(dir, 'LICENSE')); + // Copy Windows-specific files + if (platform.startsWith('win32-')) { + const sharpLibvipsDir = path.join(require(`@sharpen/sharp-libvips-${platform}/lib`), '..'); + await Promise.all( + ['versions.json', 'THIRD-PARTY-NOTICES.md'].map( + filename => copyFile(path.join(sharpLibvipsDir, filename), path.join(dir, filename)) + ) + ); + } +}); diff --git a/npm/from-local-build.js b/npm/from-local-build.js new file mode 100644 index 000000000..c53713e66 --- /dev/null +++ b/npm/from-local-build.js @@ -0,0 +1,26 @@ +// Copyright 2013 Lovell Fuller and others. +// SPDX-License-Identifier: Apache-2.0 + +'use strict'; + +// Populate contents of a single npm/sharpen-sharp- package +// with the local/CI build directory for local/CI prebuild testing + +const fs = require('node:fs'); +const path = require('node:path'); + +const { buildPlatformArch } = require('../lib/libvips'); +const platform = buildPlatformArch(); +const dest = path.join(__dirname, platform); + +// Use same config as prebuild to copy binary files +const release = path.join(__dirname, '..', 'build', 'Release'); +const prebuildrc = JSON.parse(fs.readFileSync(path.join(__dirname, '..', '.prebuildrc'), 'utf8')); +const include = new RegExp(prebuildrc['include-regex'], 'i'); +fs.cpSync(release, path.join(dest, 'lib'), { + recursive: true, + filter: (file) => { + const name = path.basename(file); + return name === 'Release' || include.test(name); + } +}); diff --git a/npm/linux-arm/package.json b/npm/linux-arm/package.json new file mode 100644 index 000000000..90a0c8093 --- /dev/null +++ b/npm/linux-arm/package.json @@ -0,0 +1,45 @@ +{ + "name": "@sharpen/sharp-linux-arm", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Linux (glibc) ARM (32-bit)", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/linux-arm" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-linux-arm": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-linux-arm.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "glibc": ">=2.28" + }, + "os": [ + "linux" + ], + "libc": [ + "glibc" + ], + "cpu": [ + "arm" + ] +} diff --git a/npm/linux-arm64/package.json b/npm/linux-arm64/package.json new file mode 100644 index 000000000..43b30070b --- /dev/null +++ b/npm/linux-arm64/package.json @@ -0,0 +1,45 @@ +{ + "name": "@sharpen/sharp-linux-arm64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Linux (glibc) ARM64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/linux-arm64" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-linux-arm64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-linux-arm64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "glibc": ">=2.26" + }, + "os": [ + "linux" + ], + "libc": [ + "glibc" + ], + "cpu": [ + "arm64" + ] +} diff --git a/npm/linux-x64/package.json b/npm/linux-x64/package.json new file mode 100644 index 000000000..27e456ce1 --- /dev/null +++ b/npm/linux-x64/package.json @@ -0,0 +1,45 @@ +{ + "name": "@sharpen/sharp-linux-x64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Linux (glibc) x64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/linux-x64" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-linux-x64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-linux-x64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "glibc": ">=2.26" + }, + "os": [ + "linux" + ], + "libc": [ + "glibc" + ], + "cpu": [ + "x64" + ] +} diff --git a/npm/linuxmusl-arm64/package.json b/npm/linuxmusl-arm64/package.json new file mode 100644 index 000000000..4c07688a1 --- /dev/null +++ b/npm/linuxmusl-arm64/package.json @@ -0,0 +1,45 @@ +{ + "name": "@sharpen/sharp-linuxmusl-arm64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Linux (musl) ARM64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/linuxmusl-arm64" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-linuxmusl-arm64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-linuxmusl-arm64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "musl": ">=1.2.2" + }, + "os": [ + "linux" + ], + "libc": [ + "musl" + ], + "cpu": [ + "arm64" + ] +} diff --git a/npm/linuxmusl-x64/package.json b/npm/linuxmusl-x64/package.json new file mode 100644 index 000000000..4433bcfa9 --- /dev/null +++ b/npm/linuxmusl-x64/package.json @@ -0,0 +1,45 @@ +{ + "name": "@sharpen/sharp-linuxmusl-x64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Linux (musl) x64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/linuxmusl-x64" + }, + "license": "Apache-2.0", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-linuxmusl-x64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-linuxmusl-x64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0", + "musl": ">=1.2.2" + }, + "os": [ + "linux" + ], + "libc": [ + "musl" + ], + "cpu": [ + "x64" + ] +} diff --git a/npm/package.json b/npm/package.json new file mode 100644 index 000000000..aaa627bc1 --- /dev/null +++ b/npm/package.json @@ -0,0 +1,16 @@ +{ + "name": "@sharpen/sharp", + "version": "0.0.1-alpha.1", + "private": "true", + "workspaces": [ + "darwin-x64", + "darwin-arm64", + "linux-arm", + "linux-arm64", + "linuxmusl-arm64", + "linuxmusl-x64", + "linux-x64", + "win32-ia32", + "win32-x64" + ] +} diff --git a/npm/win32-ia32/package.json b/npm/win32-ia32/package.json new file mode 100644 index 000000000..f9d685c90 --- /dev/null +++ b/npm/win32-ia32/package.json @@ -0,0 +1,41 @@ +{ + "name": "@sharpen/sharp-win32-ia32", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Windows x86 (32-bit)", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/win32-ia32" + }, + "license": "Apache-2.0 AND LGPL-3.0-or-later", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-win32-ia32": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-win32-ia32.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0" + }, + "os": [ + "win32" + ], + "cpu": [ + "ia32" + ] +} diff --git a/npm/win32-x64/package.json b/npm/win32-x64/package.json new file mode 100644 index 000000000..c994fecc9 --- /dev/null +++ b/npm/win32-x64/package.json @@ -0,0 +1,41 @@ +{ + "name": "@sharpen/sharp-win32-x64", + "version": "0.0.1-alpha.1", + "description": "Prebuilt sharp for use with Windows x64", + "homepage": "https://sharp.pixelplumbing.com", + "repository": { + "type": "git", + "url": "git+https://github.com/lovell/sharp.git", + "directory": "npm/win32-x64" + }, + "license": "Apache-2.0 AND LGPL-3.0-or-later", + "funding": { + "url": "https://opencollective.com/libvips" + }, + "preferUnplugged": true, + "optionalDependencies": { + "@sharpen/sharp-libvips-win32-x64": "0.0.1-alpha.1" + }, + "files": [ + "lib" + ], + "publishConfig": { + "access": "public" + }, + "exports": { + "./sharp.node": "./lib/sharp-win32-x64.node", + "./package": "./package.json" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "npm": ">=9.6.5", + "yarn": ">=3.2.0", + "pnpm": ">=7.1.0" + }, + "os": [ + "win32" + ], + "cpu": [ + "x64" + ] +} diff --git a/package.json b/package.json index fe62da083..0fc6f7b6d 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "sharp", "description": "High performance Node.js image processing, the fastest module to resize JPEG, PNG, WebP, GIF, AVIF and TIFF images", - "version": "0.32.6", + "version": "0.33.0-alpha.1", "author": "Lovell Fuller ", "homepage": "https://github.com/lovell/sharp", "contributors": [ @@ -89,14 +89,16 @@ "Lachlan Newman " ], "scripts": { - "install": "(node install/libvips && node install/dll-copy && prebuild-install) || (node install/can-compile && node-gyp rebuild && node install/dll-copy)", - "clean": "rm -rf node_modules/ build/ vendor/ .nyc_output/ coverage/ test/fixtures/output.*", + "install": "node install/check || node-gyp rebuild", + "clean": "rm -rf build/ .nyc_output/ coverage/ test/fixtures/output.*", "test": "npm run test-lint && npm run test-unit && npm run test-licensing && npm run test-types", "test-lint": "semistandard && cpplint", "test-unit": "nyc --reporter=lcov --reporter=text --check-coverage --branches=100 mocha", - "test-licensing": "license-checker --production --summary --onlyAllow=\"Apache-2.0;BSD;ISC;MIT\"", + "test-licensing": "license-checker --production --summary --onlyAllow=\"Apache-2.0;BSD;ISC;LGPL-3.0-or-later;MIT\"", "test-leak": "./test/leak/leak.sh", "test-types": "tsd", + "package-from-local-build": "node npm/from-local-build", + "package-from-github-release": "node npm/from-github-release", "docs-build": "node docs/build && node docs/search-index/build", "docs-serve": "cd docs && npx serve", "docs-publish": "cd docs && npx firebase-tools deploy --project pixelplumbing --only hosting:pixelplumbing-sharp" @@ -111,7 +113,7 @@ ], "repository": { "type": "git", - "url": "git://github.com/lovell/sharp" + "url": "git://github.com/lovell/sharp.git" }, "keywords": [ "jpeg", @@ -135,13 +137,30 @@ "color": "^4.2.3", "detect-libc": "^2.0.2", "node-addon-api": "^7.0.0", - "prebuild-install": "^7.1.1", - "semver": "^7.5.4", - "simple-get": "^4.0.1", - "tar-fs": "^3.0.4", - "tunnel-agent": "^0.6.0" + "semver": "^7.5.4" + }, + "optionalDependencies": { + "@sharpen/sharp-darwin-arm64": "0.0.1-alpha.1", + "@sharpen/sharp-darwin-x64": "0.0.1-alpha.1", + "@sharpen/sharp-linux-arm": "0.0.1-alpha.1", + "@sharpen/sharp-linux-arm64": "0.0.1-alpha.1", + "@sharpen/sharp-linux-x64": "0.0.1-alpha.1", + "@sharpen/sharp-linuxmusl-arm64": "0.0.1-alpha.1", + "@sharpen/sharp-linuxmusl-x64": "0.0.1-alpha.1", + "@sharpen/sharp-win32-ia32": "0.0.1-alpha.1", + "@sharpen/sharp-win32-x64": "0.0.1-alpha.1" }, "devDependencies": { + "@sharpen/sharp-libvips-darwin-arm64": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-darwin-x64": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-dev": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-linux-arm": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-linux-arm64": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-linux-x64": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-linuxmusl-arm64": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-linuxmusl-x64": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-win32-ia32": "0.0.1-alpha.1", + "@sharpen/sharp-libvips-win32-x64": "0.0.1-alpha.1", "@types/node": "*", "async": "^3.2.4", "cc": "^3.0.1", @@ -151,33 +170,16 @@ "jsdoc-to-markdown": "^8.0.0", "license-checker": "^25.0.1", "mocha": "^10.2.0", - "mock-fs": "^5.2.0", "nyc": "^15.1.0", "prebuild": "^12.1.0", "semistandard": "^16.0.1", + "tar-fs": "^3.0.4", "tsd": "^0.29.0" }, "license": "Apache-2.0", - "config": { - "libvips": "8.14.5", - "integrity": { - "darwin-arm64v8": "sha512-1QZzICfCJd4wAO0P6qmYI5e5VFMt9iCE4QgefI8VMMbdSzjIXA9L/ARN6pkMQPZ3h20Y9RtJ2W1skgCsvCIccw==", - "darwin-x64": "sha512-sMIKMYXsdU9FlIfztj6Kt/SfHlhlDpP0Ups7ftVFqwjaszmYmpI9y/d/q3mLb4jrzuSiSUEislSWCwBnW7MPTw==", - "linux-arm64v8": "sha512-CD8owELzkDumaom+O3jJ8fKamILAQdj+//KK/VNcHK3sngUcFpdjx36C8okwbux9sml/T7GTB/gzpvReDrAejQ==", - "linux-armv6": "sha512-wk6IPHatDFVWKJy7lI1TJezHGHPQut1wF2bwx256KlZwXUQU3fcVcMpV1zxXjgLFewHq2+uhyMkoSGBPahWzlA==", - "linux-armv7": "sha512-HEZC9KYtkmBK5rUR2MqBhrVarnQVZ/TwLUeLkKq0XuoM2pc/eXI6N0Fh5NGEFwdXI2XE8g1ySf+OYS6DDi+xCQ==", - "linux-x64": "sha512-SlFWrITSW5XVUkaFPQOySAaSGXnhkGJCj8X2wGYYta9hk5piZldQyMp4zwy0z6UeRu1qKTKtZvmq28W3Gnh9xA==", - "linuxmusl-arm64v8": "sha512-ga9iX7WUva3sG/VsKkOD318InLlCfPIztvzCZKZ2/+izQXRbQi8VoXWMHgEN4KHACv45FTl7mJ/8CRqUzhS8wQ==", - "linuxmusl-x64": "sha512-yeaHnpfee1hrZLok2l4eFceHzlfq8gN3QOu0R4Mh8iMK5O5vAUu97bdtxeZZeJJvHw8tfh2/msGi0qysxKN8bw==", - "win32-arm64v8": "sha512-kR91hy9w1+GEXK56hLh51+hBCBo7T+ijM4Slkmvb/2PsYZySq5H7s61n99iDYl6kTJP2y9sW5Xcvm3uuXDaDgg==", - "win32-ia32": "sha512-HrnofEbzHNpHJ0vVnjsTj5yfgVdcqdWshXuwFO2zc8xlEjA83BvXZ0lVj9MxPxkxJ2ta+/UlLr+CFzc5bOceMw==", - "win32-x64": "sha512-BwKckinJZ0Fu/EcunqiLPwOLEBWp4xf8GV7nvmVuKKz5f6B+GxoA2k9aa2wueqv4r4RJVgV/aWXZWFKOIjre/Q==" - }, - "runtime": "napi", - "target": 9 - }, "engines": { - "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + "node": "^18.17.0 || ^20.3.0 || >=21.0.0", + "libvips": ">=8.14.5" }, "funding": { "url": "https://opencollective.com/libvips" diff --git a/src/libvips/cplusplus/VConnection.cpp b/src/libvips/cplusplus/VConnection.cpp deleted file mode 100644 index 55451415a..000000000 --- a/src/libvips/cplusplus/VConnection.cpp +++ /dev/null @@ -1,151 +0,0 @@ -/* Object part of the VSource and VTarget class - */ - -/* - - Copyright (C) 1991-2001 The National Gallery - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation; either version 2 of the License, 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 Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser 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 - - */ - -/* - - These files are distributed with VIPS - http://www.vips.ecs.soton.ac.uk - - */ - -#ifdef HAVE_CONFIG_H -#include -#endif /*HAVE_CONFIG_H*/ - -#include - -#include - -/* -#define VIPS_DEBUG -#define VIPS_DEBUG_VERBOSE - */ - -VIPS_NAMESPACE_START - -VSource -VSource::new_from_descriptor( int descriptor ) -{ - VipsSource *input; - - if( !(input = vips_source_new_from_descriptor( descriptor )) ) - throw VError(); - - VSource out( input ); - - return( out ); -} - -VSource -VSource::new_from_file( const char *filename ) -{ - VipsSource *input; - - if( !(input = vips_source_new_from_file( filename )) ) - throw VError(); - - VSource out( input ); - - return( out ); -} - -VSource -VSource::new_from_blob( VipsBlob *blob ) -{ - VipsSource *input; - - if( !(input = vips_source_new_from_blob( blob )) ) - throw VError(); - - VSource out( input ); - - return( out ); -} - -VSource -VSource::new_from_memory( const void *data, - size_t size ) -{ - VipsSource *input; - - if( !(input = vips_source_new_from_memory( data, size )) ) - throw VError(); - - VSource out( input ); - - return( out ); -} - -VSource -VSource::new_from_options( const char *options ) -{ - VipsSource *input; - - if( !(input = vips_source_new_from_options( options )) ) - throw VError(); - - VSource out( input ); - - return( out ); -} - -VTarget -VTarget::new_to_descriptor( int descriptor ) -{ - VipsTarget *output; - - if( !(output = vips_target_new_to_descriptor( descriptor )) ) - throw VError(); - - VTarget out( output ); - - return( out ); -} - -VTarget -VTarget::new_to_file( const char *filename ) -{ - VipsTarget *output; - - if( !(output = vips_target_new_to_file( filename )) ) - throw VError(); - - VTarget out( output ); - - return( out ); -} - -VTarget -VTarget::new_to_memory() -{ - VipsTarget *output; - - if( !(output = vips_target_new_to_memory()) ) - throw VError(); - - VTarget out( output ); - - return( out ); -} - -VIPS_NAMESPACE_END diff --git a/src/libvips/cplusplus/VError.cpp b/src/libvips/cplusplus/VError.cpp deleted file mode 100644 index 3be490689..000000000 --- a/src/libvips/cplusplus/VError.cpp +++ /dev/null @@ -1,49 +0,0 @@ -// Code for error type - -/* - - Copyright (C) 1991-2001 The National Gallery - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation; either version 2 of the License, 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 Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser 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 - - */ - -/* - - These files are distributed with VIPS - http://www.vips.ecs.soton.ac.uk - - */ - -#ifdef HAVE_CONFIG_H -#include -#endif /*HAVE_CONFIG_H*/ - -#include - -VIPS_NAMESPACE_START - -std::ostream &operator<<( std::ostream &file, const VError &err ) -{ - err.ostream_print( file ); - return( file ); -} - -void VError::ostream_print( std::ostream &file ) const -{ - file << _what; -} - -VIPS_NAMESPACE_END diff --git a/src/libvips/cplusplus/VImage.cpp b/src/libvips/cplusplus/VImage.cpp deleted file mode 100644 index 72c3fa9dc..000000000 --- a/src/libvips/cplusplus/VImage.cpp +++ /dev/null @@ -1,1548 +0,0 @@ -/* Object part of VImage class - * - * 30/12/14 - * - allow set enum value from string - * 10/6/16 - * - missing implementation of VImage::write() - * 11/6/16 - * - added arithmetic assignment overloads, += etc. - */ - -/* - - Copyright (C) 1991-2001 The National Gallery - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation; either version 2 of the License, 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 Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser 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 - - */ - -/* - - These files are distributed with VIPS - http://www.vips.ecs.soton.ac.uk - - */ - -#ifdef HAVE_CONFIG_H -#include -#endif /*HAVE_CONFIG_H*/ - -#include - -#include - -/* -#define VIPS_DEBUG -#define VIPS_DEBUG_VERBOSE - */ - -VIPS_NAMESPACE_START - -/** - * \namespace vips - * - * General docs for the vips namespace. - */ - -std::vector -to_vectorv( int n, ... ) -{ - std::vector vector( n ); - va_list ap; - - va_start( ap, n ); - for( int i = 0; i < n; i++ ) - vector[i] = va_arg( ap, double ); - va_end( ap ); - - return( vector ); -} - -std::vector -to_vector( double value ) -{ - return( to_vectorv( 1, value ) ); -} - -std::vector -to_vector( int n, double array[] ) -{ - std::vector vector( n ); - - for( int i = 0; i < n; i++ ) - vector[i] = array[i]; - - return( vector ); -} - -std::vector -negate( std::vector vector ) -{ - std::vector new_vector( vector.size() ); - - for( std::vector::size_type i = 0; i < vector.size(); i++ ) - new_vector[i] = vector[i] * -1; - - return( new_vector ); -} - -std::vector -invert( std::vector vector ) -{ - std::vector new_vector( vector.size() ); - - for( std::vector::size_type i = 0; i < vector.size(); i++ ) - new_vector[i] = 1.0 / vector[i]; - - return( new_vector ); -} - -VOption::~VOption() -{ - std::list::iterator i; - - for( i = options.begin(); i != options.end(); ++i ) - delete *i; -} - -// input bool -VOption * -VOption::set( const char *name, bool value ) -{ - Pair *pair = new Pair( name ); - - pair->input = true; - g_value_init( &pair->value, G_TYPE_BOOLEAN ); - g_value_set_boolean( &pair->value, value ); - options.push_back( pair ); - - return( this ); -} - -// input int ... this path is used for enums as well -VOption * -VOption::set( const char *name, int value ) -{ - Pair *pair = new Pair( name ); - - pair->input = true; - g_value_init( &pair->value, G_TYPE_INT ); - g_value_set_int( &pair->value, value ); - options.push_back( pair ); - - return( this ); -} - -// input guint64 -VOption * -VOption::set( const char *name, guint64 value ) -{ - Pair *pair = new Pair( name ); - - pair->input = true; - g_value_init( &pair->value, G_TYPE_UINT64 ); - g_value_set_uint64( &pair->value, value ); - options.push_back( pair ); - - return( this ); -} - -// input double -VOption * -VOption::set( const char *name, double value ) -{ - Pair *pair = new Pair( name ); - - pair->input = true; - g_value_init( &pair->value, G_TYPE_DOUBLE ); - g_value_set_double( &pair->value, value ); - options.push_back( pair ); - - return( this ); -} - -VOption * -VOption::set( const char *name, const char *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = true; - g_value_init( &pair->value, G_TYPE_STRING ); - g_value_set_string( &pair->value, value ); - options.push_back( pair ); - - return( this ); -} - -// input vips object (image, source, target, etc. etc.) -VOption * -VOption::set( const char *name, const VObject value ) -{ - Pair *pair = new Pair( name ); - VipsObject *object = value.get_object(); - GType type = G_OBJECT_TYPE( object ); - - pair->input = true; - g_value_init( &pair->value, type ); - g_value_set_object( &pair->value, object ); - options.push_back( pair ); - - return( this ); -} - -// input int array -VOption * -VOption::set( const char *name, std::vector value ) -{ - Pair *pair = new Pair( name ); - - int *array; - - pair->input = true; - - g_value_init( &pair->value, VIPS_TYPE_ARRAY_INT ); - vips_value_set_array_int( &pair->value, NULL, - static_cast< int >( value.size() ) ); - array = vips_value_get_array_int( &pair->value, NULL ); - - for( std::vector::size_type i = 0; i < value.size(); i++ ) - array[i] = value[i]; - - options.push_back( pair ); - - return( this ); -} - -// input double array -VOption * -VOption::set( const char *name, std::vector value ) -{ - Pair *pair = new Pair( name ); - - double *array; - - pair->input = true; - - g_value_init( &pair->value, VIPS_TYPE_ARRAY_DOUBLE ); - vips_value_set_array_double( &pair->value, NULL, - static_cast< int >( value.size() ) ); - array = vips_value_get_array_double( &pair->value, NULL ); - - for( std::vector::size_type i = 0; i < value.size(); i++ ) - array[i] = value[i]; - - options.push_back( pair ); - - return( this ); -} - -// input image array -VOption * -VOption::set( const char *name, std::vector value ) -{ - Pair *pair = new Pair( name ); - - VipsImage **array; - - pair->input = true; - - g_value_init( &pair->value, VIPS_TYPE_ARRAY_IMAGE ); - vips_value_set_array_image( &pair->value, - static_cast< int >( value.size() ) ); - array = vips_value_get_array_image( &pair->value, NULL ); - - for( std::vector::size_type i = 0; i < value.size(); i++ ) { - VipsImage *vips_image = value[i].get_image(); - - array[i] = vips_image; - g_object_ref( vips_image ); - } - - options.push_back( pair ); - - return( this ); -} - -// input blob -VOption * -VOption::set( const char *name, VipsBlob *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = true; - g_value_init( &pair->value, VIPS_TYPE_BLOB ); - g_value_set_boxed( &pair->value, value ); - options.push_back( pair ); - - return( this ); -} - -// output bool -VOption * -VOption::set( const char *name, bool *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = false; - pair->vbool = value; - g_value_init( &pair->value, G_TYPE_BOOLEAN ); - - options.push_back( pair ); - - return( this ); -} - -// output int -VOption * -VOption::set( const char *name, int *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = false; - pair->vint = value; - g_value_init( &pair->value, G_TYPE_INT ); - - options.push_back( pair ); - - return( this ); -} - -// output double -VOption * -VOption::set( const char *name, double *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = false; - pair->vdouble = value; - g_value_init( &pair->value, G_TYPE_DOUBLE ); - - options.push_back( pair ); - - return( this ); -} - -// output image -VOption * -VOption::set( const char *name, VImage *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = false; - pair->vimage = value; - g_value_init( &pair->value, VIPS_TYPE_IMAGE ); - - options.push_back( pair ); - - return( this ); -} - -// output doublearray -VOption * -VOption::set( const char *name, std::vector *value ) -{ - Pair *pair = new Pair( name ); - - pair->input = false; - pair->vvector = value; - g_value_init( &pair->value, VIPS_TYPE_ARRAY_DOUBLE ); - - options.push_back( pair ); - - return( this ); -} - -// output blob -VOption * -VOption::set( const char *name, VipsBlob **value ) -{ - Pair *pair = new Pair( name ); - - pair->input = false; - pair->vblob = value; - g_value_init( &pair->value, VIPS_TYPE_BLOB ); - - options.push_back( pair ); - - return( this ); -} - -// just g_object_set_property(), except we allow set enum from string -static void -set_property( VipsObject *object, const char *name, const GValue *value ) -{ - VipsObjectClass *object_class = VIPS_OBJECT_GET_CLASS( object ); - GType type = G_VALUE_TYPE( value ); - - GParamSpec *pspec; - VipsArgumentClass *argument_class; - VipsArgumentInstance *argument_instance; - - if( vips_object_get_argument( object, name, - &pspec, &argument_class, &argument_instance ) ) { - g_warning( "%s", vips_error_buffer() ); - vips_error_clear(); - return; - } - - if( G_IS_PARAM_SPEC_ENUM( pspec ) && - type == G_TYPE_STRING ) { - GType pspec_type = G_PARAM_SPEC_VALUE_TYPE( pspec ); - - int enum_value; - GValue value2 = { 0 }; - - if( (enum_value = vips_enum_from_nick( object_class->nickname, - pspec_type, g_value_get_string( value ) )) < 0 ) { - g_warning( "%s", vips_error_buffer() ); - vips_error_clear(); - return; - } - - g_value_init( &value2, pspec_type ); - g_value_set_enum( &value2, enum_value ); - g_object_set_property( G_OBJECT( object ), name, &value2 ); - g_value_unset( &value2 ); - } - else - g_object_set_property( G_OBJECT( object ), name, value ); -} - -// walk the options and set props on the operation -void -VOption::set_operation( VipsOperation *operation ) -{ - std::list::iterator i; - - for( i = options.begin(); i != options.end(); ++i ) - if( (*i)->input ) { -#ifdef VIPS_DEBUG_VERBOSE - printf( "set_operation: " ); - vips_object_print_name( VIPS_OBJECT( operation ) ); - char *str_value = - g_strdup_value_contents( &(*i)->value ); - printf( ".%s = %s\n", (*i)->name, str_value ); - g_free( str_value ); -#endif /*VIPS_DEBUG_VERBOSE*/ - - set_property( VIPS_OBJECT( operation ), - (*i)->name, &(*i)->value ); - } -} - -// walk the options and fetch any requested outputs -void -VOption::get_operation( VipsOperation *operation ) -{ - std::list::iterator i; - - for( i = options.begin(); i != options.end(); ++i ) - if( ! (*i)->input ) { - const char *name = (*i)->name; - - g_object_get_property( G_OBJECT( operation ), - name, &(*i)->value ); - -#ifdef VIPS_DEBUG_VERBOSE - printf( "get_operation: " ); - vips_object_print_name( VIPS_OBJECT( operation ) ); - char *str_value = g_strdup_value_contents( - &(*i)->value ); - printf( ".%s = %s\n", name, str_value ); - g_free( str_value ); -#endif /*VIPS_DEBUG_VERBOSE*/ - - GValue *value = &(*i)->value; - GType type = G_VALUE_TYPE( value ); - - if( type == VIPS_TYPE_IMAGE ) { - // rebox object - VipsImage *image = VIPS_IMAGE( - g_value_get_object( value ) ); - *((*i)->vimage) = VImage( image ); - } - else if( type == G_TYPE_INT ) - *((*i)->vint) = g_value_get_int( value ); - else if( type == G_TYPE_BOOLEAN ) - *((*i)->vbool) = g_value_get_boolean( value ); - else if( type == G_TYPE_DOUBLE ) - *((*i)->vdouble) = g_value_get_double( value ); - else if( type == VIPS_TYPE_ARRAY_DOUBLE ) { - int length; - double *array = - vips_value_get_array_double( value, - &length ); - - ((*i)->vvector)->resize( length ); - for( int j = 0; j < length; j++ ) - (*((*i)->vvector))[j] = array[j]; - } - else if( type == VIPS_TYPE_BLOB ) { - // our caller gets a reference - *((*i)->vblob) = - (VipsBlob *) g_value_dup_boxed( value ); - } - } -} - -void -VImage::call_option_string( const char *operation_name, - const char *option_string, VOption *options ) -{ - VipsOperation *operation; - - VIPS_DEBUG_MSG( "call_option_string: starting for %s ...\n", - operation_name ); - - if( !(operation = vips_operation_new( operation_name )) ) { - delete options; - throw( VError() ); - } - - /* Set str options before vargs options, so the user can't - * override things we set deliberately. - */ - if( option_string && - vips_object_set_from_string( VIPS_OBJECT( operation ), - option_string ) ) { - vips_object_unref_outputs( VIPS_OBJECT( operation ) ); - g_object_unref( operation ); - delete options; - throw( VError() ); - } - - if( options ) - options->set_operation( operation ); - - /* Build from cache. - */ - if( vips_cache_operation_buildp( &operation ) ) { - vips_object_unref_outputs( VIPS_OBJECT( operation ) ); - g_object_unref( operation ); - delete options; - throw( VError() ); - } - - /* Walk args again, writing output. - */ - if( options ) - options->get_operation( operation ); - - /* We're done with options! - */ - delete options; - - /* The operation we have built should now have been reffed by - * one of its arguments or have finished its work. Either - * way, we can unref. - */ - g_object_unref( operation ); -} - -void -VImage::call( const char *operation_name, VOption *options ) -{ - call_option_string( operation_name, NULL, options ); -} - -VImage -VImage::new_from_file( const char *name, VOption *options ) -{ - char filename[VIPS_PATH_MAX]; - char option_string[VIPS_PATH_MAX]; - const char *operation_name; - - VImage out; - - vips__filename_split8( name, filename, option_string ); - if( !(operation_name = vips_foreign_find_load( filename )) ) { - delete options; - throw VError(); - } - - call_option_string( operation_name, option_string, - (options ? options : VImage::option())-> - set( "filename", filename )-> - set( "out", &out ) ); - - return( out ); -} - -VImage -VImage::new_from_buffer( const void *buf, size_t len, const char *option_string, - VOption *options ) -{ - const char *operation_name; - VipsBlob *blob; - VImage out; - - if( !(operation_name = vips_foreign_find_load_buffer( buf, len )) ) { - delete options; - throw( VError() ); - } - - /* We don't take a copy of the data or free it. - */ - blob = vips_blob_new( NULL, buf, len ); - options = (options ? options : VImage::option())-> - set( "buffer", blob )-> - set( "out", &out ); - vips_area_unref( VIPS_AREA( blob ) ); - - call_option_string( operation_name, option_string, options ); - - return( out ); -} - -VImage -VImage::new_from_buffer( const std::string &buf, const char *option_string, - VOption *options ) -{ - return( new_from_buffer( buf.c_str(), buf.size(), - option_string, options ) ); -} - -VImage -VImage::new_from_source( VSource source, const char *option_string, - VOption *options ) -{ - const char *operation_name; - VImage out; - - if( !(operation_name = vips_foreign_find_load_source( - source.get_source() )) ) { - delete options; - throw( VError() ); - } - - options = (options ? options : VImage::option())-> - set( "source", source )-> - set( "out", &out ); - - call_option_string( operation_name, option_string, options ); - - return( out ); -} - -VImage -VImage::new_from_memory_steal( void *data, size_t size, - int width, int height, int bands, VipsBandFormat format ) -{ - VipsImage *image; - - if( !(image = vips_image_new_from_memory( data, size, - width, height, bands, format )) ) - throw( VError() ); - - g_signal_connect( image, "postclose", - G_CALLBACK( vips_image_free_buffer ), data); - - return( VImage( image ) ); -} - -VImage -VImage::new_matrix( int width, int height ) -{ - return( VImage( vips_image_new_matrix( width, height ) ) ); -} - -VImage -VImage::new_matrixv( int width, int height, ... ) -{ - VImage matrix = new_matrix( width, height ); - VipsImage *vips_matrix = matrix.get_image(); - - va_list ap; - - va_start( ap, height ); - for( int y = 0; y < height; y++ ) - for( int x = 0; x < width; x++ ) - *VIPS_MATRIX( vips_matrix, x, y ) = - va_arg( ap, double ); - va_end( ap ); - - return( matrix ); -} - -VImage -VImage::write( VImage out ) const -{ - if( vips_image_write( this->get_image(), out.get_image() ) ) - throw VError(); - - return( out ); -} - -void -VImage::write_to_file( const char *name, VOption *options ) const -{ - char filename[VIPS_PATH_MAX]; - char option_string[VIPS_PATH_MAX]; - const char *operation_name; - - vips__filename_split8( name, filename, option_string ); - if( !(operation_name = vips_foreign_find_save( filename )) ) { - delete options; - throw VError(); - } - - call_option_string( operation_name, option_string, - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -void -VImage::write_to_buffer( const char *suffix, void **buf, size_t *size, - VOption *options ) const -{ - char filename[VIPS_PATH_MAX]; - char option_string[VIPS_PATH_MAX]; - const char *operation_name; - VipsBlob *blob; - - /* Save with the new target API if we can. Fall back to the older - * mechanism in case the saver we need has not been converted yet. - * - * We need to hide any errors from this first phase. - */ - vips__filename_split8( suffix, filename, option_string ); - - vips_error_freeze(); - operation_name = vips_foreign_find_save_target( filename ); - vips_error_thaw(); - - if( operation_name ) { - VTarget target = VTarget::new_to_memory(); - - call_option_string( operation_name, option_string, - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); - - g_object_get( target.get_target(), "blob", &blob, (void *) NULL ); - } - else if( (operation_name = vips_foreign_find_save_buffer( filename )) ) { - call_option_string( operation_name, option_string, - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &blob ) ); - } - else { - delete options; - throw VError(); - } - - if( blob ) { - if( buf ) { - *buf = VIPS_AREA( blob )->data; - VIPS_AREA( blob )->free_fn = NULL; - } - if( size ) - *size = VIPS_AREA( blob )->length; - - vips_area_unref( VIPS_AREA( blob ) ); - } -} - -void -VImage::write_to_target( const char *suffix, VTarget target, - VOption *options ) const -{ - char filename[VIPS_PATH_MAX]; - char option_string[VIPS_PATH_MAX]; - const char *operation_name; - - vips__filename_split8( suffix, filename, option_string ); - if( !(operation_name = vips_foreign_find_save_target( filename )) ) { - delete options; - throw VError(); - } - - call_option_string( operation_name, option_string, - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VRegion -VImage::region() const -{ - return VRegion::new_from_image( *this ); -} - -VRegion -VImage::region( VipsRect *rect ) const -{ - VRegion region = VRegion::new_from_image( *this ); - - region.prepare( rect ); - - return region; -} - -VRegion -VImage::region( int left, int top, int width, int height ) const -{ - VRegion region = VRegion::new_from_image( *this ); - - region.prepare( left, top, width, height ); - - return region; -} - -#include "vips-operators.cpp" - -std::vector -VImage::bandsplit( VOption *options ) const -{ - std::vector b; - b.reserve(bands()); - - for( int i = 0; i < bands(); i++ ) - b.push_back( extract_band( i ) ); - - return( b ); -} - -VImage -VImage::bandjoin( VImage other, VOption *options ) const -{ - VImage v[2] = { *this, other }; - std::vector vec( v, v + VIPS_NUMBER( v ) ); - - return( bandjoin( vec, options ) ); -} - -VImage -VImage::composite( VImage other, VipsBlendMode mode, VOption *options ) const -{ - VImage v[2] = { *this, other }; - std::vector ivec( v, v + VIPS_NUMBER( v ) ); - int m[1] = { static_cast( mode ) }; - std::vector mvec( m, m + VIPS_NUMBER( m ) ); - - return( composite( ivec, mvec, options ) ); -} - -std::complex -VImage::minpos( VOption *options ) const -{ - double x, y; - - (void) min( - (options ? options : VImage::option()) -> - set( "x", &x ) -> - set( "y", &y ) ); - - return( std::complex( x, y ) ); -} - -std::complex -VImage::maxpos( VOption *options ) const -{ - double x, y; - - (void) max( - (options ? options : VImage::option()) -> - set( "x", &x ) -> - set( "y", &y ) ); - - return( std::complex( x, y ) ); -} - -// Operator overloads - -VImage -VImage::operator[]( int index ) const -{ - return( this->extract_band( index ) ); -} - -std::vector -VImage::operator()( int x, int y ) const -{ - return( this->getpoint( x, y ) ); -} - -VImage -operator+( const VImage a, const VImage b ) -{ - return( a.add( b ) ); -} - -VImage -operator+( double a, const VImage b ) -{ - return( b.linear( 1.0, a ) ); -} - -VImage -operator+( const VImage a, double b ) -{ - return( a.linear( 1.0, b ) ); -} - -VImage -operator+( const std::vector a, const VImage b ) -{ - return( b.linear( 1.0, a ) ); -} - -VImage -operator+( const VImage a, const std::vector b ) -{ - return( a.linear( 1.0, b ) ); -} - -VImage & -operator+=( VImage &a, const VImage b ) -{ - return( a = a + b ); -} - -VImage & -operator+=( VImage &a, const double b ) -{ - return( a = a + b ); -} - -VImage & -operator+=( VImage &a, const std::vector b ) -{ - return( a = a + b ); -} - -VImage -operator-( const VImage a, const VImage b ) -{ - return( a.subtract( b ) ); -} - -VImage -operator-( double a, const VImage b ) -{ - return( b.linear( -1.0, a ) ); -} - -VImage -operator-( const VImage a, double b ) -{ - return( a.linear( 1.0, -b ) ); -} - -VImage -operator-( const std::vector a, const VImage b ) -{ - return( b.linear( -1.0, a ) ); -} - -VImage -operator-( const VImage a, const std::vector b ) -{ - return( a.linear( 1.0, vips::negate( b ) ) ); -} - -VImage & -operator-=( VImage &a, const VImage b ) -{ - return( a = a - b ); -} - -VImage & -operator-=( VImage &a, const double b ) -{ - return( a = a - b ); -} - -VImage & -operator-=( VImage &a, const std::vector b ) -{ - return( a = a - b ); -} - -VImage -operator-( const VImage a ) -{ - return( a * -1 ); -} - -VImage -operator*( const VImage a, const VImage b ) -{ - return( a.multiply( b ) ); -} - -VImage -operator*( double a, const VImage b ) -{ - return( b.linear( a, 0.0 ) ); -} - -VImage -operator*( const VImage a, double b ) -{ - return( a.linear( b, 0.0 ) ); -} - -VImage -operator*( const std::vector a, const VImage b ) -{ - return( b.linear( a, 0.0 ) ); -} - -VImage -operator*( const VImage a, const std::vector b ) -{ - return( a.linear( b, 0.0 ) ); -} - -VImage & -operator*=( VImage &a, const VImage b ) -{ - return( a = a * b ); -} - -VImage & -operator*=( VImage &a, const double b ) -{ - return( a = a * b ); -} - -VImage & -operator*=( VImage &a, const std::vector b ) -{ - return( a = a * b ); -} - -VImage -operator/( const VImage a, const VImage b ) -{ - return( a.divide( b ) ); -} - -VImage -operator/( double a, const VImage b ) -{ - return( b.pow( -1.0 ).linear( a, 0.0 ) ); -} - -VImage -operator/( const VImage a, double b ) -{ - return( a.linear( 1.0 / b, 0.0 ) ); -} - -VImage -operator/( const std::vector a, const VImage b ) -{ - return( b.pow( -1.0 ).linear( a, 0.0 ) ); -} - -VImage -operator/( const VImage a, const std::vector b ) -{ - return( a.linear( vips::invert( b ), 0.0 ) ); -} - -VImage & -operator/=( VImage &a, const VImage b ) -{ - return( a = a / b ); -} - -VImage & -operator/=( VImage &a, const double b ) -{ - return( a = a / b ); -} - -VImage & -operator/=( VImage &a, const std::vector b ) -{ - return( a = a / b ); -} - -VImage -operator%( const VImage a, const VImage b ) -{ - return( a.remainder( b ) ); -} - -VImage -operator%( const VImage a, const double b ) -{ - return( a.remainder_const( to_vector( b ) ) ); -} - -VImage -operator%( const VImage a, const std::vector b ) -{ - return( a.remainder_const( b ) ); -} - -VImage & -operator%=( VImage &a, const VImage b ) -{ - return( a = a % b ); -} - -VImage & -operator%=( VImage &a, const double b ) -{ - return( a = a % b ); -} - -VImage & -operator%=( VImage &a, const std::vector b ) -{ - return( a = a % b ); -} - -VImage -operator<( const VImage a, const VImage b ) -{ - return( a.relational( b, VIPS_OPERATION_RELATIONAL_LESS ) ); -} - -VImage -operator<( const double a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_MORE, - to_vector( a ) ) ); -} - -VImage -operator<( const VImage a, const double b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_LESS, - to_vector( b ) ) ); -} - -VImage -operator<( const std::vector a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_MORE, - a ) ); -} - -VImage -operator<( const VImage a, const std::vector b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_LESS, - b ) ); -} - -VImage -operator<=( const VImage a, const VImage b ) -{ - return( a.relational( b, VIPS_OPERATION_RELATIONAL_LESSEQ ) ); -} - -VImage -operator<=( const double a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_MOREEQ, - to_vector( a ) ) ); -} - -VImage -operator<=( const VImage a, const double b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_LESSEQ, - to_vector( b ) ) ); -} - -VImage -operator<=( const std::vector a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_MOREEQ, - a ) ); -} - -VImage -operator<=( const VImage a, const std::vector b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_LESSEQ, - b ) ); -} - -VImage -operator>( const VImage a, const VImage b ) -{ - return( a.relational( b, VIPS_OPERATION_RELATIONAL_MORE ) ); -} - -VImage -operator>( const double a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_LESS, - to_vector( a ) ) ); -} - -VImage -operator>( const VImage a, const double b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_MORE, - to_vector( b ) ) ); -} - -VImage -operator>( const std::vector a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_LESS, - a ) ); -} - -VImage -operator>( const VImage a, const std::vector b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_MORE, - b ) ); -} - -VImage -operator>=( const VImage a, const VImage b ) -{ - return( a.relational( b, VIPS_OPERATION_RELATIONAL_MOREEQ ) ); -} - -VImage -operator>=( const double a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_LESSEQ, - to_vector( a ) ) ); -} - -VImage -operator>=( const VImage a, const double b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_MOREEQ, - to_vector( b ) ) ); -} - -VImage -operator>=( const std::vector a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_LESSEQ, - a ) ); -} - -VImage -operator>=( const VImage a, const std::vector b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_MOREEQ, - b ) ); -} - -VImage -operator==( const VImage a, const VImage b ) -{ - return( a.relational( b, VIPS_OPERATION_RELATIONAL_EQUAL ) ); -} - -VImage -operator==( const double a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_EQUAL, - to_vector( a ) ) ); -} - -VImage -operator==( const VImage a, const double b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_EQUAL, - to_vector( b ) ) ); -} - -VImage -operator==( const std::vector a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_EQUAL, - a ) ); -} - -VImage -operator==( const VImage a, const std::vector b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_EQUAL, - b ) ); -} - -VImage -operator!=( const VImage a, const VImage b ) -{ - return( a.relational( b, VIPS_OPERATION_RELATIONAL_NOTEQ ) ); -} - -VImage -operator!=( const double a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_NOTEQ, - to_vector( a ) ) ); -} - -VImage -operator!=( const VImage a, const double b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_NOTEQ, - to_vector( b ) ) ); -} - -VImage -operator!=( const std::vector a, const VImage b ) -{ - return( b.relational_const( VIPS_OPERATION_RELATIONAL_NOTEQ, - a ) ); -} - -VImage -operator!=( const VImage a, const std::vector b ) -{ - return( a.relational_const( VIPS_OPERATION_RELATIONAL_NOTEQ, - b ) ); -} - -VImage -operator&( const VImage a, const VImage b ) -{ - return( a.boolean( b, VIPS_OPERATION_BOOLEAN_AND ) ); -} - -VImage -operator&( const double a, const VImage b ) -{ - return( b.boolean_const( VIPS_OPERATION_BOOLEAN_AND, - to_vector( a ) ) ); -} - -VImage -operator&( const VImage a, const double b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_AND, - to_vector( b ) ) ); -} - -VImage -operator&( const std::vector a, const VImage b ) -{ - return( b.boolean_const( VIPS_OPERATION_BOOLEAN_AND, a ) ); -} - -VImage -operator&( const VImage a, const std::vector b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_AND, b ) ); -} - -VImage & -operator&=( VImage &a, const VImage b ) -{ - return( a = a & b ); -} - -VImage & -operator&=( VImage &a, const double b ) -{ - return( a = a & b ); -} - -VImage & -operator&=( VImage &a, const std::vector b ) -{ - return( a = a & b ); -} - -VImage -operator|( const VImage a, const VImage b ) -{ - return( a.boolean( b, VIPS_OPERATION_BOOLEAN_OR ) ); -} - -VImage -operator|( const double a, const VImage b ) -{ - return( b.boolean_const( VIPS_OPERATION_BOOLEAN_OR, - to_vector( a ) ) ); -} - -VImage -operator|( const VImage a, const double b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_OR, - to_vector( b ) ) ); -} - -VImage -operator|( const std::vector a, const VImage b ) -{ - return( b.boolean_const( VIPS_OPERATION_BOOLEAN_OR, - a ) ); -} - -VImage -operator|( const VImage a, const std::vector b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_OR, - b ) ); -} - -VImage & -operator|=( VImage &a, const VImage b ) -{ - return( a = a | b ); -} - -VImage & -operator|=( VImage &a, const double b ) -{ - return( a = a | b ); -} - -VImage & -operator|=( VImage &a, const std::vector b ) -{ - return( a = a | b ); -} - -VImage -operator^( const VImage a, const VImage b ) -{ - return( a.boolean( b, VIPS_OPERATION_BOOLEAN_EOR ) ); -} - -VImage -operator^( const double a, const VImage b ) -{ - return( b.boolean_const( VIPS_OPERATION_BOOLEAN_EOR, - to_vector( a ) ) ); -} - -VImage -operator^( const VImage a, const double b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_EOR, - to_vector( b ) ) ); -} - -VImage -operator^( const std::vector a, const VImage b ) -{ - return( b.boolean_const( VIPS_OPERATION_BOOLEAN_EOR, - a ) ); -} - -VImage -operator^( const VImage a, const std::vector b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_EOR, - b ) ); -} - -VImage & -operator^=( VImage &a, const VImage b ) -{ - return( a = a ^ b ); -} - -VImage & -operator^=( VImage &a, const double b ) -{ - return( a = a ^ b ); -} - -VImage & -operator^=( VImage &a, const std::vector b ) -{ - return( a = a ^ b ); -} - -VImage -operator<<( const VImage a, const VImage b ) -{ - return( a.boolean( b, VIPS_OPERATION_BOOLEAN_LSHIFT ) ); -} - -VImage -operator<<( const VImage a, const double b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_LSHIFT, - to_vector( b ) ) ); -} - -VImage -operator<<( const VImage a, const std::vector b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_LSHIFT, - b ) ); -} - -VImage & -operator<<=( VImage &a, const VImage b ) -{ - return( a = a << b ); -} - -VImage & -operator<<=( VImage &a, const double b ) -{ - return( a = a << b ); -} - -VImage & -operator<<=( VImage &a, const std::vector b ) -{ - return( a = a << b ); -} - -VImage -operator>>( const VImage a, const VImage b ) -{ - return( a.boolean( b, VIPS_OPERATION_BOOLEAN_RSHIFT ) ); -} - -VImage -operator>>( const VImage a, const double b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_RSHIFT, - to_vector( b ) ) ); -} - -VImage -operator>>( const VImage a, const std::vector b ) -{ - return( a.boolean_const( VIPS_OPERATION_BOOLEAN_RSHIFT, - b ) ); -} - -VImage & -operator>>=( VImage &a, const VImage b ) -{ - return( a = a << b ); -} - -VImage & -operator>>=( VImage &a, const double b ) -{ - return( a = a << b ); -} - -VImage & -operator>>=( VImage &a, const std::vector b ) -{ - return( a = a << b ); -} - -VIPS_NAMESPACE_END diff --git a/src/libvips/cplusplus/VInterpolate.cpp b/src/libvips/cplusplus/VInterpolate.cpp deleted file mode 100644 index ed1e2bd90..000000000 --- a/src/libvips/cplusplus/VInterpolate.cpp +++ /dev/null @@ -1,62 +0,0 @@ -/* Object part of VInterpolate class - */ - -/* - - Copyright (C) 1991-2001 The National Gallery - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation; either version 2 of the License, 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 Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser 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 - - */ - -/* - - These files are distributed with VIPS - http://www.vips.ecs.soton.ac.uk - - */ - -#ifdef HAVE_CONFIG_H -#include -#endif /*HAVE_CONFIG_H*/ - -#include - -#include - -/* -#define VIPS_DEBUG -#define VIPS_DEBUG_VERBOSE - */ - -VIPS_NAMESPACE_START - -VInterpolate -VInterpolate::new_from_name( const char *name, VOption *options ) -{ - VipsInterpolate *interp; - - if( !(interp = vips_interpolate_new( name )) ) { - delete options; - throw VError(); - } - delete options; - - VInterpolate out( interp ); - - return( out ); -} - -VIPS_NAMESPACE_END diff --git a/src/libvips/cplusplus/VRegion.cpp b/src/libvips/cplusplus/VRegion.cpp deleted file mode 100644 index 4a0428218..000000000 --- a/src/libvips/cplusplus/VRegion.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Object part of VRegion class - -#ifdef HAVE_CONFIG_H -#include -#endif /*HAVE_CONFIG_H*/ - -#include - -#include - -VIPS_NAMESPACE_START - -VRegion -VRegion::new_from_image( VImage image ) -{ - VipsRegion *region; - - if( !(region = vips_region_new( image.get_image() )) ) { - throw VError(); - } - - VRegion out( region ); - - return( out ); -} - -VIPS_NAMESPACE_END diff --git a/src/libvips/cplusplus/vips-operators.cpp b/src/libvips/cplusplus/vips-operators.cpp deleted file mode 100644 index 56d468812..000000000 --- a/src/libvips/cplusplus/vips-operators.cpp +++ /dev/null @@ -1,3760 +0,0 @@ -// bodies for vips operations -// this file is generated automatically, do not edit! - -VImage VImage::CMC2LCh( VOption *options ) const -{ - VImage out; - - call( "CMC2LCh", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::CMYK2XYZ( VOption *options ) const -{ - VImage out; - - call( "CMYK2XYZ", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::HSV2sRGB( VOption *options ) const -{ - VImage out; - - call( "HSV2sRGB", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LCh2CMC( VOption *options ) const -{ - VImage out; - - call( "LCh2CMC", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LCh2Lab( VOption *options ) const -{ - VImage out; - - call( "LCh2Lab", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::Lab2LCh( VOption *options ) const -{ - VImage out; - - call( "Lab2LCh", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::Lab2LabQ( VOption *options ) const -{ - VImage out; - - call( "Lab2LabQ", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::Lab2LabS( VOption *options ) const -{ - VImage out; - - call( "Lab2LabS", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::Lab2XYZ( VOption *options ) const -{ - VImage out; - - call( "Lab2XYZ", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LabQ2Lab( VOption *options ) const -{ - VImage out; - - call( "LabQ2Lab", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LabQ2LabS( VOption *options ) const -{ - VImage out; - - call( "LabQ2LabS", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LabQ2sRGB( VOption *options ) const -{ - VImage out; - - call( "LabQ2sRGB", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LabS2Lab( VOption *options ) const -{ - VImage out; - - call( "LabS2Lab", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::LabS2LabQ( VOption *options ) const -{ - VImage out; - - call( "LabS2LabQ", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::XYZ2CMYK( VOption *options ) const -{ - VImage out; - - call( "XYZ2CMYK", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::XYZ2Lab( VOption *options ) const -{ - VImage out; - - call( "XYZ2Lab", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::XYZ2Yxy( VOption *options ) const -{ - VImage out; - - call( "XYZ2Yxy", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::XYZ2scRGB( VOption *options ) const -{ - VImage out; - - call( "XYZ2scRGB", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::Yxy2XYZ( VOption *options ) const -{ - VImage out; - - call( "Yxy2XYZ", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::abs( VOption *options ) const -{ - VImage out; - - call( "abs", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::add( VImage right, VOption *options ) const -{ - VImage out; - - call( "add", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::affine( std::vector matrix, VOption *options ) const -{ - VImage out; - - call( "affine", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "matrix", matrix ) ); - - return( out ); -} - -VImage VImage::analyzeload( const char *filename, VOption *options ) -{ - VImage out; - - call( "analyzeload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::arrayjoin( std::vector in, VOption *options ) -{ - VImage out; - - call( "arrayjoin", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "in", in ) ); - - return( out ); -} - -VImage VImage::autorot( VOption *options ) const -{ - VImage out; - - call( "autorot", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -double VImage::avg( VOption *options ) const -{ - double out; - - call( "avg", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::bandbool( VipsOperationBoolean boolean, VOption *options ) const -{ - VImage out; - - call( "bandbool", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "boolean", boolean ) ); - - return( out ); -} - -VImage VImage::bandfold( VOption *options ) const -{ - VImage out; - - call( "bandfold", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::bandjoin( std::vector in, VOption *options ) -{ - VImage out; - - call( "bandjoin", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "in", in ) ); - - return( out ); -} - -VImage VImage::bandjoin_const( std::vector c, VOption *options ) const -{ - VImage out; - - call( "bandjoin_const", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "c", c ) ); - - return( out ); -} - -VImage VImage::bandmean( VOption *options ) const -{ - VImage out; - - call( "bandmean", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::bandrank( std::vector in, VOption *options ) -{ - VImage out; - - call( "bandrank", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "in", in ) ); - - return( out ); -} - -VImage VImage::bandunfold( VOption *options ) const -{ - VImage out; - - call( "bandunfold", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::black( int width, int height, VOption *options ) -{ - VImage out; - - call( "black", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::boolean( VImage right, VipsOperationBoolean boolean, VOption *options ) const -{ - VImage out; - - call( "boolean", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right )-> - set( "boolean", boolean ) ); - - return( out ); -} - -VImage VImage::boolean_const( VipsOperationBoolean boolean, std::vector c, VOption *options ) const -{ - VImage out; - - call( "boolean_const", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "boolean", boolean )-> - set( "c", c ) ); - - return( out ); -} - -VImage VImage::buildlut( VOption *options ) const -{ - VImage out; - - call( "buildlut", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::byteswap( VOption *options ) const -{ - VImage out; - - call( "byteswap", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::cache( VOption *options ) const -{ - VImage out; - - call( "cache", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::canny( VOption *options ) const -{ - VImage out; - - call( "canny", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::case_image( std::vector cases, VOption *options ) const -{ - VImage out; - - call( "case", - (options ? options : VImage::option())-> - set( "index", *this )-> - set( "out", &out )-> - set( "cases", cases ) ); - - return( out ); -} - -VImage VImage::cast( VipsBandFormat format, VOption *options ) const -{ - VImage out; - - call( "cast", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "format", format ) ); - - return( out ); -} - -VImage VImage::colourspace( VipsInterpretation space, VOption *options ) const -{ - VImage out; - - call( "colourspace", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "space", space ) ); - - return( out ); -} - -VImage VImage::compass( VImage mask, VOption *options ) const -{ - VImage out; - - call( "compass", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::complex( VipsOperationComplex cmplx, VOption *options ) const -{ - VImage out; - - call( "complex", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "cmplx", cmplx ) ); - - return( out ); -} - -VImage VImage::complex2( VImage right, VipsOperationComplex2 cmplx, VOption *options ) const -{ - VImage out; - - call( "complex2", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right )-> - set( "cmplx", cmplx ) ); - - return( out ); -} - -VImage VImage::complexform( VImage right, VOption *options ) const -{ - VImage out; - - call( "complexform", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::complexget( VipsOperationComplexget get, VOption *options ) const -{ - VImage out; - - call( "complexget", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "get", get ) ); - - return( out ); -} - -VImage VImage::composite( std::vector in, std::vector mode, VOption *options ) -{ - VImage out; - - call( "composite", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "in", in )-> - set( "mode", mode ) ); - - return( out ); -} - -VImage VImage::composite2( VImage overlay, VipsBlendMode mode, VOption *options ) const -{ - VImage out; - - call( "composite2", - (options ? options : VImage::option())-> - set( "base", *this )-> - set( "out", &out )-> - set( "overlay", overlay )-> - set( "mode", mode ) ); - - return( out ); -} - -VImage VImage::conv( VImage mask, VOption *options ) const -{ - VImage out; - - call( "conv", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::conva( VImage mask, VOption *options ) const -{ - VImage out; - - call( "conva", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::convasep( VImage mask, VOption *options ) const -{ - VImage out; - - call( "convasep", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::convf( VImage mask, VOption *options ) const -{ - VImage out; - - call( "convf", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::convi( VImage mask, VOption *options ) const -{ - VImage out; - - call( "convi", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::convsep( VImage mask, VOption *options ) const -{ - VImage out; - - call( "convsep", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::copy( VOption *options ) const -{ - VImage out; - - call( "copy", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -double VImage::countlines( VipsDirection direction, VOption *options ) const -{ - double nolines; - - call( "countlines", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "nolines", &nolines )-> - set( "direction", direction ) ); - - return( nolines ); -} - -VImage VImage::crop( int left, int top, int width, int height, VOption *options ) const -{ - VImage out; - - call( "crop", - (options ? options : VImage::option())-> - set( "input", *this )-> - set( "out", &out )-> - set( "left", left )-> - set( "top", top )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::csvload( const char *filename, VOption *options ) -{ - VImage out; - - call( "csvload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::csvload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "csvload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::csvsave( const char *filename, VOption *options ) const -{ - call( "csvsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -void VImage::csvsave_target( VTarget target, VOption *options ) const -{ - call( "csvsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::dE00( VImage right, VOption *options ) const -{ - VImage out; - - call( "dE00", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::dE76( VImage right, VOption *options ) const -{ - VImage out; - - call( "dE76", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::dECMC( VImage right, VOption *options ) const -{ - VImage out; - - call( "dECMC", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -double VImage::deviate( VOption *options ) const -{ - double out; - - call( "deviate", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::divide( VImage right, VOption *options ) const -{ - VImage out; - - call( "divide", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -void VImage::draw_circle( std::vector ink, int cx, int cy, int radius, VOption *options ) const -{ - call( "draw_circle", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "ink", ink )-> - set( "cx", cx )-> - set( "cy", cy )-> - set( "radius", radius ) ); -} - -void VImage::draw_flood( std::vector ink, int x, int y, VOption *options ) const -{ - call( "draw_flood", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "ink", ink )-> - set( "x", x )-> - set( "y", y ) ); -} - -void VImage::draw_image( VImage sub, int x, int y, VOption *options ) const -{ - call( "draw_image", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "sub", sub )-> - set( "x", x )-> - set( "y", y ) ); -} - -void VImage::draw_line( std::vector ink, int x1, int y1, int x2, int y2, VOption *options ) const -{ - call( "draw_line", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "ink", ink )-> - set( "x1", x1 )-> - set( "y1", y1 )-> - set( "x2", x2 )-> - set( "y2", y2 ) ); -} - -void VImage::draw_mask( std::vector ink, VImage mask, int x, int y, VOption *options ) const -{ - call( "draw_mask", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "ink", ink )-> - set( "mask", mask )-> - set( "x", x )-> - set( "y", y ) ); -} - -void VImage::draw_rect( std::vector ink, int left, int top, int width, int height, VOption *options ) const -{ - call( "draw_rect", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "ink", ink )-> - set( "left", left )-> - set( "top", top )-> - set( "width", width )-> - set( "height", height ) ); -} - -void VImage::draw_smudge( int left, int top, int width, int height, VOption *options ) const -{ - call( "draw_smudge", - (options ? options : VImage::option())-> - set( "image", *this )-> - set( "left", left )-> - set( "top", top )-> - set( "width", width )-> - set( "height", height ) ); -} - -void VImage::dzsave( const char *filename, VOption *options ) const -{ - call( "dzsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::dzsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "dzsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::dzsave_target( VTarget target, VOption *options ) const -{ - call( "dzsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::embed( int x, int y, int width, int height, VOption *options ) const -{ - VImage out; - - call( "embed", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "x", x )-> - set( "y", y )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::extract_area( int left, int top, int width, int height, VOption *options ) const -{ - VImage out; - - call( "extract_area", - (options ? options : VImage::option())-> - set( "input", *this )-> - set( "out", &out )-> - set( "left", left )-> - set( "top", top )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::extract_band( int band, VOption *options ) const -{ - VImage out; - - call( "extract_band", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "band", band ) ); - - return( out ); -} - -VImage VImage::eye( int width, int height, VOption *options ) -{ - VImage out; - - call( "eye", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::falsecolour( VOption *options ) const -{ - VImage out; - - call( "falsecolour", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::fastcor( VImage ref, VOption *options ) const -{ - VImage out; - - call( "fastcor", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "ref", ref ) ); - - return( out ); -} - -VImage VImage::fill_nearest( VOption *options ) const -{ - VImage out; - - call( "fill_nearest", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -int VImage::find_trim( int *top, int *width, int *height, VOption *options ) const -{ - int left; - - call( "find_trim", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "left", &left )-> - set( "top", top )-> - set( "width", width )-> - set( "height", height ) ); - - return( left ); -} - -VImage VImage::fitsload( const char *filename, VOption *options ) -{ - VImage out; - - call( "fitsload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::fitsload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "fitsload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::fitssave( const char *filename, VOption *options ) const -{ - call( "fitssave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VImage VImage::flatten( VOption *options ) const -{ - VImage out; - - call( "flatten", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::flip( VipsDirection direction, VOption *options ) const -{ - VImage out; - - call( "flip", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "direction", direction ) ); - - return( out ); -} - -VImage VImage::float2rad( VOption *options ) const -{ - VImage out; - - call( "float2rad", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::fractsurf( int width, int height, double fractal_dimension, VOption *options ) -{ - VImage out; - - call( "fractsurf", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "fractal_dimension", fractal_dimension ) ); - - return( out ); -} - -VImage VImage::freqmult( VImage mask, VOption *options ) const -{ - VImage out; - - call( "freqmult", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask ) ); - - return( out ); -} - -VImage VImage::fwfft( VOption *options ) const -{ - VImage out; - - call( "fwfft", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::gamma( VOption *options ) const -{ - VImage out; - - call( "gamma", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::gaussblur( double sigma, VOption *options ) const -{ - VImage out; - - call( "gaussblur", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "sigma", sigma ) ); - - return( out ); -} - -VImage VImage::gaussmat( double sigma, double min_ampl, VOption *options ) -{ - VImage out; - - call( "gaussmat", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "sigma", sigma )-> - set( "min_ampl", min_ampl ) ); - - return( out ); -} - -VImage VImage::gaussnoise( int width, int height, VOption *options ) -{ - VImage out; - - call( "gaussnoise", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -std::vector VImage::getpoint( int x, int y, VOption *options ) const -{ - std::vector out_array; - - call( "getpoint", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out_array", &out_array )-> - set( "x", x )-> - set( "y", y ) ); - - return( out_array ); -} - -VImage VImage::gifload( const char *filename, VOption *options ) -{ - VImage out; - - call( "gifload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::gifload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "gifload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::gifload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "gifload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::gifsave( const char *filename, VOption *options ) const -{ - call( "gifsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::gifsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "gifsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::gifsave_target( VTarget target, VOption *options ) const -{ - call( "gifsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::globalbalance( VOption *options ) const -{ - VImage out; - - call( "globalbalance", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::gravity( VipsCompassDirection direction, int width, int height, VOption *options ) const -{ - VImage out; - - call( "gravity", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "direction", direction )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::grey( int width, int height, VOption *options ) -{ - VImage out; - - call( "grey", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::grid( int tile_height, int across, int down, VOption *options ) const -{ - VImage out; - - call( "grid", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "tile_height", tile_height )-> - set( "across", across )-> - set( "down", down ) ); - - return( out ); -} - -VImage VImage::heifload( const char *filename, VOption *options ) -{ - VImage out; - - call( "heifload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::heifload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "heifload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::heifload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "heifload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::heifsave( const char *filename, VOption *options ) const -{ - call( "heifsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::heifsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "heifsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::heifsave_target( VTarget target, VOption *options ) const -{ - call( "heifsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::hist_cum( VOption *options ) const -{ - VImage out; - - call( "hist_cum", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -double VImage::hist_entropy( VOption *options ) const -{ - double out; - - call( "hist_entropy", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::hist_equal( VOption *options ) const -{ - VImage out; - - call( "hist_equal", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::hist_find( VOption *options ) const -{ - VImage out; - - call( "hist_find", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::hist_find_indexed( VImage index, VOption *options ) const -{ - VImage out; - - call( "hist_find_indexed", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "index", index ) ); - - return( out ); -} - -VImage VImage::hist_find_ndim( VOption *options ) const -{ - VImage out; - - call( "hist_find_ndim", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -bool VImage::hist_ismonotonic( VOption *options ) const -{ - bool monotonic; - - call( "hist_ismonotonic", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "monotonic", &monotonic ) ); - - return( monotonic ); -} - -VImage VImage::hist_local( int width, int height, VOption *options ) const -{ - VImage out; - - call( "hist_local", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::hist_match( VImage ref, VOption *options ) const -{ - VImage out; - - call( "hist_match", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "ref", ref ) ); - - return( out ); -} - -VImage VImage::hist_norm( VOption *options ) const -{ - VImage out; - - call( "hist_norm", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::hist_plot( VOption *options ) const -{ - VImage out; - - call( "hist_plot", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::hough_circle( VOption *options ) const -{ - VImage out; - - call( "hough_circle", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::hough_line( VOption *options ) const -{ - VImage out; - - call( "hough_line", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::icc_export( VOption *options ) const -{ - VImage out; - - call( "icc_export", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::icc_import( VOption *options ) const -{ - VImage out; - - call( "icc_import", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::icc_transform( const char *output_profile, VOption *options ) const -{ - VImage out; - - call( "icc_transform", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "output_profile", output_profile ) ); - - return( out ); -} - -VImage VImage::identity( VOption *options ) -{ - VImage out; - - call( "identity", - (options ? options : VImage::option())-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::ifthenelse( VImage in1, VImage in2, VOption *options ) const -{ - VImage out; - - call( "ifthenelse", - (options ? options : VImage::option())-> - set( "cond", *this )-> - set( "out", &out )-> - set( "in1", in1 )-> - set( "in2", in2 ) ); - - return( out ); -} - -VImage VImage::insert( VImage sub, int x, int y, VOption *options ) const -{ - VImage out; - - call( "insert", - (options ? options : VImage::option())-> - set( "main", *this )-> - set( "out", &out )-> - set( "sub", sub )-> - set( "x", x )-> - set( "y", y ) ); - - return( out ); -} - -VImage VImage::invert( VOption *options ) const -{ - VImage out; - - call( "invert", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::invertlut( VOption *options ) const -{ - VImage out; - - call( "invertlut", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::invfft( VOption *options ) const -{ - VImage out; - - call( "invfft", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::join( VImage in2, VipsDirection direction, VOption *options ) const -{ - VImage out; - - call( "join", - (options ? options : VImage::option())-> - set( "in1", *this )-> - set( "out", &out )-> - set( "in2", in2 )-> - set( "direction", direction ) ); - - return( out ); -} - -VImage VImage::jp2kload( const char *filename, VOption *options ) -{ - VImage out; - - call( "jp2kload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::jp2kload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "jp2kload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::jp2kload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "jp2kload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::jp2ksave( const char *filename, VOption *options ) const -{ - call( "jp2ksave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::jp2ksave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "jp2ksave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::jp2ksave_target( VTarget target, VOption *options ) const -{ - call( "jp2ksave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::jpegload( const char *filename, VOption *options ) -{ - VImage out; - - call( "jpegload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::jpegload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "jpegload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::jpegload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "jpegload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::jpegsave( const char *filename, VOption *options ) const -{ - call( "jpegsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::jpegsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "jpegsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::jpegsave_mime( VOption *options ) const -{ - call( "jpegsave_mime", - (options ? options : VImage::option())-> - set( "in", *this ) ); -} - -void VImage::jpegsave_target( VTarget target, VOption *options ) const -{ - call( "jpegsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::jxlload( const char *filename, VOption *options ) -{ - VImage out; - - call( "jxlload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::jxlload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "jxlload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::jxlload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "jxlload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::jxlsave( const char *filename, VOption *options ) const -{ - call( "jxlsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::jxlsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "jxlsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::jxlsave_target( VTarget target, VOption *options ) const -{ - call( "jxlsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::labelregions( VOption *options ) const -{ - VImage mask; - - call( "labelregions", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "mask", &mask ) ); - - return( mask ); -} - -VImage VImage::linear( std::vector a, std::vector b, VOption *options ) const -{ - VImage out; - - call( "linear", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "a", a )-> - set( "b", b ) ); - - return( out ); -} - -VImage VImage::linecache( VOption *options ) const -{ - VImage out; - - call( "linecache", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::logmat( double sigma, double min_ampl, VOption *options ) -{ - VImage out; - - call( "logmat", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "sigma", sigma )-> - set( "min_ampl", min_ampl ) ); - - return( out ); -} - -VImage VImage::magickload( const char *filename, VOption *options ) -{ - VImage out; - - call( "magickload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::magickload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "magickload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -void VImage::magicksave( const char *filename, VOption *options ) const -{ - call( "magicksave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::magicksave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "magicksave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -VImage VImage::mapim( VImage index, VOption *options ) const -{ - VImage out; - - call( "mapim", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "index", index ) ); - - return( out ); -} - -VImage VImage::maplut( VImage lut, VOption *options ) const -{ - VImage out; - - call( "maplut", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "lut", lut ) ); - - return( out ); -} - -VImage VImage::mask_butterworth( int width, int height, double order, double frequency_cutoff, double amplitude_cutoff, VOption *options ) -{ - VImage out; - - call( "mask_butterworth", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "order", order )-> - set( "frequency_cutoff", frequency_cutoff )-> - set( "amplitude_cutoff", amplitude_cutoff ) ); - - return( out ); -} - -VImage VImage::mask_butterworth_band( int width, int height, double order, double frequency_cutoff_x, double frequency_cutoff_y, double radius, double amplitude_cutoff, VOption *options ) -{ - VImage out; - - call( "mask_butterworth_band", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "order", order )-> - set( "frequency_cutoff_x", frequency_cutoff_x )-> - set( "frequency_cutoff_y", frequency_cutoff_y )-> - set( "radius", radius )-> - set( "amplitude_cutoff", amplitude_cutoff ) ); - - return( out ); -} - -VImage VImage::mask_butterworth_ring( int width, int height, double order, double frequency_cutoff, double amplitude_cutoff, double ringwidth, VOption *options ) -{ - VImage out; - - call( "mask_butterworth_ring", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "order", order )-> - set( "frequency_cutoff", frequency_cutoff )-> - set( "amplitude_cutoff", amplitude_cutoff )-> - set( "ringwidth", ringwidth ) ); - - return( out ); -} - -VImage VImage::mask_fractal( int width, int height, double fractal_dimension, VOption *options ) -{ - VImage out; - - call( "mask_fractal", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "fractal_dimension", fractal_dimension ) ); - - return( out ); -} - -VImage VImage::mask_gaussian( int width, int height, double frequency_cutoff, double amplitude_cutoff, VOption *options ) -{ - VImage out; - - call( "mask_gaussian", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "frequency_cutoff", frequency_cutoff )-> - set( "amplitude_cutoff", amplitude_cutoff ) ); - - return( out ); -} - -VImage VImage::mask_gaussian_band( int width, int height, double frequency_cutoff_x, double frequency_cutoff_y, double radius, double amplitude_cutoff, VOption *options ) -{ - VImage out; - - call( "mask_gaussian_band", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "frequency_cutoff_x", frequency_cutoff_x )-> - set( "frequency_cutoff_y", frequency_cutoff_y )-> - set( "radius", radius )-> - set( "amplitude_cutoff", amplitude_cutoff ) ); - - return( out ); -} - -VImage VImage::mask_gaussian_ring( int width, int height, double frequency_cutoff, double amplitude_cutoff, double ringwidth, VOption *options ) -{ - VImage out; - - call( "mask_gaussian_ring", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "frequency_cutoff", frequency_cutoff )-> - set( "amplitude_cutoff", amplitude_cutoff )-> - set( "ringwidth", ringwidth ) ); - - return( out ); -} - -VImage VImage::mask_ideal( int width, int height, double frequency_cutoff, VOption *options ) -{ - VImage out; - - call( "mask_ideal", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "frequency_cutoff", frequency_cutoff ) ); - - return( out ); -} - -VImage VImage::mask_ideal_band( int width, int height, double frequency_cutoff_x, double frequency_cutoff_y, double radius, VOption *options ) -{ - VImage out; - - call( "mask_ideal_band", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "frequency_cutoff_x", frequency_cutoff_x )-> - set( "frequency_cutoff_y", frequency_cutoff_y )-> - set( "radius", radius ) ); - - return( out ); -} - -VImage VImage::mask_ideal_ring( int width, int height, double frequency_cutoff, double ringwidth, VOption *options ) -{ - VImage out; - - call( "mask_ideal_ring", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "frequency_cutoff", frequency_cutoff )-> - set( "ringwidth", ringwidth ) ); - - return( out ); -} - -VImage VImage::match( VImage sec, int xr1, int yr1, int xs1, int ys1, int xr2, int yr2, int xs2, int ys2, VOption *options ) const -{ - VImage out; - - call( "match", - (options ? options : VImage::option())-> - set( "ref", *this )-> - set( "out", &out )-> - set( "sec", sec )-> - set( "xr1", xr1 )-> - set( "yr1", yr1 )-> - set( "xs1", xs1 )-> - set( "ys1", ys1 )-> - set( "xr2", xr2 )-> - set( "yr2", yr2 )-> - set( "xs2", xs2 )-> - set( "ys2", ys2 ) ); - - return( out ); -} - -VImage VImage::math( VipsOperationMath math, VOption *options ) const -{ - VImage out; - - call( "math", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "math", math ) ); - - return( out ); -} - -VImage VImage::math2( VImage right, VipsOperationMath2 math2, VOption *options ) const -{ - VImage out; - - call( "math2", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right )-> - set( "math2", math2 ) ); - - return( out ); -} - -VImage VImage::math2_const( VipsOperationMath2 math2, std::vector c, VOption *options ) const -{ - VImage out; - - call( "math2_const", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "math2", math2 )-> - set( "c", c ) ); - - return( out ); -} - -VImage VImage::matload( const char *filename, VOption *options ) -{ - VImage out; - - call( "matload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::matrixinvert( VOption *options ) const -{ - VImage out; - - call( "matrixinvert", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::matrixload( const char *filename, VOption *options ) -{ - VImage out; - - call( "matrixload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::matrixload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "matrixload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::matrixprint( VOption *options ) const -{ - call( "matrixprint", - (options ? options : VImage::option())-> - set( "in", *this ) ); -} - -void VImage::matrixsave( const char *filename, VOption *options ) const -{ - call( "matrixsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -void VImage::matrixsave_target( VTarget target, VOption *options ) const -{ - call( "matrixsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -double VImage::max( VOption *options ) const -{ - double out; - - call( "max", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::measure( int h, int v, VOption *options ) const -{ - VImage out; - - call( "measure", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "h", h )-> - set( "v", v ) ); - - return( out ); -} - -VImage VImage::merge( VImage sec, VipsDirection direction, int dx, int dy, VOption *options ) const -{ - VImage out; - - call( "merge", - (options ? options : VImage::option())-> - set( "ref", *this )-> - set( "out", &out )-> - set( "sec", sec )-> - set( "direction", direction )-> - set( "dx", dx )-> - set( "dy", dy ) ); - - return( out ); -} - -double VImage::min( VOption *options ) const -{ - double out; - - call( "min", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::morph( VImage mask, VipsOperationMorphology morph, VOption *options ) const -{ - VImage out; - - call( "morph", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "mask", mask )-> - set( "morph", morph ) ); - - return( out ); -} - -VImage VImage::mosaic( VImage sec, VipsDirection direction, int xref, int yref, int xsec, int ysec, VOption *options ) const -{ - VImage out; - - call( "mosaic", - (options ? options : VImage::option())-> - set( "ref", *this )-> - set( "out", &out )-> - set( "sec", sec )-> - set( "direction", direction )-> - set( "xref", xref )-> - set( "yref", yref )-> - set( "xsec", xsec )-> - set( "ysec", ysec ) ); - - return( out ); -} - -VImage VImage::mosaic1( VImage sec, VipsDirection direction, int xr1, int yr1, int xs1, int ys1, int xr2, int yr2, int xs2, int ys2, VOption *options ) const -{ - VImage out; - - call( "mosaic1", - (options ? options : VImage::option())-> - set( "ref", *this )-> - set( "out", &out )-> - set( "sec", sec )-> - set( "direction", direction )-> - set( "xr1", xr1 )-> - set( "yr1", yr1 )-> - set( "xs1", xs1 )-> - set( "ys1", ys1 )-> - set( "xr2", xr2 )-> - set( "yr2", yr2 )-> - set( "xs2", xs2 )-> - set( "ys2", ys2 ) ); - - return( out ); -} - -VImage VImage::msb( VOption *options ) const -{ - VImage out; - - call( "msb", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::multiply( VImage right, VOption *options ) const -{ - VImage out; - - call( "multiply", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::niftiload( const char *filename, VOption *options ) -{ - VImage out; - - call( "niftiload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::niftiload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "niftiload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::niftisave( const char *filename, VOption *options ) const -{ - call( "niftisave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VImage VImage::openexrload( const char *filename, VOption *options ) -{ - VImage out; - - call( "openexrload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::openslideload( const char *filename, VOption *options ) -{ - VImage out; - - call( "openslideload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::openslideload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "openslideload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -VImage VImage::pdfload( const char *filename, VOption *options ) -{ - VImage out; - - call( "pdfload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::pdfload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "pdfload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::pdfload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "pdfload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -int VImage::percent( double percent, VOption *options ) const -{ - int threshold; - - call( "percent", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "threshold", &threshold )-> - set( "percent", percent ) ); - - return( threshold ); -} - -VImage VImage::perlin( int width, int height, VOption *options ) -{ - VImage out; - - call( "perlin", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::phasecor( VImage in2, VOption *options ) const -{ - VImage out; - - call( "phasecor", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "in2", in2 ) ); - - return( out ); -} - -VImage VImage::pngload( const char *filename, VOption *options ) -{ - VImage out; - - call( "pngload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::pngload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "pngload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::pngload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "pngload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::pngsave( const char *filename, VOption *options ) const -{ - call( "pngsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::pngsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "pngsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::pngsave_target( VTarget target, VOption *options ) const -{ - call( "pngsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::ppmload( const char *filename, VOption *options ) -{ - VImage out; - - call( "ppmload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::ppmload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "ppmload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::ppmsave( const char *filename, VOption *options ) const -{ - call( "ppmsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -void VImage::ppmsave_target( VTarget target, VOption *options ) const -{ - call( "ppmsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::premultiply( VOption *options ) const -{ - VImage out; - - call( "premultiply", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::profile( VImage *rows, VOption *options ) const -{ - VImage columns; - - call( "profile", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "columns", &columns )-> - set( "rows", rows ) ); - - return( columns ); -} - -VipsBlob *VImage::profile_load( const char *name, VOption *options ) -{ - VipsBlob *profile; - - call( "profile_load", - (options ? options : VImage::option())-> - set( "profile", &profile )-> - set( "name", name ) ); - - return( profile ); -} - -VImage VImage::project( VImage *rows, VOption *options ) const -{ - VImage columns; - - call( "project", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "columns", &columns )-> - set( "rows", rows ) ); - - return( columns ); -} - -VImage VImage::quadratic( VImage coeff, VOption *options ) const -{ - VImage out; - - call( "quadratic", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "coeff", coeff ) ); - - return( out ); -} - -VImage VImage::rad2float( VOption *options ) const -{ - VImage out; - - call( "rad2float", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::radload( const char *filename, VOption *options ) -{ - VImage out; - - call( "radload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::radload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "radload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::radload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "radload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::radsave( const char *filename, VOption *options ) const -{ - call( "radsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::radsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "radsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::radsave_target( VTarget target, VOption *options ) const -{ - call( "radsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::rank( int width, int height, int index, VOption *options ) const -{ - VImage out; - - call( "rank", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height )-> - set( "index", index ) ); - - return( out ); -} - -VImage VImage::rawload( const char *filename, int width, int height, int bands, VOption *options ) -{ - VImage out; - - call( "rawload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename )-> - set( "width", width )-> - set( "height", height )-> - set( "bands", bands ) ); - - return( out ); -} - -void VImage::rawsave( const char *filename, VOption *options ) const -{ - call( "rawsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -void VImage::rawsave_fd( int fd, VOption *options ) const -{ - call( "rawsave_fd", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "fd", fd ) ); -} - -VImage VImage::recomb( VImage m, VOption *options ) const -{ - VImage out; - - call( "recomb", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "m", m ) ); - - return( out ); -} - -VImage VImage::reduce( double hshrink, double vshrink, VOption *options ) const -{ - VImage out; - - call( "reduce", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "hshrink", hshrink )-> - set( "vshrink", vshrink ) ); - - return( out ); -} - -VImage VImage::reduceh( double hshrink, VOption *options ) const -{ - VImage out; - - call( "reduceh", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "hshrink", hshrink ) ); - - return( out ); -} - -VImage VImage::reducev( double vshrink, VOption *options ) const -{ - VImage out; - - call( "reducev", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "vshrink", vshrink ) ); - - return( out ); -} - -VImage VImage::relational( VImage right, VipsOperationRelational relational, VOption *options ) const -{ - VImage out; - - call( "relational", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right )-> - set( "relational", relational ) ); - - return( out ); -} - -VImage VImage::relational_const( VipsOperationRelational relational, std::vector c, VOption *options ) const -{ - VImage out; - - call( "relational_const", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "relational", relational )-> - set( "c", c ) ); - - return( out ); -} - -VImage VImage::remainder( VImage right, VOption *options ) const -{ - VImage out; - - call( "remainder", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::remainder_const( std::vector c, VOption *options ) const -{ - VImage out; - - call( "remainder_const", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "c", c ) ); - - return( out ); -} - -VImage VImage::replicate( int across, int down, VOption *options ) const -{ - VImage out; - - call( "replicate", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "across", across )-> - set( "down", down ) ); - - return( out ); -} - -VImage VImage::resize( double scale, VOption *options ) const -{ - VImage out; - - call( "resize", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "scale", scale ) ); - - return( out ); -} - -VImage VImage::rot( VipsAngle angle, VOption *options ) const -{ - VImage out; - - call( "rot", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "angle", angle ) ); - - return( out ); -} - -VImage VImage::rot45( VOption *options ) const -{ - VImage out; - - call( "rot45", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::rotate( double angle, VOption *options ) const -{ - VImage out; - - call( "rotate", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "angle", angle ) ); - - return( out ); -} - -VImage VImage::round( VipsOperationRound round, VOption *options ) const -{ - VImage out; - - call( "round", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "round", round ) ); - - return( out ); -} - -VImage VImage::sRGB2HSV( VOption *options ) const -{ - VImage out; - - call( "sRGB2HSV", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::sRGB2scRGB( VOption *options ) const -{ - VImage out; - - call( "sRGB2scRGB", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::scRGB2BW( VOption *options ) const -{ - VImage out; - - call( "scRGB2BW", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::scRGB2XYZ( VOption *options ) const -{ - VImage out; - - call( "scRGB2XYZ", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::scRGB2sRGB( VOption *options ) const -{ - VImage out; - - call( "scRGB2sRGB", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::scale( VOption *options ) const -{ - VImage out; - - call( "scale", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::sequential( VOption *options ) const -{ - VImage out; - - call( "sequential", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::sharpen( VOption *options ) const -{ - VImage out; - - call( "sharpen", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::shrink( double hshrink, double vshrink, VOption *options ) const -{ - VImage out; - - call( "shrink", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "hshrink", hshrink )-> - set( "vshrink", vshrink ) ); - - return( out ); -} - -VImage VImage::shrinkh( int hshrink, VOption *options ) const -{ - VImage out; - - call( "shrinkh", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "hshrink", hshrink ) ); - - return( out ); -} - -VImage VImage::shrinkv( int vshrink, VOption *options ) const -{ - VImage out; - - call( "shrinkv", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "vshrink", vshrink ) ); - - return( out ); -} - -VImage VImage::sign( VOption *options ) const -{ - VImage out; - - call( "sign", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::similarity( VOption *options ) const -{ - VImage out; - - call( "similarity", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::sines( int width, int height, VOption *options ) -{ - VImage out; - - call( "sines", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::smartcrop( int width, int height, VOption *options ) const -{ - VImage out; - - call( "smartcrop", - (options ? options : VImage::option())-> - set( "input", *this )-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::sobel( VOption *options ) const -{ - VImage out; - - call( "sobel", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::spcor( VImage ref, VOption *options ) const -{ - VImage out; - - call( "spcor", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "ref", ref ) ); - - return( out ); -} - -VImage VImage::spectrum( VOption *options ) const -{ - VImage out; - - call( "spectrum", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::stats( VOption *options ) const -{ - VImage out; - - call( "stats", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::stdif( int width, int height, VOption *options ) const -{ - VImage out; - - call( "stdif", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::subsample( int xfac, int yfac, VOption *options ) const -{ - VImage out; - - call( "subsample", - (options ? options : VImage::option())-> - set( "input", *this )-> - set( "out", &out )-> - set( "xfac", xfac )-> - set( "yfac", yfac ) ); - - return( out ); -} - -VImage VImage::subtract( VImage right, VOption *options ) const -{ - VImage out; - - call( "subtract", - (options ? options : VImage::option())-> - set( "left", *this )-> - set( "out", &out )-> - set( "right", right ) ); - - return( out ); -} - -VImage VImage::sum( std::vector in, VOption *options ) -{ - VImage out; - - call( "sum", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "in", in ) ); - - return( out ); -} - -VImage VImage::svgload( const char *filename, VOption *options ) -{ - VImage out; - - call( "svgload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::svgload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "svgload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::svgload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "svgload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -VImage VImage::switch_image( std::vector tests, VOption *options ) -{ - VImage out; - - call( "switch", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "tests", tests ) ); - - return( out ); -} - -void VImage::system( const char *cmd_format, VOption *options ) -{ - call( "system", - (options ? options : VImage::option())-> - set( "cmd_format", cmd_format ) ); -} - -VImage VImage::text( const char *text, VOption *options ) -{ - VImage out; - - call( "text", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "text", text ) ); - - return( out ); -} - -VImage VImage::thumbnail( const char *filename, int width, VOption *options ) -{ - VImage out; - - call( "thumbnail", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename )-> - set( "width", width ) ); - - return( out ); -} - -VImage VImage::thumbnail_buffer( VipsBlob *buffer, int width, VOption *options ) -{ - VImage out; - - call( "thumbnail_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer )-> - set( "width", width ) ); - - return( out ); -} - -VImage VImage::thumbnail_image( int width, VOption *options ) const -{ - VImage out; - - call( "thumbnail_image", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out )-> - set( "width", width ) ); - - return( out ); -} - -VImage VImage::thumbnail_source( VSource source, int width, VOption *options ) -{ - VImage out; - - call( "thumbnail_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source )-> - set( "width", width ) ); - - return( out ); -} - -VImage VImage::tiffload( const char *filename, VOption *options ) -{ - VImage out; - - call( "tiffload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::tiffload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "tiffload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::tiffload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "tiffload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::tiffsave( const char *filename, VOption *options ) const -{ - call( "tiffsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::tiffsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "tiffsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::tiffsave_target( VTarget target, VOption *options ) const -{ - call( "tiffsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::tilecache( VOption *options ) const -{ - VImage out; - - call( "tilecache", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::tonelut( VOption *options ) -{ - VImage out; - - call( "tonelut", - (options ? options : VImage::option())-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::transpose3d( VOption *options ) const -{ - VImage out; - - call( "transpose3d", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::unpremultiply( VOption *options ) const -{ - VImage out; - - call( "unpremultiply", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::vipsload( const char *filename, VOption *options ) -{ - VImage out; - - call( "vipsload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::vipsload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "vipsload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::vipssave( const char *filename, VOption *options ) const -{ - call( "vipssave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -void VImage::vipssave_target( VTarget target, VOption *options ) const -{ - call( "vipssave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::webpload( const char *filename, VOption *options ) -{ - VImage out; - - call( "webpload", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "filename", filename ) ); - - return( out ); -} - -VImage VImage::webpload_buffer( VipsBlob *buffer, VOption *options ) -{ - VImage out; - - call( "webpload_buffer", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "buffer", buffer ) ); - - return( out ); -} - -VImage VImage::webpload_source( VSource source, VOption *options ) -{ - VImage out; - - call( "webpload_source", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "source", source ) ); - - return( out ); -} - -void VImage::webpsave( const char *filename, VOption *options ) const -{ - call( "webpsave", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "filename", filename ) ); -} - -VipsBlob *VImage::webpsave_buffer( VOption *options ) const -{ - VipsBlob *buffer; - - call( "webpsave_buffer", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "buffer", &buffer ) ); - - return( buffer ); -} - -void VImage::webpsave_mime( VOption *options ) const -{ - call( "webpsave_mime", - (options ? options : VImage::option())-> - set( "in", *this ) ); -} - -void VImage::webpsave_target( VTarget target, VOption *options ) const -{ - call( "webpsave_target", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "target", target ) ); -} - -VImage VImage::worley( int width, int height, VOption *options ) -{ - VImage out; - - call( "worley", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::wrap( VOption *options ) const -{ - VImage out; - - call( "wrap", - (options ? options : VImage::option())-> - set( "in", *this )-> - set( "out", &out ) ); - - return( out ); -} - -VImage VImage::xyz( int width, int height, VOption *options ) -{ - VImage out; - - call( "xyz", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::zone( int width, int height, VOption *options ) -{ - VImage out; - - call( "zone", - (options ? options : VImage::option())-> - set( "out", &out )-> - set( "width", width )-> - set( "height", height ) ); - - return( out ); -} - -VImage VImage::zoom( int xfac, int yfac, VOption *options ) const -{ - VImage out; - - call( "zoom", - (options ? options : VImage::option())-> - set( "input", *this )-> - set( "out", &out )-> - set( "xfac", xfac )-> - set( "yfac", yfac ) ); - - return( out ); -} diff --git a/test/types/sharp.test-d.ts b/test/types/sharp.test-d.ts index b1f28de8c..2500b9191 100644 --- a/test/types/sharp.test-d.ts +++ b/test/types/sharp.test-d.ts @@ -73,8 +73,6 @@ readableStream.pipe(transformer).pipe(writableStream); console.log(sharp.format); console.log(sharp.versions); -console.log(sharp.vendor.current); -console.log(sharp.vendor.installed.join(', ')); sharp.queue.on('change', (queueLength: number) => { console.log(`Queue contains ${queueLength} task(s)`); diff --git a/test/unit/agent.js b/test/unit/agent.js deleted file mode 100644 index 95d587311..000000000 --- a/test/unit/agent.js +++ /dev/null @@ -1,52 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const assert = require('assert'); -const agent = require('../../lib/agent'); - -describe('HTTP agent', function () { - it('Without proxy', function () { - assert.strictEqual(null, agent()); - }); - - it('HTTPS proxy with auth from HTTPS_PROXY', function () { - process.env.HTTPS_PROXY = 'https://user:pass@secure:123'; - let logMsg = ''; - const proxy = agent(msg => { logMsg = msg; }); - delete process.env.HTTPS_PROXY; - assert.strictEqual('object', typeof proxy); - assert.strictEqual('secure', proxy.options.proxy.host); - assert.strictEqual(123, proxy.options.proxy.port); - assert.strictEqual('user:pass', proxy.options.proxy.proxyAuth); - assert.strictEqual(443, proxy.defaultPort); - assert.strictEqual(logMsg, 'Via proxy https://secure:123 with credentials'); - }); - - it('HTTPS proxy with auth from HTTPS_PROXY using credentials containing special characters', function () { - process.env.HTTPS_PROXY = 'https://user,:pass=@secure:789'; - let logMsg = ''; - const proxy = agent(msg => { logMsg = msg; }); - delete process.env.HTTPS_PROXY; - assert.strictEqual('object', typeof proxy); - assert.strictEqual('secure', proxy.options.proxy.host); - assert.strictEqual(789, proxy.options.proxy.port); - assert.strictEqual('user,:pass=', proxy.options.proxy.proxyAuth); - assert.strictEqual(443, proxy.defaultPort); - assert.strictEqual(logMsg, 'Via proxy https://secure:789 with credentials'); - }); - - it('HTTP proxy without auth from npm_config_proxy', function () { - process.env.npm_config_proxy = 'http://plaintext:456'; - let logMsg = ''; - const proxy = agent(msg => { logMsg = msg; }); - delete process.env.npm_config_proxy; - assert.strictEqual('object', typeof proxy); - assert.strictEqual('plaintext', proxy.options.proxy.host); - assert.strictEqual(456, proxy.options.proxy.port); - assert.strictEqual(null, proxy.options.proxy.proxyAuth); - assert.strictEqual(443, proxy.defaultPort); - assert.strictEqual(logMsg, 'Via proxy http://plaintext:456 no credentials'); - }); -}); diff --git a/test/unit/libvips.js b/test/unit/libvips.js index 31ba655ff..7ab720fd0 100644 --- a/test/unit/libvips.js +++ b/test/unit/libvips.js @@ -7,7 +7,6 @@ const assert = require('assert'); const fs = require('fs'); const semver = require('semver'); const libvips = require('../../lib/libvips'); -const mockFS = require('mock-fs'); const originalPlatform = process.platform; @@ -59,10 +58,6 @@ describe('libvips binaries', function () { assert.strictEqual('string', typeof minimumLibvipsVersion); assert.notStrictEqual(null, semver.valid(minimumLibvipsVersion)); }); - it('hasVendoredLibvips returns a boolean', function () { - const hasVendoredLibvips = libvips.hasVendoredLibvips(); - assert.strictEqual('boolean', typeof hasVendoredLibvips); - }); it('useGlobalLibvips can be ignored via an env var', function () { process.env.SHARP_IGNORE_GLOBAL_LIBVIPS = 1; @@ -71,62 +66,48 @@ describe('libvips binaries', function () { delete process.env.SHARP_IGNORE_GLOBAL_LIBVIPS; }); - it('cachePath returns a valid path ending with _libvips', function () { - const cachePath = libvips.cachePath(); - assert.strictEqual('string', typeof cachePath); - assert.strictEqual('_libvips', cachePath.substr(-8)); - assert.strictEqual(true, fs.existsSync(cachePath)); - }); }); - describe('integrity', function () { - it('reads value from environment variable', function () { - const prev = process.env.npm_package_config_integrity_platform_arch; - process.env.npm_package_config_integrity_platform_arch = 'sha512-test'; - - const integrity = libvips.integrity('platform-arch'); - assert.strictEqual('sha512-test', integrity); - - process.env.npm_package_config_integrity_platform_arch = prev; - }); - it('reads value from package.json', function () { - const prev = process.env.npm_package_config_integrity_linux_x64; - delete process.env.npm_package_config_integrity_linux_x64; - - const integrity = libvips.integrity('linux-x64'); - assert.strictEqual('sha512-', integrity.substr(0, 7)); - - process.env.npm_package_config_integrity_linux_x64 = prev; + describe('Build time platform detection', () => { + it('Can override platform with npm_config_platform and npm_config_libc', () => { + process.env.npm_config_platform = 'testplatform'; + process.env.npm_config_libc = 'testlibc'; + const [platform] = libvips.buildPlatformArch().split('-'); + assert.strictEqual(platform, 'testplatformtestlibc'); + delete process.env.npm_config_platform; + delete process.env.npm_config_libc; + }); + it('Can override arch with npm_config_arch', () => { + process.env.npm_config_arch = 'test'; + const [, arch] = libvips.buildPlatformArch().split('-'); + assert.strictEqual(arch, 'test'); + delete process.env.npm_config_arch; }); }); - describe('safe directory creation', function () { - before(function () { - mockFS({ - exampleDirA: { - exampleDirB: { - exampleFile: 'Example test file' - } - } - }); + describe('Build time directories', () => { + it('sharp-libvips include', () => { + const dir = libvips.buildSharpLibvipsIncludeDir(); + assert.strictEqual(fs.statSync(dir).isDirectory(), true); }); - after(function () { mockFS.restore(); }); - - it('mkdirSync creates a directory', function () { - const dirPath = 'createdDir'; - - libvips.mkdirSync(dirPath); - assert.strictEqual(true, fs.existsSync(dirPath)); + it('sharp-libvips cplusplus', () => { + const dir = libvips.buildSharpLibvipsCPlusPlusDir(); + assert.strictEqual(fs.statSync(dir).isDirectory(), true); }); - it('mkdirSync does not throw error or overwrite an existing dir', function () { - const dirPath = 'exampleDirA'; - const nestedDirPath = 'exampleDirA/exampleDirB'; - assert.strictEqual(true, fs.existsSync(dirPath)); - - libvips.mkdirSync(dirPath); + it('sharp-libvips lib', () => { + const dir = libvips.buildSharpLibvipsLibDir(); + assert.strictEqual(fs.statSync(dir).isDirectory(), true); + }); + }); - assert.strictEqual(true, fs.existsSync(dirPath)); - assert.strictEqual(true, fs.existsSync(nestedDirPath)); + describe('Runtime detection', () => { + it('platform', () => { + const [platform] = libvips.runtimePlatformArch().split('-'); + assert.strict(['darwin', 'linux', 'linuxmusl', 'win32'].includes(platform)); + }); + it('arch', () => { + const [, arch] = libvips.runtimePlatformArch().split('-'); + assert.strict(['arm', 'arm64', 'ia32', 'x64'].includes(arch)); }); }); diff --git a/test/unit/platform.js b/test/unit/platform.js deleted file mode 100644 index 402ee28bb..000000000 --- a/test/unit/platform.js +++ /dev/null @@ -1,91 +0,0 @@ -// Copyright 2013 Lovell Fuller and others. -// SPDX-License-Identifier: Apache-2.0 - -'use strict'; - -const assert = require('assert'); -const platform = require('../../lib/platform'); - -describe('Platform-detection', function () { - it('Can override arch with npm_config_arch', function () { - process.env.npm_config_arch = 'test'; - assert.strictEqual('test', platform().split('-')[1]); - delete process.env.npm_config_arch; - }); - - it('Can override platform with npm_config_platform', function () { - process.env.npm_config_platform = 'test'; - assert.strictEqual('test', platform().split('-')[0]); - delete process.env.npm_config_platform; - }); - - it('Can override ARM version via --arm-version', function () { - process.env.npm_config_arch = 'arm'; - process.env.npm_config_arm_version = 'test'; - assert.strictEqual('armvtest', platform().split('-')[1]); - delete process.env.npm_config_arm_version; - delete process.env.npm_config_arch; - }); - - it('Can override ARM64 version via --arm-version', function () { - process.env.npm_config_arch = 'arm64'; - process.env.npm_config_arm_version = 'test'; - assert.strictEqual('arm64vtest', platform().split('-')[1]); - delete process.env.npm_config_arm_version; - delete process.env.npm_config_arch; - }); - - if (process.config.variables.arm_version) { - it('Can detect ARM version via process.config', function () { - process.env.npm_config_arch = 'arm'; - assert.strictEqual(`armv${process.config.variables.arm_version}`, platform().split('-')[1]); - delete process.env.npm_config_arch; - }); - } - - if (!process.config.variables.arm_version) { - it('Defaults to ARMv6 for 32-bit', function () { - process.env.npm_config_arch = 'arm'; - assert.strictEqual('armv6', platform().split('-')[1]); - delete process.env.npm_config_arch; - }); - } - - it('Defaults to ARMv8 for 64-bit', function () { - process.env.npm_config_arch = 'arm64'; - assert.strictEqual('arm64v8', platform().split('-')[1]); - delete process.env.npm_config_arch; - }); - - it('Can ensure version ARMv7 if electron version is present', function () { - process.env.npm_config_arch = 'arm'; - process.versions.electron = 'test'; - assert.strictEqual('armv7', platform().split('-')[1]); - delete process.env.npm_config_arch; - delete process.versions.electron; - }); - - it('Can override libc if platform is linux', function () { - process.env.npm_config_platform = 'linux'; - process.env.npm_config_libc = 'test'; - assert.strictEqual('linuxtest', platform().split('-')[0]); - delete process.env.npm_config_platform; - delete process.env.npm_config_libc; - }); - - it('Handles libc value "glibc" as default linux', function () { - process.env.npm_config_platform = 'linux'; - process.env.npm_config_libc = 'glibc'; - assert.strictEqual('linux', platform().split('-')[0]); - delete process.env.npm_config_platform; - delete process.env.npm_config_libc; - }); - - it('Discards libc value on non-linux platform', function () { - process.env.npm_config_platform = 'win32'; - process.env.npm_config_libc = 'gnuwin32'; - assert.strictEqual('win32', platform().split('-')[0]); - delete process.env.npm_config_platform; - delete process.env.npm_config_libc; - }); -}); diff --git a/test/unit/util.js b/test/unit/util.js index 817bc6ca7..fd881a80d 100644 --- a/test/unit/util.js +++ b/test/unit/util.js @@ -146,14 +146,6 @@ describe('Utilities', function () { }); }); - describe('Vendor', function () { - it('Contains expected attributes', function () { - assert.strictEqual('object', typeof sharp.vendor); - assert.strictEqual('string', typeof sharp.vendor.current); - assert.strictEqual(true, Array.isArray(sharp.vendor.installed)); - }); - }); - describe('Block', () => { it('Can block a named operation', () => { sharp.block({ operation: ['test'] });