2023-08-04 12:24:49 -04:00
|
|
|
|
using System.Security;
|
2020-02-26 17:20:47 -05:00
|
|
|
|
using System.Windows.Forms;
|
|
|
|
|
using Vanara.PInvoke;
|
|
|
|
|
|
2023-03-31 11:47:53 -04:00
|
|
|
|
namespace Vanara.Windows.Shell;
|
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
internal interface IMessageWindowHost
|
|
|
|
|
{
|
|
|
|
|
void WndProc(ref Message msg);
|
|
|
|
|
}
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")]
|
|
|
|
|
[SecuritySafeCritical]
|
|
|
|
|
internal class HostedMessageWindow<THost> : NativeWindow where THost : IMessageWindowHost
|
|
|
|
|
{
|
|
|
|
|
private readonly THost host;
|
|
|
|
|
private GCHandle rooting;
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
internal HostedMessageWindow(THost host) => this.host = host ?? throw new ArgumentNullException(nameof(host));
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
~HostedMessageWindow()
|
|
|
|
|
{
|
|
|
|
|
if (Handle != default && !DoNotClose)
|
|
|
|
|
User32.PostMessage(Handle, (uint)User32.WindowMessage.WM_CLOSE);
|
|
|
|
|
}
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
protected virtual bool DoNotClose => false;
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
public void LockReference(bool locked)
|
|
|
|
|
{
|
|
|
|
|
if (locked)
|
|
|
|
|
{
|
|
|
|
|
if (!rooting.IsAllocated)
|
|
|
|
|
rooting = GCHandle.Alloc(host, GCHandleType.Normal);
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
if (rooting.IsAllocated)
|
|
|
|
|
rooting.Free();
|
|
|
|
|
}
|
|
|
|
|
}
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
protected override void OnThreadException(Exception e) => Application.OnThreadException(e);
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")]
|
|
|
|
|
protected override void WndProc(ref Message m)
|
|
|
|
|
{
|
|
|
|
|
host.WndProc(ref m);
|
|
|
|
|
base.WndProc(ref m);
|
|
|
|
|
}
|
|
|
|
|
}
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")]
|
|
|
|
|
internal class WindowMessageHook<THost> : HostedMessageWindow<THost> where THost : IMessageWindowHost
|
|
|
|
|
{
|
|
|
|
|
public WindowMessageHook(Control parent, THost host) : base(host)
|
|
|
|
|
{
|
|
|
|
|
if (parent is null) throw new ArgumentNullException(nameof(parent));
|
2023-08-21 13:11:05 -04:00
|
|
|
|
parent.HandleCreated += (s, e) => AssignHandle(((Control?)s)?.Handle ?? IntPtr.Zero);
|
2023-08-04 12:24:49 -04:00
|
|
|
|
parent.HandleDestroyed += (s, e) => ReleaseHandle();
|
|
|
|
|
}
|
2020-02-26 17:20:47 -05:00
|
|
|
|
|
2023-08-04 12:24:49 -04:00
|
|
|
|
protected override bool DoNotClose => true;
|
|
|
|
|
}
|