Vue2(一):Vue介绍、模板语法、数据绑定、el和data的两种写法、MVVM、数据代理、事件

一、Vue介绍

Vue是一套用于构建用户界面的渐进式JavaScript框架。

1.Vue特点

(1)采用组件化模式,提高代码复用率、且让代码更好维护。

.vue里面封装了html、css、js,可以把那个模块直接拿来用

(2)声明式编码,让编码人员无需直接操作DOM,提高开发效率

(3)使用虚拟DOM和优秀的Diff算法

数据转换成真实DOM之间先转化为虚拟DOM,当数据变化,通过Diff算法比较一下虚拟DOM的变化,把新的数据做处理,不变的数据不变.

2.vue中的el和data

el首先根据vue实例拿到容器进行解析,看有没有vue语法,把该填的数据填进去才在页面上显示出来。

<div id="root">
        <!-- 建立容器 -->
        <h3>您好!{{name}}</h3>
    </div>
    <script type="text/javascript">
    //const x=
     new Vue({
        el:'#root',//el将Vue实例与前面的容器建立联系,值通常为css选择器字符串
        data:{//我想要把动态的数据放在Vue中,但是数据可能不光姓名,所以不能直接data:‘ttt’
            name:'ttt'
        }
    })
//把容器里变化的容器交给vue实例去做
    </script>

el将Vue实例与前面的容器建立联系,值通常为css选择器字符串

data里面存放动态变化的数据,数据供el所指定的容器去使用(也就是为啥直接写name就行),不写死的数据放在vue中,要在html中引用的话用{{ }}跟其他的分割开,而且不用写data.name,直接写name。

const x也不需要。

注意:(1)vue实例和容器是一对一的,不能多个vue实例的名字对应一个容器,也不能多个容器被一个vue实例接管,等以后遇到很多数据的情况,vue会分给手下(组件)

(2){{xxx}}里面必须是js里面的表达式,xxx可以读取到data中的所有属性

(3)真实开发中只有一个vue实例,配合组件使用

二、模板语法

1.插值语法

就像上面代码那样的{{ }},注意事项如上

2.指令语法

用于解析标签(标签属性、标签体内容、绑定事件、、、)

<div id="root">
       <a v-bind:href="url">dianwo</a>
    </div>
    <script type="text/javascript">
    const x=new Vue({
        el:'#root',
        data:{
            name:'ttt',
            url:'http://www.baidu.com'
        }
    })

我想把动态的网址添加进去,不能{{url}},也不能直接“url”,正确方法是在href前面加v-bind:(绑定),表示为vue当中的指令v-???,引号里的东西就当js表达式处理

v-bind:能简写为:

什么时候用差值和指令?

差值语法:用于指定标签体内容,起始标签和结束标签中间夹着的内容<>标签体</>

指令语法:管理标签属性

 <div id="root">
        
       <a v-bind:href="school.url">dianwo</a>
    </div>
    <script type="text/javascript">
    const x=new Vue({
        el:'#root',
        data:{
            name:'ttt',
            school:{
                url:'http://www.baidu.com'
            }
            
        }
    })

也可以这样嵌套调用,这个时候就不能直接写url了,因为data里面只有name和school,要想调用school中的得school.url。

三、数据绑定

1.单向数据绑定v-bind

数据只能从data流向页面

 <div id="root">
       单向数据绑定:<input type="text" v-bind:value="name">
       
    </div>
    <script type="text/javascript">
    new Vue({
        el:'#root',
        data:{
           name:'尚硅谷'
        }
    })

用v-bind进行数据绑定,改变代码中的name值,表单内的内容会改变,但是改变表单中的(添加123),name值不变。

2.双向数据绑定v-model

页面和data双向流

<div id="root">
       单向数据绑定:<input type="text" v-bind:value="name">
       双向数据绑定:<input type="text" v-model:value="name">
    </div>
    <script type="text/javascript">
    new Vue({
        el:'#root',
        data:{
           name:'尚硅谷'
        }
    })
    

这个是双向的,改变表单值name也同时变化

注意:1.v-model只能用在表单类元素(输入类元素:input、单向框、多选框、select框、多行输入等等都有value值的)上,因为要是连输入都输入不了如何去影响name值呢?所以根本不给它加这种功能。

2.v-model:value可以简写为v-model。

四、el和data的两种写法

