diff --git a/CHANGELOG.md b/CHANGELOG.md
index a5292a67..f780a26f 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,25 +1,25 @@
# Changelog
-All notable changes to this project will be documented in this file.
+All notable changes to NetVips will be documented in this file. See [here](CHANGELOG.native.md) for the changes to the [pre-compiled binaries of libvips](https://www.nuget.org/packages/NetVips.Native/).
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
-## [1.1.0] - ???
+## [1.1.0] - Unreleased
### Added
-- Pre-compiled libvips binaries for a few distros ([#21](https://github.com/kleisauke/net-vips/issues/21)):
- - [NetVips.Native.linux-x64](https://www.nuget.org/packages/NetVips.Native.linux-x64) - Linux x64 glibc (Ubuntu, Debian, etc).
- - [NetVips.Native.linux-musl-x64](https://www.nuget.org/packages/NetVips.Native.linux-musl-x64) - Linux x64 musl (Alpine, Gentoo Linux, etc).
- - [NetVips.Native.osx-x64](https://www.nuget.org/packages/NetVips.Native.osx-x64) - macOS x64.
+- A new [NetVips.Native](https://www.nuget.org/packages/NetVips.Native/) package containing the pre-compiled libvips binaries for Linux, macOS and Windows ([#21](https://github.com/kleisauke/net-vips/issues/21)).
+ - Changes to the [NetVips.Native.*](https://www.nuget.org/packages?q=id%3ANetVips.Native) packages will be documented [here](CHANGELOG.native.md).
+- Add `Base.GetSuffixes()` to get a list of all the filename suffixes supported by libvips ([libvips/ruby-vips#186](https://github.com/libvips/ruby-vips/issues/186)).
+- Add support for progress feedback (`image.SetProgress()`) and signal handling (`image.SignalConnect()`) ([#31](https://github.com/kleisauke/net-vips/issues/31)).
+- Add `image.SetKill()` and `image.IsKilled()` ([#31](https://github.com/kleisauke/net-vips/issues/31), [libvips/libvips@91d0e7e](https://github.com/libvips/libvips/commit/91d0e7e3d06fe6293f8e7513f30fd21585ea4305)).
### Changed
- Improve memory management ([#26](https://github.com/kleisauke/net-vips/issues/26)).
-- The bundled libvips Windows binaries were split into different NuGet packages:
- - [NetVips.Native.win-x64](https://www.nuget.org/packages/NetVips.Native.win-x64) - Windows 64-bit.
- - [NetVips.Native.win-x86](https://www.nuget.org/packages/NetVips.Native.win-x86) - Windows 32-bit.
+- The bundled libvips Windows binaries were moved to the [NetVips.Native](https://www.nuget.org/packages/NetVips.Native/) package.
- Update the [NetVips.Benchmarks](https://github.com/kleisauke/net-vips/tree/master/tests/NetVips.Benchmarks).
-- A statically linked libvips binary is build for Windows. This reduces the number of DLLs from 37 to 3 ([libvips/build-win64#21](https://github.com/libvips/build-win64/issues/21#issuecomment-458112440)).
+- The overloadable operators `==` and `!=` have been changed to `Equal` and `NotEqual` to avoid conflicts with `null` checks.
+- Some methods are overloaded instead of defining the parameters as `object` type.
### Removed
-- The `UseGlobalLibvips` property since the bundled libvips binaries are split into different NuGet packages.
+- The `UseGlobalLibvips` property since the bundled libvips binaries were moved to the [NetVips.Native](https://www.nuget.org/packages/NetVips.Native/) package.
## [1.0.7] - 2019-01-18
### Changed
@@ -85,7 +85,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/)
### Added
- First release!
-[1.1.0]: https://github.com/kleisauke/net-vips/compare/v1.0.7...v1.1.0
+[1.1.0]: https://github.com/kleisauke/net-vips/compare/v1.0.7...1.1.0
[1.0.7]: https://github.com/kleisauke/net-vips/compare/v1.0.6...v1.0.7
[1.0.6]: https://github.com/kleisauke/net-vips/compare/v1.0.5...v1.0.6
[1.0.5]: https://github.com/kleisauke/net-vips/compare/v1.0.4...v1.0.5
diff --git a/CHANGELOG.native.md b/CHANGELOG.native.md
new file mode 100644
index 00000000..fc5ce1b8
--- /dev/null
+++ b/CHANGELOG.native.md
@@ -0,0 +1,33 @@
+# Changelog
+All notable changes to the pre-compiled binaries of libvips will be documented in this file. The version number of these NuGet packages is in sync with libvips' version number.
+The changes of libvips are documented [here](https://github.com/libvips/libvips/blob/master/ChangeLog).
+
+The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
+
+## [8.8.0] - Unreleased
+### Note
+If you would like to see a complete list of all the new features, changes and bug fixes, please visit the the release notes of libvips:
+https://github.com/libvips/libvips/releases
+
+## [8.7.4] - 2019-04-10
+### Added
+- A [NetVips.Native](https://www.nuget.org/packages/NetVips.Native/) package which depends on the other [NetVips.Native.*](https://www.nuget.org/packages?q=id%3ANetVips.Native) packages.
+
+### Changed
+- The OS X binaries are now distributed with [`jpeg-turbo`](https://github.com/libjpeg-turbo/libjpeg-turbo) instead than [`jpeg`](https://www.ijg.org/) ([lovell/package-libvips-darwin#3](https://github.com/lovell/package-libvips-darwin/pull/3)).
+
+## [8.7.4 beta 1] - 2019-02-25
+### Added
+- Pre-compiled libvips binaries for a few distros ([#21](https://github.com/kleisauke/net-vips/issues/21)):
+ - [NetVips.Native.linux-x64](https://www.nuget.org/packages/NetVips.Native.linux-x64) - Linux x64 glibc (Ubuntu, Debian, etc).
+ - [NetVips.Native.linux-musl-x64](https://www.nuget.org/packages/NetVips.Native.linux-musl-x64) - Linux x64 musl (Alpine, Gentoo Linux, etc).
+ - [NetVips.Native.osx-x64](https://www.nuget.org/packages/NetVips.Native.osx-x64) - macOS x64.
+ - [NetVips.Native.win-x64](https://www.nuget.org/packages/NetVips.Native.win-x64) - Windows 64-bit.
+ - [NetVips.Native.win-x86](https://www.nuget.org/packages/NetVips.Native.win-x86) - Windows 32-bit.
+
+### Changed
+- A statically linked libvips binary is build for Windows. This reduces the number of DLLs from 37 to 3 ([libvips/build-win64#21](https://github.com/libvips/build-win64/issues/21#issuecomment-458112440)).
+
+[8.8.0]: https://github.com/kleisauke/libvips-packaging/compare/v8.7.4...HEAD
+[8.7.4]: https://github.com/kleisauke/libvips-packaging/compare/v8.7.4-beta1...v8.7.4
+[8.7.4 beta 1]: https://github.com/kleisauke/libvips-packaging/releases/tag/v8.7.4-beta1
diff --git a/documentation/docfx.json b/documentation/docfx.json
index b7b8a5d9..ff1a1dfb 100644
--- a/documentation/docfx.json
+++ b/documentation/docfx.json
@@ -30,6 +30,10 @@
"files": "CHANGELOG.md",
"src": ".."
},
+ {
+ "files": "CHANGELOG.native.md",
+ "src": ".."
+ },
{
"files": [
"tutorial/**/*.{md,yml}",
diff --git a/src/NetVips/ExtensionMethods.cs b/src/NetVips/ExtensionMethods.cs
index 39efbfc6..c34ad4fd 100644
--- a/src/NetVips/ExtensionMethods.cs
+++ b/src/NetVips/ExtensionMethods.cs
@@ -252,28 +252,5 @@ internal static string ToReadableBytes(this ulong value)
return $"{dValue:n2} {sizeSuffixes[i]}";
}
-
- ///
- /// Connects a callback function ()
- /// to a signal for a particular .
- ///
- /// The instance to connect to.
- /// A string of the form "signal-name::detail".
- /// The to connect.
- /// Data to pass to handler calls.
- /// The handler id.
- /// If it failed to connect the signal.
- internal static uint Connect(this GObject instance, string detailedSignal, GCallback callback,
- IntPtr data = default)
- {
- var ret = GSignal.ConnectData(instance, detailedSignal, callback, data, null, default);
-
- if (ret == 0)
- {
- throw new Exception("Failed to connect signal.");
- }
-
- return ret;
- }
}
}
\ No newline at end of file
diff --git a/src/NetVips/GObject.cs b/src/NetVips/GObject.cs
index 6d8eb2f6..908f72d6 100644
--- a/src/NetVips/GObject.cs
+++ b/src/NetVips/GObject.cs
@@ -2,6 +2,8 @@ namespace NetVips
{
using System;
using System.Runtime.InteropServices;
+ using System.Collections.Generic;
+ using NetVips.Internal;
///
/// Manage lifetime.
@@ -10,6 +12,12 @@ public class GObject : SafeHandle
{
// private static Logger logger = LogManager.GetCurrentClassLogger();
+ ///
+ /// We have to record all of the delegates to
+ /// prevent them from being re-located or disposed of by the garbage collector.
+ ///
+ private readonly List _handles = new List();
+
// Handy for debugging
// public static int NObjects;
@@ -32,6 +40,35 @@ internal GObject(IntPtr pointer)
// logger.Debug($"GObject = {pointer}");
}
+ ///
+ /// Connects a callback function () to a signal on this object.
+ ///
+ ///
+ /// The callback will be triggered every time this signal is issued on this instance.
+ ///
+ /// A string of the form "signal-name::detail".
+ /// The callback to connect.
+ /// Data to pass to handler calls.
+ /// The handler id.
+ /// If it failed to connect the signal.
+ public uint SignalConnect(string detailedSignal, Delegate callback, IntPtr data = default)
+ {
+ // prevent the delegate from being re-located or disposed of by the garbage collector
+ var delegateHandle = GCHandle.Alloc(callback);
+ _handles.Add(delegateHandle);
+
+ // get the pointer for the delegate which can be passed to the native code
+ var callbackPtr = Marshal.GetFunctionPointerForDelegate(callback);
+ var ret = GSignal.ConnectData(this, detailedSignal, callbackPtr, data, null, default);
+
+ if (ret == 0)
+ {
+ throw new Exception("Failed to connect signal.");
+ }
+
+ return ret;
+ }
+
///
/// Decreases the reference count of object.
/// When its reference count drops to 0, the object is finalized (i.e. its memory is freed).
@@ -44,6 +81,14 @@ protected override bool ReleaseHandle()
if (!IsInvalid)
{
Internal.GObject.Unref(handle);
+
+ // release all handles recorded by this object
+ foreach (var gcHandle in _handles)
+ {
+ gcHandle.Free();
+ }
+
+ _handles.Clear();
}
// NObjects--;
diff --git a/src/NetVips/Image.cs b/src/NetVips/Image.cs
index 1b240491..35a4634b 100644
--- a/src/NetVips/Image.cs
+++ b/src/NetVips/Image.cs
@@ -21,11 +21,6 @@ public sealed partial class Image : VipsObject
///
private GCHandle _dataHandle;
- ///
- /// Ref for .
- ///
- private GCHandle _progressHandle;
-
///
internal Image(IntPtr pointer)
: base(pointer)
@@ -1426,7 +1421,7 @@ public void SetKill(bool kill)
return;
}
- VipsImage.SetKill(this, kill ? 1 : 0);
+ VipsImage.SetKill(this, kill ? 1 : 0);
}
///
@@ -1456,11 +1451,15 @@ public void SetKill(bool kill)
public void SetProgress(IProgress progress, CancellationToken token = default)
{
VipsImage.SetProgress(this, progress == null ? 0 : 1);
+ if (progress == null)
+ {
+ return;
+ }
var lastPercent = 0;
var isKilled = false;
- GCallback evalCallback = (imagePtr, progressPtr, userDataPtr) =>
+ EvalCallback evalCallback = (imagePtr, progressPtr, userDataPtr) =>
{
// Block evaluation on this image if a cancellation
// has been requested for this token.
@@ -1483,15 +1482,12 @@ public void SetProgress(IProgress progress, CancellationToken token = defau
var progressStruct = progressPtr.Dereference();
if (progressStruct.Percent != lastPercent)
{
- progress?.Report(progressStruct.Percent);
+ progress.Report(progressStruct.Percent);
lastPercent = progressStruct.Percent;
}
};
- // prevent it from being re-located or disposed of by the garbage collector
- _progressHandle = GCHandle.Alloc(evalCallback);
-
- this.Connect(Internal.Enums.VipsEvaluation.Eval, evalCallback);
+ SignalConnect(Internal.Enums.VipsEvaluation.Eval, evalCallback);
}
#endregion
@@ -1630,17 +1626,12 @@ public override int GetHashCode()
///
protected override void Dispose(bool disposing)
{
- // release references to delegates / data objects
+ // release reference to our secret ref
if (_dataHandle.IsAllocated)
{
_dataHandle.Free();
}
- if (_progressHandle.IsAllocated)
- {
- _progressHandle.Free();
- }
-
// Call our base Dispose method
base.Dispose(disposing);
}
diff --git a/src/NetVips/Internal/GObject.cs b/src/NetVips/Internal/GObject.cs
index a979ae4b..d1b6cd2e 100644
--- a/src/NetVips/Internal/GObject.cs
+++ b/src/NetVips/Internal/GObject.cs
@@ -163,16 +163,13 @@ internal struct Struct
[SuppressUnmanagedCodeSecurity, UnmanagedFunctionPointer(CallingConvention.Cdecl)]
internal delegate void GClosureNotify(IntPtr data, IntPtr closure);
- [SuppressUnmanagedCodeSecurity, UnmanagedFunctionPointer(CallingConvention.Cdecl)]
- internal delegate void GCallback(IntPtr gobjectPtr, IntPtr pspecPtr, IntPtr userDataPtr);
-
internal static class GSignal
{
[SuppressUnmanagedCodeSecurity]
[DllImport(Libraries.GObject, CallingConvention = CallingConvention.Cdecl,
EntryPoint = "g_signal_connect_data")]
internal static extern uint ConnectData(NetVips.GObject instance,
- [MarshalAs(UnmanagedType.LPStr)] string detailedSignal, GCallback cHandler, IntPtr data,
+ [MarshalAs(UnmanagedType.LPStr)] string detailedSignal, IntPtr cHandler, IntPtr data,
GClosureNotify destroyData, Enums.GConnectFlags connectFlags);
}
}
\ No newline at end of file
diff --git a/src/NetVips/Internal/Vips.cs b/src/NetVips/Internal/Vips.cs
index 583de79b..5802ce47 100644
--- a/src/NetVips/Internal/Vips.cs
+++ b/src/NetVips/Internal/Vips.cs
@@ -295,6 +295,9 @@ internal static extern void SetArrayInt(ref GValue.Struct value,
internal static extern void SetArrayImage(ref GValue.Struct value, int n);
}
+ [SuppressUnmanagedCodeSecurity, UnmanagedFunctionPointer(CallingConvention.Cdecl)]
+ internal delegate void EvalCallback(IntPtr imagePtr, IntPtr progressPtr, IntPtr userDataPtr);
+
internal static class VipsImage
{
[SuppressUnmanagedCodeSecurity]
diff --git a/tests/NetVips.Tests/IoFuncsTests.cs b/tests/NetVips.Tests/IoFuncsTests.cs
index 6f37d9b2..6b1657d2 100644
--- a/tests/NetVips.Tests/IoFuncsTests.cs
+++ b/tests/NetVips.Tests/IoFuncsTests.cs
@@ -162,15 +162,13 @@ public void TestSetProgress()
var progress = new Progress(percent =>
{
- // Tests whether the actual percentage is higher
- // than the last percentage received.
- Assert.True(percent > lastPercent);
lastPercent = percent;
});
im.SetProgress(progress);
var buf = im.DzsaveBuffer("image-pyramid");
Assert.True(buf.Length > 0);
+ Assert.True(lastPercent <= 100);
}
[Fact]