Необходимо проверить, перекрывается ли окно программы (чужой) другими окнами системы - C#

Узнай цену своей работы

Формулировка задачи:

Необходимо проверить перекрывается ли окно программы(чужой), другими окнами системы. План таков. 1. Перечислить все поверхностные окна системы 2. Получить hwnd перечисленных окон 3. Получить координаты используя GetWindowRect 4. Перевести координаты в переменные Rectagle 5. Использовать Rectagle.Contains для определения перекрытия. Я не уверен что выбрал правильное решение. Оно мне кажется очень громоздким. Жду любой помощи, спасибо.
Нашёл вот такое дело на делфи. может кто поможет на шарп переложить
// Это - главная функция. На входе - хэндл проверяемого окна,
// на выходе - перекрыто оно другими (True), или нет (False).
function IsWindowOverlapped(Wnd: HWND): boolean;
var
 OldWnd: HWND;
begin
 // Запомним хэндл окна
 OldWnd := Wnd; 
 // И пройдемся по всем окнам верхнего уровня в системе,
 // передав адрес OldWnd, как параметр callback-функции
 EnumWindows(@EnumWindowProc, LParam(@OldWnd));
 // Если OldWnd изменилось, то окно перекрыто
 Result := OldWnd <> Wnd
end;
 
type
PWnd = ^HWND;
 
// Это callback-функция для EnumWindows. Пока она не вернет
// False, перебор окон продолжается. Wnd - хэндл очередного окна, TargetWnd - адрес переменной OldWnd (см. выше)
function EnumWindowProc(Wnd: HWND; TargetWnd: PWnd): BOOL; stdcall;
var
 Rct, TargetRct, OverRct: TRect;
 P: TPoint;
begin
 // Берем прямоугольник окна Wnd и нашего окна
 GetWindowRect(Wnd, Rct);
 GetWindowRect(TargetWnd^, TargetRct); 
 // Проверяем их пересечение
 Result := not IntersectRect(OverRct, Rct, TargetRct); 
 // Если пересекаются, надо выяснить, какое окно сверху
 if not Result then
 begin
  // Берем центр области пересечения
  P.X := (OverRct.Left + OverRct.Right) div 2;
  P.Y := (OverRct.Top + OverRct.Bottom) div 2;
  // И получаем окно верхнего уровня в этой точке
  Wnd := GetTopParent(WindowFromPoint(P));
  // Если это не наше окно, то надо остановить перебор и в
  // переменную OldWnd записать хэндл перекрывающего окна
  Result := Wnd <> TargetWnd^; // Кажется, здесь ошибка, надо =
  if not Result then TargetWnd^ := Wnd
end
end;
 
// Это вспомогательная функция. Если Wnd - это хэндл дочернего
// окна, то дает его родительское окно верхнего уровня, иначе
// дает само это окно
function GetTopParent(Wnd: HWND): HWND;
begin
repeat
  Result := GetParent(Wnd);
  if Result <> 0 then Wnd := Result
until Result = 0;
Result := Wnd
end;
Первый пунк вроде готов.
        public class WindowArray : ArrayList
        {
            private delegate bool EnumWindowsCB(int hwnd, IntPtr param);
 
            [DllImport("user32")]
            private static extern int EnumWindows(EnumWindowsCB cb, IntPtr param);
 
            private static bool MyEnumWindowsCB(int hwnd, IntPtr param)
            {
                GCHandle gch = (GCHandle)param;
                WindowArray itw = (WindowArray)gch.Target;
                itw.Add(hwnd);
                return true;
            }
 
            public WindowArray()
            {
                GCHandle gch = GCHandle.Alloc(this);
                EnumWindowsCB ewcb = new EnumWindowsCB(MyEnumWindowsCB);
                EnumWindows(ewcb, (IntPtr)gch);
                gch.Free();
            }
        }
