如何正确地将数据从控制器传递到视图?

时间:2013-09-22 23:34:13

标签: php model-view-controller

我目前的实施:

class SomeController extends AppController
{
    function someaction()
    {   
        $d['text'] = "ahoy!";
        $this->render("someactionView", $d);
    }
}

AppController

function render($file, $data = "")
{
    require "views/" . $file . ".php";
}

$data将在视图文件中可用。这是正确的实施吗?这种实现有谬误吗?

3 个答案:

答案 0 :(得分:9)

  

$data将在视图文件中可用。这是正确的吗?   实施?这种实现有谬误吗?

基本上你像大多数框架一样实现它。这有几个问题:

  • 控制器接受输入并发送输出(打破单一责任原则)
  • 视图与HTML紧密耦合。因此,您不能将相同的视图重用于其他内容,例如XML,JSON。
  • 如果您使用require "views/" . $file . ".php";方法render()进行操作,那么您再次强烈关注它。如果您更改视图的位置怎么办?然后你必须稍微重写你的方法。这种方法仅仅会杀死重用能力。

刷新基本知识:

控制器(也称为编辑器)

仅用于单一目的。它会更改模型状态 - 也就是说,它应该采用来自$_POST$_GET$_FILES$_COOKIE的输入。在控制器中,只应进行变量分配,不再是

class Controller
{
   public function indexAction()
   {
        $this->view->setVar('age', $this->request->getPostParam('age'));
        $this->view->setVar('user', $this->request->getPostParam('user'));
        //...
   }
}

视图

视图可以直接访问模型。为了使make视图更易于重用和维护,你最好将所需的东西作为函数参数(或通过setter)传递

class View
{
   public function render($templateFile, array $vars = array())
   {
      ob_start();
      extract($vars);
      require($templateFile);

      return ob_get_clean();
   }
}

应如何初始化视图以及如何将变量传递给它?

首先 - 视图应该在MVC-triad之外实例化。由于控制器会写入视图或模型 - 您可以通过控制器传递变量进行查看。

$model = new Model();
$view = new View($model);

$controller = new Controller($view);

// This will assign variables to view
$controller->indexAction();

echo $view->render();
  
    
      

注意:在现实世界中,模型不是类,而是抽象层。我将其称为Model用于演示目的。

    
  

答案 1 :(得分:3)

IMO render()方法属于视图而不属于控制器。代码应如下所示:

控制器:

class SomeController extends AppController
{
    function someaction()
    {   
        $d['text'] = "ahoy!";
        $view = new SomeActionView();
        $view->assign('data', $d);
        echo $view->render();
    }
}

查看基类:

class View
{

    protected $data;

    function render($template) {
        ob_start();
        // you can access $this->data in template
        require "views/" . $template . ".php";
        $str = ob_get_contents();
        ob_end_clean();
        return $str;
    }


    function assign($key, $val) {
        $this->data[$key] = $val;
    }
}

扩展View类

class SomeActionView extends View
{

    public function render($template = 'someActionTemplate') {
        return parent::render($template);
    }

}

答案 2 :(得分:2)

  

这是正确的实施吗?这种实现有谬误吗?

简短的回答:没有和几个。

首先,你所拥有的是没有观点。这只是一个愚蠢的php template。 MVC中的视图是实例,包含应用程序的UI逻辑。他们从模型层提取信息,并根据收到的信息创建响应。此响应可以是简单文本,JSON文档,从多个模板组装的HTML页面,也可以是HTTP标头。

对于控制器,它的唯一任务是改变模型层的状态和(在极少数情况下)当前视图。控制器初始化视图,也不填充模板。