I'm using Vuetify Calendar to display events.
The event time is displayed in am/pm format. But I need them in 24 hour format. I'm trying to display the event details using the event slot.
<v-calendar
ref="calendar"
v-model="value"
locale="en"
color="primary"
type="week"
:events="events"
:event-color="getEventColor"
:event-ripple="false"
#change="getEvents"
#click:event="showEvent"
:weekdays="weekday"
:interval-format="intervalFormat"
>
<template v-slot:event="{ event, timed, eventSummary, }">
<div class="v-event-draggable" v-html="eventSummary()" ></div>
</template>
</v-calendar>
The eventSummary method uses the configured locale to display the time. So instead of using that you could generate the html yourself.
I created the function formatEventTime to format the time in a 24-Hour format.
methods: {
formatEventTime(date) {
return new Date(date).toLocaleTimeString('en-US', {
hour: "2-digit",
minute: "2-digit",
hour12: false
})
}
}
Your calendar component would look like this:
<v-calendar
ref="calendar"
v-model="value"
locale="en"
color="primary"
type="week"
:events="events"
:event-color="getEventColor"
:event-ripple="false"
#change="getEvents"
#click:event="showEvent"
:weekdays="weekday"
:interval-format="intervalFormat"
>
<template v-slot:event="{ event }">
<div class="v-event-draggable">
<strong>{{ event.name }}</strong><br>
{{ formatEventTime(event.start) }} - {{ formatEventTime(event.end) }}
</div>
</template>
</v-calendar>
Related
I have the following template:
<template>
<q-item tag="label" v-ripple>
<q-popup-edit
v-model="editedModel"
#before-show="onFieldClick"
#save="setValue"
:cover="false"
fit
buttons
>
<template v-slot:title>
<div class="text-mono">{{ name }}</div>
</template>
<q-select
dense
autofocus
emit-value
v-model="editedModel"
multiple
:options="options"
counter
/>
</q-popup-edit>
<q-item-section>
<q-item-label class="text-mono">{{ name }}</q-item-label>
<q-item-label caption>{{ description }}</q-item-label>
<q-item-label caption>{{ model }}</q-item-label>
</q-item-section>
</q-item>
</template>
The #save method is never called. What do I miss? Thanks.
For me worked the following:
I added: v-slot="scope" to the q-popup-edit
<q-popup-edit v-model="initialValue" v-slot="scope" buttons #save="save">
and then I replaced my v-model inside q-input to this:
<q-input v-model="scope.value" >
I have a multiple selection Vue component that feeds items to display in an input box. As of now, it adds items based on the order of selection, but I wanted to template it to sort by sort_order after selection (objective_id, category_id, objective_code, objective_description, disabled_flag, sort_order are all passed into objectiveArray object). Is this possible to do in Vuetify?
<v-flex xs12>
<v-tooltip :disabled="!showTooltip" top>
<v-select
slot="activator"
class="objective-select"
v-model="record.objectives"
:items="objectiveArray"
label="Objective(s)"
placeholder="Enter Objective(s)"
:error-messages="objectiveErrors"
:return-object="true"
item-text="objectiveDescription"
multiple
#blur="v.$each[index].objectives.$touch()">
<template v-slot:selection="{ item, index }">
<v-chip
color="primary"
dark
class="objective-chip"
:class="{
mobile:isMobile,
tablet:isTablet
}">
<span>{{ item.objectiveDescription }}</span>
</v-chip>
</template>
</v-select>
<span>Select one or more procedure objective(s)</span>
</v-tooltip>
</v-flex>
You can sort your bound v-model after the #input event fires. Here is a simple example:
<template>
<div>
<v-select
v-model="selected"
:items="items"
item-text="id"
item-value="id"
multiple
#input="sortSelection"
return-object
>
</v-select>
</div>
</template>
<script>
export default {
data: () => ({
selected: [],
items: [{id:1},{id:2},{id:3},{id:4},{id:5},{id:6}]
}),
methods: {
sortSelection() {
this.selected.sort((x, y) => {
if (x.id > y.id) return 1
else if (y.id > x.id) return -1
else return 0
})
}
}
}
</script>
As long as your sort_order is a number you can just substitute it for the id field in my example.
I've form.blade.php file , here's it's content
<app-add-new-file-form inline-template :subjects="{{ json_encode($subjects) }}">
<v-form method="POST" action=" {{ route('files.store') }} " enctype="multipart/form-data">
#csrf
<div class="my-8">
<v-select v-model="subject" :items="subjects" :item-value="subject" name="subject" menu-props="auto"
label="Subject" hide-details single-line></v-select>
<p class="text-danger">{{ $errors->first('subject') }}</p>
</div>
</v-form>
</app-add-new-file-form>
and in my vue components I've this code below :
<script>
export default {
props: ["subjects"],
data: () => {
return {
subject: "",
};
}
};
</script>
However, when i submit the form, the subject value is set to null on any subject I select
Note : the subjects array comes from laravel then I encode it to json.
It is stated that Vuetify v-select does not have an input value. Longer answer by Vuetify dev here. They are just not setting the value to input.
The solution would be to add a hidden input that keeps the selected value and is submitted with form.
Example codepen
new Vue({
el: '#app',
vuetify: new Vuetify(),
data: () => ({
subjects: ['Subject1', 'Subject2', 'Subject3', 'Subject4'],
selectedSubject: ''
}),
})
<div id="app">
<v-app id="inspire">
<v-container fluid>
<v-row align="center">
<v-col class="d-flex" cols="12" sm="6">
<v-select
v-model="selectedSubject"
:items="subjects"
label="Subjects"
solo
></v-select>
<input type="hidden" v-model="selectedSubject" name="subject">
</v-col>
</v-row>
</v-container>
</v-app>
</div>
I included an example image where to find input value from devtools. If you check v-select input value, it is empty. Then of you check the hidden inputs value it has the selected value.
Example image where to find input value
Im using laravel, vue, and bootstrap-vue.
I have created a vue component that displays a table of elements (subnets in this example).
For each of them I show a component (modal_edit-subnet) thats should open a modal that allows to edit the data of the element of the related row.
The problem is that it shows modals for all of the table elements. For example, if the table has 3 rows, it shows 3 modals (after closing one it shows the next). Each of the modals with the data of each of the rows.
I've tried to add "key"s but no success.
What am i doing wrong?
Thanks!
Component that shows the table
<template>
<div>
<b-card class="text-center">
<b-table small striped hover :items="data_subnets" :fields="fields" :tbody-tr-class="rowClass">
<template slot="[ip_address]" slot-scope="data_subnets">
<b>{{ long2ip(data_subnets.item.ip_address) }}</b>
</template>
<template slot="[actions]" slot-scope="data_subnets">
v-on:deleteSubnet="deleteSubnet"></modal_delete-subnet>
<modal_edit-subnet :key="'modal_edit_subnet' + data_subnets.item.id" :subnet="data_subnets.item" v-on:editSubnet="editSubnet"></modal_edit-subnet>
</template>
</b-table>
</b-card>
</div>
</template>
Modal modal_edit-subnet
<template>
<div>
<b-button size="sm" v-b-modal.modal-edit-subnet>Edit</b-button>
<b-modal
id="modal-edit-subnet"
ref="modal"
title="Edit subnet"
#ok="handleOk"
>
This is subnet {{data_subnet.id}}
</b-modal>
</div>
</template>
The problem is that:
You're rendering a modal for each row of the table and;
Reading the docs, it seems like the modal is triggered by the id, and your b-modal id is not dynamic depending on the row.
How to fix it:
Use just one modal on the b-table level
Dynamically inject id into your modal_edit-subnet component:
<template>
<div>
<b-button size="sm" v-b-modal[id]>Edit</b-button>
<b-modal
:id="id"
ref="modal"
title="Edit subnet"
#ok="handleOk"
>
This is subnet {{data_subnet.id}}
</b-modal>
</div>
</template>
<script>
export default {
props: {
id: {
type: String | Number
}
}
}
</script>
Use v-model (this is the way I would do it)
<template>
<div>
<b-button size="sm" #click="show = true">Edit</b-button>
<b-modal
v-model="show"
ref="modal"
title="Edit subnet"
#ok="handleOk"
>
This is subnet {{data_subnet.id}}
</b-modal>
</div>
</template>
<script>
export default {
data() {
return {
show: false
}
}
}
</script>
VueJS markup:
<v-menu
lazy
:close-on-content-click="false"
v-model="modal"
transition="scale-transition"
offset-y
full-width
:nudge-right="40"
max-width="290px"
min-width="290px">
<v-text-field
slot="activator"
label="Issue Date"
v-model="date"
append-icon="event"
readonly
>
</v-text-field>
<v-date-picker v-model="date" no-title scrollable actions>
<template scope="{ save, cancel }">
<v-card-actions>
<v-spacer></v-spacer>
<v-btn flat color="primary" #click="cancel">Cancel</v-btn>
<v-btn flat color="primary" #click="save">OK</v-btn>
</v-card-actions>
</template>
</v-date-picker>
</v-menu>
HTML:
`<div class="menu__activator">
<div data-v-386ef34c="" class="input-group input-group--dirty input-group--append-icon input-group--text-field">
<label>Issue Date</label>
<div class="input-group__input">
<input readonly="readonly" tabindex="0" aria-label="Issue Date" type="text">
<i aria-hidden="true" class="material-icons icon input-group__append-icon input-group__icon-cb">event</i>
</div>
<div class="input-group__details">
<div class="input-group__messages"></div>
</div>
</div>
</div>`
How it appears in browser:
I'd like to write e2e to assert some logic with the calendar date. Date is produced with moment to match current day. However I cannot figure out how to access that text value with xpath.
Xpath to get the element:
$x('//div[contains(#class, "input-group--text-field")]//input[#readonly]')
How the element appears in developer console:
With the attribute I need at the very bottom:
Xpaths I've tried which result in empty array:
$x('//div[contains(#class, "input-group--text-field")]//input[#readonly]//#value')
$x('//div[contains(#class, "input-group--text-field")]//input[#readonly]/#value')
$x('//div[contains(#class, "input-group--text-field")]//input[#readonly][0]//#value')
Edit:
Managed to get the value in chrome console:
$x('//div[contains(#class, "input-group--text-field")]//input[#aria-label="Issue Date"]')[0].value
But still struggling with Nightwatch
Any solutions with xpath or css are welcome! Thanks!
Had to import chai, but this finally worked:
.getValue('//div[contains(#class, "input-group--text-field")]//input[#aria-label="Issue Date"]', function(result) {
expect(result.value).to.equal('2017-10-17')
})