7

我正在尝试在摇摆应用程序中应用 MVC 模式。但是,鉴于您具有嵌套的面板层次结构,例如 Parent -> Child -> Grand Child -> Grand Grand Child,我面临两个主要问题。

问题1:当你有这样的层次结构时,如何在控制器和视图之间传输数据?如果我去将数据从父母传递给孩子,那么会有很多重复,如果我改变一个孩子,所有父母都需要改变。我不希望视图直接访问数据库中的数据,我希望数据仅通过控制器传输到视图。

问题 2:如何在这样的层次结构中将事件从视图传播到控制器?我正在考虑使用 PropertyChangeListener。如果控制器必须采取任何行动,View 将触发PropertyChange 事件。控制器将监听这些事件并执行一些操作。但是,如果我为层次结构这样做,那么就会有代码重复。

我有三个可能有用的想法:

  1. 要为每个面板使用控制器,但这样我最终会得到很多控制器。
  2. 使用将提供视图和控制器之间的通信的中介者设计模式。
  3. 使用 Central Reciever & Notifier 监听来自视图的所有属性更改事件,并通知感兴趣的控制器。但这只会解决我的第二个问题:

请参考下图以了解第三个想法的图片。如果是第 2 个,Mediator 将居中。

请评估并让我知道是否有人以更好的方式实施了此类问题。

在此处输入图像描述

4

3 回答 3

1

我对您的问题 1 有一个建议:

您可以拥有一个 ViewModel,其中包含另一个 View Model 的属性。在您的控制器方法上,您只需要接收父 ViewModel,因为模型绑定器将为您绑定所有属性。

public class GrandChildViewModel{
    public Int32 SelectedDropDownItem { get; set; }
    public List<Foo> ListOfFoo { get; set; }
}

public class ChildViewModel{
    public String Name { get; set; }
    public Int32 Age { get; set; }
}
public class FatherViewModel{
    public ChildViewModel Child { get; set; }
    public GrandChildViewModel GrandChild { get; set; }
}

这是层次结构的一个例子。您的 View 将仅引用 FatherViewModel。您的控制器也将收到 FatherViewModel。modelBinder 将自动完成其工作,如果您创建 HTML 如下:

@Html.TextBoxFor(m => m.Child.Name)

它将呈现输入:

<input type="text" id="Child_Name" name="Child_Name" />
于 2013-03-18T15:43:08.240 回答
1

问题1:当你有这样的层次结构时,如何在控制器和视图之间传输数据?如果我去将数据从父母传递给孩子,那么会有很多重复,如果我改变一个孩子,所有父母都需要改变。我不希望视图直接访问数据库中的数据,我希望数据仅通过控制器传输到视图。

如何通过向相关控制器注册视图来忽略层次结构并采用更线性的方法?数据可以通过模型获得,在该模型中,更改将通过ObserverorListener模式触发。

有了这个,你就不会发生任何重复。一切都将集中在一个模型或一系列模型中。在用户操作或外部事件发生后,一个或多个控制器可以在已注册视图列表上运行通知。

此外,视图绝对不应该像您所说的那样访问数据源。这里应该至少有一层抽象。如果您的控制器使用调解器模式,我将通过将请求转发到额外数据层中的接口来处理此问题。

进一步思考,我认为通过视图完成注册不是一个好主意。所以我会把这个分开。手动初始化视图或找到一种方法来遍历您需要的视图。也许通过一种自动化此步骤的工厂来获取您的意见。

问题 2:如何在这样的层次结构中将事件从视图传播到控制器?我正在考虑使用 PropertyChangeListener。如果控制器必须采取任何行动,View 将触发PropertyChange 事件。控制器将监听这些事件并执行一些操作。但是,如果我为层次结构这样做,那么就会有代码重复。

同样,您可以采用线性方法。当一个视图被注册时,控制器可以添加它的监听器。或者您可以让视图发送一些语义样式的消息(例如:doAction("Save")),这些消息可以通过调度机制进行处理。将让您决定如何转发参数。

需要 PropertyChangeListeners 吗?我的意思是,你需要那种粒度吗?

我有三个可能有用的想法:

要为每个面板使用控制器,但这样我最终会得到很多控制器。使用将提供视图和控制器之间的通信的中介者设计模式。使用 Central Reciever & Notifier 监听来自视图的所有属性更改事件,并通知感兴趣的控制器。但这只会解决我的第二个问题:

这听起来有点像HMVC。使用这种方法,每个子系统都有模型-视图-控制器三元组。这是一个有趣的想法,但可能会很混乱,并且不清楚层次结构应该如何工作以及如何实现协调/从属关系。

也许您可以为应用程序的每个模块/子系统创建第四个中性类,您可以在其中插入视图、模型和控制器,如果其中一个丢失或不正确,则抛出异常。

或者,按照中央通知器的想法,您可以让中央控制器充当其他特定于功能的控制器或更基本操作的路由机制。如何将消息重新路由到这些取决于您。注意线程,因为集中化将使此类的设计变得必不可少。

不管你做什么,尽量让事情变得简单。您应该能够拥有一个带有模型和控制器的测试视图,而不必大惊小怪。

于 2013-03-18T22:40:12.930 回答
1

当我最终使用这个 HMVC Pattern时,我遇到了类似的问题。是的,你是对的,因为会有很多控制器。但它也确实会在代码中为您提供清晰的关注点分离。您可以通过创建一些特定于应用程序的高级复合小部件来限制控制器的数量。在这种情况下,层次结构最多可以限制为 2 或 3 级,并且可以链接控制器以将事件委托给任何父/子。

从服务器加载数据后,您还可以维护 Session 映射以快速轻松地访问经常需要的数据,但我不太喜欢它。

如果开发团队理解并正确遵循该模式,则该模式运行良好。

于 2013-10-05T11:19:11.460 回答