How could I call a JQuery function upon a button click? - javascript

I have a JQuery function that fetches and displays a page worth of images through the use of JSON files. I want to display the next set of images upon a button click, but that requires adding on a short string to the request url, which is found and stored in a var when I first run the script. I need to call this JQuery function again and pass the string var to it (lastId in code below). I am an utter noob with JavaScript in general and don't know how to go about doing that.
Here is a full version of the code:
$(function runthis(un){
var lastId;
un = typeof un !== 'undefined' ? un : "";
$('#domainform').on('submit', function(event){
event.preventDefault();
$('#content').html('<center><img src="img/loader.gif" alt="loading..."></center>');
//var lastId;
var domain = $('#s').val();
var newdomain = domain.replace(/\//g, ''); // remove all slashes
var requrl = "http://www.reddit.com/r/";
var getmore;
getmore = "?after=t3_"+un;
var fullurlll = requrl + domain + ".json" + getmore;
$.getJSON(fullurlll, function(json){
var listing = json.data.children;
var html = '<ul class="linklist">\n';
for(var i=0, l=listing.length; i<20; i++) {
var obj = listing[i].data;
var votes = obj.score;
var title = obj.title;
var subtime = obj.created_utc;
var thumb = obj.thumbnail;
var subrdt = "/r/"+obj.subreddit;
var redditurl = "http://www.reddit.com"+obj.permalink;
var subrdturl = "http://www.reddit.com/r/"+obj.subreddit+"/";
var exturl = obj.url;
var imgr = exturl;
var imgrlnk = imgr.replace("target=%22_blank%22","");
var length = 14;
var myString = imgrlnk;
var mycon = imgrlnk;
var end = mycon.substring(0,14);
myString.slice(-4);
var test1 = myString.charAt(0);
var test2 = myString.charAt(1);
var timeago = timeSince(subtime);
if(obj.thumbnail === 'default' || obj.thumbnail === 'nsfw' || obj.thumbnail === '')
thumb = 'img/default-thumb.png';
if(end == "http://i.imgur" ){
$("#MyEdit").html(exturl);
html += '<li class="clearfix">\n';
html += '<img src="'+imgrlnk+'" style="max-width:100%; max-height:750px;">\n';
html += '</li>\n';
html += '<div class="linkdetails"><h2>'+title+'</h2>\n';
/*html += '<p class="subrdt">posted to '+subrdt+' '+timeago+'</p>'; /*'+test1+test2+'*/
html += '</div></li>\n';
}
if (listing && listing.length > 0) {
lastId = listing[listing.length - 1].data.id;
} else {
lastId = undefined;
}
} // end for{} loop
htmlOutput(html);
}); // end getJSON()
}); // end .on(submit) listener
function htmlOutput(html) {
html += '</ul>';
$('#content').html(html);
}
});

The way you currently are executing the function run this doesn't ever leave you a handle to that function. This means it only really exists in the context of document.ready (what $(function()) is a shortcut for).
What you want to do instead is to keep a reference to this function for later use.
If you want to be able to put it directly into an onclick='' you will need to put the function in global,
eg:
var myFunction = function() { /*Stuff here*/}
$(myFunction)
this declares a function called myFunction and then tells jQuery to execute it on document ready
Global is generally considered pretty naughty to edit. One slightly better option would be to assign the click to the button inside your javascript
eg:
$(function(){
var myFunction = function() { /*Stuff here*/}
myFunction(); //call it here
$('#my-button-id').click(myFunction);//attach a click event to the button
)
This means that the function myFunction only exists in the scope of your document.ready, not in global scope (and you don't need onclick='' at all)

tTo add listener on some event you can use live('click',function(){}) Like yhis:
<div id="my-button">some content</div>
<script type="text/javascript">
$('#my-button').live('click',function(){
//your code
})
</script>

Related

Pass 2 Functions Through One OnChange Event - With HREF on both Functions

I have asked something similar in the past but was able to resolve it by separating the functions by events. I need to be able to pass 2 href events in one Onchange Event because it is a dropdown, OR I need to be able to tie the second function into another Event.
This works only when an alert() is inserted. Once I take the alert() out it does not work. I've tried to supress the alert while still keeping it in the code and it works fine. I do not want the alert but I want the results.
HTML Here:
<select id="PartList" class="form-control form-control-lg ml-0" onChange="SelectMain();">
JavaScript Here
function sList() {
var pl = document.getElementById("PartList");
var value = pl.options[pl.selectedIndex].value;
var text = pl.options[pl.selectedIndex].text;
str = 'URL1 HERE='+ "'" + text + "'" ;
//alert(value);
//alert(text);
window.location.href = str;
}
function SelectValue() {
var pv = document.getElementById("PartList");
var value = pv.options[pv.selectedIndex].value;
str = 'URL2 HERE' + value ;
alert(value);
window.location.href = str;
}
function SelectMain() {
sList();
SelectValue();
}
function alert(message) {
console.info(message);
}
This is resolved, for those that come to this question. The problem wasn't with the JavaScript it was because the device I was sending the commands to couldn't handle the commands that fast. I have incorporated the resolved code with troubleshooting techniques.
function sList() {
var pl = document.getElementById("PartList");
var value = pl.options[pl.selectedIndex].value;
var text = pl.options[pl.selectedIndex].text;
str = 'URL1='+ "'" + text + "'" ;
//str1 = 'http://google.com';
//alert(value);
//alert(text);
window.location.href = str;
//window.open(str1);
}
function SelectValue() {
setTimeout(function(){
var pv = document.getElementById("PartList");
var value = pv.options[pv.selectedIndex].value;
str = 'URL2=' + value ;
//str1 = 'http://aol.com';
//alert(value);
window.location.href = str;
//window.open(str1);
},1000);
}

get innerHTML of the children of the currentTarget

I have this part of my html (more than one of same type):
<div class="this-product">
<img src="images/bag2.jpeg" alt="">
<span class="product-name">iPhone</span>
<span class="product-price">345445</span>
</div>
And this part of my javascript code meant to get the innerHTML of the span tags and assign them values as shown:
var productList = document.querySelectorAll('.this-product');
productList.forEach(function (element) {
element.addEventListener('click', function (event) {
var productName = document.getElementsByClassName('product-name')[0].innerHTML;
var productPrice = document.getElementsByClassName('product-price')[0].innerHTML;
var cartProductname = event.currentTarget.productName;
var cartProductprice = event.currentTarget.productPrice;
var cartContent = '<div class="cart-product"><span class="block">'+cartProductname+'</span><span class="block">'+cartProductprice+'</span></div><div class="cart-result">Total = </div><br>'
document.getElementById('dashboard-cart').innerHTML += cartContent;
});
});
Everything works well and every variable above has its value shown well apart from cartProductname and cartProductprice which display as undefined and also vscode tells me that productName is declared but not read. Where could I be wrong?
If I understand your question correctly, you could call querySelector on each product item element that you are iterating like so:
var productList = document.querySelectorAll('.this-product');
productList.forEach(function (element) {
element.addEventListener('click', function (event) {
// Update these two lines like so:
var productName = element.querySelector('.product-name').innerHTML;
var productPrice = element.querySelector('.product-price').innerHTML;
var cartProductname = productName; // event.currentTarget.productName;
var cartProductprice = productPrice; // event.currentTarget.productPrice;
var cartContent = '<div class="cart-product"><span class="block">'+cartProductname+'</span><span class="block">'+cartProductprice+'</span></div><div class="cart-result">Total = </div><br>'
document.getElementById('dashboard-cart').innerHTML += cartContent;
});
});
You can use event.currentTarget.querySelector('.product-name') to get element inside of another element

JQuery multiple input fields of each row keyup function not working

Hello I am trying to make my jquery code in working order but its not working at all, I don't know whats a problem behind it but it contains multiple text boxes in multiple rows, each row calculates its own sum
Here is Fiddle link
Here is my Code
$(document).ready(function(){
$('.employee input[type="text"]').keyup(function() {
var basic_salary = parseInt($('input[name^=txtMonthlyRate]').val());
var advance_salary = parseInt($('input[name^=txtAdvance]').val());
var recover_comm = parseInt($('input[name^=txtRecovery]').val());
var sales_comm = parseInt($('input[name^=txtSales]').val());
var deduction_salary = parseInt($('input[name^=txtDeduction]').val());
var adjustment_salary = parseInt($('input[name^=txtAdjustment]').val());
var total_sum = ((basic_salary+recover_comm+sales_comm) - (deduction_salary + advance_salary)) + adjustment_salary;
$('input[name^=txtTotal]').val(total_sum);
console.log(total_sum)
);
});
The txtSales1, txtDeduction1, txtAdjustment1 variables are camel cased in your javascript, but not on the html input name. So these return NaN.
UPDATE Also, you need to set the context of what you're referring to using the second parameter of a selector function:
$('.employee input[type="text"]').keyup(function(e) {
var $scope = $(this).closest('.employee');
var basic_salary = parseInt($('input[name^=txtMonthlyRate]', $scope).val());
var advance_salary = parseInt($('input[name^=txtAdvance]', $scope).val());
var recover_comm = parseInt($('input[name^=txtRecovery]', $scope).val());
var sales_comm = parseInt($('input[name^=txtSales]', $scope).val());
var deduction_salary = parseInt($('input[name^=txtDeduction]', $scope).val());
var adjustment_salary = parseInt($('input[name^=txtAdjustment]', $scope).val());
var total_sum = ((basic_salary+recover_comm+sales_comm) - (deduction_salary + advance_salary)) + adjustment_salary;
$('input[name^=txtTotal]', $scope).val(total_sum);
});
The txttotal1 needs to be changed to txtTotal1
The fiddle needs a closing }

Get the element below the ready-function code, in jQuery?

For example:
<script>
$(document).ready( function() {
alert( $(this).getBelowElementToThisScript('form').id );
});
</script>
<form id="IamTheNext"></form>
<form id="Iamnot"></form>
This code should show this message: IamTheNext
In addition, the solution needs to work with this example too:
<script src="getbelowelement.js"></script>
<form id="IamTheNext"></form>
<form id="Iamnot"></form>
Thanks
Try this:
var form = $('script[src="getbelowelement.js"]').next();
But I would suggest using the forms id:
var form = $('#IamTheNext');
You could also try giving the script tag an id.
This kind of approach is dangerous; script should never depend that much on where it is in the page.
That said, the following works in Firefox and Chrome and should work in the major browsers (use at your own risk).
See it in action at jsBin. Both <script> ... and <script src="..."> approaches are shown in the same page.
$(document).ready( function () {
invocationsOfThis = (typeof invocationsOfThis == 'number') ? invocationsOfThis + 1 : 1;
var scriptTags = document.getElementsByTagName ('script');
var thisScriptTag = null;
//--- Search scripts for scripts of this type.
for (var foundCnt = 0, J = 0, L = scriptTags.length; J < L; ++J)
{
/*--- Since the script can be either inline or included, search
both the script text and the script src link for our unique
identifier.
*/
var thisTag = scriptTags[J];
var scriptCode = thisTag.innerText || thisTag.textContent;
var scriptSrc = thisTag.src;
//--- IMPORTANT, change pastebin.com to the filename that you use.
if (/invocationsOfThis/i.test (scriptCode) || /pastebin.com/i.test (scriptSrc))
{
//--- Found a copy of this script; is it the right one, based on invocation cnt?
foundCnt++;
if (foundCnt == invocationsOfThis) {
thisScriptTag = thisTag;
break;
}
}
}
if (thisScriptTag) {
//--- Get the target node.
var nextForm = $(thisScriptTag).next ('form');
var nextFormId = nextForm.attr ('id');
//--- Act on the target node. Here we notify the user
nextForm.text ('This is form: "' + nextFormId + '".');
}
} );

How do i solve these issues?

I wrote simplest extension as an exercise in JS coding. This extension checks if some user (of certain social network) is online, and then outputs his/her small image, name and online status in notification alert. It checks profile page every 2 minutes via (setTimeout), but when user becomes "online", i set setTimeout to 45 minutes.(to avoid online alerts every 2 minutes).
It works, but not exactly as i expected. I have 2 issues:
1)When certain user is online and i change user id (via options page) to check another one, it doesnt happen because it waits 45 or less minutes. i tried the following code (in options.html), but it doesnt help.
2)When i change users, image output doesnt work correctly!! It outputs image of previous user!!
How do i fix these problems??
Thanks!
options.html
<script>
onload = function() {
if (localStorage.id){
document.getElementById("identifier").value = localStorage.id;
}
else {
var el = document.createElement("div");
el.innerHTML = "Enter ID!!";
document.getElementsByTagName("body")[0].appendChild(el);
}
};
function onch(){
localStorage.id = document.getElementById("identifier").value;
var bg = chrome.extension.getBackgroundPage();
if(bg.id1){
clearTimeout(bg.id1);
bg.getdata();
}
}
</script>
<body>
<h1>
</h1>
<form id="options">
<h2>Settings</h2>
<label><input type='text' id ='identifier' value='' onchange="onch()"> Enter ID </label>
</form>
</body>
</html>
backg.html
<script type="text/javascript">
var domurl = "http://www.xxxxxxxxxxxxxx.xxx/id";
var txt;
var id1;
var id2;
var imgarres = [];
var imgarr = [];
var imgels = [];
function getdata() {
if (id1){clearTimeout(id1);}
if (id2){clearTimeout(id2);}
var url = getUrl();
var xhr = new XMLHttpRequest();
xhr.open('GET',url, true);
xhr.setRequestHeader('Cache-Control', 'no-cache');
xhr.setRequestHeader('Pragma', 'no-cache');
xhr.onreadystatechange = function() {
if (xhr.readyState == 4) {
txt = xhr.responseText;
var r = txt.indexOf('<b class="fl_r">Online</b>');
var el = document.createElement("div");
el.innerHTML = txt;
var n = imgprocess(el,url);
var nam = el.getElementsByTagName("title")[0].innerHTML;
if (r != -1) {
var notification = webkitNotifications.createNotification(n, nam, 'online!!' );
notification.show();
var id1 = setTimeout(getdata, 60000*45);
}
else {
var id2 = setTimeout(getdata, 60000*2);
}
}}
xhr.send();
}
function imgprocess(text,url){
imgels = text.getElementsByTagName("IMG");
for (var i=0;i< imgels.length;i++){
if (imgels[i].src.indexOf(parse(url)) != -1){
imgarr.push(imgels[i]);
}
}
for (var p=0; p< imgarr.length; p++){
if (imgarr[p].parentNode.nodeName=="A"){
imgarres.push(imgarr[p]);
}
}
var z = imgarres[0].src;
return z;
}
function getUrl(){
if (localStorage.id){
var ur = domurl + localStorage.id;
return ur;
}
else {
var notif = webkitNotifications.createNotification(null, 'blah,blah,blah', 'Enter ID in options!!' );
notif.show();
getdata();
}
}
function init() {
getdata();
}
</script>
</head>
<body onload="init();">
</body>
</html>
In options instead of clearTimeout(bg.id1); try bg.clearTimeout(bg.id1);
For image problem looks like you never clean imgarres array, only adding elements to it and then taking the first one.
PS. You code is very hard to read, maybe if you made it well formatted and didn't use cryptic variable names you would be able to find bugs easier.
UPDATE
I think I know what the problem is. When you are setting the timeout you are using local scope variable because of var keyword, so your id1 is visible only inside this function and global id1 is still undefined. So instead of:
var id1 = setTimeout(getdata, 60000*45);
try:
id1 = setTimeout(getdata, 60000*45);
Because of this if(bg.id1){} inside options is never executed.
(bg.clearTimeout(bg.id1); should work after that, but it is not needed as you are clearing the timeout inside getdata() anyway)

Categories