Model-View-View Model を利用した汎用性のあるクラス ライブラリの使用Using Portable Class Library with Model-View-View Model

.NET Framework を使用してポータブル クラス ライブラリモデル-ビュー-ビュー モデル (MVVM) パターンを実装して、複数のプラットフォームでアセンブリを共有します。You can use the .NET Framework Portable Class Library to implement the Model-View-View Model (MVVM) pattern and share assemblies across multiple platforms.

重要

Because Portable Class Library projects target only a very specific subset of .NET implementations, we strongly discourage their use in new application development. The recommended replacement is a .NET Standard library, which targets all .NET implementations that support a specific version of the .NET Standard. For more information, see .NET Standard.

MVVM では、基になるビジネス ロジックからユーザー インターフェイスを分離するアプリケーション パターンです。MVVM is an application pattern that isolates the user interface from the underlying business logic. モデルとビュー モデル クラスを実装することができます、ポータブル クラス ライブラリPortable Class LibraryプロジェクトVisual Studio 2012Visual Studio 2012、し、さまざまなプラットフォーム用にカスタマイズされたビューを作成します。You can implement the model and view model classes in a ポータブル クラス ライブラリPortable Class Library project in Visual Studio 2012Visual Studio 2012, and then create views that are customized for different platforms. このアプローチでは、データを記述できます。 モデルとビジネス ロジックを 1 回だけ、.NET Framework、Silverlight、Windows Phone のコードを使用およびWindows 8.x ストアWindows 8.x Storeアプリは、次の図に示すようにします。This approach enables you to write the data model and business logic only once, and use that code from .NET Framework, Silverlight, Windows Phone, and Windows 8.x ストアWindows 8.x Store apps, as shown in the following illustration.

MVVM のダイアグラムを含むポータブルPortable with MVVM diagram

このトピックでは、MVVM パターンに関する一般的な情報は提供されません。This topic does not provide general information about the MVVM pattern. 使用する方法についての情報を提供するだけポータブル クラス ライブラリPortable Class LibraryMVVM を実装します。It only provides information about how to use ポータブル クラス ライブラリPortable Class Library to implement MVVM. MVVM の詳細については、次を参照してください。、 MVVM のクイック スタートします。For more information about MVVM, see the MVVM Quickstart.

MVVM をサポートするクラスClasses That Support MVVM

対象とする場合、 .NET Framework 4.5.NET Framework 4.5Windows 8.x ストア アプリ用 .NET.NET for Windows 8.x Store apps、Silverlight、または Windows Phone 7.5 for、ポータブル クラス ライブラリPortable Class Libraryプロジェクトでは、次のクラスは MVVM パターンを実装するために使用できます。When you target the .NET Framework 4.5.NET Framework 4.5, Windows 8.x ストア アプリ用 .NET.NET for Windows 8.x Store apps, Silverlight, or Windows Phone 7.5 for your ポータブル クラス ライブラリPortable Class Library project, the following classes are available for implementing the MVVM pattern:

MVVM の実装Implementing MVVM

MVVM を実装するために通常作成モデルとでは、ビュー モデルの両方をポータブル クラス ライブラリPortable Class Library、ため、プロジェクト、ポータブル クラス ライブラリPortable Class Libraryプロジェクトがポータブルでないプロジェクトを参照できません。To implement MVVM, you typically create both the model and the view model in a ポータブル クラス ライブラリPortable Class Library project, because a ポータブル クラス ライブラリPortable Class Library project cannot reference a non-portable project. モデルとビュー モデルは、同じプロジェクト内、または別のプロジェクトを指定できます。The model and view model can be in the same project or in separate projects. 個別のプロジェクトを使用する場合は、モデル プロジェクトにビューのモデル プロジェクトからの参照を追加します。If you use separate projects, add a reference from the view model project to the model project.

モデルをコンパイルし、モデル プロジェクトを表示すると後、は、ビューを含むアプリでそれらのアセンブリを参照します。After you compile the model and view model projects, you reference those assemblies in the app that contains the view. ビューは、ビュー モデルとのみやり取りをする場合のみ、ビュー モデルを含むアセンブリを参照する必要があります。If the view interacts only with the view model, you only have to reference the assembly that contains the view model.

