当前位置: 代码迷 >> Ajax >> CakePHP:两种ajax模式
  详细解决方案

CakePHP:两种ajax模式

热度:963   发布时间:2013-11-02 19:41:10.0
CakePHP:两种ajax方式
方式一:普通的Ajax方式
参考:http://stackoverflow.com/questions/12458235/how-to-send-ajax-response-to-jquery-from-cakephp
Request and Response objects http://book.cakephp.org/2.0/en/controllers/request-response.html
CakePHP2 Request请求对象 http://www.ruiwant.com/cakephp-request-object-tutorial-basic.html
Controller:
<?php
class SitesController extends AppController
{
    public $name = "Sites";

    public function ajaxListAll()
    {
        if ($this->request->is('ajax')) { //这里怎么判断。可能根据情况,但是我使用这样判断是没问题的。
            return new CakeResponse(array('body' => json_encode(array('val' => 'test ok')), 'status' => 200));
        }
    }

}
?>

return new CakeResponse(array('body' => json_encode(array('val' => 'test ok')), 'status' => 200));

javascript:
ajaxTest = function(){
    $.ajax({
        url : '/sites/ajaxListAll',
        data : {
            name : "test",
            shortname : "tst"
        },
        dataType : 'json',
        success : function(html, textStatus) {
            alert('Success ' + textStatus + html);
        },
        error : function(xhr, textStatus, errorThrown) {
            alert('An error occurred! ' + errorThrown);
        }
    });
}











方式二:把ajax得到的内容替换掉dom的某部分
参考:http://www.cnblogs.com/mafeifan/p/3170603.html
CakePHP中的ajax还是比较简单,但要注意一些细节。

app/View/Layouts下新建ajaxtest.ctp
D:\work_documents\htdocs\app\View\Layouts\ajaxtest.ctp
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>CakePHP AJAX Demo :: <?php echo $title_for_layout?></title>
<?php echo $this->Html->charset(); ?>
<?php echo $this->Html->script('jquery-1.7.2.min.js');    ?>
</head>
<body>
<div id="container">
    <center><h2>CakePHP AJAX Demo</h2></center>
    <div id="content"><?php echo $content_for_layout?></div>
    <?php
        $options = array(
            'inline'=>true,
            'cache'=>false,
            'safe' =>false
        );
        echo $this->Js->writeBuffer($options);
    ?>
</div>
</body>
</html>

要注意一定要带上 echo $this->Js->writeBuffer($options); 即输出js。
有关writeBuffer(),自己从官方文档翻译的
php:method:: writeBuffer($options = array())
将所有产生的Javascript写入到代码块中或缓存在文件中,并返回一个带链接的脚本
**选项**

- ``inline`` - (默认为真)若为真,直接在页面内输出缓存内容,若``cache``同样为真,将只产生一个带地址的script标签
- ``cache`` - (默认为假)若为真,将缓存内容保存到一个独立的js文件中,并被页面引用(译者:建议缓存内容过多时使用)
- ``clear`` - (默认为真)若为假,将阻止缓存内容被清除
- ``onDomReady`` - (默认为真)若为真,将缓存内容放到domready事件中(译者:即脚本被自动包含在$(document).ready(function ())中)
- ``safe`` - (默认为真)若为真,页面内的缓存内容被<![CDATA[ ... ]]>语句块包裹

独立出来的js缓存文件在``webroot/js``,要保证该目录可写,并且保证浏览器可以生成任何页面的脚本资源缓存



AjaxtestController.php
D:\work_documents\htdocs\app\Controller\AjaxtestController.php
<?php
class AjaxtestController extends AppController {
    var $layout  = 'ajaxtest';   //指定视图使用的布局为 ajaxtest
    var $helpers = array('Html','Js'); //需要用到的视图辅助类

    function index(){
    }

    function hello(){
        sleep(1);               //本地测试时,为了更好地看到效果,模拟延迟状态
        $this->layout = 'ajax'; //此方法为 AJAX 动作,所以布局需要使用 hello.ctp     
    }
}



Ajaxtest目录并新建index.ctp
D:\work_documents\htdocs\app\View\Ajaxtest\index.ctp
<div id="loading" style="display:none;padding:4px;color:black;
    background-color:#FAD163;width:100px"><strong>Loading...</strong></div>
<div id="view" style="display:none;background-color:#E8EEF7;
    padding:4px;border:1px solid silver;width:300px"></div>
<?php
    //设置 AJAX 选项
    $options = array(
        'update'   => '#view',
        'beforeSend'  => "$('#view').hide();$('#loading').show();",
        'complete' => "$('#loading').hide();$('#view').show();"
    );
    //使用 AjaxHelper 创建 AJAX 动作链接
    echo $this->Js->link('Click here!', '/ajaxtest/hello', $options);
?>
   



再新建一个hello.ctp,ajax加载的内容
D:\work_documents\htdocs\app\View\Ajaxtest\hello.ctp
<center>Hello, AJAX world!</center>



运行http://localhost/ajaxtest/index ,效果是有个超链接文字是'Click here!',但点击链接,内容即hello.ctp通过ajax方法加载进来了。
  相关解决方案