Как в ListBox (WPF) добавить иконку?

281
06 июня 2018, 12:40

Есть ListBox в который выводится список папок и файлов. Как в каждый item добавить маленькую иконку (как в Total Commander например)? По сути не понимаю ток как добавить эту иконку, а какую именно добавлять уже сам разберусь. Код прикрепил для примера, на всякий, так сказать

            listFiles.Items.Clear();
            ListFiles.varListPath = pathDir;
            DirectoryInfo dir = new DirectoryInfo(pathDir);
            DirectoryInfo[] dirs = dir.GetDirectories();
            listFiles.Items.Add("..");
            foreach (DirectoryInfo ListDir in dirs)
                listFiles.Items.Add(ListDir);
            FileInfo[] files = dir.GetFiles();
            foreach (FileInfo ListFiles in files)
                listFiles.Items.Add(ListFiles);
Answer 1

Отвечу сразу на вопрос.
Для подобных вещей создаются стили, которые переопределяют тот или иной элемент.

В нашем случае давайте создадим самый простой ListBox, который будет содержать в себе иконку и название файла:

<ListBox ItemsSource="{Binding Items}">
    <ListBox.ItemTemplate>
        <DataTemplate>
            <StackPanel Orientation="Horizontal">
                <Image Source="{Binding Image}" MaxWidth="20" MaxHeight="20" Margin="0,0,5,0"/>
                <TextBlock Text="{Binding Name}"/>
            </StackPanel>
        </DataTemplate>
    </ListBox.ItemTemplate>
</ListBox>

Видно, что мы указали нашему ListBox другой ItemTemplate, который содержит StackPanel с нужными элементами.

Собственно это все.

Давайте попробуем теперь заставить это работать.
Для этого нам понадобится некий класс, который будет содержать в себе свойства названия и иконки, ну и для удобства сделаем заполнение этих свойств через конструктор:

public class ItemModel
{
    public ItemModel(string name, ImageSource image)
    {
        Name = name;
        Image = image;
    }
    public string Name { get; set; }
    public ImageSource Image { get; set; }
}

Теперь я для теста создам некую коллекцию в которую добавлю все файлы из папки Windows.

public ObservableCollection<ItemModel> Items { get; set; } = new ObservableCollection<ItemModel>();
public MainWindow()
{
    InitializeComponent();
    DataContext = this;
    var files = Directory.GetFiles(@"C:\Windows");
    foreach (var file in files)
    {
        ImageSource imageSource = null;
        FileInfo fileInfo = new FileInfo(file);
        Icon icon = System.Drawing.Icon.ExtractAssociatedIcon(fileInfo.FullName);
        if (icon != null)
        {
            using (var bmp = icon.ToBitmap())
            {
                var stream = new MemoryStream();
                bmp.Save(stream, System.Drawing.Imaging.ImageFormat.Png);
                imageSource = BitmapFrame.Create(stream);
            }
        }
        Items.Add(new ItemModel(fileInfo.Name, imageSource));
    }
}

Поясню:

  • DataContext = this; - указываем источник данных для привязки.
  • var files = Directory.GetFiles(@"C:\Windows"); - получаем все файлы из указанной директории.
  • foreach (var file in files) - проходимся по всем файлам.
  • FileInfo fileInfo = new FileInfo(file); - получаем информацию о файле.
  • Icon icon = System.Drawing.Icon.ExtractAssociatedIcon(fileInfo.FullName); - получаем иконку файла.
  • using (var bmp = icon.ToBitmap()) - переводим иконку в ImageSource.
  • Items.Add(new ItemModel(fileInfo.Name, imageSource)); - добавляем данные в коллекцию.

Запускаем и любуемся:

READ ALSO
c#. Как реализовать ожидание выполнения функции?

c#. Как реализовать ожидание выполнения функции?

Имеется такой цикл с подпиской на событие:

314
Ошибка 6002, 6013, 6005 Entity Framework

Ошибка 6002, 6013, 6005 Entity Framework

Что можно сделать с ошибками такого рода или как их полечить? Код в базе менять нельзя

265
Как подключить mySQL к Python 3.6? [закрыт]

Как подключить mySQL к Python 3.6? [закрыт]

Уже насмотрелся разных видео по работе с субдНо ничего толкового так и не нашёл

227
Парсинг цифр из строки

Парсинг цифр из строки

Есть переменная:

214