Define an object that encapsulates how a set of objects interact. Mediator promotes loose coupling by keeping objects from referring to each other explicitly, and it lets you vary their interaction independently.
包装了一系列对象相互作用的方式,使得这些对象不必相互明显作用,从而使它们可以松散偶合。当某些对象之间的作用发生改变时,不会立即影响其他的一些对象之间的作用,保证这些作用可以彼此独立的变化。
一组对象以定义良好但是复杂的方式进行通信, 之间产生的相互依赖关系结构混乱且难以理解, 一个对象引用其他很多对象, 并且直接与这些对象通信, 导致难以复用该对象。
public interface IColleague {
void Execute();
}
public interface IMediator {
void Book();
void View();
void Search();
void RegisterView(ViewButton viewButton);
void RegisterSearch(SearchButton searchButton);
void RegisterBook(BookButton bookButton);
void RegisterDisplay(DisplayLabel displayLabel);
}
class Mediator : IMediator {
private ViewButton _viewButton;
private SearchButton _searchButton;
private BookButton _bookButton;
private DisplayLabel _displayLabel;
public void Book() {
this._bookButton.IsEnabled = false;
this._viewButton.IsEnabled = true;
this._searchButton.IsEnabled = true;
this._displayLabel.Content = "Booking ...";
}
public void View() {
this._bookButton.IsEnabled = true;
this._viewButton.IsEnabled = false;
this._searchButton.IsEnabled = true;
this._displayLabel.Content = "Viewing ...";
}
public void Search() {
this._bookButton.IsEnabled = true;
this._viewButton.IsEnabled = true;
this._searchButton.IsEnabled = false;
this._displayLabel.Content = "Searching ...";
}
public void RegisterView(ViewButton viewButton) {
this._viewButton = viewButton;
}
public void RegisterSearch(SearchButton searchButton) {
this._searchButton = searchButton;
}
public void RegisterBook(BookButton bookButton) {
this._bookButton = bookButton;
}
public void RegisterDisplay(DisplayLabel displayLabel) {
this._displayLabel = displayLabel;
}
}
public class BookButton : Button, IColleague {
private readonly IMediator _mediator;
public BookButton(IMediator mediator) {
this.Content = "Book";
this._mediator = mediator;
this._mediator.RegisterBook(this);
}
public void Execute() {
this._mediator.Book();
}
}
public class SearchButton : Button, IColleague {
private readonly IMediator _mediator;
public SearchButton(IMediator mediator) {
this.Content = "Search";
this._mediator = mediator;
this._mediator.RegisterSearch(this);
}
public void Execute() {
this._mediator.Search();
}
}
public class ViewButton : Button, IColleague {
private readonly IMediator _mediator;
public ViewButton(IMediator mediator) {
this.Content = "View";
this._mediator = mediator;
this._mediator.RegisterView(this);
}
public void Execute() {
this._mediator.View();
}
}
public class DisplayLabel : Label {
private readonly IMediator _mediator;
public DisplayLabel(IMediator mediator) {
this.Content = "Starting ...";
this.FontSize = 24;
//this.FontWeight = new FontWeight();
this._mediator = mediator;
this._mediator.RegisterDisplay(this);
}
}
class MediatorDemo : Window {
private readonly IMediator _mediator = new Mediator();
public MediatorDemo() {
var rootView = new Grid();
rootView.RowDefinitions.Add(new RowDefinition());
rootView.RowDefinitions.Add(new RowDefinition());
rootView.ColumnDefinitions.Add(new ColumnDefinition());
rootView.ColumnDefinitions.Add(new ColumnDefinition());
rootView.ColumnDefinitions.Add(new ColumnDefinition());
var viewButton = new ViewButton(this._mediator);
viewButton.Click += this.OnViewClick;
Grid.SetColumn(viewButton, 0);
Grid.SetRow(viewButton, 0);
rootView.Children.Add(viewButton);
var bookButton = new BookButton(this._mediator);
bookButton.Click += this.OnViewClick;
Grid.SetColumn(bookButton, 1);
Grid.SetRow(bookButton, 0);
rootView.Children.Add(bookButton);
var searchButton = new SearchButton(this._mediator);
searchButton.Click += this.OnViewClick;
Grid.SetColumn(searchButton, 2);
Grid.SetRow(searchButton, 0);
rootView.Children.Add(searchButton);
var displayLabel = new DisplayLabel(this._mediator);
Grid.SetColumn(displayLabel, 0);
Grid.SetRow(displayLabel, 1);
Grid.SetColumnSpan(displayLabel, 3);
rootView.Children.Add(displayLabel);
this.Content = rootView;
this.Width = 400;
this.Height = 200;
this.Title = "Mediator Demo";
}
private void OnViewClick(object sender, RoutedEventArgs routedEventArgs) {
var colleague = (IColleague)sender;
colleague.Execute();
}
[STAThread]
static void Main(string[] args) {
var app = new Application();
app.Startup += AppOnStartup;
app.Run();
}
private static void AppOnStartup(object sender, StartupEventArgs startupEventArgs) {
Application.Current.MainWindow = new MediatorDemo();
Application.Current.MainWindow.Show();
}
}
中介者模式也是最为常见的设计模式之一, 不管是 WinForm, WebForm 还是 WPF , 均可以考虑采用中介者模式。