【问题标题】:Read all text from external Application从外部应用程序读取所有文本
【发布时间】:2014-03-21 07:07:46
【问题描述】:

我在 C# 中有一个热键窗口应用程序,我希望在按下热键时其他应用程序的焦点窗口中的所有文本,如记事本、浏览器、命令窗口 (cmd)、Turbo c++、Pascal 等。

那么有可能吗?

如果有人有想法,请帮助我提供代码示例。

我已附上屏幕截图。我想从此窗口阅读文本。按热键时,我想阅读文本“这是我的测试文本”。

【问题讨论】:

  • 没有通用的解决方案,您需要根据具体情况处理每个应用程序。
  • 这可能对您有所帮助。至少它会给你一些方向stackoverflow.com/questions/235972/…
  • 此外,您可能必须递归地深入到子窗口以收集所有文本(结果可能很混乱)。
  • Handle(IntPtr) 我已经有了我想根据那个句柄阅读文本。
  • 请记住存在无窗口控件。也可以绘制文本。应用程序也可以使用子类化或挂钩。

标签: c# .net winapi


【解决方案1】:

user32 API 中有一个GetWindowText(), 但是如果您需要从另一个进程中的控件获取文本,GetWindowText() 将不起作用。

您必须将SendMessage() 与 WM_GETTEXT 一起使用:

const UInt32 WM_GETTEXT = 0x000D;
const UInt32 WM_GETTEXTLENGTH = 0x000E;

[DllImport("user32.dll", CharSet = CharSet.Auto)]
static extern IntPtr SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", CharSet = CharSet.Auto)]
static extern IntPtr SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, StringBuilder lParam);


static string GetWindowTextRaw(IntPtr hwnd)
{
    // Allocate string length 
    int length = (int)SendMessage(hwnd, WM_GETTEXTLENGTH, IntPtr.Zero, IntPtr.Zero);
    StringBuilder sb = new StringBuilder(length + 1);
    // Get window text
    SendMessage(hwnd, WM_GETTEXT, (IntPtr)sb.Capacity, sb);
    return sb.ToString();
}

【讨论】:

  • 感谢您的回答。这个我已经试过了。它适用于记事本、浏览器和许多应用程序,但不适用于命令提示符 (cmd)、Turbo c++、pascal 和任何基于 dos 的屏幕。
  • 我认为没有通用的方法可以做到这一点。顺便说一句,你为什么需要这样做?
  • 我想在按下热键时获取该文本。
  • 为什么不用剪贴板热键CTRL+A、CTRL+C,然后用CTRL+V粘贴呢?
  • 我已经用过了,但它在 Turbo C++、命令提示符(cmd)和所有基于 dos 的屏幕上都不起作用。
【解决方案2】:

自称为“屏幕阅读器”(针对视障人士)的应用程序会做类似的事情。

他们使用旧的 MSSA(Microsoft Active Accessibility)API 和/或新的 UIAutomation API。

使用这两个 API,如果您有一个“主窗口”HWND,那么您可以浏览制作应用程序的组件树。然后您可以检索属性,例如“文本”或“名称”等。

如果应用程序不支持 Accessive 技术,您将依靠个案解决方案,这意味着最终会出现糟糕的 hack(如 API 挂钩)或更常规的方法(如 DLL 注入和在 JAVA 中使用 JNI Invocation API案例)。

【讨论】:

  • @Ashish 的代码示例是什么?你用谷歌还是在 Stackoverflow 上搜索过?
  • 我已经在 Google 和 Stackoverflow 中搜索过,但是在我将它添加到 stackoverflow 之后我无法找到。
  • 当您搜索 UIAutomation 示例时,google 会给出很多结果。你用什么查询,没有结果???
  • 我也得到了很多结果,这些结果只与记事本和基于窗口的应用程序交互,但不与 Turbo c++ 和命令提示符(cmd)交互。
  • 我的问题是我想从 Turbo c++ 和命令提示符 (cmd) 等 dos 基本窗口中获取文本。
【解决方案3】:

这是不能直接通过C#实现的,

微软仍然提供 WMI 服务,可用于获取有关机器和进程的最大信息。请检查MSDN

您可以从here 下载 WMI 工具并可能检查 Win32 类和方法,您可能会找到适合您要求的有用信息

【讨论】:

  • 这不是答案。也许是另一个问题。
猜你喜欢
  • 2011-11-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-09-06
  • 1970-01-01
  • 2012-06-05
  • 1970-01-01
相关资源
最近更新 更多