Ajax submit after validation (jQuery Mobile + Validator) - ajax

I'm having trouble getting this to work. It validates the fields as expected, but no matter what I try, I can't properly hook the submit.
Here's my form:
<form action="" id="m-frm-contact_us" class="m-contact_submit" method="post" data-ajax="false">
<input type="text" name="firstName" placeholder="FIRST NAME" title="" id="first" class="contact full required" minlength="2" maxlength="36" />
<input type="text" name="lastName" placeholder="LAST NAME" id="last" class="contact full required" minlength="2" maxlength="36" />
<input type="email" name="mail" placeholder="E-MAIL ADDRESS" id="mail" class="contact full required email" />
<button type="submit" name="submit_contact" value="clicked">Submit</button>
</form>
My JS:
$(document).ready(function(){
$.validator.addMethod(
'placeholder', function(value, element) {
return value != $(element).attr("placeholder");
}, 'This field is required.'
);
$("#m-frm-contact_us").validate({
rules: {
firstName: {
required: true,
minlength: 5,
placeholder: true
},
lastName: {
required: true,
minLength: 5,
placeholder: true
},
mail: {
required: true,
email: true,
placeholder: true
}
},
messages: {
firstName: "First name is required.",
lastName: "Last name is required.",
email: "Valid email address is required."
},
submitHandler: function(form) {
console.log('submitHandler fired.');
contact.submit();
return false;
}
});
$('#m-frm-contact_us').submit(function(e){
console.log('Submit event fired.');
e.preventDefault();
return false;
});
var contact = {
submit : function(){
console.log('Form is being submitted.');
}
};
});
The only thing I get in my console is 'Submit event fired.', called on form submit. Despite my efforts, the form always tries to post to itself, reloading the page.
I want to execute this code on submit:
var contact = {
submit : function(){
console.log('Form is being submitted.');
var _this = this,
post = $.post("/path/to/submit.php", $("#m-frm-contact_us").serialize(), function(response){
try{
if(response==1) {
_this.passed();
} else {
_this.error();
}
}
catch(e){
if(typeof e == 'string') console.log(e);
_this.error();
}
});
},
error : function(){ $.mobile.changePage("#error"); },
passed : function(){ $.mobile.changePage("#passed"); }
}
What am I missing?

