-
Notifications
You must be signed in to change notification settings - Fork 9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
How to get output on Powershell or Cmd #8
Comments
Yes, it is possible to get it directly via Powershell. I created some sample code (My PowerShell is a bit rusty): # Importing GlobalSystemMediaTransportControlsSessionManager ( Source: https://superuser.com/a/1342416 )
[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control,ContentType=WindowsRuntime] | Out-Null
Add-Type -AssemblyName System.Runtime.WindowsRuntime
# Adding Awaitable ( Source: https://superuser.com/a/1342416 )
$asTaskGeneric = ([System.WindowsRuntimeSystemExtensions].GetMethods() | ? { $_.Name -eq 'AsTask' -and $_.GetParameters().Count -eq 1 -and $_.GetParameters()[0].ParameterType.Name -eq 'IAsyncOperation`1' })[0]
Function Await($WinRtTask, $ResultType) {
$asTask = $asTaskGeneric.MakeGenericMethod($ResultType)
$netTask = $asTask.Invoke($null, @($WinRtTask))
$netTask.Wait(-1) | Out-Null
$netTask.Result
}
# Getting the session manager ( Matches code: https://github.com/DubyaDude/WindowsMediaController/blob/61ba73aad7632bdda4ba415d9391882287de656e/WindowsMediaController/Main.cs#L63 )
$WindowsSessionManager = Await ([Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager]::RequestAsync()) ([Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager])
# Getting current sessions ( Matches code: https://github.com/DubyaDude/WindowsMediaController/blob/61ba73aad7632bdda4ba415d9391882287de656e/WindowsMediaController/Main.cs#L76 )
$controlSessionList = $WindowsSessionManager.GetSessions()
foreach ($controlSession in $controlSessionList) {
# Getting the session source app ( Matches code: https://github.com/DubyaDude/WindowsMediaController/blob/61ba73aad7632bdda4ba415d9391882287de656e/WindowsMediaController/Main.cs#L172 )
Write-Output $controlSession.SourceAppUserModelId
# Getting the session's playback info ( Matches code: https://github.com/DubyaDude/WindowsMediaController/blob/61ba73aad7632bdda4ba415d9391882287de656e/WindowsMediaController/Main.cs#L180 )
$playbackInfo = $controlSession.GetPlaybackInfo()
Write-Output $playbackInfo.PlaybackStatus
# Getting the session's media properties ( Matches code: https://github.com/DubyaDude/WindowsMediaController/blob/61ba73aad7632bdda4ba415d9391882287de656e/WindowsMediaController/Main.cs#L195 )
$mediaProperties = Await ($controlSession.TryGetMediaPropertiesAsync()) ([Windows.Media.Control.GlobalSystemMediaTransportControlsSessionMediaProperties])
Write-Output $mediaProperties.Title
Write-Output $mediaProperties.Artist
} With the above code, I got the following output while listening to Spotify:
For exacts of what you can get from this, I'd recommend looking at this CS file in this repo: https://github.com/DubyaDude/WindowsMediaController/blob/master/WindowsMediaController/Main.cs Let me know if you have any other questions :) |
Hi, thanks for guide, you helped much i worked on SystemMediaTransportControls a bit, and dropping result here for future readers [Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control,ContentType=WindowsRuntime]|Out-Null
Add-Type -AssemblyName System.Runtime.WindowsRuntime
$asTaskGeneric=([System.WindowsRuntimeSystemExtensions].GetMethods()|?{$_.Name -eq 'AsTask' -and $_.GetParameters().Count -eq 1 -and $_.GetParameters()[0].ParameterType.Name -eq 'IAsyncOperation`1'})[0]
Function Await($WinRtTask,$ResultType){
$netTask=($asTaskGeneric.MakeGenericMethod($ResultType)).Invoke($null,@($WinRtTask))
$netTask.Wait(-1)|Out-Null
$netTask.Result
}
$playingstatus=$false
$playinginfo="Play"
$playingArr=$false
$smtc=[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager]
$smtcArr=@()
$i=-1
foreach($Session in (Await($smtc::RequestAsync())($smtc)).GetSessions()){
$a=@()
$i++
$a+="----------"
$a+=$Session.SourceAppUserModelId
$a+=$Session.GetPlaybackInfo().PlaybackStatus
$prop=Await($Session.TryGetMediaPropertiesAsync())([Windows.Media.Control.GlobalSystemMediaTransportControlsSessionMediaProperties])
$a+=$prop.Artist + " - " + $prop.Title
if($a -contains "Playing"){$playingArr=$i}
$a+="----------"
$smtcArr+=,$a
}
$smtcCount=$smtcArr.Count
write-host "********** $smtcCount Apps in Playback Session"
$smtcArr
if($playingArr -ne $false){
write-host "********** Playing App"
$smtcArr[$playingArr]
}else{
write-host "********** No Playback"
} it prints apps in session also prints playing app in array for easier selection
If there is no playback prints
|
Unsure what you mean by background task, but maybe making it more 'event-based' rather then doing a consistent query of session, media, etc. Using this: https://stackoverflow.com/a/64232782 Using command: [Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager].GetEvents() | select Name, *Method, EventHandlerType I got the output: Name : CurrentSessionChanged
AddMethod : System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken add_CurrentSessionChanged(Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control.CurrentSessionChangedEventArgs])
RemoveMethod : Void remove_CurrentSessionChanged(System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken)
RaiseMethod :
EventHandlerType : Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control.CurrentSessionChangedEventArgs]
Name : SessionsChanged
AddMethod : System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken add_SessionsChanged(Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control.SessionsChangedEventArgs])
RemoveMethod : Void remove_SessionsChanged(System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken)
RaiseMethod :
EventHandlerType : Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control.SessionsChangedEventArgs] And running [Windows.Media.Control.GlobalSystemMediaTransportControlsSession].GetEvents() | select Name, *Method, EventHandlerType Results in: Name : MediaPropertiesChanged
AddMethod : System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken add_MediaPropertiesChanged(Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSession,Windows.Media.Control.MediaPropertiesChangedEventArgs])
RemoveMethod : Void remove_MediaPropertiesChanged(System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken)
RaiseMethod :
EventHandlerType : Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSession,Windows.Media.Control.MediaPropertiesChangedEventArgs]
Name : PlaybackInfoChanged
AddMethod : System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken add_PlaybackInfoChanged(Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSession,Windows.Media.Control.PlaybackInfoChangedEventArgs])
RemoveMethod : Void remove_PlaybackInfoChanged(System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken)
RaiseMethod :
EventHandlerType : Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSession,Windows.Media.Control.PlaybackInfoChangedEventArgs]
Name : TimelinePropertiesChanged
AddMethod : System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken add_TimelinePropertiesChanged(Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSession,Windows.Media.Control.TimelinePropertiesChangedEventArgs])
RemoveMethod : Void remove_TimelinePropertiesChanged(System.Runtime.InteropServices.WindowsRuntime.EventRegistrationToken)
RaiseMethod :
EventHandlerType : Windows.Foundation.TypedEventHandler`2[Windows.Media.Control.GlobalSystemMediaTransportControlsSession,Windows.Media.Control.TimelinePropertiesChangedEventArgs] Which makes it seems it's possible to get it to be event-based like this project is. |
Also, please be aware of issue #6 which seems to affect a few events |
yep i have tried to add event with Add-Type -AssemblyName System.Runtime.WindowsRuntime
[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control,ContentType=WindowsRuntime]|Out-Null
$t=([System.WindowsRuntimeSystemExtensions].GetMethods()|?{$_.Name -eq 'AsTask' -and $_.GetParameters().Count -eq 1 -and $_.GetParameters()[0].ParameterType.Name -eq 'IAsyncOperation`1'})[0]
function aw($w,$r){$m=($t.MakeGenericMethod($r)).Invoke($null,@($w));$m.Wait(-1)|Out-Null;$m.Result}
$AppDomain=[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager];
$Action={Write-Host -ForegroundColor Green -Object 'Assembly was loaded!';};
Register-ObjectEvent -InputObject $AppDomain -EventName CurrentSessionChanged -Action $Action -OutVariable EventSubscription -SourceIdentifier CurrentSessionChanged; returns
thanks anyways here is my taskbar code if you want to further experiment (Get-Process -Id $pid).PriorityClass='idle'
Set-PSDebug -off
Add-Type -AssemblyName System.Windows.Forms,System.Runtime.WindowsRuntime
#thanks to [DubyaDude](https://github.com/DubyaDude) on imporing SMTC to powershell
[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager,Windows.Media.Control,ContentType=WindowsRuntime]|Out-Null
$t=([System.WindowsRuntimeSystemExtensions].GetMethods()|?{$_.Name -eq 'AsTask' -and $_.GetParameters().Count -eq 1 -and $_.GetParameters()[0].ParameterType.Name -eq 'IAsyncOperation`1'})[0]
function aw($w,$r){$m=($t.MakeGenericMethod($r)).Invoke($null,@($w));$m.Wait(-1)|Out-Null;$m.Result}
# .\ parent folder selection not works with vbs, you should define complete path
$f="C:\ProgramData\Apps\System\Taskbar\TrayIcons"
function n{New-Object Windows.Forms.NotifyIcon}
function k($v){(New-object -com wscript.shell).SendKeys([char]$v)|Out-Null}
function i($v){New-Object System.Drawing.Icon("$f\ico\$v.ico")}
$p=n;$l=i("pl");$u=i("ps")
$p.add_click({k(179)})
function pf{
$x=@()
$ps=$false
$pt="Play"
$sm=[Windows.Media.Control.GlobalSystemMediaTransportControlsSessionManager]
foreach($s in (aw($sm::RequestAsync())($sm)).GetSessions()){
$a=@()
$a+=$s.GetPlaybackInfo().PlaybackStatus
$pr=aw($s.TryGetMediaPropertiesAsync())([Windows.Media.Control.GlobalSystemMediaTransportControlsSessionMediaProperties])
$a+=$pr.Artist+" - "+$pr.Title
if($a -contains "Playing"){$ps=$true;$pt=$a[1]}
$x+=$a
$s=$null
}
$p.icon=if($ps){$u}else{$l}
#sets tray icon tooltip to artist - track tile
$p.text=$pt
$x=$a=@()
}
$n=n;$n.icon=i("nx");$n.text="Next"
#Right click on next button sends previous shortcut
$n.add_MouseDown({if($_.Button -eq [Windows.Forms.MouseButtons]::left){k(176)}else{k(177)}})
$o=n;$o.icon=i("op");$o.text="Options"
$o.add_click({& "$f\Options.ps1"})
$o,$n,$p|%{$_.visible=$true}
#while keeps taskbar icons visible, and keeps script running
#reducing sleep time to increases CPU usage much
#clearing host keeps ram usage stable, otherwise smtc outputs increase ram usage over time
While(1){
pf|Out-Null
[System.GC]::Collect()
Clear-Host
[Microsoft.PowerShell.PSConsoleReadLine]::ClearHistory()
start-sleep -s 1
} sorry for short variable names but it reduces RAM usage much on powershell scripts i prefer to not using sample cmd exe at this point smtc works nice, thanks to you icon files im reducing priorty to low for easier process selection on windows startup i launch with a vbs file that checks is there a powershell process with low priority. this one prevents multiple launches
|
I see, doing a bit of research on Regarding the RAM, I've only used Powershell for some automation at my old job. So, I'm not too proficient in a lot of the details/complicated parts. |
Unfortunately, seems I couldn't get it working. The issue of not supporting WinRT events seems to be a very long-standing one (PowerShell/PowerShell#2181). I'll close this as it's the most I can do in terms of helping you. If you have any further questions don't hesitate to ask. |
thanks for all infos, you really helped much |
Thanks for sharing this one
im trying to get playback status, other infos would be nice too
is that possible to get data on powershell
The text was updated successfully, but these errors were encountered: