10

I know that if you run:

rundll32.exe desk.cpl,InstallScreenSaver toasters.scr

you can set the screensaver to toasters.scr but it also opens up the screensaver configuration dialog. Is there a way to set the screensaver on Windows without opening any dialog by running a command?

Pablo Fernandez
  • 279,434
  • 135
  • 377
  • 622
  • 1
    Do you have good intentions or bad intentions? – Andreas Rejbrand Apr 12 '18 at 08:02
  • 1
    @AndreasRejbrand I have good intentions. I'm developing Dashman (https://dashman.tech) and the main use of it is a screensaver, so, during the installation, I want to give the option to set it as default, but the dialog is a bit confusing. – Pablo Fernandez Apr 12 '18 at 08:02
  • I see, that seems fair. Still, I suspect there is no documented way of doing this. A quick Google search for "Windows set screensaver programmatically" gives a few hints, though. Since the installer probably is running with elevated privileges, these might actually work. – Andreas Rejbrand Apr 12 '18 at 08:04
  • @AndreasRejbrand: I'm happy with undocumented ones ;) – Pablo Fernandez Apr 12 '18 at 08:08
  • 1
    https://msdn.microsoft.com/en-us/library/dd405477(v=vs.85).aspx – Hans Passant Apr 23 '18 at 20:00
  • 1
    @pupeno Have you looked at this post: https://stackoverflow.com/questions/8383589/how-do-i-change-the-screensaver-programatically – Sorceri Apr 23 '18 at 20:26
  • You want to avoid UAC protection? Or it doesn't matters? – Maciej Pulikowski Apr 25 '18 at 10:39
  • @MaciejPulikowski: I'm not trying to circumvent security protections, so, it doesn't matter if it hits UAC or not. I guess in most cases it wouldn't as it's the user's screensaver. – Pablo Fernandez Apr 25 '18 at 10:50

4 Answers4

11

I have found two ways to do it:

1) Add in registry, make sure is active and setTimeOut (only minutes)

CMD

reg add "HKEY_CURRENT_USER\Control Panel\Desktop" /v SCRNSAVE.EXE /t REG_SZ /d C:\Windows\System32\Mystify.scr /f
reg add "HKEY_CURRENT_USER\Control Panel\Desktop" /v ScreenSaveActive /t REG_SZ /d 1 /f
reg add "HKEY_CURRENT_USER\Control Panel\Desktop" /v ScreenSaveTimeOut /t REG_SZ /d 60 /f

JAVA

setScreenSaver(true, 1, "C:\\Windows\\System32\\Mystify.scr");

/**
 * set screen saver active, timeout and scr, only works in Windows
 * @param isActive
 * @param timeOutMin only minutes
 * @param pathToScr path to scr
 * @throws IOException
 */
public static void setScreenSaver(boolean isActive, int timeOutMin, String pathToScr) throws IOException{
    String _isActive = isActive ? "1" : "0";
    //only works with minutes, min. 1 min
    String _timeOut = timeOutMin > 1 ? timeOutMin*60+"" : "60";
    Runtime.getRuntime().exec(new String[] { "reg", "add", "HKEY_CURRENT_USER\\Control Panel\\Desktop", "/v", "SCRNSAVE.EXE", "/t", "REG_SZ", "/d", pathToScr,"/f" });
    Runtime.getRuntime().exec(new String[] { "reg", "add", "HKEY_CURRENT_USER\\Control Panel\\Desktop", "/v", "ScreenSaveActive", "/t", "REG_SZ", "/d", _isActive,"/f" });
    Runtime.getRuntime().exec(new String[] { "reg", "add", "HKEY_CURRENT_USER\\Control Panel\\Desktop", "/v", "ScreenSaveTimeOut", "/t", "REG_SZ", "/d", _timeOut,"/f" });
}

2) Get path from registry and rewrite scr file, but if is set to null, you can't do it.

