public/Add-ContextMenuToControl.ps1
<# .SYNOPSIS Adds custom context menu to control for type-sensitive menu items .DESCRIPTION Adds custom context menu to control for type-sensitive menu items. Event handler inspects PSTypeNames of object clicked on, builds appropriate menu, displays it, and responds to menu item clicks .PARAMETER window The window that the control is in .PARAMETER controlName The name of the control (used if Control is not passed) .PARAMETER control The control .PARAMETER Output An optional scriptblock to use to send output from a menu clicked event. .EXAMPLE An example .NOTES General notes #> function Add-ContextMenuToControl{ Param([Parameter(ParameterSetName='NamedControl')]$window, [Parameter(ParameterSetName='NamedControl')]$controlName, [Parameter(ParameterSetName='ControlObject')]$control, [scriptblock]$Output) if($output){ $script:output=$output } if(-not $control){ $control=$window.GetControlByName($controlname) } $control.ContextMenu=new-object System.Windows.Controls.ContextMenu $control.Add_ContextMenuOpening({ Param($sender,$e) if($this| get-member -Name Items){ $selectedItem=$this.SelectedItem $clickedItem=$selectedItem } else { $selectedItem=$this $clickedItem=$this } if($SelectedItem -is [System.Windows.Controls.Control] -and $selectedItem.Tag){ $selectedItem=$selectedItem.Tag } if($null -eq $selectedItem){ $e.handled=$true } else { $items=get-RelevantMenuItems -item $selectedItem $items |foreach-object { $item=$_ $script=[scriptblock]($item.Tag) $useControl=[boolean]($item | get-member UseControl) $item.Add_click({ #LocalOutHost '--------------------' if($useControl){ $selectedItem=$clickedItem } $values=& $script $selectedItem $values | out-string -Width 200 | LocalOutHost #LocalOutHost '--------------------' }.GetNewClosure()) $this.ContextMenu.Items.Add($item) | out-null} } }) $control.add_ContextMenuClosing({ $this.ContextMenu.Items.Clear() }) } |