ListBox交替着色PowerShell

时间:2016-08-16 18:18:51

标签: forms winforms powershell

我似乎被困在尝试为我的表单添加一些风格。我有一个ListBox,我想为每隔一行添加备用着色。这甚至可能吗?我试着查看$ ListBox.Items属性,下面我没有看到任何背景选项。有什么想法吗?

$ListBox = New-Object System.Windows.Forms.ListBox
$ListBox.Size = '325,95'
$ListBox.Location = '345,25'
$ListBox.Items.Add("Checking...") > $null

2 个答案:

答案 0 :(得分:1)

使用Windows窗体中的ListBox控件执行此操作的唯一方法是劫持每行的实际绘图。

首先,更改DrawMode的<{1}}属性:

ListBox

这将允许我们通过the DrawItem event覆盖项目的图形呈现。

现在我们需要的是定义将绘制项目的函数。我发现this great example in C#正在进行备用行颜色而不会影响所选项目。

幸运的是,C#是easily ported to PowerShell

$ListBox.DrawMode = [System.Windows.Forms.DrawMode]::OwnerDrawFixed

Et瞧:

Alternate row colors in ListBox

答案 1 :(得分:0)

根据您的代码的外观,您不是在使用XAML,但我想将其添加为替代方法。

您可以通过将XAML编写为UI的前端代码并在触发器中指定setter属性来设置样式触发器来设置此项。然后在ListBox控件中,您可以指定在ItemContanerStyle属性上创建的样式的名称,并指定AlertnationCount为2,以便使用您指定的颜色突出显示每一行。

下面的示例显示了在向列表框添加文本时它的工作原理。

#Build the GUI
[xml]$xaml = @"
<Window 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    x:Name="Window" Title="Initial Window" WindowStartupLocation = "CenterScreen" 
    Width = "313" Height = "800" ShowInTaskbar = "True" Background = "lightgray"> 
    <ScrollViewer VerticalScrollBarVisibility="Auto">
        <StackPanel >
            <StackPanel.Resources>
                <Style x:Key="AlternatingRowStyle" TargetType="{x:Type Control}" >
                    <Setter Property="Background" Value="LightBlue"/>
                    <Setter Property="Foreground" Value="Black"/>
                    <Style.Triggers>
                        <Trigger Property="ItemsControl.AlternationIndex" Value="1">                            
                            <Setter Property="Background" Value="White"/>
                            <Setter Property="Foreground" Value="Black"/>                                
                        </Trigger>                            
                    </Style.Triggers>
                </Style>     
            </StackPanel.Resources>
            <TextBox  IsReadOnly="True" TextWrapping="Wrap">
                Type something and click Add
            </TextBox>
            <TextBox x:Name = "inputbox"/>
            <Button x:Name="button1" Content="Add"/>
            <Button x:Name="button2" Content="Remove"/>
            <Expander IsExpanded="True">
                <ListBox x:Name="listbox" SelectionMode="Extended" AlternationCount="2"                 
                ItemContainerStyle="{StaticResource AlternatingRowStyle}"/>
            </Expander >
        </StackPanel>
    </ScrollViewer >
</Window>
"@

$reader=(New-Object System.Xml.XmlNodeReader $xaml)
$Window=[Windows.Markup.XamlReader]::Load( $reader )
 
#region Connect to Controls    
Write-Verbose "Connecting to controls"
$xaml.SelectNodes("//*[@*[contains(translate(name(.),'n','N'),'Name')]]") | ForEach {
    New-Variable -Name $_.Name -Value $Window.FindName($_.Name) -Force
}
#endregion Connect to Controls

$Window.Add_SourceInitialized({
    #Have to have something initially in the collection
    $Script:observableCollection = New-Object System.Collections.ObjectModel.ObservableCollection[string]
    $listbox.ItemsSource = $observableCollection
    $inputbox.Focus()
})
 
#Events
$button1.Add_Click({
     $observableCollection.Add($inputbox.text)
     $inputbox.Clear()
})
$button2.Add_Click({
    ForEach ($item in @($listbox.SelectedItems)) {
        $observableCollection.Remove($item)
    }
}) 
$Window.ShowDialog() | Out-Null