How to color each row in listView in wpf ?

Chocolade 536 Reputation points
2023-01-05T16:19:54.127+00:00

The xaml code with the listView

<Window x:Class="Lab_ListView.MainWindow"  
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"  
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"  
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"  
        xmlns:local="clr-namespace:Lab_ListView"  
        mc:Ignorable="d"  
        Title="Video Game List" Height="450" Width="800">  
  
    <Grid Margin="0,0,10,10">  
        <Label Content="Game Name" HorizontalAlignment="Left" Margin="40,59,0,0" VerticalAlignment="Top"/>  
        <TextBox x:Name="GameNameTextBox" HorizontalAlignment="Left" Height="23" Margin="121,62,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="366"/>  
        <Button x:Name="AddBtn" Content="Add" HorizontalAlignment="Left" Margin="121,151,0,0" VerticalAlignment="Top" Width="75" Click="AddBtn_Click"/>  
        <ListView x:Name="listView" ScrollViewer.CanContentScroll="True" ScrollViewer.VerticalScrollBarVisibility="Auto" Grid.Row="1">  
            <ListView.View>  
                <GridView>  
                    <GridViewColumn Header="IP"  DisplayMemberBinding="{Binding IP}" Width="Auto"/>  
                    <GridViewColumn Header="PING" DisplayMemberBinding="{Binding Ping}" Width="Auto"/>  
                    <GridViewColumn Header="Host Name" DisplayMemberBinding="{Binding DNS}" Width="Auto"/>  
                    <GridViewColumn Header="Mac" DisplayMemberBinding="{Binding MAC}" Width="Auto"/>  
                    <GridViewColumn Header="Výrobce" DisplayMemberBinding="{Binding Manufacturer}" Width="Auto"/>  
                </GridView>  
            </ListView.View>  
        </ListView>  
        <Button Content="Button" HorizontalAlignment="Left" Margin="101,99,0,0" VerticalAlignment="Top" Click="Button_Click"/>  
        <Button Content="Button" HorizontalAlignment="Left" Margin="31,99,0,0" VerticalAlignment="Top" Click="Button_Click_1"/>  
    </Grid>  
</Window>  

The main window cs code

using System;  
using System.Collections.Generic;  
using System.Globalization;  
using System.Linq;  
using System.Reflection;  
using System.Text;  
using System.Threading;  
using System.Threading.Tasks;  
using System.Windows;  
using System.Windows.Controls;  
using System.Windows.Data;  
using System.Windows.Documents;  
using System.Windows.Input;  
using System.Windows.Media;  
using System.Windows.Media.Imaging;  
using System.Windows.Navigation;  
using System.Windows.Shapes;  
  
namespace Lab_ListView  
{  
    /// <summary>  
    /// Interaction logic for MainWindow.xaml  
    /// </summary>  
    public partial class MainWindow : Window  
    {  
        List<ListViewItem> ITEMS = new List<ListViewItem>();  
  
        public MainWindow()  
        {  
            InitializeComponent();  
  
            this.WindowStartupLocation = WindowStartupLocation.CenterScreen;  
        }  
  
        public class Device  
        {  
            public string IP { get; set; }  
            public string Ping { get; set; }  
            public string DNS { get; set; }  
            public string MAC { get; set; }  
            public string Manufacturer { get; set; }  
        }  
  
        private void ChangeRowColor(int RowIndex, SolidColorBrush NewBackground)  
        {  
            ITEMS[RowIndex].Background = NewBackground;  
            listView.Items.Refresh();  
        }  
  
        private void Button_Click(object sender, RoutedEventArgs e)  
        {  
            for (int i = 1; i < 20; i++)  
            {  
                ListViewItem OneItem = new ListViewItem();  
                OneItem.Background = Brushes.LightGray;  
                OneItem.Content = new Device() { IP = "1.1.1.1", Ping = "30ms", DNS = "XYZ", MAC = "2F:3C:5F:41:F9", Manufacturer = "Intel" };  
                ITEMS.Add(OneItem);  
                listView.ItemsSource = ITEMS;  
            }  
            listView.Items.Refresh();  
        }  
  
        private async Task Button_Click_1(object sender, RoutedEventArgs e)  
        {  
            await Main();  
        }  
  
