脚本设置开始菜单显示的文件夹

最近发现了一款pxe网络安装工具iVentoy,可以极大的简化pxe环境的搭建。在测试安装的过程中同时也开启了一件自己一直想做的事情,就是安装完成后使用批处理对新的Windows进行一系列设置以简化初始化流程,减少重装系统的操作成本和时间成本。

现在的情况是已经完成大部分的设置的自动化,包括但不限于以下内容:

  • 未识别的驱动安装、显卡驱动更新
  • NAS账号添加、网络磁盘挂载、设置盘符、创建快捷方式
  • 系统激活、修改主机名、设置环境变量、设置系统盘符、开启远程桌面、其他系统优化
  • 设置桌面图片、设置开始菜单、设置任务栏、设置资源管理器、设置右键菜单
  • 自动安装软件、卸载内置应用、设置文件关联、设置开机启动软件

今天要说明的就是如何使用Powershell脚本设置开始菜单显示的文件夹

Windows下大部分的设置可以通过注册表去进行,所以在最开始写脚本的时候使用了procmon去监视注册表的操作,直到在设置有哪些文件夹显示在开始菜单的左侧时遇到了以下问题

  • 监控到的注册表路径是:HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows\CurrentVersion\CloudStore\Store\Cache\DefaultAccount$de${1843bc7e-7dbe-4826-ae22-037763b69955}$$windows.data.unifiedtile.startglobalproperties\Current,很明显中间的这一段1843bc7e-7dbe-4826-ae22-037763b69955在每次重装后肯定会发生变化。
  • 监控到的注册表键Data是一个二进制,虽然可以设置整个,但是不知道具体对应的是哪些设置。

经过网上一系列的资料查找,我找到了以下两种设置方式

方式1:注册表设置组策略

这个方法来自这篇文章:Add or Remove Folders on Start List in Windows 10

文章里使用的是使用注册表设置组策略的方式。

Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\PolicyManager\current\device\Start]
“AllowPinnedFolderDocuments”=dword:00000000
“AllowPinnedFolderDocuments_ProviderSet”=dword:00000001
“AllowPinnedFolderDownloads”=dword:00000000
“AllowPinnedFolderDownloads_ProviderSet”=dword:00000001
“AllowPinnedFolderFileExplorer”=dword:00000000
“AllowPinnedFolderFileExplorer_ProviderSet”=dword:00000001
“AllowPinnedFolderMusic”=dword:00000000
“AllowPinnedFolderMusic_ProviderSet”=dword:00000001
“AllowPinnedFolderNetwork”=dword:00000000
“AllowPinnedFolderNetwork_ProviderSet”=dword:00000001
“AllowPinnedFolderPersonalFolder”=dword:00000000
“AllowPinnedFolderPersonalFolder_ProviderSet”=dword:00000001
“AllowPinnedFolderPictures”=dword:00000000
“AllowPinnedFolderPictures_ProviderSet”=dword:00000001
“AllowPinnedFolderSettings”=dword:00000000
“AllowPinnedFolderSettings_ProviderSet”=dword:00000001
“AllowPinnedFolderVideos”=dword:00000000
“AllowPinnedFolderVideos_ProviderSet”=dword:00000001

虽然解决了设置的问题,但是也产生了一个很明显的副作用,那就是导入后设置项目会直接置灰,无法再次设置。

方法2:直接设置注册表

这个方法来自这篇文章:Choose which folders appear on Start

简单来说这个Data的二进制也有固定的格式。帖子里对Data的值做了详细的说明。

前20字节固定为 02,00,00,00,xx,xx,xx,xx,xx,xx,xx,xx,00,00,00,00,43,42,01,00 ,其中xx的地方为时间戳(可能是最后更改的时间戳),这些可以直接从注册表中当前存在的数据中获取,因为它们对于调整的其余部分没有意义。

接下来的3个字节取决于你是否想在开始菜单显示最近添加的应用,如果想要显示,则可以跳到下一个部分,如果不想要显示,那么接下来的3个字节是 c2,14,01 (这部分是在后续设置的时候发现的,帖子中并没有提及)

接下来取决于你是否想要任何项目。如果不想要,可以直接跳到最后一部分。如果想要,那么接下来的4个字节是 cb,32,0a,yy ,其中yy是显示项目的数量。

