Save dynamically created table content in excel file using SheetJS - javascript

I add rows into html table dynamically and I want to save the table content into xlsx file using SheetJs. The generated file is empty. Is somehow possible to do this in this case when table content was added this way?
I also tried to add the rows rigth before creating the xlsx file..
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-2.1.4.js"
integrity="sha256-siFczlgw4jULnUICcdm9gjQPZkw/YPDqhQ9+nAOScE4=" crossorigin="anonymous"></script>
<script type="text/javascript"
src="https://cdnjs.cloudflare.com/ajax/libs/amcharts/3.21.15/plugins/export/libs/FileSaver.js/FileSaver.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/xlsx/0.15.6/xlsx.full.min.js"></script>
<style>
table,
td {
border: 1px solid black;
}
</style>
</head>
<body>
<script src="https://cdnjs.cloudflare.com/ajax/libs/xlsx/0.10.3/xlsx.full.min.js">
</script>
<p>Click the button to add a new row at the first position of the
table and then add cells and content</p>
<table id="myTable">
<TR>
</TR>
</table>
<button type="button" id="first" onclick="First('myTable')">Principal</button>
<button id="button-a">Create Excel</button>
<script>
function First(tableID) {
let table = document.getElementById(tableID)
table.innerHTML = "<tr>first</tr>";
}
</script>
<script>
var wb = XLSX.utils.table_to_book(document.getElementById('myTable'), { sheet: "Sheet JS" });
var wbout = XLSX.write(wb, { bookType: 'xlsx', bookSST: true, type: 'binary' });
function s2ab(s) {
var buf = new ArrayBuffer(s.length);
var view = new Uint8Array(buf);
for (var i = 0; i < s.length; i++) view[i] = s.charCodeAt(i) & 0xFF;
return buf;
}
$("#button-a").click(function () {
saveAs(new Blob([s2ab(wbout)], { type: "application/octet-stream" }), 'test.xlsx');
});
</script>
</body>
</html>

Issues
text inside tr instead of td in dynamic content. This results in the table structure like below.
XLSX.utils.table_to_book called before table content created.
Working Demo
https://jsfiddle.net/aswinkumar863/95zsfg64/1/

Related

Parse a Google spreadsheet into a Javascript array

