Function onSelect is faster than click - javascript

I use autosuggestion plugin and option onSelect - that option change values to other fields. Everything is fine when I select first time item but when I click on input field with class .auto second time (where already have item) then fucntion onSelect is faster than function click which give me ID where I need to update field.
This looks like this:
function dajjson() {
$('.auto').click(function () {
koji = $(this).attr('data-ajdi5');
console.log(koji);
});
$.ajax({
url: "autoUsluge.php",
type: "GET",
async: true,
dataType: "JSON",
success: function (data) {
$('.auto').autocomplete({
lookup: data,
showNoSuggestionNotice: true,
noSuggestionNotice: '<div> + Dodaj novu uslugu</div>',
beforeRender: function (container) {
$('.autocomplete-suggestions').append('<div> + Dodaj novu uslugu</div>');
},
onSelect: function (suggestion) {
console.log(koji);
$('#cena_' + koji).val(suggestion.cena);
console.log(suggestion.cena);
$('#jmere' + koji).val(suggestion.jmere);
$('#kol' + koji).val(suggestion.kol);
$('#popust' + koji).val(suggestion.popust);
$('#pdv' + koji).val(suggestion.porez);
koji = 0;
}
});
},
error: function (data) {
console.log(data);
console.log('GRESKA NEKA');
}
});
};
So how I can solve problem with function select. How I can get koji before onSelect start?

I think using the .change() event is what you want here. It will fire after the value has changed. The .mousedown() event will fire even earlier than .click().

Related

jQuery autocomplete variable scope

