gpt4 book ai didi

c# - 获取 PrintDialog 的模态对话框句柄

转载 作者:太空狗 更新时间:2023-10-29 23:31:19 26 4
gpt4 key购买 nike

我在 .net 2.0 上有一个 Windows 应用程序。在 Form1 上,我打开了一个 PrintDialog。如何从我的代码中获取该对话框的句柄?

我已经尝试了很多 win32 函数:EnumWindowsEnumChildWindowsFindWindowFindWindowEx 但它不能找到我的 PrintDialog。我所能找到的只是 Form1 及其子控件。我无法获得 PrintDialog 的句柄。

一些我试过的代码:

导入win32:

    [DllImport("user32.dll", SetLastError = true)]
public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

调用 win32 函数:

using (PrintDialog dlg = new PrintDialog
{
AllowCurrentPage = false,
AllowSomePages = true,
AllowSelection = false
})
{
IntPtr printHandle = CustomPrintDialog.FindWindow("#32770", "Print");
// some logic with printHandle go here
if (dlg.ShowDialog(this)==DialogResult.OK){
// some logic go here
}
}

我用 Spy++ 检查过,仍然有一个 PrintDialog 窗口。 PrintDialog 窗口的父窗口句柄与 Form1 的 句柄完全相同。

谁能帮我从它的父窗口获取PrintDialog 的句柄?

最佳答案

问题是 PrintDialog 的底层窗口是在 ShowDialog 方法执行期间创建的。它在调用此方法之前不存在,这就是您找不到窗口的原因。因此,您必须将您对 PrintDialog 句柄的工作注入(inject)到 ShowDialog 中。这可以在 Control.BeginInvoke 方法的帮助下实现:

public partial class Form1 : Form
{
...

private ShowPrintDialog()
{
using (var pd = new PrintDialog())
{
BeginInvoke(new MethodInvoker(TweakPrintDialog));
if (pd.ShowDialog(this) == DialogResult.OK)
{
// printing
}
}
}

private void TweakPrintDialog()
{
var printDialogHandle = GetActiveWindow();
// do your tweaking here
}

[DllImport("user32.dll", SetLastError = true)]
private static extern IntPtr GetActiveWindow();
}

另一个问题是找到PrintDialog 窗口。 GetActiveWindow 确实是实现此目的的一种直接方法,因为在 ShowDialog 运行时对话框应该处于事件状态。更可靠的解决方案可能包括枚举顶级窗口并分析其所有者和/或其他 Prop 。这是一种可能的方法,假设打印对话框是目前唯一由表单拥有的窗口。修改了前面代码段中的 TweakPrintDialog 方法:

    private void TweakPrintDialog()
{
uint processId;
var threadId = GetWindowThreadProcessId(this.Handle, out processId);
EnumThreadWindows(threadId, FindPrintDialog, IntPtr.Zero);
// printDialogHandle field now contains the found handle
// do your tweaking here
}

private IntPtr printDialogHandle;

private bool FindPrintDialog(IntPtr handle, IntPtr lParam)
{
if (GetWindow(handle, GW_OWNER) == this.Handle)
{
printDialogHandle = handle;
return false;
}
else
{
return true;
}
}

[DllImport("user32.dll", SetLastError = true)]
private static extern uint GetWindowThreadProcessId(IntPtr hWnd, out uint lpdwProcessId);

private delegate bool EnumWindowProc(IntPtr handle, IntPtr lParam);

[DllImport("user32.dll", SetLastError = true)]
private static extern bool EnumThreadWindows(uint threadId, EnumWindowProc enumProc, IntPtr lParam);

private const uint GW_OWNER = 4;

[DllImport("user32.dll", SetLastError = true)]
private static extern IntPtr GetWindow(IntPtr handle, uint cmd);

关于c# - 获取 PrintDialog 的模态对话框句柄,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22360213/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com