2009-04-30 78 views
1

我有以下简单功能:重构的启用/禁用按钮切换功能

private void EnableDisable941ScheduleBButton() 
    { 
     if (this._uosDepositorFrequency.Value != null) 
      this._btnScheduleB.Enabled = ((int)this._uosDepositorFrequency.Value == 0); 
    } 

这其中我想分成被动视图和主持人一个WinForm类的成员。显而易见的是,业务逻辑与用户界面布线缠绕在一起。我只是不确定将它们分开的最佳方式。

为了给出一点上下文,该函数从窗体中的三个位置调用。 _uosDepositorFrequency是一个只有两个按钮的单选按钮组。

任何想法?

更新:

好的,也许它不像我想象的那么明显。业务规则规定,如果雇主进行半周期存款(_uosDepositorFrequency.Value = 0),则他们需要填写附表B表格。

+0

您是否真的需要将所有业务规则移出UI层?这通常会带来更多的复杂性,有时候值得一提的逻辑(尤其是你所展示的逻辑......) – 2009-04-30 16:01:01

+0

嗯,我把业务规则分开的原因是因为表单将会是取而代之,但规则仍然存在。 – 2009-04-30 16:06:19

+0

够公平的。我在下面的答案中给了你一个选项。但是,我个人会保留原样,只是为替换人员发表评论;一般而言,只有当您在多个用户界面之间共享业务规则时才有意义... – 2009-04-30 16:16:35

回答

0

首先我要感谢所有回答我的问题的人。

我花了一些时间在这个工作,我相信我已经想出了一个解决方案。

首先我公开了_uosDepositorFrequency.Value和_btnScheduleB.Enabled作为公共属性并更新了视图界面我还花了一些时间来定义存储频率的枚举。

public bool EnableScheduleB 
    { 
     get 
     { 
      return _btnScheduleB.Enabled; 
     } 
     set 
     { 
      _btnScheduleB.Enabled = value; 
     } 
    } 

    public DepositFrequency DepositorFrequency 
    { 
     get 
     { 
      return (DepositFrequency)_uosDepositorFrequency.Value; 
     } 
     set 
     { 
      _uosDepositorFrequency.Value = (int)value; 
     } 
    } 

然后我将原始函数的主体复制到我的演示者,并将其修改为使用我刚刚创建的属性。原始函数中的空检查结果是不必要的,因为_uosDepositorFrequency控件在别处被初始化。

public void UpdateScheduleBStatus() 
    { 
     ReturnView.EnableScheduleB = ReturnView.DepositorFrequency == DepositFrequency.Semiweekly; 
    } 

最后_uosDepositorFrequency_ValueChanged事件处理程序进行了更新,呼叫UpdateScheduleBStatus。

private void _uosDepositorFrequency_ValueChanged(object sender, System.EventArgs e) 
    { 
     Presenter.UpdateScheduleBStatus(); 
    } 

评论欢迎光临。

0

我不认为这是商业逻辑。它看起来像我的UI逻辑。我不会改变它。

虽然如果我使用wpf,我会将启用状态绑定到数据。

0

也许我错过了一些东西,但我不确定在那里看到了商业逻辑。你只是根据表单上的其他控件是否有价值来启用/禁用按钮。我没有看到需要重构这个方法,这对我来说都是查看逻辑。

0

这听起来像是你将UI逻辑和业务规则混为一谈。你有的代码是UI逻辑,不应该重构。您所说的商业规则是,如果_btnScheduleB的值为0那么您需要让用户填写表单。您的商业逻辑应该是在用户可以继续使用_btnScheduleB之前确保您有填好的表单。

2

主持人:

if(this._uosDepositorFrequency.Value > 0) //int objects cannot be null 
     ViewData["ScheduleBRequired"] = true; 

查看:

private  void Draw() 
    { 
      if ((bool)ViewData["ScheduleBRequired"]){ 
        this._btnScheduleB.Enabled = true; 
        this._validatorScheduleB.Active = true; //required data should be checked clientside with js 
      } 
    } 

如果它是一个businessrequirement,这应该被填补,它应该由主持人来触发。 ui负责遵循主讲人的决定。例如要求ScheduleB或不...

0

替代方案(我不是说它是一个更好的)是选择更改事件的无线电控制更新模型(雇主实体?),其中依次触发UI订阅的某种DepositorChanged事件并相应地启用/禁用计划按钮。观察者模式,或多或少。

也就是说,上述替代方法会产生更多的复杂性,我建议将其留给UI代码(添加关于它的注释或使用中间布尔变量向读者陈述意图)。特别是如果这是该规则唯一使用的地方。

关于代码的一个注意事项:这是一个宗教性的争论,它将类字段用下划线前缀或使用this.代替。我认为每个人都同意使用两者都是多余的......

0

正如其他人指出,这是保持你的用户界面一致,所以真的不是业务逻辑。你可以删除这样的空检查。

this._btnScheduleB.Enabled = (int)(this._uosDepositorFrequency.Value ?? 0) == 0; 
0

我不会太担心重构两行代码,除非它真的没有在当前的格式是有意义的。