2009-07-21 2 views
2

Целью настоящего является обновление пользовательского интерфейса. Обычно я делаю это на клиенте, однако это приложение использует код позади. В любом случае, мой вопрос заключается в том, что я пытаюсь очистить эти утверждения if else, и я думал, что шаблон стратегии может быть уместным. Мне не нужно, чтобы все было сделано для меня, но если бы вы могли дать мне пару указателей, чтобы идти. Сначала я создаю интерфейс, а затем каждая стратегия реализует интерфейс? Здесь полезны дженерики? Какие типы методов должны быть в интерфейсе? Любая вещь, которая заставит меня идти, будет очень оценена.Помощь рефактору - шаблон стратегии

if (someObject.Status == 'A') { 
        btnRecordCall.Enabled = false; 
        btnAddMailOrStatusAction.Enabled = false; 
        btnPayments.Enabled = false; 
        btnAddressMaint.Enabled = false; 
        btnFilter.Enabled = false; 
        btnAddCoverage.Enabled = false; 
        btnPolicyForms.Enabled = false; 
        lblIsArchived.Text = "********** THIS CLAIM HAS BEEN ARCHIVED **********"; 
       } else if (someObject.Status == 'D') { 
        btnRecordCall.Enabled = false; 
        btnAddMailOrStatusAction.Enabled = false; 
        btnPayments.Enabled = false; 
        btnAddressMaint.Enabled = false; 
        btnFilter.Enabled = false; 
        btnAddCoverage.Enabled = false; 
        btnPolicyForms.Enabled = false; 
        lblIsArchived.Text = "- De-archive Request Pending"; 
       } else { 
        btnRecordCall.Enabled = true; 
        btnAddMailOrStatusAction.Enabled = true; 
        btnPayments.Enabled = true; 
        btnAddressMaint.Enabled = true; 
        btnFilter.Enabled = true; 
        btnAddCoverage.Enabled = true; 
        btnPolicyForms.Enabled = true; 
        lblIsArchived.Text = ""; 
       } 

Спасибо, ~ ск

ответ

3

Ну, прежде всего, если вы собираетесь использовать шаблон стратегии с интерфейсом вы можете интерфейс, как это.

public interface IStrategyUI 
{ 
    void Execute(); 
} 

затем несколько классов для вашей логики

public class StatusAStrategy : IStrategyUI 
{ 
    public void Execute() 
    { 
     //implement 
    } 
} 

тогда ваш, если заявление может быть завод технически.

IStrategyUI logic; 

switch(someObject.Status) 
{ 
    case 'A': logic = new StatusAStrategy(); 
      //etc etc 

} 

logic.Execute(); 

или вы можете вернуть этот объект в качестве интерфейса и инкапсулировать оператор switch другим способом или классом фабрики.

Чтобы вы могли использовать его так.

IStrategyUI logic = StrategyFactory.GetStrategy(status); 
logic.Execute(); 

Это зависит от вас.

Также я не использую класс защиты, но вы можете, если хотите.

Вы также можете сделать это с делегатами.

класса Сдерживание

class StrategyHolder 
    { 
     public Action Strategy { get; set; } 

     public void Execute() 
     { 
      if(this.Strategy != null) 
       this.Strategy(); 
     } 
    } 

Различные методы стратегии.

void EnableStatusA() 
{ 
    //do everything for status A 
} 

переключатель заявление

StrategyHolder logic = new StrategyHolder(); 

switch(someObject.Status) 
    { 
     case 'A': logic.Strategy = EnableStatusA; 
       //etc etc 

    } 

return logic; 

Зов это снаружи.

StrategyHolder logic = StrategyFactory.GetStrategy(status); 
logic.Execute(); 
+0

Спасибо Стэн. В методе выполнения в реализациях, как мне получить ссылки на элементы управления страницей? Я передаю ссылки на страницу и выполняю findcontrol ('someId')? или есть лучший способ? – Hcabnettek

+0

Да, вы можете передать ссылку на страницу, а затем сделать то же самое, что делали до того, как я нарисовал страницу.lblIsArchived.Text = ""; и т. д. Вы можете передать ссылку на страницу в конструкторе или в методе Execute. тебе решать. –

3

Если все кнопки получить то же самое что позволяет независимо от статуса, как в вашем примере, то я бы скрыть, что далеко в списке кнопок и просто перебирать их. Тогда ваши параметры для стратегии сводятся к одному булеву и строке - и это довольно легко сделать в любом случае. Если в этом есть большая сложность, тогда разные классы, реализующие интерфейс, который устанавливает элементы управления, будут в порядке, возможно, с абстрактным суперклассом, который содержит общую логику.

+0

Спасибо, Карл. – Hcabnettek

0

Я думаю, что вы ищете State patten. Это похоже на шаблон стратегии, за исключением того, что каждому объекту состояния обычно присваивается ссылка на объект контекста (в вашем случае это форма), когда он создается. Это позволяет различным состояниям делать вещи объекту контекста в ответ на события.

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

public interface IFormState 
{ 
    void EnableDisableControls(); 
} 

public class DefaultState : IFormState 
{ 
    private MyForm context; 

    public DefaultState(MyForm context) 
    { 
     this.context = context; 
    } 

    protected MyForm Context 
    { 
     get 
     { 
      return this.context; 
     } 
    } 

    public virtual void EnableDisableControls() 
    { 
     this.context.btnRecordCall.Enabled = true; 
     this.context.btnAddMailOrStatusAction.Enabled = true; 
     this.context.btnPayments.Enabled = true; 
     this.context.btnAddressMaint.Enabled = true; 
     this.context.btnFilter.Enabled = true; 
     this.context.btnAddCoverage.Enabled = true; 
     this.context.btnPolicyForms.Enabled = true; 
     this.context.lblIsArchived.Text = ""; 
    } 
} 

public class StateA : DefaultState 
{ 
    public StateA(MyForm context) 
     : base(context) 
    { 
    } 

    public override void EnableDisableControls() 
    { 
     base.EnableDisableControls(); 

     this.Context.lblIsArchived.Text = "********** THIS CLAIM HAS BEEN ARCHIVED **********"; 
     // etc... 
    } 
} 
Смежные вопросы