2010-08-04 6 views
1

У меня есть приложение, у которого есть окно, похожее на один ниже.GUI Design Pattern, MVP, Tab Control

alt text http://a.imageshack.us/img137/7481/screenshotxh.jpg

Требование в том, что, когда пользователь нажимает кнопку Сохранить все должно получить спасение. Кнопки «Сохранить» и «Сброс» являются «общими» для всех вкладок. Следовательно, когда выбрана вкладка «Личная информация» и нажата «Сохранить», программа также должна сохранять изменения, внесенные на вкладке «Друзья», и изменения, внесенные на вкладке «История занятости».

приложение уже имеет код ниже и я хочу сохранить этот код:

-PersonalInformationView, PersonalInformationPresenter, PersonalInformationModel

-FriendsView, FriendsPresenter, FriendsModel

-EmploymentHistoryView, EmploymentHistoryPresenter, EmploymentHistoryModel

У каждого ведущего есть Сохранить метод.

Вопрос в том, что было бы хорошим шаблоном дизайна для использования, учитывая, что я хочу держать код, который у меня уже есть. Кроме того, я хочу, чтобы в этом окне была модель, вид, презентатор. Или, может быть, мне нужно немного перефразировать мой вопрос: Каков наилучший способ включения «суб-представлений», «суб-презентаторов» при программировании MVP?

С уважением, MadSeb

ответ

0

Я хотел бы сделать свой новый презентаторов взять в суб предъявителей в качестве аргументов конструктора, что-то вроде:

class DialogPresenter { 

    private readonly IDialogView view; 
    private readonly PersonalInformationPresenter personal; 
    private readonly FriendsPresenter friends; 
    private readonly EmploymentHistoryPresenter history; 

    void DialogPresenter(IDialogView view, PersonalInformationPresenter personal, FriendsPresenter friends, EmploymentHistoryPresenter history) { 
     this.view = view; 
     this.personal = personal; 
     this.friends = friends; 
     this.history = history; 
    } 

    bool Display() { 
     this.personal.Display(); 
     this.friends.Display(); 
     this.history.Display(); 

     return this.view.Display() == DialogResult.Ok; 
    } 

    void Save() { 
     this.personal.Save(); 
     this.friends.Save(); 
     this.history.Save(); 
    } 
} 

Конечно , если ваши Ведущими имели общий интерфейс между ними, это может быть упрощена (и сделать более расширяемой) как так:

class DialogPresenter { 

    private readonly IDialogView view; 
    private readonly IPresenters[] presenters; 

    void DialogPresenter(IDialogView view, IPresenters[] presenters) 
    { 
     this.view = view; 
     this.presenters = presenters; 
    } 

    bool Display() { 
     foreach (var item in this.presenters) 
      item.Display(); 

     return this.view.Display() == DialogResult.Ok; 
    } 

    void Save() { 
     var validation = new List<string>(); 

     foreach (var item in this.presenters) 
      validation.AddRange(item.Validate()); 

     if (validation.Count > 0) { 
       _view.ShowErrors(validation); 
       return; 
     } 

     foreach (var item in this.presenters) 
      validation.AddRange(item.Save()); 
    } 
} 

Edit: телефонный код будет someth ING как это:

void DisplayForm() { 

    using (var frm = new frmDisplay) { 

     //or just use DI to get the models etc 
     var personal = new PersonalInformationPresenter(personalModel, frm.PersonalTab); //some properties to expose your views 
     var friends = new FriendsPresenter(friendslModel, frm.FriendsTab); 
     var history = new EmploymentHistoryPresenter(employmentHistoryModel, frm.HistoryTab); 

     var presenter = new DialogPresenter(frm, personal, friends, history); 
     if (presenter.Display()) {  
      presenter.Save(); 
     } 
    } 
} 

Надеется, что это какое-то inpsiration/помощи :)

+0

Это действительно действительно вдохновляет. Однако у меня есть следующая проблема. Метод «Сохранить» каждого ведущего выполняет валидацию данных перед сохранением, а в случае его отказа - открывается view.DisplayValidationErrors() * и отображается msgbox («Почтовый код отсутствует» и т. Д.) Если я решила использовать кода, вы предложили пользователю получить один msg.box для ошибок проверки на первой вкладке, один msg.box для ошибок проверки во второй вкладке. но я хочу, чтобы все ошибки проверки были агрегированы только в одном msg.box. – MadSeb

+0

Я обновил свой ответ (второй блок кода), чтобы показать, как я обрабатываю этот – Pondidum

1

лично я бы предложил сделать абстрактный интерфейс, ISaveable или osmething и убедитесь, что каждый из предъявителей осуществить это, чем пройти через каждый ведущий в качестве объекта ISaveable и сохранить каждый из них.

+0

..ы от ведущего «главного зрения» У меня нет доступа к Ведущим «под вид «(PersonalInformationView, FriendsView, EmploymentHistoryView) .. У меня есть доступ к самим« представлениям »... – MadSeb

0

Мое предложение состоит в том, чтобы создать ISaveableView с сохранением метода. Каждый из ваших представлений реализует интерфейс. Я предполагаю, что ваши вкладки реализуют просмотренные вами виды. При нажатии на кнопку сохранить, можно привести активную вкладку, чтобы ISaveableView и вызвать его метод сохранения

+0

привет, это хороший ответ, но метод« Сохранить »не является частью представления, а является частью ведущего. ........но я предполагаю, что могу сделать метод «Сохранить» в представлении, и этот метод вызовет «Сохранить» презентатора. – MadSeb