Музей юмора - только отборный юмор

Музей юмора

для остроумных людей с хорошим чувством юмора и для программистов
Поиск смешное про:
Искать

Библиотека CSF MVVM

calabonga 22.08.2010 Программы NET

Silverlight 4: MVVM + ListBox или демонстрация библиотеки CSF-MVVM

Очень часто приходится писать небольшие программки (Silverlight), например, чтобы протестировать ту или иную функцию. Так вот, каждый раз проводить подготовку для того чтобы хотя бы просто запустить проект дело не быстрое. Что такое “подготовка”? Например, написать класс, который будет базовым для всех ViewModel’s и будет реализовывать интерфейс INotifyPropertyChanged. Или написать DelegateCommand<T>, который реализует ICommand интерфейс. Или еще какие-нибудь полезные и правильные вещи. Много и часто пользовался MVVM Light Toolkit, но часто бывает что и эта библиотечка большая и требует немного больше времени, чем можно себе позволить.

Именно от того, что лень – двигатель прогресса, как-то сама собой написалась простенька и легковесная библиотека для разработки Silverlight-приложение с использованием MVVM шаблона программирования. Размер библиотеки  (Calabonga.Silverlight.Framework.dll) всего 12 Кб, ну просто очень легкая!

Итак, теперь примеры использования.

Допустим у нас есть класс:

public class Person
   
{
        public string FirstName { get; set; }
        public string LastName { get; set; }
        public int Age { get; set; }
    }

Очень простой класс. А еще у нас есть поставленная задача, использую MVVM сделать какую-нибудь выборку из ListBox в “куда-нибудь”. Очень простая и довольно тупая задача. Ну что ж, как говорят французы - “се ля ви” (такова жизнь). Чего не придумаешь лишь бы показать что может делать библиотека.

Создадим класс PersonsViewModel и унаследуем его от ViewModelBase, что уже содержится в CFF-MVVM. Прилепим к этому классу некоторые команды и свойства:

public class PersonsViewModel : ViewModelBase {
        #region конструктор
        public PersonsViewModel()
        {
            if (!DesignerProperties.IsInDesignTool)
            {
                GeneratePersonList();
            }
        }
        #endregion

        #region
скрытые методы
        private void GeneratePersonList()
        {
            List<Person> list = new List<Person>()
            {
               new Person(){ FirstName="Владлен", LastName="Суходрищев", Age=32},
               new Person(){ FirstName="Афонасий", LastName="Пискоструев", Age=22},
               new Person(){ FirstName="Антон", LastName="Застратов", Age=36}
            };

            PersonList = new ObservableCollection<Person>(list);
        }
        #endregion

        #region
команда RemoveSelectionCommand

        /// <summary>
        ///
Команда RemoveSelectionCommand
       
/// </summary>
       
public DelegateCommand<ListBox> RemoveSelectionCommand
        {
            get
           
{
                return new DelegateCommand<ListBox>((e) => this.RemoveSelectionCommandExecute(e));
            }
        }

        /// <summary>
        ///
Процедура выполняет команды RemoveSelectionCommand
       
/// </summary>
       
private void RemoveSelectionCommandExecute(ListBox list)
        {
            // выполнение команды ShowSelection
           
MessageBox.Show("Отменен выбор: " + list.SelectedItems.Count.ToString() + " элемента(ов)");
            list.SelectedItem = null;
            this.SelectedList.Clear();
            OnPropertyChanged(SelectedListPropertyName);
        }       

        #endregion // end команда RemoveSelectionCommand

       
#region команда UpdateSelectionCommand

        /// <summary>
        ///
Команда UpdateSelectionCommand
       
/// </summary>
       
public DelegateCommand<SelectionChangedEventArgs> UpdateSelectionCommand
        {
            get
           
{
                return new DelegateCommand<SelectionChangedEventArgs>((e) => this.UpdateSelectionCommandExecute(e),
                    (e) => this.CanExecuteUpdateSelection(e));
            }
        }

