mirror of https://github.com/dahall/Vanara.git
Added nullability to Magnification and tests
parent
163affe6ba
commit
3aa52d622f
|
@ -394,6 +394,38 @@ public static partial class Magnification
|
||||||
[return: MarshalAs(UnmanagedType.Bool)]
|
[return: MarshalAs(UnmanagedType.Bool)]
|
||||||
public static extern bool MagSetColorEffect(HWND hwnd, in MAGCOLOREFFECT pEffect);
|
public static extern bool MagSetColorEffect(HWND hwnd, in MAGCOLOREFFECT pEffect);
|
||||||
|
|
||||||
|
/// <summary>Sets the color transformation matrix for a magnifier control.</summary>
|
||||||
|
/// <param name="hwnd">
|
||||||
|
/// <para>Type: <c>HWND</c></para>
|
||||||
|
/// <para>The magnification window.</para>
|
||||||
|
/// </param>
|
||||||
|
/// <param name="pEffect">
|
||||||
|
/// <para>Type: <c>PMAGCOLOREFFECT</c></para>
|
||||||
|
/// <para>The color transformation matrix, or <c>NULL</c> to remove the current color effect, if any.</para>
|
||||||
|
/// </param>
|
||||||
|
/// <returns>
|
||||||
|
/// <para>Type: <c>BOOL</c></para>
|
||||||
|
/// <para>Returns <c>TRUE</c> if successful, or <c>FALSE</c> otherwise.</para>
|
||||||
|
/// </returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// <para>
|
||||||
|
/// The magnifier control uses the color transformation matrix to apply a color effect to the entire magnifier window. If the
|
||||||
|
/// function is called multiple times, the most recent color transform is used.
|
||||||
|
/// </para>
|
||||||
|
/// <para>This function requires Windows Display Driver Model (WDDM)-capable video cards.</para>
|
||||||
|
/// <para>Examples</para>
|
||||||
|
/// <para>The following example sets a color transformation matrix that converts the colors displayed in the magnifier to grayscale.</para>
|
||||||
|
/// <para>
|
||||||
|
/// <code>// Description: // Converts the colors displayed in the magnifier window to grayscale, or // returns the colors to normal. // Parameters: // hwndMag - Handle of the magnifier control. // fInvert - TRUE to convert to grayscale, or FALSE for normal colors. // BOOL ConvertToGrayscale(HWND hwndMag, BOOL fConvert) { // Convert the screen colors in the magnifier window. if (fConvert) { MAGCOLOREFFECT magEffectGrayscale = {{ // MagEffectGrayscale { 0.3f, 0.3f, 0.3f, 0.0f, 0.0f }, { 0.6f, 0.6f, 0.6f, 0.0f, 0.0f }, { 0.1f, 0.1f, 0.1f, 0.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 1.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 0.0f, 1.0f } }}; return MagSetColorEffect(hwndMag, &magEffectGrayscale); } // Return the colors to normal. else { return MagSetColorEffect(hwndMag, NULL); } }</code>
|
||||||
|
/// </para>
|
||||||
|
/// </remarks>
|
||||||
|
// https://docs.microsoft.com/en-us/windows/win32/api/magnification/nf-magnification-magsetcoloreffect BOOL MagSetColorEffect( HWND
|
||||||
|
// hwnd, PMAGCOLOREFFECT pEffect );
|
||||||
|
[DllImport(Lib_Magnification, SetLastError = false, ExactSpelling = true)]
|
||||||
|
[PInvokeData("magnification.h", MSDNShortId = "NF:magnification.MagSetColorEffect")]
|
||||||
|
[return: MarshalAs(UnmanagedType.Bool)]
|
||||||
|
public static extern bool MagSetColorEffect(HWND hwnd, [In, Optional] IntPtr pEffect);
|
||||||
|
|
||||||
/// <summary>Changes the color transformation matrix associated with the full-screen magnifier.</summary>
|
/// <summary>Changes the color transformation matrix associated with the full-screen magnifier.</summary>
|
||||||
/// <param name="pEffect">
|
/// <param name="pEffect">
|
||||||
/// <para>Type: <c>PMAGCOLOREFFECT</c></para>
|
/// <para>Type: <c>PMAGCOLOREFFECT</c></para>
|
||||||
|
@ -529,7 +561,7 @@ public static partial class Magnification
|
||||||
[DllImport(Lib_Magnification, SetLastError = false, ExactSpelling = true)]
|
[DllImport(Lib_Magnification, SetLastError = false, ExactSpelling = true)]
|
||||||
[PInvokeData("magnification.h", MSDNShortId = "NF:magnification.MagSetImageScalingCallback")]
|
[PInvokeData("magnification.h", MSDNShortId = "NF:magnification.MagSetImageScalingCallback")]
|
||||||
[return: MarshalAs(UnmanagedType.Bool)]
|
[return: MarshalAs(UnmanagedType.Bool)]
|
||||||
public static extern bool MagSetImageScalingCallback(HWND hwnd, MagImageScalingCallback callback);
|
public static extern bool MagSetImageScalingCallback(HWND hwnd, MagImageScalingCallback? callback);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sets the current active input transformation for pen and touch input, represented as a source rectangle and a destination rectangle.
|
/// Sets the current active input transformation for pen and touch input, represented as a source rectangle and a destination rectangle.
|
||||||
|
@ -579,7 +611,7 @@ public static partial class Magnification
|
||||||
[DllImport(Lib_Magnification, SetLastError = true, ExactSpelling = true)]
|
[DllImport(Lib_Magnification, SetLastError = true, ExactSpelling = true)]
|
||||||
[PInvokeData("magnification.h", MSDNShortId = "NF:magnification.MagSetInputTransform")]
|
[PInvokeData("magnification.h", MSDNShortId = "NF:magnification.MagSetInputTransform")]
|
||||||
[return: MarshalAs(UnmanagedType.Bool)]
|
[return: MarshalAs(UnmanagedType.Bool)]
|
||||||
public static extern bool MagSetInputTransform([MarshalAs(UnmanagedType.Bool)] bool fEnabled, [Optional] in RECT pRectSource, [Optional] in RECT pRectDest);
|
public static extern bool MagSetInputTransform([MarshalAs(UnmanagedType.Bool)] bool fEnabled, [In, Optional] PRECT? pRectSource, [In, Optional] PRECT? pRectDest);
|
||||||
|
|
||||||
/// <summary>Sets the list of windows to be magnified or the list of windows to be excluded from magnification.</summary>
|
/// <summary>Sets the list of windows to be magnified or the list of windows to be excluded from magnification.</summary>
|
||||||
/// <param name="hwnd">
|
/// <param name="hwnd">
|
||||||
|
@ -737,7 +769,7 @@ public static partial class Magnification
|
||||||
// { float transform[5][5]; } MAGCOLOREFFECT, *PMAGCOLOREFFECT;
|
// { float transform[5][5]; } MAGCOLOREFFECT, *PMAGCOLOREFFECT;
|
||||||
[PInvokeData("magnification.h", MSDNShortId = "NS:magnification.tagMAGCOLOREFFECT")]
|
[PInvokeData("magnification.h", MSDNShortId = "NS:magnification.tagMAGCOLOREFFECT")]
|
||||||
[StructLayout(LayoutKind.Sequential)]
|
[StructLayout(LayoutKind.Sequential)]
|
||||||
public struct MAGCOLOREFFECT
|
public struct MAGCOLOREFFECT : IEquatable<MAGCOLOREFFECT>
|
||||||
{
|
{
|
||||||
private const int dimLen = 5;
|
private const int dimLen = 5;
|
||||||
|
|
||||||
|
@ -916,41 +948,6 @@ public static partial class Magnification
|
||||||
public static bool operator !=(MAGCOLOREFFECT lhs, MAGCOLOREFFECT rhs) => !(lhs == rhs);
|
public static bool operator !=(MAGCOLOREFFECT lhs, MAGCOLOREFFECT rhs) => !(lhs == rhs);
|
||||||
|
|
||||||
/// <summary>An Identity Matrix for MAGCOLOREFFECT.</summary>
|
/// <summary>An Identity Matrix for MAGCOLOREFFECT.</summary>
|
||||||
|
|
||||||
/* Unmerged change from project 'Vanara.PInvoke.Magnification (net48)'
|
|
||||||
Before:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new MAGCOLOREFFECT { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
After:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Unmerged change from project 'Vanara.PInvoke.Magnification (net7.0)'
|
|
||||||
Before:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new MAGCOLOREFFECT { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
After:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Unmerged change from project 'Vanara.PInvoke.Magnification (netcoreapp3.1)'
|
|
||||||
Before:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new MAGCOLOREFFECT { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
After:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Unmerged change from project 'Vanara.PInvoke.Magnification (netstandard2.0)'
|
|
||||||
Before:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new MAGCOLOREFFECT { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
After:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Unmerged change from project 'Vanara.PInvoke.Magnification (net45)'
|
|
||||||
Before:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new MAGCOLOREFFECT { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
After:
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
|
||||||
*/
|
|
||||||
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
public static readonly MAGCOLOREFFECT Identity = new() { transform00 = 1, transform11 = 1, transform22 = 1, transform33 = 1, transform44 = 1 };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -291,7 +291,7 @@ public class WindowBase : MarshalByRefObject, IDisposable, IWindowInstance, IWin
|
||||||
/// <summary>Performs an implicit conversion from <see cref="WindowBase"/> to <see cref="HWND"/>.</summary>
|
/// <summary>Performs an implicit conversion from <see cref="WindowBase"/> to <see cref="HWND"/>.</summary>
|
||||||
/// <param name="w">The <see cref="WindowBase"/> instance.</param>
|
/// <param name="w">The <see cref="WindowBase"/> instance.</param>
|
||||||
/// <returns>The result of the conversion.</returns>
|
/// <returns>The result of the conversion.</returns>
|
||||||
public static implicit operator HWND(WindowBase w) => w.Handle;
|
public static implicit operator HWND(WindowBase? w) => w?.Handle ?? HWND.NULL;
|
||||||
|
|
||||||
[DebuggerStepThrough]
|
[DebuggerStepThrough]
|
||||||
private void CheckDetached()
|
private void CheckDetached()
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
using NUnit.Framework;
|
using NUnit.Framework;
|
||||||
using NUnit.Framework.Internal;
|
using NUnit.Framework.Internal;
|
||||||
|
using System.Diagnostics;
|
||||||
using static Vanara.PInvoke.Magnification;
|
using static Vanara.PInvoke.Magnification;
|
||||||
|
using static Vanara.PInvoke.User32;
|
||||||
|
|
||||||
namespace Vanara.PInvoke.Tests;
|
namespace Vanara.PInvoke.Tests;
|
||||||
|
|
||||||
|
@ -14,6 +16,13 @@ public class MagnificationTests
|
||||||
{ 0.0f, 0.0f, 0.0f, 1.0f, 0.0f },
|
{ 0.0f, 0.0f, 0.0f, 1.0f, 0.0f },
|
||||||
{ 0.0f, 0.0f, 0.0f, 0.0f, 1.0f }});
|
{ 0.0f, 0.0f, 0.0f, 0.0f, 1.0f }});
|
||||||
|
|
||||||
|
//static readonly MAGCOLOREFFECT invert = new(new[,] {
|
||||||
|
// { -1.0f, 0.0f, 0.0f, 0.0f, 0.0f },
|
||||||
|
// { 0.0f, -1.0f, 0.0f, 0.0f, 0.0f },
|
||||||
|
// { 0.0f, 0.0f, -1.0f, 0.0f, 0.0f },
|
||||||
|
// { 0.0f, 0.0f, 0.0f, 1.0f, 0.0f },
|
||||||
|
// { 1.0f, 1.0f, 1.0f, 0.0f, 1.0f }});
|
||||||
|
|
||||||
[OneTimeSetUp]
|
[OneTimeSetUp]
|
||||||
public void _Setup()
|
public void _Setup()
|
||||||
{
|
{
|
||||||
|
@ -26,6 +35,58 @@ public class MagnificationTests
|
||||||
Assert.IsTrue(MagUninitialize());
|
Assert.IsTrue(MagUninitialize());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Test]
|
||||||
|
public void GetSetMagEffect()
|
||||||
|
{
|
||||||
|
VisibleWindow? hwndHost = null;
|
||||||
|
HWND hwndMag = default;
|
||||||
|
new System.Threading.Thread(() =>
|
||||||
|
{
|
||||||
|
const string WindowClassName = "Magnification Test";
|
||||||
|
|
||||||
|
HINSTANCE hInst = Kernel32.GetModuleHandle().ReleaseOwnership();
|
||||||
|
hwndHost = new VisibleWindow(WindowClassName, hInst, WindowClassName, new SIZE(300, 200), exStyle: WindowStylesEx.WS_EX_TOPMOST | WindowStylesEx.WS_EX_LAYERED | WindowStylesEx.WS_EX_TRANSPARENT);
|
||||||
|
Assert.False(hwndHost.Handle.IsNull);
|
||||||
|
|
||||||
|
// Make the window opaque.
|
||||||
|
SetLayeredWindowAttributes(hwndHost, 0, 255, LayeredWindowAttributes.LWA_ALPHA);
|
||||||
|
|
||||||
|
// Create a magnifier control that fills the client area.
|
||||||
|
var r = hwndHost.ClientRect;
|
||||||
|
var tmp = CreateWindow(WC_MAGNIFIER, "MagnifierWindow", WindowStyles.WS_CHILD | (WindowStyles)MagnifierStyles.MS_SHOWMAGNIFIEDCURSOR | WindowStyles.WS_VISIBLE,
|
||||||
|
0, 0, r.Width, r.Height, hwndHost, default, hInst);
|
||||||
|
if ((hwndMag = tmp.ReleaseOwnership()) != HWND.NULL)
|
||||||
|
{
|
||||||
|
hwndHost.Show();
|
||||||
|
new MessagePump().Run(hwndHost);
|
||||||
|
}
|
||||||
|
}).Start();
|
||||||
|
System.Threading.Thread.Yield();
|
||||||
|
System.Threading.Thread.Sleep(500);
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Assert.That(hwndMag, ResultIs.ValidHandle);
|
||||||
|
|
||||||
|
Assert.That(MagGetColorEffect(GetDesktopWindow(), out var eff), ResultIs.FailureCode(Win32Error.ERROR_NOT_SUPPORTED));
|
||||||
|
Assert.That(MagSetColorEffect(GetDesktopWindow(), eff), ResultIs.FailureCode(Win32Error.ERROR_NOT_SUPPORTED));
|
||||||
|
|
||||||
|
MAGTRANSFORM matrix = new(2f);
|
||||||
|
Assert.That(MagSetWindowTransform(hwndMag, matrix), ResultIs.Successful);
|
||||||
|
Assert.That(MagGetWindowTransform(hwndMag, out var m2), ResultIs.Successful);
|
||||||
|
Assert.AreEqual(matrix, m2);
|
||||||
|
|
||||||
|
Assert.That(MagGetColorEffect(hwndMag, out eff), ResultIs.Successful);
|
||||||
|
Assert.True(eff.IsIdentity);
|
||||||
|
Assert.That(MagSetColorEffect(hwndMag, grayeff), ResultIs.Successful);
|
||||||
|
Assert.That(MagSetColorEffect(hwndMag), ResultIs.Successful);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
hwndHost?.Close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
[Test]
|
[Test]
|
||||||
public void MagGetSetFullscreenTransformTest()
|
public void MagGetSetFullscreenTransformTest()
|
||||||
{
|
{
|
||||||
|
@ -47,7 +108,7 @@ public class MagnificationTests
|
||||||
{
|
{
|
||||||
Assert.That(MagSetFullscreenColorEffect(grayeff), ResultIs.Successful);
|
Assert.That(MagSetFullscreenColorEffect(grayeff), ResultIs.Successful);
|
||||||
Assert.That(MagGetFullscreenColorEffect(out var grayeff_get), ResultIs.Successful);
|
Assert.That(MagGetFullscreenColorEffect(out var grayeff_get), ResultIs.Successful);
|
||||||
Assert.That(grayeff.transform, Is.EquivalentTo(grayeff_get.transform));
|
Assert.AreEqual(grayeff, grayeff_get);
|
||||||
System.Threading.Thread.Sleep(1000);
|
System.Threading.Thread.Sleep(1000);
|
||||||
Assert.That(MagSetFullscreenColorEffect(MAGCOLOREFFECT.Identity), ResultIs.Successful);
|
Assert.That(MagSetFullscreenColorEffect(MAGCOLOREFFECT.Identity), ResultIs.Successful);
|
||||||
}
|
}
|
||||||
|
@ -110,42 +171,4 @@ public class MagnificationTests
|
||||||
Assert.AreEqual(11.2f, tfx[1, 2]);
|
Assert.AreEqual(11.2f, tfx[1, 2]);
|
||||||
Assert.AreEqual(12.2f, tfx[2, 2]);
|
Assert.AreEqual(12.2f, tfx[2, 2]);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
private static bool CreateMagnifier(HINSTANCE hInstance)
|
|
||||||
{
|
|
||||||
const string WindowClassName = "Magnification Test";
|
|
||||||
|
|
||||||
// Register the host window class.
|
|
||||||
var wcex = new WNDCLASSEX
|
|
||||||
{
|
|
||||||
cbSize = (uint)Marshal.SizeOf<WNDCLASSEX>(),
|
|
||||||
style = 0,
|
|
||||||
lpfnWndProc = HostWndProc,
|
|
||||||
hInstance = hInstance,
|
|
||||||
hCursor = LoadCursor(default, IDC_ARROW),
|
|
||||||
hbrBackground = (HBRUSH)(1 + COLOR_BTNFACE),
|
|
||||||
lpszClassName = WindowClassName
|
|
||||||
};
|
|
||||||
|
|
||||||
if (RegisterClassEx(wcex) == 0)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
// Create the host window.
|
|
||||||
hwndHost = CreateWindowEx(WindowStylesEx.WS_EX_TOPMOST | WindowStylesEx.WS_EX_LAYERED | WindowStylesEx.WS_EX_TRANSPARENT,
|
|
||||||
WindowClassName, WindowClassName, WindowStyles.WS_CLIPCHILDREN, 0, 0, 0, 0, default, default, hInstance, default);
|
|
||||||
if (hwndHost.IsInvalid)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
// Make the window opaque.
|
|
||||||
SetLayeredWindowAttributes(hwndHost, 0, 255, LayeredWindowAttributes.LWA_ALPHA);
|
|
||||||
|
|
||||||
// Create a magnifier control that fills the client area.
|
|
||||||
hwndMag = CreateWindow(WC_MAGNIFIER, "MagnifierWindow", WindowStyles.WS_CHILD | WindowStyles.MS_SHOWMAGNIFIEDCURSOR | WindowStyles.WS_VISIBLE,
|
|
||||||
0, 0, LENS_WIDTH, LENS_HEIGHT, hwndHost, NULL, hInstance, NULL);
|
|
||||||
return !hwndMag.IsInvalid;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static IntPtr HostWndProc(HWND hwnd, uint uMsg, IntPtr wParam, IntPtr lParam) => throw new NotImplementedException();
|
|
||||||
*/
|
|
||||||
}
|
}
|
Loading…
Reference in New Issue