I currently have a block of code that exports tables in my HTML body to one excel file.
$(document).ready(function() {
$("#btnExport").click(function(e) {
//getting values of current time for generating the file name
var dt = new Date();
var day = dt.getDate();
var month = dt.getMonth() + 1;
var year = dt.getFullYear();
var hour = dt.getHours();
var mins = dt.getMinutes();
var postfix = day + "." + month + "." + year + "_" + hour + "." + mins;
//creating a temporary HTML link element (they support setting file names)
var a = document.createElement('a');
//getting data from our div that contains the HTML table
var data_type = 'data:application/vnd.ms-excel';
var table_div = document.getElementsByClassName("dvData");
var table_html = table_div[0].outerHTML.replace(/ /g, '%20');
var table_html2 = table_div[1].outerHTML.replace(/ /g, '%20');
var table_html3 = table_div[2].outerHTML.replace(/ /g, '%20');
a.href = data_type + ', ' + table_html + "<br></br>" + table_html2 + "<br></br>" + table_html3;
//setting the file name
a.download = 'exported_table_' + postfix + '.xls';
//triggering the function
a.click();
//just in case, prevent default behaviour
e.preventDefault();
});
});
</script>
When the excel file opens, I want it to have some vba code that automatically runs when the user opens the downloaded file.
Is this possible? If so, how do I "embed" the vba code into the excel file my code exports?
Related
<script type="text/javascript">
$(document).ready(function () {
//getting values of current time for generating the file name
$(".toExcelButton").click(function(){
var dt = new Date();
var day = dt.getDate();
var month = dt.getMonth() + 1;
var year = dt.getFullYear();
var hour = dt.getHours();
var mins = dt.getMinutes();
var postfix = day + "." + month + "." + year + "_" + hour + "." + mins;
//creating a temporary HTML link element (they support setting file names)
var a = document.createElement('a');
//getting data from our div that contains the HTML table
var data_type = 'data:application/vnd.ms-excel';
var table_div = document.getElementById('dvData');
var table_html = table_div.outerHTML.replace(/ /g, '%20');
a.href = data_type + ', ' + table_html;
//setting the file name
a.download = 'exported_table_' + postfix + '.xls';
//triggering the function
a.click();
//just in case, prevent default behaviour
e.preventDefault();
})
});
</script>
Need to export div tables to excel. The above code works fine in Chrome but not working in IE. Can anyone help me out on the same.
In IE a dynamically created anchor tag needs to be added to the DOM to execute its click event. Furthermore the download attribute is not supported in the IE:
Download attribute on A tag not working in IE
Edit:
Recently I posted many answers handling this issue, here are two of those:
image does not download with it's own extension
JS Base64 string to downloadable pdf - Edge
Basically you have to use msSaveOrOpenBlob() in IE:
var tF = 'Whatever.xls';
var tB = new Blob(..);
if(window.top.navigator.msSaveOrOpenBlob){
//Store Blob in IE
window.top.navigator.msSaveOrOpenBlob(tB, tF)
}
else{
//Store Blob in others
var tA = document.body.appendChild(document.createElement('a'));
tA.href = URL.createObjectURL(tB);
tA.download = tF;
tA.style.display = 'none';
tA.click();
tA.parentNode.removeChild(tA)
}
In the case above:
var tT = new XMLSerializer().serializeToString(document.querySelector('table')); //Serialised table
var tF = 'Whatever.xls'; //Filename
var tB = new Blob([tT]); //Blob
if(window.top.navigator.msSaveOrOpenBlob){
//Store Blob in IE
window.top.navigator.msSaveOrOpenBlob(tB, tF)
}
else{
//Store Blob in others
var tA = document.body.appendChild(document.createElement('a'));
tA.href = URL.createObjectURL(tB);
tA.download = tF;
tA.style.display = 'none';
tA.click();
tA.parentNode.removeChild(tA)
}
https://jsfiddle.net/23ao1v0s/1/
Please check the below given link. I think you will get a solution for your question
https://github.com/rainabba/jquery-table2excel
I've written some scripts to convert the pagination (20 photos per ajax request) from instagram json feeds to csv for easily storing the photo urls in our database. Our CMS is automatically able to convert CSV files into SQl files either by replacing the table or by appending to it. The problem is it will only work if ALL of the columns are the same.
It's close to totally working but I can't import my generated csvs because they keep getting an empty column where it should be line breaking to a new row because the final CSV output contains a comma + line break when it should only be returning the line break (i.e. without a trailing comma).
Encoding is UTF-8 and line breaks are being added using "\n". I've tried console logging just about every step of the process and it seems that there that
Here's a picture of one of the CSVs I am generating: http://screencast.com/t/dZfqN08A
Below is all the relevant code:
First I'm using ajax with a jsonp callback to load instagram photos based on a hashtag.
Photos are loaded like this:
function loadNext(nextUrl) {
$.ajax({
url: url,
cache: false,
type: 'POST',
dataType: "jsonp",
success: function(object) {
console.log('loadmore');
if (object) {
console.log(object);
$('.loadmore').fadeOut(500);
// chargement photos gallerie
$.each( object.data, function(home, photo) {
photo = '<div class="photo photo-load">' +
'<img class="pull-me" src="' + photo.images.low_resolution.url + '" height="380px" width="380px" alt="photo">' +
'<div class="dot"></div>' +
'<div class="share" >' +
'<!-- AddThis Button BEGIN -->' +
'<div class="addthis_toolbox addthis_default_style addthis_16x16_style">' +
'<a class="addthis_button_twitter"></a>' +
'<a class="addthis_button_facebook"></a>' +
'</div>' +
'<!-- AddThis Button END -->' +
'</div>' +
'<div class="text-photo">' +
'<div class="svg line w-line"></div>' +
'<h4 class="left">'+ photo.user.username + '</h4>' +
'<h4 class="right share-photo">PARTAGE</h4>' +
'</div>' +
'<div class="vote w-path-hover">' +
'<div class="fb-like" data-href="http://dev.kngfu.com/maurice/" data-layout="box_count" data-action="like" data-show-faces="false" data-share="false"></div>' +
'<div class="insta-like">' +
'<div class="count-box">' +
'<p>'+ photo.likes.count + '</p>' +
'</div>' +
'<a class="insta-button" title="Pour appuyer votre proposition préférée, rendez-vous sur Instagram." href="http://instagram.com/" ><i class="fa fa-instagram"></i>J aime</a>' +
'</div> ' +
'<div class="w-path"></div>' +
'<div class="base-cross"></div>' +
'<h4 class="vote-button">VOTE</h4>' +
'</div>' +
'</div>';
$(photo).appendTo( $( ".gallery" ) );
});
url = object.pagination.next_url;
console.log(url);
} else {
console.log("error");
}
} // end success func.
});
}
Then in a separate ajax call I can convert the same json feed to a csv file using this function (this function also calls a couple other functions so the dependent functions are included below the ajax call):
function convertJSON (nextUrl) {
$.ajax({
url: url,
cache: false,
type: 'POST',
dataType: "jsonp",
success: function(object) {
if (object) {
console.log(object);
var fromJSON = new Array();
i = 0;
$.each( object.data, function(home, photo) {
i++;
var photopath = photo.images.low_resolution.url;
var postID = photo.id;
var userID = photo.user.id;
var user = photo.user.username;
// watch out for those wild fullnames in instagram json
var fullname = photo.user.full_name;
fullname = fullname.replace(/[^a-z0-9]+|\s+/gmi, " ");
//console.log(fullname);
var likes = photo.likes.count;
var winner = 0;
var winnerplace = " ";
var campaign = "maurice1";
var timestamp = photo.created_time;
// easydate field formatting
var date = new Date();
date.setSeconds( timestamp );
var photodeleted = 0;
// add new rows to csv
var linebreak = "\n";
var arrayFromJSON = new Array( linebreak+photopath,
postID,
userID,
user,
fullname,
likes,
winner,
winnerplace,
campaign,
timestamp,
date,
photodeleted );
fromJSON[i] = arrayFromJSON.join();
});
//url = object.pagination.next_url;
//console.log(url);
//console.log( fromJSON );
makeCSV( fromJSON );
} else {
console.log("error");
}
} // end success func.
});
}
// json to csv converter
function makeCSV (JSONData) {
//console.log("makeCSV() function was started");
var data = encodeURIComponent(JSONData);
var currentTime = new Date().getTime();
var date = getDate( currentTime );
//console.log(JSONData);
var fileName = date;
var uri = "data:text/csv;charset=utf-8," // sets mime/data type
+ "photopath," // now 12 strings which are the CSV's column titles
+ "postid,"
+ "userid,"
+ "username,"
+ "fullname,"
+ "likes,"
+ "winner,"
+ "winnerplace,"
+ "campaign,"
+ "creationdate,"
+ "easydate,"
+ "photodeleted"
+ data; // finally append our URI encoded data
console.log(uri);
// generate a temp <a /> tag that will auto start our download when the function is called
var link = document.createElement("a");
link.id = new Date().getTime();
link.href = uri;
// link visibility hidden
link.style = "visibility:hidden";
link.download = fileName + ".csv";
// append anchor tag and click
$("div#hidden").append(link);
link.click();
//document.body.removeChild(link);
}
// this function just makes human readable dates for CSV filename and id of our link tag
function getDate() {
var date = new Date();
//zero-pad a single zero if needed
var zp = function (val){
return (val <= 9 ? '0' + val : '' + val);
}
//zero-pad up to two zeroes if needed
var zp2 = function(val){
return val <= 99? (val <=9? '00' + val : '0' + val) : ('' + val ) ;
}
var d = date.getDate();
var m = date.getMonth() + 1;
var y = date.getFullYear();
var h = date.getHours();
var min = date.getMinutes();
var s = date.getSeconds();
var ms = date.getMilliseconds();
return '' + y + '-' + zp(m) + '-' + zp(d) + ' ' + zp(h) + 'h' + zp(min) + 'm' + zp(s) + 's';
}
From all the console logging I've done, I can definitely assure you that I'm getting no trailing comma until the final step where the json array data gets URI encoded.
Since this extra column is also included in the header row I'm wondering if it has to do with this line?
var uri = "data:text/csv;charset=utf-8," // sets mime/data type
I've also tried ISO-8859-1 encoding but I get the same result.
Does anyone know why this is happening? Any help would be appreciated
Your passing an array of lines to encodeURIComponent. That will stringify the array, joining it with a comma - which you don't want.
What you should do is
var arrayFromJSON = new Array( photopath,
// remove linebreak here ^
postID,
userID,
user,
fullname,
likes,
winner,
winnerplace,
campaign,
timestamp,
date,
photodeleted );
fromJSON[i] = arrayFromJSON.join(",");
// make comma explicit: ^^^
…
makeCSV( fromJSON );
…
var data = encodeURIComponent(JSONData.join("\n"));
// join the lines by a linebreak: ^^^^
…
var uri = "data:text/csv;charset=utf-8," // sets mime/data type
+ "photopath," // now 12 strings which are the CSV's column titles
+ "postid,"
+ "userid,"
+ "username,"
+ "fullname,"
+ "likes,"
+ "winner,"
+ "winnerplace,"
+ "campaign,"
+ "creationdate,"
+ "easydate,"
+ "photodeleted"
+ "\n"
// ^^^^^^ add linebreak
+ data; // finally append our URI encoded data
I am using the javascript code for export html table to .xls file.Its work in crome and when data is not large.But when data is large then it shows me error like
The code which i have used for export the table as .xls file is as below:
function exportDiv() {
//working on crome perfectly
var dt = new Date();
var day = dt.getDate();
var month = dt.getMonth() + 1;
var year = dt.getFullYear();
var hour = dt.getHours();
var mins = dt.getMinutes();
var postfix = day + "." + month + "." + year + "_" + hour + "." + mins;
var a = document.createElement('a');
var data_type = 'data:application/vnd.ms-excel';
var table_div = document.getElementById('tbl-1');
var table_html = table_div.outerHTML.replace(/ /g, '%20');
a.href = data_type + ', ' + table_html;
a.download = 'exported_table_' + postfix + '.xls';
a.click();
e.preventDefault();
}
I have also sufficient 4 gb ram so i think its not memory limit problem.
Can you please help me for how to export large data?
Edit: I ahve used this way also
var table_html=encodeURIComponent(table_div.outerHTML);
But still same error come.
Most likely you've hit the 2 MB URL limit in Chrome. You can read about it here - issue link. I suggest you try your app in Firefox, if it works, then that is the issue.
excel sheet has got a character limit for 32767 characters similar to that of an excel cell.
for reference check this link : http://office.microsoft.com/en-in/excel-help/excel-specifications-and-limits-HP010073849.aspx
I have called the tableToexcel function on button click like as below and it is working fine in firefix.
<a id="dlink" style="display:none;"></a>
var tableToExcel = (function () {
var uri = 'data:application/vnd.ms-excel;base64,'
, template = '<html xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:x="urn:schemas-microsoft-com:office:excel" xmlns="http://www.w3.org/TR/REC-html40"><head><!--[if gte mso 9]><xml><x:ExcelWorkbook><x:ExcelWorksheets><x:ExcelWorksheet><x:Name>{worksheet}</x:Name><x:WorksheetOptions><x:DisplayGridlines/></x:WorksheetOptions></x:ExcelWorksheet></x:ExcelWorksheets></x:ExcelWorkbook></xml><![endif]--></head><body><table>{table}</table></body></html>'
, base64 = function (s) { return window.btoa(unescape(encodeURIComponent(s))) }
, format = function (s, c) { return s.replace(/{(\w+)}/g, function (m, p) { return c[p]; }) }
return function (table, name, filename) {
if (!table.nodeType) table = document.getElementById(table)
var ctx = { worksheet: name || 'Worksheet', table: table.innerHTML }
document.getElementById("dlink").href = uri + base64(format(template, ctx));
document.getElementById("dlink").download = filename;
document.getElementById("dlink").click();
}
})();
I've got a simple HTML page (generated by an external application) that contains a table view.
I am trying to scrape off the tables from the page and put them in an Excel workbook.
I have managed to put the whole HTML contents in a workbook by using the method available here.
Code from the related question:
var tableToExcel = (function() {
var uri = 'data:application/vnd.ms-excel;base64,'
, template = '<html xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:x="urn:schemas-microsoft-com:office:excel" xmlns="http://www.w3.org/TR/REC-html40"><head><!--[if gte mso 9]><xml><x:ExcelWorkbook><x:ExcelWorksheets><x:ExcelWorksheet><x:Name>{worksheet}</x:Name><x:WorksheetOptions><x:DisplayGridlines/></x:WorksheetOptions></x:ExcelWorksheet></x:ExcelWorksheets></x:ExcelWorkbook></xml><![endif]--></head><body><table>{table}</table></body></html>'
, base64 = function(s) { return window.btoa(unescape(encodeURIComponent(s))) }
, format = function(s, c) { return s.replace(/{(\w+)}/g, function(m, p) { return c[p]; }) }
return function(table, name) {
if (!table.nodeType) table = document.getElementById(table)
var ctx = {worksheet: name || 'Worksheet', table: table.innerHTML}
window.location.href = uri + base64(format(template, ctx))
}
})()
JSFiddle
The method however does not support multiple spreadsheets. What I need is for every HTML table being in it's own SpreadSheet in the same Excel workbook. Something like this:
I have tried to create a sample Excel document with two spreadsheets and then reverse engineer it by looking at an export in .html format. Unfortunately I failed to understand how to recreate the connection betwee a workbook and it's sheets.
As far as I can understand the format() function does the 'magical' combining of the worksheet data and the Excel template. The function looks very cryptic to me, so I have no idea how to go about modifying it.
What I need as an end game is having the possibility to call something like.
tableToExcel(document.getElementsByTagName('table'), 'Workbook Name');
Any ideas if this is at all possible, and if so - how to go about making it happen?
Checkout this blog post: http://www.kubilayerdogan.net/?p=218
$(document).ready(function() {
$("#btnExport").click(function(e) {
//getting values of current time for generating the file name
var dt = new Date();
var day = dt.getDate();
var month = dt.getMonth() + 1;
var year = dt.getFullYear();
var hour = dt.getHours();
var mins = dt.getMinutes();
var postfix = day + "." + month + "." + year + "_" + hour + "." + mins;
//creating a temporary HTML link element (they support setting file names)
var a = document.createElement('a');
//getting data from our div that contains the HTML table
var data_type = 'data:application/vnd.ms-excel';
var table_div = document.getElementById('dvData');
var table_html = table_div.outerHTML.replace(/ /g, '%20');
a.href = data_type + ', ' + table_html;
//setting the file name
a.download = 'exported_table_' + postfix + '.xls';
//triggering the function
a.click();
//just in case, prevent default behaviour
e.preventDefault();
});
});
You can see it in action in jsfiddle: http://jsfiddle.net/kublaios/8ZQN4/1/
I will be printing two fields using for fields using for loop in javascript. First field is the name and second field is the link to download that file. This table will be generated dynamically. I want to keep a counter saying how many times a particular file is downloaded on the generated table.
for (i=0; i<resp.items.length; i++) {
var titulo = resp.items[i].title;
var fechaUpd = resp.items[i].modifiedDate;
var userUpd = resp.items[i].lastModifyingUserName;
var userEmbed = resp.items[i].embedLink;
var userAltLink = resp.items[i].alternateLink;
var download = resp.items[i].webContentLink;
var hold="Download";
var flag=0;
<!-- var fileInfo = document.createElement('li');
<!-- fileInfo.appendChild(document.createTextNode('TITLE: ' + titulo + ' - LAST MODIF: ' + fechaUpd + ' - BY: ' + userUpd +' url: ' + hold.link(download)));
<!-- document.getElementById('content').appendChild(fileInfo);
document.write(titulo + " ");
document.write(hold.link(download) + "<br>");
<!--flag=1;
}
<!--if(flag!=1){
<!--document.write("not found!");
<!--}
});