How to implement “Clear” button in vue2-daterange-picker? - vuejs2

Looking at vue2-daterange-picker examples at
https://innologica.github.io/vue2-daterange-picker/#usage
I wonder how it is implemented with Clear button?
I need to make such button and empty values as default values (not 1 Jan 1970).

This worked for me:
Your button needs to update the dateRange object or rather 'reset' it to the default in this case.
Button
<button class="btn btn-info" #click="clearDate()" type="button"> Clear </button>
Methods
methods:{
clearDate() {
this.dateRange.startDate = null;
this.dateRange.endDate = null;
},
}
I am new to all this stuff, and I realise my response is some months after the question, but I hope that it helps.

Related

In Vue, how to get the content of a textarea?

I want to keep the value of a variable identical with the content of a textarea.
I don't want to use v-bind or v-model, because I have already bound the textarea with another value.
This is a notebook app, and the textarea is used to display the content of a note, so it has been bound using v-bind with a note object, like
<textarea cols="30" rows="3" v-bind:value="note"></textarea>
Now, I want to add the "edit note" functionality. So when the content of the textarea changes, I want to store its value into a variable, and when the "submit" button is clicked, I pass the value of the variable, which contains the new content of the note, to backend to update the note.
My question is, how to store the textarea's content into the variable after each time the content changes?
I think I cannot use v-model because this way the note will be changed right after the content of the textarea is modified (though not sent to backend), but this is not what I want. What I want is the note to be changed only after the "submit" button is clicked. Thus, I cannot use v-model
Should I use v-on:change? If so, how to get the content of the textarea?
Like,
<textarea v-on:change="updateTheVariable(I need to get the content of the textarea here)"> ... </textarea>
methods: {
updateTheVariable(content of the textarea) {
this.variable = content of the textarea
}
}
Thanks
I'm assuming this thing only shows up when you click some kind of edit button which is why you don't want to alter note so try something like this instead
<button type="button" v-if="!editMode" #click="editNote">Edit</button>
<form v-if="editMode" #submit="handleSubmit">
<fieldset :disabled="saving">
<textarea v-model="editingNote"></textarea>
<button type="submit">Edit</button>
</fieldset>
</form>
export default {
data: () => ({
note: 'whatever', // maybe it's a prop, maybe assigned later, doesn't matter
editMode: false,
editingNote: null, // this will be used to bind the edited value
saving: false
}),
methods: {
editNote () {
this.editingNote = this.note
this.editMode = true
this.saving = false
},
async handleSubmit () {
this.saving = true // disables form inputs and buttons
await axios.post('/notes/update', { note: this.editingNote}) // just an example
this.note = this.editingNote // or maybe use data from the response ¯\_(ツ)_/¯
// or if it's a prop, this.$emit('updated', this.editingNote)
this.editMode = false
}
}
}
As #Phil indicated in a deleted post, the right way to do it is
<textarea #input="updateTheVariable($event.target.value)"></textarea>
.
.
.
methods:{
updateTheVariable(value){
this.variable = value
}
}

VUEJS Check if user liked post

I want to check if user is already like the post. I get an array with users who liked the post but I don't know how to hide button if logged in username exists in the likes array. Heres the code part:
<span v-for="like in b.likes">
{{like}} // {"username": "Gohanas" } { "username": "Zlotte" }
</span>
<button class="likeButton" #click="like(b._id)">LIKE</button>
Since Zlotte exists in here I want to hide LIKE button. How can I do that ?
Here is an example for this, just replace the Zlotte with current use username:
<button
v-if="!b.likes.find(u => u.username === 'Zlotte')"
class="likeButton"
#click="like(b._id)"
>
LIKE
</button>
I think the best way to solve this is by creating a computed with this code in it:
return b.likes.filter(({ username }) => username === <here the variable for the current username>).length;
More readable variant:
return b.likes.filter((like) => {
return like.username === <here the variable for the current username>;
}).length;
I'm not sure of the structure of b, so I'm not sure if you have the current users' name available in there.
If you have added the computed, you can use it in the template to v-if or v-show the button:
<button class="likeButton" #click="like(b._id)" v-if="<name of the computed here>">LIKE</button>

Vue v-model input change mobile chrome not work