モデルModel

次の例にある単純なモデル クラスを示しています、ポータブル クラス ライブラリPortable Class Libraryプロジェクト。The following example shows a simplified model class that could reside in a ポータブル クラス ライブラリPortable Class Library project.

using System;

namespace SimpleMVVM.Model
{  
    public class Customer
    {
        public int CustomerID
        {
            get; 
            set;   
        }

        public string FullName
        {
            get;
            set;
        }

        public string Phone
        {
            get; 
            set;
        }
    }
}
Namespace SimpleMVVM.Model

    Public Class Customer
        Public Property CustomerID() As Integer
        Public Property FullName() As String
        Public Property Phone() As String
    End Class
End Namespace

次の例では、設定、取得、およびデータを更新する簡単な方法を示しています、ポータブル クラス ライブラリPortable Class Libraryプロジェクト。The following example shows a simple way to populate, retrieve, and update the data in a ポータブル クラス ライブラリPortable Class Library project. 実際のアプリでは、Windows Communication Foundation (WCF) サービスなどのソースからデータを取得します。In a real app, you would retrieve the data from a source such as a Windows Communication Foundation (WCF) service.

using System;
using System.Collections.Generic;
using System.Linq;

namespace SimpleMVVM.Model
{
    public class CustomerRepository
    {
        private List<Customer> _customers;

        public CustomerRepository()
        {
            _customers = new List<Customer>
            {
                new Customer(){ CustomerID = 1, FullName="Dana Birkby", Phone="394-555-0181"},
                new Customer(){ CustomerID = 2, FullName="Adriana Giorgi", Phone="117-555-0119"},
                new Customer(){ CustomerID = 3, FullName="Wei Yu", Phone="798-555-0118"}
            };
        }

        public List<Customer> GetCustomers()
        {
            return _customers;
        }

        public void UpdateCustomer(Customer SelectedCustomer)
        {
            Customer customerToChange = _customers.Single(c => c.CustomerID == SelectedCustomer.CustomerID);
            customerToChange = SelectedCustomer;
        }
    }
}
Namespace SimpleMVVM.Model
    Public Class CustomerRepository
        Private _customers As List(Of Customer)

        Public Sub New()
            _customers = New List(Of Customer) From
            {
                New Customer() With {.CustomerID = 1, .FullName = "Dana Birkby", .Phone = "394-555-0181"},
                New Customer() With {.CustomerID = 2, .FullName = "Adriana Giorgi", .Phone = "117-555-0119"},
                New Customer() With {.CustomerID = 3, .FullName = "Wei Yu", .Phone = "798-555-0118"}
            }
        End Sub

        Public Function GetCustomers() As List(Of Customer)
            Return _customers
        End Function

        Public Sub UpdateCustomer(SelectedCustomer As Customer)
            Dim customerToChange = _customers.Single(Function(c) c.CustomerID = SelectedCustomer.CustomerID)
            customerToChange = SelectedCustomer
        End Sub
    End Class
End Namespace

ビュー モデルView Model

MVVM パターンを実装するときに、ビュー モデルの基本クラスが頻繁に追加されます。A base class for view models is frequently added when implementing the MVVM pattern. 次の例では、基本クラスを示します。The following example shows a base class.

using System;
using System.ComponentModel;

namespace SimpleMVVM.ViewModel
{
    public abstract class ViewModelBase : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        protected virtual void OnPropertyChanged(string propName)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(propName));
            }
        }
    }
}
Imports System.ComponentModel

Namespace SimpleMVVM.ViewModel

    Public MustInherit Class ViewModelBase
        Implements INotifyPropertyChanged

        Public Event PropertyChanged As PropertyChangedEventHandler Implements INotifyPropertyChanged.PropertyChanged

        Protected Overridable Sub OnPropertyChanged(propname As String)
            RaiseEvent PropertyChanged(Me, New PropertyChangedEventArgs(propname))
        End Sub
    End Class
End Namespace

実装、ICommandインターフェイスは、MVVM パターンでよく使用されます。An implementation of the ICommand interface is frequently used with the MVVM pattern. ICommand インターフェイスを実装する例を次に示します。The following example shows an implementation of the ICommand interface.