I'm having an issue with scope of variables in this function. Basically, when a user focuses on a textbox which will have a jQuery dropdown, I want to save the old value in the textbox, if present in order to restore it if required. I have also tried to declare previous outside the function and as window.previous but without success. The problem is that when I use the previous variable from within the .dropdown function I always get it back as undefined
// Delete option allows a user to delete the value directly from the textbox associated with the dropdown.
// Otherwise he will be warned and always forced to make a choice.
// With value will add an extra value to a textbox that has _val apended to the current id
// Create new, if set will open a new confirmation to add the item to the dropdown list
function acomplete(element, source, deleteoption, withvalue, createnew, createtable, createcolumn, retid) {
var previous;
// Add arrow as this is a dropdown
$(element).addClass("dropdown");
$(element).autocomplete({
source: source,
minLength: 0,
global: false,
select: function (event, ui) {
if (withvalue == true) {
$("#" + $(this).attr("id") + "_val").val(ui.item.thevalue);
//$("#" + $(this).attr("id") + "_val").trigger("change");
}
// Update hidden on select option
$("#" + $(this).attr("id") + "_id").val(ui.item.id);
// For items that have change event bound trigger ot so we are updating data in table.
$("#" + $(this).attr("id") + "_id").trigger("change");
},
focus: function (event, ui) {
// Save old value for backup
previous = this.value;
},
change: function (event, ui) {
//alert($(this).val());
if (!ui.item && $(this).val().length > 0) { // Item not selected in the dropdown list
$.ajax({
url: "ajax/check_dropdown_item_exists.php",
global: false,
method: "POST",
data: {
table: createtable,
colnames: createcolumn,
colvals: encodeURI(String($(this).val().toUpperCase())),
},
success: function (data) {
if (data != "TRUE") {
// Ask confirm to add new item to table
$.confirm('ITEM DOES NOT EXIST! ADD TO LIST?', function (answer) {
if (answer) {
$.ajax({
url: "inc/insert_table_field.php",
global: false,
method:"POST",
data: {
table: createtable,
colnames: createcolumn,
colvals: String($(this).val().toUpperCase()),
retid: retid,
},
success: function (data) {
if ($.isNumeric(data)) {
$("#" + $(element).attr("id") + "_id").val(data);
// Set the newly created value in dropdown
//$(element).val(String($(element).val().toUpperCase()));
// And update DB
$("#" + $(element).attr("id") + "_id").trigger("change");
} else {
$.alert(data);
}
},
error: function () {
$.alert('ERROR CREATING THE NEW ITEM!');
}
})
} else {
alert(previous)
// NO so blank
$(this).val(previous).focus();
}
})
} else {
// Commit change with value that already exists
// fecth item id and trigger select event
$.ajax({
url: "ajax/get_dropdown_item_id.php",
global: false,
method: "POST",
data: {
table: createtable,
colnames: createcolumn,
colvals: String($(element).val().toUpperCase()),
retid: retid,
},
success: function (data) {
if ($.isNumeric(data)) {
$("#" + $(element).attr("id") + "_id").val(data);
$("#" + $(element).attr("id") + "_id").trigger("change");
}
}
})
}
}
})
} else {
$(this).val((ui.item ? ui.item.label : "")); // If empty put back the last one
if (!ui.item) {
if (deleteoption !== true) {
this.value = "";
$.alert('YOU CAN SELECT FROM DROPDOWN ONLY!');
$(element).val(element.oldvalue).focus();
} else {
$("#" + $(this).attr("id") + "_id").val("");
$("#" + $(this).attr("id") + "_id").trigger("change");
}
}
}
}
}).dblclick(function () {
$(this).autocomplete("search", "");
}).click(function () {
$(this).autocomplete("search", "");
})
}
The problem is that focus don't react on focusing the textbox/input, but instead the result from autocomplete.
That means that when you click in the textbox the function focus will not start only if you select a result.
The best solution for you to get previous would be:
$(your element).click(function() {
previous = $(this).val()
}
This is from the documentation of jQueryUi Autocomplete:
focus( event, ui )
Triggered when focus is moved to an item (not selecting). The default action is to replace the text field's value with the value of the focused item, though only if the event was triggered by a keyboard interaction.
Canceling this event prevents the value from being updated, but does not prevent the menu item from being focused.
focus documentation

How to access the value of a select Box as variable onChange inside another function

I want to access the value of #schooSelect inside ajax so i can send some data to php onChange.
$.LoadBooks = function () {
$(document).on('change', '#SchoolSelect', (function (e) {
var SchoolVal = ($(this).val())
$.LoadBooks()
}))
var SchoolVal = ($('#SchoolSelect').val())
$.ajax({
type: "GET",
data: {
data: SchoolVal
},
url: "../php/booksads.php"
}).done(function (feedback) {
$('#booksads').html(feedback)
});
}
$.LoadBooks()
Your code is strangely structured. You are somehow "recursively" calling $.LoadBooks inside the event handler, which will cause a new event handler to be added to the element, which is certainly not what you want.
Just bind the event handler once, outside the function:
var loadBooks = function(schoolVal) {
$.ajax({
type: "GET",
data: {
data: schoolVal
},
url: "../php/booksads.php"
}).done(function (feedback) {
$('#booksads').html(feedback)
});
}
$(document).on('change', '#SchoolSelect', function(e) {
loadBooks($(this).val());
});
You can either pass the value of the select element to the function (as shown here) or call var schoolVal = $('#SchoolSelect').val() inside of it to get the value.
The convention is that only the name of constructor functions start with a capital letter. And if your function is related to jQuery in particular, you shouldn't add it to $.

toggling class on click by javascript on ajax post success

This code works fine for first click as it changes class along with image which is referenced from CSS. But when I click second time it acts like clicked in previous class which I assume removed already.
if(Model.SeenItWantToSeeIt.Status==1)
{
<div class="movie_data">
<div class="usermovie_option"> </div>
</div>
<div class="clear"></div>
}
else{
<div class="movie_data">
<div class="usermovie_option"> </div>
</div>
<div class="clear"></div>
}
And Javascript for toggling class is
$(".want_to_see_it").click(function () {
var wantToSeeIt = $(this);
alert('clicked on want to see it.');
$.ajax({
url: '#Url.Action("SeenIt", "MovieProfile")',
data: { Status: 1, MovieID: movieID },
dataType: 'json',
type: "POST",
success: function (data) {
wantToSeeIt.removeClass();
wantToSeeIt.addClass("dont_want_to_see_it");
$("dont_want_to_see_it").show();
},
error: function (data) {
alert('Error occurred.');
}
});
});
$(".dont_want_to_see_it").click(function () {
alert('clicked on donot want to see it');
var wantToSeeIt = $(this);
$.ajax({
url: '#Url.Action("SeenIt", "MovieProfile")',
data: { Status: 0, MovieID: movieID },
dataType: 'json',
type: "POST",
success: function (data) {
wantToSeeIt.removeClass();
wantToSeeIt.addClass("want_to_see_it");
$("want_to_see_it").show();
},
error: function (data) {
alert('Error occurred.');
}
});
});
And problem is it shows "clicked on donot want to see it" or "clicked on want to see it" as alert every time I click . What I have to do is this message should alternate every time I Click on their respective image.
Problem here is that you want to change the handlers dynamically on click of each element. But events are bound to the element directly using click event.
One option is to hide and show respective items.
Another option is to bind and unbind events.
Third option is to use event delegation. Your requirement will work with this since with event delegation events are not directly attached to the elements, they are instead delegated. So the moment you swap the class name event subscribed for that class name will automatically get delegated. SO next click on the same element will go to the other event handler attached its new class name. See if this is what you were looking for.
$(document).on('click',".want_to_see_it" ,function (e) {
var wantToSeeIt = $(this);
alert('clicked on want to see it.');
///Your ajax
wantToSeeIt.removeClass();
wantToSeeIt.addClass("dont_want_to_see_it");
$(".dont_want_to_see_it").show();
});
$(document).on('click',".dont_want_to_see_it" ,function (e) {
alert('clicked on donot want to see it');
var wantToSeeIt = $(this);
///Your ajax
wantToSeeIt.removeClass();
wantToSeeIt.addClass("want_to_see_it");
$(".want_to_see_it").show();
});
Note:- In the example i have attached to the document, You should n't attach it to the document, instead attach it to any containing element that is present in DOM at any time.
Demo
There was another issue, you missed . before the classname in your ajax success.
The problem is you need to unbind("click") to clear the previous handler then bind a new event handler for its new class.
Instead of unbinding and rebinding, do in one handler:
$(".usermovie_option a").on("click", function () {
var status = 0;
if ($(this).hasClass("want_to_see_it")) {
status = 1;
}
$.ajax({
url: '#Url.Action("SeenIt", "MovieProfile")',
data: { Status: status, MovieID: movieID,
dataType: 'json',
type: "POST",
success: function (data) {
$(this).toggleClass("want_to_see_it");
$(this).toggleClass("dont_want_to_see_it");
},
error: function (data) {
alert('Error occurred.');
}
});
});

jQuery change event returns null when manually fired on $(document).ready();

I'm currently writing a JQuery plugin that loads colors from a JSON web service into a drop down list.
The drop down list background-color changes according to the selected value. For the most part it is working. on any regular change it works as expected, the problem I am having is on the initial page load I am using triggerHandler("change"); and it triggers but I seem to be getting an undefined error on the selected value from the drop down list on page load so it doesn't trigger the color change on the drop down list
My code is:
$.fn.bindColorsList = function (options) {
var defColor = options.defaultColor;
var svcUrl = options.svcurl;
//var f_target = options.filterTarget;
var $this = this;
$.ajax({
url: options.svcurl,
dataType: 'json',
/*data: { filter: src_filt },*/
success: function (fonts) { fillcolors(fonts, $this) },
error: function () { appendError(f_target, "colors failed to load from server") }
});
this.on("change", function (event) {
log($(event.target).attr("id") + " change detected");
//change ddl dropdown color to reflect selected item ;
var hcolor = $this.find('option:selected').attr("name");
$this.attr("style", "background-color:" + hcolor);
});
function fillcolors(colors, target) {
$(target).empty();
$.each(colors, function (i, color) {
$(target).append("<option name='"+color.HexValue+"' value='" + color.Name + "' style='background-color:"+color.HexValue+"'>"+color.Name+"</option>");
});
};
//in a seperate file
$(document).ready(function () {
$("#dd-font-color").bindColorsList({ svcurl: "/home/colors"});
$("#dd-back-color").bindColorsList({ svcurl: "/home/colors" });
});
You are doing an AJAX request to populate your dropdown which, by the way, is an asynchronous one. In this case you need to trigger the event in the success callback of the AJAX request.
var $this = this;
// Bind the onchange event
$this.on("change", function (event) {
..
});
// Populate using AJAX
$.ajax({
...
success: function (fonts) {
// Populate the values
fillcolors(fonts, $this);
// Trigger the event
$this.trigger("change");
},
...
});
That's it.

problem with jquery ui`s autocomplete select callback (1.8)

With this code:
function setupRow(event, ui) {
var textbox, // how do i get to the textbox that triggered this? from there
// on i can find these neighbours:
hiddenField = textbox.next(),
select = textbox.parents('tr').find('select');
textbox.val(ui.item.Name);
hiddenField.val(ui.item.Id);
$.each(ui.item.Uoms, function(i, item){
select.append($('<option>' + item + '</option>'));
});
return false;
}
function setupAutoComplete(){
var serviceUrl = "/inventory/items/suggest";
$("input.inputInvItemName").autocomplete({
source: function(request, response) {
$.ajax({
url: serviceUrl,
data: request,
dataType: "json",
success: function(data) {
response($.map(data.InventoryItems, function(item) {
return {
value: item.Name
};
}));
},
select: function(event, ui) {
setupRow(event, ui);
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
alert(textStatus);
}
});
},
minLength: 3,
delay: 500
});
}
everything seems ok. Problem is the select handler never fires, not even the anonymous function that wraps my original delegate setupRow for debugging purposes is ever called.
anyone can see my error?
I also left a question in the comment: how do I get to the textbox that had the autosuggestion. Cannot use id here, because these text boxes are multiples and generated on the fly, interactively. Or is there another way to do the same thing?
Thanks for any help!
OP point of view
var textbox, // how do i get to the textbox that triggered this? from there
// on i can find these neighbours:
My Point of view
have you tried,
var textbox = $(event.target);
or you can do this,
OP point of view
select: function(event, ui) {
setupRow(event, ui);
},
My point of view
select: setupRow;
then
var textbox = this; // just a guess... wait..
anyone can see my error?
I think you forgot to put ';' .
$.ajax({
url: serviceUrl,
data: request,
dataType: "json",
success: function(data) {
response($.map(data.InventoryItems, function(item) {
return {
value: item.Name
}
}));
Or is there another way to do the same thing?
I think u are using the jquery ui autocomplete plugin.If yes, you can retreive like this.
$('.ui-autocomplete-input')
Otherwise, you can set a specific class to those textboxes and access those textbox through that class.
ok, got a step closer by using
inputs.bind("autocompleteselect", setupRow);
now setupRow fires.
Now it seems, that the success callback transforms the data, I get returned.I need to find a way, to both display the right value in the dropdown, without destroying the requests response...
Any ideas?

Categories

Resources