At a user registration web form I validate via ajax whether a username already exists in DB. When a username already exists, the corresponding input-text will go .has-error class.
Edit
I changed the ng-class attribute to {'has-error':signup.userUnavaliable()} but even though that the input is not seemly getting such class, in other words the mail input text is not getting red.
I place the directive at the wrapper as this is how the Bootstrap docs tell it.
This is how my form looks like now:
<form class="form-inline" role="form">
<div class="form-group" ng-class="{'has-error':signup.userUnavaliable()}">
<input type="email" class="form-control input-lg" ng-model="signup.mail" placeholder="e-mail" ng-change="signup.userExists(signup.mail)">
</div>
<div class="form-group">
<input type="password" class="form-control input-lg" placeholder="ContraseƱa" ng-nodel="signup.password">
</div>
<div class="checkbox">
<label>
<input type="checkbox" ng-model="signup.role" value="admin"> Administrador
</label>
</div>
<button type="submit" class="btn btn-primary" ng-disabled="signup.unavaliable">Registrar</button>
</form>
And this is my Controller:
app.controller('SignUpController',function ($scope, $http) {
$scope.userUnavaliable = function() {
return $scope.unavaliable
}
$scope.print = function(msg) {
console.log(msg)
}
this.userExists = function(mail) {
if (mail) {
var who = $http.get("/existingUsers/"+mail)
who.success(function(data,status, headers, config) {
if (data.mail) {
$scope.unavaliable = true
console.log(data.mail + " ya existe en la DB")
}
else{
$scope.unavaliable = false
}
});
who.error(function(data, status, headers, config) {
alert("AJAX failed!");
})
}
}
})
Also, I'm trying to disable the button and it's not gettin such effect, so I think my controller has any issue.
As given in bootstrap validation states, if you want your label color to be changed according to the validation state of the input, you will have to apply ng-class on that.
Here is the sample code that I had written a little while. Please note that to take advantage of Angular JS validation states on form elements, you need to provide name to all input types.
This code would turn the input box plus label color red or green depending upon the validation state.
<div class="form-group"
ng-class="( newProfileForm.email.$dirty ? (newProfileForm.email.$valid ? 'has-success has-feedback' : 'has-error has-feedback' ) : ' ')"
>
<label class="col-sm-4 control-label">Email</label>
<div class="col-sm-6">
<input type="email" name="email" class="form-control" ng-model="user.mail" ng-required='true'>
<!-- Invalid Span -->
<span ng-if='newProfileForm.email.$invalid && newProfileForm.email.$dirty' class="glyphicon glyphicon-remove form-control-feedback"></span>
<!-- Valid Span -->
<span ng-if='newProfileForm.email.$valid' class="glyphicon glyphicon-ok form-control-feedback"></span>
<p ng-show="newProfileForm.email.$invalid && newProfileForm.email.$dirty" class="bg-danger pad">Please enter valid email.</p>
</div>
</div>
[EDIT] Explanation for name attribute.
Angular makes use of name attribute to determine the state of the input control. So, if you have a input control with name username. Even your form should have a name for angular validation states.
AngularJS would use the fallowing variables to check its validation state.
formname.username.$valid = if username is alright according to validation rules.
formname.username.$invalid = if username is invalid
formname.username.$dirty = if user has edited the input box
formname.username.$pristine = if user has not edited the input box.
Angular makes use of name attribute for validaiton.
And if you want your button to be disabled depending upon the availability of the user.
Use something like
<button class="btn btn-default" ng-disabled="unavaliable">Submit</button>
try
<div class="form-group" ng-class="{'has-error':signup.userUnavaliable()}">
Related
I am trying to handle some JavaScript work, which I don't have much experience with. I have a 2 part form where a user enters their personal info, and then company info. I am trying to set some of the company fields to what they already entered in their personal info.
I don't want the user to have to retype address, email, etc.
for example, I have...
<div class="form-group">
<label for="email">Email<span>*</span></label>
<input name="email" type="text" class="form-control required" id="email"placeholder="Email" value=".
{{email}}">
<span id="span_email" class="error-msg"></span>
And...
<div class="form-group">
<label for="comp_email">Company Email<span>*</span></label>
<input name="comp_email" type="text" class="form-control required" id="comp_email"placeholder="Email"
value="{{comp_email}}">
<span id="span_email" class="error-msg"></span>
How would I be able to set that second comp_email field to initially have the email info, so the user doesn't have to retype, unless they actually wanted to change the comp_email to another email address?
EDIT
It is all in one form, just separated by divs. Initially, when the page is loaded, the account section div is displayed, when the user hits next, it triggers the display of the business info.
<input type="button" onclick="nextFormPage(); window.scrollTo(0, 100)"
class="btn btn-danger btn-block" value="Next">
The nextFormPage() function just hides the first div and displays the second div.
You have tagged both javascript and jQuery so I'm not sure which you are using. But you can do this with a single line either way:
Javascript::
document.getElementById("comp_email").value = document.getElementById("email").value;
document.getElementById("email").value gets the value from the email input and we set the value of the document.getElementById("comp_email") by setting its value attribute:
jQuery:
$("#comp_email").val( $("#email").val() );
$("#email").val() get the value from the email input and $("#comp_email").val( ... ); sets the text passed in as the input value.
Javascript Working Example
function nextFormPage(){
document.getElementById("comp_email").value = document.getElementById("email").value;
}
<div class="form-group">
<label for="email">Email<span>*</span></label>
<input name="email" type="text" class="form-control required" id="email" placeholder="Email" value="">
<span id="span_email" class="error-msg"></span>
<div class="form-group">
<label for="comp_email">Company Email<span>*</span></label>
<input name="comp_email" type="text" class="form-control required" id="comp_email" placeholder="Email"
value="">
<span id="span_email" class="error-msg"></span>
<input type="button" onclick="nextFormPage(); window.scrollTo(0, 100)"
class="btn btn-danger btn-block" value="Next">
If your user is logged in, you should pass all of their information to the form, including their email. For example:
const logIn = () => {
... some code to get the user ...
... pass the user to the form, probably through an event listener...
let button = document.createElement("button")
button.textContent = "Edit"
button.addEventListener('click', () => {editYourStuff(user)}
}
const editYourStuff = user => {
... grab whatever your form is called ...
editForm.email.value = user.email
}
This should pre populate your form with the email
I have my chat and I dont want people to send empty message so I would like that my input become required. Thanks for your help.
I tried to put "required='required'" in the input line, I also tried veeValidate but it broke my chat when I use it, I also tried to put "Required = true" in Props and data but without a good result
This is ChatForm.vue
<template>
<div class="input-group" >
<input id="btn-input" type="text" name="message" class="form-control input-sm" placeholder="Ecrire..." v-model="newMessage" #keyup.enter="sendMessage">
<span class="input-group-btn">
<button class="btn btn-primary btn-sm" id="btn-chat" #click="sendMessage">
✓
</button>
</span>
</div>
</template>
<script>
export default {
props: ['user'],
data() {
return {
newMessage: '',
}
},
methods: {
sendMessage() {
this.$emit('messagesent', {
user: this.user,
message: this.newMessage
});
setTimeout(function() {
const messages = document.getElementById('mess_cont');
messages.scrollTop = messages.scrollHeight;
}, 200);
this.newMessage = '';
}
}
}
</script>
And this is my form in the app.blade.php
<div id="app" class="container-chat">
<div class="row">
<div class="col-md-12 col-md-offset-2">
<div class="col-md-12 col-md-offset-2">
<div class="panel-body panel-content" id="mess_cont">
<chat-messages id="mess" :messages="messages" :currentuserid="{{Auth::user()->id}}"></chat-messages>
</div>
<div class="panel-footer">
<chat-form
v-on:messagesent="addMessage"
:user="{{ Auth::user() }}"
></chat-form>
</div>
</div>
</div>
</div>
</div>
Try to change your ChatForm.vue like this:
<template>
<form #submit.prevent="sendMessage">
<div class="input-group" >
<input id="btn-input" type="text" name="message" class="form-control input-sm" placeholder="Ecrire..." v-model="newMessage" required>
<span class="input-group-btn">
<button class="btn btn-primary btn-sm" type="submit" id="btn-chat">
✓
</button>
</span>
</div>
</template>
You are not treating the input in the correct way, the input which is required needs to be inside a form and the required keyword will prevent the form submission if the input field is empty.
There are a few things I would do differently.
1/ Wrap your chat form in a tag, and execute the sendMessage() method on submit. This will give your users a nicer experience, as they can just to submit the message.
2/ Convert the button into a submit button so it triggers the form.submit event.
3/ You can easily disable the button by checking whether newMessage has contents. I don't think you need vee validate or anything else to achieve this; for something as simple as a chat form, your user doesn't need much more feedback than seeing a disabled button to realise (s)he needs to write something first.
4/ in the addMessage method you can just check the contents of newMessage and not do anything when it's empty. This is perfectly fine because you already hinted the user by disabling the button too.
I think this is a subtle way where you guide your user, but don't overdo it.
Please add name attributes to all of your form elements. Some of the element in my form had name attribute and some didn't. Element which had name attributes worked correctly but the one's which didn't had name failed.
I'm making a issue reporting form with categories and sub categories. The form also requires the user to add their e-mail address (from a list). The list has the data-live-search = true to give them the possibility to search for it in the list.
The form submits if you first start to type in the search field for the e-mail and then selects it, but if you don't write in the search bar and just select it from the list (without typing anything), the form won't submit... This is what the form looks like (a simplified version, but still not working):
<form role="form" name="form" id="form" action="file.php" method="post">
<!-- AUTHOR NAME -->
<div class="form-group" id="form-group-author-name">
<label class="sr-only" for="author-name">Author's name</label>
<input type="text" name="author-name" id="form-author-name" placeholder="Author's name" class="form-control" required>
</div>
<!-- AUTHOR E-MAIL -->
<div class="form-group" id="form-group-author-email">
<select class="selectpicker" name="author-email" id="form-author-email" data-width="100%" title="Author's e-mail" data-live-search="true" required>
<option>email1#example.com</option>
<option>email2#example.com</option>
<option>email3#example.com</option>
<option>email4#example.com</option>
<option>email5#example.com</option>
</select>
<p class="help-block">Search for your e-mail.</p>
</div>
<button type="submit" class="btn">Submit</button>
</form>
I've also tried to add an event listener to the select field and use $("#" + "form-author-email").selectpicker('refresh'); and document.getElementById("form-author-email").value = $("#" + "form-author-email").val(); in case it was because of the field not updateing, but that wasn't working either.
If I use console.log($("#" + "form-author-email").val()); I still get the value selected, so I don't understand what the problem is.
I've figured out the problem. I've added a jQuery validation function (for all input fields) that used e.preventDefault(); and added a error styling-class if the input was empty, which it would always be if they didn't type anything into the search bar. I've add the code below in case anybody has done the same thing:
jQuery(document).ready(function() {
$('.form input[type="text"]').on('focus', function() {
$(this).removeClass('error');
});
$('.form').on('submit', function(e) {
$(this).find('input[type="text"]').each(function(){
if( $(this).val() == "" ) {
e.preventDefault();
$(this).addClass('error');
}
else {
$(this).removeClass('error');
}
});
});
});
I have an application with add friend feature, in that feature, user must fill their friend's username in the textbox. this is the html code:
<div content-for="title">
<span>Add Friend</span>
</div>
<form class="form-inline" role="form">
<div class="form-group">
<label class="sr-only" for="exampleInputEmail2">User ID</label>
<input type="text" class="form-control" data-ng-model="add.email" id="exampleInputEmail2" placeholder="User ID">
</div>
<button type="submit" class="btn btn-default" data-ng-click="addfriends()">Add</button>
the interface will be like this
and this is the js code:
// addfriend
$scope.add = {};
$scope.addfriends = function(){
$scope.messages = {
email : $scope.add.email,
userid : $scope.datauser['data']['_id']
};
//event add friend
socket.emit('addfriend',$scope.messages,function(callback){
if(!callback['error']){
$scope.datauser['data']['penddingrequest'].push(callback['data']);
//push pendding request to localstorage user
localStorageService.remove('user');
localStorageService.add('user', $scope.datauser);
$scope.add['email'] = '';
alert('Successfully added friend');
}else{
var msg = callback['error'];
navigator.notification.alert(msg,'','Error Report','Ok');
}
});
};
I want to change this feature little bit, I want to make this textbox showing some suggestion based on the input, like if user input 'a', the textbox will show all user id that start with 'a'. something like twitter's searchbox or instagram searchbox. these user ids is from database.
example searchbox of web instagram
my question is how to change this textbox to be autocomplete but still work like before? thanks very much
There are many ways to do this.
First is this one: You basically create Angular directive for your input.
http://jsfiddle.net/sebmade/swfjT/
Another way to do is to attach onKeyUp event to your input:
<div class="form-group">
<label class="sr-only" for="exampleInputEmail2">User ID</label>
<input type="text" class="form-control" data-ng-model="add.email" id="exampleInputEmail2" placeholder="User ID" ng-keyup="searchFriends()">
<div ng-model="searchFriendsResult" />
</div>
And then, in your controller, you create a searchFriends function that will:
Search your database
Display the result in the view.
Something like this (not a complete code):
$scope.searchFriends = function(value){
// Make Ajax call
var userRes = $resource('/user/:username', {username: '#username'});
userRes.get({username:value})
.$promise.then(function(users) {
$scope.searchFriendsResult = users;
});
};
Use Bootstrap Typeahead
<input type="text" ng-model="asyncSelected"
placeholder="Locations loaded via $http"
uib-typeahead="address for address in getLocation($viewValue)"
typeahead-loading="loadingLocations"
typeahead-no-results="noResults"
class="form-control"/>
I have a ember-app-kit application. For the form I am using ember default views. But for form validations I have came across with this lib which everyone highly recommends. Ember Validations By Docyard . But I am not sure how to implement the same with my eak set-up.
Questions that I have:
1. Where should I add validations ?
2. What to declare when defining validations?
3. Errors how to show them on focus out or even on submit button ?
Say for example I have a sign up form and I want to validate firstname lastname, email, password, gender(select options) . How should I go about it ?
If possible please clarify the queries with a JSbin.
Validations should go to controller, unless your working with dyanmic formsets, which can be duplicated. Also u have to wrap ControllerObject into this
var AddController = Ember.ArrayController.extend(Ember.Validations.Mixin, {}
To start validation u have to make new Object named validations
You have to add input value to be validated
validations: {
newFirstname:{
format: { with: /^[A-Za-z-]{2,16}$/, allowBlank: true, message: 'Enter valid name.' }
},
newFamilyname: {
format: { with: /^[A-Za-z-]{3,16}$/ , message: 'Required field lastname.' }
}
},
Showing errors.
<div class="row">
<div class="col-md-6 col-xs-4">
<label>First name: </label>
{{input type="text" placeholder="First name" value=newFirstname class="form-control"}}
{{#if errors.newFirstname}}
<span class="error errorForValidation"><span class="glyphicon glyphicon-warning-sign"></span> {{errors.newFirstname}}</span>
{{/if}}
</div>
<div class="col-md-6 col-xs-4">
<label>*Last name: </label>
{{input type="text" placeholder="Family name" value=newFamilyname class="form-control"}}
{{#if errors.newFamilyname}}
<span class="error"><span class="glyphicon glyphicon-warning-sign"></span> {{errors.newFamilyname}}</span>
{{/if}}
</div>
</div><!--end row-->
Showing button when validation is flawless
<button type="submit" class="btn btn-primary" {{bind-attr disabled="isInvalid"}}{{action 'GetData'}}>Create</button>
JSBIN : http://emberjs.jsbin.com/iDeQABo/17/edit