`
helloyesyes
  • 浏览: 1304267 次
  • 性别: Icon_minigender_2
  • 来自: 武汉
文章分类
社区版块
存档分类
最新评论

第八天-Ajax交互

阅读更多
Symfony回顾

在七个小时的工作之后,askeet程序已经很好了。主页显示问题列表,问题的详细内容显示其答案,用户具有一个配置页面,而各种主题列表也可以由每一页的侧边栏访问。我们社区加强的FAQ处在其正确的方向上,而现在用户还不可以修改数据。

如果web中数据操作的基础是长长的表单,那么今天的AJAX技术可以改变程序的构建方式。而这也同样适用于askeet。在这个指南中,我们将会显示在askeet中添加加强的AJAX交互。其目标就是允许一个已注册的用户声明其对某一个问题的兴趣。

在布局中添加一个指示器

当一个异步请求发送时,AJAX网站的用户并不需要考虑通常的动作暂停,而结果会很快显示。这就是所有的AJAX交互页面应能够可以显示一个活动的指示器的原因。

正因为如此,在全局的layout.php的<body>顶部添加下面的代码行:

<div id="indicator" style="display: none"></div>

尽管默认情况下这是隐藏的,但是当AJAX请求发送时,<div>就会显示。他是空的,但是main.css样式表指定其形状与内容:

div#indicator
{
position: absolute;
width: 100px;
height: 40px;
left: 10px;
top: 10px;
z-index: 900;
background: url(/images/indicator.gif) no-repeat 0 0;
}

添加AJAX交互来声明兴趣

一个AJAX交互由三部分组成:调用者(一个链接,一个按钮或者是其他的用户启动动作的控件),一个服务器动作,以及页面中向用户显示动作结果的区域。

调用者

让我们回到显示的问题。如果我们还记得第四天,一个问题可以在一个问题列表中显示,也可以在问题详细中显示。

这就是将问题标题与兴趣块重构到一个_interested_user.php片段中的原因。再次打开这个片段,添加一个链接允许用户声明其兴趣:

<?php use_helper('User') ?>

<div class="interested_mark" id="mark_<?php echo $question->getId() ?>">
<?php echo $question->getInterestedUsers() ?>
</div>

<?php echo link_to_user_interested($sf_user, $question) ?>

这个链接所做的不仅是重定向到另一个页面。事实上,如果一个用户已经指定了其对某一个问题的兴趣,他就不可以再一次声明。而且如果这个用户没有被认证,呃,这将是我们后面要讨论的情况。

这个链接是在一个帮助器函数中编写的,这就需要在askeet/apps/frontend/lib/helper/UserHelper.php中创建:

<?php

use_helper('Javascript');

function link_to_user_interested($user, $question)
{
if ($user->isAuthenticated())
{
$interested = InterestPeer::retrieveByPk($question->getId(), $user->getSubscriberId());
if ($interested)
{
// already interested
return 'interested!';
}
else
{
// didn't declare interest yet
return link_to_remote('interested?', array(
'url' => 'user/interested?id='.$question->getId(),
'update' => array('success' => 'block_'.$question->getId()),
'loading' => "Element.show('indicator')",
'complete' => "Element.hide('indicator');".visual_effect('highlight', 'mark_'.$question->getId()),
));
}
}
else
{
return link_to('interested?', 'user/login');
}
}

?>

link_to_remote()函数是AJAX交互的第一个元素:调用者。他声明了当用户点击链接时必须请求哪个动作(在这里为user/interested)以及页面中的哪个区域必须使用动作结果进行更新。两个事件处理器(loding与complete)被添加进来并且与原型javascript函数相关联。原型库提供了手动的javascript工具来使用简单的函数调用实现页面中的可视效果。唯一的不足是文档的缺乏,但是源码是相当直接的。

我们选择使用帮助器而不是partial,是因为这个函数的PHP代码要多于HTML代码。

不要忘记在question/_list片段中添加id id="block_<?php echo $question->getId() ?>"。

<div class="interested_block" id="block_<?php echo $question->getId() ?>">
<?php include_partial('interested_user', array('question' => $question)) ?>
</div>

结果区域

link_to_remote() javascript帮助器的update属性指定了结果区域。在这个例子中,user/interested动作的结果将会替换id为block_XX的元素的内容。如果我们还感到迷惑,我们可以查看一下这个模板片段中所集成的内容:

...
<div class="interested_block" id="block_<?php echo $question->getId() ?>">
<!-- between here -->
<?php use_helper('User') ?>
<div class="interested_mark" id="mark_<?php echo $question->getId() ?>">
<?php echo $question->getInterestedUsers() ?>
</div>
<?php echo link_to_user_interested($sf_user, $question) ?>
<!-- and there -->
</div>
...

两段注释的中间区域即为结果区域。这个动作一旦执行,就会替换这些内容。

第二个id(mark_XX)的兴趣是十分明显的。link_to_remote帮助器的完整事件处理器将高亮显示已点击的兴趣的interested_mark <div>层,在动作返回一个兴趣的增量数。

服务器动作

AJAX调用器指向user/interested动作。这个动作必须在Interest表中为当前的问题以及当前的用户创建新的记录。在Symfony中我们可以这样来做:

public function executeInterested()
{
$this->question = QuestionPeer::retrieveByPk($this->getRequestParameter('id'));
$this->forward404Unless($this->question);

$user = $this->getUser()->getSubscriber();

$interest = new Interest();
$interest->setQuestion($this->question);
$interest->setUser($user);
$interest->save();
}

在这里我们要记住,Interest对象的->save()方法已经被修改来增加相关用户的interested_user域。所以对于当前问题感兴趣的用户数目会在动作调用之后自动增加。

那么结果的interestedSuccess.php模板应如何显示呢?
<?php include_partial('question/interested_user', array('question' => $question)) ?>

他会再一次显示问题模块的_interested_user.php片段。这就是我们编写这个片段的最大好处。

我们必须禁止这个模板的布局(modules/user/config/view.yml):

interestedSuccess:
has_layout: off

最终测试

AJAX兴趣的开发到现在就结束了。我们可以进行相应的测试,在登陆页面输入已存在的用户名与密码,显示问题列表,并且点击'interested?'链接。当请求发往服务器时就会显示指示器。然后,当服务器应答后增加的数目就会高亮显示。我们可以注意到初始的'interested?'链接现在变为'interested'并且没有链接,这样就是我们的link_to_interested帮助器所起的作用。

添加一个内联'sign-in'表单

我们在前面说到只有注册用户可以声明对某一个问题的兴趣。这就意味着如果一个未授权的用户点击一个'interested?'链接时,必须首先显示登陆页面。

但是等一下。为什么用户要装入一个新的页面来登陆,而失去与他所声明的感兴趣的问题失去联系呢?一个更好的办法就是在页面上动态装入一个登陆页面。这就是我们将要做的工作。

在布局中添加一个隐藏登陆表单

打开全局布局(askeet/apps/frontend/templates/layout.php),添加下面的代码(header与content div之间的内容):

<?php use_helper('Javascript') ?>

<div id="login" style="display: none">
<h2>Please sign-in first</h2>

<?php echo link_to_function('cancel', visual_effect('blind_up', 'login', array('duration' => 0.5))) ?>

<?php echo form_tag('user/login', 'id=loginform') ?>
nickname: <?php echo input_tag('nickname') ?><br />
password: <?php echo input_password_tag('password') ?><br />
<?php echo input_hidden_tag('referer', $sf_params->get('referer') ? $sf_params->get('referer') : $sf_request->getUri()) ?>
<?php echo submit_tag('login') ?>
</form>
</div>

再一次说明,这个表单默认是隐藏的。referer隐藏标记包含referer请求参数,或者是当前的URI。

当非授权用户点击interested链接时显示表单

我们还记得在前面编写的User帮助器吗?现在我们将要来处理非授权用户的情况。打开askeet/lib/helper/UserHelper.php文件,将下面的代码行:

return link_to('interested?', 'user/login');return link_to('interested?', 'user/login');

改为:

return link_to_function('interested?', visual_effect('blind_down', 'login', array('duration' => 0.5)));

当用户为非授权时,'interested?'上的链接会载入一个原型javascript效果(blind_down)来为login id留出空间。

登陆用户

user/login动作已经在第五天编写完成了,并且在第六天进行了重构。我们需要再一次进行修改。

public function executeLogin()
{
if ($this->getRequest()->getMethod() != sfRequest::POST)
{
// display the form
$this->getRequest()->getParameterHolder()->set('referer', $this->getRequest()->getReferer());

return sfView::SUCCESS;
}
else
{
// handle the form submission
// redirect to last page
return $this->redirect($this->getRequestParameter('referer', '@homepage'));
}
}

现在的工作已经很完美了,保存的referer将会用户重定向到用户点击以前所在的页面。

现在测试AJAX功能。一个未注册的用户点击时将会显示一个登陆页面而不离开当前页面。如果用户名与密码通过了认证,页面会进行刷新,用户可以点击他之前想要点击的'interested?'链接。

明天见
分享到:
评论

相关推荐

    WXHHDI01-AJAX-B1-GetStarted-CS

    【描述】中的重复部分"HDI01-AJAX-B1-GetStarted-CS"可能是课程或文档编号,暗示这是一个系列教程的第一部分,专注于基础的AJAX应用。"CS"可能代表"客户端脚本"或"计算机科学",强调这是从客户端视角学习AJAX。 ...

    第五章-JQUERY-Ajax

    **第五章 - JQUERY-AJAX** 在Web开发中,AJAX(Asynchronous JavaScript and XML)是一种用于创建动态网页的技术,允许在不刷新整个页面的情况下与服务器交换数据并更新部分网页内容。jQuery是一个广泛使用的...

    Jquery-Ajax获取手机号归属地实例

    通过这个实例,我们可以看到jQuery-Ajax在实现异步数据交互中的强大能力,以及如何结合第三方API获取并展示动态数据。对于开发者来说,理解并掌握这一技能,对于提升用户体验和构建高效Web应用至关重要。

    javascript-ajax基本属性方法详解

    JavaScript中的AJAX(Asynchronous JavaScript and XML)是一种创建动态网页的技术,允许在不重新加载整个页面的情况下,与服务器交换数据并更新部分网页内容。这里我们将深入讲解JavaScript的基础知识以及AJAX的...

    第34章 项目1-博客前端:封装库--Ajax发文1

    在本章“项目1-博客前端:封装库--Ajax发文”中,我们将探讨如何使用Ajax技术来实现一个博客文章的发布功能。Ajax(Asynchronous JavaScript and XML)是一种创建动态网页的技术,它允许我们在不重新加载整个页面的...

    第34章 项目1-博客前端:封装库--Ajax登录1

    Ajax(Asynchronous JavaScript and XML)的核心优势在于它允许网页在无需刷新整个页面的情况下与服务器进行交互,从而避免了传统表单提交时页面刷新的中断感。 **一、问题所在** 传统的登录方式通常涉及以下问题:...

    第12章 JS-Web-API-Ajax【每个工程师必须熟练掌握的技能】.rar

    Ajax使得前端工程师能够通过后台通信在不重新加载整个网页的情况下获取和更新数据,从而极大地提高了Web应用的交互性和响应性。 一、Ajax基础 Ajax基于JavaScript,通过创建XMLHttpRequest对象来实现与服务器的异步...

    python1903笔记 09-Ajax.zip

    Python 1903 笔记中的第 09 部分主要聚焦于 AJAX(Asynchronous JavaScript and XML)技术,这是一种在不刷新整个页面的情况下更新网页内容的技术。AJAX 通过组合 JavaScript、XMLHttpRequest 对象和 DOM(文档对象...

    第八章 AJAX基础

    第八章探讨了AJAX(Asynchronous JavaScript and XML)基础,这是一种用于创建富互联网应用程序(Rich Internet Applications,简称RIA)的关键技术。富客户端技术旨在提供更好的用户体验,避免传统网页每次操作都...

    ACCP5.0课件-SSH AJAX第6-9章课件

    第八章:Hibernate ORM Hibernate是一个流行的Java持久化框架,它简化了数据库操作。这一章会介绍Hibernate的基本概念,如实体类、对象关系映射(ORM)、Session和Transaction管理。学员将学习如何通过Hibernate API...

    js-jq-ajax-grigliaquad:Ajax第一步

    jQuery是JavaScript的一个库,简化了DOM操作、事件处理、动画和Ajax交互等任务,使得开发者能够更高效地编写代码。 【标签】"HTML" 表明这个项目或教程可能涉及HTML结构,HTML是构成网页的基本元素,用于定义网页...

    AJAX培训 - 第一讲:AJAX基础

    ### AJAX培训 - 第一讲:AJAX基础 #### 一、引言 随着网络技术的发展,用户对于网页的交互性和实时性有了更高的期待。传统的Web应用程序每次与服务器交互都需要进行整个页面的刷新,这种方式不仅效率低下,而且用户...

    医疗病历交互系统-医疗病历交互系统的设计与实现代码-java-springboot-代码-源码-项目-系统-毕设-网站-代码

    医疗病历交互系统-医疗病历交互系统的设计与实现代码-java-springboot-基于springboot的医疗病历交互系统项目-代码-源码-项目-系统-毕设-网站 1、技术栈:java,springboot,vue,ajax,maven,mysql,MyBatisPlus等 ...

    AJAX揭秘-第一部分-AJAX Shoutbox

    **AJAX揭秘 - 第一部分:AJAX Shoutbox** AJAX(Asynchronous JavaScript and XML)是一种在无需重新加载整个网页的情况下更新部分网页内容的技术。它通过在后台与服务器交换数据并更新部分网页,实现了用户体验的...

    疯狂ajax讲义 --第二版--下载地址-华为网盘

    通过《疯狂Ajax讲义》第二版的学习,开发者不仅可以掌握Ajax技术,还能为构建更加高效、交互丰富的Web应用打下坚实的基础。书中的下载地址和评论提示表明,这是一个社区共享的资源,可能包含了其他开发者的经验和...

    AJAX-2.rar

    AJAX 的核心是浏览器的 `XMLHttpRequest` 对象,它允许JavaScript在后台与服务器进行通信,而不会影响用户对页面的交互。这意味着用户可以在等待服务器响应的同时继续浏览或操作页面的其他部分。 **2. 动态更新:**...

    疯狂ajax源代码第01-12章

    8. **Ajax与Comet** (第08章) - **Comet技术**:长轮询和流式传输,实现服务器向客户端推送数据。 9. **Ajax与Web存储** (第09章) - **Cookie、LocalStorage和SessionStorage**:讲解三种在客户端存储数据的方式...

    基于J2EE的Ajax宝典--源代码

    可能在第8章出现相关示例。 4. **异步数据加载和页面局部更新**:通过Ajax实现表格数据的动态加载,或者表单验证的实时反馈,可能在第10章进行演示。 5. **高级Ajax应用**:第11章可能是进阶内容,如Ajax的缓存...

    四天学会AJAX

    **第一天:认识AJAX** AJAX,全称Asynchronous JavaScript and XML(异步JavaScript和XML),是一种在无需刷新整个网页的情况下,能够更新部分网页的技术。它通过在后台与服务器进行少量数据交换,使得网页实现异步...

    14.3-ajax-giphy-party

    在本项目"14.3-ajax-giphy-party"中,我们主要探讨的是使用...通过学习和实践"14.3-ajax-giphy-party"项目,开发者不仅可以掌握Ajax的基本用法,还能了解如何与第三方API交互、处理JSON数据以及提升Web应用的用户体验。

Global site tag (gtag.js) - Google Analytics