I've a project in which I've a datatable.vue which is looping through a data and showing some data table, have some button like edit, delete. What I want to achieve is in that loop, use a reusable dialog component, which will load and upon confirmation, trigger itemDelete method. the DialogComponent is vuetifiy (v-dialog).
<template v-slot:item.action="{ item }">
<v-btn icon color="blue" :to="{ path: updatePath, query: { id: item.id } }">
<v-icon small>mdi-pencil</v-icon>
</v-btn>
<v-btn icon color="red" #click="$emit('deleteItem', item)">
<v-icon small>mdi-delete</v-icon>
</v-btn>
</template>
this is current code of datatable, and has method deleteItem which deletes the item, I want to modify this and add reusable dialogbox (ill use this dialogbox later in other places), which will have confirmation of delete and triggers itemDelete method here.
on Vueitfy, I got this.
<v-dialog
v-model="dialog"
width="500"
>
<template v-slot:activator="{ on, attrs }">
<v-btn
color="red lighten-2"
dark
v-bind="attrs"
v-on="on"
>
Click Me
</v-btn>
</template>
<v-card>
<v-card-title
class="headline grey lighten-2"
primary-title
>
Confirmation
</v-card-title>
<v-card-text>
Are you sure?
</v-card-text>
<v-divider></v-divider>
<v-card-actions>
<v-spacer></v-spacer>
<v-btn
color="primary"
text
#click="dialog = false"
>
Confirm
</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
and I made component DialogBox of it, I'm new to Vue. Thanks
There is better way to do this:
write this in your item.action slot:
<template v-slot:item.action="{ item }">
<v-btn icon color="blue" :to="{ path: updatePath, query: { id: item.id } }">
<v-icon small>mdi-pencil</v-icon>
</v-btn>
<v-dialog v-model="dialog" width="500">
<template v-slot:activator="{ on, attrs }">
<v-btn
color="red lighten-2"
dark
icon
v-bind="attrs"
v-on="on"
>
<v-icon small>mdi-delete</v-icon>
</v-btn>
</template>
<v-card>
<v-card-title
class="headline grey lighten-2"
primary-title
>
Confirmation
</v-card-title>
<v-card-text>
Are you sure?
</v-card-text>
<v-divider></v-divider>
<v-card-actions>
<v-spacer></v-spacer>
<v-btn
color="primary"
text
#click="deleteItem(item)"
>
Confirm
</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
</template>
and create the deleteItem method:
method:{
createItem(item){
this.$emit('deleteItem', item);
this.dialog = false;
}
}
Related
I'm using v-slot:activator with v-btn in my Vuejs project. it works fine but the button stays hovered as if it was pressed
<v-dialog v-model="dialog" max-width="600px">
<template v-slot:activator="{ on, attrs }">
<v-btn color="#F65C38" dark class="mt-1 mr-2" width="209px" v-on="on" v-bind="attrs"> Example Btn </v-btn>
</template>
<v-card>
<v-card-title>
<span class="text-h5">{{ formTitle }}</span>
</v-card-title>
<v-card-text>
<v-form ref="form" v-model="valid">
<v-container>
<v-row>
</v-row>
</v-container>
</v-form>
</v-card-text>
<v-card-actions class="d-flex justify-center">
<v-btn color="#f66037" plain #click="close" elevation="4" dark width="209" class="mb-6"> No </v-btn>
<v-btn color="#F65C38" #click="save" dark width="209" class="mb-6"> save </v-btn>
</v-card-actions>
</v-card>
</v-dialog>
data:
dialog: false
watch:
dialog(val) {
val || this.close();
},
method:
close() {
this.dialog = false;
this.$nextTick(() => {
this.editedItem = Object.assign({}, this.defaultItem);
this.editedIndex = -1;
});
before click
after click
You can remove focus manually using native JS method:
document.activeElement.blur()
In your example you can place this row into $nextTick:
...
close() {
this.dialog = false;
this.$nextTick(() => {
this.editedItem = Object.assign({}, this.defaultItem);
this.editedIndex = -1;
document.activeElement.blur()
});
},
Test this at CodePen.
My tooltip doesn't work with my Custom Component. I wrap a Dialog in a Component and I want to add a tooltip.
My Vue.js version is 2.5.17 and Vuetify 2.1.15
Componant A :
<v-tooltip bottom>
<template v-slot:activator="{ on }" v-slot:item={item}>
<ComponentB v-on="on">
</ComponentB>
</template>
<span>Hello world!</span>
</v-tooltip>
Component B:
<template>
<v-dialog v-model="dialog" persistent max-width="800px">
<template v-slot:activator="{ on }">
<v-icon small v-on="on">
add_comment
</v-icon>
</template>
<v-card>
<v-card-title>
<span class="headline">Title</span>
<v-spacer></v-spacer>
<v-btn icon #click="dialog = false">
<v-icon>mdi-close</v-icon>
</v-btn>
</v-card-title>
<v-card-text class="pb-0">
Hello world!
</v-card-text>
<v-card-actions>
<v-spacer></v-spacer>
<v-btn
color="primary"
text
#click="dialog = false"
>
I accept
</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
</template>
I am beginner in VueJs, so may someone can help me :)
I would personally just move the tooltip into the child component, since it is technically part of the child component anyway. I did the best I could with the example code below, given the limited amount of code you provided in your question. Hopefully this helps!
<!-- Component A (Parent) -->
<template>
<ComponentB :item="item" />
</template>
<!-- Component B (Child) -->
<template>
<v-dialog v-model="dialog" persistent max-width="800px">
<v-tooltip bottom>
<template v-slot:activator="{ on }" v-slot:item="item">
<v-icon small v-on="on">
add_comment
</v-icon>
</template>
<span>Hello world!</span>
</v-tooltip>
<v-card>
<v-card-title>
<span class="headline">Title</span>
<v-spacer></v-spacer>
<v-btn icon #click="dialog = false">
<v-icon>mdi-close</v-icon>
</v-btn>
</v-card-title>
<v-card-text class="pb-0">
Hello world!
</v-card-text>
<v-card-actions>
<v-spacer></v-spacer>
<v-btn
color="primary"
text
#click="dialog = false"
>
I accept
</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
</template>
<script>
export default {
props: {
item: {
type: Object,
default() {
return {};
}
}
}
};
</script>
I made a table component in my project as I have multiple tables that I want to all look the same.
I insert my table onto my page and everything is working fine.
On the table is a dialog which opens correctly but inside that dialog is another one of my table components and this does not render.
It will work if I change the name of the component and have two separate instances but that is not what I am trying to do.
How can I get my table working across all components? Using Vue CLI.
Table component:
<template>
<v-data-table :headers="headers" :items="items" :no-data-text="noDataText" :dark="dark">
<template v-slot:top>
<v-toolbar :dark="dark" flat>
<v-toolbar-title>{{ title }}</v-toolbar-title>
<v-divider class="mx-4" inset vertical></v-divider>
<v-spacer></v-spacer>
<v-btn #click="dialog=true" color="success" class="mr-2">
Load Default Frames
<v-icon right>mdi-download</v-icon>
</v-btn>
<v-btn color="primary" class="mr-2">
Create New Frame
<v-icon right>mdi-image-plus</v-icon>
</v-btn>
<Dialog v-model="dialog" />
<!-- <Frame v-model="dialog" :editedFrame="editedFrame" :oldIndex="oldIndex" #close="close" />
<DefaultFrames v-model="defaultFramesDialog" :selectable="true" :items="defaultFrames" />-->
</v-toolbar>
</template>
</v-data-table>
</template>
Dialog component:
<template>
<v-dialog v-model="dialog">
<v-card :dark="dark">
<v-card-title>
{{ name}}
<v-divider class="mx-4" inset vertical></v-divider>
<v-spacer></v-spacer>
<v-btn icon #click="dialog = false">
<!-- <v-icon #click="$emit('close')">mdi-close</v-icon> -->
</v-btn>
</v-card-title>
<Table :is="child_component" :headers="frameHeaders" :items="defaultFrames" />
<v-card-actions>
<v-btn #click="log">Log</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
</template>
Table.vue
<template>
<v-btn #click.stop="emitOpenDialog">Open Dialog</v-btn>
</template>
<script>
export default {
methods: {
emitOpenDialog() {
// I've use vueBus for emiting
this.$bus.emit("open-dialog")
}
}
}
</script>
Dialog.vue
<template>
<v-dialog v-model="dialog"> ... </v-dialog>
</template>
<script>
export default {
data: () => ({
dialog: false
},
created() {
this.$bus.on("open-dialog", this.openDialog)
},
beforeUnmount() {
this.$bus.off("open-dialog")
},
methods: {
openDialog() {
this.dialog = true
}
}
}
Go to https://vuetifyjs.com/en/components/toolbars
On the top left toolbar we see links: store, support, ecosystem, version, locate
How do I create this style of toolbar button link (with dropdown items)?
(I am unable to find an example)
It's a simple plain menu component.
Click on the example button (dropdown) and on "support"
and you will see, that they behave the same.
If you inspect the "support" button with your browser (Firefox, Chrome Shortcut F12 for both),
you can see thats a "v-menu"(menu component) and you can see the CSS used for it.
<template>
<div>
<v-toolbar rounded tile>
<v-app-bar-nav-icon> </v-app-bar-nav-icon>
<v-app-bar-title>
<route-link to="/" tag style="cursor:pointer">ProjectName</route-link>
</v-app-bar-title>
<v-spacer></v-spacer>
<v-toolbar-items>
<v-btn flat to="/">
Home
</v-btn>
<v-menu :rounded="rounded" open-on-hover offset-y transition="slide-x-transition" bottom right>
<template v-slot:activator="{ on, attrs }">
<v-btn flat v-bind="attrs" v-on="on">
Services
</v-btn>
</template>
<v-list dense>
<v-list-item v-for="(item, index) in services" :key="index" router :to="item.link">
<v-list-item-action>
<v-list-item-title>{{ item.title }}</v-list-item-title>
</v-list-item-action>
</v-list-item>
</v-list>
</v-menu>
<v-btn to="/about" flat>
About Us
</v-btn>
<v-btn to="/contact" flat>
Contact Us
</v-btn>
</v-toolbar-items>
<v-spacer></v-spacer>
<v-toolbar-items class="hidden-sm-and-down">
<v-btn to="/signup" flat>Sign Up </v-btn>
<v-btn to="/login" flat>login</v-btn>
</v-toolbar-items>
<v-menu open-on-hover transition="slide-x-transition" bottom right offset-y>
<template v-slot:activator="{ on, attrs }">
<v-btn icon v-bind="attrs" v-on="on">
<v-icon>mdi-dots-vertical</v-icon>
</v-btn>
</template>
<v-card class="mx-auto" max-width="300" tile>
<v-list dense>
<v-subheader>THEMES</v-subheader>
<v-list-item-group v-model="theme" color="primary">
<v-list-item v-for="(item, i) in themes" :key="i" router :to="item.link">
<v-list-item-action>
<v-icon v-text="item.icon"></v-icon>
</v-list-item-action>
<v-list-item-action>
<v-list-item-title v-text="item.text"></v-list-item-title>
</v-list-item-action>
</v-list-item>
</v-list-item-group>
</v-list>
</v-card>
</v-menu>
</v-toolbar>
</div>
</template>
<script>
export default {
data: () => ({
activate: true,
theme: 1,
themes: [{
text: "Dark",
icon: "mdi-clock"
},
{
text: "Light",
icon: "mdi-account"
}
],
mini: true,
services: [{
icon: "mdi-domain",
title: "Media Monitoring",
link: "/mmrservices"
},
{
icon: "mdi-message-text",
title: "Audience Measurement",
link: "/amrservices"
},
{
icon: "mdi-flag",
title: "Integration Analysis"
}
]
})
};
</script>
I am using Vuetify framework for VueJS and I am trying to recreate the Data table edit dialog but instead of static values, I want the edit dialog to be dynamic (User can specify editable fields).
The problem is that I can't use the key I get from v-for for v-model like this.
<v-dialog v-model="dialog" max-width="500px">
<v-card>
<v-card-title>
<span class="headline">Edit Item</span>
</v-card-title>
<v-card-text>
<v-container grid-list-md>
<v-layout wrap>
<v-flex xs12 sm6 md4 v-for="(item, key, index) in editable_fields">
{{key}}
<h1>{{editedItem}}</h1>
<v-text-field v-model="editedItem.key" :label="key"></v-text-field>
</v-flex>
</v-layout>
</v-container>
</v-card-text>
<v-card-actions>
<v-spacer></v-spacer>
<v-btn color="blue darken-1" flat #click.native="close">Cancel</v-btn>
<v-btn color="blue darken-1" flat #click.native="save_edit">Save</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
And these are my props and data:
props: {
editable_fields: {
type: Object
default: ()=> {name: '', email: ''}
}
}
data: ->
editedItem = #editable_fields
return {editedItem: editedItem}
So the question is how should I approach to this?