Powershell script из ярлыка для изменения рабочего стола
Любые идеи и предложения по поводу того, почему это работает при запуске с помощью PS, но не при запуске из ярлыка, определенного как:
%SystemRoot%\system32\WindowsPowerShell\v1.0\powershell.exe -File "C:\Users\bin\ChangeDesktop.ps1"
Содержимое ChangeDesktop.ps1:
set-itemproperty -path "HKCU:Control Panel\Desktop" -name WallPaper -value ""
rundll32.exe user32.dll, UpdatePerUserSystemParameters
Если я нахожусь в среде командной строки PS, фоновый рисунок рабочего стола автоматически удаляется и обновляется, за исключением того, что мне нужно вручную обновить рабочий стол, чтобы произвести изменение.
Система - это Windows Server 2008 R2 - новая установка. Script executepolicy имеет значение RemoteSigned, и я не вижу никаких ошибок PS. Я просто не вижу автоматического обновления рабочего стола при работе с ярлыком на рабочем столе.
царапины головы
Ответы
Ответ 1
rundll32.exe user32.dll, UpdatePerUserSystemParameters
фактически не менял обоев для меня на коробке x64 2008 года. Это делает, хотя... Он вызывает API Win32, чтобы ссылаться на изменение обоев. Если вы сохраните это как ваш ChangeDesktop.ps1 script, он должен работать. Так как он находится ниже, он удалит обои для рабочего стола. Однако, если вы хотите установить его, вы можете отредактировать последнюю строку с помощью пути к файлу поддерживаемого изображения следующим образом:
[Wallpaper.Setter]::SetWallpaper( 'C:\Wallpaper.bmp', 0 )
Второй аргумент для стиля:
0: Плитка
1: Центр
2: Растяжка
3: Без изменений
script:
Add-Type @"
using System;
using System.Runtime.InteropServices;
using Microsoft.Win32;
namespace Wallpaper
{
public enum Style : int
{
Tile, Center, Stretch, NoChange
}
public class Setter {
public const int SetDesktopWallpaper = 20;
public const int UpdateIniFile = 0x01;
public const int SendWinIniChange = 0x02;
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
private static extern int SystemParametersInfo (int uAction, int uParam, string lpvParam, int fuWinIni);
public static void SetWallpaper ( string path, Wallpaper.Style style ) {
SystemParametersInfo( SetDesktopWallpaper, 0, path, UpdateIniFile | SendWinIniChange );
RegistryKey key = Registry.CurrentUser.OpenSubKey("Control Panel\\Desktop", true);
switch( style )
{
case Style.Stretch :
key.SetValue(@"WallpaperStyle", "2") ;
key.SetValue(@"TileWallpaper", "0") ;
break;
case Style.Center :
key.SetValue(@"WallpaperStyle", "1") ;
key.SetValue(@"TileWallpaper", "0") ;
break;
case Style.Tile :
key.SetValue(@"WallpaperStyle", "1") ;
key.SetValue(@"TileWallpaper", "1") ;
break;
case Style.NoChange :
break;
}
key.Close();
}
}
}
"@
[Wallpaper.Setter]::SetWallpaper( '', 0 )
Первоначально из PoshCode: http://poshcode.org/491
Ответ 2
Это может показаться странным, но то, что сработало для меня, было использование одиночных кавычек вместо двойных. Таким образом, это будет выглядеть так:
Set-ItemProperty -path "HKCU:Control Panel\Desktop" -name 'wallpaper' -value 'some value'
rundll32.exe user32.dll, UpdatePerUserSystemParameters
Ответ 3
script, предоставленный Энди Арисменди, потрясающий!
Я использовал его для создания веселого проекта - установил случайные обои, очищенные от сети.
Я размещаю его здесь для всех, кого это интересует. Перед его использованием вам нужно изменить несколько констант в верхней части источника script. Вам также нужно загрузить библиотеку HtmlAgilityPack.dll
(в комментариях script есть инструкции).
Наслаждайтесь!
P.S. Если сайт обоев, который я использую, сходит или меняет свой макет, соскабливание в script пойдет в ад, но, тем не менее, с моим script в качестве примера, я готов поспорить, что вы сможете построить еще один скребок для обоев.
############## CONSTANTS ##############
# add the library for parsing html - HtmlAgilityPack - download it with nuget from https://www.nuget.org/packages/HtmlAgilityPack
# download nuget command line from https://dist.nuget.org/index.html and install HtmlAgilityPack with "nuget install HtmlAgilityPack" from the cmd
# enter the path to HtmlAgilityPack.dll library used for html parsing
$html_parser_path = "C:\Users\username\Documents\htmlagilitypack\HtmlAgilityPack.1.4.9.5\lib\Net20\HtmlAgilityPack.dll"
# choose where your wallpapers will be downloaded
$wallpaper_dir_path = "C:\Users\username\Pictures\"
# get random wallpaper category from wallpaperscraft.com - the ones below are my favourite categories, edit it if you want to get other categories
<#
you can choose your favorite wallpaper categories from the list below
3D
Abstract
Animals
Anime
Brands
Cars
City
Fantasy
Flowers
Food
Games
Girls
Hi-Tech
Holidays
Macro
Men
Movies
Music
Nature
Other
Space
Sport
Textures
TV Series
Vector
#>
$categories = @("animals","flowers","macro","nature","space")
# I download my wallpapers from the site below - real quality wallpapers
# don't forget to change your resolution - I'm using a 1920x1080 monitor
<#
A list of resolutions to choose from:
1600x1200
1400x1050
1280x1024
1280x960
1152x864
1024x768
3840x2400
3840x2160
3840x1200
2560x1600
2560x1440
2560x1080
2560x1024
2048x1152
1920x1200
1920x1080
1680x1050
1600x900
1440x900
1280x800
1280x720
2160x3840
1440x2560
1366x768
1080x1920
1024x600
960x544
800x1280
800x600
720x1280
540x960
480x854
480x800
400x480
360x640
320x480
320x240
240x400
240x320
2732x2732
2048x2048
1080x1920
1024x1024
750x1334
640x1136
640x960
320x480
1366x768
1920x1080
360x640
1024x768
1600x900
1280x900
1440x900
1280x1024
800x600
1680x1050
2560x1440
320x480
1920x1200
480x800
720x1280
#>
$resolution = "1920x1080" # default resolution
$url = "https://wallpaperscraft.com/catalog/category/$resolution" # category is a placeholder
############## END OF CONSTANT DECLARATIONS ##############
Add-Type @"
using System;
using System.Runtime.InteropServices;
using Microsoft.Win32;
namespace Wallpaper
{
public enum Style : int
{
Tile, Center, Stretch, NoChange
}
public class Setter {
public const int SetDesktopWallpaper = 20;
public const int UpdateIniFile = 0x01;
public const int SendWinIniChange = 0x02;
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
private static extern int SystemParametersInfo (int uAction, int uParam, string lpvParam, int fuWinIni);
public static void SetWallpaper ( string path, Wallpaper.Style style ) {
SystemParametersInfo( SetDesktopWallpaper, 0, path, UpdateIniFile | SendWinIniChange );
RegistryKey key = Registry.CurrentUser.OpenSubKey("Control Panel\\Desktop", true);
switch( style )
{
case Style.Stretch :
key.SetValue(@"WallpaperStyle", "2") ;
key.SetValue(@"TileWallpaper", "0") ;
break;
case Style.Center :
key.SetValue(@"WallpaperStyle", "1") ;
key.SetValue(@"TileWallpaper", "0") ;
break;
case Style.Tile :
key.SetValue(@"WallpaperStyle", "1") ;
key.SetValue(@"TileWallpaper", "1") ;
break;
case Style.NoChange :
break;
}
key.Close();
}
}
}
"@
Add-Type -Path $html_parser_path
$rand_index = Get-Random -minimum 0 -maximum $categories.Length
$random_category = $categories[$rand_index]
# replace the placeholder "category" with the random category chosen above
$url = $url -replace "category", $random_category
$doc = New-Object HtmlAgilityPack.HtmlDocument
$doc.LoadHtml((New-Object System.Net.WebClient).DownloadString($url))
# NOTE: the html parser I'm using locates elements by XPath only
$page_links = $doc.DocumentNode.SelectSingleNode("//div[contains(@class, 'pages')]").SelectNodes("a")
# get last page link
$last_page_link = $page_links[$page_links.Count - 1].GetAttributeValue("href", "")
# get last page number
$last_page_number = [regex]::match($last_page_link,'.*page(\d+)').Groups[1].Value
$random_page_number = Get-Random -minimum 0 -maximum $last_page_number
$random_page_addr = ""
# page 1 doesn't add anything to the url
if ($random_page_number -gt 0){
$random_page_addr = "/page$random_page_number"
}
$doc.LoadHtml((New-Object System.Net.WebClient).DownloadString("$url$random_page_addr"))
# get wallpaper divs
$wallpaper_divs = $doc.DocumentNode.SelectNodes("//div[contains(@class, 'wallpaper_pre')]")
$random_wallpaper_div = Get-Random -minimum 0 -maximum 15 # there are 15 wallpapers on a page
# get a sample wallpaper link which has to be substituted later
$sample_wallpaper_link = $wallpaper_divs[$random_wallpaper_div].SelectNodes("a")[0].GetAttributeValue("href", "")
# substitute the above link to get the image link itself
$sample_wallpaper_link = $sample_wallpaper_link -replace "download", "image"
$sample_wallpaper_link = $sample_wallpaper_link -replace "/$resolution", "_$resolution.jpg"
$sample_wallpaper_link = $sample_wallpaper_link -replace "//", "https://"
$wallpaper_image_name = [regex]::match($sample_wallpaper_link,'.*image/(\w+)').Groups[1].Value
$wallpaper_image_name = "$wallpaper_image_name.jpg"
$wc = New-Object System.Net.WebClient
$save_location = "$wallpaper_dir_path$wallpaper_image_name"
$wc.DownloadFile($sample_wallpaper_link, "$save_location")
[Wallpaper.Setter]::SetWallpaper($save_location, 1 )
Ответ 4
Этот script творит чудеса. Для развертывания домена мы не хотели, чтобы он постоянно менял фон каждый раз, когда пользователь входит в систему.
Я сделал следующие изменения, чтобы проверить, существует ли фон на компьютере в нужном месте, если он существует, а затем выйти, если он не будет продолжать копирование файла и установить фон.
он сначала отображает скрытый общий ресурс, копирует файл в нужный каталог, устанавливает обои и отключает скрытую часть. если "X" уже используется вашей компанией, вставьте еще одну букву диска.: D
$strFileName="C:\Users\Public\Pictures\background.jpg"
If (Test-Path $strFileName){
# // File exists
Exit-PSSession
}Else{
# // File does not exist
New-PSDrive -Name X -PSProvider Filesystem -Root \\hiddenfileshare\wallpapers
Copy-Item X:\background.jpg C:\Users\Public\Pictures
[Wallpaper.Setter]::SetWallpaper( 'C:\Users\Public\Pictures\background.jpg', 0 )
Remove-PSDrive X
}