required attribute on textbox in html doesn't work - javascript

I have a popover with a form inside. And It is already out and ready for submission, here is the code for the popover
<div id="popover-head" class="hide">Add new subject</div>
<div id="popover-content" class="hide">
<form class="form-inline" id="pop-form" method="POST" action="../admin/module_add_subject.do">
<div class="form-group">
<!-- This input is what i'm talking about -->
<input type="text" name="subjectName" id="subject-name" required="required" pattern="^[\S\s]{3,25}[A-z]+$" title="Only accept alphabet characters and length is minimum of 3 and max of 25 " placeholder="Subject name.."/>
<button class="btn btn-primary" type="button" id="add-subject" ><i class="icon-white icon-ok"></i></button>
</div>
<p></p>
<p style="color:red" id="error-message"></p>
</form>
</div>
The input above I'm sure the regex is working. When I change the button to submitthe required is working perfectly fine but when I change it back to button then it is not working again.
The reason why my submit button is a type="button" because of this code:
$(document).on('click', '#add-subject', function(e) {
$.post('../admin/module_check_subject.do', { subjectName: $('#subject-name').val() },
function( data ) {
// if data from the database is empty string
if( $.trim( data ).length != 0 ) {
// hide pop-over
$('#popover').popover('hide');
// submit form
$('#pop-form').submit();
} else {
$('#error-message').text('Subject already exist.' );
}
}
})
.fail( function () {
bootbox.alert('Failed to check, please try again later.');
});
});
What I'm doing is on submit i'll check out first in my database if the input text in the textbox exist in the database, then if the text exist the database stop the submission of the form and display error at the p tag

By the form submission algorithm, validation is not performed when a form is submitted using the submit() method. The idea is, more or less, that when you submit a form with a script, your script should also carry out any checks deemed necessary.
Within your script, you can call the checkValidity() method to carry out the normal validation that would be performed if the form were submitted with a submit button. Note that it performs static validation only.

Related

Validate a form element without/before submitting the form with JavaScript

I have an HTML form that has its elements displayed in various Bootstrap modals. The first modal has a text box input that and a "Next" button to open the next modal. When the "next" button is pressed. I want to check if the text box is empty, and trigger a validation message. The form does not get submitted until the very end. Everything I've tried has not worked so far.
Javascript/jQuery code
$("#add_assistant_next").click(function () {
var textInput = document.getElementById('add_assistant_user');
var text = textInput.value;
if (text === "") {
textInput.setCustomValidity('Please fill out this field.');
textInput.checkValidity();
var form = $('#form_add_assistant');
form.find(':submit').click();
} else {
textInput.setCustomValidity('');
}
});
HTML
<form name="add_assistant" method="post" id="form_add_assistant">
<div class="modal-body">
<div class="step">
<span class="fas fa-arrow-right choose-arrow mr-1"></span>1. Choose a user to add
</div>
<div class="pl-3 pt-1">
<div>
<input type="text" id="add_assistant_user" name="add_assistant[user]" required="required" placeholder="UCInetID or UCI email address" class="mr-0 form-control" />
<button type="button" id="add_assistant_next" name="add_assistant[next]" data-toggle="modal" data-target="#add-user-modal" class="btn btn-outline-secondary btn">Look up user</button>
</div>
<input type="hidden" name="user_search_route" value="/courseSpace/20900/listAssistantEnrollment">
</div>
</div>
... form continues in other modals
Your JS code is probably fighting with Bootstrap for control of that button. To get around that, and have your validation, you could try modifying your code to have a middle step / temporary button to help with validation first before actually submitting. So something like this:
Javascript/jQuery code
$("#my_temp_button").click(function () {
var textInput = document.getElementById('add_assistant_user');
var text = textInput.value;
// Might also want to handle null and undefined cases?
if (text === "" || text === undefined || text === null) {
// I'm assuming if it's empty, it doesn't pass validation,
// so we just display this warning and wait for the user to fix it:
textInput.setCustomValidity('Please fill out this field.');
} else {
// it's not empty so validate:
if (textInput.checkValidity()) {
// it passed validation, so ok to submit.
// call the real button:
$('#add_assistant_next').click();
// do you need this?
var form = $('#form_add_assistant');
form.find(':submit').click();
} else {
// it failed validation, so display another error?
textInput.setCustomValidity('Try again.');
}
}
});
HTML:
<form name="add_assistant" method="post" id="form_add_assistant">
<div class="modal-body">
<div class="step">
<span class="fas fa-arrow-right choose-arrow mr-1"></span>1. Choose a user to add
</div>
<div class="pl-3 pt-1">
<div>
<input type="text" id="add_assistant_user" name="add_assistant[user]" required="required" placeholder="UCInetID or UCI email address" class="mr-0 form-control" />
<!-- Feel free to change the id name. This is the button the user sees. It's only purpose is to give your function above full control to it and prevent Bootstrap from touching it and jumping to the next modal without having the user fix the validation failure first: -->
<button type="button" id="my_temp_button" class="btn btn-outline-secondary btn">Look up user</button>
<!-- Hide the real button from the user: -->
<div style="display:none">
<button type="button" id="add_assistant_next" name="add_assistant[next]" data-toggle="modal" data-target="#add-user-modal" class="btn btn-outline-secondary btn">Look up user</button>
</div>
</div>
<input type="hidden" name="user_search_route" value="/courseSpace/20900/listAssistantEnrollment">
</div>
</div>
...
Have you tried adding a trap for the submit event itself?
$('#form_add_assistant').submit(function(evt){
//do your validation here
if (validation fails){
return false; // OR, alternatively, `evt.preventDefault()`
}
//form submission will continue if not returned false
});
References:
https://api.jquery.com/submit/
How to conduct manual form validation via jQuery .submit()

