1

我有一些猜词游戏的工作代码。但我担心它不会限制设计规则,尤其是MVC模式。附图是我GUI目前的。我将物品从一个班级扔到另一个班级,我听说这是一种糟糕的风格。虽然我同意这一点,但我无法MVC为猜词游戏或通常称为的刽子手提出好的模式方法。主应用程序将有一些这样的:

public class Application {

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {

            @Override
            public void run() {
                runApp();
            }

        });
    }

    public static void runApp() {
        Model model = new Model();
        View view = new View(model); //not sure if this correct, some suggest it is valid and some not

        Controller controller = new Controller(view, model);
    }

}

我将如何处理这个?如GUI附图中所示,将是View类。这包括所有JButtons, Textfield, borders, labels等。附加actionlisteners到课堂JButtonsView

controller传递eventsmodel. 例如,如果letter buttons单击了一些,它将传递单击的字母“A”,model 并且model将发送指令以controller进行更新viewview直接更新。根据我对MVC模式的理解,model该类必须与 和 分开实现和view测试controller。我不明白我怎么能在这里做到这一点。我有完整的代码可用。我需要重构以限制到 MVC 模式。请传递您的建议。在此处输入图像描述

4

4 回答 4

2

编辑:MVC(netbeans 项目,由我制作)的工作示例在此处下载或在此处下载。谁不知道 netbeans:在 dist 中是可执行的 .jar 文件,在 src 中是源代码。它显示了具有两种不同视图的 MVC 模式。在左侧,您可以左键或右键单击创建圆形或正方形,在右侧您可以在表格中看到这些正方形和圆形。您可以更改表格中正方形或圆形的值(如大小或位置),并将其更新为更新视图的模型,因此在左侧您可以看到该正方形或圆形如何移动或调整大小。

你有很好的方法,但你很少出错。这是一个基本的、简单的 MVC 模型:

在此处输入图像描述

如您所见,model不会将任何内容发送到controller.

如何构建MVC应用程序?Mabye 最好从model. 除了输入/输出处理之外,model应该有一切。所有的数据,所有的逻辑。

所以你应该有 3 个主要的类:控制器、视图、模型。

例如,您只需使用按钮创建表单,在每次点击中添加一个“A”字母到表单中间。

View课堂上,您有update方法,可以将“A”字母的数量绘制和/或重新绘制到表单中。

当你点击按钮时,它会跳转到方法buttonClicked中。这会调用控制器上的方法,说明控制器刚刚发生了什么。控制器看到并操作模型中的数据(在此示例中调用方法addA)。在这之后,模型应该知道他被改变了,所以他在连接的视图类上调用更新方法,重新绘制打印在表单中间的“A”的计数。

添加

一个模型可以有多个视图!我们可以再添加一个视图,在表单的左上角打印使用的“A”的数量。模型可以有视图列表,而不仅仅是视图,并且在更改时,他只是更新所有视图。

伪代码

public class Application {
    private Model model = new Model();
    private Controller controller = new Controller();
    private View view = new View();

    public Application(){
        model.registerView(view);
        controller.registerModel(model);
        view.registerController(controller);
    }
}
于 2013-10-24T01:25:04.020 回答
2

我认为您感到困惑的领域之一是“责任”。每个组件负责什么以及它实际上可以做什么。

问题不在于您在程序周围传递对象,而更多的是您传递的对象暴露了您的应用程序的某些部分,而接收者不知道或不应该被允许操作。

我的意思是,如果您要将“按钮”面板传递给“猜测”面板,因为您希望能够允许“猜测”面板检测何时单击按钮,那么您已经暴露了“按钮”面板到您的应用程序中无权实际看到它的区域。

是什么阻止“猜测”面板移除组件?没有什么...

相反,我们应该使用interfaceswhich 来确定应用程序的每个部分可以做什么和不能做什么,以及可以使用哪些信息。

这就是你建模的地方。模型决定了哪些信息可用,如何访问它以及可能触发哪些事件以通知相关方模型已更改。