1.el的另一种灵活写法:.$mount(‘#root’)

<div id="root">
       你好!{{name}}
    </div>
    <script type="text/javascript">
    const x=new Vue({
       // el:'#root',
        data:{
           name:'尚硅谷'
        }
    })
    console.log(x);
    setTimeout(()=>{
        x.$mount('#root')
    },4000);

比用el麻烦一点但是更灵活,可以在后面设置箭头函数等四秒钟再去显示。

mount:挂载

2.data的函数式写法

前面那种写法叫做对象式写法

<div id="root">
       你好!{{name}}
    </div>
    <script type="text/javascript">
    const x=new Vue({
        el:'#root',
        data:function(){
            return {
                name:'ttt'
            }
        }
    })

将data写成一个函数,最后必须得有返回,函数式更麻烦但是等学组件之后必须得用函数式。

如果在return返回之前打印一下this观察调用data的对象,结果是vue实例对象(当是普通函数function的时候,如果是箭头函数翻两层到window),所以data函数必须写成function函数,可以简写为data(){ }

五、理解MVVM

M:模型(Model):对应data中的数据
V:视图(View):模板(页面)
VM:视图模型(View Model):Vue实例对象

下面那条线的意思是通过vue把数据进行绑定显示在页面上

上面的线:比如说双向数据绑定,页面的数据改变name就变了,所以我得时时刻刻监听这个数据框,然后存在数据里(对dom的一种监听)

<div id="root">
       <h1>学校名称:{{name}}</h1>
       <h1>学校地址:{{address}}</h1>
    </div>
    <script type="text/javascript">
    new Vue({
        el:'#root',
        data:{
            name:'hb',
            address:'北京'
        }
        
    })

div盒子属于view;  new Vue属于ViewModel;  name和address属于Model。

所以以后再用变量去接收实例的时候就用vm,我们在data写的所有属性都给到了vm身上,而且vm身上的属性和方法我们都可以在模版上调用。

六、数据代理

1.Object.defineProperty

let person={
        name:'章三',
        sex:'男',
        //age:18
    }
    Object.defineProperty(person,'age',{
        value:18
    })
   console.log(person);

Object.defineProperty()用法:第一个参数写对象,第二个是属性名,然后是配置项,可以写很多的配置,这里只写了value。

后面的object等等代码跟我直接加age:18表面上看没什么区别

实际上用Object.defineProperty方法的age的颜色会更淡一点,它不能枚举(也就是age属性不参与遍历)、age是不能修改值的、也不能用delete.age进行删除。

(1)如果就用这种方法的话怎么遍历呢?在value下面加enumberable:true;控制属性是否可以枚举,默认值false。

(2)如果就用这种方法的话怎么修改age值呢?在enumberable下面加writable:true;控制属性是否可以被修改,默认值false。

(3)如果就用这种方法的话怎么删除age呢?在writable下面加configurable:true;控制属性是否可以被删除,默认值false。

如果没有value的话,我想要age=18,但是又不想直接写进person里去,(let number=18然后age=number行不行?)不行!

因为以后再去修改number的话,age还是18不会改变的,除非再赋值一遍person.age=number

怎么让我改了number,age就跟着改呢?

Object.defineProperty(person,'age',{
        // value:18,
        // enumberable:true,
        // writable:true,
        // configurable:true
       // get:function
           get(){//简写
            return number
        }
    })

添加get函数,当有人读取person的age属性时,get函数(getter)就会被调用,返回值是age的值

当有人修改person的age属性时,set函数(setter)就会被调用,且会收到修改的具体值

Object.defineProperty(person,'age',{
        // value:18,
        // enumberable:true,
        // writable:true,
        // configurable:true
        get:function(){
            console.log('有人查看age属性了')
            return number
        },
        set(value){
            console.log('有人修改age属性了',value)
            number=value;
        }
    })

2.什么是数据代理?

通过一个对象代理另一个对象中属性的操作(读/写)

通过obj2来管理obj1里面的x(读/写)

let obj1={x:100};
    let obj2={y:200}
    Object.defineProperty(obj2,'x',{
        //可以有人通过obj2来访问x属性
        get(){
            return obj1.x//obj2没有x,交给他的是obj1的x
        },
        set(value){
            obj1.x=value;

        }
    })

3.Vue中的数据代理

(1)通过vm对象来代理data对象中属性的操作

data:{
            name:'hb',
            address:'bj'
        }

这一小段中的name和address其实都有get和set方法,也就是数据代理

(2)Vue中数据代理的好处:

更加方便的操作data中的数据

(3)基本原理:

通过Object.defineProperty()把data对象中所有属性添加到vm上。
为每一个添加到vm上的属性,都指定一个getter/setter。
在getter/setter内部去操作(读/写)data中对应的数据。

七、事件相关内容

1.事件处理

1、使用v-on:xxx或@xxx绑定事件,其中xxx是事件名。
2、事件的回调需要配置在methods对象中,最终会在vm上。
3、methods中配置的函数,不要用箭头函数!否则this就不是vm了。
4、methods中配置的函数,都是被Vue所管理的函数,this的指向是vm 或 组件实例对象。
5、@click="demo" 和 @click="demo($event)" 效果一致,但后者可以传参。
6、如果不传参,默认第一个形参是事件对象;如果传参,按照参数顺序来接,如果想接事件对象,要传入$event关键字

<div id="root">
        <h2>欢迎来到{{name}}学习</h2>
        <button @click="showInfo1">点我提示信息1</button>
        <button @click="showInfo2(66,$event)">点我提示信息2</button>
        <!-- v-on:click当点击的时候 ,省略写法@click-->
    </div>
    <script type="text/javascript">
    
    const vm=new Vue({
        el:'#root',
        data:{
            name:'hb',
            address:'bj'
        },
        methods:{
            showInfo1(a,b,c,d){
        //模版只能用vue实例里的东西,所以写在外面不起作用
               alert('hi');
               console.log(a,b,c,d)
               //PointerEvent{}  undefined undefined undefined
          },
          showInfo2(number,event){
               alert('hi');
               console.log(number)//66
               console.log(event)
          }
        }
    })

(1)绑定事件可以直接在行内 v-on:,v-on:click当点击的时候,简写@click

(2)事件不能写在vue实例外面,因为上面的盒子模版用的都是vue中的,用methods配置项

(3)传参的时候自动传入event事件,如果想传数的话可以加(66),再想传event的话加$

2.事件修饰符

1、prevent:阻止默认事件(常用)
2、stop:阻止事件冒泡(常用)
3、once:事件只触发一次(常用)
4、capture:使用事件的捕获模式
5、self:只有event.target是当前操作的元素时才触发事件
6、passive:事件的默认行为立即执行,无需等待事件的回调执行完毕(移动端用的多一点)

<body>
    <div id="root">
        <h2>欢迎来到{{name}}学习</h2>
        <a href="http://www.baidu.com" @click.prevent="showInfo">点我提示信息</a>
        <div @click="showInfo">
            <button @click.stop="showInfo">点我提示</button>
            <!-- hi了两次,冒泡的 .stop阻止冒泡-->
        </div>
        <button @click.once="showInfo">点我提示</button>
        <!-- 事件只发生一次 -->
        <div class="box1" @click.capture="showMsg(1)">box1
            <!-- 不加之前是2 1,我想点box2之后输出1 2,让box1捕获 -->
            <div class="box2" @click="showMsg(2)">box2</div>
        </div>
        <div @click.self="showInfo">
            <button @click="showInfo">点我提示</button>
            <!--点完之后又弹两次button,冒泡了,self是当前操作的元素时才能触发事件 -->
        </div>
        <ul @wheel.passive="demo">
            <!-- scrool是滚动条动一下就输出 -->
            <!-- wheel是鼠标上的滚轮没滚动一下就输出 -->
            <li>1</li>
            <li>2</li>
            <li>3</li>
            <li>4</li>
        </ul>
    </div>
    <script type="text/javascript">
    
    const vm=new Vue({
        el:'#root',
        data:{
            name:'hb',
            address:'bj'
        },
        methods:{
            showInfo(e){
                //e.preventDefault()这样写可以阻止弹窗之后跳转
                //e.stopPropagation()阻止冒泡
               //alert('hi');
               console.log(e.target)
              
        },
        showMsg(e){
            console.log(e);
        },
        demo(){
            for(let i=0;i<10000;i++)
            {
                console.log('@');
            }
            console.log('累鼠了');
            //我们可以发现当使用wheel的时候刚动了一下滚轮滚动条是没有动的,
            //因为它先要执行你添加的事件然后再去做它的默认事件
            //加上passive就能解决了(事件的默认行为会立即执行
        }
    }
    })
    

    </script>
</body>

3.键盘事件

用keyup用的比较多,keyup.enter

<div id="root">
        <h2>欢迎来到{{name}}学习</h2>
        <input type="text" placeholder="按下回车提示输入" @keyup.enter="showInfo">
        <!-- 按下回车才显示输入了啥,不是输入一个显示一个 -->
    </div>
const vm=new Vue({
        el:'#root',
        data:{
            name:'hb',
            address:'bj'
        },
        methods:{
            showInfo(e){
                console.log(e.target.value)
           }
        }
    })

如果你想用的按钮这上面没有咋办?

Vue未提供别名的按键,可以使用按键原始的key值去绑定,但注意要转为kebab-case(短横线命名)

 <input type="text" placeholder="按下回车提示输入" @keyup.caps-lock="showInfo">

注意:1.keyCode是按键的编码,key是按键的名字

2.系统修饰键(用法特殊):ctrl、alt、shift、meta(win键)

  • 配合keyup使用:按下修饰键的同时,再按下其他键,随后释放其他键,事件才被触发。
  • 配合keydown使用:正常触发事件。

在用keyup.tab的时候,按下它会从输入框移走,默认在抬起来之前就失去对元素获取焦点了

所以得用keydown

3、也可以使用keyCode去指定具体的按键(不推荐)keyup.13(enter)

4、Vue.config.keyCodes.自定义键名 = 键码,可以去定制按键别名(不推荐)

Vue.config.keyCodes.huiche = 13; //定义一个别名为huiche的enter按键

4.补充两个细节

1、修饰符可以连续写

<button @click.stop.prevent="showInfo">你好</button>

既能阻止冒泡也能阻止跳转,前后顺序是不一样的

2、如果先让两个键同时按下才触发,键名也可以连续绑定

比如按下ctrl+y触发showInfo方法

<input type="text" @keyup.ctrl.y="showInfo">
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值