Skip to content
This repository was archived by the owner on Jun 4, 2024. It is now read-only.

Issue 342 - Add column type support for conditionals #343

Merged
merged 3 commits into from
Feb 11, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,19 @@
All notable changes to this project will be documented in this file.
This project adheres to [Semantic Versioning](http://semver.org/).

## [Unreleased]
### Added
[#342](https://github.com/plotly/dash-core/issues/342)
- Added `column_type` condition to style `if`; allows applying styles based on the type of the column for props
- `style_cell_conditional`
- `style_data_conditional`
- `style_filter_conditional`
- `style_header_conditional`

### Fixed
[#342](https://github.com/plotly/dash-core/issues/342)
- Added already supported `filter` nested prop / condition to `style_data_conditional` props definition

## [3.4.0] - 2019-02-08
### Added
[#364](https://github.com/plotly/dash-table/pull/364)
Expand Down
6 changes: 3 additions & 3 deletions dash_table/bundle.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion dash_table/bundle.js.map

Large diffs are not rendered by default.

6 changes: 3 additions & 3 deletions dash_table/demo.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion dash_table/demo.js.map

Large diffs are not rendered by default.

76 changes: 76 additions & 0 deletions dash_table/metadata.json
Original file line number Diff line number Diff line change
Expand Up @@ -1048,6 +1048,24 @@
}
],
"required": false
},
"column_type": {
"name": "enum",
"value": [
{
"value": "'any'",
"computed": false
},
{
"value": "'numeric'",
"computed": false
},
{
"value": "'text'",
"computed": false
}
],
"required": false
}
},
"required": false
Expand Down Expand Up @@ -1083,6 +1101,28 @@
],
"required": false
},
"column_type": {
"name": "enum",
"value": [
{
"value": "'any'",
"computed": false
},
{
"value": "'numeric'",
"computed": false
},
{
"value": "'text'",
"computed": false
}
],
"required": false
},
"filter": {
"name": "string",
"required": false
},
"row_index": {
"name": "union",
"value": [
Expand Down Expand Up @@ -1138,6 +1178,24 @@
}
],
"required": false
},
"column_type": {
"name": "enum",
"value": [
{
"value": "'any'",
"computed": false
},
{
"value": "'numeric'",
"computed": false
},
{
"value": "'text'",
"computed": false
}
],
"required": false
}
},
"required": false
Expand Down Expand Up @@ -1169,6 +1227,24 @@
],
"required": false
},
"column_type": {
"name": "enum",
"value": [
{
"value": "'any'",
"computed": false
},
{
"value": "'numeric'",
"computed": false
},
{
"value": "'text'",
"computed": false
}
],
"required": false
},
"header_index": {
"name": "union",
"value": [
Expand Down
9 changes: 7 additions & 2 deletions src/dash-table/DataTable.js
Original file line number Diff line number Diff line change
Expand Up @@ -861,7 +861,8 @@ export const propTypes = {
style_cell_conditional: PropTypes.arrayOf(PropTypes.shape({
// .exact
if: PropTypes.shape({
column_id: PropTypes.oneOfType([PropTypes.string, PropTypes.number])
column_id: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
column_type: PropTypes.oneOf(['any', 'numeric', 'text'])
})
})),

Expand All @@ -874,6 +875,8 @@ export const propTypes = {
// .exact
if: PropTypes.shape({
column_id: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
column_type: PropTypes.oneOf(['any', 'numeric', 'text']),
filter: PropTypes.string,
row_index: PropTypes.oneOfType([
PropTypes.number,
PropTypes.oneOf(['odd', 'even'])
Expand All @@ -889,7 +892,8 @@ export const propTypes = {
style_filter_conditional: PropTypes.arrayOf(PropTypes.shape({
// .exact
if: PropTypes.shape({
column_id: PropTypes.oneOfType([PropTypes.string, PropTypes.number])
column_id: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
column_type: PropTypes.oneOf(['any', 'numeric', 'text'])
})
})),

Expand All @@ -902,6 +906,7 @@ export const propTypes = {
// .exact
if: PropTypes.shape({
column_id: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
column_type: PropTypes.oneOf(['any', 'numeric', 'text']),
header_index: PropTypes.oneOfType([
PropTypes.number,
PropTypes.oneOf(['odd', 'even'])
Expand Down
20 changes: 15 additions & 5 deletions src/dash-table/conditional/index.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { ColumnId, Datum } from 'dash-table/components/Table/props';
import { ColumnId, Datum, ColumnType } from 'dash-table/components/Table/props';
import SyntaxTree from 'core/syntax-tree';

export interface IConditionalElement {
Expand All @@ -17,10 +17,14 @@ export interface INamedElement {
column_id?: ColumnId;
}

export type ConditionalBasicFilter = INamedElement;
export type ConditionalDataCell = IConditionalElement & IIndexedRowElement & INamedElement;
export type ConditionalCell = INamedElement;
export type ConditionalHeader = IIndexedHeaderElement & INamedElement;
export interface ITypedElement {
column_type?: ColumnType;
}

export type ConditionalBasicFilter = INamedElement & ITypedElement;
export type ConditionalDataCell = IConditionalElement & IIndexedRowElement & INamedElement & ITypedElement;
export type ConditionalCell = INamedElement & ITypedElement;
export type ConditionalHeader = IIndexedHeaderElement & INamedElement & ITypedElement;

function ifAstFilter(ast: SyntaxTree, datum: Datum) {
return ast.isValid && ast.evaluate(datum);
Expand All @@ -32,6 +36,12 @@ export function ifColumnId(condition: INamedElement | undefined, columnId: Colum
condition.column_id === columnId;
}

export function ifColumnType(condition: ITypedElement | undefined, columnType?: ColumnType) {
return !condition ||
condition.column_type === undefined ||
condition.column_type === (columnType || ColumnType.Any);
}

export function ifRowIndex(condition: IIndexedRowElement | undefined, rowIndex: number) {
if (!condition ||
condition.row_index === undefined) {
Expand Down
12 changes: 9 additions & 3 deletions src/dash-table/derived/style/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,9 @@ import {
IIndexedHeaderElement,
IIndexedRowElement,
INamedElement,
ifColumnId
ITypedElement,
ifColumnId,
ifColumnType
} from 'dash-table/conditional';

export interface IConvertedStyle {
Expand All @@ -31,15 +33,19 @@ export interface IConvertedStyle {
matchesFilter: (datum: Datum) => boolean;
}

type GenericIf = Partial<IConditionalElement & IIndexedHeaderElement & IIndexedRowElement & INamedElement>;
type GenericIf = Partial<IConditionalElement & IIndexedHeaderElement & IIndexedRowElement & INamedElement & ITypedElement>;
type GenericStyle = Style & Partial<{ if: GenericIf }>;

function convertElement(style: GenericStyle) {
const indexFilter = style.if && (style.if.header_index || style.if.row_index);
let ast: SyntaxTree;

return {
matchesColumn: (column: IVisibleColumn) => ifColumnId(style.if, column.id),
matchesColumn: (column: IVisibleColumn) =>
!style.if || (
ifColumnId(style.if, column.id) &&
ifColumnType(style.if, column.type)
),
matchesRow: (index: number) =>
indexFilter === undefined ?
true :
Expand Down
40 changes: 40 additions & 0 deletions tests/visual/percy-storybook/Style.percy.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import React from 'react';
import { storiesOf } from '@storybook/react';
import DataTable from 'dash-table/DataTable';
import fixtures from './fixtures';
import { ColumnType } from 'dash-table/components/Table/props';

const setProps = () => { };

// Legacy: Tests previously run in Python
const fixtureStories = storiesOf('DashTable/Fixtures', module);
fixtures.forEach(fixture => fixtureStories.add(fixture.name, () => (<DataTable {...Object.assign(fixture.props)} />)));

storiesOf('DashTable/Style type condition', module)
.add('with 1 column', () => (<DataTable
setProps={setProps}
id='table'
data={[
{ a: 1, b: 2, c: '3', d: '4', e: 5, f: 6, g: 7, h: 8 },
{ a: 11, b: 22, c: '33', d: '44', e: 55, f: 66, g: 77, h: 88 },
{ a: 111, b: 222, c: '333', d: '444', e: 555, f: 666, g: 777, h: 888 }
]}
columns={[
{ id: 'a', name: 'A', type: ColumnType.Any },
{ id: 'b', name: 'B', type: ColumnType.Any },
{ id: 'c', name: 'C', type: ColumnType.Text },
{ id: 'd', name: 'D', type: ColumnType.Text },
{ id: 'e', name: 'E', type: ColumnType.Numeric },
{ id: 'f', name: 'F', type: ColumnType.Numeric },
{ id: 'g', name: 'G' },
{ id: 'h', name: 'H' }
]}
style_data_conditional={[
{ if: { column_type: ColumnType.Any, row_index: 'even' }, background_color: 'blue', color: 'white' },
{ if: { column_type: ColumnType.Text, row_index: 'even' }, background_color: 'red', color: 'white' },
{ if: { column_type: ColumnType.Numeric, row_index: 'even' }, background_color: 'green', color: 'white' },
{ if: { column_type: ColumnType.Any }, background_color: 'blue' },
{ if: { column_type: ColumnType.Text }, background_color: 'red' },
{ if: { column_type: ColumnType.Numeric }, background_color: 'green' }
]}
/>));