v-model depending on conditions [duplicate] - javascript

I have a vue component that shows a form populated with items from a selected item to edit. Now I don't want to have to use a second form for creating a new item. At the moment I auto populate and update the item with v-model which obviously updates the object. Am I not able to use conditional operators in this like so?
<form #submit.prevent>
<div class="field">
<label class="label">Job Title</label>
<p class="control">
<input type="text" class="input" placeholder="Job title" v-model="experiences[editIndex].title ? experiences[editIndex].title : ''" />
</p>
</div>
</form>

You can use conditional operators with v-model, but you can't give v-model a string like you're attempting in your example.
I wouldn't use the same form for editing and creating (might be preference). I would make the form its own component and then make two additional form components for editing and creating.
However, if you really want to handle the logic in each input's v-model directive, you would need to give it a variable in the last part of the ternary operator. Something like this:
v-model="experiences[i].title ? experiences[i].title : newExperience.title"

If you use eslint-plugin-vue it will complain about ternary in v-model.
ESLint: 'v-model' directives require the attribute value which is
valid as LHS. (vue/valid-v-model)
So I'd rather explicitly use a pair of :value and #input props.
Like that:
<input
type="text"
class="input"
placeholder="Job title"
:value="experiences[editIndex].title ? experiences[editIndex].title : ''"
#input="experiences[editIndex].title = $event.target.value"
/>
Also, you can use some function for #input, which will check property existence and add it if necessary.

Related

How to include form field attributes based on state in React?

I am trying to make an accessible form in React and I need to toggle the attribute aria-describedby based on the state of the field (i.e., if it has an error associated with it).
I know how to toggle the value of the attribute, but with regards to WCAG, a present but empty attribute of this type will fail. The entire attribute needs to be fully present or fully absent. Anything I try in-line throws errors and breaks the render.
To give an example, this is what I've been trying:
<label>
<input type="text" name="someName" ref="someRef" {!this.state.isValid ? aria-describedby="helperText" : ''} required />
<p id="helperText">Helper text for this form field.</p>
</label>
Again though, an empty attribute value for aria-describedby is invalid.
Is there any way to acheive this?
Just spread it like this:
<input type="text"
name="someName"
ref="someRef"
{... !this.state.isValid && {'aria-describedby': 'helperText'} }
required />
This is basically spread operator usage.

v-model in dynamic component

I have a list of dynamic components that I render with a for loop.
<component
v-for="component in components"
:key="component.componentId"
:is="component.type"
:componentId="component.componentId">
</component>
One of the different component types is an element that contains an input field. I want to attach v-model to that input.
<input type="text" :name="name">
works but when I do
<input type="text" :name="name" v-model="value">
I get no errors but the component is not rendered. However
<input type="text" :name="name" :value="value" #input="setValue">
works, if used with an appropriate method setValue to update the value attribute.
How should I use v-model in the component?
Apparently dynamic type bindings don't work with v-model. Found a commit in the repository that confirms this. For some reason it doesn't give me the warning, even though process.env.NODE_ENV == undefined.
In the original question I stripped a lot of code to make it more readable but seems like I missed the important part.

How to check if form field is touched and empty in Angular

I want to warn the user if the form field is touched and left empty. I can check if the empty field is touched with $pristine. But if I preload form data from $scope, $pristine doesn't work. Also, I don't want to use required parameter, I only want to inject warning-style with ng-class.
<div ng-class="{'has-warning': !form.name.$pristine}">
<input type="text" name="name" ng-model="people.name">
</div>
There are several state properties set on the ngModel described here. You may want to consider using form.name.$dirty or form.name.$touched instead.
edit
Try using:
ng-class="{'has-warning': form.name.$touched && people.name.length === 0}"
You can try using ngFocus:
Specify custom behavior on focus event.
https://docs.angularjs.org/api/ng/directive/ngFocus
<div ng-class="{'has-warning': !form.name.isValid}">
<input type="text" name="name" ng-model="people.name" ng-focus="form.name.isValid = people.name ? true : false">
</div>
I would suggest to use :
form.name.$touched && form.name.$invalid
it should work

knockout textinput modify observeable not updating text

i´m using textinput data-binding off the latest knockout version.
on an input like:
<input type="text" placeholder="name" data-bind="textinput:vm.found().term">
and it works just like a charme, problem:
when i modify the value with some other script like:
vm.found().term("somecontent")
the input does not change?
i need the value of the textinput to change when i change the observable
the doc says nothing about textInput
You should never have raw, deeply nested bindings like you have there. Assuming the found value has changed, it the text box will still be bound to the previous found object. You probably should be using a with binding somewhere.
<div data-bind="with: vm.found">
<input type="text" placeholder="name" data-bind="textinput: term">
</div>

Dynamically generating validation attribute on input using interpolation

Edit: This question is no longer relevant as of Angular version: 1.3.0-beta.12 you can now parse ng-minlength and ng-maxlength dynamic values. See: https://github.com/angular/angular.js/issues/5319
My problem is quite simple: I need to dynamically create input validation (ex. ng-minlength) using interpolation.
And doing that I am running into some issues specifically generating the validation attributes for ng-minlength and ng-maxlength. I assume this is due to them only taking constants?
Below you can see my code, the reason I am using a wrapper through outerForm is that I cannot dynamically generate the name attribute of input elements using interpolation, and that I have to wrap each set of repeated inputs in an ngForm directive and nest these in an outer form element.
So again, the problem lies in the attribute ng-minlength="field.ValidationAttributes['data-val-length-min']" not being properly set.
When I print the value directly using {{field.ValidationAttributes['data-val-length-min']}} the value appears correct.
Do I have to create a directive to parse my information, do I need to create my own min/max validation or am I simply running into a syntax error?
<form name="outerForm">
<div ng-repeat="field in logEntry.StringValues">
<ng-form name="innerForm">
<input type="text" name="foo" ng-model="item.foo" ng-minlength="field.ValidationAttributes['data-val-length-min']" required/>
<span ng-show="innerForm.foo.$error.required">required</span>
<span ng-show="innerForm.foo.$error.minlength">to short</span>
</ng-form>
</div>
</form>
Hi you can use double {} to interpolate dynamic validation rules please see here: http://jsbin.com/xayiro/1/
If you can post you field.ValidationAttributes model I can update jsbin.
HTML:
<ng-form name="innerForm">
<input type="text" name="foo" ng-model="item.foo" ng-minlength="{{validation.minlength}}" required/>
<span ng-show="innerForm.foo.$error.required">required</span>
<span ng-show="innerForm.foo.$error.minlength">to short</span>
</ng-form>
JS:
$scope.validation= {
maxlength:20,
minlength:3
};

Categories