Trigger JQuery event on ajax response element - javascript

I have a problem with event triggering in my codeigniter project. I want to load a table dynamically in my page. This table is returned from my controller through an ajax call. And I want to trigger a click event in a span in that table. I tried this in many ways, but its not working. I am attaching my code here. please help me to find a solution.
controller :
$str = '<table>
<tr>
<td class="cost date" id="date_'.$request['SupplyID'].'">
<span class="editable" style="display: none;">
<input type="text" class="expiry" autocomplete="off" data-date-id="date_'.$request['SMSSupplyID'].'">
</span>
<span class="cnt" style="display: inline;">Choose</span>
</td>
</tr>
</table>';
echo $str;
script in view :
function loadmore()
{
var url;
url = '/SMS/SMS/loadMoreRequests';
$.ajax({
type: 'post',
url: url,
data: {
limit:val
},
success: function (response) { console.log(response);
$("#requestListTable").html(response);
val +=10;
}
});
}
$('.date').find('.cnt').on('click', function(){
console.log(1); // for testing
});
I tried the following changes, but no use
1)
$('.date').find('.cnt').live('click', function(){
console.log(1); // for testing
});
2)
$('.date').find('.cnt').click(function(){
console.log(1); // for testing
});

$("container for the table").on("click", ".cnt", function() {
});
You can use the event delegation for this. Bind the event to a parent element which is present on the dom on document ready. Or you can simply use,
$("body").on("click", ".cnt", function() {
});

You can try this
$(document).find(".cnt").on("click",function(){
console.log(1); // for testing
});

You need to delegate the Event to the dynamically created elements.
$(document).on('click','.cnt',function(){
alert("Processing comes here");
});

Related

Have to click element twice for Jquery event to work

I have an ajax function that I have to click twice to work. I would like it to just work with one click. It was working before I added a click event that checks the text of what I'm clicking and uses it as part of the URL. My problem likely resides there. I need a fresh perspective on what might be wrong.
Jquery:
function ajaxShow(){
$('#formats a').click(function(e) {
var txt = $(e.target).text();
console.log(txt);
$.ajax({
url : "./enablereports/" + txt + ".html",
data: "html",
contentType:"application/x-javascript; charset:ISO-8859-1",
beforeSend: function(jqXHR) {
jqXHR.overrideMimeType('text/html;charset=iso-8859-1');
},
success : function (data) {
$("#rightDiv").html(data);
}
});
});
}
HTML:
<body>
<div id="wrapper">
<div id="enablestuff" class="yellowblock">
<h3 id="title" class="header">Enable Formats</h3>
</div>
<div id="formats" class="lightorangeblock">
ADDSTAMP<br>
SCLGLDNB<br>
SCLGLVNB<br>
</div>
</div>
<div id="rightWrap">
<div id="rightDiv">
</div>
</div>
</body>
It's cause you're binding the jQuery handler inside of your onclick function - just remove the entire onclick attribute and bind your handler outside the function.
$('#formats a').click(function(e) {
e.preventDefault();
var txt = $(e.target).text();
console.log(txt);
$.ajax({
url : "./enablereports/" + txt + ".html",
data: "html",
contentType:"application/x-javascript; charset:ISO-8859-1",
beforeSend: function(jqXHR) {
jqXHR.overrideMimeType('text/html;charset=iso-8859-1');
},
success : function (data) {
$("#rightDiv").html(data);
}
});
});
And the HTML
<div id="formats" class="lightorangeblock">
ADDSTAMP<br>
SCLGLDNB<br>
SCLGLVNB<br>
</div>
The problem is that each of the anchor elements has an inline event handler that points to ajaxShow, which then sets up the actual event handler for future clicks.
Instead, eliminate the inline handlers and just set up the actual handler without the ajaxShow wrapper.
I would also suggest that you don't use <a> elements since you aren't actually navigating anywhere, so the use of the element is semantically incorrect and will cause problems for people who rely on assistive technologies to use the web. Instead, since you want line breaks in between each "link", use <div> elements and just style them to look like links.
Lastly, you've used the name attribute on one of your last div elements, but name is only valid on form fields. You could give it an id if needed.
$('#formats div').click(function(e) {
var txt = $(e.target).text();
console.log(txt);
$.ajax({
url : "./enablereports/" + txt + ".html",
data: "html",
contentType:"application/x-javascript; charset:ISO-8859-1",
beforeSend: function(jqXHR) {
jqXHR.overrideMimeType('text/html;charset=iso-8859-1');
},
success : function (data) {
$("#rightDiv").html(data);
}
});
});
#formats div { text-decoration:underline; color:blue; cursor:pointer; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="wrapper">
<div id="enablestuff" class="yellowblock">
<h3 id="title" class="header">Enable Formats</h3>
</div>
<div id="formats" class="lightorangeblock">
<div>ADDSTAMP</div>
<div>SCLGLDNB</div>
<div>SCLGLVNB</div>
</div>
</div>
<div id="rightWrap">
<div id="rightDiv"></div>
</div>
I was able to get this working by adding ajaxShow(); into a $(document).ready(function ().
Dirty, but it works.

Table not getting displayed on a button click in AngularJS

Hi I'm learning AngularJS and I have a question. I want to display a table on a button click. On clicking the button, JSON data gets fetched but I have to press the button twice for the data to be displayed.
This is the HTML page.
<html>
<body>
<div class="container">
<label for="tags" style="margin-top: 30px;margin-left: 15px;">GSTIN </label>
<input id="tags">
<button ng-click="searchfunction()">search</button>
</div>
<br/>
<hr>
<div class="container">
<div ng-show="tshow" ng-repeat="x in searchdata">
<table class="table table-bordered table-responsive">
<thead>
<tr>
<th>MON</th>
<th>SGST</th>
<th>CGST</th>
<th>IGST</th>
<th>CESS</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="i in x">
<td>{{i.mon}}</td>
<td>{{i.sgst}}</td>
<td>{{i.cgst}}</td>
<td>{{i.igst}}</td>
<td>{{i.cess}}</td>
</tr>
</tbody>
</table>
</div>
</div>
</body>
</html>
This is the controller:
app.controller("searchcontroller", function ($scope,$http) {
$scope.tshow=false;
function make_base_auth(user, password) {
var tok = user + ':' + password;
var hash = btoa(tok);
return "Basic " + hash;
}
$scope.searchfunction=function() {
$scope.tshow=true;
var tf=document.getElementById("tags");
var value=tf.value;
var auth = make_base_auth("gstadmn112","Gstn#123");
var url6 = "http://164.100.148.67:8080/wsgstr3B/rest/payment/gstinsearch?gstin="+value+"&year=201718";
xml = new XMLHttpRequest();
// jQuery
$.ajax({
url : url6,
method : 'GET',
beforeSend : function(req) {
req.setRequestHeader('Authorization', auth);
},
success:function(response) {
console.log(response);
scope.searchdata=response;
},
failure:function() {
window.alert("wrong input data doesn't exist");
}
});
}
});
I need to click twice on the search button for the table to be displayed. I want the table to be hidden initially and once the search is successful the table should be displayed. The table is hidden initially and after clicking twice correct data gets displayed.
Maybe, you try to add $scope.tshow=true; in function success:
success:function(response) {
console.log(response);
$scope.tshow=true;
$scope.searchdata=response;
},
P.S. I advise to use $http instead of $ajax.
This problem is related to the digest loop of angularjs which keeps all changes sync between your view and controller.
When you invoke the searchfunction(), angularjs will know whats happening inside the method and sync the changes made with the view when its completed.
The problem is that your method uses $.ajax which has some async callback methods.
When these methods gets invoked angularjs have already left the party (digest loops is over) and don't know what these methods have done to your controller $scope.
The jQuery success callback will however set the $scope.searchdata=response; and this change gets notified the next time angularjs is in the party (the next time you click).
So basically you need to make sure angularjs is aware of the async methods which makes changes to your $scope.
To solve this I would inject angularjs own $http service (which takes care of async changes to the scope) and use that instead.
var req = {
method: 'GET',
url: url6,
headers: {
'Authorization': auth
}
}
$http(req).then(function(response){
console.log(response);
$scope.searchdata=response;
}, function(){
window.alert("wrong input data doesn't exist");
});
You can use this way.
$scope.searchfunction=function(){
$scope.tshow=true;
var tf=document.getElementById("tags");
var value=tf.value;
$http.get("http://164.100.148.67:8080/wsgstr3B/rest/payment/gstinsearch?gstin="+value+"&year=201718")
.success(function(result) {
$scope.searchdata=response;
$scope.tshow=false;
})
.error(function() {
window.alert("wrong input data doesn't exist");
});
}

Passing parameters to on click jquery event from dynamic list of anchor tags

I'm working on a list of elements in my asp.net mvc project. Each element is part of a ul, and the list elements are generated based on a list in my model.
I'm trying to add a delete button to each of these elements, but I'm struggelig a bit with how to make these elements unique, for jquery to pass the correct parameters to my action later on.
Each element has its own guid, but I can't figure out how to pass these along to the .on('click') jquery handler.
Here's the relevant part of my razor view:
<ul class="panel-tasks ui-sortable">
#foreach (RunModel run in Model.PlannedRuns)
{
<li>
<label>
<i class="fa fa-edit"></i>
<!--<i class="fa fa-ellipsis-v icon-dragtask"></i>-->
<span class="task-description">#run.Name</span>
<span class="sl-task-details">#run.RunTask</span>
<span class="sl-task-unit">#run.ConveyanceId</span>
<span class="sl-task-location">#run.Operation.WellContract.Location, #run.Operation.WellContract.Name</span>
</label>
<div class="options">
</i>
</div>
</li>
}
</ul>
And here's my javascript:
<script type="text/javascript">
$("#del").on("click", function (runId) {
$.ajax({
url: "#Url.Action("DeleteRun", "Planning")",
type: "GET",
dataType: "json",
data: { runId: runId },
error: function (msg) {
// Error handling
},
success: function (msg) {
// Success handling
}
});
});
</script>
I do realize I could add onClick to the anchor tag passing along the id as a parameter there, but I was hoping using jquery would do the trick, like mentioned above. Also, is there a recommended approach for doing tasks like this when several html elements use the same method?
You can use a data-* parameter on the delete button specific to that instance which you can then retrieve on click. You also need to make the delete button use a class attribute, otherwise they will be duplicated in the loop. Try this:
<div class="options">
<i class="fa fa-trash-o"></i>
</div>
$(".del").on("click", function (e) {
e.preventDefault();
var runid = $(this).data('runid');
$.ajax({
url: "#Url.Action("DeleteRun", "Planning")",
type: "GET",
dataType: "json",
data: { runId: runId },
error: function (msg) {
// Error handling
},
success: function (msg) {
// Success handling
}
});
});
The answers using data- attributes are elegant and do the job. However, I would like to propose a (slightly) different approach:
#foreach (RunModel run in Model.PlannedRuns)
{
<li id="#run.Id">
...........
</li>
}
Inside the a elements, set your del id as class.
$(".del").on("click", function () {
var runid = $(this).parent().id;
//..............
});
The advantages of this solution:
Your li elements have an id which can be used by other JavaScript functions as well
No need to play around with attributes (be careful as Firefox is very picky with data- attributes)
Additionally, your delete a elements won't have duplicate ids.
You can access the item clicked with $(this) in a click event (and most events).
$(".del").on("click", function () {
var runId = $(this).data("runId");
$.ajax({
url: "#Url.Action("DeleteRun", "Planning")",
type: "GET",
dataType: "json",
data: { runId: runId },
error: function (msg) {
// Error handling
},
success: function (msg) {
// Success handling
}
});
});
and insert the id as data-runId= in the HTML:
<i class="fa fa-trash-o"></i>
As the delete button is a boookmark only (#) the only effect it may have is to move the page to the top. To stop that add an event parameter and call preventdefault() on it. (or simply return false from the event handler).
$(".del").on("click", function (e) {
e.preventDefault();
And as Rory McCrossan points out, you should not have duplicate ids on your delete buttons (use a class). Dupe ids will actually work on most browsers, but are considered a bad thing :)

Passing in a global javascript array to jQuery document(ready)

I have the following html rendered from templating (jsRender)
<div class="noteActions top" style="z-index: 3;">
<span onclick="noteAction('add', 13808, 0 );"></span>
<span onclick="noteAction('update',13808, 106344 );"></span>
<span onclick="noteAction('delete', 13808, 106344 );"></span>
</div>
My issue is I have a function outside the document ready that is setting a data array that later, a jquery dialog window submits via ajax to the handler to update the database
What's happening is the data array correctly passes everything except the jquery vals by class selector (pr-body, pr-title), they pass as NULL
javascript - outside document (ready)
var updateUrl = 'handlers/Poster.ashx',
data;
function noteAction(action, prospectID, noteID){
data = {
'operation': action,
'prospectid':prospectID,
'note-body' : $('.pr-body').val(),
'note-title' : $('.pr-title').val(),
'note-id':noteID,
};
if (action == 'add'){
$( "#dialogPostIt" ).dialog("open", "option", "title", "Add Post It");
} else if (action == 'update'){
$( "#dialogPostIt" ).dialog("open", "option", "title", "Edit Post It");
} else if (action == 'delete'){
if (!confirm('Are you sure you want to delete')) return false;
$.post(updateUrl+"?operation=delete&noteid="+noteID, function(data) {
$('#stickyNote-'+noteID).remove();
});
}
}
jquery - document ready
$(document).ready(function() {
$( "#dialogPostIt" ).dialog({autoOpen: false, modal:true,
buttons: {
'Save': function() {
$.ajax({
url: updateUrl,
data: data,
success: function(json, textStatus, jqXHR){
.....
html
<div id="dialogPostIt" >
<form id="postItNow" action="" method="post" class="note-form">
<label for="note-title">Title (description)</label>
<input type="text" name="note-title" id="note-title" class="pr-title" value="" />
<label for="note-body">Text of the note</label>
<textarea name="note-body" id="note-body" class="pr-body" cols="30" rows="6"> </textarea>
</form></div>
I previously was setting the data array inside the dialog save button function(), which worked fine, but I needed to make some of the array elements dynamic based on event
The array doesnt have to be global from my requirements, i just couldnt think of another way todo this
As Always, any help is greatly appreciated
Well, i feel like a real dope, it actually is working fine, issue was pilot error -_-
The data array was returning the values correctly, problem is there was no values yet , as the data was set prior to the subsequent dialog containing the form, so no form vals couldve been filled in yet
the fix
javascript outside the document ready
function noteAction(action, prospectID, noteID){
data = {
'operation': action,
'prospectid':prospectID,
'notebody' : '',
'notetitle' : '',
'noteid':noteID,
};
jquery in dialog (document ready)
$( "#dialogPostIt" ).dialog({autoOpen: false, modal:true,
buttons: {
'Save': function() {
data.notebody = $('.pr-body').val();
data.notetitle= $('.pr-title').val(),
$.ajax({
url: updateUrl,
data: data,

How to detect the div in which a link to a javascript function has been clicked

I have the following html code:
<div id="result1" class="result">
... some html ...
... link
... some html ...
</div>
<div id="result2" class="result">
... some html ...
... link
... some html ...
</div>
<div id="result3" class="result">
</div>
<div id="result4" class="result">
</div>
The goal is to update the content of the next div when I click on the link. So for instance, when I click on a link in #result2, the content of #result3 will be updated.
Here is the javascript function:
<script>
function updateNext(elem, uri) {
$.ajax({
url: uri,
success: function(data) {
elem.closest('.result').nextAll().html('');
elem.closest('.result').next().html(data);
}
});
}
</script>
However, when I use the link, elem is set as the window, not the link itself.
The content of the div is generated by a server which should not know the position of the div in which the code he is generating will be.
I also tried with a
<a href="javascript:" onclick="updateNext(...
with no other result...
any idea ? :-)
Thanks,
Arnaud.
this returns the window when used in href, but here it returns the actual link:
... link
Don't forget to use the jQuery $ in:
$(elem).closest('.result').nextAll().html('');
$(elem).closest('.result').next().html(data);
Why do you use inline scripts when you alrady are using jQuery?
I've setup a Fiddle for you which does what you want: http://jsfiddle.net/eLA3P/1/
The example code:
$('div.result a').click(function() {
$(this).closest('div.result').next().html('test');
return false;
});
First, you must remove those href="javascript:..." attributes. Please never use them again, they are evil.
Then, bind a click handler via jQuery, which you are alredy using:
// since you dynamically self-update the a elements, use "live()":
$("div.result a").live("click", function () {
var $myDiv = $(this).closest("div.result");
$.ajax({
url: "/build/some/url/with/" + $myDiv.attr("id"),
success: function(data) {
$myDiv.next("div.result").html(data);
}
});
return false;
});
Done.
Try to use jQuery to bind the event instead putting a javascript link in the href.
<div id="result1" class="result">
link
</div>
$('.resultLink').click(function(){
var elem = $(this);
$.ajax({
url: uri,
success: function(data) {
elem.closest('.result').nextAll().html('');
elem.closest('.result').next().html(data);
}
});
});
You should do it like this:
http://jsfiddle.net/hJhC7/
The inline JavaScript is gone, and the href is being used to store the "uri", whatever that might be. I'm assuming it's different for each link.
The //remove this lines are just to make $.ajax work with jsFiddle.
$('.update').click(function(e) {
e.preventDefault();
var elem = $(this);
$.ajax({
type: 'post', //remove this
data: {html: Math.random() }, //remove this
url: $(this).attr('href'),
success: function(data) {
//not sure why you're doing this
//elem.closest('.result').nextAll().html('');
elem.closest('.result').next().html(data);
}
});
});
with this HTML:
<div id="result1" class="result">
link
</div>
<div id="result2" class="result">
link
</div>
<div id="result3" class="result">
link
</div>

Categories