使用Handlebars模块化你的页面

Handlebars的layout和partials

Handlebars的layout文件和partials文件,可以是我们很轻松的组织一些公共的页面或代码片段,使得前端视图可维护性非常高。

Handlebars的layout文件

Express+express-handlebars项目中,我们定义好页面的layout文件后,然后在内容变化的位置加入{{{body}}},这样我们每次渲染页面都会替换到{{{body}}}中,这种“布局文件”的概念大大的降低了我们的维护成本。

Handlebars的partials文件

partials文件,也就是片段文件,可以放置公共的引用。
在配置Handlebars的时候,我们可以指定partials文件目录:

var hbs = exphbs.create({
    partialsDir: 'views/partials',
    layoutsDir: "views/layouts/",
    defaultLayout: 'main',
    extname: '.hbs',
    helpers: hbsHelper
});

这样在partials目录下定义的handlebars文件都会是partials文件,使用方法:{{> head}}

下面是一个布局文件(layout.hbs),同时使用了partials文件,可供参考:

<!doctype html>
<html>
<head>
    {{> head}}
</head>
<body class="hold-transition skin-blue layout-top-nav">
<div class="wrapper">
    {{>header}}
    <!-- Full Width Column -->
    <div class="content-wrapper">
        <div class="container">
            {{{body}}}
        </div>
    </div>
</div>
{{>footer}}
<script src="/js/app.js"></script>
</body>
</html>

使用Helper实现段落功能

所谓段落功能,就是我们在页面预置一个位置,动态来渲染这个位置的代码(代码可以是html、js、或者css)。
概念听起来可以有些模糊,我们举个例子:


举个栗子

我们已经知道,上面的layout.hbs文件是一个布局文件,所有的跳转页面都会通过这个布局文件来渲染内容,那么现在假如有一个个例页面(/hello请求渲染的页面),需要用js来处理一段代码呢?

<script>
alert('hello world');
</script>

如果我们在layout中加入这段js代码,那么所有的页面都会打印hello world,显然不是我们想要的,我们仅仅是想在请求/hello的时候打印。

用partials?可以吗?答案是不可以。
partials仅能来组织公共的代码片段,不是用来个性化的。

那么又有童靴提出解决方案:在/hello渲染的页面底下加上不就行了吗?
如:hello.hbs

这也是一种解决方案,但是出来的代码不伦不类,查看/hello渲染的页面源码:

```javascript
<!doctype html>
<html>
<head>
    {{> head}}
</head>
<body class="hold-transition skin-blue layout-top-nav">
<div class="wrapper">
    {{>header}}
    <!-- Full Width Column -->
    <div class="content-wrapper">
        <div class="container">
            <script>
            alert('hello world');
            </script>
        </div>
    </div>
</div>
{{>footer}}
<script src="/js/app.js"></script>
</body>
</html>

我们的script代码片段跑到container里了!这个简单的例子能满足需求,但是加入javascript片段依赖jquery,而jquery是在{{>footer}}里引用呢?这里肯定就会报错了。

使用Helper优雅的解决段落问题

Handlebars提供了强大的Helper支持,使我们解决这个问题变得简单明了。

首先我们定义一个helper,来组织这些个性片段(这些片段可能包含js、css、特殊的html等等)。

section: function(name, block){
    if(!this._sections) this._sections = {};
    this._sections[name] = block.fn(this);
    return null;
},

在这个helper 中,我们定义了_sections变量(需要理解handlebars中的this关键字),当指定了_sectionsname时,就会动态渲染session中的内容。

如何使用?
首先我们可以在layout中预置一个section。如果我们渲染动态的js段落,需要放到{{> footer}}下面。以下是改造后的layout文件部分代码:

{{>footer}}
<script src="/js/app.js"></script>
{{{_sections.js}}}
</body>
</html>

说明:{{{_sections.js}}}这段是预置的代码,意思是从this._sections变量中取namejs的段落,渲染在这里。如果当前页面没有js则不渲染。

位置预置好了,我们就可以写具体的段落了。接上个例子,只想在请求/hello页面中打印hello world,就可以在hello.hbs中任意位置加入下面段落(最好是在页面最底下,方便维护)。

{{#section 'js'}}
    <script>
        alert('hello world')
    </script>
{{/section}}

这样当我们请求/hello时,就会打印hello world,请求其他页面则不会有这段js代码。

养成良好的代码组织能力,有助于提高我们的编码质量!

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

  • hbs是Express提供的默认视图引擎, 是对Handlerbars的封装. 具体用法参考下面的项目地址, 这里...
    烈风裘阅读 14,804评论 0 3
  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 176,401评论 25 709
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 136,159评论 19 139
  • 本文介绍seajs和hanlebars,并实现前端控件组件化. 我想实现的是把组件单独一个文件夹,js和css,h...
    木易林1阅读 5,264评论 0 1
  • 早饭后,步行去银行办事,现在外出只要距离不是很远我就选择步行,一方面可以健身,一方面能够欣赏路边风景。今天的太阳有...
    荷塘恋雨阅读 2,642评论 0 2

友情链接更多精彩内容