все же перечисляет он явно больше окон чем реально видимых.
Всё решено кроме непосредственно проверки перекрытия. Я неправильно понял значение Rectagle.Contains. И она не годится для поставленной задачи. Имеем координаты, нужно составить условия что бы сравнить два окна.
IntPtr hw0 = FindWindows.FindWindow("Progman", "Program Manager");
                    EnumWindow.EnumWindows((hWnd, lParam) =>
                    {
                        if (IsWindowVisibles.IsWindowVisible(hWnd) == true && proverkashowhide.IsIconic(hWnd) == false && hwnd != hWnd && hWnd != hw0)
                        {
                            FindWindowRect.RECT RectAllHwnd = new FindWindowRect.RECT();
                            FindWindowRect.GetWindowRect(hWnd, ref RectAllHwnd);
 
                            Rectangle RDC = new Rectangle(RectAllHwnd.Left, RectAllHwnd.Top, RectAllHwnd.Right - RectAllHwnd.Left, RectAllHwnd.Bottom - RectAllHwnd.Top);
 
                            Console.WriteLine(nos);
                            Console.WriteLine(RDC);
 
                            if (nos.Contains(RDC) == true)
                            {
                                Console.WriteLine("true");
                            }
                            else
                            {
                                Console.WriteLine("false");
                            }
                        }
                        return true;
                    }, IntPtr.Zero);
Вроде бы класс получился помогите правильно задать метод что бы возвращались значения true или false
// Класс для проверки на перекрытие
 
using System; // для IntPtr
using System.Drawing; // Для Rectangle
using System.Runtime.InteropServices; // Для импорта API функций
 
namespace ConsoleApplication3
{
    class IsWindowsIntersect
    {
 
        // Функция для проверки видимое ли окно
        [DllImport("user32.dll", CharSet = CharSet.Auto)]
        public static extern bool IsWindowVisible(IntPtr hWnd);
 
        // Функция для проверки не свёрнуто ли окно
        [DllImport("user32.dll")]
        [return: MarshalAs(UnmanagedType.Bool)]
        public static extern bool IsIconic(IntPtr hWnd);
 
        // Функция для поиска дискриптора по классу и имени окна
        [DllImport("USER32.DLL", CharSet = CharSet.Unicode)]
        public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);
 
        // Проверка на перекрытие
        public static bool intersect(IntPtr hwnd)
        {
 
            //Перечисляем все окна системы
            EnumWindow.EnumWindows((HWND, lParam) =>
            {
 
                // Выполняем если окна видимые
                if (IsWindowVisible(HWND) == true)
                {
 
                    // Выполняем если окно не свёрнуто
                    if (IsIconic(HWND) == false)
                    {
 
                        // Выполняем если не наше окно для проверки
                        if (hwnd != HWND)
                        {
 
                            // Выполняем если не окно рабочего стола
                            if (HWND != FindWindow("Progman", "Program Manager"))
                            {

                                FindWindowRect.RECT Recthwnd = new FindWindowRect.RECT();
                                FindWindowRect.GetWindowRect(hwnd, ref Recthwnd);
 
                                FindWindowRect.RECT RectHWND = new FindWindowRect.RECT();
                                FindWindowRect.GetWindowRect(HWND, ref RectHWND);

                                Rectangle rectangle1 = new Rectangle(Recthwnd.Left, Recthwnd.Top, Recthwnd.Right - Recthwnd.Left, Recthwnd.Bottom - Recthwnd.Top);
                                Rectangle rectangle2 = new Rectangle(RectHWND.Left, RectHWND.Top, RectHWND.Right - RectHWND.Left, RectHWND.Bottom - RectHWND.Top);
                                Rectangle rectangle3 = new Rectangle();
 
                                if (rectangle1.IntersectsWith(rectangle2))
                                {
                                    rectangle3 = Rectangle.Intersect(rectangle1, rectangle2);
                                    if (!rectangle3.IsEmpty)
                                    {
                                        Console.WriteLine("Окно перекрыто");
                                        return true;
                                    }
                                }
                            }
                        }
                    }
                }
                return true;
            }
            , IntPtr.Zero);
            Console.WriteLine("Окно не перекрыто");
            return false;
        }
    }
}
public static bool intersect(IntPtr hwnd)
26 строка

Решение задачи: «Необходимо проверить, перекрывается ли окно программы (чужой) другими окнами системы»

textual
Листинг программы
                    int ff = 0;
                    IsWindowsIntersect.Enum(hwnd, ref ff);
                    if (ff == 1)
                    {
                        Console.WriteLine("Окно перекрыто");
                    }
                    else
                    {
                        Console.WriteLine("Окно не перекрыто");
                    }

ИИ поможет Вам:


  • решить любую задачу по программированию
  • объяснить код
  • расставить комментарии в коде
  • и т.д
Попробуйте бесплатно

Оцени полезность:

12   голосов , оценка 4.083 из 5
Похожие ответы