Vue component practice

Vue components

axios implements data requests

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="./js/vue.js"></script>
    <script src="https://unpkg.com/axios/dist/axios.min.js"></script>

</head>
<body>
<div id="app">
    <ul>
        <li v-for="film in films_list">
            <p>The name of the film is:{{film.name}}</p>
            <img :src="film.poster" alt="" width="100px" height="150px">
            <p>Movie introduction:{{film.synopsis}}</p>
        </li>
    </ul>

</div>

</body>
<script>

    var vm = new Vue({
        el: '#app',
        data: {
            films_list:[]
        },
        created() {
            axios.get('http://127.0.0.1:5000/films').then(res => {
                console.log(res.data)
                this.films_list=res.data.data.films
            })

        }
    })
</script>
</html>
from flask import Flask,make_response,jsonify

app=Flask(__name__)
@app.route('/films')
def films():
    import json
    with open('./movie.json','r',encoding='utf-8') as f:
        res=json.load(f)
    obj = make_response(jsonify(res))
    obj.headers['Access-Control-Allow-Origin']='*'
    return obj

if __name__ == '__main__':
    app.run()

Calculation properties

We can cache the calculation by calculating the attribute computed. What does that mean?

In Vue, we can use interpolation to display data. For ordinary interpolation functions, as soon as the page is refreshed, the function will be recalculated. No matter the value related to the function will change, the function will also be recalculated, resulting in reduced operation efficiency;

Then we can write the user-defined function in calculated to control, and use the function as an attribute. There is no need to add parentheses for calling. Only when the attribute (variable) used by the function changes, the function will recalculate. This can reduce the pressure and reduce the waste of resources

Case 1: initial capitalization

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Calculation properties</title>
    <script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
    <link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/css/bootstrap.min.css" rel="stylesheet">
    <script src="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js"></script>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
    <div style="font-size: 20px">
        Input content:<input type="text" v-model="mytext"> ----> {{mytext.substring(0,1).toUpperCase()+mytext.substring(1)}}
        <br><br>
        <p>Function binding(It will refresh the page and is not recommended): <input type="text" :value="getName()"></p>
        <p>Calculation properties(recommend): <input type="text" :value="getName1"></p>
    </div>

    <hr>
    <div style="font-size: 20px">
         <p>Input content:<input type="text" v-model="mytext1"> ----->{{mytext1}}</p>
    </div>
</div>
</body>
<script>
    var vm = new Vue({
        el: '#app',
        data: {
            mytext: '',
            mytext1:''
        },
        methods:{
            getName(){
                console.log('Function mode, I executed')
                return this.mytext.substring(0,1).toUpperCase()+this.mytext.substring(1)
            }
        },
        //Calculation properties
        computed:{
            getName1(){
                console.log('Calculate properties, I executed')
                return this.mytext.substring(0,1).toUpperCase()+this.mytext.substring(1)
            }

        }
    })
</script>
</html>

We can find that only those related to attributes can be printed. If the following input only prints ordinary functions, even if the function is not related to mytext1

Case 2: filtering cases

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Filter case</title>
    <script src="https://cdn.bootcdn.net/ajax/libs/vue/2.6.12/vue.min.js"></script>
</head>
<body>
<div id="box">
    <p><input type="text" v-model="myText"  placeholder="Please enter the content to filter:"></p>
    <ul>
        <li v-for="data in newList">{{data}}</li>
    </ul>
</div>
</body>
<script>
    var vm = new Vue({
        el: '#box',
        data: {
            myText: '',
            dataList: ['a', 'at', 'atom', 'be', 'beyond', 'cs', 'csrf'],
        },

        computed:{

            newList(){
                var _this = this
                console.log('Yes',_this)
                 var datalist2 = _this.dataList.filter(function(item){
                    console.log(_this)
                     return item.indexOf(_this.myText) > -1

                })
                return datalist2

            }
        }
    })
</script>
</html>


Listening properties

watch to set the listening property. When mytext changes, the function and method bound to mytext will be executed

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">

    <input type="text" v-model="mytext">--->{{mytext}}


</div>

