Как найти неизвестное окно и передать туда сообщение?

Программирование на Visual Basic, главный форум. Обсуждение тем программирования на VB 1—6.
Даже если вы плохо разбираетесь в VB и программировании вообще — тут вам помогут. В разумных пределах, конечно.
Правила форума
Темы, в которых будет сначала написано «что нужно сделать», а затем просьба «помогите», будут закрыты.
Читайте требования к создаваемым темам.
arthur2
Продвинутый гуру
Продвинутый гуру
Аватара пользователя
 
Сообщения: 1688
Зарегистрирован: 23.01.2008 (Ср) 14:35

Как найти неизвестное окно и передать туда сообщение?

Сообщение arthur2 » 20.12.2008 (Сб) 15:30

Задача, собственно, в следующем: мне нужно посылать сообщение WM_CHAR тому окну, которое было активно до моей проги.

Как найти то окно, которое поле ввода внутри окна верхнего уровня? Активное окно я найду, а как внутри него найти то место, где текстовый курсор, если вообще неизвестно заранее, ни какого он класса, ни ещё чего

Пока ищу просто окно из под курсора:
Код: Выделить всё
Option Explicit
Private Declare Function SendMessage Lib "user32" Alias "SendMessageW" (ByVal hwnd As Long, ByVal wMsg As Long, ByVal wParam As Long, lParam As Any) As Long
Private Declare Function WindowFromPoint Lib "user32" (ByVal xPoint As Long, ByVal yPoint As Long) As Long
Private Declare Function GetCursorPos Lib "user32" (lpPoint As POINTAPI) As Long

Private Type POINTAPI
    X As Long
    Y As Long
End Type

Private Declare Function GetForegroundWindow Lib "user32" () As Long

Const WM_CHAR = &H102

Dim hw2 As Long

Private Sub Form_Click()
   
   SendMessage hw2, WM_CHAR, &H3A9, 0 'условно - посылаю в текстовый редактор нужную букву
   
End Sub

Private Sub Form_MouseUp(Button As Integer, Shift As Integer, X As Single, Y As Single)
 
  Dim p As POINTAPI, hw As Long
  GetCursorPos p
  hw = WindowFromPoint(p.X, p.Y)
  If hw <> hwnd Then
    Caption = hw
    hw2 = hw
  End If

End Sub


Но, во-первых, хотелось бы найти автоматически. Ну то есть, получить то окно, в котором был курсор до того, как фокус оказался у меня.

А во-вторых, способ прокатывает на блокноте, но не работает, например, с вордом :(
(или не то окно находится, или оно этого сообщения не принимает)
Артур
 
   

Twister
Теоретик
Теоретик
Аватара пользователя
 
Сообщения: 2251
Зарегистрирован: 28.06.2005 (Вт) 12:32
Откуда: Алматы

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение Twister » 22.12.2008 (Пн) 9:46

Как найти то окно, которое поле ввода внутри окна верхнего уровня?

GetFocus() тебе поможет. Но только если
window is attached to the calling thread's message queue
Punto, к примеру, справляется с этой проблемой внедрением своей dll в АП чужих процессов.

получить то окно, в котором был курсор до того, как фокус оказался у меня
Сразу после того, как твое окно получило фокус, ты можешь найти предыдущее активное - оно следующее в z-ордере. А вот узнать, в каком именно поле был keyboard focus ты не сможешь. Можно лишь следить за изменением фокуса (опять же - dll) и запоминать.
А я все практикую лечение травами...

arthur2
Продвинутый гуру
Продвинутый гуру
Аватара пользователя
 
Сообщения: 1688
Зарегистрирован: 23.01.2008 (Ср) 14:35

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение arthur2 » 22.12.2008 (Пн) 10:13

Twister
да уж... Совсем не хотелось связываться с глобальными хуками, но кажется, придётся?

Собственно, мне нужно одно из двух:

1. Или чтобы фокус был у меня, и тогда нужно посылать WM_CHAR тому полю ввода, которое было активно до меня.

2. Или чтобы фокус бы там где есть, и тогда мне нужно знать, какие клавиши нажимаются.

Блин, кажется, ни то ни другое без внедрения в чужое адресное пространство не получится?

Мне бы даже GetKeyboardState по таймеру подошла бы, не шпиона же пишу, но и она не видит состояние клавиш в чужих окнах :(

А Punto работает в висте?
Артур
 
   

iGrok
Артефакт VBStreets
Артефакт VBStreets
 
Сообщения: 4272
Зарегистрирован: 10.05.2007 (Чт) 16:11
Откуда: Сетевое сознание

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение iGrok » 22.12.2008 (Пн) 11:28

arthur2 писал(а):А Punto работает в висте?

Начиная с какой-то-там версии - да.
label:
cli
jmp label

arthur2
Продвинутый гуру
Продвинутый гуру
Аватара пользователя
 
Сообщения: 1688
Зарегистрирован: 23.01.2008 (Ср) 14:35

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение arthur2 » 22.12.2008 (Пн) 12:05

iGrok
Интересно, как?
Ладно, всё равно "внедрение своей dll в АП чужих процессов" кажется мне задачей почти непреодолимой (а если и преодолимой, то с ненадёжным результатом - по крайней мере, в моём исполнении)

Было бы ништяк, если бы выгорело с DirectX 5. Ведь там состояние клавиш читается для всей системы?
Артур
 
   

tyomitch
Пользователь #1352
Пользователь #1352
Аватара пользователя
 
Сообщения: 12822
Зарегистрирован: 20.10.2002 (Вс) 17:02
Откуда: חיפה

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение tyomitch » 22.12.2008 (Пн) 13:38

arthur2 писал(а):1. Или чтобы фокус был у меня, и тогда нужно посылать WM_CHAR тому полю ввода, которое было активно до меня.

Запросто. GetGUIThreadInfo тебе в руки.
Изображение

arthur2
Продвинутый гуру
Продвинутый гуру
Аватара пользователя
 
Сообщения: 1688
Зарегистрирован: 23.01.2008 (Ср) 14:35

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение arthur2 » 22.12.2008 (Пн) 22:00

tyomitch
Спасибо! Иду разбираться :)
Артур
 
   

arthur2
Продвинутый гуру
Продвинутый гуру
Аватара пользователя
 
Сообщения: 1688
Зарегистрирован: 23.01.2008 (Ср) 14:35

Re: Как найти неизвестное окно и передать туда сообщение?

Сообщение arthur2 » 24.12.2008 (Ср) 11:31

Здорово! Всё получилось! Находит окно с фокусом клавы, в том числе и у ворда... но вот посылать сообщение WM_CHAR получается куда угодно, кроме ворда :( Может, нужно посылать что-то другое? типа кейдауна?


позже:
Бинго!!! вместо SendMessageW поставил PostMessageW, и всё заработало и для ворда!

А возможно, чтобы каретка в чужом неактивном окне не пряталась? было бы вообще здорово
Артур
 
   


Вернуться в Visual Basic 1–6

Кто сейчас на конференции

Сейчас этот форум просматривают: Yandex-бот и гости: 88

    TopList