        public async Task Main()  
        {  
            await Task.Run(() => {  
                // Just loop.  
                for (int i = 0; i < ITEMS.Count; i++)  
                {  
                    var random = new Random();  
                    var b = PickRandomBrush(random);  
                    ChangeRowColor(i, (SolidColorBrush)b);  
                }  
            });  
        }  
  
        private Brush PickRandomBrush(Random rnd)  
        {  
            Brush result = Brushes.Transparent;  
            Type brushesType = typeof(Brushes);  
            PropertyInfo[] properties = brushesType.GetProperties();  
            int random = rnd.Next(properties.Length);  
            result = (Brush)properties[random].GetValue(null, null);  
            return result;  
        }  
    }  
}  
  

First i click the button to add the items to the listView then i click the button1 to color the items.

If i'm just making in the button1 click event :

System.Windows.Media.SolidColorBrush bb = new SolidColorBrush();  
bb.Color = Colors.Red;  
ChangeRowColor(1, bb);  

it will color the first row in index 1 at red.

but i want to make some changes and add some stuff.

i want to make the loop of changing the colors in a thread that's why i'm using async Task.
i want few things to do :

  1. to make the loop of colors changing in a thread so it will not freeze the whole application.
  2. to make it to change each row to a different random color each time nonstop.
  3. first to make it once i can't make it to change each row in a different color. if i'm using this loop in a regular button click event it will color all the row's in the same random picked color.
  4. i want that each row will have another color ! and then to make it in a thread and also to make it nonstop changing the colors maybe using a timer ?

another problem is that i'm getting error on line 25 in the Mainwindow.xaml

<Button Content="Button" HorizontalAlignment="Left" Margin="31,99,0,0" VerticalAlignment="Top" Click="Button_Click_1"/>  

The error :

Severity Code Description Project File Line Suppression State
Error CS0407 'Task MainWindow.Button_Click_1(object, RoutedEventArgs)' has the wrong return type Lab-ListView C:\Lab-ListView-master\Lab-ListView-master\Lab-ListView\MainWindow.xaml 25 Active

Windows Presentation Foundation
Windows Presentation Foundation
A part of the .NET Framework that provides a unified programming model for building line-of-business desktop applications on Windows.
2,813 questions
C#
C#
An object-oriented and type-safe programming language that has its roots in the C family of languages and includes support for component-oriented programming.
11,210 questions
XAML
XAML
A language based on Extensible Markup Language (XML) that enables developers to specify a hierarchy of objects with a set of properties and logic.
830 questions
0 comments No comments
{count} votes