例如。您的“按钮”面板会告诉模型用户已经做出了另一个猜测(响应用户按下按钮)。然后模型会引发一个事件,通知“猜测”面板发生了变化。然后“猜测”面板会相应地更新它的状态,向模型询问它需要的信息,以表示模型的当前状态(就它负责的情况而言)。

你可以看看

现在,使用 MCV 模式,视图必须能够看到模型,控制器必须能够看到视图和模型,而模型并不关心。

控制器正在侦听视图的更改(即用户交互),并将其传递给模型。模型触发有关其状态更改的通知,并且视图通过根据需要更新自身来响应这些更改。

例如,用户单击“按钮”面板上的按钮。“按钮”面板的控制器检测到此事件(可能通过ActionListener),它处理此操作并更新模型。

该模型更新其内部状态并触发某种事件。

“猜测”面板检测到模型中的这种变化(通过某种侦听器)并相应地更新它的视图(根据模型的指示更新猜测和图像)。

现在,请记住,Swing 不使用纯 MCV 模式,它的控件(即按钮)既是控制器又是视图,所以在玩这些时要小心...

我将从HangManModel interface定义您要公开的所有属性的 a 开始,例如猜测、“秘密”词以及可能做出的错误猜测的数量以及游戏的状态(输赢)。

我还将定义可能注册到模型的侦听器,它描述了该模型可以生成的事件。您可以根据自己的需要使用 aPropertyChangeListener甚至 a或定义自己的,例如...ChangeListener

public interface HangManModel {

    public void addGuess(char guess);

    public char[] getGuesses();
    public String getSecretWord();
    public int getState(); // running, win or lose

    public void addChangeListener(ChangeListener listener);
    public void removeChangeListener(ChangeListener listener);

}

现在这只是一个例子,就个人而言,我可能会习惯于隐藏秘密词并公开它的属性(例如它的长度)。您也可能很想为秘密词提供一个设置器,因此可以重置模型......

这将代表您的应用程序的“心脏”,围绕它,您将构建您的视图和控制器。

于 2013-10-24T03:02:43.283 回答
1

有趣的问题......到目前为止,我听说过桌面应用程序中使用的 MVP 和 MVVM 设计模式,但我从未见过用于此类应用程序的 MVC。但是,我只是采用了 Spring MVC(最好的 java web 框架)并尝试将其应用于桌面应用程序。

  1. 我会创建一个前端控制器来处理应用程序的所有事件。
  2. 此控制器获取一个事件并将其发送到 EventResolver。
  3. EventResolver 将扮演“控制器”角色的方法和类的名称或内容返回给前端控制器。
  4. 在前端控制器创建这个类的一个实例并调用一个方法之后。
  5. 在方法体中调用一些业务逻辑,并将 ViewResolver 的模型和 id 返回到前面的 Controler。6 前端控制器再次分析结果并调用适当的 ViewResolver。

是的,这就是 spring MVC 的工作原理,我只是复制了它)但是为什么不使用最好的!

于 2013-10-24T01:26:05.663 回答
0

MVC 有很多不同的风格,但它们都具有相同的总体思想。

首先要了解的是模型是什么。模型的工作是处理所有的逻辑代码。所以在这种情况下,模型会跟踪猜到了哪些字母,猜的是什么单词,游戏是否结束,以及显示了多少个火柴人。

基本上,您应该能够从函数调用到模型中完整地模拟游戏。

有几种方法可以将信息从模型传递到视图。视图可以定期轮询模型以查看是否有任何更新。这种方法不是很优雅。对小型项目通常有效的一种简单方法是将 View 对象传递给 Model 对象,并且每当模型中发生任何变化时,刷新视图中的所有内容。对于较小的 UI 来说,这样做没什么大不了的。最后,您可以创建一个监听器注册系统(观察者模式),让视图的特定部分订阅模型中的特定事件。这种方法是我为较大的 UI 项目所做的。

控制器的工作是将用户输入传递给模型。因此,控制器和视图通常可以定义在同一个类中。这没关系!让您的 JButtons 有一个直接调用模型的 click 方法比告诉某个 Controller 类将其传递给模型要好得多。

于 2013-10-24T01:21:01.420 回答