If i open https://v2.vuejs.org/v2/guide/forms.html#Text and edit text - no effect on typing text in mobile chrome. #keyup #input #keypress - v-model does not change when I'm typing
<input v-model="message" #keyup="log" placeholder="Edit">
<p>Edited: {{ message }}</p>
How can i fix it? I need get input value on typing (#keyup #input)
Update: After a lot of discussion, I've come to understand that this is a feature, not a bug. v-model is more complicated than you might at first think, and a mobile 'keyboard' is more complicated than a keyboard. This behaviour can surprise, but it's not wrong. Code your #input separately if you want something else.
Houston we might have a problem. Vue does not seem to be doing what it says on the tin. V-model is supposed to update on input, but if we decompose the v-model and code the #input explicitly, it works fine on mobile. (both inputs behave normally in chrome desktop)
For display on mobiles, the issue can be seen at...
https://jsbin.com/juzakis/1
See this github issue.
function doIt(){
var vm = new Vue({
el : '#vueRoot',
data : {message : '',message1 : ''}
})
}
doIt();
<script src="https://cdn.jsdelivr.net/npm/vue#2.5.16/dist/vue.js"></script>
<div id='vueRoot'>
<h1>v-model</h1>
<div>
<input type='text'
v-model='message'
>
{{message}}
</div>
<h1>Decomposed</h1>
<div>
<input type='text'
:value='message1'
#input='evt=>message1=evt.target.value'
>
{{message1}}
</div>
</div>
I tried all solutions I could find on the internet, nothing worked for me. in the end i came up with this, finally works on android!
Trick is to use compositionupdate event:
<input type="text" ... v-model="myinputbox" #compositionupdate="compositionUpdate($event)">
......
......
methods: {
compositionUpdate: function(event)
{
this.myinputbox = event.data;
},
}
Ok, I dont know if there is another solution for this issue, but it can be solved with a simple directive:
Vue.directive('$model', {
bind: function (el, binding, vnode) {
el.oninput = () => (vnode.context[binding.expression] = el.value)
}
})
using it just like
<input v-$model="{toBind}">
There is an issue on the oficial repo, and they say this is the normal behavior (because the composition mode), but I still need the functionality
EDIT: A simpler solution for me was to just use #input.native. Also, the this event has (now?) a isComposing attribute which we can use to either take $event.data into account, or $event.target.value
In my case, the only scheme that worked was handling #keydown to save the value before the user action, and handling #keyup to process the event if the value had changed. NOTE: the disadvantage of this is that any non-keyboard input (like copy/paste with a mouse) will not work.
<md-input
v-else
:value="myValue"
ref="input"
#keydown="keyDownValue = $event.target.value"
#keyup="handleKeyUp($event)"
#blur="handleBlur()"
/>
With handleKeyUp in my case being:
handleKeyUp(evt){
if(evt.target.value !== this.keyDownValue){
this.$emit('edited', evt);
}
}
My use case was the following:
I requested a search endpoint in the backend to get suggestions as the user typed. Solutions like handling #compositionupdate lead to sending several several requests to the backend (I also needed #input for non-mobile devices). I reduced the number of requests sent by correctly handling #compositionStarted, but there was still cases where 2 requests were sent for just 1 character typed (when composition was left then, e.g. with space character, then re-entered, e.g. with backspace character).

KnockoutJs + DataTables Server side binding + ButtonEvent

I have a KnockoutJs and DataTables project. All data is coming server-side.
My Question is this:
In one column we have a button with a data-bind="click: someFunction"
Obviously this is not getting called because the page is already bound before the grid is loaded. Fair enough. Inside the table definition I override the "fnDrawCallback" function and add this code
self.addButtonEventsToGridRow(self, $("#tableDomId #buttonId"));
and the function looks like this
self.addButtonEventsToGridRow = function (model, element) {
for (var i = 0; i < element.length; i++) {
ko.cleanNode(element[i]);
ko.applyBindings(model, element[i]);
}
};
I have to do this for every button. (Obviously that in itself is ugly)
"<button type='button' id='buttonId' class='btn btn-primary btn-xs' data-bind='click: someFunction'>ButtonText</button>"
However, now the event DOES fire. I can prove this
self.someFunction = function(data) {
console.log(data);
}
Here is the problem. The "data" object passed in seems to be the entire viewmodel, not the actual row data.
I feel my solution in itself is a failure, but I cannot find a proper way to make this work.
I am open to either modifying my solution, or if someone can point me to the proper way this is supposed to work I would greatly appreciate it.
FYI, here is my UGLY workaround for this issue inside the "render" overdide for the particular column. Note if I
"<button type='button' id='buttonId' class='btn btn-primary btn-xs' data-bind='click: function(){ return someFunction(" + fulldata + ");}'>ButtonText</button>" +

Get data from child tag in riot.js

I want to create a tag like this
<mytag>
<p class={ hide: doEdit }>
<a class="icon1" onmousedown={ startEdit }></a>
<input type="text" value={ opts.value } readonly/>
</p>
<p class={ hide: !doEdit }>
<a class="icon2 onmousedown={ endEdit }></a>
<input name="editfield" type="text" value={ opts.value }/>
</p>
this.doEdit = false
startEdit(e){
this.doEdit = true
this.update()
}
endEdit(e){
this.doEdit = false
opts.value = this.editfield.value // this does not change opts.value, unfortunately
this.update()
}
</mytag>
If it would have worked, i could have used it like
var mydatamodel = {"input1":"email","input2":"name"}
<mytag value={ mydatamodel.input1 }></mytag>
<mytag value={ mydatamodel.input2 }></mytag>
Unfortunately, this does not seem to work. mydatamodel.xy does not get updated, i cannot assign a new value to opts.value (there is no exception, opts.value simply won't change its value).
What would a good way be to update the parents model according to the new values of the "editfield" in the children?
It is possible to access the data using this.mytag[i].editfield. But this is no good solution for larger forms.
I also tried using a custom event and trigger it in the child tag. However, i did not yet find a proper generic solution to update the model in the parent tag. This approach led to something clumsy as the "this.mytag[i].editfield"-way.
Is there a method to create the child tags in such a way that it is possible to write
<mytag value={ mydatamodel.input1 }></mytag>
where mydatamodel.input1 is updated as soon as it changes in the child tag?
Thanks for your thoughts.
Set the callback through an attribute:
<my-tag
title={ globalModel.input1.title }
val={ globalModel.input1.val }
onendedit={ endEdit1 }></my-tag>
Then send back the value through callback.
endEdit (e) {
this.doEdit = false
if (opts.onendedit)
opts.onendedit(this.editfield.value)
}
It seems better to add an outer tag. See detail on plunkr
You may have an interest on RiotControll, too. This is a kind of Flux solution for Riot.js, FYI.
Update: rewrote the answer after the information via comment.