Drupal专业开发指南 第9章 Drupal区块(Drupal block)(3)创建区块

  
译者: 老葛,eskalate科技公司

创建一个区块:

在本例中,你将创建两个区块,它们使得内容修改更易于管理。首先,你将创建一个区块用于列出等待批准的评论,然后你将创建一个区块以列出未发布的节点。两个区块都提供了用于修改相应内容的编辑表单的链接。

让我们创建一个名为approval.module的模块。它将包含我们的区块代码。在路径sites/all/modules/custom下面创建一个名为approval的文件夹(如果modulescustom不存在的话,你需要创建它们)。

接下来,向文件中添加approval.info文件:

; $Id$

name = Approval

description = Blocks for facilitating pending content workflow.

version = "$name$"

 

然后,在添加approval.module文件:

<?php

// $Id$

/**

* @file

* Implements various blocks to improve pending content workflow.

*/

当你创建好这些文件后,在Administer Site building

Modules下面启用该模块。你将继续使用approval.module,所以不要关闭文本编辑器。

 

       接下来我们添加区块钩子方法并实现list操作,我们的区块将出现在区块管理页面的区块列表中(参看图9-5.

9-5 在区块列表中,你可以看到你创建的区块了。

 

注意数组的键info不是区块启用时所展示给用户的区块标题。而是一个仅出现在管理员可以配置的区块列表页面的描述。你将在接下来的查看(view)情景中实现真正的区块标题。首先,你需要创建额外的配置选项,为了实现这一点,使用下面的代码来实现配置(configue)情景,你创建了一个新的表单字段,当你点击区块列表页面区块右边的配置链接时,即可看到它,如图9-6所示:

9-6 带有区块定制字段的区块配置表单

 

当如图9-6所示的区块配置表单被提交后,它将触发下一步操作,这里是保存,你将使用它来保存表单字段值。

function approval_block($op = 'list', $delta = 0, $edit = array()) {

switch ($op) {

case 'list':

$blocks[0]['info'] = t('Pending comments');

return $blocks;

case 'configure':

$form['approval_block_num_posts'] = array(

'#type' => 'textfield',

'#title' => t('Number of pending comments to display'),

'#default_value' => variable_get('approval_block_num_posts', 5),

);

return $form;

case 'save':

variable_set('approval_block_num_posts',

(int) $edit['approval_block_num_posts']);

break;

}

}

 

 

通过使用Drupal自带的变量系统variable_set(),你将区块所展示的评论的数目保存了下来。注意这里使用了类型转换,将其转换为整数,目的是对数据进行清洁检查,最后添加查看操作,当区块显示时,返回一个待定评论的列表。

function approval_block($op = 'list', $delta = 0, $edit = array()) {

switch ($op) {

case 'list':

$blocks[0]['info'] = t('Pending comments');

return $blocks;

 

case 'configure':

$form['approval_block_num_posts'] = array(

'#type' => 'textfield',

'#title' => t('Number of pending comments to display'),

'#default_value' => variable_get('approval_block_num_posts', 5),

);

return $form;

case 'save':

variable_set('approval_block_num_posts', (int)

$edit['approval_block_num_posts']);

break;

case 'view':

if (user_access('administer comments')) {

// Retrieve the number of pending comments to display that

// we saved earlier in the 'save' op, defaulting to 5.

$num_posts = variable_get('approval_block_num_posts', 5);

// Query the database for unpublished comments.

$result = db_query_range('SELECT c.* FROM {comments} c WHERE

c.status = %d ORDER BY c.timestamp', COMMENT_NOT_PUBLISHED, 0,

$num_posts);

// Preserve our current location so user can return after editing.

$destination = drupal_get_destination();

$items = array();

while ($comment = db_fetch_object($result)) {

$items[] = l($comment->subject, 'node/'. $comment->nid, array(),

NULL, 'comment-'. $comment->cid). ' '.

l(t('[edit]'), 'comment/edit/'. $comment->cid, array(),

$destination);

}

$block['subject'] = t('Pending comments');

// We theme our array of links as an unordered list.

$block['content'] = theme('item_list', $items);

}

return $block;

}

}

这里我们通过对数据库进行查询来获得待定的评论,将评论的标题展示为链接,同时为每一个评论追加一个编辑链接,如图9-7所示

9-7 “待定评论”列表区块在它启用后的情况。它展示了两个待定评论

 

在前面的代码中,注意我们是如何使用方法drupal_get_destination()的,这个方法将记住在你提交表单以前你所在的页面,所以当你更新一个评论以后(或者发布,或者删除),它将自动重定向到你原来所在的页面。

 

使用下面的代码,设置了区块的标题:

$block['subject'] = t('Pending comments');

 

现在待定区块已经完成,让我们在approval_block()钩子函数中定义另一个区块---它列出了所有未发布的节点,并提供了指向它们的编辑页面的链接。

function approval_block($op = 'list', $delta = 0, $edit = array()) {

switch ($op) {

case 'list':

$blocks[0]['info'] = t('Pending comments');

$blocks[1]['info'] = t('Unpublished nodes');

return $blocks;

}

}

注意这里是如何为每一个区块分配一个键值的($blocks[0], $blocks[1], . . . $blocks[n]

)。区块模块将最终使用这些键值作为$delta参数。这里我们将“待定评论”区块的$delta ID定义为0,“未发布节点”区块的$delta ID定义为1。在这里也可以使用“待定”和“未发布”作为键值。有程序员的习惯决定使用哪种键值,而键值不一定是数字形式。

下面是完整的例子,我们的新区块如图9-8所示:

function approval_block($op = 'list', $delta = 0, $edit = array()) {

switch ($op) {

case 'list':

$blocks[0]['info'] = t('Pending comments');

$blocks[1]['info'] = t('Unpublished nodes');

return $blocks;

case 'configure':

// Only in block 0 (the Pending comments block) can one

// set the number of comments to display.

if ($delta == 0) {

$form['approval_block_num_posts'] = array(

'#type' => 'textfield',

'#title' => t('Number of pending comments to display'),

'#default_value' => variable_get('approval_block_num_posts', 5),

);

}

return $form;

case 'save':

if ($delta == 0) {

variable_set('approval_block_num_posts', (int)

$edit['approval_block_num_posts']);

}

break;

case 'view':

if ($delta == 0 && user_access('administer comments')) {

// Retrieve the number of pending comments to display that

// we saved earlier in the 'save' op, defaulting to 5.

$num_posts = variable_get('approval_block_num_posts', 5);

// Query the database for unpublished comments.

$result = db_query_range('SELECT c.* FROM {comments} c WHERE c.status = %d

ORDER BY c.timestamp', COMMENT_NOT_PUBLISHED, 0, $num_posts);

$destination = drupal_get_destination();

$items = array();

while ($comment = db_fetch_object($result)) {

$items[] = l($comment->subject, 'node/'. $comment->nid, array(),

NULL, 'comment-'. $comment->cid). ' '.

l(t('[edit]'), 'comment/edit/'. $comment->cid, array(),

$destination);

}

$block['subject'] = t('Pending Comments');

// We theme our array of links as an unordered list.

$block['content'] = theme('item_list', $items);

}

elseif ($delta == 1 && user_access('administer nodes')) {

// Query the database for the 5 most recent unpublished nodes.

// Unpublished nodes have their status column set to 0.

$result = db_query_range('SELECT title, nid FROM {node} WHERE

status = 0 ORDER BY changed DESC', 0, 5);

$destination = drupal_get_destination();

while ($node = db_fetch_object($result)) {

$items[] = l($node->title, 'node/'. $node->nid). ' '.

l(t('[edit]'), 'node/'. $node->nid .'/edit', array(),

$destination);

}

$block['subject'] = t('Unpublished nodes');

// We theme our array of links as an unordered list.

$block['content'] = theme('item_list', $items);

}

return $block;

}

}

 

9-8 区块启用后,列出了未发布节点列表

 

由于你有多个区块,你查看操作下,你使用了if…elseif来构建。在每一种情况下,你检查被查看区块的$delta以决定你是否该运行该段代码。在脚本形式里,它看起来如下所示:

if ($delta == 0) {

// Do something to block 0

}

elseif ($delta == 1) {

// Do something to block 1

}

elseif ($delta == 2) {

// Do something to block 2

}

 

在“未发布节点”区块启用后,区块的最终结果如图9-8所示。

 

额外例子:添加一个“待定用户”区块

如果你想扩展approval.module,你可以添加另一个区块,以展示等待站点管理员批准的用户帐号。这将作为作业留给读者自己动手将其放到approval.module模块中去。这里展示了一个在假定的userapproval.module模块中的类似的例子:

function userapproval_block($op = 'list', $delta = 0, $edit = array()) {

switch ($op) {

case 'list':

$blocks[0]['info'] = t('Pending users');

return $blocks;

case 'view':

if (user_access('administer users')) {

$result = db_query_range('SELECT uid, name, created FROM {users}

WHERE uid != 0 AND status = 0 ORDER BY created DESC', 0, 5);

$destination = drupal_get_destination();

// Defensive coding: we use $u instead of $user to avoid potential namespace

// collision with global $user variable should this code be added to later.

while ($u = db_fetch_object($result)) {

$items[] = theme('username', $u). ' '.

l('[edit]', 'user/'. $u->uid. '/edit', array(), $destination);

}

$block['subject'] = t('Pending users');

$block['content'] = theme('item_list', $items);

}

return $block;

}

}

 

在安装模块时,启用一个区块

 

有时,你想在安装模块时,将一个区块自动展示出来。这非常直接,通过查询语句直接将区块的设置信息直接插入到blocks表中即可。查询放在钩子方法hook_install(),钩子方法位于模块的.install文件中。下面是一个例子,当Drupal被安装时,用户模块启用了用户区块(参看modules/system/system.install):

db_query("INSERT INTO {blocks} (module, delta, theme, status) VALUES

('user', 0, '%s', 1)", variable_get('theme_default', 'garland'));

上面的数据库查询语句将区块插入到了区块表中,并将它的状态设置为1,所以它被启用了。

 

 

区块可视化例子

在区块管理接口里面,你可以在区块配置页面的“页面可视化配置”里面加入php代码片段。当一个页面被构建时,Drupal将运行php代码片段来决定区块是否被显示。一些常用的代码片段例子如下所示。每一段代码返回TRUE或FALSE来指示区块对于特定请求是否可见。

 

将区块仅展示给登录用户

$user->id不为0时,返回TRUE

<?php

global $user;

return (bool) $user->uid;

?>

 

将区块仅展示给匿名用户

$user->id为0时,返回TRUE

<?php

global $user;

return !(bool) $user->uid;

?>

 

小结

在本章,你学到了以下几点:

区块是什么以及它们与节点的区别

区块的可视化和位置配置是如何设定的

如何定义一个或多个区块

如何在默认情况下启用区块

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值