跟着官档学 Vue.js (一) - 新手上路

在最近的web世界里,如果还想继续生存下去,不得不去接触一些新的概念. Vue.js 已经出来有几个年头了,最近热度却一直在上升。

哎呀,看过了好几遍文档了,可是日常中的使用又不是辣魔频繁,所以干脆瓦们跟着官方文档来把 Vue.js 学一遍吧。

对了,本文是针对 Vue 2.0 展开的~

好喜欢它官网清新简洁的风格,忍不住就想把它学下来

学习之路

不知道为什么,去网上搜索的学习资料,很多数都是从 vue-cli 开始教学的,很多教程虽说是教程,但却不那么容易看懂。作为一名平日高度使用 jquery ,没有接触过这种新型框架的人,上手往往是很困难的,既然是这样,我们的学习之路不如就抛开所有的打包工具,抛开所有的手脚架工具,单纯地从引入 vue.js 这个文件来学习,循序渐进地学怎么样呢?

你说不行也没用,我就打算这么做。

所以,我们就跟着官方文档,一章一章地看下去,发现问题,解决问题,学下去吧!

Vue.js 是什么

当我们要学一个新东西的时候,往往会去想,这个东西是什么,能干什么,学了之后有什么好处之类的。没错,这个东西困扰了我很久,强迫症患者往往要思考,如何正确地去使用这个新东西。但是呢,官档的第一句话已经很好地说明清楚了。

Vue.js(读音 /vjuː/,类似于 view) 是一套构建用户界面的渐进式框架

什么是 渐进式框架 , 我在这里得到了一些答案。总而言之,渐进式框架就是,你要拿 Vue.js 在项目里占多大的比重都可以。比如说,你只是想让他来完成一些界面操作,用来取代 jquery 的部分功能,这是最简单的,如果你能力可以,完全可以利用 Vue.js 来构建整个项目(包括前后端)。

所以,根本就没有最正确的使用方法,只有最恰当的使用方法。

到这里,不得不在学习之路上补一个点,如果想要从习惯使用的 jquery 转到 Vue.js 的开发上来,完全可以两个工具放在一起,
慢慢把某一个项目里的 jquery 代码或者说页面重构成用 Vue.js 开发的。(渣油,其实也不会很难)

准备上手

好了,从现在开始我们跟着 官网的 介绍页 里面的 demo 来写一写。

打开我们最喜欢用的文本编辑器~然后写一个空的 html 文档,然后引入 vue.js 文件。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>learn Vue</title>
    <script src="vue.js"></script>
</head>
<body>

</body>
</html>

(我这里是把 vue.js 事先下载下来了。)

声明式渲染

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>learn Vue</title>
    <script src="vue.js"></script>
</head>
<body>
    <div id="app">
        {{ message }}
    </div>
    <script>
        var app = new Vue({
            el: '#app',
            data: {
                message: 'Hello Vue!'
            }
        })
    </script>
</body>
</html>

我们跟着官方文档的例子,这是第一个例子,叫做 声明式渲染,我们会发现,在代码中出现了一个以前没有看过的语法。{{}},它是由两组花括号括起来的,中间放了一个这里暂且叫做变量的 message ,看样子应该是和下面 script 中的 message 是同一个东西。
我们从浏览器打开这个页面,就会发现,在浏览器中输出了 Hello Vue!

对了,必须把 <script> 标签放在特殊语法的后面,要不然你将看到浏览器输出 {{ message }} ,这是因为 #app 还没生成完毕就已经执行了vue代码。

这个例子中,我们 声明 了一个 app 变量,其中存放了一个 Vue实例。什么是 Vue实例 暂时不关紧要,重要的是我们声明了一个 app 变量,意味着我们可以在浏览器中的 JavaScript控制台 更改这个变量的内容。

(我把 app.message 改成了其他的文字内容)

也就是,<script> 标签中的 data 里面的变量都被绑定到 声明变量app 本身了。更改相应的变量会导致dom中相应元素的变化,官方称之为 响应式

同样的,我们刚才是绑定了一个 message 变量到了某个元素的 文本节点 上,即标签内容,我们还可以把这个变量绑定到 属性节点 上:

<div id="app-2">
  <span v-bind:title="message">
    鼠标悬停几秒钟查看此处动态绑定的提示信息!
  </span>
</div>
<script>
    var app2 = new Vue({
        el: '#app-2',
        data: {
            message: '页面加载于 ' + new Date()
        }
    });
</script>

title 属性是用来显示一个元素的提示的,当鼠标悬停在上面的时候就会显示 title 中的内容。在 vue 的语法中,它让我们在 title 前面加上 v-bind,然后用 半角冒号: 连接起来,在引号中放入 message 这个变量,就能完成绑定。

需要注意的是,绑定变量给属性节点的时候,不需要使用花括号括起来,例如:

<span v-bind:title="{{message}}"></span>
<span title="{{message}}"></span>

以上都是错误的语法。

实践中还发现:如果一个声明式的 Vue变量 中出现了渲染错误,那么与其相关的整个元素,即是el中指定的那个元素,不会被渲染出来。但是在此之外的所有元素都会照常显示。

条件与循环

Vue.js 提供了很多方便的东西,最简单的体现在了这里,条件与循环。想想我们平时如何用 jquery 显示隐藏一个元素:

<div id="app-3">
    <p>现在你看到我了</p>
