织梦如何判断栏目是否有子栏目?

99ANYc3cd6
预计阅读时长 13 分钟
位置: 首页 织梦建站 正文

最核心、最常用的方法是使用 TypeLink 标签结合 hasChildren 变量。

织梦判断是否有子栏目
(图片来源网络,侵删)

最常用、最推荐的方法(TypeLink + hasChildren

这是织梦官方推荐且最简洁的方法。TypeLink 标签会自动解析出栏目的层级关系,并通过 hasChildren 这个布尔值(真/假)来判断。

适用场景

  • 在导航栏循环中,判断当前栏目是否需要显示下拉菜单。
  • 在栏目列表页,判断当前栏目下是否还有子栏目。

标签代码示例

假设你要在主导航栏中循环输出所有顶级栏目,并为有子栏目的栏目添加一个下拉箭头或下拉菜单。

{dede:channelartlist typeid='0' row='10'}
  <li>
    <a href="{dede:field name='typeurl'/}">{dede:field name='typename'/}</a>
    <!-- 关键判断:hasChildren 为真,则显示子栏目列表 -->
    [field:hasChildren runphp='yes']
      if(@me) {
        @me = '<ul class="sub-nav">';
        @me .= dede_get_son(@me);
        @me .= '</ul>';
      } else {
        @me = '';
      }
    [/field:hasChildren]
  </li>
{/dede:channelartlist}

代码解析:

  1. {dede:channelartlist typeid='0' row='10'}:

    织梦判断是否有子栏目
    (图片来源网络,侵删)
    • typeid='0': 表示获取所有顶级栏目。
    • row='10': 限制只显示10个顶级栏目。
    • 这个标签会循环每一个顶级栏目。
  2. {dede:field name='typeurl'/}{dede:field name='typename'/}:

    分别输出当前顶级栏目的链接和名称。

  3. [field:hasChildren runphp='yes']:

    • 这是核心部分。hasChildrenchannelartlist 标签自动生成的变量,表示当前栏目是否有子栏目。
    • runphp='yes' 允许我们在PHP代码块中处理这个变量。
  4. if(@me):

    • @merunphp 中代表当前标签的值。hasChildren 的值是 1 (有子栏目) 或 0 (无子栏目)。
    • if(@me) 等同于 if(1)if(0),可以用来判断条件是否成立。
  5. @me = dede_get_son(@me);:

    • 这是一个织梦内置函数,用于获取当前栏目的所有子栏目,它会返回一个包含所有子栏目链接和列表的HTML字符串。
    • 注意:这里的 @me 在函数调用前是 hasChildren 的值,调用后 @me 会被函数的返回值(即子栏目的HTML)覆盖。
  6. 简化写法(更常用): 你不需要写这么复杂的PHP判断,织梦的 sonclass 变量可以直接使用。

    {dede:channelartlist typeid='0' row='10'}
      <li>
        <a href="{dede:field name='typeurl'/}">{dede:field name='typename'/}</a>
        <!-- 直接使用 sonclass 变量,它会自动判断并生成子栏目列表 -->
        {dede:field name='sonclass'/}
      </li>
    {dede:channelartlist}

    sonclass 变量在后台的“栏目调用”标签设置中,默认就是“只显示栏目链接”,它会自动处理 hasChildren 的判断,hasChildren 为真,它才会输出子栏目的列表。


使用SQL查询(灵活但稍复杂)

如果你想在更复杂逻辑中判断,或者不使用 channelartlist 标签,可以直接执行SQL查询。

适用场景

  • 在自定义PHP文件或模型中判断。
  • 需要结合其他复杂条件进行判断。

思路

查询 dede_arctype 表,找到当前栏目的ID,然后检查 reid (父栏目ID) 字段等于当前栏目ID的记录是否存在。

示例代码(在模板中使用 runphp

假设你当前在某个栏目的内容页,想判断这个栏目是否有子栏目。

{dede:field name='typeid' runphp='yes'}
  $typeid = @me; // 获取当前栏目的ID
  // 引入数据库配置
  require_once(DEDEROOT.'/data/common.inc.php');
  // 执行SQL查询
  $dsql->SetQuery("SELECT COUNT(*) as num FROM `#@__arctype` WHERE `reid` = $typeid");
  $dsql->Execute();
  $row = $dsql->GetObject();
  // 如果查询结果大于0,则有子栏目
  if ($row->num > 0) {
    @me = '本栏目有子栏目!';
  } else {
    @me = '本栏目没有子栏目。';
  }
{/dede:field}

代码解析:

  1. {dede:field name='typeid' runphp='yes'}: 获取当前内容或栏目页的ID,并启用PHP。
  2. $typeid = @me;: 将获取到的ID保存到变量 $typeid 中。
  3. require_once(DEDEROOT.'/data/common.inc.php');: 引入织梦的数据库配置文件,以便使用 $dsql 数据库对象。
  4. $dsql->SetQuery(...): 设置SQL查询语句。
    • #@__arctype: 这是织梦的表名前缀机制,#@__ 会被替换为你在配置中设置的表前缀(如 dede_)。
    • reiddede_arctype 表中记录父栏目ID的字段。
    • COUNT(*) as num: 计算子栏目的数量。
  5. $dsql->Execute();: 执行查询。
  6. $row = $dsql->GetObject();: 获取查询结果。
  7. if ($row->num > 0): 判断查询到的数量是否大于0。
  8. @me = '...';: 根据判断结果,给 @me 赋值,这个值会最终显示在页面上。

总结与建议

方法 优点 缺点 推荐场景
TypeLink / sonclass 代码简洁,效率高,官方推荐 灵活性相对较低,主要用于模板循环 导航栏、栏目列表页等绝大多数场景
SQL查询 灵活性极高,可结合任何复杂条件 代码量大,需要手动处理数据库连接,效率稍低 在自定义PHP文件、复杂模型或需要特殊逻辑时使用

对于99%的模板开发需求,强烈推荐使用方法一,它既简单又高效,是织梦CMS的内置特性,专门为此类场景设计,只有在方法一无法满足需求时,才考虑使用方法二。

-- 展开阅读全文 --
头像
织梦如何调用会员登录状态?
« 上一篇 今天
标签如何调用?
下一篇 » 今天

相关文章

取消
微信二维码
支付宝二维码

目录[+]