Skip to content

Commit

Permalink
Use hierarchies instead of allRows() (#30)
Browse files Browse the repository at this point in the history
* Use a hierarchy root to check for null.

* Use intersection between leaf node row sets to mark in google barchart.

Co-authored-by: Erik Brandin <[email protected]>
  • Loading branch information
objerke and ebrandin authored May 26, 2021
1 parent 9b6f19b commit 66e722a
Show file tree
Hide file tree
Showing 5 changed files with 49 additions and 49 deletions.
21 changes: 12 additions & 9 deletions examples/js-areachart-d3/src/render.js
Original file line number Diff line number Diff line change
Expand Up @@ -94,29 +94,32 @@ export async function render(state, mod, dataView, windowSize, chartType, rounde
} else {
mod.controls.errorOverlay.hide("rowCount");
}

const colorHierarchy = await dataView.hierarchy("Color");
const xHierarchy = await dataView.hierarchy("X");

const allRows = await dataView.allRows();
if (allRows == null) {
// By awaiting one hierarchy root, all rows will be fetched.
const colorRoot = await colorHierarchy.root();
const xRoot = await xHierarchy.root();
if (colorRoot == null) {
// Return and wait for next call to render when reading data was aborted.
// Last rendered data view is still valid from a users perspective since
// a document modification was made during a progress indication.
return;
}

const colorHierarchy = await dataView.hierarchy("Color");
const xHierarchy = await dataView.hierarchy("X");
const colorLeaves = colorRoot.leaves();
const xLeaves = xRoot.leaves();

const colorSeries = buildColorSeries(
(await colorHierarchy.root()).leaves(),
(await xHierarchy.root()).leaves(),
colorLeaves,
xLeaves,
!xHierarchy.isEmpty,
!!(await dataView.continuousAxis("Y")),
chartType.value(),
gapfill.value()
);

const xLeaves = (await xHierarchy.root()).leaves();
const colorLeaves = (await colorHierarchy.root()).leaves();

const xAxisMeta = await mod.visualization.axis("X");
const yAxisMeta = await mod.visualization.axis("Y");
const colorAxisMeta = await mod.visualization.axis("Color");
Expand Down
34 changes: 12 additions & 22 deletions examples/js-dev-barchart-googlecharts/src/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -57,20 +57,18 @@ Spotfire.initialize(async (mod) => {
mod.controls.errorOverlay.hide();

/**
* Get rows from dataView
* Get the color hierarchy.
*/
const rows = await dataView.allRows();
if (rows == null) {
const colorHierarchy = await dataView.hierarchy("Color");
const colorRoot = await colorHierarchy.root();

if (colorRoot == null) {
// User interaction caused the data view to expire.
// Don't clear the mod content here to avoid flickering.
return;
}

/**
* Get the color hierarchy.
*/
const colorHierarchy = await dataView.hierarchy("Color");
const colorLeafNodes = (await colorHierarchy.root()).leaves();
const colorLeafNodes = colorRoot.leaves();
const colorDomain = colorHierarchy.isEmpty
? ["All Values"]
: colorLeafNodes.map((node) => node.formattedPath());
Expand Down Expand Up @@ -199,21 +197,9 @@ Spotfire.initialize(async (mod) => {
const { row, column } = selection;
const xIndex = row;
const colorIndex = (column - 1) / 2;
selectRow(xIndex, colorIndex);
});

/**
* Select a row by `x` and `color` indexes.
*/
function selectRow(xIndex, colorIndex) {
rows.forEach((row) => {
var rowColorIndex = !colorHierarchy.isEmpty ? row.categorical("Color").leafIndex : 0;
var rowXIndex = !xHierarchy.isEmpty ? row.categorical("X").leafIndex : 0;
if (rowXIndex == xIndex && rowColorIndex == colorIndex) {
row.mark();
}
});
}
intersection(xLeafNodes[xIndex].rows(), colorLeafNodes[colorIndex].rows()).forEach((r) => r.mark());
});

/**
* Add click events for background and both axes
Expand Down Expand Up @@ -305,6 +291,10 @@ Spotfire.initialize(async (mod) => {
name == stacking.name && stacking.set(value);
}

function intersection(rows1, rows2) {
return rows1.filter((r) => rows2.indexOf(r) > -1);
}

/**
* Trigger render complete when chart is ready
*/
Expand Down
15 changes: 9 additions & 6 deletions examples/js-dev-starter-ie11/src/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,15 @@
* in the license file that is distributed with this file.
*/

//@ts-check - Get type warnings from the TypeScript language server. Remove if not wanted

// Manually import the array polyfills because the API is using functions not supported in IE11.
import "core-js/es/array";

//@ts-check - Get type warnings from the TypeScript language server. Remove if not wanted
/**
* Get access to the Spotfire Mod API by providing a callback to the initialize method.
*/
Spotfire.initialize(async (mod) => {
window.Spotfire.initialize(async (mod) => {
/**
* Create the read function.
*/
Expand Down Expand Up @@ -47,10 +48,12 @@ Spotfire.initialize(async (mod) => {
mod.controls.errorOverlay.hide();

/**
* Get rows from dataView
* Get the hierarchy of the categorical X-axis.
*/
const rows = await dataView.allRows();
if (rows == null) {
const xHierarchy = await dataView.hierarchy("X");
const xRoot = await xHierarchy.root();

if (xRoot == null) {
// User interaction caused the data view to expire.
// Don't clear the mod content here to avoid flickering.
return;
Expand All @@ -61,7 +64,7 @@ Spotfire.initialize(async (mod) => {
*/
const container = document.querySelector("#mod-container");
container.textContent = `windowSize: ${windowSize.width}x${windowSize.height}\r\n`;
container.textContent += `should render: ${rows.length} rows\r\n`;
container.textContent += `should render: ${xRoot.rows().length} rows\r\n`;
container.textContent += `${prop.name}: ${prop.value()}`;

/**
Expand Down
10 changes: 6 additions & 4 deletions examples/js-dev-starter/src/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -46,10 +46,12 @@ Spotfire.initialize(async (mod) => {
mod.controls.errorOverlay.hide();

/**
* Get rows from dataView
* Get the hierarchy of the categorical X-axis.
*/
const rows = await dataView.allRows();
if (rows == null) {
const xHierarchy = await dataView.hierarchy("X");
const xRoot = await xHierarchy.root();

if (xRoot == null) {
// User interaction caused the data view to expire.
// Don't clear the mod content here to avoid flickering.
return;
Expand All @@ -60,7 +62,7 @@ Spotfire.initialize(async (mod) => {
*/
const container = document.querySelector("#mod-container");
container.textContent = `windowSize: ${windowSize.width}x${windowSize.height}\r\n`;
container.textContent += `should render: ${rows.length} rows\r\n`;
container.textContent += `should render: ${xRoot.rows().length} rows\r\n`;
container.textContent += `${prop.name}: ${prop.value()}`;

/**
Expand Down
18 changes: 10 additions & 8 deletions examples/ts-dev-gauge-googlecharts/src/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,22 +31,24 @@ Spotfire.initialize(async (mod) => {
}

mod.controls.errorOverlay.hide("DataView");
let rows = await dataView.allRows();
if (rows == null) {

let categoryHierarchy = await dataView.hierarchy("Category");
let categoryRoot = await categoryHierarchy!.root();

if (categoryRoot == null) {
// Return and wait for next call to render when reading data was aborted.
// Last rendered data view is still valid from a users perspective since
// a document modification was made during a progress indication.
return;
}

// Check for empty axis expression before.
let hasCategory = (await dataView.categoricalAxis("Category")) != null;
let hasMeasurement = (await dataView.continuousAxis("Measurement")) != null;

// Transform the rows to the google visualization format.
let data: [string, number][] = rows.map((row) => [
hasCategory ? row.categorical("Category").formattedValue() : "",
hasMeasurement ? row.continuous("Measurement").value() ?? 0 : 0
let data: [string, number][] = categoryRoot.leaves().map((leaf) => [
leaf.formattedPath(),
hasMeasurement ? leaf.rows()[0]?.continuous("Measurement").value() ?? 0 : 0
]);

// Render the visualization using the transformed data
Expand All @@ -55,9 +57,9 @@ Spotfire.initialize(async (mod) => {
// Add marking highlight using the marking color, if marking is enabled.
let marking = await dataView.marking();
let gauges = gauge.element.getElementsByTagName("td");
rows.forEach((row, index) => {
categoryRoot.leaves().forEach((leaf, index) => {
gauges[index].style.background =
row.isMarked() && marking
marking && leaf.rows().filter(r => r.isMarked()).length
? "radial-gradient(" + marking.colorHexCode + " 50%, transparent 100%)"
: "transparent";
});
Expand Down

0 comments on commit 66e722a

Please sign in to comment.