I am facing a trivial issue with a code found on web that performs a countdown:
Uncommenting var minutes and seconds it works, but if I try to get minutes and seconds variables through getElementById the code does not work anymore.. why? any suggestion to correct this behaviour?
<html>
<head>
<script>
var interval;
//var minutes = 0;
//var seconds = 2;
window.onload = function() {
var minutes = document.getElementById("idtextmin").value;
var seconds = document.getElementById("idtextsec").value;
countdown('countdown');
}
function countdown(element) {
interval = setInterval(function() {
var el = document.getElementById(element);
if(seconds == 0) {
if(minutes == 0) {
el.innerHTML = "countdown's over!";
clearInterval(interval);
return;
} else {
minutes--;
seconds = 60;
}
}
if(minutes > 0) {
var minute_text = minutes + (minutes > 1 ? ' minutes' : ' minute');
} else {
var minute_text = '';
}
var second_text = seconds > 1 ? 'seconds' : 'second';
el.innerHTML = minute_text + ' ' + seconds + ' ' + second_text + ' remaining';
seconds--;
}, 1000);
}
</script>
</head>
<body>
<form>
Min<input type="text" id="idtextmin" name="textmin" value="2" />
Sec<input type="text" id="idtextsec" name="textsec" value="9" />
</form>
<div id='countdown'></div>
</body>
</html>
Move your code after your HTML, getElementById won't find them because they're not yet declared. As alternative move them inside your onload function:
<script>
// Declare them here, assign their initial value
// in the onload event when HTML elements will be available
var minutes;
var seconds;
window.onload = function() {
minutes = document.getElementById("idtextmin").value;
seconds = document.getElementById("idtextsec").value;
countdown('countdown');
}
function countdown(element) {
interval = setInterval(function() {
var el = document.getElementById(element);
if(seconds == 0) {
if(minutes == 0) {
el.innerHTML = "countdown's over!";
clearInterval(interval);
return;
} else {
minutes--;
seconds = 60;
}
}
if(minutes > 0) {
var minute_text = minutes + (minutes > 1 ? ' minutes' : ' minute');
} else {
var minute_text = '';
}
var second_text = seconds > 1 ? 'seconds' : 'second';
el.innerHTML = minute_text + ' ' + seconds + ' ' + second_text + ' remaining';
seconds--;
}, 1000);
}
</script>
</head>
<body>
<form>
Min<input type="text" id="idtextmin" name="textmin" value="2" />
Sec<input type="text" id="idtextsec" name="textsec" value="9" />
</form>
<div id='countdown'></div>
</body>
</html>
Its because you are setting the minutes and second and again then setting it by get element id the is jumbling up code that u use.
Also try the javascript at end of the body. always leta the rendering complete then run script.
put everything inside the window.onload function
this works for me:
<html>
<head>
<script>
var interval;
//var minutes = 0;
//var seconds = 2;
window.onload = function() {
var minutes = document.getElementById("idtextmin").value;
var seconds = document.getElementById("idtextsec").value;
countdown('countdown');
function countdown(element) {
interval = setInterval(function() {
var el = document.getElementById(element);
if(seconds == 0) {
if(minutes == 0) {
el.innerHTML = "countdown's over!";
clearInterval(interval);
return;
} else {
minutes--;
seconds = 60;
}
}
if(minutes > 0) {
var minute_text = minutes + (minutes > 1 ? ' minutes' : ' minute');
} else {
var minute_text = '';
}
var second_text = seconds > 1 ? 'seconds' : 'second';
el.innerHTML = minute_text + ' ' + seconds + ' ' + second_text + ' remaining';
seconds--;
}, 1000);
}
}
</script>
</head>
<body>
<form>
Min<input type="text" id="idtextmin" name="textmin" value="2" />
Sec<input type="text" id="idtextsec" name="textsec" value="9" />
</form>
<div id='countdown'></div>
</body>
</html>
Related
While everything is running in the software, I get this error when I make a selection from the dropdown list in only one part. Where am I making a mistake? or is it a server error?
I have not received this error in any Laravel before. When trying to get something from a dropdown list, this error comes to the console and there is no reaction on the site.
https://prnt.sc/vaujzf
<script type="text/javascript">
$("ul#product").siblings('a').attr('aria-expanded','true');
$("ul#product").addClass("show");
$("ul#product #adjustment-create-menu").addClass("active");
var lims_product_array = [];
var product_code = [];
var product_name = [];
var product_qty = [];
$('.selectpicker').selectpicker({
style: 'btn-link',
});
$('#lims_productcodeSearch').on('input', function() {
var warehouse_id = $('#warehouse_id').val();
temp_data = $('#lims_productcodeSearch').val();
if (!warehouse_id) {
$('#lims_productcodeSearch').val(temp_data.substring(0, temp_data.length - 1));
alert('Please select Warehouse!');
}
});
$('select[name="warehouse_id"]').on('change', function() {
var id = $(this).val();
$.get('getproduct/' + id, function(data) {
lims_product_array = [];
product_code = data[0];
product_name = data[1];
product_qty = data[2];
$.each(product_code, function(index) {
lims_product_array.push(product_code[index] + ' (' + product_name[index] + ')');
});
});
});
var lims_productcodeSearch = $('#lims_productcodeSearch');
lims_productcodeSearch.autocomplete({
source: function(request, response) {
var matcher = new RegExp(".?" + $.ui.autocomplete.escapeRegex(request.term), "i");
response($.grep(lims_product_array, function(item) {
return matcher.test(item);
}));
},
response: function(event, ui) {
if (ui.content.length == 1) {
var data = ui.content[0].value;
$(this).autocomplete( "close" );
productSearch(data);
};
},
select: function(event, ui) {
var data = ui.item.value;
productSearch(data);
}
});
$("#myTable").on('input', '.qty', function() {
rowindex = $(this).closest('tr').index();
checkQuantity($(this).val(), true);
});
$("table.order-list tbody").on("click", ".ibtnDel", function(event) {
rowindex = $(this).closest('tr').index();
$(this).closest("tr").remove();
calculateTotal();
});
$(window).keydown(function(e) {
if (e.which == 13) {
var $targ = $(e.target);
if (!$targ.is("textarea") && !$targ.is(":button,:submit")) {
var focusNext = false;
$(this).find(":input:visible:not([disabled],[readonly]), a").each(function() {
if (this === e.target) {
focusNext = true;
}
else if (focusNext) {
$(this).focus();
return false;
}
});
return false;
}
}
});
$('#adjustment-form').on('submit', function(e) {
var rownumber = $('table.order-list tbody tr:last').index();
if (rownumber < 0) {
alert("Please insert product to order table!")
e.preventDefault();
}
});
function productSearch(data) {
$.ajax({
type: 'GET',
url: 'lims_product_search',
data: {
data: data
},
success: function(data) {
var flag = 1;
$(".product-code").each(function(i) {
if ($(this).val() == data[1]) {
rowindex = i;
var qty = parseFloat($('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ') .qty').val()) + 1;
$('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ') .qty').val(qty);
checkQuantity(qty);
flag = 0;
}
});
$("input[name='product_code_name']").val('');
if(flag) {
var newRow = $("<tr>");
var cols = '';
cols += '<td>' + data[0] + '</td>';
cols += '<td>' + data[1] + '</td>';
cols += '<td><input type="number" class="form-control qty" name="qty[]" value="1" required step="any" /></td>';
cols += '<td class="action"><select name="action[]" class="form-control act-val"><option value="-">{{trans("file.Subtraction")}}</option><option value="+">{{trans("file.Addition")}}</option></select></td>';
cols += '<td><button type="button" class="ibtnDel btn btn-md btn-danger">{{trans("file.delete")}}</button></td>';
cols += '<input type="hidden" class="product-code" name="product_code[]" value="' + data[1] + '"/>';
cols += '<input type="hidden" class="product-id" name="product_id[]" value="' + data[2] + '"/>';
newRow.append(cols);
$("table.order-list tbody").append(newRow);
rowindex = newRow.index();
calculateTotal();
}
}
});
}
function checkQuantity(qty) {
var row_product_code = $('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ')').find('td:nth-child(2)').text();
var action = $('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ')').find('.act-val').val();
var pos = product_code.indexOf(row_product_code);
if ( (qty > parseFloat(product_qty[pos])) && (action == '-') ) {
alert('Quantity exceeds stock quantity!');
var row_qty = $('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ')').find('.qty').val();
row_qty = row_qty.substring(0, row_qty.length - 1);
$('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ')').find('.qty').val(row_qty);
}
else {
$('table.order-list tbody tr:nth-child(' + (rowindex + 1) + ')').find('.qty').val(qty);
}
calculateTotal();
}
function calculateTotal() {
var total_qty = 0;
$(".qty").each(function() {
if ($(this).val() == '') {
total_qty += 0;
} else {
total_qty += parseFloat($(this).val());
}
});
$("#total-qty").text(total_qty);
$('input[name="total_qty"]').val(total_qty);
$('input[name="item"]').val($('table.order-list tbody tr:last').index() + 1);
}
</script>
I have the following JS and HTML code and I want to disable the button when ajax request is submitting so the user wont be able to double click and disturb the process.
function doReshare(_intPostId) {
if(typeof cLogin === 'undefined')
var cLogin = checkLogin();
if(cLogin!=true)
return;
var date = new Date();
var mainId = _intPostId;
var type = 1;
var active = 0;
var postFinded = 0;
jQuery(".reshare_" + _intPostId).each(function() {
postFinded = 1;
objElement = jQuery(this);
if(objElement.hasClass('sm2_playing') || objElement.hasClass('sm2_paused')) {
// track is active
active = 1;
}
if(objElement.hasClass('is_album')) {
mainId = objElement.closest('div.playlist-box').attr('id').replace('album_', '');
// mainId = objElement.data('mainid');
}
var intLikesCurrentCount = parseInt(objElement.find(".likes_count").first().text(), 10);
if(!objElement.find(".refeed_fct").hasClass("active")) {
if(active)
jQuery('.player-icons.dorepost').addClass('active');
objElement.find(".refeed_fct").addClass("active");
//objElement.find(".likes_count").html("<i class=\"fa fa-heart-o\"></i> " + (intLikesCurrentCount + 1));
} else {
objElement.find(".refeed_fct").removeClass("active");
if(active)
jQuery('.player-icons.dorepost').removeClass('active');
type = 0;
//objElement.find(".likes_count").html("<i class=\"fa fa-heart-o\"></i> " + (intLikesCurrentCount - 1));
}
});
if(!postFinded) {
if(!jQuery(".player-icons.dorepost").hasClass("active")) {
jQuery('.player-icons.dorepost').addClass('active');
} else {
jQuery('.player-icons.dorepost').removeClass('active');
}
}
jQuery("#vowave").append('<img width="1" height="1" src="/reshare/' + mainId + '/' + type + '?time=' + date.getTime() + '" />');
}
and the html
<span class="refeed_fct" onclick="doReshare(10309)">
<i class="fa fa-retweet"></i> <div class="inline hidden-mobile">Repost</div>
</span>
Thank you
Maybe you should set the objElement's onclick listener to an empty function
There is a problem with my run time execution in my code. It takes too long to finish, since I have to loop a large amounts of data to look for matching data. I used array on the first loop value though, I don't know how to array the second value without affecting the first array.
Name of the first array : Source
Name of the Second array : Target
Here is my Code:
function inactive_sort_cebu() {
var ss = SpreadsheetApp.openById('169vIeTMLK4zN5VGCw1ktRteCwMToU8eGABFDxg52QBk');
// var sheet = ss.getSheets()[0];// Manila Roster
var sheet2 = ss.getSheets()[1];// Cebu Roster
var column = sheet2.getRange("C1:C").getValues();
var last = column.filter(String).length;
// -----------------------------------------------------------
var ss1 = SpreadsheetApp.openById('153ul2x2GpSopfMkCZiXCjmqdPTYhx4QiOdP5SBYzQkc');
// var sched_sheet = ss1.getSheets()[0];// ScheduledForm_Manila
var sched_sheet2 = ss1.getSheets()[1];// ScheduledForm_Cebu
var column2 = sched_sheet2.getRange("C1:C").getValues();
var last2 = column2.filter(String).length;
//// -------------------------Manila-Roster---------------------------------
var i= 2;
var column3 = sched_sheet2.getRange("J1:J").getValues();
var a = column3.filter(String).length - 1;
// var a = 0;
try{
var source = sched_sheet2.getRange("C2:C").getValues();
for (a;a<=last2;){
/// this is the code that i need to array without affecting the other array which is the source variable
var target = sheet2.getRange("C"+ i).getValue();
if(source[a] == target){
// Get "No Schedule Request data on Cell H
var data = sched_sheet2.getRange("H"+(a+2)).getValue();
// Get "Schedule Request data on Cell F
var data1 = sched_sheet2.getRange("F"+(a+2)).getValue();
var condition_1 = sched_sheet2.getRange("D"+(a+2)).getValue();
var condition_2 = sched_sheet2.getRange("G"+(a+2)).getValue();
var format_Con_2 = Utilities.formatDate(condition_2, 'Asia/Manila', 'm/dd/yyyy');
var condition_3 = sched_sheet2.getRange("K"+ (a+2)).getValue();
var date = new Date();
var date_Manila = Utilities.formatDate(date, 'Asia/Manila', 'm/dd/yyyy');
if(condition_1 == "No Schedule Request" && format_Con_2 <= date_Manila && condition_3 ==""){
sheet2.getRange("AA"+ i).setValue("N - "+ data);
sched_sheet2.getRange("J"+ (a+2)).setValue("Cebu");
sched_sheet2.getRange("K"+ (a+2)).setValue("Done");
a++;
}
else if (condition_1 == "Schedule Request" && format_Con_2 <= date_Manila && condition_3 ==""){
sheet2.getRange("AA"+ i).setValue("Y - "+data1);
sched_sheet2.getRange("J"+ (a+2)).setValue("Cebu");
sched_sheet2.getRange("K"+ (a+2)).setValue("Done");
a++;
}
else{a++;}
i=2;}
else {i++;}
}
This is a simple example of a web app that puts an editable spreadsheet on an HTML Page. Publish as a webapp. I loops through the 2D array that you get when you getValues from the getDataRange() method. In this case I'm just intertwining html into the mix.
Code.gs:
var SSID='SpreadsheetID';
var sheetName='Sheet Name';
function htmlSpreadsheet(mode)
{
var mode=(typeof(mode)!='undefined')?mode:'dialog';
var br='<br />';
var s='';
var hdrRows=1;
var ss=SpreadsheetApp.openById(SSID);
var sht=ss.getSheetByName(sheetName);
var rng=sht.getDataRange();
var rngA=rng.getValues();
s+='<table>';
for(var i=0;i<rngA.length;i++)
{
s+='<tr>';
for(var j=0;j<rngA[i].length;j++)
{
if(i<hdrRows)
{
s+='<th id="cell' + i + j + '">' + '<input id="txt' + i + j + '" type="text" value="' + rngA[i][j] + '" size="10" onChange="updateSS(' + i + ',' + j + ');" />' + '</th>';
}
else
{
s+='<td id="cell' + i + j + '">' + '<input id="txt' + i + j + '" type="text" value="' + rngA[i][j] + '" size="10" onChange="updateSS(' + i + ',' + j + ');" />' + '</th>';
}
}
s+='</tr>';
}
s+='</table>';
//s+='<div id="success"></div>';
s+='</body></html>';
switch (mode)
{
case 'dialog':
var userInterface=HtmlService.createHtmlOutputFromFile('htmlss').setWidth(1000).setHeight(450);
userInterface.append(s);
SpreadsheetApp.getUi().showModelessDialog(userInterface, 'Spreadsheet Data for ' + ss.getName() + ' Sheet: ' + sht.getName());
break;
case 'web':
var userInterface=HtmlService.createHtmlOutputFromFile('htmlss').setWidth(1000).setHeight(450);
return userInterface.append(s).setXFrameOptionsMode(HtmlService.XFrameOptionsMode.ALLOWALL);
}
}
function updateSpreadsheet(i,j,value)
{
var ss=SpreadsheetApp.openById(SSID);
var sht=ss.getSheetByName(sheetName);
var rng=sht.getDataRange();
var rngA=rng.getValues();
rngA[i][j]=value;
rng.setValues(rngA);
var data = {'message':'Cell[' + Number(i + 1) + '][' + Number(j + 1) + '] Has been updated', 'ridx': i, 'cidx': j};
return data;
}
function doGet()
{
var output=htmlSpreadsheet('web');
return output;
}
htmlss.html:
<!DOCTYPE html>
<html>
<head>
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script>
$(function() {
});
function updateSS(i,j)
{
var str='#txt' + String(i) + String(j);
var value=$(str).val();
$(str).css('background-color','#ffff00');
google.script.run
.withSuccessHandler(successHandler)
.updateSpreadsheet(i,j,value)
}
function successHandler(data)
{
$('#success').text(data.message);
$('#txt' + data.ridx + data.cidx).css('background-color','#ffffff');
}
console.log('My Code');
</script>
<style>
th{text-align:left}
</style>
</head>
<body>
<div id="success"></div>
My page gets a response from response_ajax.php with this code:
<input class="btn" name="send_button" type="button" value="check"
onClick=
"xmlhttpPost('/response_ajax.php',
'MyForm',
'MyResult',
'<img src=/busy.gif>')";
return false;"
>
I get a response; however, jQuery scripts don't work with an arrived code. I'm trying to add script inside response_ajax.php, but nothing happens:
<?php
// ... //
echo '
<div id="whois-response">
<pre>' .$str. '</pre>
</div>
<script>
(function($){
$(function(){
alert("loaded");
});
})(jQuery);
</script>
';
?>
xmlhttpPost function:
function xmlhttpPost(strURL,formname,responsediv,responsemsg) {
var xmlHttpReq = false;
var self = this;
// Xhr per Mozilla/Safari/Ie7
if (window.XMLHttpRequest) {
self.xmlHttpReq = new XMLHttpRequest();
}
// per tutte le altre versioni di IE
else if (window.ActiveXObject) {
self.xmlHttpReq = new ActiveXObject("Microsoft.XMLHTTP");
}
self.xmlHttpReq.open('POST', strURL, true);
self.xmlHttpReq.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
self.xmlHttpReq.onreadystatechange = function() {
if (self.xmlHttpReq.readyState == 4) {
// Quando pronta, visualizzo la risposta del form
updatepage(self.xmlHttpReq.responseText,responsediv);
}
else{
// In attesa della risposta del form visualizzo il msg di attesa
updatepage(responsemsg,responsediv);
}
}
self.xmlHttpReq.send(getquerystring(formname));
}
function getquerystring(formname) {
var form = document.forms[formname];
var qstr = "";
function GetElemValue(name, value) {
qstr += (qstr.length > 0 ? "&" : "")
+ escape(name).replace(/\+/g, "%2B") + "="
+ escape(value ? value : "").replace(/\+/g, "%2B");
//+ escape(value ? value : "").replace(/\n/g, "%0D");
}
var elemArray = form.elements;
for (var i = 0; i < elemArray.length; i++) {
var element = elemArray[i];
var elemType = element.type.toUpperCase();
var elemName = element.name;
if (elemName) {
if (elemType == "TEXT"
|| elemType == "TEXTAREA"
|| elemType == "PASSWORD"
|| elemType == "BUTTON"
|| elemType == "RESET"
|| elemType == "SUBMIT"
|| elemType == "FILE"
|| elemType == "IMAGE"
|| elemType == "HIDDEN")
GetElemValue(elemName, element.value);
else if (elemType == "CHECKBOX" && element.checked)
GetElemValue(elemName,
element.value ? element.value : "On");
else if (elemType == "RADIO" && element.checked)
GetElemValue(elemName, element.value);
else if (elemType.indexOf("SELECT") != -1)
for (var j = 0; j < element.options.length; j++) {
var option = element.options[j];
if (option.selected)
GetElemValue(elemName,
option.value ? option.value : option.text);
}
}
}
return qstr;
}
function updatepage(str,responsediv){
document.getElementById(responsediv).innerHTML = str;
}
I may be wrong, but I'm pretty sure you can't do multiline strings unless it is configured to do so (and running a newer version of PHP):
echo '
<div id="whois-response">
<pre>' .$str. '</pre>
</div>
<script>
(function($){
$(function(){
alert("loaded");
});
})(jQuery);
</script>
';
Try changing that to:
echo <<<EOD
<div id="whois-response">
<pre> $str </pre>
</div>
<script>
(function($){
$(function(){
alert("loaded");
});
})(jQuery);
</script>
EOD;
I think your AJAX response is a PHP error instead of the script you think it is returning.
Got it to work by adding jQuery staff as a function
function updatepage(str,responsediv){
document.getElementById(responsediv).innerHTML = str;
(function($){
$(function(){
$('html').my_jQuery_staff();
});
})(jQuery);
}
Main JavaScript file with jQuery:
// ~~ jQuery ~~
$(document).ready(function () {
$.fn.my_jQuery_staff= function() {
return this.each(function() {
// Include jQuery staff here.
});
};
$('html').my_jQuery_staff();
});
I am using jquery ajax to pull from the twitter api, i'm sure there's a easy way, but I can't find it on how to get the "tweet" to render any links that were tweeted to appear as a link. Right now it's only text.
$.ajax({
type : 'GET',
dataType : 'jsonp',
url : 'http://search.twitter.com/search.json?q=nettuts&rpp=2',
success : function(tweets) {
var twitter = $.map(tweets.results, function(obj, index) {
return {
username : obj.from_user,
tweet : obj.text,
imgSource : obj.profile_image_url,
geo : obj.geo
};
});
UPDATE:
The following function (plugin) works perfectly.
(function($) {
$.socialFader = function(options) {
var settings = {
tweetHolder : null,
tweetCount : 100,
fadeSpeed : 500,
tweetName: 'jquery'
};
if (options) {
$.extend(settings, options);
};
var URL = "http://search.twitter.com/search.json?q="+settings.tweetName+"&rpp=" + settings.tweetCount + "&callback=?";
function relative_time(time_value) {
var values = time_value.split(" ");
time_value = values[1] + " " + values[2] + ", " + values[5] + " " + values[3];
var parsed_date = Date.parse(time_value);
var relative_to = (arguments.length > 1) ? arguments[1] : new Date();
var delta = parseInt((relative_to.getTime() - parsed_date) / 1000);
delta = delta + (relative_to.getTimezoneOffset() * 60);
var r = '';
if (delta < 60) {
r = 'a minute ago';
} else if(delta < 120) {
r = 'couple of minutes ago';
} else if(delta < (45*60)) {
r = (parseInt(delta / 60)).toString() + ' minutes ago';
} else if(delta < (90*60)) {
r = 'an hour ago';
} else if(delta < (24*60*60)) {
r = '' + (parseInt(delta / 3600)).toString() + ' hours ago';
} else if(delta < (48*60*60)) {
r = '1 day ago';
} else {
r = (parseInt(delta / 86400)).toString() + ' days ago';
}
return r;
};
String.prototype.hashify = function() {
return this.replace(/#([A-Za-z0-9\/\.]*)/g, function(m) {
return '<a target="_new" href="http://twitter.com/search?q=' + m.replace('#','') + '">' + m + "</a>";
});
};
String.prototype.linkify = function(){
return this.replace(/[A-Za-z]+:\/\/[A-Za-z0-9-_]+\.[A-Za-z0-9-_:%&\?\/.=]+/, function(m) {
return m.link(m);
});
};
String.prototype.atify = function() {
return this.replace(/#[\w]+/g, function(m) {
return '' + m + "";
});
};
$.getJSON(URL, function(JSON) {
$.each(JSON.results, function(i, tweet) {
var profilePicture = tweet.profile_image_url;
var userLink = tweet.from_user;
var text = tweet.text;
text = text.linkify().atify().hashify();
var createdAt = new Date(tweet.created_at);
var myTweet = '' + userLink + ' ';
myTweet += text;
$(settings.tweetHolder).append('<li class="cycles">' + myTweet + '</li>');
});
var elements = $(settings.tweetHolder).children();
var timeOutStart = 5000;
function fader(elementId) {
setTimeout(function() {
$(elements[elementId]).fadeOut(settings.fadeSpeed, function() {
$(elements[elementId + 1]).fadeIn(settings.fadeSpeed);
});
}, timeOutStart * (elementId));
};
for (var j = 0; j < elements.length; j++) {
fader(j);
};
});
};
})(jQuery);
Within my Ready Statement :
$.socialFader({ tweetHolder:"#twitter", tweetName:"nettuts", tweetCount:2 });
Here is a plugin I wrote which really simplifies the tweet/json aggregation then parsing. It fades the tweets in and out. Just grab the needed code. Enjoy.
(function($) {
$.socialFader = function(options) {
var settings = {
tweetHolder : null,
tweetCount : 99,
fadeSpeed : 500,
};
if (options) {
$.extend(settings, options);
};
var URL = "http://search.twitter.com/search.json?q=jquery&rpp=" + settings.tweetCount + "&callback=?";
function relative_time(time_value) {
var values = time_value.split(" ");
time_value = values[1] + " " + values[2] + ", " + values[5] + " " + values[3];
var parsed_date = Date.parse(time_value);
var relative_to = (arguments.length > 1) ? arguments[1] : new Date();
var delta = parseInt((relative_to.getTime() - parsed_date) / 1000);
delta = delta + (relative_to.getTimezoneOffset() * 60);
var r = '';
if (delta < 60) {
r = 'a minute ago';
} else if(delta < 120) {
r = 'couple of minutes ago';
} else if(delta < (45*60)) {
r = (parseInt(delta / 60)).toString() + ' minutes ago';
} else if(delta < (90*60)) {
r = 'an hour ago';
} else if(delta < (24*60*60)) {
r = '' + (parseInt(delta / 3600)).toString() + ' hours ago';
} else if(delta < (48*60*60)) {
r = '1 day ago';
} else {
r = (parseInt(delta / 86400)).toString() + ' days ago';
}
return r;
};
String.prototype.hashify = function() {
return this.replace(/#([A-Za-z0-9\/\.]*)/g, function(m) {
return '<a target="_new" href="http://twitter.com/search?q=' + m.replace('#','') + '">' + m + "</a>";
});
};
String.prototype.linkify = function(){
return this.replace(/[A-Za-z]+:\/\/[A-Za-z0-9-_]+\.[A-Za-z0-9-_:%&\?\/.=]+/, function(m) {
return m.link(m);
});
};
String.prototype.atify = function() {
return this.replace(/#[\w]+/g, function(m) {
return '' + m + "";
});
};
$.getJSON(URL, function(JSON) {
$.each(JSON.results, function(i, tweet) {
var profilePicture = tweet.profile_image_url;
var userLink = tweet.from_user;
var text = tweet.text;
text = text.linkify().atify().hashify();
var createdAt = new Date(tweet.created_at);
var myTweet = '' + userLink + ' ';
myTweet += text;
$(settings.tweetHolder).append('<li class="cycles">' + myTweet + '</li>');
});
var elements = $(settings.tweetHolder).children();
var timeOutStart = 5000;
function fader(elementId) {
setTimeout(function() {
$(elements[elementId]).fadeOut(settings.fadeSpeed, function() {
$(elements[elementId + 1]).fadeIn(settings.fadeSpeed);
});
}, timeOutStart * (elementId));
};
for (var j = 0; j < elements.length; j++) {
fader(j);
};
});
};
})(jQuery);
You need to parse the tweet content, find the urls and then put them in between yourself.
Unfortunately, at the moment, the search API doesn't have the facility to break out tweet entities (i.e., links, mentions, hashtags) like some of the REST API methods. So, you could either parse out the entities yourself (I use regular expressions) or call back into the rest API to get the entities.
If you decide to call back into the REST API, and once you have extracted the status ID from the search API results, you would make a call to statuses/show like the following:
http://api.twitter.com/1/statuses/show/60183527282577408.json?include_entities=true
In the resultant JSON, notice the entities object.
"entities":{"urls":[{"expanded_url":null,"indices":[68,88],"url":"http:\/\/bit.ly\/gWZmaJ"}],"user_mentions":[],"hashtags":[{"text":"wordpress","indices":[89,99]}]}
You can use the above to locate the specific entities in the tweet (which occur between the string positions denoted by the indices property) and transform them appropriately.
If you prefer to parse the entities yourself, here are the (.NET Framework) regular expressions I use:
Link Match Pattern
(?:<\w+.*?>|[^=!:'"/]|^)((?:https?://|www\.)[-\w]+(?:\.[-\w]+)*(?::\d+)?(?:/(?:(?:[~\w\+%-]|(?:[,.;#:][^\s$]))+)?)*(?:\?[\w\+%&=.;:-]+)?(?:\#[\w\-\.]*)?)(?:\p{P}|\s|<|$)
Mention Match Pattern
\B#([\w\d_]+)
Hashtag Match Pattern
(?:(?:^#|[\s\(\[]#(?!\d\s))(\w+(?:[_\-\.\+\/]\w+)*)+)
Twitter also provides an open source library that helps capture Twitter-specific entities like links, mentions and hashtags. This java file contains the code defining the regular expressions that Twitter uses, and this yml file contains test strings and expected outcomes of many unit tests that exercise the regular expressions in the Twitter library.
How you process the tweet is up to you, however I process a copy of the original tweet, and pull all the links first, replacing them in the copy with spaces (so as not to modify the string length.) I capture the start and end locations of the match in the string, along with the matched content. I then pull mentions, then hashtags -- again replacing them in the tweet copy with spaces.
This approach ensures that I don't find false positives for mentions and hashtags in any links in the tweet.
I slightly modified previous one. Nothing lefts after all tweets disappears one by one.
Now it checks if there is any visible tweets and then refreshes tweets.
(function($) {
$.socialFader = function(options) {
var settings = {
tweetHolder : null,
tweetCount : 99,
fadeSpeed : 500,
};
if (options) {
$.extend(settings, options);
};
var URL = "http://search.twitter.com/search.json?q=istanbul&rpp=" + settings.tweetCount + "&callback=?";
function relative_time(time_value) {
var values = time_value.split(" ");
time_value = values[1] + " " + values[2] + ", " + values[5] + " " + values[3];
var parsed_date = Date.parse(time_value);
var relative_to = (arguments.length > 1) ? arguments[1] : new Date();
var delta = parseInt((relative_to.getTime() - parsed_date) / 1000);
delta = delta + (relative_to.getTimezoneOffset() * 60);
var r = '';
if (delta < 60) {
r = 'a minute ago';
} else if(delta < 120) {
r = 'couple of minutes ago';
} else if(delta < (45*60)) {
r = (parseInt(delta / 60)).toString() + ' minutes ago';
} else if(delta < (90*60)) {
r = 'an hour ago';
} else if(delta < (24*60*60)) {
r = '' + (parseInt(delta / 3600)).toString() + ' hours ago';
} else if(delta < (48*60*60)) {
r = '1 day ago';
} else {
r = (parseInt(delta / 86400)).toString() + ' days ago';
}
return r;
};
String.prototype.hashify = function() {
return this.replace(/#([A-Za-z0-9\/\.]*)/g, function(m) {
return '<a target="_new" href="http://twitter.com/search?q=' + m.replace('#','') + '">' + m + "</a>";
});
};
String.prototype.linkify = function(){
return this.replace(/[A-Za-z]+:\/\/[A-Za-z0-9-_]+\.[A-Za-z0-9-_:%&\?\/.=]+/, function(m) {
return m.link(m);
});
};
String.prototype.atify = function() {
return this.replace(/#[\w]+/g, function(m) {
return '' + m + "";
});
};
$.getJSON(URL, function(JSON) {
$(settings.tweetHolder).find('li.cycles').remove();
$.each(JSON.results, function(i, tweet) {
var profilePicture = tweet.profile_image_url;
var userLink = tweet.from_user;
var text = tweet.text;
text = text.linkify().atify().hashify();
var createdAt = new Date(tweet.created_at);
var myTweet = '' + userLink + ' ';
myTweet += text;
$(settings.tweetHolder).append('<li class="cycles">' + myTweet + '</li>');
});
var elements = $(settings.tweetHolder).children();
var timeOutStart = 5000;
function fader(elementId) {
setTimeout(function() {
$(elements[elementId]).fadeOut(settings.fadeSpeed, function() {
$(elements[elementId + 1]).fadeIn(settings.fadeSpeed);
});
if (jQuery('#twitter ul li.cycles:visible').length==1) {
jQuery.socialFader({ tweetHolder:"#twitter ul", tweetCount:5 });
}
}, timeOutStart * (elementId));
};
for (var j = 0; j < elements.length; j++) {
fader(j);
};
});
};
})(jQuery);
jQuery(document).ready(function(){
jQuery.socialFader({ tweetHolder:"#twitter ul", tweetCount:5 });
});