Export excel with formulas is not working #549

Closed
opened 2017-02-05 14:37:26 +00:00 by omershelef · 2 comments
omershelef commented 2017-02-05 14:37:26 +00:00 (Migrated from github.com)

I am trying to export excel with formulas, my code runs in chrome.
I use the f option in cell object in order to create excel formulas. the rest of the code is based on the writexlsx demo (http://sheetjs.com/demos/writexlsx.html).
There is no error or anything, the excel is just exported with the cell empty instead of formulas.

Here is the code:

 function exportCsv() {
      var ws_name = "All employees";
      var data = [[1,2,3, 4],[1, 20, 8, {f: 'A2+B2'}]];
      var wb = new Workbook(), ws = sheet_from_array_of_arrays(data);

      /* add worksheet to workbook */
      wb.SheetNames.push(ws_name);
      wb.Sheets[ws_name] = ws;


      var wbout = XLSX.write(wb, {bookType:'xlsx', bookSST:true, type: 'binary'});
      saveAs(new Blob([s2ab(wbout)],{type:"application/octet-stream"}), "test.xlsx")
    }


    function Workbook() {
      if(!(this instanceof Workbook)) return new Workbook();
      this.SheetNames = [];
      this.Sheets = {};
    }

    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;
    }

    function datenum(v, date1904) {
      if(date1904) v+=1462;
      var epoch = Date.parse(v);
      return (epoch - new Date(Date.UTC(1899, 11, 30))) / (24 * 60 * 60 * 1000);
    }


    function sheet_from_array_of_arrays(data, opts) {
      var ws = {};
      var range = {s: {c:10000000, r:10000000}, e: {c:0, r:0 }};
      for(var R = 0; R != data.length; ++R) {
        for(var C = 0; C != data[R].length; ++C) {
          if(range.s.r > R) range.s.r = R;
          if(range.s.c > C) range.s.c = C;
          if(range.e.r < R) range.e.r = R;
          if(range.e.c < C) range.e.c = C;

          if(data[R][C] == null) continue;

          if(data[R][C].f == undefined) {
            var cell = {v: data[R][C] };

            if(typeof cell.v === 'number') cell.t = 'n';
            else if(typeof cell.v === 'boolean') cell.t = 'b';
            else if(cell.v instanceof Date) {
              cell.t = 'n'; cell.z = XLSX.SSF._table[14];
              cell.v = datenum(cell.v);
            }
            else cell.t = 's';
          }
          else {
            var cell = data[R][C];
          }

          var cell_ref = XLSX.utils.encode_cell({c:C,r:R});
          ws[cell_ref] = cell;
        }
      }
      if(range.s.c < 10000000) ws['!ref'] = XLSX.utils.encode_range(range);
      return ws;
    }
    
   exportCsv();
I am trying to export excel with formulas, my code runs in chrome. I use the _f_ option in _cell object_ in order to create excel formulas. the rest of the code is based on the writexlsx demo (http://sheetjs.com/demos/writexlsx.html). There is no error or anything, the excel is just exported with the cell empty instead of formulas. Here is the code: ``` function exportCsv() { var ws_name = "All employees"; var data = [[1,2,3, 4],[1, 20, 8, {f: 'A2+B2'}]]; var wb = new Workbook(), ws = sheet_from_array_of_arrays(data); /* add worksheet to workbook */ wb.SheetNames.push(ws_name); wb.Sheets[ws_name] = ws; var wbout = XLSX.write(wb, {bookType:'xlsx', bookSST:true, type: 'binary'}); saveAs(new Blob([s2ab(wbout)],{type:"application/octet-stream"}), "test.xlsx") } function Workbook() { if(!(this instanceof Workbook)) return new Workbook(); this.SheetNames = []; this.Sheets = {}; } 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; } function datenum(v, date1904) { if(date1904) v+=1462; var epoch = Date.parse(v); return (epoch - new Date(Date.UTC(1899, 11, 30))) / (24 * 60 * 60 * 1000); } function sheet_from_array_of_arrays(data, opts) { var ws = {}; var range = {s: {c:10000000, r:10000000}, e: {c:0, r:0 }}; for(var R = 0; R != data.length; ++R) { for(var C = 0; C != data[R].length; ++C) { if(range.s.r > R) range.s.r = R; if(range.s.c > C) range.s.c = C; if(range.e.r < R) range.e.r = R; if(range.e.c < C) range.e.c = C; if(data[R][C] == null) continue; if(data[R][C].f == undefined) { var cell = {v: data[R][C] }; if(typeof cell.v === 'number') cell.t = 'n'; else if(typeof cell.v === 'boolean') cell.t = 'b'; else if(cell.v instanceof Date) { cell.t = 'n'; cell.z = XLSX.SSF._table[14]; cell.v = datenum(cell.v); } else cell.t = 's'; } else { var cell = data[R][C]; } var cell_ref = XLSX.utils.encode_cell({c:C,r:R}); ws[cell_ref] = cell; } } if(range.s.c < 10000000) ws['!ref'] = XLSX.utils.encode_range(range); return ws; } exportCsv(); ```
titustt commented 2017-02-10 04:17:25 +00:00 (Migrated from github.com)

#307
Refer this pull request. One of the functions inside the library needs to be changed. If you're running off a local copy of this library, you can directly make changes to the function and run.

#307 Refer this pull request. One of the functions inside the library needs to be changed. If you're running off a local copy of this library, you can directly make changes to the function and run.
SheetJSDev commented 2017-03-18 00:56:01 +00:00 (Migrated from github.com)

We updated the write test with an example

We updated the [write test](https://github.com/SheetJS/js-xlsx/blob/master/tests/write.js#L82-L93) with an example
Sign in to join this conversation.
No Milestone
No Assignees
1 Participants
Notifications
Due Date
The due date is invalid or out of range. Please use the format 'yyyy-mm-dd'.

No due date set.

Dependencies

No dependencies set.

Reference: sheetjs/sheetjs#549
No description provided.