It's been 2 years since I last did any programming or contributed to this forum I'm back with a question I hope someone can help me with.
I have an app written in MFC which can be run by multiple users logged into XP. I need to add some event handling so that when one user switches to another, the app is effectively "paused" for the user until their account is switched back to.
I can handle the "pause" part, I just need to know how my app can know that the account under which it is running is not the active desktop account.
which appears to be a terminal server sdk function which will cause the message WM_WTSSESSION_CHANGE to be sent as a callback to the window with the hWnd specified above. All well and good, and probably just the ticket. Problem is, it requires _WIN32_WINNT 0x0501 to compile, and my app is set to 0x0400 because it is to run on 98 and 2k also.
So, I need some other way to detect user switching in an MFC app, that will compile on an xp system in vs2003, but will still run on a 98/2k system.
Thanks a lot for your suggestions.
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
All well and good, and probably just the ticket. Problem is, it requires _WIN32_WINNT 0x0501 to compile, and my app is set to 0x0400 because it is to run on 98 and 2k also.
So, I need some other way to detect user switching in an MFC app, that will compile on an xp system in vs2003, but will still run on a 98/2k system.
Do you really think it might be other way to detect? The way to detect remains the same, but the way to compile must be different. I think it should be explicit WTSRegisterSessionNotification resolving by LoadLibrary("wtsapi32.dll")+GetProcAddress(..., "WTSRegisterSessionNotification").
In case you don't find wtsapi32.dll you may be sure it's no user switching present in system.
End explicit function address resolution never could stop your compile with 0x0400 version specified.
other way you can consider is to listen to WM_ENDSESSION to detect logoff now at that point you can check the current logged user using the ::GetUserName(..) and start a timer or thread that start to check if the user name has changed and when it is you can stop the pausing of your app.
i now its not perfect idea but since you cant use WM_WTSSESSION_CHANGE i cant think of someting else in the moment.
Cheers
If a post helped you dont forget to "Rate This Post"
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
other way you can consider is to listen to WM_ENDSESSION to detect logoff now at that point you can check the current logged user using the ::GetUserName(..) and start a timer or thread that start to check if the user name has changed and when it is you can stop the pausing of your app.
i now its not perfect idea but since you cant use WM_WTSSESSION_CHANGE i cant think of someting else in the moment.
Cheers
Thanks for the suggestion. I'll look into this ...
<revisited>
... actually, this won't work i don't think. Switching a user doesnt cause a WM_ENDSESSION, these apps remain running in memory so no logging off is done. If the user logs off, my app exits, so no problem anyway.
It's specifically switch user i need to cater for.
Last edited by jase jennings; January 2nd, 2006 at 05:21 PM.
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
Do you really think it might be other way to detect? The way to detect remains the same, but the way to compile must be different. I think it should be explicit WTSRegisterSessionNotification resolving by LoadLibrary("wtsapi32.dll")+GetProcAddress(..., "WTSRegisterSessionNotification").
In case you don't find wtsapi32.dll you may be sure it's no user switching present in system.
End explicit function address resolution never could stop your compile with 0x0400 version specified.
Thanks for this idea. Like I said, it's been 2 years since I sat down in front of Visual Studio and coded, and my knowledge is rusty to the say the least. I hadn't even considered using LoadLibrary. It's a good idea, I'll try it ..
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
Thanks for this idea. Like I said, it's been 2 years since I sat down in front of Visual Studio and coded, and my knowledge is rusty to the say the least. I hadn't even considered using LoadLibrary. It's a good idea, I'll try it ..
Sorry Igor. I am struggling with GetProcAddress(). It's been such a long time ...
I cannot work out the rest of the code required here :
Code:
m_hInstWtsapi32 = LoadLibrary("wtsapi32.dll");
if(m_hInstWtsapi32!=NULL)
{
// switch user available (windows terminal services)
???? = GetProcAddress(m_hInstWtsapi32, "WTSRegisterSessionNotification").
}
I can't figure the data type to declare which will be returned by GetProcAddress(), and I've no idea how I will then call the function and make provision for handling the message callback this way.
I'll need some more help with the syntax, or I'm right back to looking for an alternative method.
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
Sorry Igor. I am struggling with GetProcAddress(). It's been such a long time ...
I cannot work out the rest of the code required here :
Code:
m_hInstWtsapi32 = LoadLibrary("wtsapi32.dll");
if(m_hInstWtsapi32!=NULL)
{
// switch user available (windows terminal services)
???? = GetProcAddress(m_hInstWtsapi32, "WTSRegisterSessionNotification").
}
I can't figure the data type to declare which will be returned by GetProcAddress(), and I've no idea how I will then call the function and make provision for handling the message callback this way.
I'll need some more help with the syntax, or I'm right back to looking for an alternative method.
Thanks a lot for that code, I'm please you posted it because I did manage to put something together and I'm relieved to see that your code is very similar to mine I shall use yours though, as my typedef was a little different and possibly wrong ...
Getting back to the problem though, I am still unable to compile without setting _WIN32_WINNT to 0x0501, as the message WM_WTSESSION_CHANGE is unavailable without it.
I then DoModal() on my apps main dialog. The dialog has the following message handler :
Code:
// in the .h message map
afx_msg LRESULT OnWTSessionChange(WPARAM wParam, LPARAM lParam);
// in the .cpp message map
ON_MESSAGE(0x02b1, OnWTSessionChange)//WM_WTSSESSION_CHANGE
// the actual handler
LRESULT CMyDlg::OnWTSessionChange(WPARAM wParam, LPARAM lParam)
{
AfxMessageBox("OnWTSessionChange");
return 1;
}
This handler never gets called. Can you see what I'm doing wrong?
Thanks for your continued help, much appreciated.
Last edited by jase jennings; January 3rd, 2006 at 06:43 AM.
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
I don't know what GetMainWnd() is . But I just copied and pasted your code and replaced it with:
WTSRegisterSessionNotification(GetSafeHwnd(),NOTIFY_FOR_THIS_SESSION);
I don't know what GetMainWnd() is . But I just copied and pasted your code and replaced it with:
WTSRegisterSessionNotification(GetSafeHwnd(),NOTIFY_FOR_THIS_SESSION);
I see the message box, no prblem
Well, I'm doing the LoadLibrary stuff and setting up the call back from my CWinApp derived class, so i can't use GetSafeHwnd() ...
I take it you are doing this within your CWnd derived class?
Could you tell me where you are doing the LoadLibrary() & WTSRegisterSessionNotification() calls please?
Thanks
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
Here is my dialog class.
As you see:
1. To keep matters simple, am not doing a loadlibrary, instead calling API directly. That shouldn't be an issue in any case, unless loadlibrary is failing for some reason on your machine.
2. I use GetSafeHwnd() in OnInitDialog. I don't know why you cannot use GetSafeHwnd(). Anyways, my first suspicion is that the HWND supplied to the WTS API is not a valid one ( possibly NULL ). So, why don't you try in 2 steps, first get HWND in whatever way you think of, and then pass it to WST API. Note that since you are handling the WM_WTSSESSION message in your dialog class, the HWND passed to the WTS registration API also has to be the HWND of your dialog object ( which again should be same as one returned by GetSafeHwnd() or by accessing the protected member m_hWnd)
I put the code in my dialogs InitDialog and now it all works nicely.
The documentation I had been reading suggested that the code should be place in InitInstance(), therefore in the CWinApp derived class.
The kb I was reading was specifically talking about the Windows SDK however, and not MFC.
Many thanks for trying this for me and helping me solve the problem (of my own making
Thanks
Jase
www.slideshowdesktop.com
View your images and photos on your desktop with ease using SlideShow Desktop, the desktop wallpaper manager for Microsoft Windows....
* The Best Reasons to Target Windows 8
Learn some of the best reasons why you should seriously consider bringing your Android mobile development expertise to bear on the Windows 8 platform.