简体   繁体   中英

Vue.js won't adhere to multiple instances

I have tried creating a like button for comments using Vue.js. However, the like button only seems to work on one comment (first) while the second comment appears as if it doesn't even recognize Vue.js syntax. Can someone point me in the right direction?

CodePen: http://codepen.io/chrisburton/pen/EVKLxL


 new Vue({ el: '.containComments', data: { liked: false, likesCount: 0 }, methods: { toggleLike: function() { this.liked = ! this.liked; this.liked ? this.likesCount++ : this.likesCount--; } } }); 
 @import url(http://fonts.googleapis.com/css?family=Source+Sans+Pro:200,300,400,200italic,300italic); @import url(https://dl.dropboxusercontent.com/u/26380646/rocknroll/assets/style.css); * {-webkit-box-sizing: border-box;-moz-box-sizing: border-box;-o-box-sizing: border-box;box-sizing: border-box;} a { -webkit-transition: .1s color linear; -moz-transition: .1s color linear; -o-transition: .1s color linear; transition: .1s color linear; } a:hover { -webkit-transition: .25s color linear; -moz-transition: .25s color linear; -o-transition: .25s color linear; transition: .25s color linear; } /* ************************ Project Start ************************ */ html {font-size: 18px;} body { background:; color: #404040; font-family: 'Source Sans Pro', Georgia; font-size: 1em; font-weight: 200; line-height: 1.65; letter-spacing: .01em; margin: 50px 0; padding: 0 25px; } section { max-width: 500px; min-width: 300px; margin: 50px auto; } div.containComments { position: relative; border-bottom: solid 1px rgba(178, 179, 153, .15); margin: 0 auto 50px auto; } div.containComments:last-child { border: none; } p.username { font-weight: 300; margin-bottom: 25px; } p.username a { color: #BFBFA8; text-transform: lowercase; text-decoration: none; } .reply { color: #BFBFA8; cursor: pointer; } p.username a:hover {color: #000;} p.username img.maskable { position: absolute; top: -10px; left: -70px; width: 50px; height: 50px; border-width: 0; border-radius: 100%; } .likesCount, .icon-rocknroll { position: relative; float: right; opacity: 0; } .likesCount { top: 4px; left: 0; font-size: 15px; margin-right: .05em; } .icon-rocknroll { top: 7px; left: 0; background: none; border: 0; outline: none; font-family: "icons"; font-size: 13px; opacity: 0; cursor: pointer; } div.containComments:hover .icon-rocknroll { opacity: .44; } div.containComments:hover .icon-rocknroll:hover, div.containComments:hover .likesCount { opacity: .75; } .active, active:hover, div.containComments:hover .active { opacity: .75; } div.containComments:hover .active:hover { opacity: .44; } p.info { font-size: 18px; margin-bottom: 50px; } code { font-family: "Source Code Pro"; } /* Break */ @media (max-width: 775px) { section {max-width: 400px;} .icon-rocknroll {float: right;} } /* Smartphones Landscape */ @media (max-width: 600px) { section {max-width: 350px;} div.containComments {padding: 0 25px;} img.maskable { position: relative !important; top:0 !important; left: 0 !important; display: inline-block; vertical-align: middle; margin-right: 5px; } .icon-rocknroll { float: right; top: 16px; } .likesCount { top: 12px; } p.info {margin-left: 0;} .closed { width: 280px; } } /* Smartphones Portrait */ @media (max-width: 500px) { body {padding: 0;} section {max-width: 270px;} img.maskable { position: relative !important; top:0 !important; left: 0 !important; display: inline-block; vertical-align: middle; margin-right: 5px; } .icon-rocknroll { float: right; top: 15px; } p.info {margin-left: 0;} .closed { width: 270px; text-align: center; margin: 0 auto 50px auto; } } 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/vue/0.12.14/vue.min.js"></script> <section class="comments"> <div class="containComments"> <p class="username"> <img class="maskable" src="https://en.gravatar.com/userimage/18343163/cf3a7b15b60479a37b2167e84ffb85a6.jpg?size=100" /> <a href="https://twitter.com/chrisburton">chrisburton</a> <button class="icon-rocknroll" v-class="active: liked" v-on="click: toggleLike"></button> <span class="likesCount" v-class="active: liked">{{ likesCount }}</span> </p> <p class="info">Thank you for visiting all the way from New York. This is just a test to determine if the Twitter API is working as it should. You should see your profile image and your username at the very top that links to your account. You should also see that I wrote in a thank you introduction with your location.</p> </div> <div class="containComments"> <p class="username first"> <img class="maskable" src="http://assets.arabiaweddings.com/sites/default/files/news/2014/06/anna.jpg" /> <a href="#">AnnaWintour</a> <button class="icon-rocknroll" v-class="active: liked" v-on="click: toggleLike"></button> <span class="likesCount" v-class="active: liked">{{ likesCount }}</span> </p> <p class="info first"><span class="reply">@chrisburton</span> +1. Really interesting reply.</p> </div> </section> 

You have to create a Vue.component with a template to be able to reuse the code.

Vue.js

Vue.component('like', {
    template: "<button class='icon-rocknroll' v-class='active: liked' v-on='click: toggleLike'></button>\
               <span class='likesCount' v-class='active: liked'>{{ likesCount }}</span>",
    data: function() {
        return {
            liked: false,
            likesCount: 0
        }
    },
    methods: {
        toggleLike: function() {
            this.liked = !this.liked;
            this.liked ? this.likesCount++ : this.likesCount--;
        }
    }
});
new Vue({
    el: '#app',
});

HTML

<like></like>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM