2013-08-19 7 views
1

Я не могу заставить PeekMessage работать. На самом деле я бы ожидал, что он наполнит меня сообщениями, но это возвращаемое значение равно 0.WinApi - PeekMessage Всегда возвращает False

Я использую WinForm, запускаю фоновый поток, который просматривает сообщения и использует окно с помощью мыши. Окно можно использовать как всегда, но сообщения не могут быть просмотрены. Что я делаю не так ? Последняя ошибка - 0 все время.

[StructLayout(LayoutKind.Sequential)] 
public struct NativeMessage 
{ 
    public IntPtr handle; 
    public uint msg; 
    public IntPtr wParam; 
    public IntPtr lParam; 
    public uint time; 
    public Point p; 
    public override string ToString() 
    { 
     return handle + ", " + msg + ", " + wParam + ", " + lParam + ", " + time + ", " + p; 
    } 
} 

[DllImport("user32.dll")] 
public static extern int PeekMessage(out NativeMessage lpMsg, IntPtr window, uint wMsgFilterMin, uint wMsgFilterMax, uint wRemoveMsg); 

public Form1() 
{ 
    ThreadPool.QueueUserWorkItem(o => run()); 
} 

private void run() 
{ 
    for (int i = 0; i < 1000000;) 
    { 
     NativeMessage a = new NativeMessage(); 
     int c = PeekMessage(out a, IntPtr.Zero, (uint) 0, (uint) 0, (uint) 0); 
     if (c != 0) 
      trace(" -> " + c); // prints strings 
    } 
} 

Решено:

  • Я назвал Show() в главном потоке, чтобы показать, что моя форма
  • и перенаправил основной поток для входа сообщений
  • (не XY проблема, мне нужно PeekMessage работать или, по крайней мере, понимать, как его использовать)

(спасибо за показывая мне ошибку, я сделал)

+0

Основываясь на вашем коде, вы не создаете окно в этом потоке. Почему вы ожидаете каких-либо сообщений в очереди потока? – Noseratio

+0

@Noseratio Нет необходимости в потоке владеть любыми окнами для получения сообщений. В конце концов есть ['PostThreadMessage'] (http://msdn.microsoft.com/en-us/library/windows/desktop/ms644946.aspx). – IInspectable

+0

@Inpectable, я не вижу ничего в коде выше. Вот почему я спросил, почему OP ожидает поток сообщений. – Noseratio

ответ

1

очереди окна сообщений являются для каждого потока, если не связан каким-либо образом (AttachThreadInput, окна родительского отношения ...)

4

При передаче NULL (т.е. 0) для параметра hWnd, функция PeekMessage извлекает сообщения потоков и сообщения для любого окна, принадлежащего текущему потоку. Это называется в явном виде в the documentation:

HWND [в, по выбору]

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

Если HWND является NULL, PeekMessage извлекает сообщения для любого окна, которое принадлежит текущему потоку, и все сообщения по очереди сообщений текущего потока которого HWND значения NULL (см MSG структуру). Поэтому, если hWnd - NULL, обрабатываются как оконные сообщения, так и сообщения потоков.

Поскольку вы вызываете эту функцию в новом потоке в ThreadPool, нет никаких сообщений для его извлечения. Этот поток не связан ни с одним окном и не имеет сообщений.

Функция возвращает FALSE (т. Е. 0), когда сообщений нет.

Если вы звоните PeekMessage в основной поток пользовательского интерфейса (тот, который связан с вашей формой), вы получите быстрый просмотр всех сообщений, предназначенных для вашего окна формы.

+0

Ну, я действительно прочитал эту заметку о потоке, но поскольку у каждого окна есть собственный поток, я был смущен тем, как 1 поток может заглядывать в сообщения других окон, как указано в примечании к параметру. И я просто хочу регистрировать все сообщения через PeekMessage и позволять им переводить сам API. – Bitterblue

+0

@mini В каждом окне есть * not * есть своя нить. Фактически, общая ситуация почти точно противоположна: каждое окно работает на * одном * потоке; он называется потоком пользовательского интерфейса. И чтобы ответить на ваш другой вопрос, поток может просматривать сообщения других окон, передавая в ручку интересующего окна. –

+1

PeekMessage не является хорошим механизмом регистрации, конечно, не тем, как вы его используете. Есть лучшие способы сделать это, но это совершенно другой вопрос. Я бы ответил на это, если бы вы спросили об этом. Остерегайтесь [проблемы XY] (http://meta.stackexchange.com/questions/66377/what-is-the-xy-problem). –