基础篇27. 菜单的覆写(上)

ok,我们现在的网站缺少一个菜单,因此,我们来演示一下如何为Drupal网站添加菜单,并且把它做成我们需要的样式。

在结构页面,点击菜单,可以管理网站所有的菜单,还可以添加新的菜单。他们各有各的用处,如果你是新手,应该尝试熟悉它们。这里我们只看main navigation,也就是主导航条。

我们编辑这个菜单,可以看到目前只有首页一个项目。我们为了演示目的,先建立几个没有实际链接的项目,你可以在你的网站有了内容之后,再修改这些链接,目前你只需要填写链接名称和#字符。

我们随意创建几个链接:产品展示、我们的团队、联系我们、关于我们。

现在主导航条一共有5个项目,我们拖拽项目前面的十字箭头图标,来调整项目的顺序和层级关系。在最后,将关于我们这个项目,往右边拖拽,使他成为联系我们的二级菜单。

drupal 菜单 编辑

然后我们在info文件中建立一个新的区域 Nav。

 nav: Nav

并且在区域布局页面中,将main navigation这个区块放置到Nav区域中。

区域布局

最后在首页模板中将Nav区域打印出来。

注意这里调整了模板文件中的class,用于放置logo和菜单的div的宽度被改成了10栏,而放置用户入口的按钮的div被改成了2栏。

以上这些步骤之前已经演示过2次了,这里就不具体演示了。

刷新首页之后,你可以看到,在logo的下方打印出了主导航条。但是我们还需要继续修改样式。首先,查看元素,找到负责输出这个导航条的模板。我们可以看到,它位于基主题中,名字是menu.html.twig。然后可以看到,twig debug模式为我们提供了一个专门用于主导航条的模板建议:menu--main.html.twig ,我们拷贝这个名字,因为一会要用到。

然后在编辑器中找到stable基主题中的menu.html.twig模板,将他复制一份到我们的主题文件夹中,并且重命名为刚才拷贝的名字。

重建缓存,刷新页面之后,我们可以看到,现在负责输出导航条的模板就来自于我们的nowicode主题文件夹了。

然后,修改这个模板文件,并添加适当的CSS规则,我们就可以得到视频中所展示的结果了。

drupal 菜单

详细的修改过程非常精彩,请阅读文档,一定不要错过哦!!

让我们来看一下这个模板文件。

