Skip to content

Instantly share code, notes, and snippets.

@davybrion
Created September 15, 2012 14:04
Show Gist options
  • Save davybrion/3728097 to your computer and use it in GitHub Desktop.
Save davybrion/3728097 to your computer and use it in GitHub Desktop.
code snippets for "MVP In Silverlight/WPF: Implementing The Details UserControl" post
public class UserGroupDetailBindingModel : BindingModel<UserGroupDetailBindingModel>
{
private string originalName;
private Guid? originalId;
private UserGroupDto originalSelectedParent;
public ObservableCollection<UserGroupDto> SuitableParentUserGroups { get; private set; }
private UserGroupDto selectedParentUserGroup;
public UserGroupDto SelectedParentUserGroup
{
get { return selectedParentUserGroup; }
set
{
selectedParentUserGroup = value;
NotifyPropertyChanged(m => m.SelectedParentUserGroup);
}
}
private Guid? id;
public Guid? Id
{
get { return id; }
set
{
id = value;
NotifyPropertyChanged(m => m.Id);
NotifyPropertyChanged(m => m.IsExistingUserGroup);
}
}
public bool IsExistingUserGroup { get { return id.HasValue && id.Value != Guid.Empty; } }
private string name;
public string Name
{
get { return name; }
set
{
name = value;
NotifyPropertyChanged(m => m.Name);
}
}
public UserGroupDetailBindingModel()
{
SuitableParentUserGroups = new ObservableCollection<UserGroupDto>();
Clear();
AddValidationFor(m => m.Name)
.When(m => string.IsNullOrWhiteSpace(m.name))
.WithMessage("name is a required field");
}
public void Clear()
{
SuitableParentUserGroups.Clear();
SuitableParentUserGroups.Add(new UserGroupDto { Id = Guid.Empty, Name = "None" });
SelectedParentUserGroup = SuitableParentUserGroups[0];
originalId = Id = null;
originalName = Name = null;
originalSelectedParent = SelectedParentUserGroup;
}
public void Populate(IEnumerable<UserGroupDto> suitableParentUserGroups, UserGroupDto currentUserGroup = null)
{
foreach (var suitableParentUserGroup in suitableParentUserGroups)
{
SuitableParentUserGroups.Add(suitableParentUserGroup);
}
if (currentUserGroup != null)
{
originalName = Name = currentUserGroup.Name;
originalId = Id = currentUserGroup.Id;
originalSelectedParent = SelectedParentUserGroup;
if (currentUserGroup.ParentId.HasValue)
{
originalSelectedParent = SelectedParentUserGroup = SuitableParentUserGroups.First(u => u.Id == currentUserGroup.ParentId);
}
}
}
public void RevertToOriginalValues()
{
Name = originalName;
Id = originalId;
SelectedParentUserGroup = originalSelectedParent;
}
}
public class UserGroupDetailPresenter : Presenter<IUserGroupDetailsView, UserGroupDetailBindingModel>,
IListenTo<UserGroupSelectedEvent>, IListenTo<UserGroupNeedsToBeCreatedEvent>
{
public UserGroupDetailPresenter(IUserGroupDetailsView view, IEventAggregator eventAggregator, IAsyncRequestDispatcherFactory requestDispatcherFactory)
: base(view, eventAggregator, requestDispatcherFactory) {}
public override void Initialize()
{
View.Hide();
EventAggregator.Subscribe(this);
}
public void Handle(UserGroupNeedsToBeCreatedEvent receivedEvent)
{
View.PreventDeletion();
LoadData();
}
public void Handle(UserGroupSelectedEvent receivedEvent)
{
View.EnableEverything();
LoadData(receivedEvent.SelectedUserGroupId);
}
private void LoadData(Guid? userGroupId = null)
{
BindingModel.Clear();
var requestDispatcher = RequestDispatcherFactory.CreateAsyncRequestDispatcher();
if (userGroupId.HasValue)
{
requestDispatcher.Add(new CheckPermissionsRequest {PermissionsToCheck = new[] {Permissions.DeleteUserGroup, Permissions.EditUserGroup}});
requestDispatcher.Add(new GetUserGroupRequest { UserGroupId = userGroupId.Value });
}
requestDispatcher.Add(new GetSuitableParentUserGroupsRequest {UserGroupId = userGroupId});
requestDispatcher.ProcessRequests(ResponsesReceived, PublishRemoteException);
}
private void ResponsesReceived(ReceivedResponses receivedResponses)
{
if (receivedResponses.HasResponse<GetUserGroupResponse>())
{
BindingModel.Populate(receivedResponses.Get<GetSuitableParentUserGroupsResponse>().SuitableParentUserGroups,
receivedResponses.Get<GetUserGroupResponse>().UserGroup);
}
else
{
BindingModel.Populate(receivedResponses.Get<GetSuitableParentUserGroupsResponse>().SuitableParentUserGroups);
}
if (receivedResponses.HasResponse<CheckPermissionsResponse>())
{
var response = receivedResponses.Get<CheckPermissionsResponse>();
if (!response.AuthorizationResults[Permissions.DeleteUserGroup]) View.PreventDeletion();
if (!response.AuthorizationResults[Permissions.EditUserGroup]) View.PreventModification();
}
View.Show();
}
public void PersistChanges()
{
BindingModel.ValidateAll();
if (BindingModel.HasErrors) return;
var dispatcher = RequestDispatcherFactory.CreateAsyncRequestDispatcher();
dispatcher.Add(new SaveUserGroupRequest
{
Id = BindingModel.Id,
Name = BindingModel.Name,
ParentId = BindingModel.SelectedParentUserGroup.Id != Guid.Empty ? BindingModel.SelectedParentUserGroup.Id : (Guid?)null
});
dispatcher.ProcessRequests(PersistChanges_ResponseReceived, PublishRemoteException);
}
private void PersistChanges_ResponseReceived(ReceivedResponses responses)
{
var response = responses.Get<SaveUserGroupResponse>();
if (response.NewUserGroupId.HasValue)
{
BindingModel.Id = response.NewUserGroupId.Value;
}
EventAggregator.Publish(new UserGroupChangedEvent
{
Id = BindingModel.Id.Value,
Name = BindingModel.Name,
ParentId = BindingModel.SelectedParentUserGroup.Id != Guid.Empty ? BindingModel.SelectedParentUserGroup.Id : (Guid?)null,
IsNew = response.NewUserGroupId.HasValue
});
}
public void Delete()
{
var dispatcher = RequestDispatcherFactory.CreateAsyncRequestDispatcher();
dispatcher.Add(new DeleteUserGroupRequest { UserGroupId = BindingModel.Id.Value });
dispatcher.ProcessRequests(DeleteUserGroup_ResponseReceived, PublishRemoteException);
}
private void DeleteUserGroup_ResponseReceived(ReceivedResponses responses)
{
EventAggregator.Publish(new UserGroupDeletedEvent(BindingModel.Id.Value));
}
public void Cancel()
{
BindingModel.RevertToOriginalValues();
}
}
<MVP:View x:Class="SilverlightMVP.Client.Views.UserGroupDetail"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:MVP="clr-namespace:SilverlightMVP.Client.Infrastructure.MVP" >
<Grid x:Name="LayoutRoot" Background="White" MinHeight="75" MaxHeight="75" MinWidth="455" >
<Grid.ColumnDefinitions>
<ColumnDefinition />
<ColumnDefinition />
<ColumnDefinition />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<TextBlock Text="Name" Grid.Column="0" Grid.Row="0" />
<TextBox x:Name="NameTextBox" Text="{Binding Path=Name, Mode=TwoWay, ValidatesOnExceptions=True, NotifyOnValidationError=True}"
Grid.Column="1" Grid.Row="0" Grid.ColumnSpan="2" />
<TextBlock Text="Parent" Grid.Column="0" Grid.Row="1" />
<ComboBox x:Name="SuitableParentUserGroupsComboBox" ItemsSource="{Binding Path=SuitableParentUserGroups}" MinWidth="150"
DisplayMemberPath="Name" SelectedItem="{Binding Path=SelectedParentUserGroup, Mode=TwoWay}"
Grid.Column="1" Grid.Row="1" Grid.ColumnSpan="2" />
<Button x:Name="DeleteButton" Content="Delete" Click="DeleteButton_Click" Grid.Column="0" Grid.Row="2" />
<Button x:Name="CancelButton" Content="Cancel" Click="CancelButton_Click" Grid.Column="1" Grid.Row="2" />
<Button x:Name="SaveButton" Content="Save" Click="SaveButton_Click" Grid.Column="2" Grid.Row="2" />
</Grid>
</MVP:View>
public interface IUserGroupDetailsView : IView
{
void PreventDeletion();
void PreventModification();
void EnableEverything();
}
public partial class UserGroupDetail : IUserGroupDetailsView
{
private readonly UserGroupDetailPresenter presenter;
public UserGroupDetail()
{
InitializeComponent();
presenter = CreateAndInitializePresenter<UserGroupDetailPresenter>();
}
public void EnableEverything()
{
DeleteButton.Visibility = Visibility.Visible;
CancelButton.Visibility = Visibility.Visible;
SaveButton.Visibility = Visibility.Visible;
NameTextBox.IsEnabled = true;
SuitableParentUserGroupsComboBox.IsEnabled = true;
}
public void PreventDeletion()
{
DeleteButton.Visibility = Visibility.Collapsed;
}
public void PreventModification()
{
NameTextBox.IsEnabled = false;
SuitableParentUserGroupsComboBox.IsEnabled = false;
CancelButton.Visibility = Visibility.Collapsed;
SaveButton.Visibility = Visibility.Collapsed;
}
private void DeleteButton_Click(object sender, RoutedEventArgs e)
{
presenter.Delete();
}
private void CancelButton_Click(object sender, RoutedEventArgs e)
{
presenter.Cancel();
}
private void SaveButton_Click(object sender, RoutedEventArgs e)
{
presenter.PersistChanges();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment