x
This website is using cookies. We use cookies to ensure that we give you the best experience on our website. More info. That's Fine
HPC:Factor Logo 
 
Latest Forum Activity

How do I call a desktop wallpaper update?

1 2
I dunk for bananas Page Icon Posted 2023-02-18 9:04 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
I'm having a startup application write the registry key that defines a certain wallpaper, but it evidently happens too late, as only the default wallpaper loads. Right clicking the desktop and selecting "properties" shows though that the change was registered, it just wasn't applied. Clicking "ok" applies it.

Is there a way to call for this update manually?
 Top of the page
C:Amie Page Icon Posted 2023-02-18 9:28 PM
#
Avatar image of C:Amie
Administrator
H/PC Oracle

Posts:
17,955
Location:
United Kingdom
Status:
 Top of the page
I dunk for bananas Page Icon Posted 2023-02-18 10:32 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
Thank you! Does anyone know how this could possible be called from an eVB application?
 Top of the page
C:Amie Page Icon Posted 2023-02-18 10:53 PM
#
Avatar image of C:Amie
Administrator
H/PC Oracle

Posts:
17,955
Location:
United Kingdom
Status:
You'll have to try and import its dispatch function from (probably) coredll

 
Public Const HWND_BROADCAST As Long = &HFFFF& 
Public Const WM_SETTINGCHANGE As Long = &H1A

Public Declare Function PostMessage Lib "coredll" _
Alias "PostMessageA" _
(ByVal hwnd As Long, _
ByVal wMsg As Long, _
ByVal wParam As Long, _
lParam As Any) As Long

Call PostMessage(HWND_BROADCAST, WM_SETTINGCHANGE, 0&, ByVal 0&)
 Top of the page
I dunk for bananas Page Icon Posted 2023-03-18 5:01 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
I wasn't able to get it to work at all unfortunately.. Do you know how I would call for that in C#? I apologize for asking again, I'm not that good with coding yet
 Top of the page
WinCEDev Page Icon Posted 2023-03-18 6:13 PM
#
Avatar image of WinCEDev
Factor Fanatic

Posts:
70
Location:
Europe
Status:
Hi,

I think there are some small errors in C:Amie's function declaration that may prevent it from working.
I modified a couple of things, could you try it again with this code?
Public Const HWND_BROADCAST As Long = &HFFFF&    
Public Const WM_SETTINGCHANGE As Long = &H1A    

Public Declare Function PostMessage Lib "coredll" _
Alias "PostMessageW" _
(ByVal hwnd As Long, _
ByVal wMsg As Long, _
ByVal wParam As Long, _
ByVal lParam As Long) As Long

Call PostMessage(HWND_BROADCAST, WM_SETTINGCHANGE, 0&, 0&)