I rebuilt the JS, and was able to get this working. Here's the code, in case anyone experiences a similar issue:
Form:
<form action="" method="post" id="m-frm-contact_us" novalidate="novalidate">
<input type="text" name="firstName" placeholder="FIRST NAME" title="" id="first" class="contact full required placeholder noSpecial" minlength="2" maxlength="36">
<input type="text" name="lastName" placeholder="LAST NAME" id="last" class="contact full required placeholder" minlength="2" maxlength="36">
<input type="email" name="mail" placeholder="E-MAIL ADDRESS" id="mail" class="contact full required email">
<button type="submit" name="submit_contact" value="clicked">Submit</button>
</form>
JS:
$.validator.addMethod('noPlaceholder', function(value, element) {
return value !== element.defaultValue;
}, 'This field is required.');
$.validator.addMethod(
'placeholder', function(value, element) {
return value != $(element).attr("placeholder");
}, 'This field is required.'
);
$.validator.addMethod("regex", function(value, element, regexp) {
var check = false;
var re = new RegExp(regexp);
return this.optional(element) || re.test(value);
}, "No special Characters allowed here. Use only upper and lowercase letters (A through Z; a through z)");
$('#m-frm-contact_us').submit(function(event) {
event.preventDefault();
if($(this).validate({
rules : {
first_name : {
required : true,
maxlength : 36,
regex : /^[A-Za-z\s`'"\\-]+$/
},
last_name : {
required : true,
maxlength : 36,
regex : /^[A-Za-z\s`'"\\-]+$/
}
}
}).form()) {
var $form = $(this), formData = {
firstName : $form.find('#first').val(),
lastName : $form.find('#last').val(),
mail : $form.find('#mail').val()
};
$.post('/path/to/submit.php', formData, function(response) {
if(response == 1) {
$.mobile.changePage("#passed");
} else {
$.mobile.changePage("#error");
}
})
};
return false;
})

Related

Laravel only gets checked items from checklist

I have form with multiple input data and checklists but in controller I'm just getting checked items and no result for unchecked items.
This is what I get
"send_mail" => array:2 [▼
0 => "on"
1 => "on"
]
This is what I need
"send_mail" => array:2 [▼
0 => "off"
1 => "on"
2 => "off"
3 => "on"
]
Blade
<form enctype="multipart/form-data" action="{{route(''xxxxxxxx)}}" method="POST">
#csrf
#method('POST')
<input name="name" id="name" class="form-control">
<div class="form-check">
<input class="form-check-input" checked type="checkbox" name="send_mail[]">
<label class="form-check-label">Send Mail</label>
</div>
<div id="newRows">
// new rows (same as above) will add here by javascript
</div>
<button type="submit" class="btn btn-primary">Send</button>
</form>
Controller
public function test(Request $request) {
dd($request->all());
}
By default <input type="checkbox"> won't return if it hasn't been checked.
A classic method of fixing this is to duplicate the checkbox with a hidden input:
<input type="hidden" name="send_mail" value="0" />
<input type="checkbox" name="send_mail" value="1" />
This would require, however, moving away from the array of checkboxes you currently have.
The alternative is to use Javascript to submit your form.
I faced a similar scenario back then. I managed to solve it by using JavaScript (jQuery to be specific) to submit the form.
I wrote up a reusable function to append the unchecked items.
Reusable function:
const prepareJQCheckboxFormData = (jQForm, jQSerializedFormData, checkboxNameAttr) => {
let name;
let data = [];
checkboxNameAttr?.substr(-2) === "[]"
? name = checkboxNameAttr
: name = `${checkboxNameAttr}[]`;
let hasItem = false;
jQForm.find("input[name='" + name + "']")
.add(jQForm.find("input[name='" + name?.substr(0, name.length - 2) + "']"))
.each(function () {
if (($(this).attr("checked") === true) || $(this).is(":checked")) {
hasItem = true;
}
});
if (!hasItem) {
jQSerializedFormData.push({
name, value: [""]
});
}
$(jQSerializedFormData).each(function (i, field) {
if (field.name !== name?.substr(0, name.length - 2)) {
data.push(field);
} else {
data.push({
name: `${field.name}[]`,
value: field.value
});
}
});
return data;
};
Form submission:
Assuming that the form 'id' is 'mail-form'
const form = $("#mail-form");
const btnSave = $("#mail-form button[type='submit']");
btnSave.click(function (e) {
e.preventDefault();
$.ajax({
type: form.attr("method"),
url: form.attr("action"),
processData: false, // Important for multipart-formdata submissions!
contentType: false, // Important for multipart-formdata submissions!
cache: false,
data: prepareJQCheckboxFormData(form, form.serializeArray(), "send_mail[]"),
success: function (response) {
// ...
},
error: function (jqXHR) {
// ...
},
beforeSend: function () {
// ...
}
});
});
<div class="form-check">
<input type="checkbox" name="send_mail[]">
<label>Name1</label>
</div>
<div class="form-check">
<input checked type="checkbox" name="send_mail[]">
<label>Name2</label>
</div>
(another 2 div tag here)

I don't know why this error comes inside Laravel?

I have made this code, I want to facilitate user to dynamically enter text and display fields which have values, but I'm unable to get the result when I run it laravel+VueJs component view. below is my code
<template>
<div>
<div>
<label>Name</label>
<input type="text" #change="addRow">
</div>
<div> <label>Email</label>
<input type="text" #change="addRow1">
</div>
<div v-for="row in rows" :key="row.id">
<button-counter :id="row.id" :value="row.value"></button-counter>
</div>
</div>
<script type="text/javascript">
Vue.component('button-counter', {
props: {
value: {
default: ''
}
},
template: '<input type="text" style="margin-top: 10px;" v-model="value" >',
})
export default {
mounted() {
console.log('Component mounted.')
},
data: {
rows: [],
count:0
},
methods: {
addRow: function () {
var txtCount=1;
id='txt_'+txtCount;
this.rows.push({ value:'MyName' , description: "textbox1", id });
},
addRow1: function () {
var txtCount=1;
id='txt2_'+txtCount;
this.rows.push({ value: "myEmail", description: "textbox2", id });
}
}
}
data should be a function that returns an object holding data you want to manipulate, and you need to define the id as a variable, here's a working Vue SFC
<template>
<div>
<div>
<label>Name</label>
<input type="text" #change="addRow" />
</div>
<div>
<label>Email</label>
<input type="text" #change="addRow1" />
</div>
<div v-for="row in rows" :key="row.id">
<button-counter :id="row.id" :value="row.value"></button-counter>
</div>
</div>
</template>
<script type="text/javascript">
Vue.component("button-counter", {
props: {
value: {
default: ""
}
},
template: '<input type="text" style="margin-top: 10px;" v-model="value" >'
});
export default {
data() {
return {
rows: [],
count: 0
};
},
methods: {
addRow: function() {
var txtCount = ++this.count;
let id = "txt_" + txtCount;
this.rows.push({ value: "MyName", description: "textbox1", id });
},
addRow1: function() {
var txtCount = ++this.count;
let id = "txt2_" + txtCount;
this.rows.push({ value: "myEmail", description: "textbox2", id });
}
}
};
</script>
Hope this helps

Inserting a general validation alert using KnockoutJS validation

I'd looking for the most effective way of inserting a general validation alert "Please check your submission" to be positioned above the fieldset, instead of in an alert pop-up as coded below.
http://jsfiddle.net/Nz38D/3/
HTML:
<script id="customMessageTemplate" type="text/html">
<em class="customMessage" data-bind='validationMessage: field'></em>
</script>
<fieldset>
<legend>Details</legend>
<label>First name:
<input data-bind='value: firstName' />
</label>
<label>Last name:
<input data-bind='value: lastName' />
</label>
<div data-bind='validationOptions: { messageTemplate: "customMessageTemplate" }'>
<label>Email:
<input data-bind='value: emailAddress' required pattern="#" />
</label>
</fieldset>
<br>
<button type="button" data-bind='click: submit'>Submit</button>
<br>
<br> <span data-bind='text: errors().length'></span> errors
JS:
ko.validation.rules.pattern.message = 'Invalid.';
ko.validation.configure({
decorateElement: true,
registerExtenders: true,
messagesOnModified: true,
insertMessages: true,
parseInputAttributes: true,
messageTemplate: null
});
var viewModel = function() {
this.firstName = ko.observable().extend({
minLength: 2,
maxLength: 10
});
this.lastName = ko.observable().extend({
required: true
});
this.emailAddress = ko.observable().extend({ // custom message
required: {
message: 'Enter your email address.'
}
});
this.submit = function () {
if (this.errors().length == 0) {
alert('Thank you.');
} else {
alert('Please check your submission.');
this.errors.showAllMessages();
}
};
this.errors = ko.validation.group(this);
};
ko.applyBindings(new viewModel());
I inserted a virtual element to hold the validation summary message and bound its display to an observable in the click function: http://jsfiddle.net/sx42q/2/
HTML:
<!-- ko if: displayAlert -->
<p class="customMessage" data-bind="text: validationSummary"></p> <br />
<!-- /ko -->
JS:
this.validationSummary = ko.observable("Complete missing fields below:");
this.displayAlert = ko.observable(false);
this.submit = function () {
if (this.errors().length == 0) {
alert('Thank you.');
} else {
this.displayAlert(true);
this.errors.showAllMessages();
}

jQuery Validator not working for upper validation

I am validating two sections of a webpage the first validation section validates however the second validator is not for some reason.
$(function(){
/* first validation - works*/
jVal = {
//validate firstName
'firstName': function(){
//appends #firstNameInfo with .info to body
$('body').append('<div id="firstNameInfo" class="info"></div>');
//create variables
var firstNameInfo = $('#firstNameInfo');
var ele = $('#firstName');
var patt = /^[a-zA-Z][a-zA-Z]{1,20}$/;
if(!patt.test(ele.val())) {
jVal.errors = true;
firstNameInfo.removeClass('correct').addClass('error');
ele.removeClass('normal').addClass('wrong');
}else{
firstNameInfo.removeClass('error').addClass('correct');
ele.removeClass('wrong').addClass('normal');
}
},
//validate lastName
'lastName': function() {
$('body').append('<div id="lastNameInfo" class="info"></div>');
var lastNameInfo = $('#lastNameInfo');
var ele =$('#lastName');
var patt = /^[a-zA-Z][a-zA-Z]{1,20}$/;
if(!patt.test(ele.val())){
jVal.errors = true;
lastNameInfo.removeClass('correct').addClass('error');
ele.removeClass('normal').addClass('wrong');
}else{
lastNameInfo.removeClass('error').addClass('correct');
ele.removeClass('wrong').addClass('normal');
}
},
//validate phone
'phone' : function(){
$('body').append('<div id="phoneInfo" class="info"></div>');
var phoneInfo = $('#phoneInfo');
var ele = $('#phone');
var patt = /^((\+?1-)?\d\d\d-)?\d\d\d-\d\d\d\d$/;
if(!patt.test(ele.val())) {
jVal.errors = true;
phoneInfo.removeClass('correct').addClass('error');
ele.removeClass('normal').addClass('wrong');
}else{
phoneInfo.removeClass('error').addClass('correct');
ele.removeClass('wrong').addClass('normal');
}
},
//validate zipcode
'zip' : function() {
$('body').append('<div id="zipInfo" class="info"></div>');
var zipInfo = $("#zipInfo");
var ele = $('#content_form #zip');
var patt = /^\d\d\d\d\d$/;
if(!patt.test(ele.val())){
jVal.errors = true;
zipInfo.removeClass('correct').addClass('error');
ele.removeClass('normal').addClass('wrong');
}else{
zipInfo.removeClass('error').addClass('correct');
ele.removeClass('wrong').addClass('normal');
}
},
//submit button code
'sendForm':function(){
if(!jVal.errors){
$('#content_form').submit();
}
},
};
$('#content_form #submit').click(function(){
var obj = $.browser.webkit ? $('body') : $('html');
jVal.errors = false;
jVal.firstName();
jVal.lastName();
jVal.phone();
jVal.zip();
jVal.sendForm();
return false;
$('#firstName').change(jVal.firstName);
$('#lastName').change(jVal.lastName);
$('#email').change(jVal.email);
$('#content_form #zip').change(jVal.zip);
});
/**** Second Validation Does Not work ******/
kVal ={
'zip' : function() {
$('body').append('<div id="Infozip" class="info"></div>');
var Infozip = $("#Infozip");
var ele = $('#form #zip');
var patt = /^\d\d\d\d\d$/;
if(!patt.test(ele.val())){
kVal.error = true;
Infozip.removeClass('correct').addClass('error');
ele.removeClass('normal').addClass('wrong');
}else{
Infozip.removeClass('error').addClass('correct');
ele.removeClass('wrong').addClass('normal');
}
},
//submit button code
'send':function(){
if(!kVal.errors){
$('#form').submit();
}
},
};
$('#form button#submit').click(function(){
var obj = $.browser.webkit ? $('body') : $('html');
kVal.errors = false;
kVal.zip();
kVal.send();
return false;
$('#form #zip').change(kVal.zip);
});
}); /*main function closer*/
HTML FOR FIRST Validation -WORKING -
<div id="content_form">
<p>
<label class="block">
<input type="text" id="firstName" type="firstName" autocomplete="on" value="first name">
</label>
<label class="block">
<input type="text" id="lastName" type="lastName" autocomplete="on" value="last name">
</label>
<label class="block">
<input type="text" id="phone" type="phone" autocomplete="on" value="phone">
</label>
<label class="block">
<input type="text" id="zip" type="zip" autocomplete="on" value="zip code">
</label>
<button type="submit" id="submit" value="Submit" title="submit">submit</button>
</p>
</div><!-- end form -->
HTML FOR SECOND Validation
<div id="form">
<p>
<label class="block">
<input type="text" id="zip" type="zip" autocomplete="on" value="zip code">
</label>
<button type="submit" id="submit" value="CHECK NOW" title="check now">check now</button>
</p>
</div><!-- end form -->
You have the same id on both zip fields, which is probably causing your problems. The docs for the jQuery #id selector has this to say;
Each id value must be used only once within a document. If more than
one element has been assigned the same ID, queries that use that ID
will only select the first matched element in the DOM. This behavior
should not be relied on, however; a document with more than one
element using the same ID is invalid.
That is, your selection in $('#form #zip').change(kVal.zip); will not use the hierarchy under #form to find #zip, it will still find the first instance in the entire DOM.

Remote Validation in jQuery not validating

This form will INSERT both an email and password into my MYSQL db
First, I am trying to validate an email remotely to make sure it does not exists, and also that
the Pswd and Pswd2 are equal.
the script writes to the db, but the validation is not working. I am new to JQ and Ajax so any help would be apprecated.
Thanks.
FORM:
<link rel="stylesheet" href="http://code.jquery.com/mobile/1.0.1/jquery.mobile-1.0.1.min.css" />
<script src="http://code.jquery.com/jquery-1.6.4.min.js"></script>
<script src="http://code.jquery.com/mobile/1.0.1/jquery.mobile-1.0.1.min.js"></script>
<script src="jquery.validate.js" type="text/javascript"></script>
<script src="http://ajax.aspnetcdn.com/ajax/jquery.validate/1.9/additional-methods.min.js"></script>
...
<div data-role="content">
<form id="AddUser" class="ui-body ui-body-a ui-corner-all" data-ajax="true" >
<fieldset>
<div data-role="fieldcontain">
<label for="Email">Email Address:</label>
<input id="Email" type="email" />
<label for="Pswd">Password:</label>
<input id="Pswd" type="password" />
<label for="Pswd2">Confirm Password:</label>
<input id="Pswd2" type="password" />
</div>
<button type="submit" id="submit" data-theme="b" name="submit" value="submit-value">Submit</button>
</fieldset>
</form>
</div>
...
below is the js inside the document:
<script>
$(document).ready(function() {
var validator =
$('#AddUser').validate({
rules: {
Pswd: {
required: true,
},
Pswd2: {
required: true,
equalTo: "#Pswd"
},
Email: {
required: true,
email: true,
remote: "process/ValidateEmail.php"
}
},
messages: {
Pswd: {
required: "Provide a password",
},
Pswd2: {
required: "Repeat your password",
equalTo: "Enter the same password as above"
},
Email: {
required: "Not A Valid Email Address",
remote: "already in use"
}
}
}); // end var validator
if (validator)
{
$("#AddUser").submit(function(){
//make Variables
var emailVar =$('input[id=Email]').val();
var pswdVar = $('input[id=Pswd]').val();
var pswdconfirm = $('input[id=Pswd2]').val();
var querystring = "Email="+emailVar+"&Pswd="+pswdVar;
$.post("process/AddUser.php",querystring);
}); //end submit()
}; // end if validator
}); //end ready()
</script>
the Validator file (ValidateEmail.php)
<?php
$UserEmail = $_POST["Email"];
include "connection.php";
$sqlEmail= mysql_query("Select EmailAddress from USERS where EmailAddress='$UserEmail'");
$EmailCheck=mysql_fetch_array($sqlEmail);
if (mysql_num_rows($EmailCheck) > 0) {
echo json_encode(true);
} else {
echo json_encode(false);
}
?>
I went back to the code after some research and found it riddled with errors in both the js and the php validation:
<script>
$(document).ready(function()
{
var validator = $("#AddUser").validate({
rules: {
Email: {
required: true,
email: true,
remote: "process/ValidateEmail.php"
},
Pswd: {
required: true,
},
Pswd2: {
required: true,
equalTo: "#Pswd"
},
},
messages: {
Pswd: {
required: "Provide a password",
},
Pswd2: {
required: "Repeat your password",
equalTo: "Password Mismatch"
},
Email: {
required: "Invalid Email",
remote: jQuery.format("{0} is already used")
}
},
// the errorPlacement has to take the table layout into account
errorPlacement: function(error, element) {
error.appendTo(element.parent().next());
},
// specifying a submitHandler prevents the default submit, good for the demo
submitHandler: function() {
//make Variables
var emailVar =$('input[id=Email]').val();
var pswdVar = $('input[id=Pswd]').val();
var pswdconfirm = $('input[id=Pswd2]').val();
var querystring = "Email="+emailVar+"&Pswd="+pswdVar;
$.post("process/AddUser.php",querystring);
$('#AddUser').clearForm();
return false;
},
// set this class to error-labels to indicate valid fields
success:
function(label) {
label.html(" ").addClass("checked");
}
});
});
</script>
email: {
required: true,
email: true,
remote: {
url: "check-email.php",
type: "post",
data: {
email: function() {
return $("[name='email']").val();
}
}
}
},
and the php must look like this:
$email= $_POST['email'];
include 'connect.php';
$email = trim(mysql_real_escape_string($email));
$query = mysql_query("SELECT COUNT(id) FROM users WHERE email = '$email'") or die(mysql_error());
echo (mysql_result($query, 0) == 1) ? 'false' : 'true';
be careful not to echo just false or true it must be echoed like this 'false' or true

Resources