vue相关语法知识点

一、文本传值


<template>
  <div id="app">
    {{title}}
  </div
</template>

<script>
export default {
  name: 'App',
  data(){
    return{
      title:"第一个vue项目",
    }
  }
}
</script>

<style>
#app {
  color: red;
  margin-top: 60px;
} 
</style>

首先通过这个例子来介绍vue的一些基础语法和基础结构,一个vue项目主要由html结构,处理逻辑和样式组成,对应的就是这里的template,script,style,从这个例子就是可以看出一个最基础的vue项目的模板,为了规范,一般来说,根容器div 的id和下面的name会和该vue项目取一样的名字,script中的data用于数据的存储,一般这里就是在data中申明属性,也可以给出属性的初始值,在实例代码中,定义了一个title的属性并给它的初始值为“第一个vue项目”,现在属性已经申明并且给出了初始值,想要让这句话展示在我们的页面上,就需要让html拿到我们的属性的值,这就需要完成数据绑定,在vue中是通过使用{{}}来完成数据绑定,同时在下面的style中完成对样式的设置。

二、属性(v-bind)


<template>
  <div id="app">
    <span v-bind:title="message">
      <a :href="url">
    鼠标悬停查看此处动态绑定的提示信息!
    </a>
  </span>
  </div>
</template>

<script>
export default {
  name: 'App',
  data(){
    return{
     message: '页面加载于 ' + new Date().toLocaleString(),
     url:"https://www.baidu.com/",
    }
  }
}
</script>

<style>
#app {
  margin-top: 60px;
} 
</style>

在这个例子中首先申明了两个属性message 和url ,message 显示的是一条页面加载的时间,url定义了一个网址,在html结构中,使用了属性绑定v-bind指令,通过v-bind:title把message 属性绑定到了这个span标签上,在vue中属性的绑定可以把v-bind省略,就像这里把url属性绑定到a标签上,通过鼠标悬浮可以看到页面加载时间,这个就是message属性,点击跳转页面,这里页面的网址就是url。

三、条件判断(v-if)


<template>
  <div v-if="seen">
    你看到我啦
  </span>
  </div>
</template>

<script>
export default {
  name: 'App',
  data(){
    return{
     seen:false
    }
  }
}
</script>

<style>
#app {
  margin-top: 60px;
} 
</style>

在这一个例子中介绍v-if条件判断指令,同样定义seen属性为false,在html结构中在根容器div上使用了vif条件判断指令对seen属性进行判断,若为真则在页面上会显示文字,若为假则不显示。通过对seen的值的判断,可以决定是都显示文本内容。

四、循环(v-for)


<template>
  <div>
    <ul>
      <li v-for="character in characters">{{character}}</li>
    </ul>
    <ul>
      <li v-for="(ninja, index) in ninjas">{{ index }} . {{ ninja.name }} - {{ ninja.age }}</li>
    </ul>
    <ul>
      <li v-for="(value, key) in object">{{ key }} : {{ value }}</li>
    </ul>
  </div>
</template>

<script>
export default {
  name: 'App',
  data(){
    return{
     characters: ['Mario', 'Luigi', 'Yoshi', 'Bowser'],
     ninjas: [
        { name: 'Ryu', age: 25 },
        { name: 'Yoshi', age: 35 },
        { name: 'Ken', age: 55 }
      ],
    object: {
      name: 'app',
      url: 'http://www.baidu.com',
      slogan: '开心最重要!'
    }   
    }
  }
}
</script>

<style>
#app {
  margin-top: 60px;
} 
</style>

这个例子主要介绍的是v-for循环指令,定义了一个characters 数组,ninjas对象数组和object对象,现在要做的就是去遍历数组拿到里面的内容,可以直接通过数组下标的形式拿到内容,但是这样在实际项目中是不切实际的,就可以通过ul标签中的li标签使用循环指令vfor去遍历出characters 数组中的所有内容,同样通过{{}}来数据绑定。

同样,也可以提供两个参数,当前ninjas 是数组,ninja 拿到的就是一个对象,就可以用对象.属性的形式拿到里面具体的内容。

五、绑定事件(v-on)