Form data object is not formed on first click when validation fails; only on second click

I'm using a pretty simple form to submit something to our API. I added some form validation using a directive called Angular UI Form Validation. I'm just submitting an object with 2 properties; 'id', and 'points'. I'm running into a strange issue that I've been having a lot of trouble solving and hope I can get some help here.
The form validation works fine. If I enter a value into the input field that doesn't pass, you can't submit the form and a message beneath the input saying why appears. However, if I then remove the incorrect input and put in a correct input, the message is still there. If I click on the submit button, the message disappears. If I click the submit button again, it submits. I've noticed, however, that if I just press the enter key it submits right away.
I threw some console.log's in there, and it looks like the problem is that a formData object isn't created on the first click; only on the second. Here is the html:
<form name="pointsField">
<p><input type="number" ng-model="formData.points"
validation-only-numbers="true"
validation-field-required="{message:'Points value is required.',value:true}"
min="0"/></p>
<p><button class="btn btn-success" type="button" ng-click="updatePoints(pointsField)" ng-disabled="loading">
<span ng-if="loading"><i class="fa fa-circle-o-notch fa-la fa-spin"></i></span>Update Points
</button></p>
</form>
And here is the Javascript (keep in mind that the formData object is created when the controller is initialized, and it is just an empty object):
$scope.updatePoints = function(formData) {
console.log('formData ', formData);
$scope.$broadcast('runCustomValidations');
if(formData.$invalid){
return;
}
var pointsObject = {
"id": $scope.userId,
"points": $scope.formData.points
};
$scope.loading = true;
User.updateUserPoints(pointsObject).then(function(response) {
if(response.success) {
Notification.now.success(response.message);
$scope.loading = false;
} else {
Notification.now.error(response.message);
$scope.loading = false;
}
}, function(reason) {
Notification.now.error(reason.message);
$scope.loading = false;
});
};
If anyone can help me out I'd be eternally grateful. Thank you!
try adding novalidate in your form tag if this does not work dont use angular ui Form validation just use below format to validate .
<form name="pointsField" novalidate>
<input type="text" id="username" name="username" placeholder="Email Address"
ng-model="user.username" autocomplete="off" required >
<span class="text-danger" ng-show="pointsField.username.$dirty && pointsField.username.$invalid">
<span ng-show="pointsField.username.$error.required">Email Address is required</span>
</span>
<button type="submit" class="submit center" ng-disabled="pointsField.$invalid || dataLoading ">
<form>

Javascript submitting wrong form

