Working With Data Grids

A Data Grid holds table-style data such as the lines of an expense report. These examples total a column, number the rows, use values within a row, and fill a grid from another grid.

How grid data is stored

A Data Grid's value is a list of rows. Each row holds the values of the components inside the grid, by property name. For a grid expenseLines containing a Currency component expenseAmount:

  • data.expenseLines is the list of rows.

  • data.expenseLines[0].expenseAmount is the amount on the first row.

  • In a script on a component inside the grid, row holds the current row, so row.expenseAmount is the amount on the same row.

Number and Currency components store numbers, so they can be added directly. A new Data Grid starts with one empty row.

Total a column

Add a Currency component outside the grid for the total. On its Data tab, under Calculated Value → JavaScript Value, enter:

JavaScript
var total = 0;

(data.expenseLines || []).forEach(function (line) {
  total += Number(line.expenseAmount) || 0;
});

// Round to cents.
value = Math.round(total * 100) / 100;

Change expenseLines and expenseAmount to your own property names. The same loop can calculate averages, counts or anything else across the rows.

Number the rows

Add a Number component inside the Data Grid. As its calculated value, enter:

JavaScript
value = data.expenseLines.indexOf(row) + 1;

To start at a number the user enters (startNumber) and count in steps (stepBy), both outside the grid:

JavaScript
var index = data.expenseLines.indexOf(row);
value = (Number(data.startNumber) || 1) + index * (Number(data.stepBy) || 1);

Row numbering works in a Data Grid. Don't use it in an Edit Grid: rows loaded from a saved submission show 0.

Calculate within a row

Components inside a grid can use other values from the same row. For a line total from quantity and unit price:

JavaScript
value = (Number(row.quantity) || 0) * (Number(row.unitPrice) || 0);

To copy one value in the row to another:

JavaScript
value = row.requestedAmount || null;

Fill a grid from another grid

Copy rows from one grid (employees, with first and last) into a second grid (badges, with firstName and lastName). Use a button so the copy happens when the user asks for it. In the button's Button Custom Logic:

JavaScript
// Empty the target grid, then add one row for each source row.
data.badges = data.badges || [];
data.badges.length = 0;

(data.employees || []).forEach(function (employee) {
  data.badges.push({
    firstName: employee.first,
    lastName: employee.last
  });
});

Each object added becomes a new row. Its property names must match the property names of the components in the target grid.