<template>
  <div>
    <button v-on:click="num++">+1</button>
    <button @click="num--">-1</button>
    <button v-on:click="addtwo()">+2</button>
    <button v-on:click="subtract(5)">-5</button>
    <p>num is {{num}}</p>
  </div>
</template>

<script>
export default {
  name: 'App',
  data(){
    return{
     num:10,
    }
  },
  methods:{
    addtwo:function(){
      this.num=this.num+2;
    },
    subtract:function(dec){
      this.num=this.num-dec;
    }
  },
}
</script>

<style>
#app {
  margin-top: 60px;
} 
</style>

这个例子介绍的是事件,通过这个例子介绍通过事件去改变属性,v-on就是用来绑定事件的 ,click事件,doubleclick事件,鼠标事件,键盘事件,在data中申明了num,初始值为10,在这里通过v-on绑定了点击事件,点击之后num加1,同样v-on可以简写为一个@,这里实现了num减1,但是在实际中我们不会就在这里对属性做一些操作,我们会把这一块的业务逻辑在我们script中去实现,我们把这些对属性的操作写在指定的方法里面,这里加2就是写在addtwo 这个方法中,在vue中所有的方法就写在methods里面,这是固定写法,addtwo:function() ,接下来就要操作当前属性,要拿到属性就只要this.num就可以了,这样就实现了加2的这个方法并且绑定事件到按钮上了,需要说明一点,这里加不加括号都是可以的,但是在使用{{}}去使用方法的时候就一定要加括号,不然它会识别为属性,在事件中如果有传参的话也是一定要有括号的,就比如这里通过参数的形式去是减5这个方法,就用dec来接收参数。

六、双向数据绑定(v-model)


<template>
  <div>
    <label>姓名:</label>
    <input type="text" v-model="name">
    <span>{{name}}</span>
  </div>
</template>

<script>
export default {
  name: 'App',
  data(){
    return{
      name:""
    }
  }
}
</script>

<style>
label{
    display: block;
    margin: 20px 0 10px
}
</style>

双向数据绑定一定是和input,select,textarea相关的,因为这第三个标签可以去输入,输入后就可以输出,在vue中是通过v-model 实现数据的双向绑定的,在这里我们把name这个属相绑定在input输入框上,同时我们在span标签中把name显示出来,可以观察到随着输入框中的变化,span标签中的文本也会跟着变化。

七、组件嵌套


实现组建的嵌套4个vue文件来实现。其中app.vue为父组件,header.vue组件、content.vue组件和footer.vue组件为子组件。

app.vue的代码如下:

<template>
    <div>
        <div class="text" v-bind:title="title">{{title}}</div>
        <app-header></app-header>
        <app-content></app-content>
        <app-footer></app-footer>  
        <app-header></app-header> 
    </div>
</template>

<script>
// Imports
import Header from './components/Header.vue';
import Content from './components/Content.vue';
import Footer from './components/Footer.vue';
export default {
    components: {
        'app-header': Header,
        'app-content': Content,
        'app-footer': Footer,
    },
    data () {
        return {
            
            title:"hello"
        }
    },
    methods:{
       
    }
}
</script>

<style scoped>
body{
    margin: 0;
    font-family: 'Nunito SemiBold';
}
.text{
    font-size: 200px;
    color:pink;
}
</style>

header.vue的代码如下:

<template>
    <header @click="changetitle">
        <h1>{{ title }}</h1>
    </header>
</template>

<script>
export default {
    data(){
        return{
            title: '这是header'
        }
    },
    methods:{
        changetitle:function(){
             this.title="已经改变title啦!!"
            // this.$emit("tc","子向父传值成功啦");
        }
    },
}
</script>

<style scoped>
header{
    background: lightgreen;
    padding: 10px;
}
h1{
    color: #222;
    text-align: center;
}
</style>

content.vue的代码如下:

<template>
    <div id="content">
        <ul>
            <li v-for="arr in arrs" v-on:click="arr.show = !arr.show">
                <h2>{{ arr.name }}</h2>
                <h3 v-show="arr.show">{{ arr.age }}</h3>
            </li>
        </ul>
    </div>