To explain what I changed: Windows CE only contains 'wide' (unicode) versions of the Win32 API functions, so you would have to use PostMessageW instead of PostMessageA. Also eVB does not support inline ByVal or declaring API function arguments 'As Any'. The way I modified the declaration is technically not really correct (lParam should actually be ByRef and isn't always a Long) but it should do the job in this case since we're not using it anyway. Just don't use this declaration for code where lParam is actually needed or it will not work. I like to prefix API declarations with the name of the module or form they're in so that I can modify them for each particular situation. (On the desktop version of VB, the ability to declare 'As Any' avoids this situation).

If you can't get it to work I would be more than happy to look at your code.

Edited by WinCEDev 2023-03-18 6:15 PM
 Top of the page
I dunk for bananas Page Icon Posted 2023-03-18 11:33 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
Thank you! How would I get this code to work? If I just paste it in the editor, it tells me that it's missing a startup object
 Top of the page
WinCEDev Page Icon Posted 2023-03-19 12:06 AM
#
Avatar image of WinCEDev
Factor Fanatic

Posts:
70
Location:
Europe
Status:
That message means that eVB does not know where the entry point of your program is, this is where the runtime starts executing your code when someone runs your application.
If you get this message then I think you selected a formless project from the new project dialog, and you currently just have a module added to the project.

In that case, you can just add a Sub called Main to the module, and add the PostMessage line in it, the other code can remain outside of that function.
So something like this:
 
Private Const HWND_BROADCAST   As Long = &HFFFF 
Private Const WM_SETTINGCHANGE As Long = &H1A

Public Declare Function PostMessage _
Lib "coredll" _
Alias "PostMessageW" (ByVal hwnd As Long, _
ByVal wMsg As Long, _
ByVal wParam As Long, _
ByVal lParam As Long) As Long

Private Sub Main()
Call PostMessage(HWND_BROADCAST, WM_SETTINGCHANGE, 0, 0)
End Sub

I made a couple more adjustments to the code, the above example runs in the emulator for me.
You should be able to modify the registry value before you broadcast WM_SETTINGCHANGE and that should update the wallpaper.

Edited by WinCEDev 2023-03-19 12:19 AM
 Top of the page
C:Amie Page Icon Posted 2023-03-19 10:11 AM
#
Avatar image of C:Amie
Administrator
H/PC Oracle

Posts:
17,955
Location:
United Kingdom
Status:
Oh yeah, I've typed PostMessageA haven't I
 Top of the page
I dunk for bananas Page Icon Posted 2023-03-19 11:25 AM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
Thank you!! The code compiles, though it doesn't work in updating the desktop It just momentarily shows the hourglass cursor, but nothing else seems to happen
What could be causing this?

Edited by I dunk for bananas 2023-03-19 11:32 AM
 Top of the page
I dunk for bananas Page Icon Posted 2023-03-19 1:33 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
I also just found another annoying thing:
When I set the new wallpaper in the registry, it will show the little preview of it in the wallpaper properties window, but clicking OK doesn't update it, nothing happens. If I manually select that exact same image file with the wallpaper properties application and click OK it updates just fine

I also found this (you have to copy/paste the URL for it to work: https://learn.microsoft.com/en-us/previous-versions/ms942638(v=msdn.10) ) , which seems to include a specific function to change the wallpaper (SPI_SETDESKWALLPAPER), perhaps this is what we want?

Edit: I tried it, but absolutely nothing happens when I run this code, no error messages or anything:

Private Const SPI_SETDESKWALLPAPER As Long = 20 
Public Declare Function SystemParametersInfo _ 
Lib "coredll" (ByVal uiAction As Long, _
ByVal uiParam As Long, _
ByVal pvParam As Long, _
ByVal fWinIni As Long) As Long
Private Sub Main()
Call SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, "\test.bmp", 0)
End Sub




Edited by I dunk for bananas 2023-03-19 2:17 PM
 Top of the page
I dunk for bananas Page Icon Posted 2023-03-19 2:44 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
I've changed pvParam to String, but there's still nothing happening
 Top of the page
WinCEDev Page Icon Posted 2023-03-19 3:38 PM
#
Avatar image of WinCEDev
Factor Fanatic

Posts:
70
Location:
Europe
Status:
I have made a little bit of progress, though nothing functional so far.

I noticed PostMessage was returning 0 indicating an error condition, though in the emulator calling GetLastError does not really seem to work, and on my Jornada it always seems to return 120 (ERROR_CALL_NOT_IMPLEMENTED). However I think this is just one of eVB's many oddities as I have gotten back 120 many times where the function call actually succeeded in other scenarios.

So I set up a test project in desktop VB6 to see if I could at least get it to work there. PostMessage still returned 0, this time GetLastError returned 1159 (ERROR_MESSAGE_SYNC_ONLY) or "The message can be used only with synchronous operations.". On desktop Windows, using SendMessage seems to work, and matches the documentation (Microsoft says to use SendMessageTimeout but that doesn't exist on CE 2.11).

Unfortunately, even when trying with SendMessage it still does not work on Windows CE.

On a side note, the reason why PostMessage is preferable with HWND_BROADCAST is because SendMessage will lock up your application if one of the other applications on the system is not responding.

I also tried to send the message directly to the desktop window, but then found that GetDesktopWindow is documented on MSDN but not actually exported from Coredll, at least not on CE 2.11.

Out of interest, what device and Windows CE version are you testing on? MSDN says that SPI_SETDESKWALLPAPER is only supported on Windows CE 2.12 and higher. I only have CE 2.11 and older to test on so I don't think I can verify if this works. I could try it on my Compaq iPAQ H3970 with Pocket PC 2002 (CE 3.0) though since there is no 'desktop' in the traditional sense on Pocket PC I don't know if that is a reliable test subject.

Edited by WinCEDev 2023-03-19 3:41 PM
 Top of the page
I dunk for bananas Page Icon Posted 2023-03-19 3:43 PM
#
Avatar image of I dunk for bananas
H/PC Elite

Posts:
686
Location:
Europe
Status:
I'm on CE 5, it's an older TV receiver!
I've been trying to implement it in C# in the meantime and I've had no success either
 Top of the page
WinCEDev Page Icon Posted 2023-03-19 4:15 PM
#
Avatar image of WinCEDev
Factor Fanatic

Posts:
70
Location:
Europe
Status:
Could you try to run the below code and tell me the result for each test? I'm not sure what we should actually be entering for fWinIni but this should hopefully shed some light on what might be going wrong.

 
Private Const SPI_SETDESKWALLPAPER As Long = 20 

Private Const SPIF_UPDATEINIFILE As Integer = &H1

Private Const SPIF_SENDCHANGE As Integer = &H2

Public Declare Function SystemParametersInfo _
Lib "Coredll" (ByVal uiAction As Long, _
ByVal uiParam As Long, _
ByVal pvParam As String, _
ByVal fWinIni As Long) As Long

Public Declare Function GetLastError Lib "Coredll" () As Long

Private Sub Main()

Dim lngResult As Long

lngResult = SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, "\test.bmp", 0)

MsgBox "Test 1:" & vbNewLine & vbNewLine & "Return value: " & lngResult & vbNewLine & "GetLastError: " & GetLastError

lngResult = SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, "\test.bmp", SPIF_UPDATEINIFILE)

MsgBox "Test 2:" & vbNewLine & vbNewLine & "Return value: " & lngResult & vbNewLine & "GetLastError: " & GetLastError

lngResult = SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, "\test.bmp", SPIF_SENDCHANGE)

MsgBox "Test 3:" & vbNewLine & vbNewLine & "Return value: " & lngResult & vbNewLine & "GetLastError: " & GetLastError

lngResult = SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, "\test.bmp", SPIF_UPDATEINIFILE Or SPIF_SENDCHANGE)

MsgBox "Test 4:" & vbNewLine & vbNewLine & "Return value: " & lngResult & vbNewLine & "GetLastError: " & GetLastError

End Sub
 Top of the page
1 2
Jump to forum:
Seconds to generate: 0.218 - Cached queries : 72 - Executed queries : 9