</body>
<script>
    var vm = new Vue({
        el: '#app',
        data: {
            mytext: '',
        },
        watch: {
            // This function is executed whenever mytext changes
            mytext: function () {
                console.log('I've changed, execution')

            }
        }


    })
</script>
</html>

Local component

What is written in components is local components. The location is limited and can only be used locally

For example, in the following example, the Top component can only be used in the tag (div) whose id is app. If you want to redefine a sub component in the Top component, it can only be used in the div in the template in the component

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
    <Top></Top>
    <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br>
    <Bottom></Bottom>
</div>

</body>
<script>
    var vm = new Vue({
        el: '#app',
        data: {},
        // What is defined here is called a local component, which can only be used locally, and can only be used in the tag with id app
        components: {
            'Top': {
                //Write it in a div
                template: `
                    <div>
                        <h1 style="background: pink;font-size: 60px;text-align: center">{{name}}</h1>
                        <hr>
                        <button @click="handleC">Order me to see beauty</button>
                    </div>
                `,
                //data is a function that can set the return value
                data() {
                    return {
                        name: "I'm the head"
                    }
                },
                methods: {
                    handleC() {
                        alert('beauty')
                    }
                },
            },
            'Bottom': {
                template: `
                    <div>
                        <hr>
                        <h1 style="background: green;font-size: 60px;text-align: center">{{name}}</h1>

                    </div>
                `,
                data() {
                    return {
                        name: "I'm the tail"
                    }
                },

            },

        },


    })
</script>
</html>

Global components

Any location can be used, but it must also be within the div managed by the vue instance

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
    <top></top>


</div>

</body>
<script>
    // Define global components, which can be used anywhere, or locally
    Vue.component('top', {
            template: `
                <div>
                    <h1 style="background: pink;font-size: 60px;text-align: center">{{name}}</h1>
                    <hr>
                    <button @click="handleC">Order me to see beauty</button>
                </div>
            `,
            data() {
                return {
                    name: "I'm the head"
                }
            },
            methods: {
                handleC() {
                    alert('beauty')
                }
            },

        },)

    var vm = new Vue({
        el: '#app',
    })
</script>
</html>

Parent to child of component communication

Data is shared differently between components, and data is transferred. If we want to transfer data from the parent component to the child component, we can implement it through props custom attribute, such as the following example:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
    <link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/css/bootstrap.min.css" rel="stylesheet">
    <script src="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js"></script>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
    Subcomponent display:<top :value="handleName"></top>
    <hr>
    Parent component input:<input type="text" v-model="handleName">

</div>

</body>
<script>

    Vue.component('top', {
        template: ` <div>
                    <h1 style="background: tomato;font-size: 30px;text-align: center">{{value}}</h1>
                    </div>             `,
        // It must be called props, and the name of the custom attribute is put in the array
        props:{
            value: String,  // key is the user-defined attribute name and value is the type name. If it is another type, an error will be reported
        },
        //props can also be written in the form of array without verification function
        // props:['value',]
    })
    var vm = new Vue({
        el: '#app',
        data: {
            handleName: ''
        }
    })
</script>
</html>

Child of component communication

PS: all Vue built-in objects appear as $xx

We can pass data from the child component to the parent component through custom events, and use $emit('custom event ', parameter) in the child component

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
    <link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/css/bootstrap.min.css" rel="stylesheet">
    <script src="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js"></script>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
<top @myevent="handleRecv"></top>
    <hr>
  <h1 style="background: green;font-size: 60px;text-align: center">Parent component</h1>
 <p>Receiving data sent by sub components:{{childText}}</p>
</div>

</body>
<script>

    Vue.component('top', {
        template: ` <div>
                        <h1 style="background: tomato;font-size: 60px;text-align: center">{{myheader}}</h1>
                        <p>Sub component input:<input type="text" v-model="text"></p>
                        <p><button class="btn-success"  @click="handleSend">Send data to parent component</button></p>
                    </div>             `,
        data(){
            return {
                myheader:'Subcomponents',
                text:''
            }
        },
        methods:{
            handleSend(){
                //Myevent is a custom event, which means that the text of the sub component is handed over to the myevent event event for processing
                this.$emit('myevent',this.text)
            }
        }

    })
    var vm = new Vue({
        el: '#app',
        data: {
            //Receive data from sub components
            childText:''
        },
        methods: {
            handleRecv(data){
                // Receive the parameter and assign it to the childText of the parent component
                this.childText=data
            }
        }
    })
</script>
</html>

ref attribute (communication between components)

Common label usage

Common tags use the ref attribute. What you get through $refs is the tag where the ref attribute is located. What you get is an object. If multiple tags write the ref attribute, all tags with the ref attribute will be brought into one object. You can operate and set html, as shown in the following example:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
    <link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/css/bootstrap.min.css" rel="stylesheet">
    <script src="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js"></script>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
    <h1 style="align-content: center">Common label usage ref</h1>
    <p><input type="text" ref="myinput"></p>
    <p><img src="" height="100px" width="100px" ref="myimg"></p>
    <p><button @click="handleC">Point me</button>
</p>
</div>
</body>
<script>

    let vm = new Vue({
        el: '#app',
        data: {
             text:''
        },
        methods: {
            handleC(){
                console.log('I was ordered')
                console.log(this.$refs)  // It is all objects with ref attribute written on the tag {myinput: real tag, myimg: real tag}
                console.log(this.$refs.myinput.value)
                //Set value
                this.$refs.myinput.value='HammerZe'
                //Set src attribute to display pictures
                this.$refs.myimg.src='https://img0.baidu.com/it/u=3608430476,1945954109&fm=253&fmt=auto&app=138&f=JPEG?w=500&h=494'
            }
        }
    })
</script>
</html>

The component uses the ref attribute

The ref attribute, if placed on a component, is the current component object

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
    <link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/css/bootstrap.min.css" rel="stylesheet">
    <script src="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js"></script>
    <script src="./js/vue.js"></script>
</head>
<body>
<div id="app">
<!-- Component use ref attribute   -->
<top ref="top"></top>
<p>signal communication:<input type="text" v-model="text"></p>
<p>Parent component button:<button @click="handleC">Point me</button></p>
</p>
</div>
</body>
<script>
   Vue.component('top', {
        template: `
            <div>
                <h1>{{myheader}}</h1>
                <p>Subcomponent buttons:<button @click="handleC">Order me to see beauty</button></p>
                <hr>
            </div>
        `,
        data() {
            return {
                myheader: "head",
            }
        },
        methods:{
            handleC(){
                alert("beauty")
            }
        }



    },)
    let vm = new Vue({
        el: '#app',
        data: {
             text:''
        },
        methods: {
        //Place on assembly
        handleC() {
             console.log(this.$refs.top) //VueComponent {_uid: 1, _isVue: true, $options: {...}, _renderProxy: Proxy, _self: VueComponent, ...}
            /*Son to father*/
            // The parent component takes the value of the child component
            console.log(this.$refs.top.myheader)
            // this.text=this.$refs.top.myheader
            // The parent component calls the method of the child component
            this.$refs.top.handleC()

            /*Father to son*/
            this.$refs.top.myheader=this.text
        }
        }
    })
</script>
</html>

Event bus (not commonly used)

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="js/vue.js"></script>
</head>
<body>
<div id="box">
    <child1></child1>
    <child2></child2>
</div>
</body>
<script>
    var bus=new Vue() //A vue instance of new is the central event bus
    Vue.component('child1', {
        template: `<div>
            <input type="text" ref="mytext">
            <button @click="handleClick">Point me</button>
        </div>`,
        methods:{
            handleClick(){
                bus.$emit('suibian',this.$refs.mytext.value) //Publish a message with the same name as the subscription message
            }
        }
    })
    Vue.component('child2', {
        template: `<div>
                    <div>Messages received {{msg}}</div>
                    </div>`,
        data(){
            return {msg:''}
        },
        mounted(){
            //In the life cycle, the dom of the current component is created and executed
            console.log('Current component dom Execute after creating')
            //Subscribe to messages
            bus.$on('suibian',(item)=>{
                console.log('I got it',item)
                this.msg=item
            })
        }
    })
    var vm = new Vue({
        el: '#box',
        data: {},
        methods: {
            handleClick() {
                console.log(this)
                //this.$refs.mytext gets the input control and takes out the value value
                console.log(this.$refs.mytext.value)
                console.log(this.$refs.mychild.text)
                // this.$refs.mychild.add()
                this.$refs.mychild.add('Transfer parameters')

            }
        }

    })
</script>
</html>

Dynamic components and keep alive

Dynamic component: click on different connections to display different pages, realize jump, use component tag, bind with is attribute, and specify which display which

Keep alive: use the keep alive tag to keep the original input content without destroying the component

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="./js/vue.js"></script>
</head>
<style>
    #menu {
        font-size: 18px;
        font-weight: bold;
    }

    #menu li {
        text-decoration: none; /*Remove the front dot*/
        list-style: none;
        float: left;
        margin-right: 20px;

    }

</style>
<body>
<div id="app">
    <ul id="menu">
        <li @click="changeC('index')">home page</li> &nbsp;
        <li @click="changeC('order')" >order</li>
        <li @click="changeC('good')">commodity</li>
    </ul>


    <keep-alive>
        <component :is='who'></component>
    </keep-alive>


</div>

</body>
<script>
    //Three components
    Vue.component('index', {
        template: `
            <div style="overflow:hidden;">
                <h1>Home page content</h1>
            </div>
        `,
    },)
    //Keep the entered order information
    Vue.component('order', {
        template: `
            <div>
                <h1>Order content</h1>
                Please enter the order to query:<input type="text">
            </div>
        `,
    },)
    Vue.component('good', {
        template: `
            <div>
                <h1>Commodity content</h1>
            </div>
        `,
    },)

    var vm = new Vue({
        el: '#app',
        data: {
            //index is displayed by default
            who: 'index'

        },
        methods: {
            changeC(data) {
                this.who = data
            }
        }

    })
</script>
</html>

Tags: Vue

Posted by bluebyyou on Sun, 17 Apr 2022 18:36:22 +0930