WinForms 中的模型-视图-呈现器
我第一次尝试使用 WinForms 来实现 MVP 方法。
我试图理解每一层的功能。
在我的程序中,我有一个 GUI 按钮,单击该按钮会打开一个 openfiledialog 窗口。
因此,使用 MVP,GUI 处理按钮单击事件,然后调用 Presenter.openfile();
在 Presenter.openfile() 中,是否应该将该文件的打开委托给模型层,或者由于没有数据或逻辑要处理,是否应该简单地响应请求并打开 openfiledialog 窗口?
更新:我决定提供赏金,因为我觉得我在这方面需要进一步的帮助,并且最好根据我下面的具体要点进行定制,以便我了解背景。
好的,在阅读了 MVP 后,我决定实施被动视图。实际上,我将在 Winform 上拥有一堆控件,这些控件将由 Presenter 处理,然后将任务委托给模型。我的具体要点如下:
当winform加载时,它必须获取一个树视图。我是否正确地认为视图应该调用一个方法,例如:presenter.gettree(),这反过来将委托给模型,模型将获取树视图的数据,创建它并配置它,将其返回给Presenter,它反过来将传递给视图,然后简单地将其分配给面板?
对于 Winform 上的任何数据控件来说,这是否相同,因为我也有一个 datagridview?
我的应用程序有许多具有相同程序集的模型类。它还支持插件架构,其中的插件需要在启动时加载。视图是否会简单地调用演示者方法,而演示者方法又会调用加载插件并在视图中显示信息的方法?哪一层将控制插件引用。视图会保存对它们或演示者的引用吗?
我认为视图应该处理有关演示的所有事情(从树视图节点颜色到数据网格大小等)是否正确?
我认为它们是我主要关心的问题,如果我了解这些流程应该如何进行,我想我会没事的。
I am trying to implement the MVP method for the first time, using WinForms.
I am trying to understand the function of each layer.
In my program I have a GUI button that when clicked upon opens a openfiledialog window.
So using MVP, the GUI handles the button click event and then calls presenter.openfile();
Within presenter.openfile(), should that then delegate the opening of that file to the model layer, or as there is no data or logic to process, should it simply act on the request and open the openfiledialog window?
Update: I have decided to offer a bounty as I feel I need further assistance on this, and preferably tailored to my specific points below, so that I have context.
Okay, after reading up on MVP, I have decided to implement the Passive View. Effectively I will have a bunch of controls on a Winform that will be handled by a Presenter and then the tasks delegated to the Model(s). My specific points are below:
When the winform loads, it has to obtain a treeview. Am I correct in thinking that the view should therefore call a method such as: presenter.gettree(), this in turn will delegate to the model, which will obtain the data for the treeview, create it and configure it, return it to the presenter, which in turn will pass to the view which will then simply assign it to, say, a panel?
Would this be the same for any data control on the Winform, as I also have a datagridview?
My App, has a number of model classes with the same assembly. It also supports a plugin architecture with plugins that need to be loaded at startup. Would the view simply call a presenter method, which in turn would call a method that loads the plugins and display the information in the view? Which tier would then control the plugin references. Would the view hold references to them or the presenter?
Am I correct in thinking that the view should handle every single thing about presentation, from treeview node colour, to datagrid size, etc?
I think that they are my main concerns and if I understand how the flow should be for these I think I will be okay.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
演示者应按照您的建议对请求端进行操作,显示 openfiledialog 窗口。由于模型不需要任何数据,演示者可以而且应该处理该请求。
假设您需要数据来在模型中创建一些实体。您可以将流槽传递到访问层,在访问层中您有一个从流创建实体的方法,但我建议您在演示者中处理文件的解析,并在模型中为每个实体使用构造函数或 Create 方法。
The presenter should act on the request end show the openfiledialog window as you suggested. Since no data is required from the model the presenter can, and should, handle the request.
Let's assume you need the data to create some entities in your model. You can either pass the stream trough to the access layer where you have a method to create entities from the stream, but I suggest you handle the parsing of the file in your presenter and use a constructor or Create method per entity in your model.
这是我对 MVP 和您的具体问题的粗浅看法。
首先,用户可以与之交互或只是显示的任何内容都是视图。这种视图的规律、行为和特征由接口描述。该界面可以使用 WinForms UI、控制台 UI、Web UI 甚至根本没有 UI 来实现(通常在测试演示者时) - 具体实现并不重要,只要它遵守其视图界面的法则即可。
第二,视图始终由演示者控制。这种演示者的规律、行为和特征也由界面来描述。该接口对具体视图实现没有兴趣,只要它遵守其视图接口的规则即可。
第三,由于演示者控制其视图,为了最大限度地减少依赖性,让视图了解有关其演示者的任何信息实际上没有任何好处。演示者和视图之间有一个商定的合同,并且由视图界面声明。
第三的含义是:
对于您的问题,上面的代码可能看起来像这样:
除了上面的内容之外,我通常还有一个基本的 IView 接口,我在其中存储了 Show() 和我的观点通常受益的任何所有者视图或视图标题。
对于你的问题:
1. 当winform加载时,它必须获得一个树视图。我是否正确地认为视图应该调用一个方法,例如:presenter.gettree(),这反过来将委托给模型,模型将获取树视图的数据,创建它并配置它,将其返回给演示者,然后将传递给视图,然后将其简单地分配给面板?
< strong>2. 对于 Winform 上的任何数据控件来说,这是否相同,因为我也有一个 datagridview?
3. 我的应用程序有许多具有相同程序集的模型类。它还支持插件架构,其中的插件需要在启动时加载。视图是否会简单地调用演示者方法,而演示者方法又会调用加载插件并在视图中显示信息的方法?哪一层将控制插件引用。该视图是否包含对他们或演示者的引用?
4. 我认为视图应该处理有关演示的所有事情(从树视图节点颜色到数据网格大小等)是否正确?
点击节点的数据怎么样?
5. 如果当我点击树节点时,我是否应该将特定节点传递给演示者,然后从该节点传递给演示者会计算出它需要什么数据,然后向模型询问该数据,然后将其呈现回视图?
This is my humble take on MVP and your specific issues.
First, anything that a user can interact with, or just be shown, is a view. The laws, behavior and characteristics of such a view is described by an interface. That interface can be implemented using a WinForms UI, a console UI, a web UI or even no UI at all (usually when testing a presenter) - the concrete implementation just doesn't matter as long as it obeys the laws of its view interface.
Second, a view is always controlled by a presenter. The laws, behavior and characteristics of such a presenter is also described by an interface. That interface has no interest in the concrete view implementation as long as it obeys the laws of its view interface.
Third, since a presenter controls its view, to minimize dependencies there's really no gain in having the view knowing anything at all about its presenter. There's an agreed contract between the presenter and the view and that's stated by the view interface.
The implications of Third are:
For your issue, the above could look like this in somewhat simplified code:
In addition to the above, I usually have a base
IView
interface where I stash theShow()
and any owner view or view title that my views usually benefit from.To your questions:
1. When the winform loads, it has to obtain a treeview. Am I correct in thinking that the view should therefore call a method such as: presenter.gettree(), this in turn will delegate to the model, which will obtain the data for the treeview, create it and configure it, return it to the presenter, which in turn will pass to the view which will then simply assign it to, say, a panel?
2. Would this be the same for any data control on the Winform, as I also have a datagridview?
3. My App, has a number of model classes with the same assembly. It also supports a plugin architecture with plugins that need to be loaded at startup. Would the view simply call a presenter method, which in turn would call a method that loads the plugins and display the information in the view? Which tier would then control the plugin references. Would the view hold references to them or the presenter?
4. Am I correct in thinking that the view should handle every single thing about presentation, from treeview node colour, to datagrid size, etc?
What about data for clicked nodes?
5. If when I click on the treenodes, should I pass through the specific node to the presenter and then from that the presenter would work out what data it needs and then asks the model for that data, before presenting it back to the view?
演示者包含视图中的所有逻辑,应以 @JochemKempe 说。实际上,按钮单击事件处理程序调用 Presenter.OpenFile()。然后演示者能够确定应该做什么。
如果它决定用户必须选择一个文件,它会回调视图(通过视图界面)并让包含所有 UI 技术的视图显示
OpenFileDialog
。这是一个非常重要的区别,因为不应允许演示者执行与正在使用的 UI 技术相关的操作。然后,所选文件将返回给演示者,继续其逻辑。这可能涉及应处理文件的任何模型或服务。
在我看来,使用 MVP 模式的主要原因是将 UI 技术与视图逻辑分开。因此,演示者协调所有逻辑,而视图将其与 UI 逻辑分开。这具有非常好的副作用,使演示者完全可进行单元测试。
更新:由于演示者是在一个特定视图中找到的逻辑的体现,因此视图-演示者关系在我看来是一对一的关系。出于所有实际目的,一个视图实例(例如表单)与一个演示者实例交互,而一个演示者实例仅与一个视图实例交互。
也就是说,在我使用 WinForms 实现 MVP 时,演示者始终通过代表视图 UI 功能的接口与视图交互。对于哪个视图实现该接口没有限制,因此不同的“小部件”可以实现相同的视图接口并重用演示者类。
The presenter, which contains all logic in the view, should respond to the button being clicked as @JochemKempe says. In practical terms, the button click event handler calls
presenter.OpenFile()
. The presenter is then able to determine what should be done.If it decides that the user must select a file, it calls back into the view (via a view interface) and let the view, which contains all UI technicalities, display the
OpenFileDialog
. This is a very important distinction in that the presenter should not be allowed to perform operations tied to the UI technology in use.The selected file will then be returned to the presenter which continues its logic. This may involve whatever model or service should handle processing the file.
The primary reason for using an MVP pattern, imo is to separate the UI technology from the view logic. Thus the presenter orchestrates all logic while the view keeps it separated from UI logic. This has the very nice side effect of making the presenter fully unit testable.
Update: since the presenter is the embodiment of the logic found in one specific view, the view-presenter relationship is IMO a one-to-one relationship. And for all practical purposes, one view instance (say a Form) interacts with one presenter instance, and one presenter instance interacts with only one view instance.
That said, in my implementation of MVP with WinForms the presenter always interacts with the view through an interface representing the UI abilities of the view. There is no limitation on what view implements this interface, thus different "widgets" may implement the same view interface and reuse the presenter class.