using System;
using System.Windows.Input;

namespace SimpleMVVM.ViewModel
{
    public class RelayCommand : ICommand
    {
        private readonly Action _handler;
        private bool _isEnabled;

        public RelayCommand(Action handler)
        {
            _handler = handler;
        }

        public bool IsEnabled
        {
            get { return _isEnabled; }
            set
            {
                if (value != _isEnabled)
                {
                    _isEnabled = value;
                    if (CanExecuteChanged != null)
                    {
                        CanExecuteChanged(this, EventArgs.Empty);
                    }
                }
            }
        }

        public bool CanExecute(object parameter)
        {
            return IsEnabled;
        }

        public event EventHandler CanExecuteChanged;

        public void Execute(object parameter)
        {
            _handler();
        }
    }
}
Imports System.Windows.Input

Namespace SimpleMVVM.ViewModel

    Public Class RelayCommand
        Implements ICommand

        Private _isEnabled As Boolean
        Private ReadOnly _handler As Action

        Public Sub New(ByVal hander As Action)
            _handler = hander
        End Sub

        Public Event CanExecuteChanged As EventHandler Implements ICommand.CanExecuteChanged

        Public Property IsEnabled() As Boolean
            Get
                Return _isEnabled
            End Get
            Set(ByVal value As Boolean)
                If (value <> _isEnabled) Then
                    _isEnabled = value
                    RaiseEvent CanExecuteChanged(Me, EventArgs.Empty)
                End If
            End Set
        End Property

        Public Function CanExecute(parameter As Object) As Boolean Implements ICommand.CanExecute
            Return IsEnabled
        End Function

        Public Sub Execute(parameter As Object) Implements ICommand.Execute
            _handler()
        End Sub

    End Class
End Namespace

次の例では、簡略化されたビュー モデルを示します。The following example shows a simplified view model.

using System;
using System.Collections.Generic;
using SimpleMVVM.Model;

namespace SimpleMVVM.ViewModel
{
    public class CustomerViewModel : ViewModelBase
    {
        private List<Customer> _customers;
        private Customer _currentCustomer;
        private CustomerRepository _repository;

        public CustomerViewModel()
        {
            _repository = new CustomerRepository();
            _customers = _repository.GetCustomers();

            WireCommands();
        }

        private void WireCommands()
        {
            UpdateCustomerCommand = new RelayCommand(UpdateCustomer);
        }

        public RelayCommand UpdateCustomerCommand
        {
            get;
            private set;
        }

        public List<Customer> Customers
        {
            get { return _customers; }
            set { _customers = value; }
        }

        public Customer CurrentCustomer
        {
            get
            {
                return _currentCustomer;
            }

            set
            {
                if (_currentCustomer != value)
                {
                    _currentCustomer = value;
                    OnPropertyChanged("CurrentCustomer");
                    UpdateCustomerCommand.IsEnabled = true;
                }
            }
        }

        public void UpdateCustomer()
        {
            _repository.UpdateCustomer(CurrentCustomer);
        }
    }
}
Imports System.Collections.Generic
Imports SimpleMVVM.Model

Namespace SimpleMVVM.ViewModel

    Public Class CustomerViewModel
        Inherits ViewModelBase

        Private _customers As List(Of Customer)
        Private _currentCustomer As Customer
        Private _repository As CustomerRepository
        Private _updateCustomerCommand As RelayCommand

        Public Sub New()
            _repository = New CustomerRepository()
            _customers = _repository.GetCustomers()

            WireCommands()
        End Sub

        Private Sub WireCommands()
            UpdateCustomerCommand = New RelayCommand(AddressOf UpdateCustomer)
        End Sub

        Public Property UpdateCustomerCommand() As RelayCommand
            Get
                Return _updateCustomerCommand
            End Get
            Private Set(value As RelayCommand)
                _updateCustomerCommand = value
            End Set
        End Property

        Public Property Customers() As List(Of Customer)
            Get
                Return _customers
            End Get
            Set(value As List(Of Customer))
                _customers = value
            End Set
        End Property

        Public Property CurrentCustomer() As Customer
            Get
                Return _currentCustomer
            End Get
            Set(value As Customer)
                If _currentCustomer.Equals(value) Then
                    _currentCustomer = value
                    OnPropertyChanged("CurrentCustomer")
                    UpdateCustomerCommand.IsEnabled = True
                End If
            End Set
        End Property

        Public Sub UpdateCustomer()
            _repository.UpdateCustomer(CurrentCustomer)
        End Sub
    End Class
