I have a form where depending on the value in field 'a', an optional field 'b' is enabled/disabled.
If data is submitted with an a-value where b is enabled, the database contains a value for b as well.
The problem is that when the user then edits that record, selecting an a-value where b is disabled, I want the submit to submit a 'blank' value (empty string) in order to clean the database record.
(please do no argue that the backend should be intelligent enough to discard the b value in that case ... since that is out of my control)
I tried to enable the b-field and setting it to '' before submitting, but the b-field still isn't submitted. (using the on-beforeaction-submit)
I even tried to fiddle with other parameters (like originalValue) to make sure the b-field is dirty. I even tested with a random value (for the setValue call), just to make sure it's not a 'blank' field behaviour. But even when setting 'X' , the value isn't submitted. Nothing helps.
I'm sure i'm overlooking something really trivial, but I can't figure it out.
So after spending hours to find out reading through posts and testing, I give up and address to the community.
Thx,
C.
form.on('beforeaction', function(form, action) {
if (action.type == 'submit') {
//clean disabled fields before submitting
if (item!='general') {
var escid = Ext.getCmp('spcway-' + item + '-form-escid');
if (escid.disabled) {escid.enable(); escid.originalValue='abc'; escid.allowBlank=true; escid.setValue(''); escid.allowBlank=false}
if (item!='status') {
var escoption = Ext.getCmp('spcway-' + item + '-form-escoption');
if (escoption.disabled) {escoption.enable(); escoption.originalValue='abc'; escoption.setValue('')}
}
}
return true;
}
});
Set the field to readonly instead of disabled, then it will still be posted with the form data but will not be editable for the user.
<label>disabled</label>
<input type="text" disabled/>
<label>readonly</label>
<input type="text" readonly/>
Related
So basically what I'm trying to do as a measure of security (and a learning process) is to my own "Capthca" system. What happens is I have twenty "label's" (only one shown below for brevity), each with an ID between 1 and 20. My javascript randomly picks one of these ID's and makes that picture show up as the security code. Each label has its own value which corresponds to the text of the captcha image.
Also, I have the submit button initially disabled.
What I need help with is figuring out how to enable the submit button once someone types in the proper value that matches the value listed in the HTML label element.
I've posted the user input value and the ID's value and even when they match the javascript won't enable the submit button.
I feel like this is a really really simple addition/fix. Help would be much much appreciated!!!
HTML code
<div class="security">
<label class="captcha enabled" id="1" value="324n48nv"><img src="images/security/1.png"></label>
</div>
<div id="contact-div-captcha-input" class="contact-div" >
<input class="field" name="human" placeholder="Decrypt the image text here">
</div>
<input id="submit" type="submit" name="submit" value="Send the form" disabled>
Javascript code
//Picks random image
function pictureSelector() {
var number = (Math.round(Math.random() * 20));
//Prevents zero from being randomly selected which would return an error
if (number === 0) {
number = 1;
};
console.log(number);
//Set the ID variable to select which image gets enabled
pictureID = ("#" + number);
//If the siblings have a class of enabled, remove it
$(pictureID).siblings().removeClass("enabled");
//Add the disabled class to all of the sibling elements so that just the selected ID image is showing
$(pictureID).siblings().addClass("disabled");
//Remove the disabled class from the selected ID
$(pictureID).removeClass("disabled");
//Add the enabled class to the selected ID
$(pictureID).addClass("enabled");
};
//Calls the pictureSelector function
pictureSelector();
//Gets the value of the picture value
var pictureValue = $(pictureID).attr("value");
console.log(pictureValue);
//Gets the value of the security input box as the user presses the keys and stores it as the variable inputValue
$("#contact-div-captcha-input input").keyup(function(){
var inputValue = $("#contact-div-captcha-input input").val();
console.log(inputValue);
});
console.log($("#contact-div-captcha-input input").val());
//Checks to see if the two values match
function equalCheck() {
//If they match, remove the disabled attribute from the submit button
if ($(pictureValue) == $("#contact-div-captcha-input input").val()) {
$("#submit").removeAttr("disabled");
}
};
equalCheck();
UPDATE
Fiddle here
UPDATE #2
$("#contact-div-captcha-input input").keyup(function(){
var inputValue = $("#contact-div-captcha-input input").val();
console.log(inputValue);
if (pictureValue === inputValue) {
$("#inputsubmit").removeAttr("disabled");
}
});
So I got it working 99.9%, now the only problem is that if someone were to backspace or delete the correct value they have inputted, the submit button does not then change back to disabled. Any pointers?
Known issue.
Give your button a name OTHER THAN submit. That name interferes with the form's submit.
EDIT
A link was requested for this -- I don't have a link for pure JavaScript, but the jQuery docs do mention this issue:
http://api.jquery.com/submit/
Forms and their child elements should not use input names or ids that
conflict with properties of a form, such as submit, length, or method.
Name conflicts can cause confusing failures. For a complete list of
rules and to check your markup for these problems, see DOMLint.
EDIT 2
http://jsfiddle.net/m55asd0v/
You had the CSS and JavaScript sections reversed. That code never ran in JSFiddle.
You never re-called equalCheck. I added a call to your keyUp handler.
For some reason you wrapped pictureValue inside a jQuery object as $(pictureValue) which couldn't have possibly done what you wanted.
Basic debugging 101:
A console.log inside of your equalCheck would have shown you that function was only called once.
A console log checking the values you were comparing would have shown
that you had the wrong value.
Basic attention to the weird highlighting inside of JSFiddle would have shown you had the code sections in the wrong categories.
Tried to solve this multiple ways. 1. by simply adding the normal html "checked" default option to radio buttons in my form and 2. having js functions do it, being the gist of the ideas tried.
The issue: I'm finding that no matter how I do it, if the radio is designated as checked by default (before the user makes his/her choice), anything done after that will not be saved correctly (if at all) in localStorage. localStorage WILL save the initial default selections, however but, nothing can be changed from then on (even after "physically" selecting another option).
I know localStorage is working because if I leave off the default designation (and for the rest of the inputs) it functions perfectly.
The form code:
<label>Who is the contact person for this event?<span class="requiredtext">*</span></label>
<input type="radio" name="Contact_Person" id="Contact_Person1" value="Submitter is the contact person" onclick="contacthide()" checked required> I am<br />
<input type="radio" name="Contact_Person" id="Contact_Person2" value="Submitter is not the contact person" onclick="contactshow()" required>
The localStorage save code:
function localStoragefunctions() {
localStorage.clear();
if (Modernizr.localstorage) {
//Set variable to show that data is saved
localStorage.setItem("flag", "set");
//Save radio and checkbox data
$(window).bind('unload', function() {
$('input[type=radio]').each(function() {
localStorage.setItem('radio_' + $(this).attr('id'), JSON.stringify({
checked: this.checked
}));
});
});
The code that spits it back out if the user goes back to make changes before final submission:
$(document).ready(function() {
if (Modernizr.localstorage) {
//Browser supports it
if (localStorage.getItem("flag") == "set") {
$('input[type=radio]').each(function() {
var state = JSON.parse(localStorage.getItem('radio_' + $(this).attr('id')));
if (state) this.checked = state.checked;
});
Other than this, I have a confirmation page that grabs all of the variables stored in localStorage and presents them to the user for final inspection before they hit submit for good.
That consists of: var ContactPerson = localStorage.getItem('Contact_Person'); and then a document.write that spits out html and the variable's value. Again, this works fine if I don't try to set default radio choices (and works great for all other input types).
The ideal outcome would be choosing the most likely radio button choices by default so that it could possibly save the user time. I'd like to not have to present them with a form where they have to physically click each radio button if I can "make that decision for them" before hand.
Hope this all makes sense!
I know this an old question, but I've been troubleshooting a similar issue and thought I'd share my solution.
When you set your localStorage item, you are saving both radio inputs and their values, b/c your using the ID attribute as your key.
localStorage.setItem('radio_' + $(this).attr('id'), JSON.stringify({ checked: this.checked }));
This could be ok, but I've taken a different approach. And, I maybe missing something, so comments are welcome.
Instead, I use $(this).attr('name') to set the key. As a result, when either radio button in selected, you are saving the value to the same localStorage key.
In my scenario, I'm storing many inputs to localStorage, so my solution is a bit abstract. I'm calling saveToLocalStorage() using jQuery's .change() method on each input. Also, I'm saving the input's value directly to localStorage.
function saveToLocalStorage(input) {
if ( $(input).attr('type')=='radio' ) {
localStorage[$(input).attr('name')] = $(input).val();
} else {
localStorage[$(input).attr('id')] = $(input).val();
}
}
When retrieving from localStorage, I had to check if the localStorage key:value pair matched the radio input before selecting it. Otherwise, I was selecting both radio inputs. Note, in my scenario, I'm working with jQuery 1.4.4, hence the attr('checked', 'checked').
$('input[type=radio]').each(function() {
var key = $(this).attr('name');
var val = localStorage[key];
if ( $(this).attr('name') == key && $(this).attr('value') == val ) {
$(this).attr('checked', 'checked');
}
});
I am trying to pass a value for when a checkbox is either in a checked state or if it's not checked.
However, it doesn't appear to pass the non-checked state. the code I am using is below:
if (document.getElementById('PRODUCT_REVIEW_EMAILS_FIELD').checked == true){
document.getElementById('PRODUCT_REVIEW_EMAILS_FIELD').value = 'on';
}
else {
document.getElementById('PRODUCT_REVIEW_EMAILS_FIELD').value = 'off';
}
I have added an alert:
alert(document.getElementById('PRODUCT_REVIEW_EMAILS_FIELD').value);
which surprisingly shows the 'off' value - however - this isn't passed successfully.
What am I missing?
This is normal, expected and well-defined behaviour.
Checkboxes have an arbitrary value;
When a checkbox's checked attribute is on, it is submitted as part of a form with that value;
When a checkbox's checked attribute is off, it is not submitted at all.
HTML 4.01 says:
Checkboxes (and radio buttons) are on/off switches that may be toggled by the user. A switch is "on" when the control element's checked attribute is set. When a form is submitted, only "on" checkbox controls can become successful.
And:
When the user submits a form (e.g., by activating a submit button), the user agent processes it as follows.
Step one: Identify the successful controls
Step two: Build a form data set
A form data set is a sequence of control-name/current-value pairs constructed from successful controls. [..]
HTML5 says similar things.
You could write your back-end code to expect fields with a certain name, and react accordingly when they are missing.
You can handle the true on/off values of a checkbox this way (will post when checkbox is on and off). Basically this uses a hidden form field with the name PRODUCT_REVIEW_EMAILS_FIELD and populates it with the value. Hidden form fields always post.
<form>
<input id="tempCheckbox" type="checkbox" name="Temp_PRODUCT_REVIEW_EMAILS_FIELD">
<input id="checkboxvalue" type="hidden" name="PRODUCT_REVIEW_EMAILS_FIELD" value="Off">
</form>
<script type="text/javascript">
document.getElementById("tempCheckbox").onclick = function () {
if (this.checked) {
document.getElementById("checkboxvalue").value = "On";
}
else {
document.getElementById("checkboxvalue").value = "Off";
}
}
// used to run on page load to verify the correct value is set incase your server side
// script defaults the checkbox to on
document.getElementById("tempCheckbox").onclick();
</script>
You can do it on the server side so not to relay on JavaScript.
To do it you must add a reference input field right before every checkbox.
<form>
<input type="hidden" name="checkboxes" value="reference"/>
<input type="checkbox" name="checkboxes" value="checked"/>
</form>
This will make parameters come in array of values: "reference-checked" sequence if checkbox is checked and just "reference" if it is unchecked. You can have arbitrary amount of such checkboxes, this will not affect your logic.
Now for the server side. Assuming that you get your 'checkboxes' as a String array, here's the logic (in Java) to parse the values:
List<Boolean> parsed = new ArrayList<Boolean>();
for (int i = 0; i < checkboxes.length; i++) {
if (i < checkboxes.length - 1 && "checked".equals(checkboxes[i + 1])) {
parsed.add(true);
i++;
else {
parsed.add(false);
}
}
Now you have a nice array of booleans that correlates to the order, amount and state of checkboxes you have.
I have some javascript which catches changes to a form then calls the form's regular submit function. The form is a GET form (for a search) and i have lots of empty attributes come through in the params. What i'd like to do is to delete any empty attributes before submitting, to get a cleaner url: for example, if someone changes the 'subject' select to 'english' i want their search url to be
http://localhost:3000/quizzes?subject=English
rather than
http://localhost:3000/quizzes?term=&subject=English&topic=&age_group_id=&difficulty_id=&made_by=&order=&style=
as it is at the moment. This is just purely for the purpose of having a cleaner and more meaningful url to link to and for people's bookmarks etc. So, what i need is something along these lines, but this isn't right as i'm not editing the actual form but a js object made from the form's params:
quizSearchForm = jQuery("#searchForm");
formParams = quizSearchForm.serializeArray();
//remove any empty fields from the form params before submitting, for a cleaner url
//this won't work as we're not changing the form, just an object made from it.
for (i in formParams) {
if (formParams[i] === null || formParams[i] === "") {
delete formParams[i];
}
}
//submit the form
I think i'm close with this, but i'm missing the step of how to edit the actual form's attributes rather than make another object and edit that.
grateful for any advice - max
EDIT - SOLVED - thanks to the many people who posted about this. Here's what i have, which seems to work perfectly.
function submitSearchForm(){
quizSearchForm = jQuery("#searchForm");
//disable empty fields so they don't clutter up the url
quizSearchForm.find(':input[value=""]').attr('disabled', true);
quizSearchForm.submit();
}
The inputs with attribute disabled set to true won't be submitted with the form. So in one jQuery line:
$(':input[value=""]').attr('disabled', true);
$('form#searchForm').submit(function() {
$(':input', this).each(function() {
this.disabled = !($(this).val());
});
});
You can't do it that way if you call the form's submit method; that will submit the entire form, not the array you've had jQuery create for you.
What you can do is disable the form fields that are empty prior to submitting the form; disabled fields are omitted from form submission. So walk through the form's elements and for each one that's empty, disable it, and then call the submit method on the form. (If its target is another window, you'll then want to go back and re-enable the fields. If its target is the current window, it doesn't matter, the page will be replaced anyway.)
Well one thing you could do would be to disable the empty inputs before calling "serializeArray"
$('#searchForm').find('input, textarea, select').each(function(_, inp) {
if ($(inp).val() === '' || $(inp).val() === null)
inp.disabled = true;
}
});
The "serializeArray()" routine will not include those in its results. Now, you may need to go back and re-enable those if the form post is not going to result in a completely refreshed page.
Maybe some of the proposed solutions worked at the moment the question was made (March 2010) but today, August 2014, the solution of disabling empty inputs is just not working. The disabled fields are sended too in my Google Chrome. However, I tried removing the "name" attribute and it worked fine!
$('form').submit(function(){
$(this).find('input[name], select[name]').each(function(){
if (!$(this).val()){
$(this).removeAttr('name');
}
});
});
Update:
Ok, probably the reason because disabling fields doesn't worked to me is not that something changed since 2010. But still not working in my Google Chrome. I don't know, maybe is just in the linux version. Anyway, I think that removing the name attr is better since, despite what policy takes the browser about disabled fields, there is no way to send the parameters if the name attr is missing. Another advantage is that usually disabling fields implies some style changes, and is not nice to see a style change in the form a second before the form is finally submited.
There is also a drawback, as Max Williams mentioned in the comments, since the remove name attr solution is not toggleable. Here is a way to avoid this problem:
$('form').submit(function(){
$(this).find('input[name], select[name]').each(function(){
if (!$(this).val()){
$(this).data('name', $(this).attr('name'));
$(this).removeAttr('name');
}
});
});
function recoverNames(){
$(this).find('input[name], select[name]').each(function(){
if ($(this).data('name')){
$(this).attr('name', $(this).data('name'));
}
});
}
However, I think this is not a very common case since we are submitting the form so it is assumed that there is no need to recover the missing name attrs.
Your problem helped me figure out my situation, which is a bit different - so maybe someone else can benefit from it. Instead of directly submitting a form, I needed to prevent empty form elements from being collected into a serialized array which is then posted via AJAX.
In my case, I simply needed to loop through the form elements and disable all that were empty, and then collect the leftovers into an array like so:
// Loop through empty fields and disable them to prevent inclusion in array
$('#OptionB input, select').each(function(){
if($(this).val()==''){
$(this).attr('disabled', true);
}
});
// Collect active fields into array to submit
var updateData = $('#OptionB input, select').serializeArray();
Or serialize, clear empty key=value pairs with regex and call window.location:
$("#form").submit( function(e){
e.preventDefault();
//convert form to query string, i.e. a=1&b=&c=, then cleanup with regex
var q = $(this).serialize().replace(/&?[\w\-\d_]+=&|&?[\w\-\d_]+=$/gi,""),
url = this.getAttribute('action')+ (q.length > 0 ? "?"+q : "");
window.location.href = url;
});
Another approach I always recommend is to do that on server side, so you are able to:
Validate the input data correctly
Set default values
Change input values if needed
Have a clean URL or a friendly URL such as "/quizzes/english/level-1/"
Otherwise you will have to deal with text input, select, radio etc...
if(document.frmMain.POL_NO.value == "")
{
alert("Select Policy Number");
document.frmMain.ENDT_NO.value="";
document.frmMain.POL_NO.focus();
return false;
}
Can anyone explain the above code to me? I am new to Javascript.
It appears to be a bit of validation code to make sure a user has entered a value for an item referred to as "Policy Number". It is the sort of code that gets called when submitting a form to check that the values the user has entered are valid.
In detail:
if(document.frmMain.POL_NO.value == "")
Only run this code if the item called in POL_NO the form called frmMain doesn't have a value yet.
alert("Select Policy Number");
Display a message to tell the user that they need to enter a value.
document.frmMain.ENDT_NO.value="";
Set the ENDT_NO item of frmMain to a blank value.
document.frmMain.POL_NO.focus();
Set the focus to the POL_NO item (the same as the user tabbing to it or clicking on it).
return false;
Return false to the code that called the function that this code is in. If this code is used in the event handler for the submit button on a form then returning false will stop the form from being submitted to the server until the POL_NO item has a value.
If the contents of the item POL_NO from the form frmMain is empty, then throw an alert and change the value of the ENDT_NO item value to nothing (empty) and after that focus on the element POL_NO. Return false after that (I assume this code executes at onSubmit event, so the form won't be submitted if POL_NO doesn't have a value)
Probably the logic is that the ENDT_NO can't have a value if POL_NO is empty.
Enjoy!
document.frmMain is a form in the page, and POL_NO and ENDT_NO are fields in the form, presumably listboxes.
This code is a simple validation script to make sure you filled out the form correctly.
//if POL_NO hasn't been set (no policy number selected):
if(document.frmMain.POL_NO.value == "")
{
//show a message box
alert("Select Policy Number");
//clear the value (if any) of ENDT_NO
document.frmMain.ENDT_NO.value="";
//set the form focus to POL_NO (select it, as if you had clicked on it)
document.frmMain.POL_NO.focus();
//stop the form from being submitted
return false;
}
I'm assuming this code is part of a function which is called by frmMain's onSubmit event (and event handler) -- when the function returns false the submit is cancelled. Were this not here, it would show the message box, clear ENDT_NO, select POL_NO and then submit anyways.
Note that referencing members of a form in the document.formName.fieldName.property fashion is deprecated. The correct way is to use getElementById or a similar function:
document.frmMain.ENDT_NO.value = ""; //bad
document.getElementById("ENDT_NO").value = ""; //correct
HTML document
your HTML document has this defined somewhere in its content
<form id="frmMain" ...>
<input type="..." id="POL_NO">
<input type="..." id="ENDT_NO">
</form>
SCRIPT code
So. Your script checks whether your POL_NO input field has a value.
If it doesn't (it's an empty string),
it displays an alert (information window) and
empties ENDT_NO field's value and
puts focus on the POL_NO field - so the user can immediately start selecting/typing a value in this field
returns false - probably to cancel form submission
Business logic
Based on the logic of this script, the business process obviously doesn't allow any value in ENDT_NO field, until there's a value in POL_NO.
Observation
If you need to change something about this code (if there's a bug in it), I strongly suggest you get to know Javascript/DOM/HTML before doing any changes.
Actually your code does a pretty simple validation, just read the code and find the fields POL_NO and ENDT_NO in your HTML output. Here is my comments :
// if your POL_NO field is empty,
if(document.frmMain.POL_NO.value == "")
{
// warn user that he need to select Policy number
alert("Select Policy Number");
// set ENDT_NO field's value to empty
document.frmMain.ENDT_NO.value="";
// set POL_NO active - focussed
document.frmMain.POL_NO.focus();
return false;
}
If the value of the input named POL_NO in the form frmMain is empty, then show a message "Select Policy Number", empty the input named ENDT_NO, give the focus to the input named POL_NO, and the exit the function with the return value "false".