Reputation: 173
I'm still quite new to vuejs and was watching one of many videos online to teach myself, when a question came to my mind.
With vuetify I build a navigation drawer that is looping (v-for) through a list of menu items and printing the details of the items with v-if.
Now for the question I have:
In vuejs, is there a way to bind a method from vues 'methods' like singOut()
to an @click
by passing the method with a variable.
@click="item.method"
and @click="{item.method}"
didn't work for me.
Clearification: There could be more methods than singOut()
I would want to bind to @click
. Because of that I'm looking for a more dynamic way to bind the method.
Thanks in advance :)
new Vue({
el: '#app',
data: {
items: [
{ icon: "lightbulb_outline", text: "Notes", path: '/tools/notes' },
{ icon: "access_alarm", text: "Worktime", path: '/tools/worktime' },
{ divider: true },
{ heading: "Labels" },
{ icon: "add", text: "Create new label" },
{ divider: true },
{ heading: "Account" },
{ icon: "lock_open", text: "Login", path: '/signin' },
{ icon: "mdi-account-plus", text: "Sign Up", path: '/signup' },
{ icon: "mdi-logout", text: "Sign Out", method: 'singOut()' },
{ divider: true },
{ icon: "settings", text: "Settings", path: '/' },
{ icon: "chat_bubble", text: "Trash", path: '/' },
{ icon: "help", text: "Help", method: 'sendAlert("Really want to delete?")' },
{ icon: "phonelink", text: "App downloads", method: 'sendAlert("Leaving the app")' },
{ icon: "keyboard", text: "Keyboard shortcuts", path: '/' }
]
},
methods: {
navigateTo(path) {
if (path) {
this.$router.push(path);
} else {
this.$router.push('/');
}
},
singOut(){
this.$store.dispatch('singOut');
},
sendAlert(msg) {
alert(msg);
}
}
});
ul {
list-style: none;
}
<script src="https://unpkg.com/vue/dist/vue.js"></script>
<div id="app">
<ul>
<li v-for="(item,i) in items">
<span v-if="item.heading" :key="i"><b>{{item.heading}}</b></span>
<span v-else-if="item.divider" :key="i">--------</span>
<span v-else-if="item.method" @click="item.method" :key="i" style="cursor:pointer;">{{item.text}} (+ @click->Method)</span>
<span v-else> {{item.text}} -> {{item.path}}</span>
</li>
</ul>
</div>
Upvotes: 2
Views: 1389
Reputation: 19022
Split method in method-name and argument properties.
You can create for example call
method which calls passed function with passed arguments @click="call(item.method, item.args)"
.
<v-btn v-for="item in items" :key="item.id" @click="call(item.method, item.args)">
{{item.text}}
</v-btn>
items: [
...
{ id: 5, text: "5", method: "methodTwo", args: ["Another message", 123] },
methods: {
call(method, args = []) {
this[method](...args)
},
Make custom assertions as needed.
Any flaw in this approach?
Upvotes: 2
Reputation: 3756
Since you already have singOut()
in your methods: {}
, in your html for @click
, just use @click="singOut(item.method)"
Your singOut()
must be able to accept the params.
singOut(method) {
// method here
console.log(method)
}
I think this is not what you want to achieve because your method in the object consists of functions.
Using your current data:
items: [
{ icon: 'help', text: 'Help', method: 'Some method here', alert: 'Really want to delete?' }
]
What I suggest you could do is
alert
and set the string to it.@click
event to a method with the item as the params; use that method to trigger an alert()
with the alert
property value in it.Example:
singOut(item) {
// handle the alert if it exists
if (item.alert) {
this.sendAlert(item.alert)
}
// handle the method value
console.log(item.method)
}
Upvotes: 0