Accepted answer
  1. Peter Fleischer (former MVP) 19,331 Reputation points
    2023-01-05T20:11:50.027+00:00

    Hi,
    try following demo as MVVM with your code:

    <Window x:Class="WpfApp1.Window116"  
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"  
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
            xmlns:d="http://schemas.microsoft.com/expression/blend/2008"  
            xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"  
            xmlns:local="clr-namespace:WpfApp116"  
            mc:Ignorable="d"  
            Title="Chocolade-4229_230105" Height="450" Width="800">  
      <Window.DataContext>  
        <local:ViewModel/>  
      </Window.DataContext>  
      <Grid Margin="0,0,10,10">  
        <Label Content="Game Name" HorizontalAlignment="Left" Margin="40,59,0,0" VerticalAlignment="Top"/>  
        <TextBox x:Name="GameNameTextBox" HorizontalAlignment="Left" Height="23" Margin="121,62,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="366"/>  
        <Button x:Name="AddBtn" Content="Add" HorizontalAlignment="Left" Margin="121,151,0,0" VerticalAlignment="Top" Width="75" Command="{Binding}" CommandParameter="AddBtn_Click"/>  
        <ListView x:Name="listView" ScrollViewer.CanContentScroll="True" ScrollViewer.VerticalScrollBarVisibility="Auto" Grid.Row="1" ItemsSource="{Binding View}">  
          <ListView.ItemContainerStyle>  
            <Style TargetType="ListViewItem">  
              <Setter Property="Background" Value="{Binding BackgroundColor}"/>  
            </Style>   
            </ListView.ItemContainerStyle>  
          <ListView.View>  
            <GridView>  
              <GridViewColumn Header="IP"  DisplayMemberBinding="{Binding IP}" Width="Auto"/>  
              <GridViewColumn Header="PING" DisplayMemberBinding="{Binding Ping}" Width="Auto"/>  
              <GridViewColumn Header="Host Name" DisplayMemberBinding="{Binding DNS}" Width="Auto"/>  
              <GridViewColumn Header="Mac" DisplayMemberBinding="{Binding MAC}" Width="Auto"/>  
              <GridViewColumn Header="Výrobce" DisplayMemberBinding="{Binding Manufacturer}" Width="Auto"/>  
            </GridView>  
          </ListView.View>  
        </ListView>  
        <Button Content="Button" HorizontalAlignment="Left" Margin="101,99,0,0" VerticalAlignment="Top" Command="{Binding}" CommandParameter="Button_Click"/>  
        <Button Content="Button" HorizontalAlignment="Left" Margin="31,99,0,0" VerticalAlignment="Top" Command="{Binding}" CommandParameter="Button_Click_1"/>  
      </Grid>  
    </Window>  
    

    and ViewModel:

    using System;  
    using System.Collections.ObjectModel;  
    using System.ComponentModel;  
    using System.Reflection;  
    using System.Runtime.CompilerServices;  
    using System.Threading.Tasks;  
    using System.Windows;  
    using System.Windows.Data;  
    using System.Windows.Input;  
    using System.Windows.Media;  
      
    namespace WpfApp116  
    {  
    	public class ViewModel : ICommand, INotifyPropertyChanged  
    	{  
    		private CollectionViewSource cvs = new CollectionViewSource();  
    		private ObservableCollection<Device> col = new ObservableCollection<Device>();  
      
    		public ICollectionView View { get => cvs.View; }  
      
    		public event EventHandler CanExecuteChanged;  
    		public bool CanExecute(object parameter) => true;  
    		public async void Execute(object parameter)  
    		{  
    			switch (parameter.ToString())  
    			{  
    				case "AddBtn_Click":  
    					break;  
    				case "Button_Click":  
    					for (int i = 1; i < 20; i++)  
    					{  
    						Device dev = new Device() { IP = "1.1.1.1", Ping = "30ms", DNS = "XYZ", MAC = "2F:3C:5F:41:F9", Manufacturer = "Intel" };  
    						col.Add(dev);  
    					}  
    					cvs.Source = col;  
    					OnPropertyChanged(nameof(View));  
    					break;  
    				case "Button_Click_1":  
    					await Main();  
    					break;  
    				default:  
    					break;  
    			}  
    		}  
      
    		Random random = new Random();  
      
    		private async Task Main()  
    		{  
    			await Task.Run(() =>  
    			{  
    				// Just loop.  
    				foreach (Device dev in col) dev.BackgroundColor = PickRandomBrush(random);  
    			});  
    		}  
      
    		private Brush PickRandomBrush(Random rnd)  
    		{  
    			Brush result = Brushes.Transparent;  
    			Type brushesType = typeof(Brushes);  
    			PropertyInfo[] properties = brushesType.GetProperties();  
    			int random = rnd.Next(properties.Length);  
    			result = (Brush)properties[random].GetValue(null, null);  
    			return result;  
    		}  
      
    		public event PropertyChangedEventHandler PropertyChanged;  
    		protected void OnPropertyChanged([CallerMemberName] string propName = "") =>  
    			PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propName));  
    	}  
      
    	public class Device : INotifyPropertyChanged  
    	{  
    		public string IP { get; set; }  
    		public string Ping { get; set; }  
    		public string DNS { get; set; }  
    		public string MAC { get; set; }  
    		public string Manufacturer { get; set; }  
      
    		private Brush _backgroundColor;  
    		public Brush BackgroundColor  
    		{  
    			get => this._backgroundColor;  
    			set  
    			{  
    				this._backgroundColor = value;  
    				OnPropertyChanged();  
    			}  
    		}  
      
    		public event PropertyChangedEventHandler PropertyChanged;  
    		protected void OnPropertyChanged([CallerMemberName] string propName = "") =>  
    			PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propName));  
    	}  
    }  
    

    Result:

    276658-x.gif

    1 person found this answer helpful.
    0 comments No comments

0 additional answers

Sort by: Most helpful

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.