@flourish/chart-layout
Advanced tools
Comparing version 1.0.0-prerelease.8 to 1.0.0
{ | ||
"name": "@flourish/chart-layout", | ||
"version": "1.0.0-prerelease.8", | ||
"version": "1.0.0", | ||
"description": "Create axes", | ||
@@ -18,8 +18,8 @@ "main": "chart-layout.js", | ||
"@flourish/eslint-plugin-flourish": "^0.7.2", | ||
"eslint": "^5.16.0", | ||
"husky": "^2.2.0", | ||
"lint-staged": "^8.1.6", | ||
"rollup": "^1.10.1", | ||
"rollup-plugin-node-resolve": "^4.2.3", | ||
"uglify-js": "^3.5.7" | ||
"eslint": "^6.5.1", | ||
"husky": "^3.0.9", | ||
"lint-staged": "^9.4.2", | ||
"rollup": "^1.25.2", | ||
"rollup-plugin-node-resolve": "^5.2.0", | ||
"uglify-js": "^3.6.4" | ||
}, | ||
@@ -34,3 +34,3 @@ "repository": { | ||
"dependencies": { | ||
"@flourish/enhanced-arrays": "1.0.0-prerelease.2", | ||
"@flourish/enhanced-arrays": "1.0.0", | ||
"@flourish/pocket-knife": "^0.3.1", | ||
@@ -37,0 +37,0 @@ "d3-scale": "2.1.2", |
@@ -19,4 +19,12 @@ # Flourish chart layout | ||
Import `@flourish/chart-layout` into your `template.yml` settings. | ||
Import the `@flourish/chart-layout` setting into your `template.yml`, e.g.: | ||
```yml | ||
- X axis | ||
- property: x | ||
import: "@flourish/chart-layout/x" | ||
- Y axis | ||
- property: y | ||
import: "@flourish/chart-layout/y" | ||
``` | ||
@@ -28,3 +36,3 @@ ## How to use | ||
``` js | ||
import createChartLayout from "@flourish/layout"; | ||
import createChartLayout from "@flourish/chart-layout"; | ||
var container = select(layout.getSection("primary")).select("svg"); // see @flourish/layout | ||
@@ -67,7 +75,7 @@ var props = { x: state.x, y: state.y }; | ||
### `chart_layout.xData([[values], accessor])` | ||
### `chart_layout.xData([values, [accessor]])` | ||
Gets or sets the data associated with the horizontal axis. | ||
### `chart_layout.yData([[values], accessor])` | ||
### `chart_layout.yData([values, [accessor]])` | ||
@@ -88,2 +96,20 @@ Gets or sets the data associated with the vertical axis. | ||
## Width and height methods of `chart_layout` | ||
### `chart_layout.height([value])` | ||
If `value` is specified, sets the _total_ height of the `chart_layout` area and returns the `chart_layout` instance. If `value` is any falsy value other than `undefined`, the height of the bounding rectangle of `chart_layout.container` is used. If `value` is `undefined` returns the calculated _total_ height of the `chart_layout` area. | ||
### `chart_layout.plotHeight()` | ||
Returns the calculated _plot_ height of the `chart_layout` area. | ||
### `chart_layout.plotWidth()` | ||
Returns the calculated _plot_ width of the `chart_layout` area. | ||
### `chart_layout.width([value])` | ||
If `value` is specified, sets the _total_ width of the `chart_layout` area and returns the `chart_layout` instance. If `value` is any falsy value other than `undefined`, the width of the bounding rectangle of `chart_layout.container` is used. If `value` is `undefined` returns the calculated _total_ width of the `chart_layout` area. | ||
## Other methods of `chart_layout` | ||
@@ -101,6 +127,2 @@ | ||
### `chart_layout.height([value])` | ||
If `value` is specified, sets the total height of the `chart_layout` area. If `value` is any falsy value other than `undefined`, the height of the bounding rectangle of `chart_layout.container` is used. | ||
### `chart_layout.identifier([value])` | ||
@@ -110,6 +132,5 @@ | ||
### `chart_layout.width([value])` | ||
### `chart_layout.xForceZero([value])` | ||
If `value` is specified and is truthy then the x axis will include 0 if the data is numeric and the x-axis linear, regardless of the `xData` values. User-set `min` and `max` settings can overcome this restriction. | ||
If `value` is specified, sets the total width of the `chart_layout` area. If `value` is any falsy value other than `undefined`, the width of the bounding rectangle of `chart_layout.container` is used. | ||
### `chart_layout.xFormat([func])` | ||
@@ -122,2 +143,5 @@ If `func` is specified, sets the formatting function to be applied to the tick formats on the x axis. The `func` function is called for every tick on the x axis on `update` with the ticks own value as the only argument. The value returned is then used as the printed tick label. If `chart_layout.xFormat` is never called with a `func` or `func` is falsy (but not undefined) the default formatting function, `function(value) { return "" + value; }`, is used. | ||
### `chart_layout.yForceZero([value])` | ||
If `value` is specified and is truthy then the y axis will include 0 if the data is numeric and the y-axis linear, regardless of the `yData` values. User-set `min` and `max` settings can overcome this restriction. | ||
### `chart_layout.yFormat([func])` | ||
@@ -124,0 +148,0 @@ If `func` is specified, sets the formatting function to be applied to the tick formats on the y axis. The `func` function is called for every tick on the y axis on `update` with the ticks own value as the only argument. The value returned is then used as the printed tick label. If `chart_layout.yFormat` is never called with a `func` or `func` is falsy (but not undefined) the default formatting function, `function(value) { return "" + value; }`, is used. |
@@ -11,3 +11,3 @@ import { prepareState } from "./state"; | ||
import { initXTicks, initYTicks } from "./ticks"; | ||
import { initXScale, initYScale } from "./scales"; | ||
import { initPlotWidth, initPlotHeight, initXScale, initYScale, initZeroAxis } from "./scales"; | ||
import { initUpdate } from "./update"; | ||
@@ -38,4 +38,8 @@ | ||
instance._yTicks = initYTicks(instance, state); | ||
instance.plotWidth = initPlotWidth(instance, state); | ||
instance.plotHeight = initPlotHeight(instance, state); | ||
instance.xScale = initXScale(instance, state); | ||
instance.yScale = initYScale(instance, state); | ||
instance.xZeroAxis = initZeroAxis(instance); | ||
instance.yZeroAxis = initZeroAxis(instance); | ||
instance.update = initUpdate(instance, state); | ||
@@ -42,0 +46,0 @@ |
@@ -10,10 +10,42 @@ import { scaleLinear, scaleLog, scalePoint } from "d3-scale"; | ||
function getLinearScale(data, min, max) { | ||
var scale = scaleLinear().domain(data.extent()).nice(); | ||
function getLinearDomain(data, min, max, include_zero) { | ||
var FALLBACK_DOMAIN_RANGE = 100; // If we can't construct a sensible default domain, make an arbitrary one this wide | ||
if (min === max) min = max = null; // If min and max are equal then ignore them both | ||
// If we have min and max then it's easy | ||
if (min !== null && max !== null) return [min, max]; | ||
var domain; | ||
if (data.range) { // Standard case: multiple different values | ||
domain = scaleLinear().domain(data.extent()).nice().domain(); | ||
if (include_zero) domain[0] >= 0 ? domain[0] = 0 : domain[1] = 0; | ||
} | ||
else if (data.length) { // Only one unique value | ||
var value = data.min; | ||
if (value > 0) domain = [0, 2 * value]; // Place value in middle of domain starting at 0 | ||
else if (value < 0) domain = [2 * value, 0]; // Place value in middle of domain ending at 0 | ||
else domain = [-FALLBACK_DOMAIN_RANGE/2, FALLBACK_DOMAIN_RANGE/2]; // Domain centred on 0 with arbitrary min and max | ||
} | ||
else domain = [0, FALLBACK_DOMAIN_RANGE]; // No values at all: pick arbitrary domain values | ||
if (min !== null) { | ||
domain[0] = min; | ||
// If domain values now match we need to do something, so change the non-specified max value | ||
if (domain[0] === domain[1]) domain[1] = min + (data.range || FALLBACK_DOMAIN_RANGE); | ||
} | ||
else if (max !== null) { | ||
domain[1] = max; | ||
// If domain values now match we need to do something, so change the non-specified min value | ||
if (domain[0] === domain[1]) domain[0] = max - (data.range || FALLBACK_DOMAIN_RANGE); | ||
} | ||
return domain; | ||
} | ||
function getLinearScale(data, min, max, include_zero) { | ||
var domain = getLinearDomain(data, min, max, include_zero); | ||
var scale = scaleLinear().domain(domain); | ||
scale.type = "numeric"; | ||
if (min === max) return scale; | ||
var domain = scale.domain(); | ||
if (min !== null) domain[0] = min; | ||
if (max !== null) domain[1] = max; | ||
return scale.domain(domain); | ||
return scale; | ||
} | ||
@@ -141,2 +173,25 @@ | ||
function initPlotWidth(instance, state) { | ||
return function() { | ||
return instance.width() - (getLeftMargin(instance, state) + getRightMargin(instance)); | ||
}; | ||
} | ||
function initPlotHeight(instance, state) { | ||
return function() { | ||
return instance.height() - (getTopMargin(instance, state) + getBottomMargin(instance, state)); | ||
}; | ||
} | ||
function initZeroAxis(instance) { | ||
var zero_axis = false; | ||
return function(value) { | ||
if (value === undefined) return zero_axis; | ||
zero_axis = !!value; | ||
return instance; | ||
}; | ||
} | ||
function initXScale(instance, state) { | ||
@@ -151,7 +206,7 @@ return function(form) { | ||
else { | ||
xScale = getLinearScale(x_data, state.x.linear_min, state.x.linear_max); | ||
xScale = getLinearScale(x_data, state.x.linear_min, state.x.linear_max, instance.xZeroAxis()); | ||
} | ||
if (form === "domain_only") return xScale; | ||
var x_width = instance.plotWidth(); | ||
var left_margin = getLeftMargin(instance, state); | ||
var x_width = instance.width() - (left_margin + getRightMargin(instance)); | ||
var range = [ left_margin, left_margin + x_width ]; | ||
@@ -174,7 +229,7 @@ var offset = form === "global" && instance.xOffset(); | ||
else { | ||
yScale = getLinearScale(y_data, state.y.linear_min, state.y.linear_max); | ||
yScale = getLinearScale(y_data, state.y.linear_min, state.y.linear_max, instance.yZeroAxis()); | ||
} | ||
if (form === "domain_only") return yScale; | ||
var y_height = instance.plotHeight(); | ||
var top_margin = getTopMargin(instance, state); | ||
var y_height = instance.height() - (top_margin + getBottomMargin(instance, state)); | ||
var range = [ top_margin, top_margin + y_height ]; | ||
@@ -188,2 +243,2 @@ var offset = form === "global" && instance.yOffset(); | ||
export { initXScale, initYScale }; | ||
export { initPlotWidth, initPlotHeight, initXScale, initYScale, initZeroAxis }; |
@@ -13,2 +13,12 @@ function tickSorter(a, b) { | ||
export { tickSorter }; | ||
function userSelectNone(selection) { | ||
selection | ||
.style("user-select", "none") | ||
.style("-moz-user-select", "none") | ||
.style("-webkit-user-select", "none") | ||
.style("-ms-user-select", "none") | ||
.style("cursor", "default"); | ||
} | ||
export { tickSorter, userSelectNone }; |
import { select } from "d3-selection"; | ||
import { remToPx, xyToTranslate, angleToRotate, linesIntersect } from "../../utils"; | ||
import { tickSorter } from "./utils"; | ||
import { tickSorter, userSelectNone } from "./utils"; | ||
@@ -142,3 +142,4 @@ | ||
sel.append("text").attr("text-anchor", "middle") | ||
.attr("transform", tickLabelTransform); | ||
.attr("transform", tickLabelTransform) | ||
.call(userSelectNone); | ||
}); | ||
@@ -208,2 +209,3 @@ | ||
.style("font-weight", x.title_weight) | ||
.call(userSelectNone) | ||
.transition() | ||
@@ -338,3 +340,4 @@ .duration(0) | ||
sel.append("text").attr("text-anchor", "middle") | ||
.attr("transform", tickLabelTransform); | ||
.attr("transform", tickLabelTransform) | ||
.call(userSelectNone); | ||
}); | ||
@@ -404,2 +407,3 @@ | ||
.style("font-weight", x.title_weight) | ||
.call(userSelectNone) | ||
.transition() | ||
@@ -406,0 +410,0 @@ .duration(0) |
import { select } from "d3-selection"; | ||
import { remToPx, xyToTranslate, angleToRotate, linesIntersect } from "../../utils"; | ||
import { tickSorter } from "./utils"; | ||
import { tickSorter, userSelectNone } from "./utils"; | ||
@@ -134,3 +134,4 @@ | ||
sel.append("text").attr("text-anchor", "right") | ||
.attr("transform", tickLabelTransform); | ||
.attr("transform", tickLabelTransform) | ||
.call(userSelectNone); | ||
}); | ||
@@ -204,2 +205,3 @@ | ||
.style("font-weight", y.title_weight) | ||
.call(userSelectNone) | ||
.transition() | ||
@@ -206,0 +208,0 @@ .duration(0) |
Sorry, the diff of this file is too big to display
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
268139
7275
1
146
+ Added@flourish/enhanced-arrays@1.0.0(transitive)
- Removed@flourish/enhanced-arrays@1.0.0-prerelease.2(transitive)