</div>
<button id="btn">显示隐藏</button>
<script>
    $(function(){
        var p = $("#app-3").children("p");
        $("#btn").click(function(){
            if(p.css("display") != "none"){
                p.css("display","none");
            }else{
                p.css("display","block");
            }
        });

    });
</script>

在上面的例子中通过点击按钮就可以显示和隐藏那个p元素。一旦当我们的项目扩大的时候,要定位到那个p元素或者是要更改p元素的css的时候就是一个头疼的问题。当我们换成用 Vue.js 来做的时候,代码就像这样:

<div id="app-3">
    <p v-if="seen">现在你看到我了</p>
</div>
<button id="btn">显示隐藏</button>
<script>
    var app3 = new Vue({
        el: '#app-3',
        data: {
            seen: true
        }
    });

    $(function(){
        $("#btn").click(function(){
            app3.seen = ! app3.seen;
        });
    });
</script>

Vue 提供了一个 v-if 命令,和前面的参数绑定差不多,也是绑定了一个 Vue 实例中 data 中的变量。通过改变上面代码中的 seen 值,就可以决定是否显示那个所谓的 <p> 元素。

值得一提的是,我们jquery的做法是通过改变p元素的css来让它显示与否的,但是vue的做法是,至少 v-if 的做法是,true 的时候把这个元素渲染在dom里,false 的时候不渲染这个元素在dom里,打开浏览器的开发者工具就知道啦~

接下来就是 v-for 命令,我觉得官方的例子老是用一些长得差不多的变量名,一开始很难看懂,所以我稍微改了一下这个例子。

<div id="app-4">
    <ul>
        <li v-for="num in numbers">{{num}}</li>
    </ul>
</div>
<script>
    var app4 = new Vue({
        el: '#app-4',
        data: {
            numbers: [12,32,1,445,6,657,73,5,43],
            num: 1 //<-专门用来混淆你的
        }
    });
</script>

上面的例子中,我们在 data 中定义了一个 numbers 数组,然后利用 v-for 命令把数组中的每一个数字都取出来放在了num 里面,这样有几个数字, <li> 标签会被相应地渲染多少个出来。效果如下截图:

我们可以注意到,花括号语法中的 num 指的是 num in numbers 中的 num,在 data 中定义的 num 变量,并不会被这个 v-for 语法读取到。

oh,我还发现 num in numbers 还可以写成 num of numbers,更接近 es6 语法。

处理用户输入

web开发肯定离不开表单,表单也难以离开用户输入。vue 官方文档提供的例子是这样的

<div id="app-5">
    <p>{{ message }}</p>
    <button v-on:click="reverseMessage">逆转消息</button>
</div>
<script>
    var app5 = new Vue({
        el: '#app-5',
        data: {
            message: 'Hello Vue.js!'
        },
        methods: {
            reverseMessage: function () {
                this.message = this.message.split('').reverse().join('');
            }
        }
    });
</script>

其实第一次看文档的时候看到这里是挺懵逼的。所以我们现在捋一捋。

在这里我们接触到了一个新的指令 v-on,它是用来绑定事件的,在 html 中,我们如果直接在标签上绑定点击事件是这么写的:

<div onclick="someMethod"></div>

然后会在 js 中定义一个 someMethod() 方法,而在 Vue 中,我们需要使用 v-on:click="someMethod" 来绑定点击事件,和前面的 v-bind 很相似。然而,这里的 someMethod() 并不是直接随便写在 js 中。而是要写在 Vue 实例的methods 对象里面

注意:methods,methods,methods,默念三遍,注意s的发音。data,data,data,注意没有s的发音!

这不是折腾嘛,为什么不能直接把方法写在data里面?这就和上面的例子有关了,仔细看 reverseMessage() 方法,其中有一个东西值得注意 this.message ,用左半边眼睛想一下就知道它是要调用 data 中的 message,如果把 reverseMessage() 写在了 data 中,调用将会出错,反正会出现很多奇奇怪怪的问题,所以我们一定要 按照Vue套路行事数据放data,方法放methods

接下来,最具魅力的指令是 v-model,它能够完成的事情实在是太神奇了,官方的例子如下:

<div id="app-6">
    <p>{{ message }}</p>
    <input v-model="message">
</div>
<script>
    var app6 = new Vue({
        el: '#app-6',
        data: {
            message: 'Hello Vue!'
        }
    });
</script>


也就是在输入框输入了什么东西,上面的p元素就会相应地更新成什么内容。

正因为有这一个指令的存在,我们在开发的过程中,完全不用关心某一些dom操作,我们只需关心他们是怎么联系在一起的。

例子中存在着三个 message ,v-modal 绑定的那个 message 代表着,一旦输入框发生了变化,就会把输入框的内容更新给 Vue实例 中 data 中的 message,然后将响应式地渲染到 <p> 标签里面的那个 message。

v-modal 的具体细节在之后的章节里面会有更加详细的说明。

如果我们想要输入之后,边输入,边输出一个逆转的字符串,就像再上面那个例子一样,使用 v-model 指令,有办法吗?当然有办法,不过现在还不是我们新手入门应该做的事情。


好啦,官档中还有一部分是关于组件化的,我们可以放在一起再学习,所以这里就是文章末尾啦。

通过第一节课,我们基本上了解了一些最基础的 Vue 语法:

  1. 给元素绑定文本节点需要使用 {{ foo }} 两个花括号

  2. 给元素绑定属性节点需要使用 指令:属性="foo" 的形式

  3. 几个最最基本的指令 v-bind,v-on,v-if,v-for,v-modal

  vue.js