Yii - 设计问题 - 保持拨号与主视图文件分离并访问它们

时间:2011-08-23 14:38:13

标签: yii

我有一个案例,在我的视图文件中有6个链接并点击它们打开CJuiDialog框。我将所有6个对话框代码保存在同一个视图文件中以及链接,这导致文件很大并将它们一起加载一次。理想情况是只有当用户点击时才会加载对话框链接。

那么我们是否可以只保留主视图文件中的链接代码并将所有对话框保存在单独的文件中,并仅在用户点击链接时加载它们

我的意思是

index.php ( view containing only links)
_dialog1 ( containing code for first dialog )
_dialog2 ( containing code for second dialog )
_dialog3 ( containing code for third dialog )
_dialog4 ( containing code for fourth dialog )
_dialog5 ( containing code for fifth dialog )
_dialog6 ( containing code for sixth dialog )

示例代码

//First Dialog code

     $this->beginWidget('zii.widgets.jui.CJuiDialog', array(
            'id'=>'mydialog1',
            'options'=>array(
                'title'=>'Dialog box 1',
                'autoOpen'=>false,
                'modal'=>true,      
            ),
        ));

        echo 'First dialog content here';

        $this->endWidget('zii.widgets.jui.CJuiDialog');

        echo CHtml::link('open dialog', '#', array(
            'onclick'=>'$("#mydialog1").dialog("open"); return false;',
        ));

//2nd dialog code 

$this->beginWidget('zii.widgets.jui.CJuiDialog', array(
            'id'=>'mydialog2',
            'options'=>array(
                'title'=>'Dialog box 1',
                'autoOpen'=>false,
                'modal'=>true,      
            ),
        ));

        echo 'dialog2 content here';

        $this->endWidget('zii.widgets.jui.CJuiDialog');

        echo CHtml::link('open dialog', '#', array(
            'onclick'=>'$("#mydialog2").dialog("open"); return false;',
        ));

我带来的解决方案

//In controller

       public function actionOpenDialog1()
    {
        $data = array();
        $this->renderPartial('_dialogContent1', $data, false, true);
    }
       public function actionOpenDialog2()
    {
        $data = array();
        $this->renderPartial('_dialogContent2', $data, false, true);
    }

//In index.view

<div id="data">
</div>

<?php
echo CHtml::ajaxButton ("Open first dialog", CController::createUrl('dialogTesting/openDialog1'),array('update' => '#data'));

echo CHtml::ajaxButton ("Open second dialog", CController::createUrl('dialogTesting/openDialog2'),array('update' => '#data'));
?>

//_dialogContent1.php

<?php

 $this->beginWidget('zii.widgets.jui.CJuiDialog', array(
            'id'=>'mydialog1',
            'options'=>array(
                'title'=>'Dialog box 1',
                'autoOpen'=>true,
                'modal'=>true,
            ),
        ));

        echo 'first dialog content here';

        $this->endWidget('zii.widgets.jui.CJuiDialog');
?>


//_dialogContent2.php

<?php

 $this->beginWidget('zii.widgets.jui.CJuiDialog', array(
            'id'=>'mydialog1',
            'options'=>array(
                'title'=>'Dialog box 1',
                'autoOpen'=>true,
                'modal'=>true,
            ),
        ));

        echo 'first dialog content here';

        $this->endWidget('zii.widgets.jui.CJuiDialog');
?>

非常感谢你的帮助

此致

Kiran

3 个答案:

答案 0 :(得分:1)

命名文件
Yii中的约定是命名视图文件:

  • index.php:完整视图
  • _dialog1.php:部分视图(包含在其他视图中)

子视图
然后,您可以使用CController::renderPartial()包含部​​分视图:

$this->beginWidget(...);
$this->renderPartial('_dialog1', array('var1' => 23, 'var2' => "var"));
$this->endWidget(...);

分解代码
这应该使您的源节点更轻。但我建议你走得更远,避免重复所有这些小部件调用。为此,您应该为对话框参数定义一个结构并循环它。类似的东西:

$dialogs = array(
    'mydialog1' => array(
        'file' => '_dialog1',
        'options' => array('title' => "My title 1",),
    ),
    'mydialog2' => array(
        'file' => '_dialog12,
        'options' => array('title' => "My title 2",),
    ),
);
$defaultOptions = array(
    'autoOpen' => false,
    'modal' => true,      
);
foreach ($dialogs as $id => $dialog) {
    $this->beginWidget(
        'zii.widgets.jui.CJuiDialog',
        array(
            'id' => $id,
            'options' => CMap::mergeArray($defaultOptions, $dialog['options']),
        )
    );
    // ... include partial view ...

此分解将使您的代码更紧凑,但它将简化未来的更改。使用数据结构来避免代码重复是一种众所周知的做法。

<强> AJAX
最后,如果您真的想要动态加载部分视图,那意味着您必须使用AJAX。请注意,因为从用户的角度来看,您的页面可能不那么活跃。如果你的所有表单都相当于几Kb的HTML,那么就没有AJAX的nedd了。但如果你走这条路,那么你需要:

  • 添加仅包含<div id="dialog-ajax"></div>
  • 的CJuiDialog
  • 创建另一个将在对话框视图中应用renderPartial()的操作。
  • 使用像function dialog1() {jQuery("#dialog-ajax").load(...);}这样写JS的代码替换上一个foreach循环的内容。如果要动态更改小部件标题,则需要进行黑客攻击。
  • 将一些事件(点击)绑定到这些JS函数。

另一种方法是让你的aJAX动作渲染一个完整的CJuiDialog,它可能更简单并避免JS黑客攻击。无论如何,我不确定你真的需要AJAX。

答案 1 :(得分:1)

我的回答

//在控制器中

   public function actionOpenDialog1()
{
    $data = array();
    $this->renderPartial('_dialogContent1', $data, false, true);
}
   public function actionOpenDialog2()
{
    $data = array();
    $this->renderPartial('_dialogContent2', $data, false, true);
}

//在index.view

'#data'));

echo CHtml :: ajaxButton(“打开第二个对话框”,CController :: createUrl('dialogTesting / openDialog2'),array('update'=&gt;'#data')); ?&GT;

// _ dialogContent1.php

$ this-&gt; beginWidget('zii.widgets.jui.CJuiDialog',array(             的 'id'=&GT; 'mydialog1',             '选项'=&GT;阵列(                 'title'=&gt;'对话框1',                 '的AutoOpen'=&GT;真,                 '模态'=&GT;真,             )         ));

    echo 'first dialog content here';

    $this->endWidget('zii.widgets.jui.CJuiDialog');

&GT;

// _ dialogContent2.php

$ this-&gt; beginWidget('zii.widgets.jui.CJuiDialog',array(             的 'id'=&GT; 'mydialog1',             '选项'=&GT;阵列(                 'title'=&gt;'对话框1',                 '的AutoOpen'=&GT;真,                 '模态'=&GT;真,             )         ));

    echo 'first dialog content here';

    $this->endWidget('zii.widgets.jui.CJuiDialog');

&GT;

答案 2 :(得分:0)

你可以在你的页面中简单地包含一个空的CJuiDialog,当它需要显示时,用jQuery AJAX加载内容(load是最简单的,可能就足够了)返回一个渲染打开对话框之前的相应视图。