Skip to content

Commit

Permalink
docs: add docs to storybook docs about textContrast
Browse files Browse the repository at this point in the history
  • Loading branch information
rshen91 committed May 29, 2020
1 parent 462debe commit 01b7052
Show file tree
Hide file tree
Showing 5 changed files with 188 additions and 17 deletions.
166 changes: 166 additions & 0 deletions docs/0-Intro/1-Overview.mdx
Original file line number Diff line number Diff line change
@@ -1,3 +1,17 @@
import { Chart, Datum, Partition, PartitionLayout, Settings } from '../../src';
import { mocks } from '../../src/mocks/hierarchical/index';
import { config } from '../../src/chart_types/partition_chart/layout/config/config';
import { ShapeTreeNode } from '../../src/chart_types/partition_chart/layout/types/viewmodel_types';
import {
categoricalFillColor,
colorBrewerCategoricalStark9,
countryLookup,
indexInterpolatedFillColor,
interpolatorCET2s,
interpolatorTurbo,
productLookup,
regionLookup,
} from '../../stories/utils/utils';
import { Meta, Story } from "@storybook/addon-docs/blocks";

<Meta title="Introduction/Elastic Charts Overview" />
Expand Down Expand Up @@ -255,3 +269,155 @@ type PointStyleAccessor = (
```

> Note: When overriding bar or point styles be mindful of performance and these accessor functions will be call on every bar/point is every series. Precomputing any expensive task before rendering.
### Background Colors and Text Contrast
You can provide the `backgroundColor` of the container that the chart will be placed onto. You can set the `textContrast` to a boolean value or a number. The default `textContrast` is set to 4.5 but you can always disable this or set your own numerical amount.

> Note: This functionality is currently available for Partition charts. Please see the partition background and partition label stories.
```js
config: {
fillLabel: {
textInvertible: true,
textContrast: true, // can also be set to a number
}
}
```
`textInvertible` will have to be set to true for `textContrast` to be set as well. To see an example of where this applies, please see the Partitions Background story within Stylings. Charts are included below but are static.
If you have `textInvertible` set to true, but do not have `textContrast` set to true, then the red slices, Europe, North America, and Asia, will have white text:

<Chart className="story-chart">
<Settings theme={{background : {color: `rgba(155, 155, 155, 1)`}}} />
<Partition
id="spec_1"
data={mocks.miniSunburst}
valueAccessor={(d) => d.exportVal}
valueFormatter={(d) => `$${config.fillLabel.valueFormatter(Math.round(d / 1000000000))}\xa0Bn`}
layers={[
{
groupByRollup: (d) => d.sitc1,
nodeLabel: (d) => productLookup[d].name,
shape: {
fillColor: (d) => {
return categoricalFillColor(colorBrewerCategoricalStark9, 0.7)(d.sortIndex);
},
},
},
{
groupByRollup: (d) => countryLookup[d.dest].continentCountry.substr(0, 2),
nodeLabel: (d) => regionLookup[d].regionName,
shape: {
fillColor: (d) => {
return categoricalFillColor(colorBrewerCategoricalStark9, 0.5)(d.parent.sortIndex);
},
},
},
{
groupByRollup: (d) => d.dest,
nodeLabel: (d) => countryLookup[d].name,
shape: {
fillColor: (d) => {
return categoricalFillColor(colorBrewerCategoricalStark9, 0.3)(d.parent.parent.sortIndex);
},
},
},
]}
config={{
partitionLayout: PartitionLayout.sunburst,
linkLabel: {
maxCount: 0,
fontSize: 14,
},
fontFamily: 'Arial',
fillLabel: {
valueFormatter: (d) => `$${config.fillLabel.valueFormatter(Math.round(d / 1000000000))}\xa0Bn`,
fontStyle: 'italic',
textInvertible: true,
textContrast: false,
fontWeight: 900,
valueFont: {
fontFamily: 'Menlo',
fontStyle: 'normal',
fontWeight: 100,
},
},
margin: { top: 0, bottom: 0, left: 0, right: 0 },
minFontSize: 1,
idealFontSizeJump: 1.1,
outerSizeRatio: 1,
emptySizeRatio: 0,
circlePadding: 4,
backgroundColor: 'rgba(229,229,229,1)',
}}
/>
</Chart>



Now if you set the `textContrast` to true as well, these slices also become black in text color:

<Chart className="story-chart">
<Settings theme={{background : {color: `rgba(155, 155, 155, 1)`}}} />
<Partition
id="spec_1"
data={mocks.miniSunburst}
valueAccessor={(d) => d.exportVal}
valueFormatter={(d) => `$${config.fillLabel.valueFormatter(Math.round(d / 1000000000))}\xa0Bn`}
layers={[
{
groupByRollup: (d) => d.sitc1,
nodeLabel: (d) => productLookup[d].name,
shape: {
fillColor: (d) => {
return categoricalFillColor(colorBrewerCategoricalStark9, 0.7)(d.sortIndex);
},
},
},
{
groupByRollup: (d) => countryLookup[d.dest].continentCountry.substr(0, 2),
nodeLabel: (d) => regionLookup[d].regionName,
shape: {
fillColor: (d) => {
return categoricalFillColor(colorBrewerCategoricalStark9, 0.5)(d.parent.sortIndex);
},
},
},
{
groupByRollup: (d) => d.dest,
nodeLabel: (d) => countryLookup[d].name,
shape: {
fillColor: (d) => {
return categoricalFillColor(colorBrewerCategoricalStark9, 0.3)(d.parent.parent.sortIndex);
},
},
},
]}
config={{
partitionLayout: PartitionLayout.sunburst,
linkLabel: {
maxCount: 0,
fontSize: 14,
},
fontFamily: 'Arial',
fillLabel: {
valueFormatter: (d) => `$${config.fillLabel.valueFormatter(Math.round(d / 1000000000))}\xa0Bn`,
fontStyle: 'italic',
textInvertible: true,
textContrast: true,
fontWeight: 900,
valueFont: {
fontFamily: 'Menlo',
fontStyle: 'normal',
fontWeight: 100,
},
},
margin: { top: 0, bottom: 0, left: 0, right: 0 },
minFontSize: 1,
idealFontSizeJump: 1.1,
outerSizeRatio: 1,
emptySizeRatio: 0,
circlePadding: 4,
backgroundColor: 'rgba(229,229,229,1)',
}}
/>
</Chart>
24 changes: 12 additions & 12 deletions src/chart_types/partition_chart/layout/utils/calcs.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,40 +23,40 @@ describe('calcs', () => {
it('hex input - should change white text to black when background is white', () => {
const expected = '#000';
const result = makeHighContrastColor('#fff', '#fff');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
it('rgb input - should change white text to black when background is white ', () => {
const expected = '#000';
const result = makeHighContrastColor('rgb(255, 255, 255)', 'rgb(255, 255, 255)');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
it('rgba input - should change white text to black when background is white ', () => {
const expected = '#000';
const result = makeHighContrastColor('rgba(255, 255, 255, 1)', 'rgba(255, 255, 255, 1)');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
it('word input - should change white text to black when background is white ', () => {
const expected = '#000';
const result = makeHighContrastColor('white', 'white');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
// test contrast computation
it('should provide at least 4.5 contrast', () => {
const foreground = '#fff'; // white
const background = 'rgba(255, 255, 51, 0.3)'; // light yellow
const result = '#000'; // black
expect(result).toEqual(makeHighContrastColor(foreground, background));
expect(result).toBe(makeHighContrastColor(foreground, background));
});
it('should use black text for hex value', () => {
const foreground = '#fff'; // white
const background = '#7874B2'; // Thailand color
const result = '#000'; // black
expect(result).toEqual(makeHighContrastColor(foreground, background));
expect(result).toBe(makeHighContrastColor(foreground, background));
});
it('should switch to black text if background color is in rgba() format', () => {
it('should switch to black text if background color is in rgba() format - Thailand', () => {
const containerBackground = 'white';
const background = 'rgba(120, 116, 178, 0.7)';
const resultForCombined = 'rgba(161, 158, 201, 1)';
const resultForCombined = 'rgba(161, 158, 201, 1)'; // 0.3 'rgba(215, 213, 232, 1)'; // 0.5 - 'rgba(188, 186, 217, 1)'; //0.7 - ;
expect(combineColors(background, containerBackground)).toBe(resultForCombined);
const foreground = 'white';
const resultForContrastedText = '#000'; //switches to black text
Expand All @@ -67,22 +67,22 @@ describe('calcs', () => {
it('should return correct RGBA with opacity greater than 0.7', () => {
const expected = 'rgba(102, 43, 206, 1)';
const result = combineColors('rgba(121, 47, 249, 0.8)', '#1c1c24');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
it('should return correct RGBA with opacity less than 0.7', () => {
const expected = 'rgba(226, 186, 187, 1)';
const result = combineColors('rgba(228, 26, 28, 0.3)', 'rgba(225, 255, 255, 1)');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
it('should return correct RGBA with the input color as a word vs rgba or hex value', () => {
const expected = 'rgba(0, 0, 255, 1)';
const result = combineColors('blue', 'black');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
it('should return the correct RGBA with hex input', () => {
const expected = 'rgba(212, 242, 210, 1)';
const result = combineColors('#D4F2D2', '#BEB7DF');
expect(result).toEqual(expected);
expect(result).toBe(expected);
});
});
});
Expand Down
8 changes: 7 additions & 1 deletion src/chart_types/partition_chart/layout/utils/calcs.ts
Original file line number Diff line number Diff line change
Expand Up @@ -141,12 +141,18 @@ export function getTextColorIfTextInvertible(
? `rgb(${255 - tr}, ${255 - tg}, ${255 - tb})`
: `rgba(${255 - tr}, ${255 - tg}, ${255 - tb}, ${to})`
: textColor;
} else if (textContrast === true) {
} else if (textContrast === true && typeof textContrast !== 'number') {
return inverseForContrast
? to === undefined
? makeHighContrastColor(`rgb(${255 - tr}, ${255 - tg}, ${255 - tb})`, backgroundColor)
: makeHighContrastColor(`rgba(${255 - tr}, ${255 - tg}, ${255 - tb}, ${to})`, backgroundColor)
: makeHighContrastColor(textColor, backgroundColor);
} else if (typeof textContrast === 'number') {
return inverseForContrast
? to === undefined
? makeHighContrastColor(`rgb(${255 - tr}, ${255 - tg}, ${255 - tb})`, backgroundColor, textContrast)
: makeHighContrastColor(`rgba(${255 - tr}, ${255 - tg}, ${255 - tb}, ${to})`, backgroundColor, textContrast)
: makeHighContrastColor(textColor, backgroundColor, textContrast);
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -118,8 +118,6 @@ export function linkTextLayout(
const labelText = cutToLength(rawText, maxTextLength);
const valueText = valueFormatter(valueGetter(node));

// const { width, emHeightAscent, emHeightDescent } = measure(linkLabel.fontSize, [{ ...labelFontSpec, text }])[0];
// const { width: valueWidth } = measure(linkLabel.fontSize, [{ ...valueFontSpec, text: valueText }])[0];
const labelFontSpec: Font = {
fontStyle: 'normal',
fontVariant: 'normal',
Expand Down Expand Up @@ -172,7 +170,7 @@ export function linkTextLayout(
valueFontSpec,
};
})
.filter((l: LinkLabelVM) => l.text !== ''); // cull linked labels whose text was truncated to nothing;
.filter(({ text }) => text !== ''); // cull linked labels whose text was truncated to nothing;
return { linkLabels, valueFontSpec, labelFontSpec, strokeColor };

function fitText(measure: TextMeasure, desiredText: string, allottedWidth: number, fontSize: number, box: Box) {
Expand Down
3 changes: 2 additions & 1 deletion stories/stylings/20_partition_background.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ export const Example = () => {
},
};
const invertTextColors = boolean('invert colors for lightness/darkness', true);
const toggleTextContrast = boolean('set text contrast to true or false', true);
return (
<Chart className="story-chart">
<Settings theme={partialColorTheme} />
Expand Down Expand Up @@ -85,7 +86,7 @@ export const Example = () => {
valueFormatter: (d: number) => `$${config.fillLabel.valueFormatter(Math.round(d / 1000000000))}\xa0Bn`,
fontStyle: 'italic',
textInvertible: invertTextColors,
textContrast: false,
textContrast: toggleTextContrast,
fontWeight: 900,
valueFont: {
fontFamily: 'Menlo',
Expand Down

0 comments on commit 01b7052

Please sign in to comment.