列出所有打开的资源管理器的 Powershell 脚本 windows
Powershell script to list all open Explorer windows
显示了一个 Powershell 脚本,用于生成打开的文件资源管理器 windows 及其路径的列表。
我的目标是捕获当前打开的资源管理器集 windows,并使用如下命令写出一个 CMD 文件:C:\WINDOWS\explorer.exe /e, "C:\open\this\folder"
所以我想以正常路径表示法获得完整路径和文件夹名称。这是资源管理器标题栏中显示的内容 Windows:"C:\open\this\Favorite folder"
建议的代码是:
function Get-WindowTitle($handle) {
Get-Process |
Where-Object { $_.MainWindowHandle -eq $handle } |
Select-Object -Expand MainWindowTitle
}
$app = New-Object -COM 'Shell.Application'
$app.Windows() |
Select-Object LocationURL, @{n='Title';e={Get-WindowTitle $_.HWND}}
如上所示,LocationURL 提供 escaped-URL 样式的完整路径:
file:///C:/open/this/Favorite%20%folder"
@{n='Title';e={Get-WindowTitle $_.HWND}} 组件生成一个列 "Title",它被截断为 5 个字符:
C:\...
一个资源管理器 window 的完整输出如下所示:
LocationURL Title
----------- -----
file:///C:/open/this/Favorite%20%folder C:...
我发现我可以通过用许多空格填充字符串 'Title' 来避免截断。该字符串的宽度似乎决定了输出的最大宽度。
不过,我观察到只有大约 60% 的打开的资源管理器 windows 列出了路径。其余的只是一个空行。
我尝试了“$app.Windows() | Select-Object LocationName”,但输出仅包含资源管理器文件夹名称,而不是资源管理器标题中显示的完整路径和文件夹。
另一个谜团是为什么脚本运行这么慢。如果我打开了 10 个资源管理器 windows,脚本将运行 30 秒,每条路径大约需要 3 秒。
对于这个脚本:
function Get-WindowTitle($handle) {
Get-Process |
Where-Object { $_.MainWindowHandle -eq $handle } |
Select-Object -Expand MainWindowTitle
}
$app = New-Object -COM 'Shell.Application'
$app.Windows() |
Select-Object LocationName,@{n=' ------------Title---------------- ';e={Get-WindowTitle $_.HWND}}
这是输出(为了保护隐私用 *** 进行了一些编辑)
PS C:\E***> .\OpenExplorer.ps1
LocationName ------------Title----------------
------------ ----------------------------------------------------------------------------------
2019-07
Ame****
2019 Priv...
2019-10-3... C:\E\Event Presentations19-10-31 Priv**********bcast
E C:\E
5G Brief ... C:\E\Tech************ingG Brief (2018)
36 Series...
2019 DE* ... C:\E*****N19 DE*******************
Newsletters C:\E\Newsletters
Reports C:\E\Tech************ing\Reports
2019-10-2... C:\E**********s19-10-29 *********************
2019-11 C:\Data\Docs\Stand*********2419-11
UB****
Financial... C:\E\Financ************
Expenses C:\E\Internal\Expenses
E C:\E
E***
我假设您真正感兴趣的是打开的资源管理器 windows 的 本地文件系统路径 ,不一定是 window 标题(它们不是'保证反映完整路径)。
有点模糊,.Windows()
方法返回的 window objects 在它们的 .Document.Folder.Self.Path
属性.[=19= 中包含本地路径表示]
(New-Object -ComObject 'Shell.Application').Windows() | ForEach-Object {
$localPath = $_.Document.Folder.Self.Path
"C:\WINDOWS\explorer.exe /e, `"$localPath`""
}
以上产生的输出如下:
C:\WINDOWS\explorer.exe /e, "C:\Users\jdoe"
C:\WINDOWS\explorer.exe /e, "C:\Program Files"
您可以根据需要将其输出到批处理文件,例如通过将 | Set-Content file.cmd
附加到上述命令。
注意:windows 是按照 创建 的顺序列出的,因此您无法推断出其中哪一个是最近激活的。请参阅 this answer 找到最顶层的文件资源管理器 window 并确定其中显示的路径的解决方案。
I found I could avoid the truncation
截断只是一个显示工件 - 数据仍然存在。
您可以通过以下两种方式之一使数据可见:
管道到 Format-Table -AutoSize
以确保列值不被截断,space 允许
管道到 Format-List
,这将在其自己的行上显示每个 属性(line-wrapping 过长的值)。
所以我想以正常路径表示法获得完整路径和文件夹名称。这是资源管理器标题栏中显示的内容 Windows:"C:\open\this\Favorite folder"
建议的代码是:
function Get-WindowTitle($handle) {
Get-Process |
Where-Object { $_.MainWindowHandle -eq $handle } |
Select-Object -Expand MainWindowTitle
}
$app = New-Object -COM 'Shell.Application'
$app.Windows() |
Select-Object LocationURL, @{n='Title';e={Get-WindowTitle $_.HWND}}
如上所示,LocationURL 提供 escaped-URL 样式的完整路径:
file:///C:/open/this/Favorite%20%folder"
@{n='Title';e={Get-WindowTitle $_.HWND}} 组件生成一个列 "Title",它被截断为 5 个字符:
C:\...
一个资源管理器 window 的完整输出如下所示:
LocationURL Title
----------- -----
file:///C:/open/this/Favorite%20%folder C:...
我发现我可以通过用许多空格填充字符串 'Title' 来避免截断。该字符串的宽度似乎决定了输出的最大宽度。 不过,我观察到只有大约 60% 的打开的资源管理器 windows 列出了路径。其余的只是一个空行。
我尝试了“$app.Windows() | Select-Object LocationName”,但输出仅包含资源管理器文件夹名称,而不是资源管理器标题中显示的完整路径和文件夹。
另一个谜团是为什么脚本运行这么慢。如果我打开了 10 个资源管理器 windows,脚本将运行 30 秒,每条路径大约需要 3 秒。
对于这个脚本:
function Get-WindowTitle($handle) {
Get-Process |
Where-Object { $_.MainWindowHandle -eq $handle } |
Select-Object -Expand MainWindowTitle
}
$app = New-Object -COM 'Shell.Application'
$app.Windows() |
Select-Object LocationName,@{n=' ------------Title---------------- ';e={Get-WindowTitle $_.HWND}}
这是输出(为了保护隐私用 *** 进行了一些编辑)
PS C:\E***> .\OpenExplorer.ps1
LocationName ------------Title----------------
------------ ----------------------------------------------------------------------------------
2019-07
Ame****
2019 Priv...
2019-10-3... C:\E\Event Presentations19-10-31 Priv**********bcast
E C:\E
5G Brief ... C:\E\Tech************ingG Brief (2018)
36 Series...
2019 DE* ... C:\E*****N19 DE*******************
Newsletters C:\E\Newsletters
Reports C:\E\Tech************ing\Reports
2019-10-2... C:\E**********s19-10-29 *********************
2019-11 C:\Data\Docs\Stand*********2419-11
UB****
Financial... C:\E\Financ************
Expenses C:\E\Internal\Expenses
E C:\E
E***
我假设您真正感兴趣的是打开的资源管理器 windows 的 本地文件系统路径 ,不一定是 window 标题(它们不是'保证反映完整路径)。
有点模糊,.Windows()
方法返回的 window objects 在它们的 .Document.Folder.Self.Path
属性.[=19= 中包含本地路径表示]
(New-Object -ComObject 'Shell.Application').Windows() | ForEach-Object {
$localPath = $_.Document.Folder.Self.Path
"C:\WINDOWS\explorer.exe /e, `"$localPath`""
}
以上产生的输出如下:
C:\WINDOWS\explorer.exe /e, "C:\Users\jdoe"
C:\WINDOWS\explorer.exe /e, "C:\Program Files"
您可以根据需要将其输出到批处理文件,例如通过将 | Set-Content file.cmd
附加到上述命令。
注意:windows 是按照 创建 的顺序列出的,因此您无法推断出其中哪一个是最近激活的。请参阅 this answer 找到最顶层的文件资源管理器 window 并确定其中显示的路径的解决方案。
I found I could avoid the truncation
截断只是一个显示工件 - 数据仍然存在。
您可以通过以下两种方式之一使数据可见:
管道到
Format-Table -AutoSize
以确保列值不被截断,space 允许管道到
Format-List
,这将在其自己的行上显示每个 属性(line-wrapping 过长的值)。