然后链接你想要显示的项目。一个项目始终以05开头,以00结束。

  • 文件浏览器:05,bc,c9,a8,a4,01,24,8c,ac,03,44,89,85,01,66,a0,81,ba,cb,bd,d7,a8,a4,82,01,00
  • 设置:05,86,91,cc,93,05,24,aa,a3,01,44,c3,84,01,66,9f,f7,9d,b1,87,cb,d1,ac,d4,01,00
  • 文档:05,ce,ab,d3,e9,02,24,da,f4,03,44,c3,8a,01,66,82,e5,8b,b1,ae,fd,fd,bb,3c,00
  • 下载:05,af,e6,9e,9b,0e,24,de,93,02,44,d5,86,01,66,bf,9d,87,9b,bf,8f,c6,d4,37,00
  • 音乐:05,a0,8c,ac,80,0b,24,d1,fe,01,44,b2,98,01,66,aa,bd,d0,e1,cc,ea,df,b9,15,00
  • 图片:05,a0,8f,fc,c1,03,24,8a,d0,03,44,80,99,01,66,b0,b5,99,dc,cd,b0,97,de,4d,00
  • 视频:05,c5,cb,ce,95,04,24,86,fb,01,44,f4,85,01,66,80,c9,ce,d4,af,d9,9e,c4,b5,01,00
  • 网络:05,c4,82,d6,f3,0f,24,8d,10,44,ae,85,01,66,8b,b5,d3,e9,fe,d2,ed,b1,94,01,00
  • 个人文件夹:05,ca,e0,f6,a5,07,24,ca,f2,03,44,e8,9e,01,66,8b,ad,8f,c2,f9,a0,87,d4,bc,01,00

最后的10个字节始终是 c2,3c,01,c2,46,01,c5,5a,01,00

帖子在说明了Data二进制内容的同时也让我了解到了如何处理这个变化的注册表路径

实践

最后,根据帖子中的内容,我也稍微修改了一下设置开始菜单的函数

Function Start-folder{
  param([ValidateCount(0,10)][String[]]$itemsToDisplay)
  $key = Get-ItemProperty "HKCU:\Software\Microsoft\Windows\CurrentVersion\CloudStore\Store\Cache\DefaultAccount\*windows.data.unifiedtile.startglobalproperties\Current"
  $data = $key.Data[0..19] -Join ","
  If ($itemsToDisplay.Length -gt 0) {
    If ($itemsToDisplay -contains "recently") {
      $data += ",203,50,10,$($itemsToDisplay.Length)"
    }else{
      $data += ",194,20,1,203,50,10,$($itemsToDisplay.Length)"
    }
    If ($itemsToDisplay -contains "explorer") {
      $data += ",5,188,201,168,164,1,36,140,172,3,68,137,133,1,102,160,129,186,203,189,215,168,164,130,1,0"
    }
    If ($itemsToDisplay -contains "settings") {
      $data += ",5,134,145,204,147,5,36,170,163,1,68,195,132,1,102,159,247,157,177,135,203,209,172,212,1,0"
    }
    If ($itemsToDisplay -contains "documents") {
      $data += ",5,206,171,211,233,2,36,218,244,3,68,195,138,1,102,130,229,139,177,174,253,253,187,60,0"
    }
    If ($itemsToDisplay -contains "downloads") {
      $data += ",5,175,230,158,155,14,36,222,147,2,68,213,134,1,102,191,157,135,155,191,143,198,212,55,0"
    }
    If ($itemsToDisplay -contains "music") {
      $data += ",5,160,140,172,128,11,36,209,254,1,68,178,152,1,102,170,189,208,225,204,234,223,185,21,0"
    }
    If ($itemsToDisplay -contains "pictures") {
      $data += ",5,160,143,252,193,3,36,138,208,3,68,128,153,1,102,176,181,153,220,205,176,151,222,77,0"
    }
    If ($itemsToDisplay -contains "videos") {
      $data += ",5,197,203,206,149,4,36,134,251,1,68,244,133,1,102,128,201,206,212,175,217,158,196,181,1,0"
    }
    If ($itemsToDisplay -contains "network") {
      $data += ",5,196,130,214,243,15,36,141,16,68,174,133,1,102,139,181,211,233,254,210,237,177,148,1,0"
    }
    If ($itemsToDisplay -contains "personal") {
      $data += ",5,202,224,246,165,7,36,202,242,3,68,232,158,1,102,139,173,143,194,249,160,135,212,188,1,0"
    }
  }
  $data += ",194,60,1,194,70,1,197,90,1,0"
  Set-ItemProperty -Path $key.PSPath -Name "Data" -Type Binary -Value $data.Split(",")
}
#设置开始菜单右侧只显示资源管理器和设置,并且开始菜单隐藏最近添加的应用
Start-folder explorer,settings

运行结果完美,又可以减少一步重装系统后的操作了🎉

参考文献

Add or Remove Folders on Start List in Windows 10

Choose which folders appear on Start

本文链接 https://blog.kimi360.top/97a24c5b2e7e/

本文采用 知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议 (CC BY-NC-ND 4.0) 进行许可。