Maciej Pulikowski
  • 2,457
  • 3
  • 15
  • 34
  • That looks very good. I'm going to be trying it later today or tomorrow. Please, bear with me while I deal with some emergencies. – Pablo Fernandez Apr 25 '18 at 10:51
  • @pupeno, I am surprised because you mentioned that you are running `rundll32.exe desk.cpl,InstallScreenSaver toasters.scr`, so you already knew how to do run a command in Java. And this answer added a cosmetic patch to mine. This is not two ways, this is just approach 1 and how to execute it in Java. I didn't post that in my answer because the critical part your problem and the solution was `reg add "HKEY_CURRENT_USER\Control Panel\Desktop" /v SCRNSAVE.EXE /t REG_SZ /d C:\Windows\system32\toasters.scr /f` and the original question was about screensaver only, not timeouts – Tarun Lalwani Apr 29 '18 at 05:23
  • @TarunLalwani Your method don't check if screensaver is turned on, timeout is extra. It didn't worked for me, i had "ScreenSaveActive" set to 0. I added Java code, because i implemented this function to my app Remote Administration Tool (RAT) to manage computers in company. So i just shared it. Second method is to rewrite existing .scr file, it is not a Java code. Btw. good job for top1 Quarter. – Maciej Pulikowski Apr 29 '18 at 07:29
  • `It didn't worked for me, i had "ScreenSaveActive" set to 0`, that's what I would have loved to hear earlier :-). Appreciate the clarification. And also `2) Get path from registry and rewrite scr file, but if is set to null, you can't do it.` did you mean overwrite the screensaver itself? – Tarun Lalwani Apr 29 '18 at 08:47
  • I mean to overwrite already used scr. But you will need to take ownership of the file using a administrator account. – Maciej Pulikowski Apr 29 '18 at 20:31
  • Why these values are in string format? – Mayur May 27 '22 at 10:45
11

The modern way, with powershell

Set-ItemProperty -Path "HKCU:\Control Panel\Desktop" -Name ScreenSaveActive -Value 1
Set-ItemProperty -Path "HKCU:\Control Panel\Desktop" -Name ScreenSaveTimeOut -Value 60
Set-ItemProperty -Path "HKCU:\Control Panel\Desktop" -Name scrnsave.exe -Value "c:\windows\system32\mystify.scr"

You can put these in a ScrnInstaller.ps1 script that you execute with the command:

$ powershell -WindowStyle hidden -f "ScrnInstaller.ps1"

NB: Thoses parameters are superseeded by group policy parameters (eg., to force a screen saver for users in an enterprise). You have several ways to force it here.

With user / domain / site awareness: group policy

Using powershell and group policy, you can manage for which Organizational Unit / Domain / Site you're affecting the change, and it's having prevedence over user settings.

Changing group policy in the case of the screen saver time out:

Get-Command -Module GroupPolicy
New-GPO -Name "ScreenSaverTimeOut" -Comment "Sets the time to 900 seconds"
Set-GPRegistryValue -Name "ScreenSaverTimeOut" -Key "HKCU\Software\Policies\Microsoft\Windows\Control Panel\Desktop" -ValueName ScreenSaveTimeOut -Type DWord -Value 900
New-GPLink -Name "ScreenSaverTimeOut" -Target "ou=MyOU,dc=myenterprise,dc=com"
gpupdate /force /target:computer

for myenterprise.com. For New-GPLink parameters: msdn reference

Then you can review your GP:

Get-GPO -Name "ScreenSaverTimeOut" | Get-GPOReport -ReportType HTML -Path $Home\report.html
Invoke-Item $Home\report.html
Soleil
  • 6,404
  • 5
  • 41
  • 61
  • 1
    if you don't see registry settings applied, run `rundll32.exe user32.dll, UpdatePerUserSystemParameters` – Devstr Jun 18 '21 at 20:23
  • Weirdly, I had to run that UpdatePerUserSystemParameters call ~twice~ to have it update. Win10, 21H2. Even then it still didn't update sometimes in the UI. – Jon Marnock Nov 30 '21 at 03:57
1

Instead of running that command you should just run the command

reg add "HKEY_CURRENT_USER\Control Panel\Desktop" /v SCRNSAVE.EXE /t REG_SZ /d C:\Windows\system32\toasters.scr /f

This will update the screensaver

Tarun Lalwani
  • 142,312
  • 9
  • 204
  • 265
0
c:\Windows\System32\scrnsave.scr -start

The above live in a batch file will start the blank screen saver. Pros; Replacing scrnsave.scr with one of the other 5 screensavers in C:\Windows\system32\ will work just as well. You will not need to restart your system and it will start right up. Cons; I don't know how to set the timeout. I suspect there would be an argument for the line like c:\Windows\System32\scrnsave.scr /ScreenSaveTimeOut = 150 -start I think there needs to be a separate batch file to stop the screen saver.