{#
/**
 * @file
 * Theme override to display a menu.
 *
 * Available variables:
 * - menu_name: The machine name of the menu.
 * - items: A nested list of menu items. Each menu item contains:
 *   - attributes: HTML attributes for the menu item.
 *   - below: The menu item child items.
 *   - title: The menu link title.
 *   - url: The menu link url, instance of \Drupal\Core\Url
 *   - localized_options: Menu link localized options.
 *   - is_expanded: TRUE if the link has visible children within the current
 *     menu tree.
 *   - is_collapsed: TRUE if the link has children within the current menu tree
 *     that are not currently visible.
 *   - in_active_trail: TRUE if the link is in the active trail.
 */
#}
{% import _self as menus %}

{#
  We call a macro which calls itself to render the full tree.
  @see http://twig.sensiolabs.org/doc/tags/macro.html
#}
{{ menus.menu_links(items, attributes, 0) }}

{% macro menu_links(items, attributes, menu_level) %}
  {% import _self as menus %}
  {% if items %}
    {% if menu_level == 0 %}
      <ul{{ attributes }}>    {# 第33行 #}
    {% else %}
      <ul>
    {% endif %}
    {% for item in items %}
      <li{{ item.attributes }}>
        {{ link(item.title, item.url) }}    {# 第39行 #}
        {% if item.below %}
          {{ menus.menu_links(item.below, attributes, menu_level + 1) }}
        {% endif %}
      </li>
    {% endfor %}
    </ul>
  {% endif %}
{% endmacro %}

首先,模板中的注释介绍了模板中各个变量的作用,值得一读。

然后,整个模板代码的主体是一个twig中的macro。核心开发者很显然知道我们这些弱爆了的Themer不知道macro是什么东东,所以很贴心的在注释中添加了twig官网关于macro文档的地址,还解释说调用这个macro是为了在页面上渲染整个目录树。(有木有觉得这个解释有点然并卵的味道?)

不过好在我们这些弱爆了的Themer只要知道在哪里可以控制markup就行了。如果你想搞清楚这个macro到底是什么,请阅读云客的《原生twig模板引擎详解(上集:设计师篇)》

所以,第33行,我们用addClass为最顶层的ul标签加上一个class,代码见文档。

<ul{{ attributes.addClass('nav') }}>

用此代码替换原始代码。此处的nav是bootstrape中导航条的顶层ul所必有的类名。而代码中的

menu_level == 0

也印证了这一点。

注意这里只加了一个class,你也可以添加多个class,那么他们要用英文逗号隔开,并且每个class要放在一对引号中间,格式如下:

<ul{{ attributes.addClass('nav','class1','class2') }}>

接着,第39行代码:

{{ link(item.title, item.url) }}

是用来输出li中的a标签的。这里的link是另一个twig中的函数(function)。你可以在官网文档中找到它的解释。并且我们通过官网文档可以知道,如果要为这里的a标签添加class我们需要使用这样的格式:

{{ link(item.title, item.url, { 'class':['foo', 'bar', 'baz']} ) }}

其中item.title是链接的名字,item.url是链接的地址。

我们需要将第39行改成:

{{ link(item.title, item.url, { 'class':['btn', 'btn-info-outline']} ) }}

或者:

{{ link(item.title, item.url, item.attributes.addClass('btn', 'btn-info-outline') ) }}

或者直接写成:

<a href="{{ item.url }}" class="btn btn-info-outline" >{{ item.title }} </a>

此处class="btn btn-info-outline”的作用,其实在之前“我的账户”按钮时,就已经使用过了。它可以把链接变成按钮,并且为按钮添加一个带圆角的外边框,以起到修饰作用。

至于,上面三种写法你应该用哪一种,主要看通过attributes输出的HTML属性删除之后是否会影响网站功能。系统通常都会通过attributes对象添加一些HTML属性,这些属性有的时候会被其他模块所使用,如果删除了,这些模块所提供的功能就会出问题。有些类代表的含义只有在系统处理阶段才能判断出来,前端虽然可以给出命名,但没法做判断,这也是系统需要提供类的一个原因,典型的如:required、error、active等等。还有些表单具备的类不只是用来做外观,也用来执行一些功能。

如果你的网站不需要使用这些功能,则三种写法都可以,如果需要,则使用Attribute,换句话说,使用Attribute是比较保险的做法。关于Attribute的更多细节,请看第二章的相关内容。

而在我们这个例子中,检查元素的时候你会发现,第38行的item.attributes并没有为li标签添加任何class,也就是说,不存在丢失class而导致功能缺失的问题,因此可以直接添加需要添加的class,而不必使用Attribute。

然后我们在CSS中再添加几条代码:

#block-nowicode-branding{
    float: left;
}

.nav{
    float: right;
}

#block-nowicode-main-menu ul li {
    float: left;
    margin: 0 10px;
}

这里前两条是为了让logo和导航条分别向左和向右浮动。最后一条规则是让导航条中的每个项目都向左浮动,这样就不会垂直的堆叠起来,并且为按钮之间添加一个20像素的间距。

到这里,我们就做出了视频结尾部分的菜单样式。

但是,此处还遗留了一些问题:

  1. 未显示二级菜单。
  2. 不是响应式的菜单。
  3. 所有的菜单页面都有一个is-active的class。

前面两个问题,我们留到下一节讲。这里先只谈第三条。这里只有首页应该有这个is-active的class,因为我们在首页。其他几个项目包含is-active是因为我们之前创建菜单项目的时候填写的是空链接地址#,因此,在实际项目中只要填入真实的node地址即可即可解决这个问题。

 

本书共84小节:

评论 (写第一个评论)