I have a Google spreadsheet (https://docs.google.com/spreadsheets/d/e/2PACX-1vRc8Lx0N-wf3f1xAAXkNFUqQjaWPFcde3YjK02gCBqGpUrULwHC6NC0sndeLJBvOyKkA88hvtH335pR/pubhtml) which I'd like to access in a webpage to use with Google Maps API.
As per Google API'S documentation, the script should look like this:
<html>
<head>
<script type="text/javascript" src="https://www.gstatic.com/charts/loader.js"></script>
<script>
google.charts.load('current', { 'packages': ['map'] });
google.charts.setOnLoadCallback(drawMap);
function drawMap() {
var data = google.visualization.arrayToDataTable([
['Country', 'Population'],
['China', 'China: 1,363,800,000'],
['India', 'India: 1,242,620,000'],
['US', 'US: 317,842,000'],
['Indonesia', 'Indonesia: 247,424,598'],
['Brazil', 'Brazil: 201,032,714'],
['Pakistan', 'Pakistan: 186,134,000'],
['Nigeria', 'Nigeria: 173,615,000'],
['Bangladesh', 'Bangladesh: 152,518,015'],
['Russia', 'Russia: 146,019,512'],
['Japan', 'Japan: 127,120,000']
]);
var options = {
showTooltip: true,
showInfoWindow: true
};
var map = new google.visualization.Map(document.getElementById('chart_div'));
map.draw(data, options);
};
</script>
</head>
<body>
<div id="chart_div"></div>
</body>
</html>
So my goal is to dynamically replace:
[
['Country', 'Population'],
['China', '1,363,800,000'],
['India', '1,242,620,000'],
['US', '317,842,000'],
['Indonesia', '247,424,598'],
['Brazil', '201,032,714'],
['Pakistan', '186,134,000'],
['Nigeria', '173,615,000'],
['Bangladesh', '152,518,015'],
['Russia', 'Russia: 146,019,512'],
['Japan', 'Japan: 127,120,000']
]
...with the content of the Google Spreadsheet.
I am new at JS, and I'm struggling to properly convert an exported JSON from Google Spreadsheets into a JS array. Searching around, I stumbled upon an interresting script:
<!doctype html>
<html>
<head>
<script src="//ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script type="text/javascript">
var spData = null;
function doData(json) {
spData = json.feed.entry;
}
function drawCell(tr, val) {
var td = $("<td/>");
tr.append(td);
td.append(val);
return td;
}
function drawRow(table, rowData) {
if (rowData == null) return null;
if (rowData.length == 0) return null;
var tr = $("<tr/>");
table.append(tr);
for(var c=0; c<rowData.length; c++) {
drawCell(tr, rowData[c]);
}
return tr;
}
function drawTable(parent) {
var table = $("<table/>");
parent.append(table);
//console.log(table);
return table;
}
function readData(parent) {
var data = spData;
var table = drawTable(parent);
var rowData = [];
for(var r=0; r<data.length; r++) {
var cell = data[r]["gs$cell"];
var val = cell["$t"];
if (cell.col == 1) {
drawRow(table, rowData);
rowData = [];
}
rowData.push(val);
}
drawRow(table, rowData);
}
$(document).ready(function(){
readData($("#data"));
});
</script>
<script src="https://spreadsheets.google.com/feeds/cells/1TTeG6mp2rb61Yxi5KO3GFmZ3qQ3RAMlB9bisLciuj-M/1/public/values?alt=json-in-script&callback=doData"></script>
<style type="text/css">
table {border-collapse: collapse; width: 100%;}
th, td {border: thin solid black; padding: 3px;}
tr.head th, tr.head td {background-color: #EDEDED; border-bottom: 4px double black;}
span.linetitle {font-weight: bold;}
div.lineclass {font-style: italic;}
.title, .result {width: 80%;}
.notes {width: 15%;}
h1 {text-align: center;}
body {margin: 12px; font-size: 12px;}
</style>
<style type="text/css" media="print">
form {display: none;}
</style>
</head>
<body>
<h1>Parse Google Spreadsheet with JavaScript</h1>
<div id="data"/>
</body>
</html>
...which fetches the spreadsheet, and turns it into a HTML table. However, I can't seem to find a way to build an array from this.
After this long context, here's my question: how can I fetch the Google spreadsheet to insert it as data in the drawMap function above?
The Google spreadsheet API you are using is supposed to be called with JSONP.
I used jQuery's simple implementation of JSONP via the $.ajax function.
You can see my solution with line by line explanations:
var spreadsheetUrl = 'https://spreadsheets.google.com/feeds/cells/1TTeG6mp2rb61Yxi5KO3GFmZ3qQ3RAMlB9bisLciuj-M/1/public/values?alt=json-in-script&callback=doData';
// The callback function the JSONP request will execute to load data from API
function doData(data) {
// Final results will be stored here
var results = [];
// Get all entries from spreadsheet
var entries = data.feed.entry;
// Set initial previous row, so we can check if the data in the current cell is from a new row
var previousRow = 0;
// Iterate all entries in the spreadsheet
for (var i = 0; i < entries.length; i++) {
// check what was the latest row we added to our result array, then load it to local variable
var latestRow = results[results.length - 1];
// get current cell
var cell = entries[i];
// get text from current cell
var text = cell.content.$t;
// get the current row
var row = cell.gs$cell.row;
// Determine if the current cell is in the latestRow or is a new row
if (row > previousRow) {
// this is a new row, create new array for this row
var newRow = [];
// add the cell text to this new row array
newRow.push(text);
// store the new row array in the final results array
results.push(newRow);
// Increment the previous row, since we added a new row to the final results array
previousRow++;
} else {
// This cell is in an existing row we already added to the results array, add text to this existing row
latestRow.push(text);
}
}
handleResults(results);
}
// Do what ever you please with the final array
function handleResults(spreadsheetArray) {
console.log(spreadsheetArray);
}
// Create JSONP Request to Google Docs API, then execute the callback function doData
$.ajax({
url: spreadsheetUrl,
jsonp: 'doData',
dataType: 'jsonp'
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

Read excel file and display in html

I have an excel file that contains data. I want to read that file and display the results in html / web page using JS or Angular JS.
A very simple way of reading an *.xslx file in a browser:
(displaying the results in html / web page using JS or Angular JS is trivial after that, though I'd suggest React over Angular)
https://catamphetamine.github.io/read-excel-file/
<input type="file" id="input" />
import readXlsxFile from 'read-excel-file'
const input = document.getElementById('input')
input.addEventListener('change', () => {
readXlsxFile(input.files[0]).then((data) => {
// `data` is an array of rows
// each row being an array of cells.
})
})
In the example above data is raw string data.
It can be parsed to JSON with a strict schema by passing schema argument. See API docs for an example of that.
API docs:
http://npmjs.com/package/read-excel-file
SheetsJS/js-xlsx Github repository is designed for working with XLSX files in web development. This would be really useful for you. Read up on this and learn how to use it, no need to reinvent the wheel either. Good luck.
JsZip did this very efficently. Take a look at it. And refer link to read local file using JSZip, you can then need to process to get the data in the excel file. Digging through the help documents will let you know how to do so.
Try this
<html>
<head>
<meta charset="utf-8" />
<title>Convert Excel to HTML Table using JavaScript</title>
<meta name="viewport" content="width=device-width, initial-scale=1" />
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css" integrity="sha384-Gn5384xqQ1aoWXA+058RXPxPg6fy4IWvTNh0E263XmFcJlSAwiGgFAW/dAiS6JXm" crossorigin="anonymous">
<script type="text/javascript" src="https://unpkg.com/xlsx#0.15.1/dist/xlsx.full.min.js"></script>
</head>
<body>
<div class="container">
<h2 class="text-center mt-4 mb-4">Convert Excel to HTML Table using JavaScript</h2>
<div class="card">
<div class="card-header"><b>Select Excel File</b></div>
<div class="card-body">
<input type="file" id="excel_file" />
</div>
</div>
<div id="excel_data" class="mt-5"></div>
</div>
</body>
</html>
<script>
const excel_file = document.getElementById('excel_file');
excel_file.addEventListener('change', (event) => {
if(!['application/vnd.openxmlformats-officedocument.spreadsheetml.sheet', 'application/vnd.ms-excel'].includes(event.target.files[0].type))
{
document.getElementById('excel_data').innerHTML = '<div class="alert alert-danger">Only .xlsx or .xls file format are allowed</div>';
excel_file.value = '';
return false;
}
var reader = new FileReader();
reader.readAsArrayBuffer(event.target.files[0]);
reader.onload = function(event){
var data = new Uint8Array(reader.result);
var work_book = XLSX.read(data, {type:'array'});
var sheet_name = work_book.SheetNames;
var sheet_data = XLSX.utils.sheet_to_json(work_book.Sheets[sheet_name[0]], {header:1});
if(sheet_data.length > 0)
{
var table_output = '<table class="table table-striped table-bordered">';
for(var row = 0; row < sheet_data.length; row++)
{
table_output += '<tr>';
for(var cell = 0; cell < sheet_data[row].length; cell++)
{
if(row == 0)
{
table_output += '<th>'+sheet_data[row][cell]+'</th>';
}
else
{
table_output += '<td>'+sheet_data[row][cell]+'</td>';
}
}
table_output += '</tr>';
}
table_output += '</table>';
document.getElementById('excel_data').innerHTML = table_output;
}
excel_file.value = '';
}
});
</script>

Import Excel file to a table of HTML page

I have a simple Excel file in my computer at "D:/Book1.xls". I want to import it to make a table and append the table to a div tag in my HTML page.
Would you modify my code below?
<!DOCTYPE html>
<html>
<head>
<meta charset="EUC-KR">
<title>Insert title here</title>
<style type="text/css">
</style>
<script src='http://alasql.org/console/alasql.min.js'></script>
<script src='http://alasql.org/console/xlsx.core.min.js'></script>
<script src="./libs/jquery-2.1.4.js"></script>
<script type="text/javascript">
$(document).ready(function() {
alasql('select * into html("#res",{headers:true}) \
from xlsx("d:/Book1.xls",\
{headers:true})');
alert("end of function")
});
</script>
</head>
<body>
<div id="res">res</div>
</body>
</html>
The problem is you are trying to get access of file directly from web page which is not possible. You cannot access any file outside of you browser. For that you have to select the input element of html and after getting the file data you can store it to javascript variable.
<script src="alasql.min.js"></script>
<script src="xlsx.core.min.js"></script>
<p>Select CSV file to read:</p>
<input id="readfile" type="file" onchange="loadFile(event)"/>
<script>
function loadFile(event) {
alasql('SELECT * FROM FILE(?,{headers:true})',[event],function(data){
console.log(data);
// You can data to div also.
});
}
</script>
Scripts
<script src="http://ajax.aspnetcdn.com/ajax/modernizr/modernizr-2.8.3.js"></script>
<script src="http://code.jquery.com/jquery-1.11.3.min.js"></script>
<script src="http://code.jquery.com/ui/1.11.1/jquery-ui.min.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/infragistics.core.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/infragistics.lob.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_core.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_collections.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_text.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_io.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_ui.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.documents.core_core.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_collectionsextended.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.excel_core.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_threading.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.ext_web.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.xml.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.documents.core_openxml.js"></script>
<script type="text/javascript" src="http://cdn-na.infragistics.com/igniteui/2018.2/latest/js/modules/infragistics.excel_serialization_openxml.js"></script>
JS
$(function () {
$("#input").on("change", function () {
var excelFile,
fileReader = new FileReader();
$("#result").hide();
fileReader.onload = function (e) {
var buffer = new Uint8Array(fileReader.result);
$.ig.excel.Workbook.load(buffer, function (workbook) {
var column, row, newRow, cellValue, columnIndex, i,
worksheet = workbook.worksheets(0),
columnsNumber = 0,
gridColumns = [],
data = [],
worksheetRowsCount;
// Both the columns and rows in the worksheet are lazily created and because of this most of the time worksheet.columns().count() will return 0
// So to get the number of columns we read the values in the first row and count. When value is null we stop counting columns:
while (worksheet.rows(0).getCellValue(columnsNumber)) {
columnsNumber++;
}
// Iterating through cells in first row and use the cell text as key and header text for the grid columns
for (columnIndex = 0; columnIndex < columnsNumber; columnIndex++) {
column = worksheet.rows(0).getCellText(columnIndex);
gridColumns.push({ headerText: column, key: column });
}
// We start iterating from 1, because we already read the first row to build the gridColumns array above
// We use each cell value and add it to json array, which will be used as dataSource for the grid
for (i = 1, worksheetRowsCount = worksheet.rows().count(); i < worksheetRowsCount; i++) {
newRow = {};
row = worksheet.rows(i);
for (columnIndex = 0; columnIndex < columnsNumber; columnIndex++) {
cellValue = row.getCellText(columnIndex);
newRow[gridColumns[columnIndex].key] = cellValue;
}
data.push(newRow);
}
// we can also skip passing the gridColumns use autoGenerateColumns = true, or modify the gridColumns array
createGrid(data, gridColumns);
}, function (error) {
$("#result").text("The excel file is corrupted.");
$("#result").show(1000);
});
}
if (this.files.length > 0) {
excelFile = this.files[0];
if (excelFile.type === "application/vnd.ms-excel" || excelFile.type === "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" || (excelFile.type === "" && (excelFile.name.endsWith("xls") || excelFile.name.endsWith("xlsx")))) {
fileReader.readAsArrayBuffer(excelFile);
} else {
$("#result").text("The format of the file you have selected is not supported. Please select a valid Excel file ('.xls, *.xlsx').");
$("#result").show(1000);
}
}
})
});
function createGrid(data, gridColumns) {
if ($("#grid1").data("igGrid") !== undefined) {
$("#grid1").igGrid("destroy");
}
$("#grid1").igGrid({
columns: gridColumns,
autoGenerateColumns: true,
dataSource: data,
width: "100%",
});
}
HTML
<input type="file" id="input" accept="application/vnd.ms-excel, application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" />
<div id="result"></div>
<table id="grid1"></table>

Read from file into html listbox by javascript function

I have been trying to read data from file ans display it into some kind of listBov in html page by using java script.
I have been trying many cources, but there is no working code (I've trying on IE, Firefox and Chrome)
There is one of the attempt to do that, but it also without success:
File 1:
indexTST.html
<html>
<head>
<script language="JavaScript" type="text/javascript" src="java.js">
</script>
<body>
<td><form name="listBox" action="javascript:void 0;">
<select name="listBox" size="10">
<option>Select your home location</option>
<option>unknown</option>
</select>
</form>
<script type="text/javascript" language="JavaScript">
loadData();
with (document.listBox) {
listBox.options.length=0;
for (var i=0; i<Table.length; i++) {
listBox.options[listBox.options.length]=new Option(Table[i]);
}
}
reset1();
</script>
</body>
</html>
File 2:
java.js
var Table = [];
var txtFile;
function loadData2() {
Table = [];
lines = txtFile.responseText.split("\n");
for (i = 0; i < lines.length-1; i++) {
Table.push(lines[i]);
}
}
function loadData() {
var f = "dataFile.txt";
alert('01');
txtFile.open("GET", f, false);
alert('02');
txtFile.onreadystatechange=loadData2;
txtFile.send(null);
}
File 4:
dataFile.txt
Data 01
Data 02
Data 03
end
What I'm trying to achieve is:
Read text data from file (between 1 and 5 000 lines) and the file is on the server side (not local browser side)
Display it into some kind of listBox on web page
It's need to be "clickable/selectable" - because when user select i.e. item 5 - this one item need to be save into "saved.txt"
Thanks for help
Read a file and appends its contents by line to a list, and log the selected options. I hope it helps.
<!DOCTYPE html>
<html>
<body>
<h3>Read file</h3>
<input id="file-input" type="file" id="myFile">
<select multiple id="list"></select>
<button onclick="logSelected()">Log selected</button>
<script>
function readSingleFile(evt) {
//Retrieve the first (and only!) File from the FileList object
var f = evt.target.files[0];
if (f) {
var r = new FileReader();
r.onload = function(e) {
var contents = e.target.result;
console.log(contents);
var select = document.getElementById('list');
var lines = contents.split('\n');
lines.map(function(line){
var docLine = document.createElement('option');
docLine.innerHTML = line;
select.appendChild(docLine);
});
}
r.readAsText(f);
} else {
alert("Failed to load file");
}
}
document.getElementById('file-input').addEventListener('change', readSingleFile, false);
function logSelected(){
var select = document.getElementById("list");
var selected = [];
for (var i = 0; i < select.length; i++) {
if (select.options[i].selected) selected.push(select.options[i].value);
}
console.log(selected);
};
</script>
</body>
</html>

inserting td in a tr with ID using javascript

I have to insert a td inside a tr which has a ID using javascript.Can someone please help me or guide me in the right direction.Sorry it might be simple but I m very new to javascript.
<html>
<head>
<script type="text/javascript">
function insertText ()
{
//function to insert any text on the tr with id "tr1"
}
</script>
</head>
<body onload="javascript:insertText()">
<table>
<tr id="tr1">
</tr>`
</table>
</body>
</html>
function insertText ()
{
var td = document.getElementById('tr1').insertCell(0);
td.innerHTML = "Some Text";
}
The main advantage of insertCell (and insertRow) is that they allow you to specify an index where the new cell (or row) is to be inserted.
Try this:
function insertText ()
{
var el = document.createElement('td');
el.innerHTML = 'Hello World';
document.getElementById("tr1").appendChild(el);
}

Categories