1, Vue overview
What is Vue js
Vue (pronunciation / vju) ː/, Similar to view) is a progressive framework for building user interfaces. Unlike other large frameworks, Vue is designed to be applied layer by layer from bottom to top. Vue's core library only focuses on view layers, which is not only easy to start, but also easy to integrate with third-party libraries or existing projects. On the other hand, when combined with modern tool chains and various supporting class libraries, Vue can also provide drivers for complex single page applications.
Vue.js is a progressive framework for building a data-driven web interface. Vue. The goal of JS is to realize the data binding of response and combined view components through the simplest API as possible.
MVVM mode
MVVM is short for model View ViewModel. It is essentially an improved version of MVC. MVVM abstracts the state and behavior of the View. Let's separate the View UI from the business logic.
MVVM mode is the same as MVC mode. Its main purpose is to separate View and Model
Vue.js is a Javascript library that provides MVVM style bidirectional data binding, focusing on the View layer. Its core is the VM in MVVM, that is, ViewModel. ViewModel is responsible for connecting View and Model to ensure the consistency of View and data. This lightweight architecture makes front-end development more efficient and convenient.
MVVM splitting is interpreted as:
Model:Responsible for data storage View:Responsible for page display View Model:Responsible for business logic processing (e.g Ajax Request, etc.), process the data and submit it to the view for display
The problem to be solved by MVVM is to completely separate the business logic code from the view code, so that their respective responsibilities are clearer and the later code maintenance is simpler
VM (view Model) can decouple the view view from the Model. The work of VM is Vue JS.
vue. Functions of JS
1) Declarative rendering: Vue The core of JS is a system that allows a concise template syntax to declaratively render data into DOM.
For example: use Vue The interpolation expression of JS is placed anywhere in Dom, and the value of the difference expression will be rendered in Dom.
2) Conditions and loops: Vue. Net can be used in dom The v-if, v-for and other tags provided by JS facilitate the judgment and circulation of data.
3) Bidirectional data binding: Vue provides v-model instruction, which can easily realize bidirectional binding between Dom element and data object, that is, modify the value in Dom element, automatically modify the bound data object, modify the value of data object, and automatically modify the value in Dom element.
4) Handle user input: in order to allow users to interact with your application, we can add an event listener with the v-on instruction to call the methods defined in the Vue instance
5) Component application construction: vue JS can define components one by one and reference components in vue pages. This function is very suitable for building large-scale applications.
Vue. Use of JS
1)stay html Page usage script introduce vue.js The library is ready to use. 2)use Npm Managing dependencies, using webpack Packaging tool pair vue.js Application packaging. 3)Vue-CLI Scaffolding, use vue.js Officially provided CLI Script rack will be easy to create vue.js Engineering prototype.
VueJS quick start
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title>Vue quick get start</title> <!-- Development environment version with helpful command line warnings --> <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script> </head> <body> <div id="app"> <!--Vue Interpolation expression of data The data defined in is displayed here--> <!--Quite so MVVM Medium View This role--> {{message}} </div> </body> <script> //view model //Creating Vue objects //vm: View Model in MVVM var vm=new Vue({ //vue takes over the area with id app el:"#app", data:{ message:"Hello Vue!",// This is equivalent to the role of Model in MVVM } }); </script> </html>
Two. Template syntax
1. Interpolation expression
The most common form of data binding is text interpolation using "Mustache" syntax (double braces). The Mustache tag will be replaced with the value of the msg attribute on the corresponding data object. Whenever the msg attribute on the bound data object changes, the content of the interpolation will be updated.
<div id="app"> <!--Vue Interpolation expression of data The data defined in is displayed here--> {{message}} <!-- Ternary operator --> {{ tag ? "true" : "false" }} <!-- Mathematical operation--> {{number*3.14}} </div> <script> //Creating Vue objects new Vue({ //vue takeover id is app area el:"#app", data:{ message:"Hello Vue!", tag:true, number:100, } }); </script>
The expression will be displayed in the Vue As an instance under the data scope JavaScript Resolved. Limit each binding to a single expression.
<!--Interpolation expressions are not supported--> {{var a = 1;}} {{if(a = 1){}}}
2. Instruction
Directives are special features with v-prefix. The value of the instruction attribute is expected to be a single JavaScript expression (v-for is the exception). When the value of an expression changes, the function of the instruction is to apply its associated influence to the DOM responsively.
1.v-if
<p v-if="seen">Now you see me</p> v-if The instruction will be based on the expression seen The true and false values of are inserted/remove p Element.
2.v-text and v-html
Double braces interpret the data as plain text rather than HTML code. Use the v-html instruction to output real HTML
v-text can render the value of a variable into a specified element, which can solve the problem of flickering interpolation expressions
<div id="app"> <div v-text="message"></div> <div v-html="message"></div> <div id="div1"></div> <div id="div2"></div> </div> <script> new Vue({ el:"#app", data:{ message:"<h1>Hello Vue</h1>" } }); //innerText and innerHTML of traditional js window.onload = function(){ document.getElementById("div1").innerHTML="<h1>Hello</h1>"; document.getElementById("div2").innerText="<h1>Hello</h1>"; } </script>
3.v-bind
The v-bind instruction can receive a "parameter", which is represented by a colon after the instruction name. Used to update HTML responsively.
here href Is a parameter, v-bind The instruction sets the value of the element href Properties and expressions url Value binding for. <a v-bind:href="url">...</a> ## v-bind Interpolation syntax cannot work on HTML In terms of features, it should be used in this case v-bind instructions <!-- Complete grammar --> <a v-bind:href="url">...</a> <!-- abbreviation --> <a :href="url">...</a>
<div id="app"> <font size="5" v-bind:color="red">Hello Vue!</font> <font size="5" :color="green">Hello Vue!</font> </div> <script> //Interpolation expressions cannot be used for attribute values of html tags //To set the value of the variable to the attribute of the html tag, you need to use v-bind //v-bind can also be simplified and used directly: new Vue({ el:"#app", data:{ red:"red", green:"green" } }) </script>
v-on instruction, which is used to listen for DOM events
<a v-on:click="doSomething">...</a>
3. Abbreviations
The v-prefix is used as a visual cue to identify Vue specific characteristics in the template.: And @ are legal characters for feature names and can be correctly resolved in all Vue enabled browsers.
1.v-bind abbreviation
v ‐ bind can bind data objects to any attribute of dom.
v ‐ bind can bind one or more features to dom objects, such as dynamically binding style and class
<!-- Complete grammar --> <a v-bind:href="url">...</a> <div v‐bind:style="{ fontSize: size + 'px' }"></div> <!-- abbreviation --> <a :href="url">...</a> <div :style="{ fontSize: size + 'px' }"></div>
2.v-on abbreviation
<!-- Complete grammar --> <a v-on:click="doSomething">...</a> <!-- abbreviation --> <a @click="doSomething">...</a>
3, Calculate properties and listeners
1. Calculation attribute
The original intention of the expression in the template is to be used for simple operations. Putting too much logic in the template will make the template too heavy and difficult to maintain. For any complex logic, computational properties should be used. Calculated properties are cached based on their responsive dependencies, and they are re evaluated only when the relevant responsive dependencies change.
Counterexample:
<div id="example"> {{ message.split('').reverse().join('') }} </div>
Positive example:
<div id="example"> <p>Original message: "{{ message }}"</p> <p>Computed reversed message: "{{ reversedMessage }}"</p> </div> var vm = new Vue({ el: '#example', data: { message: 'Hello' }, computed: { // Calculate the getter of the property reversedMessage: function () { // `this ` points to the vm instance return this.message.split('').reverse().join('') } } })
2. Listener
Vue provides a more general way to respond to changes in data through the watch option. This approach is most useful when asynchronous or expensive operations need to be performed when data changes.
watch listens to the attribute value. When the value changes, the function is executed
new Vue({ el: '#example', data: { message: 'Hello', }, methods:{ }, watch: { //This function is executed when the message value changes message: function (newValue, oldValue) { console.log(newValue) console.log(oldValue) } } })
4, Class is bound to Style
1. Bind HTML Class
Object syntax
Bind an object to v-bind:class and dynamically switch classes.
<div class="static" v-bind:class="{ active: isActive, 'text-danger': hasError}"></div> <div v-bind:class="classObject"></div> </div> data: { isActive: true, hasError:false, classObject: { active: true, 'text-danger': false } }, //Render result: <div class="static active"></div>
Bind a calculated property of a return object
<div v-bind:class="classObject"></div> data: { isActive: true, hasError:false, }, computed: { classObject: function () { return { active: this.isActive 'text-danger': this.error } } } //Render result: <div class="static active"></div>
Array syntax
Bind an array to v-bind:class to apply a class list.
<div v-bind:class="[activeClass, errorClass]"></div> data: { activeClass: 'active', errorClass: 'text-danger' } //Render result: <div class="active text-danger"></div>
You can switch class es in the list according to conditions, and use ternary expressions
<div v-bind:class="[isActive ? activeClass : '', errorClass]"></div> data: { isActive : true, } //Render result: <div class="activeClass "></div>
Used on components
When the class attribute is used on a component, these classes will be added to the root element of the component
Vue.component('my-component', { template: '<p class="foo bar">Hi</p>' }) <my-component v-bind:class="{ active: isActive }"></my-component> data: { isActive : true, } //Render result: <p class="foo bar active">Hi</p>
2. Bind inline style
Object syntax
<div v-bind:style="{ color: activeColor, fontSize: fontSize + 'px' }"></div> <div v-bind:style="styleObject"></div> data: { activeColor: 'red', fontSize: 30, styleObject: { color: 'red', fontSize: '13px' } }
Array syntax
The array syntax of v-bind:style can apply multiple style objects to the same element
<div v-bind:style="[baseStyles, overridingStyles]"></div> data: { baseStyles: 'red', overridingStyles: { color: 'red', fontSize: '13px' } }
5, Conditional rendering
1.v-if
The v-if instruction is used to render a piece of content conditionally. Because v-if is an instruction, it must be added to an element
<div v-if="type === 'A'"> A </div> <!--v-else The label needs to follow closely v-if After the label of, there can be no other label in the middle--> <div v-else-if="type === 'B'"> B </div> <div v-else> Not A/B </div>
2. Manage reusable elements with key
Vue renders elements as efficiently as possible, often reusing existing elements rather than rendering from scratch. Just add a key attribute with unique value to express that two or more elements are completely independent and do not need to be reused.
After adding the key, the two input boxes are independent and will be re rendered after each v-if judgment
<template v-if="loginType === 'username'"> <label>Username</label> <input placeholder="Enter your username" key="username-input"> </template> <template v-else> <label>Email</label> <input placeholder="Enter your email address" key="email-input"> </template>
3.v-show
The v-show instruction is used to display elements according to conditions. Elements with v-show are always rendered and retained in the DOM. V-show simply switches the CSS attribute display of an element.
<h1 v-show="ok">Hello!</h1>
4.v-if and v-show
v-if ensures that the event listeners and subcomponents in the condition block are properly destroyed and rebuilt during the switching process. If the condition is false at the initial rendering, nothing is done -- the conditional block does not start rendering until the condition first becomes true.
v-show no matter what the initial conditions are, the elements will always be rendered and simply switch based on CSS.
v-if has higher switching overhead, while v-show has higher initial rendering overhead.
<body> <div id="app"> <span v-if="flag">Heelo</span> <span v-show="flag">Vue</span> <button @click="fun">switch</button> </div> </body> <script> new Vue({ el:"#app", data:{ flag:false }, methods:{ fun:function(){ this.flag = !this.flag; } } }) </script>
6, List rendering
The v-for instruction renders a list based on an array. The v-for instruction requires a special syntax in the form of item in items, where items is the source data array and item is the alias of the array element being iterated.
Provide key s when using v-for as much as possible to improve performance
<body> <div id="app"> <ul> <li :key="index "v-for="(item,index) in arr ">{{item}}={{index}} </li> </ul> </div> </body> <script> //view model new Vue({ el:"#app", data:{ arr:[1,2,3,4,5] } }) </script>
Using v-for on components
<div id="example"> <item-list v-for="(item,index) in arr" v-bind:title="item" :key="index"></item-list> </div> <script> Vue.component('item-list', { template: '<li> {{ title }}</li>', props: ['title'] }) new Vue({ el: '#example', data: { arr:[1,2,3,4,5] }, }) </script>
v-for operand
<body> <div id="app"> <ul> <li v-for="(value, name, index) in product " v-bind:key="index"> {{ index }}. {{ name }}: {{ value }} </li> </ul> </div> </body> <script> //view model new Vue({ el:"#app", data:{ product:{ id:1, name:"computer", price:5555 } } }) </script>
Operand array
<body> <div id="app"> <table border="1"> <tr> <td>Serial number</td> <td>number</td> <td>name</td> <td>Price</td> </tr> <tr v-for="(product,index) in products "> <td>{{index}}</td> <td>{{product.id}}</td> <td>{{product.name}}</td> <td>{{product.price}}</td> </tr> </table> </div> </body> <script> //view model new Vue({ el:"#app", data:{ products:[ { id:1,name:"Notebook computer",price:5000 }, { id:2,name:"mobile phone",price:3000 }, { id:3,name:"television",price:4000 } ] } }) </script>
Operate on an integer
<span v-for="n in 10">{{ n }} </span>
7, Event handling
Listening events
The v-on instruction listens for DOM events and runs some JavaScript code when triggered.
<button v-on:click="counter += 1">Add 1</button> data: { counter: 0 }
Event handling method
v-on can receive the name of a method to be called, and the processing logic is written in the method.
<!-- Complete grammar --> <a v-on:click="doSomething">...</a> <!-- abbreviation --> <a @click="doSomething">...</a>
<div id="app"> {{message}} <button v-on:click="fun('v-on')">vue of onclick</button> </div> <script> new Vue({ el:"#app", data:{ message:"Hello Vue!" }, methods:{ fun:function(msg){ alert("Hello Vue!"); this.message = msg; } } }); </script>
Use the special variable $event to access the original DOM event in the processing method
v-on:keydown
<div id="app"> Vue mode:<input type="text" v-on:keydown="fun($event)"> <hr/> tradition JS Method:<input type="text" onkeydown="showKeyCode()"/> </div> <script> new Vue({ el:"#app", methods:{ // $event is an event object in vue, which is the same as the event object in traditional js fun:function(event){ var keyCode = event.keyCode; if(keyCode < 48 || keyCode > 57){ //Disable keyboard keys event.preventDefault(); } alert(keyCode); if(event.keyCode == 13){ alert("Press enter"); } } } }); //Traditional js keyboard press event function showKeyCode(){ //event object is the same as document object and window object and can be used directly var keyCode = event.keyCode; //keyCode=48(0) keyCode=57(9) 0-9 => 48-57 if(keyCode < 48 || keyCode > 57){ //Disable keyboard keys event.preventDefault(); } alert(keyCode); if(event.keyCode == 13){ alert("Press enter"); } } </script>
v-on:mouseover
<div id="app"> <div @mouseover="fun1" style="width: 200px;height: 200px;background-color: aqua"> <textarea @mouseover="fun2($event)">This is a text field</textarea> </div> <div onmouseover="divmouseover()" style="width: 200px;height: 200px;background-color: aquamarine"> <textarea onmouseover="textareamouseover()">This is a text field</textarea> </div> </div> <script> /** * @Event name is the abbreviation of v-on: event name * @mouseover Equivalent to v-on:mouseover */ new Vue({ el:"#app", methods:{ fun1:function(){ alert("Mouse over div upper!"); }, fun2:function(event){ alert("Mouse over textarea upper!"); //Prevent bubbling. If not, execute fun2 and fun1 at the same time event.stopPropagation(); } } }); //Traditional js mode function divmouseover(){ alert("The mouse moved to div upper!"); } function textareamouseover(){ alert("The mouse moved to textarea upper!"); //Prevent bubbling. If not, execute textareamouseover() and divmouseover() at the same time; event.stopPropagation(); } </script>
Event modifier
Vue.js provides event modifiers for v-on to handle DOM event details, such as event Preventdefault() or event stopPropagation().
Vue.js Pass by point(.)Represents the instruction suffix to invoke the modifier. .stop .prevent .capture .self .once
<!-- Prevent click events from continuing to propagate --> <a v-on:click.stop="doThis"></a> <!-- Submitting an event no longer reloads the page --> <form v-on:submit.prevent="onSubmit"></form> <!-- Modifiers can be concatenated --> <a v-on:click.stop.prevent="doThat"></a> <!-- Only modifiers --> <form v-on:submit.prevent></form> <!-- Use event capture mode when adding event listeners --> <!-- That is, events triggered by internal elements are processed here first, and then handed over to internal elements for processing --> <div v-on:click.capture="doThis">...</div> <!-- Only when event.target Is the handler function triggered when the current element itself --> <!-- That is, the event is not triggered from an internal element --> <div v-on:click.self="doThat">...</div> <!-- The click event will only be triggered once --> <a v-on:click.once="doThis"></a> <!-- Default behavior for scrolling events (Rolling behavior) Will be triggered immediately --> <!-- Without waiting `onScroll` complete --> <!-- This includes `event.preventDefault()` Situation --> <div v-on:scroll.passive="onScroll">...</div>
<div id="app"> <form @submit.prevent action="http://www.baidu.com" method="post" > <input type="submit" value="Submit"> </form> <form action="http://www.baidu.com" method="post" onsubmit="return checkForm()"> <input type="submit" value="Submit"> </form> <hr/> <div @mouseover="fun1" id="div"> <textarea @mouseover.stop="fun2($event)">This is a text field</textarea> </div> </div> <script> new Vue({ el:"#app", methods:{ fun1:function(){ alert("Mouse over div upper"); }, fun2:function(event){ alert("Mouse over textarea upper,And the bubbling event is prevented"); } } }); //Traditional js mode function checkForm(){ alert(1); //Form validation must have an explicit boolean return value //The return method name must be added when applying the verification method return false; } </script>
Key modifier
Vue allows you to add key modifiers for v-on when listening for keyboard events.
All key code aliases: .enter .tab .delete (capture "delete" and "Backspace" key) .esc .space .up .down .left .right .ctrl .alt .shift .meta
<div id="app"> <input type="text" v-on:keyup.enter="fun"> </div> <script> new Vue({ el:'#app', methods:{ fun:function(){ alert("Press enter"); } } }); </script>
8, Form input binding
The v-model instruction creates a two-way data binding on forms, and elements. It will automatically select the correct method to update the element according to the control type.
v-model
<body> <div id="app"> <form action="" method="post"> user name:<input type="text" name="username" v-model="user.username"><br/> password:<input type="text" name="password" v-model="user.password"><br/> </form> </div> </body> <script> new Vue({ el:"#app", data:{ user:{ username:"test", password:"1234" } } }) </script>
9, Vue lifecycle
Each Vue instance goes through a series of initialization processes before being created
vue has these states in the life cycle: beforeCreate,created,beforeMount,mounted,beforeUpdate,updated,beforeDestroy,destroyed.
In the process of instantiation, Vue will call these life cycle hooks, providing us with the opportunity to execute custom logic.
Life cycle diagram
The process from creation to destruction of vue instances
establish vue Instance (initialization) data,load el) Data mount vue example data Render data from to web page HTML (label) Re render (when vue of data If the data changes, it will be re rendered to HTML (label) Destroy instance
Life cycle presentation coding
<body> <div id="app"> {{message}} </div> </body> <script> var vm = new Vue({ el: "#app", data: { message: 'hello world' }, beforeCreate: function() { //data cannot be operated before initialization console.log(this); showData('establish vue Before instance', this); }, created: function() { //Execute after data initialization and modify / obtain the value in data before template loading //this.message= "created"; showData('establish vue After instance', this); }, beforeMount: function() { //After the template is loaded and before the data is initially rendered (mounted), the values in the data can be modified / obtained //this.message= "beforeMount"; showData('Mount to dom front', this); }, mounted: function() { //After the initial rendering (mounting) of the data, you can modify the variables in the data, but it will not affect the rendering of v-once //this.message= "mounted"; showData('Mount to dom after', this); }, beforeUpdate: function() { //After data rendering, re rendering is triggered when the data in data changes, and this function is executed before rendering //After the data is modified, before re rendering to the page //this.message= "beforeUpdate"; showData('Before data change update', this); }, updated: function() { //After the data is modified, it is re rendered to the page //this.message= "updated"; showData('After data change and update', this); }, beforeDestroy: function() { showData('vue Before instance destruction', this); }, destroyed: function() { showData('vue After instance destruction', this); } }); function realDom() { console.log('real dom Structure:' + document.getElementById('app').innerHTML); } function showData(process, obj) { console.log(process); console.log('data Data:' + obj.message) console.log('Mounted objects:') console.log(obj.$el) realDom(); console.log('------------------') console.log('------------------') } // vm.message = "good..."; vm.$destroy(); </script>
Hook function
In order to facilitate developers to carry out specific operations in different stages of the vue instance life cycle, vue provides a function before and after the four stages of the life cycle. This function does not need to be called by developers. When the vue instance reaches the specified stage of the life cycle, it will automatically call the corresponding function.
vue During object initialization, the beforeCreate,created,beforeMount,mounted These hooks
beforeCreate
The data has not been monitored, bound to the vue object instance, or mounted
created
The data has been bound to the object instance, but the object has not been mounted
beforeMount
The template has been compiled. The corresponding element object has been generated according to the data and template, and the data object is associated with the el attribute of the object. The el attribute is an HTMLElement object. That is, at this stage, the vue instance creates this html fragment through the native createElement and other methods to prepare to inject it into the mount point corresponding to the el attribute specified by the vue instance
mounted
Attaching the content of el to el is equivalent to executing (el) in jquery HTML (el), generate the real dom on the page, and then you will find that the elements of dom and el are consistent. After that, you can use methods to get the dom object under the el element and perform various operations
When the data changes, the beforeUpdate and updated methods are called
beforeUpdate
Before updating the data to dom, we can see that the $el object has been modified, but the dom data on our page has not changed
updated:
The dom structure will find the minimum path to update the dom structure of the page through the principle of virtual dom, and update the changes to the dom to complete the update
Instance destruction
beforeDestroy,destroed
For instance destruction, vue instances still exist, but the event monitoring and the binding of watcher object data and view, that is, data-driven
10, Component use
Usually, an application will be organized in the form of a nested component tree. The application may have components such as page header, sidebar and content area, and each component contains other components such as navigation links and blog posts.
Component registration
In order to be used in the template, the component must first be registered for Vue Can identify. There are two types of component registration: global registration and local registration. Component pass Vue.component Global registration
button-counter.js
// Define a new component called button counter Vue.component('button-counter', { data: function () { return { count: 0 } }, template: '<button v-on:click="count++">You clicked me {{ count }} times.</button>', methods:{ test:function(){ alert("Functions defined in components"); } } })
Globally registered components can be used in any newly created Vue root instance (through new Vue) after they are registered, as well as in the templates of all sub components in their component tree.
Data defines the data rendered by the template of the component
HTML module of template component (HTML tag \ css style)
methods defines the JS function of the tag event binding in the component
Component reference
Defining components requires dependencies vue.js,When referencing custom components js The file must be referenced before vue.js The reference of the component must be in the vue example el In the specified container
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <div id="container"> <button-counter></button-counter> </div> <script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/button-counter.js" ></script> <script type="text/javascript"> var vm = new Vue({ el:"#container", }); </script> </body> </html>
Component communication
The vue instance itself is a component. The component referenced in the el container specified by the vue instance is called a child component, and the current vue instance is the parent component
Father to son
Pass data to sub components through prop. Prop is some custom attributes that you can register on the component. When a value is passed to a prop attribute, it becomes a property of that component instance.
When a vue instance references a component, it passes data to the referenced component
Subcomponents
button-counter.js
A component can have any number of by default prop,Any value can be passed to any prop.
// Define a new component called button counter Vue.component('button-counter', { data: function () { return { count: 0 } }, props: ['title'], template: '<h3>{{ title }}</h3>', methods:{ test:function(){ alert("Functions defined in components"); } } })
Parent component
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <div id="container"> <button-counter title="Blogging with Vue"></button-counter> <!--use v-bind To dynamically transfer prop--> <button-counter :title=text></button-counter> </div> <script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/button-counter.js" ></script> <script type="text/javascript"> var vm = new Vue({ el:"#container", data(){ text:"text", }, }); </script> </body> </html>
Son to father
The function of the parent component is "called" through the button of the child component, and the value is passed through the function
Subcomponents
button-counter.js
// Define a new component called button counter Vue.component('button-counter', { data: function () { return { count: 123 } }, template: '<div><button @click=change()>Son to father</button></div>', methods:{ change(){ this.$emit("my-event",this.count); } } })
Parent component
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <div id="container"> <button-counter @my-event=myEvent></button-counter> {{text}} </div> <script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/button-counter.js" ></script> <script type="text/javascript"> var vm = new Vue({ el:"#container", data(){ text:"text", }, methods:{ change(data){ this.text=data; } } }); </script> </body> </html>
11, Component slot
When a vue component is customized, some contents in the component are allowed to be defined when calling the component, which is called a slot.
Use of slots
When customizing a component, the slot is defined in the template of the component through the slot tag
Subcomponents
button-counter.js
// Define a new component called button counter Vue.component('button-counter', { data: function () { return { count: 0 } }, props: ['title'], template: '<h2>1111111</h3> <slot></slot> <h4>33333333</h4>', })
Parent component
When the component is invoked in the parent component, the template that specifies the slot is filled.
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <div id="container"> <button-counter > <!--Component label contains HTML The default is the template filled into the slot--> <h3>2222222</h3> </button-counter> </div> <script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/button-counter.js" ></script> <script type="text/javascript"> var vm = new Vue({ el:"#container", data(){ text:"text", }, }); </script> </body> </html>
Named slot
When the number of slots in the component is > 1, you need to add the name attribute to the slot tag in the component to specify the name of the slot
Subcomponents
button-counter.js
// Define a new component called button counter Vue.component('button-counter', { data: function () { return { count: 0 } }, props: ['title'], template: '<h2>1111111</h3> <slot name="slot1"></slot> <slot name="slot2"></slot> <h4>33333333</h4>', })
Parent component
When the component is invoked in the parent component, the template that specifies the slot is filled.
<!DOCTYPE html> <html> <body> <div id="container"> <button-counter > <!--Define a template and fill it into the component name=slot1 Slot for--> <template slot="slot1"> <h3>slot1</h3> </template> <!--Define a template and fill it into the component name=slot2 Slot for--> <template slot="slot2"> <h3>slot2</h3> </template> </button-counter> </div> <script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/button-counter.js" ></script> <script type="text/javascript"> var vm = new Vue({ el:"#container", data(){ text:"text", }, }); </script> </body> </html>
Slot scope
Subcomponents
button-counter.js
// Define a new component called button counter Vue.component('button-counter', { data: function () { return { msg: "hello" } }, props: ['title'], template: '<h2>1111111</h3> <slot name="slot1" v-bind:title="msg"></slot> <h4>33333333</h4>', })
Parent component
Use the slot SCOP attribute on the template that fills the slot to obtain the value of the slot binding
<!DOCTYPE html> <html> <body> <div id="container"> <button-counter > <!--When filling component slots with templates, you can use slot-scope Property to get the data bound to the component slot--> <template slot="slot1" slot-scope="res"> <h3>{{res.title}}</h3> </template> </button-counter> </div> <script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/button-counter.js" ></script> <script type="text/javascript"> var vm = new Vue({ el:"#container", data(){ text:"text", }, }); </script> </body> </html>
12, Axios
Axios is a promise based HTTP library that can be used in browsers and node JS
vue itself has no communication capability, and is usually used in combination with axios (a js framework focusing on asynchronous communication)
axios data communication vue Data rendering
Introducing Axios
1. Install axios module
npm install axios import axios from 'axios';
2. Import with script
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
get request
axios.get('/user/findUserById?id=1') .then(function (response) { console.log(response); }).catch(function (err) { console.log(err); }); axios.get('/user/findUserById', { params: { id: 1 } }).then(function (response) { console.log(response); }).catch(function (err) { console.log(err); });
post request
axios.post('/user/login', { username: 'admin', password: 'admin' }) .then(function (res) { console.log(res); }) .catch(function (err) { console.log(err); });
Custom request
User defined request method, request parameters, request header and request body (post)
axios({ url:"http://localhost:8888/user/login", method:"post", params:{ //Set request line value username:"admin", password: "admin" }, headers:{ //Set request header }, data:{ //Set request body (post/put) } }).then(function(res){ console.log(res) });
Concurrent request
methods:{ test:function(){ //Send asynchronous request axios.all([test1(),test2()]).then(axios.spread(function (r1, r2) { // Both requests are now complete console.log(r1); console.log(r2); })); } } }); function test1() { return axios.get('http://localhost:8888/user/findUserById?id=1'); } function test2() { return axios.get('http://localhost:8888/user/findUserById?id=2'); } }
Axios usage example
methods:{ findUserList:function(){ //Define a variable to indicate that it is a vue object var _this = this; axios.get('/user/findUserList') .then(function (response) { _this.userList = response.data;//Assign value to userList with response data console.log(_this.userList); }) .catch(function (error) { console.log(error); }) }, findUserById:function (userid) { var _this = this; axios.get('/user/findUserById',{params:{id:userid}}) .then(function (response) { _this.user = response.data; console.log(_this.user); }) .catch(function (error) { console.log(error); }) }, updateUser:function (user) { var _this = this; axios.post('/user/updateUser', _this.user) .then(function (response) { console.log(response); }) .catch(function (error) { console.log(error); }); } }, //Trigger the request when the page is loaded created:function() { this.findUserList(); }
Arrow function
The parameter res of axios callback function is not the data returned by the interface, but represents a response object; res.data represents the data responded by the interface
test:function(){ //Send asynchronous request axios.get("http://localhost:8888/user/findUserById?id=2").then( (res)=>{ if(res.data.code == 200){ console.log(res.data.data); } }); }
13, Routing router
router It is a plug-in officially provided by vue to realize component jump
1. Reference router
npm installation
npm install vue-router
Via Vue Use () explicitly installs the routing function
import Vue from 'vue' import VueRouter from 'vue-router' Vue.use(VueRouter)
Online CDN
<script src="https://unpkg.com/vue/dist/vue.js"></script> <script src="https://unpkg.com/vue-router/dist/vue-router.js"></script>
Offline mode
<script type="text/javascript" src="js/vue.js" ></script> <script type="text/javascript" src="js/vue-router.js"></script>
2.router example
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script src="https://unpkg.com/vue-router/dist/vue-router.js"></script> </head> <body> <div id="app"> <h1>Hello App!</h1> <button @click="routeParams">Console printing router information</button> <button @click="goBack">Returns the last route</button> <p> <!-- use router-link Components to navigate. --> <!-- Pass in `to` Property specifies the link. --> <!-- <router-link> By default, it will be rendered as a `<a>` label --> <router-link to="/foo">Go to Foo</router-link> <router-link to="/bar">Go to Bar</router-link> </p> <!-- Route exit --> <!-- The components to which the route matches will be rendered here --> <router-view></router-view> <script type="text/javascript"> // 0. If you use modularization mechanism to program and import Vue and vuerouter, you need to call Vue use(VueRouter) // 1. Define (route) components. // You can import from other files const Foo = {template: '<div>foo</div>'} const Bar = {template: '<div>bar</div>'} // 2. Define route // Each route should map a component. Where "component" can be // Via Vue The component constructor created by extend(), // Or, just a component configuration object. // We'll talk about nested routing later. const routes = [ {path: '/foo', component: Foo}, {path: '/bar', component: Bar} ] // 3. Create a router instance and then transfer it to 'routes' configuration // You can also transfer other configuration parameters, but let's do it first. const router = new VueRouter({ routes // (abbreviation) equivalent to routes: routes }) // 4. Create and mount root instances. // Remember to inject routes through router configuration parameters, // So that the whole application has routing function const app = new Vue({ router, methods: { goBack() { window.history.length > 1 ? this.$router.go(-1) : this.$router.push('/') }, routeParams() { console.log(this.$route) } } }).$mount('#app') // Now, the application has started! </script> </div> </body> </html>
3. Dynamic route matching
wildcard
Wildcard, * can match any path. Use wildcard to define the path. Pay attention to the order of route declaration
- /User - * matches any path starting with user -
- /*Match all paths
const routes = [ {path: '/foo-*', component: Foo}, {path: '/*', component: Bar} ]
Routing parameters
/user/:id, which can match the path starting with / user /
<router-link to="/user/123">Go to User</router-link>
const routes = [ // Dynamic path parameters start with a colon {path: '/user/:id', component: User }, ]
Both / user/foo and / user/bar will map to the same route
A path parameter is marked with a colon:. When a route is matched, the parameter value will be set to this$ route. Params, which can be used within each component. Therefore, we can update the User's template and output the current User's ID
const User = { template: '<div>User {{ $route.params.id }}</div>' }
Set multi segment "path parameter" in route
pattern | Matching path | $route.params |
---|---|---|
/user/:username | /user/evan | { username: 'evan' } |
/user/:username/post/:post_id | /user/evan/post/123 | { username: 'evan', post_id: '123' } |
priority
The same path can match multiple routes. At this time, the matching priority is in the order of route definition: the earlier the route is defined, the higher the priority is.
Nested Route
Displays the secondary route in the component of the primary route
Components to navigate
<p> <!-- use router-link Components to navigate. --> <!-- Pass in `to` Property specifies the link. --> <!-- <router-link> By default, it will be rendered as a `<a>` label --> <router-link to="/user/123">Go to User</router-link> <router-link to="/user/foo">Go to Foo</router-link> <router-link to="/user/bar">Go to Bar</router-link> </p> <!-- Route exit --> <!-- <router-view> It is the top-level exit, rendering the components matched by the highest-level route --> <router-view></router-view>
Define (route) components
const Foo = {template: '<div>foo</div>'} const Bar = {template: '<div>bar</div>'} <!--A rendered component can also contain its own nesting <router-view>--> const User = { template: ` <div class="user"> <h2>User {{ $route.params.id }}</h2> <router-view></router-view> </div> ` }
Define route
<!--To render components in nested exits, you need to VueRouter Used in parameters of children to configure--> const routes = [ { path: '/user/:id', component: User, children: [ { // When / user/:id/foo matches successfully, // Foo will be rendered in the User's < router View > path: 'foo', component: Foo }, { // When / user/:id/bar matches successfully // The Bar will be rendered in the User's < router View > path: 'bar', component: Bar } ] } ]
4. Programming navigation
In addition to using the create a tag to define the navigation link, we can also use the instance method of router to write code.
stay Vue Inside the instance, you can $router Access the routing instance. So you can call this.$router.push. Want to navigate to a different URL,Then use router.push method. This method will history A new record is added to the stack, so when the user clicks the browser Back button, it returns to the previous record URL. When clicked <router-link> This method will be called internally, so click <router-link :to="..."> Equivalent to calling router.push(...).
Declarative | Programming |
---|---|
<router-link :to='..'> | router.push(...) |
push()
Click event
<button @click="goUser">Go to User</button>
Navigation
<router-link to="/user/bar">Go to Bar</router-link> <router-view></router-view>
Routing component
const User = { template: ` <div> <h2>User {{ $route.params.id }}</h2> <router-view></router-view> </div> ` }
Routing rules
{path: '/user/:id',component: User}
Click event departure routing rules
methods: { goUser() { //Code implementation routing jump: programming navigation this.$router.push("/user/456"); }, }
push() parameter
// character string router.push('home') // object router.push({ path: 'home' }) // Named route router.push({ name: 'user', params: { userId: '123' }}) // With query parameters, it becomes / register?plan=private router.push({ path: 'register', query: { plan: 'private' }})
replace()
With router Push is very similar. The only difference is that it does not add a new record to history, but is the same as its method name - replacing the current history record.
Declarative | Programming |
---|---|
<router-link :to="..." replace> | router.replace(...) |
go()
The parameter of this method is an integer, which means the number of steps forward or backward in the history record, similar to window history. go(n).
// A step forward in the browser record is equivalent to history forward() router.go(1) // One step backward is equivalent to history back() router.go(-1) // Record 3 steps forward router.go(3) // If the history record is not enough, it will fail silently router.go(-100) router.go(100)
goBack() { window.history.length > 1 ? this.$router.go(-1) : this.$router.push('/') },
5. Named route
When defining a route, you can specify a name for the route. When navigating a route, you can navigate by the name of the route
<div id="app"> <router-link :to="{ name: 'user', params: { userId: 123 }}">User</router-link> <router-view></router-view> <script type="text/javascript"> const User = { template: ` <div> <h2>User {{ $route.params.userId }}</h2> </div> ` } const router = new VueRouter({ routes: [ { path: '/user/:userId', name: 'user', component: User } ] }) const app = new Vue({ router, }).$mount('#app') </script> </div>
Equivalent to code calling router push()
router.push({ name: 'user', params: { userId: 123 } })
6. Named routing view
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script src="https://unpkg.com/vue-router/dist/vue-router.js"></script> </head> <body> <div id="container"> <router-link to="/a">aa</router-link> <router-link to="/b">bb</router-link> <!--Routing view--> <!--If there is more than one routing view router-view,Need to give router-view appoint name,Use in routing components Map multiple components according to name Set components and router-view Binding relationship--> <router-view name="v1"></router-view> <router-view name="v2"></router-view> <!--If router-view If no name is set, the default is default. --> <router-view ></router-view> </div> <script type="text/javascript"> const component1 = { template: "<div>component1---v1---Routing view</div>" }; const component2 = { template: "<div>component2---v2---Routing view</div>" }; const component3 = { template: "<div>component3---v1---Routing view</div>" }; const component4 = { template: "<div>component4---v2---Routing view</div>" }; const component5 = { template: "<div>component5---default---Routing view</div>" }; const router = new VueRouter({ routes: [ { path: "/a", components: { default: component5, v1: component1, v2: component2 } }, { path: "/b", components: { default: component5, v1: component3, v2: component4 } } ] }); var vm = new Vue({ el: "#container", router: router }); </script> </body> </html>
7. Redirection and alias
When the user accesses / a, the URL will be replaced with / B, and then the matching route will be / b
redirect
Redirect from / a to / b
const router = new VueRouter({ routes: [ { path: '/a', redirect: '/b' } ] })
Route naming redirection
The target of redirection can also be a named route
const router = new VueRouter({ routes: [ { path: '/a', redirect: { name: 'foo' }} ] })
Route alias
/The alias of a is / b, which means that when the user accesses / b, the URL will remain / b, but the route matching will be / A, just as the user accesses / A.
const router = new VueRouter({ routes: [ { path: '/a', component: A, alias: '/b' } ] })
8. Routing component transmission parameters
Using $route in a component will form a high coupling with its corresponding route, so that the component can only be used on some specific URL s, which limits its flexibility.
Through / url/:attr, the value is transmitted to the component through the route, and there is $route coupling
const User = { template: '<div>User {{ $route.params.id }}</div>' } const router = new VueRouter({ routes: [{ path: '/user/:id', component: User }] })
Decoupling by props
<router-link to="/user/123">User</router-link> <router-view></router-view> const User = { props: ['id'], template: '<div>User {{ id }}</div>' } const router = new VueRouter({ routes: [ { path: '/user/:id', component: User, props: true }, // For routes containing named views, you must add the 'props' option for each named view separately: { path: '/user/:id', components: { default: User, sidebar: Sidebar }, props: { default: true, sidebar: false } } ] })