</template>

<script>
export default {
    data(){
        return{
            arrs: [
                {name: 'AA', age: 10, show: false},
                {name: 'BB', age: 20, show: false},
                {name: 'CC', age: 30, show: false}
            ],
        }
    },
}
</script>

<style scoped>
#content{
    width: 100%;
    max-width: 1200px;
    margin: 40px auto;
    padding: 0 20px;
    box-sizing: border-box;
}
ul{
    display: flex;
    flex-wrap: wrap;
    list-style-type: none;
    padding: 0;
}
li{
    flex-grow: 1;
    flex-basis: 300px;
    text-align: center;
    padding: 30px;
    border: 1px solid #222;
    margin: 10px;
}
</style>

footer.vue的代码如下:

<template>
    <footer>
        <p>{{ copyright }}</p>
    </footer>
</template>

<script>
export default {
    data(){
        return{
            copyright: '这是footer'
        }
    }
}
</script>

<style scoped>
footer{
    background: #222;
    padding: 6px;
}
p{
        color: lightgreen;
        text-align: center;
}
</style>

效果图如下:


首先,header.vue组件中实现的是显示title属性,并且还绑定了一个点击事件,当点击是可以实现tltle的改变。content.vue组件中实现的是通过v-for循环遍历出arrs数组中的对象并且显示对象中的属性,同时绑定了点击事件来改变show属性的值,根据show的值可以改变arr.age的可见性。footer.vue组件中实现的是显示copyright。

本来这三个组件都是相对独立的组件,想要在一个页面中同时显示这三个组件就需要通过组件嵌套来实现,如实例代码,将header、content、footer三个组件作为子组件全部显示在父组件app中。想要在父组件app中使用其他的组件,只需要import+注册即可。

八、组件传值--父组件向子组件


在组件嵌套的实例代码中,子组件content中的数组是直接定义在它自己的data中,但是在实际项目中,假如有很多组件都要用到arrs数组,开发者是不可能在每一个子组件中去定义一遍arrs数组的。最好的解决办法就是将arrs数组抽离出来,定义在父组件中,然后再传递给需要的子组件去调用。

如果将arrs数组写在父组件app中,那么,如何才能将arrs数组传递到子组件中呢?这就需要找到父组件app和子组件content的契合点,就是在父组件app的template中的<app-content></app-content>,在这个契合点将arrs数组绑定上去,再去子组件content中去拿就可以了。

而对于子组件content,只需要用props属性中去接收数据即可。这样通过父组件向子组件传值的效果和组件嵌套中的实例代码中效果是一致的。

app.vue的代码如下:

<template>
    <div>
        <div class="text" v-bind:title="title">{{title}}</div>
        <app-header></app-header>
        <app-content v-bind:arrs="arrs"></app-content>
        <app-footer></app-footer>  
        <app-header></app-header> 
    </div>
</template>

<script>
// Imports
import Header from './components/Header.vue';
import Content from './components/Content.vue';
import Footer from './components/Footer.vue';
export default {
    components: {
        'app-header': Header,
        'app-content': Content,
        'app-footer': Footer,
    },
    data () {
        return {
            arrs: [
                {name: 'AA', age: 10, show: false},
                {name: 'BB', age: 20, show: false},
                {name: 'CC', age: 30, show: false}
            ],
            title:"hello"
        }
    },
    methods:{
        
    }
}
</script>

<style scoped>
body{
    margin: 0;
    font-family: 'Nunito SemiBold';
}
.text{
    font-size: 200px;
    color:pink;
}
</style>

content.vue的代码如下:

<template>
    <div id="content">
        <ul>
            <li v-for="arr in arrs" v-on:click="arr.show = !arr.show">
                <h2>{{ arr.name }}</h2>
                <h3 v-show="arr.show">{{ arr.age }}</h3>
            </li>
        </ul>
    </div>
</template>

<script>
export default {
    data(){
        return{
            
        }
    },
     props:["arrs"]
}
</script>