End Namespace

表示View

.NET Framework 4.5.NET Framework 4.5アプリ、Windows 8.x ストアWindows 8.x Storeアプリ、Silverlight ベースのアプリまたは Windows Phone 7.5 アプリの場合は、モデルとビュー モデル プロジェクトを含むアセンブリを参照することができます。From a .NET Framework 4.5.NET Framework 4.5 app, Windows 8.x ストアWindows 8.x Store app, Silverlight-based app, or Windows Phone 7.5 app, you can reference the assembly that contains the model and view model projects. 対話するビューを作成するには、ビュー モデルを使用します。You then create a view that interacts with the view model. 取得し、ビュー モデルからデータを更新する Windows Presentation Foundation (WPF) アプリを簡略化されたは、次の例です。The following example shows a simplified Windows Presentation Foundation (WPF) app that retrieves and updates data from the view model. Windows Phone、Silverlight で同様のビューを作成またはWindows 8.x ストアWindows 8.x Storeアプリ。You could create similar views in Silverlight, Windows Phone, or Windows 8.x ストアWindows 8.x Store apps.

<Window x:Class="SimpleWPF.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:viewModels="clr-namespace:SimpleMVVM.ViewModel;assembly=SimpleMVVM.ViewModel"
        Title="MainWindow" Height="350" Width="525">
    <Window.Resources>
        <viewModels:MainPageViewModel x:Key="ViewModel" />
    </Window.Resources>
    <Grid DataContext="{Binding Source={StaticResource ViewModel}}">
        <Grid.ColumnDefinitions>
            <ColumnDefinition></ColumnDefinition>
            <ColumnDefinition></ColumnDefinition>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="Auto"></RowDefinition>
        </Grid.RowDefinitions>
        <TextBlock Height="23" Margin="5" HorizontalAlignment="Right" Grid.Column="0" Grid.Row="0" Name="textBlock2" 
                   Text="Select a Customer:" VerticalAlignment="Top" />
        <ComboBox Height="23" HorizontalAlignment="Left" Grid.Column="1" Grid.Row="0" Name="CustomersComboBox" VerticalAlignment="Top" Width="173" 
                  DisplayMemberPath="FullName" SelectedItem="{Binding Path=CurrentCustomer, Mode=TwoWay}" ItemsSource="{Binding Path=Customers}" />
        <TextBlock Height="23" Margin="5" HorizontalAlignment="Right" Grid.Column="0" Grid.Row="1" Name="textBlock4" Text="Customer ID" />
        <TextBlock Height="23" Margin="5" HorizontalAlignment="Right" Grid.Column="0" Grid.Row="2" Name="textBlock5" Text="Name" />
        <TextBlock Height="23" Margin="5" HorizontalAlignment="Right" Grid.Column="0" Grid.Row="3" Name="textBlock9" Text="Phone" />
        <TextBlock Height="23" HorizontalAlignment="Left" Grid.Column="1" Grid.Row="1" Name="CustomerIDTextBlock" 
                   Text="{Binding ElementName=CustomersComboBox, Path=SelectedItem.CustomerID}" />
        <TextBox Height="23" HorizontalAlignment="Left" Grid.Column="1" Grid.Row="2" Width="219" 
                 Text="{Binding Path=CurrentCustomer.FullName, Mode=TwoWay}" />
        <TextBox Height="23" HorizontalAlignment="Left" Grid.Column="1" Grid.Row="3" Width="219" 
                 Text="{Binding Path=CurrentCustomer.Phone, Mode=TwoWay}" />
        <Button
            Command="{Binding UpdateCustomerCommand}"
            Content="Update" Height="23" HorizontalAlignment="Right" Grid.Column="0" Grid.Row="4" 
            Name="UpdateButton" VerticalAlignment="Top" Width="75" />
    </Grid>
</Window>

関連項目See Also

ポータブル クラス ライブラリPortable Class Library