As a workaround for not being able to have nested forms, I've written a system that uses Javascript to update an outside form's hidden input values and then submit the form. It is working just fine on one page in my site, but for some reason it isn't on another page. In the browser's JS console, I see the correct ID for the form I want submitted, but the server-side keeps showing a different form's data.
Here are relevant code snippets:
So the button's onclick action calls the JS function updateAndSubmitForm () to submit the actual form I want submitted for this button ("formAddStage") and NOT for the surrounding form "form-update-plan".
<form id="form-update-plan" class="form-horizontal" action="/secure/treatment-components/EditTreatmentPlan" method="POST">
<input type="hidden" name="requestedAction" value="plan-edit-update">
...
<button role="button" class="btn btn-default btn-xs" title="Add a stage to this treatment plan."
onclick='updateAndSubmitForm("formAddStage", ${treatmentPlan.treatmentPlanID }, 0, 0)'>
<span class="glyphicon glyphicon-plus" aria-hidden="true"></span>
</button>
...
</form>
Here is the form "formAddStage" which is at the botton of the page outside of the form that contains the button:
<form id="formAddStage" action="/secure/treatment-components/CreateStage" method="POST">
<input type="hidden" name="requestedAction" value="add-stage-to-treatment-plan">
<input type="hidden" name="path" value="${path }">
<input type="hidden" id="taskIDDynamic" name="taskID" value="" >
<input type="hidden" id="stageIDDynamic" name="stageID" value="" >
<input type="hidden" id="treatmentPlanIDDynamic" name="treatmentPlanID" value="${treatmentPlan.treatmentPlanID }">
<input type="hidden" name="clientUUID" value="${clientUUID }" >
</form>
And here is the JavaScript which gets the form by the ID supplied, gets and sets the values of the hidden fields in that form with the supplied values, then submits.
function updateAndSubmitForm(formID, treatmentPlanID, stageID, taskID){
var form = document.getElementById(formID);
var inputTaskID = form.elements["taskIDDynamic"];
inputTaskID.value = taskID;
var inputStageID = form.elements["stageIDDynamic"];
inputStageID.value = stageID;
var inputTreatmentPlanID = form.elements["treatmentPlanIDDynamic"];
inputTreatmentPlanID.value = treatmentPlanID;
var requestedAction = form.elements["requestedAction"];
console.log("Updating and submitting form " + form.id + " - requestedAction: " + requestedAction.value);
//alert("Updating and submitting form " + formID + " - requestedAction: " + requestedAction.value);
form.submit();
};
So, in summary, clicking the button should call the JS function updateAndSubmitForm() which then gets the form designated in the method's argument "formID" and then take the remaining arguments to update the values of the form and then submit it.
What ends up happening is that my browser console reports the proper information (form id = "formAddStage" and requestedAction = "add-stage-to-treatment-plan") but the server side reports getting information from the form (id="form-update-plan") that is surrounding the button (e.g. request.getParameter("requestedAction") returns "plan-edit-update" instead of "add-stage-to-treatment-plan".
Any ideas about why form.submit() in the JS function does not seem to submit the proper form or why the server is getting a different form?
The button element within the "form-update-plan" form does not have a type specified, it will therefore be defaulting to a type of submit and submitting the "form-update-plan" form.
Try this:
<button type="button"

AJAX and submit button on form interaction

I'm creating a simple website and a html page on it which contains a table that shows products. I load this table using AJAX and it work properly. Here is a screenshot:
Under the table I have buttons which perform CRUD operations using AJAX.
They communicate to a php script on a server outside of my domain using GET method.
When I click on Add product it opens a form with a button that whose onclick event calls a function which adds a product using AJAX. But, when I click, the whole page reloads and the product is not added. If I put the value that says wheter the call is async to false, it works as intended and the product is added to the table, however that is not the point of AJAX.
This is my code for adding a product(delete and update are almost the same).
<div id="addProductPopup">
<div id="popupContact">
<form id="form" method="post" name="form">
<img id="close" src="/servis/Resursi/Slike/close.png" onclick ="hide('addProductPopup');">
<h2>Dodavanje proizvoda</h2>
<hr>
<input id="name" name="naziv" placeholder="Naziv proizvoda" type="text" required>
<input id="kolicina" name="kolicina" placeholder="Količina proizvoda" type="text" required>
<input id="url" name="url" placeholder="URL slike" type="text" required>
<input type="submit" value="Pošalji" class="popupButtons" onclick="addProduct()">
</form>
</div>
When I click on submit this function is called:
function addProduct(){
var isValid = true;
var url = "http://zamger.etf.unsa.ba/wt/proizvodi.php?brindexa=16390";
var amount = document.form.kolicina.value;
var naziv = document.form.naziv.value;
var slikaurl = document.form.url.value;
var validity = validateFields(naziv, slikaurl, amount);
if(!validity) return false;
var product = {
naziv: naziv,
kolicina: amount,
slika: slikaurl
};
var requestObject = new XMLHttpRequest();
requestObject.onreadystatechange = function(event) {
if (requestObject.readyState == 4 && requestObject.status == 200)
{
loadProducts();
event.preventDefault();
}
}
requestObject.open("POST", url, true);
requestObject.setRequestHeader("Content-type","application/x-www-form-urlencoded");
requestObject.send("akcija=dodavanje" + "&brindexa=16390&proizvod=" + JSON.stringify(product));
}
It is because you are not preventing the default action of the submit button click.
You can return false from an event handler to prevent the default action of an event so
<input type="submit" value="Pošalji" class="popupButtons" onclick="addProduct(); return false;">
But since you have a form with a submit button, I think it will be better to use the submit event handler like
<form id="form" method="post" name="form" onsubmit="addProduct(); return false;">
....
<input type="submit" value="Pošalji" class="popupButtons">
Your problem is that your submit button still executes a real submit. You could change your addProducts method. The method have to return false to prevent the real submit.
Submit button performs default Submit action for HTML code.
Try to change Submit tag into Button tag. Or after AddProduct() in OnClick JS Action put
return false;
Simple Change put input type="button" instead of tpye="submit"
<input type="button" value="Pošalji" class="popupButtons" onclick="addProduct()">

parsley 2.0.3 not working with boostrap 3

i am trying to use parsely.js on my html page to validate input box. currently this html page contains one input box and one submit button. the structure is created using bootstrap 3 and this page does not contain Form tag.
<div role='form'>
<div class="row form-group">
<div class="col-xs-3">
<label title="fullname">Full Name</label>
</div>
<div class="col-xs-4">
<input type="text" class='form-control' id="name" name="fullName" data-parsley-required="true" data-parsley-required-message="Please insert your name"/>
</div>
</div>
<input type="submit" class= "btn btn-danger"/> </div>
i am calling parsley.js like
function validateInput()
{
var handle = $("input[name='fullName']").parsley({
successClass: "has-success",
errorClass: "has-error",
classHandler: function (el) {
return $(el).closest('.form-group');//not working
},
errorsWrapper: "<span class='help-block'></span>",
errorTemplate: "<span></span>",
});
return handle.isValid();
}
on click of Submit button. it returns true/false correctly and create span tag also. but error classes are not applied. even data-parsley-required-message'Please insert your name' is not working.
when i put alert($(el)) or alert(el) it gives [object Object]. i think el should be the input object on which i am calling parsley function. but i am not able to get el.attr('id') or any other attribute. it returns undefined. i have also tried
//return el.closest('.form-group');//not working
//return el.$element.closest('.form-group)//not working
//return $(el).$element.closest('.form-group')//not working
I can not use Form tag as i am using this html structure in sharepoint content edtior web part.
A few things first:
Parsley allows you to bind it to a field, so you won't have a problem without the form element (see docs);
The classHandler function recieves an object of the type ParsleyField. With this object, you can access the input element with el.$element (for example: alert(el.$element.attr('id'));
I have made the following changes to your validateInput function:
<script type="text/javascript">
function validateInput() {
$("input[name='fullName']").parsley({
successClass: "has-success",
errorClass: "has-error",
classHandler: function (el) {
return el.$element.closest('.form-group'); //working
},
errorsWrapper: "<span class='help-block'></span>",
errorTemplate: "<span></span>",
});
// Returns true / false if the field has been validated. Does not affect UI.
//$("input[name='fullName']").parsley().isValid());
// validate field and affects UI
$("input[name='fullName']").parsley().validate();
}
</script>
With this code, the message is presented correctly, and the successClass and errorClass are appended to the div form-group.
See the following working jsfiddle

Categories