<style scoped>
#content{
    width: 100%;
    max-width: 1200px;
    margin: 40px auto;
    padding: 0 20px;
    box-sizing: border-box;
}
ul{
    display: flex;
    flex-wrap: wrap;
    list-style-type: none;
    padding: 0;
}
li{
    flex-grow: 1;
    flex-basis: 300px;
    text-align: center;
    padding: 30px;
    border: 1px solid #222;
    margin: 10px;
}
</style>

九、组件传值--子组件向父组件


在实际的项目开发,也经常会有子组件向父组件传值的情况。还是以组件嵌套中的代码为例,子组件header中有title这个属性,现想要通过子组件header的点击事件来改变父组件app中的title,就需要用到子组件向父组件传值。

首先需要在子组件header的changetitle方法中去注册一个事件,注册事件用到的就是this.emit(),注册事件时,第一个参数表示你要注册的时间的名字,第二个参数表示你要传递的内容。比如注册一个叫tc的事件,传递的内容就是“子组件向父组件传值成功”。

接下来就需要在父组件app中去绑定tc,绑定的时间名字应该和注册时取的名字一样。在父组件app和子组件header的契合点<app-header></app-header>处绑定tc事件,执行的是updatetitle的方法,而该方法只需要在父组件app中去定义即可。

app.vue的代码如下:

<template>
    <div>
        <div class="text" v-bind:title="title">{{title}}</div>
        <!-- <app-header></app-header> -->
        <app-header v-on:tc="updatetitle($event)"></app-header>
        <app-content v-bind:arrs="arrs"></app-content>
        <app-footer></app-footer>  
        <app-header></app-header> 
    </div>
</template>

<script>
// Imports
import Header from './components/Header.vue';
import Content from './components/Content.vue';
import Footer from './components/Footer.vue';
export default {
    components: {
        'app-header': Header,
        'app-content': Content,
        'app-footer': Footer,
    },
    data () {
        return {
            arrs: [
                {name: 'AA', age: 10, show: false},
                {name: 'BB', age: 20, show: false},
                {name: 'CC', age: 30, show: false}
            ],
            title:"hello"
        }
    },
    methods:{
        updatetitle(title){
            this.title=title;
        }
    }
}
</script>

<style scoped>
body{
    margin: 0;
    font-family: 'Nunito SemiBold';
}
.text{
    font-size: 200px;
    color:pink;
}
</style>

header.vue的代码如下:

<template>
    <header @click="changetitle">
        <h1>{{ title }}</h1>
    </header>
</template>

<script>
export default {
    data(){
        return{
            title: '这是header'
        }
    },
    methods:{
        changetitle:function(){
             this.title="已经改变title啦!!"
             this.$emit("tc","子向父传值成功啦");
        }
    },
}
</script>

<style scoped>
header{
    background: lightgreen;
    padding: 10px;
}
h1{
    color: #222;
    text-align: center;
}
</style>

效果图如下:


image.png
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,425评论 4 361
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,058评论 1 291
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,186评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,848评论 0 204
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,249评论 3 286
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,554评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,830评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,536评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,239评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,505评论 2 244
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,004评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,346评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 32,999评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,060评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,821评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,574评论 2 271
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,480评论 2 267

推荐阅读更多精彩内容

  • vue概述 在官方文档中,有一句话对Vue的定位说的很明确:Vue.js 的核心是一个允许采用简洁的模板语法来声明...
    li4065阅读 7,108评论 0 25
  • Vue.js特性:渐进式技术栈 轻量级的框架 双向数据绑定 指令 插件化 Vue实例书写模板: 访问Vue实例的属...
    猫晓封浪阅读 1,318评论 0 0
  • 主要还是自己看的,所有内容来自官方文档。 介绍 Vue.js 是什么 Vue (读音 /vjuː/,类似于 vie...
    Leonzai阅读 3,269评论 0 25
  • 1.vue.js的两个核心是什么? vue.js的两个核心分别是数据驱动(MVVM)和组件化。 一、数据驱动 数据...
    fengcol阅读 1,038评论 0 3
  • 每个 Vue 应用都是通过用 Vue 函数创建一个新的 Vue 实例开始的: 实例生命周期钩子 每个 Vue 实例...
    Timmy小石匠阅读 1,340评论 0 11