1. Focus problem in win32 program

I'm having a problem with a program I'm working on where I seem to be losing focus on my window. I've put together a sample program which illustrates the problem.

This program simply reports keys typed and mouse position when a key is typed or the mouse is clicked. There is a button that simply reports that it has been clicked when activated.

The problem is that once I click on the button I cannot get the keyboard input anymore. The mouse monitoring still works. If I use Alt-F I can still get to the menu (the menus don't actually do anything, they are just there to show that this access still exists).

It appears to me that my focus has shifted to the button rather than the whole window and it isn't clear to me what I need to do to restore focus to the window so that my keystroke processing will work. I've tried using setFocus(Win) (as the code shows) but that doesn't seem to make any difference.

Any suggestions appreciated.

Note that this is code excerpted from my JoKoSoKo program which was originally written years ago. It could be that new functionality has been added to Win32lib which would work better than what I've used. If anyone has suggestions for better ways to access the keyboard I'd be willing to listen, but if it involves radically altering my key stroke processing in the program, I'm not too sure how much I want to change unless I have to.

I'm using the beta Euphoria and version V0.70.8 15/Mar/2009 of win32lib (from the changes file in the include directory)

include Win32Lib.ew without warning

atom winWidth, winHeight winWidth = 800 winHeight = 600 sequence winSettings winSettings = {} atom result result = 0 constant X = 2 constant Y = 1

constant Win = create( Window, "JoKoSoko", 0, Default, Default, winWidth, winHeight, 0 ),

The menus FileMenu = create( Menu, "&File", Win, 0, 0, 0, 0, 0 ), MenuOpen = create( MenuItem, "&Load (^L)", FileMenu, 0, 0, 0, 0, 0 ), myButton = create(PushButton,"Button", Win,582,0,75,28,0 )

procedure Paint( integer iD_,integer evenT_,sequence paramS_ )

winSettings = getSize( Win ) winHeight = winSettings[4] - winSettings[2] winWidth = winSettings[3] - winSettings[1]

end procedure

setHandler( Win , w32HPaint, {-1, routine_id("Paint")})


procedure onClick_myButton( integer iD_,integer evenT_,sequence paramS_ ) result = message_box( "You clicked my button!", "onClick_myButton", 0 )

setFocus(Win) end procedure

setHandler( myButton , w32HClick, {-1, routine_id( "onClick_myButton" )})


procedure winMouse( integer iD_,integer evenT_,sequence paramS_ ) integer event, x, y, shift event = paramS_[1] x = paramS_[2] y = paramS_[3] shift = paramS_[4]

if event=LeftDown then result = message_box( sprintf("You left-clicked at (%d,%d)!",{x,y}), "winMouse", 0 )

elsif event=RightDown then result = message_box( sprintf("You right-clicked at (%d,%d)!",{x,y}), "winMouse", 0 )

end if

end procedure

setHandler( Win , w32HMouse, {-1, routine_id( "winMouse" )})


procedure keyPressProcessing( integer iD_,integer evenT_,sequence paramS_ )

atom keyCode atom shift

keyCode = paramS_[1] shift = paramS_[2]

result=message_box(sprintf("You typed key %d while shift was %d!",{keyCode,shift}), "keyPressProcessing", 0 ) end procedure

setHandler( Win , w32HKeyPress, {-1, routine_id( "keyPressProcessing" )})


WinMain( Win, Normal )

new topic     » topic index » view message » categorize

2. Re: Focus problem in win32 program

OK, I've read some more win32lib docs and found getFocus(). Using that I've modified my message boxes to show which ID has focus at the time of the message box.

Starting out all key strokes and mouse clicks showed ID 3 with the focus. When I clicked on the button it changed to ID 15. I tried to modify my windows paint routine (something I felt was likely to get called) such that if it noticed that the focus ID changed from its initial value it would use setFocus to change it back. This has not helped except that I can see the focusID has changed after I click on the button.

Again, any suggestions welcomed.

Here is my modified example code:

include Win32Lib.ew 
 without warning 
 
atom     winWidth,             winHeight              
         winWidth    = 800     winHeight      = 600    
sequence winSettings 
	 winSettings = {} 
atom	result 
	result = 0 
integer focusID 
        focusID = 0 
 
constant X = 2 
constant Y = 1 
 
constant Win =   
    create( Window, "Focus Problem Example", 0, Default, Default, winWidth, winHeight, 0 ), 
 
-- The menus 
    FileMenu  = create( Menu,     "&File",           Win,      0, 0, 0, 0, 0 ), 
    MenuOpen  = create( MenuItem, "&Load (^L)",      FileMenu, 0, 0, 0, 0, 0 ), 
    myButton   = create(PushButton,"Button",    Win,582,0,75,28,0 ) 
 
procedure Paint( integer iD_,integer evenT_,sequence paramS_ ) 
 
  integer localFocusID 
 
  if focusID = 0 then 
    -- the initial condition 
    focusID = getFocus() 
  end if 
  
  winSettings = getSize( Win ) 
  winHeight = winSettings[4] - winSettings[2] 
  winWidth  = winSettings[3] - winSettings[1] 
   
    localFocusID = getFocus() 
    if localFocusID != focusID then 
      setFocus(focusID) 
    end if 
 
end procedure 
 
setHandler( Win , w32HPaint, {-1, routine_id("Paint")}) 
 
---------------------------------------- 
 
procedure onClick_myButton( integer iD_,integer evenT_,sequence paramS_ ) 
 
      integer localFocusID 
 
      localFocusID = getFocus() 
      result = message_box( sprintf("You clicked my button! ID %d has focus.",{localFocusID}), 
                        "onClick_myButton", 0 ) 
 
end procedure 
 
setHandler( myButton , w32HClick, {-1, routine_id( "onClick_myButton" )}) 
 
---------------------------------------- 
 
procedure winMouse( integer iD_,integer evenT_,sequence paramS_ ) 
 
    integer event, x, y, shift 
    event = paramS_[1] 
    x     = paramS_[2] 
    y     = paramS_[3] 
    shift = paramS_[4] 
    integer localFocusID 
 
    localFocusID = getFocus() 
    if event=LeftDown then 
      result = message_box( sprintf("You left-clicked at (%d,%d)! ID %d has focus.",{x,y,localFocusID}), 
                        "winMouse", 0 ) 
 
    elsif event=RightDown then 
      result = message_box( sprintf("You right-clicked at (%d,%d)!",{x,y}), 
                        "winMouse", 0 ) 
 
    end if 
 
    localFocusID = getFocus() 
    if localFocusID != focusID then 
      setFocus(focusID) 
    end if 
 
end procedure 
    
setHandler( Win , w32HMouse, {-1, routine_id( "winMouse" )}) 
 
----------------------------------------------------------------------------- 
 
procedure keyPressProcessing( integer iD_,integer evenT_,sequence paramS_ ) 
 
  integer keyCode 
  integer shift 
  integer localFocusID 
   
  keyCode = paramS_[1] 
  shift   = paramS_[2] 
 
  localFocusID = getFocus() 
  result=message_box(sprintf("You typed key %d while shift was %d! id %d has focus", 
			     {keyCode,shift,localFocusID}), 
                        "keyPressProcessing", 0 ) 
end procedure 
 
setHandler( Win , w32HKeyPress, {-1, routine_id( "keyPressProcessing" )}) 
 
------------------------------------------- 
 
WinMain( Win, Normal ) 
 
 
 
new topic     » goto parent     » topic index » view message » categorize

3. Re: Focus problem in win32 program

OK. I played around with it some more and found the reference to the GotFocus event. So I created a new procedure which sets the focus when that event occurs. This seems a little goofy. After all, the event occurs when the focus is set (in this case to ID 3). Within the procedure which handles the w32HGotFocus I then have to use set the focus to the correct ID. I tried it without actually updating the focus within the handling code and the program worked as previously described. So apparently, after the event occurs when the focus is set to the window's ID, I can have some code that notices that the event occurs, and within that code I have to set the focus to the window's ID to make it stick.

Whatever. I think I've got it working.

new topic     » goto parent     » topic index » view message » categorize

4. Re: Focus problem in win32 program

JoKeR said...

I'm having a problem with a program I'm working on where I seem to be losing focus on my window...

I think there is a bug in the focus setting logic when it comes to Windows. As a workaround, try using this handler instead ...

setHandler( Screen , w32HKeyPress, routine_id( "keyPressProcessing" )) 


This will cause every key press to trigger the handler, regardless of which control has focus.

new topic     » goto parent     » topic index » view message » categorize

5. Re: Focus problem in win32 program

Thanks. I'll give it a try. Do you think this is a Windows problem or a win32lib problem?

new topic     » goto parent     » topic index » view message » categorize

6. Re: Focus problem in win32 program

JoKeR said...

Thanks. I'll give it a try. Do you think this is a Windows problem or a win32lib problem?

The bug is in win32lib. Basically, when using setFocus() on the window itself, it actually sets focus to one of its controls in the instead.

new topic     » goto parent     » topic index » view message » categorize

7. Re: Focus problem in win32 program

This seems to fix it. I found in my code that I am using both keyPressProcessing and keyDownProcessing (though I'd have to look at it closer to remember why and what the difference is) so I had to change both from references to Win (my window definition) to Screen.

Thanks for your help!

new topic     » goto parent     » topic index » view message » categorize

Search



Quick Links

User menu

Not signed in.

Misc Menu