        /// <summary>
        ///
Процедура выполняет команды UpdateSelectionCommand
       
/// </summary>
       
private void UpdateSelectionCommandExecute(SelectionChangedEventArgs e)
        {
            // выполнение команды UpdateSelection
           
foreach (Person person in e.AddedItems)
            {
                if (!this.SelectedList.Contains(person))
                {
                    this.SelectedList.Add(person); 
                }
            }
            foreach (Personperson ine.RemovedItems)
            {
                this.SelectedList.Remove(person);
            }
        }
        /// <summary>
        ///
Свойство проверки возможности выполнения команды UpdateSelectionCommand()
      
/// </summary>
      
private boolCanExecuteUpdateSelection(SelectionChangedEventArgse)
        {
            // разрешен ли запуск команды
           
returne.AddedItems.Count > 0;
        }

        #endregion// end команда UpdateSelectionCommand

      
#regionсвойство PersonList

        /// <summary>
        ///
поле для хранения значений свойства<see cref="PersonList"/>
        /// </summary>
      
privateObservableCollection<Person> personList = null;

        /// <summary>
        ///
наименование поля для свойства<see cref="PersonList"/>
        /// </summary>
      
private const stringPersonListPropertyName = "PersonList";

        /// <summary>
        ///
описание.
      
/// </summary>
      
publicObservableCollection<Person> PersonList
        {
            get
          
{
                returnpersonList;
            }
            set
          
{
                personList = value;
                OnPropertyChanged(PersonListPropertyName);
            }
        }

        #endregionсвойство PersonList

        #regionсвойство SelectedList

        /// <summary>
        ///
поле для хранения значений свойства<see cref="SelectedList"/>
        /// </summary>
      
privateObservableCollection<Person> selectedPersons = newObservableCollection<Person>();

        /// <summary>
        ///
наименование поля для свойства<see cref="SelectedList"/>
        /// </summary>
      
private const stringSelectedListPropertyName = "SelectedList";

        /// <summary>
        ///
описание.
      
/// </summary>
      
publicObservableCollection<Person> SelectedList
        {
            get
          
{
                returnselectedPersons;
            }
            set
          
{
                selectedPersons = value;
                OnPropertyChanged(SelectedListPropertyName);
            }
        }

        #endregionсвойство SelectedList

А также не помешает создать класс представления для нашего приложения, в котором будет два контрола типа ListBox. В одном можно будет выбирать Items, а в другом будет показываться выбор. Кажется всё просто, но тут возникает некоторая заминка, как обработать событие SelectionChanged, если в код-behind мы ничего не должны писать (так гласит основной принцип программирования по шаблону MVVM). Помощь в решении данной проблемы окажет прикольная штука EventToCommand из моей библиотеки:

1) подключаем необходимые namespace’ы:

xmlns:csf="clr-namespace:Calabonga.Silverlight.Framework;assembly=Calabonga.Silverlight.Framework"xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity"

2) теперь в самом ListBox подключаем:

<ListBox ItemsSource="{Binding Path=PersonList}"
                Margin="12,0,244,6"
                Background="#FFF4FFFF"
                x:Name="list"
                SelectionMode="Extended"
                Grid.Row="1">           
            <ListBox.ItemTemplate>
                <DataTemplate>
                    <StackPanel Margin="5 0">
                        <StackPanel Orientation="Horizontal">
                            <TextBlock Text="{Binding Path=FirstName}"
                                      Margin="0 0 5 0" />
                            <TextBlock Text="{Binding Path=LastName}" />
                        </StackPanel>
                        <StackPanel Orientation="Horizontal">
                            <TextBlock Text="Возраст:"
                                      Margin="0 0 5 0" />
                            <TextBlock Text="{Binding Path=Age}" />
                        </StackPanel>
                    </StackPanel>
                </DataTemplate>
            </ListBox.ItemTemplate>
            <i:Interaction.Triggers>
                <i:EventTrigger EventName="SelectionChanged">
                    <csf:EventToCommand Command="{Binding Path=UpdateSelectionCommand}"
                                       IsSendEventArgsToCommand="True" />
                </i:EventTrigger>
            </i:Interaction.Triggers>
        </ListBox>

Вот, собственно говоря, и всё.

Скачать демонстрационный проект
Скачать библиотеку (Текущая версия: 1.1.7)

Просмотрено раз: 2712

Комментарии